javascript - Javascript - 选择所有复选框并更改多个类功能
问题描述
我遇到了一个我不确定正确答案的问题。我有一个 javascript 代码,我想在其中选中页面上的每个复选框,并将.absent CSS 类替换为.present对于每个具有类.tile和.absent的元素。我所看到的是这可行,但用户必须重复调用该函数才能选择页面上的每个适用元素。为什么它不是第一次选择每个元素?
如果第一段没有意义,我的目标是使功能按如下方式工作:当用户单击“标记所有存在”时,页面上的每个图块都应亮起紫色。
密码: https ://codepen.io/dansbyt/pen/yLVzJog
Javascript:
function selectall(arg){
if (arg == 'selectmulti') {var check = document.getElementsByClassName("clickable");}
if (arg == 'attendance') {
var check = document.getElementsByTagName('input');
var tile = document.getElementsByClassName('tile absent');
for(i=0; i<tile.length; i++){
tile[i].classList.add('present');
tile[i].classList.remove('absent');
}
}
for(i=0; i<check.length; i++){
if(check[i].type=='checkbox'){
check[i].checked=true;
}
}
}
function deselectall(arg){
if (arg == 'attendance') {var uncheck = document.getElementsByTagName('input');}
if (arg == 'selectmulti') {var uncheck = document.getElementsByClassName("clickable");}
for(i=0; i<uncheck.length; i++){
if(uncheck[i].type=='checkbox'){
uncheck[i].checked=false;
}
}
}
HTML:
<div id='grid'>
<input type='checkbox' id='1' value='1' disabled>
<label for='1'>
<div class='tile absent'>
<img class='tile_pic' src='../resources/pics/default.png'>
<div class='tile_title'>John Doe</div>
</div>
</label>
<input type='checkbox' id='2' value='2' disabled>
<label for='2'>
<div class='tile absent'>
<img class='tile_pic' src='../resources/pics/1/22.jpg'>
<div class='tile_title'>Kennedy Adam</div>
</div>
</label>
<input type='checkbox' class='clickable' id='3' value='3' disabled>
<label for='3'>
<div class='tile present'>
<img class='tile_pic' src='../resources/pics/1/19.jpg'>
<div class='tile_title'>Sawyer Tom</div>
</div>
</label>
<input type='checkbox' id='4' value='4' disabled>
<label for='4'>
<div class='tile absent'>
<img class='tile_pic' src='../resources/pics/1/22.jpg'>
<div class='tile_title'>Linny Baker</div>
</div>
</label>
<input type='checkbox' class='clickable' id='5' value='5' disabled>
<label for='5'>
<div class='tile present'>
<img class='tile_pic' src='../resources/pics/1/19.jpg'>
<div class='tile_title'>Patrick MeLoy</div>
</div>
</label>
<input type='checkbox' id='6' value='6' disabled>
<label for='6'>
<div class='tile absent'>
<img class='tile_pic' src='../resources/pics/default.png'>
<div class='tile_title'>Cyrus Everdeen</div>
</div>
</label>
<input type='checkbox' id='7' value='7' disabled>
<label for='7'>
<div class='tile absent'>
<img class='tile_pic' src='../resources/pics/1/22.jpg'>
<div class='tile_title'>Samuel Adams</div>
</div>
</label>
<input type='checkbox' class='clickable' id='8' value='8' disabled>
<label for='8'>
<div class='tile present'>
<img class='tile_pic' src='../resources/pics/1/19.jpg'>
<div class='tile_title'>Robert Paine</div>
</div>
</label>
<input type='checkbox' id='9' value='9' disabled>
<label for='9'>
<div class='tile absent'>
<img class='tile_pic' src='../resources/pics/1/22.jpg'>
<div class='tile_title'>Thomas Preston</div>
</div>
</label>
<input type='checkbox' class='clickable' id='10' value='10' disabled>
<label for='10'>
<div class='tile present'>
<img class='tile_pic' src='../resources/pics/1/19.jpg'>
<div class='tile_title'>Trae Smith</div>
</div>
</label>
</div>
<br><br>
<div class="attendance">
<ul>
<ul class="left">
<li> <a class="deselectall" onclick="deselectall('attendance')"> Mark All Absent </a> </li>
<li> <a class="selectall" onclick="selectall('attendance')"> Mark All Present </a> </li>
</ul>
</div>
CSS:
body {margin: 120px 25px 55px 25px}
#grid {
max-width: 1880px;
margin: 0 auto;
display: grid;
grid-gap: 20px;}
.tile {
width: 125px; height: 165px;
font-size: 0.9rem;
background-color: white;
border-radius: 4%;
overflow: hidden;
text-align: center;
box-shadow: 3px 4px #CECECE}
.tile img{max-width: 100%; max-height: 100%; display: block;}
.tile:hover:not(.absent) {background-color: #BFB3E6; box-shadow: 3px 4px #9E999E; cursor: grab; transform: scale(1.05);}
.absent {filter: grayscale(100%); color: gray;}
.tile_pic{
width: 125px;
height: 125px;
object-fit: cover;}
.tile_title {
margin-top: 10px;
font-family: 'Rubik', sans-serif;}
#grid input[type=checkbox] {display: none;}
#grid input:checked + label .tile{background-color: #9885D6; box-shadow: 3px 4px #9E999E}
@media (min-width: 430px) {#grid { grid-template-columns: repeat(5, 1fr); }}
@media (min-width: 660px) {#grid { grid-template-columns: repeat(6, 1fr); }}
@media (min-width: 890px) {#grid { grid-template-columns: repeat(7, 1fr); }}
@media (min-width: 1120px) {#grid { grid-template-columns: repeat(8, 1fr); }}
@media (min-width: 1350px) {#grid { grid-template-columns: repeat(9, 1fr); }}
@media (min-width: 1580px) {#grid { grid-template-columns: repeat(10, 1fr); }}
解决方案
随着循环的每次迭代,getElementsByClassName
结果越来越小,因为您修改的每个元素都被排除在外。
getElementsByClassName 返回对象被视为“实时集合”,因此对 DOM 的任何更改都可能实时影响此函数的结果。
将其更改为:
document.getElementsByClassName('tile absent')
对此:
document.querySelectorAll('.tile.absent')
为了让它按预期工作(一个初始查询来获取所有元素,然后修改不会影响集合)。
MDN有一个关于这个看似奇怪的功能的有用信息简介:
警告:这是一个实时的 HTMLCollection。DOM 中的更改将在更改发生时反映在数组中。如果此数组选择的元素不再符合选择器的条件,它将自动被删除。出于迭代目的,请注意这一点。
推荐阅读
- javascript - 来自外部文件的 NodeJS ExpressJS 路由不起作用抛出 404 错误
- python - 使用全局语句从类中传递python列表
- angular - Angular - 添加用户(POST)
- regex - 不能使非贪婪匹配工作
- optimization - 带约束的凸多边形中直线长度的最大总和
- angular - 为什么 JHipster JDL 只为角度/打字稿代码的枚举表达式生成字符串值?
- javascript - nodejs 承诺更好的方法来处理承诺实现中发生的错误?
- javascript - 使用 AngularJS 中的复选框按多个条件过滤数据
- jupyter-notebook - 信任 Jupyter 不受信任的笔记本
- swift - 检测命令行工具何时退出