WebBrowser的OnPropertyChange事件没有触发

本文关键字:事件 OnPropertyChange WebBrowser | 更新日期: 2023-09-27 17:49:17

我有一个网页,上面有一个输入按钮。单击此按钮,在特定的div中加载一些数据。我的问题是我无法捕捉到这些数据。

下面的代码是我试图解决这个问题,但没有成功。

private void webBrowser1_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
{
    HtmlElement div_result = webBrowser1.Document.GetElementById("div_result");
    div_result.AttachEventHandler("onpropertychange", new EventHandler(resultEventHandler));
}
private void resultEventHandler(object sender, EventArgs e)
{
    MessageBox.Show("Loaded");
}

如果我点击输入按钮,div的内容被修改,但是resultEventHandler没有触发。

我有两个问题:

  1. 在这个代码中我的错误在哪里?
  2. 有一个"正常的方式"(我的意思是不使用定时器或Aplication.DoEvents())与ajax使用WebBrowser控制在c#工作?

WebBrowser的OnPropertyChange事件没有触发

改变子元素的innerText或innerHTML不会触发父元素的onpropertychange事件

我不知道为什么HtmlElement事件不适合你。但是我有同样的问题,并通过使用COM包装器解决了它:

mshtml.HTMLDocumentClass doc = (mshtml.HTMLDocumentClass)webBrowser1.Document.DomDocument;
mshtml.IHTMLElement2 div_result = (mshtml.IHTMLElement2)doc.getElementById("div_result");
mshtml.HTMLElementEvents2_Event events = (mshtml.HTMLElementEvents2_Event)div_result;
events.onpropertychange += resultEventHandler;

这可能太迟了,但如果你仍然想知道,这里是无论如何:

1 - HtmlElementdiv_result = webBrowser1.Document.GetElementById("div_result");第1行在网页加载完成并且浏览器调用DocumentCompleted事件时执行。在事件处理程序中,你首先获取一个指向DOM元素"div_result"的指针,然后你分配一个名为div_result的HtmlElement类型变量。

2 -div_result。AttachEventHandler("onpropertychange", new eventandler (resultEventHandler));第2行-注册"onpropertychange"事件,并分配方法resultEventHandler作为侦听器方法。

每次你点击你的网页上的按钮,按钮(我假设)是在一个表单被提交,导致网页加载;顺便说一下,您没有指定单击按钮时使用的发布方法(get或post)。当网页下载完成并且DOM元素树构造完成时,调用DocumentCompleted事件。你的DocumentCompleted事件处理程序方法执行了上面描述的指令。

每次你点击你的按钮,你的网页被重新加载,你为onpropertychange事件重新分配事件监听器。您只是在分配事件侦听器。事件永远不会被调用。它将在每次单击按钮时被定义。这是一个经典的先有鸡还是先有蛋的问题。但在你的情况下,你的鸡是按钮点击事件,导致DocumentCompleted方法运行,重置方法中所有变量的状态,而你的鸡蛋是想要一个指针到DIV元素的onpropertychange事件之前,按钮被点击在网页上。你如何分配一个事件监听器到一个htmlelement之前,你可以得到一个指针从DOM尚未构建?在包含DocumentCompleted方法的类中放置一个布尔标志变量,并设置其初始状态。将div_result变量移到DocumentCompleted方法之外,以增加其作用域,并在按钮单击事件中保存其状态。这样,你将得到一个指向div元素的指针,并在网页第一次下载时设置它的onpropertychange事件监听器。如果您只想设置一个指向DIV元素的onpropertychange事件监听器的指针(我在下面的示例代码中放置了一个),则添加一个测试,并且下次单击按钮时,事件将触发。注意!确保在存储了指向任何网页元素或其事件的指针后,不会在网页中添加或删除任何元素。否则,您将不得不重新解析DOM以获得指向元素在DOM树中的新位置的指针。

//如下所示:

class SomeClass
{
    bool DocumentHasLoaded = false;
    HtmlElement div_result = null;
    //Constructor and other methods go here....
    //Then change your DocumentCompleted method to look like this:
    private void webBrowser1_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
    {
        if (DocumentHasLoaded == false)  // I prefer using a ! before the variable instead
        {
            DocumentHasLoaded = true;    // You will have to create your own appropriately timed mechanism to reset this variable's state should you want to execute the whole process again.
            div_result = webBrowser1.Document.GetElementById("div_result");
            div_result.AttachEventHandler("onpropertychange", new EventHandler(resultEventHandler));
        }
    }
}

为了回答你的第二个问题,我需要更多关于在DIV中加载的数据的信息;例如,它来自哪里,是什么类型,以及你能想到的任何其他相关信息