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 { @ViewBuilder private var serverConfigurationSections: some View {
switch self.server.configuration { switch self.server.configuration {
case .dnsOverTLS(let 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): 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 import SwiftUI
private enum FocusedField {
case address
case serverURL
}
struct DoHSections { struct DoHSections {
@Binding var server: Resolver @Binding var configuration: DoHConfiguration
@State var configuration: DoHConfiguration
@FocusState private var focusedField: FocusedField?
private func commit() {
self.server.configuration = .dnsOverHTTPS(self.configuration)
}
} }
extension DoHSections: View { extension DoHSections: View {
var body: some View { var body: some View {
Section { Section {
ForEach(0..<self.configuration.servers.count, id: \.self) { i in ForEach(0..<self.configuration.servers.count, id: \.self) { i in
TextField( NavigationLink {
"IP address", TextField(
text: .init( "IP address",
get: { self.configuration.servers[i] }, text: .init(
set: { get: { self.configuration.servers[i] },
self.configuration.servers[i] = $0 set: {
.trimmingCharacters(in: .whitespacesAndNewlines) self.configuration.servers[i] = $0
} .trimmingCharacters(in: .whitespacesAndNewlines)
}
)
) )
) .textContentType(.URL)
.focused(self.$focusedField, equals: .address) .keyboardType(.numbersAndPunctuation)
.textContentType(.URL) .autocapitalization(.none)
.keyboardType(.numbersAndPunctuation) .disableAutocorrection(true)
.autocapitalization(.none) } label: {
.disableAutocorrection(true) Text("IP address")
} Spacer()
.onDelete { Text(self.configuration.servers[i])
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") { Button("Add New Server") {
configuration.servers.append("") self.configuration.servers.append("")
self.commit()
} }
} header: { } header: {
EditButton() EditButton()
@ -66,21 +53,19 @@ extension DoHSections: View {
Section { Section {
HStack { HStack {
Text("Server URL") Text("Server URL")
Spacer()
TextField( TextField(
"Server URL", "Server URL",
text: .init( text: .init(
get: { get: {
configuration.serverURL?.absoluteString ?? "" self.configuration.serverURL?.absoluteString ?? ""
}, },
set: { set: {
configuration.serverURL = URL( self.configuration.serverURL = URL(
string: $0.trimmingCharacters(in: .whitespacesAndNewlines) string: $0.trimmingCharacters(in: .whitespacesAndNewlines)
) )
} }
) )
) )
.focused(self.$focusedField, equals: .serverURL)
.multilineTextAlignment(.trailing) .multilineTextAlignment(.trailing)
.textContentType(.URL) .textContentType(.URL)
.keyboardType(.URL) .keyboardType(.URL)
@ -92,39 +77,25 @@ extension DoHSections: View {
} footer: { } footer: {
Text("The URL of a DNS-over-HTTPS server.") 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 { struct DoHSections_Previews: PreviewProvider {
static var previews: some View { 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 { 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 import SwiftUI
private enum FocusedField {
case address
case serverName
}
struct DoTSections { struct DoTSections {
@Binding var server: Resolver @Binding var configuration: DoTConfiguration
@State var configuration: DoTConfiguration
@FocusState private var focusedField: FocusedField?
private func commit() {
self.server.configuration = .dnsOverTLS(self.configuration)
}
} }
extension DoTSections: View { extension DoTSections: View {
@ -36,23 +25,15 @@ extension DoTSections: View {
} }
) )
) )
.focused(self.$focusedField, equals: .address)
.textContentType(.URL) .textContentType(.URL)
.keyboardType(.numbersAndPunctuation) .keyboardType(.numbersAndPunctuation)
.autocapitalization(.none) .autocapitalization(.none)
.disableAutocorrection(true) .disableAutocorrection(true)
} }
.onDelete { .onDelete { self.configuration.servers.remove(atOffsets: $0) }
self.configuration.servers.remove(atOffsets: $0) .onMove { self.configuration.servers.move(fromOffsets: $0, toOffset: $1) }
self.commit()
}
.onMove {
self.configuration.servers.move(fromOffsets: $0, toOffset: $1)
self.commit()
}
Button("Add New Server") { Button("Add New Server") {
self.configuration.servers.append("") self.configuration.servers.append("")
self.commit()
} }
} header: { } header: {
EditButton() EditButton()
@ -66,7 +47,6 @@ extension DoTSections: View {
Section { Section {
HStack { HStack {
Text("Server Name") Text("Server Name")
Spacer()
TextField( TextField(
"Server Name", "Server Name",
text: .init( text: .init(
@ -77,7 +57,6 @@ extension DoTSections: View {
} }
) )
) )
.focused(self.$focusedField, equals: .serverName)
.multilineTextAlignment(.trailing) .multilineTextAlignment(.trailing)
.textContentType(.URL) .textContentType(.URL)
.keyboardType(.URL) .keyboardType(.URL)
@ -89,39 +68,25 @@ extension DoTSections: View {
} footer: { } footer: {
Text("The TLS name of a DNS-over-TLS server.") 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 { struct DoTSections_Previews: PreviewProvider {
static var previews: some View { 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 { 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"
)
)
)
} }
} }
} }