Pergunta

Estou criando um Browser Helper Object usando VS2008, C ++. Minha classe tem sido derivada de IDispEventImpl entre muitos outros

class ATL_NO_VTABLE CHelloWorldBHO :
    public CComObjectRootEx<CComSingleThreadModel>,
    public CComCoClass<CHelloWorldBHO, &CLSID_HelloWorldBHO>,
    public IObjectWithSiteImpl<CHelloWorldBHO>,
    public IDispatchImpl<IHelloWorldBHO, &IID_IHelloWorldBHO, &LIBID_HelloWorldLib, /*wMajor =*/ 1, /*wMinor =*/ 0>,
    public IDispEventImpl<1, CHelloWorldBHO, &DIID_DWebBrowserEvents2, &LIBID_SHDocVw, 1, 1>

{
.
.
.
BEGIN_SINK_MAP(CHelloWorldBHO)
     SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_DOCUMENTCOMPLETE, OnDocumentComplete)
     SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_BEFORENAVIGATE2, BeforeNavigate2)//Handle BeforeNavigate2
END_SINK_MAP()
.
.
.
}

Como resulta do código acima, meus DWebBrowserEvents2 são manipulados usando macros do ATL. Agora eu quero lidar com HTMLElementEvents2 (para detectar cliques, barras de rolagem, etc.) para que, eu QueryInterface () o objeto IHTMLDocument2 para IHTMLElement, QueryInterface () que, para IConnectionPointContainer e IConnectionPointContainer chamada :: FindConnectionPoint (DIID_HTMLElementEvents2). (Veja do MSDN artigo sobre manipulação HTMLElementEvents2). O problema é, quando eu substituir IDispatch :: Invoke na minha classe, as alças DWebBrowserEvents2 (criadas usando macros ATL) falhar. Existe uma maneira de lidar com HTMLElementEvents2 sem substituir Invoke, ou implementar invocação de tal maneira que ele lida única HTMLElementEvents2
Obrigado, Qualquer ajuda será apreciada.

Foi útil?

Solução

Não há nenhuma necessidade real para substituir Invoke ou obter IConnectionPointContainer. Uma vez que este é um projeto ATL, Implementando outra IDispEventImpl:

public IDispEventImpl<2, CHelloWorldBHO, &DIID_HTMLTextContainerEvents2, &LIBID_MSHTML, 4, 0>

faz o truque. Em seguida, afundar a entrada como:

SINK_ENTRY_EX(2, DIID_HTMLTextContainerEvents2, DISPID_ONSCROLL, OnScroll)

Em OnDocumentComplete, chamar IWebBrowser2 :: get_Document, IHTMLDocument2 :: Get_Body, e depois chamar DispEventAdvise para começar a receber eventos.

Note que eu usei DIID_HTMLTextContainerEvents2 vez de DIID_HTMLElementEvents. Isso porque o objeto corpo não suportam HTMLElementEvents2, e para o meu propósito (a alça de rolagem) isso funciona muito bem!

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top