Skip to content

Commit a87616c

Browse files
committed
Update package
1 parent bb1bdc2 commit a87616c

File tree

2 files changed

+58
-17
lines changed

2 files changed

+58
-17
lines changed

Sources/Intermodular/Helpers/AppKit/NSHostingStatusBarPopover.swift

Lines changed: 31 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -17,21 +17,35 @@ class NSHostingStatusBarPopover<ID: Equatable, Content: View>: NSHostingPopover<
1717
}
1818
}
1919

20-
public var statusItem: StatusItem<ID, Content> {
20+
var statusItem: StatusItem<ID, Content> {
2121
didSet {
2222
updateStatusBarItem(oldValue: oldValue)
2323
}
2424
}
2525

26-
public init(item: StatusItem<ID, Content>) {
26+
var isActive: Binding<Bool>? {
27+
didSet {
28+
if let isActive = isActive {
29+
if isActive.wrappedValue, !self.isShown {
30+
present(nil)
31+
}
32+
}
33+
}
34+
}
35+
36+
init(item: StatusItem<ID, Content>) {
2737
self.statusItem = item
2838

2939
super.init(rootView: item.content)
3040

41+
behavior = NSPopover.Behavior.transient
42+
3143
updateStatusBarItem(oldValue: item)
44+
45+
_ = Unmanaged.passUnretained(self).retain() // fixes a crash
3246
}
3347

34-
public required init?(coder: NSCoder) {
48+
required init?(coder: NSCoder) {
3549
fatalError("init(coder:) has not been implemented")
3650
}
3751

@@ -55,9 +69,13 @@ class NSHostingStatusBarPopover<ID: Equatable, Content: View>: NSHostingPopover<
5569
}
5670

5771
statusItem.update(_statusItemBase!)
72+
73+
if let isActive = isActive, isActive.wrappedValue, !isShown {
74+
present(nil)
75+
}
5876
}
5977

60-
public func present(_ sender: AnyObject?) {
78+
func present(_ sender: AnyObject?) {
6179
guard let statusBarButton = _statusItemBase?.button else {
6280
return
6381
}
@@ -67,19 +85,25 @@ class NSHostingStatusBarPopover<ID: Equatable, Content: View>: NSHostingPopover<
6785
of: statusBarButton,
6886
preferredEdge: NSRectEdge.maxY
6987
)
88+
89+
isActive?.wrappedValue = true
90+
}
91+
92+
func hide(_ sender: AnyObject?) {
93+
performClose(sender)
94+
95+
isActive?.wrappedValue = false
7096
}
7197

7298
@objc func togglePopover(sender: AnyObject?) {
7399
if isShown {
74-
performClose(sender)
100+
hide(sender)
75101
} else {
76102
present(sender)
77103
}
78104
}
79105

80106
deinit {
81-
_ = Unmanaged.passUnretained(self).retain() // fixes a crash
82-
83107
if let item = _statusItemBase {
84108
item.statusBar?.removeStatusItem(item)
85109
}

Sources/Intramodular/Status Bar/StatusItem.swift

Lines changed: 27 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -45,18 +45,32 @@ extension View {
4545
public func statusItem<ID: Hashable, Content: View>(
4646
id: ID,
4747
image: ImageName,
48+
isActive: Binding<Bool>? = nil,
4849
@ViewBuilder content: () -> Content
4950
) -> some View {
50-
modifier(InsertStatusBarPopover(item: StatusItem(id: id, image: image, content: content)))
51+
modifier(
52+
InsertStatusBarPopover(
53+
item: StatusItem(id: id, image: image, content: content),
54+
isActive: isActive
55+
)
56+
)
57+
.background(EmptyView().id(isActive?.wrappedValue))
5158
}
5259

5360
/// Adds a status bar item configured to present a popover when clicked.
5461
public func statusItem<ID: Hashable, Content: View>(
5562
id: ID,
5663
systemImage image: String,
64+
isActive: Binding<Bool>? = nil,
5765
@ViewBuilder content: () -> Content
5866
) -> some View {
59-
modifier(InsertStatusBarPopover(item: StatusItem(id: id, image: .system(image), content: content)))
67+
modifier(
68+
InsertStatusBarPopover(
69+
item: StatusItem(id: id, image: .system(image), content: content),
70+
isActive: isActive
71+
)
72+
)
73+
.background(EmptyView().id(isActive?.wrappedValue))
6074
}
6175
}
6276

@@ -81,20 +95,23 @@ extension StatusItem {
8195

8296
struct InsertStatusBarPopover<ID: Equatable, PopoverContent: View>: ViewModifier {
8397
let item: StatusItem<ID, PopoverContent>
98+
let isActive: Binding<Bool>?
8499

85-
@State var popover: NSHostingStatusBarPopover<ID, PopoverContent>? = nil
100+
@State private var popover: NSHostingStatusBarPopover<ID, PopoverContent>? = nil
86101

87102
@ViewBuilder
88103
func body(content: Content) -> some View {
89-
PerformAction {
90-
if let popover = self.popover {
91-
popover.statusItem = self.item
92-
} else {
93-
self.popover = NSHostingStatusBarPopover(item: self.item)
104+
content.background {
105+
PerformAction {
106+
if let popover = self.popover {
107+
popover.statusItem = self.item
108+
} else {
109+
self.popover = NSHostingStatusBarPopover(item: self.item)
110+
}
111+
112+
popover?.isActive = isActive
94113
}
95114
}
96-
97-
content
98115
}
99116
}
100117

0 commit comments

Comments
 (0)