antd3-Form表单源码

83 阅读1分钟

使用

import React, {Component} from "react";
import {Input} from "antd";
import CreateForm from "./Test";

@CreateForm
class Timeline extends Component {
 constructor(props) {
  super(props);
 }

 componentDidMount() {
  this.props.form.setFieldsValue({
   userName: "unluna"
  });
 }

 submit = () => {
  const {getFieldsValue, validateFields} = this.props.form;
 };

 render() {
  const {getFieldDecorator} = this.props.form;
  // 任何一个小组件render,所有组件都会render一次
  
  return (
   <div>
    {
     getFieldDecorator("username", {
      rules: [{
       required: true,
       message:'请输入用户名'
      }]
     })(
      <Input placeholder={"username"}/>
     )
    }
   </div>
  );
 }
}

export default Timeline;

CreateForm

import React, {Component} from "react";

export default (Cmp) => {
 return class extends Component {

  constructor(props) {
   super(props);
   this.state = {};
   this.options = {};
  }

  handleChange = (e) => {
   const {name, value} = e.target;
   this.setState({
    [name]: value,
   });
  };

  getForm = () => ({
   form: {
    setFieldsValue: (state) => {
     this.setState(state);
    },
    getFieldsValue: () => ({
     ...this.state
    }),
    validateFields: () => {
     // 伪代码
     const err=[]
     Object.keys(this.options).forEach((key) => {
      if (this.options[key].rules) {
       err.push()
      }
     });
     return err?.length
    },
    getFieldDecorator: (field, options) => {
     this.options[field] = options;
     return (Cmp) => {
      return React.cloneElement(Cmp, {
       name: field,
       value: this.state[field],
       onChange: this.handleChange
      });
     };
    },
   }
  });

  render() {
   return (
    <Cmp
     {...this.props}
     {...this.getForm()}
    />
   );
  }
 };
};

核心

  1. CreateForm,接收一个组件,返回一个新组件
  2. getFieldDecorator 函数
    • 第一个函数,做了两件事
      • 一个是把当前小组件的 option 存到form组件里面
      • 第二个事是返回一个组件
    • 第二个组件函数,直接把传进来的这个组件,clone了一下,然后把namevalueonChange传进去

缺点:任何一个小组件render,所有组件都会render一次