如何告诉AngularJS“刷新”为什么要打电话?$apply

2022-08-30 01:40:24

我有一个发生在我的自定义指令范围之外的点击事件,所以我没有使用“ng-click”属性,而是使用jQuery.click()侦听器并在我的范围内调用一个函数,如下所示:

$('html').click(function(e) {
  scope.close();
);

close() 是一个简单的函数,如下所示:

scope.close = function() {
  scope.isOpen = false;
}

在我看来,我有一个元素,“ng-show”绑定到isOpen,如下所示:

<div ng-show="isOpen">My Div</div>

调试时,我发现正在调用 close(),isOpen 正在更新为 false,但 AngularJS 视图未更新。有没有办法手动告诉Angular更新视图?还是有一种更“棱角分明”的方法来解决这个问题,我没有看到?


答案 1

解决方案是调用...

$scope.$apply();

...在我的jQuery事件回调中。


答案 2

为什么要打电话?$apply

TL;DR:每当您想要应用在Angular世界之外所做的更改时,都应该调用它。$apply


为了更新@Dustin的答案,这里解释了$apply究竟做了什么以及它为什么有效。

$apply()用于从 AngularJS 框架外部执行 AngularJS 中的表达式。(例如,来自浏览器 DOM 事件、setTimeout、XHR 或第三方库)。由于我们正在调用 AngularJS 框架,我们需要执行异常处理执行监视的正确范围生命周期。

Angular 允许将任何值用作绑定目标。然后,在任何JavaScript代码轮次结束时,它都会检查值是否已更改。检查是否有任何绑定值已更改的步骤实际上有一个方法 1。我们几乎从不直接调用它,因为我们使用它(这将调用 )。$scope.$digest()$scope.$apply()$scope.$digest

Angular 仅监视表达式中使用的变量以及作用域内生活内的任何内容。因此,如果要在 Angular 上下文之外更改模型,则需要调用这些更改进行传播,否则 Angular 将不知道它们已被更改,因此绑定将不会更新2$watch$scope.$apply()