From d21a1ed93913d607b79cf6814a5c566f58fe0b18 Mon Sep 17 00:00:00 2001 From: Your Name Date: Fri, 6 Jun 2025 22:55:09 +0300 Subject: [PATCH] =?UTF-8?q?5933=20|=20=D0=BC=D0=BD=D0=BE=D0=B6=D0=B5=D1=81?= =?UTF-8?q?=D1=82=D0=B2=D0=BE=20=D0=BF=D1=80=D0=B0=D0=B2=D0=BE=D0=BA=20?= =?UTF-8?q?=D1=81=D0=BE=D0=B3=D0=BB=D0=B0=D1=81=D0=BD=D0=BE=20=D0=BF=D0=BE?= =?UTF-8?q?=D0=B4=D0=B7=D0=B0=D0=B4=D0=B0=D1=87=D0=B0=D0=BC=20=D0=BD=D0=B0?= =?UTF-8?q?=20AE=20=D1=81=D1=82=D0=B5=D0=BD=D0=B4=D0=B5?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- wp-content/themes/cosmopet/functions.php | 30 +- .../global-functions/multisite-functions.php | 413 ++++++++++-- .../footer/assets/css/gp-style-desktop.css | 2 +- .../modules/footer/assets/js/footer.js | 1 + .../modules/forms/module-ajax-controller.php | 4 +- .../modules/forms/module-controller.php | 60 +- .../themes/cosmopet/templates/footer.twig | 128 ++-- .../themes/cosmopet/templates/header.twig | 7 + .../themes/cosmopet/templates/layout.twig | 53 ++ .../templates/where_to_buy/template_wtb.php | 628 ++++-------------- .../cosmopet/templates/where_to_buy/wtb.twig | 365 ++++++++++ 11 files changed, 1068 insertions(+), 623 deletions(-) diff --git a/wp-content/themes/cosmopet/functions.php b/wp-content/themes/cosmopet/functions.php index b6148f8..0fbcf1e 100644 --- a/wp-content/themes/cosmopet/functions.php +++ b/wp-content/themes/cosmopet/functions.php @@ -1196,10 +1196,10 @@ function remove_woocommerce_styles_on_checkout() { } - // Добавляем hreflang теги для cosmopet.shop add_action('wp_head', 'custom_hreflang_shop', 6); function custom_hreflang_shop() { + if (!is_admin() && function_exists('pll_get_post') && function_exists('pll_languages_list')) { // Защищаем от дублирования static $hreflang_added = false; if ($hreflang_added) { @@ -1207,12 +1207,34 @@ function custom_hreflang_shop() { } $hreflang_added = true; - $current_path = add_query_arg('', $_SERVER['REQUEST_URI']); + // Домены для языков $ru_domain = 'https://cosmopet-test-ru.cp.good-production.xyz'; $en_domain = 'https://cosmopet-test-ae.cp.good-production.xyz'; - echo '' . "\n"; - echo '' . "\n"; + // Текущий пост/страница + $current_post_id = get_the_ID(); + if (!$current_post_id) { + // Для случаев, когда get_the_ID() не работает (например, архивы) + $current_path = trailingslashit($_SERVER['REQUEST_URI']); + $query_string = $_SERVER['QUERY_STRING'] ? '?' . $_SERVER['QUERY_STRING'] : ''; + $ru_url = $ru_domain . $current_path . $query_string; + $en_url = $en_domain . $current_path . $query_string; + } else { + // Получаем переводы поста/страницы + $ru_post_id = pll_get_post($current_post_id, 'ru'); + $en_post_id = pll_get_post($current_post_id, 'en'); + + // Формируем URL с учетом перевода и параметров запроса + $query_string = $_SERVER['QUERY_STRING'] ? '?' . $_SERVER['QUERY_STRING'] : ''; + + $ru_url = $ru_post_id ? get_permalink($ru_post_id) . $query_string : $ru_domain . trailingslashit($_SERVER['REQUEST_URI']) . $query_string; + $en_url = $en_post_id ? get_permalink($en_post_id) . $query_string : $en_domain . trailingslashit($_SERVER['REQUEST_URI']) . $query_string; + } + + // Выводим hreflang-теги + echo '' . "\n"; + echo '' . "\n"; + } } add_action('wp_head', 'custom_checkout_padding'); diff --git a/wp-content/themes/cosmopet/global-functions/multisite-functions.php b/wp-content/themes/cosmopet/global-functions/multisite-functions.php index 2152328..6334d1f 100644 --- a/wp-content/themes/cosmopet/global-functions/multisite-functions.php +++ b/wp-content/themes/cosmopet/global-functions/multisite-functions.php @@ -1,40 +1,375 @@ - defined('SITE_DOMAIN') ? SITE_DOMAIN : null, - ]; - - return $context; -}); - - -// Отключаем канонические ссылки и hreflang от Yoast SEO -add_filter('wpseo_canonical', '__return_false'); -add_filter('wpseo_opengraph_url', '__return_false'); // Отключаем OG URL -add_filter('wpseo_add_x_default_hreflang', '__return_false'); // Отключаем hreflang от Yoast -add_filter('wpseo_disable_adjacent_rel_links', '__return_true'); // Отключаем соседние rel-ссылки - -// Добавляем каноническую ссылку -add_action('wp_head', 'custom_canonical_url', 5); -function custom_canonical_url() { - // Защищаем от дублирования - static $canonical_added = false; - if ($canonical_added) { - return; - } - $canonical_added = true; - - $current_url = home_url(add_query_arg('', $_SERVER['REQUEST_URI'])); - echo '' . "\n"; + defined('SITE_DOMAIN') ? SITE_DOMAIN : null, + ]; + + return $context; +}); + + +// Отключаем канонические ссылки и hreflang от Yoast SEO +add_filter('wpseo_canonical', '__return_false'); +add_filter('wpseo_opengraph_url', '__return_false'); // Отключаем OG URL +add_filter('wpseo_add_x_default_hreflang', '__return_false'); // Отключаем hreflang от Yoast +add_filter('wpseo_disable_adjacent_rel_links', '__return_true'); // Отключаем соседние rel-ссылки + +// Добавляем каноническую ссылку +add_action('wp_head', 'custom_canonical_url', 5); +function custom_canonical_url() { + if (!is_admin()) { + // Защищаем от дублирования + static $canonical_added = false; + if ($canonical_added) { + return; + } + $canonical_added = true; + + // Формируем текущий URL без лишних параметров + $current_url = trailingslashit(home_url($_SERVER['REQUEST_URI'])); + // Удаляем возможные параметры запроса, если они не нужны + $current_url = strtok($current_url, '?'); + echo '' . "\n"; + } +} + +add_action('wp_head', 'add_facebook_pixel'); +function add_facebook_pixel() { + ?> + + + + + + + get_status() !== 'processing' && $order->get_status() !== 'completed')) return; + + $items = []; + foreach ($order->get_items() as $item) { + $product = $item->get_product(); + $items[] = [ + 'item_id' => $product->get_id(), + 'item_name' => $product->get_name(), + 'price' => $product->get_price(), + 'quantity' => $item->get_quantity() + ]; + } + ?> + + cart ? WC()->cart->get_total('edit') : 0; + ?> + + admin_url('admin-ajax.php') + )); + + // Inline CSS + wp_enqueue_style('woocommerce-custom-styles', get_template_directory_uri() . '/style.css', array(), '1.0'); + $custom_css = " + .single_add_to_cart_button.loading { + opacity: 0.5; + cursor: not-allowed; + position: relative; + } + .single_add_to_cart_button.loading:after { + content: ''; + display: inline-block; + width: 16px; + height: 16px; + border: 2px solid #fff; + border-radius: 50%; + border-top-color: transparent; + animation: spin 1s linear infinite; + position: absolute; + right: 10px; + } + @keyframes spin { + 100% { + transform: rotate(360deg); + } + } + "; + wp_add_inline_style('woocommerce-custom-styles', $custom_css); + } +} + +// Отключаем кэширование для страниц товаров +add_action('template_redirect', function() { + if (is_product()) { + header('Cache-Control: no-cache, no-store, must-revalidate'); + header('Pragma: no-cache'); + header('Expires: 0'); + } +}); + +// Обработчик AJAX +add_action('wp_ajax_woocommerce_ajax_add_to_cart', 'woocommerce_ajax_add_to_cart'); +add_action('wp_ajax_nopriv_woocommerce_ajax_add_to_cart', 'woocommerce_ajax_add_to_cart'); + +function woocommerce_ajax_add_to_cart() { + error_log('AJAX handler called'); // Отладка: логируем вызов + + $product_id = isset($_POST['product_id']) ? absint($_POST['product_id']) : 0; + $quantity = isset($_POST['quantity']) ? absint($_POST['quantity']) : 1; + + error_log('Received product_id: ' . $product_id . ', quantity: ' . $quantity); // Отладка + + if (!$product_id) { + error_log('Invalid product_id received'); // Отладка + wp_send_json_error(array('message' => 'Неверный ID товара')); + wp_die(); + } + + $passed_validation = apply_filters('woocommerce_add_to_cart_validation', true, $product_id, $quantity); + + if ($passed_validation) { + $added = WC()->cart->add_to_cart($product_id, $quantity); + if ($added) { + error_log('Product added to cart: ' . $product_id); // Отладка + // Подготавливаем фрагменты корзины + ob_start(); + woocommerce_mini_cart(); + $mini_cart = ob_get_clean(); + + // Фрагменты для стандартной корзины и кастомного счетчика + $fragments = array( + 'div.widget_shopping_cart_content' => '
' . $mini_cart . '
', + '.mini-profile__button--counter' => '
' . WC()->cart->get_cart_contents_count() . '
' + ); + + wp_send_json_success(array( + 'message' => 'Товар успешно добавлен в корзину', + 'fragments' => apply_filters('woocommerce_add_to_cart_fragments', $fragments), + 'cart_hash' => apply_filters('woocommerce_add_to_cart_hash', WC()->cart->get_cart_hash(), array()) + )); + } else { + error_log('Failed to add product to cart: ' . $product_id); // Отладка + wp_send_json_error(array('message' => 'Не удалось добавить товар в корзину')); + } + } else { + error_log('Validation failed for product: ' . $product_id); // Отладка + wp_send_json_error(array('message' => 'Ошибка валидации товара')); + } + + wp_die(); } \ No newline at end of file diff --git a/wp-content/themes/cosmopet/modules/footer/assets/css/gp-style-desktop.css b/wp-content/themes/cosmopet/modules/footer/assets/css/gp-style-desktop.css index f02a7b9..e966923 100644 --- a/wp-content/themes/cosmopet/modules/footer/assets/css/gp-style-desktop.css +++ b/wp-content/themes/cosmopet/modules/footer/assets/css/gp-style-desktop.css @@ -172,7 +172,7 @@ } .modal__login { - width: 412px; + width: 500px; } .modal__item.active { diff --git a/wp-content/themes/cosmopet/modules/footer/assets/js/footer.js b/wp-content/themes/cosmopet/modules/footer/assets/js/footer.js index 22e286c..22e0467 100644 --- a/wp-content/themes/cosmopet/modules/footer/assets/js/footer.js +++ b/wp-content/themes/cosmopet/modules/footer/assets/js/footer.js @@ -1012,3 +1012,4 @@ if (document.querySelector('.header').classList.contains('white')) { + diff --git a/wp-content/themes/cosmopet/modules/forms/module-ajax-controller.php b/wp-content/themes/cosmopet/modules/forms/module-ajax-controller.php index dacdfd5..445e0bd 100644 --- a/wp-content/themes/cosmopet/modules/forms/module-ajax-controller.php +++ b/wp-content/themes/cosmopet/modules/forms/module-ajax-controller.php @@ -13,12 +13,12 @@ add_action('wp_ajax_nopriv_contact_form', function() { }); add_action('wp_ajax_subscribe_form', function() { - $enabledHandlers = ['b24', 'email', 'mindbox']; + $enabledHandlers = ['b24', 'email']; process_form($enabledHandlers); }); add_action('wp_ajax_nopriv_subscribe_form', function() { - $enabledHandlers = ['b24', 'email', 'mindbox']; + $enabledHandlers = ['b24', 'email']; process_form($enabledHandlers); }); diff --git a/wp-content/themes/cosmopet/modules/forms/module-controller.php b/wp-content/themes/cosmopet/modules/forms/module-controller.php index b5aa7c3..144ebc3 100644 --- a/wp-content/themes/cosmopet/modules/forms/module-controller.php +++ b/wp-content/themes/cosmopet/modules/forms/module-controller.php @@ -34,43 +34,43 @@ class zohoHandler extends FormHandler { } } -class mindboxHandler extends FormHandler { - public function handle($data) { - // Отправка в стандартный обработчик (например, email) - error_log("Отправка в mindBox: " . json_encode($data)); - // if (is_string($data)) { - // parse_str($data, $parsedData); // Преобразуем строку в массив - // $data = $parsedData; - // } +// class mindboxHandler extends FormHandler { +// public function handle($data) { +// // Отправка в стандартный обработчик (например, email) +// error_log("Отправка в mindBox: " . json_encode($data)); +// // if (is_string($data)) { +// // parse_str($data, $parsedData); // Преобразуем строку в массив +// // $data = $parsedData; +// // } - // $url = 'https://api.mindbox.ru/v3/operations/async?endpointId=cosmopet.Website&operation=DobavleniePolzovatelyaSSajta'; +// // $url = 'https://api.mindbox.ru/v3/operations/async?endpointId=cosmopet.Website&operation=DobavleniePolzovatelyaSSajta'; - // $data = array( - // "email" => $data['email'], - // "subscriptions" => array( - // array( - // "pointOfContact"=> "Email" - // ), - // ), - // ); +// // $data = array( +// // "email" => $data['email'], +// // "subscriptions" => array( +// // array( +// // "pointOfContact"=> "Email" +// // ), +// // ), +// // ); - // $data_string = json_encode(array("customer" =>$data)); +// // $data_string = json_encode(array("customer" =>$data)); - // $ch = curl_init($url); +// // $ch = curl_init($url); - // curl_setopt($ch, CURLOPT_POSTFIELDS, $data_string); +// // curl_setopt($ch, CURLOPT_POSTFIELDS, $data_string); - // curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type:application/json')); +// // curl_setopt($ch, CURLOPT_HTTPHEADER, array('Content-Type:application/json')); - // curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); +// // curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); - // $result = curl_exec($ch); +// // $result = curl_exec($ch); - // curl_close($ch); - return parent::handle($data); - } -} +// // curl_close($ch); +// return parent::handle($data); +// } +// } class emailHandler extends FormHandler { public function handle($data) { @@ -113,9 +113,9 @@ class FormHandlerFactory { if (in_array('zoho', $enabledHandlers)) { $handler = new zohoHandler($handler); } - if (in_array('mindbox', $enabledHandlers)) { - $handler = new mindboxHandler($handler); - } + // if (in_array('mindbox', $enabledHandlers)) { + // $handler = new mindboxHandler($handler); + // } if (in_array('b24', $enabledHandlers)) { $handler = new b24Handler($handler); } diff --git a/wp-content/themes/cosmopet/templates/footer.twig b/wp-content/themes/cosmopet/templates/footer.twig index 9478b5e..8ef4307 100644 --- a/wp-content/themes/cosmopet/templates/footer.twig +++ b/wp-content/themes/cosmopet/templates/footer.twig @@ -170,58 +170,86 @@ }); }); - // Находим все элементы с классом login-open document.addEventListener('DOMContentLoaded', function() { - const loginButtons = document.querySelectorAll('.login-open'); - - // Добавляем обработчик события для каждой кнопки - loginButtons.forEach(button => { - button.addEventListener('click', function(event) { - event.preventDefault(); // Предотвращаем стандартное действие (если это ссылка) - - // Находим элементы модального окна - const modal = document.querySelector('.modal'); - const modalAside = document.querySelector('.modal__aside'); - const modalLogin = document.querySelector('.modal__login'); - - // Добавляем классы active - modal.classList.add('active'); - modalLogin.classList.add('active'); - - // Устанавливаем ширину для modal__aside - modalAside.style.width = '412px'; - }); - }); - - // Опционально: добавляем функцию закрытия модального окна - // Например, при клике на фон или кнопку закрытия - const closeButtons = document.querySelectorAll('.modal-close'); - const modal = document.querySelector('.modal'); - - // Закрытие по клику на кнопку закрытия - closeButtons.forEach(button => { - button.addEventListener('click', closeModal); - }); - - // Закрытие по клику на фон (если клик не на модальное окно) - modal.addEventListener('click', function(event) { - if (event.target === modal) { - closeModal(); + // Общая функция для открытия модальных окон + function modalOpen(triggerSelector, modalSelector) { + const triggers = document.querySelectorAll(triggerSelector); + const modalLogin = document.querySelector('.modal'); + const modalItem = document.querySelector(modalSelector); + const modalAside = modalItem ? modalItem.querySelector('.modal__aside') : null; + + triggers.forEach(trigger => { + trigger.addEventListener('click', (e) => { + e.preventDefault(); // Предотвращаем стандартное поведение + + // Сбрасываем стили и классы для всех модальных окон + document.querySelectorAll('.modal__item').forEach(item => { + item.classList.remove('active'); + item.style.cssText = ''; // Сбрасываем opacity, filter и другие стили + const aside = item.querySelector('.modal__aside'); + if (aside) { + aside.style.width = ''; + } + }); + + // Открываем нужное модальное окно + if (modalLogin && modalItem) { + modal.classList.add('active'); + modalItem.classList.add('active'); + modalItem.style.opacity = '1'; // Устанавливаем видимость + modalItem.style.filter = 'blur(0px)'; // Убираем размытие + if (modalAside) { + modalAside.style.width = '500px'; // Устанавливаем ширину + } + } + }); + }); + } + + // Общая функция для закрытия модальных окон + function modalClose(closeSelector) { + const closes = document.querySelectorAll(closeSelector); + const modalLogin = document.querySelector('.modal'); + + closes.forEach(close => { + close.addEventListener('click', () => { + document.querySelectorAll('.modal__item').forEach(item => { + item.classList.remove('active'); + item.style.cssText = ''; // Сбрасываем opacity, filter и другие стили + const aside = item.querySelector('.modal__aside'); + if (aside) { + aside.style.width = ''; + } + }); + if (modalLogin) { + modal.classList.remove('active'); + } + }); + }); + } + + // Обработчик клика по фону модального окна + const modalLogin = document.querySelector('.modal'); + if (modalLogin) { + modal.addEventListener('click', (event) => { + if (event.target.classList.contains('modal')) { + const modalItem = modal.querySelector('.modal__item.active'); + if (modalItem) { + const aside = modalItem.querySelector('.modal__aside'); + if (aside) { + aside.style.width = '0px'; + } + modalItem.style.opacity = '0'; // Анимация закрытия + modalItem.style.filter = 'blur(10px)'; + setTimeout(() => { + modalItem.classList.remove('active'); + modalItem.style.cssText = ''; // Сбрасываем все стили после анимации + modal.classList.remove('active'); + }, 300); + } + } + }); } - }); - - function closeModal() { - const modal = document.querySelector('.modal'); - const modalAside = document.querySelector('.modal__aside'); - const modalLogin = document.querySelector('.modal__login'); - - // Удаляем классы active - modal.classList.remove('active'); - modalLogin.classList.remove('active'); - - // Сбрасываем ширину - modalAside.style.width = ''; - } }); diff --git a/wp-content/themes/cosmopet/templates/header.twig b/wp-content/themes/cosmopet/templates/header.twig index 856742b..5c46e03 100644 --- a/wp-content/themes/cosmopet/templates/header.twig +++ b/wp-content/themes/cosmopet/templates/header.twig @@ -187,6 +187,13 @@ + {% if CONSTANTS.DOMAIN != 'AE' %}