Skip to content

feat: DemoType mode — simulated typing for demos#33

Closed
yusufk wants to merge 7 commits into
07JP27:mainfrom
yusufk:feature/demo-type
Closed

feat: DemoType mode — simulated typing for demos#33
yusufk wants to merge 7 commits into
07JP27:mainfrom
yusufk:feature/demo-type

Conversation

@yusufk

@yusufk yusufk commented May 23, 2026

Copy link
Copy Markdown
Contributor

Summary

Implements DemoType (⌃⇧D) — simulates typing pre-entered text character-by-character into the focused app. Matches Windows ZoomIt behavior.

Changes

DemoType

  • Hotkey ⌃⇧D opens input dialog to enter/paste text
  • Click "Type" → focus returns to previous app → text types out character by character
  • Press ⌃⇧D again to stop mid-typing
  • Configurable speed: 5–60 characters/sec (default 15)
  • Settings tab for pre-configuring text and adjusting speed
  • Remembers last used text between sessions
  • Uses CGEvent Unicode key posting (requires Accessibility permission)

Focus Restore (all modes)

  • Zoom, Live Zoom, Draw, and DemoType now restore focus to the previously active app on dismiss
  • Matches Windows ZoomIt behavior

Menu Bar

  • Added Live Zoom and DemoType entries with hotkey shortcuts

Testing

  • Verified on macOS 15.7.7
  • Tested: dialog flow, typing into Terminal/TextEdit, speed adjustment, stop mid-type, focus restore

@07JP27 07JP27 left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

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

It looks like the branch for another pull request of yours and the branch for this pull request have gotten mixed together.
Please keep each branch scoped so that it reflects only the contents of its own pull request.

Comment thread design/LiveZoom-implementation-plan.md
Comment thread src/ZoomacIt/Overlay/LiveZoomView.swift
Comment thread src/ZoomacIt/Overlay/LiveZoomWindowController.swift
Comment thread src/ZoomacIt/Models/Settings.swift
Comment thread src/ZoomacIt/Models/Settings.swift Outdated
Comment thread src/ZoomacIt/Models/Settings.swift
Comment thread src/ZoomacIt/App/AppDelegate.swift
@yusufk yusufk force-pushed the feature/demo-type branch from 921f934 to 4d47fc2 Compare May 24, 2026 13:01
@yusufk

yusufk commented May 24, 2026

Copy link
Copy Markdown
Contributor Author

Fixed — rebased the branch so it only contains the DemoType commit on top of main. All Live Zoom references have been removed. The branch is now properly scoped to just this feature.

Changes:

  • Removed Live Zoom hotkey registration, menu item, and controller references
  • Kept only DemoType-specific code (controller, settings tab, hotkey, menu entry, focus restore)

@yusufk

yusufk commented May 24, 2026

Copy link
Copy Markdown
Contributor Author

These branches have been rebased — each now only contains commits scoped to its own feature. Could you take another look?

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 a new DemoType mode (simulated typing via ⌃⇧D) and wires it into the app’s hotkey/settings/menu infrastructure, plus introduces “restore focus to previous app” behavior for existing overlay modes.

Changes:

  • Added DemoType settings (text + characters/sec) persisted in Settings and covered by unit tests.
  • Registered a new global hotkey and added a DemoType menu bar item.
  • Introduced DemoTypeController to show an input dialog and post per-character CGEvents; added focus save/restore plumbing in AppDelegate.

Reviewed changes

Copilot reviewed 10 out of 10 changed files in this pull request and generated 8 comments.

Show a summary per file
File Description
src/ZoomacItTests/SettingsTests.swift Adds tests for DemoType defaults and round-trips.
src/ZoomacIt/Settings/SettingsView.swift Adds DemoType as a new Settings tab.
src/ZoomacIt/Settings/DemoTypeTab.swift New SwiftUI tab to edit DemoType text + typing speed.
src/ZoomacIt/Models/Settings.swift Persists DemoType hotkey/text/speed in UserDefaults + reset support.
src/ZoomacIt/Core/HotkeyManager.swift Registers/unregisters the ⌃⇧D hotkey and dispatches callbacks.
src/ZoomacIt/Core/DemoTypeController.swift New controller implementing the modal input dialog + simulated typing loop.
src/ZoomacIt/App/StatusBarController.swift Adds DemoType item to the status bar menu with shortcut display.
src/ZoomacIt/App/AppDelegate.swift Hooks DemoType into HotkeyManager; adds previous-app focus save/restore usage for modes.
src/ZoomacIt.xcodeproj/project.pbxproj Adds new files to the Xcode project.
README.md Marks DemoType as implemented in feature coverage table.

