This repository has been archived by the owner on Sep 14, 2023. It is now read-only.
forked from flutter/plugins
-
Notifications
You must be signed in to change notification settings - Fork 2
/
WebViewActivity.java
179 lines (153 loc) · 5.86 KB
/
WebViewActivity.java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
package io.flutter.plugins.urllauncher;
import android.annotation.TargetApi;
import android.app.Activity;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.os.Build;
import android.os.Bundle;
import android.os.Message;
import android.provider.Browser;
import android.view.KeyEvent;
import android.webkit.WebChromeClient;
import android.webkit.WebResourceRequest;
import android.webkit.WebView;
import android.webkit.WebViewClient;
import androidx.annotation.NonNull;
import java.util.HashMap;
import java.util.Map;
/* Launches WebView activity */
public class WebViewActivity extends Activity {
/*
* Use this to trigger a BroadcastReceiver inside WebViewActivity
* that will request the current instance to finish.
* */
public static String ACTION_CLOSE = "close action";
private final BroadcastReceiver broadcastReceiver =
new BroadcastReceiver() {
@Override
public void onReceive(Context context, Intent intent) {
String action = intent.getAction();
if (ACTION_CLOSE.equals(action)) {
finish();
}
}
};
private final WebViewClient webViewClient =
new WebViewClient() {
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.LOLLIPOP) {
view.loadUrl(url);
return false;
}
return super.shouldOverrideUrlLoading(view, url);
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, WebResourceRequest request) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
view.loadUrl(request.getUrl().toString());
}
return false;
}
};
private WebView webview;
private IntentFilter closeIntentFilter = new IntentFilter(ACTION_CLOSE);
// Verifies that a url opened by `Window.open` has a secure url.
private class FlutterWebChromeClient extends WebChromeClient {
@Override
public boolean onCreateWindow(
final WebView view, boolean isDialog, boolean isUserGesture, Message resultMsg) {
final WebViewClient webViewClient =
new WebViewClient() {
@TargetApi(Build.VERSION_CODES.LOLLIPOP)
@Override
public boolean shouldOverrideUrlLoading(
@NonNull WebView view, @NonNull WebResourceRequest request) {
final String url = request.getUrl().toString();
if (isSecure(url)) {
webview.loadUrl(url);
}
return true;
}
@Override
public boolean shouldOverrideUrlLoading(WebView view, String url) {
if (isSecure(url)) {
webview.loadUrl(url);
}
return true;
}
};
final WebView newWebView = new WebView(webview.getContext());
newWebView.setWebViewClient(webViewClient);
final WebView.WebViewTransport transport = (WebView.WebViewTransport) resultMsg.obj;
transport.setWebView(newWebView);
resultMsg.sendToTarget();
return true;
}
private boolean isSecure(String url) {
return url.startsWith("https://") || url.startsWith("http://");
}
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
webview = new WebView(this);
setContentView(webview);
// Get the Intent that started this activity and extract the string
final Intent intent = getIntent();
final String url = intent.getStringExtra(URL_EXTRA);
final boolean enableJavaScript = intent.getBooleanExtra(ENABLE_JS_EXTRA, false);
final boolean enableDomStorage = intent.getBooleanExtra(ENABLE_DOM_EXTRA, false);
final Bundle headersBundle = intent.getBundleExtra(Browser.EXTRA_HEADERS);
final Map<String, String> headersMap = extractHeaders(headersBundle);
webview.loadUrl(url, headersMap);
webview.getSettings().setJavaScriptEnabled(enableJavaScript);
webview.getSettings().setDomStorageEnabled(enableDomStorage);
// Open new urls inside the webview itself.
webview.setWebViewClient(webViewClient);
// Multi windows is set with FlutterWebChromeClient by default to handle internal bug: b/159892679.
webview.getSettings().setSupportMultipleWindows(true);
webview.setWebChromeClient(new FlutterWebChromeClient());
// Register receiver that may finish this Activity.
registerReceiver(broadcastReceiver, closeIntentFilter);
}
private Map<String, String> extractHeaders(Bundle headersBundle) {
final Map<String, String> headersMap = new HashMap<>();
for (String key : headersBundle.keySet()) {
final String value = headersBundle.getString(key);
headersMap.put(key, value);
}
return headersMap;
}
@Override
protected void onDestroy() {
super.onDestroy();
unregisterReceiver(broadcastReceiver);
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
if (keyCode == KeyEvent.KEYCODE_BACK && webview.canGoBack()) {
webview.goBack();
return true;
}
return super.onKeyDown(keyCode, event);
}
private static String URL_EXTRA = "url";
private static String ENABLE_JS_EXTRA = "enableJavaScript";
private static String ENABLE_DOM_EXTRA = "enableDomStorage";
/* Hides the constants used to forward data to the Activity instance. */
public static Intent createIntent(
Context context,
String url,
boolean enableJavaScript,
boolean enableDomStorage,
Bundle headersBundle) {
return new Intent(context, WebViewActivity.class)
.putExtra(URL_EXTRA, url)
.putExtra(ENABLE_JS_EXTRA, enableJavaScript)
.putExtra(ENABLE_DOM_EXTRA, enableDomStorage)
.putExtra(Browser.EXTRA_HEADERS, headersBundle);
}
}