I have a form with a couple of conditionally rendered fields. The form is made up of MUI components, react-hook-form and yup for its validation.
Additionally, I have added a console.log() within the AutocompleteCoffee, RadioBtnGroup, TxtField components that will execute every time the components are rendered.
Scenario
When the page loads you can see a log from each component. Nothing new here.
When you select "Yes" from, Do you like coffee? a new field will be rendered. This action triggers a rerender of all the components on the page.
I am using the watch method from react-hook-form to keep track of the question mentioned above.
const coffee = watch("coffee", "No");
...
{coffee === "Yes" ? (
<AutocompleteCoffee
required
fullWidth
name="coffeType"
label="Which coffee type"
control={control}
options={coffeList}
error={!!errors.coffeType}
helperText={errors?.coffeType?.message}
/>
) : null}
...
You can see the working CodeSandbox here.
Question
I was wondering how to prevent all the wasted renders. Any ideas?
Thank you in advance!
I've got this performance issue once. As per docs, you should switch to callback way of calling watch or to useWatch
This API will trigger re-render at the root of your app or form,
consider using a callback or the useWatch API
if you are experiencing performance issues.
code would look like:
instead of your coffee check, do <MaybeCoffee control={control} errors={errors} /> and remove watch("coffee", "No") as well.
Then add a component MaybeCoffee:
const MaybeCoffee = ({ control, errors }) => {
const coffee = useWatch({ control, name: "coffee" }) || "No";
return coffee === "Yes" ? (
<AutocompleteCoffee
required
fullWidth
name="coffeType"
label="Which coffes type"
control={control}
options={coffeList}
error={!!errors.coffeType}
helperText={errors?.coffeType?.message}
/>
) : null;
}
an example https://codesandbox.io/s/testing-rerenders-forked-19invg?file=/src/components/MainForm.js