@@ -82,6 +82,14 @@ export function CDK_DRAG_CONFIG_FACTORY(): CdkDragConfig {
82
82
/** Options that can be used to bind a passive event listener. */
83
83
const passiveEventListenerOptions = normalizePassiveListenerOptions ( { passive : true } ) ;
84
84
85
+ /**
86
+ * Time in milliseconds for which to ignore mouse events, after
87
+ * receiving a touch event. Used to avoid doing double work for
88
+ * touch devices where the browser fires fake mouse events, in
89
+ * addition to touch events.
90
+ */
91
+ const MOUSE_EVENT_IGNORE_TIME = 800 ;
92
+
85
93
/** Element that can be moved inside a CdkDropList container. */
86
94
@Directive ( {
87
95
selector : '[cdkDrag]' ,
@@ -174,6 +182,12 @@ export class CdkDrag<T = any> implements AfterViewInit, OnDestroy {
174
182
175
183
/** Subscription to the event that is dispatched when the user lifts their pointer. */
176
184
private _pointerUpSubscription = Subscription . EMPTY ;
185
+ /**
186
+ * Time at which the last touch event occurred. Used to avoid firing the same
187
+ * events multiple times on touch devices where the browser will fire a fake
188
+ * mouse event for each touch event, after a certain time.
189
+ */
190
+ private _lastTouchEventTime : number ;
177
191
178
192
/** Subscription to the stream that initializes the root element. */
179
193
private _rootElementInitSubscription = Subscription . EMPTY ;
@@ -347,8 +361,14 @@ export class CdkDrag<T = any> implements AfterViewInit, OnDestroy {
347
361
// starting another sequence for a draggable parent somewhere up the DOM tree.
348
362
event . stopPropagation ( ) ;
349
363
364
+ const isDragging = this . _isDragging ( ) ;
365
+ const isTouchEvent = this . _isTouchEvent ( event ) ;
366
+ const isAuxiliaryMouseButton = ! isTouchEvent && ( event as MouseEvent ) . button !== 0 ;
367
+ const isSyntheticEvent = ! isTouchEvent && this . _lastTouchEventTime &&
368
+ this . _lastTouchEventTime + MOUSE_EVENT_IGNORE_TIME > Date . now ( ) ;
369
+
350
370
// Abort if the user is already dragging or is using a mouse button other than the primary one.
351
- if ( this . _isDragging ( ) || ( ! this . _isTouchEvent ( event ) && event . button !== 0 ) ) {
371
+ if ( isDragging || isAuxiliaryMouseButton || isSyntheticEvent ) {
352
372
return ;
353
373
}
354
374
@@ -375,10 +395,14 @@ export class CdkDrag<T = any> implements AfterViewInit, OnDestroy {
375
395
}
376
396
377
397
/** Starts the dragging sequence. */
378
- private _startDragSequence ( ) {
398
+ private _startDragSequence ( event : MouseEvent | TouchEvent ) {
379
399
// Emit the event on the item before the one on the container.
380
400
this . started . emit ( { source : this } ) ;
381
401
402
+ if ( this . _isTouchEvent ( event ) ) {
403
+ this . _lastTouchEventTime = Date . now ( ) ;
404
+ }
405
+
382
406
if ( this . dropContainer ) {
383
407
const element = this . _rootElement ;
384
408
@@ -413,7 +437,7 @@ export class CdkDrag<T = any> implements AfterViewInit, OnDestroy {
413
437
// per pixel of movement (e.g. if the user moves their pointer quickly).
414
438
if ( distanceX + distanceY >= this . _config . dragStartThreshold ) {
415
439
this . _hasStartedDragging = true ;
416
- this . _ngZone . run ( ( ) => this . _startDragSequence ( ) ) ;
440
+ this . _ngZone . run ( ( ) => this . _startDragSequence ( event ) ) ;
417
441
}
418
442
419
443
return ;
@@ -473,10 +497,14 @@ export class CdkDrag<T = any> implements AfterViewInit, OnDestroy {
473
497
this . _passiveTransform . x = this . _activeTransform . x ;
474
498
this . _passiveTransform . y = this . _activeTransform . y ;
475
499
this . _ngZone . run ( ( ) => this . ended . emit ( { source : this } ) ) ;
500
+ this . _dragDropRegistry . stopDragging ( this ) ;
476
501
return ;
477
502
}
478
503
479
- this . _animatePreviewToPlaceholder ( ) . then ( ( ) => this . _cleanupDragArtifacts ( ) ) ;
504
+ this . _animatePreviewToPlaceholder ( ) . then ( ( ) => {
505
+ this . _cleanupDragArtifacts ( ) ;
506
+ this . _dragDropRegistry . stopDragging ( this ) ;
507
+ } ) ;
480
508
}
481
509
482
510
/** Cleans up the DOM artifacts that were added to facilitate the element being dragged. */
0 commit comments