antd react可拖拽,布局配置

import { DragDropContext, Droppable, Draggable } from 'react-beautiful-dnd';可拖拽的包

可拖拽:DraggableRow/index.jsx 子组件
import React, { useState,useRef } from 'react';
import { Modal, Form, Select, Input, Button, Row, Col,Tooltip} from 'antd'
import { DragDropContext, Droppable, Draggable } from 'react-beautiful-dnd';
import { CloseCircleOutlined, ExclamationCircleOutlined} from '@ant-design/icons';
import styles from './index.less'
import { debounce } from 'lodash';
const grid = 8;
const getItemStyle = (isDragging, draggableStyle) => ({
    // some basic styles to make the items look a bit nicer
    userSelect: 'none',
    // padding: grid * 4,
    margin: `0 0 ${grid}px 0`,

    // change background colour if dragging
    background: isDragging ? '#fff' : '#fff',
    // border: '1px solid #ddd',
    margin: '0px auto 10px auto',
    width:"70%",
    // styles we need to apply on draggables
    ...draggableStyle,
});
const reorder = (list, startIndex, endIndex) => {
    const result = Array.from(list);
    const [removed] = result.splice(startIndex, 1);
    result.splice(endIndex, 0, removed);
    let arr = [];
    result.map((v, k) => {
        arr.push(v);
    });
    return arr;
};

