Skip to content

Pass native pinch gestures through on Fusion - #4

Open
SnackForever wants to merge 2 commits into
marcin-nb:mainfrom
SnackForever:feature/fusion-background-ax
Open

Pass native pinch gestures through on Fusion#4
SnackForever wants to merge 2 commits into
marcin-nb:mainfrom
SnackForever:feature/fusion-background-ax

Conversation

@SnackForever

Copy link
Copy Markdown

Summary

This PR adds focused Fusion-page detection so ResolveZoom passes native pinch
gestures through while DaVinci Resolve's Fusion page is active.

Fusion already handles pinch zoom natively. On the other Resolve pages,
ResolveZoom keeps the existing magnify-to-Option-scroll conversion used for
timeline zoom.

Why Accessibility polling

Resolve does not expose its active page through a public API.

Testing with Accessibility Inspector showed that Resolve exposes the page tabs
as AXCheckBox elements:

  • Media
  • Cut
  • Edit
  • Fusion
  • Color
  • Fairlight
  • Deliver

The selected page has AXValue == 1.

The tab label is not reliably exposed in AXTitle; Resolve stores it in
AXDescription, so the scan uses AXTitle first and falls back to
AXDescription.

AXObserver was considered, but it is not reliable here: Resolve's Qt UI can
destroy and recreate Accessibility elements when pages change, invalidating
observer references. Polling from a freshly acquired window tree is therefore
the more robust approach.

Safety and performance

The original proof of concept used a main-run-loop timer and performed AX work
synchronously. That is unsafe because each AXUIElementCopyAttributeValue
call is synchronous IPC into Resolve; a busy Resolve process can delay it for
seconds and block the event tap.

This implementation avoids that path entirely:

  • A DispatchSourceTimer schedules a lightweight poll every second. Runtime
    testing showed that a run-loop Timer could be delayed until a focus or
    desktop change; the dispatch timer keeps scheduling independent of those
    run-loop modes.
  • The timer only captures Resolve's PID. It performs no AX traversal.
  • The recursive AX walk runs on a dedicated serial .utility queue.
  • AXUIElementSetMessagingTimeout(..., 0.05) is applied before each AX
    request.
  • Each complete scan has a 250 ms upper budget.
  • An AX error, including kAXErrorCannotComplete, aborts the current scan
    rather than continuing through the tree.
  • Only the completed page result returns to the main queue.
  • Page state changes are applied only when a confirmed page change is found.
  • Scan IDs and polling generations discard stale results and prevent
    overlapping scan updates.
  • The event-tap callback never performs Accessibility IPC.

If Resolve is loading or its AX server is unavailable, the last confirmed
state is retained. This avoids accidentally re-enabling interception while
Fusion is still loading.

Validation

Manual testing confirmed:

  • Edit is detected and keeps ResolveZoom's existing timeline zoom conversion.
  • Fusion is detected and receives the original magnify gesture.
  • Edit/Fusion state changes no longer depend on changing desktop or focus.
  • Temporary AX failures are bounded and do not block the event tap.

AI disclosure

This implementation and PR description were produced with assistance from
GPT-5.6 running in Zed. The human contributor performed the DaVinci Resolve
runtime testing, reported behavior and logs, and reviewed the intended scope.

Copilot AI lite review requested due to automatic review settings August 10, 2026 13:18

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

Pull request overview

Adds DaVinci Resolve “Fusion page” detection via Accessibility polling so ResolveZoom can pass native pinch gestures through when Fusion is active, while preserving the existing magnify→Option-scroll behavior on other pages.

Changes:

  • Introduces a periodic, bounded AX-tree scan (off the event-tap hot path) to infer Resolve’s active page.
  • Uses the detected page to pause gesture interception on Fusion and resume elsewhere.
  • Updates README to document Fusion-aware behavior and polling/performance characteristics.

Reviewed changes

Copilot reviewed 2 out of 2 changed files in this pull request and generated 1 comment.

File Description
ResolveZoom/AppDelegate.swift Adds Fusion page polling/scan pipeline and uses it to bypass magnify conversion while Fusion is active.
README.md Documents Fusion-aware pinch handling and the background polling approach.

💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread ResolveZoom/AppDelegate.swift Outdated
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
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.

2 participants