При классическом использовании функционала работы с купонами в Битриксе, размер скидки и обновление цен в корзине происходит в момент сохранения заказа. До этого момента объект Basket содержит «исходную» цену товара, а DiscountCouponsManager знает о примененных купонах.
Разбираемся, как показывать цену товаров в корзине до момента оформления заказа с учетом примененных скидок.
Алгоритм прост и состоит из нескольких шагов:
- создаем виртуальный клон корзины без сохранения в базу данных
- применяем скидки к корзине
- вычисляем реальную стоимость товаров
Реализуется это так:
$registry = Bitrix\Sale\Registry::getInstance(Bitrix\Sale\Registry::REGISTRY_TYPE_ORDER); $basketClass = $registry->getBasketClassName(); /** Получаем текущую корзину пользователя */ $basket = $basketClass::loadItemsForFUser( Bitrix\Sale\Fuser::getId(), Bitrix\Main\Context::getCurrent()->getSite() ); /** @var Sale\Basket $basketClone */ $basketClone = $basket->createClone(); $orderableBasket = $basketClone->getOrderableItems(); unset($basketClone); $coupons = DiscountCouponsManager::get(false, [], false, true); if (!empty($coupons) && !$orderableBasket->isEmpty()) { /** Магия расчета цен */ $discounts = Sale\Discount::buildFromBasket( $orderableBasket, new Sale\Discount\Context\Fuser(Fuser::getId()) ); $discountResult = $discounts->calculate(); if ($discountResult->isSuccess()) { /** Получение массива цен и обновление свойств виртуальной корзины */ $showPrices = $discounts->getShowPrices(); if (!empty($showPrices['BASKET'])) { foreach ($showPrices['BASKET'] as $basketCode => $data) { $basketItem = $orderableBasket->getItemByBasketCode($basketCode); if ($basketItem instanceof Sale\BasketItemBase) { $basketItem->setFieldNoDemand('BASE_PRICE', $data['SHOW_BASE_PRICE']); $basketItem->setFieldNoDemand('PRICE', $data['SHOW_PRICE']); } } unset($basketItem, $basketCode); } unset($showPrices); } unset($discountResult); } /** Формирование ответа для фронта или другие действия */
Мы используем виртуальную корзину, поэтому можно наполнять ее произвольными товарами и вычислять, сколько будет стоить та или иная позиция с учетом введенной пользователем скидки.
Больше статей и материалов по web-разработке в tg-канале - подписывайтесь!
Подписаться в telegram