将触摸事件传递给 iOS 状态栏

Posted

技术标签:

【中文标题】将触摸事件传递给 iOS 状态栏【英文标题】:Passing touch events to iOS status bar 【发布时间】:2011-03-27 10:22:04 【问题描述】:

我有一个 UIWindow,其 windowLevel 设置为 UIWindowLevelStatusBar+1。此窗口有一个半透明的视图,可以阻止状态栏。我有时需要将触摸事件从视图传递到状态栏。有什么想法吗?

【问题讨论】:

我想知道 VoiceOver 将如何告诉时间、信号和电池电量。我认识一个 VoiceOver 用户,他不能使用大约 70% 的应用程序,因为它们是由不关心用户的懒惰开发人员编写的。 :// 这没问题,视图是半透明的,大部分时间应该接收事件。这就是问题所在。 @ssteinberg 当 VoiceOver 被启用时,双击就是轻击,单击选择某物并说出它。如果您的视图与状态栏重叠,则不会在其上选择任何项目。 再次,这就是我的问题所在,大多数时候我希望将触摸事件传递到状态栏,好像什么都没有。有时我需要拦截它们。仅隐藏视图不是一种选择。 您的应用可能会因阻止/覆盖状态栏而被拒绝进入 App Store。 【参考方案1】:

因此,似乎可以使用覆盖 hitTest:withEvent: 的 UIWindow 的自定义子类来手动检测子视图中的触摸,并始终返回 nil。

- (UIView*)hitTest:(CGPoint)point withEvent:(UIEvent *)event 
    if ([event type]==UIEventTypeTouches) 
        UIView *v=[super hitTest:point withEvent:event];
        if (customSubViewthatCoversStatusBarOnly==v) 
            //doLotsOfCoolStuff
    

    return nil;

状态栏识别所有触摸,因此滚动到顶部、返回通话、VoiceOver 等不会中断。我仍然可以拦截状态栏上的点击。

我刚刚破解了这个。我可能会在本周晚些时候将更新上传到 App Store,其中包含更成熟的版本,看看苹果会做多少抱怨。

编辑 - 4 月 7 日: 获得了苹果的认可。完美运行。

【讨论】:

【参考方案2】:

您可能会在github 上发现此组件很有帮助。

否则,Cocoa with Love 的博文也许真的很有用。

【讨论】:

谢谢。 Cocoa 帖子已经过时,拦截触摸很简单。拦截并传递到状态栏是问题所在。这个 MTStatusBar,看起来很有趣,但它会主动阻止状态栏,这看起来不像 Apple 喜欢的东西。 当然。如果您追求 Reeder 应用程序所具有的那种行为,在更新期间它只覆盖状态栏的一小部分,那么这个 MTStatusBar 可能是编码的开始?【参考方案3】:

据我了解,您应该使用- (UIView *)hitTest:(CGPoint)point withEvent:(UIEvent *)event 来实现该行为。基本上,如果想要处理触摸事件,你要么返回 self,要么返回 [super hitTest:point withEvent:event] 让状态栏处理触摸事件。

查看UIView Class Reference 了解更多信息。

编辑:正如乔纳森所说,Apple 可能不会批准这一点。

【讨论】:

不,我很确定我昨天尝试过,返回 [super hitTest:point withEvent:event] 并没有这样做。

以上是关于将触摸事件传递给 iOS 状态栏的主要内容,如果未能解决你的问题,请参考以下文章

将触摸事件传递给多个选项之一

将触摸事件传递给 UICollectionViewCell 内容?

如何在 iPad 应用程序隐藏状态栏区域中获取触摸事件?

将触摸事件传递给父视图

仅当触摸类型为手指时,如何将触摸事件传递给其他视图?

iOS-事件处理