views:

62

answers:

2

I am trying to create multiple dependent dropdowns (selects) with a unique way. I want to restrict the use of selectors and want to achieve this by using a single class selectors on all SELECTs; by figuring out the SELECT that was changed by its index. Hence, the SELECT[i] that changed will change the SELECT[i+1] only (and not the previous ones like SELECT[i-1]).

For html like this:

<select class="someclass">
    <option value="volvo">Volvo</option>
    <option value="saab">Saab</option>
    <option value="mercedes">Mercedes</option>
    <option value="audi">Audi</option>
</select>

<select class="someclass">
</select>

<select class="someclass">          
</select>

where the SELECTs other than the first one will get something via AJAX.

I see that the following Javascript gives me correct value of the correct SELECT and the value of i also corresponds to the correct SELECT.

$(function() {
    $(".someclass").each(function(i) {
        $(this).change(function(x) {
            alert($(this).val() + i);
        });
    });         
});

Please note that I really want the minimum selector approach. I just cannot wrap my head around on how to approach this. Should I use Arrays? Like store all the SELECTS in an Array first and then select those?

I believe that since the above code already passes the index i, there should be a way without Arrays also.

Thanks a bunch. AJ

UPDATE:

Here is somewhat better description:

  1. There are more than 2 `SELECT`s on the page with class `someclass`. SELECT[0] has some values initially and its successors are empty as they will change based on the value of their respective immediate ancestor.
  2. If there is a change in `SELECT[i]`, it fires an event and `SELECT[i+1]` is populated with appropriate `OPTION`s.
  3. `SELECT[i+2]` and further successors are reset if they had any data before. So, only immediate child is populated but further successors are reset.

I hope I articulated well. Please let me know if you need more clarification on what I want.

+1  A: 

Inside the change(), you can grab the next select element using the eq() function.

$('.someclass').eq(i + 1);

Alternatively (and better, I think), you can also use next() function.

$(this).next('.someclass');
BalusC
Thanks a lot. I have edited the question and added some more explanation. Do you think it is possible to know the number of SELECTs with 'someclass' class before hand? Just so that I can reset the subsequent SELECTs and only set the immediate successor of a SELECT that changes.
AJ
Yes, just `$('.someclass').length` will return the number.
BalusC
+1  A: 

EDIT: Corrected version.

$(function() {
    var $all = $('.someclass');              // Reference all the selects
    var last = $('.someClass').length - 1;   // Store index of last select

     $(".someclass").change(function() {

        var $th = $(this);           // Reference the changed select

        var index = $all.index($th);     // Grab the index of the changed select

        if(index != last) {              // If the selected wasn't the last,

            var $next = $all.eq(index + 1)      // reference the next select

            $all.filter(':gt(' + index + ')').empty(); // and empty all selects greater than the 
                                                       // index of the changed one.
                                                       // This will include the one that is about
                                                       //     to be populated.
                // Then presumably perform some AJAX
                //    based on $th.val(); to populate
                //    $next with options.
         }
    });         
});
patrick dw
I think you are close to what I want but the precise thing is that I want to change the immediate successor SELECT of a SELECT that is changed and want to reset all the subsequent SELECTs. I have Edited the question and added some more explanation. I hope that helps but do let me know if I am not clear enough. Thanks a lot.
AJ
Updated my answer with various solutions for selecting the other selects. I'm falling asleep, so I don't know if I'm on track. Hope it helps anyway.
patrick dw
I am sleepy too. Guess we are in the same Time Zone. I will take a look at the answer tomorrow. I gave +1 to see your reputation hit 5000. Sweet :) Thanks.
AJ
Woo hoo! Thanks for the vote!
patrick dw
@AJ - OK. Sleep is good. :) I updated my answer. Basically just stored the select elements that you need to manipulate separately in variables. You may not need to store them. I just did it for clarity. Let me know if it works for you.
patrick dw
I really appreciate your help @patrick. I do not want to sound pushy but what just wanted to know what approach I should take if they are not siblings?What if I do this: `$("select.someclass")`. Would jQuery think of those selects with that `.someclass` as siblings no matter if there are `DIV`s and `P`s in the middle?Earlier this morning, I was trying with storing them in an array? How do you see that as an approach? Thanks a lot.
AJ
I see. I actually had it that way before. Not a problem. I'll change it back in a minute.
patrick dw
Just noticed I had a bonehead mistake. Corrected now. Sorry about that.
patrick dw
Thanks a lot for your help.
AJ