2023-04-11 18:18:31 +02:00
|
|
|
import SwiftUI
|
2023-12-27 21:57:32 +01:00
|
|
|
import SwiftData
|
|
|
|
import SFSafeSymbols
|
2024-04-22 12:58:49 +02:00
|
|
|
import Combine
|
2023-04-11 18:18:31 +02:00
|
|
|
|
|
|
|
struct SettingsView: View {
|
|
|
|
|
2023-08-14 10:39:29 +02:00
|
|
|
let keyManager: KeyManagement
|
2023-04-11 18:18:31 +02:00
|
|
|
|
2023-12-27 21:57:32 +01:00
|
|
|
@ObservedObject
|
|
|
|
var coordinator: RequestCoordinator
|
|
|
|
|
2023-04-11 18:18:31 +02:00
|
|
|
@Binding
|
|
|
|
var serverAddress: String
|
|
|
|
|
|
|
|
@Binding
|
|
|
|
var localAddress: String
|
2023-08-07 15:47:40 +02:00
|
|
|
|
2024-04-22 12:58:49 +02:00
|
|
|
@Binding
|
|
|
|
var localPort: UInt16
|
|
|
|
|
|
|
|
@State
|
|
|
|
private var localPortString = ""
|
|
|
|
|
2023-04-11 18:18:31 +02:00
|
|
|
var body: some View {
|
|
|
|
NavigationView {
|
|
|
|
ScrollView {
|
|
|
|
VStack(alignment: .leading, spacing: 8) {
|
|
|
|
VStack(alignment: .leading) {
|
|
|
|
Text("Server address")
|
|
|
|
.bold()
|
|
|
|
TextField("Server address", text: $serverAddress)
|
2023-08-07 15:47:40 +02:00
|
|
|
.foregroundColor(.secondary)
|
2023-04-11 18:18:31 +02:00
|
|
|
.padding(.leading, 8)
|
2023-12-27 21:57:32 +01:00
|
|
|
HStack {
|
|
|
|
Button("Test") {
|
|
|
|
coordinator.checkConnection(using: .throughServer)
|
|
|
|
}.padding(8)
|
|
|
|
if coordinator.state == .deviceAvailable {
|
|
|
|
Image(systemSymbol: .checkmarkCircle)
|
|
|
|
.foregroundColor(.green)
|
|
|
|
} else if coordinator.state != .notChecked {
|
|
|
|
Text(coordinator.state.description)
|
|
|
|
.font(.caption)
|
|
|
|
.foregroundStyle(.secondary)
|
|
|
|
}
|
|
|
|
}
|
2023-04-11 18:18:31 +02:00
|
|
|
}.padding(.vertical, 8)
|
|
|
|
VStack(alignment: .leading) {
|
|
|
|
Text("Local address")
|
|
|
|
.bold()
|
|
|
|
TextField("Local address", text: $localAddress)
|
2023-08-07 15:47:40 +02:00
|
|
|
.foregroundColor(.secondary)
|
2023-04-11 18:18:31 +02:00
|
|
|
.padding(.leading, 8)
|
2024-04-22 12:58:49 +02:00
|
|
|
TextField("UDP Port", text: $localPortString)
|
|
|
|
.keyboardType(.numberPad)
|
|
|
|
.onReceive(Just(localPortString)) { newValue in
|
|
|
|
let filtered = newValue.filter { "0123456789".contains($0) }
|
|
|
|
if filtered != newValue {
|
|
|
|
self.localPortString = filtered
|
|
|
|
if let value = UInt16(filtered) {
|
|
|
|
self.localPort = value
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
.foregroundColor(.secondary)
|
|
|
|
.padding(.leading, 8)
|
2023-04-11 18:18:31 +02:00
|
|
|
}.padding(.vertical, 8)
|
|
|
|
ForEach(KeyManagement.KeyType.allCases) { keyType in
|
|
|
|
SingleKeyView(
|
2023-08-14 10:39:29 +02:00
|
|
|
keyManager: keyManager,
|
2023-04-11 18:18:31 +02:00
|
|
|
type: keyType)
|
|
|
|
}
|
|
|
|
}.padding()
|
2024-04-22 12:58:49 +02:00
|
|
|
}.onAppear {
|
|
|
|
self.localPortString = "\(localPort)"
|
2023-04-11 18:18:31 +02:00
|
|
|
}
|
|
|
|
.navigationTitle("Settings")
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-12-27 21:57:32 +01:00
|
|
|
#Preview {
|
|
|
|
do {
|
|
|
|
let config = ModelConfiguration(isStoredInMemoryOnly: true)
|
|
|
|
let container = try ModelContainer(for: HistoryItem.self, configurations: config)
|
|
|
|
|
|
|
|
let item = HistoryItem.mock
|
|
|
|
container.mainContext.insert(item)
|
|
|
|
try container.mainContext.save()
|
|
|
|
return SettingsView(
|
2023-08-14 10:39:29 +02:00
|
|
|
keyManager: KeyManagement(),
|
2023-12-27 21:57:32 +01:00
|
|
|
coordinator: .init(modelContext: container.mainContext),
|
2023-04-11 18:18:31 +02:00
|
|
|
serverAddress: .constant("https://example.com"),
|
2024-04-22 12:58:49 +02:00
|
|
|
localAddress: .constant("192.168.178.42"),
|
|
|
|
localPort: .constant(1234))
|
2023-12-27 21:57:32 +01:00
|
|
|
} catch {
|
|
|
|
fatalError("Failed to create model container.")
|
2023-04-11 18:18:31 +02:00
|
|
|
}
|
|
|
|
}
|