我认为当触摸或点击视图时,首先调用其处理程序,然后调用其superview的处理程序(向上传播)。
但是如果superview的userInteractionEnabled
设置为NO,那么所有子视图和后代也会因用户交互而被禁用吗?如果我们只想禁用主视图但又不想禁用子视图,该怎么办?
答案 0 :(得分:23)
如果这可能会有所帮助,我在Matt Neuburg编程的iOS 5中发现了这一点。 467:
userInteractionEnabled
如果设置为NO,则从中排除此视图(及其子视图) 接受接触。触及此视图或其中一个子视图“堕落 通过“对它背后的观点。”
此外,Apple的iOS事件处理指南说:
窗口对象使用命中测试和响应者链来查找 查看接收触摸事件。在命中测试中,窗口调用 hitTest:withEvent:在视图层次结构的最顶层视图上;这个 方法通过递归调用pointInside:withEvent:on each 视图层次结构中的视图返回YES,继续向下 层次结构,直到找到触摸范围内的子视图 发生。该视图成为热门测试视图。
和编程iOS 5由Matt Neuburg编写,第485页提到如果视图被标记为userInteractionEnabled
为NO
,或hidden
标记为YES
,或者不透明度已接近为0,那么HitTest
将不会遍历视图及其子视图(因此不会考虑任何触摸)。
答案 1 :(得分:19)
您可以覆盖hitTest(_:withEvent:)
以忽略视图本身,但仍会对其子视图进行触摸。
class ContainerStackView : UIStackView {
override func hitTest(point: CGPoint, withEvent event: UIEvent?) -> UIView? {
let result = super.hitTest(point, withEvent: event)
if result == self { return nil }
return result
}
}
答案 2 :(得分:15)
你不能这样做,
相反,您可以更改视图的布局,如下所示:
Main View-> subViews
要
Container View -> Main View that you want to set as inactive
-> other views that you want to still active
因此,您当前的主视图和当前的子视图将成为兄弟姐妹,新容器视图的子视图
答案 3 :(得分:1)
第一种方法
- (BOOL) gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldReceiveTouch:(UITouch *)touch
{
if ([touch.view.superview isKindOfClass:[SuperViewParent class]]) return FALSE;
return TRUE;
}
第二种方法
UITapGestureRecognizer *r = [[UITapGestureRecognizer alloc] initWithTarget:self action:@selector(agentPickerTapped:)];
r.cancelsTouchesInView = NO;
[agentPicker addGestureRecognizer:r];