d8ea367c228d64ded69f9a2f592da7d2c2d2b007
[platform/framework/web/crosswalk.git] / src / xwalk / runtime / android / core / src / org / xwalk / core / XWalkWebChromeClient.java
1 /*
2  * Copyright (C) 2008 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16
17 package org.xwalk.core;
18
19 import android.app.Activity;
20 import android.content.Context;
21 import android.content.pm.ActivityInfo;
22 import android.graphics.Bitmap;
23 import android.net.Uri;
24 import android.os.Message;
25 import android.view.Gravity;
26 import android.view.View;
27 import android.view.ViewGroup;
28 import android.webkit.WebStorage;
29 import android.webkit.ConsoleMessage;
30 import android.webkit.ValueCallback;
31 import android.widget.FrameLayout;
32
33 /**
34  * It's an internal legacy class which is to handle kinds of ui related
35  * callback functions. It only handles those which are not exposed to
36  * external users compared to XWalkUIClient.
37  */
38 public class XWalkWebChromeClient {
39     private Context mContext;
40     private View mCustomXWalkView;
41     private XWalkView mXWalkView;
42     private XWalkWebChromeClient.CustomViewCallback mCustomViewCallback;
43     private XWalkContentsClient mContentsClient = null;
44     private long XWALK_MAX_QUOTA = 1024 * 1024 * 100;
45
46     public XWalkWebChromeClient(Context context, XWalkView view) {
47         mContext = context;
48         mXWalkView = view;
49     }
50
51     void setContentsClient(XWalkContentsClient client) {
52         mContentsClient = client;
53     }
54
55     /**
56      * Notify the host application of a change in the document title.
57      * @param view The XWalkView that initiated the callback.
58      * @param title A String containing the new title of the document.
59      */
60     public void onReceivedTitle(XWalkView view, String title) {}
61
62     /**
63      * Notify the host application of a new favicon for the current page.
64      * @param view The XWalkView that initiated the callback.
65      * @param icon A Bitmap containing the favicon for the current page.
66      */
67     public void onReceivedIcon(XWalkView view, Bitmap icon) {}
68
69     /**
70      * Notify the host application of the url for an apple-touch-icon.
71      * @param view The XWalkView that initiated the callback.
72      * @param url The icon url.
73      * @param precomposed True if the url is for a precomposed touch icon.
74      */
75     public void onReceivedTouchIconUrl(XWalkView view, String url,
76             boolean precomposed) {}
77
78     /**
79      * A callback interface used by the host application to notify
80      * the current page that its custom view has been dismissed.
81      */
82     public interface CustomViewCallback {
83         /**
84          * Invoked when the host application dismisses the
85          * custom view.
86          */
87         public void onCustomViewHidden();
88     }
89
90     /**
91      * Notify the host application that the current page would
92      * like to show a custom View.
93      * @param view is the View object to be shown.
94      * @param callback is the callback to be invoked if and when the view
95      * is dismissed.
96      */
97     public void onShowCustomView(View view, CustomViewCallback callback) {
98         Activity activity = mXWalkView.getActivity();
99
100         if (mCustomXWalkView != null || activity == null) {
101             callback.onCustomViewHidden();
102             return;
103         }
104
105         mCustomXWalkView = view;
106         mCustomViewCallback = callback;
107
108         if (mContentsClient != null) {
109             mContentsClient.onToggleFullscreen(true);
110         }
111
112         // Add the video view to the activity's ContentView.
113         activity.getWindow().addContentView(view,
114                 new FrameLayout.LayoutParams(
115                         ViewGroup.LayoutParams.MATCH_PARENT,
116                         ViewGroup.LayoutParams.MATCH_PARENT,
117                         Gravity.CENTER));
118     }
119
120     /**
121      * Notify the host application that the current page would
122      * like to show a custom View in a particular orientation.
123      * @param view is the View object to be shown.
124      * @param requestedOrientation An orientation constant as used in
125      * {@link ActivityInfo#screenOrientation ActivityInfo.screenOrientation}.
126      * @param callback is the callback to be invoked if and when the view
127      * is dismissed.
128      */
129     public void onShowCustomView(View view, int requestedOrientation,
130             CustomViewCallback callback) {};
131
132     /**
133      * Notify the host application that the current page would
134      * like to hide its custom view.
135      */
136     public void onHideCustomView() {
137         Activity activity = mXWalkView.getActivity();
138
139         if (mCustomXWalkView == null || activity == null) return;
140
141         if (mContentsClient != null) {
142             mContentsClient.onToggleFullscreen(true);
143         }
144
145         // Remove video view from activity's ContentView.
146         FrameLayout decor = (FrameLayout) activity.getWindow().getDecorView();
147         decor.removeView(mCustomXWalkView);
148         mCustomViewCallback.onCustomViewHidden();
149
150         mCustomXWalkView = null;
151         mCustomViewCallback = null;
152     }
153
154     /**
155      * Request the host application to create a new window. If the host
156      * application chooses to honor this request, it should return true from
157      * this method, create a new XWalkView to host the window, insert it into the
158      * View system and send the supplied resultMsg message to its target with
159      * the new XWalkView as an argument. If the host application chooses not to
160      * honor the request, it should return false from this method. The default
161      * implementation of this method does nothing and hence returns false.
162      * @param view The XWalkView from which the request for a new window
163      *             originated.
164      * @param isDialog True if the new window should be a dialog, rather than
165      *                 a full-size window.
166      * @param isUserGesture True if the request was initiated by a user gesture,
167      *                      such as the user clicking a link.
168      * @param resultMsg The message to send when once a new XWalkView has been
169      *                  created. resultMsg.obj is a
170      *                  {@link XWalkView.XWalkViewTransport} object. This should be
171      *                  used to transport the new XWalkView, by calling
172      *                  {@link XWalkView.XWalkViewTransport#setXWalkView(XWalkView)
173      *                  XWalkView.XWalkViewTransport.setXWalkView(XWalkView)}.
174      * @return This method should return true if the host application will
175      *         create a new window, in which case resultMsg should be sent to
176      *         its target. Otherwise, this method should return false. Returning
177      *         false from this method but also sending resultMsg will result in
178      *         undefined behavior.
179      */
180     public boolean onCreateWindow(XWalkView view, boolean isDialog,
181             boolean isUserGesture, Message resultMsg) {
182         return false;
183     }
184
185    /**
186     * Tell the client that the quota has been exceeded for the Web SQL Database
187     * API for a particular origin and request a new quota. The client must
188     * respond by invoking the
189     * {@link WebStorage.QuotaUpdater#updateQuota(long) updateQuota(long)}
190     * method of the supplied {@link WebStorage.QuotaUpdater} instance. The
191     * minimum value that can be set for the new quota is the current quota. The
192     * default implementation responds with the current quota, so the quota will
193     * not be increased.
194     * @param url The URL of the page that triggered the notification
195     * @param databaseIdentifier The identifier of the database where the quota
196     *                           was exceeded.
197     * @param quota The quota for the origin, in bytes
198     * @param estimatedDatabaseSize The estimated size of the offending
199     *                              database, in bytes
200     * @param totalQuota The total quota for all origins, in bytes
201     * @param quotaUpdater An instance of {@link WebStorage.QuotaUpdater} which
202     *                     must be used to inform the XWalkView of the new quota.
203     */
204     // Note that the callback must always be executed at some point to ensure
205     // that the sleeping WebCore thread is woken up.
206     // Since the parameter type WebStorage.QuotaUpdater and this API are
207     // deprecated in Android 4.4, while this parameter type and this API
208     // are still used before Android 4.4, no other API and parameter are
209     // to replace them, suppress the compiling warnings for Android 4.4
210     // due to deprecation.
211     @SuppressWarnings("deprecation")
212     public void onExceededDatabaseQuota(String url, String databaseIdentifier,
213             long quota, long estimatedDatabaseSize, long totalQuota,
214             WebStorage.QuotaUpdater quotaUpdater) {
215         // This default implementation passes the current quota back to WebCore.
216         // WebCore will interpret this that new quota was declined.
217         quotaUpdater.updateQuota(XWALK_MAX_QUOTA);
218     }
219
220    /**
221     * Tell the client that the quota has been reached for the Application Cache
222     * API and request a new quota. The client must respond by invoking the
223     * {@link WebStorage.QuotaUpdater#updateQuota(long) updateQuota(long)}
224     * method of the supplied {@link WebStorage.QuotaUpdater} instance. The
225     * minimum value that can be set for the new quota is the current quota. The
226     * default implementation responds with the current quota, so the quota will
227     * not be increased.
228     * @param requiredStorage The amount of storage required by the Application
229     *                        Cache operation that triggered this notification,
230     *                        in bytes.
231     * @param quota The quota, in bytes
232     * @param quotaUpdater An instance of {@link WebStorage.QuotaUpdater} which
233     *                     must be used to inform the XWalkView of the new quota.
234     */
235     // Note that the callback must always be executed at some point to ensure
236     // that the sleeping WebCore thread is woken up.
237     // Since the parameter type WebStorage.QuotaUpdater and this API are
238     // deprecated in Android 4.4, while this parameter type and this API
239     // are still used before Android 4.4, no other API and parameter are
240     // to replace them, suppress the compiling warnings for Android 4.4
241     // due to deprecation.
242     @SuppressWarnings("deprecation")
243     public void onReachedMaxAppCacheSize(long requiredStorage, long quota,
244             WebStorage.QuotaUpdater quotaUpdater) {
245         quotaUpdater.updateQuota(XWALK_MAX_QUOTA);
246     }
247
248     /**
249      * Notify the host application that web content from the specified origin
250      * is attempting to use the Geolocation API, but no permission state is
251      * currently set for that origin. The host application should invoke the
252      * specified callback with the desired permission state. See
253      * {@link GeolocationPermissions} for details.
254      * @param origin The origin of the web content attempting to use the
255      *               Geolocation API.
256      * @param callback The callback to use to set the permission state for the
257      *                 origin.
258      */
259     public void onGeolocationPermissionsShowPrompt(String origin,
260             XWalkGeolocationPermissions.Callback callback) {
261         // Allow all origins for geolocation requests here for Crosswalk.
262         // TODO(yongsheng): Need to define a UI prompt?
263         callback.invoke(origin, true, false);
264     }
265
266     /**
267      * Notify the host application that a request for Geolocation permissions,
268      * made with a previous call to
269      * {@link #onGeolocationPermissionsShowPrompt(String,GeolocationPermissions.Callback) onGeolocationPermissionsShowPrompt()}
270      * has been canceled. Any related UI should therefore be hidden.
271      */
272     public void onGeolocationPermissionsHidePrompt() {}
273
274     /**
275      * Tell the client that a JavaScript execution timeout has occured. And the
276      * client may decide whether or not to interrupt the execution. If the
277      * client returns true, the JavaScript will be interrupted. If the client
278      * returns false, the execution will continue. Note that in the case of
279      * continuing execution, the timeout counter will be reset, and the callback
280      * will continue to occur if the script does not finish at the next check
281      * point.
282      * @return boolean Whether the JavaScript execution should be interrupted.
283      */
284     public boolean onJsTimeout() {
285         return true;
286     }
287
288     /**
289      * Report a JavaScript error message to the host application. The ChromeClient
290      * should override this to process the log message as they see fit.
291      * @param message The error message to report.
292      * @param lineNumber The line number of the error.
293      * @param sourceID The name of the source file that caused the error.
294      * @deprecated Use {@link #onConsoleMessage(ConsoleMessage) onConsoleMessage(ConsoleMessage)}
295      *      instead.
296      */
297     @Deprecated
298     public void onConsoleMessage(String message, int lineNumber, String sourceID) { }
299
300     /**
301      * Report a JavaScript console message to the host application. The ChromeClient
302      * should override this to process the log message as they see fit.
303      * @param consoleMessage Object containing details of the console message.
304      * @return true if the message is handled by the client.
305      */
306     public boolean onConsoleMessage(ConsoleMessage consoleMessage) {
307         // Call the old version of this function for backwards compatability.
308         onConsoleMessage(consoleMessage.message(), consoleMessage.lineNumber(),
309                 consoleMessage.sourceId());
310         return false;
311     }
312
313     /**
314      * When not playing, video elements are represented by a 'poster' image. The
315      * image to use can be specified by the poster attribute of the video tag in
316      * HTML. If the attribute is absent, then a default poster will be used. This
317      * method allows the ChromeClient to provide that default image.
318      *
319      * @return Bitmap The image to use as a default poster, or null if no such image is
320      * available.
321      */
322     public Bitmap getDefaultVideoPoster() {
323         return null;
324     }
325
326     /**
327      * When the user starts to playback a video element, it may take time for enough
328      * data to be buffered before the first frames can be rendered. While this buffering
329      * is taking place, the ChromeClient can use this function to provide a View to be
330      * displayed. For example, the ChromeClient could show a spinner animation.
331      *
332      * @return View The View to be displayed whilst the video is loading.
333      */
334     public View getVideoLoadingProgressView() {
335         return null;
336     }
337
338     /** Obtains a list of all visited history items, used for link coloring
339      */
340     public void getVisitedHistory(ValueCallback<String[]> callback) {
341     }
342
343     /**
344      * Tell the client that the page being viewed is web app capable,
345      * i.e. has specified the fullscreen-web-app-capable meta tag.
346      * @hide
347      */
348     public void setInstallableWebApp() { }
349
350     /**
351      * Tell the client that the page being viewed has an autofillable
352      * form and the user would like to set a profile up.
353      * @param msg A Message to send once the user has successfully
354      *      set up a profile and to inform the WebTextView it should
355      *      now autofill using that new profile.
356      * @hide
357      */
358     public void setupAutoFill(Message msg) { }
359 }