Refactor DoTSections and DoHSections

This commit is contained in:
Kenta Kubo 2023-04-25 01:41:51 +09:00
parent 4d7f7c2ef3
commit ef7916d5e7
3 changed files with 66 additions and 120 deletions

View file

@ -110,9 +110,19 @@ extension DetailView: View {
@ViewBuilder private var serverConfigurationSections: some View {
switch self.server.configuration {
case .dnsOverTLS(let configuration):
DoTSections(server: self.$server, configuration: configuration)
DoTSections(
configuration: .init(
get: { configuration },
set: { self.server.configuration = .dnsOverTLS($0) }
)
)
case .dnsOverHTTPS(let configuration):
DoHSections(server: self.$server, configuration: configuration)
DoHSections(
configuration: .init(
get: { configuration },
set: { self.server.configuration = .dnsOverHTTPS($0) }
)
)
}
}
}

View file

@ -7,52 +7,39 @@
import SwiftUI
private enum FocusedField {
case address
case serverURL
}
struct DoHSections {
@Binding var server: Resolver
@State var configuration: DoHConfiguration
@FocusState private var focusedField: FocusedField?
private func commit() {
self.server.configuration = .dnsOverHTTPS(self.configuration)
}
@Binding var configuration: DoHConfiguration
}
extension DoHSections: View {
var body: some View {
Section {
ForEach(0..<self.configuration.servers.count, id: \.self) { i in
TextField(
"IP address",
text: .init(
get: { self.configuration.servers[i] },
set: {
self.configuration.servers[i] = $0
.trimmingCharacters(in: .whitespacesAndNewlines)
}
NavigationLink {
TextField(
"IP address",
text: .init(
get: { self.configuration.servers[i] },
set: {
self.configuration.servers[i] = $0
.trimmingCharacters(in: .whitespacesAndNewlines)
}
)
)
)
.focused(self.$focusedField, equals: .address)
.textContentType(.URL)
.keyboardType(.numbersAndPunctuation)
.autocapitalization(.none)
.disableAutocorrection(true)
}
.onDelete {
self.configuration.servers.remove(atOffsets: $0)
self.commit()
}
.onMove {
self.configuration.servers.move(fromOffsets: $0, toOffset: $1)
self.commit()
.textContentType(.URL)
.keyboardType(.numbersAndPunctuation)
.autocapitalization(.none)
.disableAutocorrection(true)
} label: {
Text("IP address")
Spacer()
Text(self.configuration.servers[i])
}
}
.onDelete { self.configuration.servers.remove(atOffsets: $0) }
.onMove { self.configuration.servers.move(fromOffsets: $0, toOffset: $1) }
Button("Add New Server") {
configuration.servers.append("")
self.commit()
self.configuration.servers.append("")
}
} header: {
EditButton()
@ -66,21 +53,19 @@ extension DoHSections: View {
Section {
HStack {
Text("Server URL")
Spacer()
TextField(
"Server URL",
text: .init(
get: {
configuration.serverURL?.absoluteString ?? ""
self.configuration.serverURL?.absoluteString ?? ""
},
set: {
configuration.serverURL = URL(
self.configuration.serverURL = URL(
string: $0.trimmingCharacters(in: .whitespacesAndNewlines)
)
}
)
)
.focused(self.$focusedField, equals: .serverURL)
.multilineTextAlignment(.trailing)
.textContentType(.URL)
.keyboardType(.URL)
@ -92,39 +77,25 @@ extension DoHSections: View {
} footer: {
Text("The URL of a DNS-over-HTTPS server.")
}
.onChange(of: self.focusedField) { newValue in
if newValue == nil {
self.commit()
}
}
.onChange(of: self.server) { server in
switch server.configuration {
case .dnsOverTLS:
preconditionFailure("unreachable")
case .dnsOverHTTPS(let configuration):
self.configuration = configuration
}
}
.onDisappear {
self.commit()
}
}
}
struct DoHSections_Previews: PreviewProvider {
static var previews: some View {
let configuration = DoHConfiguration(
servers: [
"1.1.1.1",
"1.0.0.1",
"2606:4700:4700::1111",
"2606:4700:4700::1001",
],
serverURL: URL(string: "https://cloudflare-dns.com/dns-query")
)
let resolver = Resolver(name: "1.1.1.1", configuration: .dnsOverHTTPS(configuration))
Form {
DoHSections(server: .constant(resolver), configuration: configuration)
DoHSections(
configuration: .constant(
.init(
servers: [
"1.1.1.1",
"1.0.0.1",
"2606:4700:4700::1111",
"2606:4700:4700::1001",
],
serverURL: URL(string: "https://cloudflare-dns.com/dns-query")
)
)
)
}
}
}

View file

@ -7,19 +7,8 @@
import SwiftUI
private enum FocusedField {
case address
case serverName
}
struct DoTSections {
@Binding var server: Resolver
@State var configuration: DoTConfiguration
@FocusState private var focusedField: FocusedField?
private func commit() {
self.server.configuration = .dnsOverTLS(self.configuration)
}
@Binding var configuration: DoTConfiguration
}
extension DoTSections: View {
@ -36,23 +25,15 @@ extension DoTSections: View {
}
)
)
.focused(self.$focusedField, equals: .address)
.textContentType(.URL)
.keyboardType(.numbersAndPunctuation)
.autocapitalization(.none)
.disableAutocorrection(true)
}
.onDelete {
self.configuration.servers.remove(atOffsets: $0)
self.commit()
}
.onMove {
self.configuration.servers.move(fromOffsets: $0, toOffset: $1)
self.commit()
}
.onDelete { self.configuration.servers.remove(atOffsets: $0) }
.onMove { self.configuration.servers.move(fromOffsets: $0, toOffset: $1) }
Button("Add New Server") {
self.configuration.servers.append("")
self.commit()
}
} header: {
EditButton()
@ -66,7 +47,6 @@ extension DoTSections: View {
Section {
HStack {
Text("Server Name")
Spacer()
TextField(
"Server Name",
text: .init(
@ -77,7 +57,6 @@ extension DoTSections: View {
}
)
)
.focused(self.$focusedField, equals: .serverName)
.multilineTextAlignment(.trailing)
.textContentType(.URL)
.keyboardType(.URL)
@ -89,39 +68,25 @@ extension DoTSections: View {
} footer: {
Text("The TLS name of a DNS-over-TLS server.")
}
.onChange(of: self.focusedField) { newValue in
if newValue == nil {
self.commit()
}
}
.onChange(of: self.server) { server in
switch server.configuration {
case .dnsOverTLS(let configuration):
self.configuration = configuration
case .dnsOverHTTPS:
preconditionFailure("unreachable")
}
}
.onDisappear {
self.commit()
}
}
}
struct DoTSections_Previews: PreviewProvider {
static var previews: some View {
let configuration = DoTConfiguration(
servers: [
"1.1.1.1",
"1.0.0.1",
"2606:4700:4700::1111",
"2606:4700:4700::1001",
],
serverName: "cloudflare-dns.com"
)
let resolver = Resolver(name: "1.1.1.1", configuration: .dnsOverTLS(configuration))
Form {
DoTSections(server: .constant(resolver), configuration: configuration)
DoTSections(
configuration: .constant(
.init(
servers: [
"1.1.1.1",
"1.0.0.1",
"2606:4700:4700::1111",
"2606:4700:4700::1001",
],
serverName: "cloudflare-dns.com"
)
)
)
}
}
}