Angularjs:为什么当我点击表格行时,它会在ng-if中执行函数?



我有代码 https://jsfiddle.net/8t45enfg/2/
源代码很简单,假设数组列表只有一个元素
HTML代码:

<div ng-controller="myController">
<table>
<tr>
<th>Name</th>
<th>Age</th>
<th>Job</th>
</tr>
<tr ng-repeat="a in list" ng-click='doClick()'>
<td ng-if='doCheck()'>{{ a.name }}</td>
<td>{{ a.age }}</td>
<td>{{ a.job }}</td>
</tr>
</table>
</div>

Js 代码

module.controller("myController", function($scope) {
$scope.list = [ { name: 'test', age: 100, job: 'IT'} ]
$scope.doClick = function() {
console.log('doClick');
}
$scope.doCheck = function() {
console.log('doCheck');
return true;
}
});
  1. 当我运行代码时,doCheck((执行了两次,为什么?它应该执行一次
  2. 主要问题是当我单击数据行时,doCheckdoClick都被调用,我以为它会只调用doClick,而不是doCheck,因为我对doCheck没有操作。这让我难以理解

我不是该主题的完整专家,但这是我对您的问题的理解。

每当在您的页面上进行更改时,该页面都会设置为"脏",当下一个周期到达ng-if时,它将重新评估。

因此,要回答您的第一个问题,ng-if在加载时进行评估(调用doCheck()(,然后加载页面的其余部分,导致页面设置为"脏",因此重新评估ng-if,导致再次调用doCheck()

这会导致"doCheck"出现两次。

你的第二个问题也是如此。每单击时,都会重新评估doCheck(),从而导致调用doClick()doCheck()。 如果要避免每次都调用doCheck(),请在ng-if中使用变量,然后创建一个函数来更改该变量。

我希望这有所帮助,我相信一些棱角分明的巫师会给你一个更好的答案!

这是因为Angular 的摘要循环

以下是Dave Ceddia博客中的一些重要引述 - 控制器功能被多次执行,以帮助您理解原因:

安格尔的摘要周期

你所看到的是工作中的摘要循环。摘要周期为 Angular 的自动更新魔术如何工作——这就是打字的原因 进入输入框会自动更新任何引用其的内容 价值。

当摘要循环运行时,它有效地重绘了所有 页面上可能已更改。

Angular使用一些技巧来找到"可能已经改变的一切", 主要技术是观察者。创建这些观察程序 当您使用ng-ifng-class等指令时自动,以及 当您使用像{{ yourBindingHere }}这样的绑定时。

这些事情中的每一个都会注册一个观察者。当安格尔的文摘 循环运行,要求每个观察者更新其状态。在以下情况下:ng-class,它会重新运行绑定到它的函数,看看有没有任何东西 需要改变。这就是您的控制器功能运行多个的原因 次,并且每次页面上的某些内容发生更改时,它都会再次运行。

对于Q1
doCheck(( 是您创建的函数,这意味着每次 html 运行时它都会检查。如果要对标签执行检查条件,则必须使用变量而不是函数。

对于第二季度。 当您单击该行时,doClick将触发,然后doCheck函数也将运行,因为您在ng-if条件下使用了该函数,因此将再次重新评估

我希望这个答案能帮助你理解。我已经通过小的更改修改了您的代码。

<div ng-controller="myController">
<table>
<tr>
<th>Name</th>
<th>Age</th>
<th>Job</th>
</tr>
<tr ng-repeat="a in list" ng-click='doClick()'>
<td ng-if='doCheckCondition'>{{ a.name }}</td>
<td>{{ a.age }}</td>
<td>{{ a.job }}</td>
</tr>
</table>
</div>

JS脚本

module.controller("myController", function($scope) {
$scope.list = [ { name: 'test', age: 100, job: 'IT'} ]
$scope.doClick = function() {
console.log('doClick');
//Do something and set it true the $scope.doCheckCondition
}
$scope.doCheckCondition = false

最新更新