iOS 常规

监听手势滑动距离

2019-12-04  本文已影响0人  乐视薯片

这几天一直在纠结怎么监听滑动手势,获得滑动的距离,但是就是没有一篇文章解决我的问题,自己摸索了好久,才知道怎么搞,这么有纪念意义,一定要记录一下。

我写的SDK,需要监听用户滑动屏幕的距离,如果重写touchesBegan这一类方法,有两大缺点:一、如果客户的app里有重写这些方法,则会冲突;二、如果用户手势点击到了响应优先级高的地方(比如按钮),则不会执行这些方法,达不到我们想要的效果。因此,只能拦截系统方法sendEvent了,也就是苹果所谓的黑魔法。

那么这样,又怎么获得滑动的长度呢?

拦截方法就可以获得UIEvent对象,从而得到触摸事件UItouch对象,UITouch对象有个phase属性,这个属性有四个取值:UITouchPhaseBegan、UITouchPhaseMoved、UITouchPhaseStationary、UITouchPhaseEnded、UITouchPhaseCancelled。其中的began、moved、ended就可以实现我们想要的结果了。

拦截到系统的sendEvent,先执行我们的事件处理方法,然后执行系统的方法,还是上代码吧!!!

staticfloatswipeLength =0;

staticCGPointprePoint;

@implementationWindowHook

+ (instancetype)sharedWindowHook

{

    staticWindowHook*windowHook =nil;

    staticdispatch_once_tpredicate;

    dispatch_once(&predicate, ^{

    windowHook = [[selfalloc]init];

});

returnwindowHook;

}

+ (void)initialize

{

     Method sendEvent=class_getInstanceMethod([UIWindowclass],@selector(sendEvent:));

     Method sendEventMySelf=class_getInstanceMethod([selfclass],@selector(sendEventHooked:));

     IMPsendEventImp =method_getImplementation(sendEvent);

     class_addMethod([UIWindowclass],@selector(sendEventOriginal:), sendEventImp,method_getTypeEncoding(sendEvent));

     IMPsendEventMySelfImp =method_getImplementation(sendEventMySelf);

     class_replaceMethod([UIWindowclass],@selector(sendEvent:), sendEventMySelfImp,method_getTypeEncoding(sendEvent));

}

对事件怎么处理呢,看下面:

- (void)sendEventHooked:(UIEvent*)event

{

      [selfperformSelector:@selector(sendEventOriginal:)withObject:event];

      NSSet*touches = [eventallTouches];

      UITouch*touch = [touchesanyObject];

      UITouchPhasephase = touch.phase;

      UIWindow*keyWindow = [[UIApplicationsharedApplication]keyWindow];

      CGPointcurrentPoint = [touchlocationInView:keyWindow];

      NSLog(@"(%f,%f)",currentPoint.x,currentPoint.y);

      switch(phase) {

          caseUITouchPhaseBegan:

          {

               prePoint= currentPoint;

          }

          break;

          caseUITouchPhaseMoved:

          {

               floatdistance =fabs(currentPoint.y-prePoint.y);

               swipeLength=swipeLength+distance;

               prePoint= currentPoint;

          }

          break;

          caseUITouchPhaseEnded:

          {

                NSLog(@"%f",swipeLength);

                swipeLength=0;

          }

           break;

          default:

           break;

     }

}

我理解的还是比较浅显,有错的地方,还请大家指出来啊!!!

上一篇下一篇

猜你喜欢

热点阅读