【问题标题】:Invoke BHO from IE toolbar button从 IE 工具栏按钮调用 BHO
【发布时间】:2016-12-22 22:54:11
【问题描述】:

我正在编写 IE BHO,当单击 IE 工具栏按钮时必须调用它。 我有功能 BHO,它是 dll 函数 DllMain DllGetClassObject 等。还有实现 IObjectWithSiteIOleCommandTarget 的 COM 类和实现 IClassFactory 的类工厂。我知道它可以工作,因为我连接了EventSinc,它调用了 OnDocumentComplete 和其他事件。

我在DllRegisterServer 函数中有注册码,并且regsvr32.exe 已成功安装。

现在我想添加 IE 工具栏按钮,它会在点击时调用 BHO 功能,所以我找到了这篇文章 Adding Toolbar Buttons 并根据它在我的 DllRegisterServer 中添加了按钮注册。还将IOleCommandTarget 添加到上述com 对象和“实现” Exec 方法,其中包含写入文件的代码(以检查是否调用了Exec)。重新编译卸载并再次安装后,在按钮上单击DllGetClassObject 调用第一次单击,所有连续单击都没有任何反应。

那么有什么问题呢?

来自DllRegisterServer的工具栏按钮注册部分

if(RegCreateKeyEx(HKEY_LOCAL_MACHINE, _T("SOFTWARE\\Microsoft\\Internet Explorer\\Extensions\\") CLSID_IEPlugin_Str, 0, NULL, 0, KEY_ALL_ACCESS, NULL, &hk, NULL) != ERROR_SUCCESS) return SELFREG_E_CLASS;
RegSetValueEx(hk, _T("ButtonText"), 0, REG_SZ, (const BYTE*)_T("BHO Toolbar Button"), sizeof("BHO Toolbar Button") * sizeof(TCHAR));
RegSetValueEx(hk, _T("Default Visible"), 0, REG_SZ, (const BYTE*)_T("Yes"), sizeof("Yes") * sizeof(TCHAR));
RegSetValueEx(hk, _T("CLSID"), 0, REG_SZ, (const BYTE*)_T("{1FBA04EE-3024-11d2-8F1F-0000F87ABD16}"), sizeof("{1FBA04EE-3024-11d2-8F1F-0000F87ABD16}") * sizeof(TCHAR));
RegSetValueEx(hk, _T("ClsidExtension"), 0, REG_SZ, (const BYTE*)_T("{29DE271C-7936-4C23-BD79-18F6AB7A4AA4}"), sizeof("{29DE271C-7936-4C23-BD79-18F6AB7A4AA4}") * sizeof(TCHAR));
RegCloseKey(hk);

COM 类CObjectWithSite 标头:

#ifndef __OBJECTWITHSITE_H__
#define __OBJECTWITHSITE_H__

#include <Ocidl.h>
#include <Exdisp.h>

class CObjectWithSite : public IObjectWithSite, public IOleCommandTarget
{
public:

    // Constructor and destructor
    CObjectWithSite();
    virtual ~CObjectWithSite();

    // IUnknown methods
    STDMETHODIMP QueryInterface(REFIID riid,void** ppvObject);
    STDMETHODIMP_(ULONG) AddRef();
    STDMETHODIMP_(ULONG) Release();

    // IObjectWithSite methods
    STDMETHODIMP SetSite(IUnknown* pUnkSite);
    STDMETHODIMP GetSite(REFIID riid,void** ppvSite);

    // IOleCommandTarget methods
    STDMETHODIMP QueryStatus(const GUID* pguidCmdGroup, ULONG cCmds, OLECMD prgCmds[], OLECMDTEXT* pCmdText);
    STDMETHODIMP Exec(const GUID* pguidCmdGroup, DWORD nCmdID, DWORD nCmdexecopt, VARIANT* pvaIn, VARIANT* pvaOut);

protected:
    UINT m_uRefCount;
    IWebBrowser2* m_pSite   = nullptr;  // the currently set site
    IConnectionPoint* m_pCP = nullptr;  // the active connection point interface
    DWORD m_adviseCookie;               // used by ConnectEventSink() and DisconnectEventSink() in conjunction with pCP
};

#endif // __OBJECTWITHSITE_H__

【问题讨论】:

    标签: c++ internet-explorer com bho


    【解决方案1】:

    因此,单击按钮时,即从创建选项卡时调用 DllGetClassObject 的同一线程调用 DllGetClassObject。它创建 bho 的新实例并调用 IOleCommandTarget::Exec。如果在 DllGetClassObject 中尝试查询接口旧的 ClassFactory 对象(也重用之前创建的对象),则会发生崩溃。因此,似乎必须在按钮单击时创建 bho 的新实例。

    【讨论】:

      猜你喜欢
      • 2013-07-09
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-07-15
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多