一、OCX控件开发常见的问题

1、OCX控件在IE8浏览器下不能使用问题

原因:IE8会拦截OCX控件的方法。

解决方法:在OCX控件开发时加入安全接口。

(1)在有”Crtl“字样的头文件”.h“中加入如下代码:

  1. #include <objsafe.h>
        #include <objsafe.h> 

并在头文件类的内部加入如下安全接口,代码如下:

  1. //ISafeObject
  2. DECLARE_INTERFACE_MAP()
  3. BEGIN_INTERFACE_PART(ObjSafe, IObjectSafety)
  4. STDMETHOD_(HRESULT, GetInterfaceSafetyOptions) (
  5. /* [in] */ REFIID riid,
  6. /* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,
  7. /* [out] */ DWORD __RPC_FAR *pdwEnabledOptions
  8. );
  9. STDMETHOD_(HRESULT, SetInterfaceSafetyOptions) (
  10. /* [in] */ REFIID riid,
  11. /* [in] */ DWORD dwOptionSetMask,
  12. /* [in] */ DWORD dwEnabledOptions
  13. );
  14. END_INTERFACE_PART(ObjSafe);
  15. //ISafeObject
//ISafeObject
DECLARE_INTERFACE_MAP()
BEGIN_INTERFACE_PART(ObjSafe, IObjectSafety)
STDMETHOD_(HRESULT, GetInterfaceSafetyOptions) (
/* [in] */ REFIID riid,
/* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,
/* [out] */ DWORD __RPC_FAR *pdwEnabledOptions
);
STDMETHOD_(HRESULT, SetInterfaceSafetyOptions) (
/* [in] */ REFIID riid,
/* [in] */ DWORD dwOptionSetMask,
/* [in] */ DWORD dwEnabledOptions
);
END_INTERFACE_PART(ObjSafe);
//ISafeObject

(2)在有”Ctrl“字样的CPP文件中添加如下代码:注下面类名这里都以”CxxxCtrl“为本例的类名,加入到你代码中请注意替换。

  1. BEGIN_INTERFACE_MAP( CxxxCtrl, COleControl )
  2. INTERFACE_PART(CxxxCtrl, IID_IObjectSafety, ObjSafe)
  3. END_INTERFACE_MAP()
  4. /////////////////////////////////////////////////////////////////////////////
  5. // Dispatch map
  6. // IObjectSafety member functions
  7. ULONG FAR EXPORT CxxxCtrl::XObjSafe::AddRef()
  8. {
  9. METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
  10. return pThis->ExternalAddRef();
  11. }
  12. ULONG FAR EXPORT CxxxCtrl::XObjSafe::Release()
  13. {
  14. METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
  15. return pThis->ExternalRelease();
  16. }
  17. HRESULT FAR EXPORT CxxxCtrl::XObjSafe::QueryInterface(REFIID iid, void FAR* FAR* ppvObj)
  18. {
  19. METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
  20. return (HRESULT)pThis->ExternalQueryInterface(&iid, ppvObj);
  21. }
  22. const DWORD dwSupportedBits = INTERFACESAFE_FOR_UNTRUSTED_CALLER | INTERFACESAFE_FOR_UNTRUSTED_DATA;
  23. const DWORD dwNotSupportedBits = ~ dwSupportedBits;
  24. //.............................................................................
  25. // CxxxCtrl::XObjSafe::GetInterfaceSafetyOptions
  26. // Allows container to query what interfaces are safe for what. We're
  27. // optimizing significantly by ignoring which interface the caller is
  28. HRESULT STDMETHODCALLTYPE CxxxCtrl::XObjSafe::GetInterfaceSafetyOptions(
  29. /* [in] */ REFIID riid,
  30. /* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,
  31. /* [out] */ DWORD __RPC_FAR *pdwEnabledOptions)
  32. {
  33. METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
  34. HRESULT retval = ResultFromScode(S_OK);
  35. // does interface exist?
  36. IUnknown FAR* punkInterface;
  37. retval = pThis->ExternalQueryInterface(&riid, (void * *)&punkInterface);
  38. if (retval != E_NOINTERFACE) { // interface exists
  39. punkInterface->Release(); // release it--just checking!
  40. }
  41. // we support both kinds of safety and have always both set,
  42. // regardless of interface
  43. *pdwSupportedOptions = *pdwEnabledOptions = dwSupportedBits;
  44. return retval; // E_NOINTERFACE if QI failed
  45. }
  46. /////////////////////////////////////////////////////////////////////////////
  47. // CxxxCtrl::XObjSafe::SetInterfaceSafetyOptions
  48. // Since we're always safe, this is a no-brainer--but we do check to make
  49. // sure the interface requested exists and that the options we're asked to
  50. // set exist and are set on (we don't support unsafe mode).
  51. HRESULT STDMETHODCALLTYPE CxxxCtrl::XObjSafe::SetInterfaceSafetyOptions(
  52. /* [in] */ REFIID riid,
  53. /* [in] */ DWORD dwOptionSetMask,
  54. /* [in] */ DWORD dwEnabledOptions)
  55. {
  56. METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
  57. // does interface exist?
  58. IUnknown FAR* punkInterface;
  59. pThis->ExternalQueryInterface(&riid, (void * *)&punkInterface);
  60. if (punkInterface) { // interface exists
  61. punkInterface->Release(); // release it--just checking!
  62. }else
  63. {
  64. // interface doesn't exist
  65. return ResultFromScode(E_NOINTERFACE);
  66. }
  67. // can't set bits we don't support
  68. if (dwOptionSetMask & dwNotSupportedBits) {
  69. return ResultFromScode(E_FAIL);
  70. }
  71. // can't set bits we do support to zero
  72. dwEnabledOptions &= dwSupportedBits;
  73. // (we already know there are no extra bits in mask )
  74. if ((dwOptionSetMask & dwEnabledOptions) != dwOptionSetMask) {
  75. return ResultFromScode(E_FAIL);
  76. }
  77. // don't need to change anything since we're always safe
  78. return ResultFromScode(S_OK);
  79. }
