From 261151a9f7d6a03a708c5d3f331e53898fe7adc9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Le=CC=81o=20Natan?= Date: Thu, 17 Oct 2024 12:57:29 +0300 Subject: [PATCH] Demo project updates --- LNPopupSettings | 2 +- .../DemoScenes/NavDemoView.swift | 5 +- .../DemoScenes/PopupDemoView.swift | 93 +++++++++++++------ .../DemoScenes/TabDemoView.swift | 28 +++--- .../DemoScenes/TabNavView.swift | 61 ++++++++---- LNPopupUIExample/LNPopupUIExample/Info.plist | 2 +- .../LNPopupUIExample/SceneSelection.swift | 14 +++ Package.swift | 2 +- 8 files changed, 141 insertions(+), 66 deletions(-) diff --git a/LNPopupSettings b/LNPopupSettings index bb11839..9f2a5fb 160000 --- a/LNPopupSettings +++ b/LNPopupSettings @@ -1 +1 @@ -Subproject commit bb118398edeb3fe4fc577e035e95a3230d5e71c5 +Subproject commit 9f2a5fb8056646765feecd55322f3196e1d8da4a diff --git a/LNPopupUIExample/LNPopupUIExample/DemoScenes/NavDemoView.swift b/LNPopupUIExample/LNPopupUIExample/DemoScenes/NavDemoView.swift index 1ef530c..52e0170 100644 --- a/LNPopupUIExample/LNPopupUIExample/DemoScenes/NavDemoView.swift +++ b/LNPopupUIExample/LNPopupUIExample/DemoScenes/NavDemoView.swift @@ -36,7 +36,10 @@ struct NavDemoView : View { var body: some View { MaterialNavigationStack { - SafeAreaDemoView(colorSeed:"nil", includeToolbar: true, includeLink: true, presentBarHandler: presentBarHandler, appearanceHandler: appearanceHandler, hideBarHandler: hideBarHandler, showDismissButton: false, onDismiss: onDismiss) + let bottomButtonsHandlers = SafeAreaDemoView.BottomButtonHandlers(presentBarHandler: presentBarHandler, appearanceHandler: appearanceHandler, hideBarHandler: hideBarHandler) + let bottomBarHideSupport = SafeAreaDemoView.BottomBarHideSupport(showsBottomBarHideButton: true) + + SafeAreaDemoView(colorSeed:"nil", includeToolbar: true, includeLink: true, bottomButtonsHandlers: bottomButtonsHandlers, showDismissButton: false, onDismiss: onDismiss, bottomBarHideSupport: bottomBarHideSupport) .navigationBarTitle("Navigation View") .navigationBarTitleDisplayMode(.inline) .toolbar { diff --git a/LNPopupUIExample/LNPopupUIExample/DemoScenes/PopupDemoView.swift b/LNPopupUIExample/LNPopupUIExample/DemoScenes/PopupDemoView.swift index bcc19fc..e348a5e 100644 --- a/LNPopupUIExample/LNPopupUIExample/DemoScenes/PopupDemoView.swift +++ b/LNPopupUIExample/LNPopupUIExample/DemoScenes/PopupDemoView.swift @@ -90,18 +90,29 @@ struct BackgroundViewColorModifier: ViewModifier { } struct HideShowTabBarModifier: ViewModifier { - let includePadding: Bool - let hideShowTabBar: () -> Void + @Environment(\.horizontalSizeClass) var horizontalSizeClass + + @Binding var bottomBarHideSupport: SafeAreaDemoView.BottomBarHideSupport? @ViewBuilder func body(content: Content) -> some View { - content.toolbar { - ToolbarItem(placement: .navigationBarLeading) { - Button { - hideShowTabBar() - } label: { - Image(systemName: "rectangle.bottomthird.inset.fill") - }.padding(includePadding ? .horizontal : [], 8) + if #available(iOS 18.0, *), bottomBarHideSupport?.showsBottomBarHideButton ?? false { + content.toolbar { + ToolbarItem(placement: .navigationBarLeading) { + Button { + withAnimation { + bottomBarHideSupport?.isBottomBarPresented.toggle() + } + } label: { + if UIDevice.current.userInterfaceIdiom == .pad && horizontalSizeClass == .regular && bottomBarHideSupport?.isBottomBarTab ?? false { + Image(systemName: "rectangle.topthird.inset.filled") + } else { + Image(systemName: "rectangle.bottomthird.inset.filled") + } + } + } } + } else { + content } } } @@ -116,6 +127,18 @@ struct TrailingImageLabelStyle: LabelStyle { } struct SafeAreaDemoView : View { + struct BottomButtonHandlers { + var presentBarHandler: (() -> Void)? = nil + var appearanceHandler: (() -> Void)? = nil + var hideBarHandler: (() -> Void)? = nil + } + + struct BottomBarHideSupport { + var showsBottomBarHideButton: Bool = false + var isBottomBarTab: Bool? = false + var isBottomBarPresented: Bool = true + } + let includeLink: Bool let includeToolbar: Bool let offset: Bool @@ -131,10 +154,9 @@ struct SafeAreaDemoView : View { let appearanceHandler: (() -> Void)? let hideBarHandler: (() -> Void)? - @State private var isBottomBarPresented: Bool - let bottomBarPresentationButtonPadding: Bool + @State var bottomBarHideSupport: BottomBarHideSupport? - init(colorSeed: String = "nil", colorIndex: Int = 0, includeToolbar: Bool = false, includeLink: Bool = false, offset: Bool = false, isPopupOpen: Binding? = nil, presentBarHandler: (() -> Void)? = nil, appearanceHandler: (() -> Void)? = nil, hideBarHandler: (() -> Void)? = nil, showDismissButton: Bool? = nil, onDismiss: (() -> Void)? = nil, isBottomBarPresented: State? = nil) { + init(colorSeed: String = "nil", colorIndex: Int = 0, includeToolbar: Bool = false, includeLink: Bool = false, offset: Bool = false, isPopupOpen: Binding? = nil, bottomButtonsHandlers: BottomButtonHandlers? = nil, showDismissButton: Bool? = nil, onDismiss: (() -> Void)? = nil, bottomBarHideSupport: BottomBarHideSupport? = nil) { self.includeLink = includeLink self.includeToolbar = includeToolbar self.offset = offset @@ -150,12 +172,11 @@ struct SafeAreaDemoView : View { self.colorSeed = colorSeed self.colorIndex = colorIndex - self.presentBarHandler = presentBarHandler - self.appearanceHandler = appearanceHandler - self.hideBarHandler = hideBarHandler + self.presentBarHandler = bottomButtonsHandlers?.presentBarHandler + self.appearanceHandler = bottomButtonsHandlers?.appearanceHandler + self.hideBarHandler = bottomButtonsHandlers?.hideBarHandler - _isBottomBarPresented = isBottomBarPresented ?? State(initialValue: true) - bottomBarPresentationButtonPadding = isBottomBarPresented != nil + _bottomBarHideSupport = State(initialValue: bottomBarHideSupport) } var body: some View { @@ -200,8 +221,11 @@ struct SafeAreaDemoView : View { Spacer() NavigationLink { - SafeAreaDemoView(colorSeed: colorSeed, colorIndex: colorIndex + 1, includeToolbar: includeToolbar, includeLink: includeLink, presentBarHandler: presentBarHandler, appearanceHandler: appearanceHandler, hideBarHandler: hideBarHandler, showDismissButton: true, onDismiss: onDismiss, isBottomBarPresented: _isBottomBarPresented) + let bottomButtonsHandlers = BottomButtonHandlers(presentBarHandler: presentBarHandler, appearanceHandler: appearanceHandler, hideBarHandler: hideBarHandler) + + SafeAreaDemoView(colorSeed: colorSeed, colorIndex: colorIndex + 1, includeToolbar: includeToolbar, includeLink: includeLink, bottomButtonsHandlers: bottomButtonsHandlers, showDismissButton: true, onDismiss: onDismiss) .navigationTitle("LNPopupUI") + .toolbarRoleIfPad18() } label: { Label { Text("Next") @@ -218,11 +242,9 @@ struct SafeAreaDemoView : View { .edgesIgnoringSafeArea([.top, .bottom]) .fontWeight(.semibold) .tint(Color(uiColor: .label)) - .modifier(HideShowTabBarModifier(includePadding: bottomBarPresentationButtonPadding) { - isBottomBarPresented.toggle() - }) - .toolbar(includeToolbar && isBottomBarPresented ? .visible : .hidden, for: .bottomBar) - .toolbar(isBottomBarPresented ? .visible : .hidden, for: .tabBar) + .modifier(HideShowTabBarModifier(bottomBarHideSupport: $bottomBarHideSupport)) + .toolbar(includeToolbar && bottomBarHideSupport?.isBottomBarPresented ?? true ? .visible : .hidden, for: .bottomBar) + .toolbar(bottomBarHideSupport?.isBottomBarPresented ?? true ? .visible : .hidden, for: .tabBar) } } } @@ -242,6 +264,14 @@ struct HapticFeedbackModifier: ViewModifier { } } +struct LimitFloatingContentWidthModifier: ViewModifier { + @AppStorage(.limitFloatingWidth, store: .settings) var limitFloatingWidth: Bool = true + + @ViewBuilder func body(content: Content) -> some View { + content.popupBarLimitFloatingContentWidth(limitFloatingWidth) + } +} + struct MarqueeModifier: ViewModifier { @AppStorage(.marqueeEnabled, store: .settings) var marqueeEnabled: Bool = false @AppStorage(.marqueeCoordinationEnabled, store: .settings) var marqueeCoordinationEnabled: Bool = true @@ -446,6 +476,7 @@ struct PopupDemoViewModifier: ViewModifier { .popupCloseButtonStyle(closeButtonStyle) .modifier(MarqueeModifier()) .modifier(HapticFeedbackModifier()) + .modifier(LimitFloatingContentWidthModifier()) .modifier(FloatingBackgroundEffectModifier(blurEffectStyle: blurEffectStyle, barStyle: barStyle)) .modifier(BackgroundEffectModifier(blurEffectStyle: blurEffectStyle, barStyle: barStyle)) .modifier(CustomBarModifier(customPopupBar: customPopupBar)) @@ -495,16 +526,22 @@ fileprivate extension View { } struct MaterialTabView: View { - let content: Content + let tabView: any View + init(@ViewBuilder content: () -> Content) { - self.content = content() + tabView = TabView { + content().fixBottomBarAppearance() + } + } + + @available(iOS 18.0, *) + init(@TabContentBuilder content: () -> C) where Content == TabContentBuilder.Content, C : TabContent { + tabView = TabView.init(content: content) } var body: some View { - TabView { - content.fixBottomBarAppearance() - } + AnyView(tabView) } } diff --git a/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabDemoView.swift b/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabDemoView.swift index 4e4ede8..4678803 100644 --- a/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabDemoView.swift +++ b/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabDemoView.swift @@ -29,7 +29,9 @@ struct InnerView : View { var body: some View { ZStack(alignment: .topTrailing) { - SafeAreaDemoView(colorSeed: tabIdx != nil ? (tabIdx! == -1 ? "tab_\(Int.random(in: 0..<1000))" : "tab_\(tabIdx!)") : "nil", presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler, showDismissButton: showDismissButton) + let bottomButtonsHandlers = SafeAreaDemoView.BottomButtonHandlers(presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) + + SafeAreaDemoView(colorSeed: tabIdx != nil ? (tabIdx! == -1 ? "tab_\(Int.random(in: 0..<1000))" : "tab_\(tabIdx!)") : "nil", bottomButtonsHandlers: bottomButtonsHandlers, showDismissButton: showDismissButton) if let showDismissButton, showDismissButton == true { VStack { Button("Gallery") { @@ -43,6 +45,8 @@ struct InnerView : View { } struct TabDemoView : View { + @Environment(\.horizontalSizeClass) var horizontalSizeClass + @State private var isBarPresented: Bool = true private let onDismiss: () -> Void let demoContent: DemoContent @@ -62,22 +66,12 @@ struct TabDemoView : View { var body: some View { MaterialTabView { - InnerView(tabIdx:0, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "1.square") - } - InnerView(tabIdx:1, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "2.square") - } - InnerView(tabIdx:2, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "3.square") - } - InnerView(tabIdx:3, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "4.square") - } + ForEach(1..<5) { idx in + InnerView(tabIdx:idx - 1, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) + .tabItem { + Label("Tab", systemImage: "1.square") + } + } } .popupDemo(demoContent: demoContent, isBarPresented: $isBarPresented, includeContextMenu: UserDefaults.settings.bool(forKey: .contextMenuEnabled)) } diff --git a/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabNavView.swift b/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabNavView.swift index f95fb3f..1f4dd14 100644 --- a/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabNavView.swift +++ b/LNPopupUIExample/LNPopupUIExample/DemoScenes/TabNavView.swift @@ -10,7 +10,27 @@ import SwiftUI import LoremIpsum import LNPopupUI +struct ToolbarRolePad18Modifier: ViewModifier { + @Environment(\.horizontalSizeClass) var horizontalSizeClass + + func body(content: Content) -> some View { + return content.toolbarRole(UIDevice.current.userInterfaceIdiom == .pad && horizontalSizeClass == .regular ? .editor : .navigationStack) + } +} + +extension View { + func toolbarRoleIfPad18() -> some View { + if #available(iOS 18.0, *) { + return self.modifier(ToolbarRolePad18Modifier()) + } else { + return self + } + } +} + struct InnerNavView : View { + + let tabIdx: Int let onDismiss: () -> Void @@ -19,14 +39,20 @@ struct InnerNavView : View { var body: some View { MaterialNavigationStack { - SafeAreaDemoView(colorSeed:"tab_\(tabIdx)", includeLink: true, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler, showDismissButton: true, onDismiss: onDismiss) + let bottomButtonsHandlers = SafeAreaDemoView.BottomButtonHandlers(presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) + let bottomBarHideSupport = SafeAreaDemoView.BottomBarHideSupport(showsBottomBarHideButton: true, isBottomBarTab: true) + + SafeAreaDemoView(colorSeed: "tab_\(tabIdx)", includeLink: true, bottomButtonsHandlers: bottomButtonsHandlers, showDismissButton: true, onDismiss: onDismiss, bottomBarHideSupport: bottomBarHideSupport) .navigationBarTitle("Tab View + Navigation View") .navigationBarTitleDisplayMode(.inline) + .toolbarRoleIfPad18() } } } struct TabNavView : View { + @Environment(\.horizontalSizeClass) var horizontalSizeClass + @State private var isBarPresented: Bool = true private let onDismiss: () -> Void @@ -46,25 +72,26 @@ struct TabNavView : View { } var body: some View { - MaterialTabView { - InnerNavView(tabIdx:0, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "1.square") - } - InnerNavView(tabIdx:1, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "2.square").foregroundStyle(.red) - } - InnerNavView(tabIdx:2, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "3.square") + if #available(iOS 18.0, *) { + MaterialTabView { + ForEach(1..<5) { idx in + Tab("Tab\(UIDevice.current.userInterfaceIdiom == .pad && horizontalSizeClass == .regular ? " \(idx)" : "")", systemImage: "\(idx).square") { + InnerNavView(tabIdx:idx - 1, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) + } } - InnerNavView(tabIdx:3, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) - .tabItem { - Label("Tab", systemImage: "4.square") + } + .popupDemo(demoContent: demoContent, isBarPresented: $isBarPresented, includeContextMenu: UserDefaults.settings.bool(forKey: .contextMenuEnabled)) + } else { + MaterialTabView { + ForEach(1..<5) { idx in + InnerNavView(tabIdx:idx - 1, onDismiss: onDismiss, presentBarHandler: presentBarHandler, hideBarHandler: hideBarHandler) + .tabItem { + Label("Tab", systemImage: "\(idx).square").foregroundStyle(.red) + } } + } + .popupDemo(demoContent: demoContent, isBarPresented: $isBarPresented, includeContextMenu: UserDefaults.settings.bool(forKey: .contextMenuEnabled)) } - .popupDemo(demoContent: demoContent, isBarPresented: $isBarPresented, includeContextMenu: UserDefaults.settings.bool(forKey: .contextMenuEnabled)) } } diff --git a/LNPopupUIExample/LNPopupUIExample/Info.plist b/LNPopupUIExample/LNPopupUIExample/Info.plist index 5b7dc77..0530399 100644 --- a/LNPopupUIExample/LNPopupUIExample/Info.plist +++ b/LNPopupUIExample/LNPopupUIExample/Info.plist @@ -17,7 +17,7 @@ CFBundlePackageType $(PRODUCT_BUNDLE_PACKAGE_TYPE) CFBundleShortVersionString - 1.8.7 + 1.9.-1 CFBundleVersion 1 LSApplicationCategoryType diff --git a/LNPopupUIExample/LNPopupUIExample/SceneSelection.swift b/LNPopupUIExample/LNPopupUIExample/SceneSelection.swift index f4dbaca..f3228f7 100644 --- a/LNPopupUIExample/LNPopupUIExample/SceneSelection.swift +++ b/LNPopupUIExample/LNPopupUIExample/SceneSelection.swift @@ -37,6 +37,19 @@ fileprivate struct LNHeaderFooterView: View { } } +extension View { + func pagePresentationIfPossible() -> some View { + if #available(iOS 18.0, *) { + return self + .presentationSizing( + .page + ) + } else { + return self + } + } +} + struct SceneSelection: View { @Environment(\.horizontalSizeClass) var horizontalSizeClass @Environment(\.verticalSizeClass) var verticalSizeClass @@ -100,6 +113,7 @@ struct SceneSelection: View { NavDemoView(demoContent: DemoContent()) { viewSheetPresented.toggle() } + .pagePresentationIfPossible() }) CellPaddedButton("View") { viewPresented.toggle() diff --git a/Package.swift b/Package.swift index fc12271..c7c3c0f 100644 --- a/Package.swift +++ b/Package.swift @@ -20,7 +20,7 @@ let package = Package( ], dependencies: [ // .package(path: "../LNPopupController"), - .package(url: "https://github.com/LeoNatan/LNPopupController.git", from: Version(stringLiteral: "2.19.6")), + .package(url: "https://github.com/LeoNatan/LNPopupController.git", from: Version(stringLiteral: "2.20.1")), // .package(path: "../LNSwiftUIUtils"), .package(url: "https://github.com/LeoNatan/LNSwiftUIUtils.git", from: Version(stringLiteral: "1.1.0")) ],