WooCommerce自定义计算商品价格无法被优惠券识别问题
解决WooCommerce自定义计算价格无法使用优惠券的问题
我之前处理过一模一样的场景,问题出在:你通过woocommerce_add_cart_item修改的价格只是购物车的显示价格,WooCommerce的优惠券系统默认会读取商品的原始价格或者会话中未被正确标记的价格,不会自动识别你自定义计算后的数值。下面是完整的解决方案:
核心思路
要让优惠券生效,需要做到两点:
- 把用户输入的宽高数据持久化到购物车会话中(避免页面刷新后丢失)
- 让WooCommerce在计算优惠券、订单小计的时候,使用我们自定义计算后的价格,而不是商品原始价格
完整代码实现
// 1. 保存自定义宽高数据到购物车项,并计算初始自定义价格 add_filter('woocommerce_add_cart_item', 'save_custom_dimensions_and_calculate_price', 30, 3); function save_custom_dimensions_and_calculate_price($cart_item_data, $product_id, $variation_id) { // 检查是否有提交的宽高数据 if(isset($_POST['custom_width']) && isset($_POST['custom_height'])) { $width = floatval($_POST['custom_width']); $height = floatval($_POST['custom_height']); // 确保数值合法 if($width > 0 && $height > 0) { $product = wc_get_product($variation_id ? $variation_id : $product_id); $base_price = $product->get_price(); $custom_price = $base_price * $width * $height; // 保存自定义数据到购物车项 $cart_item_data['custom_dimensions'] = [ 'width' => $width, 'height' => $height, 'calculated_price' => $custom_price ]; // 给购物车项添加唯一键,避免同商品合并(可选,根据需求) $cart_item_data['unique_key'] = md5(microtime().rand()); } } return $cart_item_data; } // 2. 从会话中恢复自定义数据,确保页面刷新后不丢失 add_filter('woocommerce_get_cart_item_from_session', 'restore_custom_dimensions_from_session', 30, 3); function restore_custom_dimensions_from_session($cart_item, $values, $cart_item_key) { if(isset($values['custom_dimensions'])) { $cart_item['custom_dimensions'] = $values['custom_dimensions']; } return $cart_item; } // 3. 修改购物车项的显示价格和小计,让优惠券识别自定义价格 add_action('woocommerce_before_calculate_totals', 'apply_custom_price_to_cart_item', 30); function apply_custom_price_to_cart_item($cart) { if(is_admin() && !defined('DOING_AJAX')) return; foreach($cart->get_cart() as $cart_item_key => $cart_item) { if(isset($cart_item['custom_dimensions']['calculated_price'])) { // 设置购物车项的价格,这一步是让优惠券计算时使用这个价格 $cart_item['data']->set_price($cart_item['custom_dimensions']['calculated_price']); } } } // 4. 可选:在购物车页面显示自定义宽高信息(提升用户体验) add_filter('woocommerce_get_item_data', 'display_custom_dimensions_in_cart', 30, 2); function display_custom_dimensions_in_cart($item_data, $cart_item) { if(isset($cart_item['custom_dimensions'])) { $item_data[] = [ 'key' => '自定义尺寸', 'value' => $cart_item['custom_dimensions']['width'] . ' × ' . $cart_item['custom_dimensions']['height'] ]; } return $item_data; }
代码说明
woocommerce_add_cart_item:负责捕获用户提交的宽高数据,计算自定义价格,并把这些数据存入购物车项woocommerce_get_cart_item_from_session:确保页面刷新或者跳转后,自定义数据不会丢失woocommerce_before_calculate_totals:这是关键!通过set_price()方法直接修改商品对象的价格,WooCommerce的优惠券系统会读取这个修改后的价格进行计算,而不是原始价格display_custom_dimensions_in_cart:可选的辅助函数,在购物车页面显示用户输入的尺寸,让用户清楚价格计算依据
测试注意事项
- 测试前清空购物车,避免旧数据干扰
- 确保优惠券的设置是针对“商品价格”生效的(比如百分比折扣、固定金额折扣)
- 如果是变量商品,要确保
$variation_id的判断正确
内容的提问来源于stack exchange,提问作者Abilash Erikson
相关产品推荐
相关产品推荐

