我正在尝试在由JavaScript呈现的网站上获得一些内容。因此,我正在使用WebView
运行Visibility=Collapsed
。我要等待unitl NavigationCompleted
并运行一些JavaScript,然后返回该值。
代码如下:
private async void Foo()
{
// Want to get value here
var content = await GetContent();
}
private async Task<string> GetContent()
{
string content;
async void handler(WebView sender, WebViewNavigationCompletedEventArgs args)
{
content = await webView.InvokeScriptAsync("eval", new string[] { script });
webView.NavigationCompleted -= handler;
}
webView.NavigationCompleted += handler;
webView.Navigate(uri);
return content;
}
由于GetContent()
中没有等待,因此该函数总是在触发NavigationCompleted
之前返回。
答案 0 :(得分:1)
我认为您应该使用TaskCompletionSource。执行脚本后,创建一个源,并在事件处理程序的末尾设置其结果。返回内容之前,请等待任务完成源的任务。
答案 1 :(得分:1)
您可以使用SemaphoreSlim
异步等待NavigationCompleted
提出并处理:
private async Task<string> GetContent()
{
string content;
using (SemaphoreSlim semaphoreSlim = new SemaphoreSlim(0, 1))
{
async void handler(WebView sender, WebViewNavigationCompletedEventArgs args)
{
content = await webView.InvokeScriptAsync("eval", new string[] { script });
webView.NavigationCompleted -= handler;
semaphoreSlim.Release();
}
webView.NavigationCompleted += handler;
webView.Navigate(uri);
await semaphoreSlim.WaitAsync().ConfigureAwait(false);
}
return content;
}
答案 2 :(得分:0)
如果要等待,可以使用ManualResetEvent
。只需确保您不要在UI线程上使用ManualResetEvent.WaitOne
即可挂起应用程序。