我问这个问题是因为经过一些研究,我在网上找不到令人满意的答案。
我的需求很简单,我有一个UITableViewController,当我单击一个单元格时,我需要显示一个加载器(在加载WKWebViewContent的同时),然后推送下一个UIViewController,并且已经在其中加载了WKWebView。
我尝试过:
class TableViewController: UITableViewController, WKNavigationDelegate {
var webviewToLoad:WKWebView!
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
let htmlString = "some html content"
webviewToLoad = WKWebView(frame: .zero, configuration: WKWebViewConfiguration())
webviewToLoad.navigationDelegate = self
webviewToLoad.loadHTMLString(htmlString, baseURL: Bundle.main.resourceURL)
}
override func prepare(for segue: UIStoryboardSegue, sender: Any?) {
if segue.identifier == "postview"{
let destinationController = segue.destination as! ViewController
destinationController.webView= webviewToLoad
}
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
print("Loaded!")
self.performSegue(withIdentifier: "postview", sender: self)
}
}
class ViewController: UIViewController, WKUIDelegate {
var webView: WKWebView!
override func loadView() {
let webConfiguration = WKWebViewConfiguration()
webView = WKWebView(frame: .zero, configuration: webConfiguration)
webView.uiDelegate = self
self.view = webView
}
override func viewDidLoad() {
super.viewDidLoad()
}
}
didFinish
被调用,但最终的WKWebView为空。
也许这不是正确的方法,有什么想法吗?
答案 0 :(得分:1)
didFinish被调用,但最终的WKWebView为空
因为您从未做过任何使它 not 为空白的操作。您的代码说:
var webviewToLoad:WKWebView!
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
webviewToLoad = WKWebView(frame: .zero, configuration: WKWebViewConfiguration())
webviewToLoad.navigationDelegate = self
webviewToLoad.loadHTMLString(htmlString, baseURL: Bundle.main.resourceURL)
}
因此,您所做的一切都是关于webviewToLoad
。但是webviewToLoad
与在出现以下问题之后在ViewController中出现的webView
不是相同的class ViewController: UIViewController, WKUIDelegate {
var webView: WKWebView!
}
:
webView
那是您要为其提供内容的Web视图。您根本没有这样做;您的代码都没有碰到if segue.identifier == "postview"{
let destinationController = segue.destination as! ViewController
destinationController.webView = webviewToLoad
}
来提供内容。
我认为您的困惑的核心在这里:
loadView
您不能仅将一个Web视图替换为另一个Web视图,并期望一切都能神奇地工作; if segue.identifier == "postview"{
let destinationController = segue.destination as! ViewController
// make `loadView` run
destinationController.loadViewIfNeeded()
let webView = destinationController.webView
// now load _this_ `webView` with content!
let htmlString = "some html content"
webView.loadHTMLString(htmlString, baseURL: Bundle.main.resourceURL)
}
仍将使原始的空白Web视图成为您的视图并出现在界面中。
相反,您想要的是这种体系结构:
Repository
答案 1 :(得分:1)
由于@matt的回答不完整,因此我的解决方案是在推送下一个视图控制器之前等待webview加载:
class TableViewController: UITableViewController, WKNavigationDelegate, WKUIDelegate {
var webviewToLoad:WKWebView!
var destinationController:ViewController!
var alert:UIAlertController!
override func viewDidLoad() {
super.viewDidLoad()
}
override func tableView(_ tableView: UITableView, didSelectRowAt indexPath: IndexPath) {
alert = UIAlertController(title: "Alert", message: "Loading", preferredStyle: .alert)
destinationController = UIStoryboard.init(name: "Main", bundle: Bundle.main).instantiateViewController(withIdentifier: "ViewController") as? ViewController
destinationController!.loadViewIfNeeded()
let webView:WKWebView = destinationController!.webView
webView.navigationDelegate = self
webView.uiDelegate = self
self.present(alert, animated: true, completion: nil)
let htmlString = "my html code"
webView.loadHTMLString(htmlString, baseURL: Bundle.main.resourceURL)
}
func webView(_ webView: WKWebView, didFinish navigation: WKNavigation!) {
alert.dismiss(animated: false, completion: nil)
self.navigationController?.pushViewController(destinationController!, animated: true)
}
}
还有带有Webview的UIViewController:
class ViewController: UIViewController, WKUIDelegate, WKNavigationDelegate {
var webView: WKWebView!
@IBOutlet var viewForWebview: UIView!
@IBOutlet var heightWebviewConstraint: NSLayoutConstraint!
override func viewDidLoad() {
super.viewDidLoad()
}
override func loadView() {
super.loadView()
webView = WKWebView()
if (webView != nil) {
webView!.frame = viewForWebview.frame
webView.translatesAutoresizingMaskIntoConstraints = false
viewForWebview.addSubview(webView!)
NSLayoutConstraint.activate([
webView.topAnchor.constraint(equalTo: viewForWebview.topAnchor),
webView.bottomAnchor.constraint(equalTo: viewForWebview.bottomAnchor),
webView.leadingAnchor.constraint(equalTo: viewForWebview.leadingAnchor),
webView.trailingAnchor.constraint(equalTo: viewForWebview.trailingAnchor)
])
}
}
override func viewDidLayoutSubviews() {
super.viewDidLayoutSubviews()
heightWebviewConstraint.constant = self.webView.scrollView.contentSize.height
self.view.setNeedsLayout()
self.view.setNeedsUpdateConstraints()
}
}
此代码在加载Webview时显示UIAlertController,然后关闭警报控制器,并在已加载Webview的情况下推送下一个控制器。