由于您使用订单总计来计算您的费用,并且您使用的挂钩位于内部calculate_totals()
方法,一旦订单更新,您始终需要按“重新计算”按钮才能获得正确的费用总额和正确的订单总金额以及正确的金额.
自 WooCommerce 3 以来,您的代码已经过时,并且有些过时,并且存在一些错误......例如add_fee() https://github.com/woocommerce/woocommerce/blob/4.8.0/includes/legacy/abstract-wc-legacy-order.php#L105-L106 and update_fee() https://github.com/woocommerce/woocommerce/blob/4.8.0/includes/legacy/abstract-wc-legacy-order.php#L261-L262方法已被弃用并被其他一些方法取代。
请改用以下内容:
add_action( 'woocommerce_order_after_calculate_totals', "custom_order_after_calculate_totals", 10, 2 );
function custom_order_after_calculate_totals( $and_taxes, $order ) {
if ( did_action( 'woocommerce_order_after_calculate_totals' ) >= 2 )
return;
$percentage = 0.03; // Fee percentage
$fee_data = array(
'name' => __('3% CC Fee'),
'amount' => wc_format_decimal( $order->get_total() * $percentage ),
'tax_status' => 'none',
'tax_class' => ''
);
$fee_items = $order->get_fees(); // Get fees
// Add fee
if( empty($fee_items) ){
$item = new WC_Order_Item_Fee(); // Get an empty instance object
$item->set_name( $fee_data['name'] );
$item->set_amount( $fee_data['amount'] );
$item->set_tax_class($fee_data['tax_class']);
$item->set_tax_status($fee_data['tax_status']);
$item->set_total($fee_data['amount']);
$order->add_item( $item );
$item->save(); // (optional) to be sure
}
// Update fee
else {
foreach ( $fee_items as $item_id => $item ) {
if( $item->get_name() === $fee_data['name'] ) {
$item->set_amount($fee_data['amount']);
$item->set_tax_class($fee_data['tax_class']);
$item->set_tax_status($fee_data['tax_status']);
$item->set_total($fee_data['amount']);
$item->save();
}
}
}
}
代码位于活动子主题(或活动主题)的functions.php 文件中。经过测试并有效。
一旦订单更新并且按重新计算按钮后 (以获得正确的订单总数)自动添加和更新的费用都会很好地工作。
有关的:在 Woocommerce 3 中以编程方式向订单添加费用 https://stackoverflow.com/questions/53603746/add-a-fee-to-an-order-programmatically-in-woocommerce-3/53604944#53604944
Update
现在,如果它因任何原因不起作用,您应该删除相关项目进行更新并添加新项目,如下所示:
add_action( 'woocommerce_order_after_calculate_totals', "custom_order_after_calculate_totals", 10, 2 );
function custom_order_after_calculate_totals( $and_taxes, $order ) {
if ( did_action( 'woocommerce_order_after_calculate_totals' ) >= 2 )
return;
$percentage = 0.03; // Fee percentage
$fee_data = array(
'name' => __('3% CC Fee'),
'amount' => wc_format_decimal( $order->get_total() * $percentage ),
'tax_status' => 'none',
'tax_class' => ''
);
$fee_items = $order->get_fees(); // Get fees
// Add fee
if( empty($fee_items) ){
$item = new WC_Order_Item_Fee(); // Get an empty instance object
$item->set_name( $fee_data['name'] );
$item->set_amount( $fee_data['amount'] );
$item->set_tax_class($fee_data['tax_class']);
$item->set_tax_status($fee_data['tax_status']);
$item->set_total($fee_data['amount']);
$order->add_item( $item );
$item->save(); // (optional) to be sure
}
// Update fee
else {
foreach ( $fee_items as $item_id => $item ) {
if( $item->get_name() === $fee_data['name'] ) {
$item->remove_item( $item_id ); // Remove the item
$item = new WC_Order_Item_Fee(); // Get an empty instance object
$item->set_name( $fee_data['name'] );
$item->set_amount( $fee_data['amount'] );
$item->set_tax_class($fee_data['tax_class']);
$item->set_tax_status($fee_data['tax_status']);
$item->set_total($fee_data['amount']);
$order->add_item( $item );
$item->save(); // (optional) to be sure
}
}
}
}