【问题标题】:Asynchronous methods and a event异步方法和事件
【发布时间】:2015-09-29 14:58:32
【问题描述】:

我使用 awesomium 来自动化网站。我尝试使用异步编程,因为我不希望我的 GUI 冻结,但是当应用程序没有时,我在一个事件中遇到问题(出现一个弹出窗口,我想在此弹出窗口中进行一些操作,直到我关闭它)不要继续我想要的。触发事件后,我希望我的应用程序继续使用事件方法(webc_ShowCreatedWebView,然后使用 popupTwitter(method),但我发现在执行 JavaScript 代码时,控件从第一个方法返回 While。我怎么能这样做在调用 Earnpoints 方法并触发事件以完成事件和方法之后,然后控件在 while 中返回。

  private async void button4_Click(object sender, EventArgs e)
    {
        Twitter twitter = new Twitter(webView);
        twitter.Login(webView);
        webView.ShowCreatedWebView += webc_ShowCreatedWebView;
        addmefast.Login(webView);
        int i = 0;
        while (i < 10)
        {
            Task earnpoints = EarnPoints(webView);
            await earnpoints;
            //Here i don't want to continue until EarnPoints method > webc_ShowCreatedWebView event > popupTwitter method it's finished.
            i++;
        }
    }

    public async Task EarnPoints(IWebView web)
    {
        web.Source = "http://addmefast.com/free_points/twitter".ToUri();
        await Task.Delay(3000);
        web.ExecuteJavascript("document.getElementsByClassName('single_like_button btn3-wrap')[0].click();"); //event fired: webc_ShowCreatedWebView
    }

    async void webc_ShowCreatedWebView(object sender, ShowCreatedWebViewEventArgs e)
    {
        WebView view = new WebView(e.NewViewInstance);
        await popupTwitter(view);
    }

   async Task popupTwitter(WebView view)
    {
        Popupform FormTwitter = new Popupform(view);
        FormTwitter.Show();
       await  Task.Delay(6000);
        FormTwitter.Twitter();
        await Task.Delay(2000);
        FormTwitter.Close();
        await  Task.Delay(4000);
    }

【问题讨论】:

  • 听起来 awesomium 不理解异步事件。如果是这样的话,除了要求他们支持异步之外,你真的无能为力。
  • 在我看来 webc_ShowCreatedWebView 只有在 EarnPoints 已经返回后才会被触发。也许你可以使用 EventWaitHandle 并且只在 popupTwitter 方法中设置它。 while 循环将阻塞,直到设置了 EventWaitHandle。 MSDN 文档:link

标签: c# events asynchronous awesomium


【解决方案1】:

我在使用 awesomium 实现异步方法时也遇到了问题,但它可以正常工作。

首先我做了这个包装。必须在主线程上创建。

public class AsyncWebView
{

    public static SynchronizationContext _synchronizationContext;
    private readonly WebView _webView;

    public AsyncWebView()
    {
        _synchronizationContext = SynchronizationContext.Current;

        _webView = WebCore.CreateWebView(1024, 900);
    }

    public async Task Navigate(String url)
    {
        Debug.WriteLine("Navigating");
        TaskCompletionSource<bool> tcs = new TaskCompletionSource<bool>();

        FrameEventHandler handler = (sender, args) =>
        {
            Debug.WriteLine(args.Url);

            if (!_webView.IsNavigating && !_webView.IsLoading)
                tcs.SetResult(true);
        };

        _webView.LoadingFrameComplete += handler;

        _synchronizationContext.Send(SetWebViewSource, url);

        await tcs.Task;

        _webView.LoadingFrameComplete -= handler;

        Debug.WriteLine("Done");

    }

    private void SetWebViewSource(object url)
    {
        _webView.Source = new Uri((string)url);
    }
}

用法:

async Task test()
{
    await webView.Navigate("http://www.nytimes.com");
    Debug.WriteLine("All done");
}

只要确保你有一个 SynchronizationContext 来调用 AsyncWebView 构造函数。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-06-11
    • 2012-11-23
    • 1970-01-01
    • 2019-08-26
    • 1970-01-01
    • 2010-11-27
    • 2013-06-12
    • 2013-01-27
    相关资源
    最近更新 更多