思路:
1、首先需要两个DIV,一个是和视口一样大drag-mask,绑定mouseMove事件和mouseUp事件,另一个是和Modal一样大的drag-target,绑定mouseDown事件;
2、已知Modal的样式.ant-modal{position:relative;top:100px;left:0px;},通过更改top、left改变Modal位置;
3、mouseDown事件时,记录坐标
handleMoseDown=(evt)=>{ this.setSate({ dragging:true, preX:evt.pageX, preY:evt.pageY, }) }
4、mouseMove事件时,根据上一次的坐标和这一次的坐标计算Modal的新位置;
handleMouseMove=(evt)=>{ const {preX,preY,styleLeft,styleTop} = this.state; const left = styleLeft + (evt.pageX-preX); const top = styleTop + (evt.pageY-preY); this.setState({ preX:evt.pageX, preY:evt.pageY, styleLeft:left, styleTop:top, }) }
DEMO代码如下:
import React, { Component } from ‘react‘;
import ReactDom from ‘react-dom‘;
import { Modal, Empty } from ‘antd‘;
import ‘./dragable.less‘;
export default class DragableModal extends Component {
constructor(props) {
super(props);
this.state = {
visible:false,
dragging: false,
preX: 0,
preY: 0,
styleTop: 100,
styleLeft:0,
}
this.windowH = document.body.clientHeight;
this.windowW = document.body.clientWidth;
}
show = () => {
this.setState({
visible: true,
dragging: false,
preX: 0,
preY: 0,
styleTop: 100,
styleLeft:0,
})
}
hide = () => {
this.setState({
visible:false
})
}
isOverWindow = (moveX, moveY) => {
const er = 10;
if (moveX < er) return true;
if (moveX > (this.windowW - er)) return true;
if (moveY < er) return true;
if (moveY > (this.windowH - er)) return true;
return false;
}
handleMoseDown=(evt)=>{
this.setSate({
dragging:true,
preX:evt.pageX,
preY:evt.pageY,
})
}
handleMouseMove = (evt) => {
if (this.isOverWindow) {
this.hanldeMouseUp();
return;
}
const {preX,preY,styleLeft,styleTop} = this.state;
const left = styleLeft + (evt.pageX-preX);
const top = styleTop + (evt.pageY-preY);
this.setState({
preX:evt.pageX,
preY:evt.pageY,
styleLeft:left,
styleTop:top,
})
}
hanldeMouseUp = () => {
this.setState({dragging:false})
}
render() {
const { visible, dragging, styleLeft, styleTop } = this.state;
const style = { left: styleLeft, top: styleTop }
return (
<div>
<Modal
title=‘拖拽测试‘
visible={visible}
onCancel={this.hide}
style={style}
maskClosable={false}
>
<div className=‘drag-target‘ onMouseDown={this.handleMoseDown}></div>
<Empty description=‘啥也没有O_o‘ />
{
dragging &&
<div
className=‘drag-mask‘
onMouseMove={this.handleMouseMove}
onMouseUp={this.hanldeMouseUp}
></div>
}
</Modal>
</div>
)
}
}
.drag-mask{ position: fixed; left: 0; right: 0; top: 0; bottom: 0; z-index: 1001; } .drag-target{ position: absolute; left: 0; right: 0; top: 0; bottom: 0; cursor: move; }
如果需要复用可以将其改写成高阶组件。
欢迎指出问题欢迎讨论
原文:https://www.cnblogs.com/JerryD/p/12161628.html