我有两扇窗户——前一扇,后一扇。前面的用于在后面的上面覆盖一些东西。我希望能够捕捉到前窗某些部分的触摸,而不是其他部分;我希望前窗在某些区域接收触摸,但在其他区域将它们传递到后窗。
关于我如何做到这一点的任何想法?
好的,这就是我所做的:我在前窗口中创建了两个视图。第一个视图覆盖了我想要捕捉的区域;第二个,我希望触摸通过的地方。我将 UIWindow 子类化并覆盖了 hitTest:withEvent 方法,如下所示:
- (UIView *) hitTest:(CGPoint)point withEvent:(UIEvent *)event {
// See if the hit is anywhere in our view hierarchy
UIView *hitTestResult = [super hitTest:point withEvent:event];
// ABKSlideupHostOverlay view covers the pass-through touch area. It's recognized
// by class, here, because the window doesn't have a pointer to the actual view object.
if ([hitTestResult isKindOfClass:[ABKSlideupHostOverlayView class]]) {
// Returning nil means this window's hierachy doesn't handle this event. Consequently,
// the event will be passed to the host window.
return nil;
}
return hitTestResult;
}
在创建前窗口的类中,我使用手势识别器来捕捉对第一个视图的触摸。
与 2017 年代码相同:
class PassView: UIView {}
class UIHigherWindow: UIWindow {
override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {
let hitView = super.hitTest(point, with: event)
if hitView!.isKind(of: PassView.self) {
return nil
}
return hitView
}
}
您的“uber”窗口将是一些视图控制器,UberVc。
只需将UberVc的主视图(即简单的背景.view)设为PassView即可。
然后在 UberVc 上添加说按钮等。
上面的代码会导致对按钮的任何点击进入 UberVc,而对按钮以外的任何点击(即在“背景”上)都会进入您的常规窗口/VC。
我有一个类似的问题:额外的 UIWindow 应该有一个透明的视图和一些棘手的子视图。必须通过这些棘手视图之外的所有触摸。
我最终使用了 Anna 代码的修改版本,它使用视图的标签而不是类型检查。这种方式不需要创建视图子类:
class PassTroughWindow: UIWindow {
var passTroughTag: Int?
override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {
let hitView = super.hitTest(point, with: event)
if let passTroughTag = passTroughTag {
if passTroughTag == hitView?.tag {
return nil
}
}
return hitView
}
}
假设您创建了一个窗口和根视图控制器,您可以像这样使用它:
let window: PassTroughWindow
//Create or obtain window
let passTroughTag = 42
window.rootViewController.view.tag = passTroughTag
window.passTroughTag = passTroughTag
//Or with a view:
let untouchableView: UIView // Create it
untouchableView.tag = passTroughTag
window.addSubview(untouchableView)
不要使用多个 UIWindows,而是使用 获取关键窗口[[UIApplication sharedApplication] keyWindow]
,然后将视图添加到其中:
mainWindow = [[UIApplication sharedApplication] keyWindow];
[mainWindow addSubview:view]