export default (props)=>{
    const { list, config } = props;
    const {
        activeKey,
        setHomeList,
        setDuapList,
        setVisible,
        setIsEdit,
        setCurrentEditItem,
        setOtherVisible,
        onRowDelete,
        setEditOtherOrder,
        setItemTypeCode,
        renderOrder,
    } = config
    const onDragEnd = (result) => { //拖拽结束事件
        console.log('result', result);
        let arr = [...list]
        if (!result.destination) {
            return;
        }
        const newList = reorder(arr, result.source.index, result.destination.index);
        let IdList = [];
        if(!!newList && newList.length){
            newList.map(item=>{
                IdList.push(item.Id)
            })
        }
        if(!!IdList && IdList.length){
            renderOrder(IdList)
        }
        if (activeKey == "1001") {
            setHomeList(newList)
        }else{
            setDuapList(newList)
        }
    }

    const handleEditItem = (e,item,index) =>{
        e.preventDefault();
        e.stopPropagation();

        Modal.confirm({
            icon: <ExclamationCircleOutlined />,
            content: 'Are you sure to delete?',
            okText: 'Confirm',
            cancelText: 'Cancel',
            onOk() {
                onRowDelete(item)
            },
        })
    }

    const handleEditOtherItem = (e, item, index, order) =>{
        e.preventDefault();
        e.stopPropagation();
        setOtherVisible(true);
        setIsEdit(true);
        setItemTypeCode(item.DisplayItemDetailList[order-1].ItemType)
        console.log('item', item);
        console.log('index', index);
        console.log('order', order);
        setCurrentEditItem(item);
        setEditOtherOrder(order);
    }

    const onIntroductionEdit = (e, item, index) =>{
        e.preventDefault();
        e.stopPropagation();
        setCurrentEditItem(item);
        setVisible(true);
        setIsEdit(true);
    }

    const onVideoEdit = (e, item, index) =>{
        e.preventDefault();
        e.stopPropagation();
        setCurrentEditItem(item);
        setVisible(true);
        setIsEdit(true);
    }

    return (
        <div style={{background:"#fff",paddingBottom:'30px'}}>
            <DragDropContext onDragEnd={onDragEnd}>
                <Droppable droppableId="droppable">
                    {(provided, snapshot) => (
                        <div ref={provided.innerRef} {...provided.droppableProps}>
                            {list.map((item, index) => {
                                let dom;
                                if (item.FunctionType == 1001) {  //
                                    dom = <div
                                        editform="false"
                                        key={item.Id}
                                        style={{ padding: "0 20px", background: "#fff", position: "relative" }}
                                        // onClick={() => {
                                        //     this.showEditModal(item);
                                        // }}
                                    >
                                        <Draggable
                                            shouldRespectForcePress={true}
                                            key={item.index}
                                            draggableId={item.Id}
                                            index={index}
                                        >
                                            {(provided, snapshot) => (
                                                <div
                                                    ref={provided.innerRef}
                                                    {...provided.draggableProps}
                                                    {...provided.dragHandleProps}
                                                    style={getItemStyle(
                                                        snapshot.isDragging,
                                                        provided.draggableProps.style
                                                    )}
                                                >
                                                    <div className={styles.droppableItem} onClick={(e) => { onIntroductionEdit(e,item,index)}}>Introduction</div>
                                                </div>
                                            )}
                                        </Draggable>
                                        <CloseCircleOutlined className='deleteDraggableItem' onClick={(e) => { handleEditItem(e, item, index) }} />
                                    </div>
                                } else if (item.FunctionType == 1002){
                                    dom = (
                                        <div
                                            editform="false"
                                            key={item.Id}
                                            style={{ padding: "0 20px", background: "#fff", position: "relative" }}
                                            // onClick={() => {
                                            //     this.showEditModal(item);
                                            // }}
                                        >
                                            <Draggable
                                                shouldRespectForcePress={true}
                                                key={item.index}
                                                draggableId={item.Id}
                                                index={index}
                                            >
                                                {(provided, snapshot) => (
                                                    <div
                                                        ref={provided.innerRef}
                                                        {...provided.draggableProps}
                                                        {...provided.dragHandleProps}
                                                        style={getItemStyle(
                                                            snapshot.isDragging,
                                                            provided.draggableProps.style
                                                        )}
                                                    >
                                                        <div className={styles.droppableItem} onClick={(e) => { onVideoEdit(e, item, index) }}>Video</div>
                                                    </div>
                                                )}
                                            </Draggable>
                                            <CloseCircleOutlined className='deleteDraggableItem' onClick={(e) => { handleEditItem(e, item, index) }} />
                                        </div>
                                    );
                                } else if (item.FunctionType == 1003 && item.Quantity == 1){
                                    dom = (
                                        <div
                                            editform="false"
                                            key={item.Id}
                                            style={{ padding: "0 20px", background: "#fff", position: "relative" }}
                                            // onClick={() => {
                                            //     this.showEditModal(item);
                                            // }}
                                        >
                                            <Draggable
                                                shouldRespectForcePress={true}
                                                key={item.index}
                                                draggableId={item.Id}
                                                index={index}
                                            >
                                                {(provided, snapshot) => (
                                                    <div
                                                        ref={provided.innerRef}
                                                        {...provided.draggableProps}
                                                        {...provided.dragHandleProps}
                                                        style={getItemStyle(
                                                            snapshot.isDragging,
                                                            provided.draggableProps.style
                                                        )}
                                                    >
                                                        <div className={styles.droppableItem} onClick={(e) => { handleEditOtherItem(e, item, index, 1) }}>
                                                            <p>{!!item.DisplayItemDetailList[0].ItemTypeString ? item.DisplayItemDetailList[0].ItemTypeString : ""}</p>
                                                            <p>{!!item.DisplayItemDetailList[0].Title ? item.DisplayItemDetailList[0].Title : "Click to select the display content"}</p>
                                                        </div>
                                                    </div>
                                                )}
                                            </Draggable>
                                            <CloseCircleOutlined className='deleteDraggableItem' onClick={(e) => { handleEditItem(e, item, index) }} />
                                        </div>
                                    );
                                } else if (item.FunctionType == 1003 && item.Quantity == 2) {
                                    dom = (
                                        <div
                                            editform="false"
                                            key={item.Id}
                                            style={{ padding: "0 20px", background: "#fff", position: "relative" }}
                                            // onClick={() => {
                                            //     this.showEditModal(item);
                                            // }}
                                        >
                                            <Draggable
                                                shouldRespectForcePress={true}
                                                key={item.index}
                                                draggableId={item.Id}
                                                index={index}
                                            >
                                                {(provided, snapshot) => (
                                                    <div
                                                        ref={provided.innerRef}
                                                        {...provided.draggableProps}
                                                        {...provided.dragHandleProps}
                                                        style={getItemStyle(
                                                            snapshot.isDragging,
                                                            provided.draggableProps.style
                                                        )}
                                                    >
                                                        <Row gutter={[16,16]}>
                                                            <Col span={8}>
                                                                <div className={styles.droppableItemDiv} onClick={(e) => { handleEditOtherItem(e, item, index, 1) }}>
                                                                    <p>{!!item.DisplayItemDetailList[0].ItemTypeString ? item.DisplayItemDetailList[0].ItemTypeString : ""}</p>
                                                                    <p>{!!item.DisplayItemDetailList[0].Title ? item.DisplayItemDetailList[0].Title : "Click to select the display content"}</p>
                                                                </div>
                                                            </Col>
                                                            <Col span={16}>
                                                                <div className={styles.droppableItemDiv} onClick={(e) => { handleEditOtherItem(e, item, index, 2) }}>
                                                                    <p>{!!item.DisplayItemDetailList[1].ItemTypeString ? item.DisplayItemDetailList[1].ItemTypeString : ""}</p>
                                                                    <p>{!!item.DisplayItemDetailList[1].Title ? item.DisplayItemDetailList[1].Title : "Click to select the display content"}</p>
                                                                </div>
                                                            </Col>
                                                        </Row>
                                                        
                                                    </div>
                                                )}
                                            </Draggable>
                                            <CloseCircleOutlined className='deleteDraggableItem' onClick={(e) => { handleEditItem(e, item, index) }} />
                                        </div>
                                    );
                                } else if (item.FunctionType == 1003 && item.Quantity == 3) {
                                    dom = (
                                        <div
                                            editform="false"
                                            key={item.Id}
                                            style={{ padding: "0 20px", background: "#fff", position: "relative" }}
                                            // onClick={() => {
                                            //     this.showEditModal(item);
                                            // }}
                                        >
                                            <Draggable
                                                shouldRespectForcePress={true}
                                                key={item.index}
                                                draggableId={item.Id}
                                                index={index}
                                            >
                                                {(provided, snapshot) => (
                                                    <div
                                                        ref={provided.innerRef}
                                                        {...provided.draggableProps}
                                                        {...provided.dragHandleProps}
                                                        style={getItemStyle(
                                                            snapshot.isDragging,
                                                            provided.draggableProps.style
                                                        )}
                                                    >
                                                        <Row gutter={[16, 16]}>
                                                            <Col span={8}>
                                                                <div className={styles.droppableItemDiv} onClick={(e) => { handleEditOtherItem(e, item, index, 1) }}>
                                                                    <p>{!!item.DisplayItemDetailList[0].ItemTypeString ? item.DisplayItemDetailList[0].ItemTypeString : ""}</p>
                                                                    <p>{!!item.DisplayItemDetailList[0].Title ? item.DisplayItemDetailList[0].Title :"Click to select the display content"}</p>
                                                                </div>
                                                            </Col>
                                                            <Col span={8}>
                                                                <div className={styles.droppableItemDiv} onClick={(e) => { handleEditOtherItem(e, item, index, 2) }}>
                                                                    <p>{!!item.DisplayItemDetailList[1].ItemTypeString ? item.DisplayItemDetailList[1].ItemTypeString : ""}</p>
                                                                    <p>{!!item.DisplayItemDetailList[1].Title ? item.DisplayItemDetailList[1].Title : "Click to select the display content"}</p>
                                                                </div>
                                                            </Col>
                                                            <Col span={8}>
                                                                <div className={styles.droppableItemDiv} onClick={(e) => { handleEditOtherItem(e, item, index, 3) }}>
                                                                    <p>{!!item.DisplayItemDetailList[2].ItemTypeString ? item.DisplayItemDetailList[2].ItemTypeString : ""}</p>
                                                                    <p>{!!item.DisplayItemDetailList[2].Title ? item.DisplayItemDetailList[2].Title : "Click to select the display content"}</p>
                                                                </div>
                                                            </Col>
                                                        </Row>
                                                    </div>
                                                )}
                                            </Draggable>
                                            <CloseCircleOutlined className='deleteDraggableItem' onClick={(e) => { handleEditItem(e, item, index) }} />
                                        </div>
                                    );
                                }
                                return dom;
                            })}
                            {provided.placeholder}
                        </div>
                    )}
                </Droppable>
            </DragDropContext>
        </div>
    )
}

