Home | History | Annotate | Download | only in webkit
      1 /*
      2  * Copyright (C) 2006 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 android.webkit;
     18 
     19 import android.annotation.IntDef;
     20 import android.annotation.NonNull;
     21 import android.annotation.Nullable;
     22 import android.annotation.SystemApi;
     23 import android.annotation.Widget;
     24 import android.content.Context;
     25 import android.content.Intent;
     26 import android.content.pm.PackageInfo;
     27 import android.content.res.Configuration;
     28 import android.graphics.Bitmap;
     29 import android.graphics.Canvas;
     30 import android.graphics.Paint;
     31 import android.graphics.Picture;
     32 import android.graphics.Rect;
     33 import android.graphics.drawable.Drawable;
     34 import android.net.Uri;
     35 import android.net.http.SslCertificate;
     36 import android.os.Build;
     37 import android.os.Bundle;
     38 import android.os.Handler;
     39 import android.os.Looper;
     40 import android.os.Message;
     41 import android.os.RemoteException;
     42 import android.os.StrictMode;
     43 import android.print.PrintDocumentAdapter;
     44 import android.security.KeyChain;
     45 import android.util.AttributeSet;
     46 import android.util.Log;
     47 import android.util.SparseArray;
     48 import android.view.DragEvent;
     49 import android.view.KeyEvent;
     50 import android.view.MotionEvent;
     51 import android.view.View;
     52 import android.view.ViewDebug;
     53 import android.view.ViewGroup;
     54 import android.view.ViewHierarchyEncoder;
     55 import android.view.ViewStructure;
     56 import android.view.ViewTreeObserver;
     57 import android.view.accessibility.AccessibilityEvent;
     58 import android.view.accessibility.AccessibilityNodeInfo;
     59 import android.view.accessibility.AccessibilityNodeProvider;
     60 import android.view.autofill.AutofillValue;
     61 import android.view.inputmethod.EditorInfo;
     62 import android.view.inputmethod.InputConnection;
     63 import android.view.textclassifier.TextClassifier;
     64 import android.widget.AbsoluteLayout;
     65 
     66 import java.io.BufferedWriter;
     67 import java.io.File;
     68 import java.lang.annotation.Retention;
     69 import java.lang.annotation.RetentionPolicy;
     70 import java.util.List;
     71 import java.util.Map;
     72 
     73 /**
     74  * <p>A View that displays web pages. This class is the basis upon which you
     75  * can roll your own web browser or simply display some online content within your Activity.
     76  * It uses the WebKit rendering engine to display
     77  * web pages and includes methods to navigate forward and backward
     78  * through a history, zoom in and out, perform text searches and more.
     79  *
     80  * <p>Note that, in order for your Activity to access the Internet and load web pages
     81  * in a WebView, you must add the {@code INTERNET} permissions to your
     82  * Android Manifest file:
     83  *
     84  * <pre>
     85  * {@code <uses-permission android:name="android.permission.INTERNET" />}
     86  * </pre>
     87  *
     88  * <p>This must be a child of the <a
     89  * href="{@docRoot}guide/topics/manifest/manifest-element.html">{@code <manifest>}</a>
     90  * element.
     91  *
     92  * <p>For more information, read
     93  * <a href="{@docRoot}guide/webapps/webview.html">Building Web Apps in WebView</a>.
     94  *
     95  * <h3>Basic usage</h3>
     96  *
     97  * <p>By default, a WebView provides no browser-like widgets, does not
     98  * enable JavaScript and web page errors are ignored. If your goal is only
     99  * to display some HTML as a part of your UI, this is probably fine;
    100  * the user won't need to interact with the web page beyond reading
    101  * it, and the web page won't need to interact with the user. If you
    102  * actually want a full-blown web browser, then you probably want to
    103  * invoke the Browser application with a URL Intent rather than show it
    104  * with a WebView. For example:
    105  * <pre>
    106  * Uri uri = Uri.parse("https://www.example.com");
    107  * Intent intent = new Intent(Intent.ACTION_VIEW, uri);
    108  * startActivity(intent);
    109  * </pre>
    110  * <p>See {@link android.content.Intent} for more information.
    111  *
    112  * <p>To provide a WebView in your own Activity, include a {@code <WebView>} in your layout,
    113  * or set the entire Activity window as a WebView during {@link
    114  * android.app.Activity#onCreate(Bundle) onCreate()}:
    115  *
    116  * <pre class="prettyprint">
    117  * WebView webview = new WebView(this);
    118  * setContentView(webview);
    119  * </pre>
    120  *
    121  * <p>Then load the desired web page:
    122  *
    123  * <pre>
    124  * // Simplest usage: note that an exception will NOT be thrown
    125  * // if there is an error loading this page (see below).
    126  * webview.loadUrl("https://example.com/");
    127  *
    128  * // OR, you can also load from an HTML string:
    129  * String summary = "&lt;html>&lt;body>You scored &lt;b>192&lt;/b> points.&lt;/body>&lt;/html>";
    130  * webview.loadData(summary, "text/html", null);
    131  * // ... although note that there are restrictions on what this HTML can do.
    132  * // See {@link #loadData(String,String,String)} and {@link
    133  * #loadDataWithBaseURL(String,String,String,String,String)} for more info.
    134  * // Also see {@link #loadData(String,String,String)} for information on encoding special
    135  * // characters.
    136  * </pre>
    137  *
    138  * <p>A WebView has several customization points where you can add your
    139  * own behavior. These are:
    140  *
    141  * <ul>
    142  *   <li>Creating and setting a {@link android.webkit.WebChromeClient} subclass.
    143  *       This class is called when something that might impact a
    144  *       browser UI happens, for instance, progress updates and
    145  *       JavaScript alerts are sent here (see <a
    146  * href="{@docRoot}guide/developing/debug-tasks.html#DebuggingWebPages">Debugging Tasks</a>).
    147  *   </li>
    148  *   <li>Creating and setting a {@link android.webkit.WebViewClient} subclass.
    149  *       It will be called when things happen that impact the
    150  *       rendering of the content, eg, errors or form submissions. You
    151  *       can also intercept URL loading here (via {@link
    152  * android.webkit.WebViewClient#shouldOverrideUrlLoading(WebView,String)
    153  * shouldOverrideUrlLoading()}).</li>
    154  *   <li>Modifying the {@link android.webkit.WebSettings}, such as
    155  * enabling JavaScript with {@link android.webkit.WebSettings#setJavaScriptEnabled(boolean)
    156  * setJavaScriptEnabled()}. </li>
    157  *   <li>Injecting Java objects into the WebView using the
    158  *       {@link android.webkit.WebView#addJavascriptInterface} method. This
    159  *       method allows you to inject Java objects into a page's JavaScript
    160  *       context, so that they can be accessed by JavaScript in the page.</li>
    161  * </ul>
    162  *
    163  * <p>Here's a more complicated example, showing error handling,
    164  *    settings, and progress notification:
    165  *
    166  * <pre class="prettyprint">
    167  * // Let's display the progress in the activity title bar, like the
    168  * // browser app does.
    169  * getWindow().requestFeature(Window.FEATURE_PROGRESS);
    170  *
    171  * webview.getSettings().setJavaScriptEnabled(true);
    172  *
    173  * final Activity activity = this;
    174  * webview.setWebChromeClient(new WebChromeClient() {
    175  *   public void onProgressChanged(WebView view, int progress) {
    176  *     // Activities and WebViews measure progress with different scales.
    177  *     // The progress meter will automatically disappear when we reach 100%
    178  *     activity.setProgress(progress * 1000);
    179  *   }
    180  * });
    181  * webview.setWebViewClient(new WebViewClient() {
    182  *   public void onReceivedError(WebView view, int errorCode, String description, String failingUrl) {
    183  *     Toast.makeText(activity, "Oh no! " + description, Toast.LENGTH_SHORT).show();
    184  *   }
    185  * });
    186  *
    187  * webview.loadUrl("https://developer.android.com/");
    188  * </pre>
    189  *
    190  * <h3>Zoom</h3>
    191  *
    192  * <p>To enable the built-in zoom, set
    193  * {@link #getSettings() WebSettings}.{@link WebSettings#setBuiltInZoomControls(boolean)}
    194  * (introduced in API level {@link android.os.Build.VERSION_CODES#CUPCAKE}).
    195  *
    196  * <p class="note"><b>Note:</b> Using zoom if either the height or width is set to
    197  * {@link android.view.ViewGroup.LayoutParams#WRAP_CONTENT} may lead to undefined behavior
    198  * and should be avoided.
    199  *
    200  * <h3>Cookie and window management</h3>
    201  *
    202  * <p>For obvious security reasons, your application has its own
    203  * cache, cookie store etc.&mdash;it does not share the Browser
    204  * application's data.
    205  *
    206  * <p>By default, requests by the HTML to open new windows are
    207  * ignored. This is {@code true} whether they be opened by JavaScript or by
    208  * the target attribute on a link. You can customize your
    209  * {@link WebChromeClient} to provide your own behavior for opening multiple windows,
    210  * and render them in whatever manner you want.
    211  *
    212  * <p>The standard behavior for an Activity is to be destroyed and
    213  * recreated when the device orientation or any other configuration changes. This will cause
    214  * the WebView to reload the current page. If you don't want that, you
    215  * can set your Activity to handle the {@code orientation} and {@code keyboardHidden}
    216  * changes, and then just leave the WebView alone. It'll automatically
    217  * re-orient itself as appropriate. Read <a
    218  * href="{@docRoot}guide/topics/resources/runtime-changes.html">Handling Runtime Changes</a> for
    219  * more information about how to handle configuration changes during runtime.
    220  *
    221  *
    222  * <h3>Building web pages to support different screen densities</h3>
    223  *
    224  * <p>The screen density of a device is based on the screen resolution. A screen with low density
    225  * has fewer available pixels per inch, where a screen with high density
    226  * has more &mdash; sometimes significantly more &mdash; pixels per inch. The density of a
    227  * screen is important because, other things being equal, a UI element (such as a button) whose
    228  * height and width are defined in terms of screen pixels will appear larger on the lower density
    229  * screen and smaller on the higher density screen.
    230  * For simplicity, Android collapses all actual screen densities into three generalized densities:
    231  * high, medium, and low.
    232  * <p>By default, WebView scales a web page so that it is drawn at a size that matches the default
    233  * appearance on a medium density screen. So, it applies 1.5x scaling on a high density screen
    234  * (because its pixels are smaller) and 0.75x scaling on a low density screen (because its pixels
    235  * are bigger).
    236  * Starting with API level {@link android.os.Build.VERSION_CODES#ECLAIR}, WebView supports DOM, CSS,
    237  * and meta tag features to help you (as a web developer) target screens with different screen
    238  * densities.
    239  * <p>Here's a summary of the features you can use to handle different screen densities:
    240  * <ul>
    241  * <li>The {@code window.devicePixelRatio} DOM property. The value of this property specifies the
    242  * default scaling factor used for the current device. For example, if the value of {@code
    243  * window.devicePixelRatio} is "1.0", then the device is considered a medium density (mdpi) device
    244  * and default scaling is not applied to the web page; if the value is "1.5", then the device is
    245  * considered a high density device (hdpi) and the page content is scaled 1.5x; if the
    246  * value is "0.75", then the device is considered a low density device (ldpi) and the content is
    247  * scaled 0.75x.</li>
    248  * <li>The {@code -webkit-device-pixel-ratio} CSS media query. Use this to specify the screen
    249  * densities for which this style sheet is to be used. The corresponding value should be either
    250  * "0.75", "1", or "1.5", to indicate that the styles are for devices with low density, medium
    251  * density, or high density screens, respectively. For example:
    252  * <pre>
    253  * &lt;link rel="stylesheet" media="screen and (-webkit-device-pixel-ratio:1.5)" href="hdpi.css" /&gt;</pre>
    254  * <p>The {@code hdpi.css} stylesheet is only used for devices with a screen pixel ratio of 1.5,
    255  * which is the high density pixel ratio.
    256  * </li>
    257  * </ul>
    258  *
    259  * <h3>HTML5 Video support</h3>
    260  *
    261  * <p>In order to support inline HTML5 video in your application you need to have hardware
    262  * acceleration turned on.
    263  *
    264  * <h3>Full screen support</h3>
    265  *
    266  * <p>In order to support full screen &mdash; for video or other HTML content &mdash; you need to set a
    267  * {@link android.webkit.WebChromeClient} and implement both
    268  * {@link WebChromeClient#onShowCustomView(View, WebChromeClient.CustomViewCallback)}
    269  * and {@link WebChromeClient#onHideCustomView()}. If the implementation of either of these two methods is
    270  * missing then the web contents will not be allowed to enter full screen. Optionally you can implement
    271  * {@link WebChromeClient#getVideoLoadingProgressView()} to customize the View displayed whilst a video
    272  * is loading.
    273  *
    274  * <h3>HTML5 Geolocation API support</h3>
    275  *
    276  * <p>For applications targeting Android N and later releases
    277  * (API level > {@link android.os.Build.VERSION_CODES#M}) the geolocation api is only supported on
    278  * secure origins such as https. For such applications requests to geolocation api on non-secure
    279  * origins are automatically denied without invoking the corresponding
    280  * {@link WebChromeClient#onGeolocationPermissionsShowPrompt(String, GeolocationPermissions.Callback)}
    281  * method.
    282  *
    283  * <h3>Layout size</h3>
    284  * <p>
    285  * It is recommended to set the WebView layout height to a fixed value or to
    286  * {@link android.view.ViewGroup.LayoutParams#MATCH_PARENT} instead of using
    287  * {@link android.view.ViewGroup.LayoutParams#WRAP_CONTENT}.
    288  * When using {@link android.view.ViewGroup.LayoutParams#MATCH_PARENT}
    289  * for the height none of the WebView's parents should use a
    290  * {@link android.view.ViewGroup.LayoutParams#WRAP_CONTENT} layout height since that could result in
    291  * incorrect sizing of the views.
    292  *
    293  * <p>Setting the WebView's height to {@link android.view.ViewGroup.LayoutParams#WRAP_CONTENT}
    294  * enables the following behaviors:
    295  * <ul>
    296  * <li>The HTML body layout height is set to a fixed value. This means that elements with a height
    297  * relative to the HTML body may not be sized correctly. </li>
    298  * <li>For applications targeting {@link android.os.Build.VERSION_CODES#KITKAT} and earlier SDKs the
    299  * HTML viewport meta tag will be ignored in order to preserve backwards compatibility. </li>
    300  * </ul>
    301  *
    302  * <p>
    303  * Using a layout width of {@link android.view.ViewGroup.LayoutParams#WRAP_CONTENT} is not
    304  * supported. If such a width is used the WebView will attempt to use the width of the parent
    305  * instead.
    306  *
    307  * <h3>Metrics</h3>
    308  *
    309  * <p>
    310  * WebView may upload anonymous diagnostic data to Google when the user has consented. This data
    311  * helps Google improve WebView. Data is collected on a per-app basis for each app which has
    312  * instantiated a WebView. An individual app can opt out of this feature by putting the following
    313  * tag in its manifest's {@code <application>} element:
    314  * <pre>
    315  * &lt;manifest&gt;
    316  *     &lt;application&gt;
    317  *         ...
    318  *         &lt;meta-data android:name=&quot;android.webkit.WebView.MetricsOptOut&quot;
    319  *             android:value=&quot;true&quot; /&gt;
    320  *     &lt;/application&gt;
    321  * &lt;/manifest&gt;
    322  * </pre>
    323  * <p>
    324  * Data will only be uploaded for a given app if the user has consented AND the app has not opted
    325  * out.
    326  *
    327  * <h3>Safe Browsing</h3>
    328  *
    329  * <p>
    330  * With Safe Browsing, WebView will block malicious URLs and present a warning UI to the user to
    331  * allow them to navigate back safely or proceed to the malicious page.
    332  * <p>
    333  * Safe Browsing is enabled by default on devices which support it. If your app needs to disable
    334  * Safe Browsing for all WebViews, it can do so in the manifest's {@code <application>} element:
    335  * <p>
    336  * <pre>
    337  * &lt;manifest&gt;
    338  *     &lt;application&gt;
    339  *         ...
    340  *         &lt;meta-data android:name=&quot;android.webkit.WebView.EnableSafeBrowsing&quot;
    341  *             android:value=&quot;false&quot; /&gt;
    342  *     &lt;/application&gt;
    343  * &lt;/manifest&gt;
    344  * </pre>
    345  *
    346  * <p>
    347  * Otherwise, see {@link WebSettings#setSafeBrowsingEnabled}.
    348  *
    349  */
    350 // Implementation notes.
    351 // The WebView is a thin API class that delegates its public API to a backend WebViewProvider
    352 // class instance. WebView extends {@link AbsoluteLayout} for backward compatibility reasons.
    353 // Methods are delegated to the provider implementation: all public API methods introduced in this
    354 // file are fully delegated, whereas public and protected methods from the View base classes are
    355 // only delegated where a specific need exists for them to do so.
    356 @Widget
    357 public class WebView extends AbsoluteLayout
    358         implements ViewTreeObserver.OnGlobalFocusChangeListener,
    359         ViewGroup.OnHierarchyChangeListener, ViewDebug.HierarchyHandler {
    360 
    361     private static final String LOGTAG = "WebView";
    362 
    363     // Throwing an exception for incorrect thread usage if the
    364     // build target is JB MR2 or newer. Defaults to false, and is
    365     // set in the WebView constructor.
    366     private static volatile boolean sEnforceThreadChecking = false;
    367 
    368     /**
    369      *  Transportation object for returning WebView across thread boundaries.
    370      */
    371     public class WebViewTransport {
    372         private WebView mWebview;
    373 
    374         /**
    375          * Sets the WebView to the transportation object.
    376          *
    377          * @param webview the WebView to transport
    378          */
    379         public synchronized void setWebView(WebView webview) {
    380             mWebview = webview;
    381         }
    382 
    383         /**
    384          * Gets the WebView object.
    385          *
    386          * @return the transported WebView object
    387          */
    388         public synchronized WebView getWebView() {
    389             return mWebview;
    390         }
    391     }
    392 
    393     /**
    394      * URI scheme for telephone number.
    395      */
    396     public static final String SCHEME_TEL = "tel:";
    397     /**
    398      * URI scheme for email address.
    399      */
    400     public static final String SCHEME_MAILTO = "mailto:";
    401     /**
    402      * URI scheme for map address.
    403      */
    404     public static final String SCHEME_GEO = "geo:0,0?q=";
    405 
    406     /**
    407      * Interface to listen for find results.
    408      */
    409     public interface FindListener {
    410         /**
    411          * Notifies the listener about progress made by a find operation.
    412          *
    413          * @param activeMatchOrdinal the zero-based ordinal of the currently selected match
    414          * @param numberOfMatches how many matches have been found
    415          * @param isDoneCounting whether the find operation has actually completed. The listener
    416          *                       may be notified multiple times while the
    417          *                       operation is underway, and the numberOfMatches
    418          *                       value should not be considered final unless
    419          *                       isDoneCounting is {@code true}.
    420          */
    421         public void onFindResultReceived(int activeMatchOrdinal, int numberOfMatches,
    422             boolean isDoneCounting);
    423     }
    424 
    425     /**
    426      * Callback interface supplied to {@link #postVisualStateCallback} for receiving
    427      * notifications about the visual state.
    428      */
    429     public static abstract class VisualStateCallback {
    430         /**
    431          * Invoked when the visual state is ready to be drawn in the next {@link #onDraw}.
    432          *
    433          * @param requestId The identifier passed to {@link #postVisualStateCallback} when this
    434          *                  callback was posted.
    435          */
    436         public abstract void onComplete(long requestId);
    437     }
    438 
    439     /**
    440      * Interface to listen for new pictures as they change.
    441      *
    442      * @deprecated This interface is now obsolete.
    443      */
    444     @Deprecated
    445     public interface PictureListener {
    446         /**
    447          * Used to provide notification that the WebView's picture has changed.
    448          * See {@link WebView#capturePicture} for details of the picture.
    449          *
    450          * @param view the WebView that owns the picture
    451          * @param picture the new picture. Applications targeting
    452          *     {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR2} or above
    453          *     will always receive a {@code null} Picture.
    454          * @deprecated Deprecated due to internal changes.
    455          */
    456         @Deprecated
    457         void onNewPicture(WebView view, @Nullable Picture picture);
    458     }
    459 
    460     public static class HitTestResult {
    461         /**
    462          * Default HitTestResult, where the target is unknown.
    463          */
    464         public static final int UNKNOWN_TYPE = 0;
    465         /**
    466          * @deprecated This type is no longer used.
    467          */
    468         @Deprecated
    469         public static final int ANCHOR_TYPE = 1;
    470         /**
    471          * HitTestResult for hitting a phone number.
    472          */
    473         public static final int PHONE_TYPE = 2;
    474         /**
    475          * HitTestResult for hitting a map address.
    476          */
    477         public static final int GEO_TYPE = 3;
    478         /**
    479          * HitTestResult for hitting an email address.
    480          */
    481         public static final int EMAIL_TYPE = 4;
    482         /**
    483          * HitTestResult for hitting an HTML::img tag.
    484          */
    485         public static final int IMAGE_TYPE = 5;
    486         /**
    487          * @deprecated This type is no longer used.
    488          */
    489         @Deprecated
    490         public static final int IMAGE_ANCHOR_TYPE = 6;
    491         /**
    492          * HitTestResult for hitting a HTML::a tag with src=http.
    493          */
    494         public static final int SRC_ANCHOR_TYPE = 7;
    495         /**
    496          * HitTestResult for hitting a HTML::a tag with src=http + HTML::img.
    497          */
    498         public static final int SRC_IMAGE_ANCHOR_TYPE = 8;
    499         /**
    500          * HitTestResult for hitting an edit text area.
    501          */
    502         public static final int EDIT_TEXT_TYPE = 9;
    503 
    504         private int mType;
    505         private String mExtra;
    506 
    507         /**
    508          * @hide Only for use by WebViewProvider implementations
    509          */
    510         @SystemApi
    511         public HitTestResult() {
    512             mType = UNKNOWN_TYPE;
    513         }
    514 
    515         /**
    516          * @hide Only for use by WebViewProvider implementations
    517          */
    518         @SystemApi
    519         public void setType(int type) {
    520             mType = type;
    521         }
    522 
    523         /**
    524          * @hide Only for use by WebViewProvider implementations
    525          */
    526         @SystemApi
    527         public void setExtra(String extra) {
    528             mExtra = extra;
    529         }
    530 
    531         /**
    532          * Gets the type of the hit test result. See the XXX_TYPE constants
    533          * defined in this class.
    534          *
    535          * @return the type of the hit test result
    536          */
    537         public int getType() {
    538             return mType;
    539         }
    540 
    541         /**
    542          * Gets additional type-dependant information about the result. See
    543          * {@link WebView#getHitTestResult()} for details. May either be {@code null}
    544          * or contain extra information about this result.
    545          *
    546          * @return additional type-dependant information about the result
    547          */
    548         @Nullable
    549         public String getExtra() {
    550             return mExtra;
    551         }
    552     }
    553 
    554     /**
    555      * Constructs a new WebView with an Activity Context object.
    556      *
    557      * <p class="note"><b>Note:</b> WebView should always be instantiated with an Activity Context.
    558      * If instantiated with an Application Context, WebView will be unable to provide several
    559      * features, such as JavaScript dialogs and autofill.
    560      *
    561      * @param context an Activity Context to access application assets
    562      */
    563     public WebView(Context context) {
    564         this(context, null);
    565     }
    566 
    567     /**
    568      * Constructs a new WebView with layout parameters.
    569      *
    570      * @param context an Activity Context to access application assets
    571      * @param attrs an AttributeSet passed to our parent
    572      */
    573     public WebView(Context context, AttributeSet attrs) {
    574         this(context, attrs, com.android.internal.R.attr.webViewStyle);
    575     }
    576 
    577     /**
    578      * Constructs a new WebView with layout parameters and a default style.
    579      *
    580      * @param context an Activity Context to access application assets
    581      * @param attrs an AttributeSet passed to our parent
    582      * @param defStyleAttr an attribute in the current theme that contains a
    583      *        reference to a style resource that supplies default values for
    584      *        the view. Can be 0 to not look for defaults.
    585      */
    586     public WebView(Context context, AttributeSet attrs, int defStyleAttr) {
    587         this(context, attrs, defStyleAttr, 0);
    588     }
    589 
    590     /**
    591      * Constructs a new WebView with layout parameters and a default style.
    592      *
    593      * @param context an Activity Context to access application assets
    594      * @param attrs an AttributeSet passed to our parent
    595      * @param defStyleAttr an attribute in the current theme that contains a
    596      *        reference to a style resource that supplies default values for
    597      *        the view. Can be 0 to not look for defaults.
    598      * @param defStyleRes a resource identifier of a style resource that
    599      *        supplies default values for the view, used only if
    600      *        defStyleAttr is 0 or can not be found in the theme. Can be 0
    601      *        to not look for defaults.
    602      */
    603     public WebView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes) {
    604         this(context, attrs, defStyleAttr, defStyleRes, null, false);
    605     }
    606 
    607     /**
    608      * Constructs a new WebView with layout parameters and a default style.
    609      *
    610      * @param context an Activity Context to access application assets
    611      * @param attrs an AttributeSet passed to our parent
    612      * @param defStyleAttr an attribute in the current theme that contains a
    613      *        reference to a style resource that supplies default values for
    614      *        the view. Can be 0 to not look for defaults.
    615      * @param privateBrowsing whether this WebView will be initialized in
    616      *                        private mode
    617      *
    618      * @deprecated Private browsing is no longer supported directly via
    619      * WebView and will be removed in a future release. Prefer using
    620      * {@link WebSettings}, {@link WebViewDatabase}, {@link CookieManager}
    621      * and {@link WebStorage} for fine-grained control of privacy data.
    622      */
    623     @Deprecated
    624     public WebView(Context context, AttributeSet attrs, int defStyleAttr,
    625             boolean privateBrowsing) {
    626         this(context, attrs, defStyleAttr, 0, null, privateBrowsing);
    627     }
    628 
    629     /**
    630      * Constructs a new WebView with layout parameters, a default style and a set
    631      * of custom JavaScript interfaces to be added to this WebView at initialization
    632      * time. This guarantees that these interfaces will be available when the JS
    633      * context is initialized.
    634      *
    635      * @param context an Activity Context to access application assets
    636      * @param attrs an AttributeSet passed to our parent
    637      * @param defStyleAttr an attribute in the current theme that contains a
    638      *        reference to a style resource that supplies default values for
    639      *        the view. Can be 0 to not look for defaults.
    640      * @param javaScriptInterfaces a Map of interface names, as keys, and
    641      *                             object implementing those interfaces, as
    642      *                             values
    643      * @param privateBrowsing whether this WebView will be initialized in
    644      *                        private mode
    645      * @hide This is used internally by dumprendertree, as it requires the JavaScript interfaces to
    646      *       be added synchronously, before a subsequent loadUrl call takes effect.
    647      */
    648     protected WebView(Context context, AttributeSet attrs, int defStyleAttr,
    649             Map<String, Object> javaScriptInterfaces, boolean privateBrowsing) {
    650         this(context, attrs, defStyleAttr, 0, javaScriptInterfaces, privateBrowsing);
    651     }
    652 
    653     /**
    654      * @hide
    655      */
    656     @SuppressWarnings("deprecation")  // for super() call into deprecated base class constructor.
    657     protected WebView(Context context, AttributeSet attrs, int defStyleAttr, int defStyleRes,
    658             Map<String, Object> javaScriptInterfaces, boolean privateBrowsing) {
    659         super(context, attrs, defStyleAttr, defStyleRes);
    660 
    661         // WebView is important by default, unless app developer overrode attribute.
    662         if (getImportantForAutofill() == IMPORTANT_FOR_AUTOFILL_AUTO) {
    663             setImportantForAutofill(IMPORTANT_FOR_AUTOFILL_YES);
    664         }
    665 
    666         if (context == null) {
    667             throw new IllegalArgumentException("Invalid context argument");
    668         }
    669         if (mWebViewThread == null) {
    670             throw new RuntimeException(
    671                 "WebView cannot be initialized on a thread that has no Looper.");
    672         }
    673         sEnforceThreadChecking = context.getApplicationInfo().targetSdkVersion >=
    674                 Build.VERSION_CODES.JELLY_BEAN_MR2;
    675         checkThread();
    676 
    677         ensureProviderCreated();
    678         mProvider.init(javaScriptInterfaces, privateBrowsing);
    679         // Post condition of creating a webview is the CookieSyncManager.getInstance() is allowed.
    680         CookieSyncManager.setGetInstanceIsAllowed();
    681     }
    682 
    683     /**
    684      * Specifies whether the horizontal scrollbar has overlay style.
    685      *
    686      * @deprecated This method has no effect.
    687      * @param overlay {@code true} if horizontal scrollbar should have overlay style
    688      */
    689     @Deprecated
    690     public void setHorizontalScrollbarOverlay(boolean overlay) {
    691     }
    692 
    693     /**
    694      * Specifies whether the vertical scrollbar has overlay style.
    695      *
    696      * @deprecated This method has no effect.
    697      * @param overlay {@code true} if vertical scrollbar should have overlay style
    698      */
    699     @Deprecated
    700     public void setVerticalScrollbarOverlay(boolean overlay) {
    701     }
    702 
    703     /**
    704      * Gets whether horizontal scrollbar has overlay style.
    705      *
    706      * @deprecated This method is now obsolete.
    707      * @return {@code true}
    708      */
    709     @Deprecated
    710     public boolean overlayHorizontalScrollbar() {
    711         // The old implementation defaulted to true, so return true for consistency
    712         return true;
    713     }
    714 
    715     /**
    716      * Gets whether vertical scrollbar has overlay style.
    717      *
    718      * @deprecated This method is now obsolete.
    719      * @return {@code false}
    720      */
    721     @Deprecated
    722     public boolean overlayVerticalScrollbar() {
    723         // The old implementation defaulted to false, so return false for consistency
    724         return false;
    725     }
    726 
    727     /**
    728      * Gets the visible height (in pixels) of the embedded title bar (if any).
    729      *
    730      * @deprecated This method is now obsolete.
    731      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
    732      */
    733     @Deprecated
    734     public int getVisibleTitleHeight() {
    735         checkThread();
    736         return mProvider.getVisibleTitleHeight();
    737     }
    738 
    739     /**
    740      * Gets the SSL certificate for the main top-level page or {@code null} if there is
    741      * no certificate (the site is not secure).
    742      *
    743      * @return the SSL certificate for the main top-level page
    744      */
    745     @Nullable
    746     public SslCertificate getCertificate() {
    747         checkThread();
    748         return mProvider.getCertificate();
    749     }
    750 
    751     /**
    752      * Sets the SSL certificate for the main top-level page.
    753      *
    754      * @deprecated Calling this function has no useful effect, and will be
    755      * ignored in future releases.
    756      */
    757     @Deprecated
    758     public void setCertificate(SslCertificate certificate) {
    759         checkThread();
    760         mProvider.setCertificate(certificate);
    761     }
    762 
    763     //-------------------------------------------------------------------------
    764     // Methods called by activity
    765     //-------------------------------------------------------------------------
    766 
    767     /**
    768      * Sets a username and password pair for the specified host. This data is
    769      * used by the WebView to autocomplete username and password fields in web
    770      * forms. Note that this is unrelated to the credentials used for HTTP
    771      * authentication.
    772      *
    773      * @param host the host that required the credentials
    774      * @param username the username for the given host
    775      * @param password the password for the given host
    776      * @see WebViewDatabase#clearUsernamePassword
    777      * @see WebViewDatabase#hasUsernamePassword
    778      * @deprecated Saving passwords in WebView will not be supported in future versions.
    779      */
    780     @Deprecated
    781     public void savePassword(String host, String username, String password) {
    782         checkThread();
    783         mProvider.savePassword(host, username, password);
    784     }
    785 
    786     /**
    787      * Stores HTTP authentication credentials for a given host and realm to the {@link WebViewDatabase}
    788      * instance.
    789      *
    790      * @param host the host to which the credentials apply
    791      * @param realm the realm to which the credentials apply
    792      * @param username the username
    793      * @param password the password
    794      * @deprecated Use {@link WebViewDatabase#setHttpAuthUsernamePassword} instead
    795      */
    796     @Deprecated
    797     public void setHttpAuthUsernamePassword(String host, String realm,
    798             String username, String password) {
    799         checkThread();
    800         mProvider.setHttpAuthUsernamePassword(host, realm, username, password);
    801     }
    802 
    803     /**
    804      * Retrieves HTTP authentication credentials for a given host and realm from the {@link
    805      * WebViewDatabase} instance.
    806      * @param host the host to which the credentials apply
    807      * @param realm the realm to which the credentials apply
    808      * @return the credentials as a String array, if found. The first element
    809      *         is the username and the second element is the password. {@code null} if
    810      *         no credentials are found.
    811      * @deprecated Use {@link WebViewDatabase#getHttpAuthUsernamePassword} instead
    812      */
    813     @Deprecated
    814     @Nullable
    815     public String[] getHttpAuthUsernamePassword(String host, String realm) {
    816         checkThread();
    817         return mProvider.getHttpAuthUsernamePassword(host, realm);
    818     }
    819 
    820     /**
    821      * Destroys the internal state of this WebView. This method should be called
    822      * after this WebView has been removed from the view system. No other
    823      * methods may be called on this WebView after destroy.
    824      */
    825     public void destroy() {
    826         checkThread();
    827         mProvider.destroy();
    828     }
    829 
    830     /**
    831      * Enables platform notifications of data state and proxy changes.
    832      * Notifications are enabled by default.
    833      *
    834      * @deprecated This method is now obsolete.
    835      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
    836      */
    837     @Deprecated
    838     public static void enablePlatformNotifications() {
    839         // noop
    840     }
    841 
    842     /**
    843      * Disables platform notifications of data state and proxy changes.
    844      * Notifications are enabled by default.
    845      *
    846      * @deprecated This method is now obsolete.
    847      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
    848      */
    849     @Deprecated
    850     public static void disablePlatformNotifications() {
    851         // noop
    852     }
    853 
    854     /**
    855      * Used only by internal tests to free up memory.
    856      *
    857      * @hide
    858      */
    859     public static void freeMemoryForTests() {
    860         getFactory().getStatics().freeMemoryForTests();
    861     }
    862 
    863     /**
    864      * Informs WebView of the network state. This is used to set
    865      * the JavaScript property window.navigator.isOnline and
    866      * generates the online/offline event as specified in HTML5, sec. 5.7.7
    867      *
    868      * @param networkUp a boolean indicating if network is available
    869      */
    870     public void setNetworkAvailable(boolean networkUp) {
    871         checkThread();
    872         mProvider.setNetworkAvailable(networkUp);
    873     }
    874 
    875     /**
    876      * Saves the state of this WebView used in
    877      * {@link android.app.Activity#onSaveInstanceState}. Please note that this
    878      * method no longer stores the display data for this WebView. The previous
    879      * behavior could potentially leak files if {@link #restoreState} was never
    880      * called.
    881      *
    882      * @param outState the Bundle to store this WebView's state
    883      * @return the same copy of the back/forward list used to save the state, {@code null} if the
    884      *         method fails.
    885      */
    886     @Nullable
    887     public WebBackForwardList saveState(Bundle outState) {
    888         checkThread();
    889         return mProvider.saveState(outState);
    890     }
    891 
    892     /**
    893      * Saves the current display data to the Bundle given. Used in conjunction
    894      * with {@link #saveState}.
    895      * @param b a Bundle to store the display data
    896      * @param dest the file to store the serialized picture data. Will be
    897      *             overwritten with this WebView's picture data.
    898      * @return {@code true} if the picture was successfully saved
    899      * @deprecated This method is now obsolete.
    900      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
    901      */
    902     @Deprecated
    903     public boolean savePicture(Bundle b, final File dest) {
    904         checkThread();
    905         return mProvider.savePicture(b, dest);
    906     }
    907 
    908     /**
    909      * Restores the display data that was saved in {@link #savePicture}. Used in
    910      * conjunction with {@link #restoreState}. Note that this will not work if
    911      * this WebView is hardware accelerated.
    912      *
    913      * @param b a Bundle containing the saved display data
    914      * @param src the file where the picture data was stored
    915      * @return {@code true} if the picture was successfully restored
    916      * @deprecated This method is now obsolete.
    917      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
    918      */
    919     @Deprecated
    920     public boolean restorePicture(Bundle b, File src) {
    921         checkThread();
    922         return mProvider.restorePicture(b, src);
    923     }
    924 
    925     /**
    926      * Restores the state of this WebView from the given Bundle. This method is
    927      * intended for use in {@link android.app.Activity#onRestoreInstanceState}
    928      * and should be called to restore the state of this WebView. If
    929      * it is called after this WebView has had a chance to build state (load
    930      * pages, create a back/forward list, etc.) there may be undesirable
    931      * side-effects. Please note that this method no longer restores the
    932      * display data for this WebView.
    933      *
    934      * @param inState the incoming Bundle of state
    935      * @return the restored back/forward list or {@code null} if restoreState failed
    936      */
    937     @Nullable
    938     public WebBackForwardList restoreState(Bundle inState) {
    939         checkThread();
    940         return mProvider.restoreState(inState);
    941     }
    942 
    943     /**
    944      * Loads the given URL with the specified additional HTTP headers.
    945      * <p>
    946      * Also see compatibility note on {@link #evaluateJavascript}.
    947      *
    948      * @param url the URL of the resource to load
    949      * @param additionalHttpHeaders the additional headers to be used in the
    950      *            HTTP request for this URL, specified as a map from name to
    951      *            value. Note that if this map contains any of the headers
    952      *            that are set by default by this WebView, such as those
    953      *            controlling caching, accept types or the User-Agent, their
    954      *            values may be overridden by this WebView's defaults.
    955      */
    956     public void loadUrl(String url, Map<String, String> additionalHttpHeaders) {
    957         checkThread();
    958         mProvider.loadUrl(url, additionalHttpHeaders);
    959     }
    960 
    961     /**
    962      * Loads the given URL.
    963      * <p>
    964      * Also see compatibility note on {@link #evaluateJavascript}.
    965      *
    966      * @param url the URL of the resource to load
    967      */
    968     public void loadUrl(String url) {
    969         checkThread();
    970         mProvider.loadUrl(url);
    971     }
    972 
    973     /**
    974      * Loads the URL with postData using "POST" method into this WebView. If url
    975      * is not a network URL, it will be loaded with {@link #loadUrl(String)}
    976      * instead, ignoring the postData param.
    977      *
    978      * @param url the URL of the resource to load
    979      * @param postData the data will be passed to "POST" request, which must be
    980      *     be "application/x-www-form-urlencoded" encoded.
    981      */
    982     public void postUrl(String url, byte[] postData) {
    983         checkThread();
    984         if (URLUtil.isNetworkUrl(url)) {
    985             mProvider.postUrl(url, postData);
    986         } else {
    987             mProvider.loadUrl(url);
    988         }
    989     }
    990 
    991     /**
    992      * Loads the given data into this WebView using a 'data' scheme URL.
    993      * <p>
    994      * Note that JavaScript's same origin policy means that script running in a
    995      * page loaded using this method will be unable to access content loaded
    996      * using any scheme other than 'data', including 'http(s)'. To avoid this
    997      * restriction, use {@link
    998      * #loadDataWithBaseURL(String,String,String,String,String)
    999      * loadDataWithBaseURL()} with an appropriate base URL.
   1000      * <p>
   1001      * The {@code encoding} parameter specifies whether the data is base64 or URL
   1002      * encoded. If the data is base64 encoded, the value of the encoding
   1003      * parameter must be 'base64'. HTML can be encoded with {@link
   1004      * android.util.Base64#encodeToString(byte[],int)} like so:
   1005      * <pre>
   1006      * String unencodedHtml =
   1007      *     "&lt;html&gt;&lt;body&gt;'%28' is the code for '('&lt;/body&gt;&lt;/html&gt;";
   1008      * String encodedHtml = Base64.encodeToString(unencodedHtml.getBytes(), Base64.NO_PADDING);
   1009      * webView.loadData(encodedHtml, "text/html", "base64");
   1010      * </pre>
   1011      * <p>
   1012      * For all other values of {@code encoding} (including {@code null}) it is assumed that the
   1013      * data uses ASCII encoding for octets inside the range of safe URL characters and use the
   1014      * standard %xx hex encoding of URLs for octets outside that range. See <a
   1015      * href="https://tools.ietf.org/html/rfc3986#section-2.2">RFC 3986</a> for more information.
   1016      * <p>
   1017      * The {@code mimeType} parameter specifies the format of the data.
   1018      * If WebView can't handle the specified MIME type, it will download the data.
   1019      * If {@code null}, defaults to 'text/html'.
   1020      * <p>
   1021      * The 'data' scheme URL formed by this method uses the default US-ASCII
   1022      * charset. If you need to set a different charset, you should form a
   1023      * 'data' scheme URL which explicitly specifies a charset parameter in the
   1024      * mediatype portion of the URL and call {@link #loadUrl(String)} instead.
   1025      * Note that the charset obtained from the mediatype portion of a data URL
   1026      * always overrides that specified in the HTML or XML document itself.
   1027      * <p>
   1028      * Content loaded using this method will have a {@code window.origin} value
   1029      * of {@code "null"}. This must not be considered to be a trusted origin
   1030      * by the application or by any JavaScript code running inside the WebView
   1031      * (for example, event sources in DOM event handlers or web messages),
   1032      * because malicious content can also create frames with a null origin. If
   1033      * you need to identify the main frame's origin in a trustworthy way, you
   1034      * should use {@link #loadDataWithBaseURL(String,String,String,String,String)
   1035      * loadDataWithBaseURL()} with a valid HTTP or HTTPS base URL to set the
   1036      * origin.
   1037      *
   1038      * @param data a String of data in the given encoding
   1039      * @param mimeType the MIME type of the data, e.g. 'text/html'.
   1040      * @param encoding the encoding of the data
   1041      */
   1042     public void loadData(String data, @Nullable String mimeType, @Nullable String encoding) {
   1043         checkThread();
   1044         mProvider.loadData(data, mimeType, encoding);
   1045     }
   1046 
   1047     /**
   1048      * Loads the given data into this WebView, using baseUrl as the base URL for
   1049      * the content. The base URL is used both to resolve relative URLs and when
   1050      * applying JavaScript's same origin policy. The historyUrl is used for the
   1051      * history entry.
   1052      * <p>
   1053      * The {@code mimeType} parameter specifies the format of the data.
   1054      * If WebView can't handle the specified MIME type, it will download the data.
   1055      * If {@code null}, defaults to 'text/html'.
   1056      * <p>
   1057      * Note that content specified in this way can access local device files
   1058      * (via 'file' scheme URLs) only if baseUrl specifies a scheme other than
   1059      * 'http', 'https', 'ftp', 'ftps', 'about' or 'javascript'.
   1060      * <p>
   1061      * If the base URL uses the data scheme, this method is equivalent to
   1062      * calling {@link #loadData(String,String,String) loadData()} and the
   1063      * historyUrl is ignored, and the data will be treated as part of a data: URL.
   1064      * If the base URL uses any other scheme, then the data will be loaded into
   1065      * the WebView as a plain string (i.e. not part of a data URL) and any URL-encoded
   1066      * entities in the string will not be decoded.
   1067      * <p>
   1068      * Note that the baseUrl is sent in the 'Referer' HTTP header when
   1069      * requesting subresources (images, etc.) of the page loaded using this method.
   1070      * <p>
   1071      * If a valid HTTP or HTTPS base URL is not specified in {@code baseUrl}, then
   1072      * content loaded using this method will have a {@code window.origin} value
   1073      * of {@code "null"}. This must not be considered to be a trusted origin
   1074      * by the application or by any JavaScript code running inside the WebView
   1075      * (for example, event sources in DOM event handlers or web messages),
   1076      * because malicious content can also create frames with a null origin. If
   1077      * you need to identify the main frame's origin in a trustworthy way, you
   1078      * should use a valid HTTP or HTTPS base URL to set the origin.
   1079      *
   1080      * @param baseUrl the URL to use as the page's base URL. If {@code null} defaults to
   1081      *                'about:blank'.
   1082      * @param data a String of data in the given encoding
   1083      * @param mimeType the MIME type of the data, e.g. 'text/html'.
   1084      * @param encoding the encoding of the data
   1085      * @param historyUrl the URL to use as the history entry. If {@code null} defaults
   1086      *                   to 'about:blank'. If non-null, this must be a valid URL.
   1087      */
   1088     public void loadDataWithBaseURL(@Nullable String baseUrl, String data,
   1089             @Nullable String mimeType, @Nullable String encoding, @Nullable String historyUrl) {
   1090         checkThread();
   1091         mProvider.loadDataWithBaseURL(baseUrl, data, mimeType, encoding, historyUrl);
   1092     }
   1093 
   1094     /**
   1095      * Asynchronously evaluates JavaScript in the context of the currently displayed page.
   1096      * If non-null, |resultCallback| will be invoked with any result returned from that
   1097      * execution. This method must be called on the UI thread and the callback will
   1098      * be made on the UI thread.
   1099      * <p>
   1100      * Compatibility note. Applications targeting {@link android.os.Build.VERSION_CODES#N} or
   1101      * later, JavaScript state from an empty WebView is no longer persisted across navigations like
   1102      * {@link #loadUrl(String)}. For example, global variables and functions defined before calling
   1103      * {@link #loadUrl(String)} will not exist in the loaded page. Applications should use
   1104      * {@link #addJavascriptInterface} instead to persist JavaScript objects across navigations.
   1105      *
   1106      * @param script the JavaScript to execute.
   1107      * @param resultCallback A callback to be invoked when the script execution
   1108      *                       completes with the result of the execution (if any).
   1109      *                       May be {@code null} if no notification of the result is required.
   1110      */
   1111     public void evaluateJavascript(String script, @Nullable ValueCallback<String> resultCallback) {
   1112         checkThread();
   1113         mProvider.evaluateJavaScript(script, resultCallback);
   1114     }
   1115 
   1116     /**
   1117      * Saves the current view as a web archive.
   1118      *
   1119      * @param filename the filename where the archive should be placed
   1120      */
   1121     public void saveWebArchive(String filename) {
   1122         checkThread();
   1123         mProvider.saveWebArchive(filename);
   1124     }
   1125 
   1126     /**
   1127      * Saves the current view as a web archive.
   1128      *
   1129      * @param basename the filename where the archive should be placed
   1130      * @param autoname if {@code false}, takes basename to be a file. If {@code true}, basename
   1131      *                 is assumed to be a directory in which a filename will be
   1132      *                 chosen according to the URL of the current page.
   1133      * @param callback called after the web archive has been saved. The
   1134      *                 parameter for onReceiveValue will either be the filename
   1135      *                 under which the file was saved, or {@code null} if saving the
   1136      *                 file failed.
   1137      */
   1138     public void saveWebArchive(String basename, boolean autoname, @Nullable ValueCallback<String>
   1139             callback) {
   1140         checkThread();
   1141         mProvider.saveWebArchive(basename, autoname, callback);
   1142     }
   1143 
   1144     /**
   1145      * Stops the current load.
   1146      */
   1147     public void stopLoading() {
   1148         checkThread();
   1149         mProvider.stopLoading();
   1150     }
   1151 
   1152     /**
   1153      * Reloads the current URL.
   1154      */
   1155     public void reload() {
   1156         checkThread();
   1157         mProvider.reload();
   1158     }
   1159 
   1160     /**
   1161      * Gets whether this WebView has a back history item.
   1162      *
   1163      * @return {@code true} if this WebView has a back history item
   1164      */
   1165     public boolean canGoBack() {
   1166         checkThread();
   1167         return mProvider.canGoBack();
   1168     }
   1169 
   1170     /**
   1171      * Goes back in the history of this WebView.
   1172      */
   1173     public void goBack() {
   1174         checkThread();
   1175         mProvider.goBack();
   1176     }
   1177 
   1178     /**
   1179      * Gets whether this WebView has a forward history item.
   1180      *
   1181      * @return {@code true} if this WebView has a forward history item
   1182      */
   1183     public boolean canGoForward() {
   1184         checkThread();
   1185         return mProvider.canGoForward();
   1186     }
   1187 
   1188     /**
   1189      * Goes forward in the history of this WebView.
   1190      */
   1191     public void goForward() {
   1192         checkThread();
   1193         mProvider.goForward();
   1194     }
   1195 
   1196     /**
   1197      * Gets whether the page can go back or forward the given
   1198      * number of steps.
   1199      *
   1200      * @param steps the negative or positive number of steps to move the
   1201      *              history
   1202      */
   1203     public boolean canGoBackOrForward(int steps) {
   1204         checkThread();
   1205         return mProvider.canGoBackOrForward(steps);
   1206     }
   1207 
   1208     /**
   1209      * Goes to the history item that is the number of steps away from
   1210      * the current item. Steps is negative if backward and positive
   1211      * if forward.
   1212      *
   1213      * @param steps the number of steps to take back or forward in the back
   1214      *              forward list
   1215      */
   1216     public void goBackOrForward(int steps) {
   1217         checkThread();
   1218         mProvider.goBackOrForward(steps);
   1219     }
   1220 
   1221     /**
   1222      * Gets whether private browsing is enabled in this WebView.
   1223      */
   1224     public boolean isPrivateBrowsingEnabled() {
   1225         checkThread();
   1226         return mProvider.isPrivateBrowsingEnabled();
   1227     }
   1228 
   1229     /**
   1230      * Scrolls the contents of this WebView up by half the view size.
   1231      *
   1232      * @param top {@code true} to jump to the top of the page
   1233      * @return {@code true} if the page was scrolled
   1234      */
   1235     public boolean pageUp(boolean top) {
   1236         checkThread();
   1237         return mProvider.pageUp(top);
   1238     }
   1239 
   1240     /**
   1241      * Scrolls the contents of this WebView down by half the page size.
   1242      *
   1243      * @param bottom {@code true} to jump to bottom of page
   1244      * @return {@code true} if the page was scrolled
   1245      */
   1246     public boolean pageDown(boolean bottom) {
   1247         checkThread();
   1248         return mProvider.pageDown(bottom);
   1249     }
   1250 
   1251     /**
   1252      * Posts a {@link VisualStateCallback}, which will be called when
   1253      * the current state of the WebView is ready to be drawn.
   1254      *
   1255      * <p>Because updates to the DOM are processed asynchronously, updates to the DOM may not
   1256      * immediately be reflected visually by subsequent {@link WebView#onDraw} invocations. The
   1257      * {@link VisualStateCallback} provides a mechanism to notify the caller when the contents of
   1258      * the DOM at the current time are ready to be drawn the next time the {@link WebView}
   1259      * draws.
   1260      *
   1261      * <p>The next draw after the callback completes is guaranteed to reflect all the updates to the
   1262      * DOM up to the point at which the {@link VisualStateCallback} was posted, but it may also
   1263      * contain updates applied after the callback was posted.
   1264      *
   1265      * <p>The state of the DOM covered by this API includes the following:
   1266      * <ul>
   1267      * <li>primitive HTML elements (div, img, span, etc..)</li>
   1268      * <li>images</li>
   1269      * <li>CSS animations</li>
   1270      * <li>WebGL</li>
   1271      * <li>canvas</li>
   1272      * </ul>
   1273      * It does not include the state of:
   1274      * <ul>
   1275      * <li>the video tag</li>
   1276      * </ul>
   1277      *
   1278      * <p>To guarantee that the {@link WebView} will successfully render the first frame
   1279      * after the {@link VisualStateCallback#onComplete} method has been called a set of conditions
   1280      * must be met:
   1281      * <ul>
   1282      * <li>If the {@link WebView}'s visibility is set to {@link View#VISIBLE VISIBLE} then
   1283      * the {@link WebView} must be attached to the view hierarchy.</li>
   1284      * <li>If the {@link WebView}'s visibility is set to {@link View#INVISIBLE INVISIBLE}
   1285      * then the {@link WebView} must be attached to the view hierarchy and must be made
   1286      * {@link View#VISIBLE VISIBLE} from the {@link VisualStateCallback#onComplete} method.</li>
   1287      * <li>If the {@link WebView}'s visibility is set to {@link View#GONE GONE} then the
   1288      * {@link WebView} must be attached to the view hierarchy and its
   1289      * {@link AbsoluteLayout.LayoutParams LayoutParams}'s width and height need to be set to fixed
   1290      * values and must be made {@link View#VISIBLE VISIBLE} from the
   1291      * {@link VisualStateCallback#onComplete} method.</li>
   1292      * </ul>
   1293      *
   1294      * <p>When using this API it is also recommended to enable pre-rasterization if the {@link
   1295      * WebView} is off screen to avoid flickering. See {@link WebSettings#setOffscreenPreRaster} for
   1296      * more details and do consider its caveats.
   1297      *
   1298      * @param requestId An id that will be returned in the callback to allow callers to match
   1299      *                  requests with callbacks.
   1300      * @param callback  The callback to be invoked.
   1301      */
   1302     public void postVisualStateCallback(long requestId, VisualStateCallback callback) {
   1303         checkThread();
   1304         mProvider.insertVisualStateCallback(requestId, callback);
   1305     }
   1306 
   1307     /**
   1308      * Clears this WebView so that onDraw() will draw nothing but white background,
   1309      * and onMeasure() will return 0 if MeasureSpec is not MeasureSpec.EXACTLY.
   1310      * @deprecated Use WebView.loadUrl("about:blank") to reliably reset the view state
   1311      *             and release page resources (including any running JavaScript).
   1312      */
   1313     @Deprecated
   1314     public void clearView() {
   1315         checkThread();
   1316         mProvider.clearView();
   1317     }
   1318 
   1319     /**
   1320      * Gets a new picture that captures the current contents of this WebView.
   1321      * The picture is of the entire document being displayed, and is not
   1322      * limited to the area currently displayed by this WebView. Also, the
   1323      * picture is a static copy and is unaffected by later changes to the
   1324      * content being displayed.
   1325      * <p>
   1326      * Note that due to internal changes, for API levels between
   1327      * {@link android.os.Build.VERSION_CODES#HONEYCOMB} and
   1328      * {@link android.os.Build.VERSION_CODES#ICE_CREAM_SANDWICH} inclusive, the
   1329      * picture does not include fixed position elements or scrollable divs.
   1330      * <p>
   1331      * Note that from {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1} the returned picture
   1332      * should only be drawn into bitmap-backed Canvas - using any other type of Canvas will involve
   1333      * additional conversion at a cost in memory and performance. Also the
   1334      * {@link android.graphics.Picture#createFromStream} and
   1335      * {@link android.graphics.Picture#writeToStream} methods are not supported on the
   1336      * returned object.
   1337      *
   1338      * @deprecated Use {@link #onDraw} to obtain a bitmap snapshot of the WebView, or
   1339      * {@link #saveWebArchive} to save the content to a file.
   1340      *
   1341      * @return a picture that captures the current contents of this WebView
   1342      */
   1343     @Deprecated
   1344     public Picture capturePicture() {
   1345         checkThread();
   1346         return mProvider.capturePicture();
   1347     }
   1348 
   1349     /**
   1350      * @deprecated Use {@link #createPrintDocumentAdapter(String)} which requires user
   1351      *             to provide a print document name.
   1352      */
   1353     @Deprecated
   1354     public PrintDocumentAdapter createPrintDocumentAdapter() {
   1355         checkThread();
   1356         return mProvider.createPrintDocumentAdapter("default");
   1357     }
   1358 
   1359     /**
   1360      * Creates a PrintDocumentAdapter that provides the content of this WebView for printing.
   1361      *
   1362      * The adapter works by converting the WebView contents to a PDF stream. The WebView cannot
   1363      * be drawn during the conversion process - any such draws are undefined. It is recommended
   1364      * to use a dedicated off screen WebView for the printing. If necessary, an application may
   1365      * temporarily hide a visible WebView by using a custom PrintDocumentAdapter instance
   1366      * wrapped around the object returned and observing the onStart and onFinish methods. See
   1367      * {@link android.print.PrintDocumentAdapter} for more information.
   1368      *
   1369      * @param documentName  The user-facing name of the printed document. See
   1370      *                      {@link android.print.PrintDocumentInfo}
   1371      */
   1372     public PrintDocumentAdapter createPrintDocumentAdapter(String documentName) {
   1373         checkThread();
   1374         return mProvider.createPrintDocumentAdapter(documentName);
   1375     }
   1376 
   1377     /**
   1378      * Gets the current scale of this WebView.
   1379      *
   1380      * @return the current scale
   1381      *
   1382      * @deprecated This method is prone to inaccuracy due to race conditions
   1383      * between the web rendering and UI threads; prefer
   1384      * {@link WebViewClient#onScaleChanged}.
   1385      */
   1386     @Deprecated
   1387     @ViewDebug.ExportedProperty(category = "webview")
   1388     public float getScale() {
   1389         checkThread();
   1390         return mProvider.getScale();
   1391     }
   1392 
   1393     /**
   1394      * Sets the initial scale for this WebView. 0 means default.
   1395      * The behavior for the default scale depends on the state of
   1396      * {@link WebSettings#getUseWideViewPort()} and
   1397      * {@link WebSettings#getLoadWithOverviewMode()}.
   1398      * If the content fits into the WebView control by width, then
   1399      * the zoom is set to 100%. For wide content, the behavior
   1400      * depends on the state of {@link WebSettings#getLoadWithOverviewMode()}.
   1401      * If its value is {@code true}, the content will be zoomed out to be fit
   1402      * by width into the WebView control, otherwise not.
   1403      *
   1404      * If initial scale is greater than 0, WebView starts with this value
   1405      * as initial scale.
   1406      * Please note that unlike the scale properties in the viewport meta tag,
   1407      * this method doesn't take the screen density into account.
   1408      *
   1409      * @param scaleInPercent the initial scale in percent
   1410      */
   1411     public void setInitialScale(int scaleInPercent) {
   1412         checkThread();
   1413         mProvider.setInitialScale(scaleInPercent);
   1414     }
   1415 
   1416     /**
   1417      * Invokes the graphical zoom picker widget for this WebView. This will
   1418      * result in the zoom widget appearing on the screen to control the zoom
   1419      * level of this WebView.
   1420      */
   1421     public void invokeZoomPicker() {
   1422         checkThread();
   1423         mProvider.invokeZoomPicker();
   1424     }
   1425 
   1426     /**
   1427      * Gets a HitTestResult based on the current cursor node. If a HTML::a
   1428      * tag is found and the anchor has a non-JavaScript URL, the HitTestResult
   1429      * type is set to SRC_ANCHOR_TYPE and the URL is set in the "extra" field.
   1430      * If the anchor does not have a URL or if it is a JavaScript URL, the type
   1431      * will be UNKNOWN_TYPE and the URL has to be retrieved through
   1432      * {@link #requestFocusNodeHref} asynchronously. If a HTML::img tag is
   1433      * found, the HitTestResult type is set to IMAGE_TYPE and the URL is set in
   1434      * the "extra" field. A type of
   1435      * SRC_IMAGE_ANCHOR_TYPE indicates an anchor with a URL that has an image as
   1436      * a child node. If a phone number is found, the HitTestResult type is set
   1437      * to PHONE_TYPE and the phone number is set in the "extra" field of
   1438      * HitTestResult. If a map address is found, the HitTestResult type is set
   1439      * to GEO_TYPE and the address is set in the "extra" field of HitTestResult.
   1440      * If an email address is found, the HitTestResult type is set to EMAIL_TYPE
   1441      * and the email is set in the "extra" field of HitTestResult. Otherwise,
   1442      * HitTestResult type is set to UNKNOWN_TYPE.
   1443      */
   1444     public HitTestResult getHitTestResult() {
   1445         checkThread();
   1446         return mProvider.getHitTestResult();
   1447     }
   1448 
   1449     /**
   1450      * Requests the anchor or image element URL at the last tapped point.
   1451      * If hrefMsg is {@code null}, this method returns immediately and does not
   1452      * dispatch hrefMsg to its target. If the tapped point hits an image,
   1453      * an anchor, or an image in an anchor, the message associates
   1454      * strings in named keys in its data. The value paired with the key
   1455      * may be an empty string.
   1456      *
   1457      * @param hrefMsg the message to be dispatched with the result of the
   1458      *                request. The message data contains three keys. "url"
   1459      *                returns the anchor's href attribute. "title" returns the
   1460      *                anchor's text. "src" returns the image's src attribute.
   1461      */
   1462     public void requestFocusNodeHref(@Nullable Message hrefMsg) {
   1463         checkThread();
   1464         mProvider.requestFocusNodeHref(hrefMsg);
   1465     }
   1466 
   1467     /**
   1468      * Requests the URL of the image last touched by the user. msg will be sent
   1469      * to its target with a String representing the URL as its object.
   1470      *
   1471      * @param msg the message to be dispatched with the result of the request
   1472      *            as the data member with "url" as key. The result can be {@code null}.
   1473      */
   1474     public void requestImageRef(Message msg) {
   1475         checkThread();
   1476         mProvider.requestImageRef(msg);
   1477     }
   1478 
   1479     /**
   1480      * Gets the URL for the current page. This is not always the same as the URL
   1481      * passed to WebViewClient.onPageStarted because although the load for
   1482      * that URL has begun, the current page may not have changed.
   1483      *
   1484      * @return the URL for the current page
   1485      */
   1486     @ViewDebug.ExportedProperty(category = "webview")
   1487     public String getUrl() {
   1488         checkThread();
   1489         return mProvider.getUrl();
   1490     }
   1491 
   1492     /**
   1493      * Gets the original URL for the current page. This is not always the same
   1494      * as the URL passed to WebViewClient.onPageStarted because although the
   1495      * load for that URL has begun, the current page may not have changed.
   1496      * Also, there may have been redirects resulting in a different URL to that
   1497      * originally requested.
   1498      *
   1499      * @return the URL that was originally requested for the current page
   1500      */
   1501     @ViewDebug.ExportedProperty(category = "webview")
   1502     public String getOriginalUrl() {
   1503         checkThread();
   1504         return mProvider.getOriginalUrl();
   1505     }
   1506 
   1507     /**
   1508      * Gets the title for the current page. This is the title of the current page
   1509      * until WebViewClient.onReceivedTitle is called.
   1510      *
   1511      * @return the title for the current page
   1512      */
   1513     @ViewDebug.ExportedProperty(category = "webview")
   1514     public String getTitle() {
   1515         checkThread();
   1516         return mProvider.getTitle();
   1517     }
   1518 
   1519     /**
   1520      * Gets the favicon for the current page. This is the favicon of the current
   1521      * page until WebViewClient.onReceivedIcon is called.
   1522      *
   1523      * @return the favicon for the current page
   1524      */
   1525     public Bitmap getFavicon() {
   1526         checkThread();
   1527         return mProvider.getFavicon();
   1528     }
   1529 
   1530     /**
   1531      * Gets the touch icon URL for the apple-touch-icon <link> element, or
   1532      * a URL on this site's server pointing to the standard location of a
   1533      * touch icon.
   1534      *
   1535      * @hide
   1536      */
   1537     public String getTouchIconUrl() {
   1538         return mProvider.getTouchIconUrl();
   1539     }
   1540 
   1541     /**
   1542      * Gets the progress for the current page.
   1543      *
   1544      * @return the progress for the current page between 0 and 100
   1545      */
   1546     public int getProgress() {
   1547         checkThread();
   1548         return mProvider.getProgress();
   1549     }
   1550 
   1551     /**
   1552      * Gets the height of the HTML content.
   1553      *
   1554      * @return the height of the HTML content
   1555      */
   1556     @ViewDebug.ExportedProperty(category = "webview")
   1557     public int getContentHeight() {
   1558         checkThread();
   1559         return mProvider.getContentHeight();
   1560     }
   1561 
   1562     /**
   1563      * Gets the width of the HTML content.
   1564      *
   1565      * @return the width of the HTML content
   1566      * @hide
   1567      */
   1568     @ViewDebug.ExportedProperty(category = "webview")
   1569     public int getContentWidth() {
   1570         return mProvider.getContentWidth();
   1571     }
   1572 
   1573     /**
   1574      * Pauses all layout, parsing, and JavaScript timers for all WebViews. This
   1575      * is a global requests, not restricted to just this WebView. This can be
   1576      * useful if the application has been paused.
   1577      */
   1578     public void pauseTimers() {
   1579         checkThread();
   1580         mProvider.pauseTimers();
   1581     }
   1582 
   1583     /**
   1584      * Resumes all layout, parsing, and JavaScript timers for all WebViews.
   1585      * This will resume dispatching all timers.
   1586      */
   1587     public void resumeTimers() {
   1588         checkThread();
   1589         mProvider.resumeTimers();
   1590     }
   1591 
   1592     /**
   1593      * Does a best-effort attempt to pause any processing that can be paused
   1594      * safely, such as animations and geolocation. Note that this call
   1595      * does not pause JavaScript. To pause JavaScript globally, use
   1596      * {@link #pauseTimers}.
   1597      *
   1598      * To resume WebView, call {@link #onResume}.
   1599      */
   1600     public void onPause() {
   1601         checkThread();
   1602         mProvider.onPause();
   1603     }
   1604 
   1605     /**
   1606      * Resumes a WebView after a previous call to {@link #onPause}.
   1607      */
   1608     public void onResume() {
   1609         checkThread();
   1610         mProvider.onResume();
   1611     }
   1612 
   1613     /**
   1614      * Gets whether this WebView is paused, meaning onPause() was called.
   1615      * Calling onResume() sets the paused state back to {@code false}.
   1616      *
   1617      * @hide
   1618      */
   1619     public boolean isPaused() {
   1620         return mProvider.isPaused();
   1621     }
   1622 
   1623     /**
   1624      * Informs this WebView that memory is low so that it can free any available
   1625      * memory.
   1626      * @deprecated Memory caches are automatically dropped when no longer needed, and in response
   1627      *             to system memory pressure.
   1628      */
   1629     @Deprecated
   1630     public void freeMemory() {
   1631         checkThread();
   1632         mProvider.freeMemory();
   1633     }
   1634 
   1635     /**
   1636      * Clears the resource cache. Note that the cache is per-application, so
   1637      * this will clear the cache for all WebViews used.
   1638      *
   1639      * @param includeDiskFiles if {@code false}, only the RAM cache is cleared
   1640      */
   1641     public void clearCache(boolean includeDiskFiles) {
   1642         checkThread();
   1643         mProvider.clearCache(includeDiskFiles);
   1644     }
   1645 
   1646     /**
   1647      * Removes the autocomplete popup from the currently focused form field, if
   1648      * present. Note this only affects the display of the autocomplete popup,
   1649      * it does not remove any saved form data from this WebView's store. To do
   1650      * that, use {@link WebViewDatabase#clearFormData}.
   1651      */
   1652     public void clearFormData() {
   1653         checkThread();
   1654         mProvider.clearFormData();
   1655     }
   1656 
   1657     /**
   1658      * Tells this WebView to clear its internal back/forward list.
   1659      */
   1660     public void clearHistory() {
   1661         checkThread();
   1662         mProvider.clearHistory();
   1663     }
   1664 
   1665     /**
   1666      * Clears the SSL preferences table stored in response to proceeding with
   1667      * SSL certificate errors.
   1668      */
   1669     public void clearSslPreferences() {
   1670         checkThread();
   1671         mProvider.clearSslPreferences();
   1672     }
   1673 
   1674     /**
   1675      * Clears the client certificate preferences stored in response
   1676      * to proceeding/cancelling client cert requests. Note that WebView
   1677      * automatically clears these preferences when it receives a
   1678      * {@link KeyChain#ACTION_STORAGE_CHANGED} intent. The preferences are
   1679      * shared by all the WebViews that are created by the embedder application.
   1680      *
   1681      * @param onCleared  A runnable to be invoked when client certs are cleared.
   1682      *                   The runnable will be called in UI thread.
   1683      */
   1684     public static void clearClientCertPreferences(@Nullable Runnable onCleared) {
   1685         getFactory().getStatics().clearClientCertPreferences(onCleared);
   1686     }
   1687 
   1688     /**
   1689      * Starts Safe Browsing initialization.
   1690      * <p>
   1691      * URL loads are not guaranteed to be protected by Safe Browsing until after {@code callback} is
   1692      * invoked with {@code true}. Safe Browsing is not fully supported on all devices. For those
   1693      * devices {@code callback} will receive {@code false}.
   1694      * <p>
   1695      * This should not be called if Safe Browsing has been disabled by manifest tag or {@link
   1696      * WebSettings#setSafeBrowsingEnabled}. This prepares resources used for Safe Browsing.
   1697      * <p>
   1698      * This should be called with the Application Context (and will always use the Application
   1699      * context to do its work regardless).
   1700      *
   1701      * @param context Application Context.
   1702      * @param callback will be called on the UI thread with {@code true} if initialization is
   1703      * successful, {@code false} otherwise.
   1704      */
   1705     public static void startSafeBrowsing(@NonNull Context context,
   1706             @Nullable ValueCallback<Boolean> callback) {
   1707         getFactory().getStatics().initSafeBrowsing(context, callback);
   1708     }
   1709 
   1710     /**
   1711      * Sets the list of hosts (domain names/IP addresses) that are exempt from SafeBrowsing checks.
   1712      * The list is global for all the WebViews.
   1713      * <p>
   1714      * Each rule should take one of these:
   1715      * <table>
   1716      * <tr><th> Rule </th> <th> Example </th> <th> Matches Subdomain</th> </tr>
   1717      * <tr><td> HOSTNAME </td> <td> example.com </td> <td> Yes </td> </tr>
   1718      * <tr><td> .HOSTNAME </td> <td> .example.com </td> <td> No </td> </tr>
   1719      * <tr><td> IPV4_LITERAL </td> <td> 192.168.1.1 </td> <td> No </td></tr>
   1720      * <tr><td> IPV6_LITERAL_WITH_BRACKETS </td><td>[10:20:30:40:50:60:70:80]</td><td>No</td></tr>
   1721      * </table>
   1722      * <p>
   1723      * All other rules, including wildcards, are invalid.
   1724      * <p>
   1725      * The correct syntax for hosts is defined by <a
   1726      * href="https://tools.ietf.org/html/rfc3986#section-3.2.2">RFC 3986</a>.
   1727      *
   1728      * @param hosts the list of hosts
   1729      * @param callback will be called with {@code true} if hosts are successfully added to the
   1730      * whitelist. It will be called with {@code false} if any hosts are malformed. The callback
   1731      * will be run on the UI thread
   1732      */
   1733     public static void setSafeBrowsingWhitelist(@NonNull List<String> hosts,
   1734             @Nullable ValueCallback<Boolean> callback) {
   1735         getFactory().getStatics().setSafeBrowsingWhitelist(hosts, callback);
   1736     }
   1737 
   1738     /**
   1739      * Returns a URL pointing to the privacy policy for Safe Browsing reporting.
   1740      *
   1741      * @return the url pointing to a privacy policy document which can be displayed to users.
   1742      */
   1743     @NonNull
   1744     public static Uri getSafeBrowsingPrivacyPolicyUrl() {
   1745         return getFactory().getStatics().getSafeBrowsingPrivacyPolicyUrl();
   1746     }
   1747 
   1748     /**
   1749      * Gets the WebBackForwardList for this WebView. This contains the
   1750      * back/forward list for use in querying each item in the history stack.
   1751      * This is a copy of the private WebBackForwardList so it contains only a
   1752      * snapshot of the current state. Multiple calls to this method may return
   1753      * different objects. The object returned from this method will not be
   1754      * updated to reflect any new state.
   1755      */
   1756     public WebBackForwardList copyBackForwardList() {
   1757         checkThread();
   1758         return mProvider.copyBackForwardList();
   1759 
   1760     }
   1761 
   1762     /**
   1763      * Registers the listener to be notified as find-on-page operations
   1764      * progress. This will replace the current listener.
   1765      *
   1766      * @param listener an implementation of {@link FindListener}
   1767      */
   1768     public void setFindListener(FindListener listener) {
   1769         checkThread();
   1770         setupFindListenerIfNeeded();
   1771         mFindListener.mUserFindListener = listener;
   1772     }
   1773 
   1774     /**
   1775      * Highlights and scrolls to the next match found by
   1776      * {@link #findAllAsync}, wrapping around page boundaries as necessary.
   1777      * Notifies any registered {@link FindListener}. If {@link #findAllAsync(String)}
   1778      * has not been called yet, or if {@link #clearMatches} has been called since the
   1779      * last find operation, this function does nothing.
   1780      *
   1781      * @param forward the direction to search
   1782      * @see #setFindListener
   1783      */
   1784     public void findNext(boolean forward) {
   1785         checkThread();
   1786         mProvider.findNext(forward);
   1787     }
   1788 
   1789     /**
   1790      * Finds all instances of find on the page and highlights them.
   1791      * Notifies any registered {@link FindListener}.
   1792      *
   1793      * @param find the string to find
   1794      * @return the number of occurrences of the String "find" that were found
   1795      * @deprecated {@link #findAllAsync} is preferred.
   1796      * @see #setFindListener
   1797      */
   1798     @Deprecated
   1799     public int findAll(String find) {
   1800         checkThread();
   1801         StrictMode.noteSlowCall("findAll blocks UI: prefer findAllAsync");
   1802         return mProvider.findAll(find);
   1803     }
   1804 
   1805     /**
   1806      * Finds all instances of find on the page and highlights them,
   1807      * asynchronously. Notifies any registered {@link FindListener}.
   1808      * Successive calls to this will cancel any pending searches.
   1809      *
   1810      * @param find the string to find.
   1811      * @see #setFindListener
   1812      */
   1813     public void findAllAsync(String find) {
   1814         checkThread();
   1815         mProvider.findAllAsync(find);
   1816     }
   1817 
   1818     /**
   1819      * Starts an ActionMode for finding text in this WebView.  Only works if this
   1820      * WebView is attached to the view system.
   1821      *
   1822      * @param text if non-null, will be the initial text to search for.
   1823      *             Otherwise, the last String searched for in this WebView will
   1824      *             be used to start.
   1825      * @param showIme if {@code true}, show the IME, assuming the user will begin typing.
   1826      *                If {@code false} and text is non-null, perform a find all.
   1827      * @return {@code true} if the find dialog is shown, {@code false} otherwise
   1828      * @deprecated This method does not work reliably on all Android versions;
   1829      *             implementing a custom find dialog using WebView.findAllAsync()
   1830      *             provides a more robust solution.
   1831      */
   1832     @Deprecated
   1833     public boolean showFindDialog(@Nullable String text, boolean showIme) {
   1834         checkThread();
   1835         return mProvider.showFindDialog(text, showIme);
   1836     }
   1837 
   1838     /**
   1839      * Gets the first substring consisting of the address of a physical
   1840      * location. Currently, only addresses in the United States are detected,
   1841      * and consist of:
   1842      * <ul>
   1843      *   <li>a house number</li>
   1844      *   <li>a street name</li>
   1845      *   <li>a street type (Road, Circle, etc), either spelled out or
   1846      *       abbreviated</li>
   1847      *   <li>a city name</li>
   1848      *   <li>a state or territory, either spelled out or two-letter abbr</li>
   1849      *   <li>an optional 5 digit or 9 digit zip code</li>
   1850      * </ul>
   1851      * All names must be correctly capitalized, and the zip code, if present,
   1852      * must be valid for the state. The street type must be a standard USPS
   1853      * spelling or abbreviation. The state or territory must also be spelled
   1854      * or abbreviated using USPS standards. The house number may not exceed
   1855      * five digits.
   1856      *
   1857      * @param addr the string to search for addresses
   1858      * @return the address, or if no address is found, {@code null}
   1859      * @deprecated this method is superseded by {@link TextClassifier#generateLinks(
   1860      * android.view.textclassifier.TextLinks.Request)}. Avoid using this method even when targeting
   1861      * API levels where no alternative is available.
   1862      */
   1863     @Nullable
   1864     @Deprecated
   1865     public static String findAddress(String addr) {
   1866         if (addr == null) {
   1867             throw new NullPointerException("addr is null");
   1868         }
   1869         return FindAddress.findAddress(addr);
   1870     }
   1871 
   1872     /**
   1873      * For apps targeting the L release, WebView has a new default behavior that reduces
   1874      * memory footprint and increases performance by intelligently choosing
   1875      * the portion of the HTML document that needs to be drawn. These
   1876      * optimizations are transparent to the developers. However, under certain
   1877      * circumstances, an App developer may want to disable them:
   1878      * <ol>
   1879      *   <li>When an app uses {@link #onDraw} to do own drawing and accesses portions
   1880      *       of the page that is way outside the visible portion of the page.</li>
   1881      *   <li>When an app uses {@link #capturePicture} to capture a very large HTML document.
   1882      *       Note that capturePicture is a deprecated API.</li>
   1883      * </ol>
   1884      * Enabling drawing the entire HTML document has a significant performance
   1885      * cost. This method should be called before any WebViews are created.
   1886      */
   1887     public static void enableSlowWholeDocumentDraw() {
   1888         getFactory().getStatics().enableSlowWholeDocumentDraw();
   1889     }
   1890 
   1891     /**
   1892      * Clears the highlighting surrounding text matches created by
   1893      * {@link #findAllAsync}.
   1894      */
   1895     public void clearMatches() {
   1896         checkThread();
   1897         mProvider.clearMatches();
   1898     }
   1899 
   1900     /**
   1901      * Queries the document to see if it contains any image references. The
   1902      * message object will be dispatched with arg1 being set to 1 if images
   1903      * were found and 0 if the document does not reference any images.
   1904      *
   1905      * @param response the message that will be dispatched with the result
   1906      */
   1907     public void documentHasImages(Message response) {
   1908         checkThread();
   1909         mProvider.documentHasImages(response);
   1910     }
   1911 
   1912     /**
   1913      * Sets the WebViewClient that will receive various notifications and
   1914      * requests. This will replace the current handler.
   1915      *
   1916      * @param client an implementation of WebViewClient
   1917      * @see #getWebViewClient
   1918      */
   1919     public void setWebViewClient(WebViewClient client) {
   1920         checkThread();
   1921         mProvider.setWebViewClient(client);
   1922     }
   1923 
   1924     /**
   1925      * Gets the WebViewClient.
   1926      *
   1927      * @return the WebViewClient, or a default client if not yet set
   1928      * @see #setWebViewClient
   1929      */
   1930     public WebViewClient getWebViewClient() {
   1931         checkThread();
   1932         return mProvider.getWebViewClient();
   1933     }
   1934 
   1935     /**
   1936      * Registers the interface to be used when content can not be handled by
   1937      * the rendering engine, and should be downloaded instead. This will replace
   1938      * the current handler.
   1939      *
   1940      * @param listener an implementation of DownloadListener
   1941      */
   1942     public void setDownloadListener(DownloadListener listener) {
   1943         checkThread();
   1944         mProvider.setDownloadListener(listener);
   1945     }
   1946 
   1947     /**
   1948      * Sets the chrome handler. This is an implementation of WebChromeClient for
   1949      * use in handling JavaScript dialogs, favicons, titles, and the progress.
   1950      * This will replace the current handler.
   1951      *
   1952      * @param client an implementation of WebChromeClient
   1953      * @see #getWebChromeClient
   1954      */
   1955     public void setWebChromeClient(WebChromeClient client) {
   1956         checkThread();
   1957         mProvider.setWebChromeClient(client);
   1958     }
   1959 
   1960     /**
   1961      * Gets the chrome handler.
   1962      *
   1963      * @return the WebChromeClient, or {@code null} if not yet set
   1964      * @see #setWebChromeClient
   1965      */
   1966     @Nullable
   1967     public WebChromeClient getWebChromeClient() {
   1968         checkThread();
   1969         return mProvider.getWebChromeClient();
   1970     }
   1971 
   1972     /**
   1973      * Sets the Picture listener. This is an interface used to receive
   1974      * notifications of a new Picture.
   1975      *
   1976      * @param listener an implementation of WebView.PictureListener
   1977      * @deprecated This method is now obsolete.
   1978      */
   1979     @Deprecated
   1980     public void setPictureListener(PictureListener listener) {
   1981         checkThread();
   1982         mProvider.setPictureListener(listener);
   1983     }
   1984 
   1985     /**
   1986      * Injects the supplied Java object into this WebView. The object is
   1987      * injected into the JavaScript context of the main frame, using the
   1988      * supplied name. This allows the Java object's methods to be
   1989      * accessed from JavaScript. For applications targeted to API
   1990      * level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
   1991      * and above, only public methods that are annotated with
   1992      * {@link android.webkit.JavascriptInterface} can be accessed from JavaScript.
   1993      * For applications targeted to API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN} or below,
   1994      * all public methods (including the inherited ones) can be accessed, see the
   1995      * important security note below for implications.
   1996      * <p> Note that injected objects will not appear in JavaScript until the page is next
   1997      * (re)loaded. JavaScript should be enabled before injecting the object. For example:
   1998      * <pre>
   1999      * class JsObject {
   2000      *    {@literal @}JavascriptInterface
   2001      *    public String toString() { return "injectedObject"; }
   2002      * }
   2003      * webview.getSettings().setJavaScriptEnabled(true);
   2004      * webView.addJavascriptInterface(new JsObject(), "injectedObject");
   2005      * webView.loadData("<!DOCTYPE html><title></title>", "text/html", null);
   2006      * webView.loadUrl("javascript:alert(injectedObject.toString())");</pre>
   2007      * <p>
   2008      * <strong>IMPORTANT:</strong>
   2009      * <ul>
   2010      * <li> This method can be used to allow JavaScript to control the host
   2011      * application. This is a powerful feature, but also presents a security
   2012      * risk for apps targeting {@link android.os.Build.VERSION_CODES#JELLY_BEAN} or earlier.
   2013      * Apps that target a version later than {@link android.os.Build.VERSION_CODES#JELLY_BEAN}
   2014      * are still vulnerable if the app runs on a device running Android earlier than 4.2.
   2015      * The most secure way to use this method is to target {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
   2016      * and to ensure the method is called only when running on Android 4.2 or later.
   2017      * With these older versions, JavaScript could use reflection to access an
   2018      * injected object's public fields. Use of this method in a WebView
   2019      * containing untrusted content could allow an attacker to manipulate the
   2020      * host application in unintended ways, executing Java code with the
   2021      * permissions of the host application. Use extreme care when using this
   2022      * method in a WebView which could contain untrusted content.</li>
   2023      * <li> JavaScript interacts with Java object on a private, background
   2024      * thread of this WebView. Care is therefore required to maintain thread
   2025      * safety.
   2026      * </li>
   2027      * <li> The Java object's fields are not accessible.</li>
   2028      * <li> For applications targeted to API level {@link android.os.Build.VERSION_CODES#LOLLIPOP}
   2029      * and above, methods of injected Java objects are enumerable from
   2030      * JavaScript.</li>
   2031      * </ul>
   2032      *
   2033      * @param object the Java object to inject into this WebView's JavaScript
   2034      *               context. {@code null} values are ignored.
   2035      * @param name the name used to expose the object in JavaScript
   2036      */
   2037     public void addJavascriptInterface(Object object, String name) {
   2038         checkThread();
   2039         mProvider.addJavascriptInterface(object, name);
   2040     }
   2041 
   2042     /**
   2043      * Removes a previously injected Java object from this WebView. Note that
   2044      * the removal will not be reflected in JavaScript until the page is next
   2045      * (re)loaded. See {@link #addJavascriptInterface}.
   2046      *
   2047      * @param name the name used to expose the object in JavaScript
   2048      */
   2049     public void removeJavascriptInterface(@NonNull String name) {
   2050         checkThread();
   2051         mProvider.removeJavascriptInterface(name);
   2052     }
   2053 
   2054     /**
   2055      * Creates a message channel to communicate with JS and returns the message
   2056      * ports that represent the endpoints of this message channel. The HTML5 message
   2057      * channel functionality is described
   2058      * <a href="https://html.spec.whatwg.org/multipage/comms.html#messagechannel">here
   2059      * </a>
   2060      *
   2061      * <p>The returned message channels are entangled and already in started state.
   2062      *
   2063      * @return the two message ports that form the message channel.
   2064      */
   2065     public WebMessagePort[] createWebMessageChannel() {
   2066         checkThread();
   2067         return mProvider.createWebMessageChannel();
   2068     }
   2069 
   2070     /**
   2071      * Post a message to main frame. The embedded application can restrict the
   2072      * messages to a certain target origin. See
   2073      * <a href="https://html.spec.whatwg.org/multipage/comms.html#posting-messages">
   2074      * HTML5 spec</a> for how target origin can be used.
   2075      * <p>
   2076      * A target origin can be set as a wildcard ("*"). However this is not recommended.
   2077      * See the page above for security issues.
   2078      * <p>
   2079      * Content loaded via {@link #loadData(String,String,String)} will not have a
   2080      * valid origin, and thus cannot be sent messages securely. If you need to send
   2081      * messages using this function, you should use
   2082      * {@link #loadDataWithBaseURL(String,String,String,String,String)} with a valid
   2083      * HTTP or HTTPS {@code baseUrl} to define a valid origin that can be used for
   2084      * messaging.
   2085      *
   2086      * @param message the WebMessage
   2087      * @param targetOrigin the target origin.
   2088      */
   2089     public void postWebMessage(WebMessage message, Uri targetOrigin) {
   2090         checkThread();
   2091         mProvider.postMessageToMainFrame(message, targetOrigin);
   2092     }
   2093 
   2094     /**
   2095      * Gets the WebSettings object used to control the settings for this
   2096      * WebView.
   2097      *
   2098      * @return a WebSettings object that can be used to control this WebView's
   2099      *         settings
   2100      */
   2101     public WebSettings getSettings() {
   2102         checkThread();
   2103         return mProvider.getSettings();
   2104     }
   2105 
   2106     /**
   2107      * Enables debugging of web contents (HTML / CSS / JavaScript)
   2108      * loaded into any WebViews of this application. This flag can be enabled
   2109      * in order to facilitate debugging of web layouts and JavaScript
   2110      * code running inside WebViews. Please refer to WebView documentation
   2111      * for the debugging guide.
   2112      *
   2113      * The default is {@code false}.
   2114      *
   2115      * @param enabled whether to enable web contents debugging
   2116      */
   2117     public static void setWebContentsDebuggingEnabled(boolean enabled) {
   2118         getFactory().getStatics().setWebContentsDebuggingEnabled(enabled);
   2119     }
   2120 
   2121     /**
   2122      * Gets the list of currently loaded plugins.
   2123      *
   2124      * @return the list of currently loaded plugins
   2125      * @deprecated This was used for Gears, which has been deprecated.
   2126      * @hide
   2127      */
   2128     @Deprecated
   2129     public static synchronized PluginList getPluginList() {
   2130         return new PluginList();
   2131     }
   2132 
   2133     /**
   2134      * Define the directory used to store WebView data for the current process.
   2135      * The provided suffix will be used when constructing data and cache
   2136      * directory paths. If this API is not called, no suffix will be used.
   2137      * Each directory can be used by only one process in the application. If more
   2138      * than one process in an app wishes to use WebView, only one process can use
   2139      * the default directory, and other processes must call this API to define
   2140      * a unique suffix.
   2141      * <p>
   2142      * This means that different processes in the same application cannot directly
   2143      * share WebView-related data, since the data directories must be distinct.
   2144      * Applications that use this API may have to explicitly pass data between
   2145      * processes. For example, login cookies may have to be copied from one
   2146      * process's cookie jar to the other using {@link CookieManager} if both
   2147      * processes' WebViews are intended to be logged in.
   2148      * <p>
   2149      * Most applications should simply ensure that all components of the app
   2150      * that rely on WebView are in the same process, to avoid needing multiple
   2151      * data directories. The {@link #disableWebView} method can be used to ensure
   2152      * that the other processes do not use WebView by accident in this case.
   2153      * <p>
   2154      * This API must be called before any instances of WebView are created in
   2155      * this process and before any other methods in the android.webkit package
   2156      * are called by this process.
   2157      *
   2158      * @param suffix The directory name suffix to be used for the current
   2159      *               process. Must not contain a path separator.
   2160      * @throws IllegalStateException if WebView has already been initialized
   2161      *                               in the current process.
   2162      * @throws IllegalArgumentException if the suffix contains a path separator.
   2163      */
   2164     public static void setDataDirectorySuffix(String suffix) {
   2165         WebViewFactory.setDataDirectorySuffix(suffix);
   2166     }
   2167 
   2168     /**
   2169      * Indicate that the current process does not intend to use WebView, and
   2170      * that an exception should be thrown if a WebView is created or any other
   2171      * methods in the android.webkit package are used.
   2172      * <p>
   2173      * Applications with multiple processes may wish to call this in processes
   2174      * that are not intended to use WebView to avoid accidentally incurring
   2175      * the memory usage of initializing WebView in long-lived processes that
   2176      * have no need for it, and to prevent potential data directory conflicts
   2177      * (see {@link #setDataDirectorySuffix}).
   2178      * <p>
   2179      * For example, an audio player application with one process for its
   2180      * activities and another process for its playback service may wish to call
   2181      * this method in the playback service's {@link android.app.Service#onCreate}.
   2182      *
   2183      * @throws IllegalStateException if WebView has already been initialized
   2184      *                               in the current process.
   2185      */
   2186     public static void disableWebView() {
   2187         WebViewFactory.disableWebView();
   2188     }
   2189 
   2190 
   2191     /**
   2192      * @deprecated This was used for Gears, which has been deprecated.
   2193      * @hide
   2194      */
   2195     @Deprecated
   2196     public void refreshPlugins(boolean reloadOpenPages) {
   2197         checkThread();
   2198     }
   2199 
   2200     /**
   2201      * Puts this WebView into text selection mode. Do not rely on this
   2202      * functionality; it will be deprecated in the future.
   2203      *
   2204      * @deprecated This method is now obsolete.
   2205      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
   2206      */
   2207     @Deprecated
   2208     public void emulateShiftHeld() {
   2209         checkThread();
   2210     }
   2211 
   2212     /**
   2213      * @deprecated WebView no longer needs to implement
   2214      * ViewGroup.OnHierarchyChangeListener.  This method does nothing now.
   2215      */
   2216     @Override
   2217     // Cannot add @hide as this can always be accessed via the interface.
   2218     @Deprecated
   2219     public void onChildViewAdded(View parent, View child) {}
   2220 
   2221     /**
   2222      * @deprecated WebView no longer needs to implement
   2223      * ViewGroup.OnHierarchyChangeListener.  This method does nothing now.
   2224      */
   2225     @Override
   2226     // Cannot add @hide as this can always be accessed via the interface.
   2227     @Deprecated
   2228     public void onChildViewRemoved(View p, View child) {}
   2229 
   2230     /**
   2231      * @deprecated WebView should not have implemented
   2232      * ViewTreeObserver.OnGlobalFocusChangeListener. This method does nothing now.
   2233      */
   2234     @Override
   2235     // Cannot add @hide as this can always be accessed via the interface.
   2236     @Deprecated
   2237     public void onGlobalFocusChanged(View oldFocus, View newFocus) {
   2238     }
   2239 
   2240     /**
   2241      * @deprecated Only the default case, {@code true}, will be supported in a future version.
   2242      */
   2243     @Deprecated
   2244     public void setMapTrackballToArrowKeys(boolean setMap) {
   2245         checkThread();
   2246         mProvider.setMapTrackballToArrowKeys(setMap);
   2247     }
   2248 
   2249 
   2250     public void flingScroll(int vx, int vy) {
   2251         checkThread();
   2252         mProvider.flingScroll(vx, vy);
   2253     }
   2254 
   2255     /**
   2256      * Gets the zoom controls for this WebView, as a separate View. The caller
   2257      * is responsible for inserting this View into the layout hierarchy.
   2258      * <p/>
   2259      * API level {@link android.os.Build.VERSION_CODES#CUPCAKE} introduced
   2260      * built-in zoom mechanisms for the WebView, as opposed to these separate
   2261      * zoom controls. The built-in mechanisms are preferred and can be enabled
   2262      * using {@link WebSettings#setBuiltInZoomControls}.
   2263      *
   2264      * @deprecated the built-in zoom mechanisms are preferred
   2265      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN}
   2266      */
   2267     @Deprecated
   2268     public View getZoomControls() {
   2269         checkThread();
   2270         return mProvider.getZoomControls();
   2271     }
   2272 
   2273     /**
   2274      * Gets whether this WebView can be zoomed in.
   2275      *
   2276      * @return {@code true} if this WebView can be zoomed in
   2277      *
   2278      * @deprecated This method is prone to inaccuracy due to race conditions
   2279      * between the web rendering and UI threads; prefer
   2280      * {@link WebViewClient#onScaleChanged}.
   2281      */
   2282     @Deprecated
   2283     public boolean canZoomIn() {
   2284         checkThread();
   2285         return mProvider.canZoomIn();
   2286     }
   2287 
   2288     /**
   2289      * Gets whether this WebView can be zoomed out.
   2290      *
   2291      * @return {@code true} if this WebView can be zoomed out
   2292      *
   2293      * @deprecated This method is prone to inaccuracy due to race conditions
   2294      * between the web rendering and UI threads; prefer
   2295      * {@link WebViewClient#onScaleChanged}.
   2296      */
   2297     @Deprecated
   2298     public boolean canZoomOut() {
   2299         checkThread();
   2300         return mProvider.canZoomOut();
   2301     }
   2302 
   2303     /**
   2304      * Performs a zoom operation in this WebView.
   2305      *
   2306      * @param zoomFactor the zoom factor to apply. The zoom factor will be clamped to the WebView's
   2307      * zoom limits. This value must be in the range 0.01 to 100.0 inclusive.
   2308      */
   2309     public void zoomBy(float zoomFactor) {
   2310         checkThread();
   2311         if (zoomFactor < 0.01)
   2312             throw new IllegalArgumentException("zoomFactor must be greater than 0.01.");
   2313         if (zoomFactor > 100.0)
   2314             throw new IllegalArgumentException("zoomFactor must be less than 100.");
   2315         mProvider.zoomBy(zoomFactor);
   2316     }
   2317 
   2318     /**
   2319      * Performs zoom in in this WebView.
   2320      *
   2321      * @return {@code true} if zoom in succeeds, {@code false} if no zoom changes
   2322      */
   2323     public boolean zoomIn() {
   2324         checkThread();
   2325         return mProvider.zoomIn();
   2326     }
   2327 
   2328     /**
   2329      * Performs zoom out in this WebView.
   2330      *
   2331      * @return {@code true} if zoom out succeeds, {@code false} if no zoom changes
   2332      */
   2333     public boolean zoomOut() {
   2334         checkThread();
   2335         return mProvider.zoomOut();
   2336     }
   2337 
   2338     /**
   2339      * @deprecated This method is now obsolete.
   2340      * @hide Since API level {@link android.os.Build.VERSION_CODES#JELLY_BEAN_MR1}
   2341      */
   2342     @Deprecated
   2343     public void debugDump() {
   2344         checkThread();
   2345     }
   2346 
   2347     /**
   2348      * See {@link ViewDebug.HierarchyHandler#dumpViewHierarchyWithProperties(BufferedWriter, int)}
   2349      * @hide
   2350      */
   2351     @Override
   2352     public void dumpViewHierarchyWithProperties(BufferedWriter out, int level) {
   2353         mProvider.dumpViewHierarchyWithProperties(out, level);
   2354     }
   2355 
   2356     /**
   2357      * See {@link ViewDebug.HierarchyHandler#findHierarchyView(String, int)}
   2358      * @hide
   2359      */
   2360     @Override
   2361     public View findHierarchyView(String className, int hashCode) {
   2362         return mProvider.findHierarchyView(className, hashCode);
   2363     }
   2364 
   2365     /** @hide */
   2366     @IntDef(prefix = { "RENDERER_PRIORITY_" }, value = {
   2367             RENDERER_PRIORITY_WAIVED,
   2368             RENDERER_PRIORITY_BOUND,
   2369             RENDERER_PRIORITY_IMPORTANT
   2370     })
   2371     @Retention(RetentionPolicy.SOURCE)
   2372     public @interface RendererPriority {}
   2373 
   2374     /**
   2375      * The renderer associated with this WebView is bound with
   2376      * {@link Context#BIND_WAIVE_PRIORITY}. At this priority level
   2377      * {@link WebView} renderers will be strong targets for out of memory
   2378      * killing.
   2379      *
   2380      * Use with {@link #setRendererPriorityPolicy}.
   2381      */
   2382     public static final int RENDERER_PRIORITY_WAIVED = 0;
   2383     /**
   2384      * The renderer associated with this WebView is bound with
   2385      * the default priority for services.
   2386      *
   2387      * Use with {@link #setRendererPriorityPolicy}.
   2388      */
   2389     public static final int RENDERER_PRIORITY_BOUND = 1;
   2390     /**
   2391      * The renderer associated with this WebView is bound with
   2392      * {@link Context#BIND_IMPORTANT}.
   2393      *
   2394      * Use with {@link #setRendererPriorityPolicy}.
   2395      */
   2396     public static final int RENDERER_PRIORITY_IMPORTANT = 2;
   2397 
   2398     /**
   2399      * Set the renderer priority policy for this {@link WebView}. The
   2400      * priority policy will be used to determine whether an out of
   2401      * process renderer should be considered to be a target for OOM
   2402      * killing.
   2403      *
   2404      * Because a renderer can be associated with more than one
   2405      * WebView, the final priority it is computed as the maximum of
   2406      * any attached WebViews. When a WebView is destroyed it will
   2407      * cease to be considerered when calculating the renderer
   2408      * priority. Once no WebViews remain associated with the renderer,
   2409      * the priority of the renderer will be reduced to
   2410      * {@link #RENDERER_PRIORITY_WAIVED}.
   2411      *
   2412      * The default policy is to set the priority to
   2413      * {@link #RENDERER_PRIORITY_IMPORTANT} regardless of visibility,
   2414      * and this should not be changed unless the caller also handles
   2415      * renderer crashes with
   2416      * {@link WebViewClient#onRenderProcessGone}. Any other setting
   2417      * will result in WebView renderers being killed by the system
   2418      * more aggressively than the application.
   2419      *
   2420      * @param rendererRequestedPriority the minimum priority at which
   2421      *        this WebView desires the renderer process to be bound.
   2422      * @param waivedWhenNotVisible if {@code true}, this flag specifies that
   2423      *        when this WebView is not visible, it will be treated as
   2424      *        if it had requested a priority of
   2425      *        {@link #RENDERER_PRIORITY_WAIVED}.
   2426      */
   2427     public void setRendererPriorityPolicy(
   2428             @RendererPriority int rendererRequestedPriority,
   2429             boolean waivedWhenNotVisible) {
   2430         mProvider.setRendererPriorityPolicy(rendererRequestedPriority, waivedWhenNotVisible);
   2431     }
   2432 
   2433     /**
   2434      * Get the requested renderer priority for this WebView.
   2435      *
   2436      * @return the requested renderer priority policy.
   2437      */
   2438     @RendererPriority
   2439     public int getRendererRequestedPriority() {
   2440         return mProvider.getRendererRequestedPriority();
   2441     }
   2442 
   2443     /**
   2444      * Return whether this WebView requests a priority of
   2445      * {@link #RENDERER_PRIORITY_WAIVED} when not visible.
   2446      *
   2447      * @return whether this WebView requests a priority of
   2448      * {@link #RENDERER_PRIORITY_WAIVED} when not visible.
   2449      */
   2450     public boolean getRendererPriorityWaivedWhenNotVisible() {
   2451         return mProvider.getRendererPriorityWaivedWhenNotVisible();
   2452     }
   2453 
   2454     /**
   2455      * Sets the {@link TextClassifier} for this WebView.
   2456      */
   2457     public void setTextClassifier(@Nullable TextClassifier textClassifier) {
   2458         mProvider.setTextClassifier(textClassifier);
   2459     }
   2460 
   2461     /**
   2462      * Returns the {@link TextClassifier} used by this WebView.
   2463      * If no TextClassifier has been set, this WebView uses the default set by the system.
   2464      */
   2465     @NonNull
   2466     public TextClassifier getTextClassifier() {
   2467         return mProvider.getTextClassifier();
   2468     }
   2469 
   2470     /**
   2471      * Returns the {@link ClassLoader} used to load internal WebView classes.
   2472      * This method is meant for use by the WebView Support Library, there is no reason to use this
   2473      * method otherwise.
   2474      */
   2475     @NonNull
   2476     public static ClassLoader getWebViewClassLoader() {
   2477         return getFactory().getWebViewClassLoader();
   2478     }
   2479 
   2480     /**
   2481      * Returns the {@link Looper} corresponding to the thread on which WebView calls must be made.
   2482      */
   2483     @NonNull
   2484     public Looper getWebViewLooper() {
   2485         return mWebViewThread;
   2486     }
   2487 
   2488     //-------------------------------------------------------------------------
   2489     // Interface for WebView providers
   2490     //-------------------------------------------------------------------------
   2491 
   2492     /**
   2493      * Gets the WebViewProvider. Used by providers to obtain the underlying
   2494      * implementation, e.g. when the application responds to
   2495      * WebViewClient.onCreateWindow() request.
   2496      *
   2497      * @hide WebViewProvider is not public API.
   2498      */
   2499     @SystemApi
   2500     public WebViewProvider getWebViewProvider() {
   2501         return mProvider;
   2502     }
   2503 
   2504     /**
   2505      * Callback interface, allows the provider implementation to access non-public methods
   2506      * and fields, and make super-class calls in this WebView instance.
   2507      * @hide Only for use by WebViewProvider implementations
   2508      */
   2509     @SystemApi
   2510     public class PrivateAccess {
   2511         // ---- Access to super-class methods ----
   2512         public int super_getScrollBarStyle() {
   2513             return WebView.super.getScrollBarStyle();
   2514         }
   2515 
   2516         public void super_scrollTo(int scrollX, int scrollY) {
   2517             WebView.super.scrollTo(scrollX, scrollY);
   2518         }
   2519 
   2520         public void super_computeScroll() {
   2521             WebView.super.computeScroll();
   2522         }
   2523 
   2524         public boolean super_onHoverEvent(MotionEvent event) {
   2525             return WebView.super.onHoverEvent(event);
   2526         }
   2527 
   2528         public boolean super_performAccessibilityAction(int action, Bundle arguments) {
   2529             return WebView.super.performAccessibilityActionInternal(action, arguments);
   2530         }
   2531 
   2532         public boolean super_performLongClick() {
   2533             return WebView.super.performLongClick();
   2534         }
   2535 
   2536         public boolean super_setFrame(int left, int top, int right, int bottom) {
   2537             return WebView.super.setFrame(left, top, right, bottom);
   2538         }
   2539 
   2540         public boolean super_dispatchKeyEvent(KeyEvent event) {
   2541             return WebView.super.dispatchKeyEvent(event);
   2542         }
   2543 
   2544         public boolean super_onGenericMotionEvent(MotionEvent event) {
   2545             return WebView.super.onGenericMotionEvent(event);
   2546         }
   2547 
   2548         public boolean super_requestFocus(int direction, Rect previouslyFocusedRect) {
   2549             return WebView.super.requestFocus(direction, previouslyFocusedRect);
   2550         }
   2551 
   2552         public void super_setLayoutParams(ViewGroup.LayoutParams params) {
   2553             WebView.super.setLayoutParams(params);
   2554         }
   2555 
   2556         public void super_startActivityForResult(Intent intent, int requestCode) {
   2557             WebView.super.startActivityForResult(intent, requestCode);
   2558         }
   2559 
   2560         // ---- Access to non-public methods ----
   2561         public void overScrollBy(int deltaX, int deltaY,
   2562                 int scrollX, int scrollY,
   2563                 int scrollRangeX, int scrollRangeY,
   2564                 int maxOverScrollX, int maxOverScrollY,
   2565                 boolean isTouchEvent) {
   2566             WebView.this.overScrollBy(deltaX, deltaY, scrollX, scrollY, scrollRangeX, scrollRangeY,
   2567                     maxOverScrollX, maxOverScrollY, isTouchEvent);
   2568         }
   2569 
   2570         public void awakenScrollBars(int duration) {
   2571             WebView.this.awakenScrollBars(duration);
   2572         }
   2573 
   2574         public void awakenScrollBars(int duration, boolean invalidate) {
   2575             WebView.this.awakenScrollBars(duration, invalidate);
   2576         }
   2577 
   2578         public float getVerticalScrollFactor() {
   2579             return WebView.this.getVerticalScrollFactor();
   2580         }
   2581 
   2582         public float getHorizontalScrollFactor() {
   2583             return WebView.this.getHorizontalScrollFactor();
   2584         }
   2585 
   2586         public void setMeasuredDimension(int measuredWidth, int measuredHeight) {
   2587             WebView.this.setMeasuredDimension(measuredWidth, measuredHeight);
   2588         }
   2589 
   2590         public void onScrollChanged(int l, int t, int oldl, int oldt) {
   2591             WebView.this.onScrollChanged(l, t, oldl, oldt);
   2592         }
   2593 
   2594         public int getHorizontalScrollbarHeight() {
   2595             return WebView.this.getHorizontalScrollbarHeight();
   2596         }
   2597 
   2598         public void super_onDrawVerticalScrollBar(Canvas canvas, Drawable scrollBar,
   2599                 int l, int t, int r, int b) {
   2600             WebView.super.onDrawVerticalScrollBar(canvas, scrollBar, l, t, r, b);
   2601         }
   2602 
   2603         // ---- Access to (non-public) fields ----
   2604         /** Raw setter for the scroll X value, without invoking onScrollChanged handlers etc. */
   2605         public void setScrollXRaw(int scrollX) {
   2606             WebView.this.mScrollX = scrollX;
   2607         }
   2608 
   2609         /** Raw setter for the scroll Y value, without invoking onScrollChanged handlers etc. */
   2610         public void setScrollYRaw(int scrollY) {
   2611             WebView.this.mScrollY = scrollY;
   2612         }
   2613 
   2614     }
   2615 
   2616     //-------------------------------------------------------------------------
   2617     // Package-private internal stuff
   2618     //-------------------------------------------------------------------------
   2619 
   2620     // Only used by android.webkit.FindActionModeCallback.
   2621     void setFindDialogFindListener(FindListener listener) {
   2622         checkThread();
   2623         setupFindListenerIfNeeded();
   2624         mFindListener.mFindDialogFindListener = listener;
   2625     }
   2626 
   2627     // Only used by android.webkit.FindActionModeCallback.
   2628     void notifyFindDialogDismissed() {
   2629         checkThread();
   2630         mProvider.notifyFindDialogDismissed();
   2631     }
   2632 
   2633     //-------------------------------------------------------------------------
   2634     // Private internal stuff
   2635     //-------------------------------------------------------------------------
   2636 
   2637     private WebViewProvider mProvider;
   2638 
   2639     /**
   2640      * In addition to the FindListener that the user may set via the WebView.setFindListener
   2641      * API, FindActionModeCallback will register it's own FindListener. We keep them separate
   2642      * via this class so that the two FindListeners can potentially exist at once.
   2643      */
   2644     private class FindListenerDistributor implements FindListener {
   2645         private FindListener mFindDialogFindListener;
   2646         private FindListener mUserFindListener;
   2647 
   2648         @Override
   2649         public void onFindResultReceived(int activeMatchOrdinal, int numberOfMatches,
   2650                 boolean isDoneCounting) {
   2651             if (mFindDialogFindListener != null) {
   2652                 mFindDialogFindListener.onFindResultReceived(activeMatchOrdinal, numberOfMatches,
   2653                         isDoneCounting);
   2654             }
   2655 
   2656             if (mUserFindListener != null) {
   2657                 mUserFindListener.onFindResultReceived(activeMatchOrdinal, numberOfMatches,
   2658                         isDoneCounting);
   2659             }
   2660         }
   2661     }
   2662     private FindListenerDistributor mFindListener;
   2663 
   2664     private void setupFindListenerIfNeeded() {
   2665         if (mFindListener == null) {
   2666             mFindListener = new FindListenerDistributor();
   2667             mProvider.setFindListener(mFindListener);
   2668         }
   2669     }
   2670 
   2671     private void ensureProviderCreated() {
   2672         checkThread();
   2673         if (mProvider == null) {
   2674             // As this can get called during the base class constructor chain, pass the minimum
   2675             // number of dependencies here; the rest are deferred to init().
   2676             mProvider = getFactory().createWebView(this, new PrivateAccess());
   2677         }
   2678     }
   2679 
   2680     private static WebViewFactoryProvider getFactory() {
   2681         return WebViewFactory.getProvider();
   2682     }
   2683 
   2684     private final Looper mWebViewThread = Looper.myLooper();
   2685 
   2686     private void checkThread() {
   2687         // Ignore mWebViewThread == null because this can be called during in the super class
   2688         // constructor, before this class's own constructor has even started.
   2689         if (mWebViewThread != null && Looper.myLooper() != mWebViewThread) {
   2690             Throwable throwable = new Throwable(
   2691                     "A WebView method was called on thread '" +
   2692                     Thread.currentThread().getName() + "'. " +
   2693                     "All WebView methods must be called on the same thread. " +
   2694                     "(Expected Looper " + mWebViewThread + " called on " + Looper.myLooper() +
   2695                     ", FYI main Looper is " + Looper.getMainLooper() + ")");
   2696             Log.w(LOGTAG, Log.getStackTraceString(throwable));
   2697             StrictMode.onWebViewMethodCalledOnWrongThread(throwable);
   2698 
   2699             if (sEnforceThreadChecking) {
   2700                 throw new RuntimeException(throwable);
   2701             }
   2702         }
   2703     }
   2704 
   2705     //-------------------------------------------------------------------------
   2706     // Override View methods
   2707     //-------------------------------------------------------------------------
   2708 
   2709     // TODO: Add a test that enumerates all methods in ViewDelegte & ScrollDelegate, and ensures
   2710     // there's a corresponding override (or better, caller) for each of them in here.
   2711 
   2712     @Override
   2713     protected void onAttachedToWindow() {
   2714         super.onAttachedToWindow();
   2715         mProvider.getViewDelegate().onAttachedToWindow();
   2716     }
   2717 
   2718     /** @hide */
   2719     @Override
   2720     protected void onDetachedFromWindowInternal() {
   2721         mProvider.getViewDelegate().onDetachedFromWindow();
   2722         super.onDetachedFromWindowInternal();
   2723     }
   2724 
   2725     /** @hide */
   2726     @Override
   2727     public void onMovedToDisplay(int displayId, Configuration config) {
   2728         mProvider.getViewDelegate().onMovedToDisplay(displayId, config);
   2729     }
   2730 
   2731     @Override
   2732     public void setLayoutParams(ViewGroup.LayoutParams params) {
   2733         mProvider.getViewDelegate().setLayoutParams(params);
   2734     }
   2735 
   2736     @Override
   2737     public void setOverScrollMode(int mode) {
   2738         super.setOverScrollMode(mode);
   2739         // This method may be called in the constructor chain, before the WebView provider is
   2740         // created.
   2741         ensureProviderCreated();
   2742         mProvider.getViewDelegate().setOverScrollMode(mode);
   2743     }
   2744 
   2745     @Override
   2746     public void setScrollBarStyle(int style) {
   2747         mProvider.getViewDelegate().setScrollBarStyle(style);
   2748         super.setScrollBarStyle(style);
   2749     }
   2750 
   2751     @Override
   2752     protected int computeHorizontalScrollRange() {
   2753         return mProvider.getScrollDelegate().computeHorizontalScrollRange();
   2754     }
   2755 
   2756     @Override
   2757     protected int computeHorizontalScrollOffset() {
   2758         return mProvider.getScrollDelegate().computeHorizontalScrollOffset();
   2759     }
   2760 
   2761     @Override
   2762     protected int computeVerticalScrollRange() {
   2763         return mProvider.getScrollDelegate().computeVerticalScrollRange();
   2764     }
   2765 
   2766     @Override
   2767     protected int computeVerticalScrollOffset() {
   2768         return mProvider.getScrollDelegate().computeVerticalScrollOffset();
   2769     }
   2770 
   2771     @Override
   2772     protected int computeVerticalScrollExtent() {
   2773         return mProvider.getScrollDelegate().computeVerticalScrollExtent();
   2774     }
   2775 
   2776     @Override
   2777     public void computeScroll() {
   2778         mProvider.getScrollDelegate().computeScroll();
   2779     }
   2780 
   2781     @Override
   2782     public boolean onHoverEvent(MotionEvent event) {
   2783         return mProvider.getViewDelegate().onHoverEvent(event);
   2784     }
   2785 
   2786     @Override
   2787     public boolean onTouchEvent(MotionEvent event) {
   2788         return mProvider.getViewDelegate().onTouchEvent(event);
   2789     }
   2790 
   2791     @Override
   2792     public boolean onGenericMotionEvent(MotionEvent event) {
   2793         return mProvider.getViewDelegate().onGenericMotionEvent(event);
   2794     }
   2795 
   2796     @Override
   2797     public boolean onTrackballEvent(MotionEvent event) {
   2798         return mProvider.getViewDelegate().onTrackballEvent(event);
   2799     }
   2800 
   2801     @Override
   2802     public boolean onKeyDown(int keyCode, KeyEvent event) {
   2803         return mProvider.getViewDelegate().onKeyDown(keyCode, event);
   2804     }
   2805 
   2806     @Override
   2807     public boolean onKeyUp(int keyCode, KeyEvent event) {
   2808         return mProvider.getViewDelegate().onKeyUp(keyCode, event);
   2809     }
   2810 
   2811     @Override
   2812     public boolean onKeyMultiple(int keyCode, int repeatCount, KeyEvent event) {
   2813         return mProvider.getViewDelegate().onKeyMultiple(keyCode, repeatCount, event);
   2814     }
   2815 
   2816     /*
   2817     TODO: These are not currently implemented in WebViewClassic, but it seems inconsistent not
   2818     to be delegating them too.
   2819 
   2820     @Override
   2821     public boolean onKeyPreIme(int keyCode, KeyEvent event) {
   2822         return mProvider.getViewDelegate().onKeyPreIme(keyCode, event);
   2823     }
   2824     @Override
   2825     public boolean onKeyLongPress(int keyCode, KeyEvent event) {
   2826         return mProvider.getViewDelegate().onKeyLongPress(keyCode, event);
   2827     }
   2828     @Override
   2829     public boolean onKeyShortcut(int keyCode, KeyEvent event) {
   2830         return mProvider.getViewDelegate().onKeyShortcut(keyCode, event);
   2831     }
   2832     */
   2833 
   2834     @Override
   2835     public AccessibilityNodeProvider getAccessibilityNodeProvider() {
   2836         AccessibilityNodeProvider provider =
   2837                 mProvider.getViewDelegate().getAccessibilityNodeProvider();
   2838         return provider == null ? super.getAccessibilityNodeProvider() : provider;
   2839     }
   2840 
   2841     @Deprecated
   2842     @Override
   2843     public boolean shouldDelayChildPressedState() {
   2844         return mProvider.getViewDelegate().shouldDelayChildPressedState();
   2845     }
   2846 
   2847     @Override
   2848     public CharSequence getAccessibilityClassName() {
   2849         return WebView.class.getName();
   2850     }
   2851 
   2852     @Override
   2853     public void onProvideVirtualStructure(ViewStructure structure) {
   2854         mProvider.getViewDelegate().onProvideVirtualStructure(structure);
   2855     }
   2856 
   2857     /**
   2858      * {@inheritDoc}
   2859      *
   2860      * <p>The {@link ViewStructure} traditionally represents a {@link View}, while for web pages
   2861      * it represent HTML nodes. Hence, it's necessary to "map" the HTML properties in a way that is
   2862      * understood by the {@link android.service.autofill.AutofillService} implementations:
   2863      *
   2864      * <ol>
   2865      *   <li>Only the HTML nodes inside a {@code FORM} are generated.
   2866      *   <li>The source of the HTML is set using {@link ViewStructure#setWebDomain(String)} in the
   2867      *   node representing the WebView.
   2868      *   <li>If a web page has multiple {@code FORM}s, only the data for the current form is
   2869      *   represented&mdash;if the user taps a field from another form, then the current autofill
   2870      *   context is canceled (by calling {@link android.view.autofill.AutofillManager#cancel()} and
   2871      *   a new context is created for that {@code FORM}.
   2872      *   <li>Similarly, if the page has {@code IFRAME} nodes, they are not initially represented in
   2873      *   the view structure until the user taps a field from a {@code FORM} inside the
   2874      *   {@code IFRAME}, in which case it would be treated the same way as multiple forms described
   2875      *   above, except that the {@link ViewStructure#setWebDomain(String) web domain} of the
   2876      *   {@code FORM} contains the {@code src} attribute from the {@code IFRAME} node.
   2877      *   <li>The W3C autofill field ({@code autocomplete} tag attribute) maps to
   2878      *   {@link ViewStructure#setAutofillHints(String[])}.
   2879      *   <li>If the view is editable, the {@link ViewStructure#setAutofillType(int)} and
   2880      *   {@link ViewStructure#setAutofillValue(AutofillValue)} must be set.
   2881      *   <li>The {@code placeholder} attribute maps to {@link ViewStructure#setHint(CharSequence)}.
   2882      *   <li>Other HTML attributes can be represented through
   2883      *   {@link ViewStructure#setHtmlInfo(android.view.ViewStructure.HtmlInfo)}.
   2884      * </ol>
   2885      *
   2886      * <p>If the WebView implementation can determine that the value of a field was set statically
   2887      * (for example, not through Javascript), it should also call
   2888      * {@code structure.setDataIsSensitive(false)}.
   2889      *
   2890      * <p>For example, an HTML form with 2 fields for username and password:
   2891      *
   2892      * <pre class="prettyprint">
   2893      *    &lt;label&gt;Username:&lt;/label&gt;
   2894      *    &lt;input type="text" name="username" id="user" value="Type your username" autocomplete="username" placeholder="Email or username"&gt;
   2895      *    &lt;label&gt;Password:&lt;/label&gt;
   2896      *    &lt;input type="password" name="password" id="pass" autocomplete="current-password" placeholder="Password"&gt;
   2897      * </pre>
   2898      *
   2899      * <p>Would map to:
   2900      *
   2901      * <pre class="prettyprint">
   2902      *     int index = structure.addChildCount(2);
   2903      *     ViewStructure username = structure.newChild(index);
   2904      *     username.setAutofillId(structure.getAutofillId(), 1); // id 1 - first child
   2905      *     username.setAutofillHints("username");
   2906      *     username.setHtmlInfo(username.newHtmlInfoBuilder("input")
   2907      *         .addAttribute("type", "text")
   2908      *         .addAttribute("name", "username")
   2909      *         .addAttribute("label", "Username:")
   2910      *         .build());
   2911      *     username.setHint("Email or username");
   2912      *     username.setAutofillType(View.AUTOFILL_TYPE_TEXT);
   2913      *     username.setAutofillValue(AutofillValue.forText("Type your username"));
   2914      *     // Value of the field is not sensitive because it was created statically and not changed.
   2915      *     username.setDataIsSensitive(false);
   2916      *
   2917      *     ViewStructure password = structure.newChild(index + 1);
   2918      *     username.setAutofillId(structure, 2); // id 2 - second child
   2919      *     password.setAutofillHints("current-password");
   2920      *     password.setHtmlInfo(password.newHtmlInfoBuilder("input")
   2921      *         .addAttribute("type", "password")
   2922      *         .addAttribute("name", "password")
   2923      *         .addAttribute("label", "Password:")
   2924      *         .build());
   2925      *     password.setHint("Password");
   2926      *     password.setAutofillType(View.AUTOFILL_TYPE_TEXT);
   2927      * </pre>
   2928      */
   2929     @Override
   2930     public void onProvideAutofillVirtualStructure(ViewStructure structure, int flags) {
   2931         mProvider.getViewDelegate().onProvideAutofillVirtualStructure(structure, flags);
   2932     }
   2933 
   2934     @Override
   2935     public void autofill(SparseArray<AutofillValue>values) {
   2936         mProvider.getViewDelegate().autofill(values);
   2937     }
   2938 
   2939     @Override
   2940     public boolean isVisibleToUserForAutofill(int virtualId) {
   2941         return mProvider.getViewDelegate().isVisibleToUserForAutofill(virtualId);
   2942     }
   2943 
   2944     /** @hide */
   2945     @Override
   2946     public void onInitializeAccessibilityNodeInfoInternal(AccessibilityNodeInfo info) {
   2947         super.onInitializeAccessibilityNodeInfoInternal(info);
   2948         mProvider.getViewDelegate().onInitializeAccessibilityNodeInfo(info);
   2949     }
   2950 
   2951     /** @hide */
   2952     @Override
   2953     public void onInitializeAccessibilityEventInternal(AccessibilityEvent event) {
   2954         super.onInitializeAccessibilityEventInternal(event);
   2955         mProvider.getViewDelegate().onInitializeAccessibilityEvent(event);
   2956     }
   2957 
   2958     /** @hide */
   2959     @Override
   2960     public boolean performAccessibilityActionInternal(int action, Bundle arguments) {
   2961         return mProvider.getViewDelegate().performAccessibilityAction(action, arguments);
   2962     }
   2963 
   2964     /** @hide */
   2965     @Override
   2966     protected void onDrawVerticalScrollBar(Canvas canvas, Drawable scrollBar,
   2967             int l, int t, int r, int b) {
   2968         mProvider.getViewDelegate().onDrawVerticalScrollBar(canvas, scrollBar, l, t, r, b);
   2969     }
   2970 
   2971     @Override
   2972     protected void onOverScrolled(int scrollX, int scrollY, boolean clampedX, boolean clampedY) {
   2973         mProvider.getViewDelegate().onOverScrolled(scrollX, scrollY, clampedX, clampedY);
   2974     }
   2975 
   2976     @Override
   2977     protected void onWindowVisibilityChanged(int visibility) {
   2978         super.onWindowVisibilityChanged(visibility);
   2979         mProvider.getViewDelegate().onWindowVisibilityChanged(visibility);
   2980     }
   2981 
   2982     @Override
   2983     protected void onDraw(Canvas canvas) {
   2984         mProvider.getViewDelegate().onDraw(canvas);
   2985     }
   2986 
   2987     @Override
   2988     public boolean performLongClick() {
   2989         return mProvider.getViewDelegate().performLongClick();
   2990     }
   2991 
   2992     @Override
   2993     protected void onConfigurationChanged(Configuration newConfig) {
   2994         mProvider.getViewDelegate().onConfigurationChanged(newConfig);
   2995     }
   2996 
   2997     /**
   2998      * Creates a new InputConnection for an InputMethod to interact with the WebView.
   2999      * This is similar to {@link View#onCreateInputConnection} but note that WebView
   3000      * calls InputConnection methods on a thread other than the UI thread.
   3001      * If these methods are overridden, then the overriding methods should respect
   3002      * thread restrictions when calling View methods or accessing data.
   3003      */
   3004     @Override
   3005     public InputConnection onCreateInputConnection(EditorInfo outAttrs) {
   3006         return mProvider.getViewDelegate().onCreateInputConnection(outAttrs);
   3007     }
   3008 
   3009     @Override
   3010     public boolean onDragEvent(DragEvent event) {
   3011         return mProvider.getViewDelegate().onDragEvent(event);
   3012     }
   3013 
   3014     @Override
   3015     protected void onVisibilityChanged(View changedView, int visibility) {
   3016         super.onVisibilityChanged(changedView, visibility);
   3017         // This method may be called in the constructor chain, before the WebView provider is
   3018         // created.
   3019         ensureProviderCreated();
   3020         mProvider.getViewDelegate().onVisibilityChanged(changedView, visibility);
   3021     }
   3022 
   3023     @Override
   3024     public void onWindowFocusChanged(boolean hasWindowFocus) {
   3025         mProvider.getViewDelegate().onWindowFocusChanged(hasWindowFocus);
   3026         super.onWindowFocusChanged(hasWindowFocus);
   3027     }
   3028 
   3029     @Override
   3030     protected void onFocusChanged(boolean focused, int direction, Rect previouslyFocusedRect) {
   3031         mProvider.getViewDelegate().onFocusChanged(focused, direction, previouslyFocusedRect);
   3032         super.onFocusChanged(focused, direction, previouslyFocusedRect);
   3033     }
   3034 
   3035     /** @hide */
   3036     @Override
   3037     protected boolean setFrame(int left, int top, int right, int bottom) {
   3038         return mProvider.getViewDelegate().setFrame(left, top, right, bottom);
   3039     }
   3040 
   3041     @Override
   3042     protected void onSizeChanged(int w, int h, int ow, int oh) {
   3043         super.onSizeChanged(w, h, ow, oh);
   3044         mProvider.getViewDelegate().onSizeChanged(w, h, ow, oh);
   3045     }
   3046 
   3047     @Override
   3048     protected void onScrollChanged(int l, int t, int oldl, int oldt) {
   3049         super.onScrollChanged(l, t, oldl, oldt);
   3050         mProvider.getViewDelegate().onScrollChanged(l, t, oldl, oldt);
   3051     }
   3052 
   3053     @Override
   3054     public boolean dispatchKeyEvent(KeyEvent event) {
   3055         return mProvider.getViewDelegate().dispatchKeyEvent(event);
   3056     }
   3057 
   3058     @Override
   3059     public boolean requestFocus(int direction, Rect previouslyFocusedRect) {
   3060         return mProvider.getViewDelegate().requestFocus(direction, previouslyFocusedRect);
   3061     }
   3062 
   3063     @Override
   3064     protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
   3065         super.onMeasure(widthMeasureSpec, heightMeasureSpec);
   3066         mProvider.getViewDelegate().onMeasure(widthMeasureSpec, heightMeasureSpec);
   3067     }
   3068 
   3069     @Override
   3070     public boolean requestChildRectangleOnScreen(View child, Rect rect, boolean immediate) {
   3071         return mProvider.getViewDelegate().requestChildRectangleOnScreen(child, rect, immediate);
   3072     }
   3073 
   3074     @Override
   3075     public void setBackgroundColor(int color) {
   3076         mProvider.getViewDelegate().setBackgroundColor(color);
   3077     }
   3078 
   3079     @Override
   3080     public void setLayerType(int layerType, Paint paint) {
   3081         super.setLayerType(layerType, paint);
   3082         mProvider.getViewDelegate().setLayerType(layerType, paint);
   3083     }
   3084 
   3085     @Override
   3086     protected void dispatchDraw(Canvas canvas) {
   3087         mProvider.getViewDelegate().preDispatchDraw(canvas);
   3088         super.dispatchDraw(canvas);
   3089     }
   3090 
   3091     @Override
   3092     public void onStartTemporaryDetach() {
   3093         super.onStartTemporaryDetach();
   3094         mProvider.getViewDelegate().onStartTemporaryDetach();
   3095     }
   3096 
   3097     @Override
   3098     public void onFinishTemporaryDetach() {
   3099         super.onFinishTemporaryDetach();
   3100         mProvider.getViewDelegate().onFinishTemporaryDetach();
   3101     }
   3102 
   3103     @Override
   3104     public Handler getHandler() {
   3105         return mProvider.getViewDelegate().getHandler(super.getHandler());
   3106     }
   3107 
   3108     @Override
   3109     public View findFocus() {
   3110         return mProvider.getViewDelegate().findFocus(super.findFocus());
   3111     }
   3112 
   3113     /**
   3114      * If WebView has already been loaded into the current process this method will return the
   3115      * package that was used to load it. Otherwise, the package that would be used if the WebView
   3116      * was loaded right now will be returned; this does not cause WebView to be loaded, so this
   3117      * information may become outdated at any time.
   3118      * The WebView package changes either when the current WebView package is updated, disabled, or
   3119      * uninstalled. It can also be changed through a Developer Setting.
   3120      * If the WebView package changes, any app process that has loaded WebView will be killed. The
   3121      * next time the app starts and loads WebView it will use the new WebView package instead.
   3122      * @return the current WebView package, or {@code null} if there is none.
   3123      */
   3124     @Nullable
   3125     public static PackageInfo getCurrentWebViewPackage() {
   3126         PackageInfo webviewPackage = WebViewFactory.getLoadedPackageInfo();
   3127         if (webviewPackage != null) {
   3128             return webviewPackage;
   3129         }
   3130 
   3131         IWebViewUpdateService service = WebViewFactory.getUpdateService();
   3132         if (service == null) {
   3133             return null;
   3134         }
   3135         try {
   3136             return service.getCurrentWebViewPackage();
   3137         } catch (RemoteException e) {
   3138             throw e.rethrowFromSystemServer();
   3139         }
   3140     }
   3141 
   3142     /**
   3143      * Receive the result from a previous call to {@link #startActivityForResult(Intent, int)}.
   3144      *
   3145      * @param requestCode The integer request code originally supplied to
   3146      *                    startActivityForResult(), allowing you to identify who this
   3147      *                    result came from.
   3148      * @param resultCode The integer result code returned by the child activity
   3149      *                   through its setResult().
   3150      * @param data An Intent, which can return result data to the caller
   3151      *               (various data can be attached to Intent "extras").
   3152      * @hide
   3153      */
   3154     @Override
   3155     public void onActivityResult(int requestCode, int resultCode, Intent data) {
   3156         mProvider.getViewDelegate().onActivityResult(requestCode, resultCode, data);
   3157     }
   3158 
   3159     @Override
   3160     public boolean onCheckIsTextEditor() {
   3161         return mProvider.getViewDelegate().onCheckIsTextEditor();
   3162     }
   3163 
   3164     /** @hide */
   3165     @Override
   3166     protected void encodeProperties(@NonNull ViewHierarchyEncoder encoder) {
   3167         super.encodeProperties(encoder);
   3168 
   3169         checkThread();
   3170         encoder.addProperty("webview:contentHeight", mProvider.getContentHeight());
   3171         encoder.addProperty("webview:contentWidth", mProvider.getContentWidth());
   3172         encoder.addProperty("webview:scale", mProvider.getScale());
   3173         encoder.addProperty("webview:title", mProvider.getTitle());
   3174         encoder.addProperty("webview:url", mProvider.getUrl());
   3175         encoder.addProperty("webview:originalUrl", mProvider.getOriginalUrl());
   3176     }
   3177 }
   3178