blob: f8bc5129a3cad73f83e62636c2a63606f6b021a1 [file] [log] [blame]
// Copyright 2013 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
package io.flutter.plugins.webviewflutter;
import android.os.Build;
import android.os.Message;
import android.webkit.WebChromeClient;
import android.webkit.WebResourceRequest;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.annotation.RequiresApi;
import io.flutter.plugins.webviewflutter.GeneratedAndroidWebView.WebChromeClientHostApi;
/**
* Host api implementation for {@link WebChromeClient}.
*
* <p>Handles creating {@link WebChromeClient}s that intercommunicate with a paired Dart object.
*/
public class WebChromeClientHostApiImpl implements WebChromeClientHostApi {
private final InstanceManager instanceManager;
private final WebChromeClientCreator webChromeClientCreator;
private final WebChromeClientFlutterApiImpl flutterApi;
/**
* Implementation of {@link WebChromeClient} that passes arguments of callback methods to Dart.
*/
public static class WebChromeClientImpl extends WebChromeClient implements Releasable {
@Nullable private WebChromeClientFlutterApiImpl flutterApi;
private WebViewClient webViewClient;
/**
* Creates a {@link WebChromeClient} that passes arguments of callbacks methods to Dart.
*
* @param flutterApi handles sending messages to Dart
* @param webViewClient receives forwarded calls from {@link WebChromeClient#onCreateWindow}
*/
public WebChromeClientImpl(
@NonNull WebChromeClientFlutterApiImpl flutterApi, WebViewClient webViewClient) {
this.flutterApi = flutterApi;
this.webViewClient = webViewClient;
}
// Verifies that a url opened by `Window.open` has a secure url.
@Override
public boolean onCreateWindow(
final WebView view, boolean isDialog, boolean isUserGesture, Message resultMsg) {
final WebViewClient newWindowWebViewClient =
new WebViewClient() {
@RequiresApi(api = Build.VERSION_CODES.N)
@Override
public boolean shouldOverrideUrlLoading(
@NonNull WebView view, @NonNull WebResourceRequest request) {
webViewClient.shouldOverrideUrlLoading(view, request);
return true;
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
webViewClient.shouldOverrideUrlLoading(view, url);
return true;
}
};
final WebView newWebView = new WebView(view.getContext());
newWebView.setWebViewClient(newWindowWebViewClient);
final WebView.WebViewTransport transport = (WebView.WebViewTransport) resultMsg.obj;
transport.setWebView(newWebView);
resultMsg.sendToTarget();
return true;
}
@Override
public void onProgressChanged(WebView view, int progress) {
if (flutterApi != null) {
flutterApi.onProgressChanged(this, view, (long) progress, reply -> {});
}
}
/**
* Set the {@link WebViewClient} that calls to {@link WebChromeClient#onCreateWindow} are passed
* to.
*
* @param webViewClient the forwarding {@link WebViewClient}
*/
public void setWebViewClient(WebViewClient webViewClient) {
this.webViewClient = webViewClient;
}
@Override
public void release() {
if (flutterApi != null) {
flutterApi.dispose(this, reply -> {});
}
flutterApi = null;
}
}
/** Handles creating {@link WebChromeClient}s for a {@link WebChromeClientHostApiImpl}. */
public static class WebChromeClientCreator {
/**
* Creates a {@link DownloadListenerHostApiImpl.DownloadListenerImpl}.
*
* @param flutterApi handles sending messages to Dart
* @param webViewClient receives forwarded calls from {@link WebChromeClient#onCreateWindow}
* @return the created {@link DownloadListenerHostApiImpl.DownloadListenerImpl}
*/
public WebChromeClientImpl createWebChromeClient(
WebChromeClientFlutterApiImpl flutterApi, WebViewClient webViewClient) {
return new WebChromeClientImpl(flutterApi, webViewClient);
}
}
/**
* Creates a host API that handles creating {@link WebChromeClient}s.
*
* @param instanceManager maintains instances stored to communicate with Dart objects
* @param webChromeClientCreator handles creating {@link WebChromeClient}s
* @param flutterApi handles sending messages to Dart
*/
public WebChromeClientHostApiImpl(
InstanceManager instanceManager,
WebChromeClientCreator webChromeClientCreator,
WebChromeClientFlutterApiImpl flutterApi) {
this.instanceManager = instanceManager;
this.webChromeClientCreator = webChromeClientCreator;
this.flutterApi = flutterApi;
}
@Override
public void create(Long instanceId, Long webViewClientInstanceId) {
final WebViewClient webViewClient =
(WebViewClient) instanceManager.getInstance(webViewClientInstanceId);
final WebChromeClient webChromeClient =
webChromeClientCreator.createWebChromeClient(flutterApi, webViewClient);
instanceManager.addInstance(webChromeClient, instanceId);
}
}