I have some product in WooCommerce and two categories are:
Name: ORG Test
Slug: org-test
Name: ORG Prod
Slug: org-prod
I want to calculate shipping fee per quantity ($15 per quantity) if the product matches org-prod
category:
My code attempt:
add_action('woocommerce_cart_calculate_fees', 'add_fees_on_ids');
function add_fees_on_ids() {
$total_act_fee = 0;
$business_plan_exist = false;
if (is_admin() && !defined('DOING_AJAX')) {return;}
foreach( WC()->cart->get_cart() as $cart_item ) {
$product = $cart_item['data'];
$quantity = $cart_item['quantity'];
$categories = wc_get_product_category_list( $product->get_id() );
if (strstr($categories, 'org-prod')) {
$business_plan_exist = true;
$total_act_fee = $total_act_fee + 15;
}
if ($business_plan_exist) {
WC()->cart->add_fee(__('Shipping Fees '), $total_act_fee);
}
}
}
But this does not give the desired result. The fee is applied but the total is wrong? Can you assist in figuring out why not?
Your code contains some mistakes and/or could be optimized:
WC()->cart
is not necessary, as $cart
is already passed to the callback functionhas_term()
versus wc_get_product_category_list()
and strstr()
So you get:
function action_woocommerce_cart_calculate_fees( $cart ) {
if ( is_admin() && ! defined( 'DOING_AJAX' ) )
return;
// Specific categories: the term name/term_id/slug. Several could be added, separated by a comma
$categories = array( 'org-prod', 'categorie-1', 83 );
// Initialize
$total_act_fee = 0;
$amount = 15;
// Gets cart contents
foreach ( $cart->get_cart_contents() as $cart_item ) {
// Has certain category
if ( has_term( $categories, 'product_cat', $cart_item['product_id'] ) ) {
// Get quantity
$quantity = $cart_item['quantity'];
// Addition to the total
$total_act_fee += $amount * $quantity;
}
}
// Greater than
if ( $total_act_fee > 0 ) {
// Add fee
$cart->add_fee( __( 'Shipping Fees', 'woocommerce' ), $total_act_fee, true );
}
}
add_action( 'woocommerce_cart_calculate_fees', 'action_woocommerce_cart_calculate_fees', 10, 1 );