Comment thread src/ZoomacIt/App/AppDelegate.swift
Comment thread src/ZoomacIt/App/AppDelegate.swift
Comment thread src/ZoomacIt/Core/DemoTypeController.swift
Comment thread src/ZoomacIt/Core/DemoTypeController.swift
Comment thread src/ZoomacIt/Core/DemoTypeController.swift
Comment thread src/ZoomacIt/Core/DemoTypeController.swift
Comment thread src/ZoomacIt.xcodeproj/project.pbxproj
Comment thread README.md
@07JP27

07JP27 commented May 27, 2026

Copy link
Copy Markdown
Owner

@yusufk Could you resolve conflicts?

@07JP27 07JP27 left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

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

・Please update docs/ to reflect this change as well.
・Please check Copilot's review and address it if needed.

@yusufk

yusufk commented May 27, 2026

Copy link
Copy Markdown
Contributor Author

Addressed all Copilot review feedback:

  • Race condition: demoTypeController now assigned before start()
  • activate() API: Using activate(options: .activateIgnoringOtherApps)
  • Cancel path: Restores previous app focus on Cancel/empty input
  • Accessibility check: Added AXIsProcessTrusted() preflight with prompt
  • Division by zero: Speed clamped to 1–200 range
  • O(n²) indexing: Using Array(text) for O(1) character access
  • xcuserdata: Removed from tracking, added to .gitignore
  • README: Added Accessibility permission note

Not changed:

  • pbxproj hand-edit — project uses XcodeGen but the generated output is committed per repo convention

@yusufk yusufk requested a review from 07JP27 May 27, 2026 18:30
@yusufk yusufk force-pushed the feature/demo-type branch from 9725e9d to 9099eef Compare May 29, 2026 07:49
@yusufk

yusufk commented May 30, 2026

Copy link
Copy Markdown
Contributor Author

Conflicts resolved, docs added, Copilot feedback addressed. Ready for re-review.

@07JP27 07JP27 left a comment

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

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

Thanks for working on DemoType, but I need to push back here: please verify the actual ZoomIt DemoType behavior before implementing or documenting this as compatible. The current workflow does not match ZoomIt, and this is not a small UX difference.

References:

In ZoomIt, pressing Ctrl+7 does not open an input dialog. The DemoType script is prepared ahead of time, either from a configured file or from clipboard text marked with the [start] prefix. Then Ctrl+7 immediately starts injecting the current script/snippet into the already-focused target window.

The current implementation opens a modal input dialog every time Ctrl+7 is pressed. That means the user has to enter or paste text at activation time, click Type, and then rely on focus restoration. This is fundamentally different from ZoomIt's DemoType workflow and makes the feature feel like an ad-hoc typing macro rather than DemoType.

Please re-check the upstream behavior and adjust the implementation accordingly. At minimum, the DemoType hotkey should not open a text input dialog. It should run preconfigured/preloaded DemoType text against the currently focused target app.

ZoomIt-compatible behavior to account for includes:

  • Ctrl+7 starts typing the prepared script immediately into the focused target window
  • script can be sourced from settings/file and/or clipboard with [start]
  • [end] splits the script into snippets
  • Ctrl+Shift+7 moves back to the previous snippet
  • Esc cancels an active DemoType session
  • control keywords such as [pause:n], [enter], [up], [down], [left], [right], and [paste]...[/paste] are supported, or clearly documented as not yet supported

yusufk and others added 7 commits May 31, 2026 18:16
DemoType (⌃⇧D):
- Hotkey shows input dialog to enter text
- Types text character-by-character into the previously focused app
- Configurable speed (5-60 cps, default 15)
- Settings tab for pre-configuring text and speed
- Remembers last used text

Focus restore:
- All modes (Zoom, Live Zoom, Draw, DemoType) now restore focus
  to the previously active app on dismiss

Menu bar:
- Added Live Zoom and DemoType entries with hotkey shortcuts
- testDefaultDemoTypeHotkey (⌃⇧D)
- testDefaultDemoTypeSettings (empty text, 15 cps)
- testDemoTypeHotkeyRoundTrip
- testDemoTypeTextAndSpeedRoundTrip
- Add Accessibility permission check before CGEvent posting
- Assign demoTypeController before start() to avoid race condition
- Restore previous app on Cancel/empty input paths
- Clamp speed to safe range (1-200) to prevent division by zero
- Use Array(text) for O(1) character indexing instead of O(n) String indexing
- Use activate(options:) for reliable app activation
- Remove xcuserdata from tracking, add to .gitignore
@yusufk

yusufk commented May 31, 2026

Copy link
Copy Markdown
Contributor Author

Superseded by #37 — complete rewrite based on actual ZoomIt DemoType behavior (verified against microsoft/PowerToys source code). Addresses all review feedback about branch contamination and behavior verification.

@yusufk yusufk closed this May 31, 2026
@yusufk yusufk deleted the feature/demo-type branch June 1, 2026 14:13
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.

3 participants