gesturx 1.0.0 → 1.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (63) hide show
  1. package/README.md +17 -1
  2. package/dist/core/index.d.ts +4 -0
  3. package/dist/core/manager.d.ts +15 -0
  4. package/dist/core/pan/PanRecognizer.d.ts +19 -0
  5. package/dist/core/pinch/PinchRecognizer.d.ts +29 -0
  6. package/dist/core/recognizer/Recognizer.d.ts +21 -0
  7. package/dist/core/recognizer/RecognizerEvent.d.ts +42 -0
  8. package/dist/core/recognizer/mapToRecognizerEvent.d.ts +8 -0
  9. package/dist/core/rotate/RotateRecognizer.d.ts +24 -0
  10. package/dist/core/swipe/SwipeRecognizer.d.ts +30 -0
  11. package/dist/core/swipe/SwipeRecognizer.test.d.ts +1 -0
  12. package/dist/core/swipe/isRecognizedAsSwipe.d.ts +4 -0
  13. package/dist/core/tap/TapRecognizer.d.ts +20 -0
  14. package/dist/core/tap/TapRecognizer.test.d.ts +1 -0
  15. package/dist/core/utils/events.d.ts +40 -0
  16. package/dist/core/utils/geometry.d.ts +17 -0
  17. package/dist/core/utils/utils.d.ts +17 -0
  18. package/dist/core/utils/utils.test.d.ts +1 -0
  19. package/dist/demo/App.d.ts +2 -0
  20. package/dist/demo/DebugBox.d.ts +5 -0
  21. package/dist/demo/useManager.d.ts +11 -0
  22. package/dist/demo/useTap.d.ts +5 -0
  23. package/dist/index.js +505 -0
  24. package/dist/index.js.map +1 -0
  25. package/dist/index.umd.cjs +2 -0
  26. package/dist/index.umd.cjs.map +1 -0
  27. package/dist/main.d.ts +1 -0
  28. package/dist/theme.d.ts +1 -0
  29. package/package.json +4 -1
  30. package/.github/workflows/publish.yml +0 -17
  31. package/.prettierrc.json +0 -3
  32. package/eslint.config.js +0 -18
  33. package/index.html +0 -13
  34. package/src/core/index.ts +0 -4
  35. package/src/core/manager.ts +0 -46
  36. package/src/core/pan/PanRecognizer.ts +0 -192
  37. package/src/core/pinch/PinchRecognizer.ts +0 -131
  38. package/src/core/recognizer/Recognizer.ts +0 -54
  39. package/src/core/recognizer/RecognizerEvent.ts +0 -39
  40. package/src/core/recognizer/mapToRecognizerEvent.ts +0 -142
  41. package/src/core/rotate/RotateRecognizer.ts +0 -115
  42. package/src/core/swipe/SwipeRecognizer.test.ts +0 -160
  43. package/src/core/swipe/SwipeRecognizer.ts +0 -82
  44. package/src/core/swipe/isRecognizedAsSwipe.ts +0 -13
  45. package/src/core/tap/TapRecognizer.test.ts +0 -567
  46. package/src/core/tap/TapRecognizer.ts +0 -172
  47. package/src/core/utils/events.ts +0 -186
  48. package/src/core/utils/geometry.ts +0 -115
  49. package/src/core/utils/utils.test.ts +0 -26
  50. package/src/core/utils/utils.ts +0 -58
  51. package/src/demo/App.tsx +0 -171
  52. package/src/demo/DebugBox.tsx +0 -10
  53. package/src/demo/useManager.ts +0 -40
  54. package/src/demo/useTap.tsx +0 -87
  55. package/src/index.css +0 -66
  56. package/src/main.tsx +0 -14
  57. package/src/theme.ts +0 -11
  58. package/src/vite-env.d.ts +0 -1
  59. package/tsconfig.json +0 -26
  60. package/tsconfig.node.json +0 -11
  61. package/vite.config.ts +0 -38
  62. package/vitest.config.ts +0 -8
  63. /package/{public → dist}/vite.svg +0 -0
