在React Hook表格中成功提交的代码显示

281 阅读3分钟

表单输入过程的一个关键部分是表单的提交。当使用第三方库(如React Hook Form)时,这部分的过程总是很有趣。一个常见的基本任务是让用户知道提交成功了。 那么,如何在React Hook Form中做到这一点?让我们来了解一下。

React Hook Form Successful Submission

一个例子

我们有一个简单的表单,已经使用React Hook Form实现了。该表单捕获了一个用户的名字:

type FormData = {
  name: string;
};

export default function App() {
  const { register, handleSubmit, errors } = useForm<FormData>();

  const submitForm = async (data: FormData) => {
    console.log("Submission starting", data);
    const result = await postData(data);
    console.log("Submitting complete", result.success);
  };
  return (
    <div className="app">
      <form onSubmit={handleSubmit(submitForm)}>
        <div>
          <input
            ref={register({ required: true })}
            type="text"
            name="name"
            placeholder="Enter your name"
          />
        </div>
        {errors.name && errors.name.type === "required" && (
          <div className="error">You must enter your name</div>
        )}
      </form>
    </div>
  );
}

表单上的name 字段是强制性的。我们使用React Hook Form中的errors 对象,如果这个字段没有被填入,就输出一个验证错误。

表单提交逻辑调用一个postData 函数,将表单发送到服务器上。下面是我们对postData 的模拟实现:

const postData = ({ name }: FormData): Promise<postDataResult<FormData>> => {
  return new Promise((resolve) => {
    setTimeout(() => {
      console.log(`${name} saved.`);
      resolve({ success: true });
    }, 100);
  });
};

这模拟了对服务器的调用,并返回提交成功的信息。

submitForm 只有在验证通过时才会调用

如果用户在输入任何东西之前按回车键,表单的验证检查就会失败。在这种情况下,我们的submitForm 函数将不会被React Hook Form调用。这意味着submitForm 中的逻辑不需要检查表单是否有效--我们可以假设它是有效的。

很好!

检测表单何时被提交

通常情况下,我们想在提交过程中禁用一个表单。React Hook Form有一个方便的formState 变量,包含表单是否被提交:

const {
  register,
  handleSubmit,
  errors,
  formState,} = useForm<FormData>();

我们可以在提交过程中使用它来禁用输入元素:

<input
  ref={register({
    required: { value: true, message: "You must enter your name" }
  })}
  type="text"
  name="name"
  placeholder="Enter your name"
  disabled={formState.isSubmitting}/>

我们使用formState 中的isSubmitting 变量来确定表单是否正在被提交,并将其绑定到输入的disabled 属性。

值得注意的是,当formState 发生变化时,表单会被重新渲染。

当提交完成后,isSubmitting 将被设置为false ,这意味着输入元素再次被启用。

检测表单何时被提交

我们想在表单成功提交后向用户呈现一条信息。formState 变量也包含一个isSubmitted 变量。让我们试一试吧:

<form onSubmit={handleSubmit(submitForm)}>
  ...
  {formState.isSubmitted && (
    <div className="success">Form submitted successfully</div>
  )}
</form>

因此,当isSubmitted 为真时,我们输出一条成功信息。

如果用户在填写他们的名字之前按了回车键,我们就会得到成功信息验证错误。

Submitted issue

这与我们的要求不尽相同!

所以,isSubmitted 只表明表单是否被提交--而不是是否成功提交。这确实有道理,因为React Hook Form只控制了提交的一部分。例如,在提交的过程中,服务器部分可能会发生一些它不知道的问题。

检测表单何时被成功提交

我们需要为表单是否成功提交创建我们自己的状态:

const [
  isSuccessfullySubmitted,
  setIsSuccessfullySubmitted,
] = React.useState(false);

当表单第一次被加载时,该状态被初始化为false

我们在表单被发布到服务器后设置这个状态:

const submitForm = async (data: FormData) => {
  console.log("Submission starting", data);
  const result = await postData(data);
  console.log("Submitting complete", result.success);
  setIsSuccessfullySubmitted(result.success);};

然后我们可以使用isSuccessfullySubmitted 来呈现成功信息:

{isSuccessfullySubmitted && (
  <div className="success">Form submitted successfully</div>
)}

现在,在用户成功提交表单之前,成功信息不会出现:

Successful submission

酷!我们还可以把 添加到服务器上。

我们还可以在输入元素的disabled 属性绑定中添加isSuccessfullySubmitted ,这样,当表单成功提交后,它就会被禁用:

<input
  ...
  disabled={formState.isSubmitting || isSuccessfullySubmitted}/>

包裹起来

isSubmitted 在React Hook Form的 表示表单是否被提交,而不一定是是否成功提交。我们使用我们自己的状态来表示成功提交,我们可以在提交函数中设置这个状态。 formState