-
-
Notifications
You must be signed in to change notification settings - Fork 2.8k
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
RFC: Improving Field #1371
Comments
I agree passing
But, it's not clear for me. |
Sounds good to me. Would be simpler (or unnecessary) to adapt existing components to Formik |
Based on original post it is most likely a NO. |
Correct |
I found useful to have access to |
If you find useful to access This is actually powerful pattern which allows us to use Formik with UI libraries of out choice with small amount of work. |
Sorry, I'm not sure to understand. What is/will be the good pattern for this kind of component ?
Not using |
Yes. And you use Also, you can compose your import TextField from '@material-ui/core/TextField';
import React from 'react';
const FormField = props => {
return (
<Field {...props}>
{({ field, form, meta, ...otherProps }) => {
const error = form.touched[field.name] && form.errors[field.name];
return (
<TextField
{...field}
{...otherProps}
error={!!error}
helperText={error}
/>
);
}}
</Field>
);
};
const LoginForm = () => (
<Form>
<FormField name="email" type="text" label="Email" variant="outlined" />
</Form>
); |
This will have an added bonus of resolving types on the field, as |
This seems like the right API to me. I also think that with a |
Do we prefer |
Personally I'd say |
|
Implemented in v2 |
…1406) - Deprecate `<Field component>` and `<Field render>`. These haven't been removed. However, they will yield a warning in the console. - Add `<Field as>` prop which just passes related handlers and props straight through. This should make Styled Components folks happy. Related to #1371 Closes #1407 Closes #1408
I have a question regarding deprecation of @jaredpalmer I have so many custom components in my apps ready to be passed as
So to sum up, please, DO NOT remove |
@klis87 I think you raise some valid points about perf and perhaps we should just deprecate As for optimization concerns, I think you raise very very valid points. Since
In general, My goal is for people to move away from Suggested API
|
@jaredpalmer Thx for you consideration. I really like your API proposal, I think everyone will be happy. Regarding Generally I very like
|
@klis87 i doubt we will move away from |
@crosscompile @klis87 I think we need to move |
@crosscompile should we look at using |
@jaredpalmer regarding Fast Field I am wondering about it and about using PureComponent in the user land. From what I understand, there is no way to stop Field from being rerendered anyway as Field subscribes to Formik context. Anytime something changes, even when only an input is blurred, all fields will call render because they subscribe to any formik context change, this is how React context works, bypassing any PureComponent optimisations. The only thing which can be done is not to rerender Field children. But isn't that the same as creating custom component with optimized
@jaredpalmer so actually you wont give up field level validation? I remember I read that potentially you could leave only form level validation, because field level one was complicated and affected performance |
@klis87 Yes. That was my first strategy. It mostly worked. There are some edge cases that I never handled properly, like enter key submits. However, I think that could be solved. I think it’s worth exploring again. |
Can anything be done to allow better type checking of the |
Version: 2.0.1-rc.7 Seems like the
The same issue exists in Also deprecating
|
Will investigate tomorrow. Out on a Saturday night right now 😂
…--
Jared
________________________________
From: ltctech <notifications@github.com>
Sent: Saturday, June 22, 2019 9:57 PM
To: jaredpalmer/formik
Cc: Jared Palmer; Mention
Subject: Re: [jaredpalmer/formik] RFC: Improving Field (#1371)
Version: 2.0.1-rc.7
Seems like the <Field> passes a new onBlur and onChange function whenever anything on the form changes. Is this somehow by design? With a form with 10+ fields it's noticeably laggy, especially on IE11. If I want to avoid needlessly re-rendering my custom control passed in via as I have to write my own memo equal function that ignores onBlur and onChange. Have not noticed any side effects yet but there may be some. Is there anyway to avoid this now that <FastField> is gone (now an alias of <Field>)? Also, <FastField> would not check user props, which was bad.
import isEqual from 'react-fast-compare';
//utility function
export function customFieldEqual(prevProps, nextProps) {
const { onBlur: prevOnBlur, onChange: prevOnChange, ...prevFilteredProps } = prevProps;
const { onBlur: nextOnBlur, onChange: nextOnChange, ...nextFilteredProps } = nextProps;
return isEqual(prevFilteredProps, nextFilteredProps);
}
//inside e.g. a react-select or react-datepicker wrapper
export default memo(CustomControl, customFieldEqual);
The same issue exists in useField but I can't find a way to avoid a re-render.
Also deprecating component and replacing it with as does not work for custom controls. I ended up writing a <CustomField> in ES6 that replicates <Field> minus warnings/types but includes meta with isSubmitting and isValidating flags (last two statements statement). Not sure if there is a better way to do it but it works.
export default function CustomField({
validate,
name,
render,
children,
as: is,
component,
...props
}) {
const {
validate: _validate,
validationSchema: _validationSchema,
...formik
} = useFormikContext();
React.useEffect(() => {
formik.registerField(name, {
validate: validate,
});
return () => {
formik.unregisterField(name);
};
}, [formik, name, validate]);
const [field, meta] = formik.getFieldProps({ name, ...props });
const legacyBag = { field, form: formik };
if (render) {
return render(legacyBag);
}
if (isFunction(children)) {
return children({ ...legacyBag, meta });
}
if (component) {
// This behavior is backwards compat with earlier Formik 0.9 to 1.x
if (typeof component === 'string') {
const { innerRef, ...rest } = props;
return React.createElement(
component,
{ ref: innerRef, ...field, ...rest },
children
);
}
// We don't pass `meta` for backwards compat
return React.createElement(
component,
{ field, form: formik, ...props },
children
);
}
// default to input here so we can check for both `as` and `children` above
const asElement = is || 'input';
if (typeof asElement === 'string') {
const { innerRef, ...rest } = props;
return React.createElement(
asElement,
{ ref: innerRef, ...field, ...rest },
children
);
}
const customMeta = { ...meta, isSubmitting: formik.isSubmitting, isValidating: formik.isValidating };
return React.createElement(asElement, { ...field, ...props, meta: customMeta }, children);
}
—
You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub<#1371?email_source=notifications&email_token=AA67IGYHDZQURK37ROWXR4LP33KB7A5CNFSM4G4WGOEKYY3PNVWWK3TUL52HS4DFVREXG43VMVBW63LNMVXHJKTDN5WW2ZLOORPWSZGODYKUY6Q#issuecomment-504712314>, or mute the thread<https://github.com/notifications/unsubscribe-auth/AA67IG2PSB3D7Y24BFWMU53P33KB7ANCNFSM4G4WGOEA>.
|
Upon further testing
last line:
Should maybe be:
Edit
I've taken a look at |
@jaredpalmer regarding field optimization, that might be interesting to you in case you didn't hear about it yet gnoff/rfcs#2 that could be another way to achieve much better performance and this will work with hooks too |
Yes, this would be super sweet |
@jaredpalmer I was about to do some rounds looking for lib authors who think they might benefit from useContextSelector. I have a build with it implemented and so we can actually try out libraries with the new API and see how they perform. Would you be interesting in a collab to see if it actually benefits things at some point? |
updated RFC PR: reactjs/rfcs#119 |
@jaredpalmer |
Hi @Andreyco , |
I want to take folk's temperature on some warts that I want to change related to
<Field>
as well as discuss how best to move forward in a way that doesn't force people to rewrite stuff immediately.<Field component>
This prop is the source of a ton of confusion because it does not simply pass through
onChange
,onBlur
, andvalue
but ratherfield
andform
. This means that there is some inconsistent behavior with respect to<Field component="select">
vs.<Field component={MyInput}>
. I think a decent solution is to create a new prop calledis
oras
and make that prop just pass throughonBlur
,onChange
,value
/checked
as expected. We then would put a deprecation warning oncomponent
instructing people to useas
/is
orchildren
and eventually removecomponent
entirely in future versions. Unfortunately, this will force folks to change every single"select"
and"textarea"
over time, but this at least avoids breaking changes<Field render>
This is just redundant at this point. We should put up a deprecation warning suggesting to use
children
as a function.<Field children>
We should merge #343 and add a
meta
to<Field children>
.Next Steps
In a perfect world, we make these changes gradually in a way that prevents people from having to rewrite stuff. I definitely don't want to have to rewrite all my inputs, but we need to make these changes at some point. We also need to consider that
<Field>
will have a dramatically reduced usage in the future once theuseField
hook is released.Umbrella Issues
meta
(Add meta prop to Field, FastField #343)render
andcomponent
(Create <Field as> and deprecate <Field component> and <Field render> #1406)The text was updated successfully, but these errors were encountered: