UIView touchesEnded 事件未在第一次点击时调用,但在再次点击时调用

Posted

技术标签:

【中文标题】UIView touchesEnded 事件未在第一次点击时调用,但在再次点击时调用【英文标题】:UIView touchesEnded Event not called on first tap, but called if tap again 【发布时间】:2016-01-04 09:49:11 【问题描述】:

我有一个名为“MyView”的UIView 子类。在ControllerA 中,它有一个属性MyView *myView,并将其添加到self.view。在myView 上,有一些随机的子视图从右向左滑动,然后消失。我想要做的是,当用户点击其中一个滑动子视图时,识别该视图并推送另一个控制器。

在 MyView.m 中,我覆盖了touchesBegantouchesEndedtouchesCanceled,并在每个方法中添加了 NSLog。在touchesEnded methds 中,我使用下面的代码来识别被点击的子视图:

UITouch *touch = [touches anyObject];
CGPoint touchLoaction = [touch locationInView:self];
for (UIView *subview in self.subviews) 
    if ([subview.layer.presentationLayer hitTest:touchLoaction]) 
        if (_delegate && [_delegate respondsToSelector:@selector(canvas:didSelectView:)]) 
            [_delegate canvas:self didSelectView:subview];
        
        break;
    

我的操作步骤是:

    当我点击一个子视图时,日志是:开始,结束。然后推送到controllerB。

    当我弹回到控制器 A 并点击一个子视图时,日志是:开始、取消,并且没有推送到控制器 B,因为 touchesEnded 没有被调用。

    再次点击子视图时,日志为:开始,结束,然后推送到controllerB。

我怀疑是push的原因,所以我把touchesEnded方法中的“识别”代码注释掉了,现在,当我点击一个子视图时,日志总是:开始,结束。

所以我的问题是,为什么在第 2 步中没有调用 touchesEnded 方法?

我尝试使用performSelector:afterDelay: 来延迟推送,但没有帮助。当我弹回并点击一个子视图时,它总是touchesCancelled 方法被调用,然后我再次点击,然后touchesEnded 被调用。

谁能帮我解决这个问题?提前致谢并致以最良好的祝愿!

【问题讨论】:

【参考方案1】:

检查您是否在涉及的任何视图控制器上启用了手势识别,如果是,请将其关闭。在某些情况下,识别器倾向于取消触摸。根据您的描述,我了解到您并没有使用手势识别器。

【讨论】:

感谢您的回答,但我们发现这是因为另一个模块在此视图出现时做了一些事情。它在视图上添加了一个点击手势识别器,这就是原因。【参考方案2】:

不使用 touchesBegan、touchesEnded 和 touchesCanceled,为什么不为每个子视图设置 UIGestureRecognizers? 完成此操作后,您还可以在事件发生之前捕获事件,实现 UIGestureRecognizerDelegate 方法以获得更多粒度。

- (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;


【讨论】:

以上是关于UIView touchesEnded 事件未在第一次点击时调用,但在再次点击时调用的主要内容,如果未能解决你的问题,请参考以下文章

touchesBegin 在自定义 UITableViewCell,touchesEnded 在 UIView

UIView 动画未在值更改事件上设置动画

处理包含 UIButton 的 UIView 的触摸事件

如何从 - (void)touchesEnded:withEvent: 获取 UITouch 位置的 UIView 对象?

touchesEnded:withEvent: 没有从我的 UIView 调用,它位于 UITableView 的顶部

UIScrollview 窃取触摸事件