一、简单介绍一下WTL的CShellFileDialog对话框
1、在WTL中用于实现CShellFileDialog模板有
class CShellFileDialogImpl<T>; //基于IFileDialogEvents接口的基础模板,主要封装相关事件,是CShellFileOpenDialogImpl和CShellFileSaveDialogImpl的基础
class CShellFileOpenDialogImpl<T>; //基于IFileOpenDialog接口的基础模板,IFileOpenDialog是IFileDialog的派送类,MFC中是使用IFileDialog作为成员变量的,而后通过传入的参数,实际实例化IFileOpenDialog或者IFileSaveDialog
class CShellFileOpenDialog; //基于IFileOpenDialog接口的基础模板的实现类
class CShellFileSaveDialogImpl<T>; //基于IFileSaveDialog接口的基础模板,IFileSaveDialog是IFileDialog的派送类,MFC中是使用IFileDialog作为成员变量的,而后通过传入的参数,实际实例化IFileOpenDialog或者IFileSaveDialog
class CShellFileSaveDialog; //基于IFileSaveDialog接口的基础模板的实现类
CShellFileDialogImpl<T>已经实现了所有IFileDialogEvents接口,并通过_Advise和_Unadvise来实现对事件的绑定和实际调用
CShellFileOpenDialogImpl<T>是CShellFileDialogImpl<T>派送类,并对集成了IFileOpenDialog接口应用的简单封装,主要完成了构造函数的初始化,其实际功能需要通过GetPtr函数返回的IFileOpenDialog指针来完成
CShellFileOpenDialog则是CShellFileOpenDialogImpl<T>模板的实例,其中_Advise和_Unadvise函数被刻意置空,也就是默认没有实现对自定义事件的实现功能
2、自定义事件处理
要对自定义事件进行处理,就需要自己对CShellFileOpenDialogImpl<T>模板派送一个实例,添加对应的处理函数,但不能添加_Advise和_Unadvise函数,而是让其继承CShellFileDialogImpl< T >中的相关函数用于绑定事件处理
class MyShellFileOpenDialog : public CShellFileOpenDialogImpl<CShellFileOpenDialog>
{
public:
MyShellFileOpenDialog(LPCWSTR lpszFileName = NULL,
DWORD dwOptions = FOS_FORCEFILESYSTEM | FOS_PATHMUSTEXIST | FOS_FILEMUSTEXIST,
LPCWSTR lpszDefExt = NULL,
const COMDLG_FILTERSPEC* arrFilterSpec = NULL,
UINT uFilterSpecCount = 0U) : CShellFileOpenDialogImpl<MyShellFileOpenDialog>(lpszFileName, dwOptions, lpszDefExt, arrFilterSpec, uFilterSpecCount)
{ }
virtual ~MyShellFileOpenDialog()
{ }
//删除原CShellFileOpenDialog中的_Advise和_Unadvise即可以绑定事件
//void _Advise(DWORD& /*dwCookie*/){ }
//void _Unadvise(DWORD /*dwCookie*/){ }
HRESULT OnFileOk()//添加处理函数
{
MessageBox(....);
return S_OK;
}
};
二、实现界面的自定义(IFileDialogCustomize)以及实现自定义事件处理(IFileDialogControlEvents)
1、IFileDialogControlEvents接口是系统自动从实现了IFileDialogEvents接口的对象中调取,不需要用户另外配置或绑定的
class CShellFileOpenDialogCustomizeImpl : public IFileDialogEvents, public IFileDialogControlEvents;
//或者利用WTL已经实现CShellFileDialogImpl,则我们只需要再实现IFileDialogControlEvents
template <class T>
class CShellFileDialogCustomizeImpl : public IFileDialogControlEvents< T >;
template <class T>
class CShellFileOpenDialogCustomizeImpl : public WTL::CShellFileDialogImpl< T >, public CShellFileDialogCustomizeImpl< T >
2、IFileDialogCustomize接口,此接口是用于添加控件,实现界面及控件自定义的关键,这个接口可直接从IFileOpenDialog接口中获取
ATL::CComPtr<IFileOpenDialog> m_spFileDlg;
ATL::CComPtr<IFileDialogCustomize> m_spFileDlgCust;
HRESULT hRet = m_spFileDlg.CoCreateInstance(CLSID_FileOpenDialog);
hRet = m_spFileDlg->QueryInterface(IID_PPV_ARGS(&m_spFileDlgCust));
完成后,只需要调用m_spFileDlgCust(IFileDialogCustomize)中的相关函数的调用,即可完成对对话框的添加控件的任务
保存对话框也是类似,只是接口由IFileOpenDialog变成了IFileSaveDialog
三、全部实现代码如下:
#ifndef _FILEDIALOGCUSTOMIZE_H_
#define _FILEDIALOGCUSTOMIZE_H_
#include <atlwin.h>
#include <atldlgs.h>
namespace WTL {
template <class T>
class ATL_NO_VTABLE CShellFileDialogCustomizeImpl : public IFileDialogControlEvents {
public:
// Implementation - IUnknown interface
STDMETHOD(QueryInterface)(REFIID riid, void** ppvObject)
{
if(ppvObject == NULL)
return E_POINTER;

本文详细介绍了如何在WTL中使用CShellFileDialog及其派生类实现文件对话框的自定义,包括自定义事件处理和界面定制。通过CShellFileOpenDialogCustomize和CShellFileSaveDialogCustomize实例,展示了如何添加控件和处理编码选择,以及创建自定义事件响应。
最低0.47元/天 解锁文章
1573

被折叠的 条评论
为什么被折叠?