BEGIN_INTERFACE_MAP( CxxxCtrl, COleControl )
INTERFACE_PART(CxxxCtrl, IID_IObjectSafety, ObjSafe)
END_INTERFACE_MAP() /////////////////////////////////////////////////////////////////////////////
// Dispatch map
// IObjectSafety member functions
ULONG FAR EXPORT CxxxCtrl::XObjSafe::AddRef()
{
METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
return pThis->ExternalAddRef();
}
ULONG FAR EXPORT CxxxCtrl::XObjSafe::Release()
{
METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
return pThis->ExternalRelease();
}
HRESULT FAR EXPORT CxxxCtrl::XObjSafe::QueryInterface(REFIID iid, void FAR* FAR* ppvObj)
{
METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
return (HRESULT)pThis->ExternalQueryInterface(&iid, ppvObj);
}
const DWORD dwSupportedBits = INTERFACESAFE_FOR_UNTRUSTED_CALLER | INTERFACESAFE_FOR_UNTRUSTED_DATA;
const DWORD dwNotSupportedBits = ~ dwSupportedBits;
//.............................................................................
// CxxxCtrl::XObjSafe::GetInterfaceSafetyOptions
// Allows container to query what interfaces are safe for what. We're
// optimizing significantly by ignoring which interface the caller is
HRESULT STDMETHODCALLTYPE CxxxCtrl::XObjSafe::GetInterfaceSafetyOptions(
/* [in] */ REFIID riid,
/* [out] */ DWORD __RPC_FAR *pdwSupportedOptions,
/* [out] */ DWORD __RPC_FAR *pdwEnabledOptions)
{
METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
HRESULT retval = ResultFromScode(S_OK);
// does interface exist?
IUnknown FAR* punkInterface;
retval = pThis->ExternalQueryInterface(&riid, (void * *)&punkInterface);
if (retval != E_NOINTERFACE) { // interface exists
punkInterface->Release(); // release it--just checking!
}
// we support both kinds of safety and have always both set,
// regardless of interface
*pdwSupportedOptions = *pdwEnabledOptions = dwSupportedBits;
return retval; // E_NOINTERFACE if QI failed
}
/////////////////////////////////////////////////////////////////////////////
// CxxxCtrl::XObjSafe::SetInterfaceSafetyOptions
// Since we're always safe, this is a no-brainer--but we do check to make
// sure the interface requested exists and that the options we're asked to
// set exist and are set on (we don't support unsafe mode).
HRESULT STDMETHODCALLTYPE CxxxCtrl::XObjSafe::SetInterfaceSafetyOptions(
/* [in] */ REFIID riid,
/* [in] */ DWORD dwOptionSetMask,
/* [in] */ DWORD dwEnabledOptions)
{
METHOD_PROLOGUE(CxxxCtrl, ObjSafe)
// does interface exist?
IUnknown FAR* punkInterface;
pThis->ExternalQueryInterface(&riid, (void * *)&punkInterface);
if (punkInterface) { // interface exists
punkInterface->Release(); // release it--just checking!
}else
{
// interface doesn't exist
return ResultFromScode(E_NOINTERFACE);
}
// can't set bits we don't support
if (dwOptionSetMask & dwNotSupportedBits) {
return ResultFromScode(E_FAIL);
}
// can't set bits we do support to zero
dwEnabledOptions &= dwSupportedBits;
// (we already know there are no extra bits in mask )
if ((dwOptionSetMask & dwEnabledOptions) != dwOptionSetMask) {
return ResultFromScode(E_FAIL);
}
// don't need to change anything since we're always safe
return ResultFromScode(S_OK);
}

