WordPress Ajax无限滚动下文章脚本仅加载一次技术咨询
解决Divi博客Ajax无限滚动下每篇文章JS仅加载一次的问题
你遇到的是典型的动态内容加载后的JS绑定失效问题——初始页面加载时,脚本只绑定了当时存在的DOM元素,而Ajax滚动加载的新文章并没有触发这些脚本。下面是针对Divi主题的具体解决方案:
核心思路
- 把需要在每篇文章执行的脚本封装成可复用函数,避免重复代码
- 用事件委托处理交互类脚本,确保新元素能触发事件
- 在Ajax加载新内容完成后,重新调用脚本初始化新文章
步骤1:封装文章初始化脚本
把原本写在单篇文章里的JS逻辑抽成独立函数,既能在初始页面运行,也能在新内容加载后复用:
// 封装初始化每篇文章的函数 function initPostScripts($postContainer) { // 在这里写你需要在每篇文章执行的逻辑,比如: // 1. 初始化文章内的交互组件(轮播、标签页等) $postContainer.find('.custom-carousel').slick({ dots: true, autoplay: true }); // 2. 处理文章内的自定义交互逻辑 $postContainer.find('.expand-btn').on('click', function(e) { e.preventDefault(); $(this).closest('.collapsible-section').toggleClass('expanded'); }); }
步骤2:用事件委托处理交互事件
如果脚本涉及用户交互(点击、hover等),直接绑定到元素上会导致新加载的元素无法触发事件,改用事件委托绑定到父级(比如document):
jQuery(document).ready(function($) { // 事件委托:监听所有.post内的.expand-btn点击 $(document).on('click', '.post .expand-btn', function(e) { e.preventDefault(); $(this).closest('.collapsible-section').toggleClass('expanded'); }); });
步骤3:监听Ajax加载完成事件,初始化新文章
Divi的无限滚动有自定义事件et_ajax_load_more_complete,可以用来监听新内容加载完成的时机,然后初始化新文章:
jQuery(document).ready(function($) { // 初始化页面已有的文章 initPostScripts($('.post')); // 监听Divi Ajax加载更多完成的事件 $(document).on('et_ajax_load_more_complete', function(event, $newPosts) { // 初始化刚加载的新文章 initPostScripts($newPosts); }); // 备用方案:如果自定义事件不生效,监听全局Ajax成功事件 $(document).ajaxSuccess(function(event, xhr, settings) { // 判断是否是加载博客文章的请求 if (settings.data && settings.data.includes('action=et_load_more_posts')) { // 找到未初始化的新文章(加标记避免重复初始化) const $newUninitializedPosts = $('.post').not('.post-initialized'); $newUninitializedPosts.addClass('post-initialized'); initPostScripts($newUninitializedPosts); } }); });
步骤4:优化PHP模板(singles.php)
确保每篇文章的容器有统一类名(比如post),方便JS选择元素:
<?php while ( have_posts() ) : the_post(); ?> <article id="post-<?php the_ID(); ?>" <?php post_class('post post-initialized'); ?>> <!-- 文章内容区域 --> <?php if (et_get_option('divi_integration_single_top') <> '' && et_get_option('divi_integrate_singletop') == 'on') echo(et_get_option('divi_integration_single_top')); ?> <?php get_template_part( 'includes/entry', 'single' ); ?> <?php if (et_get_option('divi_integration_single_bottom') <> '' && et_get_option('divi_integrate_singlebottom') == 'on') echo(et_get_option('divi_integration_single_bottom')); ?> <?php if ( comments_open() || get_comments_number() ) : comments_template(); endif; ?> </article> <?php endwhile; ?>
注意事项
- 不要把JS脚本直接写在每篇文章的PHP模板里,这样会导致Ajax加载时重复注入脚本,建议把所有JS放在Divi主题的自定义JS区域(Divi → 主题选项 → 集成 → 添加代码到< body >)
- 确保脚本依赖的库(比如jQuery)已经加载,并且脚本在库之后执行
- 测试前记得清除浏览器缓存和Divi的缓存,避免旧代码干扰
内容的提问来源于stack exchange,提问作者Bryan Reas
相关产品推荐
相关产品推荐

