Kordophone client for iOS and macOS
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

87 lines
2.2 KiB

import SwiftUI
import KordophoneKit
struct ConversationView : View {
var conversation: Conversation
var messages: [Message]
var sendAction: (String) -> Void
@State private var inputText = ""
@ViewBuilder
private var transcript: some View {
ScrollViewReader { proxy in
ScrollView {
LazyVStack {
ForEach(messages) { message in
if message.sentByMe {
Spacer()
}
MessageViewWrapper(message: message)
.id(message)
if !message.sentByMe {
Spacer()
}
}
}
}
.onChange(of: messages) { newValue in
proxy.scrollTo(newValue.last, anchor: .bottom)
}
}
}
@ViewBuilder
private var inputView: some View {
TextField.init(text: $inputText) {
Text("Message")
}
.padding()
.onSubmit {
if inputText.count > 0 {
sendAction(inputText)
inputText = ""
}
}
}
var body: some View {
VStack(spacing: 0) {
transcript
inputView
}
.navigationTitle(conversation.effectiveDisplayName)
}
}
struct ConversationViewWrapper : View {
var conversation: Conversation
@State private var messages = [Message]()
@EnvironmentObject private var connection: Connection
@StateObject private var updater = IntervalUpdater(5)
private func refresh() {
Task {
self.messages = await connection.messages(in: conversation) ?? .init()
}
}
var body: some View {
ConversationView(conversation: conversation, messages: messages) { sent in
Task {
await connection.send(text: sent, in: conversation)
}
refresh()
}
.onChange(of: conversation, perform: { newValue in
refresh()
})
.onAppear {
refresh()
}
.onChange(of: updater.seed) { newValue in
refresh()
}
}
}