I'm new to React, and I'd like to ask a strategy question about how best to accomplish a task where data must be communicated between sibling components.
First, I'll describe the task:
Say I have multiple <select>
components that are children of a single parent that passes down the select boxes dynamically, composed from an array. Each box has exactly the same available options in its initial state, but once a user selects a particular option in one box, it must be disabled as an option in all other boxes until it is released.
Here's an example of the same in (silly) code. (I'm using react-select
as a shorthand for creating the select boxes.)
In this example, I need to disable (ie, set disabled: true
) the options for "It's my favorite" and "It's my least favorite" when a user selects them in one select box (and release them if a user de-selects them).
var React = require('react');
var Select = require('react-select');
var AnForm = React.createClass({
render: function(){
// this.props.fruits is an array passed in that looks like:
// ['apples', 'bananas', 'cherries','watermelon','oranges']
var selects = this.props.fruits.map(function(fruit, i) {
var options = [
{ value: 'first', label: 'It\'s my favorite', disabled: false },
{ value: 'second', label: 'I\'m OK with it', disabled: false },
{ value: 'third', label: 'It\'s my least favorite', disabled: false }
];
return (
<Child fruit={fruit} key={i} options={options} />
);
});
return (
<div id="myFormThingy">
{fruitSelects}
</div>
)
}
});
var AnChild = React.createClass({
getInitialState: function() {
return {
value:'',
options: this.props.options
};
},
render: function(){
function changeValue(value){
this.setState({value:value});
}
return (
<label for={this.props.fruit}>{this.props.fruit}</label>
<Select
name={this.props.fruit}
value={this.state.value}
options={this.state.options}
onChange={changeValue.bind(this)}
placeholder="Choose one"
/>
)
}
});
Is updating the child options best accomplished by passing data back up to the parent through a callback? Should I use refs to access the child components in that callback? Does a redux reducer help?
I apologize for the general nature of the question, but I'm not finding a lot of direction on how to deal with these sibling-to-sibling component interactions in a unidirectional way.
Thanks for any help.