@@ -1,567 +0,0 @@
1
- import { describe, it, expect, beforeEach } from "vitest"
2
- import { TapRecognizer } from "./TapRecognizer"
3
- import { buffer, first, lastValueFrom, tap, timer } from "rxjs"
4
-
5
- const waitFor = (time: number) =>
6
- new Promise((resolve) => setTimeout(resolve, time))
7
-
8
- describe("TapGestureRecognizer", () => {
9
- let container = document.createElement("div")
10
-
11
- beforeEach(() => {
12
- container = document.createElement("div")
13
- document.body.appendChild(container)
14
- })
15
-
16
- function createPointerEvent({
17
- type,
18
- x,
19
- y,
20
- identifier,
21
- }: {
22
- type: string
23
- x: number
24
- y: number
25
- identifier: number
26
- }) {
27
- const event = new PointerEvent(type, {
28
- clientX: x,
29
- clientY: y,
30
- pointerId: identifier,
31
- pointerType: "touch",
32
- bubbles: true,
33
- })
34
-
35
- // @ts-ignore
36
- event.x = x
37
- // @ts-ignore
38
- event.y = y
39
-
40
- return event
41
- }
42
-
43
- function sendPointerEvent({
44
- type,
45
- x,
46
- y,
47
- container,
48
- identifier,
49
- }: {
50
- container: HTMLElement
51
- type: string
52
- x: number
53
- y: number
54
- identifier: number
55
- }) {
56
- const event = createPointerEvent({
57
- type,
58
- x,
59
- y,
60
- identifier,
61
- })
62
-
63
- sendPointerEventFromEvent({ event, container })
64
- }
65
-
66
- function sendPointerEventFromEvent({
67
- event,
68
- container,
69
- }: {
70
- event: PointerEvent
71
- container: HTMLElement
72
- }) {
73
- container.dispatchEvent(event)
74
- }
75
-
76
- it("should detect a single tap", async () => {
77
- const multiTapThreshold = 5
78
- const waitLongEnough$ = timer(100)
79
- const recognizer = new TapRecognizer({ multiTapThreshold })
80
- recognizer.initialize({
81
- container,
82
- })
83
-
84
- const values = await lastValueFrom(
85
- recognizer.events$.pipe(
86
- tap({
87
- subscribe: async () => {
88
- await waitFor(1)
89
-
90
- sendPointerEvent({
91
- container,
92
- identifier: 1,
93
- type: "pointerdown",
94
- x: 0,
95
- y: 0,
96
- })
97
- sendPointerEvent({
98
- container,
99
- identifier: 1,
100
- type: "pointerup",
101
- x: 0,
102
- y: 0,
103
- })
104
- },
105
- }),
106
- buffer(waitLongEnough$),
107
- first(),
108
- ),
109
- )
110
-
111
- expect(values).toMatchObject([{ type: "tap", taps: 1 }])
112
- })
113
-
114
- it("should detect a double tap", async () => {
115
- const multiTapThreshold = 5
116
- const waitLongEnough$ = timer(multiTapThreshold * 2)
117
- const recognizer = new TapRecognizer({ multiTapThreshold, maxTaps: 2 })
118
- recognizer.initialize({
119
- container,
120
- })
121
-
122
- const values = await lastValueFrom(
123
- recognizer.events$.pipe(
124
- tap({
125
- subscribe: async () => {
126
- await waitFor(1)
127
-
128
- sendPointerEvent({
129
- container,
130
- identifier: 1,
131
- type: "pointerdown",
132
- x: 0,
133
- y: 0,
134
- })
135
- sendPointerEvent({
136
- container,
137
- identifier: 1,
138
- type: "pointerup",
139
- x: 0,
140
- y: 0,
141
- })
142
- sendPointerEvent({
143
- container,
144
- identifier: 2,
145
- type: "pointerdown",
146
- x: 0,
147
- y: 0,
148
- })
149
- sendPointerEvent({
150
- container,
151
- identifier: 2,
152
- type: "pointerup",
153
- x: 0,
154
- y: 0,
155
- })
156
- },
157
- }),
158
- buffer(waitLongEnough$),
159
- first(),
160
- ),
161
- )
162
-
163
- expect(values).toMatchObject([{ type: "tap", taps: 2 }])
164
- })
165
-
166
- it("should detect a triple tap", async () => {
167
- const multiTapThreshold = 5
168
- const recognizer = new TapRecognizer({ multiTapThreshold, maxTaps: 3 })
169
- recognizer.initialize({
170
- container,
171
- })
172
- const waitLongEnough$ = timer(100)
173
-
174
- const values = await lastValueFrom(
175
- recognizer.events$.pipe(
176
- tap({
177
- subscribe: () => {
178
- setTimeout(() => {
179
- sendPointerEvent({
180
- container,
181
- identifier: 1,
182
- type: "pointerdown",
183
- x: 0,
184
- y: 0,
185
- })
186
- sendPointerEvent({
187
- container,
188
- identifier: 1,
189
- type: "pointerup",
190
- x: 0,
191
- y: 0,
192
- })
193
- sendPointerEvent({
194
- container,
195
- identifier: 1,
196
- type: "pointerdown",
197
- x: 0,
198
- y: 0,
199
- })
200
- sendPointerEvent({
201
- container,
202
- identifier: 1,
203
- type: "pointerup",
204
- x: 0,
205
- y: 0,
206
- })
207
- sendPointerEvent({
208
- container,
209
- identifier: 1,
210
- type: "pointerdown",
211
- x: 0,
212
- y: 0,
213
- })
214
- sendPointerEvent({
215
- container,
216
- identifier: 1,
217
- type: "pointerup",
218
- x: 0,
219
- y: 0,
220
- })
221
- })
222
- },
223
- }),
224
- buffer(waitLongEnough$),
225
- first(),
226
- ),
227
- )
228
-
229
- expect(values).toMatchObject([{ type: "tap", taps: 3 }])
230
- })
231
-
232
- it("should not detect a double tap if the second tap is after threshold", async () => {
233
- const multiTapThreshold = 5
234
- const waitLongEnough$ = timer(100)
235
- const recognizer = new TapRecognizer({ multiTapThreshold, maxTaps: 2 })
236
- recognizer.initialize({
237
- container,
238
- })
239
-
240
- const values = await lastValueFrom(
241
- recognizer.events$.pipe(
242
- tap({
243
- subscribe: async () => {
244
- await waitFor(1)
245
-
246
- sendPointerEvent({
247
- container,
248
- identifier: 1,
249
- type: "pointerdown",
250
- x: 0,
251
- y: 0,
252
- })
253
- sendPointerEvent({
254
- container,
255
- identifier: 1,
256
- type: "pointerup",
257
- x: 0,
258
- y: 0,
259
- })
260
-
261
- await waitFor(multiTapThreshold)
262
-
263
- sendPointerEvent({
264
- container,
265
- identifier: 2,
266
- type: "pointerdown",
267
- x: 0,
268
- y: 0,
269
- })
270
- sendPointerEvent({
271
- container,
272
- identifier: 2,
273
- type: "pointerup",
274
- x: 0,
275
- y: 0,
276
- })
277
- },
278
- }),
279
- buffer(waitLongEnough$),
280
- first(),
281
- ),
282
- )
283
-
284
- expect(values.length).toBe(2)
285
- expect(values).toMatchObject([
286
- { type: "tap", taps: 1, pointers: [{ pointerId: 1 }] },
287
- { type: "tap", taps: 1, pointers: [{ pointerId: 2 }] },
288
- ])
289
- })
290
-
291
- it("should not trigger tap if moved too much between down and up", async () => {
292
- const multiTapThreshold = 5
293
- const waitLongEnough$ = timer(100)
294
- const recognizer = new TapRecognizer({
295
- multiTapThreshold,
296
- posThreshold: 5,
297
- })
298
- recognizer.initialize({
299
- container,
300
- })
301
-
302
- const values = await lastValueFrom(
303
- recognizer.events$.pipe(
304
- tap({
305
- subscribe: async () => {
306
- await waitFor(1)
307
-
308
- sendPointerEvent({
309
- container,
310
- identifier: 1,
311
- type: "pointerdown",
312
- x: 0,
313
- y: 0,
314
- })
315
-
316
- sendPointerEvent({
317
- container,
318
- identifier: 1,
319
- type: "pointerup",
320
- x: 50,
321
- y: 50,
322
- })
323
- },
324
- }),
325
- buffer(waitLongEnough$),
326
- first(),
327
- ),
328
- )
329
-
330
- expect(values.length).toBe(0)
331
- })
332
-
333
- it("should not detect a tap if the pointer is held down too long", async () => {
334
- const multiTapThreshold = 5
335
- const maximumPressTime = 10
336
- const waitLongEnough$ = timer(100)
337
- const recognizer = new TapRecognizer({
338
- multiTapThreshold,
339
- posThreshold: 5,
340
- maximumPressTime,
341
- })
342
- recognizer.initialize({
343
- container,
344
- })
345
-
346
- const values = await lastValueFrom(
347
- recognizer.events$.pipe(
348
- tap({
349
- subscribe: async () => {
350
- await waitFor(1)
351
-
352
- sendPointerEvent({
353
- container,
354
- identifier: 1,
355
- type: "pointerdown",
356
- x: 0,
357
- y: 0,
358
- })
359
-
360
- await waitFor(maximumPressTime - 5)
361
-
362
- sendPointerEvent({
363
- container,
364
- identifier: 1,
365
- type: "pointerup",
366
- x: 0,
367
- y: 0,
368
- })
369
-
370
- await waitFor(multiTapThreshold * 2)
371
-
372
- sendPointerEvent({
373
- container,
374
- identifier: 2,
375
- type: "pointerdown",
376
- x: 0,
377
- y: 0,
378
- })
379
-
380
- await waitFor(maximumPressTime)
381
-
382
- sendPointerEvent({
383
- container,
384
- identifier: 2,
385
- type: "pointerup",
386
- x: 0,
387
- y: 0,
388
- })
389
- },
390
- }),
391
- buffer(waitLongEnough$),
392
- first(),
393
- ),
394
- )
395
-
396
- expect(values.length).toBe(1)
397
- expect(values).toMatchObject([
398
- { type: "tap", taps: 1, pointers: [{ pointerId: 1 }] },
399
- ])
400
- })
401
-
402
- it("should ignore taps when there are simultaneous pointers active", async () => {
403
- const recognizer = new TapRecognizer({})
404
- recognizer.initialize({
405
- container,
406
- })
407
- const waitLongEnough$ = timer(100)
408
-
409
- const values = await lastValueFrom(
410
- recognizer.events$.pipe(
411
- tap({
412
- subscribe: () => {
413
- setTimeout(() => {
414
- sendPointerEvent({
415
- container,
416
- identifier: 1,
417
- type: "pointerdown",
418
- x: 0,
419
- y: 0,
420
- })
421
- sendPointerEvent({
422
- container,
423
- identifier: 2,
424
- type: "pointerdown",
425
- x: 10,
426
- y: 10,
427
- })
428
- sendPointerEvent({
429
- container,
430
- identifier: 1,
431
- type: "pointerup",
432
- x: 0,
433
- y: 0,
434
- })
435
- sendPointerEvent({
436
- container,
437
- identifier: 2,
438
- type: "pointerup",
439
- x: 10,
440
- y: 10,
441
- })
442
- })
443
- },
444
- }),
445
- buffer(waitLongEnough$),
446
- first(),
447
- ),
448
- )
449
-
450
- expect(values.length).toBe(0) // Assuming the recognizer should ignore simultaneous taps
451
- })
452
-
453
- it("should ignore one tap if there is more than one tap", async () => {
454
- const recognizer = new TapRecognizer({
455
- multiTapThreshold: 10,
456
- maxTaps: 1,
457
- })
458
- recognizer.initialize({
459
- container,
460
- })
461
- const waitLongEnough$ = timer(100)
462
-
463
- const values = await lastValueFrom(
464
- recognizer.events$.pipe(
465
- tap({
466
- subscribe: async () => {
467
- await waitFor(1)
468
-
469
- sendPointerEvent({
470
- container,
471
- identifier: 1,
472
- type: "pointerdown",
473
- x: 0,
474
- y: 0,
475
- })
476
- sendPointerEvent({
477
- container,
478
- identifier: 1,
479
- type: "pointerup",
480
- x: 0,
481
- y: 0,
482
- })
483
-
484
- await waitFor(1)
485
-
486
- sendPointerEvent({
487
- container,
488
- identifier: 2,
489
- type: "pointerdown",
490
- x: 0,
491
- y: 0,
492
- })
493
- sendPointerEvent({
494
- container,
495
- identifier: 2,
496
- type: "pointerup",
497
- x: 0,
498
- y: 0,
499
- })
500
- },
501
- }),
502
- buffer(waitLongEnough$),
503
- first(),
504
- ),
505
- )
506
-
507
- expect(values.length).toBe(0)
508
- })
509
-
510
- it("should ignore taps when a second tap is outside of position threshold", async () => {
511
- const recognizer = new TapRecognizer({
512
- posThreshold: 5,
513
- multiTapThreshold: 10,
514
- maxTaps: Infinity,
515
- })
516
- recognizer.initialize({
517
- container,
518
- })
519
- const waitLongEnough$ = timer(100)
520
-
521
- const values = await lastValueFrom(
522
- recognizer.events$.pipe(
523
- tap({
524
- subscribe: async () => {
525
- // await waitFor(1)
526
-
527
- sendPointerEvent({
528
- container,
529
- identifier: 1,
530
- type: "pointerdown",
531
- x: 0,
532
- y: 0,
533
- })
534
- sendPointerEvent({
535
- container,
536
- identifier: 1,
537
- type: "pointerup",
538
- x: 0,
539
- y: 0,
540
- })
541
-
542
- // await waitFor(1)
543
-
544
- sendPointerEvent({
545
- container,
546
- identifier: 2,
547
- type: "pointerdown",
548
- x: 10,
549
- y: 10,
550
- })
551
- sendPointerEvent({
552
- container,
553
- identifier: 2,
554
- type: "pointerup",
555
- x: 10,
556
- y: 10,
557
- })
558
- },
559
- }),
560
- buffer(waitLongEnough$),
561
- first(),
562
- ),
563
- )
564
-
565
- expect(values.length).toBe(0)
566
- })
567
- })