阅读 134

FormRender-简易小程序表单解决方案

背景

在 ToB 场景中,需要录入众多数据,一个表单字段可能数十个,如果每个字段都写一个jsx 组件来表示,那代码量会瞬间臃肿涨至一两千行,维护起来极其不方便。因此需要一个“表单生成器”,在提高代码复用性同时也能极大提高工作效率。 为此参考了XRender 后写了一个简易版本的 FormRender 组件,分享一下使用方法以及实现思路。

开始使用

demo 地址: github.com/hexianzhi/t…

最简使用 demo:

import { Button, View } from "@tarojs/components";
import React, { useRef, useState } from "react";
import FormRender from "../../compoments/formRender";
import "./index.scss";

const formData = [
 {
   key: "a",
   title: "地址",
   type: "input",
   required: true,
   typeProps: {
     placeholder: "请输入",
   },
 },
 {
   key: "c",
   title: "国家",
   type: "picker",
   typeProps: {
     mode: "selector",
     range: ["美国", "中国", "巴西", "日本"],
   },
 },
 {
   key: "b",
   title: "备注",
   type: "textarea",
 },
];

export default function (props) {
 const formRef = useRef<any>();
 const [formValue, setformValue] = useState({});
 const [formSchema, setformSchema] = useState(formData);

 const onChange = (newValue) => {
   setformValue(newValue);
 };
 const onSubmit = () => {
   const isValid = formRef.current.validate();
   console.log("isValid: ", isValid);
 };

 return (
   <View className="index">
     <FormRender
       ref={formRef}
       formValue={formValue}
       formSchema={formSchema}
       onChange={onChange}
     ></FormRender>
     <Button onClick={onSubmit}>提交</Button>
   </View>
 );
}复制代码

效果图:

微信截图_20211102103754.png

更多用法可以查看 complex.tsx 文件

基本使用思路

  1. formSchema 描述表单信息,formValue 为表单值,这两个字段均由外部组件控制。

  • 改变 formValue:onChange

  • 改变 formSchema

    • 如果 formSchema 放在单独文件中,函数组件可以通过传递 setState 方法让回调调用,类组件一样但也可以通过绑定 this 的方式调用

    1. 外部组件 setState

    2. 内部组件引起的改动:在 formSchema 中设置回调,回调中调用外部组件中的 setState。 如 onColumnChange

  1. 校验可通过 validate 方法,validate 会通过校验formSchema 中定义的规则

formSchema 规范

具体说明可查看组件 type.d.ts 文件中的 IFormSchema 类型定义,以下为扩展说明

  • type 字段决定了使用哪个组件来渲染, 组件必须要在 widgets 文件夹下声明并导出。

  • required  和  rules  字段用于做校验判断。rules 为对象数组,可书写多个校验规则。支持 pattern 正则以及validate函数形式,其中message为提示信息。

  • titlediabledrequiredhidden 字段支持布尔值以及函数形式。可在 SupportFunctionItem 添加其他字段支持

  • titlediabledrequiredhidden 字段会展开作为第一级字段注入到自定义组件中。可在injectCompKeys添加其他字段支持

  • typeProps  字段用于补充组件支持的更为细致的属性,可自行展开或者使用高阶组件 withItemToProps 展开。

  • render 为函数,配合 type = custom 使用, 返回JSX用于自定义组件。

  • extra 用于在元素下展示更多说明信息

  • 任意其他字段会传递给自定义组件,可以根据需要自行魔改

如何扩展组件

  1. 先写好项目组件,然后在widgets文件夹下引入项目组件并注入value 等信息并导出即可,相关props可查看 IWidgetProps 接口

  2. schema 中的 custom 函数中返回 JSX 元素

重置样式应该统一在 index.scss

注意事项

  • 组件使用 React.meomo 进行性能优化,因此在更改 formSchema中注意深克隆对象进行更改对象,如果直接更改 formSchema 中的对象会导致对比函数中的 pre props 和 current props 一致,进而无法重新渲染 。(当然去掉 React.memo 也可以)

TODO

  • 性能优化,组件独立渲染互不干扰


作者:歌顿与烈焰
链接:https://juejin.cn/post/7025878046624186399

文章分类
后端
版权声明:本站是系统测试站点,无实际运营。本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 XXXXXXo@163.com 举报,一经查实,本站将立刻删除。
相关推荐