I am working on a WordPress site that uses WooCommerce. I found this piece of code that allows me to set a freight shipping option based on weight. It worked great until the client also wanted the same freight shipping option if a freight shipping class is selected on a product.
add_filter( 'woocommerce_package_rates', 'bbloomer_woocommerce_tiered_shipping', 10, 2 );
function bbloomer_woocommerce_tiered_shipping( $rates, $package ) {
if ( WC()->cart->cart_contents_weight < 300 ) {
if ( isset( $rates['fedex:PRIORITY_OVERNIGHT'], $rates['fedex:FEDEX_2_DAY'], $rates['fedex:FEDEX_GROUND'] ) );
} else {
if ( isset( $rates['flat_rate:10'] ) ) unset( $rates['fedex:PRIORITY_OVERNIGHT'], $rates['fedex:FEDEX_2_DAY'],$rates['fedex:FEDEX_GROUND'] );
}
return $rates;
}
Then I found another piece of code that could set a shipping class to a shipping option. The code I found was mean to unset
shipping options that are available but I want to isset
the freight shipping since we unset
it via the cart weight. However, I am running into an issue where the freight shipping class can no longer be set to isset
without causing major issues. Below is what I tried to do for the freight shipping.
add_filter( 'woocommerce_package_rates', 'freight_shipping_class_only', 10, 2 );
function freight_shipping_class_only( $rates, $package ) {
$shipping_class_target = 193;
$in_cart = false;
foreach( WC()->cart->cart_contents as $key => $values ) {
if( $values[ 'data' ]->get_shipping_class_id() == $shipping_class_target ) {
$in_cart = true;
break;
}
}
if( $in_cart ) {
unset( $rates['fedex:PRIORITY_OVERNIGHT'], $rates['fedex:FEDEX_2_DAY'],$rates['fedex:FEDEX_GROUND'] ); // shipping method with ID (to find it, see screenshot below)
isset( $rates['flat_rate:10'] );
}
return $rates;
}
Is there a way to set both the cart weight and the freight shipping class in one function? It would be ideal since I want them both to do the exact same thing by unset
all FedEx shipping option and isset
the freight shipping option.
Let me know if you need me to be clearer or if you have any tips.
Thanks!
As you are using 2 times the same hook, you can simply merge your functions in one.
Now with php
[isset()][1]
you need to use it in as a condition in anIF
statement to check if a variable is set (exist), but it has no effect alone outside your IF statement in your function.So in your first function the following doesn't has any effect:
if ( isset( $rates['fedex:PRIORITY_OVERNIGHT'], $rates['fedex:FEDEX_2_DAY'], $rates['fedex:FEDEX_GROUND'] ) );
So you can try this compact and efficient code instead:
add_filter( 'woocommerce_package_rates', 'freight_shipping_class_only', 20, 2 );
function freight_shipping_class_only( $rates, $package ) {
// HERE the targeted shipping class ID
$targeted_shipping_class = 193;
// Loop through cart items and checking
$found = false;
foreach( $package['contents'] as $item ) {
if( $item['data']->get_shipping_class_id() == $targeted_shipping_class ){
$found = true;
break;
}
}
// The condition
if ( isset( $rates['flat_rate:10'] ) && ( WC()->cart->get_cart_contents_weight() >= 300 || $found ) ){
unset( $rates['fedex:PRIORITY_OVERNIGHT'], $rates['fedex:FEDEX_2_DAY'], $rates['fedex:FEDEX_GROUND'] );
}
return $rates;
}
Code goes in function.php file of the active child theme (or active theme). It should work.