私はswiftUIとiOを初めて使用し、数字のみを受け入れる入力フィールドを作成しようとしています
TextField("Total number of people", text: $numOfPeople)
textFieldではアルファベット文字も使用できますが、ユーザーが数字のみを入力するように制限するにはどうすればよいですか?
Combine
とonReceive
を使用する必要はありません。次のコードも使用できます。
class Model: ObservableObject {
@Published var text : String = ""
}
struct ContentView: View {
@EnvironmentObject var model: Model
var body: some View {
TextField("enter a number ...", text: Binding(get: { self.model.text },
set: { self.model.text = $0.filter { "0123456789".contains($0) } }))
}
}
struct ContentView_Previews: PreviewProvider {
static var previews: some View {
ContentView().environmentObject(Model())
}
}
残念ながら小さなちらつきもあるので、許可されていない文字が非常に短時間表示されます(私の目ではCombine
のように少し短くなっています)。
別のアプローチとしては、TextFieldビューをラップし、2つの値を保持するビューを作成する方法があります。入力された文字列を保持するプライベート変数と、同等のDoubleを保持するバインド可能な値です。ユーザーが文字を入力するたびに、Doubleを更新しようとします。
基本的な実装は次のとおりです。
struct NumberEntryField : View {
@State private var enteredValue : String = ""
@Binding var value : Double
var body: some View {
return TextField("", text: $enteredValue)
.onReceive(Just(enteredValue)) { typedValue in
if let newValue = Double(typedValue) {
self.value = newValue
}
}.onAppear(perform:{self.enteredValue = "\(self.value)"})
}
}
次のように使用できます。
struct MyView : View {
@State var doubleValue : Double = 1.56
var body: some View {
return HStack {
Text("Numeric field:")
NumberEntryField(value: self.$doubleValue)
}
}
}
これは必要最低限の例です-不十分な入力や境界チェックなどの警告を表示する機能を追加したい場合があります...