📄 basedialog.h
字号:
/*******************************************************************************
* Copyright (C) 1980-2008 Xumingxsh
* All rights reserved.
*
* 文件名称: BaseDialog .h
* 创建日期: 2008-04-08
* 创 建 人: 徐敏荣
* 说 明: 类CBaseDialog的头文件。
*-------------------------------------------------------------------------------
* 版本 日 期 修改人 修改说明
*-------------------------------------------------------------------------------
* 1.0.0 2008-04-08 徐敏荣 完成初始版本
*******************************************************************************/
#if !defined(AFX_SEARCHBASEDIALOG_H__371A0B29_8C13_4E98_B67A_A57BFD6CF76D__INCLUDED_)
#define AFX_SEARCHBASEDIALOG_H__371A0B29_8C13_4E98_B67A_A57BFD6CF76D__INCLUDED_
/*
下面的两个宏,只是生成了每个界面类都可能有的几个静态方法的声明及实现。
ClassProc的功能是根据CBaseDialog提供的功能处理非Command意外的命令,如果对这些命令还有扩充或修改,
则不能使用这些扩展类。
ClassProc的功能是为窗体注册提供函数,前提是每个窗体只有一个实例,且名称为s_类名,如果这种假设不成立,
则也不能使用这些宏。
到这儿我产生了一种想法,既然如何处理WM_COMMAND可以调用窗体的一个函数来处理,则窗体的其他消息处理
方式其实也可以写成窗体中的函数,然后将该函数写到CBaseDialog中,该函数为虚函数。
----------------------------------------------------
把公共的处理放大些在函数【非晶态函数】CommonProc中,由静态函数CommonProc来调用。
如果遇到没有处理的信息,则使用虚函数OtherMsgProc来处理。
----------------------------------------------------
暂时,ClassProc不能取消,因为如果取消,还不知道如何用CBaseDialo中的ClassProc代替,主要是窗体对象
无法传过来。
写一些很玄的代码感觉很酷,很好玩,而且可以对公共部分进行集中处理,例如我有什么想法,可以直接修改这
些代码即可。虽然很酷, 但是要有一条,就是我不是看程序的人,否则我会头大。
看来宏还是适合来添加不同类之中的类似静态函数的,这是用宏实现抽象啊
看侯捷的书《深入浅出MFC》,学会了宏的这种用法,一试,果然好用。
还有,关于消息的机制,关于WinApp,我也可以在这里试一试。
*/
#define DECLERE_CTREVENT(class_name) \
private: \
void SetCtrlEvent(BaseControl* pctrl, void (class_name::*fuun)(WPARAM wParam, LPARAM lParam)); \
void SetCtrlEvent(int nID, void (class_name::*fun)(WPARAM wParam, LPARAM lParam));
#define DECLARE_REGISTANDPRC(class_name) \
private: \
static LRESULT CALLBACK ClassProc(HWND hWnd, \
UINT message, WPARAM wParam, LPARAM lParam);\
public: \
static int RegistClass(WNDCLASS &wc); \
static class_name s_##class_name; \
DECLERE_CTREVENT(class_name)
//void SetCtrlEvent(BaseControl* pctrl, void (class_name::*fuun)());
/*
本宏展开为:
public:
static 类名 s_类名; 我觉得不应该把 s_类名放到这里,因为用户用到该变量的时候,不容易发现他在哪儿定义
但是如果不在这儿声明s_类名,则无法保证ClassProc用到的s_类名存在
static int RegistClass(WNDCLASS &wc);
private:
static LRESULT CALLBACK ClassProc(HWND hWnd,
UINT message, WPARAM wParam, LPARAM lParam);
*/
#define IMPLEMENT_CTREVENT(class_name) \
void class_name::SetCtrlEvent(BaseControl* pctrl, void (class_name::*fun)(WPARAM wParam, LPARAM lParam)) \
{ \
this->SetCtrlEvent(pctrl->m_nID, fun); \
} \
void class_name::SetCtrlEvent(int nID, void (class_name::*fun)(WPARAM wParam, LPARAM lParam)) \
{ \
int size = m_MsgMap.GetSize(); \
for (int i = 0; i < size; i++) \
{\
MsgEvent event = m_MsgMap.GetAt(i); \
if (event.mMessage == nID) \
{\
m_MsgMap.RemoveAt(i);\
break; \
}\
}\
MsgEvent event = {nID, static_cast<CtrlEvent>(fun)}; \
m_MsgMap.Add(event); \
}
#define IMPLEMENT_REGISTANDPRC(class_name) \
class_name class_name::s_##class_name; \
LRESULT CALLBACK class_name::ClassProc(HWND hWnd, \
UINT message, WPARAM wParam, LPARAM lParam) \
{\
CBaseDialog::CommonProc(class_name::s_##class_name, hWnd, message, wParam, lParam); \
return DefWindowProc(hWnd, message, wParam, lParam); \
}\
int class_name::RegistClass(WNDCLASS &wc) \
{ \
wc.lpfnWndProc = class_name::ClassProc; \
wc.lpszClassName = TEXT(#class_name); \
return RegisterClass(&wc); \
} \
IMPLEMENT_CTREVENT(class_name)
/*
本宏展开:
类名 类名::s_类名;
LRESULT CALLBACK 类名::ClassProc(HWND hWnd,
UINT message, WPARAM wParam, LPARAM lParam)
{
CBaseDialog::CommonProc(类名::s_类名, hWnd, message, wParam, lParam);
return DefWindowProc(hWnd, message, wParam, lParam);
}
int 类名::RegistClass(WNDCLASS &wc)
{
wc.lpfnWndProc = 类名::ClassProc;
wc.lpszClassName = TEXT("类名");
return RegisterClass(&wc);
}*/
/*
因为static_cast<CtrlEvent>用法丑陋,所以把static_cast限制在这儿,使其不扩散。
*/
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#include "ToolKit.h"
#include "BaseControl.h"
#include "XMRArray.h"
#include "WndX.h"
// 定义控件事件
typedef void (CWndX::*CtrlEvent)(WPARAM wParam, LPARAM lParam);
struct MsgEvent
{
int mMessage; // 消息ID
CtrlEvent pEvent; // 消息对应的操作
};
/**=============================================================================
* 名 称: <CBaseDialog>
* 说 明: <界面程序的基类,该类实现从配置文件中动态生成界面控件的功能>
* 接 口:
* 调 用:
* 编 程: <徐敏荣>,<2008-04-08>
*=============================================================================*/
class CBaseDialog : public CWndX
{
private:
// 存储所有创建窗体的集合
static XMRArray<CBaseDialog*> s_DialogArr;
static CBaseDialog* GetBaseDialog(HWND hwnd);
static HWND CretateWnd(CreateWndStruct &wndStruct);
public:
/**------------------------------------------------------------------------------------
* 名 称: <CommonProc>
* 说 明: <回调函数的公共处理方法>
* 参 数:
* 返 回:
*---------------------------------------------------------------------------------------*/
static void CommonProc(CBaseDialog &wndDlg, HWND hWnd,
UINT message, WPARAM wParam, LPARAM lParam);
public:
CBaseDialog();
virtual ~CBaseDialog();
private:
// 屏蔽默认复制构造函数和复制操作符
CBaseDialog(const CBaseDialog& dialog){};
CBaseDialog& operator=(const CBaseDialog& dialog){}
private:
/**-----------------------------------------------------------------------------
* 名 称: <Command>
* 说 明: <执行命令函数>
* 参 数: <WPARAM wParam>:
* <LPARAM lParam>:
* 返 回:
*-----------------------------------------------------------------------------------*/
void Command(WPARAM wParam, LPARAM lParam);
public:
/**-----------------------------------------------------------------------------
* 名 称: <OnShow>
* 说 明: <显示界面>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void OnShow();
/**-----------------------------------------------------------------------------
* 名 称: <OnHide>
* 说 明: <隐藏界面>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void OnHide();
/**-------------------------------------------------------------------------------------
* 名 称: <CreateControls>
* 说 明: <根据配置文件,创建界面的所有控件>
* 参 数:
* 返 回:
*---------------------------------------------------------------------------------------*/
virtual void CreateControls();
/**-----------------------------------------------------------------------------------
* 名 称: <MoveWnd>
* 说 明: <按位置将控件放置在界面上>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void MoveWnd();
/**---------------------------------------------------------------------------------
* 名 称: <DrawItem>
* 说 明: <绘制事件>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void DrawItem(WPARAM wParam,LPARAM lParam);
void OnPaint();
protected:
/**---------------------------------------------------------------------------------
* 名 称: <SetControlPropertity>
* 说 明: <创建控件后设置控件的属性>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void SetControlPropertity();
/**---------------------------------------------------------------------------------
* 名 称: <GetIDByKey>
* 说 明: <根据键值取得控件ID>
* 参 数: <char* chKey>:<键值>
* 返 回: <控件ID>
*-----------------------------------------------------------------------------------*/
unsigned long GetIDByKey(char* chKey);
/**---------------------------------------------------------------------------------
* 名 称: <GetControls>
* 说 明: <取得当前界面中的控件>
* 参 数:
* 返 回: <当前界面中的控件>
*-----------------------------------------------------------------------------------*/
BaseControl* GetControls();
/**---------------------------------------------------------------------------------
* 名 称: <GetControlsCount>
* 说 明: <取得当前界面中的控件数量>
* 参 数:
* 返 回: <当前界面中的控件数量>
*-----------------------------------------------------------------------------------*/
int GetControlsCount();
/**---------------------------------------------------------------------------------
* 名 称: <GetControlByID>
* 说 明: <根据控件ID取得控件对象>
* 参 数: <int nID>:<控件I>
* 返 回: <控件对象>
*-----------------------------------------------------------------------------------*/
virtual BaseControl* GetControlByID(int nID);
/**---------------------------------------------------------------------------------
* 名 称: <GetControlByID>
* 说 明: <根据控件ID取得控件对象>
* 参 数: <int nID>:<控件I>
* 返 回: <控件对象>
*-----------------------------------------------------------------------------------*/
virtual BaseControl* GetControlByKey(CString strKey);
void EnableControl(int nID, bool isEnable);
void SetCtrlText(int nId, CString text);
virtual void InitDataAfterShow();
virtual void InitDataBeforeShow();
virtual void OnDraw(HDC* hDC);
private:
/**-----------------------------------------------------------------------------
* 名 称: <OnDestroyWindow>
* 说 明: <销毁界面>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
void OnDestroyWindow();
public:
CreateWndStruct m_WndStruct; // 界面样式对象
RECT m_MainRect;
protected:
/**-----------------------------------------------------------------------------
* 名 称: <OtherMsgProc>
* 说 明: <处理未处理的消息>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void OtherMsgProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);
/**-----------------------------------------------------------------------------
* 名 称: <CommandProc>
* 说 明: <处理公共的消息>
* 参 数:
* 返 回:
*-----------------------------------------------------------------------------------*/
virtual void CommandProc(HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam);
char* m_ClassName; // 当前窗体类名称
CString m_strFile; // 配置文件路径
private:
BaseControl *m_hwndControls; // 窗体中的控件
int m_ControlCount; // 界面控件数量
protected:
XMRArray<MsgEvent> m_MsgMap; // 存储消息与操作的集合
};
#endif // !defined(AFX_SEARCHBASEDIALOG_H__371A0B29_8C13_4E98_B67A_A57BFD6CF76D__INCLUDED_)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -