如何仅检测短敲击

How to detect only short taps

在我的视图控制器中,我有一个 WKWebView 并且我使用 UITapGestureRecognizer 来检测网络视图上的点击,以便 show/hide 导航栏和状态栏。我还使用 taps+javascript 来检测 Web 内容的特殊部分何时被点击。

WKWebView 使用长按允许用户 select 文本。

超级长按效果很好。网页内容select按预期由 WKWebView 编辑,生活很好。

我的问题是当用户应用 "shorter" 长按时,因为 UITapGestureRecognizer 将它们识别为点击。 WKWebView select 是文本,所以看起来用户按下的时间足够长,但在释放 UITapGestureRecognizer 时会触发指定的操作,并且我的代码 show/hide 导航栏会启动。

我想要的是仅 show/hide 用户轻按一下时的导航栏。如果他们触摸足够长的时间让 WKWebView 到 select 文本,我想让 WKWebView 处理它。

我希望通过触摸持续时间来过滤点击,但我一直无法找到确定此信息的方法。

我错过了什么吗?我可以使用 UITapGestureRecognizer 实现此目的还是需要其他方法?

我的目标是 iOS 8 和 9。

如果您有权访问选择文本的 WKWebView 使用的手势识别器,则可以使用 requireGestureRecognizerToFail:.

设置短按识别器以要求 WKWebView 识别器失败

如果您无法访问 WKWebView 使用的手势识别器,那么您可以采用这种 hackier 方法:

  1. 创建一个UILongPressGestureRecognizer。这个长按识别器本身不会做任何事情,但是步骤 2 需要它。
  2. 在您的短按识别器中,使用 requireGestureRecognizerToFail:,指定第 1 步中的 UILongPressGestureRecognizer

请注意,如果 WKWebView 在后台使用 UILongPressGestureRecognizer,则第二种方法只能奏效。

对于 WKWebView,最简单的解决方案就是使用 WKNavigationDelegate 协议中的方法,并在其内部决定是否处理 url。

public func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction,
                      decisionHandler: @escaping (WKNavigationActionPolicy) -> Void) {

    if let url = navigationAction.request.url, url.scheme?.lowercased() == Constants.mailToScheme {
      UIApplication.shared.open(url, options: [:])
      decisionHandler(.cancel)
    } else {
      decisionHandler(.allow)
    }
  }

如果@melany 代码无法正常工作,请进行以下更改...

func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: ((WKNavigationActionPolicy) -> Void)) {

        switch navigationAction.navigationType {
        case .linkActivated:
            UIApplication.shared.openURL(navigationAction.request.url!)
            decisionHandler(.cancel)
            return
        default:
            break
        }
        decisionHandler(.allow)
    }