getFieldDecorator用法(三)——Table增删改

时间:2024-04-15 18:39:11

后台管理系统常用到表单的增删改,这里也做了个封装

例如:user/index.js

import React from \'react\'
import { Card, Button, Table, Form, Input, Checkbox,Select,Radio, Icon, message, Modal, DatePicker } from \'antd\'
import axios from \'../../axios/index\'
import Utils from \'../../utils/utils\'
import ETable from \'../../components/ETable/index\'
import Moment from \'moment\'
const FormItem = Form.Item;
const Option = Select.Option;
const RadioGroup = Radio.Group;
export default class User extends React.Component{

    state = {
        list:[]
    }

    params = {
        page:1
    }

    requestList = ()=>{
        axios.ajax({
            url:\'/table/list1\',
            data:{
                params:{
                    page:this.params.page
                }
            }
        }).then((res)=>{
            let _this = this;
            this.setState({
                list:res.result.list.map((item,index)=>{
                    item.key=index
                    return item;
                }),
                pagination:Utils.pagination(res,(current)=>{
                    _this.params.page = current;
                    _this.requestList();
                })
            })
        })
    }

    componentDidMount(){
        this.requestList();
    }

    // 操作员工
    handleOperator = (type)=>{
        let item = this.state.selectedItem;
        if(type ==\'create\'){
            this.setState({
                title:\'创建员工\',
                isVisible:true,
                type
            })
        }else if(type=="edit" || type==\'detail\'){
            if(!item){
                Modal.info({
                    title: \'信息\',
                    content: \'请选择一个用户\'
                })
                return;
            }
            this.setState({
                title:type==\'edit\'?\'编辑用户\':\'查看详情\',
                isVisible:true,
                userInfo:item,
                type
            })
        }else if(type=="delete"){
            if(!item){
                Modal.info({
                    title: \'信息\',
                    content: \'请选择一个用户\'
                })
                return;
            }
            Utils.ui.confirm({
                text:\'确定要删除此用户吗?\',
                onOk:()=>{
                    axios.ajax({
                        url:\'/user/delete\',
                        data:{
                            params:{
                                id:item.id
                            }
                        }
                    }).then((res)=>{
                        if(res.code ==0){
                            this.setState({
                                isVisible:false
                            })
                            this.requestList();
                        }
                    })
                }
            })
        }
    }

    handleSubmit = ()=>{
        let type = this.state.type;
        let data = this.userForm.props.form.getFieldsValue();
        axios.ajax({
            url:type == \'create\'?\'/user/add\':\'/user/edit\',
            data:{
                params:{
                    ...data
                }
            }
        }).then((res)=>{
            if(res.code ==0){
                this.setState({
                    isVisible:false
                })
                this.requestList();
            }
        })
    }

