React Hook Form 需要 Controller 的规则总是触发

时间:2021-06-02 16:17:00

标签: reactjs react-hook-form

我开始使用 react-hook-form 来验证我的输入,但即使我在输入字段中键入/输入某些内容,require 规则也总是会触发。

import React, { useState } from "react";
import { Controller, useForm } from "react-hook-form";
import { Button, Form, Label, Input } from "reactstrap";

const setErrorStyle = (name) => {
  return {
    borderColor: name ? "red" : "",
    boxShadow: name ? "0 0 1.5px 1px red" : ""
  };
};

const App = () => {
  const [comment, setComment] = useState("");
  const {
    handleSubmit,
    control,
    formState: { errors }
  } = useForm();

  const submitForm = (data) => {
    console.log(data);
  };

  return (
    <Form onSubmit={handleSubmit(submitForm)}>
      <Label for="commentNote" className="mr-sm-10">
        Note/Comment
      </Label>
      <Controller
        name="commentNote"
        control={control}
        defaultValue={comment}
        rules={{ required: true }}
        render={({ field: { ref, onChange, ...field } }) => (
          <Input
            {...field}
            type="textarea"
            rows={5}
            id="commentNote"
            innerRef={ref}
            value={comment}
            onChange={(e) => setComment(e.target.value)}
            aria-invalid={!!errors.commentNote}
            style={setErrorStyle(errors.commentNote)}
          />
        )}
      />
      {errors.commentNote && (
        <span style={{ color: "red" }} role="alert">
          required
        </span>
      )}
      <Button type="submit" color="primary" size="sm" className="w-auto">
        Submit
      </Button>
    </Form>
  );
};

export default App;

这是用于测试的 SandBox:https://codesandbox.io/s/modern-wind-6v2gp

谢谢

1 个答案:

答案 0 :(得分:2)

原因是因为您覆盖了表单的状态处理。你实际上做的是你以这种方式维护自己的状态。如果您希望 react-hook-form 保持状态,您需要从代码中删除 onChangeInput 中的 useState 处理:

import React from "react";
import { Controller, useForm } from "react-hook-form";
import { Button, Form, Label, Input } from "reactstrap";

const setErrorStyle = (name) => {
  return {
    borderColor: name ? "red" : "",
    boxShadow: name ? "0 0 1.5px 1px red" : ""
  };
};

const App = () => {
  const {
    handleSubmit,
    control,
    formState: { errors }
  } = useForm();

  const submitForm = (data) => {
    console.log(data);
  };

  return (
    <Form onSubmit={handleSubmit(submitForm)}>
      <Label for="commentNote" className="mr-sm-10">
        Note/Comment
      </Label>
      <Controller
        name="commentNote"
        control={control}
        rules={{ required: true }}
        render={({ field: { ref, ...field } }) => (
          <Input
            {...field}
            type="textarea"
            rows={5}
            id="commentNote"
            innerRef={ref}
            aria-invalid={!!errors.commentNote}
            style={setErrorStyle(errors.commentNote)}
          />
        )}
      />
      {errors.commentNote && (
        <span style={{ color: "red" }} role="alert">
          required
        </span>
      )}
      <Button type="submit" color="primary" size="sm" className="w-auto">
        Submit
      </Button>
    </Form>
  );
};

export default App;