如果加安全代码后,还是不能正常加载,那你要确认一下,你的操作系统是64位系统吗?若是,再看一下你IE是不是也使用64位的。若是的话,那就没有办法了,我在前面的博文中已经说明了,64位的IE是不支持32位OCX控件,请使用更高的IE版本调试或者。。。建议使用IE10及以上,IE9也同样存在这样的问题。如果不是,那你再看一下找一下其他原因,或者在评论中阐述你的问题出现的现象,博友们一起帮你研究与解决。

2、OCX控件引入对话框界面后,OCX控件无法响应键盘”backspack“键。

原因:IE浏览器截获该事件,出现一按”backpack“键,网页就回退,无法正常在OCX控件上操作。

解决方法:有两种,一使用MFC中的钩子方法(不推荐,本文不详细解说),另一种是OCX控件中添加处理事件的函数来处理,具体说明请查看官网  http://support.microsoft.com/kb/168777/nl

(1)在”Ctrl“的字样的头文件上加入如下三个函数声明及一个鼠标事件。

  1. virtual BOOL OnWndMsg(UINT message, WPARAM wParam, LPARAM lParam, LRESULT* pResult);
  2. HRESULT OnActivateInPlace(BOOL bUIActivate, LPMSG pMsg);
  3. BOOL PreTranslateMessage(MSG* pMsg);
	virtual BOOL OnWndMsg(UINT message, WPARAM wParam, LPARAM lParam, LRESULT* pResult);
HRESULT OnActivateInPlace(BOOL bUIActivate, LPMSG pMsg);
BOOL PreTranslateMessage(MSG* pMsg);

一个鼠标事件 afx_msg int OnMouseActivate(CWnd* pDesktopWnd, UINT nHitTest, UINT message);

(2)在”Ctrl“字样的CPP文件中加入如下代码:

  1. BOOL CxxxCtrl::OnWndMsg(UINT message, WPARAM wParam, LPARAM lParam, LRESULT *pResult)
  2. {
  3. switch (message)
  4. {
  5. case WM_REPORT_BATCHWRITEPU_CLOSEFLAGE:
  6. this->FireSetCloseFlag((short)wParam);
  7. break;
  8. }
  9. return COleControl::OnWndMsg(message, wParam, lParam, pResult);
  10. }
  11. HRESULT CxxxCtrl::OnActivateInPlace(BOOL bUIActivate, LPMSG pMsg)
  12. {
  13. static BOOL bInsideFunc = FALSE;
  14. if (!bInsideFunc)
  15. {
  16. bInsideFunc = TRUE;
  17. HRESULT hr = COleControl::OnActivateInPlace(bUIActivate, pMsg);
  18. bInsideFunc = FALSE;
  19. return hr;
  20. }
  21. return S_OK;
  22. }
  23. BOOL CxxxCtrl::PreTranslateMessage(MSG* pMsg)
  24. {
  25. switch (pMsg->message)
  26. {
  27. case WM_KEYDOWN:
  28. case WM_KEYUP:
  29. switch (pMsg->wParam)
  30. {
  31. case VK_UP:
  32. case VK_DOWN:
  33. case VK_LEFT:
  34. case VK_RIGHT:
  35. case VK_HOME:
  36. case VK_END:
  37. ::SendMessage (GetFocus()->GetSafeHwnd(), pMsg->message, pMsg->wParam, pMsg->lParam);
  38. return TRUE;
  39. }
  40. break;
  41. }
  42. return COleControl::PreTranslateMessage(pMsg);
  43. }