    render(){
        const columns = [{
            title: \'id\',
            dataIndex: \'id\'
          }, {
            title: \'用户名\',
            dataIndex: \'username\'
          }, {
            title: \'性别\',
            dataIndex: \'sex\',
            render(sex){
                return sex ==1 ?\'男\':\'女\'
            }
          }, {
            title: \'状态\',
            dataIndex: \'state\',
            render(state){
                let config = {
                    \'1\':\'咸鱼一条\',
                    \'2\':\'风华浪子\',
                    \'3\':\'北大才子一枚\',
                    \'4\':\'百度FE\',
                    \'5\':\'创业者\'
                }
                return config[state];
            }
          },{
            title: \'爱好\',
            dataIndex: \'interest\',
            render(interest){
                let config = {
                    \'1\':\'游泳\',
                    \'2\':\'打篮球\',
                    \'3\':\'踢足球\',
                    \'4\':\'跑步\',
                    \'5\':\'爬山\',
                    \'6\':\'骑行\',
                    \'7\':\'桌球\',
                    \'8\':\'麦霸\'
                }
                return config[interest];
            }
          },{
            title: \'婚姻\',
            dataIndex: \'isMarried\',
            render(isMarried){
                return isMarried?\'已婚\':\'未婚\'
            }
          },{
            title: \'生日\',
            dataIndex: \'birthday\'
          },{
            title: \'联系地址\',
            dataIndex: \'address\'
          },{
            title: \'早起时间\',
            dataIndex: \'time\'
          }
        ];
        return (
            <div>
                <Card>
                    <Form layout="inline">
                        <FormItem>
                            <Input placeholder="请输入用户名"/>
                        </FormItem>
                        <FormItem>
                            <Input type="password" placeholder="请输入密码"/>
                        </FormItem>
                        <FormItem>
                            <Button type="primary">登 录</Button>
                        </FormItem>
                    </Form>
                </Card>
                <Card style={{marginTop:10}}>
                    <Button type="primary" icon="plus" onClick={()=>this.handleOperator(\'create\')}>创建员工</Button>
                    <Button icon="edit" onClick={()=>this.handleOperator(\'edit\')}>编辑员工</Button>
                    <Button onClick={()=>this.handleOperator(\'detail\')}>员工详情</Button>
                    <Button type="danger" icon="delete" onClick={()=>this.handleOperator(\'delete\')}>删除员工</Button>
                </Card>
                <div className="content-wrap">
                    <ETable
                        columns={columns}
                        updateSelectedItem={Utils.updateSelectedItem.bind(this)}
                        selectedRowKeys={this.state.selectedRowKeys}
                        dataSource={this.state.list}
                        pagination={this.state.pagination}
                    />
                </div>
                <Modal
                    title={this.state.title}
                    visible={this.state.isVisible}
                    onOk={this.handleSubmit}
                    width={800}
                    onCancel={()=>{
                        this.userForm.props.form.resetFields();
                        this.setState({
                            isVisible:false,
                            userInfo:\'\'
                        })
                    }}
                >
                    <UserForm userInfo={this.state.userInfo} type={this.state.type} wrappedComponentRef={(inst) => this.userForm = inst }/>
                </Modal>
            </div>
        );
    }
}
class UserForm extends React.Component{

    getState = (state)=>{
        return {
            \'1\':\'咸鱼一条\',
            \'2\':\'风华浪子\',
            \'3\':\'北大才子一枚\',
            \'4\':\'百度FE\',
            \'5\':\'创业者\'
        }[state]
    }

    render(){
        const { getFieldDecorator } = this.props.form;
        const formItemLayout = {
            labelCol: {span: 5},
            wrapperCol: {span: 16}
        };
        const userInfo = this.props.userInfo || {};
        const type = this.props.type;
        return (
            <Form layout="horizontal">
                <FormItem label="姓名" {...formItemLayout}>
                    {
                        userInfo && type==\'detail\'?userInfo.username:
                        getFieldDecorator(\'user_name\',{
                            initialValue:userInfo.username
                        })(
                            <Input type="text" placeholder="请输入姓名"/>
                        )
                    }
                </FormItem>
                <FormItem label="性别" {...formItemLayout}>
                    {
                        userInfo && type==\'detail\'?userInfo.sex==1?\'男\':\'女\':
                        getFieldDecorator(\'sex\',{
                            initialValue:userInfo.sex
                        })(
                        <RadioGroup>
                            <Radio value={1}></Radio>
                            <Radio value={2}></Radio>
                        </RadioGroup>
                    )}
                </FormItem>
                <FormItem label="状态" {...formItemLayout}>
                    {
                        userInfo && type==\'detail\'?this.getState(userInfo.state):
                        getFieldDecorator(\'state\',{
                            initialValue:userInfo.state
                        })(
                        <Select>
                            <Option value={1}>咸鱼一条</Option>
                            <Option value={2}>风华浪子</Option>
                            <Option value={3}>北大才子一枚</Option>
                            <Option value={4}>百度FE</Option>
                            <Option value={5}>创业者</Option>
                        </Select>
                    )}
                </FormItem>
                <FormItem label="生日" {...formItemLayout}>
                    {
                        userInfo && type==\'detail\'?userInfo.birthday:
                        getFieldDecorator(\'birthday\',{
                            initialValue:Moment(userInfo.birthday)
                        })(
                        <DatePicker />
                    )}
                </FormItem>
                <FormItem label="联系地址" {...formItemLayout}>
                    {
                        userInfo && type==\'detail\'?userInfo.address:
                        getFieldDecorator(\'address\',{
                            initialValue:userInfo.address
                        })(
                        <Input.TextArea rows={3} placeholder="请输入联系地址"/>
                    )}
                </FormItem>
            </Form>
        );
    }
}
UserForm = Form.create({})(UserForm);

ETable/index.js

import React from \'react\'
import Utils from \'../../utils/utils\'
import {Table} from \'antd\'
import  "./index.less"
export default class ETable extends React.Component {

    state = {}
    //处理行点击事件
    onRowClick = (record, index) => {
        let rowSelection = this.props.rowSelection;
        if(rowSelection == \'checkbox\'){
            let selectedRowKeys = this.props.selectedRowKeys;
            let selectedIds = this.props.selectedIds;
            let selectedItem = this.props.selectedItem || [];
            if (selectedIds) {
                const i = selectedIds.indexOf(record.id);
                if (i == -1) {//避免重复添加
                    selectedIds.push(record.id)
                    selectedRowKeys.push(index);
                    selectedItem.push(record);
                }else{
                    selectedIds.splice(i,1);
                    selectedRowKeys.splice(i,1);
                    selectedItem.splice(i,1);
                }
            } else {
                selectedIds = [record.id];
                selectedRowKeys = [index]
                selectedItem = [record];
            }
            this.props.updateSelectedItem(selectedRowKeys,selectedItem || {},selectedIds);
        }else{
            let selectKey = [index];
            const selectedRowKeys = this.props.selectedRowKeys;
            if (selectedRowKeys && selectedRowKeys[0] == index){
                return;
            }
            this.props.updateSelectedItem(selectKey,record || {});
        }
    };

    // 选择框变更
    onSelectChange = (selectedRowKeys, selectedRows) => {
        let rowSelection = this.props.rowSelection;
        const selectedIds = [];
        if(rowSelection == \'checkbox\'){
            selectedRows.map((item)=>{
                selectedIds.push(item.id);
            });
            this.setState({
                selectedRowKeys,
                selectedIds:selectedIds,
                selectedItem: selectedRows[0]
            });
        }
        this.props.updateSelectedItem(selectedRowKeys,selectedRows[0],selectedIds);
    };

    onSelectAll = (selected, selectedRows, changeRows) => {
        let selectedIds = [];
        let selectKey = [];
        selectedRows.forEach((item,i)=> {
            selectedIds.push(item.id);
            selectKey.push(i);
        });
        this.props.updateSelectedItem(selectKey,selectedRows[0] || {},selectedIds);
    }

    getOptions = () => {
        let p = this.props;
        const name_list = {
            "订单编号":170,
            "车辆编号":80,
            "手机号码":96,
            "用户姓名":70,
            "密码":70,
            "运维区域":300,
            "车型":42,
            "故障编号":76,
            "代理商编码":97,
            "角色ID":64
        };
        if (p.columns && p.columns.length > 0) {
            p.columns.forEach((item)=> {
                //开始/结束 时间
                if(!item.title){
                    return
                }
                if(!item.width){
                    if(item.title.indexOf("时间") > -1 && item.title.indexOf("持续时间") < 0){
                        item.width = 132
                    }else if(item.title.indexOf("图片") > -1){
                        item.width = 86
                    }else if(item.title.indexOf("权限") > -1 || item.title.indexOf("负责城市") > -1){
                        item.width = \'40%\';
                        item.className = "text-left";
                    }else{
                        if(name_list[item.title]){
                            item.width = name_list[item.title];
                        }
                    }
                }
                item.bordered = true;
            });
        }
        const { selectedRowKeys } = this.props;
        const rowSelection = {
            type: \'radio\',
            selectedRowKeys,
            onChange: this.onSelectChange,
            onSelect:(record, selected, selectedRows)=>{
                console.log(\'...\')
            },
            onSelectAll:this.onSelectAll
        };
        let row_selection = this.props.rowSelection;
        // 当属性未false或者null时,说明没有单选或者复选列
        if(row_selection===false || row_selection === null){
            row_selection = false;
        }else if(row_selection == \'checkbox\'){
            //设置类型未复选框
            rowSelection.type = \'checkbox\';
        }else{
            //默认未单选
            row_selection = \'radio\';
        }
        return <Table 
                className="card-wrap page-table"
                bordered 
                {...this.props}
                rowSelection={row_selection?rowSelection:null}
                onRow={(record,index) => ({
                    onClick: ()=>{
                        if(!row_selection){
                            return;
                        }
                        this.onRowClick(record,index)
                    }
                  })}
            />
    };
    render = () => {
        return (
            <div>
                {this.getOptions()}
            </div>
        )
    }
}

ETable/index.scss

@import \'../../style/default\';
.ant-table{
  &-thead > tr > th,
  &-tbody > tr > td{
    padding:14px 6px;
    text-align:center;
  }
  .ant-table-selection-column{
    min-width:42px!important;
    width:42px!important;;
  }

  .text-center {
    text-align: center;
  }
  .text-left {
    text-align: left;
  }
  &.ant-table-middle{
    &-thead > tr > th,
    &-tbody > tr > td{
      padding:10px 6px;
    }
  }
  &.ant-table-small{
    &-thead > tr > th,
    &-tbody > tr > td{
      padding:8px 6px;
    }
  }
}
.ant-table-pagination{
  padding:0 20px;
}

utils/utils.js

import React from \'react\';
import { Select } from \'antd\'
const Option = Select.Option;
export default {
    formateDate(time){
        if(!time)return \'\';
        let date = new Date(time);
        return date.getFullYear()+\'-\'+(date.getMonth()+1)+\'-\'+date.getDate()+\' \'+date.getHours()+\':\'+date.getMinutes()+\':\'+date.getSeconds();
    },
    pagination(data,callback){
        return {
            onChange:(current)=>{
                callback(current)
            },
            current:data.result.page,
            pageSize:data.result.page_size,
            total: data.result.total_count,
            showTotal:()=>{
                return `共${data.result.total_count}条`
            },
            showQuickJumper:true
        }
    },
    // 格式化金额,单位:分(eg:430分=4.30元)
    formatFee(fee, suffix = \'\') {
        if (!fee) {
            return 0;
        }
        return Number(fee).toFixed(2) + suffix;
    },
    // 格式化公里(eg:3000 = 3公里)
    formatMileage(mileage, text) {
        if (!mileage) {
            return 0;
        }
        if (mileage >= 1000) {
            text = text || " km";
            return Math.floor(mileage / 100) / 10 + text;
        } else {
            text = text || " m";
            return mileage + text;
        }
    },
    // 隐藏手机号中间4位
    formatPhone(phone) {
        phone += \'\';
        return phone.replace(/(\d{3})\d*(\d{4})/g, \'$1***$2\')
    },
    // 隐藏身份证号中11位
    formatIdentity(number) {
        number += \'\';
        return number.replace(/(\d{3})\d*(\d{4})/g, \'$1***********$2\')
    },
    getOptionList(data){
        if(!data){
            return [];
        }
        let options = [] //[<Option value="0" key="all_key">全部</Option>];
        data.map((item)=>{
            options.push(<Option value={item.id} key={item.id}>{item.name}</Option>)
        })
        return options;
    },
    /**
     * ETable 行点击通用函数
     * @param {*选中行的索引} selectedRowKeys
     * @param {*选中行对象} selectedItem
     */
    updateSelectedItem(selectedRowKeys, selectedRows, selectedIds) {
        if (selectedIds) {
            this.setState({
                selectedRowKeys,
                selectedIds: selectedIds,
                selectedItem: selectedRows
            })
        } else {
            this.setState({
                selectedRowKeys,
                selectedItem: selectedRows
            })
        }
    },
}

axios/index.js

import JsonP from \'jsonp\'
import axios from \'axios\'
import { Modal } from \'antd\'
export default class Axios {
    static jsonp(options) {
        return new Promise((resolve, reject) => {
            JsonP(options.url, {
                param: \'callback\'
            }, function (err, response) {
                if (response.status == \'success\') {
                    resolve(response);
                } else {
                    reject(response.messsage);
                }
            })
        })
    }

    static ajax(options){
        let loading;
        if (options.data && options.data.isShowLoading !== false){
            loading = document.getElementById(\'ajaxLoading\');
            loading.style.display = \'block\';
        }
        let baseApi = \'https://www.easy-mock.com/mock/5a7278e28d0c633b9c4adbd7/api\';
        return new Promise((resolve,reject)=>{
            axios({
                url:options.url,
                method:\'get\',
                baseURL:baseApi,
                timeout:5000,
                params: (options.data && options.data.params) || \'\'
            }).then((response)=>{
                if (options.data && options.data.isShowLoading !== false) {
                    loading = document.getElementById(\'ajaxLoading\');
                    loading.style.display = \'none\';
                }
                if (response.status == \'200\'){
                    let res = response.data;
                    if (res.code == \'0\'){
                        resolve(res);
                    }else{
                        Modal.info({
                            title:"提示",
                            content:res.msg
                        })
                    }
                }else{
                    reject(response.data);
                }
            })
        });
    }
}

效果