UWP获取任意网页加载完成后的HTML
2024-09-06 12:57:06
主要思想:通过后台WebView载入指定网页,再提取出WebView中的内容
关键代码:
var html = await webView.InvokeScriptAsync("eval", new string[] { "document.documentElement.outerHTML;" });
有一个很简单的思路,
订阅WebView NavigationCompleted事件,然后让Navigate到指定的网址,发生事件时执行这行代码
除此之外,这里还有一个异步的方法,用到了TaskCompletionSource这个东西
首先,创建一个TaskCompletionSource:
TaskCompletionSource<string> completionSource = new TaskCompletionSource<string>();
因为返回的东西是string(html),所以泛型T设置成string
然后使用lambda的形式订阅Navigation事件:
webView.NavigationCompleted += async (sender, args) =>
{
if (args.Uri != uri)
return;
await Task.Delay();
var html = await sender.InvokeScriptAsync("eval", new string[] { "document.documentElement.outerHTML;" });
webView.NavigateToString("");
webView = null;
completionSource.SetResult(html);
};
Line5的延迟200ms,是为了Navigation完成之后再给页面里的其他一些元素(比如一些js脚本)一些加载的时间(讲道理订阅事件里也应该写一个的)
Line7的导航到空是为了防止WebView里的东西继续运行从而导致一些灵异事件(尤其是一些带视频的网页,咳咳)
Line9,给Task设置个Result,await就会结束
最后:
return completionSource.Task;
封装成类:
public class WebHelper
{
public class WebLoadedArgs:EventArgs
{
public bool Success { get; private set; }
public WebErrorStatus WebErrorStatus { get; private set; }
public string Html { get; private set; } public WebLoadedArgs(WebErrorStatus webErrorStatus)
{
WebErrorStatus = webErrorStatus;
Success = false;
} public WebLoadedArgs(string Html,WebErrorStatus webErrorStatus)
{
this.Html = Html;
WebErrorStatus = webErrorStatus;
Success = true;
}
} public string Url { get; private set; }
public event EventHandler<WebLoadedArgs> WebLoaded;
private WebView webView; public WebHelper(string Url)
{
this.Url = Url;
webView = new WebView(WebViewExecutionMode.SeparateThread);
webView.Navigate(new Uri(Url));
webView.NavigationCompleted += WebView_NavigationCompleted;
webView.NavigationFailed += WebView_NavigationFailed;
} private void WebView_NavigationFailed(object sender, WebViewNavigationFailedEventArgs e)
{
WebLoaded(this, new WebLoadedArgs(e.WebErrorStatus));
} private async void WebView_NavigationCompleted(WebView sender, WebViewNavigationCompletedEventArgs args)
{ var html = await sender.InvokeScriptAsync("eval", new string[] { "document.documentElement.outerHTML;" });
webView = null;
WebLoaded(this, new WebLoadedArgs(html,args.WebErrorStatus));
} /// <summary>
/// 异步实现获取Web内容
/// </summary>
/// <param name="Url">网址</param>
/// <param name="TimeOut">超时时间</param>
/// <returns>Web的Html内容</returns>
public static Task<string> LoadWebAsync(string Url,int Timeout)
{
return LoadWebAsync(Url, "", Timeout);
} /// <summary>
/// 异步实现获取Web内容
/// </summary>
/// <param name="Url">网址</param>
/// <param name="Referer">Header[Referer],用以解决一些盗链效验</param>
/// <param name="TimeOut">超时时间</param>
/// <returns>Web的Html内容</returns>
public static Task<string> LoadWebAsync(string Url,string Referer, int TimeOut)
{ WebView webView = new WebView(WebViewExecutionMode.SeparateThread);
Uri uri = new Uri(Url);
HttpRequestMessage requestMessage = new HttpRequestMessage(HttpMethod.Get, uri);
requestMessage.Headers.Add("Referer", Referer);
webView.NavigateWithHttpRequestMessage(requestMessage); TaskCompletionSource<string> completionSource = new TaskCompletionSource<string>();
webView.NavigationCompleted += async (sender, args) =>
{
if (args.Uri != uri)
return;
await Task.Delay();
var html = await sender.InvokeScriptAsync("eval", new string[] { "document.documentElement.outerHTML;" });
webView.NavigateToString("");
webView = null;
completionSource.SetResult(html);
};
webView.NavigationFailed += (sender, args) =>
{
webView = null;
completionSource.SetException(new WebException("", (WebExceptionStatus)args.WebErrorStatus));
};
DispatcherTimer timer = new DispatcherTimer();
timer.Interval = TimeSpan.FromSeconds(TimeOut);
timer.Tick += (sender, args) =>
{
timer = null;
webView.NavigateToString("");
webView = null;
completionSource.SetException(new TimeoutException());
};
timer.Start(); return completionSource.Task;
}
}
使用方法:
(事件订阅的方式)
WebHelper webHelper = new WebHelper("http://www.baidu.com/");
webHelper.WebLoaded += WebHelper_WebLoaded; private void WebHelper_WebLoaded(object sender, WebHelper.WebLoadedArgs e)
{
if(e.Success)
{
var html = e.Html;
}
}
(异步的方式)
var html = await WebHelper.LoadWebAsync("http://www.baidu.com", );
最新文章
- 重装系统后如何删除系统自带的office2003
- zabbix-agent配置文件说明
- Linux Memcache 安装配置
- C#中的yield return与Unity中的Coroutine(协程)(上)
- 使用JavaScript创建我的分页
- js获取div中的文本框数据
- 【C#】线程池
- Android问题-新电脑新系统WIN764位上安装简版本的XE8提示“Unit not found: &#39;System&#39;”
- 【C#学习笔记】二、面向对象编程
- mysql新手入门随笔
- 搭建MHA测试
- 【Django视图与网址进阶004】
- ELK之elasticsearch导致CPU居高不下系统慢解决办法
- mysql 常用语句集
- JavaScript Constructor &; prototype
- Java直接内存与非直接内存性能测试
- Bing词典vs有道词典比对测试报告——体验篇之软件适应性
- 网站中超链接方式直接添加QQ好友
- coding github 配置ssl 免密拉取代码
- 【BZOJ4052】[Cerc2013]Magical GCD 乱搞