Closed moubry closed 2 years ago
Hey @moubry,
Thanks for the detailed analysis and the explanation of the bug.
We will analyse this internally and get back to you when we have an update.
Best, Martin
Hey @moubry,
The issue was fixed with https://github.com/GetStream/stream-chat-swiftui/issues/122.
The fix was already included in yesterday's 4.19.0 release and it's also available on our main
branch.
Thanks again for the detailed report and let us know if we can help with something else.
Best, Martin
✅ Yes! Thank you. I can confirm this fixes the issue for me on all platforms.
Note: There was ONE time while testing that I was kicked out of a thread back into the channel. It happened once right after restarting the app. And then never happened again. So it can still happen under rare circumstances? I have no idea how to reproduce it, though. Certainly does not happen often enough to bother worrying about, probably.
@martinmitrevski I am facing same issue. When I go to the chat from channel list then type message then it's automatically pops back to the channels list view.
I am using my custom ChannelListItem. ChannelListItem re-render when I type something in chat textfield.
struct ChannelListItem: View {
var chatManager = Container.default.resolver.resolve(ChatManager.self)!
@Injected(\.chatClient) public var chatClient
var channel: ChatChannel
@State var navigateToChannel: Bool = false
var imageSize: CGFloat = 40
var defaultFontSize: CGFloat = 12
var nameFontSize: CGFloat = 16
var messageFontSize: CGFloat = 16
var unreadMessagesCountCircleSize: CGFloat = 18
var body: some View {
VStack {
Button {
chatManager.selectedChannel = channel
navigateToChannel.toggle()
} label: {
if let member = channel.lastActiveMembers.filter({$0.id != chatClient.currentUserId}).first {
HStack(spacing: Spacing.spacingS.rawValue) {
if let customData = member.extraData["custom_data"]?.dictionaryValue,
let profileImage = customData["profile_image"]?.stringValue {
ZStack(alignment: .topLeading) {
NukeLazyImage(sourceImageURL: profileImage)
.clipShape(Circle())
.frame(width: imageSize, height: imageSize)
}
} else {
ZStack {
Circle()
.fill(Color(.skillrPink1))
.frame(width: imageSize, height: imageSize)
Text(member.name?.getInitials() ?? "")
.font(.redHatBold(size: defaultFontSize))
.foregroundColor(.white)
.lineLimit(1)
}
}
VStack(alignment: .leading, spacing: Spacing.spacingXXS.rawValue) {
HStack {
Text(member.name ?? "")
.font(.system(size: nameFontSize))
.fontWeight(.semibold)
.foregroundColor(Color(.richBlue8))
.lineLimit(1)
Spacer()
Text(channel.lastMessageAt?.stringFromDate(formate: "h:mm a") ?? "")
.font(.system(size: messageFontSize))
.foregroundColor(Color(.richBlue7))
}
HStack {
Text(channel.lastMessageText ?? "")
.font(.system(size: messageFontSize))
.foregroundColor(Color(.richBlue7))
.lineLimit(1)
Spacer()
if (channel.unreadCount.messages > 0) {
Text("\(channel.unreadCount.messages)")
.font(.system(size: defaultFontSize))
.fontWeight(.bold)
.foregroundColor(.white)
.frame(width: unreadMessagesCountCircleSize, height: unreadMessagesCountCircleSize)
.background(Color(.skillrPink1))
.clipShape(Circle())
}
}
}
}
}
}
NavigationLink(
"",
destination: ChatChannelView(
viewFactory: CustomChatViewFactory.shared,
channelController: chatClient.channelController(for: channel.cid)
),
isActive: $navigateToChannel
)
}
.frame(minWidth: 0, maxWidth: .infinity, minHeight: 0, maxHeight: .infinity)
.padding(.horizontal, Spacing.spacingXL.rawValue)
}
}
Using ChannelListItem into the makeChannelListItem like this.
func makeChannelListItem(channel: ChatChannel, channelName: String, avatar: UIImage, onlineIndicatorShown: Bool, disabled: Bool, selectedChannel: Binding<ChannelSelectionInfo?>, swipedChannelId: Binding<String?>, channelDestination: @escaping (ChannelSelectionInfo) -> ChatChannelView<CustomChatViewFactory>, onItemTap: @escaping (ChatChannel) -> Void, trailingSwipeRightButtonTapped: @escaping (ChatChannel) -> Void, trailingSwipeLeftButtonTapped: @escaping (ChatChannel) -> Void, leadingSwipeButtonTapped: @escaping (ChatChannel) -> Void) -> some View {
ChannelListItem(channel: channel)
.frame(height: 76)
}
For reference you can see the following video
Hey @zeeshansuleman,
This is actually a different issue - you're not setting any id to the channel list item, therefore it redraws every time the state changes.
Please check our default implementation here: https://github.com/GetStream/stream-chat-swiftui/blob/5b5c839c2e5a7d0a7ac88271ad6d20ebe05242d1/Sources/StreamChatSwiftUI/ChatChannelList/ChatChannelNavigatableListItem.swift#L61.
@martinmitrevski I have used the id inside the ChannelListItem as you mentioned but not working. View re-render again and again and navigate back to the Channel List View.
NavigationLink(
"",
destination: ChatChannelView(
viewFactory: CustomChatViewFactory.shared,
channelController: chatClient.channelController(for: channel.cid)
),
isActive: $navigateToChannel
)
}
.id("\(channel.id)-navigatable")
.frame(minWidth: 0, maxWidth: .infinity, minHeight: 0, maxHeight: .infinity)
.padding(.horizontal, Spacing.spacingXL.rawValue)
Hey @zeeshansuleman,
I've tried your code and it actually works for me. The only difference I've made is that I passed the binding of the selectedChannel (since I don't have the ChatManager you're using).
It's the selectedChannel: Binding<ChannelSelectionInfo?>
in the parameters list. You can use it instead of the following line:
chatManager.selectedChannel = channel // old
selectedChannel = channel.channelSelectionInfo // use this instead
Hope this helps.
@martinmitrevski Thanks for your kind support. We fixed that issue to present the chat using Chat view on the top of the tabbar by using the ZStack.
Using the sample app included in the project, you get repeatedly kicked back out of threads upon navigating into them.
This only seems to happen when 1. you have navigated into the thread recently (doesn't happen 1st time you navigate into the thread, but happens every time after), and 2. the message list view is scrolled up (doesn't occur when you're scrolled to the bottom).
What did you do?
Reproduction steps:
DemoAppSwiftUI
target to my iPhone 11 Pro.What did you expect to happen?
I expected for the navigation to only go back when I tap the "Back" button.
What happened instead?
I was automatically kicked out into the channel without swiping back or tapping "Back". As soon as the animation pushing the thread view onto the stack finishes, it starts the animation to navigation back, popping the thread view off the stack.
Note: If you quit the app, then relaunch it, then scroll up, then go into a thread, you are NOT kicked out the 1st time you enter it. But it happens the 2nd time you attempt to navigate to it, and every time after that. So the two preconditions for this to occur are: 1. you must be scrolled up in the message list view (not at the bottom of the scroll view), and 2. you must have entered the thread before.
GetStream Environment
GetStream Chat version:
main
GetStream Chat frameworks: StreamChat, StreamChatSwiftUI iOS version: Latest version of iOS 15 Swift version: latest Xcode version: Version 13.4.1 (13F100) Device: iPhone 11 ProAdditional context
I originally reported this issue here: https://github.com/GetStream/stream-chat-swift/issues/2181.
Here is a video demonstrating the issue. Watch with sound on:
https://user-images.githubusercontent.com/144283/180090246-084f7151-ee21-496b-801f-f65d70a8e06b.MOV