背景:
需求中的一个车辆编辑页面要求输入框是大写格式,且用户是小写的字母在输入后转为大写。并不是简单的将输入框的键盘指定为大写,因为有一些系统外的输入法如搜狗输入法等是不可控的。
实现方式:
输入框使用UITextfield来实现的,想要在文字显示在textfield前就对小写进行转换,因此遵守UItextField 的UITextFieldDelegate协议,实现它的代理方法,因为我们都知道这个代理方法是是在文字还没有出现的时候的拦截,如果返回true就是直接输出了,返回false就不会直接输出,因此我们需要将转换完成后的文字添加到输入框里,首先要做的就是先找好文字的输入位置然后将文字放到textfield的属性中去并且处理光标
如下:
func textField(_ textField:UITextField, shouldChangeCharactersIn range:NSRange, replacementString string:String) ->Bool{
if string.count==0|| string ==" "{
return true
}
let nCharacter = string.unicodeScalars
var charNum:Int=0
for i in nCharacter{
charNum = Int(i.value)
if charNum >96 && charNum <123{
let uppercaseStr = string.uppercased()
let str = (textField.text!asNSString).substring(to: range.location)
let str2 = (textField.text!asNSString).substring(from: range.location)
textField.text=String.init(format:"%@%@%@",str,uppercaseStr,str2)
rx_updateTextValue.onNext(String.init(format:"%@%@%@",str,uppercaseStr,str2))
let length:Int= str2.count
let endDocument = textField.endOfDocument
let start = textField.position(from: endDocument, offset: -(length))
let end = textField.position(from: endDocument, offset: -(length))
textField.selectedTextRange= textField.textRange(from: start!, to: end!)
return false
}
ifrange.location==0{
fisrNumHandler(String.init(format:"%@",string))
}
}
return true
}
注意:
小写转为大写的算法比较简单,其中 要注意的是 rx_updateTextValue.onNext(String.init(format:"%@%@%@",str,uppercaseStr,str2)) 一定要写,因为我是用RXSwift对uitexfield的text与数据模型进行相互绑定的,而只有textField有输入时才会有效的对数据模型更行,但是我在小写转大写后返回了false,因此会认会没有输入,所以我要单独来通知数据模型我的输入框数据发生了变化。
网友评论