BOOL CxxxCtrl::OnWndMsg(UINT message, WPARAM wParam, LPARAM lParam, LRESULT *pResult)
{
switch (message)
{
case WM_REPORT_BATCHWRITEPU_CLOSEFLAGE:
this->FireSetCloseFlag((short)wParam);
break;
}
return COleControl::OnWndMsg(message, wParam, lParam, pResult);
}
HRESULT CxxxCtrl::OnActivateInPlace(BOOL bUIActivate, LPMSG pMsg)
{
static BOOL bInsideFunc = FALSE;
if (!bInsideFunc)
{
bInsideFunc = TRUE;
HRESULT hr = COleControl::OnActivateInPlace(bUIActivate, pMsg);
bInsideFunc = FALSE;
return hr;
}
return S_OK;
}
BOOL CxxxCtrl::PreTranslateMessage(MSG* pMsg)
{
switch (pMsg->message)
{
case WM_KEYDOWN:
case WM_KEYUP:
switch (pMsg->wParam)
{
case VK_UP:
case VK_DOWN:
case VK_LEFT:
case VK_RIGHT:
case VK_HOME:
case VK_END:
::SendMessage (GetFocus()->GetSafeHwnd(), pMsg->message, pMsg->wParam, pMsg->lParam);
return TRUE;
}
break;
}
return COleControl::PreTranslateMessage(pMsg);
}

并加入鼠标事件处理:

  1. int <span style="font-family: Arial, Helvetica, sans-serif;">CxxxCtrl</span>::OnMouseActivate(CWnd* pDesktopWnd, UINT nHitTest, UINT message)
  2. {
  3. // TODO: Add your message handler code here and/or call default
  4. OnActivateInPlace(TRUE, NULL); //事件加入后,请加入此行代码。
  5. return COleControl::OnMouseActivate(pDesktopWnd, nHitTest, message);
  6. }
int <span style="font-family: Arial, Helvetica, sans-serif;">CxxxCtrl</span>::OnMouseActivate(CWnd* pDesktopWnd, UINT nHitTest, UINT message)
{
// TODO: Add your message handler code here and/or call default
OnActivateInPlace(TRUE, NULL); //事件加入后,请加入此行代码。
return COleControl::OnMouseActivate(pDesktopWnd, nHitTest, message);
}

并OnCreate事件上也加上

  1. OnActivateInPlace(TRUE, NULL);
OnActivateInPlace(TRUE, NULL); 

该代码,记得在你的对话框创建前。

3、其他一些问题如果你遇上了,请看一下下面一篇博文,看看是不是有解决方案在其中。博文地址:http://blog.csdn.NET/xiaoxiaoyu85/article/details/6821205

