I have this in my Angular app:
myApp.value(mySetting, mySettingValue);
Is it possible to $watch() mySetting for changes? I've tried but can't get it to work.
This doesn't seem to do the trick:
$rootScope.$watch(function() {
return mySetting;
, function(newSettingValue) {
console.log(Date.now() + ' ' + newSettingValue);
});
You missed to true property as a 3rd parameter inside your $watch, adding true will keep deep watch on object
Code
$rootScope.$watch(function() {
return mySetting;
, function(newSettingValue) {
console.log(Date.now() + ' ' + newSettingValue);
}, true);
Example Plunkr
Related
I am curious if there is a way to disable a filter once its been applied.
for instance:
<h3 class="mention" ng-bind-html="mention | getPlace" place-directive > <span>#</span>{{mention}}</h3>
filter:
hungryApp.filter('getPlace', function($stateParams) {
return function(place) {
return '<a>' + '#' + place.placeinfo.placename + '</a>';
}
});
Once the element is rendered, is there an angular way for that filter to not effect the elements it has already filtered?
I was able to come up with a dirty solution of writing a directive that basically replaces the element with a cloned copy, but definitely not the cleanest solution.
Thanks for any suggestion.
Answer is accepted but actually not good. As in Angular 1.4 one time binding was introduced:
{{::mention | getPlace}}
Accept a boolean parameter in your filter, and make it return the input, untouched, if the boolean is true (or false).
Then pass a boolean variable as argument to your filter, and toggle it to change the behavior of the filter:
hungryApp.filter('getPlace', function($stateParams) {
return function(place, ignore) {
if (ignore) {
return place;
}
else {
return '<a>' + '#' + place.placeinfo.placename + '</a>';
}
};
});
In the controller:
$scope.placeFilteringIgnored = false;
$scope.togglePlaceFiltering = function() {
$scope.placeFilteringIgnored = !$scope.placeFilteringIgnored;
}
And in the view:
<h3 class="mention" ng-bind-html="mention | getPlace:placeFilteringIgnored"></h3>
<button ng-click="togglePlaceFiltering()">Toggle place filtering</button>
could you please tell me why I am getting undefined value .When I click on chart ? I make one bar chart and try to get it value .In other words try to get selected item and it’s value .
In give fiddle it gives correct value
http://jsfiddle.net/b4n9z19v/
But when I make directive and try to get it value it is giving me undefined why ?
here is code
http://plnkr.co/edit/FtDfeyd6fjHL3RNwzyCn?p=preview
$scope.chartObj = new Highcharts.Chart($scope.chartData);
$element.bind('click', function (event) {
// do your code
alert( $scope.chartData.chart.type);
alert('Category: ' + this.category + ', value: ' + this.y);
});
Why don't you add click event to the chart object, in a similar way as you did for data.json? Like this:
$scope.chartData.plotOptions.series.point.events.click = function (event) {
// do your code
alert( $scope.chartData.chart.type);
alert('Category: ' + this.category + ', value: ' + this.y);
};
See plunker: http://plnkr.co/edit/WA4TcDuoer3ix08T15QM?p=preview
How do I get text of input and use it in my test? The code bellow returs an Protractor Object and not the text.
var typed = element(by.css(css + ' input')).getAttribute('value');
if (typed === 'something') { // doSomething() }
The function getAttribute returns a promise. To access the value you can do so in a then calback
element(by.css(css + ' input')).getAttribute('value').then(function(value) {
console.log(value);
});
You don't mention what you need it for, but note that expect can handle promises passed to it, so for a lot of cases you don't need the then callback.
expect(element(by.css(css + ' input')).getAttribute('value')).toEqual('some-value');
When I select country on map, how can I get a value of this country and pass it to variable? Thanks a lot! I used amcharts.com
Or it can be another solution? I you know how to choose country on map, i'll be very grateful!
You can use "clickMapObject" event to catch all the information about clicked object. I.e.:
map.addListener("clickMapObject", function (event) {
alert( 'Clicked ID: ' + event.mapObject.id + ' (' + event.mapObject.title + ')' );
});
Here's a working example:
http://jsfiddle.net/amcharts/k67gB/light/
Please note that in order for this event to fire the country needs to be clickable. This means that either "autoZoom" needs to be enabled or all areas need to be set as "selectable":
var map = AmCharts.makeChart("mapdiv",{
...
"areasSettings": {
"autoZoom": true
}
});
Or
var map = AmCharts.makeChart("mapdiv",{
...
"areasSettings": {
"selectable": true
}
});
Trying to get a more in-depth understanding of how Angular treats data binding and understanding it better and one thing is difficult to get my head around -
In Knockout I use a computed to keep track of changes to a property. In Angular it to move this logic into the view, which is a it trivial to me, but if that is the way to do it I understand.
My question is when I am initializing a new entity with Breeze/Angular how do I create computed-like properties that are notified when changes occur to the entities property?
myEntity.fullName = ko.computed(function () {
return myEntity.firstName + ' ' + myEntity.LastName;
});
in Angular would the equivalent be
myEntity.fullName = function () {
return myEntity.firstName + ' ' + myEntity.LastName;
};
And does that properly track the entity?
You are correct to simply make it a function. If your entity as shown is added to the $scope, then you would access the property like so:
<span class="fullname">{{ user.fullName() }}</span>
Whenever Angular runs a $digest cycle, it will check for a change to the bound property. In this instance, it means it will call the fullName() function and check to see if the result has changed. If it has, anything that has a $watch attached to that item — including simple binding — will be notified of the change.
One caveat of this technique, however, is to make sure that the operations being performed within your function are relatively fast, and also have no side effects. Bound functions like this will be called many times throughout the application.
If you need to have a more complex function, it would be better to handle that within the controller, and update a property on the object manually when it changes.
I found the answer on the following website. If you don't do something similar, what you will find is that all functions are ran during the digest phase and are not triggered by the change of a dependent observable or property. The solution below allows you to only trigger the function when a value it uses is changed.
http://www.jomendez.com/2015/02/06/knockoutjs-computed-equivalent-angularjs/
Explains how to duplicate the subscribe and computed feature in knockoutjs
var myViewModel = {
personName: ko.observable('Bob')
};
myViewModel.personName.subscribe(function(oldValue) {
alert("The person's previous name is " + oldValue);
}, null, "beforeChange");
This is what I found as result of my research (this is the AngularJs equivalent) Using the $scope.$watch method see the AngularJs life cycle https://docs.angularjs.org/guide/scope
$scope.myViewModel = {
personName: 'Bob'
};
$scope.$watch(‘myViewModel.personName’, function(newValue, oldValue){
//we are able to have both the old and the new value
alert("The person's previous name is " + oldValue);
});
//knockout computed
var isVendorLoading = ko.observable(),
isCustomerLoading = ko.observable(),
isProgramLoading = ko.observable(),
isWaiting = ko.observable();
var isDataLoading = ko.computed(function () {
return isVendorLoading() || isCustomerLoading() || isProgramLoading() || isPositionLoading() || isWaiting();
});
This is the AngularJs Equivalent for KnockoutJs computed:
$scope.isDataLoading = false;
$scope.$watch(
function (scope) {
//those are the variables to watch
return { isVendorLoading: scope.isVendorLoading, isCustomerLoading: scope.isCustomerLoading, isProgramLoading: scope.isProgramLoading, isWaiting: scope.isWaiting };
},
function (obj, oldObj) {
$timeout(function () {
//$timeout used to safely include the asignation inside the angular digest processs
$scope.isDataLoading = obj.isVendorLoading || obj.isCustomerLoading || obj.isProgramLoading || obj.isPositionLoading || obj.isWaiting;
});
},
true
);