1 | /**
|
---|
2 | * Custom HammerJS configuration forked from Angular Material. With Angular v9,
|
---|
3 | * Angular Material dropped HammerJS as a dependency. This configuration was added
|
---|
4 | * automatically to this application because ng-update detected that this application
|
---|
5 | * directly used custom HammerJS gestures defined by Angular Material.
|
---|
6 | *
|
---|
7 | * Read more in the dedicated guide: https://git.io/ng-material-v9-hammer-migration
|
---|
8 | */
|
---|
9 |
|
---|
10 | import {Injectable, Inject, Optional, Type} from '@angular/core';
|
---|
11 | import {HammerGestureConfig} from '@angular/platform-browser';
|
---|
12 | import {MAT_HAMMER_OPTIONS} from '@angular/material/core';
|
---|
13 |
|
---|
14 | /**
|
---|
15 | * Noop hammer instance that is used when an instance is requested, but
|
---|
16 | * Hammer has not been loaded on the page yet.
|
---|
17 | */
|
---|
18 | const noopHammerInstance = {
|
---|
19 | on: () => {},
|
---|
20 | off: () => {},
|
---|
21 | };
|
---|
22 |
|
---|
23 | /**
|
---|
24 | * Gesture config that provides custom Hammer gestures on top of the default Hammer
|
---|
25 | * gestures. These gestures will be available as events in component templates.
|
---|
26 | */
|
---|
27 | @Injectable()
|
---|
28 | export class GestureConfig extends HammerGestureConfig {
|
---|
29 | /** List of event names to add to the Hammer gesture plugin list */
|
---|
30 | events = [
|
---|
31 | 'longpress',
|
---|
32 | 'slide',
|
---|
33 | 'slidestart',
|
---|
34 | 'slideend',
|
---|
35 | 'slideright',
|
---|
36 | 'slideleft'
|
---|
37 | ];
|
---|
38 |
|
---|
39 | constructor(@Optional() @Inject(MAT_HAMMER_OPTIONS) private hammerOptions?: any) {
|
---|
40 | super();
|
---|
41 | }
|
---|
42 |
|
---|
43 | /**
|
---|
44 | * Builds Hammer instance manually to add custom recognizers that match the
|
---|
45 | * Material Design specification. Gesture names originate from the Material Design
|
---|
46 | * gestures: https://material.io/design/#gestures-touch-mechanics
|
---|
47 | *
|
---|
48 | * More information on default recognizers can be found in the Hammer docs:
|
---|
49 | * http://hammerjs.github.io/recognizer-pan/
|
---|
50 | * http://hammerjs.github.io/recognizer-press/
|
---|
51 | * @param element Element to which to assign the new HammerJS gestures.
|
---|
52 | * @returns Newly-created HammerJS instance.
|
---|
53 | */
|
---|
54 | buildHammer(element: HTMLElement): any {
|
---|
55 | const hammer: any = typeof window !== 'undefined' ? (window as any).Hammer : null;
|
---|
56 |
|
---|
57 | if (!hammer) {
|
---|
58 | return noopHammerInstance;
|
---|
59 | }
|
---|
60 |
|
---|
61 | const mc = new hammer(element, this.hammerOptions || undefined);
|
---|
62 |
|
---|
63 | // Default Hammer Recognizers.
|
---|
64 | const pan = new hammer.Pan();
|
---|
65 | const swipe = new hammer.Swipe();
|
---|
66 | const press = new hammer.Press();
|
---|
67 |
|
---|
68 | // Notice that a HammerJS recognizer can only depend on one other recognizer once.
|
---|
69 | // Otherwise the previous `recognizeWith` will be dropped.
|
---|
70 | const slide = this._createRecognizer(pan, {event: 'slide', threshold: 0}, swipe);
|
---|
71 | const longpress = this._createRecognizer(press, {event: 'longpress', time: 500});
|
---|
72 |
|
---|
73 | // Overwrite the default `pan` event to use the swipe event.
|
---|
74 | pan.recognizeWith(swipe);
|
---|
75 |
|
---|
76 | // Since the slide event threshold is set to zero, the slide recognizer can fire and
|
---|
77 | // accidentally reset the longpress recognizer. In order to make sure that the two
|
---|
78 | // recognizers can run simultaneously but don't affect each other, we allow the slide
|
---|
79 | // recognizer to recognize while a longpress is being processed.
|
---|
80 | // See: https://github.com/hammerjs/hammer.js/blob/master/src/manager.js#L123-L124
|
---|
81 | longpress.recognizeWith(slide);
|
---|
82 |
|
---|
83 | // Add customized gestures to Hammer manager
|
---|
84 | mc.add([swipe, press, pan, slide, longpress]);
|
---|
85 |
|
---|
86 | return mc;
|
---|
87 | }
|
---|
88 |
|
---|
89 | /** Creates a new recognizer, without affecting the default recognizers of HammerJS */
|
---|
90 | private _createRecognizer(base: object, options: any, ...inheritances: object[]) {
|
---|
91 | const recognizer = new (base.constructor as Type<any>)(options);
|
---|
92 | inheritances.push(base);
|
---|
93 | inheritances.forEach(item => recognizer.recognizeWith(item));
|
---|
94 | return recognizer;
|
---|
95 | }
|
---|
96 | }
|
---|