使用支持HTML5的新浏览器时(例如FireFox 4);
表单字段具有属性required='required'
;
表格字段为空/空白;
并单击提交按钮;
浏览器检测到“required”字段为空并且不提交表单;而是浏览器显示提示,要求用户在字段中键入文本。
现在,我有一个复选框,而不是单个文本字段,其中至少有一个复选框应由用户检查/选择。
如何在此组复选框上使用HTML5 required
属性?
(由于只需要检查其中一个复选框,我无法在每个复选框上添加required
属性)
PS。如果重要,我正在使用simple_form。
更新
HTML 5 multiple
attribute可以在这里提供帮助吗?是否有人在使用它之前做了类似于我的问题的事情?
出现 HTML5规范不支持此功能: ISSUE-111: What does input.@required mean for @type = checkbox?
(问题状态:问题已被标记为已关闭且不带偏见。) 并here is the explanation。
这是一个老问题,但是想澄清一下,问题的初衷是能够在不使用Javascript的情况下完成上述操作 - 即使用HTML5方式执行此操作。回想起来,我应该让“没有Javascript”更加明显。
答案 0 :(得分:65)
不幸的是,HTML5并没有提供开箱即用的方法。
但是,使用jQuery,您可以轻松控制复选框组是否至少有一个已检查元素。
考虑以下DOM片段:
<div class="checkbox-group required">
<input type="checkbox" name="checkbox_name[]">
<input type="checkbox" name="checkbox_name[]">
<input type="checkbox" name="checkbox_name[]">
<input type="checkbox" name="checkbox_name[]">
</div>
您可以使用以下表达式:
$('div.checkbox-group.required :checkbox:checked').length > 0
如果至少检查一个元素,则返回true
。
基于此,您可以实施验证检查。
答案 1 :(得分:13)
这是一个简单的伎俩。这是jQuery代码,如果选中任何一个属性,可以通过更改required
属性来利用html5验证。以下是您的html代码(请确保为组中的所有元素添加所需的内容。)
<input type="checkbox" name="option[]" id="option-1" value="option1" required/> Option 1
<input type="checkbox" name="option[]" id="option-2" value="option2" required/> Option 2
<input type="checkbox" name="option[]" id="option-3" value="option3" required/> Option 3
<input type="checkbox" name="option[]" id="option-4" value="option4" required/> Option 4
<input type="checkbox" name="option[]" id="option-5" value="option5" required/> Option 5
以下是jQuery脚本,如果选择了任何一个脚本,它将禁用进一步的验证检查。选择使用名称元素。
$cbx_group = $("input:checkbox[name='option[]']");
$cbx_group = $("input:checkbox[id^='option-']"); // name is not always helpful ;)
$cbx_group.prop('required', true);
if($cbx_group.is(":checked")){
$cbx_group.prop('required', false);
}
小问题:由于您使用的是html5验证,请确保在验证之前,即在表单提交之前执行此操作。
// but this might not work as expected
$('form').submit(function(){
// code goes here
});
// So, better USE THIS INSTEAD:
$('button[type="submit"]').on('click', function() {
// skipping validation part mentioned above
});
答案 2 :(得分:11)
我想没有标准的HTML5方法可以做到这一点,但是如果你不介意使用jQuery库,我已经能够使用webshims'“{{3来实现”复选框组“验证“验证功能:
如果一个复选框的类别'group-required'至少有一个 表单/文档中具有相同名称的复选框必须是 检查。
这是一个如何使用它的例子:
<input name="checkbox-group" type="checkbox" class="group-required" id="checkbox-group-id" />
<input name="checkbox-group" type="checkbox" />
<input name="checkbox-group" type="checkbox" />
<input name="checkbox-group" type="checkbox" />
<input name="checkbox-group" type="checkbox" />
我主要使用webshims来填充HTML5功能,但它也有一些很棒的可选扩展功能。
它甚至允许您编写自己的自定义有效性规则。例如,我需要创建一个不基于输入名称的复选框组,所以我写了docs for group-required ...
答案 3 :(得分:7)
HTML5不直接支持只需要在复选框组中选中一个/至少一个复选框。这是我使用Javascript的解决方案:
HTML
<input class='acb' type='checkbox' name='acheckbox[]' value='1' onclick='deRequire("acb")' required> One
<input class='acb' type='checkbox' name='acheckbox[]' value='2' onclick='deRequire("acb")' required> Two
JAVASCRIPT
function deRequireCb(elClass) {
el=document.getElementsByClassName(elClass);
var atLeastOneChecked=false;//at least one cb is checked
for (i=0; i<el.length; i++) {
if (el[i].checked === true) {
atLeastOneChecked=true;
}
}
if (atLeastOneChecked === true) {
for (i=0; i<el.length; i++) {
el[i].required = false;
}
} else {
for (i=0; i<el.length; i++) {
el[i].required = true;
}
}
}
javascript将确保至少选中一个复选框,然后取消整个复选框组。如果选中的一个复选框变为未选中状态,那么它将再次需要所有复选框!
答案 4 :(得分:3)
我遇到了同样的问题,我的解决方案是:
HTML:
<form id="processForm.php" action="post">
<div class="input check_boxes required wish_payment_type">
<div class="wish_payment_type">
<span class="checkbox payment-radio">
<label for="wish_payment_type_1">
<input class="check_boxes required" id="wish_payment_type_1" name="wish[payment_type][]" type="checkbox" value="1">Foo
</label>
</span>
<span class="checkbox payment-radio">
<label for="wish_payment_type_2">
<input class="check_boxes required" id="wish_payment_type_2" name="wish[payment_type][]" type="checkbox" value="2">Bar
</label>
</span>
<span class="checkbox payment-radio">
<label for="wish_payment_type_3">
<input class="check_boxes required" id="wish_payment_type_3" name="wish[payment_type][]" type="checkbox" value="3">Buzz
</label>
<input id='submit' type="submit" value="Submit">
</div>
</form>
JS:
var verifyPaymentType = function () {
var checkboxes = $('.wish_payment_type .checkbox');
var inputs = checkboxes.find('input');
var first = inputs.first()[0];
inputs.on('change', function () {
this.setCustomValidity('');
});
first.setCustomValidity(checkboxes.find('input:checked').length === 0 ? 'Choose one' : '');
}
$('#submit').click(verifyPaymentType);
答案 5 :(得分:2)
受到@thegauraw和@Brian Woodward的答案的启发,我在这里为JQuery用户提供了一些帮助,包括自定义验证错误消息:
$cbx_group = $("input:checkbox[name^='group']");
$cbx_group.on("click", function() {
if ($cbx_group.is(":checked")) {
// checkboxes become unrequired as long as one is checked
$cbx_group.prop("required", false).each(function() {
this.setCustomValidity("");
});
} else {
// require checkboxes and set custom validation error message
$cbx_group.prop("required", true).each(function() {
this.setCustomValidity("Please select at least one checkbox.");
});
}
});
请注意,我的表单默认选中了一些复选框。
也许你们中的一些JavaScript / JQuery向导可以进一步收紧它们?
答案 6 :(得分:1)
嗨,只需使用复选框组旁边的文本框。当点击任何复选框时,将值放入该文本框。使该文本框成为必需和只读。
答案 7 :(得分:1)
我们也可以使用html5轻松完成此操作,只需要添加一些jquery代码
<强> Demo 强>
<强> HTML 强>
<form>
<div class="form-group options">
<input type="checkbox" name="type[]" value="A" required /> A
<input type="checkbox" name="type[]" value="B" required /> B
<input type="checkbox" name="type[]" value="C" required /> C
<input type="submit">
</div>
</form>
<强> Jquery的强>
$(function(){
var requiredCheckboxes = $('.options :checkbox[required]');
requiredCheckboxes.change(function(){
if(requiredCheckboxes.is(':checked')) {
requiredCheckboxes.removeAttr('required');
} else {
requiredCheckboxes.attr('required', 'required');
}
});
});
答案 8 :(得分:1)
为此您不需要 jQuery。这是在复选框的父容器 (checkbox-group-required
)、复选框元素的 .checked
属性和 Array#some
上使用事件侦听器的 vanilla JS 概念证明。
const validate = el => {
const checkboxes = el.querySelectorAll('input[type="checkbox"]');
return [...checkboxes].some(e => e.checked);
};
const formEl = document.querySelector("form");
const statusEl = formEl.querySelector(".status-message");
const checkboxGroupEl = formEl.querySelector(".checkbox-group-required");
checkboxGroupEl.addEventListener("click", e => {
statusEl.textContent = validate(checkboxGroupEl) ? "valid" : "invalid";
});
formEl.addEventListener("submit", e => {
e.preventDefault();
if (validate(checkboxGroupEl)) {
statusEl.textContent = "Form submitted!";
// Send data from e.target to your backend
}
else {
statusEl.textContent = "Error: select at least one checkbox";
}
});
<form>
<div class="checkbox-group-required">
<input type="checkbox">
<input type="checkbox">
<input type="checkbox">
<input type="checkbox">
</div>
<input type="submit" />
<div class="status-message"></div>
</form>
如果您有多个组要验证,请在每个组上添加一个循环,可选择添加错误消息或 CSS 以指示哪个组未通过验证:
const validate = el => {
const checkboxes = el.querySelectorAll('input[type="checkbox"]');
return [...checkboxes].some(e => e.checked);
};
const allValid = els => [...els].every(validate);
const formEl = document.querySelector("form");
const statusEl = formEl.querySelector(".status-message");
const checkboxGroupEls = formEl.querySelectorAll(".checkbox-group-required");
checkboxGroupEls.forEach(el =>
el.addEventListener("click", e => {
statusEl.textContent = allValid(checkboxGroupEls) ? "valid" : "invalid";
})
);
formEl.addEventListener("submit", e => {
e.preventDefault();
if (allValid(checkboxGroupEls)) {
statusEl.textContent = "Form submitted!";
}
else {
statusEl.textContent = "Error: select at least one checkbox from each group";
}
});
<form>
<div class="checkbox-group-required">
<label>
Group 1:
<input type="checkbox">
<input type="checkbox">
<input type="checkbox">
<input type="checkbox">
</label>
</div>
<div class="checkbox-group-required">
<label>
Group 2:
<input type="checkbox">
<input type="checkbox">
<input type="checkbox">
<input type="checkbox">
</label>
</div>
<input type="submit" />
<div class="status-message"></div>
</form>
答案 9 :(得分:0)
我在一组复选框中添加了一个不可见的收音机。 当至少一个选项被选中时,收音机也被设置为选中。 当所有选项都被取消时,收音机也被设置为取消。 因此,该表单使用单选提示“请检查至少一个选项”
display: none
,因为无线电无法聚焦。HTML
<form>
<div class="checkboxs-wrapper">
<input id="radio-for-checkboxes" type="radio" name="radio-for-required-checkboxes" required/>
<input type="checkbox" name="option[]" value="option1"/>
<input type="checkbox" name="option[]" value="option2"/>
<input type="checkbox" name="option[]" value="option3"/>
</div>
<input type="submit" value="submit"/>
</form>
JavaScript
var inputs = document.querySelectorAll('[name="option[]"]')
var radioForCheckboxes = document.getElementById('radio-for-checkboxes')
function checkCheckboxes () {
var isAtLeastOneServiceSelected = false;
for(var i = inputs.length-1; i >= 0; --i) {
if (inputs[i].checked) isAtLeastOneCheckboxSelected = true;
}
radioForCheckboxes.checked = isAtLeastOneCheckboxSelected
}
for(var i = inputs.length-1; i >= 0; --i) {
inputs[i].addEventListener('change', checkCheckboxes)
}
CSS
.checkboxs-wrapper {
position: relative;
}
.checkboxs-wrapper input[name="radio-for-required-checkboxes"] {
position: absolute;
margin: 0;
top: 0;
left: 0;
width: 100%;
height: 100%;
-webkit-appearance: none;
pointer-events: none;
border: none;
background: none;
}
答案 10 :(得分:0)
我意识到这里有很多解决方案,但是我发现它们都无法满足我的所有要求:
name
以便通过其API提交Github问题,并且正在使用名称label[]
在许多表单字段中分配标签(两个复选框列表和一些选择和文本框)-当然我可以做到这一点,而无需它们共享相同的名称,但是我决定尝试一下,并且有效。对此的唯一要求是jQuery。您可以将其与@ewall的出色解决方案结合使用,以添加自定义验证错误消息。
/* required checkboxes */
(function ($) {
$(function () {
var $requiredCheckboxes = $("input[type='checkbox'][required]");
/* init all checkbox lists */
$requiredCheckboxes.each(function (i, el) {
//this could easily be changed to suit different parent containers
var $checkboxList = $(this).closest("div, span, p, ul, td");
if (!$checkboxList.hasClass("requiredCheckboxList"))
$checkboxList.addClass("requiredCheckboxList");
});
var $requiredCheckboxLists = $(".requiredCheckboxList");
$requiredCheckboxLists.each(function (i, el) {
var $checkboxList = $(this);
$checkboxList.on("change", "input[type='checkbox']", function (e) {
updateCheckboxesRequired($(this).parents(".requiredCheckboxList"));
});
updateCheckboxesRequired($checkboxList);
});
function updateCheckboxesRequired($checkboxList) {
var $chk = $checkboxList.find("input[type='checkbox']").eq(0),
cblName = $chk.attr("name"),
cblNameAttr = "[name='" + cblName + "']",
$checkboxes = $checkboxList.find("input[type='checkbox']" + cblNameAttr);
if ($checkboxList.find(cblNameAttr + ":checked").length > 0) {
$checkboxes.prop("required", false);
} else {
$checkboxes.prop("required", true);
}
}
});
})(jQuery);
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
<form method="post" action="post.php">
<div>
Type of report:
</div>
<div>
<input type="checkbox" id="chkTypeOfReportError" name="label[]" value="Error" required>
<label for="chkTypeOfReportError">Error</label>
<input type="checkbox" id="chkTypeOfReportQuestion" name="label[]" value="Question" required>
<label for="chkTypeOfReportQuestion">Question</label>
<input type="checkbox" id="chkTypeOfReportFeatureRequest" name="label[]" value="Feature Request" required>
<label for="chkTypeOfReportFeatureRequest">Feature Request</label>
</div>
<div>
Priority
</div>
<div>
<input type="checkbox" id="chkTypeOfContributionBlog" name="label[]" value="Priority: High" required>
<label for="chkPriorityHigh">High</label>
<input type="checkbox" id="chkTypeOfContributionBlog" name="label[]" value="Priority: Medium" required>
<label for="chkPriorityMedium">Medium</label>
<input type="checkbox" id="chkTypeOfContributionLow" name="label[]" value="Priority: Low" required>
<label for="chkPriorityMedium">Low</label>
</div>
<div>
<input type="submit" />
</div>
</form>
答案 11 :(得分:0)
验证是否至少选中了一个复选框的非常简单的方法:
function isAtLeastOneChecked(name) {
let checkboxes = Array.from(document.getElementsByName(name));
return checkboxes.some(e => e.checked);
}
然后你可以实现任何你想要显示错误的逻辑。
答案 12 :(得分:-1)
这是使用Jquery的另一个简单技巧!!
的 HTML 强>
<form id="hobbieform">
<div>
<input type="checkbox" name="hobbies[]">Coding
<input type="checkbox" name="hobbies[]">Gaming
<input type="checkbox" name="hobbies[]">Driving
</div>
</form>
的 JQuery的强>
$('#hobbieform').on("submit", function (e) {
var arr = $(this).serialize().toString();
if(arr.indexOf("hobbies") < 0){
e.preventDefault();
alert("You must select at least one hobbie");
}
});
这就是全部...这是有效的,因为如果没有选中任何复选框,则关于复选框组(包括其名称)的任何内容都不会发布到服务器
答案 13 :(得分:-2)
尝试:
self.request.get('sports_played', allow_multiple=True)
或
self.request.POST.getall('sports_played')
更具体地说:
从复选框数组读取数据时,请确保数组具有:
len>0
在这种情况下:
len(self.request.get('array', allow_multiple=True)) > 0