This is possible with a switch statement, but that's not the best way to do it. What I'd suggest is making the following function your event handler for the change
event. You'll also need to run it on window load, to initialise it.
function updateSel() {
var sel = document.getElementById('sel');
var hidden = sel.getElementsByClassName('hidden');
for (var i=0;i<hidden.length;i++) {
var showIt = sel.value == hidden[i].dataset.toggle || sel.selectedOptions[0] == hidden[i];
hidden[i].style.display = showIt ? 'inline' : 'none';
}
}
With this HTML code for your options:
<select id="sel">
<option value="A" selected="selected">A</option>
<option value="B">B</option>
<option value="C">C</option>
<option value="D">D</option>
<option value="E" class="hidden" data-toggle="A">E</option>
<option value="X" class="hidden" data-toggle="B">X</option>
</select>
Here is a demo of this code.
What this does is the following: Everytime the value of the select
is changed, it checks if the option
tags with class="hidden"
are supposed to be visible. It's supposed to be visible when it's selected, or when the option that makes it show (which is stored in its data-toggle attribute) is selected.
switch
method
If you would want to do this with a switch statement, you'd have to define which element to show, and then hide all others. That would look like this:
function updateSel() {
var sel = document.getElementById('sel');
var hidden = sel.getElementsByClassName('hidden');
var doShow;
switch (sel.value) {
case: 'A': case 'E':
doShow = hidden['toggle-A'];
break;
case: 'B': case 'X':
doShow = hidden['toggle-B'];
break;
}
for (var i=0;i<hidden.length;i++) {
list[i].style.display = hidden[i] == doShow?'inline':'none';
}
}
For this to work you'd have to change the data-toggle
attribute to an id
though, like this:
<option value="E" class="hidden" id="toggle-A">E</option>
This fiddle shows how that'd work. It basically does the same thing, but instead of letting the script find the tag that needs to be shown all by itself, you have to define each one seperately in your switch statement. I'd suggest using the medhod above without switch statement, but if you want to be able to make for example the X <option>
show if the user selects either B or C, then the switch method is probably better. In that case, you can simply add another case 'C':
and then it'll show when the user selects C too. If you only need to show 1 specific option at a time (which it seemed like in your question), the first method is much easier to set up.
New method
In response to your comments, I've made another script that does what you requested:
here is the script's demo.
And the code itself:
<form action="javascript:void(0);" id="questionForm">
<select name="Q1">
<option selected disabled>----</option>
<option>Selected A Group</option>
<option>Selected B Group</option>
</select>
</form>
Here I've made the code as clean as possible: just the default select is shown at the start. The action=""
attribute should be changed to where you submit the function.
And the JavaScript:
//http://stackoverflow.com/q/4793604/1256925
function insertAfter(referenceNode, newNode) {
referenceNode.parentNode.insertBefore(newNode, referenceNode.nextSibling);
}
var furtherSelects = {
'Selected A Group': ['Selected C Group', 'Selected D Group'],
'Selected B Group': ['Selected E Group', 'Selected F Group'],
'Selected C Group': ['Selected G Group', 'Selected H Group'],
'Selected D Group': ['Selected I Group', 'Selected J Group', 'Selected K Group'],
'Selected E Group': ['Selected G Group', 'Selected H Group'],
'Selected F Group': ['Selected I Group', 'Selected J Group', 'Selected K Group'],
}
function checkField(){
addSelects = furtherSelects[this.value];
if (!addSelects) { //For the final load of selects, add a button to submit
var button = document.createElement('button');
button.innerHTML = 'Submit';
button.id='submitQuestionForm';
insertAfter(this, button);
return;
}
var sel = document.createElement('select');
var Q_num = parseInt(this.name.substr(1))+1;
var siblingSelects = this.parentNode.getElementsByTagName('select');
for (var i=siblingSelects.length-1;i>=0;i--) {
if (parseInt(siblingSelects[i].name.substr(1)) >= Q_num) {
siblingSelects[i].remove();
}
}
var submitButton = document.getElementById('submitQuestionForm');
if (submitButton) submitButton.remove();
sel.setAttribute('name', 'Q'+Q_num);
sel.addEventListener('change', checkField); //Make each extra element have another checkField
var option = document.createElement('option');
option.innerHTML = '----';
option.disabled = true;
option.selected = true;
sel.appendChild(option); //Add the default option first
for (var i=0;i<addSelects.length;i++) {
option = document.createElement('option');
option.innerHTML = addSelects[i];
sel.appendChild(option);
}
insertAfter(this, sel);
}
addEventListener('load', function() {
document.getElementById('questionForm')
.getElementsByTagName('select')[0]
.addEventListener('change', checkField);
});
Here I've put all the options for the selects that show after selecting another option in a single object. Here all the values for the selects are defined, with an array of options to add when that option is selected. For example if I select Selected A Group
I'll see a select with 2 options: Selected C Group
and Selected D Group
.
What the event handler does is this: It first checks if there's a list of options defined for the selected option in the furtherSelects
object (so, if furtherSelects
has a property with the name equal to the selected value). If so, it adds a submit button, and otherwise it adds the specified select tag.
It first goes through a list of all the other select tags though, to see if the question they belong to (the 3rd select belongs to the 3rd question) is a question that lies behind the question that is being modified. If so, it removes that select element. It also removes the button by default if it is there, since this part of the function will only run if there is another select to add, which means you haven't answered the final question yet.
It then creates the select tag and adds the event handler, and goes through the array of values for the select element's options, and creates each option tag and then puts that option tag in the select tag. After that, it adds the select tag to after the one that is being changed.
At the bottom there is a simple onload
event listener, which adds the onchange
event listener to the first select element.
I hope this is what you were looking for.