关于限制输入字数以前也做过,网上也很多方法。
但都不够完美,以前的测试人员也没千方百计的挑毛病,所以就糊弄过去了。
现在这个项目的测试人员为了找bug真是无所不用其极。。。。
1.一般方法就是通过UITextField的代理方法
#pragma mark - UITextFieldDelegate
- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string
{
if (textField == self.textFieldName) {
if (string.length == 0) return YES;
NSInteger existedLength = textField.text.length;
NSInteger selectedLength = range.length;
NSInteger replaceLength = string.length;
if (existedLength - selectedLength + replaceLength > 20) {
return NO;
}
}
return YES;
}
but这个方法还是有bug的。。。这个方法很容易被中文的联想、粘贴等方式突破限制长度。
2.给UITextField加事件,然后在事件里截取至最大长度
[self.textFieldName addTarget:self action:@selector(textFieldDidChange:) forControlEvents:UIControlEventEditingChanged];
- (void)textFieldDidChange:(UITextField *)textField
{
if (textField == self.textFieldName) {
if (textField.text.length > 15) {
textField.text = [textField.text substringToIndex:15];
}
}
}
你以为这样搞定了中文联想、粘贴的bug,就高枕无忧了吗。。。这方法还是有bug的,如果输入至还剩一个字符时,再输入Emoji呢?Emoji占2个字符,会被截得出现半个Emoji的情况,含半个Emoji的字符串在URL编码时会变为nil。
3.限制输入字数完美解决方案
其实就是在方案2上做了调整
- (void)textFieldDidChange:(UITextField *)textField
{
if (textField == self.textFieldName) {
if (textField.text.length > 15) {
UITextRange *markedRange = [textField markedTextRange];
if (markedRange) {
return;
}
//Emoji占2个字符,如果是超出了半个Emoji,用15位置来截取会出现Emoji截为2半
//超出最大长度的那个字符序列(Emoji算一个字符序列)的range
NSRange range = [textField.text rangeOfComposedCharacterSequenceAtIndex:15];
textField.text = [textField.text substringToIndex:range.location];
}
}
}