Radio Group On Change
Yesterday radio buttons were the bane of my existence. Trying to accurately observe change in a radio group was somewhere between challenging and [Heisenbergain](http://en.wikipedia.org/wiki/Uncertainty_principle “Werner Heisenberg - Wikipedia, the free encyclopedia”)™. I sometimes thought that looking at what was happening was causing the outcome to change. I am sure all the electron huggers out there will tell me how I am taking Heisenberg’s work lightly, but it is the best explanation I can think of right now.
Instead of complain tirelessly like usual, I decided to write some code. This will most likely become simpler once [prototype 1.6](http://www.prototypejs.org/2007/8/15/prototype-1-6-0-release-candidate “Prototype JavaScript framework: Prototype 1.6.0 release candidate”) is released to the wild. I would simplify it by making my own event, but I still needed to work so I wrote this instead.
Here is the code I came up with to observe a group of radio buttons. It can either take an array or a css selector of radio buttons to observe. It should probably also take a DOM id but since I didn’t need it I didn’t write it. Like most code I write, it is heavily based on prototype.
<code><br />
var RadioGroup = Class.create();<br />
Object.extend(RadioGroup.prototype, {<br />
initialize: function(radioButtons, onChange) {<br />
if(radioButtons instanceof Array) {<br />
this.radioButtons = radioButtons.collect(function(rb) {<br />
return $(rb);<br />
});<br />
} else {<br />
this.radioButtons = $$(radioButtons);<br />
}<br />
this.radioButtons.each(function(rb) {<br />
rb.observe("click",this._click.bindAsEventListener(this));<br />
}.bind(this));<br />
this.selected = this.findSelected();<br />
this.onChange = onChange;<br />
},<br />
_click: function(event) {<br />
var element = Event.element(event);<br />
if(element.checked) {<br />
if(element != this.selected) {<br />
this.onChange(element, this.selected);<br />
this.selected = element;<br />
}<br />
} else {<br />
var currentSelected = this.findSelected();<br />
if(currentSelected) {<br />
this.onChange(currentSelected, this.selected);<br />
this.selected = currentSelected;<br />
}<br />
}<br />
},<br />
findSelected: function() {<br />
return this.radioButtons.find(function(rb) {<br />
return rb.checked;<br />
}.bind(this));<br />
}<br />
});<br />
<br />
//USAGE<br />
new RadioGroup("#someForm input[type=radio]",<br />
function(newlyClicked, previouslyClicked) {<br />
//fire bug logging<br />
console.log(newlyClicked);<br />
console.log(previouslyClicked);<br />
});<br />
<br />
//OR<br />
new RadioGroup($(someForm).getElementsBySelector("input[type=radio]"),<br />
function(newlyClicked, previouslyClicked) {<br />
//fire bug logging<br />
console.log(newlyClicked);<br />
console.log(previouslyClicked);<br />
});</code>
Basically, you tell it which radio buttons to observe and you tell it which function to call when a change in those radio buttons occurs. Pretty straight forward, but I included the two usages, if you have any improvements please let me know.