I have a form with 3 checkboxes. I'm trying to the value of whichever checkbox is clicked on. I'm able to get the value of a hardcoded checkbox index (checkbox[0] for example), but I can't get the value of checkbox[i] with vanilla JS.
document.addEventListener("DOMContentLoaded", function() { var checkboxes = document.getElementsByClassName('checkbox'); var listType = document.getElementById('ListType'); for (var i = 0; i < checkboxes.length; i++) { checkboxes[i].addEventListener('click', function() { var inputByIndex = checkboxes[0].value; //I can get the value of the first element, but I can't get the value of whichever checkbox is checked. checkbox[i] doesn't work. listType.classList.add(inputByIndex); var spanType = document.getElementById("type"); spanType.innerText = inputByIndex; }); } });
input { margin: 20px; } #ListType.basiclist { color: red; } #ListType.accordionlist { color: blue; } #ListType.internalonly { color: pink; }
<form id="ListTypes"> <label for "basicList"><input type="checkbox" id="basicList" class="checkbox" name="basicList" value="basiclist"/>Basic List</label> <label for "accordionList"><input type="checkbox" id="accordionList" class="checkbox" name="accordionList" value="accordionlist"/>Accordion List</label> <label for "internalOnly"><input type="checkbox" id="internalOnly" class="checkbox" name="internalOnly" value="internalonly" />Internal Use Only</label> </form> <div id="ListType"> List Type: <span id="type"></span> </div>
You can use event.currentTarget
to access the element on which event has occurred.
The currentTarget read-only property of the Event interface identifies the current target for the event, as the event traverses the DOM.
document.addEventListener("DOMContentLoaded", function() { var checkboxes = document.getElementsByClassName('checkbox'); var listType = document.getElementById('ListType'); for (var i = 0; i < checkboxes.length; i++) { checkboxes[i].addEventListener('click', function(event) { var inputByIndex = event.currentTarget.value; listType.classList.add(inputByIndex); var spanType = document.getElementById("type"); spanType.innerText = inputByIndex; }); } });
input { margin: 20px; } #ListType.basiclist { color: red; } #ListType.accordionlist { color: blue; } #ListType.internalonly { color: pink; }
<form id="ListTypes"> <label for "basicList"><input type="checkbox" id="basicList" class="checkbox" name="basicList" value="basiclist"/>Basic List</label> <label for "accordionList"><input type="checkbox" id="accordionList" class="checkbox" name="accordionList" value="accordionlist"/>Accordion List</label> <label for "internalOnly"><input type="checkbox" id="internalOnly" class="checkbox" name="internalOnly" value="internalonly" />Internal Use Only</label> </form> <div id="ListType"> List Type: <span id="type"></span> </div>
In the for
loop, use let
instead of var
to make it work:
document.addEventListener("DOMContentLoaded", function() { var checkboxes = document.getElementsByClassName('checkbox'); var listType = document.getElementById('ListType'); for (let i = 0; i < checkboxes.length; i++) { checkboxes[i].addEventListener('click', function() { var inputByIndex = checkboxes[i].value; //I can get the value of the first element, but I can't get the value of whichever checkbox is checked. checkbox[i] doesn't work. listType.classList.add(inputByIndex); var spanType = document.getElementById("type"); spanType.innerText = inputByIndex; }); } });
input { margin: 20px; } #ListType.basiclist { color: red; } #ListType.accordionlist { color: blue; } #ListType.internalonly { color: pink; }
<form id="ListTypes"> <label for "basicList"><input type="checkbox" id="basicList" class="checkbox" name="basicList" value="basiclist"/>Basic List</label> <label for "accordionList"><input type="checkbox" id="accordionList" class="checkbox" name="accordionList" value="accordionlist"/>Accordion List</label> <label for "internalOnly"><input type="checkbox" id="internalOnly" class="checkbox" name="internalOnly" value="internalonly" />Internal Use Only</label> </form> <div id="ListType"> List Type: <span id="type"></span> </div>
Delegate
You need to think of the CSS for more than one listType color or use a set of radio buttons
document.addEventListener("DOMContentLoaded", function() { document.getElementById('ListTypes').addEventListener("click", function(e) { const tgt = e.target; if (tgt.type && tgt.type === 'checkbox') { const values = [...tgt.form.querySelectorAll("[type=checkbox]:checked")].map(chk => chk.value); document.getElementById("type").textContent = values.join(", ") document.getElementById("ListType").classList.add(...values); } }); });
input { margin: 20px; } #ListType.basiclist { color: red; } #ListType.accordionlist { color: blue; } #ListType.internalonly { color: pink; }
<form id="ListTypes"> <label for "basicList"><input type="checkbox" id="basicList" class="checkbox" name="basicList" value="basiclist"/>Basic List</label> <label for "accordionList"><input type="checkbox" id="accordionList" class="checkbox" name="accordionList" value="accordionlist"/>Accordion List</label> <label for "internalOnly"><input type="checkbox" id="internalOnly" class="checkbox" name="internalOnly" value="internalonly" />Internal Use Only</label> </form> <div id="ListType"> List Type: <span id="type"></span> </div>
the checkboxes
list doesn't exist within the closure of the onclick
funcion. Instead use this.value
.
You just need to select them all using the method you would like (I used querySelectorAll & ) and do an iteration over them (I used forEach() ).
This is the most simple function you can ever find.
const checkboxes = document.querySelectorAll('input[type="checkbox"]'); checkboxes.forEach(singleCheckbox => { singleCheckbox.addEventListener('click', () => alert(singleCheckbox.id)) });
<label for="first">First<input type="checkbox" id="first"/></label> <label for="second">Second<input type="checkbox" id="second"/></label> <label for="third">Third<input type="checkbox" id="third"/></label>
Just to make clear what was actually the problem with your code...
At the time you click
handler will be fired the for
loop will end its work and thus, the value of i
will become exactly checkboxes.length
, and of course, there is no checkbox with such an index, because the last of them has index (checkboxes.length - 1)
. So the reason is that the code inside of the handler is executed after for
loop ends its work.
The solutions were already provided by other users.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.