However, we also have to make one change to AndroidManifest.xml
, requesting permission to access the Internet:
<manifest xmlns:android='http://schemas.android.com/apk/res/android'
package='com.commonsware.android.webkit'>
<uses-permission android:name='android.permission.INTERNET' />
<application>
<activity android:name='.BrowserDemo1' android:label='BrowserDemo1'>
<intent-filter>
<action android:name='android.intent.action.MAIN' />
<category android:name='android.intent.category.LAUNCHER' />
</intent-filter>
</activity>
</application>
</manifest>
If we fail to add this permission, the browser will refuse to load pages.
The resulting activity looks like a Web browser, just with hidden scrollbars (see Figure 13-1).

Figure 13-1.
As with the regular Android browser, you can pan around the page by dragging it, while the directional pad moves you around all the focusable elements on the page.
What is missing is all the extra accouterments that make up a Web browser, such as a navigational toolbar.
Now, you may be tempted to replace the URL in that source code with something else, such as Google’s home page or another page that relies upon Javascript. By default Javascript is turned off in WebView
widgets. If you want to enable Javascript, call getSettings ().setJavaScriptEnabled(true);
on the WebView
instance.
Loading It Up
There are two main ways to get content into the WebView
. One, shown earlier, is to provide the browser with a URL and have the browser display that page via loadUrl()
. The browser will access the Internet through whatever means are available to that specific device at the present time (WiFi, cellular network, Bluetooth-tethered phone, well-trained tiny carrier pigeons, etc.).
The alternative is to use loadData()
. Here, you supply the HTML for the browser to view. You might use this to
• display a manual that was installed as a file with your application package
• display snippets of HTML you retrieved as part of other processing, such as the description of an entry in an Atom feed
• generate a whole user interface using HTML, instead of using the Android widget set
There are two flavors of loadData()
. The simpler one allows you to provide the content, the MIME type, and the encoding, all as strings. Typically, your MIME type will be text/html and your encoding will be UTF-8
for ordinary HTML.
For instance, if you replace the loadUrl()
invocation in the previous example with the following code, you get the result shown in Figure 13-2.
browser.loadData('<html><body>Hello, world! </body></html>',
'text/html', 'UTF-8');

Figure 13-2.
This is also available as a fully-buildable sample, as WebKit/Browser2
.
Navigating the Waters
As previously mentioned, there is no navigation toolbar with the WebView widget. This allows you to use it in places where such a toolbar would be pointless and a waste of screen real estate. That being said, if you want to offer navigational capabilities, you can, but you have to supply the UI.
WebView
offers ways to perform garden-variety browser navigation, including the following:
• reload()
to refresh the currently-viewed Web page
• goBack()
to go back one step in the browser history, and canGoBack()
to determine if there is any history to go back to
• goForward()
to go forward one step in the browser history, and canGoForward ()
to determine if there is any history to go forward to
• goBackOrForward()
to go backward or forward in the browser history, where a negative number as an argument represents a count of steps to go backward, and a positive number represents how many steps to go forward
• canGoBackOrForward()
to see if the browser can go backward or forward the stated number of steps (following the same positive/negative convention as goBackOrForward()
)
• clearCache()
to clear the browser resource cache and clearHistory()
to clear the browsing history
Entertaining the Client
If you are going to use the WebView
as a local user interface (vs. browsing the Web), you will want to be able to get control at key times, particularly when users click on links. You will want to make sure those links are handled properly, either by loading your own content back into the WebView
, by submitting an Intent to Android to open the URL in a full browser, or by some other means (see Chapter 25).
Your hook into the WebView
activity is via setWebViewClient()
, which takes an instance of a WebViewClient
implementation as a parameter. The supplied callback object will be notified of a wide range of activities, ranging from when parts of a page have been retrieved (onPageStarted()
, etc.) to when you, as the host application, need to handle certain user-or circumstance-initiated events, such as onTooManyRedirects()
and onReceivedHttpAuthRequest()
, etc.
A common hook will be shouldOverrideUrlLoading()
, where your callback is passed a URL (plus the WebView
itself) and you return true if you will handle the request or false
if you want default handling (e.g., actually fetch the Web page referenced by the URL). In the case of a feed reader application, for example, you will probably not have a full browser with navigation built into your reader, so if the user clicks a URL, you probably want to use an Intent
to ask Android to load that page in a full browser. But, if you have inserted a “fake” URL into the HTML, representing a link to some activity-provided content, you can update the WebView
yourself.
For example, let’s amend the first browser example to be a browser-based equivalent of our original example: an application that, upon a click, shows the current time.
From WebKit/Browser3
, here is the revised Java: