Reputation: 105
I am sorry, if this question was already asked, but all the answers I could find are for complicated solutions.
I have a viewController, which is webView. I added WKWebView
, to my view from WebKit library, and opened simple url. Inside of my ViewController, I have a native function called showAd
.
When the user press the button, which was implemented in javascript, it show call showRewardsAd
. I set the break point to the userContentController, however, it never goes there.
func showAd(){
print("invoked")
}
extension WFWebViewController: WKScriptMessageHandler{
func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
if message.name == "showRewardsAd"{
self.showRewards()
webView.evaluateJavaScript("test", completionHandler: nil)
}
}
}
My goal is to simply allow this function to be called from javascript part. As I know, if I want to call javascript function in swift, I simply have to say:
webview.addJavascriptInterface('javascript: function_name();')
However, in my case, I want to do it in reverse order. Call swift function in Javascript code.
Upvotes: 5
Views: 5804
Reputation: 2048
You need to inject your user script inside the webView so you could listen to JavaScript's messages when they are posted.
Firstly, you will need to initialize the webView's config and preferences, to allow javaScript:
let config = WKWebViewConfiguration()
let preferences = WKPreferences()
preferences.javaScriptEnabled = true
config.preferences = preferences
Now, you need to inject your script to listen for the click events from the webView:
let userController = WKUserContentController()
let javaScript = "showRewardsAd = function() {\n" + "window.webkit.messageHandlers.adClicked.postMessage(); }"
let script = WKUserScript(source: javaScript, injectionTime: .atDocumentEnd, forMainFrameOnly: false)
userController.addUserScript(script)
userController.add(self, name: "adClicked")
config.userContentController = userController
Now instantiate your webView with the configuration from above:
self.webView = WKWebView(frame: .zero, configuration: config)
Now, your WKScriptMessageHandler
protocol is implemented correctly:
extension WFWebViewController: WKScriptMessageHandler{
func userContentController(_ userContentController: WKUserContentController, didReceive message: WKScriptMessage) {
if message.name == "showRewardsAd"{
self.showRewards()
print("Ad is being shown.")
}
}
}
I hope this works for you. I assumed that showRewardsAd
is implemented in the JavaScript on the website which you're accessing.
Upvotes: 4