Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Observing change in radio button selection using Prototype JS

I'm relatively new to Prototype JS (v1.7), and I'm stuck on something. I'm trying to detect when a change in the radio button selection occurs. Here's the code:

Radio buttons:

<input class="amounts" type="radio" name="amount" id="amount-1" value="1" />
<input class="amounts" type="radio" name="amount" id="amount-2" value="2" />
<input class="amounts" type="radio" name="amount" id="amount-3" value="3" />

Javascript: Here's a stab I took at it, which doesn't work:

Event.observe($$('amounts'), 'change', function(event) {
    alert('change detected');
});

When the form loads, no radio buttons are checked. I'd like the Javascript to detect these events:

  1. A radio button is selected when none was previously selected
  2. The radio button selection changes

Any help would be greatly appreciated.

like image 691
Rohan Avatar asked Mar 10 '11 05:03

Rohan


2 Answers

It doesn't work because $$ returns an array of elements and Event needs a single element. Also $$('amounts') doesn't match any elements, there are no <amounts> tags.

A better way is to use a single ancestor element which is easy to identify.

<form id="amounts-form">
    <input class="amounts" type="radio" name="amount" id="amount-1" value="1" />
    <input class="amounts" type="radio" name="amount" id="amount-2" value="2" />
    <input class="amounts" type="radio" name="amount" id="amount-3" value="3" />
</form>

Now there is a unique ID to work with we can use Event.on

$('amounts-form').on('change', '.amounts', function(event) {
    alert('change detected');
});

Notice the events are being filtered by '.amounts', the period says to use the class name.
If you're using FireBug for FireFox or Chrome's developer tools then you can test parts of your script directly in the console. It really helps to find if a selector is matching the elements you think it is by typing $$('.amounts')

like image 105
clockworkgeek Avatar answered Sep 30 '22 13:09

clockworkgeek


Alternegro's answer attempts to use an iterator to attach the event handler directly to the "amount" radio elements but doesn't work for a few reasons:

  1. The "$" function doesn't take css selectors as parameters, only ids. Use "$$" instead.
  2. The css "id" attribute selector should include square braces "[]". It's also spelled wrong. "amounts-" should be "amount-" to match the ids in the example. Or just use a class selector instead: ".amounts".
  3. There is no "change" method that can be called on enumerables. Use invoke or some other enumerable method instead.

This one should work:

$$("[id^=amount-]").invoke(
    'on', 
     'change',
     function(){alert("hello " + this.id)}
)

(YMMV using "this" in the event handler. I only checked the code in Firefox)

like image 37
benrifkah Avatar answered Sep 30 '22 12:09

benrifkah