在此之前我们思考以下几个问题:
- MFC的前世今生
- 创建MFC项目
- 了解MFC生命周期
- 修改RC资源文件,设置监听
MFC的前世今生
为什么我要先讲这些?因为我发现网上下载的MFC项目已经比较老了,而在VS2017上新建的项目结构又太过于复杂,根本不适合初学者入门。怎么办呢?这里出现了一个WIN32API和CWinApp这两个名称,前者就是比较老的版本,它包含一个WinMain函数,即入口函数,比较好理解,而后者则引入了CWinApp,称之为应用程序对象,在一个MFC程序当中只允许有一个应用程序对象,在其构造函数中完成初始化。
创建MFC项目
- 创建项目
- 创建MFC
- 选择类型
了解MFC生命周期
如果找不到MFC新建项目建议先看看这篇博客
https://blog.csdn.net/qq_20330595/article/details/82379577
这边打断点才是调试生命周期的最佳办法
我的Demo项目名为mQMFC。
1. 从mQMFC.h开始
1. #pragma once 类似于OC的import,意思是避免重复引入头文件报错。
2. ‘AFXWIN_H‘为防止重复引入
3. #error 当然就是报错了
4. extern CmQMFCApp theApp; 申明全局唯一程序实例,extern表示只申明,不初始化,类似于kotlin的laterinit var。
5. CWinApp为窗口主类
6. #include “resource.h” // 主符号 固定写法
7. virtual BOOL InitInstance(); //CmQMFCApp对CWinApp的InitInstance方法的重写在mQFCApp实现
8. CmQMFCApp();注意是构造函数在mQFCApp实现。
9. DECLARE_MESSAGE_MAP() 注意 没有‘;’ 宏定义的重写
2. 生命周期:简单点说就是CWinApp为程序入口窗口,而它具有一定的生命周期,BEGIN_MESSAGE_MAP这个相当于setConclickListener方法
API | 所属类 | 功能介绍 | 备注1 | 备注2 |
---|---|---|---|---|
InitInstance | CWinApp | 重写初始化方法 唯一 | 主窗口的初始化函数 | |
DoDataExchange | CWinApp | UpdateData时候调用 | ||
OnInitDialog | CDialogEx | 对话框类已经构造,但是对话框还没有显示出来的时候 | 对话框的初始化函数 | |
OnPaint | CDialogEx | 如果向对话框添加最小化按钮,则需要下面的代码,来绘制该图标 | 对于使用文档/视图模型的 MFC 应用程序,这将由框架自动完成 | |
OnQueryDragIcon | CDialogEx | 当用户拖动最小化窗口时系统调用此函数取得光标 | ||
OnSysCommand | CDialogEx | 响应系统控制菜单的命令.(即左上角图标处) | ||
DECLARE_MESSAGE_MAP | afxwind.h | 消息宏映射申明 | 默认要写 | |
BEGIN_MESSAGE_MAP,END_MESSAGE_MAP | afxwind.h | 在BEGIN_MESSAGE_MAP()和END_MESSAGE_MAP()之间添加你的消息响应函数,为每个消息处理函数加入一个入口 | ||
ON_Notification(id, memberFxn) | 为BEGIN_MESSAGE_MAP添加消息映射入口格式 | id指定了发送通知的控件的子窗口的ID,而memberFxn指定了处理该通知的父对象中的成员函数名。 | ON_BN_CLICKED/用户单击按钮时,ON_BN_DOUBLECLICKED/双击 |
#修改RC资源文件,设置监听
1.VS修改界面是非常简单的直接拖拽即可
2.而添加点击事件则可以直接设置类向导来完成
3.虽然傻瓜式,但是对你理解流程很有帮助
生成代码如下:
//设置监听事件
BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
ON_BN_CLICKED(ID_CONFIRM, &CAboutDlg::OnClickedConfirm)
END_MESSAGE_MAP()
class CAboutDlg : public CDialogEx
{
public:
CAboutDlg();
// 对话框数据
#ifdef AFX_DESIGN_TIME
enum { IDD = IDD_ABOUTBOX };
#endif
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV 支持
// 实现
protected:
DECLARE_MESSAGE_MAP()
public:
//自动生成的申明
afx_msg void OnClickedConfirm();
};
//实现OnClickedConfirm函数 当点击确定调用该方法。
void CAboutDlg::OnClickedConfirm()
{
CString str = _T("马齐成功的 调用了 确认的点击事件");
AfxMessageBox(str);
}
总结
到此MFC的入门已经算是崭露头角,相信还有许多不清楚的地方需要继续探索,
比如一系列的 ‘重写函数’ 和 ‘常量’ 以及 ‘宏’,不过也不是没有收获,我们从中了解到了一个windows应用的启动过程,以及界面的设置和监听事件的写法,我们已经画好了一个圈,至于中间得部分,还需要我们慢慢的描绘,所谓任重而道远啊。
参考:
1. MFC 消息映射笔记 https://blog.csdn.net/q__y__l/article/details/51284699
2. MFC 鼠标事件 https://www.cnblogs.com/xuxiaorong/p/5991226.html
3. VC++ CString类完美总结(整理)https://www.cnblogs.com/MakeView660/p/6072591.html