Flutter TextField正则限制输入插入禁用字符导致内容全清如何解决?
问题原因
FilteringTextInputFormatter.allow的校验逻辑为:若新输入的完整字符串未匹配指定正则规则,会直接丢弃整个新输入值,回落到空值或上一次合法输入。当你在已有合法数字中插入.或-时,完整字符串不符合正则要求,就会触发清空逻辑。
解决方案1:使用FilteringTextInputFormatter.deny直接禁用指定字符
这是成本最低的适配方案,直接指定要拦截的.和-字符即可,Formatter会自动剔除这两个禁用字符,保留其余所有合法内容:
TextField( inputFormatters: [ // 仅拦截.和-两个字符,其余内容正常保留 FilteringTextInputFormatter.deny(RegExp(r'[.-]')), ], controller: _phoneTextController, enableInteractiveSelection: false, keyboardType: TextInputType.number, decoration: InputDecoration( fillColor: Colors.transparent, border: InputBorder.none, focusedBorder: InputBorder.none, enabledBorder: InputBorder.none, errorBorder: InputBorder.none, disabledBorder: InputBorder.none, hintText: 'number', hintStyle: HintTextFieldStyle, ), style: TextFieldStyle, )
解决方案2:自定义输入格式化器(适配更复杂的校验场景)
如果后续有其他自定义校验需求,可以自行实现TextInputFormatter,手动过滤禁用字符,同时可以适配光标位置避免错位:
class NumberOnlyInputFormatter extends TextInputFormatter { @override TextEditingValue formatEditUpdate(TextEditingValue oldValue, TextEditingValue newValue) { // 仅保留0-9的数字字符,可根据需求调整过滤规则 final filteredText = newValue.text.replaceAll(RegExp(r'[^0-9]'), ''); return newValue.copyWith( text: filteredText, // 自动适配光标位置到输入末尾,避免插入非法字符后光标跳转到开头 selection: TextSelection.collapsed(offset: filteredText.length), ); } }
使用时直接将自定义Formatter加入inputFormatters数组即可:
inputFormatters: [ NumberOnlyInputFormatter(), ],
选型说明
如果仅需要拦截.和-两个字符,优先使用方案1;如果需要严格限制仅能输入0-9的数字,建议使用方案2,光标交互体验更流畅。
内容的提问来源于stack exchange,提问作者user12051965
相关产品推荐
相关产品推荐

