├── .gitignore
├── platforms
└── android
│ ├── libs
│ ├── armeabi
│ │ └── liblbs.so
│ └── tbs_sdk_thirdapp_v3.5.0.1004_43500_sharewithdownload_withoutGame_obfs_20170801_113025.jar
│ └── src
│ └── org
│ └── apache
│ └── cordova
│ └── x5engine
│ ├── X5CordovaHttpAuthHandler.java
│ ├── X5CordovaClientCertRequest.java
│ ├── X5ExposedJsApi.java
│ ├── X5CookieManager.java
│ ├── X5WebView.java
│ ├── X5WebChromeClient.java
│ ├── X5WebViewEngine.java
│ └── X5WebViewClient.java
├── README.md
├── package.json
├── plugin.xml
└── LICENSE
/.gitignore:
--------------------------------------------------------------------------------
1 | # ignore project config
2 |
3 | /.vscode
4 | /.history
5 |
6 |
--------------------------------------------------------------------------------
/platforms/android/libs/armeabi/liblbs.so:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/runner525/x5webview-cordova-plugin/HEAD/platforms/android/libs/armeabi/liblbs.so
--------------------------------------------------------------------------------
/platforms/android/libs/tbs_sdk_thirdapp_v3.5.0.1004_43500_sharewithdownload_withoutGame_obfs_20170801_113025.jar:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/runner525/x5webview-cordova-plugin/HEAD/platforms/android/libs/tbs_sdk_thirdapp_v3.5.0.1004_43500_sharewithdownload_withoutGame_obfs_20170801_113025.jar
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # x5webview-cordova-plugin
2 | x5webview-cordova-plugin 是腾讯浏览服务(TBS)为cordova框架提供的用于android平台的cordova插件,旨在为android平台提供更好的webview浏览体验.
3 |
4 | 一.接入步骤:
5 | 1.向cordiva工程中添加x5webview插件,有如下两种方式:
6 | ```
7 | (1)cordova plugin add x5webview-cordova-plugin
8 | (2)cordova plugin add https://github.com/runner525/x5webview-cordova-plugin.git
9 |
10 | ```
11 |
12 | 二.熟悉android开发的同学可以参考x5官网来灵活使用x5内核.常用链接如下:
13 |
14 | 官网(https://x5.tencent.com/tbs/)
15 |
16 | 常见问题(https://x5.tencent.com/tbs/faq.html)
17 |
18 | 论坛(http://bbs.mb.qq.com/forum-112-1.html)
19 |
20 | 内核加载问题检测工具(http://bbs.mb.qq.com/thread-1944983-1-1.html)
21 |
22 |
--------------------------------------------------------------------------------
/platforms/android/src/org/apache/cordova/x5engine/X5CordovaHttpAuthHandler.java:
--------------------------------------------------------------------------------
1 | package org.apache.cordova.x5engine;
2 |
3 | import com.tencent.smtt.export.external.interfaces.HttpAuthHandler;
4 |
5 | import org.apache.cordova.ICordovaHttpAuthHandler;
6 |
7 | public class X5CordovaHttpAuthHandler implements ICordovaHttpAuthHandler {
8 |
9 | private final HttpAuthHandler handler;
10 |
11 | public X5CordovaHttpAuthHandler(HttpAuthHandler handler) {
12 | this.handler = handler;
13 | }
14 |
15 | /**
16 | * Instructs the XWalkView to cancel the authentication request.
17 | */
18 | public void cancel() {
19 | handler.cancel();
20 | }
21 |
22 | /**
23 | * Instructs the XWalkView to proceed with the authentication with the given credentials.
24 | *
25 | * @param username
26 | * @param password
27 | */
28 | public void proceed(String username, String password) {
29 | handler.proceed(username, password);
30 | }
31 | }
32 |
--------------------------------------------------------------------------------
/package.json:
--------------------------------------------------------------------------------
1 | {
2 | "name": "x5webview-cordova-plugin",
3 | "version": "1.1.1",
4 | "description": "Changes the default WebView to x5engine",
5 | "cordova": {
6 | "id": "x5webview-cordova-plugin",
7 | "platforms": [
8 | "android"
9 | ]
10 | },
11 | "repository": {
12 | "type": "git",
13 | "url": "git+https://github.com/runner525/x5webview-cordova-plugin.git"
14 | },
15 | "keywords": [
16 | "cordova",
17 | "chromium",
18 | "x5engine",
19 | "webview",
20 | "ecosystem:cordova",
21 | "cordova-android"
22 | ],
23 | "engines": [
24 | {
25 | "name": "cordova-android",
26 | "version": ">=4"
27 | },
28 | {
29 | "name": "cordova-plugman",
30 | "version": ">=5.2.0"
31 | }
32 | ],
33 | "author": "lz",
34 | "license": "Apache 2.0",
35 | "bugs": {
36 | "url": "https://github.com/runner525/x5webview-cordova-plugin/issues"
37 | },
38 | "homepage": "https://github.com/runner525/x5webview-cordova-plugin#readme"
39 | }
40 |
--------------------------------------------------------------------------------
/platforms/android/src/org/apache/cordova/x5engine/X5CordovaClientCertRequest.java:
--------------------------------------------------------------------------------
1 | package org.apache.cordova.x5engine;
2 |
3 |
4 | import com.tencent.smtt.export.external.interfaces.ClientCertRequest;
5 |
6 | import org.apache.cordova.ICordovaClientCertRequest;
7 |
8 | import java.security.Principal;
9 | import java.security.PrivateKey;
10 | import java.security.cert.X509Certificate;
11 |
12 |
13 | public class X5CordovaClientCertRequest implements ICordovaClientCertRequest {
14 |
15 | private final ClientCertRequest request;
16 |
17 | public X5CordovaClientCertRequest(ClientCertRequest request) {
18 | this.request = request;
19 | }
20 |
21 | /**
22 | * Cancel this request
23 | */
24 | public void cancel()
25 | {
26 | request.cancel();
27 | }
28 |
29 | /*
30 | * Returns the host name of the server requesting the certificate.
31 | */
32 | public String getHost()
33 | {
34 | return request.getHost();
35 | }
36 |
37 | /*
38 | * Returns the acceptable types of asymmetric keys (can be null).
39 | */
40 | public String[] getKeyTypes()
41 | {
42 | return request.getKeyTypes();
43 | }
44 |
45 | /*
46 | * Returns the port number of the server requesting the certificate.
47 | */
48 | public int getPort()
49 | {
50 | return request.getPort();
51 | }
52 |
53 | /*
54 | * Returns the acceptable certificate issuers for the certificate matching the private key (can be null).
55 | */
56 | public Principal[] getPrincipals()
57 | {
58 | return request.getPrincipals();
59 | }
60 |
61 | /*
62 | * Ignore the request for now. Do not remember user's choice.
63 | */
64 | public void ignore()
65 | {
66 | request.ignore();
67 | }
68 |
69 | /*
70 | * Proceed with the specified private key and client certificate chain. Remember the user's positive choice and use it for future requests.
71 | *
72 | * @param privateKey The privateKey
73 | * @param chain The certificate chain
74 | */
75 | public void proceed(PrivateKey privateKey, X509Certificate[] chain)
76 | {
77 | request.proceed(privateKey, chain);
78 | }
79 | }
80 |
--------------------------------------------------------------------------------
/platforms/android/src/org/apache/cordova/x5engine/X5ExposedJsApi.java:
--------------------------------------------------------------------------------
1 | /*
2 | Licensed to the Apache Software Foundation (ASF) under one
3 | or more contributor license agreements. See the NOTICE file
4 | distributed with this work for additional information
5 | regarding copyright ownership. The ASF licenses this file
6 | to you under the Apache License, Version 2.0 (the
7 | "License"); you may not use this file except in compliance
8 | with the License. You may obtain a copy of the License at
9 |
10 | http://www.apache.org/licenses/LICENSE-2.0
11 |
12 | Unless required by applicable law or agreed to in writing,
13 | software distributed under the License is distributed on an
14 | "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 | KIND, either express or implied. See the License for the
16 | specific language governing permissions and limitations
17 | under the License.
18 | */
19 | package org.apache.cordova.x5engine;
20 |
21 | import android.webkit.JavascriptInterface;
22 |
23 | import org.apache.cordova.CordovaBridge;
24 | import org.apache.cordova.ExposedJsApi;
25 | import org.json.JSONException;
26 |
27 | /**
28 | * Contains APIs that the JS can call. All functions in here should also have
29 | * an equivalent entry in CordovaChromeClient.java, and be added to
30 | * cordova-js/lib/android/plugin/android/promptbasednativeapi.js
31 | */
32 | class X5ExposedJsApi implements ExposedJsApi {
33 | private final CordovaBridge bridge;
34 |
35 | X5ExposedJsApi(CordovaBridge bridge) {
36 | this.bridge = bridge;
37 | }
38 |
39 | @JavascriptInterface
40 | public String exec(int bridgeSecret, String service, String action, String callbackId, String arguments) throws JSONException, IllegalAccessException {
41 | return bridge.jsExec(bridgeSecret, service, action, callbackId, arguments);
42 | }
43 |
44 | @JavascriptInterface
45 | public void setNativeToJsBridgeMode(int bridgeSecret, int value) throws IllegalAccessException {
46 | bridge.jsSetNativeToJsBridgeMode(bridgeSecret, value);
47 | }
48 |
49 | @JavascriptInterface
50 | public String retrieveJsMessages(int bridgeSecret, boolean fromOnlineEvent) throws IllegalAccessException {
51 | return bridge.jsRetrieveJsMessages(bridgeSecret, fromOnlineEvent);
52 | }
53 | }
54 |
--------------------------------------------------------------------------------
/platforms/android/src/org/apache/cordova/x5engine/X5CookieManager.java:
--------------------------------------------------------------------------------
1 | /*
2 | Licensed to the Apache Software Foundation (ASF) under one
3 | or more contributor license agreements. See the NOTICE file
4 | distributed with this work for additional information
5 | regarding copyright ownership. The ASF licenses this file
6 | to you under the Apache License, Version 2.0 (the
7 | "License"); you may not use this file except in compliance
8 | with the License. You may obtain a copy of the License at
9 |
10 | http://www.apache.org/licenses/LICENSE-2.0
11 |
12 | Unless required by applicable law or agreed to in writing,
13 | software distributed under the License is distributed on an
14 | "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 | KIND, either express or implied. See the License for the
16 | specific language governing permissions and limitations
17 | under the License.
18 | */
19 |
20 | package org.apache.cordova.x5engine;
21 |
22 | import android.annotation.TargetApi;
23 | import android.os.Build;
24 | import com.tencent.smtt.sdk.CookieManager;
25 | import com.tencent.smtt.sdk.WebView;
26 |
27 | import org.apache.cordova.ICordovaCookieManager;
28 |
29 | class X5CookieManager implements ICordovaCookieManager {
30 |
31 | protected final WebView webView;
32 | private final CookieManager cookieManager;
33 |
34 | //Added because lint can't see the conditional RIGHT ABOVE this
35 | @TargetApi(Build.VERSION_CODES.LOLLIPOP)
36 | public X5CookieManager(WebView webview) {
37 | webView = webview;
38 | cookieManager = CookieManager.getInstance();
39 |
40 | //REALLY? Nobody has seen this UNTIL NOW?
41 | // cookieManager.setAcceptFileSchemeCookies(true);
42 | cookieManager.setAcceptCookie(true);
43 |
44 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
45 | cookieManager.setAcceptThirdPartyCookies(webView, true);
46 | }
47 | }
48 |
49 | public void setCookiesEnabled(boolean accept) {
50 | cookieManager.setAcceptCookie(accept);
51 | }
52 |
53 | public void setCookie(final String url, final String value) {
54 | cookieManager.setCookie(url, value);
55 | }
56 |
57 | public String getCookie(final String url) {
58 | return cookieManager.getCookie(url);
59 | }
60 |
61 | public void clearCookies() {
62 | cookieManager.removeAllCookie();
63 | }
64 |
65 | public void flush() {
66 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
67 | cookieManager.flush();
68 | }
69 | }
70 | };
71 |
--------------------------------------------------------------------------------
/plugin.xml:
--------------------------------------------------------------------------------
1 |
2 |
3 |
7 |
8 | x5engine WebView Engine
9 | use x5webview for cordova to get a better webview browsing experience
10 | Apache 2.0
11 | x5webview,webview,chromium,cordova
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 |
--------------------------------------------------------------------------------
/platforms/android/src/org/apache/cordova/x5engine/X5WebView.java:
--------------------------------------------------------------------------------
1 | /*
2 | Licensed to the Apache Software Foundation (ASF) under one
3 | or more contributor license agreements. See the NOTICE file
4 | distributed with this work for additional information
5 | regarding copyright ownership. The ASF licenses this file
6 | to you under the Apache License, Version 2.0 (the
7 | "License"); you may not use this file except in compliance
8 | with the License. You may obtain a copy of the License at
9 |
10 | http://www.apache.org/licenses/LICENSE-2.0
11 |
12 | Unless required by applicable law or agreed to in writing,
13 | software distributed under the License is distributed on an
14 | "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 | KIND, either express or implied. See the License for the
16 | specific language governing permissions and limitations
17 | under the License.
18 | */
19 |
20 | package org.apache.cordova.x5engine;
21 |
22 | import android.content.Context;
23 | import android.util.AttributeSet;
24 | import android.view.KeyEvent;
25 | import com.tencent.smtt.sdk.WebChromeClient;
26 | import com.tencent.smtt.sdk.WebView;
27 | import com.tencent.smtt.sdk.WebViewClient;
28 |
29 | import org.apache.cordova.CordovaInterface;
30 | import org.apache.cordova.CordovaWebView;
31 | import org.apache.cordova.CordovaWebViewEngine;
32 |
33 |
34 | public class X5WebView extends WebView implements CordovaWebViewEngine.EngineView {
35 | private X5WebViewClient viewClient;
36 | X5WebChromeClient chromeClient;
37 | private X5WebViewEngine parentEngine;
38 | private CordovaInterface cordova;
39 |
40 | public X5WebView(Context context) {
41 | this(context, null);
42 | }
43 |
44 | public X5WebView(Context context, AttributeSet attrs) {
45 | super(context, attrs);
46 | }
47 |
48 | // Package visibility to enforce that only X5WebViewEngine should call this method.
49 | void init(X5WebViewEngine parentEngine, CordovaInterface cordova) {
50 | this.cordova = cordova;
51 | this.parentEngine = parentEngine;
52 | if (this.viewClient == null) {
53 | setWebViewClient(new X5WebViewClient(parentEngine));
54 | }
55 |
56 | if (this.chromeClient == null) {
57 | setWebChromeClient(new X5WebChromeClient(parentEngine));
58 | }
59 | }
60 |
61 | @Override
62 | public CordovaWebView getCordovaWebView() {
63 | return parentEngine != null ? parentEngine.getCordovaWebView() : null;
64 | }
65 |
66 | @Override
67 | public void setWebViewClient(WebViewClient client) {
68 | viewClient = (X5WebViewClient)client;
69 | super.setWebViewClient(client);
70 | }
71 |
72 | @Override
73 | public void setWebChromeClient(WebChromeClient client) {
74 | chromeClient = (X5WebChromeClient)client;
75 | super.setWebChromeClient(client);
76 | }
77 |
78 | @Override
79 | public boolean dispatchKeyEvent(KeyEvent event) {
80 | Boolean ret = parentEngine.client.onDispatchKeyEvent(event);
81 | if (ret != null) {
82 | return ret.booleanValue();
83 | }
84 | return super.dispatchKeyEvent(event);
85 | }
86 | }
87 |
--------------------------------------------------------------------------------
/platforms/android/src/org/apache/cordova/x5engine/X5WebChromeClient.java:
--------------------------------------------------------------------------------
1 | /*
2 | Licensed to the Apache Software Foundation (ASF) under one
3 | or more contributor license agreements. See the NOTICE file
4 | distributed with this work for additional information
5 | regarding copyright ownership. The ASF licenses this file
6 | to you under the Apache License, Version 2.0 (the
7 | "License"); you may not use this file except in compliance
8 | with the License. You may obtain a copy of the License at
9 |
10 | http://www.apache.org/licenses/LICENSE-2.0
11 |
12 | Unless required by applicable law or agreed to in writing,
13 | software distributed under the License is distributed on an
14 | "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 | KIND, either express or implied. See the License for the
16 | specific language governing permissions and limitations
17 | under the License.
18 | */
19 | package org.apache.cordova.x5engine;
20 |
21 | import java.util.Arrays;
22 | import android.annotation.TargetApi;
23 | import android.app.Activity;
24 | import android.content.Context;
25 | import android.content.ActivityNotFoundException;
26 | import android.content.Intent;
27 | import android.net.Uri;
28 | import android.os.Build;
29 | import android.util.Log;
30 | import android.view.Gravity;
31 | import android.view.View;
32 | import android.view.ViewGroup.LayoutParams;
33 | import com.tencent.smtt.export.external.interfaces.ConsoleMessage;
34 | import com.tencent.smtt.export.external.interfaces.GeolocationPermissionsCallback;
35 | import com.tencent.smtt.export.external.interfaces.IX5WebChromeClient;
36 | import com.tencent.smtt.export.external.interfaces.JsPromptResult;
37 | import com.tencent.smtt.export.external.interfaces.JsResult;
38 | import com.tencent.smtt.sdk.ValueCallback;
39 | import com.tencent.smtt.sdk.WebChromeClient;
40 | import com.tencent.smtt.sdk.WebStorage;
41 | import com.tencent.smtt.sdk.WebView;
42 |
43 | import android.webkit.PermissionRequest;
44 | import android.widget.LinearLayout;
45 | import android.widget.ProgressBar;
46 | import android.widget.RelativeLayout;
47 |
48 | import org.apache.cordova.CordovaDialogsHelper;
49 | import org.apache.cordova.CordovaPlugin;
50 | import org.apache.cordova.LOG;
51 |
52 | /**
53 | * This class is the WebChromeClient that implements callbacks for our web view.
54 | * The kind of callbacks that happen here are on the chrome outside the document,
55 | * such as onCreateWindow(), onConsoleMessage(), onProgressChanged(), etc. Related
56 | * to but different than CordovaWebViewClient.
57 | */
58 | public class X5WebChromeClient extends WebChromeClient {
59 |
60 | private static final int FILECHOOSER_RESULTCODE = 5173;
61 | private static final String LOG_TAG = "X5WebChromeClient";
62 | private long MAX_QUOTA = 100 * 1024 * 1024;
63 | protected final X5WebViewEngine parentEngine;
64 |
65 | // the video progress view
66 | private View mVideoProgressView;
67 |
68 | private CordovaDialogsHelper dialogsHelper;
69 | private Context appContext;
70 |
71 | private IX5WebChromeClient.CustomViewCallback mCustomViewCallback;
72 | private View mCustomView;
73 |
74 | public X5WebChromeClient(X5WebViewEngine parentEngine) {
75 | this.parentEngine = parentEngine;
76 | appContext = parentEngine.webView.getContext();
77 | dialogsHelper = new CordovaDialogsHelper(appContext);
78 | }
79 |
80 | /**
81 | * Tell the client to display a javascript alert dialog.
82 | */
83 | @Override
84 | public boolean onJsAlert(WebView view, String url, String message, final JsResult result) {
85 | dialogsHelper.showAlert(message, new CordovaDialogsHelper.Result() {
86 | @Override public void gotResult(boolean success, String value) {
87 | if (success) {
88 | result.confirm();
89 | } else {
90 | result.cancel();
91 | }
92 | }
93 | });
94 | return true;
95 | }
96 |
97 | /**
98 | * Tell the client to display a confirm dialog to the user.
99 | */
100 | @Override
101 | public boolean onJsConfirm(WebView view, String url, String message, final JsResult result) {
102 | dialogsHelper.showConfirm(message, new CordovaDialogsHelper.Result() {
103 | @Override
104 | public void gotResult(boolean success, String value) {
105 | if (success) {
106 | result.confirm();
107 | } else {
108 | result.cancel();
109 | }
110 | }
111 | });
112 | return true;
113 | }
114 |
115 | /**
116 | * Tell the client to display a prompt dialog to the user.
117 | * If the client returns true, WebView will assume that the client will
118 | * handle the prompt dialog and call the appropriate JsPromptResult method.
119 | *
120 | * Since we are hacking prompts for our own purposes, we should not be using them for
121 | * this purpose, perhaps we should hack console.log to do this instead!
122 | */
123 | @Override
124 | public boolean onJsPrompt(WebView view, String origin, String message, String defaultValue, final JsPromptResult result) {
125 | // Unlike the @JavascriptInterface bridge, this method is always called on the UI thread.
126 | String handledRet = parentEngine.bridge.promptOnJsPrompt(origin, message, defaultValue);
127 | if (handledRet != null) {
128 | result.confirm(handledRet);
129 | } else {
130 | dialogsHelper.showPrompt(message, defaultValue, new CordovaDialogsHelper.Result() {
131 | @Override
132 | public void gotResult(boolean success, String value) {
133 | if (success) {
134 | result.confirm(value);
135 | } else {
136 | result.cancel();
137 | }
138 | }
139 | });
140 | }
141 | return true;
142 | }
143 |
144 | /**
145 | * Handle database quota exceeded notification.
146 | */
147 | @Override
148 | public void onExceededDatabaseQuota(String url, String databaseIdentifier, long currentQuota, long estimatedSize,
149 | long totalUsedQuota, WebStorage.QuotaUpdater quotaUpdater)
150 | {
151 | LOG.d(LOG_TAG, "onExceededDatabaseQuota estimatedSize: %d currentQuota: %d totalUsedQuota: %d", estimatedSize, currentQuota, totalUsedQuota);
152 | quotaUpdater.updateQuota(MAX_QUOTA);
153 | }
154 |
155 | @TargetApi(8)
156 | @Override
157 | public boolean onConsoleMessage(ConsoleMessage consoleMessage)
158 | {
159 | if (consoleMessage.message() != null)
160 | LOG.d(LOG_TAG, "%s: Line %d : %s" , consoleMessage.sourceId() , consoleMessage.lineNumber(), consoleMessage.message());
161 | return super.onConsoleMessage(consoleMessage);
162 | }
163 |
164 | @Override
165 | /**
166 | * Instructs the client to show a prompt to ask the user to set the Geolocation permission state for the specified origin.
167 | *
168 | * This also checks for the Geolocation Plugin and requests permission from the application to use Geolocation.
169 | *
170 | * @param origin
171 | * @param callback
172 | */
173 | public void onGeolocationPermissionsShowPrompt(String origin, GeolocationPermissionsCallback callback) {
174 | super.onGeolocationPermissionsShowPrompt(origin, callback);
175 | callback.invoke(origin, true, false);
176 | //Get the plugin, it should be loaded
177 | CordovaPlugin geolocation = parentEngine.pluginManager.getPlugin("Geolocation");
178 | if(geolocation != null && !geolocation.hasPermisssion())
179 | {
180 | geolocation.requestPermissions(0);
181 | }
182 |
183 | }
184 |
185 | //TODO API level 7 is required for this, see if we could lower this using something else
186 | // @Override
187 | // public void onShowCustomView(View view, IX5WebChromeClient.CustomViewCallback callback) {
188 | // parentEngine.getCordovaWebView().showCustomView(view, callback);
189 | // }
190 |
191 | public void onHideCustomView() {
192 | parentEngine.getCordovaWebView().hideCustomView();
193 | }
194 |
195 | /**
196 | * Ask the host application for a custom progress view to show while
197 | * a