2

I am making a table form where the user will adjust multiple sliders in the table. I want to update the value to be displayed on the screen for each slider. I tried to do this with getElementsByClassName, but when I adjust one slider, the output value is shown in all of the other sliders. I guess I can assign an id to each slider (there are about 20), but I was wondering if there was a more efficient way to do this.

Here is a sample of the html code for the table inputs:

<form>
<table>
    <tr>
        <th rowspan="5" id="A"></th>
        <td></td>    
        <td><input type="range" min="0" max="10" value="5" step="1" onChange="sliderChange(this.value)"/><br />Current Value: <span class="sliderStatus">5</span></td>
        <td></td>
        <td><input type="range" min="0" max="10" value="5" step="1" onChange="sliderChange(this.value)"/><br />Current Value: <span class="sliderStatus">5</span></td>
    </tr>
    <tr>
        <td></td>
        <td><input type="range" min="0" max="10" value="5" step="1" onChange="sliderChange(this.value)"/><br />Current Value: <span class="sliderStatus">5</span></td>    
        <td></td>
        <td><input type="range" min="0" max="10" value="5" step="1" onChange="sliderChange(this.value)"/><br />Current Value: <span class="sliderStatus">5</span></td>

    </tr>
    <tr>
        <td></td>
        <td><input type="range" min="0" max="10" value="5" step="1" onChange="sliderChange(this.value)"/><br />Current Value: <span class="sliderStatus">5</span></td>    
        <td></td>
        <td><input type="range" min="0" max="10" value="5" step="1" onChange="sliderChange(this.value)"/><br />Current Value: <span class="sliderStatus">5</span></td>
    </table>
   </form>

and the JS Code:

//called when the user clicks the start button on the home page.
function start(){
var decisionA = prompt("Enter A:","");
var decisionB = prompt("Enter B:","");

//send user prompt inputs to A and B cells in the table<th>.
document.getElementById('A').innerHTML = decisionA;
document.getElementById('B').innerHTML = decisionB;
}

function sliderChange (val){
     var sliders = document.getElementsByClassName('sliderStatus');
     for (i = 0; i < sliders.length; i++){
     sliders[i].innerHTML = val;
     }
   }

Is there a way to make the slider value text show the adjusted slider value for each individual slider in the table using getElementsByClassName or do I need to assign 20 different ids to all the sliders? Thanks.

Mamun
  • 66,969
  • 9
  • 47
  • 59
Brent
  • 31
  • 6

2 Answers2

1

Alright here is the final answer. But you should really learn to debug your own code. Otherwise you will never be able to finish anything you're building if all your problems end up here.

#1 First of all you need to change the onChange="sliderChange(this.value)" to onChange="sliderChange(this)" and the reason for that is when you are passing the input into SliderChange(), then all you get is a value, rather than the entire input you're touching or using. And it's not smart to pass in a singular value when in reality you may need much more than that. And what do you need more than a value? you need to figure out what input has actually been changed and not only the value of the changed input. And the reason you need to know first what input has been changed is so that you can modify it again and make calls back to it. Because the value from your input doesn't tell you anything about what input has actually been changed so you can change it back again.

#2 Now that you finally have the input data, you need to figure out on what index it is since it doesn't have a specific ID to identify it by, index option allows you to basically make use of a hidden or counted for you ID. And therefore you first need to first add this line of code: var index = document.getElementsByTagName('input');

#3 Finally now that we have both the input that has been changed and the 'sliderStatus' class that we need to modify. We then need to figure out which 'sliderStatus' needs to be changed. But the problem is that no 'sliderStatus' class has been touched or modified. Therefore we need to link it somehow to the input that has been modified to the span that needs to be modified. Luckelly that's where we can make use of the index, since they follow the same order, right after another, we can count them the same way and make use of the same index.

for (i = 0; i < index.length; i++){
   if(e == index[i]){
      sliders[i].innerHTML = e.value;
   }
}
So now that we didn't pass the val, but the entire input info trough this option into sliderChange(), we can now compare all the counted indexes with the actual index that we have made changes on. And then when we have a match, only then we change something and we do it using the same index. And this is where we only now at the very end need our value that we need to modify something with. So don't be in a rush to change something. First you need to figure out what you need to change before you are trying to change it. And then use google to figure out how to find indexes etc.

function sliderChange(e){
   var index = document.getElementsByTagName('input');
   var sliders = document.getElementsByClassName('sliderStatus');

   for (i = 0; i < index.length; i++){
      if(e == index[i]){
         sliders[i].innerHTML = e.value;
      }
   }
}
Vadim Cool
  • 129
  • 10
  • 1
    Thanks @Vadim Cool. When I got up this morning, I decided I was going to start playing around with the `this` object, and I knew that I had to figure out a way to loop through the index and check if the value of the current index was the one being altered. You confirmed I was on the right track and saved me some time. Thanks for the response. – Brent Jan 07 '18 at 19:01
0

Yes it is output to all of them because all of them has the same class 'SliderStatus' and you're calling therefore a script SliderChange() that in return again gets the status of all the 'sliderStatus' classes. You need to focus on one particular change in one particular input. You can easily achieve that by making use of THIS in JS. jQuery example:

$('sliderStatus').change(function(){
   $(this).val();
});

This is just a quick example on how to retrieve data in a different way without using onClick etc.. You can probably figure out the rest.

Another example is where you can go trough each and every one of your sliders and change them as you go..

$('sliderStatus').each(function(){
   $(this).val();
});

This method allows you to check all of them at the same time. Hopefully this helps a little bit on your way to learn more JS.

Vadim Cool
  • 129
  • 10
  • Is there any way to do this without a library? I'm trying to avoid using libraries for now. I'll look up what you've showed me, but just curious if there is a way to do what I want in vanilla JS. Thank you! – Brent Jan 07 '18 at 07:39