JavaScript 进阶营

Redux-Form

2018-05-01  本文已影响639人  woow_wu7

简介

redux-form主要用于管理reudx中的form表单数据

主要模块

(1) formReducer reducer

formReducer是form表单的reducer,表单的各种操作以 Redux action 的方式,通过此 reducer 来促使 Redux store 数据的变化。

store.js


import { reducer as formReducer } from 'redux-form'    // 引入redux-form的 reducer模块



const store = createStore(
    combineReducers({
        user,
        form: formReducer,       // 使用,注意这里的form属性最好写成form,不要用其他名字
    }),
    window.devToolsExtension ? window.devToolsExtension() : undefined,
    applyMiddleware(sagaMiddleware)
)

(2) reduxForm()方法

让用reduxForm装饰的组件拥有form state和一些表单方法。

username.js


import React from 'react';
import {Field, reduxForm} from 'redux-form';     // 引入reduxForm()方法,和 Field组件

const fieldGo = (props) => {
    console.log(props, 'props')
        return(
            <div>
                <input type="text" />
            </div>
        )
}

class usenName extends React.Component {
    
    componentDidMount() {
        console.log(this.props, 'this.props')
    }
    go = () => {
        this.props.getusername(11,12,13);
        this.props.getsaga();
    }
    render() {
        return (                                   // redux-form的Field组件
                <Field                                  
                    name="FieldUserOne"
                    type="text"
                    component={fieldGo}
                >
                </Field>
            </div>
        )
    }
}

export default reduxForm({                          // 使用reduxForm()方法
    form: 'testReduxForm',                          // 该表单的名字
})(usenName);

(3) Field 等组件 --- 最简单的组件

用Field代替原本的 <input/> 组件,可以与redux-form的逻辑相连接。
·
·
·
·
·


(一) reduxForm

reduxForm的配置项

(1) form : String ------------------------- 必须

(2) initialValues : Object<String, String> ---------------- 初始值

(3) validate : (values:Object, props:Object) => errors:Object

export default reduxForm({
    form: 'user-name',
    initialValues:{selectOne: 'two'},
    validate:(value, props) => {               // reduxForm的validate属性,是一个函数
        if(!value.user) {
            return {user: 'user不能为空'}
        } else {
            return {}
        }
    }
})(userNameComponent)

·

reduxForm传给包装的组件的props

(1) handleSubmit -------------------------------- ( 重要 )

handleSubmit(eventOrSubmit) : Function




import React from 'react';
import {reduxForm, Field, FieldArray, Form  } from 'redux-form';      // 引入 Form


class userNameComponent extends React.Component {   
    render() {
        return (
            <div>      // Form中有onSubmit属性, 这里的data就是提交的表单的值
                <Form onSubmit={this.props.handleSubmit(data => console.log(data))} >
                    <div>
                        <FieldArray
                            name="field-array"
                            component={this.createFieldArray}
                        ></FieldArray>
                    </div>
                    <br/>
                    <div>
                        姓名:<Field name='initialValues' component='input'></Field>
                    </div>
                    <button type="submit">submit</button>  
                </Form>
                <br/>
            </div>
        )   
    }
}

export default reduxForm({    // reduxForm包装的组件的props中有 handleSubmit 属性
    form: 'user-name',
    initialValues: {initialValues: '马云',},
})(userNameComponent)




 // 除了用Form的onsubmit函数来触发,还可以给按钮添加事件来触发,不过,onSubmit包括点击,键盘事件等

 // <button onClick={this.props.handleSubmit(data => ...)}>提交</button> 不支持键盘事件




(二) Field 组件

Field组件必须有的属性是 name,component

(1) name属性 ------------------------------- 必须

(2) component属性 ----------------------- 必须

(3) format属性

(4) normalize属性

(5) onBlur属性

(6) onChange属性

(7) onFocus属性

(8) props属性







import React from 'react';

import {reduxForm, Field} from 'redux-form';

const goFieldComponent = (props) => {
    console.log(props, 'input ---- props7777777777777777777')
    return (
        <input type="text" placeholder="请输入用户名" {...props.input} />
    )
}
class userNameComponent extends React.Component {
    componentDidMount() {
        console.log(this.props)
    }
    render() {
        return (
            <div style={{background:'silver', padding: '30px'}}>
                这是username组件
                <br/>
                <div>
                    <span>用户名</span>
                    <Field
                        name="username"
                        component={goFieldComponent}
                        // component="input"
                        format= {(value, name) => { return value ? value.toUpperCase() : ''}}
                        normalize={(value, previousValue, allValues, previousAllValues ) => {
                            console.log(allValues,'normalize-----allValues')
                            return value.toUpperCase()
                        }}
                        onBlur={(event, newValue, previousValue, name) => {
                            event.preventDefault();
                            console.log(event, 'event');
                            console.log(newValue, 'newValue');
                            console.log(previousValue, 'previousValue');
                            console.log(name, 'name');
                        }}
                        props={{'age': 20}}
                        customAttribute={'this is custom attribute provide to component'}
                    ></Field>
                </div>
            </div>
        )
    }
}

