转载:http://blog.csdn.net/liuyan20092009/article/details/53819473

转载:https://blog.csdn.net/u012778714(封装成Duilib控件)

转载:https://blog.csdn.net/CYY_JLSAINI/article/details/80090091?utm_source=blogxgwz5

在开发中有一个需求,拖拽外部文件到客户端,然后客户端响应WM_DROPFILES消息,在拖拽消息里处理一下业务,最后把处理结果显示到客户区html中,但实际中发现当拖拽文件到客户区,浏览器首先处理了拖拽事件,外层的Win32窗口无法捕捉到拖拽消息,因此要想实现此操作,刚开始我想了一个本办法,在客户区最外层罩了一个透明的Win32原生窗口,这样拖拽文件时,在最外层透明窗口的WM_DROPFILES消息中处理具体业务,最后用C++调用js函数,在页面显示处理结果。

方法一:

透明窗口

LayeredWindow.h

  1. #ifndef _LAYEREDWINDOW_H_
  2. #define _LAYEREDWINDOW_H_
  3.  
  4. class CLayeredWindow :public WindowImplBase
  5. {
  6. public:
  7. CLayeredWindow();
  8. ~CLayeredWindow();
  9.  
  10. public:
  11. LPCTSTR GetWindowClassName() const;
  12.  
  13. virtual void OnFinalMessage(HWND hWnd);
  14.  
  15. virtual LRESULT ResponseDefaultKeyEvent(WPARAM wParam);
  16.  
  17. virtual UILIB_RESOURCETYPE GetResourceType() const;
  18.  
  19. virtual CDuiString GetSkinFile();
  20.  
  21. virtual CDuiString GetSkinFolder();
  22.  
  23. virtual CControlUI* CreateControl(LPCTSTR pstrClass);
  24.  
  25. virtual void InitWindow();
  26.  
  27. virtual void Notify(TNotifyUI& msg);
  28.  
  29. virtual LRESULT HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam);
  30.  
  31. virtual void OnClick(TNotifyUI& msg);
  32.  
  33. void OnPrepare();
  34. };
  35. #endif//_LAYEREDWINDOW_H_

LayeredWindow.cpp

  1. #include "stdafx.h"
  2. #include "LayeredWindow.h"
  3.  
  4. CLayeredWindow::CLayeredWindow()
  5. {
  6.  
  7. }
  8.  
  9. CLayeredWindow::~CLayeredWindow()
  10. {
  11.  
  12. }
  13.  
  14. LPCTSTR CLayeredWindow::GetWindowClassName() const
  15. {
  16. return _T("LayeredWindow");
  17. }
  18.  
  19. void CLayeredWindow::OnFinalMessage(HWND hWnd)
  20. {
  21. CWindowWnd::OnFinalMessage(hWnd);
  22. }
  23.  
  24. LRESULT CLayeredWindow::ResponseDefaultKeyEvent(WPARAM wParam)
  25. {
  26. if (wParam == VK_RETURN)
  27. {
  28. return FALSE;
  29. }
  30. else if (wParam == VK_ESCAPE)
  31. {
  32. return TRUE;
  33. }
  34. return FALSE;
  35. }
  36.  
  37. DuiLib::UILIB_RESOURCETYPE CLayeredWindow::GetResourceType() const
  38. {
  39. return UILIB_FILE;
  40. }
  41.  
  42. DuiLib::CDuiString CLayeredWindow::GetSkinFile()
  43. {
  44. return _T("LayeredDlg.xml");
  45. }
  46.  
  47. DuiLib::CDuiString CLayeredWindow::GetSkinFolder()
  48. {
  49. return _T("");
  50. }
  51.  
  52. CControlUI* CLayeredWindow::CreateControl(LPCTSTR pstrClass)
  53. {
  54. return NULL;
  55. }
  56.  
  57. void CLayeredWindow::InitWindow()
  58. {
  59.  
  60. //加入WS_EX_LAYERED扩展属性
  61. SetWindowLong(this->GetHWND(),GWL_EXSTYLE,
  62. GetWindowLong(this->GetHWND(),GWL_EXSTYLE)^0x80000);
  63. HINSTANCE hInst = LoadLibrary(L"User32.DLL");
  64. if(hInst)
  65. {
  66. typedef BOOL (WINAPI *MYFUNC)(HWND,COLORREF,BYTE,DWORD);
  67. MYFUNC fun = NULL;
  68. //取得SetLayeredWindowAttributes函数指针
  69. fun=(MYFUNC)GetProcAddress(hInst, "SetLayeredWindowAttributes");
  70. if(fun)fun(this->GetHWND(),,,); //0表示全透明,255表示不透明
  71. FreeLibrary(hInst);

  72. }
  73. }
  74.  
  75. void CLayeredWindow::OnPrepare()
  76. {
  77.  
  78. }
  79.  
  80. void CLayeredWindow::Notify(TNotifyUI& msg)
  81. {
  82. if( msg.sType == _T("windowinit") ) OnPrepare();
  83.  
  84. if(msg.sType == _T("click"))
  85. {
  86. }
  87.  
  88. WindowImplBase::Notify(msg);
  89. }
  90.  
  91. void CLayeredWindow::OnClick(TNotifyUI& msg)
  92. {
  93. __super::OnClick(msg);
  94. }
  95.  
  96. //禁用双击标题栏窗口最大化
  97. LRESULT CLayeredWindow::HandleMessage(UINT uMsg, WPARAM wParam, LPARAM lParam)
  98. {
  99. LRESULT lRes = ;
  100. BOOL bHandled = TRUE;
  101. switch( uMsg)
  102. {
  103. case WM_NCLBUTTONDBLCLK:
  104. {
  105. return ;
  106. }
  107. break;
  108. default:
  109. bHandled = FALSE;
  110. }
  111. return WindowImplBase::HandleMessage(uMsg,wParam,lParam);
  112. }

