添加数据后如何调整android webview的大小
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/1973565/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to resize a android webview after adding data in it
提问by Chitranshu Asthana
In a layout (linear, vertical) hierarchy I've got several views and one of them is a WebView. They all have same parameters:
在布局(线性、垂直)层次结构中,我有几个视图,其中一个是 WebView。它们都有相同的参数:
android:layout_width="fill_parent"
android:layout_height="wrap_content"
For all views, the spacing between elements is correctly handled but for the Webview there is a lot of spaces after the displayed text inside.
对于所有视图,元素之间的间距都得到了正确处理,但对于 Web 视图,内部显示的文本后面有很多空格。
I set the (HTML) text of the webview in the "onCreate" method of the activity using the layout.
我使用布局在活动的“onCreate”方法中设置了 webview 的(HTML)文本。
Is there a way to let the webview resize itself, to match its content size?
有没有办法让 webview 调整自身大小,以匹配其内容大小?
By the way, the space left vary from one device to another (emulator vs Milestone vs Hero)
顺便说一句,剩余空间因设备而异(模拟器与里程碑与英雄)
Any idea? Thanks
任何的想法?谢谢
回答by Chitranshu Asthana
I am sure this is too late but adding the method which worked for me in case somebody else comes here looking for solution.
我确信这为时已晚,但添加对我有用的方法,以防其他人来这里寻找解决方案。
Once the page finishes loading, I am injecting a javascript method to callback me JS hook. And in this method I am passing the size of .
一旦页面完成加载,我就会注入一个 javascript 方法来回调我的 JS 钩子。在这种方法中,我传递了 .
private void setupWebView() {
webView.getSettings().setJavaScriptEnabled(true);
webView.setWebViewClient(new WebViewClient() {
@Override
public void onPageFinished(WebView view, String url) {
webView.loadUrl("javascript:MyApp.resize(document.body.getBoundingClientRect().height)");
super.onPageFinished(view, url);
}
});
webView.addJavascriptInterface(this, "MyApp");
}
@JavascriptInterface
public void resize(final float height) {
MyActivity.this.runOnUiThread(new Runnable() {
@Override
public void run() {
webView.setLayoutParams(new LinearLayout.LayoutParams(getResources().getDisplayMetrics().widthPixels, (int) (height * getResources().getDisplayMetrics().density)));
}
});
}
The same solution can also be seen here.
回答by Janusz
It seems that at the moment the Webview only resizes itself if the content is too big. If the webview is bigger then the content it doesn't shrinks to reclaim the space.
目前看来,如果内容太大,Webview 只会调整自身大小。如果 webview 更大,那么它的内容不会缩小以回收空间。
回答by Fernwilter
I had the same problem. I solved by changing the visibility of the WebView.
我有同样的问题。我通过改变 WebView 的可见性来解决。
mWebView.setVisibility(View.GONE);
mWebView.loadData(".....");
mWebView.reload();
mWebView.setVisibility(View.VISIBLE);
回答by eJal
After some hours of searching and trying I found the simplest working solution. Just call this as "repaint":
经过几个小时的搜索和尝试,我找到了最简单的工作解决方案。只需将其称为“重绘”:
webView.setLayoutParams(new LinearLayout.LayoutParams(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT));
For my webview it works perfectly inside a scrollView. If you do not want to use WRAP_CONTENT, you can use your own params.
对于我的 webview,它在 scrollView 中完美运行。如果您不想使用 WRAP_CONTENT,您可以使用您自己的参数。
回答by VuVanLy
I only put the webview inside the ScrollView and set layout_height=wrap_content and it worked.
我只将 webview 放在 ScrollView 中并设置 layout_height=wrap_content 并且它起作用了。
<ScrollView
android:layout_width="fill_parent"
android:layout_height="fill_parent"
android:id="@+id/web_scrollview"
android:layout_below="@id/question_title_section"
android:layout_marginBottom="60dp"
android:scrollbars="vertical">
<WebView
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:id="@+id/question_content"
android:layout_marginLeft="4dp"
android:layout_marginRight="4dp"
android:padding="4dp">
</WebView>
</ScrollView>
And in my Activity
在我的活动中
wvQuestion = (WebView) findViewById(R.id.question_content);
wvQuestion.loadUrl(url);
回答by user1253661
I found:
我发现:
(1) there are two height in webview. MeasureHeight and contentHeight. Note that the contentHeight is computed from the webcoreThread. The two height are not consistent any time!
(1) webview中有两个高度。MeasureHeight 和 contentHeight。请注意, contentHeight 是从 webcoreThread 计算的。两个人的身高任何时候都不一致!
(2) when layout finish.the webview reload content. The contentHeight is consistent with measureHeight.
(2) 当布局完成时,webview 重新加载内容。contentHeight 与 measureHeight 一致。
So I think one solution is: make webview reload content after the layout finished.
所以我认为一种解决方案是:在布局完成后让 webview 重新加载内容。
My solution:
我的解决方案:
(1)extends webview . (2)override onlayout(),dispatchDraw(),
(1) 扩展 webview 。(2)覆盖onlayout(),dispatchDraw(),
@Override
protected void dispatchDraw(Canvas canvas) {
// TODO Auto-generated method stub
super.dispatchDraw(canvas);
//mchanged == is parameter in onlayout()
//finished == have run the code below !
if (!mchanged && !finished) {
//
String vHtml =".........." ;//your html content
this.loadDataWithBaseURL("目录浏览", vHtml, "text/html", "utf-8", null);
finished = true;
}
}
protected void onLayout(boolean changed, int l, int t, int r, int b) {
// TODO Auto-generated method stub
super.onLayout(changed, l, t, r, b);
// tttttt
if (!changed) {
this.mchanged = changed;//false
}
}
(3) webview need init before load every content.
(3) webview 在加载每个内容之前需要初始化。
public void intiFlag() {
mchanged = true;
finished = false ;
}
Hope this helps.
希望这可以帮助。
回答by caiiiycuk
You can periodically update WebView height according to javascript body height, like this:
您可以根据 javascript 主体高度定期更新 WebView 高度,如下所示:
public class WrapContentWebView extends WebView {
private static final long UPDATE_INTERVAL = 100; // ms
public WrapContentWebView(Context context) {
super(context);
init();
}
public WrapContentWebView(Context context, AttributeSet attrs) {
super(context, attrs);
init();
}
public WrapContentWebView(Context context, AttributeSet attrs, int defStyle) {
super(context, attrs, defStyle);
init();
}
private void init() {
addJavascriptInterface(new JavascriptInterface(), "java");
postDelayed(scheduleRunnable, UPDATE_INTERVAL);
}
private Runnable scheduleRunnable = new Runnable() {
@Override
public void run() {
loadUrl("javascript:window.java.onNewHeight(document.body.offsetHeight);");
postDelayed(scheduleRunnable, UPDATE_INTERVAL);
}
};
private class JavascriptInterface {
@android.webkit.JavascriptInterface
public void onNewHeight(String bodyOffsetHeight) {
if (bodyOffsetHeight == null) {
return;
}
final int newHeight =
(int) (Integer.parseInt(bodyOffsetHeight) *
getScaleY() *
getResources().getDisplayMetrics().density);
if (getLayoutParams().height != newHeight) {
((Activity) getContext()).runOnUiThread(new Runnable() {
@Override
public void run() {
getLayoutParams().height = newHeight;
requestLayout();
}
});
}
}
}
}
layout.xml:
布局.xml:
<WrapContentWebView
android:layout_width="match_parent"
android:layout_height="0dp">
</WrapContentWebView>
P.S. Checked on Android 5, 4.1, 4.04
PS 在 Android 5、4.1、4.04 上检查
回答by NameNotFound
Agree with @Fernwilter. But changing the sequence worked for me.
同意@Fernwilter。但是改变顺序对我有用。
mWebView.setVisibility(View.GONE);
mWebView.reload();
mWebView.setVisibility(View.VISIBLE);
mWebView.loadData(".....");
回答by Tuan Nguyen
It worked for me.
它对我有用。
ViewTreeObserver viewTreeObserver = dataWebView.getViewTreeObserver();
viewTreeObserver.addOnGlobalLayoutListener(new ViewTreeObserver.OnGlobalLayoutListener() {
@Override
public void onGlobalLayout() {
if (dataWebView.getMeasuredHeight() > 0) {
dataWebView.getViewTreeObserver().removeGlobalOnLayoutListener(this);
((Activity) getContext()).runOnUiThread(() -> {
dataWebView.setLayoutParams(new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, 0));
dataWebView.setVisibility(View.GONE);
dataWebView.setLayoutParams(new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, LinearLayout.LayoutParams.WRAP_CONTENT));
dataWebView.setVisibility(View.VISIBLE);
});
}
}
});
回答by Codeversed
If you simply remove the view and then add a new one back, problem solved.
如果您只是删除视图,然后再添加一个新视图,问题就解决了。
Here is an example:
下面是一个例子:
WebView current_view = (WebView) view.getChildAt(i);
CharSequence current_text = current_view.getText();
int index = parent.indexOfChild(current_view);
parent.removeView(current_view);
current_view = new WebView(context);
parent.addView(current_view, index, layoutParams);
current_view.loadDataWithBaseURL( ...however you want... );
view.invalidate();
In summary... it just adds a new WebView just like the old right back to its parent at the same index.
总之......它只是在相同的索引处添加一个新的 WebView 就像旧的一样回到它的父级。