I want my checkboxes to be linked: when I click on the level 2 checkbocks, I want all checkbockses be affected from starting from level 3. So far, I could come up only with this (I clicked on the level 2 checkbox): example
My template lookes like this:
<div id="checkbox-list" class="scrollable-list">
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="_"><label for="_">Level 1</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="_"><label for="_">Level
2</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="71" id="71"><label
for="_">Level 3</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="71:0" id="71:0"><label
for="71:0">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="71:1" id="71:1"><label
for="71:1">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="71:2" id="71:2"><label
for="71:2">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="71:3" id="71:3"><label
for="71:3">Level 4</label></li>
</ul>
</li>
<li class="checkbox-inner-element"><input type="checkbox" value="94" id="94"><label
for="_">Level 3</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="94:0" id="94:0"><label
for="94:0">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="94:1" id="94:1"><label
for="94:1">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="94:2" id="94:2"><label
for="94:2">Level 4</label></li>
</ul>
</li>
</ul>
</li>
</ul>
</li>
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="_"><label for="_">Level 2</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_"
id="_"><label for="_">Level 3</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_"
id="_"><label for="_">Level 4</label></li>
</ul>
</li>
</ul>
</li>
</ul>
</div>
I add event listeners to every checkbox I create with my script. My current JS code lookes like this:
checkbox.addEventListener('change', function () {
var flag = this.checked
var nestedCheckboxes = this.parentElement.querySelector('.checkbox-inner-element').querySelectorAll('ul li input[type="checkbox"]');
nestedCheckboxes.forEach(function (checkbox) {
checkbox.checked = flag;
checkbox.dispatchEvent(new Event('change'));
});
})
I think the problem could be in that I have both <li>
and <ul>
tags on the same level, but I couldn't come up with the solution yet.
I would use query selectors to find all of the descendant checkboxes. This solution uses the input id, which I don't believe are allowed to start with a number.
document.querySelectorAll("input[type=checkbox]").forEach(checkbox =>
checkbox.addEventListener('change', function(e) {
const activeCB = e.target;
const flag = activeCB.checked;
const descendants = activeCB.closest("li").querySelectorAll(`input[type=checkbox]`);
descendants.forEach(d => d.checked = flag);
})
)
<div id="checkbox-list" class="scrollable-list">
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="L1a"><label for="_">Level 1</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="L2a"><label for="_">Level
2</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="71" id="L3a"><label for="_">Level 3</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="71:0" id="L4a"><label for="71:0">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="71:1" id="L4b"><label for="71:1">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="71:2" id="L4c"><label for="71:2">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="71:3" id="L4d"><label for="71:3">Level 4</label></li>
</ul>
</li>
<li class="checkbox-inner-element"><input type="checkbox" value="94" id="L3b"><label for="_">Level 3</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="94:0" id="L4e"><label for="94:0">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="94:1" id="L4f"><label for="94:1">Level 4</label></li>
<li class="checkbox-inner-element"><input type="checkbox" value="94:2" id="L4g"><label for="94:2">Level 4</label></li>
</ul>
</li>
</ul>
</li>
</ul>
</li>
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="L1b"><label for="_">Level 2</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="L2b"><label for="_">Level 3</label>
<ul class="checkbox-outer-element">
<li class="checkbox-inner-element"><input type="checkbox" value="_" id="L3c"><label for="_">Level 4</label></li>
</ul>
</li>
</ul>
</li>
</ul>
</div>