From 8ee5fb66c6a025a6d03c09a0b1a07b08b5b0bb8f Mon Sep 17 00:00:00 2001 From: Kristiyan Kostadinov Date: Tue, 11 Sep 2018 19:40:20 +0200 Subject: [PATCH] fix(drag-drop): text selection not disabled on safari if user drags out of the viewport (#12864) Currently we disable text selection on all draggable elements and their handles, however that doesn't seem to be enough on Safari, because moving your cursor towards the end of the viewport causes the entire body text to be marked. These changes also disable text marking on the entire body while the user is dragging. --- src/cdk/drag-drop/drag-drop-registry.spec.ts | 10 ++++++++++ src/cdk/drag-drop/drag-drop-registry.ts | 5 +++++ src/cdk/drag-drop/drop.scss | 3 ++- 3 files changed, 17 insertions(+), 1 deletion(-) diff --git a/src/cdk/drag-drop/drag-drop-registry.spec.ts b/src/cdk/drag-drop/drag-drop-registry.spec.ts index 0d17e3e1278..216617e4804 100644 --- a/src/cdk/drag-drop/drag-drop-registry.spec.ts +++ b/src/cdk/drag-drop/drag-drop-registry.spec.ts @@ -155,6 +155,16 @@ describe('DragDropRegistry', () => { expect(dispatchTouchEvent(document, 'touchmove').defaultPrevented).toBe(true); }); + it('should disable the native interactions on the body while dragging', () => { + const firstItem = testComponent.dragItems.first; + + registry.startDragging(firstItem, createMouseEvent('mousedown')); + expect(document.body.classList).toContain('cdk-drag-drop-disable-native-interactions'); + + registry.stopDragging(firstItem); + expect(document.body.classList).not.toContain('cdk-drag-drop-disable-native-interactions'); + }); + }); @Component({ diff --git a/src/cdk/drag-drop/drag-drop-registry.ts b/src/cdk/drag-drop/drag-drop-registry.ts index 46b884a7001..13e798971dd 100644 --- a/src/cdk/drag-drop/drag-drop-registry.ts +++ b/src/cdk/drag-drop/drag-drop-registry.ts @@ -116,6 +116,10 @@ export class DragDropRegistry implements OnDestroy { const moveEvent = isTouchEvent ? 'touchmove' : 'mousemove'; const upEvent = isTouchEvent ? 'touchend' : 'mouseup'; + // We need to disable the native interactions on the entire body, because + // the user can start marking text if they drag too far in Safari. + this._document.body.classList.add('cdk-drag-drop-disable-native-interactions'); + // We explicitly bind __active__ listeners here, because newer browsers will default to // passive ones for `mousemove` and `touchmove`. The events need to be active, because we // use `preventDefault` to prevent the page from scrolling while the user is dragging. @@ -136,6 +140,7 @@ export class DragDropRegistry implements OnDestroy { if (this._activeDragInstances.size === 0) { this._clearGlobalListeners(); + this._document.body.classList.remove('cdk-drag-drop-disable-native-interactions'); } } diff --git a/src/cdk/drag-drop/drop.scss b/src/cdk/drag-drop/drop.scss index 700ff5cb61b..31bd978c287 100644 --- a/src/cdk/drag-drop/drop.scss +++ b/src/cdk/drag-drop/drop.scss @@ -8,7 +8,8 @@ $cdk-z-index-drag-preview: 1000; } .cdk-drag, -.cdk-drag-handle { +.cdk-drag-handle, +.cdk-drag-drop-disable-native-interactions { touch-action: none; -webkit-user-drag: none; -webkit-tap-highlight-color: transparent;