場(chǎng)景
公司開發(fā),需求中要求輸入框?qū)斎胛谋緝?nèi)容進(jìn)行控制,以前一貫使用length判斷。由于string情況下無論是漢字還是英文等其他字符其長(zhǎng)度均為1,精度存在差異。需要重新選定方法通過搜索我找到這個(gè)方法:
/**
* 獲取字符串字符長(zhǎng)處
*
* @param strtemp 要測(cè)試的字符
*
* @return 字符長(zhǎng)度
*/
- (int)convertToInt:(NSString *)strtemp {
int strlength = 0;
char* p = (char*)[strtemp cStringUsingEncoding:NSUnicodeStringEncoding];
for (int i=0 ; i < [strtemp lengthOfBytesUsingEncoding:NSUnicodeStringEncoding] ;i++) {
if (*p) {
p++;
strlength++;
} else {
p++;
}
}
//DLog(@"strlength==%d",strlength);
return strlength;
}
接下來該是尋找輸入框代理方法進(jìn)行字符位數(shù)控制了,查閱以前的代碼如下:
//- (BOOL)textField:(UITextField *)textField shouldChangeCharactersInRange:(NSRange)range replacementString:(NSString *)string{
////該方法無法檢測(cè)輸入框中文
// UITextField * textFile = [self.view viewWithTag:2];
// UITextField * nameTF = [self.view viewWithTag:1];
// if (textField == textFile) {
// //如果輸入的手機(jī)號(hào)大于11
// if (!range.length) {
// if (textField.text.length > 11) return NO;
// }else{
// return YES;
// }
// }
// if (textField == nameTF) {
// //如果輸入的手機(jī)號(hào)大于11
// if (!range.length) {
// if ([self convertToInt:nameTF.text] >=20) return NO;
// }else{
// return YES;
// }
// }
// return YES;
//}
在自測(cè)的過程中,我發(fā)現(xiàn)這個(gè)判定的代理方法是有局限性的,它在運(yùn)行時(shí)對(duì)漢字輸入貌似不管用,本來以為是自己的的問題,查了一下其他人也確認(rèn)了是有這個(gè)問題,這不知道算不算是蘋果的一個(gè)bug。于是我拿出針對(duì)輸入框類問題的終極大殺器(監(jiān)聽通知)來處理所面對(duì)的問題
UIKIT_EXTERN NSString *const UITextFieldTextDidBeginEditingNotification;
UIKIT_EXTERN NSString *const UITextFieldTextDidEndEditingNotification;
UIKIT_EXTERN NSString *const UITextFieldTextDidChangeNotification;
做了如下操作
UITextField * name = [topImageView viewWithTag:1];
HAFeedbackTextView * adress = [topImageView viewWithTag:4];
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(textFiledEditChanged:)
name:@"UITextFieldTextDidChangeNotification"
object:name];
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(textViewEditChanged:)
name:@"UITextViewTextDidChangeNotification"
object:adress];
由于漢字所占兩個(gè)字符,iOS截取字符是根據(jù)字符length的來操作,使用時(shí)候會(huì)出現(xiàn)數(shù)組越界導(dǎo)致閃退。
//-(void)textFiledEditChanged:(NSNotification *)obj{
// UITextField *textField = (UITextField *)obj.object;
// NSString *toBeString = textField.text;
// int stringLength = [self convertToInt:toBeString];
// if (textFile == textFiled) {
// //如果輸入的用戶名大于20
// if (stringLength>20) {
// textField.text = [toBeString substringToIndex:20];
// }
// }
//}
做出如下修改結(jié)果在測(cè)試時(shí)狂點(diǎn)按鍵會(huì)出現(xiàn)能截取需要的字符但是刪除操作時(shí)不能立即響應(yīng)刪除操作
// UITextField *textField = (UITextField *)obj.object;
// NSString *toBeString = textField.text;
// int stringLength = [self convertToInt:toBeString];
// DLog(@"toBeString===%@===%d===%lu",toBeString,stringLength,(unsigned long)toBeString.length);
// // DLog(@"stringLength===%d===%lu",stringLength,(unsigned long)toBeString.length);
// //判斷漢字還是英文
// if (stringLength>20) {
// // [MBProgressHUD showError:@"聯(lián)系人姓名為2-20個(gè)字符"];
// // return;
// if (stringLength==toBeString.length) {
// //英文
// textField.text = [toBeString substringToIndex:20];
// }else{
// //漢字
// textField.text = [toBeString substringToIndex:10];
// }
// }
}
/**
* 移除通知
*/
- (void)dealloc{
UITextField * name = [topImageView viewWithTag:1];
HAFeedbackTextView * adress = [topImageView viewWithTag:4];
[[NSNotificationCenter defaultCenter]removeObserver:self
name:@"UITextFieldTextDidChangeNotification"
object:name];
[[NSNotificationCenter defaultCenter]removeObserver:self
name:@"UITextViewTextDidChangeNotification"
object:adress];
}
后來通過查閱資料得到如下方法很好解決問題
- (void)TextFieldTextDidChange:(NSNotification*)noti{
UITextField * textField = noti.object;
NSString *toBeString = textField.text;
// NSString *lang = [[UITextInputMode currentInputMode] primaryLanguage];//廢棄方法
NSString *langstring = [[UIApplication sharedApplication]textInputMode].primaryLanguage;
if ([langstring isEqualToString:@"zh-Hans"]) { // 簡(jiǎn)體中文輸入,包括簡(jiǎn)體拼音,健體五筆,簡(jiǎn)體手寫
UITextRange *selectedRange = [textField markedTextRange];
//獲取高亮部分
UITextPosition *position = [textField positionFromPosition:selectedRange.start offset:0];
// 沒有高亮選擇的字,則對(duì)已輸入的文字進(jìn)行字?jǐn)?shù)統(tǒng)計(jì)和限制
if (!position) {
if (toBeString.length > 4) {
textField.text = [toBeString substringToIndex:4];
}
}
// 有高亮選擇的字符串,則暫不對(duì)文字進(jìn)行統(tǒng)計(jì)和限制
else{
}
}
// 中文輸入法以外的直接對(duì)其統(tǒng)計(jì)限制即可,不考慮其他語種情況
else{
if (toBeString.length > 4) {
textField.text = [toBeString substringToIndex:4];
}
}
}