Reputation: 125
I have 2 squares in a <table>
and I want that when I click one, it become black and the other don't.
My current code is working but I gave them the same function and id
, so when I click the first, it work well, but when I click the second, it's the first one that changes.
I know whats wrong, but I don't know how to correct it without having to create a function for each id
.
Let's say I want 100 squares, I won't write one function to each one, so what can I do?
function myFunc() {
var element = document.getElementById("cc");
element.classList.toggle("th");
}
table,
th,
td {
border: solid black 1px;
width: 100px;
height: 100px;
}
.th {
background-color: black;
}
<table>
<tr>
<th onclick="myFunc(this)" id="cc"></th>
<th onclick="myFunc(this)" id="cc"></th>
</tr>
</table>
Upvotes: 2
Views: 825
Reputation: 6516
First of all, and more important: id
must be unique, thats why it is called id (identifier).
Said that, I will show you two options to solve your question:
1. The better option:
Don't add any inline (direct in HTML) onclick
listener. Add a
common class to all <th>
, then in Javascript add a single listener
to each element that has the class, and use this
inside the function, since this
scope will be the clicked element.
Example:
let allTh = document.querySelectorAll(".clickableTh").forEach(x => x.onclick = myFunc)
function myFunc() {
this.classList.toggle("th");
}
table, th, td {
border:solid black 1px;
width:100px;
height:100px;
}
.th {
background-color:black;
}
<table>
<tr>
<th class="clickableTh"></th>
<th class="clickableTh"></th>
<th class="clickableTh"></th>
<th class="clickableTh"></th>
<th class="clickableTh"></th>
<th id="cc" class="notClickableTh"></th>
</tr>
</table>
2. Keeping your current structure:
As said in the comments, you pass this
as parameter (onclick="myFunc(this)"
), then inside myFunc
you don't need to find the element, you'll already have it in as parameter.
Click below to see the snippet code of example
function myFunc(elem) {
elem.classList.toggle("th");
}
table, th, td {
border:solid black 1px;
width:100px;
height:100px;
}
.th {
background-color:black;
}
<table>
<tr>
<th onclick="myFunc(this)"></th>
<th onclick="myFunc(this)"></th>
<th onclick="myFunc(this)"></th>
<th onclick="myFunc(this)"></th>
<th onclick="myFunc(this)"></th>
<th id="cc"></th>
</tr>
</table>
Upvotes: 2
Reputation: 16855
For less markup you can bind the click event on all th
var th = document.getElementsByTagName("th");
for (var i = 0; i < th.length; i++) {
th[i].addEventListener("click", function() {
this.classList.toggle("th");
});
}
th,
td {
border: solid black 1px;
width: 100px;
height: 100px;
}
.th {
background-color: black;
}
<table>
<tr>
<th></th>
<th></th>
<th></th>
<th></th>
</tr>
</table>
Upvotes: 1
Reputation: 445
Your function is storing the first square in a variable with the cc
identifier.
Instead, you should pass a reference of the element clicked and store that element in the variable. That way, the element clicked will be toggled.
function myFunc(ref) {
var element = document.getElementById(ref.id).innerHTML;
element.classList.toggle("th");
}
Notice that must also add this
to the call of the function.
Upvotes: 0