Xamarin Forms WKWebView 大小不会缩小

Xamarin Forms WKWebView size doesn't shrink

我有一个自定义 WkWebView,我将视图的 height 设置为 html 内容的大小。

这在我初始化它时效果很好,但是当我将 WkWebViewsource 更改为较短的 html.

时,问题就来了

我已经在 android 版本的应用程序中遇到了 ,我通过在 EvaluateJavaScriptAsync 之前将 HeightRequest 设置为 0 来解决这个问题。这样视野就会变大。

我用 iOS 尝试过同样的事情,但它保留了我拥有的最高内容。

例如:

如果我将 WkWebView 的源设置为 200px 高度的 html 文件并将其更改为 1000px 的 html 文件,它工作正常,我可以查看全部内容。但是,如果我尝试回到我的 200px html 文件,我会在下面得到一个 800px 的空白 space 并保持 1000px 的高度。

目标是始终让 WKWebView 的高度适应其内容的高度。

这是自定义渲染的当前版本

namespace MyNamespace.iOS.CustomControl
{
    public class AutoHeightWebViewRenderer : WkWebViewRenderer
    {
        protected override void OnElementChanged(VisualElementChangedEventArgs e)
        {
            try
            {
                base.OnElementChanged(e);

                if (NativeView != null)
                {
                    var webView = (WKWebView)NativeView;
                    NavigationDelegate = new ExtendedWKWebViewDelegate(this);
                }
            }
            catch (Exception ex)
            {
                //Log the Exception  
            }   
        }
    }


    class ExtendedWKWebViewDelegate : WKNavigationDelegate
    {

        AutoHeightWebViewRenderer webViewRenderer;

        public ExtendedWKWebViewDelegate(AutoHeightWebViewRenderer _webViewRenderer = null)
        {
            webViewRenderer = _webViewRenderer ?? new AutoHeightWebViewRenderer();
        }

        public override async void DidFinishNavigation(WKWebView webView, WKNavigation navigation)
        {
            try
            {
                var _webView = webViewRenderer.Element as AutoHeightWebView;
                if (_webView != null)
                {
                    _webView.HeightRequest = 0d;
                    await Task.Delay(300);
                    var result = await _webView.EvaluateJavaScriptAsync("(function(){return document.body.scrollHeight;})()");
                    _webView.HeightRequest = Convert.ToDouble(result);
                }
            }
            catch (Exception ex)
            {
                //Log the Exception 
            }
        }

    }
}

编辑 1: 更清楚地说,我可以更改 webview 的高度,但我不知道高度,因为它总是返回目前显示的最大 html 的高度。无论我使用 _webView.EvaluateJavaScriptAsync("(function(){return document.body.scrollHeight;})()") 还是 webView.ScrollView.ContentSize.Height.

编辑 2: 这里有一个小例子来帮助理解这个问题。我有两个按钮和我的自定义 webview(初始化为 40 HeightRequest 空 html)。 第一个按钮将 webview 的 Source 设置为 70px 长 HTML。第二个将 Source 设置为 280px 长 HTML.

在这个例子中,我点击了第一个按钮而不是第二个按钮,最后又回到了第一个按钮。您会看到 webview 在前 2 次点击时变大。但是当我选择第一个 html 时,webview 应该会缩小(从 280px 到 70px),但它会保持 280px 的长度。

第一个按钮(70px 长)

第二个按钮(280px 长)

返回第一个按钮(长度应为 70 像素而不是 280 像素)。

模拟器和 iOS 设备均出现问题。

您可以更改 webViewFrame 来更改 height

public override async void DidFinishNavigation(WKWebView webView, WKNavigation navigation)
{
    try
    {
        var _webView = webViewRenderer.Element as WebView;
        if (_webView != null)
        {

            webView.Frame = new CGRect(webView.Frame.Location, new CGSize(webView.Frame.Size.Width, 0));

            var a = webView.ScrollView.ContentSize.Height;
            var b = await _webView.EvaluateJavaScriptAsync("(function(){return document.body.scrollHeight;})()");

            Console.WriteLine(a);
            Console.WriteLine(b);

            CGRect tempRect = webView.Frame;

            // for test                    
            webView.Frame = new CGRect(tempRect.Location.X, tempRect.Location.Y, tempRect.Size.Width, float.Parse(b));

        }
    }
    catch (Exception ex)
    {
        //Log the Exception 
    }
}

我遇到了同样的问题,CustomNavigationDelegate 也只会显示相同的大尺寸,即设备显示尺寸。

我发现我已经在 XAML 的初始化部分和后面的代码中设置了它,它以某种方式覆盖了后来基于内容的计算。

在这里查看我的修复: