Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
61d2689cbc |
@@ -134,6 +134,12 @@ preferred position controls where the hidden/kept boundary lands:
|
|||||||
- Verified with `--diag-hide` across positions 100–400. Below ~200 Wi-Fi gets
|
- Verified with `--diag-hide` across positions 100–400. Below ~200 Wi-Fi gets
|
||||||
hidden too; above ~300 app icons (Now Playing, TextInput) leak back.
|
hidden too; above ~300 app icons (Now Playing, TextInput) leak back.
|
||||||
- `debug.spacerPos` (Double) overrides the seed for tuning without rebuilding.
|
- `debug.spacerPos` (Double) overrides the seed for tuning without rebuilding.
|
||||||
|
- Pressing a tray tile calls `MenuBarItemManager.press` (`kAXPressAction`, then
|
||||||
|
`kAXShowMenuAction`). Because a hidden item sits off-screen, its menu would
|
||||||
|
open off-screen; `AppDelegate` therefore calls `MenuBarHider.suspend()`
|
||||||
|
(`popoverWillShow`) to reveal items while the panel is open and `resume()`
|
||||||
|
0.6s after `popoverDidClose`. `suspend`/`resume` do not change the user's
|
||||||
|
`enabled` preference.
|
||||||
- **Order matters**: `AppDelegate` must call `setupStatusItem()` *before*
|
- **Order matters**: `AppDelegate` must call `setupStatusItem()` *before*
|
||||||
`MenuBarHider.shared.prepare()`. If the hider contracts the bar first, the
|
`MenuBarHider.shared.prepare()`. If the hider contracts the bar first, the
|
||||||
hamburger is created into the collapsed space and lands off-screen.
|
hamburger is created into the collapsed space and lands off-screen.
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ struct SimpleTopBarApp: App {
|
|||||||
/// full menu bar, a brand new item lands under the notch and is invisible;
|
/// full menu bar, a brand new item lands under the notch and is invisible;
|
||||||
/// writing `NSStatusItem Preferred Position <name>` into defaults puts it in a
|
/// writing `NSStatusItem Preferred Position <name>` into defaults puts it in a
|
||||||
/// visible slot, and the autosave name lets the user's own drag persist.
|
/// visible slot, and the autosave name lets the user's own drag persist.
|
||||||
final class AppDelegate: NSObject, NSApplicationDelegate {
|
final class AppDelegate: NSObject, NSApplicationDelegate, NSPopoverDelegate {
|
||||||
private var statusItem: NSStatusItem?
|
private var statusItem: NSStatusItem?
|
||||||
private var popover: NSPopover?
|
private var popover: NSPopover?
|
||||||
|
|
||||||
@@ -103,6 +103,7 @@ final class AppDelegate: NSObject, NSApplicationDelegate {
|
|||||||
let popover = NSPopover()
|
let popover = NSPopover()
|
||||||
popover.behavior = .transient
|
popover.behavior = .transient
|
||||||
popover.animates = false
|
popover.animates = false
|
||||||
|
popover.delegate = self
|
||||||
popover.contentViewController = NSHostingController(
|
popover.contentViewController = NSHostingController(
|
||||||
rootView: TopBarView(
|
rootView: TopBarView(
|
||||||
model: AppListModel.shared,
|
model: AppListModel.shared,
|
||||||
@@ -113,6 +114,20 @@ final class AppDelegate: NSObject, NSApplicationDelegate {
|
|||||||
self.popover = popover
|
self.popover = popover
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Reveal the hidden menu bar items while the panel is open so pressing a
|
||||||
|
// tray icon opens that app's menu at its real, on-screen position.
|
||||||
|
func popoverWillShow(_ notification: Notification) {
|
||||||
|
MenuBarHider.shared.suspend()
|
||||||
|
}
|
||||||
|
|
||||||
|
func popoverDidClose(_ notification: Notification) {
|
||||||
|
// Small delay so a menu just opened from a tray tile is fully on screen
|
||||||
|
// before the bar contracts again.
|
||||||
|
DispatchQueue.main.asyncAfter(deadline: .now() + 0.6) {
|
||||||
|
MenuBarHider.shared.resume()
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@objc private func togglePopover() {
|
@objc private func togglePopover() {
|
||||||
guard let popover, let button = statusItem?.button else { return }
|
guard let popover, let button = statusItem?.button else { return }
|
||||||
if popover.isShown {
|
if popover.isShown {
|
||||||
|
|||||||
@@ -252,6 +252,22 @@ final class MenuBarHider: ObservableObject {
|
|||||||
isHiding = hiding
|
isHiding = hiding
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// Temporarily reveal the items (e.g. while the panel is open) so pressing
|
||||||
|
/// a tray icon opens its menu at its real, on-screen position. Keeps the
|
||||||
|
/// user's `enabled` preference untouched.
|
||||||
|
func suspend() {
|
||||||
|
guard enabled else { return }
|
||||||
|
spacer?.length = 0
|
||||||
|
isHiding = false
|
||||||
|
}
|
||||||
|
|
||||||
|
/// Restore hiding after a `suspend()`.
|
||||||
|
func resume() {
|
||||||
|
guard enabled else { return }
|
||||||
|
spacer?.length = Self.hiddenLength
|
||||||
|
isHiding = true
|
||||||
|
}
|
||||||
|
|
||||||
/// Put the menu bar back the way we found it. Called on quit. Leaves the
|
/// Put the menu bar back the way we found it. Called on quit. Leaves the
|
||||||
/// user's preference intact.
|
/// user's preference intact.
|
||||||
func restore() {
|
func restore() {
|
||||||
|
|||||||
Reference in New Issue
Block a user