SwiftUI - 检测文本字段中的变化
SwiftUI - detect change in Textfield
我希望当用户在文本字段中编辑信息时它会监听变化 -> 保存按钮将从灰色变为蓝色并启用。如果用户没有编辑信息,保存按钮将被禁用。
我希望当用户在文本字段中编辑信息时它会监听变化 -> 保存按钮将从灰色变为蓝色。如果用户没有编辑信息,保存按钮将禁用
这是一个可能对您有用的简单示例,使用了一些评论建议。有 3 个主要元素,条件、禁用和颜色。
struct ContentView: View {
@State private var password = ""
@State private var passwordRepeat = ""
// here the condition you want
var isConfirmed: Bool {
if !password.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty &&
!passwordRepeat.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty &&
(password == passwordRepeat) {
return true
} else {
return false
}
}
var body: some View {
VStack {
SecureField("password", text: $password)
SecureField("password confirm", text: $passwordRepeat)
Button(action: { } ) {
Text("SAVE").accentColor(.white)
}
.disabled(!isConfirmed) // <-- here to enable/disable the button
.padding(20)
.background(isConfirmed ? Color.green : Color.gray) // <-- here to change color of the button
.cornerRadius(20)
}.frame(width: 333)
.textFieldStyle(RoundedBorderTextFieldStyle())
}
}
编辑 1:
这里有一种方法可以在您的文本字段中已经包含内容时使用该条件:
// your ProfileEditorRow equivalent
struct ContentView: View {
@ObservedObject var profileViewModel: ProfileViewModel
let refUserName: String // <-- reference user name
init(profileViewModel: ProfileViewModel) {
self.profileViewModel = profileViewModel
self.refUserName = profileViewModel.user.name // <-- here keep the initial user name
}
var isCondition: Bool {
return (refUserName == profileViewModel.name) // <-- here test for change
}
var body: some View {
VStack {
TextField("test",text: $profileViewModel.user.name)
Button(action: { print("----> SAVE") } ) {
Text("SAVE").accentColor(.white)
}
.disabled(isCondition) // <-- here to enable/disable the button
.padding(20)
.background(isCondition ? Color.gray : Color.green) // <-- here to change color of the button
.cornerRadius(20)
}.frame(width: 333)
.textFieldStyle(RoundedBorderTextFieldStyle())
}
EDIT2:条件中包含多个元素的示例
您可能有一个包含姓名、生日等的 User
结构...使用这个:
struct User {
var name
var birthday
var gender
// ....
}
struct ContentView: View {
@ObservedObject var profileViewModel: ProfileViewModel
let refUser: User // <-- reference user
init(profileViewModel: ProfileViewModel) {
self.profileViewModel = profileViewModel
self.refUser = profileViewModel.user // <-- here keep the initial user values
}
var isCondition: Bool {
return (refUser.name == profileViewModel.user.name) &&
(refUser.birthday == profileViewModel.user.birthday)
}
var body: some View {
VStack {
TextField("name",text: $profileViewModel.user.name)
TextField("birthday",text: $profileViewModel.user.birthday)
Button(action: { print("----> SAVE") } ) {
Text("SAVE").accentColor(.white)
}
.disabled(isCondition) // <-- here to enable/disable the button
.padding(20)
.background(isCondition ? Color.gray : Color.green) // <-- here to change color of the button
.cornerRadius(20)
}.frame(width: 333)
.textFieldStyle(RoundedBorderTextFieldStyle())
}
}
我希望当用户在文本字段中编辑信息时它会监听变化 -> 保存按钮将从灰色变为蓝色并启用。如果用户没有编辑信息,保存按钮将被禁用。
我希望当用户在文本字段中编辑信息时它会监听变化 -> 保存按钮将从灰色变为蓝色。如果用户没有编辑信息,保存按钮将禁用
这是一个可能对您有用的简单示例,使用了一些评论建议。有 3 个主要元素,条件、禁用和颜色。
struct ContentView: View {
@State private var password = ""
@State private var passwordRepeat = ""
// here the condition you want
var isConfirmed: Bool {
if !password.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty &&
!passwordRepeat.trimmingCharacters(in: .whitespacesAndNewlines).isEmpty &&
(password == passwordRepeat) {
return true
} else {
return false
}
}
var body: some View {
VStack {
SecureField("password", text: $password)
SecureField("password confirm", text: $passwordRepeat)
Button(action: { } ) {
Text("SAVE").accentColor(.white)
}
.disabled(!isConfirmed) // <-- here to enable/disable the button
.padding(20)
.background(isConfirmed ? Color.green : Color.gray) // <-- here to change color of the button
.cornerRadius(20)
}.frame(width: 333)
.textFieldStyle(RoundedBorderTextFieldStyle())
}
}
编辑 1:
这里有一种方法可以在您的文本字段中已经包含内容时使用该条件:
// your ProfileEditorRow equivalent
struct ContentView: View {
@ObservedObject var profileViewModel: ProfileViewModel
let refUserName: String // <-- reference user name
init(profileViewModel: ProfileViewModel) {
self.profileViewModel = profileViewModel
self.refUserName = profileViewModel.user.name // <-- here keep the initial user name
}
var isCondition: Bool {
return (refUserName == profileViewModel.name) // <-- here test for change
}
var body: some View {
VStack {
TextField("test",text: $profileViewModel.user.name)
Button(action: { print("----> SAVE") } ) {
Text("SAVE").accentColor(.white)
}
.disabled(isCondition) // <-- here to enable/disable the button
.padding(20)
.background(isCondition ? Color.gray : Color.green) // <-- here to change color of the button
.cornerRadius(20)
}.frame(width: 333)
.textFieldStyle(RoundedBorderTextFieldStyle())
}
EDIT2:条件中包含多个元素的示例
您可能有一个包含姓名、生日等的 User
结构...使用这个:
struct User {
var name
var birthday
var gender
// ....
}
struct ContentView: View {
@ObservedObject var profileViewModel: ProfileViewModel
let refUser: User // <-- reference user
init(profileViewModel: ProfileViewModel) {
self.profileViewModel = profileViewModel
self.refUser = profileViewModel.user // <-- here keep the initial user values
}
var isCondition: Bool {
return (refUser.name == profileViewModel.user.name) &&
(refUser.birthday == profileViewModel.user.birthday)
}
var body: some View {
VStack {
TextField("name",text: $profileViewModel.user.name)
TextField("birthday",text: $profileViewModel.user.birthday)
Button(action: { print("----> SAVE") } ) {
Text("SAVE").accentColor(.white)
}
.disabled(isCondition) // <-- here to enable/disable the button
.padding(20)
.background(isCondition ? Color.gray : Color.green) // <-- here to change color of the button
.cornerRadius(20)
}.frame(width: 333)
.textFieldStyle(RoundedBorderTextFieldStyle())
}
}