我有一个包含许多文本输入字段和复选框的表单。每当选中一个复选框时,应禁用所有文本输入字段和所有其他复选框(删除已检查的复选框)。取消选中此复选框后,应再次启用所有已禁用的字段。 这适用于以下代码(仅显示前3行):
<form id="myForm">
Checkbox 1: <input type="checkbox" name="checkbox1" id="checkboxOne" onclick="enableDisableAll();" />
<input type="text" id="id1" name="name1" /><br>
Checkbox 2: <input type="checkbox" name="checkbox2" id="checkboxTwo" onclick="enableDisableAll();" />
<input type="text" id="id2" name="name2" /><br>
Checkbox 3: <input type="checkbox" name="checkbox3" id="checkboxThree" onclick="enableDisableAll();" />
<input type="text" id="id3" name="name3" /><br>
</form>
function enableDisableAll() {
cb1 = document.getElementById('checkboxOne').checked;
cb2 = document.getElementById('checkboxTwo').checked;
cb3 = document.getElementById('checkboxThree').checked;
document.getElementById('checkboxOne').disabled = (cb2 || cb3);
document.getElementById('id1').disabled = (cb1 || cb2 || cb3);
document.getElementById('checkboxTwo').disabled = (cb1 || cb3);
document.getElementById('id2').disabled = (cb1 || cb2 || cb3);
document.getElementById('checkboxThree').disabled = (cb1 || cb2);
document.getElementById('id3').disabled = (cb1 || cb2 || cb3);
}
由于代码与许多复选框(cb1 || cb2 || cb3 || ....... cb(n))混淆,我想知道是否会有更优雅的可能性,例如:
function enableDisableAll(){
cb1 = document.getElementById('checkboxOne').checked;
cb2 = document.getElementById('checkboxTwo').checked;
cb3 = document.getElementById('checkboxThree').checked;
var cb_array = [];
cb_array.push("cb1");
cb_array.push("cb2");
var cb_array_imploded = cb_array.join(" || ");
document.getElementById('id1').disabled = (cb_array_imploded);
不幸的是,这不起作用。
有没有人为我的问题找到一个简单的解决方案?
答案 0 :(得分:1)
一种可能的方法如下:虽然请注意我修改了HTML,将<input type="checkbox">
元素包装在父<label>
元素中,并删除了不必要的<br />
元素以及HTML中突兀的内联事件处理程序:
// a named function bound to an element via
// via JavaScript; the 'event' argument
// is passed automatically from the
// EventTarget.addEventListener() method:
function disableIfChecked(event) {
// the event.target node is the node upon which
// the listened-for event was originally triggered:
let target = event.target;
// 'this' is also passed from the
// EventTarget.addEventListener() method; here
// retrieved all <input> elements within the
// <form> (the 'this'), convert that NodeList
// explicitly to an Array and then filter that
// Array using an Arrow function:
Array.from(this.querySelectorAll('input')).filter(
// we retain only those elements ('el') in the Array
// which are not equal to, and therefore are not, the
// changed element:
el => el !== target
// iterating over the filtered collection:
).forEach(
// each <input> element remaining in the collection
// will be disabled if the changed element is clicked,
// or enabled if the changed element is no longer clicked:
el => el.disabled = target.checked
);
}
document.querySelector('#myForm').addEventListener('change', disableIfChecked);
&#13;
/* Selecting the <label> element that follows
an <input> element: */
input+label::before {
/* Adding a line-feed character using the CSS
'content' property of the pseudo-element
to force each <label> to a new-line: */
content: '\A';
display: block;
}
&#13;
<form id="myForm">
<!-- the label element associates the text with the enclosed
input, so clicking the text focuses that input element: -->
<label>Checkbox 1: <input type="checkbox" name="checkbox1" id="checkboxOne" /></label>
<input type="text" id="id1" name="name1" />
<label>Checkbox 2: <input type="checkbox" name="checkbox2" id="checkboxTwo" /></label>
<input type="text" id="id2" name="name3" />
<label>Checkbox 3: <input type="checkbox" name="checkbox3" id="checkboxThree" /></label>
<input type="text" id="id3" name="name3" />
</form>
&#13;
JS Fiddles:commented,uncommented
为了支持不支持ES6的浏览器,以下是另一种做同样事情的方法:
// a named function bound to an element via
// via JavaScript; the 'event' argument
// is passed automatically from the
// EventTarget.addEventListener() method:
function disableIfChecked(event) {
// the event.target node is the node upon which
// the listened-for event was originally triggered:
let target = event.target;
// 'this' is also passed from the
// EventTarget.addEventListener() method; here
// retrieved all <input> elements within the
// <form> (the 'this'), convert that NodeList
// explicitly to an Array by treating the NodeList
// as an Array, using Function.prototype.call(),
// and Array.prototype.slice():
Array.prototype.slice.call(
this.querySelectorAll('input')
).filter(function(el) {
// we retain only those elements ('el') in the Array
// which are not equal to, and therefore are not, the
// changed element:
return el !== target;
// iterating over the filtered collection:
}).forEach(function(el) {
// each <input> element remaining in the collection
// will be disabled if the changed element is clicked,
// or enabled if the changed element is no longer clicked:
el.disabled = target.checked;
});
}
document.querySelector('#myForm').addEventListener('change', disableIfChecked);
&#13;
/* Selecting the <label> element that follows
an <input> element: */
input+label::before {
/* Adding a line-feed character using the CSS
'content' property of the pseudo-element
to force each <label> to a new-line: */
content: '\A';
display: block;
}
&#13;
<form id="myForm">
<!-- the label element associates the text with the enclosed
input, so clicking the text focuses that input element: -->
<label>Checkbox 1: <input type="checkbox" name="checkbox1" id="checkboxOne" /></label>
<input type="text" id="id1" name="name1" />
<label>Checkbox 2: <input type="checkbox" name="checkbox2" id="checkboxTwo" /></label>
<input type="text" id="id2" name="name3" />
<label>Checkbox 3: <input type="checkbox" name="checkbox3" id="checkboxThree" /></label>
<input type="text" id="id3" name="name3" />
</form>
&#13;
参考文献:
答案 1 :(得分:1)
选择所有表单元素并循环访问并检查id与点击的元素id相同。如果不禁用它。
function enableDisableAll(e) {
var own = e;
var form = document.getElementById("myForm");
var elements = form.elements;
for (var i = 0 ; i < elements.length ; i++) {
if(own !== elements[i] ){
if(own.checked == true){
elements[i].disabled = true;
}else{
elements[i].disabled = false;
}
}
}
}
function clearAll(){
document.getElementById("myForm").reset();
}
&#13;
<form id="myForm">
Checkbox 1: <input type="checkbox" name="checkbox1" id="checkboxOne" onclick="enableDisableAll(this);" />
<input type="text" id="id1" name="name1" /><br>
Checkbox 2: <input type="checkbox" name="checkbox2" id="checkboxTwo" onclick="enableDisableAll(this);" />
<input type="text" id="id2" name="name2" /><br>
Checkbox 3: <input type="checkbox" name="checkbox3" id="checkboxThree" onclick="enableDisableAll(this);" />
<input type="text" id="id3" name="name3" /><br>
</form>
<input class="field button2" type="button" value="Clear form" size="10" onclick="clearAll(this);">
&#13;
更新:清除所有表单字段
document.getElementById("myForm").reset();
答案 2 :(得分:0)
通常最好在复选框,单选按钮或选择等输入上使用onchange
而不是onclick
事件。
为了根据需要为尽可能多的输入提供通用解决方案,最好使用document.querySelectorAll
来获取表单中的所有输入。然后,您可以迭代所有输入并将其disabled
属性设置为目标checked
的{{1}}值。
下面的解决方案片段:
checkbox
&#13;
function enableDisableAll(event) {
var allInputs = document.querySelectorAll('#myForm input');
allInputs.forEach(function(input) {
if (input !== event.target) {
input.disabled = event.target.checked;
}
});
}
&#13;
这里的一个重要细节是,如果要将典型的事件处理函数直接分配给HTML属性,函数必须具有明确命名为 event 的单个参数。但是,建议使用javascript而不是HTML来分配事件处理程序。其语法为<form id="myForm">
Checkbox 1: <input type="checkbox" name="checkbox1" id="checkboxOne" onchange="enableDisableAll(event);" />
<input type="text" id="id1" name="name1" /><br> Checkbox 2: <input type="checkbox" name="checkbox2" id="checkboxTwo" onchange="enableDisableAll(event);" />
<input type="text" id="id2" name="name2" /><br> Checkbox 3: <input type="checkbox" name="checkbox3" id="checkboxThree" onchange="enableDisableAll(event);" />
<input type="text" id="id3" name="name3" /><br>
</form>
您可能希望通过迭代所有复选框的选择器来向每个复选框添加侦听器。