I have a php/html code where I iterate over services. And I create modal form by js, but js code is triggered only on the first element iterated over by foreach (php).
What can I do to have js process each element of the array?
Php/html
<div class="cards"> <? foreach($catalog_product as $key => $catalog_product_value): ?> <div class="card"> <div class="card__side card__side--front card__side--front-1"> <div class="header"> <h3><?=$catalog_product_value['name']?></h3> </div> <p class="btn-pink">Подробнее</p> </div> <div class="card__side card__side--back card__side--back-1"> <h3><?=$catalog_product_value['header']?></h3> <p class="flip-text"><?=$catalog_product_value['title']?></p> <?=$catalog_product_value['content']?> <button id="buy_product_form" data-item="product" data-item_id="<?=$catalog_product_value['product_id']?>" data-id="card_<?=($key + 1)?>" data-title="<?=htmlspecialchars($catalog_product_value['header'])?>" <? if (!empty($catalog_product_value['options'])): ?> data-options="<?=htmlspecialchars(json_encode($catalog_product_value['options']), ENT_QUOTES, 'UTF-8')?>" <? else: ?> data-price="<?=preg_replace('/[^0-9.]+/', '', $catalog_product_value['price'])?>" <? endif; ?> class="pop_maker"> <?=$catalog_product_value['price']?> </button> </div> </div> <? endforeach;?> </div>
js code
window.onload = function(){ button = document.getElementById('buy_product_form'); var atr = button.getAttribute('data-title'); var id = button.getAttribute('data-id'); var options = button.getAttribute('data-options'); var price = button.getAttribute('data-price'); var item_id = button.getAttribute('data-item_id'); var item = button.getAttribute('data-item'); button.id = id; var _form = document.createElement('form'); ..... };
Advertisement
Answer
The problem is because you’re using id
attributes in a repeated code block, and id
have to be unique within the DOM. Change that to a class
attribute, use querySelectorAll()
instead of getElementById()
and then use a forEach()
loop over the resulting collection. Something like this:
let buttons = document.querySelectorAll('.buy_product_form'); buttons.forEach(el => { el.addEventListener('click', e => { let button = e.target; let atr = button.dataset.title; console.log(atr); // other logic here... }); });
<div class="cards"> <div class="card"> <div class="card__side card__side--front card__side--front-1"> <div class="header"> <h3>Name</h3> </div> <p class="btn-pink">Подробнее</p> </div> <div class="card__side card__side--back card__side--back-1"> <h3>Header - Lorem ipsum</h3> <p class="flip-text"> Title </p> Content <button data-item="product" data-item_id="item_id" data-id="card_1" data-title="Lorem ipsum" class="buy_product_form pop_maker"> Price </button> </div> </div> <div class="card"> <div class="card__side card__side--front card__side--front-1"> <div class="header"> <h3>Name</h3> </div> <p class="btn-pink">Подробнее</p> </div> <div class="card__side card__side--back card__side--back-1"> <h3>Header - Foo bar</h3> <p class="flip-text"> Title </p> Content <button data-item="product" data-item_id="item_id" data-id="card_2" data-title="Foo bar" class="buy_product_form pop_maker"> Price </button> </div> </div> </div>