有没有一种通用的方法来通知所有在 UIViewController 级别开始和移动的触摸?
Posted
技术标签:
【中文标题】有没有一种通用的方法来通知所有在 UIViewController 级别开始和移动的触摸?【英文标题】:Is there a general way to be notified of all touches began and moved at the UIViewController level? 【发布时间】:2015-01-19 18:32:46 【问题描述】:我有一个UIViewController
子类,其视图具有复杂的后代视图层次结构,包括UIButton
s 和UISlider
。我想在 5 秒后在没有任何用户交互的情况下隐藏控件。 5 秒部分很简单:使用计时器。不过,我不知道检测用户交互的一般方法。
我的第一个想法是在UIViewController
子类中覆盖UIResponder
的touchesBegan:withEvent:
和touchesMoved:withEvent:
,但是当用户点击UIButton
或拖动@ 上的旋钮时不会调用它们987654329@.
如果我能提供帮助,我不想做的是注册每个控件的通知。我也不想惹UIWindow
。还有其他想法吗?
【问题讨论】:
【参考方案1】:我最终创建了一个连续的手势识别器,它可以识别何时至少有一次触摸。我将它添加到 UIViewController 子类的视图中,效果很好!我花了很长时间才意识到它需要将 cancelsTouchesInView
和 delaysTouchesEnded
都设置为 false
否则它会以某种方式失败。
class TouchDownGestureRecognizer: UIGestureRecognizer
override init(target: AnyObject, action: Selector)
super.init(target: target, action: action)
cancelsTouchesInView = false
delaysTouchesEnded = false
override func touchesBegan(touches: NSSet!, withEvent event: UIEvent!)
state = .Began
override func touchesEnded(touches: NSSet!, withEvent event: UIEvent!)
if numberOfTouches() - touches.count == 0
state = .Ended
override func touchesCancelled(touches: NSSet!, withEvent event: UIEvent!)
if numberOfTouches() - touches.count == 0
state = .Cancelled
override func shouldBeRequiredToFailByGestureRecognizer(otherGestureRecognizer: UIGestureRecognizer!) -> Bool
return false
override func shouldRequireFailureOfGestureRecognizer(otherGestureRecognizer: UIGestureRecognizer!) -> Bool
return false
override func canPreventGestureRecognizer(preventedGestureRecognizer: UIGestureRecognizer!) -> Bool
return false
override func canBePreventedByGestureRecognizer(preventingGestureRecognizer: UIGestureRecognizer!) -> Bool
return false
【讨论】:
【参考方案2】:通过在 viewDidLoad 中调用 setupTapGesture 将 UIGestureRecognizer 添加到您的 UIViewController
- (void)setupTapGesture
UITapGestureRecognizer *tapGesture = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(toggleVisibility)];
tapGesture.delegate = self;
[self.view addGestureRecognizer:tapGesture];
然后使用此回调来检测来自按钮、滑块 (UIControl) 的触摸
- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch
//To ignore touches from Player Controls View
if ([[touch.view superview] isKindOfClass:[UIControl class]])
return NO;
return YES;
【讨论】:
谢谢,这让我走上了正确的道路。我从来没有只使用gestureRecognizer: shouldReceiveTouch:
让它工作,但是自定义手势识别器可以解决问题。【参考方案3】:
为什么不使用UIGestureRecognizer
?。您可能需要为不同的可能交互类型(例如按住和滑动)设置几个不同的交互类型,但是您可以让它们都调用相同的函数来保持屏幕打开并重置计时器。
【讨论】:
以上是关于有没有一种通用的方法来通知所有在 UIViewController 级别开始和移动的触摸?的主要内容,如果未能解决你的问题,请参考以下文章