jQuery中Bootstrap Toggle无限循环问题求助
解决Bootstrap Toggle开关无限循环问题
问题根源
当AJAX请求失败需要回滚开关状态时,调用bootstrapToggle('on/off')会再次触发checkbox的change事件,导致updateStatus函数被反复调用,形成无限循环;同时原代码存在重复绑定事件、HTML元素重复ID的问题,进一步加剧了异常。
分步解决方案
1. 修复HTML重复ID问题
一个DOM元素只能拥有唯一ID,原代码中input的两个id属性冲突,先修正:
<form method="post" id="toggleForm_{{$detail['id']}}"> <input type="checkbox" id="sce_{{$detail['id']}}" data-onstyle="success" data-offstyle="danger" data-toggle="toggle" name="sce" data-on="Active" data-off="InActive" {{ $detail['status'] == 1 ? 'checked' : '' }}> <input type="hidden" class="statusForDetail" value="{{$detail['id']}}" page="sections-set-status" > </form>
2. 修改JavaScript代码解决循环与重复绑定
核心思路:
- 确保事件只绑定一次,避免多次调用
onToggle导致多事件触发 - 回滚状态时,使用不触发
change事件的方式刷新Toggle UI
修改后的完整代码:
// 抽离事件绑定逻辑,避免重复代码 function bindToggleChange(cbRef, id, page, sid) { cbRef.off('change').on('change', function() { const status_val = this.checked ? 1 : 0; updateStatus(status_val, id, page, sid, $(this)); }); } function onToggle() { var page = $(".statusForDetail").attr('page'); $(".statusForDetail").each((index, element) => { let id = $(element).val(); let sid = id; const toggleEl = $('#sce_' + sid); bindToggleChange(toggleEl, id, page, sid); }); } function updateStatus(status_val, id, page, sid, cbRef) { // 注意:移除硬编码的id=9,使用传入的id参数 // id = 9; $.ajax({ headers: { 'X-CSRF-TOKEN': $('meta[name="csrf-token"]').attr('content') }, type: "POST", url: "/admin/" + page, data: { status: status_val, id: id }, success: function(result) { if (result[0] == "Success!") { $("#updatedAt").fadeIn(0) .html(`<font color='green' font size='2px'> : ${result[0]}${result[1]}</font>`) .fadeOut(1500); } else { // 回滚状态:先解绑事件,避免触发循环 const targetChecked = status_val === 1 ? false : true; cbRef.prop('checked', targetChecked); // 用refresh刷新UI,不会触发change事件 cbRef.bootstrapToggle('refresh'); // 重新绑定事件 bindToggleChange(cbRef, id, page, sid); } }, error: function() { // 错误场景同样回滚状态 const targetChecked = status_val === 1 ? false : true; cbRef.prop('checked', targetChecked); cbRef.bootstrapToggle('refresh'); bindToggleChange(cbRef, id, page, sid); } }); }
关键修复点说明
- 使用
bootstrapToggle('refresh'):仅同步Toggle UI与checkbox的checked状态,不会触发change事件,彻底避免循环触发。 off('change').on('change'):确保每个开关只绑定一个change事件,防止多次调用onToggle导致重复触发AJAX。- 抽离
bindToggleChange函数:减少重复代码,保证事件绑定逻辑统一。
内容的提问来源于stack exchange,提问作者Orkhan Orkhan
相关产品推荐
相关产品推荐

