another.im-ios/Monal/another.im/Views/Main/Contacts/ContactsScreen.swift
2024-12-06 12:56:09 +01:00

147 lines
4.1 KiB
Swift

import SwiftUI
struct ContactsScreen: View {
@EnvironmentObject var wrapper: WrapperXMPP
@Environment(\.router) var router
var body: some View {
ZStack {
// Background color
Color.Material.Background.light
.ignoresSafeArea()
// Content
VStack(spacing: 0) {
// Header
SharedNavigationBar(
centerText: .init(text: L10n.Contacts.title),
rightButton: .init(
image: Image(systemName: "plus"),
action: {
router.showScreen(.fullScreenCover) { _ in
AddContactOrChannelScreen()
}
}
)
)
// Contacts list
if !wrapper.contacts.isEmpty {
List {
ForEach(wrapper.contacts) {
ContactsScreenRow(contact: $0)
}
}
.listStyle(.plain)
.background(Color.Material.Background.light)
} else {
Spacer()
}
}
}
}
}
private struct ContactsScreenRow: View {
@EnvironmentObject var wrapper: WrapperXMPP
@Environment(\.router) var router
var contact: Contact
var body: some View {
SharedListRow(
iconType: .charCircle(contact.name),
text: contact.contactJid,
controlType: .none
)
.onTapGesture {
startChat()
}
.swipeActions(edge: .trailing, allowsFullSwipe: false) {
Button {
router.showAlert(.confirmationDialog, title: L10n.Contacts.deleteContact, subtitle: L10n.Contacts.Delete.message) {
deleteConfirmation
}
} label: {
Label("", systemImage: "trash")
}
.tint(Color.red)
}
.contextMenu {
Button(L10n.Contacts.sendMessage, systemImage: "message") {
startChat()
}
Divider()
Button(L10n.Contacts.editContact) {
print("Edit contact")
}
Button(L10n.Contacts.selectContact) {
print("Select contact")
}
Divider()
Button(L10n.Contacts.deleteContact, systemImage: "trash", role: .destructive) {
router.showAlert(.confirmationDialog, title: L10n.Contacts.deleteContact, subtitle: L10n.Contacts.Delete.message) {
deleteConfirmation
}
}
}
}
@ViewBuilder private var deleteConfirmation: some View {
Button(role: .destructive) {
Task {
await deleteCompletely()
}
} label: {
Text(L10n.Contacts.Delete.deleteCompletely)
}
Button(role: .cancel) {} label: {
Text(L10n.Global.cancel)
}
}
private func deleteCompletely() async {
router.showModal {
LoadingScreen()
}
defer {
router.dismissModal()
}
do {
try await wrapper.deleteContact(contact)
} catch {
router.showAlert(
.alert,
title: L10n.Global.Error.title,
subtitle: L10n.Contacts.Delete.error
) {
Button(L10n.Global.ok, role: .cancel) {}
}
}
}
private func startChat() {
guard let model = wrapper.chat(with: contact) else {
router.showAlert(
.alert,
title: L10n.Global.Error.title,
subtitle: L10n.Conversation.startError
) {
Button(L10n.Global.ok, role: .cancel) {}
}
return
}
router.showScreen(.push) { _ in
ConversationScreen()
.navigationBarHidden(true)
.environmentObject(model)
}
}
}