react+ant封装可拖拽(Modal)弹窗,继承官方属性。可进行拓展
import { useState, useRef, useEffect } from "react";
import { Modal, ModalProps } from "antd";
import Draggable from "react-draggable";
import styles from "./index.module.less";
interface WebModal extends ModalProps {
openDrag?: boolean;
dragHandle?: boolean;
}
const WebReactModal= ({
openDrag = false,
dragHandle = false,
...props
}: WebModal) => {
const [position,setPosition]=useState({ x: 0, y: 0 })
const [bounds, setBounds] = useState({
left: 0,
top: 0,
bottom: 0,
right: 0,
});
const draggleRef = useRef<any>();
const onStart = (event, uiData) => {
const { clientWidth, clientHeight } = window?.document?.documentElement;
const targetRect = draggleRef?.current?.getBoundingClientRect();
setBounds({
left: -targetRect?.left + uiData.x,
right: clientWidth - (targetRect?.right - uiData.x),
top: -targetRect?.top + uiData.y,
bottom: clientHeight - (targetRect?.bottom - uiData.y),
});
};
const onDrag = (e, data) => {
const { x, y } = data;
setPosition({ x, y });
};
useEffect(() => {
if (!props.open) {
setPosition({ x: 0, y: 0 });
}
}, [props?.open]);
return (
<Modal
maskClosable={false}
className={styles.webModal}
modalRender={(modal) => (
<Draggable
handle={dragHandle?"":'.ant-modal-header'}
disabled={openDrag}
onDrag={onDrag}
bounds={bounds}
position={position}
onStart={(event, uiData) => onStart(event, uiData)}
>
<div ref={draggleRef}>{modal}</div>
</Draggable>
)}
{...props}
>
{props?.children}
</Modal>
);
};
export default WebReactModal;
.webModal {
:global {
.ant-modal-content {
.ant-modal-header {
padding: 10px;
background: #e5f0ff;
border-bottom: 1px solid #f0f0f0;
border-radius: 2px 2px 0 0;
}
}
.ant-modal-title {
color: #566286;
width: 100%;
cursor: move;
user-select: none;
font-weight: bold;
}
.ant-modal-close-x {
width: 42px;
height: 42px;
display: flex;
align-items: center;
justify-content: center;
}
}
}
<WebModalwidth={1200} onOk={()=>{}} title={"测试弹窗"} open={openA} onCancel={()=>{setOpenA(false)}}>
<div>存放弹窗中的内容</div>
</WebModal>