You are here

function commerce_discount_commerce_cart_order_refresh in Commerce Discount 7

Implements hook_commerce_cart_order_refresh().

1 call to commerce_discount_commerce_cart_order_refresh()
commerce_discount_shipping_service in ./commerce_discount.rules.inc
Rules action: Apply shipping discount.

File

./commerce_discount.module, line 14
Defines the discount and discount offer entities, bundles and functionality.

Code

function commerce_discount_commerce_cart_order_refresh($order_wrapper) {

  // Remove all discount references from the order.
  // (If there are none, setting array() would modify the order, so test first.)
  if (isset($order_wrapper->commerce_discounts) && $order_wrapper->commerce_discounts
    ->value()) {
    $order_wrapper->commerce_discounts = array();
  }
  if (!isset($order_wrapper->commerce_line_items) || $order_wrapper->commerce_line_items
    ->count() <= 0) {
    return;
  }
  $line_items_to_delete = array();
  $currency_code = commerce_default_currency();
  if (!is_null($order_wrapper->commerce_order_total
    ->value())) {
    $currency_code = $order_wrapper->commerce_order_total->currency_code
      ->value();
  }

  // We create an empty price structure to be used by discount line items,
  // we want to remove all price components present on discount line items such
  // as VAT, the discount price component itself etc.
  $empty_price = commerce_discount_empty_price($currency_code);
  foreach ($order_wrapper->commerce_line_items as $delta => $line_item_wrapper) {
    if (!$line_item_wrapper
      ->value()) {
      continue;
    }

    // Remove all the price components on discount line items, if the unit price
    // is still == 0 after evaluating order discount rules, the discount line
    // item will be deleted.
    if ($line_item_wrapper
      ->getBundle() == 'commerce_discount') {
      $line_item_wrapper->commerce_unit_price = $empty_price;
      $line_item_wrapper->commerce_total = $empty_price;
      continue;
    }
    elseif ($line_item_wrapper
      ->getBundle() == 'product_discount') {
      $line_items_to_delete[] = $line_item_wrapper
        ->getIdentifier();
      $order_wrapper->commerce_line_items
        ->offsetUnset($delta);
      continue;
    }
    elseif ($line_item_wrapper
      ->getBundle() == 'shipping') {
      $changed = commerce_discount_remove_discount_components($line_item_wrapper->commerce_unit_price);
      if ($changed) {

        // Since we're saving the line item, there's no need to manually
        // update the line item's total since that'll be done in the controller.
        $line_item_wrapper
          ->save();
      }
    }
  }

  // We need to make sure the order total is correct before evaluating discount
  // rules, order total may not be correct when our refresh implementation is
  // invoked.
  commerce_discount_calculate_order_total($order_wrapper);

  // Re-add all applicable discount price components and/or line items.
  rules_invoke_event('commerce_discount_order', $order_wrapper);

  // After the discount rules were evaluated, we need to check if we have
  // some discount line items with empty prices (we need to delete them).
  foreach ($order_wrapper->commerce_line_items as $delta => $line_item_wrapper) {
    if (!$line_item_wrapper
      ->value() || $line_item_wrapper
      ->getBundle() != 'commerce_discount') {
      continue;
    }
    $unit_price = commerce_price_wrapper_value($line_item_wrapper, 'commerce_unit_price', TRUE);
    if (empty($unit_price['amount'])) {
      $line_items_to_delete[] = $line_item_wrapper
        ->getIdentifier();
      $order_wrapper->commerce_line_items
        ->offsetUnset($delta);
    }
  }

  // Delete discount line item if necessary.
  if ($line_items_to_delete) {
    commerce_line_item_delete_multiple($line_items_to_delete, TRUE);
  }
}