Skip to content

refactor(gui): split keyboard-shortcut system into MainWindow_Shortcuts.cpp (#3351 Phase 1c)#3524

Merged
jensenpat merged 2 commits into
mainfrom
refactor/3351-phase1c-shortcuts
Jun 11, 2026
Merged

refactor(gui): split keyboard-shortcut system into MainWindow_Shortcuts.cpp (#3351 Phase 1c)#3524
jensenpat merged 2 commits into
mainfrom
refactor/3351-phase1c-shortcuts

Conversation

@ten9876

@ten9876 ten9876 commented Jun 11, 2026

Copy link
Copy Markdown
Collaborator

Summary

Fourth PR of the #3351 series. Pure code motion — no behavior change, no MainWindow.h changes.

Moves the complete keyboard-shortcut system into the new MainWindow_Shortcuts.cpp (1,087 lines):

Piece Lines
Shortcut-state definitions + accessors (s_keyboardShortcutsEnabled, shortcutGuard, …) ~40
registerShortcutActions() — the full action table 559
Slider shortcut lease (#745): begin/renew/release + eventFilter() ~365
handleCwMomentaryShortcut() + trivial keyPress/keyRelease overrides ~65

This completes the handoff MainWindowShortcutState.h promised in Phase 1b — declarations there, definitions now owned by the Shortcuts TU.

Not-pure-motion exceptions (the review surface)

  1. kSliderShortcutLeaseMs moved with its only user.
  2. panCountForLayoutId promoted from MainWindow.cpp's anon namespace to MainWindowHelpers.{h,cpp}registerShortcutActions (moved) plus two MainWindow.cpp call sites now share it cross-TU. Pure map lookup, fits the helpers file's no-state rule.
  3. isCwMomentaryActionId deliberately NOT moved — its remaining caller is the MIDI dispatch path still in MainWindow.cpp.

Everything else verbatim. Breadcrumbs at all six excision sites.

Numbers

  • MainWindow.cpp: 16,261 → 15,239 (−1,022)
  • Series running total: 19,474 → 15,239 (−21.7%)

Verification

  • Full build clean (Linux x86, RelWithDebInfo)
  • All 33 ctest suites pass (incl. the new radio_discovery_test from main)
  • a11y lint: 0 findings

QA checklist for the bench

The shortcut system touches every keyboard interaction:

  • Global shortcuts fire when enabled (try a handful from Help → Shortcuts: band up/down, mode, MOX)
  • View-menu shortcut toggle still gates them (off = dead, on = live)
  • Typing in a text field (memory name, frequency entry) does NOT trigger shortcuts
  • Click a slider → arrow keys nudge the slider (lease), then ~2 s after release, arrows return to global shortcuts
  • Same lease behavior on a TCI/DAX MeterSlider fader
  • CW momentary keys (straight key / paddles) press-and-hold from keyboard if you have them bound
  • App quit via window close while connected — clean shutdown (eventFilter intercepts Quit)

Refs #3351

…ts.cpp (#3351 Phase 1c)

Fourth PR of the #3351 monolith-decomposition series. Pure code motion —
no behavior change, no MainWindow.h changes.

Moves the complete keyboard-shortcut system out of MainWindow.cpp into
the new MainWindow_Shortcuts.cpp (1,087 lines):

- The shortcut-state definitions (s_keyboardShortcutsEnabled,
  s_sliderShortcutLeaseActive) and accessors (textInputCaptured,
  shortcutInputCaptured, shortcutGuard, leaseHolderBusy) — declared in
  MainWindowShortcutState.h since Phase 1b, owned here as of this phase,
  completing the handoff that header promised.
- registerShortcutActions() (559 lines — the full action table).
- The slider shortcut lease (#745): beginSliderShortcutLease,
  renewSliderShortcutLease, releaseSliderShortcutLease, plus
  MainWindow::eventFilter() (319 lines) which drives the lease and the
  app-quit interception.
- handleCwMomentaryShortcut() and the trivial keyPress/keyRelease
  overrides.

Supporting moves, called out for review:

- kSliderShortcutLeaseMs moved with its only user.
- panCountForLayoutId promoted from MainWindow.cpp's anonymous namespace
  to MainWindowHelpers.{h,cpp} — registerShortcutActions (moved) and two
  MainWindow.cpp call sites now share it across TUs. Pure map lookup;
  fits the helpers file's no-state rule.
- isCwMomentaryActionId NOT moved — its remaining caller is the MIDI
  dispatch path still in MainWindow.cpp; it stays file-static there.

Breadcrumb comments at all six excision sites.

MainWindow.cpp: 16,261 → 15,239 lines (series: 19,474 → 15,239, −21.7%).
Verified: full build clean, all 33 ctest suites pass (incl. the new
radio_discovery_test from main), a11y lint clean.

Refs #3351. Principle XI.
@ten9876 ten9876 requested review from a team as code owners June 11, 2026 03:45

@aethersdr-agent aethersdr-agent Bot left a comment

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.

Reviewed with a mechanical pure-motion check: I diffed every line removed from MainWindow.cpp against the new MainWindow_Shortcuts.cpp (whitespace-normalized). Every removed line is accounted for verbatim — the only lines not landing in the Shortcuts TU are the panCountForLayoutId body, which appears identically in MainWindowHelpers.cpp. Conversely, the only content in the new file that wasn't moved is the header comment, includes, and namespace scaffolding. The "pure code motion" claim holds.

Cross-TU wiring also checks out:

  • The shortcut state (s_keyboardShortcutsEnabled, s_sliderShortcutLeaseActive) and its accessors now have exactly one definition site (the Shortcuts TU), matching the extern declarations in MainWindowShortcutState.h from Phase 1b. The only outside user is MainWindow_Menus.cpp (View-menu toggle + shortcutGuard), which is the design that header documents.
  • isCwMomentaryActionId correctly stays behind — its remaining caller is the MIDI dispatch path at MainWindow.cpp:3749.
  • panCountForLayoutId in the helpers file is a stateless map lookup, consistent with that file's no-state rule, and both remaining MainWindow.cpp call sites plus the moved eventFilter use the shared helper.
  • All six moved definitions (eventFilter, registerShortcutActions, the three lease functions, handleCwMomentaryShortcut, key event overrides) exist exactly once across the GUI sources. CMake entry added; no MainWindow.h changes, as advertised.

Two minor notes, neither blocking:

  1. Missing <algorithm>/<iterator> includes. The new TU uses std::clamp, std::min/std::max, and std::size (in registerShortcutActions) but includes neither header — it currently compiles everywhere (all CI green, including MSVC) via transitive includes only. Both MainWindow.cpp and the Phase 1b sibling MainWindow_Menus.cpp include <algorithm> explicitly; suggest adding <algorithm> and <iterator> here to match and to avoid a fragile dependency on Qt header internals across upgrades.
  2. Optional: MainWindow.cpp still includes MainWindowShortcutState.h but no longer references any of its symbols after this move — the include can be dropped (fine to leave if a later phase will need it again).

Nice work — the breadcrumbs at the excision sites, the verbatim motion, and the explicit not-pure-motion list made this straightforward to verify. The QA checklist for the bench is appreciated; the lease and CW momentary paths are exactly the ones worth a hands-on pass.


🤖 aethersdr-agent · cost: $17.2202 · model: claude-fable-5

… include

Both items from the aethersdr-agent review on this PR:

1. MainWindow_Shortcuts.cpp gains explicit <algorithm> and <iterator>.
   registerShortcutActions uses std::clamp/std::min/std::max/std::size,
   which previously compiled via transitive Qt includes only — fragile
   across Qt upgrades and inconsistent with MainWindow.cpp and
   MainWindow_Menus.cpp, which both include <algorithm> explicitly.

2. MainWindow.cpp drops its now-dead MainWindowShortcutState.h include.
   After the Phase 1c move its only remaining "references" to the
   shortcut state were the breadcrumb comments. If a later phase needs
   the state again, that phase re-adds the include with its user.

Principle XI.
@ten9876

ten9876 commented Jun 11, 2026

Copy link
Copy Markdown
Collaborator Author

Both nits addressed in `2670835b`:

  1. `` + `` added to MainWindow_Shortcuts.cpp. Verified the usages you flagged (`std::size` at the step tables, `std::clamp` on RF gain, `std::min`/`max` on audio gain) — all were riding transitive Qt includes. Now explicit, matching MainWindow.cpp and MainWindow_Menus.cpp.

  2. Dead `MainWindowShortcutState.h` include dropped from MainWindow.cpp. Confirmed its only remaining "references" were the two breadcrumb comments. Took the drop-it-now option — if a later phase needs the state again, that phase re-adds the include alongside its actual user (IWYU over speculative retention).

Thanks for the mechanical pure-motion verification — diffing removed-vs-added lines whitespace-normalized is exactly the right review for this series, and it's the check I want every phase to pass.

All 33 ctest suites still green after the fixes.

@jensenpat jensenpat left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Reviewed: verified pure code motion — every line removed from MainWindow.cpp reappears verbatim in MainWindow_Shortcuts.cpp/MainWindowHelpers; only new lines are includes, breadcrumbs, and the panCountForLayoutId declaration. All CI green.

@jensenpat jensenpat merged commit 7efaa80 into main Jun 11, 2026
6 checks passed
@jensenpat jensenpat deleted the refactor/3351-phase1c-shortcuts branch June 11, 2026 13:17
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