mfc编程实例讲解(求MFC编程实例,比如如何让两个数相加,然后输出结果由于对MFC毫无了解,请写得详细些)

2024-07-23 16:49:50 4

mfc编程实例讲解(求MFC编程实例,比如如何让两个数相加,然后输出结果由于对MFC毫无了解,请写得详细些)

本文目录

求MFC编程实例,比如如何让两个数相加,然后输出结果由于对MFC毫无了解,请写得详细些

很简单.1.首先插入一个对话框资源添加两个EDIT控件,对面板进行拖放.并建立对应的对话框类.在对话框类中修改默认的OnOk函数,注意记得调用基类的OnOk;在VIEW类里添加两个int类型的成员变量用来保存输入的数据.代码如下:void CXXXDlg::OnOk(){ i1=(int)GetDlgItemInt(IDC_EDIT1); i2=(int)GetDlgItemInt(IDC_EDIT2); CDialog::OnOk();}2.在VIEW类的.CPP文件中添加上第一步定义对话框类的头文件,在VIEW添加一个成员变量,类型是对话框类的对象.在菜单资源IDR_MAINFRAME中添加一个菜单,用来弹出对话框,响应CHECK消息,在VIEW类里进行映射.在响应函数里添加如下代码:void CXXXView::OnXXX(){ CXXXDlg dlg; if(IDOK==dlg.DoModal() { CClientDC dc(this); CString str; str.Format("两数相加等于:%d",i1+i2); dc.TextOut(0,0,str,str.GetLenth()); dc.MoveTo(0,0); dc.LineTo(i1,i2); }}搞定.

MFC编程 CButton::Create

第四个参数,表示按钮的大小和位置。CRect(x1,y1,x2,y2)x1和y1表示按钮左上角坐标x2和y2表示按钮右下角坐标所以x2必须大于x1,y2必须大于y1;你的x都设成了100,按钮的宽度为0了,当然不显示了。明白了不。

mfc 数据库编程 (odbc)

没时间详细说 给你个例子 有时间晚上交流 qq 469392501void CMemoDBSDlg::OnBtnDelMember() { // TODO: Add your control notification handler code here //获取要删除的成员记录所在的行. int nItem = m_listMember.GetNextItem(-1, LVNI_SELECTED); if(nItem == -1){ AfxMessageBox("没有选择要删除的成员"); return; } //获取成员ID. int id = atoi(m_listMember.GetItemText(nItem,0)); TRY{ CString sql; //从数据库中删除记录. sql.Format("DELETE member_tab " "where member_id = %d",id); TRACE(sql); m_db.ExecuteSQL(sql); //从列表控件中删除该记录. m_listMember.DeleteItem(nItem); } CATCH(CDBException,ex) { AfxMessageBox (ex-》m_strError); AfxMessageBox (ex-》m_strStateNativeOrigin); } AND_CATCH(CException,e) { TCHAR szError; e-》GetErrorMessage(szError,100); AfxMessageBox (szError); } END_CATCH}void CMemoDBSDlg::OnBtnAddType() { // TODO: Add your control notification handler code here //添加备注类型. //初始化备注类型对话框实例. CMemoTypeDlg dlg; if(dlg.DoModal() == IDOK){ //从对话框中获取新添加的备注类型. CString strName = dlg.m_strTypeName; TRY{ CRecordset rs(&m_db); //获取最大的类型ID值. rs.Open(CRecordset::dynaset, "Select max(TYPE_ID) from MEMO_TYPE_TAB"); //初始化新类型ID值为1. int newTypeID = 1; //如果数据库已经有类型记录,则新的类型ID为最大类型ID+1 if(!rs.IsEOF()) { CDBVariant var; rs.GetFieldValue((short)0, var, SQL_C_SLONG); if (var.m_dwType != DBVT_NULL) newTypeID = var.m_iVal + 1; } CString sql; //向数据库中添加新的备忘录类型记录. sql.Format("Insert into MEMO_TYPE_TAB(TYPE_ID," "TYPE_NAME) " "VALUES(" "%d,’%s’)",newTypeID,strName); TRACE(sql); m_db.ExecuteSQL(sql); //向界面中添加记录行. InsertMemoTypeItem(newTypeID,strName); } CATCH(CDBException,ex) { AfxMessageBox (ex-》m_strError); AfxMessageBox (ex-》m_strStateNativeOrigin); } AND_CATCH(CException,e) { TCHAR szError; e-》GetErrorMessage(szError,100); AfxMessageBox (szError); } END_CATCH } }void CMemoDBSDlg::OnBtnModType() { // TODO: Add your control notification handler code here //获取要修改的类型记录 int nItem = m_listType.GetNextItem(-1, LVNI_SELECTED); //如果没有选择要修改的纪录,返回. if(nItem == -1){ AfxMessageBox("没有选择要修改的类型"); return; } //获取要修改记录的ID和名称. int id = atoi(m_listType.GetItemText(nItem,0)); CString name = m_listType.GetItemText(nItem,1); //初始化备注类型对话框. CMemoTypeDlg dlg; //给对话框的变量赋值. dlg.m_strTypeName = name; if(dlg.DoModal() == IDOK){ //获取修改后的数据. CString strName = dlg.m_strTypeName; TRY{ CString sql; //更新记录. sql.Format("UPDATE MEMO_TYPE_TAB SET TYPE_NAME = ’%s’ " " WHERE TYPE_ID = %d",strName,id); TRACE(sql); m_db.ExecuteSQL(sql); //修改界面的值. m_listType.SetItemText(nItem,1,strName); } CATCH(CDBException,ex) { AfxMessageBox (ex-》m_strError); AfxMessageBox (ex-》m_strStateNativeOrigin); } AND_CATCH(CException,e) { TCHAR szError; e-》GetErrorMessage(szError,100); AfxMessageBox (szError); } END_CATCH } }void CMemoDBSDlg::OnBtnDelType() { // TODO: Add your control notification handler code here //获取要删除的记录所在的行. int nItem = m_listType.GetNextItem(-1, LVNI_SELECTED); //如果没有选择,返回. if(nItem == -1){ AfxMessageBox("没有选择要删除的类型"); return; } //获取要删除的类型ID int id = atoi(m_listType.GetItemText(nItem,0)); TRY{ CString sql; sql.Format("DELETE MEMO_TYPE_TAB " "where TYPE_ID = %d",id); TRACE(sql); //删除类型记录 m_db.ExecuteSQL(sql); //删除界面中的记录. m_listType.DeleteItem(nItem); } CATCH(CDBException,ex) { AfxMessageBox (ex-》m_strError); AfxMessageBox (ex-》m_strStateNativeOrigin); } AND_CATCH(CException,e) { TCHAR szError; e-》GetErrorMessage(szError,100); AfxMessageBox (szError); } END_CATCH }void CMemoDBSDlg::OnBtnAddMemo() { // TODO: Add your control notification handler code here //初始化备忘录信息对话框. CMemoInfoDlg dlg; //获取所有的家庭成员的名称. for(int i = 0 ; i 《 m_listMember.GetItemCount() ; i++ ) dlg.m_strMemberArray.Add(m_listMember.GetItemText(i,1)) ; //获取所有的类型信息. for(i = 0 ; i 《 m_listType.GetItemCount() ; i++ ) dlg.m_strTypeArray.Add(m_listType.GetItemText(i,1)) ; //打开对话框,添加新的记录. if(dlg.DoModal() == IDOK){ //从对话框中获取记录值. CString strName = dlg.m_strMember; CString strType = dlg.m_strMemoType; CString strHappenDate = dlg.m_oleDate.Format("%Y-%m-%d") + " " + dlg.m_oleTime.Format("%H:%M:%S"); CString strOperDate = COleDateTime::GetCurrentTime().Format("%Y-%m-%d %H:%M:%S"); int isEvent = dlg.m_isEvent; CString strCost = dlg.m_strCost; CString strMemo = dlg.m_strMemoInfo; TRY{ CRecordset rs(&m_db); CString sql; //根据成员姓名获取成员ID值. sql.Format("Select MEMBER_ID from MEMBER_TAB where " "MEMBER_NAME = ’%s’",strName); rs.Open(CRecordset::dynaset,sql); int memberID = 1; if(!rs.IsEOF()) { CDBVariant var; rs.GetFieldValue((short)0, var, SQL_C_SLONG); if (var.m_dwType != DBVT_NULL) memberID = var.m_iVal; } rs.Close(); //根据备忘录类型获取备忘录类型ID. sql.Format("Select TYPE_ID from MEMO_TYPE_TAB where " "TYPE_NAME = ’%s’",strType); rs.Open(CRecordset::dynaset,sql); int typeID = 1; if(!rs.IsEOF()) { CDBVariant var; rs.GetFieldValue((short)0, var, SQL_C_SLONG); if (var.m_dwType != DBVT_NULL) typeID = var.m_iVal; } rs.Close(); //从SEQ_MEMO_ID序列中获取下一个值.这个值就是新的备忘录ID. rs.Open(CRecordset::dynaset, "Select max(MEMO_ID) from MEMO_INFO_TAB"); int memoID = 1; if(!rs.IsEOF()) { CDBVariant var; rs.GetFieldValue((short)0, var, SQL_C_SLONG); if (var.m_dwType != DBVT_NULL) memoID = var.m_iVal+1; } sql.Format("Insert into MEMO_INFO_TAB(MEMO_ID," "MEMBER_ID,OPER_DATE,HAPPEN_DATE," "IS_BIGEVENT,EVENT_COST,TYPE_ID,MEMO_TEXT) " "VALUES(" "%d,%d,’%s’" ",’%s’,%d,’%s’" ",%d,’%s’)",memoID,memberID, strOperDate,strHappenDate,isEvent,strCost,typeID,strMemo); TRACE(sql); m_db.ExecuteSQL(sql); //向界面中插入新的纪录. InsertMemoInfoItem(memoID,strName,strOperDate,strHappenDate,isEvent,strCost,strType,strMemo) ; } CATCH(CDBException,ex) { AfxMessageBox (ex-》m_strError); AfxMessageBox (ex-》m_strStateNativeOrigin); } AND_CATCH(CException,e) { TCHAR szError; e-》GetErrorMessage(szError,100); AfxMessageBox (szError); } END_CATCH } }

利用MFC编写MySd1应用+程序会产生哪个类,它们分别从+哪些类继承下来的

1.CaboutDlg这个是关于..对话框,不用讲了也是要讲一下的,看这个对话框,你可以了解对话框怎么做的。可以以这个为蓝本,做自己的对话框。2.CMainFrame框架类,通过阅读里面的代码,可以发现,它是窗口创建以及窗口上的工具栏、状态栏的类。3.CTestApp应用程序类,应用程序的入口,查看类视图,你可以发现,唯一的一个全局变量CXXXApptheApp;是这个类的一个实例。4.CTestDoc文档类,用于管理数据5.CTestView视图类,用于将数据显示在窗口上。特别说明一点,SDI使用了文档视图架构,即文档类只负责管理数据,视图类只负责显示。但是也可以不必拘束于此。其实这几个类和C++里的类的概念一样。只不过是程序自动生成的代码而已。你完全可以创建自己的类。

VC++语言 简单编程

一个CStatusBar 对象是一个带有一行文本输出窗格的控件,或者称为“指示器”。这些输出窗格常被用作消息行和状态指示器。一个CToolBar对象是一个工具栏控件。Windows中存在很多类控件,比如文本框、按钮什么的,上面所说的两类也是控件。MFC编程中为每种控件量身设计了一个类,通过实例化该类的对象,就可以调用相关成员函数操作该控件。

如何使用 AfxBeginThread创建MFC线程对象和Win32线程对象

一、问题的提出编写一个耗时的单线程程序:  新建一个基于对话框的应用程序SingleThread,在主对话框IDD_SINGLETHREAD_DIALOG添加一个按钮,ID为IDC_SLEEP_SIX_SECOND,标题为“延时6秒”,添加按钮的响应函数,代码如下:void CSingleThreadDlg::OnSleepSixSecond(){Sleep(6000); //延时6秒}  编译并运行应用程序,单击“延时6秒”按钮,你就会发现在这6秒期间程序就象“死机”一样,不在响应其它消息。为了更好地处理这种耗时的操作,我们有必要学习——多线程编程。二、多线程概述  进程和线程都是操作系统的概念。进程是应用程序的执行实例,每个进程是由私有的虚拟地址空间、代码、数据和其它各种系统资源组成,进程在运行过程中创建的资源随着进程的终止而被销毁,所使用的系统资源在进程终止时被释放或关闭。  线程是进程内部的一个执行单元。系统创建好进程后,实际上就启动执行了该进程的主执行线程,主执行线程以函数地址形式,比如说main或WinMain函数,将程序的启动点提供给Windows系统。主执行线程终止了,进程也就随之终止。  每一个进程至少有一个主执行线程,它无需由用户去主动创建,是由系统自动创建的。用户根据需要在应用程序中创建其它线程,多个线程并发地运行于同一个进程中。一个进程中的所有线程都在该进程的虚拟地址空间中,共同使用这些虚拟地址空间、全局变量和系统资源,所以线程间的通讯非常方便,多线程技术的应用也较为广泛。  多线程可以实现并行处理,避免了某项任务长时间占用CPU时间。要说明的一点是,目前大多数的计算机都是单处理器(CPU)的,为了运行所有这些线程,操作系统为每个独立线程安排一些CPU时间,操作系统以轮换方式向线程提供时间片,这就给人一种假象,好象这些线程都在同时运行。由此可见,如果两个非常活跃的线程为了抢夺对CPU的控制权,在线程切换时会消耗很多的CPU资源,反而会降低系统的性能。这一点在多线程编程时应该注意。  Win32 SDK函数支持进行多线程的程序设计,并提供了操作系统原理中的各种同步、互斥和临界区等操作。Visual C++6.0中,使用MFC类库也实现了多线程的程序设计,使得多线程编程更加方便。三、Win32 API对多线程编程的支持  Win32 提供了一系列的API函数来完成线程的创建、挂起、恢复、终结以及通信等工作。下面将选取其中的一些重要函数进行说明。1、HANDLE CreateThread(LPSECURITY_ATTRIBUTES lpThreadAttributes,DWORD dwStackSize,LPTHREAD_START_ROUTINE lpStartAddress,LPVOID lpParameter,DWORD dwCreationFlags,LPDWORD lpThreadId);该函数在其调用进程的进程空间里创建一个新的线程,并返回已建线程的句柄,其中各参数说明如下:lpThreadAttributes:指向一个 SECURITY_ATTRIBUTES 结构的指针,该结构决定了线程的安全属性,一般置为 NULL;dwStackSize:指定了线程的堆栈深度,一般都设置为0;lpStartAddress:表示新线程开始执行时代码所在函数的地址,即线程的起始地址。一般情况为(LPTHREAD_START_ROUTINE)ThreadFunc,ThreadFunc是线程函数名;lpParameter:指定了线程执行时传送给线程的32位参数,即线程函数的参数;dwCreationFlags:控制线程创建的附加标志,可以取两种值。如果该参数为0,线程在被创建后就会立即开始执行;如果该参数为CREATE_SUSPENDED,则系统产生线程后,该线程处于挂起状态,并不马上执行,直至函数ResumeThread被调用;lpThreadId:该参数返回所创建线程的ID;如果创建成功则返回线程的句柄,否则返回NULL。2、DWORD SuspendThread(HANDLE hThread);该函数用于挂起指定的线程,如果函数执行成功,则线程的执行被终止。 3、DWORD ResumeThread(HANDLE hThread);该函数用于结束线程的挂起状态,执行线程。 4、VOID ExitThread(DWORD dwExitCode);该函数用于线程终结自身的执行,主要在线程的执行函数中被调用。其中参数dwExitCode用来设置线程的退出码。 5、BOOL TerminateThread(HANDLE hThread,DWORD dwExitCode);  一般情况下,线程运行结束之后,线程函数正常返回,但是应用程序可以调用TerminateThread强行终止某一线程的执行。各参数含义如下:hThread:将被终结的线程的句柄;dwExitCode:用于指定线程的退出码。  使用TerminateThread()终止某个线程的执行是不安全的,可能会引起系统不稳定;虽然该函数立即终止线程的执行,但并不释放线程所占用的资源。因此,一般不建议使用该函数。6、BOOL PostThreadMessage(DWORD idThread,UINT Msg,WPARAM wParam,LPARAM lParam);该函数将一条消息放入到指定线程的消息队列中,并且不等到消息被该线程处理时便返回。idThread:将接收消息的线程的ID;Msg:指定用来发送的消息;wParam:同消息有关的字参数;lParam:同消息有关的长参数;调用该函数时,如果即将接收消息的线程没有创建消息循环,则该函数执行失败。四、Win32 API多线程编程例程例程1 MultiThread1建立一个基于对话框的工程MultiThread1,在对话框IDD_MULTITHREAD1_DIALOG中加入两个按钮和一个框,两个按钮的ID分别是IDC_START,IDC_STOP,标题分别为“启动”,“停止”,IDC_STOP的属性选中Disabled;框的ID为IDC_TIME ,属性选中Read-only; 在MultiThread1Dlg.h文件中添加线程函数声明: void ThreadFunc();注意,线程函数的声明应在类CMultiThread1Dlg的外部。在类CMultiThread1Dlg内部添加protected型变量: HANDLEhThread;DWORD ThreadID;分别代表线程的句柄和ID。 在MultiThread1Dlg.cpp文件中添加全局变量m_bRun : volatile BOOL m_bRun;m_bRun 代表线程是否正在运行。你要留意到全局变量 m_bRun 是使用 volatile 修饰符的,volatile修饰符的作用是告诉编译器无需对该变量作任何的优化,即无需将它放到一个寄存器中,并且该值可被外部改变。对于多线程引用的全局变量来说,volatile是一个非常重要的修饰符。编写线程函数: void ThreadFunc(){CTime time;CString strTime;m_bRun=TRUE;while(m_bRun){time=CTime::GetCurrentTime();strTime=time.Format("%H:%M:%S");::SetDlgItemText(AfxGetMainWnd()-》m_hWnd,IDC_TIME,strTime);Sleep(1000);}}该线程函数没有参数,也不返回函数值。只要m_bRun为TRUE,线程一直运行。双击IDC_START按钮,完成该按钮的消息函数: void CMultiThread1Dlg::OnStart(){// TODO: Add your control notification handler code herehThread=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)ThreadFunc,NULL,0,&ThreadID);GetDlgItem(IDC_START)-》EnableWindow(FALSE);GetDlgItem(IDC_STOP)-》EnableWindow(TRUE);}双击IDC_STOP按钮,完成该按钮的消息函数: void CMultiThread1Dlg::OnStop(){// TODO: Add your control notification handler code herem_bRun=FALSE;GetDlgItem(IDC_START)-》EnableWindow(TRUE);GetDlgItem(IDC_STOP)-》EnableWindow(FALSE);}编译并运行该例程,体会使用Win32 API编写的多线程。例程2 MultiThread2  该线程演示了如何传送一个一个整型的参数到一个线程中,以及如何等待一个线程完成处理。建立一个基于对话框的工程MultiThread2,在对话框IDD_MULTITHREAD2_DIALOG中加入一个框和一个按钮,ID分别是IDC_COUNT,IDC_START,按钮控件的标题为“开始”;在MultiThread2Dlg.h文件中添加线程函数声明: void ThreadFunc(int integer);注意,线程函数的声明应在类CMultiThread2Dlg的外部。在类CMultiThread2Dlg内部添加protected型变量: HANDLE hThread;DWORD ThreadID;分别代表线程的句柄和ID。 打开ClassWizard,为框IDC_COUNT添加int型变量m_nCount。在MultiThread2Dlg.cpp文件中添加:voidThreadFunc(int integer){int i;for(i=0;i《integer;i++){Beep(200,50);Sleep(1000);}}双击IDC_START按钮,完成该按钮的消息函数: void CMultiThread2Dlg::OnStart(){UpdateData(TRUE);int integer=m_nCount;hThread=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)ThreadFunc,(VOID*)integer,0,&ThreadID);GetDlgItem(IDC_START)-》EnableWindow(FALSE);WaitForSingleObject(hThread,INFINITE);GetDlgItem(IDC_START)-》EnableWindow(TRUE);}顺便说一下WaitForSingleObject函数,其函数原型为:DWORD WaitForSingleObject(HANDLE hHandle,DWORDdwMilliseconds);hHandle为要监视的对象(一般为同步对象,也可以是线程)的句柄;dwMilliseconds为hHandle对象所设置的超时值,单位为毫秒;  当在某一线程中调用该函数时,线程暂时挂起,系统监视hHandle所指向的对象的状态。如果在挂起的dwMilliseconds毫秒内,线程所等待的对象变为有信号状态,则该函数立即返回;如果超时时间已经到达dwMilliseconds毫秒,但hHandle所指向的对象还没有变成有信号状态,函数照样返回。参数dwMilliseconds有两个具有特殊意义的值:0和INFINITE。若为0,则该函数立即返回;若为INFINITE,则线程一直被挂起,直到hHandle所指向的对象变为有信号状态时为止。  本例程调用该函数的作用是按下IDC_START按钮后,一直等到线程返回,再恢复IDC_START按钮正常状态。编译运行该例程并细心体会。例程3 MultiThread3传送一个结构体给一个线程函数也是可能的,可以通过传送一个指向结构体的指针参数来完成。先定义一个结构体:typedef struct{int firstArgu,long secondArgu,…}myType,*pMyType;创建线程时CreateThread(NULL,0,threadFunc,pMyType,…);在threadFunc函数内部,可以使用“强制转换”:int intValue=((pMyType)lpvoid)-》firstArgu;long longValue=((pMyType)lpvoid)-》seconddArgu;……例程3 MultiThread3将演示如何传送一个指向结构体的指针参数。建立一个基于对话框的工程MultiThread3,在对话框IDD_MULTITHREAD3_DIALOG中加入一个框IDC_MILLISECOND,一个按钮IDC_START,标题为“开始”,一个进度条IDC_PROGRESS1;打开ClassWizard,为框IDC_MILLISECOND添加int型变量m_nMilliSecond,为进度条IDC_PROGRESS1添加CProgressCtrl型变量m_ctrlProgress;在MultiThread3Dlg.h文件中添加一个结构的定义: struct threadInfo{UINT nMilliSecond;CProgressCtrl* pctrlProgress;};线程函数的声明: UINT ThreadFunc(LPVOID lpParam);注意,二者应在类CMultiThread3Dlg的外部。在类CMultiThread3Dlg内部添加protected型变量: HANDLE hThread;DWORD ThreadID;分别代表线程的句柄和ID。在MultiThread3Dlg.cpp文件中进行如下操作:定义公共变量 threadInfo Info;双击按钮IDC_START,添加相应消息处理函数:void CMultiThread3Dlg::OnStart(){// TODO: Add your control notification handler code hereUpdateData(TRUE);Info.nMilliSecond=m_nMilliSecond;Info.pctrlProgress=&m_ctrlProgress;hThread=CreateThread(NULL,0,(LPTHREAD_START_ROUTINE)ThreadFunc,&Info,0,&ThreadID);}在函数BOOL CMultiThread3Dlg::OnInitDialog()中添加语句: {……// TODO: Add extra initialization herem_ctrlProgress.SetRange(0,99);m_nMilliSecond=10;UpdateData(FALSE);return TRUE; // return TRUE unless you set the focus to a control}添加线程处理函数:UINT ThreadFunc(LPVOID lpParam) {threadInfo* pInfo=(threadInfo*)lpParam;for(int i=0;i《100;i++){int nTemp=pInfo-》nMilliSecond;pInfo-》pctrlProgress-》SetPos(i);Sleep(nTemp);}return 0;}  顺便补充一点,如果你在void CMultiThread3Dlg::OnStart() 函数中添加语句,编译运行你就会发现进度条不进行刷新,主线程也停止了反应。什么原因呢?这是因为WaitForSingleObject函数等待子线程(ThreadFunc)结束时,导致了线程死锁。因为WaitForSingleObject函数会将主线程挂起(任何消息都得不到处理),而子线程ThreadFunc正在设置进度条,一直在等待主线程将刷新消息处理完毕返回才会检测通知事件。这样两个线程都在互相等待,死锁发生了,编程时应注意避免。例程4 MultiThread4该例程测试在Windows下最多可创建线程的数目。建立一个基于对话框的工程MultiThread4,在对话框IDD_MULTITHREAD4_DIALOG中加入一个按钮IDC_TEST和一个框IDC_COUNT,按钮标题为“测试”, 框属性选中Read-only;在MultiThread4Dlg.cpp文件中进行如下操作:添加公共变量volatile BOOL m_bRunFlag=TRUE;该变量表示是否还能继续创建线程。添加线程函数:DWORD WINAPI threadFunc(LPVOID threadNum){while(m_bRunFlag){Sleep(3000);}return 0;}只要 m_bRunFlag 变量为TRUE,线程一直运行。双击按钮IDC_TEST,添加其响应消息函数:void CMultiThread4Dlg::OnTest(){DWORD threadID;GetDlgItem(IDC_TEST)-》EnableWindow(FALSE);long nCount=0;while(m_bRunFlag){if(CreateThread(NULL,0,threadFunc,NULL,0,&threadID)==NULL){m_bRunFlag=FALSE;break;}else{nCount++;}}//不断创建线程,直到再不能创建为止m_nCount=nCount;UpdateData(FALSE);Sleep(5000);//延时5秒,等待所有创建的线程结束GetDlgItem(IDC_TEST)-》EnableWindow(TRUE);m_bRunFlag=TRUE;}五、MFC对多线程编程的支持  MFC中有两类线程,分别称之为工作者线程和用户界面线程。二者的主要区别在于工作者线程没有消息循环,而用户界面线程有自己的消息队列和消息循环。  工作者线程没有消息机制,通常用来执行后台计算和维护任务,如冗长的计算过程,打印机的后台打印等。用户界面线程一般用于处理独立于其他线程执行之外的用户输入,响应用户及系统所产生的事件和消息等。但对于Win32的API编程而言,这两种线程是没有区别的,它们都只需线程的启动地址即可启动线程来执行任务。  在MFC中,一般用全局函数AfxBeginThread()来创建并初始化一个线程的运行,该函数有两种重载形式,分别用于创建工作者线程和用户界面线程。两种重载函数原型和参数分别说明如下:(1) CWinThread* AfxBeginThread(AFX_THREADPROC pfnThreadProc,LPVOID pParam,nPriority=THREAD_PRIORITY_NORMAL,UINT nStackSize=0,DWORD dwCreateFlags=0,LPSECURITY_ATTRIBUTES lpSecurityAttrs=NULL);PfnThreadProc:指向工作者线程的执行函数的指针,线程函数原型必须声明如下: UINT ExecutingFunction(LPVOIDpParam);请注意,ExecutingFunction()应返回一个UINT类型的值,用以指明该函数结束的原因。一般情况下,返回0表明执行成功。pParam:传递给线程函数的一个32位参数,执行函数将用某种方式解释该值。它可以是数值,或是指向一个结构的指针,甚至可以被忽略;nPriority:线程的优先级。如果为0,则线程与其父线程具有相同的优先级;nStackSize:线程为自己分配堆栈的大小,其单位为字节。如果nStackSize被设为0,则线程的堆栈被设置成与父线程堆栈相同大小;dwCreateFlags:如果为0,则线程在创建后立刻开始执行。如果为CREATE_SUSPEND,则线程在创建后立刻被挂起;lpSecurityAttrs:线程的安全属性指针,一般为NULL;(2) CWinThread* AfxBeginThread(CRuntimeClass* pThreadClass,int nPriority=THREAD_PRIORITY_NORMAL,UINT nStackSize=0,DWORD dwCreateFlags=0,LPSECURITY_ATTRIBUTES lpSecurityAttrs=NULL);  pThreadClass 是指向 CWinThread的一个导出类的运行时类对象的指针,该导出类定义了被创建的用户界面线程的启动、退出等;其它参数的意义同形式1。使用函数的这个原型生成的线程也有消息机制,在以后的例子中我们将发现同主线程的机制几乎一样。下面我们对CWinThread类的数据成员及常用函数进行简要说明。m_hThread:当前线程的句柄;m_nThreadID:当前线程的ID;m_pMainWnd:指向应用程序主窗口的指针BOOL CWinThread::CreateThread(DWORD dwCreateFlags=0,UINT nStackSize=0,LPSECURITY_ATTRIBUTES lpSecurityAttrs=NULL);  该函数中的dwCreateFlags、nStackSize、lpSecurityAttrs参数和API函数CreateThread中的对应参数有相同含义,该函数执行成功,返回非0值,否则返回0。  一般情况下,调用AfxBeginThread()来一次性地创建并启动一个线程,但是也可以通过两步法来创建线程:首先创建CWinThread类的一个对象,然后调用该对象的成员函数CreateThread()来启动该线程。virtual BOOL CWinThread::InitInstance();  重载该函数以控制用户界面线程实例的初始化。初始化成功则返回非0值,否则返回0。用户界面线程经常重载该函数,工作者线程一般不使用InitInstance()。virtual int CWinThread::ExitInstance();  在线程终结前重载该函数进行一些必要的清理工作。该函数返回线程的退出码,0表示执行成功,非0值用来标识各种错误。同InitInstance()成员函数一样,该函数也只适用于用户界面线程。六、MFC多线程编程实例  在Visual C++6.0编程环境中,我们既可以编写C风格的32位Win32应用程序,也可以利用MFC类库编写C++风格的应用程序,二者各有其优缺点。基于Win32的应用程序执行代码小巧,运行效率高,但要求程序员编写的代码较多,且需要管理系统提供给程序的所有资源;而基于MFC类库的应用程序可以快速建立起应用程序,类库为程序员提供了大量的封装类,而且DeveloperStudio为程序员提供了一些工具来管理用户源程序,其缺点是类库代码很庞大。由于使用类库所带来的快速、简捷和功能强大等优越性,因此除非有特殊的需要,否则VisualC++推荐使用MFC类库进行程序开发。我们知道,MFC中的线程分为两种:用户界面线程和工作者线程。我们将分别举例说明。用 MFC 类库编程实现工作者线程

求用C++MFC编写的打砖块的编程最简单的那种,打到砖块消失,小球弹回打到挡板上弹回谢谢

C++实例编程:简单坦克大战2010-11-2212:40:22 作者:佚名 来源:IT哇咔搜集整理 我要评论 进入论坛 字号:T|T  核心提示:  因为有些东西以前练过了,而有些东西没练过,还有很多不足之处.#include#include#include#include#include#defineKEY_ESC0x01#defineKEY_SPACE0x39#defineKEY_UP0x48#defineKEY_LEFT0x4b#defineKEY_RIGHT0x4d#defineKEY_DOWN0x50/*1石头,2砖块,3水,5老家,8玩家,9敌人*/intmap.directiontwo=3;/*第一个敌人*/--

MFC基于对话框的编程中有两个对话框dlg1和dlg2,通过dlg1上的一个button来打开dlg2

你把dlg2设计成一个类,然后通过dlg1的按钮来实现初始化dlg2,基本操作如下:(我之前做的,部分截取的代码,)CLoginDlg loginDlg;//实例化一个类;loginDlg.acceptType(LoginType);//我设计的类可以接受一个参数,然后再决定初始化界面效果,所以要是没有什么参数需要传递的话,可以不用这句。loginDlg.DoModal();//差不多就是交给系统去显示。至于范围的话,需要先记录onMouseClick的point,然后通过onMouseMove的即时坐标点来判断框是否出界;出界后强制赋值就好了。。。

MFC对话框编程问题

一.模态对话框和非模态对话框 Windows对话框分为两类:模态对话框和非模态对话框。 模态对话框是这样的对话框,当它弹出后,本应用程序其他窗口将不再接受用户输入,只有该对话框响应用户输入,在对它进行相应操作退出后,其他窗口才能继续与用户交互。 非模态对话框则是,它弹出后,本程序其他窗口仍能响应用户输入。非模态对话框一般用来显示提示信息等。 大家对Windows系统很了解,相信这两种对话框应该都遇到过。之前的加法计算器对话框其实就是模态对话框。 二.模态对话框是怎样弹出的 毕竟加法计算器程序大部分都是MFC自动生成的,对话框怎么弹出来的大家可能还不是很清楚。鸡啄米下面简单说说它是在哪里弹出来的,再重新建一个新的对话框并弹出它,这样大家实践以后就能更灵活的使用模态对话框了。 大家打开Addition.cpp文件,可以看到CAdditionApp类有个InitInstance()函数,在MFC应用程序框架分析中提到过此函数,不过那是单文档应用程序App类中的,函数体不太相同,但都是进行App类实例的初始化工作。 InitInstance()函数的后半部分有一段代码就是定义对话框对象并弹出对话框的,鸡啄米下面给出这段代码并加以注释:C++代码CAdditionDlg dlg; // 定义对话框类CAdditionDlg的对象dlg m_pMainWnd = &dlg // 将dlg设为主窗口 INT_PTR nResponse = dlg.DoModal(); // 弹出对话框dlg,并将DoModal函数的返回值(退出时点击按钮的ID)赋值给nResponse if (nResponse == IDOK) // 判断返回值是否为OK按钮(其ID为IDOK,鸡啄米已经将它删除) { // TODO: Place code here to handle when the dialog is // dismissed with OK } else if (nResponse == IDCANCEL) // 判断返回值是否为Cancel按钮(其ID为IDCANCEL,鸡啄米将它的Caption改为了逗退出地) { // TODO: Place code here to handle when the dialog is // dismissed with Cancel } 弹出对话框比较关键的一个函数,就是对话框类的DoModal()函数。CDialog::DoModal()函数的原型为: virtual INT_PTR DoModal();    返回值:整数值,指定了传递给CDialog::EndDialog(该函数用于关闭对话框)的nResult参数值。如果函数不能创建对话框,则返回-1;如果出现其它错误,则返回IDABORT。 调用了它对话框就会弹出,返回值是退出对话框时所点的按钮的ID,比如,我们点了逗退出地按钮,那么DoModal返回值为IDCANCEL。 三.添加一个新对话框并弹出它 鸡啄米再为加法计算器程序添加一个对话框,以在计算之前询问用户是否确定要进行计算。大家可以完整的看下对话框的添加和弹出过程。 1.根据逗创建对话框模板和修改对话框属性地中所讲的方法,在Resource View中的逗Dialog地上点右键选择逗Insert Dialog地,创建一个新的对话框模板,修改其ID为IDD_TIP_DIALOG,Caption改为逗提示地,然后参考逗为对话框添加控件地中所讲,在对话框模板上添加一个静态文本框(static text),Caption改为逗您确定要进行加法计算吗看地,接下来修改OK按钮的Caption为逗确定地,Cancel按钮的Caption为逗取消地,最后调整各个控件的位置和对话框的大小。最终的对话框模板如下图: 2.根据逗创建对话框类和添加控件变量地中创建对话框类的方法,在对话框模板上点右键选择逗Add Class...地,弹出添加类的对话框,设置逗Class name地为CTipDlg,点逗OK地。在Solution Explorer中可以看到生成了CTipDlg类的头文件TipDlg.h和源文件TipDlg.cpp。 3.我们要在点逗计算地按钮之后弹出此提示对话框,那么就要在逗计算地按钮的消息处理函数OnBnClickedAddButton()中访问提示对话框类,所以为了访问CTipDlg类,在AdditionDlg.cpp中包含CTipDlg的头文件:#include "TipDlg.h"。 4.修改OnBnClickedAddButton()的函数体,在所有代码前,构造CTipDlg类的对象tipDlg,并通过语句tipDlg.DoModal();弹出对话框,最后判断DoModal()函数的返回值是IDOK还是IDCANCEL来确定是否继续进行计算。OnBnClickedAddButton()函数修改后如下:C++代码void CAdditionDlg::OnBnClickedAddButton() { // TODO: Add your control notification handler code here INT_PTR nRes; // 用于保存DoModal函数的返回值 CTipDlg tipDlg; // 构造对话框类CTipDlg的实例 nRes = tipDlg.DoModal(); // 弹出对话框 if (IDCANCEL == nRes) // 判断对话框退出后返回值是否为IDCANCEL,如果是则return,否则继续向下执行 return; // 将各控件中的数据保存到相应的变量 UpdateData(TRUE); // 将被加数和加数的加和赋值给m_editSum m_editSum = m_editSummand + m_editAddend; // 根据各变量的值更新相应的控件。和的框会显示m_editSum的值 UpdateData(FALSE); } 5.测试。编译运行程序后,在对话框上输入被加数和加数,点逗计算地,弹出提示对话框询问是否进行计算,如果选择逗确定地,则提示对话框退出,并在主对话框上显示被加数和加数的和,而如果选择逗取消地,则提示对话框也会退出,但主对话框显示的和不变,即没有进行加法计算。

mfc编程实例讲解(求MFC编程实例,比如如何让两个数相加,然后输出结果由于对MFC毫无了解,请写得详细些)

本文编辑:admin

更多文章:


repercussions(repercussion是什么意思)

repercussions(repercussion是什么意思)

本文目录repercussion是什么意思都是余波,repercussions和aftermath有什么区别啊repercussion是什么意思repercussion英 n.弹回,返回; 反响,影响; (光、声等的)反射; 浮动诊胎法回声

2024年6月21日 07:39

zarchiver解压(zarchiver怎么解压腾讯微云的文件)

zarchiver解压(zarchiver怎么解压腾讯微云的文件)

本文目录zarchiver怎么解压腾讯微云的文件如何使用ZArchiver对压缩文件进行处理zarchiver怎么解压腾讯微云的文件1、打开ZArchiver这个APP。2、点击APP顶部的菜单,根据文件的路径,找到文件所在的文件夹,选择需

2024年7月21日 06:23

sql查询成绩大于90分的人数(sql语句查询,并统计查询结果数量)

sql查询成绩大于90分的人数(sql语句查询,并统计查询结果数量)

本文目录sql语句查询,并统计查询结果数量sqlserver 2005如何某门课程查询大于90分以上的人数占总中人数的比例SQL查询个人最高成绩大于90或者最低成绩小于60的的人sql 中求各科成绩都大于90的学生姓名sql查询成绩大于90

2024年7月22日 11:34

net user更改管理员密码(怎么修改电脑管理员密码)

net user更改管理员密码(怎么修改电脑管理员密码)

本文目录怎么修改电脑管理员密码在不知道密码的情况下,如何修改电脑管理员密码user可以通过cmd更改administrator的密码吗win10怎么修改administrator管理员账户密码怎么修改管理员密码Windows如何修改Admi

2024年7月3日 20:13

c++计算机二级考试(计算机二级C++考什么 考试基本要求)

c++计算机二级考试(计算机二级C++考什么 考试基本要求)

本文目录计算机二级C++考什么 考试基本要求全国计算机二级C++考试知识点C++二级考什么考二级c++有必要吗计算机等级考试二级C++各章内容摘要2计算机二级C++考什么 考试基本要求 C++是一种使用非常广泛的计算机编程语言。C++是一种

2024年7月2日 19:02

craven(craven反应)

craven(craven反应)

本文目录craven反应craven“a“是啥牌烟craven是什么香烟craven反应Kesting-Craven反应: 当苯醌及萘醌类化合物的醌环上有未被取代的位置时,在碱性条件下与含活性次甲基试剂,如乙酰乙酸酯、丙二酸酯反应,呈蓝绿色

2024年7月19日 03:16

ashamed和shameful区别(ashamed与shameful区别)

ashamed和shameful区别(ashamed与shameful区别)

本文目录ashamed与shameful区别ashamed和shameful的区别Shame ashame shameful的不同shamful 和ashamed 的用法ashamed与shameful区别ashamed与shameful的

2023年6月27日 16:40

jquery分页渲染(js大数据量如何实现页面的局部渲染(不是局部刷新)--解决方法)

jquery分页渲染(js大数据量如何实现页面的局部渲染(不是局部刷新)--解决方法)

本文目录js大数据量如何实现页面的局部渲染(不是局部刷新)--解决方法怎样给Jquery动态添加的标签添加或渲染Jquery方法jquery.mobile对ul列表的样式渲染关于jquery的分页jqgridjs大数据量如何实现页面的局部渲

2024年6月26日 19:13

微信登录界面背景图(微信首页怎么换背景图)

微信登录界面背景图(微信首页怎么换背景图)

大家好,微信登录界面背景图相信很多的网友都不是很明白,包括微信首页怎么换背景图也是一样,不过没有关系,接下来就来为大家分享关于微信登录界面背景图和微信首页怎么换背景图的一些知识点,大家可以关注收藏,免得下次来找不到哦,下面我们开始吧!本文目

2024年8月19日 01:10

安踏kt7打完球脚腕会不舒服吗?安踏kt7外穿怎么样

安踏kt7打完球脚腕会不舒服吗?安踏kt7外穿怎么样

大家好,安踏kt7相信很多的网友都不是很明白,包括安踏kt7打完球脚腕会不舒服吗也是一样,不过没有关系,接下来就来为大家分享关于安踏kt7和安踏kt7打完球脚腕会不舒服吗的一些知识点,大家可以关注收藏,免得下次来找不到哦,下面我们开始吧!本

2024年8月17日 20:40

plot函数(matlab中plot函数有几种格式)

plot函数(matlab中plot函数有几种格式)

本文目录matlab中plot函数有几种格式matlab中plot函数用法MATLAB中plot函数怎么用MATLAB中plot函数和line函数作用有区别吗matlab中plot函数一共能调用多少种颜色matlab中plot函数全部功能怎

2024年7月13日 09:22

google chrome兼容性设置(谷歌浏览器兼容性视图设置在哪里)

google chrome兼容性设置(谷歌浏览器兼容性视图设置在哪里)

大家好,google chrome兼容性设置相信很多的网友都不是很明白,包括谷歌浏览器兼容性视图设置在哪里也是一样,不过没有关系,接下来就来为大家分享关于google chrome兼容性设置和谷歌浏览器兼容性视图设置在哪里的一些知识点,大家

2024年8月27日 17:55

london是什么意思(London是什么意思)

london是什么意思(London是什么意思)

本文目录London是什么意思london是什么牌子London是什么意思英 伦敦(英国首都,政治、经济、文化、交通中心,位于英格兰东南部)=London, City of=London, County of=Greater London伦

2024年7月7日 20:04

shell脚本编写(Linux的shell脚本用文本编写好后为什么要重命名)

shell脚本编写(Linux的shell脚本用文本编写好后为什么要重命名)

本文目录Linux的shell脚本用文本编写好后为什么要重命名如何编写无须人工干预的shell脚本刚想写shell脚本,不知道什么开发工具顺手请问Shell脚本编程是通过什么软件编写的吗如何编写shell脚本linux下如何编写shell脚

2024年7月2日 06:50

format factory portable(Portable Document Format是什么意思)

format factory portable(Portable Document Format是什么意思)

各位老铁们好,相信很多人对format factory portable都不是特别的了解,因此呢,今天就来为大家分享下关于format factory portable以及Portable Document Format是什么意思的问题知识

2024年8月28日 02:41

drop table时restrict和cascade的区别(说明在drop table 时,resirict 和cascade 的区别)

drop table时restrict和cascade的区别(说明在drop table 时,resirict 和cascade 的区别)

本文目录说明在drop table 时,resirict 和cascade 的区别cascade默认是什么参照完整性约束,RESTRICT和NO ACTION有什么区别数据库中restrict和casecade是什么意思说明在drop ta

2024年5月23日 16:03

影视特效制作教程(电影制作特效都有哪些步骤)

影视特效制作教程(电影制作特效都有哪些步骤)

本文目录电影制作特效都有哪些步骤我想学影视特效制作影视特效制作从何学起电影特效怎么制作影视后期制作特效制作如何进行如何实现影视特效制作影视制作后期特效都有哪些步骤怎么学习影视特效我想学习影视后期和特效制作,请问要学些什么电影特效想学影视特效

2024年7月21日 22:53

cluster集群服务器(使用Powershell配置Windows Failover Cluster群集)

cluster集群服务器(使用Powershell配置Windows Failover Cluster群集)

本文目录使用Powershell配置Windows Failover Cluster群集集群的好处集群的单词集群的单词是什么Redis-Cluster高可用集群与负载均衡集群集群技术是什么Centos7.x Redis6.2.5 Clust

2024年7月13日 10:54

capacity in which acting是什么意思(acting是什么意思)

capacity in which acting是什么意思(acting是什么意思)

本文目录acting是什么意思acting中文意思是什么Acting是什么意思acting是什么意思acting的意思是演戏。n:表演;adj:代理的;原形:act;反义词:refrain。同根词:词根:act。1、actable:adj:

2024年7月19日 12:07

合法转义字符(C语言中如何判断是不是合法转义字符)

合法转义字符(C语言中如何判断是不是合法转义字符)

大家好,关于合法转义字符很多朋友都还不太明白,不过没关系,因为今天小编就来为大家分享关于C语言中如何判断是不是合法转义字符的知识点,相信应该可以解决大家的一些困惑和问题,如果碰巧可以解决您的问题,还望关注下本站哦,希望对各位有所帮助!本文目

2024年7月19日 11:10

近期文章

本站热文

iphone vpn设置(ios设置vpn快捷开关)
2024-07-22 15:01:12 浏览:2334
windows12正式版下载(操作系统Windows Server 2012 R2,在哪能下载到,公司用的)
2024-07-20 17:26:53 浏览:1730
java安装教程(win10如何安装JAVA)
2024-07-19 19:55:49 浏览:1155
client mfc application未响应(每次进cf就提示client MFC Application未响应该怎么办啊!急急急)
2024-07-20 11:15:58 浏览:1152
标签列表

热门搜索