触摸
响应者对象
在iOS中不是任何对象都能处理事件,只有继承了UIResponder的对象才能接收并处理事件.我们称之为"响应者对象".
UIApplication,UIViewController,UIView都继承自UIResponder,因此它们都是响应者对象,都能够接收并处理事件.
UIView??????不接受触摸时间的三种情况??????????????????
- • ????不接受用户交互????????????userInteractionEnable = NO;??(例如:UILabel与UIImageView????这些控件userInteractionEnable默认为??????NO因此这些控件默认是不能接受触摸事件的)
- • ??隐藏:??hidden=YES;
- • 透明:????alpha=0.0~0.01
????响应触摸的方法,可以通过UIResponder如下的四个方法来实现
• -(void)touchesBegan:(NSSet *)touches withEvent:(UIEvent *)event;????????????????
//当用户开始触摸时触发该方法
• -(void)touchesMoved:(NSSet *)touches withEvent:(UIEvent *)event;????????????????????//当用户手指开始移动时触发该方法
• -(void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event;??????????//当用户触摸结束时触发该方法
• -(void)touchesCancelled:(NSSet *)touches withEvent:(UIEvent*)event;??????????????????????????????//当系统事件(比如内存不足,电话呼入)终止了触摸事件时激发该方法
//当用户开始触摸时触发该方法 - (void)touchesBegan:(NSSet<UITouch *> *)touches withEvent:(nullable UIEvent *)event { NSArray *touchArr = [touches allObjects];//获取用户开始触摸时手指的数量 UITouch *touch = [touchArr objectAtIndex:0]; CGPoint point = [touch locationInView:[touch view]]; //获取开始触摸时手指的位置 // NSLog(@"%d",touch.tapCount);//获取手指短时间内点击的次数 if (touch.tapCount == 1) { [self performSelector:@selector(tapOne) withObject:nil afterDelay:0.5]; //延迟0.5秒调用方法tapOne } if (touch.tapCount == 2) { //如果用户要只是响应双击,销毁延迟调用 [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(tapOne) object:nil]; } } -(void)tapOne { NSLog(@"点击一次"); } //当用户手指开始移动时触发该方法 - (void)touchesMoved:(NSSet<UITouch *> *)touches withEvent:(nullable UIEvent *)event { NSLog(@"手指移动"); } //当用户触摸结束时触发该方法 - (void)touchesEnded:(NSSet<UITouch *> *)touches withEvent:(nullable UIEvent *)event { NSLog(@"触摸手势结束"); } //当系统事件(比如内存不足,电话呼入)终止了触摸事件时激发该方法 - (void)touchesCancelled:(nullable NSSet<UITouch *> *)touches withEvent:(nullable UIEvent *)event { }
手势
UITapGestureRecognizer 点击
label = [[UILabel alloc]initWithFrame:CGRectMake(self.view.bounds.size.width/2-50, self.view.bounds.size.height/2-50, 100, 100)]; label.backgroundColor = [UIColor greenColor]; label.userInteractionEnabled = YES; [self.view addSubview:label]; UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc]initWithTarget:self action:@selector(tapGestureHandle:)]; tapGesture.numberOfTapsRequired = 1; //需要点击的次数 tapGesture.numberOfTouchesRequired = 1; //需要1根手指点击 [label addGestureRecognizer:tapGesture];
-(void)tapGestureHandle:(UITapGestureRecognizer *)gesture { NSLog(@"点击触发"); CGPoint point = [gesture locationInView:self.view]; //获取点击坐标 // }
UIPinchGestureRecognizer 捏合
UIPinchGestureRecognizer *pinchGesture = [[UIPinchGestureRecognizer alloc]initWithTarget:self action:@selector(pinchGestureHandle:)]; label.multipleTouchEnabled = YES; //允许支持多点触摸 [label addGestureRecognizer:pinchGesture];
-(void)pinchGestureHandle:(UIPinchGestureRecognizer *)gesture { CGFloat scale = gesture.scale; //获取用户捏合比例 CGFloat velocity = gesture.velocity; //获取用户捏合速度 label.transform = CGAffineTransformScale(label.transform, scale, scale); gesture.scale = 1.0; }
UIPanGestureRecognizer 拖拽
UIPanGestureRecognizer *panGesture = [[UIPanGestureRecognizer alloc]initWithTarget:self action:@selector(panGestureHandle:)]; panGesture.maximumNumberOfTouches = 1; //允许该收拾处理器最多支持几个手指拖动 panGesture.minimumNumberOfTouches = 1;//允许该收拾处理器最少支持几个手指拖动 [label addGestureRecognizer:panGesture];
-(void)panGestureHandle:(UIPanGestureRecognizer *)gesture { CGPoint point = [gesture translationInView:label]; // 获取控件位移 label.transform = CGAffineTransformTranslate(label.transform, point.x, point.y); [gesture setTranslation:CGPointMake(0, 0) inView:label]; }
UISwipeGestureRecognizer 轻扫
由于一个控件指甲一次轻扫手势只支持一个方向上的轻扫,如果需要四个方向上的轻扫手势,需要加四次
for (int i = 0; i < 4; i ++) { UISwipeGestureRecognizer *swipGesture = [[UISwipeGestureRecognizer alloc]initWithTarget:self action:@selector(swipGestureHandle:)]; swipGesture.numberOfTouchesRequired = 1; swipGesture.direction = 1 << i; [label addGestureRecognizer:swipGesture]; }
-(void)swipGestureHandle:(UISwipeGestureRecognizer *)gesture { if (gesture.direction == UISwipeGestureRecognizerDirectionRight) { NSLog(@"向右轻扫"); } if (gesture.direction == UISwipeGestureRecognizerDirectionLeft) { NSLog(@"向左轻扫"); } if (gesture.direction == UISwipeGestureRecognizerDirectionDown) { NSLog(@"向下轻扫"); } if (gesture.direction == UISwipeGestureRecognizerDirectionUp) { NSLog(@"向上轻扫"); } }
UILongPressGestureRecognizer 长按
UILongPressGestureRecognizer *longPress=[[UILongPressGestureRecognizer alloc]initWithTarget:self action:@selector(handleLongPress:)]; longPress.minimumPressDuration=1; //至少按下多少秒会触发手势 longPress.allowableMovement=1; //允许手指移动的最大距离 longPress.numberOfTouchesRequired=1; //允许用户用几根手指触发该手势 [_viewText addGestureRecognizer:longPress];
使用长按手势来显示自定义菜单项
UIMenuItem *transmItem = [[UIMenuItem alloc]initWithTitle:@"转发" action:@selector(transmItem:)]; UIMenuItem *deleteItem = [[UIMenuItem alloc]initWithTitle:@"删除" action:@selector(deleteItem:)]; UIMenuItem *reportItem = [[UIMenuItem alloc]initWithTitle:@"举报" action:@selector(reportItem:)];
-(void)handleLongPress:(UILongPressGestureRecognizer *)gesture { if (gesture.state == UIGestureRecognizerStateBegan) { NSLog(@"长按手势"); [self becomeFirstResponder]; UIMenuController *menu=[UIMenuController sharedMenuController]; [email protected][transmItem,deleteItem,reportItem]; CGRect rect=CGRectMake(10, 10, 100, 50); [menu setTargetRect:rect inView:_viewText]; [menu setMenuVisible:YES animated:YES]; } } -(BOOL)canBecomeFirstResponder { return YES; } -(BOOL)canPerformAction:(SEL)action withSender:(id)sender { if (action == @selector(transmItem:)||action == @selector(deleteItem:)||action == @selector(reportItem:)) {return YES;}else{ return NO;} }
-(void)transmItem:(id)sender { NSLog(@"转发"); } -(void)deleteItem:(id)sender { NSLog(@"删除"); } -(void)reportItem:(id)sender { NSLog(@"转发"); }
如果要是控件同时支持两个手势,需要导入
- #import <UIKit/UIGestureRecognizerSubclass.h>
并且,重写两个方法
//是否阻止另一个手势 -(BOOL)canBePreventedByGestureRecognizer:(UIGestureRecognizer *)geature{ return NO; } -(BOOL)canPreventGestureRecognizer:(UIGestureRecognizer *)preventedGestureRecognizer { return NO; }