-1

I am trying to change the background color of a <div> when someone chooses a color from the drop-down menu. It's a notes taking website and i want people can change color of the notes.

Here is the HTML code:

<select id="mySelect" class="clr-btn" style="text-align:center" onchange="change_color()">
        <option id="red" value="Red">Red</option>
        <option id="green" value="Green">Green</option>
        <option id="blue" value="Blue">Blue</option>
        </select>

Here is the Javascript:

function change_color() {
    console.log("Change-Color");
    let elm1 = document.getElementsByClassName("clr-btn");
    let elm2 = elm1.options[elm1.selectedIndex].value;
    let elm3 = document.getElementByClassName("card-body");
    document.elm3.style.background = elm2;
}

The error is getting is that "Cannot read properties of un-defined" at elm2. I can't get what is undefined in elm2. Can anyone please help me out?

Code_2
  • 23
  • 5
  • Your problem is: `let elm1 = document.getElementsByClassName("clr-btn");` if you were to use `getElementById('mySelect')` (as an example) you'd be fine. The issue is that `getElementsByClassName()` returns a collection/NodeList of elements, not just one. – David Thomas Jan 05 '22 at 12:31
  • I want to apply this on number of elements as mentioned in post i want to apply this on notes, so there are number of notes. – Code_2 Jan 05 '22 at 12:42
  • Great, so please show your "*[mcve]*" code (including relevant HTML and CSS), and explain why the answers in the linked question (of which this seems to be a duplicate) don't answer your question. – David Thomas Jan 05 '22 at 12:56
  • The linked question doesn't answer my question. I don't know why it's linked. My project is a note-taking website. So when someone enters a note and click "Add Note". The value is stored in local storage as an array. The upper given HTML runs on each element of array. And I want to apply "change color" on all notes so if 1 note is set to green, the other can be set to red, etc. And the linked question doesn't answer my question as I am facing issues when I call selected value from given options. – Code_2 Jan 05 '22 at 13:46
  • The reason your code isn't working is because of the reasons outlined in that linked duplicate: you have a collection of elements and you're trying to access them all as if they're one single element. Your use-case is different, but the cause is the same. – David Thomas Jan 05 '22 at 15:08
  • Thanks. I get that By do YOU have a solution or hint for my problem? – Code_2 Jan 05 '22 at 15:41
  • Yes, but the problem is that this question is a duplicate. If the other question doesn't answer your question update ([edit]) your question, to explain how you tried to solve the problem, how the answers in the other question failed to help. I'm not trying to be insulting, I want to help you but this site doesn't/shouldn't allow duplicates to remain. Read the "*[ask]*' guidance, and if you update your question (and tag me`@`) I may be able to reopen your question if it's sufficiently distinct, and you've made efforts to solve the problem. – David Thomas Jan 05 '22 at 15:54

1 Answers1

0

Here is a fixed version of your script:

document.body.onclick=ev=>{ // delegated click event handler to "select" a card:
 if (ev.target.classList.contains("card-body")){ // works on .card-body elements only!
  ev.target.classList.toggle("sel");
 }
}
document.querySelector("select").onchange = ev => {
  document.querySelectorAll(".card-body.sel").forEach(d=>{
    d.style.backgroundColor = ev.target.value;
    d.classList.remove("sel");
  });
}
div {display:inline-block; width:200px; margin:10px; padding:8px}
.sel {border: 1px solid gray}
<select id="mySelect" class="clr-btn" style="text-align:center">
  <option value="#ffcccc">Red</option>
  <option value="#ccffcc">Green</option>
  <option value="#ccccff">Blue</option>
</select>

<div class="card-body">this is the div to be colored ...</div>
<div>something else - not to be colored</div>
<div class="card-body">and another one ...</div>
<div class="card-body">yet another one,</div>
<div class="card-body">hard to believe - but again a card!</div>
<div class="card-body">and this lst one.</div>
Carsten Massmann
  • 26,510
  • 2
  • 22
  • 43
  • Thanks, CARSTEN It worked. But I want this to apply to multiple same elements. Like there are 12 notes and all 12 notes can have different colors. YOUR code makes all 12 notes have only 1 color which is selected, I can't change other notes color. – Code_2 Jan 05 '22 at 13:24
  • The scope of the colour change is given by the class `.card-body`. So, if you have different classes for different card groups you can define individual colour change select fields for each of these classes. – Carsten Massmann Jan 05 '22 at 13:30
  • All have some class `.card-body` that is why I used getelementsbyclassname. – Code_2 Jan 05 '22 at 13:39
  • Also can YOU explain what does = ev => and d => d does here? I can't really get these? – Code_2 Jan 05 '22 at 13:56
  • I changed the script to enable you to "select" some cards by clicking on them (they will have a thin border then). Only the *selected* cards will change colour. `ev=>{..}` is an ES2015 shorthand for `function(ev){...}`. (Strictly speaking it is more, as it does not create its own `this`!) – Carsten Massmann Jan 05 '22 at 14:02