11

我有一个带有全宽和全高 WKWebView 的自定义键盘。我已经禁用了滚动,wkWebView!.scrollView.scrollEnabled = false但在 WKWebView 底部双击时我仍然有一个奇怪的滚动行为。这里是我尝试加载的简单网页的源代码:http: //is.gd/gt8h2q(非常简单,只是一个带有绿色背景和一行文本的 div 全屏)。下面,一个GIF作为解释。这是我创建 WKWebView 的方式:

class KeyboardViewController: UIInputViewController, WKScriptMessageHandler {
var wkWebView: WKWebView?

override func loadView() {
    super.loadView()

    let contentController = WKUserContentController()
    contentController.addScriptMessageHandler(self, name:"callbackTestOne")

    let config = WKWebViewConfiguration()
    config.userContentController = contentController

    self.wkWebView = WKWebView(frame:self.view.frame, configuration:config)
    self.view = self.wkWebView!
}

override func viewDidLoad() {
    super.viewDidLoad()

    (...)

    wkWebView!.scrollView.bounces = false
    wkWebView!.scrollView.scrollEnabled = false
    wkWebView!.scrollView.backgroundColor = UIColor(red:248, green:248, blue:248, alpha:1)
    wkWebView!.scrollView.opaque = true
    wkWebView!.scrollView.showsHorizontalScrollIndicator = false
    wkWebView!.scrollView.showsVerticalScrollIndicator = false
    wkWebView!.scrollView.decelerationRate = UIScrollViewDecelerationRateNormal
}

(...)

GIF解说

4

5 回答 5

9

我遇到了类似的问题并找到了解决方案。也就是说,要删除对不当行为负责的 UITapGestureRecognizer。

WKWebView,或者更准确地说是 UIScrollView 及其包含在 WKWebView 中的子视图,添加了很多手势识别器。因此,您可以轻松地遍历视图中的所有识别器并删除您需要的识别器。

如果要从 webView 中删除所有单指双击识别器,则需要在滚动视图的子视图内进行搜索。您可以执行以下操作:

// iterate over all subviews of the WKWebView's scrollView
for subview in _webView.scrollView.subviews {

    // iterate over recognizers of subview
    for recognizer in subview.gestureRecognizers ?? [] {

        // check the recognizer is  a UITapGestureRecognizer
        if recognizer.isKind(of: UITapGestureRecognizer.self) {

            // cast the UIGestureRecognizer as UITapGestureRecognizer
            let tapRecognizer = recognizer as! UITapGestureRecognizer

            // check if it is a 1-finger double-tap
            if tapRecognizer.numberOfTapsRequired == 2 && tapRecognizer.numberOfTouchesRequired == 1 {

                // remove the recognizer
                subview.removeGestureRecognizer(recognizer)
            }
        }
    }
}

这应该可以解决您的问题。

于 2017-03-21T22:16:20.370 回答
5

哈克和肮脏的解决方案。但至少它有效。只需将您自己的 UITapGestureRecognizer 添加到包含 WKWebView 的视图中,并将您的 UIViewController 委托给此手势识别器。我使用了这段代码:

- (BOOL)gestureRecognizer:(UIGestureRecognizer *)gestureRecognizer shouldRecognizeSimultaneouslyWithGestureRecognizer:(UIGestureRecognizer *)otherGestureRecognizer {
    if ([[otherGestureRecognizer description] containsString:@"WKSyntheticClickTapGestureRecognizer"] && [[otherGestureRecognizer description] containsString:@"numberOfTapsRequired = 2"]) {
        [otherGestureRecognizer removeTarget:nil action:nil];
        return YES;
    }

更新 1 经过一番调查,我发现这种方法不太好。因为我们在长按菜单时遇到问题,尤其是在取消选择所选文本时。对我来说仍然存在问题 - 当菜单出现时长按一下,向左或向右轻轻滑动 - 有时 WKWebView 可能会开始滚动。下一个方法是为WKWebViewConfiguration 设置 WKSelectionGranularityCharacter -这不是很明显我必须说(Apple 你为什么要这样做?)所以它在 iOS8 上工作正常 - 没有双击,每个手势都可以正常工作。但是对于 iOS9,我们有坏消息 - http://www.openradar.me/23345435它坏了。于是继续调查。

于 2016-01-20T14:34:19.230 回答
1

与https://stackoverflow.com/a/42939172/2883860的想法相同,但更现代一点。

func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
    webView.scrollView.subviews.forEach { subview in
        subview.gestureRecognizers?.forEach { recognizer in
            if let tapRecognizer = recognizer as? UITapGestureRecognizer,
                tapRecognizer.numberOfTapsRequired == 2 && tapRecognizer.numberOfTouchesRequired == 1 {
                subview.removeGestureRecognizer(recognizer)
            }
        }
    }
}
于 2019-11-28T13:06:18.777 回答
0

这是用 Swift 4.2 编写的重构版本,只需将您的 WKWebView 作为参数传递并在 viewDidLoad 之类的地方调用该函数。

private func deleteDoubleTap(web: WKWebView) {
    for subview in web.scrollView.subviews {            
        let recognizers = subview.gestureRecognizers?.filter{$0 is UITapGestureRecognizer}
        recognizers?.forEach{recognizer in
            let tapRecognizer = recognizer as! UITapGestureRecognizer
            if tapRecognizer.numberOfTapsRequired == 2 && tapRecognizer.numberOfTouchesRequired == 1 {
                subview.removeGestureRecognizer(recognizer)
            }
        }
    }

}
于 2018-08-16T14:40:40.663 回答
-2

假设您可以控制您在其中显示的内容WKWebView,您应该为其设置正确的视口。这很可能会禁用此行为。

怎么样:

<meta id="viewport" name="viewport"
    content="width=device-width; user-scalable=false" />
于 2015-10-18T14:04:10.923 回答