在Xamarin浏览器控件中访问html响应内容 [英] Accessing html response content in Xamarin browser control

查看:81
本文介绍了在Xamarin浏览器控件中访问html响应内容的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我似乎有一个不寻常的要求,就是我和我的同事无法在我们的Xamarin项目中实现.我们正在尝试做的是动态处理浏览器导航到的任何页面的内容,而不是简单地处理从其访问的初始URL返回的内容.

I have what seems to be an unusual requirement that my colleagues and I haven't been able to implement in our Xamarin project. What we are trying to do is dynamically process the contents of any page that a browser navigates to rather than simply the content returned from the initial URL it accesses.

我已经看到了访问以这种方式返回的内容的解决方案:

I have seen solutions for accessing the content returned this way:

Xamarin:如何从WebView的页面中获取HTML?

但是,仅当浏览器从其指向的初始URL接收到第一个html响应时,此代码才会运行.我们需要动态处理浏览器收到的 任何 内容,即使将其重定向到其他URL或用户单击内容中的链接也是如此.我们已经使用WebBrowser.DocumentCompleted事件在.NET本机Windows客户端中实现了此功能,只要控件加载内容,就会触发该事件.Xamarin WebViewRendered加载内容时,除第一次加载外,我们没有发现任何引发事件或调用的方法,因此我们无法获取后续资源的内容.

However this code will only run when the browser receives the first html response from the initial URL it is pointed to. We need to dynamically process any content the browser receives even if it is redirected to a different URL or if the user clicks on links in the content. We have implemented this in our .NET native Windows clients using the WebBrowser.DocumentCompleted event, which is raised whenever the control loads content. We have not found any event raised or method called when the Xamarin WebViewRendered loads content except on the first load, so we have not been able to get the content of subsequent resources.

总结:如何动态获取Web浏览器导航到的任何URL的内容?答案可以包括可部署到Android和iOS的.NET Xamarin项目中可访问的任何内容,包括第三方开源代码.

To summarize: how can I dynamically get the content of any URL that a web browser navigates to? The answer can include anything accessible in a .NET Xamarin project deployable to Android and iOS including third party open source code.

推荐答案

在HTML页面完成加载后,这两种与设备相关的技术都使用JavaScript评估/执行,以便将全部html内容作为JavaScript结果接收(编辑如果您的要求不要求返回整个页面,请参见示例中的JavaScript.

Both these device-dependent techniques use JavaScript evaluation/execution after the HTML page has finished loading in order for to receive the entire html contents as a JavaScript result (edit the JavaScript in the examples if your requirements to not require the entire page to be return).

您可以通过分配实现 IValueCallback 的子类 WebViewClient 来捕获 WebView 中加载的html.页面加载完成后, OnReceiveValue 方法将包含html内容:

You can capture the loaded html within a WebView by assigning a subclassed WebViewClient that implements IValueCallback. The OnReceiveValue method will contain the html content after the page has finished loading:

public class EmbeddedWebViewClient : WebViewClient, IValueCallback
{
    public EmbeddedWebViewClient(WebView view)
    {
        view.Settings.JavaScriptEnabled = true;
    }

    public override void OnPageFinished(WebView view, string url)
    {
        base.OnPageFinished(view, url);
        Log.Info("SO", $"Page loaded from: {url}");
        view.EvaluateJavascript("(function() { return ('<html>'+document.getElementsByTagName('html')[0].innerHTML+'</html>'); })();", this);
    }

    public void OnReceiveValue(Java.Lang.Object value)
    {
        // "value" holds the html contents of the loaded page
        Log.Debug("SO", ((string)value).Substring(0, 40));
    }
}

WebViewClient用法示例:

WebView webview = FindViewById<WebView>(Resource.Id.webview);
webview.SetWebViewClient(new EmbeddedWebViewClient(webview));
webview.LoadUrl("https://xamarin.com");

Xamarin.iOS

您可以通过为其分配一个 IWKNavigationDelegate 来捕获 WKWebView 中加载的html.要么在自己的类中实现它,要么在包含 WKWebView

Xamarin.iOS

You can capture the loaded html within a WKWebView by assigning a IWKNavigationDelegate to it. Either implement it within its own class or the controller that contains the WKWebView

public class NavigationDelegate : NSObject, IWKNavigationDelegate
{
    [Export("webView:didFinishNavigation:")]
    public async void DidFinishNavigation(WKWebView webView, WKNavigation navigation)
    {
        var content = await webView.EvaluateJavaScriptAsync("(function() { return ('<html>'+document.getElementsByTagName('html')[0].innerHTML+'</html>'); })();");
        var html = FromObject(content);
        Console.WriteLine((html.ToString()).Substring(0, 40));
    }
}

WKWebView用法示例:

wkwebview = new WKWebView(UIScreen.MainScreen.Bounds, new WKWebViewConfiguration());
wkwebview.NavigationDelegate = new NavigationDelegate();
Add(wkwebview);
wkwebview.LoadRequest(new NSUrlRequest(new Uri("https://xamarin.com")));

注意:可以使用 UIWebView 完成相同的基本逻辑,但是 WKWebView 快得多,以至于如果您不需要支持iOS 7客户端,我会个人专注于使用 WKWebView

Note: This same basic logic can be done with a UIWebView, but WKWebView is so much faster that if you do not need to support iOS 7 clients, I would personally focus on using WKWebView

这篇关于在Xamarin浏览器控件中访问html响应内容的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