Javascript ey“ }, { 选:错, 描述:“马” }]; }); 应用程序指令('triStateCheckbox',函数(){ 返回{ 替换:正确, 限制:'E', 范围:{ 复选框:'=' }, 模板:“”, 控制器:函数($scope$element){ $scope.masterChange=函数(){ 对于(i=0;i
我想可以通过结合angular和javascript来解决:Javascript ey“ }, { 选:错, 描述:“马” }]; }); 应用程序指令('triStateCheckbox',函数(){ 返回{ 替换:正确, 限制:'E', 范围:{ 复选框:'=' }, 模板:“”, 控制器:函数($scope$element){ $scope.masterChange=函数(){ 对于(i=0;i,javascript,html,checkbox,angularjs,tri-state-logic,Javascript,Html,Checkbox,Angularjs,Tri State Logic,我想可以通过结合angular和javascript来解决: <div> <input type="checkbox" id="select-all" name="selectAll" value="" ng-click="checkAll($event)" /> <div > <input type="checkbox" name="childCheckbox" value="" /> <input type="check
<div>
<input type="checkbox" id="select-all" name="selectAll" value="" ng-click="checkAll($event)" />
<div >
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
</div>
</div>
在checkAll()中,以下逻辑将完成此任务
$scope.checkAll = function (source) {
checkboxes = document.getElementsByName('childCheckbox');
for (var i = 0, n = checkboxes.length; i < n; i++) {
checkboxes[i].checked = source.originalEvent.srcElement.checked;
}
$scope.checkAll=函数(源){
checkbox=document.getElementsByName('childCheckbox');
对于(变量i=0,n=checkbox.length;i
如果您不能假设ng模型被分配给布尔模型(例如,Y/N,'0'/'1')和/或您更喜欢有自己的标记,那么一种利用ngModel功能且不假设HTML结构的方法更好,IMHO
例如:
示例用法:
<fieldset indeterminate-group>
<legend>Checkbox Group</legend>
<input type="checkbox" name="c0" indeterminate-cue> Todos <br>
<input type="checkbox" name="c1" ng-model="data.c1" ng-true-value="'Y'" ng-false-value="'F'" indeterminate-item> Item 1 <br>
<input type="checkbox" name="c2" ng-model="data.c2" ng-true-value="'Y'" ng-false-value="'F'" indeterminate-item> Item 2 <br>
<input type="checkbox" name="c3" ng-model="data.c3" ng-true-value="'Y'" ng-false-value="'F'" indeterminate-item> Item 3 <br>
</fieldset>
型号:
// Bring your own model
待办事项:
- 除去主指令控制器中的项。$render()
- 给指令起一个更好的名字
- 使该指令在多个表列中易于使用
并将类型添加为指令中的“checkbox”——这似乎用户必须记住在HTML中设置一半的复选框,然后根据指令设置另一半。我建议将HTML替换为包含
的模板。这将允许用户指定任何元素(div、span、input等),它将始终工作。或者该指令可以是一个新元素,而不是一个属性。对于“list.isSelected”来说,“list[].isSelected”或“list[*].isSelected”如何表示它是一个神奇的值?据我所知,在这个示例中也不会触发不确定状态(在Opera中测试)。甚至有可能从CSS触发吗?我不知道如何触发。如果代码被更新,我会很感激,因为我认为不确定状态比CSS样式更好,因为它使用本机不确定状态。我从来不知道不确定(stackoverflow不是很好!).这是一个在复选框上设置中间属性的plunker:在“主”菜单上设置不确定属性"复选框让我想把它放在一个指令中。另外,由于服务是单例的,我认为使用这种方法会很困难,特别是如果应用程序中有多个三态复选框的实例……服务需要以某种方式跟踪它们。出于逻辑原因,我选择了带有自己控制器的指令.在你的Opera示例中,我没有看到任何不确定状态被触发。如果是horse XOR,我希望是“Select all”处于不确定状态。但非常感谢您的贡献。我现在在我的答案中添加了一个Plunker链接。如果您没有看到差异,请告诉我。您可以使用标准ng模型和ng checked指令执行Plunker中的操作。。对于列表项
是对象的情况(将复选框键映射为true/false)。这不支持不确定值。您的意思是更改子项的值并取消选中“全选”复选框?这可以通过在单击子项复选框时调用函数来完成,该函数将取消选中父项…可以吗?
app.directive('checkboxAll', function () {
return function(scope, iElement, iAttrs) {
var parts = iAttrs.checkboxAll.split('.');
iElement.attr('type','checkbox');
iElement.bind('change', function (evt) {
scope.$apply(function () {
var setValue = iElement.prop('checked');
angular.forEach(scope.$eval(parts[0]), function (v) {
v[parts[1]] = setValue;
});
});
});
scope.$watch(parts[0], function (newVal) {
var hasTrue, hasFalse;
angular.forEach(newVal, function (v) {
if (v[parts[1]]) {
hasTrue = true;
} else {
hasFalse = true;
}
});
if (hasTrue && hasFalse) {
iElement.attr('checked', false);
iElement.addClass('greyed');
} else {
iElement.attr('checked', hasTrue);
iElement.removeClass('greyed');
}
}, true);
};
});
<tri-state-checkbox checkboxes="listelements"></tri-state-checkbox>
app.directive('triStateCheckbox', function() {
return {
replace: true,
restrict: 'E',
scope: { checkboxes: '=' },
template: '<div><input type="checkbox" ng-model="master" ng-change="masterChange()">'
+ '<div ng-repeat="cb in checkboxes">'
+ '<input type="checkbox" ng-model="cb.isSelected" ng-change="cbChange()">{{cb.desc}}'
+ '</div>'
+ '</div>',
controller: function($scope, $element) {
$scope.masterChange = function() {
if($scope.master) {
angular.forEach($scope.checkboxes, function(cb, index){
cb.isSelected = true;
});
} else {
angular.forEach($scope.checkboxes, function(cb, index){
cb.isSelected = false;
});
}
};
var masterCb = $element.children()[0];
$scope.cbChange = function() {
var allSet = true, allClear = true;
angular.forEach($scope.checkboxes, function(cb, index){
if(cb.isSelected) {
allClear = false;
} else {
allSet = false;
}
});
if(allSet) {
$scope.master = true;
masterCb.indeterminate = false;
}
else if(allClear) {
$scope.master = false;
masterCb.indeterminate = false;
}
else {
$scope.master = false;
masterCb.indeterminate = true;
}
};
$scope.cbChange(); // initialize
},
};
});
<tri-state-checkbox checkboxes="listelements" class="select-all-cb">
</tri-state-checkbox>select all
<div ng-repeat="item in listelements">
<input type="checkbox" ng-model="item.isSelected"> {{item.desc}}
</div>
<div ng-repeat="elem in list">
<input type="checkbox" ng-model="elem.isSelected" /> {{elem.desc}}
</div>
<ui-select-all items="list" prop="isSelected"></ui-select-all> Select all
var app = angular.module('angularjs-starter', []);
app.controller('MainCtrl', function($scope) {
$scope.listelements = [{
isSelected: true,
desc: "Donkey"
}, {
isSelected: false,
desc: "Horse"
}];
});
app.directive('triStateCheckbox', function() {
return {
replace: true,
restrict: 'E',
scope: {
checkboxes: '='
},
template: '<input type="checkbox" ng-model="master" ng-change="masterChange()">',
controller: function($scope, $element) {
$scope.masterChange = function() {
for(i=0;i<$scope.checkboxes.length; i++)
$scope.checkboxes[i].isSelected=$scope.master;
};
$scope.$watch('checkboxes', function() {
var set=0;
for (i=0;i<$scope.checkboxes.length;i++)
set += $scope.checkboxes[i].isSelected?1:0;
$element.prop('indeterminate', false);
$scope.master = (set === 0) ? false : true;
if (set > 0 && set < i) {
$scope.master = false;
$element.prop('indeterminate', true);
}
}, true);
}
};
});
<div>
<input type="checkbox" id="select-all" name="selectAll" value="" ng-click="checkAll($event)" />
<div >
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
<input type="checkbox" name="childCheckbox" value="" />
</div>
</div>
$scope.checkAll = function (source) {
checkboxes = document.getElementsByName('childCheckbox');
for (var i = 0, n = checkboxes.length; i < n; i++) {
checkboxes[i].checked = source.originalEvent.srcElement.checked;
}
<fieldset indeterminate-group>
<legend>Checkbox Group</legend>
<input type="checkbox" name="c0" indeterminate-cue> Todos <br>
<input type="checkbox" name="c1" ng-model="data.c1" ng-true-value="'Y'" ng-false-value="'F'" indeterminate-item> Item 1 <br>
<input type="checkbox" name="c2" ng-model="data.c2" ng-true-value="'Y'" ng-false-value="'F'" indeterminate-item> Item 2 <br>
<input type="checkbox" name="c3" ng-model="data.c3" ng-true-value="'Y'" ng-false-value="'F'" indeterminate-item> Item 3 <br>
</fieldset>
angular.module('app', [])
.directive('indeterminateGroup', function() {
function IndeterminateGroupController() {
this.items = [];
this.cueElement = null;
}
...
function setAllValues(value) {
if (this.inChangeEvent) return;
this.inChangeEvent = true;
try {
this.items.forEach(function(item) {
item.$setViewValue(value);
item.$render();
});
} finally {
this.inChangeEvent = false;
}
}
return {
restrict: "A",
controller: IndeterminateGroupController,
link: function(scope, element, attrs, ctrl) {
ctrl.inputChanged = function() {
var anyChecked = false;
var anyUnchecked = false;
this.items.forEach(function(item) {
var value = item.$viewValue;
if (value === true) {
anyChecked = true;
} else if (value === false) {
anyUnchecked = true;
}
});
if (this.cueElement) {
this.cueElement.prop('indeterminate', anyChecked && anyUnchecked);
this.cueElement.prop('checked', anyChecked && !anyUnchecked);
}
};
}
};
})
.directive('indeterminateCue', function() {
return {
restrict: "A",
require: '^^indeterminateGroup',
link: function(scope, element, attrs, indeterminateGroup) {
indeterminateGroup.addCueElement(element);
var inChangeEvent = false;
element.on('change', function(event) {
if (event.target.checked) {
indeterminateGroup.checkAll();
} else {
indeterminateGroup.uncheckAll();
}
});
}
};
})
.directive('indeterminateItem', function() {
return {
restrict: "A",
require: ['^^indeterminateGroup', 'ngModel'],
link: function(scope, element, attrs, ctrls) {
var indeterminateGroup = ctrls[0];
var ngModel = ctrls[1];
indeterminateGroup.addItem(ngModel);
ngModel.$viewChangeListeners.push(function() {
indeterminateGroup.inputChanged();
});
}
};
});
// Bring your own model