I want to double the discount for products on sale with a coupon code.
For example: The product is on sale with a 10% discount. If I add the coupon code doublediscount I want to double that discount to 20%.
The coupon discount should have limit of 15%. So if a product is on sale with a 30% discount, the max added discount with the coupon code should be 15%. Resulting in a 45% discount on the regular price (sale + extra discount).
My code so far is this:
add_action( 'woocommerce_before_calculate_totals', 'double_saleprice_coupon' );
function double_saleprice_coupon( $cart ) {
    if ( is_admin() && ! defined( 'DOING_AJAX' ) )
        return;
    global $woocommerce;
    $coupon_id = 'doublediscount';
    // Loop through cart items (first loop)
    foreach ( $cart->get_cart() as $cart_item_key => $cart_item ){
        // Check if product in cart is on sale
        $product = $cart_item['data'];
        $cart_item_regular_price = $cart_item['data']->get_regular_price();
        $cart_item_sale_price = $cart_item['data']->get_sale_price();
        $cart_item_diff       = $cart_item_regular_price - $cart_item_sale_price;
        $cart_item_per_cent   = round( $cart_item_diff / $cart_item_regular_price * 100, 0 );
        if ( $product->is_on_sale() && wc_pb_is_bundled_cart_item($cart_item) === false && $cart_item_per_cent < 15 ) {
            echo 'on sale';
            echo $cart_item_per_cent;
        }
    }
}
I loop through all cart items and check if they are on sale and if the discount is below 15%. If that’s the case, I want to change the discount for these cart items.
If the cart item has a discount above 15% I don’t want to do anything. So the coupon code doublediscount would apply 15% to them.
I just don’t know how to add/change the discount of a cart item.
Advertisement
Answer
You can use the woocommerce_coupon_get_discount_amount hook instead in combination with the following coupon settings:
- Set correctly your coupon code: 
doublediscount - Discount type: 
Percentage - Amount: 
15 
Steps applied in this answer:
- Only if the specific coupon code matches and the product is on sale
 - If a product is not on sale, no discount will be applied (by the else condition equal to 0. However, if this doesn’t apply, you can simply remove the else condition)
 - Current percentage discount of the on sale product is calculated.
If this is less than the maximum added discount (
15), then the discount is doubled - If this is more, the maximum discount added (
15) will be applied automatically 
So you get:
function filter_woocommerce_coupon_get_discount_amount( $discount, $price_to_discount , $cart_item, $single, $coupon ) {
    // Returns true when viewing the cart page & only apply for this coupon
    if ( is_cart() || is_checkout() && $coupon->get_code() == 'doublediscount' ) {
        // Get an instance of the WC_Product object
        $product = $cart_item['data'];
        
        // Is a WC product
        if ( is_a( $product, 'WC_Product' ) ) {
            // On sale
            if ( $product->is_on_sale() ) {
                // Regular price
                $cart_item_regular_price = $product->get_regular_price();
                
                // Sale price
                $cart_item_sale_price = $product->get_sale_price();
                
                // Calculate the percentage difference
                $cart_item_diff = $cart_item_regular_price - $cart_item_sale_price;
                $cart_item_percentage = round( $cart_item_diff / $cart_item_regular_price * 100, 0 );
                
                // Get maximum added discount
                $max_added_discount = $coupon->get_amount();
                
                // Less than maximum added discount
                if ( $cart_item_percentage < $max_added_discount ) {
                    $discount = round( ( $price_to_discount * $cart_item_percentage ) / 100, 0 );
                }
            } else {
                $discount = 0;
            }
        }
    }
    return $discount;
}
add_filter( 'woocommerce_coupon_get_discount_amount', 'filter_woocommerce_coupon_get_discount_amount', 10, 5 );