ng-zorro11的modal组件可拖拽(模板创建的弹窗)
最近在项目中有需求可以拖拽的弹窗,网上搜索了一遍都是服务端创建的弹窗可拖拽,而通过template创建的弹窗确比较难实现,我参考了别人的实现,改造了一下,就可以实现template的拖拽。
1. 创建指令 drag-modal.directive.ts
import { Directive, ElementRef, Input } from @angular/core;
import { ModalDragService } from "./drag-modal.service";
import { NzModalRef } from ng-zorro-antd/modal;
@Directive({
selector: [dragModal]
})
export class DragModalDirective {
@Input() dragModal: NzModalRef;
constructor(private ModalDragService: ModalDragService) {
setTimeout(() => {
this.ModalDragService.dragServiceModal(this.dragModal);
}, 16);
}
}
2.创建指令服务drag-modal.service.ts
import { Injectable, RendererFactory2 } from @angular/core;
@Injectable({
providedIn: root
})
export class ModalDragService {
constructor( private rendererFactory2: RendererFactory2, ) { }
dragTemplateModal(refModal) {
const render = this.rendererFactory2.createRenderer(null, null);
const modalBackground = refModal.getElement();
const modalElement = refModal.getElement().querySelector(.ant-modal-content);
const modalTitleElement = this.createModalTitleElement(render, modalElement);
this.dragListen(render, modalTitleElement, modalElement, modalBackground);
}
dragServiceModal(refModal) {
refModal.afterOpen.subscribe(() => {
const render = this.rendererFactory2.createRenderer(null, null);
const modalBackground = refModal.getElement();
const modalElement = refModal.getElement().querySelector(.ant-modal-content);
const modalTitleElement = this.createModalTitleElement(render, modalElement);
this.dragListen(render, modalTitleElement, modalElement, modalBackground);
})
}
createModalTitleElement(render, modalElement) {
let element = document.createElement(div) as any;
render.setStyle(element, width, 100%);
render.setStyle(element, height, 54px);
render.setStyle(element, position, absolute);
render.setStyle(element, top, 0);
render.setStyle(element, left, 0);
render.setStyle(element, cursor, move);
render.setStyle(element, -moz-user-select, none);
render.setStyle(element, -webkit-user-select, none);
render.setStyle(element, -ms-user-select, none);
render.setStyle(element, -khtml-user-select, none);
render.setStyle(element, user-select, none);
render.appendChild(modalElement, element);
return element;
}
dragListen(render, modalTitleElement, modalElement, modalBackground) {
render.listen(modalTitleElement, mousedown, function (event) {
this.mouseDownX = event.clientX;
this.mouseDownY = event.clientY;
this.modalX = modalElement.offsetLeft;
this.modalY = modalElement.offsetTop;
render.setStyle(modalElement, left, `${this.modalX}px`);
render.setStyle(modalElement, top, `${this.modalY}px`);
this.canMove = true;
}.bind(this));
render.listen(modalTitleElement, mouseup, function (event) {
this.canMove = false;
}.bind(this));
render.listen(modalBackground, mousemove, function (event) {
if (this.canMove) {
let moveX = event.clientX - this.mouseDownX;
let moveY = event.clientY - this.mouseDownY;
let newModalX = this.modalX + moveX;
let newModalY = this.modalY + moveY;
render.setStyle(modalElement, left, `${newModalX}px`);
render.setStyle(modalElement, top, `${newModalY}px`);
}
}.bind(this));
}
}
3. 封装为一个moduledrag-modal.module.ts
import { NgModule } from @angular/core;
import { CommonModule } from @angular/common;
import { DragModalDirective } from "./drag-modal.directive";
import { ModalDragService } from "./drag-modal.service";
@NgModule({
providers: [ModalDragService],
declarations: [DragModalDirective],
imports: [
CommonModule,
],
exports: [DragModalDirective]
})
export class ModalDragModule { }
然后把这个模块注入到根模块中,就可以愉快地拖拽了_
4.使用#dragModal [dragModal]="dragModal"
<nz-modal #dragModal [dragModal]="dragModal"> </nz-modal>
