如何在 Ant Design 中使用 React Hook Form?

2023-04-16 13:53:45 +08:00
 jsun969

博客原文:https://jsun.lol/blog/how-to-use-react-hook-form-in-ant-design-cn
掘金:https://juejin.cn/post/7222484074480713783

前言

先解释一下标题。我想 Ant Design 这个组件库一定是被每个 React 程序员所熟知的。作为一款由阿里背书的前端组件库,其在做后台管理等业务,尤其方便。

但是 React Hook Form 这个库,可能在国内并没有那么火。尽管 Ant Design 拥有自己的 Form 组件,但是 React Hook Form 是一个非常优秀的表单处理库

其优点在于:

  1. 强性能,减少渲染次数
  2. 轻量无依赖
  3. 类型安全
  4. 支持多种验证库校验(如 Zod 、Yup 、Class Validator 、Ajv 等等)
  5. 支持多种 UI 库

GitHub ( 3w+⭐):https://github.com/react-hook-form/react-hook-form
官网:https://react-hook-form.com

从功能上来说,其比 Ant Design 的 Form.useForm 要强大不少。但是 Ant Design 目前并没有官方支持 React Hook Form 。

解决

为了解决在 Ant Design 中使用 React Hook Form 。我为此写了一个开源库来包装 Ant Design 的 Form.Item

GitHub: https://github.com/jsun969/react-hook-form-antd

示例

CodeSandbox 示例

其中使用了 Zod 进行表单校验

使用

原表单

首先,你可能原来有这样一个表单

<Form onFinish={onFinish}>
  <Form.Item
    label="Username"
    name="username"
    rules={[
      { required: true, message: 'Required' },
      { max: 15, message: 'Username should be less than 15 characters' },
    ]}
  >
    <Input />
  </Form.Item>
  <Form.Item
    label="Password"
    name="password"
    rules={[{ required: true, message: 'Required' }]}
  >
    <Input.Password />
  </Form.Item>
  <Form.Item name="remember" valuePropName="checked">
    <Checkbox>Remember me</Checkbox>
  </Form.Item>
  <Form.Item>
    <Button type="primary" htmlType="submit">
      Submit
    </Button>
  </Form.Item>
</Form>

使用 React Hook Form

使用 React Hook Form 的 useForm 并获取 control

const { control } = useForm({
  defaultValues: { username: 'jsun969', password: '', remember: true },
});

替换 Form.Item

react-hook-form-antd 中使用 FormItem 代替 Form.Item,将 control 传递给每个 FormItem

这样一来,每个 FormItem 都受到 React Hook Form 的控制,并且 name (即表单字段名)可以从 control 中推断

import { FormItem } from 'react-hook-form-antd';

// ...
<Form onFinish={onFinish}>
  <FormItem control={control} label="Username" name="username">
    <Input />
  </FormItem>
  <FormItem control={control} label="Password" name="password">
    <Input.Password />
  </FormItem>
  <FormItem control={control} name="remember" valuePropName="checked">
    <Checkbox>Remember me</Checkbox>
  </FormItem>
  <Form.Item>
    <Button type="primary" htmlType="submit">
      Submit
    </Button>
  </Form.Item>
</Form>;

用表单验证库(本文中使用 Zod ,其他验证库使用方法见 React Hook Form Resolver) 代替原先的 rules

import { zodResolver } from '@hookform/resolvers/zod';
import * as z from 'zod';

// ...

const schema = z.object({
  username: z
    .string()
    .min(1, { message: 'Required' })
    .max(15, { message: 'Username should be less than 15 characters' }),
  password: z.string().min(1, { message: 'Required' }),
  remember: z.boolean(),
});

const App = () => {
  const { control } = useForm({
    defaultValues: { username: 'jsun969', password: '', remember: true },
    resolver: zodResolver(schema),
  });
  // ...
};

onFinish 中使用 React Hook Form 的 handleSubmit

const { control, handleSubmit } = useForm(...);

return (
    <Form
      style={{ maxWidth: 600 }}
      onFinish={handleSubmit((data) => {
        ...
      })}
    >
    // ...
    </Form>
);

搞定

如此一来,即可在 Ant Design 中很方便地使用 React Hook Form 。
以上使用教程的结果即为 CodeSandbox 示例

1569 次点击
所在节点    前端开发
3 条回复
xubeiyan
2023-04-16 22:42:24 +08:00
圣诞节那个事件之后拒绝用 antd ,material UI 我觉得可以
jsun969
2023-04-17 18:49:24 +08:00
@xubeiyan 国内使用 antd 的公司还是相当多的。MUI 也有 React Hook Form 的库: https://github.com/dohomi/react-hook-form-mui
kkxi22
2023-05-21 14:27:43 +08:00
react hook form 严格来说和 antd 没关系,可以和任何组件库或者自己的写的组件结合。只需要对每个表单组件封装一个 hook form 的胶水层就可以了,可以用 hook 的方式处理表单联动是他最大的优势。采用 yup 的 schame 校验方式,让表单校验变得异常优雅。确实是一个很好用工具

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/932908

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX