WooCommerce产品分类页点击分类切换显示全量产品需求及代码求助
嘿,我来帮你搞定这个WooCommerce分类无刷新加载产品的需求!要实现点击分类名称就替换当前页面的产品内容,咱们分三步来完成:修改分类导航结构、写前端AJAX交互逻辑、添加后台AJAX处理函数。
第一步:修改archive-product.php里的分类导航代码
先把你原来的分类输出改成可交互的链接结构,同时给产品列表加个容器方便后续替换:
<dl class="archive-cat"> <?php $args = array( 'taxonomy' => 'product_cat', 'orderby' => 'name', 'hierarchical' => 0, 'hide_empty' => 0, 'exclude' => 1 // 排除默认"未分类",可根据你的实际情况调整 ); $all_categories = get_terms($args); // 显示当前选中的分类/全部产品 if (is_product_category()) { $current_cat = get_queried_object(); echo '<span class="current-cat-label">' . esc_html($current_cat->name) . '</span>'; } else { echo '<span class="current-cat-label">全部产品</span>'; } // 输出分类列表 echo '<ul class="category-list">'; foreach ($all_categories as $category) { $active_class = (is_product_category($category->term_id)) ? 'active' : ''; echo '<li> <a href="' . get_term_link($category) . '" class="category-link ' . $active_class . '" data-category-id="' . $category->term_id . '"> ' . esc_html($category->name) . ' </a> </li>'; } // 加上"全部产品"选项 $all_active = (!is_product_category()) ? 'active' : ''; echo '<li> <a href="' . get_post_type_archive_link('product') . '" class="category-link ' . $all_active . '" data-category-id="0"> 全部产品 </a> </li>'; echo '</ul>'; ?> </dl> <!-- 给产品列表套个容器,方便AJAX替换内容 --> <div class="products-container"> <?php woocommerce_product_loop_start(); ?> <?php if (wc_get_loop_prop('total')) { while (have_posts()) { the_post(); wc_get_template_part('content', 'product'); } } ?> <?php woocommerce_product_loop_end(); ?> </div>
第二步:添加前端AJAX交互代码
把这段JS代码放到archive-product.php的底部,或者通过主题的functions.php用wp_enqueue_script加载(推荐后者,更规范):
<script> jQuery(document).ready(function($) { // 监听分类链接点击事件 $('.category-link').on('click', function(e) { e.preventDefault(); // 阻止默认页面跳转 var catId = $(this).data('category-id'); var $productContainer = $('.products-container'); var $currentLink = $(this); // 添加加载状态提示 $productContainer.addClass('loading').html('<div class="loading-tip">加载中...</div>'); // 切换分类选中状态 $('.category-link').removeClass('active'); $currentLink.addClass('active'); // 发送AJAX请求到后台 $.ajax({ url: '<?php echo admin_url('admin-ajax.php'); ?>', type: 'POST', data: { action: 'load_category_products', category_id: catId, security: '<?php echo wp_create_nonce('load_cat_products_nonce'); ?>' }, success: function(response) { if (response.success) { $productContainer.removeClass('loading').html(response.data); // 可选:更新页面标题和URL,优化用户体验 if (catId === 0) { document.title = '全部产品 | <?php echo get_bloginfo('name'); ?>'; window.history.pushState({}, '', '<?php echo get_post_type_archive_link('product'); ?>'); } else { var catName = $currentLink.text(); document.title = catName + ' | <?php echo get_bloginfo('name'); ?>'; window.history.pushState({}, '', $currentLink.attr('href')); } } else { $productContainer.removeClass('loading').html('<p>加载失败,请重试</p>'); } }, error: function() { $productContainer.removeClass('loading').html('<p>加载失败,请重试</p>'); } }); }); }); </script>
第三步:添加后台AJAX处理函数
把这段代码放到主题的functions.php文件里,用来处理AJAX请求并返回对应分类的产品HTML:
// 注册AJAX回调函数(登录/未登录用户都能访问) add_action('wp_ajax_load_category_products', 'load_category_products_callback'); add_action('wp_ajax_nopriv_load_category_products', 'load_category_products_callback'); function load_category_products_callback() { // 验证请求合法性,防止恶意请求 check_ajax_referer('load_cat_products_nonce', 'security'); $cat_id = isset($_POST['category_id']) ? intval($_POST['category_id']) : 0; // 构建产品查询参数 $args = array( 'post_type' => 'product', 'posts_per_page' => wc_get_default_products_per_row() * wc_get_default_product_rows_per_page(), 'post_status' => 'publish' ); // 如果是指定分类,添加分类查询条件 if ($cat_id !== 0) { $args['tax_query'] = array( array( 'taxonomy' => 'product_cat', 'field' => 'term_id', 'terms' => $cat_id ) ); } $products_query = new WP_Query($args); ob_start(); // 开启输出缓冲,捕获产品列表的HTML if ($products_query->have_posts()) { woocommerce_product_loop_start(); while ($products_query->have_posts()) { $products_query->the_post(); wc_get_template_part('content', 'product'); // 加载WooCommerce默认产品模板 } woocommerce_product_loop_end(); } else { echo '<p>该分类下暂无产品</p>'; } wp_reset_postdata(); // 重置查询,避免影响后续内容 $products_html = ob_get_clean(); // 获取缓冲的HTML内容 wp_send_json_success($products_html); // 返回成功响应和产品HTML }
额外优化提示
- 可以给加载状态加个简单的CSS样式,提升用户体验:
.products-container.loading { opacity: 0.7; position: relative; min-height: 200px; } .loading-tip { position: absolute; top: 50%; left: 50%; transform: translate(-50%, -50%); font-size: 16px; color: #666; }
- 如果你用的是子主题,建议所有修改都在子主题里操作,避免主题更新时丢失代码。
- 测试前记得清空网站缓存,确保AJAX请求能正常触发。
内容的提问来源于stack exchange,提问作者Chen
相关产品推荐
相关产品推荐

