Dodaj dynamiczny opis kategorii na podstawie URL w szablonie listy produktów
This commit is contained in:
202
.vscode/ftp-kr.sync.cache.json
vendored
202
.vscode/ftp-kr.sync.cache.json
vendored
@@ -13017,6 +13017,18 @@
|
||||
}
|
||||
},
|
||||
"catalog": {
|
||||
"brands.tpl": {
|
||||
"type": "-",
|
||||
"size": 1405,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"index.php": {
|
||||
"type": "-",
|
||||
"size": 1279,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"listing": {
|
||||
"best-sales.tpl": {
|
||||
"type": "-",
|
||||
@@ -13056,8 +13068,8 @@
|
||||
},
|
||||
"product-list.tpl": {
|
||||
"type": "-",
|
||||
"size": 3107,
|
||||
"lmtime": 1758143132356,
|
||||
"size": 3308,
|
||||
"lmtime": 1759177327251,
|
||||
"modified": false
|
||||
},
|
||||
"search.tpl": {
|
||||
@@ -13072,6 +13084,25 @@
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
}
|
||||
},
|
||||
"manufacturers.tpl": {
|
||||
"type": "-",
|
||||
"size": 1017,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"_partials": {},
|
||||
"product.tpl": {
|
||||
"type": "-",
|
||||
"size": 8390,
|
||||
"lmtime": 1759177283842,
|
||||
"modified": false
|
||||
},
|
||||
"suppliers.tpl": {
|
||||
"type": "-",
|
||||
"size": 1107,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
}
|
||||
}
|
||||
},
|
||||
@@ -13080,26 +13111,26 @@
|
||||
"components": {},
|
||||
"custom.css": {
|
||||
"type": "-",
|
||||
"size": 4452,
|
||||
"size": 4785,
|
||||
"lmtime": 0,
|
||||
"modified": true
|
||||
},
|
||||
"dr_materac.css": {
|
||||
"type": "-",
|
||||
"size": 86188,
|
||||
"lmtime": 1758060990464,
|
||||
"size": 86633,
|
||||
"lmtime": 1759177283777,
|
||||
"modified": false
|
||||
},
|
||||
"dr_materac.css.map": {
|
||||
"type": "-",
|
||||
"size": 32470,
|
||||
"lmtime": 1758060990473,
|
||||
"size": 32640,
|
||||
"lmtime": 1759177283788,
|
||||
"modified": false
|
||||
},
|
||||
"dr_materac.scss": {
|
||||
"type": "-",
|
||||
"size": 103498,
|
||||
"lmtime": 1758060990482,
|
||||
"size": 103658,
|
||||
"lmtime": 1759177283799,
|
||||
"modified": false
|
||||
},
|
||||
"index.php": {
|
||||
@@ -13124,8 +13155,8 @@
|
||||
"js": {
|
||||
"custom.js": {
|
||||
"type": "-",
|
||||
"size": 30943,
|
||||
"lmtime": 1758061021368,
|
||||
"size": 31821,
|
||||
"lmtime": 1759177283810,
|
||||
"modified": false
|
||||
},
|
||||
"index.php": {
|
||||
@@ -17512,8 +17543,8 @@
|
||||
},
|
||||
"detail1526395446.tpl": {
|
||||
"type": "-",
|
||||
"size": 30406,
|
||||
"lmtime": 1753645488602,
|
||||
"size": 30680,
|
||||
"lmtime": 1759177283821,
|
||||
"modified": false
|
||||
},
|
||||
"detail1526396195.tpl": {
|
||||
@@ -17593,7 +17624,20 @@
|
||||
"ps_banner": {},
|
||||
"ps_bestsellers": {},
|
||||
"ps_brandlist": {},
|
||||
"ps_categoryproducts": {},
|
||||
"ps_categoryproducts": {
|
||||
"views": {
|
||||
"templates": {
|
||||
"hook": {
|
||||
"ps_categoryproducts.tpl": {
|
||||
"type": "-",
|
||||
"size": 9894,
|
||||
"lmtime": 1759177283831,
|
||||
"modified": false
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"ps_categorytree": {},
|
||||
"ps_contactinfo": {},
|
||||
"ps_crossselling": {},
|
||||
@@ -17736,7 +17780,135 @@
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"_partials": {},
|
||||
"_partials": {
|
||||
"active_filters.tpl": {
|
||||
"type": "-",
|
||||
"size": 1748,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"buy-by-phone-popup.tpl": {
|
||||
"type": "-",
|
||||
"size": 5145,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"category-header.tpl": {
|
||||
"type": "-",
|
||||
"size": 1493,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"facets.tpl": {
|
||||
"type": "-",
|
||||
"size": 7342,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"index.php": {
|
||||
"type": "-",
|
||||
"size": 1279,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"miniatures": {},
|
||||
"product-activation.tpl": {
|
||||
"type": "-",
|
||||
"size": 1400,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-additional-info.tpl": {
|
||||
"type": "-",
|
||||
"size": 1086,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-add-to-cart.tpl": {
|
||||
"type": "-",
|
||||
"size": 4246,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-cover-thumbnails.tpl": {
|
||||
"type": "-",
|
||||
"size": 3167,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-customization.tpl": {
|
||||
"type": "-",
|
||||
"size": 3406,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-details.tpl": {
|
||||
"type": "-",
|
||||
"size": 3310,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-discounts.tpl": {
|
||||
"type": "-",
|
||||
"size": 2085,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-images-modal.tpl": {
|
||||
"type": "-",
|
||||
"size": 2583,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-prices.tpl": {
|
||||
"type": "-",
|
||||
"size": 3583,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"products-bottom.tpl": {
|
||||
"type": "-",
|
||||
"size": 511,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"products-top.tpl": {
|
||||
"type": "-",
|
||||
"size": 3417,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"products.tpl": {
|
||||
"type": "-",
|
||||
"size": 2161,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"product-variants.tpl": {
|
||||
"type": "-",
|
||||
"size": 3541,
|
||||
"lmtime": 1759177283852,
|
||||
"modified": false
|
||||
},
|
||||
"quickview.tpl": {
|
||||
"type": "-",
|
||||
"size": 3276,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"sort-orders.tpl": {
|
||||
"type": "-",
|
||||
"size": 2345,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
},
|
||||
"variant-links.tpl": {
|
||||
"type": "-",
|
||||
"size": 906,
|
||||
"lmtime": 0,
|
||||
"modified": false
|
||||
}
|
||||
},
|
||||
"product.tpl": {
|
||||
"type": "-",
|
||||
"size": 8357,
|
||||
|
||||
28
category-description.php
Normal file
28
category-description.php
Normal file
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
// /category-description.php
|
||||
// Zwraca HTML opisu kategorii dopasowany do aktualnego URL (GET: url=...)
|
||||
header('Content-Type: text/html; charset=utf-8');
|
||||
|
||||
// zabezpieczenie podstawowe
|
||||
$url = isset($_GET['url']) ? (string)$_GET['url'] : '';
|
||||
// Możesz sparsować path i query:
|
||||
$parsed = parse_url($url);
|
||||
$path = $parsed['path'] ?? '';
|
||||
$query = [];
|
||||
if (!empty($parsed['query'])) {
|
||||
parse_str($parsed['query'], $query);
|
||||
}
|
||||
|
||||
// PRZYKŁADOWA logika – dopasuj do swojej:
|
||||
if ($path === '/60-koldry/s-1/rozmiar-160x200_cm/rodzaj-koldry') {
|
||||
echo 'Opis kategorii';
|
||||
exit;
|
||||
}
|
||||
if ($path === '/60-koldry/s-1/rozmiar-220x200_cm/rodzaj-koldry') {
|
||||
echo 'Opis kategorii zmieniony';
|
||||
exit;
|
||||
}
|
||||
|
||||
// Domyślnie: pobierz standardowy opis kategorii (np. po id_category w path lub z kontekstu)
|
||||
// W prostym wariancie możesz też nic nie zwracać:
|
||||
echo '';
|
||||
@@ -74,12 +74,6 @@
|
||||
<div id="category-description" class="text-muted">{$category.description nofilter}</div>
|
||||
{/if}
|
||||
{/if}
|
||||
{if $smarty.server.REQUEST_URI == '/60-koldry/s-1/rozmiar-160x200_cm/rodzaj-koldry'}
|
||||
<div id="category-description" class="text-muted">Opis kategorii</div>
|
||||
{/if}
|
||||
{if $smarty.server.REQUEST_URI == '/60-koldry/s-1/rozmiar-220x200_cm/rodzaj-koldry'}
|
||||
<div id="category-description" class="text-muted">Opis kategorii zmieniony</div>
|
||||
{/if}
|
||||
{else}
|
||||
|
||||
{include file='errors/not-found.tpl'}
|
||||
@@ -88,6 +82,143 @@
|
||||
</section>
|
||||
|
||||
</section>
|
||||
{literal}
|
||||
<script>
|
||||
(function () {
|
||||
// ============ KONFIG ============
|
||||
var ENDPOINT = '/category-description.php'; // PHP, który zwróci HTML opisu
|
||||
var SHOW_ONLY_FIRST_PAGE = false; // jeśli opis tylko na 1. stronie -> true
|
||||
var DEBOUNCE_MS = 200;
|
||||
|
||||
// ============ NARZĘDZIA ============
|
||||
var lastUrl = null;
|
||||
var debounceTimer = null;
|
||||
var inflightController = null;
|
||||
|
||||
function onReady(fn) {
|
||||
if (document.readyState === 'complete' || document.readyState === 'interactive') {
|
||||
setTimeout(fn, 0);
|
||||
} else {
|
||||
document.addEventListener('DOMContentLoaded', fn);
|
||||
}
|
||||
}
|
||||
|
||||
// Wywołuj "locationchange" przy każdej zmianie historii
|
||||
function hookHistoryEvents() {
|
||||
var wrap = function (type) {
|
||||
var orig = history[type];
|
||||
return function () {
|
||||
var ret = orig.apply(this, arguments);
|
||||
window.dispatchEvent(new Event('locationchange'));
|
||||
window.dispatchEvent(new Event(type));
|
||||
return ret;
|
||||
};
|
||||
};
|
||||
history.pushState = wrap('pushState');
|
||||
history.replaceState = wrap('replaceState');
|
||||
window.addEventListener('popstate', function () {
|
||||
window.dispatchEvent(new Event('locationchange'));
|
||||
});
|
||||
}
|
||||
|
||||
function isFirstPage(urlStr) {
|
||||
if (!SHOW_ONLY_FIRST_PAGE) return true;
|
||||
try {
|
||||
var u = new URL(urlStr, window.location.origin);
|
||||
var p = u.searchParams.get('page') || u.searchParams.get('p');
|
||||
return !p || p === '1';
|
||||
} catch (e) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
function ensureContainer() {
|
||||
var el = document.getElementById('category-description');
|
||||
if (el) return el;
|
||||
|
||||
var anchor = document.querySelector('#js-product-list-top') || document.querySelector('#js-product-list');
|
||||
el = document.createElement('div');
|
||||
el.id = 'category-description';
|
||||
el.className = 'text-muted';
|
||||
if (anchor && anchor.parentNode) {
|
||||
anchor.parentNode.insertBefore(el, anchor.nextSibling);
|
||||
} else {
|
||||
document.body.appendChild(el);
|
||||
}
|
||||
return el;
|
||||
}
|
||||
|
||||
function replaceDescriptionIfHasContent(html) {
|
||||
if (typeof html !== 'string') return;
|
||||
var clean = html.trim();
|
||||
if (!clean) return; // <-- KLUCZOWA ZMIANA: tylko jeśli coś przyszło
|
||||
|
||||
var box = ensureContainer();
|
||||
box.innerHTML = clean;
|
||||
box.style.display = '';
|
||||
}
|
||||
|
||||
function fetchDescriptionFor(urlStr) {
|
||||
if (inflightController) {
|
||||
inflightController.abort();
|
||||
inflightController = null;
|
||||
}
|
||||
inflightController = new AbortController();
|
||||
|
||||
var endpointUrl = ENDPOINT + '?url=' + encodeURIComponent(urlStr);
|
||||
|
||||
return fetch(endpointUrl, {
|
||||
method: 'GET',
|
||||
credentials: 'same-origin',
|
||||
signal: inflightController.signal,
|
||||
headers: { 'X-Requested-With': 'XMLHttpRequest' }
|
||||
})
|
||||
.then(function (res) {
|
||||
if (!res.ok) throw new Error('HTTP ' + res.status);
|
||||
return res.text();
|
||||
})
|
||||
.then(function (html) {
|
||||
replaceDescriptionIfHasContent(html); // <-- tylko podmiana, gdy niepuste
|
||||
})
|
||||
.catch(function () { /* cicho ignorujemy błąd */ })
|
||||
.finally(function () {
|
||||
inflightController = null;
|
||||
});
|
||||
}
|
||||
|
||||
function updateDescriptionDebounced() {
|
||||
clearTimeout(debounceTimer);
|
||||
debounceTimer = setTimeout(function () {
|
||||
var currentUrl = window.location.href;
|
||||
if (currentUrl === lastUrl) return;
|
||||
lastUrl = currentUrl;
|
||||
|
||||
// Jeśli chcesz pokazywać opis tylko na 1. stronie — nie ruszamy treści,
|
||||
// po prostu nie robimy requestu na stronach > 1.
|
||||
if (!isFirstPage(currentUrl)) return;
|
||||
|
||||
fetchDescriptionFor(currentUrl);
|
||||
}, DEBOUNCE_MS);
|
||||
}
|
||||
|
||||
function wirePrestashopEvents() {
|
||||
if (window.prestashop && typeof window.prestashop.on === 'function') {
|
||||
window.prestashop.on('updateProductList', updateDescriptionDebounced);
|
||||
window.prestashop.on('updatedProductList', updateDescriptionDebounced);
|
||||
window.prestashop.on('facets:changed', updateDescriptionDebounced);
|
||||
}
|
||||
document.addEventListener('updateProductList', updateDescriptionDebounced, true);
|
||||
document.addEventListener('updatedProductList', updateDescriptionDebounced, true);
|
||||
}
|
||||
|
||||
onReady(function () {
|
||||
hookHistoryEvents();
|
||||
wirePrestashopEvents();
|
||||
window.addEventListener('locationchange', updateDescriptionDebounced);
|
||||
updateDescriptionDebounced(); // start
|
||||
});
|
||||
})();
|
||||
</script>
|
||||
{/literal}
|
||||
{hook h='displayApSC' sc_key=sc2450863744}
|
||||
{/block}
|
||||
Reference in New Issue
Block a user