I am new to javascript and I have an assignment to create seven circles which should change colour on a mouse click. The first circle is changing colour but the other six just r
Elements in HTML must have a unique id
attribute, otherwise, your HTML is considered invalid.
Instead, you should use a class
, this way you can iterate through your selected elements (here I have used .forEach
), and apply the click
handler to each.
Note: Now that you're using a class, you need to use getElementsByClassName()
which will give you a HTMLCollection of matching elements.
See working example below:
const circles = [...document.getElementsByClassName("circle1")], // use spread syntax to convert collection to array
colors = ['orange', 'yellow', 'green', 'blue', 'indigo', 'violet'];
circles.forEach(circle => {
circle.onclick = function() {
color = colors.shift();
colors.push(color);
circle.style.fill = color;
}
});
<h2> Rainbow Colours</h2>
<svg height="1000" width="500">
<circle class="circle1" onclick="function()" cx="50" cy="50" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="150" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="250" r="40"
style="fill:red;"/>
<circle class="circle1" onclick="function()" cx="50" cy="350" r="40"
style="fill:red;"/>
<circle class="circle1" onclick="function()" cx="50" cy="450" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="550" r="40"
style="fill:red;"/>
<circle class="circle1" onclick="function()" cx="50" cy="650" r="40"
style="fill:red;"/>
</svg>
Use querySelectorAll('circle') to query all circles by their element name.
Also do not use the same id on all circles, element ids must be unique.
You can then use a forEach to iterate on your circles and attach your click handler with circle.addEventListener('click', handler).
Using this technique, you don't need ids or classes to refer to your circles, and you can also remove your onclick handler on each circle in your HTML:
<circle cx="50" cy="50" r="40" style="fill:red;"/>
Here is an example:
const circles = document.querySelectorAll('circle');
const colors = ['orange', 'yellow', 'green', 'blue', 'indigo','violet'];
circles.forEach(circle => {
circle.addEventListener('click', () => {
color = colors.shift();
colors.push(color);
circle.style.fill = color;
});
});
<svg height="1000" width="500">
<circle cx="50" cy="50" r="40" style="fill:red;"/>
<circle cx="50" cy="150" r="40" style="fill:red;"/>
<circle cx="50" cy="250" r="40" style="fill:red;"/>
<circle cx="50" cy="350" r="40" style="fill:red;"/>
<circle cx="50" cy="450" r="40" style="fill:red;"/>
<circle cx="50" cy="550" r="40" style="fill:red;"/>
<circle cx="50" cy="650" r="40" style="fill:red;"/>
</svg>
An id (identifier) needs to be unique, document.getElementById() always catches the first one only.
Use a class and loop
id attributes are for referencing single Items, while Class attributes are for referencing group of items..
so changing ID to Class would look like this.. -
<svg height="1000" width="500">
<circle class="circle1" onclick="function()" cx="50" cy="50" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="150" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="250" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="350" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="450" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="550" r="40"
style="fill:red;"/>
<circle class ="circle1" onclick="function()" cx="50" cy="650" r="40"
style="fill:red;"/>
</circle>
</svg>
and then you get the group of items by their class name using this..
var circle = document.getElementsByClassName("circle1");
Try it like this ` let circles = Array.from(document.querySelectorAll('circle'));
circles.forEach((circle) =>{ circle.onclick = function () { color = colors.shift(); colors.push(color); circle.style.fill = color; } } `
You need to work on class instead of a fix id. Use below code:
<!DOCTYPE html>
<html>
<head>
<title>Circles of rainbow colours</title>
</head>
<body>
<h2> Rainbow Colours</h2>
<svg height="1000" width="500">
<circle onclick="changecolor(this);" cx="50" cy="50" r="40"
style="fill:red;"/>
<circle onclick="changecolor(this);" cx="50" cy="150" r="40"
style="fill:red;"/>
<circle onclick="changecolor(this);" cx="50" cy="250" r="40"
style="fill:red;"/>
<circle onclick="changecolor(this);" cx="50" cy="350" r="40"
style="fill:red;"/>
<circle onclick="changecolor(this);" cx="50" cy="450" r="40"
style="fill:red;"/>
<circle onclick="changecolor(this);" cx="50" cy="550" r="40"
style="fill:red;"/>
<circle onclick="changecolor(this);" cx="50" cy="650" r="40"
style="fill:red;"/>
</circle>
</svg>
<script>
colors = ['orange', 'yellow', 'green', 'blue', 'indigo','violet'];
function changecolor(e) {
color = colors.shift();
colors.push(color);
e.style.fill = color;
}
</script>
</body>
</html>
hope it helps you.