1.在主窗口InitWindow函数里面创建透明窗口

2.在主窗口的WM_SIZE 和 WM_MOVE消息中移动这个透明窗口,让其跟随主窗口移动

方法二:

最好的办法是取消CEF浏览器对拖拽事件的处理,这样让外层Win32窗口处理拖拽事件

研究了一下CEF源码,发现有一个类CefDragHandler,是浏览器拖拽事件,可以让你自己的CLientHandler继承这个类,然后重写它里面的虚函数

  1. virtual bool OnDragEnter(CefRefPtr<CefBrowser>browser,CefRefPtr<CefDragData> dragData,CefDragHandler::DragOperationsMask mask)
    {

CEF_REQUIRE_UI_THREAD();

// Forbid dragging of link URLs.
    if (mask & DRAG_OPERATION_LINK)
    return true;

return false;

  1. }

让其返回true,取消拖拽响应,刚开始只重写了这个虚函数,但在拖拽时还是无法禁止,最后发现少写一个获取拖拽事件处理器

// CefClient 事件处理器,如果没有对应处理器则默认使用内部处理器

  1. virtual CefRefPtr<CefDragHandler> GetDragHandler() {
  2. return this;
  3. }

加上这个函数后,才能真正禁止拖拽事件

方法三:

如果在html页面中有拖拽操作的业务,使用方法二也会被禁止掉不能拖拽,所以想实现禁止从外部拖拽,同时在浏览器内部可以拖拽,就使用这种方法

只在你的html中上这些代码,C++不需要处理拖拽事件了:

  1. <body ondragover="event.preventDefault();" ondrop="event.preventDefault();"></body>

