手势问题:UISwipeGestureRecognizer + UISlider

26

我遇到了一个与手势相关的问题。我使用 UISwipeGestureRecognizer 实现了左右滑动事件,这个功能正常运作。但是,我遇到的问题是在同一视图中的 UISlider 不兼容。滑动滑块的动作被误认为是左右滑动手势。

有人遇到过这个问题吗?有什么想法可以解决它吗?

非常感谢。

以下是视图控制器中包含的代码:

 - (void)viewDidLoad {

            [super viewDidLoad];

                //Setup handling of LEFT and RIGHT swipes
             UISwipeGestureRecognizer *recognizer;

                recognizer = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:@selector(handleSwipeFrom:)];
                [recognizer setDirection:(UISwipeGestureRecognizerDirectionRight)];
                [[self view] addGestureRecognizer:recognizer];
                [recognizer release];

                recognizer = [[UISwipeGestureRecognizer alloc] initWithTarget:self action:@selector(handleSwipeFrom:)];
                [recognizer setDirection:(UISwipeGestureRecognizerDirectionLeft)];
                [[self view] addGestureRecognizer:recognizer];
                [recognizer release];
        }

    -(void)handleSwipeFrom:(UISwipeGestureRecognizer *)recognizer {

      if (recognizer.direction == UISwipeGestureRecognizerDirectionRight) {
       NSLog(@"Swipe Right");
       //Do stuff
      }

      if (recognizer.direction == UISwipeGestureRecognizerDirectionLeft) {
       NSLog(@"Swipe Left");
       //Do stuff
      }
    }
3个回答

58

处理这个问题最简单的方法可能是防止手势识别器捕获到滑块的触摸事件。你可以通过将自己设置为委托对象,然后实现相关协议来实现。

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch {
    if ([touch.view isKindOfClass:[UISlider class]]) {
        // prevent recognizing touches on the slider
        return NO;
    }
    return YES;
}

如果这个方法不行的话,有可能滑动条实际上有子视图接收触摸事件,所以你可以沿着 superview 链向上移动,逐个测试每一个视图。


关键点:您可以通过将自己设置为委托并实现该委托来实现这一点,就像[panRecognizer setDelegate:self]这样-而不是UISlider(根据您的命名和类设置等)。另外,回答很棒。 - toblerpwn
不完整的答案,还有漏洞。请勿使用。 - AlexK
@AlexKornhauser 请详细说明。 - Lily Ballard
不指定如何使用委托。 - AlexK
1
@AlexKornhauser,“如何使用手势识别器委托?”不是这个问题的重点。这是文档已经回答的内容。请不要声明答案是“有缺陷”的,因为它们假定您已经了解官方文档解释的基础知识。 - Lily Ballard

3

Swift 4.0版本。 不要忘记UIGestureRecognizerDelegate。

func gestureRecognizer(_ gestureRecognizer: UIGestureRecognizer, shouldReceive touch: UITouch) -> Bool {

    if let touchedView = touch.view, touchedView.isKind(of: UISlider.self) {
        return false
    }

    return true
}

0

我在Lily回复之前解决了这个问题。这是我使用的代码,但是Lily的看起来更干净(我还没有测试Lily的代码):

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch {
    BOOL AllowSwipes = YES;

        CGPoint point1 = [touch locationInView:_sliderLeft];
        CGPoint point2 = [touch locationInView:_sliderRight];

        //Left slider test
        if ([_sliderLeft hitTest:point1 withEvent:nil] != nil) {
            AllowSwipes = NO;
            NSLog(@"On Left Slider");
        }

        //Right slider test
        if ([_sliderRight hitTest:point2 withEvent:nil] != nil) {
            AllowSwipes = NO;
            NSLog(@"On Right Slider");
        }
    }
    return AllowSwipes;
}

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接