Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

$watch vs. ngChange

Say that you want to do something when a property of $scope changes. And say that this property is bound to an input field. What are the advantages/disadvantages of using $watch vs. using ngChange?

html

<input ng-model="foo" ng-change="increment()">
<p>foo: {{foo}}</p>

<!-- I want to do something when foo changes.
     In this case keep track of the number of changes. -->
<p>fooChangeCount: {{fooChangeCount}}</p>

js

// Option 1: $watch
$scope.$watch('foo', function() {
  $scope.fooChangeCount++;
});

// Option 2: ngChange
$scope.fooChangeCount = 0;
$scope.increment = function() {
  $scope.fooChangeCount++;
};

http://plnkr.co/edit/4xJWpU6AN9HIp0OSZjgm?p=preview

I understand that there are times when you need to use $watch (if the value you're looking to watch isn't bound to an input field). And I understand that there are times when you need to use ngChange (when you want to do something in response to a change in an input, but not necessarily in response to a scope property change).

However, in this case both accomplish the same thing.

My thoughts:

  • ngChange seems cleaner, and easier to understand what's happening.
  • $watch seems like it might be slightly faster, but probably negligible. With ngChange, I think Angular would have to do some extra work in the compile phase to set up the event listeners, and perhaps extra event listeners decrease speed a bit. Regardless of whether or not you use ngChange, the digest cycle runs on changes, so you have an opportunity to listen for something and call a function in response to changes.
like image 707
Adam Zerner Avatar asked Dec 16 '14 17:12

Adam Zerner


2 Answers

Bottom line - You can achieve with $watch every thing you can achieve with ng-change but not vice-versa.

Purposes:

ngChange - binded to a HTML element

$watch - observing scope's model objects (HTML object models included)

My rule of thumb - if you can use ng-change use it to match your scenario, otherwise use $watch

Why you shouldnt use $watch?

  1. It’s inefficient - Adding complexity to your $digest
  2. It’s hard to test effectively
  3. It's not clean
like image 148
Ben Diamant Avatar answered Nov 08 '22 04:11

Ben Diamant


You have it mostly right. ng-change is very DOM specific and for evaluating an expression when the change event fires on a DOM element.

$watch however, is a lower-level (and more general purpose) utility that watches your view model or $scope. So your watch function will fire every time the user types a key (in the example of an input).

So to contrast, one listens to DOM events, the other watches your data.

like image 31
Jon Jaques Avatar answered Nov 08 '22 06:11

Jon Jaques