-
Notifications
You must be signed in to change notification settings - Fork 1.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Make onChange event handler accept standard event object as argument #1860
Comments
We opted to be consistent across all our onChange events rather than having some with value and others with events. Thank you for your feedback. |
@ktabors I think it would be nice to pass the event object at least as a second parameter. For example I'm now trying to user react-spectrum with react-hook-form and it expects an event object. So I run into this issue. |
I think the problem is that there isn't always a DOM event for all change events. It might be true for input elements but for other components that's not the case. We'd rather be consistent and avoid leaking implementation details of our components if possible. What is react-hook-form doing with these events? If it requires a change event, wouldn't that mean it won't work with anything other than native DOM elements? For example, a custom select dropdown isn't going to have native DOM change events available. |
@devongovett I'm a big fan of consistancy too. But I'm not quite sure that providing the change event would necessarily mean leaking implementation details. I think when you change the standard behaviour of a common element like input, it's a good practice to give at least some fallback. A lot of other ui libraries like material-ui und ant-design etc. also stick to the change event. I think it's simply because it's the default behaviour. I don't know what exactely react-hook-form does with those events, but I'm assuming not much beside reading the value. But the register function expects a change event. What I'm actually trying to build is a more smart Form component, like in this example, because I don't quite like how react-spectrum handles the forms. It's ok for small forms but it's a bit boilerplatty. I don't want to repeat the validation logic or the logic needed to prevent a form from being submitted, if the form is prestine or invalid. I've found a workaroung by using the controller hook, but if react-spectrum would provide the change event, I could reduce some overhead. |
@devongovett by introducing new onValueChange event you can achieve both consistency and interoperability. Use onValueChange everywhere and onChange only in situations when there is a native onChange event. |
The problem is it won't work for all form components. Only text fields and maybe radios/checkboxes. For more complex custom form controls like custom selects, comboboxes, number fields, sliders, etc., there is no DOM change event available. So would those components just not work with react-hook-form? I feel like this is more of a limitation of react-hook-form only working with native DOM form elements and not custom components... |
I just took a look at the react-hook-form documentation. You noted this earlier as a workaround, but it's actually the recommended way to handle this as per react-hook-form documentation. Their recommendation is to use |
@devongovett I don't propose it for all controls, just for those that have a change event. I think they should not hide it completetly and give some fallback option instead. Either as a second parameter or as a different property. Something like @smashercosmo proposed it to do. And not because it's not possible with react-hook-form (and alike) but because it changes the default behaviour that can become handy when you want to extend some functionality, as you can see in my example. Edit: And for other controls there is the mentioned @snowystinger yes, thanks, you are right. I've tryed it once and it didn't worked out and I was irrititated by the name of the onChange parameter, that is still |
I think since there is an alternative here, I'm going to close this. The main reasons we don't pass through DOM events in onChange (and in general across most of our events) are:
|
I totally agree with your response given the design goals of the library. That said, it leaves a feature gap for every user wanting to doing any sort of form validation that implements their design system with react-aria. Given that form validation is basically a requirement for any app of meaningful complexity—should Forms are hard, and you likely don't want to take on a problem of this scope and I understand that. Do you think its appropriate for react-aria to attempt to solve this issue? Or maybe an adjacent project should be spun off to solve compatibility between |
Did you try using the |
If you're ok with tightly coupling your design system to your form library of choice, that's a good approach. Maybe I just need to make that admission and get on with it 😅 |
I'm not sure I'd include it in the actual design system components. React Spectrum definitely doesn't. Applications should be able to combine them themselves. For example: const {
field: { onChange, value, ref },
// ...
} = useController(/* ... */);
<MyDesignSystemTextFieldBuiltWithReactAria onChange={onChange} value={value} ref={ref} /> |
Right that's the bit I'm finding particularly challenging. interface RadioProps extends Omit<AriaRadioProps, 'onChange' | 'onBlur'> {
onChange?: React.ChangeEventHandler<HTMLInputElement>
onBlur?: React.FocusEventHandler<HTMLInputElement>
}
const Radio = React.forwardProps(function Radio({ onChange, onBlur, ...props}, ref) {
const state = React.useContext(RadioGroupContext) as RadioGroupState
const { inputProps } = useRadio(
props,
state,
useObjectRef(ref)
)
return <OtherStuff>
<input {...mergeProps(inputProps, focusProps, { onChange, onBlur )} ref={ref} />
</OtherStuff>
}) Anyways, I'm not expecting any type of support. More to say, is my struggle representative of others' struggles attempting to create a design system based on I find myself often referring to A scenario I'm trying to avoid in my own design system is consumers having to answer the question—how do I connect this component to form state? Maybe I appreciate your patience with my poorly constructed observations 🥶 |
Hmm, according to the
In general, I'm not sure there is a way to avoid |
My mistake, I shouldn't have assumed that This conversation is sorta leading me to believe that building a design system with a DOM-friendly, uncontrolled-field-friendly API is more to blame for the complexity than |
🙋 Feature Request
Currently there is inconsistency in how react-area handles events. Almost all of the event handlers accept standard event object as argument. Except for onChange handler, which only accepts 'value'.
🤔 Expected Behavior
onChange handler should accept standard event object as argument
😯 Current Behavior
onChange handler only accepts value as argument
💁 Possible Solution
Introduce onValueChange event which will pass value to the event handler and change onChange event to pass event object to the event handler (in equivalent to onFocus and onFocusChange events)
🔦 Context
This inconsistency makes it hard to integrate with third-party libraries (like react-hook-form) which pass standard onChange handler to the component.
The text was updated successfully, but these errors were encountered: