我有一个AngularJS指令,它在以下模板中呈现实体集合:
<table class="table">
<thead>
<tr>
<th><input type="checkbox" ng-click="selectAll()"></th>
<th>Title</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="e in entities">
<td><input type="checkbox" name="selected" ng-click="updateSelection($event, e.id)"></td>
<td>{{e.title}}</td>
</tr>
</tbody>
</table>
正如你所看到的,这是一个<代码>
最好的方法是什么:
我当前的实现是在我的指令中添加一个自定义控制器:
controller: function($scope) {
// Array of currently selected IDs.
var selected = $scope.selected = [];
// Update the selection when a checkbox is clicked.
$scope.updateSelection = function($event, id) {
var checkbox = $event.target;
var action = (checkbox.checked ? 'add' : 'remove');
if (action == 'add' & selected.indexOf(id) == -1) selected.push(id);
if (action == 'remove' && selected.indexOf(id) != -1) selected.splice(selected.indexOf(id), 1);
// Highlight selected row. HOW??
// $(checkbox).parents('tr').addClass('selected_row', checkbox.checked);
};
// Check (or uncheck) all checkboxes.
$scope.selectAll = function() {
// Iterate on all checkboxes and call updateSelection() on them??
};
}
更具体地说,我想知道:
上面的代码是属于控制器还是应该进入链接功能
- 如果jQuery不一定存在(AngularJS不需要),那么什么是进行DOM遍历的最佳方法?没有jQuery,我很难只选择父级
非常感谢。
Liviu的回答对我很有帮助。希望这不是一个糟糕的形式,但是我做了一个小提琴,将来可能会帮助别人。
需要的两个重要部分是:
$scope.entities = [{
"title": "foo",
"id": 1
}, {
"title": "bar",
"id": 2
}, {
"title": "baz",
"id": 3
}];
$scope.selected = [];
在处理复选框时,我更喜欢使用ngModel和ngChange指令。ngModel允许您将复选框的选中/未选中状态绑定到实体上的属性:
<input type="checkbox" ng-model="entity.isChecked">
每当用户选中或取消选中复选框时,entity.isChecked
值也会更改。
如果这就是您所需要的,那么您甚至不需要ngClick或ngChange指令。由于您有“全部选中”复选框,显然您需要做的不仅仅是在有人选中复选框时设置属性的值。
当使用带有复选框的ngModel时,最好使用ngChange而不是ngClick来处理选中和未选中的事件。ngChange就是为这种情况而做的。它利用ngModelController进行数据绑定(它将侦听器添加到ngModelController的$viewChangeListeners数组中。此数组中的侦听器在设置模型值后被调用,从而避免了此问题)。
<input type="checkbox" ng-model="entity.isChecked" ng-change="selectEntity()">
。。。在控制器中。。。
var model = {};
$scope.model = model;
// This property is bound to the checkbox in the table header
model.allItemsSelected = false;
// Fired when an entity in the table is checked
$scope.selectEntity = function () {
// If any entity is not checked, then uncheck the "allItemsSelected" checkbox
for (var i = 0; i < model.entities.length; i++) {
if (!model.entities[i].isChecked) {
model.allItemsSelected = false;
return;
}
}
// ... otherwise ensure that the "allItemsSelected" checkbox is checked
model.allItemsSelected = true;
};
同样,标题中的“全部选中”复选框:
<th>
<input type="checkbox" ng-model="model.allItemsSelected" ng-change="selectAll()">
</th>
。。。和
// Fired when the checkbox in the table header is checked
$scope.selectAll = function () {
// Loop through all the entities and set their isChecked property
for (var i = 0; i < model.entities.length; i++) {
model.entities[i].isChecked = model.allItemsSelected;
}
};
CSS
什么是最好的方式。。。将CSS类添加到<代码>
如果使用ngModel方法进行数据绑定,那么只需将ngClass指令添加到
<tr ng-repeat="entity in model.entities" ng-class="{selected: entity.isChecked}">
在这里查看完整的Plunker。
这就是我一直在做这类事情的方式。Angular倾向于对dom的声明性操作,而不是命令式操作(至少我是这样玩的)。
标记
<table class="table">
<thead>
<tr>
<th>
<input type="checkbox"
ng-click="selectAll($event)"
ng-checked="isSelectedAll()">
</th>
<th>Title</th>
</tr>
</thead>
<tbody>
<tr ng-repeat="e in entities" ng-class="getSelectedClass(e)">
<td>
<input type="checkbox" name="selected"
ng-checked="isSelected(e.id)"
ng-click="updateSelection($event, e.id)">
</td>
<td>{{e.title}}</td>
</tr>
</tbody>
</table>
在控制器中
var updateSelected = function(action, id) {
if (action === 'add' && $scope.selected.indexOf(id) === -1) {
$scope.selected.push(id);
}
if (action === 'remove' && $scope.selected.indexOf(id) !== -1) {
$scope.selected.splice($scope.selected.indexOf(id), 1);
}
};
$scope.updateSelection = function($event, id) {
var checkbox = $event.target;
var action = (checkbox.checked ? 'add' : 'remove');
updateSelected(action, id);
};
$scope.selectAll = function($event) {
var checkbox = $event.target;
var action = (checkbox.checked ? 'add' : 'remove');
for ( var i = 0; i < $scope.entities.length; i++) {
var entity = $scope.entities[i];
updateSelected(action, entity.id);
}
};
$scope.getSelectedClass = function(entity) {
return $scope.isSelected(entity.id) ? 'selected' : '';
};
$scope.isSelected = function(id) {
return $scope.selected.indexOf(id) >= 0;
};
//something extra I couldn't resist adding :)
$scope.isSelectedAll = function() {
return $scope.selected.length === $scope.entities.length;
};
编辑:getSelectedClass()
需要整个实体,但调用时仅使用实体的id,现在已更正
问题内容: 我有一个AngularJS 指令,该指令在以下模板中呈现实体集合: 如您所见,在这里可以单独选择每一行并带有自己的复选框,也可以通过位于中的主复选框来一次选择所有行。相当经典的用户界面。 最好的方法是: 选择单行(即,选中复选框时,将所选实体的ID添加到内部数组,然后将CSS类添加到包含该实体的CSS类以反映其所选状态)? 一次选择所有行?(即,针对中的所有行执行上述操作) 我当前的实
问题内容: 我正在一个angularjs项目上工作,并且在select.not内没有绑定存在问题,但是相同的概念正在另一个select标签和同一html页面中工作。下面是代码。 功能放置在控制器中。 任何人的帮助都是非常可贵的……谢谢。 问题答案: 基于小马的托尼的小提琴: 使用控制器: http://jsfiddle.net/basarat/3y5Pw/43/
问题内容: 我已经编辑了数据,并试图仅获取用户已选择的数据。我不确定该怎么做,这就是我所拥有的: HTML: JS: 我确实以一种方式使它工作-通过向每个对象添加属性并将复选框的更改为,然后可以在函数中对此进行过滤。但是,这似乎效率很低,如果可以避免,我不想在模型中添加额外的属性。 有没有更好的办法 ? 问题答案: 的JavaScript HTML http://plnkr.co/edit/lqt
问题内容: 我喜欢使用指令制作自定义组件。我检查了很多教程,它使我感到困惑,任何人都可以解释指令的工作原理。我计划制造的组件是 呼喊列表的模板将像这样 问题答案: 这是您的指令,带有一些内联注释: 和模板文件: 现在,您可以在代码中使用它,如下所示: 控制器: 视图: 希望这可以帮助!
问题内容: 我正在尝试构建一个指令,该 指令 负责在其声明的元素上 添加更多指令 。例如,我要建立一个指令,需要增加的照顾,和。 如果我尝试添加这些属性然后使用,则显然会生成一个无限循环,因此我正在检查是否已添加所需的属性: 当然,如果我没有该元素,则将设置属性,但不会引导该指令。 这种方法正确还是我做错了?有没有更好的方法来实现相同的行为? UDPATE :鉴于这是实现此目标的唯一方法,是否有一
问题内容: 我想过滤结果。 有一个葡萄酒清单,我的愿望是当未选中任何复选框时,将显示整个葡萄酒清单。 当仅选中1个复选框时,显示相关类别 当选中多个复选框时,将显示相关类别 我是AngularJS的新手,我尝试了ng-model都没有成功,这是没有与函数关联的ng-model的代码: 如何使用ng-model或ng-change将功能与每个复选框按钮相关联以具有实时过滤模型? 问题答案: 只是添加