用了MFC将近有好几个月的时间,在此记录MFC项目的一点经验:
最基本的创建控件,可以直接在工具栏直接拖控件到对话框中,可以通过设置控件的属性Owner Draw来设置可以改变控件的外观,变得更美观,在项目中自己实现了一个类CNewButton,可以直接在对按钮控件添加该类的对象,利用该对象直接调用类的变量Picname使用图片就可以直接设置图片到该控件,每创建一个控件和变量或者对象名都会对应使用如DDX_Control(pDX, IDC_BUTTON5, m_Button_X_left);映射关系将该控件与一个ID号绑定,相应的通过该控件控制某部分功能的话,直接右键控件添加事件处理程序即可,自动会添加该程序,在头文件中会声明函数如:afx_msg void OnBnClickedButton5();afx_msg前面添加说明该函数是系统自动创建的消息处理函数,同时会在类文件中有ON_BN_CLICKED(IDC_BUTTON5, &CSporescopeDlg::OnBnClickedButton5),该语句说明的是点击该ID号对应的控件会调用OnBnClickedButton5函数,其中ON_BN_CLICKED就是一个MFC的一种消息类型,还有可以在MFC项目中在类向导中直接添加消息类型,如ON_WM_TIMER()定时器消息, ON_WM_SIZE()窗口变化消息,所以说MFC中是靠消息映射的一种机制。如以下所示就是MFC消息映射机制
DECLARE_MESSAGE_MAP()
BEGIN_MESSAGE_MAP(类, CDialog)
ON_BN_CLICKED(控件,&处理函数)
ON_MESSAGE(消息,&处理函数)
ON_MESSAGE_VOID(消息,&处理函数)
END_MESSAGE_MAP()
BEGIN_MESSAGE_MAP(CSporescopeDlg, CDialogEx)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_WM_CTLCOLOR()
ON_BN_CLICKED(IDC_BUTTON5, &CSporescopeDlg::OnBnClickedButton5)
ON_BN_CLICKED(IDC_BUTTON6, &CSporescopeDlg::OnBnClickedButton6)
ON_BN_CLICKED(IDC_BUTTON7, &CSporescopeDlg::OnBnClickedButton7)
ON_BN_CLICKED(IDC_BUTTON8, &CSporescopeDlg::OnBnClickedButton8)
ON_BN_CLICKED(IDC_BUTTON9, &CSporescopeDlg::OnBnClickedButton9)
ON_BN_CLICKED(IDC_BUTTON10, &CSporescopeDlg::OnBnClickedButton10)
ON_BN_CLICKED(IDC_BUTTON12, &CSporescopeDlg::OnBnClickedButton12)
ON_BN_CLICKED(IDC_BUTTON13, &CSporescopeDlg::OnBnClickedButton13)
ON_WM_TIMER()
ON_CBN_SELCHANGE(IDC_COMBO2, &CSporescopeDlg::OnCbnSelchangeCombo2)
ON_BN_CLICKED(IDC_BUTTON16, &CSporescopeDlg::OnBnClickedButton16)
ON_BN_CLICKED(IDC_BUTTON17, &CSporescopeDlg::OnBnClickedButton17)
ON_BN_CLICKED(IDC_BUTTON18, &CSporescopeDlg::OnBnClickedButton18)
ON_BN_CLICKED(IDC_BUTTON20, &CSporescopeDlg::OnBnClickedButton20)
ON_BN_CLICKED(IDC_BUTTON21, &CSporescopeDlg::OnBnClickedButton21)
ON_EN_CHANGE(IDC_EDIT_X, &CSporescopeDlg::OnEnChangeEditX)
ON_BN_CLICKED(IDC_BUTTON_CAMERA, &CSporescopeDlg::OnBnClickedButtonCamera)
ON_WM_MOUSEMOVE()
ON_BN_CLICKED(IDC_BUTTON4, &CSporescopeDlg::OnBnClickedButton4)
ON_WM_CLOSE()
ON_BN_CLICKED(IDC_BUTTON19, &CSporescopeDlg::OnBnClickedButton19)
ON_STN_CLICKED(IDC_STATIC_IMAGE, &CSporescopeDlg::OnStnClickedStaticImage)
ON_BN_CLICKED(IDC_BUTTON23, &CSporescopeDlg::OnBnClickedButton23)
ON_BN_CLICKED(IDC_BUTTON24, &CSporescopeDlg::OnBnClickedButton24)
ON_BN_CLICKED(IDC_BUTTON_START, &CSporescopeDlg::OnBnClickedButtonStart)
ON_STN_CLICKED(IDC_TIME, &CSporescopeDlg::OnStnClickedTime)
//ON_STN_CLICKED(IDC_STATIC_MOVE, &CSporescopeDlg::OnStnClickedStaticMove)
ON_WM_SIZE()
ON_WM_CREATE()
ON_BN_CLICKED(IDC_BUTTON3, &CSporescopeDlg::OnBnClickedButton3)
ON_BN_CLICKED(IDC_BUTTON27, &CSporescopeDlg::OnBnClickedButton27)
END_MESSAGE_MAP()
MFC使用多线程:通常使用AfxBeginThread创建线程,该函数如下:
CWinThread* AFXAPI AfxBeginThread(
AFX_THREADPROC pfnThreadProc, //参数1,线程的入口函数,声明形式如:UINT MyThreadFunction( LPVOID pParam );
LPVOID pParam,//参数2,传递入线程的参数,类型为LPVOID
int nPriority,
UINT nStackSize,
DWORD dwCreateFlags,
LPSECURITY_ATTRIBUTES lpSecurityAttrs//参数3、4、5分别指定线程的优先级、堆栈大小、创建标识、安全属性,含义同用户界面线程
)
- AfxBeginThread除前面两个参数外,后面几个都是默认参数,可以将它们省略。前两个参数中,第一个是线程函数的指针,第二个是传递给这个函数的参数。所以可以使用AfxBeginThread(ThreadProc,this);把this传过去,线程函数就可以使用和操作类的成员了。千万注意的是线程函数是静态类函数成员
- 经常使用SerialPortThread = AfxBeginThread(serial_Process, this, 0, 0, 0, NULL);这种方式创建并开启一个线程,而如下的方式是只是创建一个线程,并使用CREATE_SUSPENDED标识表示挂起该线程,并没有当时就启动该线程,必须要使用ResumeThread唤醒才能启动线程,进而调用该线程函数:
SerialPortThread = AfxBeginThread(serial_Process, this, 0, 0, CREATE_SUSPENDED, NULL);//CREATE_SUSPENDED//THREAD_PRIORITY_NORMAL
SerialPortThread->ResumeThread();
3. 结束线程,正常使用AfxBeginThread(serial_Process, this, 0, 0, 0, NULL);形式创建并开启一个线程,线程函数serial_Process执行完并返回一个值,通常是0表示表示成功执行并结束该线程。
4. 在线程函数如UINT CSporescopeDlg::serial_Process(LPVOID pParam)如果要调用类中其他函数或者变量必须在该函数内部声明一个该类的类指针,通过pParam强制转化,如下所示:
UINT CSporescopeDlg::serial_Process(LPVOID pParam)
{
CSporescopeDlg*B = (CSporescopeDlg *)pParam;//利用pParam强制创建该CSporescopeDlg类的类指针
while (B->whetherSerialinit)通过B指针调用CSporescopeDlg的变量
{
B->openuart();//通过B指针调用CSporescopeDlg的函数
}
AfxMessageBox(_T("请用户打开相机"));
return 0;
}
关于多线程还有很多,后面再续。。。