Home > Software design >  How to make a cleaner code that counts multiple button clicks using vanilla JS?
How to make a cleaner code that counts multiple button clicks using vanilla JS?

Time:03-29

I'm using a counter for button clicks and it's working fine, but I would like to ask how I can make it cleaner and less repetitive and still do the same function?

To give a perspective, I'm using this to track usage of hundreds of buttons, therefore the code can look really messy if I stick to use my current script.

How would I go about and make this simpler and cleaner?

function clickCounter1() {
  if (typeof(Storage) !== "undefined") {
    if (localStorage.clickcount1) {
      localStorage.clickcount1 = Number(localStorage.clickcount1)   1;
    } else {
      localStorage.clickcount1 = 1;
    }
    document.getElementById("result1").innerHTML = "Btn 1: "   localStorage.clickcount1;
  }
}

function clickCounter2() {
  if (typeof(Storage) !== "undefined") {
    if (localStorage.clickcount2) {
      localStorage.clickcount2 = Number(localStorage.clickcount2)   1;
    } else {
      localStorage.clickcount2 = 1;
    }
    document.getElementById("result2").innerHTML = "Btn 2: "   localStorage.clickcount2;
  }
}

function clickCounter3() {
  if (typeof(Storage) !== "undefined") {
    if (localStorage.clickcount3) {
      localStorage.clickcount3 = Number(localStorage.clickcount3)   1;
    } else {
      localStorage.clickcount3 = 1;
    }
    document.getElementById("result3").innerHTML = "Btn 3: "   localStorage.clickcount3;
  }
}
<button onclick="clickCounter1()" type="button">Btn 1</button>
<button onclick="clickCounter2()" type="button">Btn 2</button>
<button onclick="clickCounter3()" type="button">Btn 3</button>

<br>

<div id="result1"></div>
<div id="result2"></div>
<div id="result3"></div>

Important functions are just two:

  1. Count the clicks for each button
  2. Store in local storage

Thank you very much in advance!

CodePudding user response:

you can try this

function clickCounter(num) {
    if (typeof (Storage) !== "undefined") {
        if (localStorage.getItem(`clickcount${num}`)) {
            localStorage.setItem(`clickcount${num}`, Number(localStorage.getItem(`clickcount${num}`))   1);
        } else {
            localStorage.setItem(`clickcount${num}`, 1);
        }
        document.getElementById(`result${num}`).innerHTML = `Btn ${num}: `   localStorage.getItem(`clickcount${num}`);
    }
}
<button onclick="clickCounter(1)" type="button">Btn 1</button>
<button onclick="clickCounter(2)" type="button">Btn 2</button>
<button onclick="clickCounter(3)" type="button">Btn 3</button>
<br>
<div id="result1"></div>
<div id="result2"></div>
<div id="result3"></div>

You can do it even shorter like this:

function clickCounter(num) {
    if (typeof (Storage) !== "undefined") {
        let storedItem = localStorage.getItem(`clickcount${num}`);
        storedItem ? localStorage.setItem(`clickcount${num}`, Number(storedItem)   1) : localStorage.setItem(`clickcount${num}`, 1);
        document.getElementById(`result${num}`).innerHTML = `Btn ${num}: ${storedItem}`;
    }
}

Update in case you want to show buttons names you can simply do this:

<button onclick="clickCounter(this, 1)" type="button" data-name="First">Btn 1</button>
<button onclick="clickCounter(this, 2)" type="button" data-name="Second">Btn 2</button>
<button onclick="clickCounter(this, 3)" type="button" data-name="Third">Btn 3</button>
<br>
<div id="result1"></div>
<div id="result2"></div>
<div id="result3"></div>

Your javascript should looks like this:

function clickCounter(btn, num) {
    if (typeof (Storage) !== "undefined") {
        let storedItem = localStorage.getItem(`clickcount${num}`),
            btnName = $(btn).attr('data-name');
        storedItem ? localStorage.setItem(`clickcount${num}`, Number(storedItem)   1) : localStorage.setItem(`clickcount${num}`, 1);
        document.getElementById(`result${num}`).innerHTML = `${btnName}: ${storedItem}`;
    }
}

CodePudding user response:

You can try the below approach to do so. By creating a single function clickCounter() and passing it the button's Id/name. It will work the same.

Working code:

function clickCounter(btnId) {
  if (typeof(Storage) !== "undefined") {
    if (localStorage[btnId]) {
      localStorage[btnId] = Number(localStorage[btnId])   1;
    } else {
      localStorage[btnId] = 1;
    }
    document.getElementById("result1").textContent = "Btn 1: "   localStorage[btnId];
  }
}
<button onclick="clickCounter('clickcount1')" type="button">Click me!</button>
<button onclick="clickCounter('clickcount2')" type="button">Click me!</button>
<button onclick="clickCounter('clickcount3')" type="button">Click me!</button>

<br>

<div id="result1"></div>
<div id="result2"></div>
<div id="result3"></div>

CodePudding user response:

there are several things to say about the code you show us.

  1. Use localStorage.setItem() and localStorage.getItem() to manipulate data on the local storage (the API is done like it)
  2. Prefer to register events on DOM element in the javascript code, not directly in the HTML code (it is a best practise)

Here is an example of implementation I did and it works:

<button type="button" id="btn1">Btn 1</button>
<button type="button" id="btn2">Btn 2</button>
<button type="button" id="btn3">Btn 3</button>

<br>

<div id="resultbtn1"></div>
<div id="resultbtn2"></div>
<div id="resultbtn3"></div>

function handleClickCounter(id) {
    if (typeof(Storage) !== "undefined") {
        if (localStorage.getItem(id)) {
            localStorage.setItem(id, Number(localStorage.getItem(id))   1);
        } else {
            localStorage.setItem(id, 1);
        }
        document.getElementById("result" id).textContent = "Btn "   id   ": "   localStorage.getItem(id);
    }
}


const buttons = document.querySelectorAll("button");    // change by more specific selector if needed

for (const button of buttons) {
    console.log(button.id)
    button.addEventListener("click", () => handleClickCounter(button.id));
}

Of course this code can be improved. Good luck and feel free to ask clarification :)

  • Related