It is a great library but I am wondering is it possible for reusable onchnage function?
I have multiple select options and input.
Can I reuse the onchange function and this.setState based on their event target name or others properties?
I tried event, it returns value and name only
this.state{
color: null,
size: null,
type: null,
colorOptions: array,
sizeOptions: array,
typeOptions: array
}
onChange = (e) => {
const name = e.target.name;
this.setState({ [name]: value });
}
According to the docs, the onChange method gets two arguments, option, and {action}. It does not receive the event.
<Select {...otherProps} onChange={(option, {action}) => doSomethingWith(option, action)} />
If you're wrapping the Select, then your component this scope is relevant to maintaining your target.
With <Select> I cannot get my target. I created an example and get onChange working. Is it a better way to reuse the onChange method or update the state with the defaultValue?
Thank you.
@susuwatari2
To update your state for each Select with the same function, you could do it like this:
class MyComponent extends Component {
{...}
onChange = (opt, name) => {
this.setState({ [name]: opt.value });
}
render() {
return <Select onChange={(opt) => this.onChange(opt, 'color')} {...} />
}
}
Thank you @Rall3n !! It works prefect on your demo,
I have the same issue as https://github.com/JedWatson/react-select/issues/1909
I cannot use
onChange = (opt, name) => {
this.setState({
[name]: opt.value
});
};
mine only works with opt, not opt.value
Do you have any ideas?
How to get my defaultValue is working as this.state? Does it matter with the react life cycle?
As @gwyneplaine mentioned in the issue:
The defaultValue and value props both expect objects in the shape of
{ value: string | number, label: string }
So you have to give them the whole option objects. For this, you can use Array.prototype.find, which is supported by almost all browsers except IE, which you might want to polyfill, if you have to.
<Select defaultValue={options.find(elem => elem.value === this.state.value)} {...} />
But I would recommend using value instead of defaultValue, as the latter only sets the value for first render / mount, and value will keep the state and the selected value always synchronized.
@susuwatari2 this issue appears to be resolved
thanks @Rall3n and @cutterbl for the triage
closing
Every other type of input in React pretty much passes target as a sub-property of the first onChange argument.
Except react-select. 馃
@waynebloss
```
onChange={option => {
let val = "";
if (option) {
val = option.value;
}
this.handleChange.call(this, {
target: {
name: "produtoId",
value: val
}
});
}}
@kivervinicius Yes, thanks. Been there, done that. That code is so trivial (well outside of your unusual .call semantics) that perhaps it should have just been built into the component eh?
Surely that's better than hauling around 13 lines of boilerplate code every time you want to use a select box, lmao!
thank you so much @Rall3n, I've been looking for this for quite a while!
In the version 2.0.11 and above to update your state for each Select with the same function, you could do it like this:
class MyComponent extends Component{
state={
sortBy: null
}
handleSelectChange = (selectedOption, { name }) => {
this.setState({ [name]: selectedOption.value });
}
render() {
return <Select name="sortBy" onChange={this.handleSelectChange} {...} />
}
}
Most helpful comment
@susuwatari2
To update your state for each Select with the same function, you could do it like this:
CodeSandbox