单击绑定指令更新控制器$ scope后,是否需要调用Angular的$ apply?

时间:2014-02-09 18:52:51

标签: javascript angularjs jqlite

以下片段,此处为Plunker:http://plnkr.co/edit/WA6tIfqXV6dO4pbsqxu9?p=preview

我经常遇到的一个挑战是在指令元素上触发绑定时从指令范围更新控制器范围,例如: “点击”。我通过在更改指令的范围后调用$ apply()来实现它,但这是否有点过分?

所以说我有一个名为“value”的控制器值:

  .controller( 'coolCtrl', [ '$scope', function( $scope )
  {
    $scope.value = 1;
  }])

我希望在单击指令元素时从指令中增加该值:

  .directive( 'testScope', function()
  {
    return {
      restrict: 'E',
      replace: true,
      scope: {
        value: '='
      },
      template: '<button>Increase value</button>',
      link: function( scope, element, attrs )
      {
        // Note: just using standard jqLite here
        element.on( 'click', function()
        {
          scope.value++;
          scope.$apply();
        });
      }
    };
  })

是否需要调用$ apply以在每次点击时更新父范围?如果用户正在键入该内容,那么整个父内容范围向下是否必须在每个keydown上经历一个$ digest周期?

PS我对Angular的熟悉是令人羞愧的。

1 个答案:

答案 0 :(得分:1)

如果您使用的是本机浏览器事件,则必须使用$apply将更改显示为有角度。是的,如果您使用keydown,将会发生完整的摘要周期。但在大多数情况下,这不是问题。

如果您使用的是ng- *指令,那么您可能真的会减少代码。例如,您可以使用ng-click解决问题:

.directive( 'testScope', function()
  {
    return {
      restrict: 'E',
      replace: true,
      scope: {
        value: '='
      },
      controller: function($scope){
          $scope.increase = function(){
            $scope.value++;
          }
      },
      template: '<button ng-click="increase()">Increase value</button>'
    }; 
  })

如果你这样做,就不需要手动调用$apply。这是有角度的方式......