Duilib嵌入CEF禁止浏览器响应拖拽事件的更多相关文章

  1. Duilib嵌入CEF以及JavaScript与C++交互

    转载:http://blog.csdn.net/foruok/article/details/50573612 转载:http://blog.csdn.net/foruok/article/detai ...

  2. window响应拖拽文件操作

    window响应拖拽文件操作 1.首先调用DragAcceptFiles,让控件或者窗体支持文件拖动操作函数功能:用来为拖放文件作初始化.函数原型: void DragAcceptFiles( HWN ...

  3. js之拖拽事件

    js之拖拽事件 api:https://www.runoob.com/jsref/event-ondrag.html 拖拽事件是js原生的事件,使用时在div上添加 draggable="t ...

  4. html5拖拽事件 xhr2 实现文件上传 含进度条

    <!DOCTYPE html> <html> <head> <meta http-equiv="Content-Type" content ...

  5. H5原生拖拽事件

    使用原生js实现简单的拖拽事件 <!DOCTYPE html> <html lang="en"> <head> <meta charset ...

  6. HTML5 02. 多媒体控件、拖拽事件、历史记录、web存储、应用程序缓存、地理定位、网络状态

    多媒体 video:是行内块(text-align: center; 对行内块适用) <figure></figure>: 多媒体标签 : <figcaption> ...

  7. JS Event 鼠标拖拽事件

    <!DOCTYPE html><html> <head>        <meta charset="UTF-8">         ...

  8. HTML5深入学习之鼠标跟随,拖拽事件

    知识点(鼠标跟随): mousedown: 当用户用鼠标点击在某一元素上就会触发该事件 mouseover:  当鼠标指针在某一元素上移动就会触发改事件 下面这个例子的效果就是鼠标点击元素后,元素跟着 ...

  9. day50—JavaScript鼠标拖拽事件

    转行学开发,代码100天——2018-05-05 今天通过鼠标拖拽事件复习巩固一下鼠标事件. 鼠标拖拽事件需要记住两点: 1.距离不变 2.鼠标事件(按下,移动,抬起) <div id=&quo ...

随机推荐

  1. 解决报错:scandir() has been disabled for security reasons

    服务器环境: LNMP 在服务器部署代码时候.遇到了这个问题. 蛋疼啊! 2 解决办法:  打开phpinfo.php , 搜索: scandir 找到disabled_function,确认此函数未 ...

  2. Sun公司的产品AnswerBook存在多种漏洞

    一.未授权管理脚本访问漏洞: 1.受影响版本: Sun-AnswerBook2     1.2-1.4.2 2.攻击测试手段 http://a.b.c.d:8888/ab2/@AdminViewErr ...

  3. sort排序和uniq统计命令

    author:headsen chen date: 2018-08-13  11:08:09 1,sort:排序的功能,默认安装ASCII码来排序,-n 安装数值排,-r 按照倒序来排 [root@b ...

  4. 什么是真正的APM?

    近年来APM行业被越来越多的企业所关注,尤其是在2014年末,NewRelic的成功上市,更加激发了人们对这个行业前景的无限遐想.那么究竟什么是APM?APM的目的是什么?要求我们做什么?有不少企业对 ...

  5. Android软件开发之EditText 详解(八)

    原创作品,允许转载,转载时请务必以超链接形式标明文章 原始出处 .作者信息和本声明.否则将追究法律责任.http://xys289187120.blog.51cto.com/3361352/65718 ...

  6. 使用Spring报错:No default constructor found;

    Exception in thread "main" org.springframework.beans.factory.BeanCreationException: Error ...

  7. JS判断当前是否是IE浏览器,并返回时IE几?

    原文参考: https://www.cnblogs.com/liuyanxia/p/5855760.html 具体代码示例: 这里返回的是:如果不是IE浏览器返回 -1 ,返回 7/8/9/10/11 ...

  8. pandas处理日期时间,按照时间筛选

    pandas有着强大的日期数据处理功能,本期我们来了解下pandas处理日期数据的一些基本功能,主要包括以下三个方面: 按日期筛选数据 按日期显示数据 按日期统计数据 运行环境为 windows系统, ...

  9. scikit_learn 中文说明入门

    原文:http://www.cnblogs.com/taceywong/p/4568806.html 原文地址:http://scikit-learn.org/stable/tutorial/basi ...

  10. SQL---->mySQl数据库1------表内容的增删改查

    增: insert into user(id,username,birthday,entry_date,job,salary,resume) values(1,'aaaa','1995-12-10', ...