My go to for javascript help is https://developer.mozilla.org/en-US/docs/Web/JavaScript
Also there is an entire new series on Javascript here on laracasts.
Be part of JetBrains PHPverse 2026 on June 9 – a free online event bringing PHP devs worldwide together.
I have 7 accordions that have arrow icons. And I'm making the code in JavaScript as below, but do I have to repeat it 7x?
const collapsed = document.getElementById('collapsed-parent');
const icon = document.querySelector('#collapsed-parent .fa-angle-down');
collapsed.addEventListener('click', function () {
if (icon == document.querySelector('#collapsed-parent .fa-angle-down')) {
icon.classList.remove('fa-angle-down')
icon.classList.add('fa-angle-up')
console.log('parent up');
} else if (icon == document.querySelector('#collapsed-parent .fa-angle-up')) {
icon.classList.remove('fa-angle-up')
icon.classList.add('fa-angle-down')
console.log('parent down');
}
})
const collapsedChildOne = document.getElementById('collapsed-child-one');
const iconChildOne = document.querySelector('#collapsed-child-one .fa-angle-down');
collapsedChildOne.addEventListener("click", () => {
arrowUpAndDown(iconChildOne);
console.log('okk child');
});
const collapsedChildTwo = document.getElementById('collapsed-child-two');
const iconChildTwo = document.querySelector('#collapsed-child-two .fa-angle-down');
collapsedChildTwo.addEventListener("click", () => {
arrowUpAndDown(iconChildTwo);
console.log('two');
});
const collapsedChildThree = document.getElementById('collapsed-child-three');
const iconChildThree = document.querySelector('#collapsed-child-three .fa-angle-down');
collapsedChildThree.addEventListener("click", () => {
arrowUpAndDown(iconChildThree);
console.log('three');
});
const collapsedChildFour = document.getElementById('collapsed-child-four');
const iconChildFour = document.querySelector('#collapsed-child-four .fa-angle-down');
collapsedChildFour.addEventListener("click", () => {
arrowUpAndDown(iconChildFour);
console.log('four');
});
function arrowUpAndDown(icon) {
const angleDown = "fa-angle-down"
const angleUp = "fa-angle-up"
icon.classList.toggle(angleDown)
icon.classList.toggle(angleUp)
}
@mhmmdva I put together a sample proof-of-concept to illustrate how you could handle it
<style>
.hidden {
display: none;
}
.arrow-down::before {
content: '93';
}
.arrow-up::before {
content: '91';
}
.accordion {
border: solid 1px black;
}
.accordion section h2 {
margin: 0;
background-color: grey;
cursor: default;
border-bottom: solid 1px black;
}
</style>
<div class="accordion">
<section>
<h2>Section 1 <i class="arrow-down"></i></h2>
<div class="hidden">
Lorem ipsum dolor sit amet.
</div>
</section>
<section>
<h2>Section 2 <i class="arrow-down"></i></h2>
<div class="hidden">
Lorem ipsum dolor sit amet.
</div>
</section>
<section>
<h2>Section 3 <i class="arrow-down"></i></h2>
<div class="hidden">
Lorem ipsum dolor sit amet.
</div>
</section>
</div>
<script>
// using a class, instead of an id, allows you to have
// multiple accordions on the same page
document.querySelectorAll('.accordion').forEach(function (accordion) {
let current;
// this will toggle CSS classes on a section relevant elements
function toggleSection(section, isVisible) {
const icon = section.querySelector('i');
icon.classList.toggle('arrow-up', isVisible);
icon.classList.toggle('arrow-down', !isVisible);
section.querySelector('div').classList.toggle('hidden', !isVisible);
}
// by adding the event listener to the parent element
// a listener is no longer needed for each individual section
accordion.addEventListener('click', function (event) {
// stop this event from bubbling up into the DOM tree
event.stopPropagation();
// find the event parent section
const clicked = event.target.closest('section');
// this will hide the clicked section if it is currently visible
current = clicked === current ? null : clicked;
// walk thorugh each section to check its state
accordion.querySelectorAll('section')
.forEach((section) => toggleSection(section, section === current));
});
});
</script>
Code is functional, just copy and paste, save as an HTML file, and open in a browser to explore how it works.
Modern JS frameworks improved the frontend landscape by a lot, but I feel concepts like event bubbling are being lost.
Hope this helps =)
Please or to participate in this conversation.