Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

What is the Recommended Event for Updating WebView Navigation UI?

WebView offers goBack() and goForward() for implementing typical back-button behavior, which can be tied to buttons, action bar items, or whatever:

  @Override
  public boolean onOptionsItemSelected(MenuItem item) {
    switch(item.getItemId()) {
      case R.id.back:
        if (webView.canGoBack()) {
          webView.goBack();
        }
        break;

      case R.id.fwd:
        if (webView.canGoForward()) {
          webView.goForward();
        }
        break;

      case R.id.reload:
        webView.reload();
        break;

      default:
        return(super.onOptionsItemSelected(item));
    }

    return(true);
  }

WebView also has canGoBack() and canGoForward(), to tell you if those are viable options given the current navigation history in the WebView, shown above as guards around the goBack() and goForward() calls.

In theory, canGoBack() and canGoForward() could be used to enable or disable buttons, action bar items, or whatever. This would give you the typical browser UI, where the back and forward buttons are only available to the user when they would have an actual effect.

What is not obvious is when we should be calling canGoBack() and canGoForward() and enabling/disabling those buttons. Should that be in:

  • onPageStarted() in a custom WebViewClient?
  • doUpdateVisitedHistory() in a custom WebViewClient?
  • in some other callback?
  • some combination of these?
  • every second or so purely on a timer, because we have no reliable callback for determining when those should get updated?
like image 558
CommonsWare Avatar asked Jul 06 '15 13:07

CommonsWare


People also ask

Which of the following is enabled by default in Android WebView?

The WebView class is an extension of Android's View class that allows you to display web pages as a part of your activity layout. It does not include any features of a fully developed web browser, such as navigation controls or an address bar. All that WebView does, by default, is show a web page.

Which method is used to load webpages WebView?

The loadUrl() and loadData() methods of Android WebView class are used to load and display web page.

How do I close WebView on Android?

Add a close button and on its click set: webview. setVisibility(View. INVISIBLE); webview.

Is Android WebView deprecated?

This interface was deprecated in API level 12. This interface is now obsolete.


2 Answers

The docs of canGoBack() currently state that it returns true if

this WebView has a back history item

canGoForward() has a similar Javadoc.

The problem is that it isn't clearly documented when the back history has been changed. It would depend entirely on the implementation of the WebView(Client) and this could always change in the future. It might even be different on various Android devices/versions/forks.

doUpdateVisitedHistory() is also not clearly documented:

Notify the host application to update its visited links database.

The problem is that it doesn't state WHEN it is being called, only that you need to update your visited links. It could be called earlier or later than you desire, depending on the WebView(Client) implementation.

I think the choice is yours to determine how safe you would like to make your code against possible failures.

Personally, I would go with updating at onPageStarted(), onPageFinished() and doUpdateVisitedHistory() because it works in all reasonably expected conditions and doesn't have the performance overhead of polling with a timer.
Then I would test it on devices of several brands and Android versions to see if it behaves like I expect it to.
If it then still doesn't work, one could consider implementing a timer/polling mechanism.

like image 191
Byte Welder Avatar answered Oct 16 '22 08:10

Byte Welder


You can check using the methods canGoBack() and canGoForward() in the onPageFinished callback. This way, you know a new page has just finished loading, thus you can verify if the webview can go forward or back and then enable/disable your buttons.

I used it this way and it works great

like image 22
DDsix Avatar answered Oct 16 '22 07:10

DDsix