From ce1254eb8a22b4fdbe4153f5c97474d4670da045 Mon Sep 17 00:00:00 2001 From: KrLite Date: Fri, 20 Dec 2024 19:23:21 +0800 Subject: [PATCH] =?UTF-8?q?=F0=9F=90=9B=20Trying=20to=20improve=20window?= =?UTF-8?q?=20sizing?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../Luminare/Main Window/LuminareView.swift | 38 ++++++------------- .../Luminare/Main Window/LuminareWindow.swift | 19 +--------- .../Utilities/EnvironmentValues.swift | 5 --- .../Extensions/View+Extensions.swift | 25 ++---------- .../Utilities/LuminareManagerProtocol.swift | 17 ++------- 5 files changed, 20 insertions(+), 84 deletions(-) diff --git a/Sources/Luminare/Main Window/LuminareView.swift b/Sources/Luminare/Main Window/LuminareView.swift index 3a124f7..9f62775 100644 --- a/Sources/Luminare/Main Window/LuminareView.swift +++ b/Sources/Luminare/Main Window/LuminareView.swift @@ -17,52 +17,38 @@ public struct LuminareView: View where Content: View { @Environment(\.luminareTint) private var tint @Environment(\.luminareWindow) private var window - @Environment(\.luminareWindowMinWidth) private var minWidth - @Environment(\.luminareWindowMaxWidth) private var maxWidth - @Environment(\.luminareWindowMinHeight) private var minHeight - @Environment(\.luminareWindowMaxHeight) private var maxHeight // MARK: Fields @ViewBuilder public let content: () -> Content @State private var currentAnimation: LuminareWindowAnimation? + @State private var contentSize: CGSize = .zero // MARK: Body public var body: some View { content() - .background { - GeometryReader { proxy in - Color.clear - .onAppear { - setSize(size: proxy.size, animate: false) - } - .onChange(of: proxy.size) { - setSize(size: $0, animate: true) - } - } - } - .frame( - minWidth: minWidth, maxWidth: maxWidth, - minHeight: minHeight, maxHeight: maxHeight, - alignment: .leading - ) .focusable(false) .buttonStyle(.luminare) .overrideTint(tint) + // Handle content size change + .onGeometryChange(for: CGSize.self) { proxy in + proxy.size + } action: { newValue in + contentSize = newValue + } + .onAppear { setSize(size: contentSize, animate: false) } + .onChange(of: contentSize) { setSize(size: $0, animate: true) } } // MARK: Functions func setSize(size: CGSize, animate: Bool) { - guard let window else { - return - } + guard let window else { return } + guard size.width > 0, size.height > 0 else { return } - if let animation = currentAnimation { - animation.stop() - } + currentAnimation?.stop() var frame = NSRect( origin: window.frame.origin, diff --git a/Sources/Luminare/Main Window/LuminareWindow.swift b/Sources/Luminare/Main Window/LuminareWindow.swift index 41154b8..22d2b9d 100644 --- a/Sources/Luminare/Main Window/LuminareWindow.swift +++ b/Sources/Luminare/Main Window/LuminareWindow.swift @@ -18,8 +18,6 @@ public class LuminareWindow: NSWindow { /// - content: the content view of the window, wrapped in a ``LuminareView``. public init( blurRadius: CGFloat? = nil, - minFrame: CGSize = .init(width: 100, height: 100), - maxFrame: CGSize = .init(width: CGFloat.infinity, height: CGFloat.infinity), content: @escaping () -> some View ) { self.initializationTime = .now @@ -28,13 +26,12 @@ public class LuminareWindow: NSWindow { contentRect: .zero, styleMask: [.titled, .fullSizeContentView, .closable, .resizable], backing: .buffered, - defer: false // if true, background blur will break + defer: false // If true, background blur will break ) let view = NSHostingView( rootView: LuminareView(content: content) .environment(\.luminareWindow, self) - .luminareWindowFrame(min: minFrame, max: maxFrame) ) contentView = view @@ -52,20 +49,6 @@ public class LuminareWindow: NSWindow { alphaValue = 0 } - public convenience init( - blurRadius: CGFloat? = nil, - minWidth: CGFloat = 100, minHeight: CGFloat = 100, - maxWidth: CGFloat = .infinity, maxHeight: CGFloat = .infinity, - content: @escaping () -> some View - ) { - self.init( - blurRadius: blurRadius, - minFrame: .init(width: minWidth, height: minHeight), - maxFrame: .init(width: maxWidth, height: maxHeight), - content: content - ) - } - /// Shows this window. /// This action activates the current application and orders the window to the frontmost. public func show() { diff --git a/Sources/Luminare/Utilities/EnvironmentValues.swift b/Sources/Luminare/Utilities/EnvironmentValues.swift index bf14a43..4240ea3 100644 --- a/Sources/Luminare/Utilities/EnvironmentValues.swift +++ b/Sources/Luminare/Utilities/EnvironmentValues.swift @@ -29,11 +29,6 @@ public extension EnvironmentValues { @Entry var luminareWindow: NSWindow? @Entry var luminareSidebarOverflow: CGFloat = 50 @Entry var luminareClickedOutside: Bool = false - - @Entry var luminareWindowMinWidth: CGFloat = 100 - @Entry var luminareWindowMaxWidth: CGFloat = .infinity - @Entry var luminareWindowMinHeight: CGFloat = 100 - @Entry var luminareWindowMaxHeight: CGFloat = .infinity } // MARK: - Modals diff --git a/Sources/Luminare/Utilities/Extensions/View+Extensions.swift b/Sources/Luminare/Utilities/Extensions/View+Extensions.swift index 2572d49..e64b969 100644 --- a/Sources/Luminare/Utilities/Extensions/View+Extensions.swift +++ b/Sources/Luminare/Utilities/Extensions/View+Extensions.swift @@ -12,7 +12,10 @@ extension View { transform(self) } - @ViewBuilder func assigning(_ keyPath: WritableKeyPath, _ value: V?) -> some View { + @ViewBuilder func assigning( + _ keyPath: WritableKeyPath, + _ value: V? + ) -> some View { if let value { environment(keyPath, value) } else { @@ -134,26 +137,6 @@ public extension View { environment(\.luminareAnimationFast, animation) } - @ViewBuilder func luminareWindowFrame( - min: CGSize? = nil, - max: CGSize? = nil - ) -> some View { - assigning(\.luminareWindowMinWidth, min?.width) - .assigning(\.luminareWindowMaxWidth, max?.width) - .assigning(\.luminareWindowMinHeight, min?.height) - .assigning(\.luminareWindowMaxHeight, max?.height) - } - - @ViewBuilder func luminareWindowFrame( - minWidth: CGFloat? = nil, maxWidth: CGFloat? = nil, - minHeight: CGFloat? = nil, maxHeight: CGFloat? = nil - ) -> some View { - assigning(\.luminareWindowMinWidth, minWidth) - .assigning(\.luminareWindowMaxWidth, maxWidth) - .assigning(\.luminareWindowMinHeight, minHeight) - .assigning(\.luminareWindowMaxHeight, maxHeight) - } - @ViewBuilder func luminareSizebarOverflow(_ overflow: CGFloat) -> some View { environment(\.luminareSidebarOverflow, overflow) } diff --git a/Sources/Luminare/Utilities/LuminareManagerProtocol.swift b/Sources/Luminare/Utilities/LuminareManagerProtocol.swift index 4319e9d..f36c033 100644 --- a/Sources/Luminare/Utilities/LuminareManagerProtocol.swift +++ b/Sources/Luminare/Utilities/LuminareManagerProtocol.swift @@ -12,8 +12,6 @@ public protocol LuminareManagerProtocol: View { var isVisible: Bool { get } var blurRadius: CGFloat? { get } - var minFrame: CGSize { get } - var maxFrame: CGSize { get } mutating func show() mutating func close() @@ -32,25 +30,16 @@ public extension LuminareManagerProtocol { var blurRadius: CGFloat? { nil } - - var minFrame: CGSize { - .init(width: 100, height: 100) - } - - var maxFrame: CGSize { - .init(width: CGFloat.infinity, height: CGFloat.infinity) - } } public extension LuminareManagerProtocol { mutating func show() { if luminare == nil { - let body = body + let body = self luminare = LuminareWindow( blurRadius: blurRadius, - minFrame: minFrame, - maxFrame: maxFrame - ) { body } + content: { body } + ) luminare?.center() }