Телеграм: @bazarow_ru mihail@bazarow.ru Проверяю почту и телеграм 2-3 раза в день.
С 1 по 10 января 2024 будет сделан редизайн сайта.
Пришла пора освежиться!

Если товар в корзине, поменять кнопку на "В корзине" в новом шаблоне 1С-Битрикс

Просмотров: 2610

Ранее я уже делал заметку на эту тему. Тогда, мы меняли значение input-а при добавлении товара в корзину в старых шаблонах детальной карточки.
В этой заметке рассмотрю этот же функционал для нового шаблона, при этом поправим и некоторый SEO момент данного функционала.

Логика работы будет заключаться в том что при клике на кнопку "В корзину" мы ее прячем и показываем, ранее спрятанную, ссылку "В корзине" которая будет отправлять пользователя на оформление заказа.

Рассматривать буду на примере детальной карточки, но заметка подойдет и для списка элементов раздела, с небольшой модификацией. При этом, если пользователь вышел из карточки (добавив товар в корзину) и снова в нее вернулся - у него останется ссылка "В корзине".

Заменям ссылку-кнопку "В корзину" на "В корзине", при клике

Блок с ссылкой кнопкой, в шаблоне, выглядит так:


<?if ($showAddBtn){?>
<div class="mb-3">
	<a
	class="btn <?=$showButtonClassName?> product-item-detail-buy-button"
	id="<?=$itemIds['ADD_BASKET_LINK']?>"
	href="javascript:void(0);">
		В корзину
	</a>
</div>
<?php}?>

Сначала, давайте сменим ссылку a на span, так как для SEO не очень хорошо наличие ссылки ведущей в никуда.

В карточке, может быть это не очень критично, но вот в списке таких ссылок получается много (да, эту инструкцию можно применить и для списка товаров). Меняем a на span и удаляем href, все будет работать - больше ничего не надо дорабатывать. Заодно избавимся от переизбытка class-ов, что бы проще версталось:


<?if ($showAddBtn){?>
<div class="mb-3">
	<span 
	class="add_to_cart" 
	id="<?=$itemIds['ADD_BASKET_LINK']?>">
		В корзину
	</span>
</div>
<?php}?>

У это spana-а есть уникальный для товара идентификатор , привязавшись к нему будем прятать span, при клике и показывать кнопку перехода в корзину.


<?if ($showAddBtn){?>
<div class="mb-3">
	<span 
	class="add_to_cart" 
	id="<?=$itemIds['ADD_BASKET_LINK']?>">
 		В корзину
 	</span>
 	<a 
	 class="link_to_card_dn" 
	 href="<?=$arParams['BASKET_URL']?>" 
	 id="to_cart_<?=$itemIds['ADD_BASKET_LINK']?>">
 		В корзине
 	</a>
 </div>

 <script>
 $('#<?= $itemIds['BASKET_ACTIONS_ID'] ?>').click(function () {
     $(this).addClass('add_to_cart_dn');
     $('#to_cart_<?=$itemIds['ADD_BASKET_LINK']?>').addClass('link_to_card_db');
 });
 </script>

<style type="text/css">
<!--
.link_to_card_dn, .add_to_cart_dn {
	 display: none;
}
.link_to_card_db {
	 display: block;
}
-->
</style>
<?php}?>

Суть заключается в следующем: изначально span c "В корзину" виден, а ссылка "В корзине" спрятана в display:none.

  • При клике по span-у к нему добавляется class add_to_cart_dn который его прячет (добавляет стиль с display:none)
  • К ссылке "В корзине" добавляется class link_to_card_db который переводит ее в display: block;
Само собой стили и скрипты данной логики можно разнести по файлам style.css и script.js, что бы не болтались прямо в шаблоне. Оставил так для упрощения.

Здесь все готово. Но, если пользователь обновит страницу, все стили вернутся в исходное состояние и хотя товар и будет в корзине, пользователь увидит кнопку "В корзину".

Проверка наличия товара в корзине

Что бы поправить этот момент нужно проверить наличие текущего товара в корзине пользователя и обработать вывод кнопок "В корзину" и "В корзине"

В result_modifer.php карточки товара добавляем:


$dbBasketItems = CSaleBasket::GetList(
    array(
        "NAME" => "ASC",
        "ID" => "ASC"
    ),
    array(
        "FUSER_ID" => CSaleBasket::GetBasketUserID(),
        "LID" => SITE_ID,
        "PRODUCT_ID" => $arResult['ID'],
        "ORDER_ID" => "NULL",
        "DELAY" => "N"
    ),
    false,
    false,
    array("PRODUCT_ID")
);
while ($arItemsBasket = $dbBasketItems->Fetch()) {
    $arResult['ITEM_HAS_IN_CART'] = $arItemsBasket['PRODUCT_ID'];
}

Методом CSaleBasket::GetBasketUserID мы получили корзину текущего пользователя и отфильтровали текущий товар. Если этот товар есть в корзине-то $arResult['ITEM_HAS_IN_CART'] будет не пустой.

Далее дорабатываем наш кусочек кода:


<if ($showAddBtn){
if ($arResult['ITEM_HAS_IN_CART']) {
	$itemInCart = true;
}
?>
<div class="mb-3">
	<span
 	class="add_to_cart<?echo $itemInCart ? ' add_to_cart_dn' : ''?>"
 	id="<?=$itemIds['ADD_BASKET_LINK']?>">
 		В корзину
 	</span>
	<a
	 class="link_to_card_dn<?echo $itemInCart ? ' link_to_card_db' : ''?>"
	 href="<?=$arParams['BASKET_URL']?>"
	 id="to_cart_<?=$itemIds['ADD_BASKET_LINK']?>" >
	 	В корзине
	 </a>
 </div>

 <script>
 $('#<?= $itemIds['BASKET_ACTIONS_ID'] ?>').click(function () {
     $(this).addClass('add_to_cart_dn');
     $('#to_cart_<?=$itemIds['ADD_BASKET_LINK']?>').addClass('link_to_card_db');
 });
 </script>

<style type="text/css">
<!--
.link_to_card_dn, .add_to_cart_dn {
	 display: none;
}
.link_to_card_db {
	display: block;
}
-->
</style>
<?php}?>

Тут все просто: если $arResult['ITEM_HAS_IN_CART'] существует мы сразу прячем span и показываем ссылку "В корзине", теми же самыми стилями которые используем в js скрипте.

При желании, можно вообще попрятать все за условие, что бы в исходном коде и не было упоминания о spаn-е и скрипте. Тут уже, на ваше усмотрение:

Михаил Базаров 28.05.2022
Что бы спрятатаь, точнее не показывать, всплывающее окно о добавлении товара в корзину.

В шаблоне catalog.item и catalog.element комментируем строчку с инициализацией этого окна.
Находим ее в файлах script.js

Код
this.initPopupWindow();

в секции
Код
basketResult: function(arResult)