美文网首页iOS学习笔记iOS DeveloperiOS开发
实现跟微信、支付宝一样输入支付密码

实现跟微信、支付宝一样输入支付密码

作者: 搬运工开发者 | 来源:发表于2017-05-27 17:39 被阅读343次

    最近的项目中需要实现类似微信和支付宝的输入密码一样的功能,自己查看了以下资料,思路大致如下:
    1、让需要键盘的responder成为第一响应者
    2、使用UIKeyInput协议使自定义的view具备输入的功能
    3、通过CoreGraphics框架绘制出密码输入框的外框和里面的小黑点

    UIKeyInput协议需要实现的3个方法

    #if UIKIT_DEFINE_AS_PROPERTIES
    @property(nonatomic, readonly) BOOL hasText;
    #else
    - (BOOL)hasText;
    #endif
    - (void)insertText:(NSString *)text;
    - (void)deleteBackward
    

    效果图

    1.gif

    新建需要显示密码的view KKPassWordView
    KKPassWordView.h

    @class KKPassWordView;
    
    @protocol KKPassWordViewDelegate <NSObject>
    /** 监听改变 */
    - (void)passWordView:(KKPassWordView *)passWordView didChange:(NSString *)password;
    /** 监听输入完成 */
    - (void)passWordView:(KKPassWordView *)passWordView endEditing:(NSString *)password;
    /** 监听开始输入 */
    - (void)passWordBeginEditing:(KKPassWordView *)passWordView;
    
    @end
    
    @interface KKPassWordView : UIView
    - (void)setNum:(CGFloat)num pointColor:(UIColor *)pointColor pointSize:(CGFloat)pointSize delegate:(id<KKPassWordViewDelegate>)delgate;
    @property (nonatomic, weak) id<KKPassWordViewDelegate> delegate;
    @end
    

    需要创建的属性

    @interface KKPassWordView()<UIKeyInput>
    /** 用于存储文本 */
    @property (copy, nonatomic) NSMutableString *text;
    /** 文本长度 */
    @property (assign, nonatomic) NSInteger num;
    /** 方框大小 */
    @property (assign, nonatomic) CGFloat squareWidth;
    /** 远点颜色 */
    @property (strong, nonatomic) UIColor *pointColor;
    @property (assign, nonatomic) CGFloat pointSize;
    @end
    

    让KKPassWordView成为第一响应者,并设置键盘类型

    /** 成为第一响应者 */
    - (BOOL)canBecomeFirstResponder {
        
        return YES;
    }
    /** 键盘类型 */
    - (UIKeyboardType)keyboardType {
        return UIKeyboardTypeNumberPad;
    }
    

    UIKeyInput 需要实现的协议,每次调用[self setNeedsDisplay]会自动调用drawRect()方法,通过drawRect方法绘制小黑点,边框等。

    /** 用于显示的文本对象是否有任何文本 */
    - (BOOL)hasText {
       return self.text.length > 0;
    }
    
    /** 插入文本 */
    - (void)insertText:(NSString *)text {
       if (self.text.length <= _num) {
           //判断是不是数字
           NSCharacterSet *cs = [[NSCharacterSet characterSetWithCharactersInString:MONEYNUMBERS] invertedSet];
           NSString *filtered = [[text componentsSeparatedByCharactersInSet:cs] componentsJoinedByString:@""];
           BOOL basicTest = [text isEqualToString:filtered];
           if (basicTest) {
               [self.text appendString:text];
               if (_delegate && [_delegate respondsToSelector:@selector(passWordView:didChange:)]) {
                   [_delegate passWordView:self didChange:self.text];
               }
               
               if (self.text.length == self.num) {
                   if ([self.delegate respondsToSelector:@selector(passWordView:endEditing:)]) {
                       [_delegate passWordView:self endEditing:self.text];
                   }
               }
               
               [self setNeedsDisplay];
           }
       }
    }
    /** 删除字符串 */
    - (void)deleteBackward{
       if (self.text.length > 0) {
           [self.text deleteCharactersInRange:NSMakeRange(self.text.length - 1, 1)];
           if (_delegate && [_delegate respondsToSelector:@selector(passWordView:didChange:)]) {
               [_delegate passWordView:self didChange:self.text];
           }
       }
       [self setNeedsDisplay];
    }
    

    drawRect

    /** 绘制 */
    - (void)drawRect:(CGRect)rect {
        CGFloat height = rect.size.height;
        CGFloat width = rect.size.width;
        CGFloat x = (width - self.squareWidth*self.num)/2.0;
        CGFloat y = (height - self.squareWidth)/2.0;
        
        CGContextRef context = UIGraphicsGetCurrentContext();
    
        CGContextAddRect(context, CGRectMake( x, y, self.squareWidth*self.num, self.squareWidth));
        CGContextSetLineWidth(context, 1);
        CGContextSetStrokeColorWithColor(context, [UIColor grayColor].CGColor);
        CGContextSetFillColorWithColor(context, [UIColor whiteColor].CGColor);
        //画竖条
        for (int i = 1; i <= self.num; i++) {
            CGContextMoveToPoint(context, x+i*self.squareWidth, y);
            CGContextAddLineToPoint(context, x+i*self.squareWidth, y+self.squareWidth);
            CGContextClosePath(context);
        }
        CGContextDrawPath(context, kCGPathFillStroke);
        CGContextSetFillColorWithColor(context, self.pointColor.CGColor);
        //画黑点
        for (int i = 1; i <= self.text.length; i++) {
            CGContextAddArc(context, x+i*self.squareWidth - self.squareWidth/2.0, y+self.squareWidth/2, self.pointSize, 0, M_PI*2, YES);
            CGContextDrawPath(context, kCGPathFill);
        }
    }
    

    初始化

    - (void)setNum:(CGFloat)num pointColor:(UIColor *)pointColor pointSize:(CGFloat)pointSize delegate:(id<KKPassWordViewDelegate>)delgate {
        self.num = num;
        self.pointColor = [UIColor blackColor];
        self.pointSize = pointSize;
        self.delegate = delgate;
        self.squareWidth = CGRectGetWidth(self.frame)*1.0 / num;
        [self setNeedsDisplay];
    }
    - (NSMutableString *)text {
        if (_text == nil) {
            _text = [NSMutableString string];
        }
        return _text;
    }
    

    demo:http://code.cocoachina.com/view/135154

    相关文章

      网友评论

        本文标题:实现跟微信、支付宝一样输入支付密码

        本文链接:https://www.haomeiwen.com/subject/brqxfxtx.html