# disco/1.2.85/functions/bogo.php

Discount Rules for WooCommerce – Disco | Dynamic Pricing, Conditions, Bulk, Bundle, BOGO, version 1.2.85. 187 lines.

- Page: https://pluginprobe.com/plugins/disco/1.2.85/code/functions/bogo.php
- Raw: https://pluginprobe.com/plugins/disco/1.2.85/raw/functions/bogo.php
- Modified: 2025-08-28T04:33:22+00:00

Line numbers below start at 1. Link to a line or a range by appending a fragment to the
page URL, for example `https://pluginprobe.com/plugins/disco/1.2.85/code/functions/bogo.php#L10-L20`.

```php
<?php
// phpcs:disable
/**
 * Disco
 *
 * @package   Disco
 * @author    Ohidul Islam <wahid0003@gmail.com>
 * @link      http://domain.tld
 * @license   GPL 2.0+
 * @copyright 2022 WebAppick
 */

// Ensure the file is not accessed directly.
if (!defined('ABSPATH')) {
	exit;
}

use Disco\App\Disco;
use Disco\App\Utility\Helper;
use Disco\App\Utility\Settings;

if ( ! function_exists( 'disco_cart_apply_free_items' ) ) {
	function disco_cart_apply_free_items( $cart ) {
		if ( is_admin() && ! defined( 'DOING_AJAX' ) ) {
			return;
		}

		if( Settings::get( 'discount_priority_type' ) === 'woocommerce_coupon' ) {
			return $cart;
		}

		if ( did_action( 'woocommerce_before_calculate_totals' ) >= 2 ) {
			return;
		}

		if ( $cart->is_empty() ) {
			return;
		}

		// Clone cart to avoid free products when calculating discount
		$cart_copy = new WC_Cart;

		foreach ( $cart->get_cart() as $cart_item ) {
			if ( ! empty( $cart_item['is_free_product'] ) ) {
				continue;
			}

			$cart_copy->add_to_cart(
				$cart_item['product_id'],
				$cart_item['quantity'],
				$cart_item['variation_id'] ?? 0,
				$cart_item['variation'] ?? array(),
				$cart_item['cart_item_data'] ?? array()
			);
		}

		foreach ( $cart->get_applied_coupons() as $coupon_code ) {
			$cart_copy->apply_coupon( $coupon_code );
		}

		$discounts  = ( new Disco )->get_cart_items_discount_for_bogo( $cart_copy );
		$free_ids   = $discounts['get_ids'] ?? array();
		$free_qty   = $discounts['get_qty'] ?? 0;
		$bogo_type  = $discounts['bogo_type'] ?? 'products';

		// Remove invalid free items from cart
		foreach ( $cart->get_cart() as $cart_item_key => $cart_item ) {
			if ( ! isset( $cart_item['is_free_product'] ) || ! $cart_item['is_free_product'] ) {
				continue;
			}

			$product_id = $cart_item['product_id'];

			if (
				( $bogo_type === 'categories' && ! Helper::is_in_category( $product_id, $free_ids ) )
				|| ( $bogo_type !== 'categories' && ! in_array( $product_id, $free_ids, true ) )
			) {
				$cart->remove_cart_item( $cart_item_key );
			}
		}

		if ( empty( $free_qty ) || empty( $free_ids ) ) {
			return;
		}

		if ( $bogo_type === 'categories' ) {
			$free_count = 0;

			foreach ( $cart->get_cart() as $cart_item_key => $cart_item ) {
				if ( $free_count >= $free_qty ) {
					break;
				}

				if ( ! empty( $cart_item['is_free_product'] ) ) {
					continue;
				}

				$product_id = $cart_item['product_id'];

				if ( Helper::is_in_category( $product_id, $free_ids ) ) {
					$remaining_qty = $free_qty - $free_count;

					// Only mark item free if the full quantity fits
					if ( $cart_item['quantity'] <= $remaining_qty ) {
						$cart->cart_contents[ $cart_item_key ]['is_free_product'] = true;
						$free_count += $cart_item['quantity'];
					} else {
						continue;
					}
				}
			}
		} else {
			// Product-based free items
			foreach ( $free_ids as $product_id ) {
				$found = false;

				foreach ( $cart->get_cart() as $cart_item_key => $cart_item ) {
					if (
						intval( $cart_item['product_id'] ) === intval( $product_id )
						&& ! empty( $cart_item['is_free_product'] )
					) {
						$current_qty = $cart_item['quantity'];
						if ( $current_qty !== $free_qty ) {
							$cart->set_quantity( $cart_item_key, $free_qty );
						}
						$found = true;
						break;
					}
				}

				if ( ! $found ) {
					$cart->add_to_cart( $product_id, $free_qty, 0, array(), array( 'is_free_product' => true ) );
				}
			}
		}
	}

	add_action( 'woocommerce_before_calculate_totals', 'disco_cart_apply_free_items', 5 );
}


if ( ! function_exists( 'disco_set_free_product_price' ) ) {

	/**
	 * Set the price of free products to zero.
	 *
	 * @param \WC_Cart $cart Cart Object.
	 */
	function disco_set_free_product_price( $cart ) {
		if ( is_admin() && ! defined( 'DOING_AJAX' ) ) {
			return;
		}

		foreach ( $cart->get_cart() as $cart_item_key => $cart_item ) {
			if ( empty( $cart_item['is_free_product'] ) ) {
				continue;
			}

			// Only process if not already handled
			if ( empty( $cart_item['free_product_processed'] ) ) {
				$cart_item['data']->set_price( 0 );
				$cart_item['data']->set_regular_price( 0 );

				$cart->cart_contents[ $cart_item_key ]['free_product_note'] = __( 'This item is added as free!', 'disco' );

				// Mark as processed to avoid duplicate changes
				$cart->cart_contents[ $cart_item_key ]['free_product_processed'] = true;
			}
		}
	}
	add_action( 'woocommerce_before_calculate_totals', 'disco_set_free_product_price', 10 );
}

if ( ! function_exists( 'disco_free_product_label' ) ) {
	function disco_free_product_label( $item_data, $cart_item ) {
		if ( ! empty( $cart_item['free_product_note'] ) ) {
			$item_data[] = array(
				'key'   => __( 'Note', 'disco' ),
				'value' => $cart_item['free_product_note'],
			);
		}
		return $item_data;
	}

	add_filter( 'woocommerce_get_item_data', 'disco_free_product_label', 10, 2 );
}

```
