mirror of
https://github.com/simplex-chat/simplex-chat.git
synced 2025-06-28 20:29:53 +00:00
experiment
This commit is contained in:
parent
085ada470e
commit
c952c9e623
1 changed files with 102 additions and 87 deletions
|
@ -78,7 +78,7 @@ struct ChatView: View {
|
||||||
}
|
}
|
||||||
VStack(spacing: 0) {
|
VStack(spacing: 0) {
|
||||||
ZStack(alignment: .bottomTrailing) {
|
ZStack(alignment: .bottomTrailing) {
|
||||||
chatItemsList()
|
ChatItemsList(chat: $chat, mergedItems: $mergedItems, revealedItems: $revealedItems, scrollModel: $scrollModel, loadingMoreItems: $loadingMoreItems, allowLoadMoreItems: $allowLoadMoreItems, ignoreLoadingRequests: $ignoreLoadingRequests, searchText: $searchText, theme: $theme)
|
||||||
FloatingButtons(theme: theme, scrollModel: scrollModel, chat: chat, loadingMoreItems: $loadingMoreItems)
|
FloatingButtons(theme: theme, scrollModel: scrollModel, chat: chat, loadingMoreItems: $loadingMoreItems)
|
||||||
}
|
}
|
||||||
connectingText()
|
connectingText()
|
||||||
|
@ -441,105 +441,120 @@ struct ChatView: View {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
struct ChatItemsList: View {
|
||||||
|
@Binding var chat: Chat
|
||||||
|
@Binding var mergedItems: MergedItems
|
||||||
|
@Binding var revealedItems: [Int64]
|
||||||
|
@Binding var scrollModel: ReverseListScrollModel
|
||||||
|
@Binding var loadingMoreItems: Bool
|
||||||
|
@Binding var allowLoadMoreItems: Bool
|
||||||
|
@Binding var ignoreLoadingRequests: Int64?
|
||||||
|
@Binding var searchText: String
|
||||||
|
@Binding var theme: AppTheme
|
||||||
|
|
||||||
private func chatItemsList() -> some View {
|
var searchValueIsEmpty: Bool { get { searchText.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty } }
|
||||||
let cInfo = chat.chatInfo
|
|
||||||
return GeometryReader { g in
|
var body: some View {
|
||||||
let _ = logger.debug("LALAL RELOAD \(im.reversedChatItems.count)")
|
let im = ItemsModel.shared
|
||||||
// LALAL CAN I CHANGE BINDING LIKE THIS IN ignoreLoadingRequests?
|
let cInfo = chat.chatInfo
|
||||||
ReverseList(mergedItems: $mergedItems, revealedItems: $revealedItems, unreadCount: Binding.constant(chat.chatStats.unreadCount), scrollState: $scrollModel.state, loadingMoreItems: $loadingMoreItems, allowLoadMoreItems: $allowLoadMoreItems, ignoreLoadingRequests: searchValueIsEmpty ? $ignoreLoadingRequests : Binding.constant(nil)) { index, mergedItem in
|
return GeometryReader { g in
|
||||||
let ci = switch mergedItem {
|
let _ = logger.debug("LALAL RELOAD \(im.reversedChatItems.count)")
|
||||||
case let .single(item, _, _): item.item
|
// LALAL CAN I CHANGE BINDING LIKE THIS IN ignoreLoadingRequests?
|
||||||
case let .grouped(items, _, _, _, _, _, _, _): items.boxedValue.last!.item
|
ReverseList(mergedItems: $mergedItems, revealedItems: $revealedItems, unreadCount: Binding.constant(chat.chatStats.unreadCount), scrollState: $scrollModel.state, loadingMoreItems: $loadingMoreItems, allowLoadMoreItems: $allowLoadMoreItems, ignoreLoadingRequests: searchValueIsEmpty ? $ignoreLoadingRequests : Binding.constant(nil)) { index, mergedItem in
|
||||||
}
|
let ci = switch mergedItem {
|
||||||
let voiceNoFrame = voiceWithoutFrame(ci)
|
case let .single(item, _, _): item.item
|
||||||
let maxWidth = cInfo.chatType == .group
|
case let .grouped(items, _, _, _, _, _, _, _): items.boxedValue.last!.item
|
||||||
? voiceNoFrame
|
}
|
||||||
? (g.size.width - 28) - 42
|
let voiceNoFrame = voiceWithoutFrame(ci)
|
||||||
: (g.size.width - 28) * 0.84 - 42
|
let maxWidth = cInfo.chatType == .group
|
||||||
: voiceNoFrame
|
? voiceNoFrame
|
||||||
? (g.size.width - 32)
|
? (g.size.width - 28) - 42
|
||||||
: (g.size.width - 32) * 0.84
|
: (g.size.width - 28) * 0.84 - 42
|
||||||
return ChatItemWithMenu(
|
: voiceNoFrame
|
||||||
chat: $chat,
|
? (g.size.width - 32)
|
||||||
index: index,
|
: (g.size.width - 32) * 0.84
|
||||||
isLastItem: index == mergedItems.items.count - 1,
|
return ChatItemWithMenu(
|
||||||
chatItem: ci,
|
chat: $chat,
|
||||||
merged: mergedItem,
|
index: index,
|
||||||
maxWidth: maxWidth,
|
isLastItem: index == mergedItems.items.count - 1,
|
||||||
composeState: $composeState,
|
chatItem: ci,
|
||||||
selectedMember: $selectedMember,
|
merged: mergedItem,
|
||||||
showChatInfoSheet: $showChatInfoSheet,
|
maxWidth: maxWidth,
|
||||||
revealedItems: $revealedItems,
|
composeState: $composeState,
|
||||||
selectedChatItems: $selectedChatItems,
|
selectedMember: $selectedMember,
|
||||||
forwardedChatItems: $forwardedChatItems,
|
showChatInfoSheet: $showChatInfoSheet,
|
||||||
reveal: { reveal in
|
revealedItems: $revealedItems,
|
||||||
mergedItem.reveal(reveal, $revealedItems)
|
selectedChatItems: $selectedChatItems,
|
||||||
updateMergedItemsTask?.cancel()
|
forwardedChatItems: $forwardedChatItems,
|
||||||
mergedItems = MergedItems.create(ItemsModel.shared.reversedChatItems, chat.chatStats.unreadCount, revealedItems, ItemsModel.shared.chatState)
|
reveal: { reveal in
|
||||||
|
mergedItem.reveal(reveal, $revealedItems)
|
||||||
|
updateMergedItemsTask?.cancel()
|
||||||
|
mergedItems = MergedItems.create(ItemsModel.shared.reversedChatItems, chat.chatStats.unreadCount, revealedItems, ItemsModel.shared.chatState)
|
||||||
|
}
|
||||||
|
)
|
||||||
|
.environmentObject(theme) // crashes without this line when scrolling to the first unread in ReverseList
|
||||||
|
.id(ci.id) // Required to trigger `onAppear` on iOS15
|
||||||
|
} loadItems: { unchecked, pagination, visibleItemIndexesNonReversed in
|
||||||
|
if unchecked {
|
||||||
|
await loadChatItemsUnchecked(cInfo, pagination, visibleItemIndexesNonReversed)
|
||||||
|
} else {
|
||||||
|
await loadChatItems(cInfo, pagination, visibleItemIndexesNonReversed)
|
||||||
}
|
}
|
||||||
)
|
|
||||||
.environmentObject(theme) // crashes without this line when scrolling to the first unread in ReverseList
|
|
||||||
.id(ci.id) // Required to trigger `onAppear` on iOS15
|
|
||||||
} loadItems: { unchecked, pagination, visibleItemIndexesNonReversed in
|
|
||||||
if unchecked {
|
|
||||||
await loadChatItemsUnchecked(cInfo, pagination, visibleItemIndexesNonReversed)
|
|
||||||
} else {
|
|
||||||
await loadChatItems(cInfo, pagination, visibleItemIndexesNonReversed)
|
|
||||||
}
|
}
|
||||||
}
|
.onAppear {
|
||||||
.onAppear {
|
mergedItems = MergedItems.create(im.reversedChatItems, chat.chatStats.unreadCount, revealedItems, ItemsModel.shared.chatState)
|
||||||
mergedItems = MergedItems.create(im.reversedChatItems, chat.chatStats.unreadCount, revealedItems, ItemsModel.shared.chatState)
|
loadLastItems($loadingMoreItems, chat.chatInfo)
|
||||||
loadLastItems($loadingMoreItems, chat.chatInfo)
|
allowLoadMoreItems = false
|
||||||
allowLoadMoreItems = false
|
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
|
||||||
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
|
allowLoadMoreItems = true
|
||||||
allowLoadMoreItems = true
|
}
|
||||||
}
|
}
|
||||||
}
|
.onChange(of: im.reversedChatItems) { items in
|
||||||
.onChange(of: im.reversedChatItems) { items in
|
updateMergedItemsTask?.cancel()
|
||||||
updateMergedItemsTask?.cancel()
|
//updateMergedItemsTask = Task {
|
||||||
updateMergedItemsTask = Task {
|
|
||||||
let items = MergedItems.create(items, chat.chatStats.unreadCount, revealedItems, ItemsModel.shared.chatState)
|
let items = MergedItems.create(items, chat.chatStats.unreadCount, revealedItems, ItemsModel.shared.chatState)
|
||||||
if Task.isCancelled {
|
//if Task.isCancelled {
|
||||||
return
|
// return
|
||||||
}
|
//}
|
||||||
await MainActor.run {
|
//await MainActor.run {
|
||||||
mergedItems = items
|
mergedItems = items
|
||||||
|
//}
|
||||||
|
//}
|
||||||
|
}
|
||||||
|
.onChange(of: revealedItems) { revealed in
|
||||||
|
updateMergedItemsTask?.cancel()
|
||||||
|
mergedItems = MergedItems.create(im.reversedChatItems, chat.chatStats.unreadCount, revealed, ItemsModel.shared.chatState)
|
||||||
|
}
|
||||||
|
.onChange(of: chat.chatStats.unreadCount) { unreadCount in
|
||||||
|
updateMergedItemsTask?.cancel()
|
||||||
|
mergedItems = MergedItems.create(im.reversedChatItems, unreadCount, revealedItems, ItemsModel.shared.chatState)
|
||||||
|
}
|
||||||
|
.onChange(of: chat.id) { _ in
|
||||||
|
loadLastItems($loadingMoreItems, chat.chatInfo)
|
||||||
|
allowLoadMoreItems = false
|
||||||
|
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
|
||||||
|
allowLoadMoreItems = true
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
.opacity(ItemsModel.shared.isLoading ? 0 : 1)
|
||||||
.onChange(of: revealedItems) { revealed in
|
.padding(.vertical, -InvertedTableView.inset)
|
||||||
updateMergedItemsTask?.cancel()
|
.onTapGesture { hideKeyboard() }
|
||||||
mergedItems = MergedItems.create(im.reversedChatItems, chat.chatStats.unreadCount, revealed, ItemsModel.shared.chatState)
|
.onChange(of: searchText) { _ in
|
||||||
}
|
Task { await loadChat(type: chat.chatInfo.chatType, id: chat.chatInfo.apiId, search: searchText) }
|
||||||
.onChange(of: chat.chatStats.unreadCount) { unreadCount in
|
|
||||||
updateMergedItemsTask?.cancel()
|
|
||||||
mergedItems = MergedItems.create(im.reversedChatItems, unreadCount, revealedItems, ItemsModel.shared.chatState)
|
|
||||||
}
|
|
||||||
.onChange(of: chat.id) { _ in
|
|
||||||
loadLastItems($loadingMoreItems, chat.chatInfo)
|
|
||||||
allowLoadMoreItems = false
|
|
||||||
DispatchQueue.main.asyncAfter(deadline: .now() + 0.5) {
|
|
||||||
allowLoadMoreItems = true
|
|
||||||
}
|
}
|
||||||
}
|
.onChange(of: im.itemAdded) { added in
|
||||||
.opacity(ItemsModel.shared.isLoading ? 0 : 1)
|
if added {
|
||||||
.padding(.vertical, -InvertedTableView.inset)
|
im.itemAdded = false
|
||||||
.onTapGesture { hideKeyboard() }
|
if FloatingButtonModel.shared.isReallyNearBottom {
|
||||||
.onChange(of: searchText) { _ in
|
scrollModel.scrollToBottom()
|
||||||
Task { await loadChat(type: chat.chatInfo.chatType, id: chat.chatInfo.apiId, search: searchText) }
|
}
|
||||||
}
|
|
||||||
.onChange(of: im.itemAdded) { added in
|
|
||||||
if added {
|
|
||||||
im.itemAdded = false
|
|
||||||
if FloatingButtonModel.shared.isReallyNearBottom {
|
|
||||||
scrollModel.scrollToBottom()
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ViewBuilder private func connectingText() -> some View {
|
@ViewBuilder private func connectingText() -> some View {
|
||||||
if case let .direct(contact) = chat.chatInfo,
|
if case let .direct(contact) = chat.chatInfo,
|
||||||
!contact.sndReady,
|
!contact.sndReady,
|
||||||
|
@ -1112,7 +1127,7 @@ struct ChatView: View {
|
||||||
.onAppear {
|
.onAppear {
|
||||||
// LALAL
|
// LALAL
|
||||||
//return ()
|
//return ()
|
||||||
|
|
||||||
if markedRead {
|
if markedRead {
|
||||||
return
|
return
|
||||||
} else {
|
} else {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue