在 Angular 1 中,更改检测是通过对 $scope 层次结构进行脏检查来进行的。我们会在模板、控制器或组件中隐式或显式创建观察者。
在 Angular 2 中,我们不再有 $scope,但我们确实重写了 setInterval、setTimeout 等。我可以看到 Angular 如何使用它来触发 $digest,但是 Angular 如何确定发生了什么变化,特别是考虑到 Object.observe 从未进入浏览器?
Example
这是一个简单的例子。服务中定义的对象在 setInterval 中更新。每个时间间隔都会重新编译 DOM。
Angular 如何知道 AppComponent 正在监视服务,并且服务的属性值已更改?
var InjectedService = function() {
var val = {a:1}
setInterval(() => val.a++, 1000);
return val;
}
var AppComponent = ng.core
.Component({
selector: "app",
template:
`
{{service.a}}
`
})
.Class({
constructor: function(service) {
this.service = service;
}
})
AppComponent.parameters = [ new ng.core.Inject( InjectedService ) ];
document.addEventListener('DOMContentLoaded', function() {
ng.platform.browser.bootstrap(AppComponent, [InjectedService])
});
Angular 创建一个变化检测器对象(参见变更检测器参考 https://angular.io/docs/ts/latest/api/core/index/ChangeDetectorRef-class.html) 每个组件,它跟踪每个模板绑定的最后一个值,例如{{service.a}}
。默认情况下,在每个异步浏览器事件(例如来自服务器的响应、单击事件或超时事件)之后,Angular 更改检测将执行并使用这些更改检测器对象对每个绑定进行脏检查。
如果检测到更改,则会传播该更改。例如。,
- 如果输入属性值发生更改,新值将传播到组件的输入属性。
- If a
{{}}
绑定值更改,新值传播到 DOM 属性textContent
.
- 如果值
x
样式、属性或类绑定的更改 – 即,[style.x]
or [attr.x]
or [class.x]
– 新值传播到 DOM 以更新样式、HTML 属性或类。
Angular 使用 Zone.js 创建自己的区域(NgZone https://angular.io/docs/ts/latest/api/core/NgZone-class.html),它对所有异步事件(浏览器 DOM 事件、超时、AJAX/XHR)进行猴子修补。这就是更改检测能够在每个异步事件之后自动运行的方式。即,在每个异步事件处理程序(函数)完成后,将执行 Angular 更改检测。
我在此答案中有更多详细信息和参考链接:Angular2 相当于 AngularJS $watch 吗? https://stackoverflow.com/questions/34569094/what-is-the-angular2-equivalent-to-an-angularjs-watch/34570122#34570122
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)