Created
November 29, 2018 05:51
-
-
Save Muzammil-Bilwani/f0b40b1e1ce0ad87ec246d3f90c81b25 to your computer and use it in GitHub Desktop.
Drag a modal with a dragger Directive in angular
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@Directive({ | |
// tslint:disable-next-line:directive-selector | |
selector: "[draggable]" | |
}) | |
export class DraggableDirective implements AfterViewInit, OnDestroy { | |
@Input() dragHandle: string; | |
@Input() dragTarget: string; | |
// Element to be dragged | |
private target: HTMLElement; | |
// Drag handle | |
private handle: HTMLElement; | |
private delta = { x: 0, y: 0 }; | |
private offset = { x: 0, y: 0 }; | |
private destroy$ = new Subject<void>(); | |
constructor(private elementRef: ElementRef, private zone: NgZone) { | |
} | |
public ngAfterViewInit(): void { | |
// console.log('Directive up'); | |
this.handle = this.dragHandle ? document.querySelector(this.dragHandle) as HTMLElement : | |
this.elementRef.nativeElement; | |
this.target = document.querySelector(this.dragTarget) as HTMLElement; | |
this.setupEvents(); | |
} | |
public ngOnDestroy(): void { | |
this.destroy$.next(); | |
} | |
private setupEvents() { | |
this.zone.runOutsideAngular(() => { | |
const mousedown$ = Observable.fromEvent(this.handle, "mousedown"); | |
const mousemove$ = Observable.fromEvent(document, "mousemove"); | |
const mouseup$ = Observable.fromEvent(document, "mouseup"); | |
const mousedrag$ = mousedown$.switchMap((event: MouseEvent) => { | |
const startX = event.clientX; | |
const startY = event.clientY; | |
return mousemove$ | |
// tslint:disable-next-line:no-shadowed-variable | |
.map((event: MouseEvent) => { | |
event.preventDefault(); | |
this.delta = { | |
x: event.clientX - startX, | |
y: event.clientY - startY | |
}; | |
}) | |
.takeUntil(mouseup$); | |
}).takeUntil(this.destroy$); | |
mousedrag$.subscribe(() => { | |
if (this.delta.x === 0 && this.delta.y === 0) { | |
return; | |
} | |
this.translate(); | |
}); | |
mouseup$.takeUntil(this.destroy$).subscribe(() => { | |
this.offset.x += this.delta.x; | |
this.offset.y += this.delta.y; | |
this.delta = { x: 0, y: 0 }; | |
}); | |
}); | |
} | |
private translate() { | |
requestAnimationFrame(() => { | |
this.target.style.transform = ` | |
translate(${this.offset.x + this.delta.x}px, | |
${this.offset.y + this.delta.y}px) | |
`; | |
}); | |
} | |
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<mat-icon matTooltip="Hold and move to drag" class="drager hand" [draggable] dragHandle=".drager" dragTarget=".mat-dialog-container">drag_indicator</mat-icon> | |
<!-- Can be any div or any element --> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment