热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

MFC单文档实现文件拖拽功能

其实实现的原理很简单,就是让程序响应和处理WM_DROPFILES消息。主要用到三个函数:VOIDDragAcceptFiles(HWNDhWnd,BOOLfAcce

其实实现的原理很简单,就是让程序响应和处理WM_DROPFILES消息。主要用到三个函数:

VOID DragAcceptFiles(      
HWND hWnd,
BOOL fAccept
);
UINT DragQueryFile(      
HDROP hDrop,
UINT iFile,
LPTSTR lpszFile,
UINT cch
);
VOID DragFinish(          HDROP hDrop);

首先我们建立一个MFC的单文档程序,命名为DragFiles

在生成的CDragFilesView类的OnCreate函数的末尾添加一条函数调用

DragAcceptFiles(TRUE);//支持文件拖拽
在MSDN中DragAcceptFiles的描述是这样的

DragAcceptFiles Function

Registers whether a window accepts dropped files.

//注册一个窗口,是否支持拖拽文件

Syntax

VOID DragAcceptFiles(      
HWND hWnd,
BOOL fAccept
);

Parameters

hWnd
The identifier of the window that is registering whether it will accept dropped files.
//需要支持拖拽操作的窗口句柄
fAccept
A value that indicates if the window identified by the hWnd parameter accepts dropped files. This value is TRUE to accept dropped files or FALSE to discontinue accepting dropped files.
一个布尔值,指示是否支持拖拽

Return Value

No return value.

Remarks

An application that calls DragAcceptFiles with the fAccept parameter set to TRUE has identified itself as able to process the WM_DROPFILES message from File Manager.

如果一个应用程序调用了DragAcceptFiles函数并将fAccept参数设置成了TRUE,那么它就指定了自己可以处理来自文件管理器的WM_DROPFILES消息。

Function Information

Minimum DLL Version shell32.dll version 4.0 or later
Custom Implementation No
Header shellapi.h
Import library shell32.lib
Minimum operating systems Windows NT 3.1, Windows 95
可以看到在调用这个API函数的时候需要包含shellapi.h头文件,并且导入lib文件
#pragma comment(lib,"shell32.lib")
但是我们上面调用的函数只有一个参数,这是因为我们调用的那个函数时MFC封装过得函数,是CWnd类的一个成员函数。包含在atlwin.h 中,底层还是调用上面的那个API函数实现的。
由于文档是覆盖在主窗体上的,所以必须用文档类来处理WM_DROPFILES消息。
接下来我们给文档类添加WM_DROPFILES的消息处理函数:
void CDragFilesView::OnDropFiles(HDROP hDropInfo)
{
// TODO: Add your message handler code here and/or call default
UINT nFileNum = DragQueryFile(hDropInfo, 0xFFFFFFFF, NULL, 0); // 拖拽文件个数
TCHAR strFileName[MAX_PATH]; //定义一个缓冲区,接收文件名字
for (int i = 0; i {
DragQueryFile(hDropInfo, i, strFileName, MAX_PATH);//获得拖曳的文件名
m_vetFileNames.push_back(strFileName); //m_vetFileNames是一个文档类中的成员变量,std::vector 保存文件名
}
DragFinish(hDropInfo); //释放hDrop ,销毁系统为存储拖拽文件的文件名所开辟的内存块

Invalidate(TRUE);//让窗口无效,重绘
CView::OnDropFiles(hDropInfo);
}
在启动拖拽动作时,操作系统会分配一块内存存储拖拽的文件的信息,并通过一个HDROP类型的句柄把该块内存的地址传递给函数OnDropFiles函数。
然后我们调用DragQueryFile。这个函数的原型是:
UINT DragQueryFile(      
HDROP hDrop, //包含拖拽文件的文件名的结构标识
UINT iFile, //拖拽的文件索引,如果是0xFFFFFFFF,那么函数返回拖拽的文件的个数,否则根据索引将文件名字拷贝到lpszFile缓冲区中
LPTSTR lpszFile, //接收文件名的缓冲区,如果是NULL,函数返回缓冲区需要的大小
UINT cch //lpszFile buffer的大小
);
如果iFile设置了0xFFFFFFFF返回拖拽文件的个数,否则返回拷贝文件名的字符数

//为了验证拖拽效果,我们将文件名输出到文档中

//在OnDrow中处理

void CDragFilesView::OnDraw(CDC* pDC)
{
CDragFilesDoc* pDoc = GetDocument();ASSERT_VALID(pDoc);if (!pDoc)return;// TODO: 在此处为本机数据添加绘制代码std::vector::iterator pos;int y=0;TEXTMETRIC tm;//系统字体信息结构体pDC->GetTextMetrics(&tm);//获得系统字体信息,为了得到字体高度for(pos=m_vetFileNames.begin();pos!=m_vetFileNames.end();pos++)//将文件名输出{pDC->TextOut(0,y,*pos);y+=tm.tmHeight;}}

最后执行效果:












推荐阅读
  • 全面介绍Windows内存管理机制及C++内存分配实例(四):内存映射文件
    本文旨在全面介绍Windows内存管理机制及C++内存分配实例中的内存映射文件。通过对内存映射文件的使用场合和与虚拟内存的区别进行解析,帮助读者更好地理解操作系统的内存管理机制。同时,本文还提供了相关章节的链接,方便读者深入学习Windows内存管理及C++内存分配实例的其他内容。 ... [详细]
  • 本文介绍了PE文件结构中的导出表的解析方法,包括获取区段头表、遍历查找所在的区段等步骤。通过该方法可以准确地解析PE文件中的导出表信息。 ... [详细]
  • vue使用
    关键词: ... [详细]
  • Nginx使用(server参数配置)
    本文介绍了Nginx的使用,重点讲解了server参数配置,包括端口号、主机名、根目录等内容。同时,还介绍了Nginx的反向代理功能。 ... [详细]
  • 本文介绍了三种方法来实现在Win7系统中显示桌面的快捷方式,包括使用任务栏快速启动栏、运行命令和自己创建快捷方式的方法。具体操作步骤详细说明,并提供了保存图标的路径,方便以后使用。 ... [详细]
  • Go Cobra命令行工具入门教程
    本文介绍了Go语言实现的命令行工具Cobra的基本概念、安装方法和入门实践。Cobra被广泛应用于各种项目中,如Kubernetes、Hugo和Github CLI等。通过使用Cobra,我们可以快速创建命令行工具,适用于写测试脚本和各种服务的Admin CLI。文章还通过一个简单的demo演示了Cobra的使用方法。 ... [详细]
  • 怎么在PHP项目中实现一个HTTP断点续传功能发布时间:2021-01-1916:26:06来源:亿速云阅读:96作者:Le ... [详细]
  • .NetCoreWebApi生成Swagger接口文档的使用方法
    本文介绍了使用.NetCoreWebApi生成Swagger接口文档的方法,并详细说明了Swagger的定义和功能。通过使用Swagger,可以实现接口和服务的可视化,方便测试人员进行接口测试。同时,还提供了Github链接和具体的步骤,包括创建WebApi工程、引入swagger的包、配置XML文档文件和跨域处理。通过本文,读者可以了解到如何使用Swagger生成接口文档,并加深对Swagger的理解。 ... [详细]
  • 本文介绍了NetCore WebAPI开发的探索过程,包括新建项目、运行接口获取数据、跨平台部署等。同时还提供了客户端访问代码示例,包括Post函数、服务器post地址、api参数等。详细讲解了部署模式选择、框架依赖和独立部署的区别,以及在Windows和Linux平台上的部署方法。 ... [详细]
  • 本文介绍了闭包的定义和运转机制,重点解释了闭包如何能够接触外部函数的作用域中的变量。通过词法作用域的查找规则,闭包可以访问外部函数的作用域。同时还提到了闭包的作用和影响。 ... [详细]
  • Commit1ced2a7433ea8937a1b260ea65d708f32ca7c95eintroduceda+Clonetraitboundtom ... [详细]
  • 在开发app时,使用了butterknife后,在androidStudio打包apk时可能会遇到报错。为了解决这个问题,可以通过打开proguard-rules.pro文件进行代码混淆来解决。本文介绍了具体的混淆代码和方法。 ... [详细]
  • C# WPF自定义按钮的方法
    本文介绍了在C# WPF中实现自定义按钮的方法,包括使用图片作为按钮背景、自定义鼠标进入效果、自定义按压效果和自定义禁用效果。通过创建CustomButton.cs类和ButtonStyles.xaml资源文件,设计按钮的Style并添加所需的依赖属性,可以实现自定义按钮的效果。示例代码在ButtonStyles.xaml中给出。 ... [详细]
  • Go GUIlxn/walk 学习3.菜单栏和工具栏的具体实现
    本文介绍了使用Go语言的GUI库lxn/walk实现菜单栏和工具栏的具体方法,包括消息窗口的产生、文件放置动作响应和提示框的应用。部分代码来自上一篇博客和lxn/walk官方示例。文章提供了学习GUI开发的实际案例和代码示例。 ... [详细]
  • Oracle seg,V$TEMPSEG_USAGE与Oracle排序的关系及使用方法
    本文介绍了Oracle seg,V$TEMPSEG_USAGE与Oracle排序之间的关系,V$TEMPSEG_USAGE是V_$SORT_USAGE的同义词,通过查询dba_objects和dba_synonyms视图可以了解到它们的详细信息。同时,还探讨了V$TEMPSEG_USAGE的使用方法。 ... [详细]
author-avatar
ryan__bug
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有