jQuery使用html()替换动态DOM后事件与操作失效问题
问题产生原因
两个异常分别对应两个独立的前端逻辑问题:
- 类添加逻辑不生效:代码注释标注
thisObj = '.process-attendance',说明thisObj只是字符串类型的选择器,不是jQuery实例。直接对字符串调用.closest()、.find()这类jQuery方法会直接抛出JS错误,后续所有DOM操作代码都会中断执行,根本没有运行到addClass的步骤,打开浏览器控制台可以看到明确的xxx.closest is not a function报错。 - 动态元素点击事件不触发:
$(".show-emp").click()属于静态事件绑定,只会给页面初始加载时已经存在的.show-emp元素绑定事件。Ajax替换tbody内容后,新插入的.show-emp是动态生成的DOM节点,初始化阶段不存在,自然没有绑定对应的点击回调。
修复方法
1. 修正jQuery对象调用逻辑
不要直接用字符串选择器调用jQuery方法,先将其包装为合法的jQuery实例,再执行后续DOM操作。如果当前Ajax是点击.process-attendance按钮触发的,建议在点击事件回调最开始就保存当前按钮的jQuery引用,避免页面存在多个同class元素时选错目标。
修正后的success回调代码如下:
success:function(response){ // 包装为jQuery对象,若为点击触发可提前在事件外存好$(this)直接使用 const $thisObj = $('.process-attendance'); const element = response.data; const el_data = $(element).filter('.group-payroll').find('.body-component').html(); const $targetTable = $thisObj.closest('table'); $targetTable.find('tbody').html(el_data); // 之前中断的类添加逻辑可正常执行 $targetTable.find('thead').addClass('done-group'); $targetTable.find('tbody').addClass('done-group'); }
2. 改用事件委托绑定动态元素事件
把原来直接绑定在.show-emp上的点击事件,改为绑定到不会被Ajax替换的父级节点上,利用事件冒泡机制触发回调,不管内部DOM怎么动态替换都能正常响应。
// 删除原来的静态绑定代码,替换为事件委托写法 $(document).on('click', '.show-emp', function () { showEmployee($(this)); }); function showEmployee(el) { $(el).closest('tbody').find('.employee').toggle(); $(el).closest('tbody').find('.employee-head').toggle(); }
注意:事件委托的父级选择器越靠近动态元素性能越好,如果页面中
.group-payroll表格是初始加载就存在的,也可以把$(document)换成$('.group-payroll'),减少事件冒泡的层级。
内容的提问来源于stack exchange,提问作者Catto
相关产品推荐
相关产品推荐

