在什么样的顺序做角度观察和事件侦听器执行呢? [英] In what order do angular watchers and event listeners execute?

查看:180
本文介绍了在什么样的顺序做角度观察和事件侦听器执行呢?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如果一个第一个变化范围属性,然后第二个广播一个事件时,将相应的观察者的回调和事件侦听器回调总是以相同的顺序执行?例如:

If one changes a scope property first, and then broadcasts an event second, will the corresponding watcher callback and event listeners callback always be executed in that same order? For example:

$scope.foo = 3;
$scope.$broadcast('bar');

和其他地方的:

$scope.$watch('foo', function fn1(){...});
$scope.$on('bar', function fn2(){...});

威尔 FN1 永远是 FN2 之前执行,或者反之亦然,或者顺序不可靠在?请pferably引用来源,$ P $官方的角度文档。

Will fn1 always be executed prior to fn2, or visa-versa, or can the order not be relied upon? Please cite sources, preferably to official angular docs.

在情况下,它重要的:让我们假设在$ scope.foo =和$广播发生在由NG-点击调用的函数(即用户交互)

In case it matters: lets assume the $scope.foo= and the $broadcast occur in a function invoked by an ng-click (i.e. user interaction)

【旁白】对不起问题的标题是马虎 - 请重新命名,如果你有更好的东西。

[aside] Sorry question title is sloppy - please rename if you have something better.

推荐答案

要明白发生了什么,你需要了解角的的 $消化周期和事件的 $排放和$播出功能。

To understand what is happening, you need to understand Angular's $digest cycle and event $emit and $broadcast functions.

,我还了解到,角<一个href=\"https://books.google.co.uk/books?id=mZXjwz5X08EC&pg=PT547&lpg=PT547&dq=angularjs%20does%20not%20use%20any%20kind%20of%20polling%20mechanism%20to%20periodically%20check%20for%20model%20changes&source=bl&ots=T4H4PSXaST&sig=qR-usD2QqriowWkSNmkRC7EI1Rk&hl=en&sa=X&ei=4Y1mU_uCDYPBO4LkgJAH&ved=0CDEQ6AEwAA#v=onepage&q=angularjs%20does%20not%20use%20any%20kind%20of%20polling%20mechanism%20to%20periodically%20check%20for%20model%20changes&f=false\"相对=nofollow>不使用任何形式的投票机制,定期检查模型变化。这不是在角文档说明,但可以进行测试(见这个答案类似的问题)。

Based on some research, I've also learned that Angular does not use any kind of polling mechanism to periodically check for model changes. This is not explained in the Angular docs, but can be tested (see this answer to a similar question).

把所有的一起,我写一个简单的实验并得出结论,你可以依靠你事件处理程序先运行,那么你的手表功能。这是有道理的,因为手表的功能可以消化循环中被​​称为连续多次。

Putting all of that together, I wrote a simple experiment and concluded that you can rely on your event handlers running first, then your watch functions. Which makes sense, because the watch functions can be called several times in succession during the digest loop.

以下code ...

The following code...

template.html

<div ng-app="myApp">
  <div watch-foo ng-controller="FooController">
    <button ng-click="changeFoo()">
      Change
    </button>
  </div>
</div>

的script.js

angular.module('myApp', [])
  .directive('watchFoo', watchFooDirective)
  .controller('FooController', FooController);

function watchFooDirective($rootScope) {
  return function postLink(scope) {
    scope.$watch(function () {
        return scope.foo;
    }, function (value) {
        console.log('scope.$watch A');
    });
    scope.$on('foo', function (value) {
        console.log('scope.$on A');
    });
    $rootScope.$on('foo', function (value) {
        console.log('$rootScope.$on A');
    });
    $rootScope.$on('foo', function (value) {
        console.log('$rootScope.$on B');
    });
    scope.$on('foo', function (value) {
        console.log('scope.$on B');
    });
    scope.$watch(function () {
        return scope.foo;
    }, function (value) {
        console.log('scope.$watch B');
    });
  };
}

function FooController($scope) {
  $scope.foo = 'foo';
  $scope.changeFoo = function() {
    $scope.foo = 'bar';
    $scope.$emit('foo');
  };
}

...产生在控制台下面的结果点击更改按钮时:

...yields the following results in the console when the 'Change' button is clicked:

scope.$on A
scope.$on B
$rootScope.$on A
$rootScope.$on B
scope.$watch A
scope.$watch B

更新

下面是另一个测试,说明了手表的回调在消化循环被调用了两次,但该事件处理程序不被称为第二次:的 https://jsfiddle.net/sscovil/ucb17tLa/

Here is another test that illustrates the watch callback being called twice in the digest loop, but the event handlers not being called a second time: https://jsfiddle.net/sscovil/ucb17tLa/

和第三次测试发射表函数内部的事件,然后更新被监视的值:的https:/ /jsfiddle.net/sscovil/sx01zv3v/

And a third test that emits an event inside the watch function, then updates the value being watched: https://jsfiddle.net/sscovil/sx01zv3v/

在所有的情况下,你可以依靠的事件侦听器表函数之前被调用。

In all cases, you can rely on the event listeners being called before the watch functions.

这篇关于在什么样的顺序做角度观察和事件侦听器执行呢?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