How to apply javascript to multiple button groups

只愿长相守 提交于 2020-07-05 23:54:56

问题


I have css and js on a button group so that when you click a button from the group it shows as active, and when you click a different button, that button becomes active and the rest are cleared. I have to have 22 of these button groups (I only put 2 here for the sake of space) on my page, when I have just one the code works, but when I add the others everything comes crumbling down, can anyone help! How do use the script multiple times, where the script is applied to every group and doesn't intervene with the others.

function codeAddress() {
  var header = document.getElementById("myDIV");
  var btns = header.getElementsByClassName("btn");
  for (var i = 0; i < btns.length; i++) {
    btns[i].addEventListener("click", function() {
      var current = document.getElementsByClassName("active");
      current[0].className = current[0].className.replace(" active", "");
      this.className += " active";
    });
  }
}
window.onload = codeAddress;
.btn {
  background-color: white;
  border: 3px solid #0099ff;
  color: #0099ff;
  cursor: pointer;
  float: left;
  padding: 10px 16px;
  font-size: 18px;
}

.active,
.btn:hover {
  background-color: #0099ff;
  color: white;
  border: 3px solid #0099ff;
  cursor: pointer;
}
<div id="myDIV">
  <button class="btn active">GQL</button>
  <button class="btn">PSV</button>
  <button class="btn">WT2</button>
  <button class="btn">NBV</button>
  <button class="btn">MBD</button>
</div>
<div id="myDIV">
  <button class="btn active">GQL</button>
  <button class="btn">PSV</button>
  <button class="btn">WT2</button>
  <button class="btn">NBV</button>
  <button class="btn">MBD</button>
</div>

回答1:


Here give this ago. I believe this is the intended response you expect when clicking button from different groups. Something like radio buttons. As already mentioned an ID can only represent one element not several. Use class instead. So i have changed your id to a class btn-group.

function codeAddress() {
    const btnClick = function () {
        this.parentNode.getElementsByClassName("active")[0].classList.remove("active");
        this.classList.add("active");
    };
    document.querySelectorAll(".btn-group .btn").forEach(btn => btn.addEventListener('click', btnClick));

    // This is the same as above just another way of doing it. use which ever you like
    // var btns = document.querySelectorAll(".btn-group .btn");
    // for (var i = 0; i < btns.length; i++) {
    //     btns[i].addEventListener("click", function () {
    //         this.parentNode.getElementsByClassName("active")[0].classList.remove("active");
    //         this.classList.add("active");
    //     });
    // }
   
}
window.onload = codeAddress;
.btn {
    background-color: white;
    border: 3px solid #0099ff;
    color: #0099ff;
    cursor: pointer;
    float: left;
    padding: 10px 16px;
    font-size: 18px;
}

.active,
.btn:hover {
    background-color: #0099ff;
    color: white;
    border: 3px solid #0099ff;
    cursor: pointer;
}
<div class="btn-group">
    <button class="btn active">GQL</button>
    <button class="btn">PSV</button>
    <button class="btn">WT2</button>
    <button class="btn">NBV</button>
    <button class="btn">MBD</button>
</div>
<br style="clear:both">
<div class="btn-group">
    <button class="btn active">GQL</button>
    <button class="btn">PSV</button>
    <button class="btn">WT2</button>
    <button class="btn">NBV</button>
    <button class="btn">MBD</button>
</div>



回答2:


It's not working because you have multiple IDs:

<div id="myDIV">...</div>
<div id="myDIV">...</div>

You can't do this - first, it's invalid HTML, and second, it'll do one of two things with the JS: cause an error, which you can see in the console, or it'll treat header as a NodeList, which is a collection of nodes that match the query selection, which means that it won't work. If you make them all have different IDs (e.g. div1, div2, div3, etc), it'll work if you modify your code to take multiple divs.
The other option is to make a class (e.g. myDIV) and modify your existing JavaScript code to use a class.




回答3:


Instead of individual buttons, I would recommend using radio buttons for something like this. It already has functionality built in to group together for a selection similar to what you're going for. Then you just have to use built in commands to set the active button or check the values.

https://www.w3schools.com/jsref/prop_radio_checked.asp

https://www.w3schools.com/html/html_forms.asp




回答4:


Here the example what you need https://jsbin.com/bomegabiqo/1/edit?html,js,output

First of all, I want to say that you don't need to have two div with the same id The second point is that you need to attach eventListener to the parent element, due to best-practice and performance optimization (you can read about it somewhere)

So here is updated version of HTML:

<div id="myGroupButtonsWrapper">  
  <div id="myDIV">
    <button class="btn active">GQL</button>
    <button class="btn">PSV</button>
    <button class="btn">WT2</button>
    <button class="btn">NBV</button>
    <button class="btn">MBD</button>
  </div>
  <div id="myDIVV">
    <button class="btn">GQL</button>
    <button class="btn">PSV</button>
    <button class="btn">WT2</button>
    <button class="btn">NBV</button>
    <button class="btn">MBD</button>
  </div>
</div>

And JavaScript:

function codeAddress() {

  function myClickCallback(e) {
    if (e.target.className === 'btn') {
      var allButtons = document.querySelectorAll("#myGroupButtonsWrapper .btn");

      allButtons.forEach((elem) => {
        elem.className = elem.className.replace(" active", "");           
      });
      e.target.className += ' active';    
    } else {
      return;
    }
  }

  var header = document.getElementById("myGroupButtonsWrapper");   
  header.addEventListener("click", myClickCallback);    
} 
window.onload = codeAddress;



回答5:


it is fairly simple to accomplish this using just 3 steps.

// First step is to create a onBtnClick handler function:
// The btn which was clicked can be accessed from event.target
// And then we can use the build in function classList.toggle to toggle the active class on that btn
const onBtnClickHandler = function (ev){ev.target.classList.toggle("active")};

// Next step is to find all btns, this can be done using the build in querySelectorAll function
const btns = document.querySelectorAll('.btn'); //returns NodeList array

// Last step is to add the eventListener callback function to each btn
btns.forEach(btn => btn.addEventListener('click', onBtnClickHandler));

Hope this helps.



来源:https://stackoverflow.com/questions/53255306/how-to-apply-javascript-to-multiple-button-groups

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!