Cannot read property 'replace' of undefined in angularJS? - angularjs

I am using emoji filter, I am getting error that "Cannot read property 'replace' of undefined".
Errro is:
TypeError: Cannot read property 'replace' of undefined
at g.<anonymous> (file:///C:/xampp/htdocs/web_UI/js/emoji.min.js:1:10531)
at e (file:///C:/xampp/htdocs/web_UI/js/angular.min.js:155:305)
at Ia.| (file:///C:/xampp/htdocs/web_UI/js/angular.min.js:143:248)
at Object.A.constant [as get] (file:///C:/xampp/htdocs/web_UI/js/angular.min.js:154:212)
at g.$digest (file:///C:/xampp/htdocs/web_UI/js/angular.min.js:98:307)
at g.$apply (file:///C:/xampp/htdocs/web_UI/js/angular.min.js:101:157)
at HTMLAnchorElement.<anonymous> (file:///C:/xampp/htdocs/web_UI/js/angular.min.js:177:65)
at HTMLAnchorElement.m.event.dispatch (file:///C:/xampp/htdocs/web_UI/js/jquery.min.js:3:8436)
at HTMLAnchorElement.r.handle (file:///C:/xampp/htdocs/web_UI/js/jquery.min.js:3:5146)
Html code:
<div class="row" ng-repeat="n in q.answers" ng-bind-html = " n | emoji">
json response:
{
"data":[
{
"id":10,
"title":"what is internet?",
"userID":2,
"question":"what is internet?",
"viewed":0,
"votes":5,
"answers":[
{"id":15,
"questionID":10,
"userID":2,
"answer":"search on google ....:)",
"correct":"0",
"votes":7
},
{
"id":47,
"questionID":10,
"userID":2,
"answer":"test :smiley:",
"correct":"0","votes":0,
}
]}
]
}
js function:
QAApp.controller('askbyctrl', function ($scope, $http){
$http.get(server + 'api').success(function(data) {
/*console.log(data);*/
$scope.qa = data;
});
$scope.select = function(item) {
/*console.log(item);*/
$scope.selected = item
}
$scope.isSelected = function(item) {
return $scope.selected == item
}
});
then in html for answer use ng-repeat="q in qa.data" and to display answer use n in q.answers"
Please tell me how can I solve it?
Plunker link

This is the working code...
angular.module("app", ['emoji', 'ngSanitize']).controller("AppCtrl", function ($scope) {
$scope.messages = [
"Animals: :dog: :cat: :snake:",
"People: :smile: :confused: :angry:",
"Places: :house: :school: :hotel:"
];
});
<body ng-app="app" ng-controller="AppCtrl">
<ul>
<li ng-repeat="message in messages" ng-bind-html="message | emoji"></li>
</ul>
</body>

You need to apply the emoji filter to a string, however your n in q.answers is looping through a list of objects (not strings). You need to change your HTML to this:
<div class="row" ng-repeat="n in q.answers" ng-bind-html = "n.answer | emoji">
Check this plunker.

Related

(newbie) Get data from array of objects using ng-repeat and for loop

I have to access some objects inside an array:
.success(function(data) {
$scope.activities = data.result[0].attributes
});
And I can access this particular index, as expected, inside my view with
<div ng-repeat="x in activities">
<p>{{x.name}}: {{x.value}}</p>
</div>
Now obviously, this only returns the first object in the array, at index 0. (Right?). So I figure I have to somehow loop the function..
.success(function(data) {
for(var i = 0; i < data.result.length; i++) {
$scope.activities = data.result[i].attributes;
}
});
As far as I can tell, the actual for loop is working.. but I need help in the next step exposing this to my view.
Here is my plunker: https://plnkr.co/edit/2ZukY3Oq8vYvghfCruHx?p=preview
(although the data is not available, I have added what the response looks like in the comments)
Well, since the JSON data you pasted in plnkr is invalid, I don't know what attributes means, if it's just an object or it's an array of objects, anyway I made it as a single object.
EDIT
Since now I know attributes is an Array of objects, you can achieve what you want using special repeats.
Here's a snippet working:
(function() {
"use strict";
angular.module('app', [])
.controller('mainCtrl', function($scope) {
$scope.getLeadActivities = function() {
var url = 'xxxxxxxx.mktorest.com';
var endpoint = '/rest/v1/activities.json';
var activityTypeIds = '46';
var access_token = $scope.access_token;
var leadIds = $scope.leadId;
var nextPageToken = $scope.pagingToken;
// This is your data from API
var data = {
"requestId":"14213#155c8de2578",
"success":true,
"nextPageToken":"EOXAPD2V5UOJ5B3S5GGP7NUCX6UI6BFXCWHPJXF245PN2QTGMF3Q====",
"moreResult":false,
"result":[
{
"id":75843491,
"leadId":5334578,
"activityDate":"2016-07-06T06:45:11Z",
"activityTypeId":46,
"primaryAttributeValue":"Web",
"attributes":[
{
"name":"myDataName",
"value":"myDataValue"
}
]
},
{
"id":75843491,
"leadId":5334578,
"activityDate":"2016-07-06T06:45:11Z",
"activityTypeId":46,
"primaryAttributeValue":"Web",
"attributes":[
{
"name":"myDataName2",
"value":"myDataValue2"
}
]
},
{
"id":75843491,
"leadId":5334578,
"activityDate":"2016-07-06T06:45:11Z",
"activityTypeId":46,
"primaryAttributeValue":"Web",
"attributes":[
{
"name":"myDataName3",
"value":"myDataValue3"
}
]
}
]
};
// You'll put it inside the THEN method of your $http.get
$scope.activities = data.result;
}
});
})();
<!DOCTYPE html>
<html ng-app="app">
<head>
<script src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.5.7/angular.min.js"></script>
</head>
<body ng-controller="mainCtrl">
<button ng-click="getLeadActivities()">Get Lead Activities</button>
<div ng-repeat-start="activity in activities"></div>
<ul ng-repeat-end ng-repeat="attr in activity.attributes">
<li ng-bind="attr.name + ': ' + attr.value"></li>
</ul>
</body>
</html>
As per my understanding of your issue, you can solve it by using two ng-repeat clauses.
Your controller code,
.success(function(data) {
$scope.ativitiesArray = data.result;
});
Your html code,
<div ng-repeat="activities in activitiesArray track by $index">
<div ng-repeat="x in activities.attributes track by $index">
<p>{{x.name}}: {{x.value}}</p>
</div>
</div>
I've added track by $index phrase to ng-repeat as it will increase performance. Also, as per suggestions in the comments, please avoid using .success(). It is recommended to use .then().
Hope this solves the issue.

Define custom angularjs filter not using module model

I have read about the module way of defining a filter:
myApp.filter('filtername', function() {
return function() {
};
});
But what if I am using a simple function controller for my angular app and not as a module?
I.e. all I have at the top of my html is:
<html ng-app ng-controller="MyApp">
and then I include a js file with a simple controller:
function MyApp($scope, $http){
}
but I need to define a custom filter - in my particular case I'm trying to order an ngRepeat using Justin Klemm's object ordering filter. So how can I define a filter not using the module style syntax?
If you want create a new filter in your app you could define the your custom filter like below:
in your js
angular.module("yourModule")
.filter("yourFilretName",function(){
return function(value,arg1,arg2 .....){
var result = [];
// filter processing the object that pass the filtering, must be push on the result array
return result;
}
})
in your template
<your-tag ng-repeat="book in bookList | yourFilretName :arg1:agr2:....:argn>
.....
</your-tag>
<div ng-app="myApp" ng-controller="myCtrl">
<ul>
<li ng-repeat="item in items | filter: myFilter">{{ item }}</li>
</ul>
...
var myApp= angular.module("myApp", []);
myApp.controller('myCtrl', function($scope ) {
function myFilter(item) {
return item == "some condition"
}
})

Using ng-repeat in order to iterate over object properties and ordering by value instead of key with ng 1.3

I am in reference to the angular documentation about ngRepeat and iterating over object properties which states:
<div ng-repeat="(key, value) in myObj"> ... </div>
You need to be aware that the JavaScript specification does not define
the order of keys returned for an object. (To mitigate this in Angular
1.3 the ngRepeat directive used to sort the keys alphabetically.)
Say I have the following object:
var myObj = {FOO: 0, BAR: 1};
and want it to be ordered by value (i.e. 0 & 1) instead of keys. How can this be achieved with angular? (I use angular 1.3 by the way).
I have tried:
ng-repeat="(key, value) in myObj | orderBy:value"
But it does not work...
Can anyone please help?
Just as with filter, orderBy works with arrays only. One simple solution is to use a function that returns an array from an object:
<!DOCTYPE html>
<html>
<script src="http://ajax.googleapis.com/ajax/libs/angularjs/1.4.8/angular.min.js"></script>
<body>
<div ng-app="myApp" ng-controller="namesCtrl">
<input type="text" ng-model="searchText"/>
<ul ng-init="nameArray=objArray(names)">
<li ng-repeat="x in nameArray | filter:searchText | orderBy: 'value.name'">
{{x.value.name}}
</li>
</ul>
</div>
<script>
angular.module('myApp', []).controller('namesCtrl', function($scope) {
$scope.searchText='';
$scope.names = {
"1": {
"name": "some"
},
"2": {
"name": "values"
},
"3": {
"name": "are"
},
"4": {
"name": "there"
},
"5": {
"name": "here"
}
};
$scope.objArray=function (obj) {
var result=[];
for (var key in obj) {
result.push({
key: key,
value: obj[key]
});
}
return result;
}
});
</script>
</body>
</html>
I believe the best and elegant solution is to make a filter that changes your object into an array. Therefore you can reuse it thought all your project in your template without coding any js.
Here is what the filter would look like:
(function () {
'use strict';
angular.module('app').filter('toArray', toArray);
toArray.$inject = [];
function toArray() {
return toArrayFilter;
function toArrayFilter(input) {
if (angular.isArray(input)) return input;
var list = [];
angular.forEach(input, iterateProperty, list);
return list;
function iterateProperty(elt, key) {
this.push({ key: key, value: elt });
}
}
}
})();
and here is how you would use it in your html template:
<div ng-repeat="element in myObject | toArray | orderBy:value">
{{element.key}}:
<pre>{{element.value | json}}</pre>
</div>

Determine layers in wms address angularjs

I am using angularjs and I want to enter a wms address and check what are the available layers that I could select. Ive tried http.Capabilities but its not working.
Check the sample below. This might help you.
<div ng-app ng-controller="WMSCtrl">
<ul>
<li ng-repeat="num in nums">{{num}}</li>
{{data}}
<button ng-click="get_data()">Get stuff</button>
</ul>
function WMSCtrl($scope, $http) {
$scope.nums = [1,2,3]
$scope.data = null;
$scope.get_data = function() {
var url2 = 'http://giswebservices.massgis.state.ma.us/geoserver/wms?VERSION=1.1.1&LAYERS=massgis:GISDATA.ACECS_POLY&SRS=EPSG:26986&BBOX=11830.0,776202.9449152543,348201.0,961492.0550847457&WIDTH=708&HEIGHT=390&INFO_FORMAT=text/javascript&FEATURE_COUNT=10&QUERY_LAYERS=massgis:GISDATA.ACECS_POLY&X=120&Y=109&FORMAT&STYLES=&SERVICE=WMS'
$http.jsonp(url2, {params : {REQUEST: 'GetFeatureInfo'}});
}
window.parseResponse = function(data) {
$scope.data = data
}
}
Plunker given below link

AngularJS - JSON and return all results

I'm trying to write a basic search function using AngularJS. I have written a service that finds my JSON file and binds it to a $scope object $scope.SearchResult
What i am trying to do it perform a search on the items within SearchResult when the user enters a string. For any matches found,return the entire contents.
HTML:
<div ng-controller="MainCtrl">
<p>Hello {{name}}!</p>
<input ng-model="searchText">
<button ng-click="performSearch(searchText)">Submit</button>
{{ item }}
</div>
JS:
app.controller('MainCtrl', function($scope) {
$scope.name = 'World';
$scope.SearchResult = [
{
"Index":1,
"Title":"Help",
"Snippet":"You found Mr Happy",
"Url":"www.test.co.uk"
},
{
"Index":2,
"Title":"Conatct",
"Snippet":"You found Mr Happy",
"Url":"www.test.co.uk"
},
{
"Index":3,
"Title":"Help",
"Snippet":"You found Mrs Angry",
"Url":"www.test.co.uk"
},
{
"Index":4,
"Title":"Help",
"Snippet":"You found Mr Sad",
"Url":"www.test.co.uk"
}
];
$scope.performSearch = function(searchText) {
console.log("Performing a search....");
angular.forEach($scope.SearchResult.Snippet, function(item) {
if( item.label.indexOf(searchText) >= 0 ) filtered.push(item);
console.log(item);
});
}
});
So if HAPPY was entered in the input field, 2 matches would be found and displayed.
Heres a plunker: http://plnkr.co/edit/mOjcYUbFpoveaDw12NjE?p=preview

Resources