我遇到的问题是decimalFormatter不会触发和更新绑定,除非textField 触发提交事件,即点击返回。
因此,我正在寻找如何手动触发文本字段提交事件?
下面的格式化程序代码将采用任何数字,并确保它始终有一个小数位(IE -- 10.5),并且如果插入了字母字符,这也正是我想要的,还将输入恢复为以前的有效输入。
import SwiftUI
import Combine
struct StandardRegimen: View {
@State private var totalDose = 6000.0
private var decimalFormatter: NumberFormatter = {
let f = NumberFormatter()
f.isLenient = true
f.numberStyle = .none
f.maximumFractionDigits = 1
f.minimumFractionDigits = 1
f.alwaysShowsDecimalSeparator = true
return f
}()
var body: some View{
return
VStack(alignment:.center,spacing:10){
TextField("?", value:$totalDose, formatter: self.decimalFormatter, onCommit: {
print("COMMITED!");
}).font(.system(size: 25.0))
.textFieldStyle(RoundedBorderTextFieldStyle())
.keyboardType(.decimalPad)
}
}
Run Code Online (Sandbox Code Playgroud)
如果删除修饰符代码.keyboardType(.decimalPad)并按键盘上的返回键,它将触发COMMITED 消息并关闭键盘
但是,如果您保留小数点修饰符,则无法触发提交,因为小数点没有返回键。
我在这里写了一个关于如何通过点击开放空间区域来让键盘消失的答案(使用 SwiftUI 时如何隐藏键盘?)
我已经研究了使用绑定到字符串并使用文本字段text初始值设定项参数而不是值的其他解决方案,因为这将与绑定值一起正常工作,但是这会在每次击键时更新以获得一些非常不稳定的结果(IE - 这对用户来说很难输入和编辑错误)当我正在寻找它仅在 commit 之后运行格式化程序时,我希望在用户点击以关闭键盘时发生这种情况,因为我不会在十进制小键盘上有返回键选项。
对解决此问题的任何帮助表示赞赏。
这可能有点晚了,但我想出了一种使用其他键盘类型和 a 的解决方法TextField:我使用onEditingChanged事件而不是onCommit事件并检查Bool传递到方法中的值。如果该值为 false,它将复制该onCommit方法的行为。这是您的代码,但格式为使用我的方法:
import SwiftUI
import Combine
struct StandardRegimen: View {
@State private var totalDose = 6000.0
private var decimalFormatter: NumberFormatter = {
let f = NumberFormatter()
f.isLenient = true
f.numberStyle = .none
f.maximumFractionDigits = 1
f.minimumFractionDigits = 1
f.alwaysShowsDecimalSeparator = true
return f
}()
var body: some View{
VStack(alignment:.center,spacing:10){
TextField("?", value:$totalDose, formatter: self.decimalFormatter, onEditingChanged: { edit in
// Editing has finished
if !edit {
print("COMMITED!");
}
}).font(.system(size: 25.0))
.textFieldStyle(RoundedBorderTextFieldStyle())
.keyboardType(.decimalPad)
}
}
}
Run Code Online (Sandbox Code Playgroud)
该解决方案应该适用于所有键盘类型(我只测试了常规键盘和数字键盘)。