0

I need to make a change on the icons passing the class .fa-plus to .fa-minus thats for this menu

<div class="accordion-menu">
                                <h2 class="accordion-header" id="subseccOne">
                                    <button class="accordion-button-m" type="button" >
                                        <i class="fa-solid fa-plus"  data-bs-toggle="collapse" data-bs-target="#subsecollapseOne" aria-expanded="true" aria-controls="subsecollapseOne"></i> <a class="item-section" href="">SEGUNDO NIVEL </a>
                                    </button>
                                </h2>
                                <div id="subsecollapseOne" class="accordion-collapse collapse" aria-labelledby="subseccOne" data-bs-parent="#subsecc">
                                    <div class="accordion-body">
                                        <div class="accordion" id="accordionExample">
                                            <div class="accordion-menu">
                                                <h2 class="accordion-header" id="headingOne">
                                                    <button class="accordion-button-m" type="button" >
                                                         <i class="fa-solid fa-plus"  data-bs-toggle="collapse" data-bs-target="#collapseOne" aria-expanded="true" aria-controls="collapseOne" ></i> <a class="item-section" href="">  TERCER NIVEL </a>
                                                    </button>
                                                </h2>
                                                <div id="collapseOne" class="accordion-collapse collapse" aria-labelledby="headingOne" data-bs-parent="#accordionExample">
                                                    <div class="accordion-body">
                                                        <strong>This is the first item's accordion body.</strong> It is shown by default, until the collapse plugin adds the appropriate classes that we use to style each element. These classes control the overall appearance, as well as the showing and hiding via CSS transitions. You can modify any of this with custom CSS or overriding our default variables. It's also worth noting that just about any HTML can go within the <code>.accordion-body</code>, though the transition does limit overflow.
                                                    </div>
                                                </div>
                                            </div>
                                            <div class="accordion-menu">
                                                <h2 class="accordion-header" id="headingTwo">
                                                    <button class="accordion-button-m collapsed" type="button" >
                                                        <i class="fa-solid fa-plus"  data-bs-toggle="collapse" data-bs-target="#collapseTwo" aria-expanded="false" aria-controls="collapseTwo"></i> <a class="item-section" href="">  TERCER NIVEL </a>
                                                    </button>
                                                </h2>
                                                <div id="collapseTwo" class="accordion-collapse collapse" aria-labelledby="headingTwo" data-bs-parent="#accordionExample">
                                                    <div class="accordion-body">
                                                        <strong>This is the second item's accordion body.</strong> It is hidden by default, until the collapse plugin adds the appropriate classes that we use to style each element. These classes control the overall appearance, as well as the showing and hiding via CSS transitions. You can modify any of this with custom CSS or overriding our default variables. It's also worth noting that just about any HTML can go within the <code>.accordion-body</code>, though the transition does limit overflow.
                                                    </div>
                                                </div>
                                            </div>
                                            <div class="accordion-menu">
                                                <h2 class="accordion-header" id="headingThree">
                                                    <button class="accordion-button-m collapsed" type="button" >
                                                        <i class="fa-solid fa-plus"  data-bs-toggle="collapse" data-bs-target="#collapseThree" aria-expanded="false" aria-controls="collapseThree"></i> <a class="item-section" href="">  TERCER NIVEL </a>
                                                    </button>
                                                </h2>
                                                <div id="collapseThree" class="accordion-collapse collapse" aria-labelledby="headingThree" data-bs-parent="#accordionExample">
                                                    <div class="accordion-body">
                                                        <strong>This is the third item's accordion body.</strong> It is hidden by default, until the collapse plugin adds the appropriate classes that we use to style each element. These classes control the overall appearance, as well as the showing and hiding via CSS transitions. You can modify any of this with custom CSS or overriding our default variables. It's also worth noting that just about any HTML can go within the <code>.accordion-body</code>, though the transition does limit overflow.
                                                    </div>
                                                </div>
                                            </div>
                                        </div>
                                    </div>
                                </div>
                            </div>

my JavaScript function is this

const icon= document.querySelectorAll(".fa-solid");
    const plusIcon = document.querySelectorAll(".fa-plus");
    
    
    for (i =0; i < plusIcon.length; i++){
        plusIcon[i].addEventListener("click", function (){
           
            icon.classList.remove("fa-plus");
            icon.classList.add("fa-minus")
        });
    }

I dont know why the console print this error, When the click event run on tghe function

menu_funcionalidad.js:29 Uncaught TypeError: Cannot read properties of undefined (reading 'remove') at HTMLElement.

2 Answers2

0

You are getting the error because you already assigned icon to a nodeList, so when trying to change the classes, icon is not an individual element. I would suggest using event.target to manipulate the element that has been clicked.

const icon= document.querySelectorAll(".fa-solid");
const plusIcon = document.querySelectorAll(".fa-plus");
    
    
for (i =0; i < plusIcon.length; i++){
    plusIcon[i].addEventListener("click", e => {
       e.target.classList.remove("fa-plus");
       e.target.classList.add("fa-minus");
       plusIcon.forEach(item => {
         if (item !== e.target) item.classList.add('//class-name');
       });
    });
}
Sarah
  • 354
  • 1
  • 12
  • This actually is working, when i click in the icon make the change but when i click i another icon dont reset the previous, you know how i can make that reset on the icons that I am not interacting – Santiago Diaz Jul 27 '22 at 17:27
  • I've updated my answer with a `forEach` that checks for elements that haven't been clicked – Sarah Jul 27 '22 at 17:42
  • Yeah its working i just need to put some conditions on inside the Event listener but Thank you so much for you help, this help me a lot. – Santiago Diaz Jul 27 '22 at 17:57
0

document.querySelectorAll(".fa-solid") will return a nodeList, meaning that when you attempt to access the classList inside your loop, you're attempting to access the classList of a nodeList, which is not possible.

If you want to add/remove the icons for each item in that node list, you can iterate over that list with .forEach() (See more here).

If you want to add/remove the icon from the element you're currently iterating over, replace icon.classList... with i.classList.

If the second route is what you're looking for, you could also add in a check inside the loop like:

for (i =0; i < plusIcon.length; i++){
        plusIcon[i].addEventListener("click", function (){
            if (i.classList.contains("fa-plus") {
                icon.classList.remove("fa-plus");
            } else 
                icon.classList.add("fa-minus");
            }                 
    });
}
McCambley
  • 1
  • 1