diff --git a/apps/ios/Shared/Views/Chat/ChatView.swift b/apps/ios/Shared/Views/Chat/ChatView.swift index b047451991..097efbc8e2 100644 --- a/apps/ios/Shared/Views/Chat/ChatView.swift +++ b/apps/ios/Shared/Views/Chat/ChatView.swift @@ -47,65 +47,70 @@ struct ChatView: View { @State private var showDeleteSelectedMessages: Bool = false @State private var allowToDeleteSelectedMessagesForAll: Bool = false + @AppStorage(DEFAULT_TOOLBAR_MATERIAL) private var toolbarMaterial = ToolbarMaterial.bar.rawValue + var body: some View { if #available(iOS 16.0, *) { - let v = viewBody - .scrollDismissesKeyboard(.immediately) - .keyboardPadding() - if (searchMode) { - v.toolbarBackground(.thinMaterial, for: .navigationBar) - } else { - v.toolbarBackground(.visible, for: .navigationBar) - } + viewBody + .scrollDismissesKeyboard(.immediately) + .keyboardPadding() + .toolbarBackground(.hidden, for: .navigationBar) } else { viewBody } } - + + @ViewBuilder private var viewBody: some View { let cInfo = chat.chatInfo - return VStack(spacing: 0) { - if searchMode { - searchToolbar() + ZStack { + let wallpaperImage = theme.wallpaper.type.image + let wallpaperType = theme.wallpaper.type + let backgroundColor = theme.wallpaper.background ?? wallpaperType.defaultBackgroundColor(theme.base, theme.colors.background) + let tintColor = theme.wallpaper.tint ?? wallpaperType.defaultTintColor(theme.base) + Color.clear.ignoresSafeArea(.all) + .if(wallpaperImage != nil) { view in + view.modifier( + ChatViewBackground(image: wallpaperImage!, imageType: wallpaperType, background: backgroundColor, tint: tintColor) + ) + } + VStack(spacing: 0) { + ZStack(alignment: .bottomTrailing) { + chatItemsList() + floatingButtons(counts: floatingButtonModel.unreadChatItemCounts) + } + connectingText() + if selectedChatItems == nil { + ComposeView( + chat: chat, + composeState: $composeState, + keyboardVisible: $keyboardVisible + ) + .disabled(!cInfo.sendMsgEnabled) + } else { + SelectedItemsBottomToolbar( + chatItems: ItemsModel.shared.reversedChatItems, + selectedChatItems: $selectedChatItems, + chatInfo: chat.chatInfo, + deleteItems: { forAll in + allowToDeleteSelectedMessagesForAll = forAll + showDeleteSelectedMessages = true + }, + moderateItems: { + if case let .group(groupInfo) = chat.chatInfo { + showModerateSelectedMessagesAlert(groupInfo) + } + } + ) + } + } + } + .safeAreaInset(edge: .top) { + VStack(spacing: .zero) { + if searchMode { searchToolbar() } Divider() } - ZStack(alignment: .bottomTrailing) { - let wallpaperImage = theme.wallpaper.type.image - let wallpaperType = theme.wallpaper.type - let backgroundColor = theme.wallpaper.background ?? wallpaperType.defaultBackgroundColor(theme.base, theme.colors.background) - let tintColor = theme.wallpaper.tint ?? wallpaperType.defaultTintColor(theme.base) - chatItemsList() - .if(wallpaperImage != nil) { view in - view.modifier( - ChatViewBackground(image: wallpaperImage!, imageType: wallpaperType, background: backgroundColor, tint: tintColor) - ) - } - floatingButtons(counts: floatingButtonModel.unreadChatItemCounts) - } - connectingText() - if selectedChatItems == nil { - ComposeView( - chat: chat, - composeState: $composeState, - keyboardVisible: $keyboardVisible - ) - .disabled(!cInfo.sendMsgEnabled) - } else { - SelectedItemsBottomToolbar( - chatItems: ItemsModel.shared.reversedChatItems, - selectedChatItems: $selectedChatItems, - chatInfo: chat.chatInfo, - deleteItems: { forAll in - allowToDeleteSelectedMessagesForAll = forAll - showDeleteSelectedMessages = true - }, - moderateItems: { - if case let .group(groupInfo) = chat.chatInfo { - showModerateSelectedMessagesAlert(groupInfo) - } - } - ) - } + .background(ToolbarMaterial.material(toolbarMaterial)) } .navigationTitle(cInfo.chatViewName) .background(theme.colors.background) @@ -352,7 +357,6 @@ struct ChatView: View { } .padding(.horizontal) .padding(.vertical, 8) - .background(.thinMaterial) } private func voiceWithoutFrame(_ ci: ChatItem) -> Bool { @@ -397,20 +401,21 @@ struct ChatView: View { } loadPage: { loadChatItems(cInfo) } - .onTapGesture { hideKeyboard() } - .onChange(of: searchText) { _ in - loadChat(chat: chat, search: searchText) - } - .onChange(of: chatModel.chatId) { chatId in - if let chatId, let c = chatModel.getChat(chatId) { - chat = c - showChatInfoSheet = false - loadChat(chat: c) - } - } - .onChange(of: im.reversedChatItems) { _ in - floatingButtonModel.chatItemsChanged() + .padding(.vertical, -InvertedTableView.inset) + .onTapGesture { hideKeyboard() } + .onChange(of: searchText) { _ in + loadChat(chat: chat, search: searchText) + } + .onChange(of: chatModel.chatId) { chatId in + if let chatId, let c = chatModel.getChat(chatId) { + chat = c + showChatInfoSheet = false + loadChat(chat: c) } + } + .onChange(of: im.reversedChatItems) { _ in + floatingButtonModel.chatItemsChanged() + } } } diff --git a/apps/ios/Shared/Views/Chat/ComposeMessage/ComposeView.swift b/apps/ios/Shared/Views/Chat/ComposeMessage/ComposeView.swift index 1364958172..5219cbba7a 100644 --- a/apps/ios/Shared/Views/Chat/ComposeMessage/ComposeView.swift +++ b/apps/ios/Shared/Views/Chat/ComposeMessage/ComposeView.swift @@ -281,6 +281,7 @@ struct ComposeView: View { @State private var stopPlayback: Bool = false @AppStorage(DEFAULT_PRIVACY_SAVE_LAST_DRAFT) private var saveLastDraft = true + @AppStorage(DEFAULT_TOOLBAR_MATERIAL) private var toolbarMaterial = ToolbarMaterial.bar.rawValue var body: some View { VStack(spacing: 0) { @@ -381,7 +382,7 @@ struct ComposeView: View { } } } - .background(.thinMaterial) + .background(ToolbarMaterial.material(toolbarMaterial)) .onChange(of: composeState.message) { msg in if composeState.linkPreviewAllowed { if msg.count > 0 { diff --git a/apps/ios/Shared/Views/Chat/ReverseList.swift b/apps/ios/Shared/Views/Chat/ReverseList.swift index 1f504fb5c1..7d50a58c15 100644 --- a/apps/ios/Shared/Views/Chat/ReverseList.swift +++ b/apps/ios/Shared/Views/Chat/ReverseList.swift @@ -53,6 +53,7 @@ struct ReverseList: UIV super.init(style: .plain) // 1. Style + tableView = InvertedTableView() tableView.separatorStyle = .none tableView.transform = .verticalFlip tableView.backgroundColor = .clear @@ -132,6 +133,11 @@ struct ReverseList: UIV NotificationCenter.default.post(name: .chatViewWillBeginScrolling, object: nil) } + override func viewDidAppear(_ animated: Bool) { + tableView.clipsToBounds = false + parent?.viewIfLoaded?.clipsToBounds = false + } + /// Scrolls up func scrollToNextPage() { tableView.setContentOffset( @@ -272,3 +278,29 @@ func withConditionalAnimation( try body() } } + + +class InvertedTableView: UITableView { + static let inset = CGFloat(100) + + static let insets = UIEdgeInsets( + top: inset, + left: .zero, + bottom: inset, + right: .zero + ) + + override var contentInsetAdjustmentBehavior: UIScrollView.ContentInsetAdjustmentBehavior { + get { .never } + set { } + } + + override var contentInset: UIEdgeInsets { + get { Self.insets } + set { } + } + + override var adjustedContentInset: UIEdgeInsets { + Self.insets + } +} diff --git a/apps/ios/Shared/Views/Helpers/ChatWallpaper.swift b/apps/ios/Shared/Views/Helpers/ChatWallpaper.swift index d8ddc1c306..35bb21354d 100644 --- a/apps/ios/Shared/Views/Helpers/ChatWallpaper.swift +++ b/apps/ios/Shared/Views/Helpers/ChatWallpaper.swift @@ -81,7 +81,7 @@ struct ChatViewBackground: ViewModifier { case WallpaperType.empty: () } } - ) + ).ignoresSafeArea(.all) } }