在应用程序的开发中,对话框用于与用户交流互动,故对话框的操作必不可少。现将经验总结如下。
1.菜单名称的中文显示。需要在资源视图中选择相应菜单项,设置属性为中文即可。
2.创建模态对话框需要调用CDialo类的成员函数:DoModal.
CWnd::PostNcDestroy
virtual void PostNcDestroy( );
问题原因清楚了,其实就是要我们注意,在谁的堆栈上分配的内存,就在谁的堆栈上释放。
方案一:在DLL里面申请的内存,就在DLL里面释放,不要由其他模块去释放;(为了区分第二条,这个前提是exe 和 dll都使用mtd方式编译)
方案二:让所有的PE共享一个堆栈句柄,所有的模块都采用的mdd方式编译;
(上面说的是Debug选项下),原因在于,采用mdd编译时,所有的模块都会共享同一个msvcr*.dll,堆栈句柄作为静态变量保存在里面,所以所有的模块都是同一个堆栈上申请、释放内存,不管哪个模块都可以释放其他模块申请的内存了。而采用mtd编译时,所有模块都相当于有自己独立的一个mscvr*.dll(相当于把msvcr*.dll中需要的代码都打包到自己里面去了),因此每个模块在加载的时候都有自己独立的堆栈,这时去删除其他模块申请的内存,堆栈检测该指针肯定就是无效的了。
6.fatal error LNK1168.
原来是在之前的debug之后,这个进程并没有完全被终止,可以到任务管理器中查找到相应的进程(这里为OgreExample),然后结束所有的这个进程。重新debug就不再会出现这个问题了。
7. CButton类的Create()函数. BOOL Create( LPCTSTR lpszCaption, DWORD dwStyle, const RECT& rect, CWnd* pParentWnd, UINT nID );
lpszCaption是按钮上显示的文本;dwStyle指定按钮风格,可以是按钮风格与窗口风格的组合,取值有:
窗口风格:·WS_CHILD 子窗口,必须有 ·WS_VISIBLE 窗口可见,一般都有 ·WS_DISABLED 禁用窗口,创建初始状态为灰色不可用的按钮时使用
·WS_TABSTOP 可用Tab键选择 ·WS_GROUP 成组,用于成组的单选按钮中的第一个按钮
按钮风格:·BS_PUSHBUTTON 下压式按钮,也即普通按钮 ·BS_AUTORADIOBUTTON 含自动选中状态的单选按钮
·BS_RADIOBUTTON 单选按钮,不常用 ·BS_AUTOCHECKBOX 含自动选中状态的复选按钮
·BS_CHECKBOX 复选按钮,不常用 ·BS_AUTO3STATE 含自动选中状态的三态复选按钮
·BS_3STATE 三态复选按钮,不常用
以上风格指定了创建的按钮类型,不能同时使用,但必须有其一。
·BS_BITMAP 按钮上将显示位图
·BS_DEFPUSHBUTTON 设置为默认按钮,只用于下压式按钮,一个对话框中只能指定一个默认按钮
·rect指定按钮的大小和位置;
·pParentWnd指示拥有按钮的父窗口,不能为NULL;
·nID指定与按钮关联的ID号,用上一步创建的ID号。
8.MFC中的操作主要是基于类进行的,故障进行控件操作时,也要建立相应的控件类。
9.CWnd 类对象都有一个成员变量m_hWnd,用来保存与窗口对象相关联的窗口句柄。如果窗口对象没有与任何窗口相关联,则此句柄为NULL,
10.CWnd::GetDlgItem。返回窗口中指定参数ID的子元素的句柄,可以通过返回的句柄对窗口内的子元素进行操作。
typedef struct tagRECT{ LONG left; LONG top;LONG right;LONG bottom;} RECT;
其中 left、top分别表示矩形左上角顶点的横坐标和纵坐标,right、bottom分别表示矩形右下角顶点的横坐标和纵坐标。由于CRect提供了一些成员函数和重载运算符,使得CRect的操作更加方便。
操作函数
-
HWND_BOTTOM:将窗口置于Z序的底部。如果参数hWnd标识了一个顶层窗口,则窗口失去顶级位置,并且被置在其他窗口的底部。
-
HWND_NOTOPMOST:将窗口置于所有非顶层窗口之上(即在所有顶层窗口之后)。如果窗口已经是非顶层窗口则该标志不起作用。
-
HWND_TOP:将窗口置于Z序的顶部。
-
HWND_TOPMOST:将窗口置于所有非顶层窗口之上。即使窗口未被激活窗口也将保持顶级位置。
-
SWP_ ASYNCWINDOWPOS:如果调用进程不拥有窗口,系统会向拥有窗口的线程发出需求。这就防止调用线程在其他线程处理需求的时候发生死锁。
-
SWP_DEFERERASE:防止产生WM_SYNCPAINT消息。
-
SWP_DRAWFRAME:在窗口周围画一个边框(定义在 窗口类描述中)。
-
SWP_FRAMECHANGED:给窗口发送WM_NCCALCSIZE消息,即使窗口尺寸没有改变也会发送该消息。如果未指定这个标志,只有在改变了窗口尺寸时才发送WM_NCCALCSIZE。
-
SWP_HIDEWINDOW;隐藏窗口。
-
SWP_NOACTIVATE:不激活窗口。如果未设置标志,则窗口被激活,并被设置到其他最高级窗口或非最高级组的顶部(根据参数hWndlnsertAfter设置)。
-
SWP_NOCOPYBITS:清除客户区的所有内容。如果未设置该标志,客户区的有效内容被保存并且在窗口尺寸更新和重定位后拷贝回客户区。
-
SWP_NOMOVE:维持当前位置(忽略X和Y参数)。
-
SWP_NOOWNERZORDER:不改变z序中的所有者窗口的位置。
-
SWP_NOREDRAW:不重画改变的内容。如果设置了这个标志,则不发生任何重画动作。适用于客户区和非客户区(包括标题栏和滚动条)和任何由于窗回移动而露出的父窗口的所有部分。如果设置了这个标志,应用程序必须明确地使窗口无效并区重画窗口的任何部分和父窗口需要重画的部分。
-
SWP_NOREPOSITION:与SWP_NOOWNERZORDER标志相同。
-
SWP_NOSENDCHANGING:防止窗口接收WM_WINDOWPOSCHANGING消息。
-
SWP_NOSIZE:维持当前尺寸(忽略cx和Cy参数)。
-
SWP_NOZORDER:维持当前Z序(忽略hWndlnsertAfter参数)。
-
SWP_SHOWWINDOW:显示窗口。
LONGSetWindowLong(
HWND
hWnd,
//handletowindow
int
nlndex,
//offsetofvaluetoset
LONG
dwNewLong
//newvalue
);
nlndex 指定将设定的大于等于0的偏移值。有效值的范围从0到额外类的存储空间的字节数减4:例如若指定了12或多于12个字节的额外窗口存储空间,则应设索引位8来访问第三个4字节,同样设置0访问第一个4字节,4访问第二个4字节。要设置其他任何值,可以指定下面值之一:
常量
| 常量值 |
意义
|
---|---|---|
GWL_EXSTYLE
| -20 |
设定一个新的扩展风格。
|
GWL_HINSTANCE
| -6 |
设置一个新的应用程序实例句柄。
|
GWL_ID
| -12 |
设置一个新的窗口
标识符。
|
GWL_STYLE
| -16 |
设定一个新的窗口风格。
|
GWL_USERDATA
| -21 |
设置与窗口有关的32位值。每个窗口均有一个由创建该窗口的应用程序使用的32位值。
|
GWL_WNDPROC
| -4 |
为窗口过程设定一个新的地址。
|
GWL_HWNDPARENT | -8 | 改变子窗口的父窗口,应使用SetParent函数。 |
常量
| 常量值 |
意义
|
---|---|---|
DWL_DLGPROC
| DWLP_MSGRESULT + sizeof(LRESULT) (值:4) |
设置对话框过程的新地址。
|
DWL_MSGRESULT
| 0 |
设置在对话框过程中处理的消息的
返回值。
|
DWL_USER
| DWLP_DLGPROC + sizeof(DLGPROC) (值:8) |
设置的应用程序私有的新的额外信息,例如一个句柄或
指针。
|
dwNewLong 指定的替换值。
如果函数成功,返回值是指定的32位整数的原来的值。如果函数失败,返回值为0。若想获得更多错误信息,请调用GetLastError函数。如果指定32位整数的原来的值为0,并且函数成功,则返回值为0,但是函数并不清除最后的错误信息,这就很难判断函数是否成功。这时,就应在调用SetWindowLong之前调用SetLastError(0)函数来清除最后的错误信息。这样,如果函数失败就会返回0,并且GetLastError。也返回一个非零值。
LRESULT
CALLBACK WndProc(
//WndProc名称可自由定义
HWND
hwnd,
UINT
uMsg,
WPARAM
wParam,
LPARAM
lParam
);