Java 调用 JavaScript:
val webview: WebView
val script: String
webview.loadUrl("javascript:${script}")
webview.evaluateJavascript(script) { resultFromJS: String? ->
// callback
}
Example
let platform = {
name: 'Android',
hello: function(what) {
return this.name + ': Hello ' + what
}
}
val script = "platform.hello('World')"
webview.loadUrl("javascript:${script}")
webview.evaluateJavascript(script) { resultFromJS: String? ->
assert resultFromJS == "Android: Hello World"
}
JavaScript 调用 Java:
let resultFromAndroid = android.hello('World')
assert resultFromAndroid == 'Android: Hello World'
window.open('android://toast?msg=Hello')
alert('Hello Android')
let result = confirm('Yes or No')
assert result === true
// assert result === false
let username = prompt('input username', 'Tony')
assert username == 'Peter'
Example
class JavaScriptHandler {
@JavascriptInterface
fun hello(what: String): String {
return "Android: Hello ${what}"
}
}
webview.addJavascriptInterface(JavaScriptHandler(), "android")
webview.setWebViewClient(object : WebViewClient() {
override fun shouldOverrideUrlLoading(view: WebView, request: WebResourceRequest): Boolean {
if ("android" == request.url.scheme) {
if ("toast" == request.url.authority) {
toast(request.url.getQueryParameters("msg"))
}
return true
}
return super.shouldOverrideUrlLoading(view, request)
}
})
webview.setWebChromeClient(object : WebChromeClient() {
override fun onJsAlert(view: WebView, url: String, message: String, result: JsResult): Boolean {
if ("Hello Android" == message) {
toast(message)
result.confirm()
return true
}
return super.onJsAlert(view, url, message, result)
}
override fun onJsConfirm(view: WebView, url: String, message: String, result: JsResult): Boolean {
if ("Yes or No" == message) {
result.confirm()
// result.cancel()
return true
}
return super.onJsConfirm(view, url, message, result)
}
override fun onJsPrompt(view: WebView, url: String, message: String, defaultValue: String, result: JsPromptResult): Boolean {
if ("input username" == message) {
assert defaultValue == "Tony"
result.confirm("Peter")
// result.cancel()
return true
}
return super.onJsPrompt(view, url, message, defaultValue, result)
}
})
WebView 加速方案
- WebView 首次创建耗时较长-提前创建一个 WebView 备用,缺点:额外的内存开销
- WebView 初始化的同时由 Native 代理网络请求,后续 WebView 直接使用 Native 请求的网络数据
- HTML 离线包缓存策略,内存 + 文件 + 网络,更新策略(构建 Server 主动推送离线包给 Client 的能力,新旧版本离线包通过 Diff 算法生成最小补丁文件,把这个补丁文件推送给客户端来更新旧版本的离线包)
- 同步渲染采用 chunk 编码-网络请求先返回固定的静态资源,再返回业务数据,从而让前端加载资源和后端加载 API 不互相阻塞
- JS 脚本执行慢,就让脚本在最后执行,不阻塞 HTML 解析
-
网友评论