WKWebView - ngăn cuộn tự động được kích hoạt bởi lựa chọn văn bản của người dùng


8

Khi người dùng thực hiện thao tác chạm và giữ để chọn một từ và sau đó kéo ngón tay của họ về phía cạnh trên hoặc dưới của màn hình, trang sẽ tự động cuộn để phù hợp với lựa chọn.

đây là một đoạn phim ngắn chứng minh điều đó

Tôi muốn ngăn chặn hành vi này trong a WKWebView.

Đây là những gì tôi đã cố gắng cho đến nay:

trong một bridge.jstệp có thể truy cập vào webview:

var shouldAllowScrolling = true;

document.addEventListener('selectionchange', e => {
    shouldAllowScrolling = getSelectedText().length === 0;
    window.webkit.messageHandlers.selectionChangeHandler.postMessage(
        {
            shouldAllowScrolling: shouldAllowScrolling
        });
    console.log('allow scrolling = ', shouldAllowScrolling);
});

và sau đó trong một WKScriptMessageHandlerthực hiện:

public func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage)
    {
        switch message.name
        {
        case "selectionChangeHandler":
            let params = paramsDictionary(fromMessageBody: message.body)
            let shouldEnableScrolling = params["shouldAllowScrolling"] as? Bool ?? true
            cell?.webView.scrollView.isScrollEnabled = shouldEnableScrolling
            cell?.webView.scrollView.isUserInteractionEnabled = shouldEnableScrolling // not together with the line above 
        default:
            fatalError("\(#function): received undefined message handler name: \(message.name)")
        }
    }

Tương tự, tôi đã thử gọi preventDefault()hàm trực tiếp trong tệp javascript cho một loạt các sự kiện, cụ thể là scrolltouchmovenhư vậy:

document.addEventListener('touchmove', e => {
    if (!shouldAllowScrolling) {
        e.preventDefault()
    }
}, {passive: false});

cả hai phương pháp đều ngăn cuộn thành công khi một số văn bản được chọn nhưng không ghi đè hành vi được mô tả ở đầu câu hỏi của tôi.

Tôi có thể chấp nhận các giải pháp trong cả Swift và JavaScript hoặc kết hợp cả hai.

Câu trả lời:


5

Cuối cùng tôi đã giải quyết vấn đề này bằng cách lưu vị trí cuộn cuối cùng và cuộn đến nó khi thích hợp, như vậy:

var shouldAllowScrolling = true;
var lastSavedScrollLeft = 0;
var lastSavedScrollTop = 0;

function saveScrollPosition() {
    lastSavedScrollLeft = window.pageXOffset || document.documentElement.scrollLeft;
    lastSavedScrollTop = window.pageYOffset || document.documentElement.scrollTop;
}

document.addEventListener('touchstart', e => {
    saveScrollPosition();
});

document.addEventListener('touchend', () => {
    // enable scrolling when the user lifts their finger, to allow scrolling while text selection is still present
    shouldAllowScrolling = true;
});

document.addEventListener('scroll', e => {
    if (!shouldAllowScrolling) {
        window.scrollTo(lastSavedScrollLeft, lastSavedScrollTop);
    }
});

document.addEventListener('selectionchange', e => {
    shouldAllowScrolling = getSelectedText().length === 0;
});

Nếu ai đó có thể cung cấp một giải pháp thanh lịch hơn để ngăn chặn việc cuộn hoàn toàn không vui lòng chấp nhận nó.

BIÊN TẬP:

giải pháp này có thể gây ra rung lắc / jitter nhẹ.

điều đó có thể được giải quyết bằng cách thực hiện cuộn cuộn tự nhiên thông qua việc WKWebViewgọi ngược lại với window.scrollTo()javascript.

Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.