我正在努力从手势识别器中获取我想要的行为,特别是如果其他人已经被解雇则取消某些手势。
我有一个scrollView设置为分页和每个页面中的多个子视图。如果用户点击页面的右侧或左侧,我已添加了触摸手势识别器以滚动到下一页或上一页。
// Add a gesture recogniser turn pages on a single tap at the edge of a page
UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(tapGestureHandler:)];
tapGesture.cancelsTouchesInView = NO;
[self addGestureRecognizer:tapGesture];
[tapGesture release];
和我的手势处理程序:
- (void) tapGestureHandler:(UIGestureRecognizer *) gestureRecognizer {
const CGFloat kTapMargin = 180;
// Get the position of the point tapped in the window co-ordinate system
CGPoint tapPoint = [gestureRecognizer locationInView:nil];
// If the tap point is to the left of the page then go back a page
if (tapPoint.x > (self.frame.size.width - kTapMargin)) [self scrollRectToVisible:pageViewRightFrame animated:YES];
// If the tap point is to the right of the page then go forward a page
else if (tapPoint.x < kTapMargin) [self scrollRectToVisible:pageViewLeftFrame animated:YES];
}
一切正常,除非我在页面上有子视图,其中有按钮。如果用户触摸subView上的按钮,我希望能够忽略点击以翻页,我无法弄清楚如何执行此操作。
干杯
戴夫
答案 0 :(得分:19)
最终对我有用的解决方案是使用hitTest来确定点按手势位置下方是否有任何按钮。如果有,那么只需忽略其余的手势代码。
似乎运作良好。想知道我所做的事情是否有任何问题。
- (void) tapGestureHandler:(UIGestureRecognizer *) gestureRecognizer {
const CGFloat kTapMargin = 180;
// Get the position of the point tapped in the window co-ordinate system
CGPoint tapPoint = [gestureRecognizer locationInView:nil];
// If there are no buttons beneath this tap then move to the next page if near the page edge
UIView *viewAtBottomOfHeirachy = [self.window hitTest:tapPoint withEvent:nil];
if (![viewAtBottomOfHeirachy isKindOfClass:[UIButton class]]) {
// If the tap point is to the left of the page then go back a page
if (tapPoint.x > (self.bounds.size.width - kTapMargin)) [self scrollRectToVisible:pageViewRightFrame animated:YES];
// If the tap point is to the right of the page then go forward a page
else if (tapPoint.x < kTapMargin) [self scrollRectToVisible:pageViewLeftFrame animated:YES];
}
}
答案 1 :(得分:12)
Apple documentation显示答案:
- (void)viewDidLoad {
[super viewDidLoad];
// Add the delegate to the tap gesture recognizer
self.tapGestureRecognizer.delegate = self;
}
// Implement the UIGestureRecognizerDelegate method
-(BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch: (UITouch *)touch {
// Determine if the touch is inside the custom subview
if ([touch view] == self.customSubview){
// If it is, prevent all of the delegate's gesture recognizers
// from receiving the touch
return NO;
}
return YES;
}
当然在这种情况下,customSubview将是包含按钮的页面上的子视图(甚至是其上的按钮)
答案 2 :(得分:1)
Swift 3
设置 UITapGestureRecognizer
let tap = UITapGestureRecognizer(target: self, action: #selector(Class.didTap))
tap.delegate = self
UITapGestureRecognizer 委托方法:
func gestureRecognizer(_ gestureRecognizer: UIGestureRecognizer, shouldReceive touch: UITouch) -> Bool {
return touch.view != buttonThatShouldCancelTapGesture
}
答案 3 :(得分:0)
您可以继承UIView并覆盖-touchesBegan
选择器,或者您可以使用子视图的opaque
属性来使它们对触摸“不可见”(如果view.opaque = NO,则视图忽略触摸事件)。