Description
Background
I see from this issue thread that recent changes were pushed in 15.6.x
that have – to my mind – broken some of the expected behavior when it comes to firing onChange
events in a group of radio button inputs.
I am aware of the conversation in #1471, but the problem it's describing is not exactly the same as this so far as I can tell.
Note that the problem I'm about to describe does not occur in React <=15.4.x
.
Expectations
We would expect an individual radio button's onChange
to fire in these two conditions (among others):
- A radio input is clicked and it's state changes
- A label for any radio input is clicked, causing (1).
Indeed, native elements work precisely this way:
<html>
<head></head>
<body>
<input type="radio" id="radio1" name="radiogroup"/>
<label for="radio1">One</label>
<input type="radio" id="radio2" name="radiogroup"/>
<label for="radio2">Two</label>
</body>
<script>
var r1 = document.getElementById('radio1');
var r2 = document.getElementById('radio2');
var handler = function(event){
console.log(event);
};
r1.addEventListener('change', handler);
r2.addEventListener('change', handler);
</script>
</html>
If you click the above radio buttons and observe the console output, you'll see that the event is firing as expected: only when a desired input's state is being changed to something new.
React Expectations
The following React component will work as expected in 15.4.x
but not 15.6.x
:
const RadioTest = (props) => {
let handler = (event) => {
console.log(event);
}
return(){
<div>
<input
type="radio"
name="radiogroup1"
id="radio1"
onChange={handler}/>
<label htmlFor="radio1">One</label>
<input
type="radio"
name="radiogroup1"
id="radio2"
onChange={handler}/>
<label htmlFor="radio2">Two</label>
</div>
}
};
In 15.4.x
React, this the inputs in this component will work as you'd expect and as the native DOM elements work. This Codepen shows it working properly with 15.4.1
In 15.6.x
, the onChange
event seems to only fire once. Here is another Codepen showing it doesn't work when 15.6.1 is imported.
It is, of course, entirely possible that I am doing something incorrectly (and have been doing so for a couple of years now), but the breaking change to my components only came with recent updates.