I have two related drop-down lists, in which the contents in the second drop-down list depends on the selection made in the first one. For example, in the following HTML code, you will choose application method first. If you choose Aerial as the application method, then you will answer further question such as aerial size dist. Otherwise, you need to answer ground spray type.
So once the webpage is loaded, the two second level drop-down lists (aerial size dist., and ground spray type.) are hidden. They will appear only when related choice is made in the first one (application method).
I am able to achieve this feature in jQuery (below jQuery code). But my approach is pretty stupid. My question is:
Is there a way to select the whole row, without using counting its sequence (nth-child())? Can I choose the whole row, based on selecting an element ID ? For example, can I first select $('#id_A') and then expand my selection to the whole row?
Is there a better way (a loop?) to achieve this hide or show feature rather than paring all the possible choices (($(this).val() == "X") )?
Thanks!
Here is the HTML code, and the form is generated by Django:
<div class="articles">
<form method="GET" action=_output.html>
<table align="center">
<tr><th><label for="id_application_method">Application method:</label></th><td><select name="application_method" id="id_application_method">
<option value="">Pick first</option>
<option value="A">Aerial</option>
<option value="B">Ground</option>
</select></td></tr>
<tr><th><label for="id_A">Aerial Size Dist:</label></th><td><select name="aerial_size_dist" id="id_A">
<option value="A1" selected="selected">A1</option>
<option value="A2">A2</option>
</select></td></tr>
<tr><th><label for="id_B">Ground spray type:</label></th><td><select name="ground_spray_type" id="id_B">
<option value="B1" selected="selected">B1</option>
<option value="B2">B2</option>
</select></td></tr>
</table>
</form>
</div>
Here is the jQuery code:
<script type="text/javascript" src=" .7.2/jquery.js"></script>
<script>$(function() {
$("tr:nth-child(2)").hide();
$("tr:nth-child(3)").hide();
$('#id_application_method').change(function() {
($(this).val() == "A") ?
$("tr:nth-child(2)").show() : $("tr:nth-child(2)").hide();
($(this).val() == "B") ?
$("tr:nth-child(3)").show() : $("tr:nth-child(3)").hide();
});});</script>
I have two related drop-down lists, in which the contents in the second drop-down list depends on the selection made in the first one. For example, in the following HTML code, you will choose application method first. If you choose Aerial as the application method, then you will answer further question such as aerial size dist. Otherwise, you need to answer ground spray type.
So once the webpage is loaded, the two second level drop-down lists (aerial size dist., and ground spray type.) are hidden. They will appear only when related choice is made in the first one (application method).
I am able to achieve this feature in jQuery (below jQuery code). But my approach is pretty stupid. My question is:
Is there a way to select the whole row, without using counting its sequence (nth-child())? Can I choose the whole row, based on selecting an element ID ? For example, can I first select $('#id_A') and then expand my selection to the whole row?
Is there a better way (a loop?) to achieve this hide or show feature rather than paring all the possible choices (($(this).val() == "X") )?
Thanks!
Here is the HTML code, and the form is generated by Django:
<div class="articles">
<form method="GET" action=_output.html>
<table align="center">
<tr><th><label for="id_application_method">Application method:</label></th><td><select name="application_method" id="id_application_method">
<option value="">Pick first</option>
<option value="A">Aerial</option>
<option value="B">Ground</option>
</select></td></tr>
<tr><th><label for="id_A">Aerial Size Dist:</label></th><td><select name="aerial_size_dist" id="id_A">
<option value="A1" selected="selected">A1</option>
<option value="A2">A2</option>
</select></td></tr>
<tr><th><label for="id_B">Ground spray type:</label></th><td><select name="ground_spray_type" id="id_B">
<option value="B1" selected="selected">B1</option>
<option value="B2">B2</option>
</select></td></tr>
</table>
</form>
</div>
Here is the jQuery code:
<script type="text/javascript" src=" https://ajax.googleapis./ajax/libs/jquery/1.7.2/jquery.js"></script>
<script>$(function() {
$("tr:nth-child(2)").hide();
$("tr:nth-child(3)").hide();
$('#id_application_method').change(function() {
($(this).val() == "A") ?
$("tr:nth-child(2)").show() : $("tr:nth-child(2)").hide();
($(this).val() == "B") ?
$("tr:nth-child(3)").show() : $("tr:nth-child(3)").hide();
});});</script>
Share
Improve this question
asked Apr 17, 2012 at 23:08
TTTTTT
4,43413 gold badges76 silver badges129 bronze badges
2 Answers
Reset to default 5I think iKnowKungFoo's answer is very straightforward (it's got my vote). I noticed you said your form is generated by Django though. In case it's not straightforward for you to modify your generated HTML markup, here is another solution to your problem.
$(document).ready(function() {
var $aerialTr = $('#id_A').closest('tr').hide();
var $groundSprayTr = $('#id_B').closest('tr').hide();
$('#id_application_method').change(function() {
var selectedValue = $(this).val();
if(selectedValue === 'A') {
$aerialTr.show();
$groundSprayTr.hide();
} else if (selectedValue === 'B') {
$aerialTr.hide();
$groundSprayTr.show();
} else {
$aerialTr.hide();
$groundSprayTr.hide();
}
});
});
Here is a jsFiddle to test: http://jsfiddle/willslab/n54cE/2/
It should work with your existing markup. It selects the tr's based on the current IDs for the select boxes. If you change those IDs, you will need to modify the selectors accordingly.
I hope that helps!
Edit: Here is another alternative, "hybrid" approach inspired by iKnowKungFoo. His solution is very elegant, so I bined it with my own. This works without changes to HTML or CSS.
$(document).ready(function() {
$('#id_A').closest('tr').addClass('method_options').hide();
$('#id_B').closest('tr').addClass('method_options').hide();
$('#id_application_method').change(function() {
$('tr.method_options').hide();
$('#id_' + $(this).val()).closest('tr').show();
});
});
jsFiddle link: http://jsfiddle/willslab/6ASJu/3/
Your questions describe the right ideas. You just have to structure your HTML to take advantage of them.
JSFiddle posted here: http://jsfiddle/iknowkungfoo/TKamw/
HTML - I added an ID and CLASS to each TR that match the values in your primary SELECT:
<div class="articles">
<form method="get" action="_output.html">
<table align="center">
<tr>
<th><label for="id_application_method">Application method:</label></th>
<td><select name="application_method" id="id_application_method">
<option value="">Pick first</option>
<option value="A">Aerial</option>
<option value="B">Ground</option>
</select></td>
</tr>
<tr id="tr_A" class="method_options">
<th><label for="id_A">Aerial Size Dist:</label></th>
<td><select name="aerial_size_dist" id="id_A">
<option value="A1" selected="selected">A1</option>
<option value="A2">A2</option>
</select></td>
</tr>
<tr id="tr_B" class="method_options">
<th><label for="id_B">Ground spray type:</label></th>
<td><select name="ground_spray_type" id="id_B">
<option value="B1" selected="selected">B1</option>
<option value="B2">B2</option>
</select></td>
</tr>
</table>
</form>
</div>
CSS - hide those TRs by default:
tr.method_options { display: none; }
JavaScript/jQuery - When the primary SELECT changes, hide all TRs with a CLASS of "method_options". Then, Find the TR whose ID matches the value of the selected option in the primary SELECT and show it. If there is no match, then nothing is shown.
$(document).ready(function(){
$('#id_application_method').on('change', function() {
$('tr.method_options').hide();
$('#tr_' + $(this).val() ).show();
});
});