feat(core): doubleClickDragZoom gesture#10327
Merged
Merged
Conversation
Adds the Google Maps-style touch zoom: a quick tap followed by a press-and-drag with the same finger zooms in/out continuously without ever using the second finger. Useful for one-handed touch interaction. - New DOUBLE_TAP_DRAG event channel routed through pointerdown/move/up. - Tap timing constants tuned for snap response without false triggers. - _onPointerDown promotes a stored single tap to a one-finger zoom session when the second tap lands close enough in time and space. - _onPointerMove drives controllerState.zoom relative to vertical drag; _onPointerUp finalizes and suppresses the trailing dblclick. - pan handlers short-circuit while a one-finger zoom is active.
7cea955 to
b1e6a61
Compare
chrisgervang
approved these changes
Jun 10, 2026
Comment on lines
+273
to
+279
| case 'pointerdown': | ||
| return this._onDoubleClickDragPointerDown(event); | ||
| case 'pointermove': | ||
| return this._onDoubleClickDragPointerMove(event); | ||
| case 'pointerup': | ||
| case 'pointercancel': | ||
| return this._onDoubleClickDragPointerUp(event); |
Collaborator
There was a problem hiding this comment.
For follow up, does mjoinir need a 'dblclickmove'? There isn't a second up pointer event so I'm not sure
| PINCH: ['pinchstart', 'pinchmove', 'pinchend'], | ||
| MULTI_PAN: ['multipanstart', 'multipanmove', 'multipanend'], | ||
| DOUBLE_CLICK: ['dblclick'], | ||
| DOUBLE_CLICK_DRAG: ['pointerdown', 'pointermove', 'pointerup', 'pointercancel'], |
Collaborator
There was a problem hiding this comment.
@Pessimistress suggested a good refactor would be to implement a new recognizer in mjolnir for this. It'd simplify the controller compared to using raw pointer events.
Collaborator
Author
There was a problem hiding this comment.
Id like to gain some perspective on how platforms like OS organize their gesture recognition across mobile, mouse, and Vision Pro, I strongly agree gesture recognition should be managed within mjolnir.
55 tasks
This file contains hidden or 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
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Adds a Google/Apple Maps-style one-finger double-click/tap-and-drag zoom gesture for touch users, exposed as its own controller option:
The gesture lets users:
This gives mobile users a precise one-handed zoom path without requiring pinch zoom, on-screen controls, or desktop double-click zoom behavior.
Comparison Videos
Apple Maps Reference
trim.DD19513B-5915-4050-8865-99E128A9E9A0.MOV
deck.gl GlobeController Demo
trim.31AA42AB-9ACB-4104-8629-9C7557592B20.MOV
The deck.gl demo uses the same one-finger sequence against a GlobeView controller path, matching the mobile map interaction model users already expect.
Why
One-handed mobile map navigation currently has a gap: users can pan with one finger, but controlled zoom generally requires either a second finger or visible zoom controls. The double-click/tap-and-drag gesture is a standard mobile map pattern and lets users zoom in or out while keeping their thumb on the map.
While validating on iOS Safari, repeated touch gestures could also trigger page-level selection/callout affordances over the canvas. This PR keeps the gesture path inside deck.gl while leaving browser UI guard CSS to app developers, with reusable guidance documented for apps using deck.gl controllers.
What Changed
doubleClickDragZoomcontroller option, defaulting totrue.DOUBLE_CLICK_DRAGpointer-event gesture path through pointer down, move, up, and cancel handling.DOUBLE_CLICK_DRAG_PIXELS_PER_ZOOM = 120.dblclickafter the drag gesture so release does not apply a second zoom.doubleClickDragZoomin the Controller API.developer-guide/tips-and-tricks.md#optimization-for-mobileand links to that guidance fromcontroller.md.Behavior Notes
doubleClickDragZoomcontrols this gesture independently fromdoubleClickZoomandtouchZoom.doubleClickZoom: false, because the gesture is continuous pointer-driven zoom rather than double-click zoom.touchZoomis disabled, because this is a distinct one-finger gesture.Validation
MapController supports double-click drag zoom when double click and touch zoom are disabled, covering the full pointer sequence and release behavior.MapController disables double-click drag zoom, covering the new controller option gate.yarn test -- test/modules/core/controllers/controllers.spec.ts test/modules/core/lib/deck.spec.tsgit diff --checkhttp://127.0.0.1:3000/with placeholder map API env vars; only dependency source-map warnings fromarcwere reported.Merge Notes
This is intentionally scoped to the reusable one-finger double-click/tap-and-drag zoom gesture, the dedicated controller option, and app-owned docs/example interaction hardening discovered during mobile validation. GlobeView pointer anchoring/parity work is handled separately in #10307, and the local comparison demo combined the two branches only for manual mobile validation.