欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  移动技术

iOS开发之UITextField的文本格式扩展

程序员文章站 2022-08-12 19:43:30
iOS开发之UITextField的文本格式扩展,在开发的过程中,为了使产品美观,和数据易读。我们经常会接到这样的需求,比如:在用户输入手机号码的地方自动空格,在TextField...

iOS开发之UITextField的文本格式扩展,在开发的过程中,为了使产品美观,和数据易读。我们经常会接到这样的需求,比如:在用户输入手机号码的地方自动空格,在TextField框里面自动生成手机号码的格式, 类似与这样的需求还有身份证格式和银行卡格式!

这个需求的难点在于,在输入的时候在合适的位置添加空格和在删除的时候也一并把空格删除掉!

在这里我写了一个UITextField的分类,来实现手机号;银行卡,以及身份证号码输入的时候进行格式化:

#import 

typedef NS_ENUM(NSInteger, HBTextFieldFormatType) {
    kHBTextFieldTypeFormatUnkown = 0, // 未知
    kHBTextFieldTypeFormatBankCard,   // 银行卡号格式
    kHBTextFieldTypeFormatPhoneNO,    // 手机号码格式
    kHBTextFieldTypeFormatIDNO,       // 身份证号码格式
};
@interface UITextField (Format)

@property (nonatomic, assign) HBTextFieldFormatType textFormatType;


@end

.m文件的实现:

 

 

#import "UITextField+Format.h"
#import 

static NSString *formatType = @"formatType";

@implementation UITextField (Format)
@dynamic textFormatType;

- (void)setTextFormatType:(HBTextFieldFormatType)textFormatType{
    objc_setAssociatedObject(self,&formatType,@(textFormatType),OBJC_ASSOCIATION_COPY);
    
    [self addTarget:self action:@selector(reformatAsBankNumber:) forControlEvents:UIControlEventEditingChanged];
}

- (HBTextFieldFormatType )textFormatType{
    NSString *textFormatType = (NSString *)objc_getAssociatedObject(self, &formatType);
    return [textFormatType integerValue];
}


-(void)reformatAsBankNumber:(UITextField *)textField {
    
    /**
     *  判断正确的光标位置
     */
    NSUInteger targetCursorPostion = [textField offsetFromPosition:textField.beginningOfDocument toPosition:textField.selectedTextRange.start];
    NSString *numberWithoutSpaces = [self removeNonDigits:textField.text andPreserveCursorPosition:&targetCursorPostion];
    
    NSString *numberWithSpaces;
    if(self.textFormatType == kHBTextFieldTypeFormatBankCard){
        numberWithSpaces = [self insertSpacesEveryFourDigitsIntoString:numberWithoutSpaces andPreserveCursorPosition:&targetCursorPostion];
    }else if (self.textFormatType == kHBTextFieldTypeFormatPhoneNO){
        numberWithSpaces = [self insertSpacesIntoPhoneNumberString:numberWithoutSpaces andPreserveCursorPosition:&targetCursorPostion];
    }else if (self.textFormatType == kHBTextFieldTypeFormatIDNO){
        numberWithSpaces = [self insertSpacesIntoIDNOString:numberWithoutSpaces andPreserveCursorPosition:&targetCursorPostion];
    }
    
    textField.text = numberWithSpaces;
    UITextPosition *targetPostion = [textField positionFromPosition:textField.beginningOfDocument offset:targetCursorPostion];
    [textField setSelectedTextRange:[textField textRangeFromPosition:targetPostion toPosition:targetPostion]];
}

/**
 *  除去非数字字符,确定光标正确位置
 *
 *  @param string         当前的string
 *  @param cursorPosition 光标位置
 *
 *  @return 处理过后的string
 */
- (NSString *)removeNonDigits:(NSString *)string andPreserveCursorPosition:(NSUInteger *)cursorPosition {
    NSUInteger originalCursorPosition =*cursorPosition;
    NSMutableString *digitsOnlyString = [NSMutableString new];
    
    for (NSUInteger i=0; i0)
        {
            if(i%4 == 0) {
                [stringWithAddedSpaces appendString:@" "];
                
                if(i0)
        {
            if(i == 3 || i == 7) {
                [stringWithAddedSpaces appendString:@" "];
                
                if(i0)
        {
            if(i == 6 || i == 10 || i == 14) {
                [stringWithAddedSpaces appendString:@" "];
                
                if(i

 这里需要注意的是OC的分类允许给分类添加属性,但不会自动生成getter、setter方法,所以我们必须自己实现他的getter、setter,但是要通过运行时建立关联引用! 我们这个类实现也正是利用OC的这个特征,在重写setter方法的时机给UITextField文本格式的实现提供了入口!