$watch ngModel from inside directive using isolate scope

前端 未结 6 1852
刺人心
刺人心 2020-12-08 09:13

I am trying to watch my model value from inside my linking function.

scope.$watch(attrs.ngModel, function() {
       console.log(\"Changed\"); 
    });


        
相关标签:
6条回答
  • 2020-12-08 09:33

    The proper way to do this is:

    app.directive('myDirective', function () {
      return {
        require: 'ngModel',
        link: function (scope, element, attrs, ngModel) {
    
            ngModel.$render = function () {
                var newValue = ngModel.$viewValue;
                console.log(newValue)
            };
    
        }
      };
    });
    
    0 讨论(0)
  • 2020-12-08 09:41

    This is an extension of @ Emmanuel's answer above to answer @Martin Velez, although I know it's pretty late! (Also I can't make comments yet, so if this isn't the right place for this, sorry!)

    I'm not sure which version of Angular OP was using, but in Angular#1.2+ at least on the official docs https://docs.angularjs.org/api/ng/type/ngModel.NgModelController#$render, $render is listed like this:

    Called when the view needs to be updated. It is expected that the user of the ng-model directive will implement this method.

    The $render() method is invoked in the following situations:

    $rollbackViewValue() is called. If we are rolling back the view value to the last committed value then $render() is called to update the input control. The value referenced by ng-model is changed programmatically and both the $modelValue and the $viewValue are different from last time. Since ng-model does not do a deep watch, $render() is only invoked if the values of $modelValue and $viewValue are actually different from their previous value.

    I interpret this to mean that the correct way to $watch an ngModel from a directive is to require ngModel and implement a link function that injects ngModelController. Then use the ngModel API that's built in to $render-on-change ($watch), or whatever else.

    0 讨论(0)
  • 2020-12-08 09:46

    You'll need to watch a function that returns the $modelValue you're watching.

    The following code shows a basic example:

    app.directive('myDirective', function (){
        return {
            require: 'ngModel',
            link: function(scope, element, attrs, ngModel) {
               scope.$watch(function () {
                  return ngModel.$modelValue;
               }, function(newValue) {
                   console.log(newValue);
               });
            }
         };
    });
    

    Here's a plunker of the same idea in action.

    0 讨论(0)
  • 2020-12-08 09:46

    There are 2 ways to do it.

    1) You can use $attrs.[any_attribute] and set on it any listener

    2) You can have isolated scope with 2 ways binding variable and set a listener on it.If you want more,here is a cool article

    http://www.w3docs.com/snippets/angularjs/bind-variable-inside-angularjs-directive-isolated-scope.html

    0 讨论(0)
  • 2020-12-08 09:50

    The problem is that you $watching attrs.ngModel which is equal to "myModel". You do not have "myModel" bound in your scope. You want to $watch "model". That is what is bound in the scope of your directive. See http://jsfiddle.net/BtrZH/5/

    0 讨论(0)
  • 2020-12-08 09:50

    Here is another way to do this:

    app.directive('myDirective', function (){
        return {
            require: 'ngModel',
            link: function(scope, element, attrs, ngModel) {
               attrs.$observe('ngModel', function(value){ // Got ng-model bind path here
                  scope.$watch(value,function(newValue){ // Watch given path for changes
                      console.log(newValue);  
                  });
               });
            }
        };
    });
    

    Doing it that way you will be able to listen value changes with binds like that

    0 讨论(0)
提交回复
热议问题