You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

WooCommerce商品归档/列表页倒计时显示异常问题求助

WooCommerce 促销倒计时短代码修复(归档页统一倒计时问题)

问题根源

你的代码在商品单页正常,但归档/列表页所有商品倒计时相同,核心问题有两个:

  • JS代码在循环中重复输出,每次都会覆盖countDownDate变量,最终所有计数器使用最后一个商品的促销结束时间
  • 所有倒计时元素共用同一个.countdown-counter类,JS无法区分每个商品对应的计数器

修正后的代码

add_shortcode( 'woocommerce_timer_two', 'sales_timer_countdown_product_two', 20 );
function sales_timer_countdown_product_two($atts) {
    extract( shortcode_atts( array(
        'id' => get_the_ID(),
    ), $atts, 'woocommerce_timer_two' ) ); 

    global $product;
    
    // 如果未定义产品对象,通过ID获取
    if ( ! is_a($product, 'WC_Product') && get_post_type($id) === 'product' ) {
        $product = wc_get_product($id);
    }
    
    if ( is_a($product, 'WC_Product') ) {
        $sale_date = get_post_meta( $product->get_id(), '_sale_price_dates_to', true );
        
        if ( ! empty( $sale_date ) ) {
            // 输出带唯一标识和销售时间数据属性的倒计时容器
            ?>
            <div class="product-countdown" data-product-id="<?php echo esc_attr($product->get_id()); ?>">
                 <span class="countdown-counter" data-countdown="<?php echo esc_attr($sale_date); ?>"></span>
            </div>
            <?php
        }
    }
}

// 将JS代码移到页脚,只加载一次
add_action('wp_footer', 'sales_timer_countdown_js');
function sales_timer_countdown_js() {
    ?>
    <script>
    jQuery(function($){
        "use strict";

        // 遍历每个带data-countdown属性的计数器
        $('.countdown-counter[data-countdown]').each( function() {
            var $this = $(this);
            var $parent = $this.parent();
            var countDownDate = parseInt($this.data('countdown')) * 1000;

            // 更新倒计时
            var x = setInterval(function() {
                var now = new Date().getTime();
                var distance = countDownDate - now;     
                
                // 时间计算
                var days = Math.floor(distance / (1000 * 60 * 60 * 24));
                var hours = Math.floor((distance % (1000 * 60 * 60 * 24)) / (1000 * 60 * 60));
                var minutes = Math.floor((distance % (1000 * 60 * 60)) / (1000 * 60));
                var seconds = Math.floor((distance % (1000 * 60)) / 1000);
                
                // 格式化输出(修复原代码中days和hours直接拼接的问题)
                var html = days + " : " + hours + " : " + minutes + " : " + seconds;
                $this.html(html);
                
                // 倒计时结束后隐藏容器
                if (distance < 0) {
                    clearInterval(x);
                    $parent.hide();
                }
            }, 1000);
            
            // 移除属性避免重复初始化
            $this.removeAttr('data-countdown');
        });
    });
    </script>
    <?php
}

关键修改说明

  • 分离JS与PHP循环:把JS代码移到wp_footer钩子中,只加载一次,避免循环中重复输出导致的变量覆盖
  • 唯一标识与数据存储:给每个倒计时元素添加data-countdown属性存储当前商品的促销结束时间,用商品ID作为容器的标识(可选)
  • JS遍历独立处理:通过data-countdown属性定位每个计数器,读取对应商品的时间进行计算,确保每个倒计时独立运行
  • 修复语法错误:原代码中countdown="'. $html .'"是无效的($html未定义),改为用data属性存储时间戳
  • 优化输出格式:修复原代码中days和hours直接拼接的问题,添加分隔符让倒计时格式更清晰

内容的提问来源于stack exchange,提问作者Viko

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.13 13:10:31