Я постараюсь описать как можно подробнее суть моей проблемы, что я пытаюсь сделать и что я уже пробовал сделать, итак..
Имеется каталог товаров и мне нужно, что бы по нажатию на определённый элемент списка выводились карточки товаров относящиеся к тематике выбранного элемента списка.
.
Как реализовать вывод карточек товаров я знаю. И без Ajax это выглядело бы так:
Была бы ссылка передающая название раздела методом "GET".
<a href = "?pc">Комплектующие ПК</a>
Код php который выводит карточки товара в нужном месте:
if (isset(($_GET['pc']))) {
$query = "SELECT * FROM `tableName`";
$result = $pdo->query($query);
foreach ($result as $array) {
$name = $array['name']; //наименование товара
$price = $array['price']; //цена товара
include 'card.php'; //подключение шаблона "карточки товара"
}
}
И сам шаблон карточки товара "card.php":
<div class = "card">
<div class = "card-header fl">
<p class = "product-name fl-al-c"> <?php echo $name; ?> </p> <!-- Наименование -->
</div>
<div class = "card-content fl">
<img src = "images/img.png" alt = "#">
</div>
<div class = "card-footer fl-al-c">
<p class = "price"> <?php echo $price; ?> </p> <!-- Цена товара -->
</div>
</div>
Но теперь мне необходимо сделать тоже самое, но с помощью Ajax который я начал изучать совсем недавно.
Я построил следующий Ajax запрос:
Sel.on('click', function(){
Ext.Ajax.request({
url: 'php/handler.php',
method: 'POST',
params: {
category: 'pc'
},
success: function (response) {
var objAjax = Ext.decode(response.responseText); //запись полученных данных в objAjax
var elementsInObjAjax = (Object.keys(objAjax).length); //количество элементов в objAjax
console.log("Ajax request: success // (sendAjaxRequest)");
console.log(objAjax);
for (var i = 0; i < elementsInObjAjax; i++) {
name = objAjax[i]['name']; //наименование
price = objAjax[i]['price']; //цена
$('#products').load('php/card.php');
}
},
failure: function () {
console.log("Ajax request: failure // (sendAjaxRequest)");
}
});
});
И написал вот такой код обработчика:
if ((isset($_POST['category'])) && (!empty($_POST['category']))) {
$tableName = $_POST['category'];
$query = "SELECT * FROM `$tableName`";
$result = $pdo->query($query);
$data = array();
foreach ($result as $array) {
array_push($data, $array);
}
echo json_encode($data);
}
Как видно из консоли, все данные были получены.
Но в результате, выводиться только одна карточка. Код в теле цикла for повторяется столько раз, сколько элементов в массиве полученном от сервера. Но вот следующий фрагмент:
$('#products').load('php/card.php');
Похоже работает только один раз или просто заменяет предыдущие данные в карте на новые.
Я довольно долго рылся в интернете в поисках ответа на тему обработки ответа и вставки на страницу, но так ничего и не нашёл. Видимо плохо искал.
Документация $.load говорит, что после запроса весь контейнер заменяется html-ответом с сервера.
Один из способов - прокинуть коллбэк в сам $.load, который по завершению дополняет контейнер, и соответственно очищать контейнер при первом вызове во избежании перезаполнения "старыми" данными.
const $products = $('#products')
function concatProducts (newHtml) {
let oldHtml = $products.html()
$products.html(oldHtml + newHtml)
}
// до главного вызова (цикла)
$products.html('')
// далее получаем html и конкатенируем
$products.load('php/card.php', concatProducts)
А так - способов много - от любого ajax-метода jQuery/библиотек типа axios до классического fetch/XMLHttpRequest, зависит уже от задач и потребностей.
В Вашем случае, если с сервера приходит html - нужно его просто вставить в контейнер, два варианта - либо конкатенировать (если запросов на каждую карточку несколько), либо обновлять html-код контейнера (если запрос один на пачку карточек).
В случае с json-ответом достаточно создать html-шаблон карточки и рисовать, например используя underscore/php-шаблоны или обычный html.
Для вывода карточки товара можно создать следующую функцию:
function renderCARD(t) {
var Card = {
tag: 'div',
cls: 'card fadeIn',
id: id,
children: [{
tag: 'div',
cls: 'card-header fl pc-c',
children: [{
tag: 'p',
cls: 'product-name fl-al-c',
html: name
}]
},{
tag: 'div',
cls: 'card-content fl',
children: [{
tag: 'img src = "images/products/computer-parts/no-image.png" alt = "#"',
}]
},{
tag: 'div',
cls: 'card-footer fl-al-c',
children: [{
tag: 'p',
cls: 'price',
html: price
}]
}]
};
Ext.core.DomHelper.append(t, Card);
}
Далее нужно вызвать функцию renderCARD(t) в цикле:
for (var i = 0; i < elementsInObjAjax; i++) {
name = objAjax[i]['name'];
price = objAjax[i]['price'];
id = objAjax[i]['id'];
renderCARD(products);
}
Кофе для программистов: как напиток влияет на продуктивность кодеров?
Рекламные вывески: как привлечь внимание и увеличить продажи
Стратегії та тренди в SMM - Технології, що формують майбутнє сьогодні
Выделенный сервер, что это, для чего нужен и какие характеристики важны?
Современные решения для бизнеса: как облачные и виртуальные технологии меняют рынок
Нужно реализовать следующее: Заменять английскую E на YE, если E стоит в начале любого слова в строке или после a, o, i, e, u, y