我有一个带有以下代码段的控制器,
...
$scope.selected_contents = [];
$scope.$watch('selected_contents', function (sel_contents) {
console.log(sel_contents, 'selected contents');
}, true);
...
指令,
commonDirectives.directive('chkbox', function() {
return {
restrict: 'A',
require: '?ngModel',
scope : {
item : '=item',
selection_pool: '=selectionPool'
},
link: function(scope, elem, attrs, ngModel) {
console.log('selected contents are', scope.selection_pool);
// watch selection_pool
scope.$watch('selection_pool', function (pool) {
console.log(pool, scope.selection_pool, 'pool updated');
if (_.contains(pool, scope.item)) {
elem.prop('checked', true);
}
else {
elem.prop('checked', false);
}
});
// toggle the selection of this component
var toggle_selection = function () {
if(_.indexOf(scope.selection_pool, scope.item) != -1) {
scope.selection_pool = _.without(scope.selection_pool , scope.item);
}
else {
scope.selection_pool.push(scope.item);
}
};
elem.on('click', toggle_selection);
}
};
});
以及使用该指令的模板
<tr ng-repeat="content in contents">
<td><input type="checkbox" selection_pool="selected_contents" item="content" chkbox></td>
</tr>
问题是,指令中selection_pool
的更改未反映到控制器中的selected_contents
。我错过了什么?
更新1:
根据@mohamedrias的建议,我用scope.$apply
包装了范围内的更改。这样做只会在添加内容时更新控制器中的selected_contents
,但在删除内容时不会更新。
...
// toggle the selection of this component
var toggle_selection = function () {
if(_.indexOf(scope.selection_pool, scope.item) != -1) {
scope.$apply(function () {
scope.selection_pool = _.without(scope.selection_pool , scope.item);
});
}
else {
scope.$apply(function () {
scope.selection_pool.push(scope.item);
});
}
};
...
答案 0 :(得分:1)
Angular使用name-with-dashes作为属性名称和camelCase for 相应的指令名称
来自here。
应该从此selection_pool
更改变量:
<input type="checkbox" selection_pool="selected_contents" item="content" chkbox>
到selection-pool
:
<input type="checkbox" selection-pool="selected_contents" item="content" chkbox>
这个selectionPool
进入指令:
scope : {
item : '=item',
selectionPool: '=selectionPool'
}
编辑:由于selectionPool
是一个数组,因此您应该使用$watchCollection
:
scope.$watchCollection('selectionPool', function (pool)
当你在toggle_selection
函数中添加/删除数组中的值时,应该包含在$timeout
函数中:
$timeout(function () {
if (_.indexOf(scope.selectionPool, scope.item) != -1) {
scope.selectionPool = _.without(scope.selectionPool, scope.item);
} else {
scope.selectionPool.push(scope.item);
}
});
这是为了确保之后将会应用digest
个周期。
以下是处理 jsfiddle 的代码:http://jsfiddle.net/0rvcguz0/3/
答案 1 :(得分:0)
经过一整天的研究,我结束了here。如果有人在Angularjs
范围内遇到任何问题,我强烈建议您阅读。
在我的案例中,正确的解决方案是用对象包裹selected_contents
。 e.g。
$scope.selected = {};
$scope.selected.contents = [];
然后在模板中将selcted_contents
替换为selected.contents
。
但我仍然不明白,[]
或数组也是一个对象。我之前的代码应该根据我在wiki中找到的信息工作。如果有人能解释我为什么我真的很感激它:)。