Nút cuộn trên nhấp vào ScrollView / WKWebView, Swift
Tôi đang làm việc trên SwiftUI, nhưng vì không có WKWebView nên tôi đã tạo nó thông qua UIViewRepresentable.
Đây là một số mã:
func makeUIView(context: Context) -> WKWebView {
let jsScript = "var meta = document.createElement('meta'); meta.setAttribute('name', 'viewport'); meta.setAttribute('content', 'width=device-width'); document.getElementsByTagName('head')[0].appendChild(meta);"
let userScript = WKUserScript(source: jsScript, injectionTime: .atDocumentEnd, forMainFrameOnly: true)
let wkController = WKUserContentController()
wkController.addUserScript(userScript)
let wkWebConfiguration = WKWebViewConfiguration()
wkWebConfiguration.userContentController = wkController
let webView = WKWebView(frame: .null, configuration: wkWebConfiguration)
webView.translatesAutoresizingMaskIntoConstraints = false
webView.loadHTMLString(htmlBody, baseURL: nil)
return webView
}
func updateUIView(_ uiView: WKWebView, context: Context) {
if let htmlBody = self.htmlBody {
uiView.loadHTMLString(htmlBody, baseURL: nil)
}
}
func makeCoordinator() -> Coordinator {
Coordinator(self)
}
Những gì tôi cần làm là cuộn xuống dưới cùng của nó khi nhấp vào nút.
Vì vậy, trong Chế độ xem SwiftUI của tôi, tôi có var @State và tôi chuyển nó vào UIViewRepresentable của mình.
Đây là những gì tôi đã thử (bên trong bản cập nhậtUIView của tôi):
if scrollWebView {
let scrollPoint = CGPoint(x: 0, y: yourWebView.scrollView.contentSize.height - webView.frame.size.height)
webView.scrollView.setContentOffset(scrollPoint, animated: true)
}
Nhưng mã này (khi nhấp vào nút) cuộn lên đầu WkWebView của tôi. Ngay cả khi tôi thay đổi dấu hiệu của y. Nó luôn cuộn lên trên cùng thay vì dưới cùng.
Tôi không nghĩ mình có thể đạt được điều này trong Chế độ xem SwiftUI của mình và tôi không thể tìm thấy cách cuộn xuống cuối WKWebView của mình.
Tôi cũng nghĩ rằng hành vi (vì tôi có thể làm webView.scrollView) tương tự như ScrollView.
Bất kỳ giúp đỡ?
Trả lời
Đây là một bản demo đơn giản về cách tiếp cận khả thi. Đã thử nghiệm với Xcode 12 / iOS 14.
struct DemoWebView : UIViewRepresentable {
let text: String
@Binding var scrollToBottom: Bool
func makeUIView(context: Context) -> WKWebView {
let webview = WKWebView()
webview.loadHTMLString(text, baseURL: nil)
return webview
}
func updateUIView(_ webview: WKWebView, context: Context) {
if scrollToBottom {
let point = CGPoint(x: 0, y: webview.scrollView.contentSize.height - webview.frame.size.height)
webview.scrollView.setContentOffset(point, animated: true)
DispatchQueue.main.async {
self.scrollToBottom = false // turn it back for reuse
}
}
}
}
và cách sử dụng như thế nào
@State private var scroll = false
var body: some View {
VStack {
Button("Bottom") { self.scroll = true }
DemoWebView(text: self.htmlText, scrollToBottom: $scroll)
}
}