1

2つの長時間実行されるタスクを実行して開始するプログラムがあります。タスクの1つは、レンダリングされたページを取得できるようにWebBrowser ActiveXコントロールを使用する必要があるWebスクレーパーです。私はメッセージループのアパートの状態を設定できるようにスレッドを開始する必要がありますコントロールを使用するために。私がこれを行うと、プログラムはうまく動作する、または少なくともフェッチされた最初のページについては動作します。後続のページ/呼び出し、Webブラウザがタイムアウトして状態が「初期化されていません」のまま残っているようです。私のコードをトレースすると、WebClientの "HandleDestroyed"という火災は見られません。タスク内のウェブブラウザースレッドを実行する

WebBrowserコントロールや自分のクラスを再度破棄して、再度再利用するには、何をする必要がありますか?

public static string AXFetch(string url, string ua) 
{ 
    TestBrowser TB = new TestBrowser(); 
    Thread th = new Thread(() => TB.MakeLiRequest(url,ua)); 
    th.SetApartmentState(ApartmentState.STA); 
    th.Start(); 
    th.Join(new TimeSpan(0, 0, 90)); //90 second timeout 
    SiteData = TB.DocumentText; 
    TB = null; 
    return SiteData; 
} 

class TestBrowser 
{ 
    public string DocumentText = ""; 
    private bool DocCompleted = false; 

    public TestBrowser() 
    { 

    } 

    private void reset_fetch_status() 
    { 
     this.DocCompleted = false; 
     this.DocumentText = ""; 
    } 


    public void MakeLiRequest(string url, string UA) 
    { 
     reset_fetch_status(); 
       using (WebBrowser wb = new WebBrowser()) 
     { 
      wb.Visible = false; 
      wb.AllowNavigation = true; 
      wb.ScriptErrorsSuppressed = true; 
      wb.DocumentCompleted += this.wb_DocumentCompleted; 
      wb.Navigate(url, "_self", null, "User-Agent: " + UA + "\r\n"); 
      WaitForPage(); 
      wb.Url = null; 
      wb.DocumentCompleted -= this.wb_DocumentCompleted; 
     } 
    } 

    private void HandleDestroyed(Object sender, EventArgs e) 
    { 
       //This never seems to fire, I don't knwo why 
     Logging.DoLog("You are in the Control.HandleDestroyed event."); 

    } 

    private bool WaitForPage() 
    { 
     int timer = 0; 
     while (this.DocCompleted == false) 
     { 
      Application.DoEvents(); 
      System.Threading.Thread.Sleep(100); 
      ++timer; 
      if (timer == (PageTimeOut * 10)) 
      { 
       Console.WriteLine("WebBrowser Timeout has been reached"); 
       Application.Exit(); 
       return false; 
      } 

     } 
     return true; 
    } 

    private void wb_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e) 
    { 
     WebBrowser wb = (WebBrowser)sender; 
     if (wb.ReadyState == WebBrowserReadyState.Complete) 
     { 
      this.DocumentText = wb.DocumentText; 
      this.DocCompleted = true; 
     } 
    } 

} 

答えて

0

ハンドルでは、親フォームによってのみ呼び出されます。

あなたはWebBrowserコントロールからアクセスしようとしていた場合は、このエラーになるだろう:

Error 1 Cannot access protected member 
'System.Windows.Forms.Control.OnHandleDestroyed(System.EventArgs)' via a 
qualifier of type 'System.Windows.Forms.WebBrowser'; the qualifier must be of type 'stackoverflowpost47036339.Form1' (or derived from it) 

はまた、あなたはそれをフックされていません。しかし、Webブラウザに親フォームを与えていないので、呼び出すことはできません。これを親フォームに接続する方法です。

 form1.HandleDestroyed += Form1_HandleDestroyed; 
    } 

    void Form1_HandleDestroyed(object sender, EventArgs e) 
    { 

    } 
関連する問題