React Hook 表单:如何避免重复将 Control 和 Errors 属性传递到多个文本字段?

问题描述 投票:0回答:1

我正在使用 react-hook-form 来验证反应中的表单。到目前为止我就是这样做的。我创建了一个用react-hook-form

TextField
组件包裹
Controller
的组件。然后我用我的形式。

组件: TextfieldController

import { Controller } from "react-hook-form";

const TextfieldController = ({
    control,
    errors,
    id,
    label,
    placeholder = "",
    size = 50,
    ...otherProps
}: TextfieldControllerProps) => {
    return (
        <Field>
            <Controller
                name={id}
                control={control}
                render={({ field }) => (
                    <TextField
                        {...field}
                        {...otherProps}
                        id={id}
                        label={label}
                        size={size}
                        placeholder={placeholder}
                    />
                )}
            />
            {errors[id] && <Error>{errors[id]?.message?.toString()}</Error>}
        </Field>
    )
}

用途:

<FormView title="API Artifact" onClose={handleOnClose}>
    <TextfieldController
        required
        autoFocus
        id="apiName"
        label="Name"
        placeholder="Name"
        control={control}
        errors={errors}
    />
    <TextfieldController
        required
        id="apiContext"
        label="Context"
        placeholder="Context"
        control={control}
        errors={errors}
    />
    // continue...
</FormView>

在这种情况下,应该为

control
组件的每次使用提供
errors
TextfieldController
道具,即使整个表单的两个道具都是相同的。有没有办法避免这种情况?

我尝试使用自定义挂钩。从钩子中获取

control
组件时传递
errors
TextfieldController
,使用时传递其他道具。但由于重新渲染,它会导致失去对
onChange
的关注。

const { TextfieldController } = useTextfieldController({ control, errors });

如果有更好的方法,我不想完全使用这个自定义钩子。有更好的方法吗?

typescript react-hook-form react-custom-hooks
1个回答
0
投票

您可以使用

useFromContext
挂钩 访问
control
内的
errors
TextfieldController

import { Controller, useFormContext } from "react-hook-form";

const TextfieldController = ({
  id,
  label,
  placeholder = "",
  size = 50,
  ...otherProps
}) => {
  const { formState: { errors }, control } = useFormContext();

  return (
    <Field>
      <Controller
        name={id}
        control={control}
        render={({ field }) => (
          <TextField
            {...field}
            {...otherProps}
            id={id}
            label={label}
            size={size}
            placeholder={placeholder}
          />
        )}
      />
      {errors[id] && <Error>{errors[id]?.message?.toString()}</Error>}
    </Field>
  );
};

如文档中所述,您需要用

formProvider
包裹您的表单。
例如,您可以在
FormView
组件中执行此操作。

© www.soinside.com 2019 - 2024. All rights reserved.