export default reduxForm({
    form: 'user-name'
})(userNameComponent)



props

Props

Input Props

(1) input.name : String
(2) input.value: any

Meta Props

(1) meta.initial : any ----------------------------------- field 的初始值
(2) meta.form : String ------------------------------ form表单的name值
(3) meta.error : String -------------------------------(重要)
(4) meta.dispatch : Function ----------------------- dispatch()
const goFieldComponent = (props) => {
    console.log(props, 'input ---- props7777777777777777777')
    props.meta.dispatch({
        type: 'GET_NAME',
        payload: 'woowwu'
    });
    return (
        <input type="text" placeholder="请输入用户名" {...props.input} />
    )
}
(5) meta.active : boolean ---------------------------- focus (true)
(6) meta.dirty : boolean ------------------------------ change (true)
(7) meta.pristine : boolean -------------------------- change (false)
(8) meta.visited: boolean -----------------------只要获得过焦点,就为true
(9) meta.submitting : boolean
(10) meta.valid : boolean

Field例子

//select


import React from 'react';

import {reduxForm, Field} from 'redux-form';
import {Select} from 'antd';
const Option = Select.Option;


class userNameComponent extends React.Component {

    getSelect = ({input, meta, ...rest}) => {
        return (
            <Select style={{ width: 120 }} {...input} {...meta}>     // input对象中有value属性
                <Option value="two">星期二</Option>
                <Option value="thr">星期三</Option>
                <Option value="for">星期四</Option>
                <Option value="fiv">星期五</Option>
            </Select>
        )
    }
    getInput = ({input, meta}) => {
        console.log(meta.error)
        return (
            <div>
                <input type="text" {...input} />
                {meta.error}                       // 显示validate未通过验证的错误信息
            </div>
            
        )
    }
    render() {
        return (
            <div style={{background:'silver', padding: '30px'}}>
                <div>                               
                    <Field             
                        name="selectOne"
                        component={this.getSelect}       
                        props={{value:'two'}}  
                    ></Field>                      // name 和 component 为必须字段
                    
                     <Field name="user" component={this.getInput}></Field>
                </div>
            </div>
        )
    }
}

export default reduxForm({                 // reduxForm包装组件
    form: 'user-name',                     // 该表单的名字是 ‘user-name’
    initialValues:{selectOne: 'two'}       // form表单初始值设置, Field selectOne 的初始值是‘two’
    validate:(value, props) => {           // 同步验证,return的对象在props的 meta属性中
        if(!value.user) {
            return {user: 'user不能为空'}
        } else {
            return {}
        }
    }    
})(userNameComponent)

·
·
·
·
·


(三) FieldArray

(1) 主要属性

(2) props

fields

(1) fields.name
(2) fields.forEach(callback) : Function
(3) fields.get(index) : Function
(4) fields.getAll() : Function
(5) fields.length : Number
(6) fields.map(callback) ------------------------------ (重要)
(7) fields.move(from:Integer, to:Integer) : Function
(8) fields.pop()fields.push(value:Any)fields.remove(index:Integer)fields.removeAll()fields.shift()fields.unshift(value:Any)fields.swap(indexA:Integer, indexB:Integer) 对换位置

meta

FieldArray实例:

// FieldArray实例   ------------ 添加,删除,嵌套


import React from 'react';
import {reduxForm, Field, FieldArray} from 'redux-form';



class userNameComponent extends React.Component {

    addMessage = (props) =>  {
        return (
            <div>
                <button onClick={() => props.fields.push({})} >添加信息</button>
                {
                    props.fields.map( (field2, index2)  => (
                    <div key={index2}>
                            爱好:<Field name={`${field2}-add`} component="input"></Field>
                    </div>
                    ))
                }
            </div>
        )
    }
    
createFieldArray = ({fields, meta}) => {
    return (
        <div>                                                                 // fields.push()
            <button onClick={() => fields.push({})}>添加个人信息表单</button>  
            <div>
            {
                fields.map( (field, index)  => {                              // feilds.map()
                    return (
                        <div key={index}>
                            姓名:<Field name={`${field}-name`} component="input"></Field>
                            <br/>
                            年龄:<Field name={`${field}-age`} component="input"></Field>
                            <br/>
                            爱好:<Field name={`${field}-hobby`} component="input"></Field>
                            <div>                                           // 里层的FielsArray
                               <FieldArray                                 
                                   name={`${field}-addHobby`} 
                                   omponent={this.addMessage}>
                               </FieldArray> 
                            </div>
                            <div 
                               style={{position: 'relative', left:'300px'}} 
                               onClick={() => fields.remove(index)}     // fields.remove(index)
                             >
                               <button>删除表单</button> 
                            </div>
                        </div>
                    )
                })
            }
            </div>
        </div>
    )
}

    render() {
        return (
           <div>                                                          // 第一个 FieldArray
               <FieldArray                              
                name="field-array"
                component={this.createFieldArray}
               ></FieldArray>
           </div>
        )   
    }
}

export default reduxForm({
    form: 'user-name',
})(userNameComponent)


上一篇下一篇

猜你喜欢

热点阅读