Skip to content

Improve POI context menu open speed & smoothness #5460

Open
aleksandr-tata wants to merge 3 commits into
masterfrom
task_5337_context_menu_opens_slowly
Open

Improve POI context menu open speed & smoothness #5460
aleksandr-tata wants to merge 3 commits into
masterfrom
task_5337_context_menu_opens_slowly

Conversation

@aleksandr-tata

Copy link
Copy Markdown
Contributor

Reduces the perceived latency and jank when opening the POI context menu on tap, bringing it closer to the Android timing.
Changes

  • Single-tap delay instead of requireGestureRecognizerToFail. Removed the requireGestureRecognizerToFail: links between the single-tap context-menu recognizer and the zoom recognizers (they imposed the system's ~400 ms double-tap arbitration on every tap). Replaced with a tunable kSingleTapContextMenuDelay (0.15 s): the menu is scheduled after the tap and cancelled if a second tap begins (touch.tapCount >= 2) or a double-tap zoom fires. Net effect: single tap opens faster while double-tap-to-zoom still works.

  • Two-phase menu build. On a collapsed open (showFullMenu == NO) only the header rows are built before the slide; the detail rows are built right after the slide completes (setDetailRowsDeferred: / buildDeferredDetailRows). This keeps the table render off the animation's critical path.

  • Deferred row reloads during the slide (setRowUpdatesDeferred:) so async row updates don't reload the table mid-animation.

  • Marker and selection polygon drawn first. Menu presentation now yields one runloop cycle before building the menu controller, so the context pin marker and the selected-object polygon/contour highlight render immediately, before the heavier controller/menu build runs.

  • Slide animation 0.3 s → 0.15 s.

@aleksandr-tata aleksandr-tata requested a review from tigrim June 11, 2026 16:19
@aleksandr-tata aleksandr-tata linked an issue Jun 11, 2026 that may be closed by this pull request
1 task
Comment thread Sources/Views/OATargetPointView.mm Outdated
[UIView animateWithDuration:0.3 animations:^{

[self.customController setRowUpdatesDeferred:YES];
[UIView animateWithDuration:0.15 animations:^{

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In Android, mainView.animate().y(posY).setDuration(200) is used. I'd use the same duration here(0.2). We should also align the animation timing with the designer

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

_grPointContextMenu.delegate = self;

// prevents single tap to fire together with double tap
[_grSymbolContextMenu requireGestureRecognizerToFail:_grZoomIn];

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This change introduces a regression compared to the previous requireGestureRecognizerToFail: behavior.

The current implementation relies on a fixed 0.15s delay before opening the context menu. However, a valid double tap can still occur after that delay (while remaining within iOS double-tap recognition timing). In that case, the delayed block may already have executed and opened the POI menu before zoomInGestureDetected is triggered.

zoomInGestureDetected only cancels the pending block, but it does not dismiss a menu that has already been shown. As a result, a double-tap-to-zoom gesture can also display the context menu.

The previous requireGestureRecognizerToFail: approach did not have this issue because it waited for the system double-tap recognition window before handling the single-tap action.

Could we preserve the previous behavior or otherwise ensure that the context menu is not shown when a valid double tap is recognized?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The 0.15s delay is shorter than the system's double-tap window, so a valid second tap can arrive after the block already opened the POI menu. By then cancelPendingContextMenu has nothing to cancel, and the menu stays up on a double-tap zoom.
Increasing the delay won't help: iOS doesn't expose the real double-tap interval, and any safe value would bring back the latency this task removed.
So I handle both cases instead. zoomInGestureDetected: now also dismisses the menu if the delayed block already showed it (within a short 0.4s guard tied to the double-tap, so an unrelated menu is never closed). If the block hasn't fired yet, it's just cancelled as before.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Context menu opens twice as slowly on iOS compared to Android

2 participants