Как реализовать async. завершено событие для внешнего использования в.NET?

У меня есть этот простой проект для захвата внутренних данных HTML-элемента. Это DLL-проект.

public class WebGrabber
 {
 public string URL { set; get; }

 public string Element { set; get; }

 public bool FindByID { set; get; }

 private WebBrowser b { set; get; }

 private mshtml.IHTMLDocument2 doc { set; get; }

 public void GetPageElementInnerHTML(string url, string element, bool findById)
 {
 URL = url;
 Element = element;
 FindByID = findById;

 b = new WebBrowser();
 b.Navigate(url);
 b.DocumentCompleted += new WebBrowserDocumentCompletedEventHandler(b_DocumentCompleted);
 }

 void b_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
 {
 doc = (IHTMLDocument2)b.Document.DomDocument;

 string result = "";

 IHTMLElement head = (IHTMLElement)((IHTMLElementCollection)doc.all.tags("head")).item(null, 0);

 result += "" + head.innerHTML + "";

 if (null != doc)
 {
 foreach (IHTMLElement element in doc.all)
 {
 if (element is mshtml.IHTMLDivElement)
 {
 dynamic div = element as HTMLDivElement; 

 if (FindByID)
 {
 string id = div.id;

 if (id == Element)
 {
 result += "" + div.IHTMLElement_innerHTML + "";

 break;
 }
 }
 else
 {
 string className = div.className;

 if (className == Element)
 {
 result += "" + div.IHTMLElement_innerHTML + "";

 break;
 }
 }
 }
 }
 }
 doc.close(); 
 }
 }

Мне нужно реализовать доступ к переменной результата строки.

Таким образом, можно было бы получить асинхронно эту переменную из другого проекта.

Возможно, мне нужен GetResult(); метод?....

Как я могу это сделать?

Спасибо!

2 ответа

Вы можете передать обработчик событий в качестве аргумента, а затем работать с результатом в приложении no в библиотеке классов. O просто передать обратный вызов и вызвать после завершения загрузки.

Я здесь новый, поэтому надеюсь, что понял, чего вы хотели.

Передача evnthandler

public void GetPageElementInnerHTML (строковый url, строковый элемент, bool findById, WebBrowserDocumentCompletedEventHandler downloadComplete)

Использование делегата:

открытый класс WebGrabber {

public string URL { set; get; }

 public string Element { set; get; }

 public bool FindByID { set; get; }

 private WebBrowser b { set; get; }

 private mshtml.IHTMLDocument2 doc { set; get; }

 public delegate void DownloadCompletedDelegate(string result);

 private DownloadCompletedDelegate _downloadedComplete;

 public void GetPageElementInnerHTML(string url, string element, bool findById, DownloadCompletedDelegate downloadComplete)
 {
 _downloadedComplete = downloadComplete;
 URL = url;
 Element = element;
 FindByID = findById;

 b = new WebBrowser();
 b.Navigate(url);
 b.DocumentCompleted += new WebBrowserDocumentCompletedEventHandler(b_DocumentCompleted);
 }

 void b_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
 {
 doc = (IHTMLDocument2)b.Document.DomDocument;

 string result = "";

 IHTMLElement head = (IHTMLElement)((IHTMLElementCollection)doc.all.tags("head")).item(null, 0);

 result += "" + head.innerHTML + "";

 if (null != doc)
 {
 foreach (IHTMLElement element in doc.all)
 {
 if (element is mshtml.IHTMLDivElement)
 {
 dynamic div = element as HTMLDivElement;

 if (FindByID)
 {
 string id = div.id;

 if (id == Element)
 {
 result += "" + div.IHTMLElement_innerHTML + "";

 break;
 }
 }
 else
 {
 string className = div.className;

 if (className == Element)
 {
 result += "" + div.IHTMLElement_innerHTML + "";

 break;
 }
 }
 }
 }
 }
 doc.close();

 _downloadedComplete.Invoke(result);
 }
 }

В APP

GetPageElementInnerHTML (URL, элемент, true/false, CompletedCallback);

private void CompletedCallback (результат строки) {//ваш код

}


Вот рабочий код:

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using mshtml;
using System.Collections;

namespace MyCompany.WebpageGrabber
{
 // A delegate type for hooking up change notifications.
 public delegate void ChangedEventHandler(object sender, EventArgs e);

 public class WebGrabber : ArrayList
 {
 // An event that clients can use to be notified whenever the
 // elements of the list change.
 public event ChangedEventHandler Changed;

 // Invoke the Changed event; called whenever list changes
 protected virtual void OnChanged(EventArgs e)
 {
 if (Changed != null)
 Changed(this, e);
 }

 // Override some of the methods that can change the list;
 // invoke event after each
 public override int Add(object value)
 {
 int i = base.Add(value);
 OnChanged(EventArgs.Empty);
 return i;
 }

 public override void Clear()
 {
 base.Clear();
 OnChanged(EventArgs.Empty);
 }

 public override object this[int index]
 {
 set
 {
 base[index] = value;
 OnChanged(EventArgs.Empty);
 }
 }

 public string URL { set; get; }

 public string Element { set; get; }

 public bool FindByID { set; get; }

 private WebBrowser b { set; get; }

 private mshtml.IHTMLDocument2 doc { set; get; }

 public void GetPageElementInnerHTML(string url, string element, bool findById)
 {
 URL = url;
 Element = element;
 FindByID = findById;

 b = new WebBrowser();
 b.Navigate(url);
 b.DocumentCompleted += new WebBrowserDocumentCompletedEventHandler(b_DocumentCompleted);
 }

 void b_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
 {
 doc = (IHTMLDocument2)b.Document.DomDocument;

 string result = "";

 IHTMLElement head = (IHTMLElement)((IHTMLElementCollection)doc.all.tags("head")).item(null, 0);

 result += "" + head.innerHTML + "";

 if (null != doc)
 {
 foreach (IHTMLElement element in doc.all)
 {
 if (element is mshtml.IHTMLDivElement)
 {
 dynamic div = element as HTMLDivElement;

 if (FindByID)
 {
 string id = div.id;

 if (id == Element)
 {
 result += "" + div.IHTMLElement_innerHTML + "";

 break;
 }
 }
 else
 {
 string className = div.className;

 if (className == Element)
 {
 result += "" + div.IHTMLElement_innerHTML + "";

 break;
 }
 }
 }
 }
 }
 doc.close();

 this.Add(result);
 }
 }
}

и вот код, как мы его называем:

private void Window_Loaded(object sender, RoutedEventArgs e)
{
 WebGrabber g = new WebGrabber();

 g.GetPageElementInnerHTML("http://www.google.com/web/guest/home", "portlet-borderless-container", false);

 g.Changed += new ChangedEventHandler(g_Changed); 
}

void g_Changed(object sender, EventArgs e)
{
 var html = ((WebGrabber)sender)[0]; 
}

licensed under cc by-sa 3.0 with attribution.