使用WebViewClient和/或WebChromeClient,您可以在页面加载时获取侦听器,但是在WebView显示任何内容之前,有时会在WebView中包含任何内容之前调用它.
什么是确定WebView何时显示其内容的有效方法?
编辑:(试图更清楚)
当我在WebView中加载页面时,我想将滚动设置为特定位置.看起来在页面加载之前无法设置滚动位置,并且它具有实际的内容高度.因此,我尝试了两种不同的方法来确定页面何时完成加载,来自WebViewClient的onPageFinished()以及来自WebChromeClient的onProgressChanged().这两个都告诉我页面何时完成加载.
但问题是,有时在页面显示之前调用它,因此页面没有高度,滚动调用什么都不做.
我试图找到一种可靠的方法来确定页面何时可以滚动,即.当它的内容高度.
我想我可以在完成加载后设置一个检查循环,以便在高度可用时继续寻找,但这看起来很像黑客.希望有一种更清洁的方式.
我用PictureListener成功地使用了Richard的答案几年,但我不再推荐这个作为最佳解决方案.
这有两个原因:
webView.setPictureListener和PictureListener都弃用.
使用此侦听器将导致WebView经常分配新图片.这种分配很昂贵,这可能会对性能产生一些重大影响甚至导致JellyBean MR1上的本机崩溃.
相反,我建议创建WebView的子类并覆盖invalidate(),如下所示:
@Override public void invalidate() { super.invalidate(); if (getContentHeight() > 0) { // WebView has displayed some content and is scrollable. } }
如果您仍想使用PictureListener方法,那么在完成后将setPictureListener恢复为null将获得更好的性能.
编辑:自从我第一次发布此功能以来,此方法已在Android API 12中弃用.谢谢,Google!我会留下原始答案:
是的 - 有一个听众知道内容何时完成加载.我不得不在我的项目中创建一个,所以我可以做一个启动画面,直到webview加载页面为止.
它被称为.setPictureListener.
例如:
mWebView.setPictureListener(new MyPictureListener()); //... and then later on.... class MyPictureListener implements PictureListener { @Override public void onNewPicture(WebView view, Picture arg1) { // put code here that needs to run when the page has finished loading and // a new "picture" is on the webview. } }
这里建议的解决方案充其量只是hacky,而有一个非常干净的解决方案,根据Android文档:
WebViewClient client = new WebViewClient() { @Override public void onPageFinished(WebView view, String url) { Log.d("MYAPP", "Page loaded"); } }; webView.setWebViewClient(client);
我读了这个讨论,我也遇到了同样的问题.
我搜索了很多,但他们不是他们承诺的解决方案.
而且我不想使用已弃用的`onNewPicture`回调.
在我自己的情况下,我只需要在活动开始时恢复`WebView`滚动位置,我认为这是大多数情况,因为当活动任务堆栈进入后台时,Android会自动保存`WebView`状态,所以当它弹出到前台,看起来会一样.如果它在后台被杀死,我相信你会设法将状态保存在像`onPause`这样的Activity生命周期方法中.
所以,我没有扩展`WebView`而是覆盖blah,blah,blah ......,而是使用Handler和post model.
private final Handler mHandler = new Handler(); // in onCreate mHandler.postDelayed(new Runnable() { @Override public void run() { if (mWebView.getContentHeight() > 0) { mWebView.scrollTo(0, mLastPosition); Log.d("scrolling", "true"); mHandler.removeCallbacks(this); } else { mHandler.postDelayed(this, 100); } } }, 100);
此代码块将进行peridically检查是否可以操作WebView页面,如果是,它会进行滚动并删除回调,否则循环.我测试了这个并且发现它通常不会花很长时间.
希望这可以帮助!