動畫實現解鎖-文件目錄node
效果圖
ViewController.h文件
//建立自定義的View,遵照協議,設置代理,實現代理方法
1 #import "LYPaintView.h" 2 3 #import "ViewController.h" 4 5 @interface ViewController ()<LYPaintViewDelegate> 6 7 @end 8 9 @implementation ViewController 10 11 - (void)viewDidLoad { 12 [super viewDidLoad]; 13 self.view.backgroundColor=[UIColor colorWithPatternImage:[UIImage imageNamed:@"bg"]]; 14 //加載子定的View 15 LYPaintView *paintView=[LYPaintView paintView]; 16 //設置代理 17 paintView.delegate=self; 18 19 paintView.center =self.view.center; 20 //添加View 21 [self.view addSubview:paintView]; 22 } 23 //修改狀態欄的狀態 24 -(UIStatusBarStyle)preferredStatusBarStyle{ 25 return UIStatusBarStyleLightContent; 26 } 27 //實現代理方法 28 -(BOOL)checkPwd:(LYPaintView *)paintView withPwd:(NSString *)pawd{ 29 if ([pawd isEqualToString:@"345"]) { 30 return YES; 31 } 32 return NO; 33 } 34 @end
LYPaintView.h
//文件內容,主要是建立協議,設置代理屬性
1 #import <UIKit/UIKit.h> 2 @class LYPaintView; 3 //建立協議 4 @protocol LYPaintViewDelegate <NSObject> 5 //協議的方法 6 -(BOOL)checkPwd:(LYPaintView *)paintView withPwd:(NSString *)pawd; 7 8 @end 9 10 @interface LYPaintView : UIView 11 +(instancetype)paintView; 12 @property(nonatomic,weak)id <LYPaintViewDelegate>delegate; 13 @end
LYPaintView.m
//實現解鎖數組
#import "LYPaintView.h" #define CZLineColor [UIColor colorWithRed:0.0 green:170/255.0 blue:255/255.0 alpha:0.5] @interface LYPaintView () @property(nonatomic,strong)NSMutableArray *btnsArray; @property(nonatomic,strong)UIColor *lineColor; @property(nonatomic,assign)CGPoint currentPoint; @end @implementation LYPaintView //快速建立對象類方法 +(instancetype)paintView{ return [[[NSBundle mainBundle]loadNibNamed:@"LYPaintView" owner:nil options:nil]lastObject]; } //開始觸摸事件 -(void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{ //獲取觸摸點 UITouch *touch=touches.anyObject; CGPoint point=[touch locationInView:self]; //遍歷按鈕看觸摸點是否在按鈕上 [self.subviews enumerateObjectsUsingBlock:^(__kindof UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { BOOL isContain=CGRectContainsPoint(obj.frame, point); if (isContain && obj.highlighted==NO) { obj.highlighted=YES; [self.btnsArray addObject:obj]; }else{ obj.highlighted =NO; } }]; } //觸摸移動時 -(void)touchesMoved:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event{ //獲取當前的觸摸點 UITouch *touch=touches.anyObject; CGPoint point=[touch locationInView:self]; //設置當前點 self.currentPoint=point; //遍歷按鈕看觸摸點是否在按鈕上 [self.subviews enumerateObjectsUsingBlock:^(__kindof UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { BOOL isContain=CGRectContainsPoint(obj.frame, point); if (isContain && obj.highlighted==NO) { obj.highlighted=YES; [self.btnsArray addObject:obj]; } }]; //重繪 [self setNeedsDisplay]; } //觸摸結束時 -(void)touchesEnded:(NSSet<UITouch *> *)touches withEvent:(UIEvent *)event { //消除最後的線 UIButton *lastBtn = self.btnsArray.lastObject; self.currentPoint=lastBtn.center; [self setNeedsDisplay]; //遍歷觸摸過的按鈕得到輸入的密碼 NSMutableString *password=[NSMutableString string]; [self.btnsArray enumerateObjectsUsingBlock:^(UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { NSInteger tag=obj.tag; [password appendFormat:@"%@",@(tag)]; }]; BOOL isTrue; //代理實現判斷密碼是否一致 if ([self.delegate respondsToSelector:@selector(checkPwd:withPwd:)]) { isTrue = [self.delegate checkPwd:self withPwd:password]; } if (isTrue) { NSLog(@"密碼正確"); //密碼正確時恢復按鈕的狀態 [self.btnsArray enumerateObjectsUsingBlock:^(UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { obj.highlighted=NO; }]; [self.btnsArray removeAllObjects]; [self setNeedsDisplay]; }else{ NSLog(@"密碼錯誤"); //密碼錯誤時線變爲紅色 self.userInteractionEnabled=NO; [self.btnsArray enumerateObjectsUsingBlock:^(UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { obj.highlighted=NO; obj.enabled=NO; }]; self.lineColor=[UIColor redColor]; [self setNeedsDisplay]; //延遲1秒恢復按鈕的原來狀態 dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1.0 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{ [self.btnsArray enumerateObjectsUsingBlock:^(UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { obj.enabled=YES; }]; [self.btnsArray removeAllObjects]; [self setNeedsDisplay]; self.userInteractionEnabled=YES; self.lineColor=CZLineColor; }); } } //加載按鈕 -(void)awakeFromNib{ self.lineColor=CZLineColor; for (int i=0; i<9; i++) { //建立按鈕並添加 UIButton *btn=[[UIButton alloc]init]; btn.tag=i; btn.userInteractionEnabled = NO; [btn setBackgroundImage:[UIImage imageNamed:@"gesture_node_normal"] forState:UIControlStateNormal]; [btn setBackgroundImage:[UIImage imageNamed:@"gesture_node_highlighted"] forState:UIControlStateHighlighted]; [btn setBackgroundImage:[UIImage imageNamed:@"gesture_node_error"] forState:UIControlStateDisabled]; [self addSubview:btn]; } } //設置按鈕的frame -(void)layoutSubviews{ [super layoutSubviews]; int conNum=3; CGFloat btnW=70; CGFloat btnH=70; CGFloat magin=(self.frame.size.width - conNum *btnW)/(conNum -1); [self.subviews enumerateObjectsUsingBlock:^(__kindof UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { NSInteger col=idx % conNum; NSInteger row=idx / conNum; CGFloat btnX=col *(magin + btnW); CGFloat btnY=row *(magin + btnH); obj.frame=CGRectMake(btnX, btnY, btnW, btnH); }]; } //drawRect方法繪製線條 - (void)drawRect:(CGRect)rect { //若是數組內沒有元素就不要繪製了 if (self.btnsArray.count==0) { return ; } //建立路徑 UIBezierPath *path=[UIBezierPath bezierPath]; [self.btnsArray enumerateObjectsUsingBlock:^(UIButton * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) { if (idx==0) { [path moveToPoint:obj.center]; }else{ [path addLineToPoint:obj.center]; } }]; //添加最後的線段 [path addLineToPoint:self.currentPoint]; [self.lineColor setStroke]; [path setLineWidth:10]; [path setLineCapStyle:kCGLineCapRound]; [path setLineJoinStyle:kCGLineJoinRound]; //渲染 [path stroke]; } //懶加載按鈕數組 -(NSMutableArray *)btnsArray{ if (_btnsArray==nil) { _btnsArray=[NSMutableArray array]; } return _btnsArray; } @end