引入 拖拽组件:
父组件
import moment from 'moment';
import styles from './index.less';
import PanelTitle from '@/components/PanelTitle';
import React, { useEffect, useState } from 'react';
import { ExclamationCircleOutlined, EllipsisOutlined, PlusOutlined } from '@ant-design/icons';
import { Form, Input, Row, Col, Modal, Table, Button, Menu, Dropdown, message, Tooltip, Select, Radio } from 'antd';
import DisplaySettingModifyRow from '@/components/DisplaySettingModifyRow';
import DisplayOtherModifyModal from '@/components/DisplayOtherModifyModal';
// import DisplayApp from '@/components/DisplayApp';
import DraggableRow from '@/components/DraggableRow';
import {
    GetRowTypeDropdown,
    GetItemTypeDropdown,
    GetDisplayList,
    DisplayRowAdd,
    DisplayRowItemEdit,
    GetItemContentDropdown,
    DisplayConfigPublish,
    DisplayRowDelete,
    DisplayOrderUpdate,
} from '@/services/displaySetting'
import { v4 as uuidv4 } from 'uuid';
import { history, Link } from 'umi';
import { debounce } from 'lodash';
import { get } from '@umijs/deps/compiled/lodash';
const { Option } = Select
export default () => {
    const [form] = Form.useForm();
    const [pageSize, setPageSize] = useState(10);
    const [totalCount, setTotalCount] = useState(0);
    const [dataSource, setDataSource] = useState([]);
    const [currentPage, setCurrentPage] = useState(1);
    const [visible, setVisible] = useState(false);  //添加或编辑一行的modal
    const [otherVisible, setOtherVisible] = useState(false);    //编辑某个other的modal
    const [isEdit, setIsEdit] = useState(false);    //是否是编辑
    const [homeList, setHomeList] = useState([]);   //Home Display的列表数据
    const [duapList, setDuapList] = useState([]);   //DUAP Display的列表数据
    const [activeKey, setActiveKey] = useState('1001');  //当前激活的tab
    const [rowType, setRowType] = useState([]);  //
    const [itemType, setItemType] = useState([]);
    const [contentList, setContentList] = useState([]);
    const [itemTypeCode, setItemTypeCode] = useState(1001);
    const [currentEditItem, setCurrentEditItem] = useState({});     //当前编辑的数据
    const [editOtherOrder, setEditOtherOrder] = useState(null);     //编辑Other中的某条数据的Order


    useEffect(() => {    //加载初始数据
        GetRowTypeDropdown({}).then(res => {
            setRowType(res)
        })
        GetItemTypeDropdown({}).then(res => {
            setItemType(res)
        })
    }, [])

    useEffect(() => { //根据Other中的Type获取联动的Content数据
        GetItemContentDropdown({
            ItemType: itemTypeCode
        }).then(res => {
            if (!!res && res.length) {
                setContentList(res)
            } else {
                setContentList([])
            }
        })
    }, [itemTypeCode])

    useEffect(() => {     //切换tabs时获取列表数据
        GetDisplayList({
            PageType: activeKey,
            IsPublished: false
        }).then(res => {
            if (!!res && res.length) {
                if (activeKey == '1001') {
                    setHomeList(res)
                } else if (activeKey == '1002') {
                    setDuapList(res)
                }
            }
        })
    }, [activeKey])

    const getList = () => {   //获取Home 或者 DUAP China的列表数据
        GetDisplayList({
            PageType: activeKey,
            IsPublished: false
        }).then(res => {
            if (!!res && res.length) {
                if (activeKey == '1001') {
                    setHomeList(res)
                } else if (activeKey == '1002') {
                    setDuapList(res)
                }
            } else {
                if (activeKey == '1001') {
                    setHomeList([])
                } else if (activeKey == '1002') {
                    setDuapList([])
                }
            }
        })
    }

    const onChange = (e) => {    //切换tab
        setActiveKey(e.target.value)
    }
    const handleAdd = () => { //添加一行
        setIsEdit(false);
        setVisible(!visible)
    }

    const onModifyRowFinish = (values) => {   //Introduction 和 Video 以及Other中的每个模块编辑回调
        switch (activeKey) {
            case '1001':
                if (isEdit) {
                    if (!!values.FunctionType) {
                        delete values.FunctionType
                    }
                    DisplayRowItemEdit(values).then(res => {
                        if (!!res && res.ReturnCode == 1001) {
                            message.success('Edit successfully')
                            getList();
                        } else {
                            message.error(res.MessageEnglish)
                        }
                    })
                } else {
                    values.PageType = activeKey;
                    DisplayRowAdd(values).then(res => {
                        console.log(res);
                        if (!!res && res.ReturnCode == 1001) {
                            message.success("Add successfully");
                            getList();
                        } else {
                            message.error(res.MessageEnglish)
                        }
                    })
                }
                break;
            case '1002':
                if (isEdit) {
                    delete values.FunctionType
                    DisplayRowItemEdit(values).then(res => {
                        if (!!res && res.ReturnCode == 1001) {
                            message.success('Edit successfully')
                            getList();
                        } else {
                            message.error(res.MessageEnglish)
                        }
                    })
                } else {
                    values.PageType = activeKey;
                    DisplayRowAdd(values).then(res => {
                        console.log(res);
                        if (!!res && res.ReturnCode == 1001) {
                            message.success("Add successfully");
                            getList();
                        } else {
                            message.error(res.MessageEnglish)
                        }
                    })
                }
                break;
            default:
                break;
        }

    }

    const onRowDelete = (values) => {    //删除一行
        DisplayRowDelete({ Id: values.Id }).then(res => {
            if (!!res && res.ReturnCode == 1001) {
                message.success('Delete successfully');
                getList()
            } else {
                message.error(res.MessageEnglish)
            }
        })
    }

    const onPublish = () => {    //发布
        DisplayConfigPublish({ PageType: activeKey }).then(res => {
            if (!!res && res.ReturnCode == 1001) {
                message.success('Publish successfully');
                // location.reload();
                GetDisplayList({
                    PageType: activeKey,
                    IsPublished: false
                }).then(res => {
                    if (!!res && res.length) {
                        if (activeKey == '1001') {
                            setHomeList(res)
                        } else if (activeKey == '1002') {
                            setDuapList(res)
                        }
                    }
                })

            } else {
                message.error(res.MessageEnglish)
            }
        })
    }

    const renderOrder = (IdList) => {
        DisplayOrderUpdate({ IdList }).then(res => {
            if (!!res && res.ReturnCode == 1001) {
                message.success('Operation successful')
            }
        })
    }

    return (
        <div className={styles.FeedbackContainer}>
            <PanelTitle title="Homepage Setting" />
            <div className={styles.FeedbackMain}>
                <div className={styles.radioBtn}>
                    <Radio.Group onChange={onChange} defaultValue={activeKey}>
                        <Radio.Button value="1001">Home(PC)</Radio.Button>
                        <Radio.Button value="1002">DUAP China(PC)</Radio.Button>
                        {/* <Radio.Button value="1003">Display(APP)</Radio.Button> */}
                    </Radio.Group>
                </div>
                {
                    activeKey == '1001' || activeKey == '1002' ?
                        <div className={styles.displayContent}>
                            <div className={styles.displayContent_previewBtn}>
                                <Button style={{ marginRight: '15px' }} onClick={onPublish}>Publish</Button>
                                <Button onClick={() => { activeKey == '1001' ? window.open('/userInterface/home?preview=true') : window.open('/userInterface/duapChina?preview=true') }}>Preview</Button>
                            </div>
                            <div className={styles.displayContent_addBtn} onClick={handleAdd}>
                                Add
                            </div>
                        </div>
                        : ""
                }
            </div>
            <DisplaySettingModifyRow
                visible={visible}
                onCancel={setVisible}
                isEdit={isEdit}
                setIsEdit={setIsEdit}
                currentEditItem={currentEditItem}
                onModifyRowFinish={onModifyRowFinish}
                rowType={rowType}
            />
            {
                activeKey == '1001' || activeKey == "1002" ? <DraggableRow config={
                    {
                        activeKey,
                        setHomeList: setHomeList,
                        setDuapList: setDuapList,
                        setVisible: setVisible,
                        setIsEdit: setIsEdit,
                        setCurrentEditItem: setCurrentEditItem,
                        setOtherVisible: setOtherVisible,
                        onRowDelete: onRowDelete,
                        setEditOtherOrder: setEditOtherOrder,
                        setItemTypeCode: setItemTypeCode,
                        renderOrder: renderOrder,
                    }
                } list={activeKey == "1001" ? homeList : activeKey == '1002' ? duapList : []} /> : ""
            }
            <DisplayOtherModifyModal
                itemType={activeKey == '1001' ? itemType : [itemType[0]]}
                visible={otherVisible}
                onCancel={setOtherVisible}
                contentList={contentList}
                setItemTypeCode={setItemTypeCode}
                onModifyRowFinish={onModifyRowFinish}
                setIsEdit={setIsEdit}
                isEdit={isEdit}
                editOtherOrder={editOtherOrder}
                currentEditItem={currentEditItem}
            />
            {/* {
                activeKey == '1003'?<DisplayApp/>:""
            } */}
        </div>
    )
};















版权声明:本文为zhangyubababa原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明。