Skip to content

Make Find/Replace topmost only while main window has focus#11243

Merged
niksedk merged 2 commits into
mainfrom
find-replace-topmost-follows-owner
May 29, 2026
Merged

Make Find/Replace topmost only while main window has focus#11243
niksedk merged 2 commits into
mainfrom
find-replace-topmost-follows-owner

Conversation

@niksedk
Copy link
Copy Markdown
Member

@niksedk niksedk commented May 29, 2026

Summary

  • Find/Replace dialogs now toggle Topmost dynamically based on owner/child window activation instead of being unconditionally topmost.
  • Avoids the dialogs floating above other applications on macOS (where Avalonia maps Topmost to NSWindowLevel.Floating process-wide), without needing an OperatingSystem.IsMacOS() branch.
  • Alternative to Fix Find and Replace dialogs floating above other apps on macOS #11234.

Implementation

  • New WindowService.KeepTopmostWhileOwnerActive(child, owner) helper subscribes to Activated/Deactivated on both windows and recomputes child.Topmost = owner.IsActive || child.IsActive. Handlers are removed on child.Closed.
  • ShowFind and ShowReplace in MainViewModel call the helper instead of setting window.Topmost = true.
  • ShowWrapAroundDialog no longer needs to manually flip Topmost around MessageBox.Show — the message box stealing focus already triggers the helper to drop the dialog out of topmost.

Test plan

  • macOS: open Find, switch to another app — Find no longer floats above it.
  • macOS: switch back to Subtitle Edit — Find pops back above the main window.
  • macOS: click the Find window, switch to another app — Find drops behind.
  • macOS: trigger wrap-around search so the MessageBox appears over the Find dialog — message box appears in front, Find dialog returns to topmost after closing.
  • Windows: existing behavior unchanged (Find on top while main active, drops when main loses focus).
  • Linux: existing behavior unchanged.
  • Same checks for Replace.

🤖 Generated with Claude Code

Avoids the Find/Replace dialogs floating above other applications on
macOS, where Avalonia maps Topmost to NSWindowLevel.Floating
process-wide. Topmost is now toggled dynamically based on owner/child
activation, giving the same behavior on Windows, Linux, and macOS
without an OS-specific branch.

Alternative to #11234.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Copy link
Copy Markdown
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Updates Find/Replace tool-window behavior so they are only Topmost while Subtitle Edit (or the tool window itself) is active, preventing the dialogs from floating above other applications on macOS due to Avalonia’s Topmost mapping.

Changes:

  • Added WindowService.KeepTopmostWhileOwnerActive(child, owner) to dynamically recompute Topmost based on window activation state.
  • Updated MainViewModel.ShowFind / ShowReplace to use the new helper instead of unconditional Topmost = true.
  • Simplified wrap-around MessageBox handling by removing manual Topmost toggling around MessageBox.Show.

Reviewed changes

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

File Description
src/ui/Logic/WindowsService.cs Adds helper to keep owned tool windows topmost only while owner/child is active.
src/ui/Features/Main/MainViewModel.cs Switches Find/Replace to the helper and removes manual topmost flipping around wrap-around MessageBox.

Comment thread src/ui/Logic/WindowsService.cs
IsLoaded reflects the logical tree and can still be true briefly after
the native window is torn down, so a queued Dispatcher callback could
touch Topmost on a disposed window. IsClosing() (IsVisible +
PlatformImpl null check) is the pattern used elsewhere in the UI layer.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
@niksedk niksedk merged commit a4f38b8 into main May 29, 2026
1 of 3 checks passed
@niksedk niksedk deleted the find-replace-topmost-follows-owner branch May 29, 2026 03:07
@GrampaWildWilly
Copy link
Copy Markdown

This business of windows hovering over others sounds a lot like it's related to a comment I added to #11229. I don't know if you noticed it. It seems to me like what you're dealing with here, with certain windows allowed to & not allowed to hover over certain other windows is very closely related to the issue I raised in the other pull request. I'm speculating that the work you're doing here is applicable there as well.

mjuhasz pushed a commit to mjuhasz/subtitleedit that referenced this pull request May 29, 2026
Apply WindowService.KeepTopmostWhileOwnerActive — introduced for
Find/Replace in SubtitleEdit#11243 — to the undocked video player and audio
visualizer windows. They now stay visually above SE main while either
SE window is the active app, and drop behind when SE loses focus to
another application.

This addresses GrampaWildWilly's follow-up on SubtitleEdit#11229
("the audio visualizer doesn't stay visible, floating on top of the
main window") without touching Alt+Tab behavior — KeepTopmost… is just
a Z-order knob; the two undocked windows remain independent
top-levels in the Alt+Tab list, which was the point of SubtitleEdit#11229.

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.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.

3 participants