#include <objsafe.h>//OCX控件在IE8浏览器下不能使用问题的更多相关文章

  1. VC2005从开发MFC ActiveX ocx控件到发布到.net网站的全部过程

      开篇语:最近在弄ocx控件发布到asp.net网站上使用,就是用户在使用过程中,自动下载安装ocx控件.(此文章也是总结了网上好多人写的文章,我只是汇总一下,加上部分自己的东西,在这里感谢所有在网 ...

  2. ocx控件避免弹出警告的类--2

    本文与 OCX控件避免弹出安全警告的类 http://www.cnblogs.com/lidabo/archive/2013/03/26/2981852.html 有些类似,只不过增加了几行代码(红色 ...

  3. html 调用ocx控件

    !DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/x ...

  4. 调用ocx ActiveX控件详解(做一个简单的ocx控件)

    背景 最近做的项目都和插件有关,就是在页面中调用插件的方法,然后进行操作. 插件就是ocx ActiveX控件,具体的说明可以自己去了解一下,在这里就不做赘述. 具体调用方式很简单: 1.在页面中写一 ...

  5. 帮同事写了几行代码,在 安装/卸载 程序里 注册/卸载 OCX控件

    写了个小控制台程序,这个程序用来注册 / 卸载OCX控件,用在Inno Setup做的安装卸载程序里. #include "stdafx.h" #include <windo ...

  6. OCX控件避免弹出安全警告的类

    1.要加一个头文件:         #include <objsafe.h>2.在控件头文件中加入: 1 DECLARE_INTERFACE_MAP()2 BEGIN_INTERFACE ...

  7. MFC中开发ocx控件,html容器收不到ocx的事件Event

    问题背景: MFC开发ocx控件,主窗口就是ctrl类,主窗口类中调度接口和事件映射添加,执行OK,外部html容器中接收事件成功,如下: ctrl.h中声明事件映射函数 void EVTPENSIG ...

  8. PHP调用OCX控件的具体方法

    需要设置php.ini文件,找到这行com.allow_dcom=true,把com组件支持启用 使用PHP调用OCX控件,本不是个难题,但现实中采用flash回避的方法更通用.真正使用ocx的不多, ...

  9. ocx控件针对网页刷新和关闭分别进行区分处理

    当ocx加载在网页上时,如果对网页执行F5刷新事件,ocx控件会销毁ocx的窗口类,但是ocx的APP类是不会销毁的. 只有当网页被关闭时,才销毁app类. --------------------- ...

随机推荐

  1. MySql数据库忘记root密码

    以windows为例: 1. 关闭正在运行的MySQL服务.(services.msc运行停止服务) 2. 打开DOS窗口,转到mysql\bin目录.(输入cd..返回到c盘根目录下,一般MySQL ...

  2. 如何使用花生壳 发布WCF服务 进行外网访问

    当我们发布WCF服务的时候,可以直接通过服务器的域名或者IP进行. 但是如果仅仅是通过花生壳进行域名解析,需要我们自己在设置的时候注意以下几点, 直接用图说明问题 1.首先配置花生壳,在红色处填写一个 ...

  3. C#编程语言与面向对象——类与对象

    由于ASP.NET技术是全面向对象的,因此,要掌握这一技术,必须具备有扎实的面向对象理论基础 使用C#编程,所有的程序代码几乎都放在类中,不存在独立于类中之外的函数,因此,类是面向对象编程的基本单元 ...

  4. myeclipse10中文注释乱码问题

    将别人的项目或JAVA文件导入到自己的Eclipse中时,常常会出现JAVA文件的中文注释变成乱码的情况,主要原因就是别人的IDE编码格式和自己的Eclipse编码格式不同. 总结网上的建议和自己的体 ...

  5. jquery的ajax和jsonp的写法

    交互 ajax jsonp ajax跟之前一模一样 $(document).ready(function(){     $.ajax({         url:'get.php',         ...

  6. Html菜鸡大杂烩

    <!DOCTYPE html> <html> <head lang="en"> <meta charset="UTF-8&quo ...

  7. Swift处理堆栈问题——给定两组序列,其中一个序列表示栈的push 顺序,判断另一个序列有没有可能是对应的pop 顺序

    题目:输入两个整数序列.其中一个序列表示栈的push 顺序,判断另一个序列有没有可能是对应的pop 顺序.为了简单起见,我们假设push 序列的任意两个整数都是不相等的.比如输入的push 序列是1. ...

  8. Your stream was neither an OLE2 stream, nor an OOXML stream.问题的解决

    先说说问题的来源 ,使用NPOI读取Except,先通过流来读取,如果符合要求,就将流保存为文件. 众所周知,流只能读一次,所以在流读取之前需要将流拷贝一份,保存文件的时候使用. protected ...

  9. I2C

    1.I2C协议个. 2.1 I2CADR 地址寄存器CPU也可以是I2C的Slave,CPU的I2C地址有 I2CADR指定 2.2 I2CFDR 频率设置寄存器The serial bit cloc ...

  10. eclipse连接mysql,插入数据时乱码

    问题:如果eclipse中项目的编码方式为utf-8 插入数据后,在数据库中查看后,汉字出现乱码情况 解决方法: 1.在获取连接的时候将conn = DriverManager.getConnecti ...