因为同学新公司的变态要求,禁用IE右键菜单,开始我建议直接用JS实现,同学说不能修改页面源码,估计页面是其他公司的,只好用BHO实现。由于BHO会对所有页面生效,只好在BHO里判断指定页面生效(很变态^_^)。
言归正传,直接创建ATL工程TestBHO,添加类TestBHOCtrl,
class ATL_NO_VTABLE CTestBHOCtrl :
public CComObjectRootEx<CComSingleThreadModel>,
public CComCoClass<CTestBHOCtrl, &CLSID_TestBHOCtrl>,
public IObjectWithSiteImpl<CTestBHOCtrl>,
public IDispatchImpl<ITestBHOCtrl, &IID_ITestBHOCtrl, &LIBID_TestBHOLib, /*wMajor =*/ 1, /*wMinor =*/ 0>,
public IDocHostUIHandler,
public IDispEventImpl <1, CTestBHOCtrl, &DIID_DWebBrowserEvents2, &LIBID_SHDocVw, 1, 1>
说明:IObjectWithSiteImpl:ATL对IObjectWithSite的简单封装,一般需重写SetSite,IE在打开和关闭页面时都会调用此接口,
IDocHostUIHandler:编写本程序的主要目标,重写IDocHostUIHandler的ShowContextMenu方法,直接返回S_OK可屏蔽 菜单,也可以在里面弹出自定义菜单。
在COM_MAP中添加 COM_INTERFACE_ENTRY(IDocHostUIHandler)
IDispEventImpl :为了截获事件(DISPID_DOCUMENTCOMPLETE)。
//手工添加
BEGIN_SINK_MAP(CTestBHOCtrl)
SINK_ENTRY_EX(1, DIID_DWebBrowserEvents2, DISPID_DOCUMENTCOMPLETE, OnDocumentComplete)
END_SINK_MAP()
主要实现方法:
最后写完,碰到一个问题,就是BHO死活不能被IE加载,因为第一次写,Baidu了一阵,发现需要在rgs文件里添加注册表内容,注册BHO。
添加以下内容之后,重新生成,一切OK(注:D35AEDEE-555B-46A8-B186-D2AC99A032A4是需要改成自己的CLSID)。