How to display each buttons in one function in JavaScript

Viewed 69

So, I'm trying to build a calculator and the first thing I want to do is to display all the buttons in my output. I have created a function called displayButtons and inside, I got the first 2 buttons by id however, when I try to display them, only the number 2 displays. One way to fix this is to create a function for each numbers and then it'll work but that's not what I want. I've also tried nesting the functions for each number within a function, but I wasn't able to call it properly onclick. Any ideas? Thanks in advance!

HTML code:

<div id="output"></div>
        <div class="numbers">
            <button value="1" id="one" onclick="displayButtons()">1</button>
            <button value="2" id="two" onclick="displayButtons()">2</button>

JS code:

function displayButtons() {

    var one = document.getElementById("one").value;
    document.getElementById("output").innerHTML = one;


    var two = document.getElementById("two").value;
    document.getElementById("output").innerHTML = two

}
6 Answers

Have you tried a for loop? you'd be able to add a click functionality with a closure or 'let' keyword or a separate function.. run the following in codepen, see how it works and if this is something that can be useful.


    function createButtons() {
       //let is block scoped, not function scoped
        for (let i = 1; i <= 5; i++) {
          var body = document.getElementsByTagName("BODY")[0];
          var button = document.createElement("BUTTON");
          button.innerHTML = 'Button ' + i;
          button.onclick = function() {
               alert('This is button ' + i);
          }
          body.appendChild(button);
        }
     }
      
     createButtons();

There is multiple solutions for this, but here a simple one: you can use the event data to get the info of the button clicked, then you can do what you want with these values.

HTML

<div id="output"></div>
<div class="numbers">
  <button value="1" id="one">1</button>
  <button value="2" id="two">2</button>
</div>

JS

document.querySelectorAll('.numbers button').forEach(button => { 
  button.addEventListener('click', (e) => {
    console.log(e.target.id, e.target.value)
  })
})

To display the output on clicking of numbers, you can pass in a this object inside the function like this

<button value="1" id="one" onclick="displayButtons(this)">1</button>

and when you click on it, you'll receive the button node inside the function full code would be

   <div class="numbers">
        <button value="1" id="one" onclick="displayButtons(this)">1</button>
        <button value="2" id="two" onclick="displayButtons(this)">2</button>
    </div>


    <script>
        function displayButtons(button) {
            document.getElementById("output").innerHTML += button.value
        }
    </script>

You keep overwriting the innerHTML, to that's why you only see the 2.

I recommend that you change your approach. All of your buttons are in div.numbers. Add a single click event listener to the numbers div. This event listener will fire if any of the buttons are pressed, because the click event bubbles. This is called event delegation.

In the click event handler, you can see which button has been clicked and add the value of the clicked button to div#output.

const output = document.querySelector('#output');
const numbers = document.querySelector('.numbers');

numbers.addEventListener('click', ({ target }) => {
  if (!target.hasAttribute('value')) {
    return;
  }
  
  output.textContent += target.value;
});
<div id="output"></div>
<div class="numbers">
  <button value="1">1</button>
  <button value="2">2</button>
  <button value="3">3</button>
  <button value="4">4</button>
  <button value="5">5</button>
</div>

Each time you press a button, you're overwriting the entire innerHTML, so you're replacing the whole content by the new one.

You should append the value instead, using += operator

Furthermore you may consider to use innerText instead of innerHTML, and use addEventListener instead of onclick=

<div id="output"></div>
<div class="numbers">
    <button value="1" id="one">1</button>
    <button value="2" id="two">2</button>
</div>

... and after ...

<script>
document.querySelector(".numbers").addEventListener('click', e => {
    if( e.target.nodeName === "BUTTON" )
        document.getElementById("output").innerText += e.target.value;
});
</script>

You have to get the id of every button in onclick parameter like: onclick= displayButtons(id) it will create different click event for every buttton then

function displayButton(id){
let oldValue = document.getElementById("output").innerHtml
document.getElementById("output").innerHTML = oldValue + id;}
Related