如何实现多组Checkbox对应的Progress Bar独立工作?
解决多组Checkbox独立控制对应Progress Bar的问题
我来帮你搞定这个问题~你的核心问题在于全局变量val被所有卡片共享,而且更新进度条的时候没有定位到当前Checkbox所在的卡片,导致所有进度条同步变化。咱们调整代码,让每组卡片的进度条完全独立运作:
问题分析
- 全局的
val变量:所有卡片共用同一个进度值,勾选任意卡片的Checkbox都会累加/累减这个全局值,导致所有进度条一起变 - 进度条更新范围错误:
$(".progress .progress-bar").each(...)会选中页面上所有进度条,而不是当前卡片的那一个 - 任务数量的初始化和更新没有绑定到对应卡片
修改后的完整代码
HTML部分(修正了一处class拼写错误)
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script> <link href="https://stackpath.bootstrapcdn.com/bootstrap/4.1.1/css/bootstrap.min.css" rel="stylesheet" /> <script src="https://stackpath.bootstrapcdn.com/bootstrap/4.1.1/js/bootstrap.min.js"></script> <div class="card"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <div class="progress"> <div class="progress-bar bg-primary" role="progressbar" style="" aria-valuenow="0" aria-valuemin="0" aria-valuemax="100"></div> </div> <p class="task-quantity"></p> </div> <div class="card"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <input type="checkbox" class="new-control-input"> <div class="progress"> <div class="progress-bar bg-primary" role="progressbar" style="" aria-valuenow="0" aria-valuemin="0" aria-valuemax="100"></div> </div> <p class="task-quantity"></p> </div>
JavaScript部分
// 初始化每个卡片的基础数据 $('.card').each(function() { const $card = $(this); const chkLength = $card.find('input[type="checkbox"]').length; const perCheckboxPercent = 100 / chkLength; // 把总数量、单选项百分比、当前进度存在卡片的data属性里 $card.data({ totalCheckboxes: chkLength, perCheckboxPercent: perCheckboxPercent, currentProgress: 0 }); // 初始化任务数量文本 $card.find('.task-quantity').text(`0/${chkLength}`); // 给每个Checkbox设置单选项对应的百分比值 $card.find('input[type="checkbox"]').val(perCheckboxPercent); }); // 监听Checkbox状态变化 $('.card .new-control-input').on('change', function() { const $checkbox = $(this); // 找到当前Checkbox所在的卡片 const $card = $checkbox.closest('.card'); // 从卡片data里取出当前进度和单选项百分比 let currentProgress = $card.data('currentProgress'); const perPercent = $card.data('perCheckboxPercent'); const total = $card.data('totalCheckboxes'); // 更新进度值 if ($checkbox.is(':checked')) { currentProgress += perPercent; } else { currentProgress -= perPercent; } // 确保进度值在0-100之间(避免浮点精度问题导致的异常) currentProgress = Math.max(0, Math.min(100, currentProgress)); // 把更新后的进度存回卡片data $card.data('currentProgress', currentProgress); // 更新当前卡片的进度条宽度 $card.find('.progress-bar').css('width', `${currentProgress}%`); // 更新任务数量文本:统计当前卡片已勾选的Checkbox数量 const checkedCount = $card.find('input[type="checkbox"]:checked').length; $card.find('.task-quantity').text(`${checkedCount}/${total}`); });
关键改动说明
- 用卡片的
data()存储独立数据:每个卡片的总Checkbox数、单选项百分比、当前进度都存在自己的data属性里,不再共用全局变量 - 限定操作范围:通过
closest('.card')找到当前Checkbox所属的卡片,所有后续操作(更新进度条、任务数量)都只针对这个卡片内的元素 - 优化进度计算:增加了进度值的边界处理,避免因为浮点运算导致进度超过100%或低于0%
- 修正任务数量统计:直接统计当前卡片已勾选的Checkbox数量,更准确直观
这样修改后,每个Card里的Checkbox就会独立控制自己的Progress Bar了,完全不会互相影响~
内容的提问来源于stack exchange,提问作者Owaiz Yusufi
相关产品推荐
相关产品推荐

