MFC – 控制管理
MFC – 控制管理
在 MFC 应用程序中,在将控件可视化地添加到应用程序后,如果您想在代码中引用它,您可以声明一个基于该控件或与该控件关联的变量。MFC 库允许您为应用程序中使用的某些控件声明两种类型的变量,即值或控件变量。
-
一个变量用于存储在控件中的信息,也称为Control Variable/Instance。
-
另一个变量称为控制值变量。用户可以使用此变量对该控件执行某种操作。
控制变量/实例
控制变量是基于管理控件的类的变量。例如,按钮控件基于 CButton 类。
为了在实际编程中看到这些概念,让我们创建一个基于 MFC 对话框的项目 MFCControlManagement。

创建项目后,您将在设计器窗口中看到以下对话框。

步骤 1 – 删除 TODO 行并拖动一个复选框和一个编辑控件,如下面的快照所示。将复选框的标题更改为启用控制。

步骤 2 – 右键单击复选框。

步骤 3 – 选择添加变量。
第 4 步– 您现在可以看到添加成员变量向导。

您可以在此对话框中选择不同的选项。对于复选框,变量类型是 CButton。在此对话框中默认选中它。
同样,控件ID也是默认选中的,现在我们需要在Category组合框中选择Control,在Variable Name编辑框中输入m_enableDisableCheck,点击finish。
步骤 5 – 同样,添加编辑控件的控制变量,其设置如下面的快照所示。

观察对话框类的头文件。您可以看到现在已经添加了新变量。
CButton m_enableDisableCheck; CEdit m_myEditControl;
控制值变量
您可以为控件声明的另一种类型的变量是值变量。并非所有控件都提供值变量。
-
值变量必须能够处理存储在它要引用的控件中的值的类型。
-
例如,因为基于文本的控件用于处理文本,您可以为其声明基于文本的数据类型。这通常是一个 CString 变量。
让我们看看复选框和编辑控件的这种类型的变量。
步骤 1 – 右键单击复选框并选择添加变量。

步骤 2 – 变量类型是 BOOL。从类别下拉列表中选择值。
步骤 3 – 单击完成继续。
步骤 4 – 同样,使用以下快照所示的设置为编辑控件添加值变量。

第 5 步– 在变量类型中键入 CString,在变量名字段中键入 m_editControlVal。
步骤 6 – 您现在可以在头文件中看到这些变量。
bool m_enableDisableVal; CString m_editControlVal;
控制事件处理程序
将控件添加到应用程序后,无论是直观地添加它还是动态创建它,您还将决定如何处理用户可以在控件上执行的可能操作。
-
对于已经与类关联的项目对话框,您可以在创建事件处理程序时利用一些快捷方式。
-
您可以为默认控件通知事件或任何适用的 Windows 消息快速创建处理程序。
让我们看一下为复选框添加事件处理程序的相同示例。
步骤 1 – 右键单击要处理通知事件的控件。

步骤 2 – 在快捷菜单上,单击添加事件处理程序以显示事件处理程序向导。

步骤 3 – 在消息类型框中选择事件以添加到在类列表框中选择的类。
步骤 4 – 在函数处理程序名称框中接受默认名称,或提供您选择的名称。
步骤 5 – 单击添加并编辑以添加事件处理程序。
第 6 步– 您现在可以看到在 CMFCControlManagementDlg.cpp 文件末尾添加了以下事件。
void CMFCControlManagementDlg::OnBnClickedCheck1() {
// TODO: Add your control notification handler code here
}
控制管理
到目前为止,我们已经看到了如何向应用程序添加控件。我们现在将看到如何根据用户要求管理这些控件。我们可以在特定的事件处理程序中使用控制变量/实例。
步骤 1 – 让我们看看下面的例子。在这里,我们将在选中/取消选中复选框时启用/禁用编辑控件。
第 2 步– 我们现在添加了复选框单击事件处理程序。这是实现 –
void CMFCControlManagementDlg::OnBnClickedCheck1() {
// TODO: Add your control notification handler code here
UpdateData(TRUE);
if (m_enableDisableVal)
m_myEditControl.EnableWindow(TRUE);
else
m_myEditControl.EnableWindow(FALSE);
}
第 3 步– 创建对话框时,我们需要将以下代码添加到 CMFCControlManagementDlg::OnInitDialog()。这将管理这些控件。
UpdateData(TRUE); if (m_enableDisableVal) m_myEditControl.EnableWindow(TRUE); else m_myEditControl.EnableWindow(FALSE);
第 4 步– 这是 CMFCControlManagementDlg.cpp 文件的完整实现。
// MFCControlManagementDlg.cpp : implementation file
//
#include "stdafx.h"
#include "MFCControlManagement.h"
#include "MFCControlManagementDlg.h"
#include "afxdialogex.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#endif
// CAboutDlg dialog used for App About
class CAboutDlg : public CDialogEx {
public:
CAboutDlg();
// Dialog Data
#ifdef AFX_DESIGN_TIME
enum { IDD = IDD_ABOUTBOX };
#endif
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
// Implementation
protected:
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialogEx(IDD_ABOUTBOX) {
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX) {
CDialogEx::DoDataExchange(pDX);
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialogEx)
END_MESSAGE_MAP()
// CMFCControlManagementDlg dialog
CMFCControlManagementDlg::CMFCControlManagementDlg(CWnd* pParent /* = NULL*/)
:CDialogEx(IDD_MFCCONTROLMANAGEMENT_DIALOG, pParent) ,
m_enableDisableVal(FALSE) , m_editControlVal(_T("")) {
m_hIcon = AfxGetApp()→ LoadIcon(IDR_MAINFRAME);
}
void CMFCControlManagementDlg::DoDataExchange(CDataExchange* pDX) {
CDialogEx::DoDataExchange(pDX);
DDX_Control(pDX, IDC_CHECK1, m_enableDisableCheck);
DDX_Control(pDX, IDC_EDIT1, m_myEditControl);
DDX_Check(pDX, IDC_CHECK1, m_enableDisableVal);
DDX_Text(pDX, IDC_EDIT1, m_editControlVal);
}
BEGIN_MESSAGE_MAP(CMFCControlManagementDlg, CDialogEx)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(IDC_CHECK1, &CMFCControlManagementDlg::OnBnClickedCheck1)
END_MESSAGE_MAP()
// CMFCControlManagementDlg message handlers
BOOL CMFCControlManagementDlg::OnInitDialog() {
CDialogEx::OnInitDialog();
// Add "About..." menu item to system menu.
// IDM_ABOUTBOX must be in the system command range.
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL) {
BOOL bNameValid;
CString strAboutMenu;
bNameValid = strAboutMenu.LoadString(IDS_ABOUTBOX);
ASSERT(bNameValid);
if (!strAboutMenu.IsEmpty()) {
pSysMenu → AppendMenu(MF_SEPARATOR);
pSysMenu → AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
}
}
// Set the icon for this dialog. The framework does this automatically
// when the application's main window is not a dialog
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
// TODO: Add extra initialization here
UpdateData(TRUE);
if (m_enableDisableVal)
m_myEditControl.EnableWindow(TRUE);
else
m_myEditControl.EnableWindow(FALSE);
return TRUE; // return TRUE unless you set the focus to a control
}
void CMFCControlManagementDlg::OnSysCommand(UINT nID, LPARAM lParam) {
if ((nID & 0xFFF0) == IDM_ABOUTBOX) {
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}else {
CDialogEx::OnSysCommand(nID, lParam);
}
}
// If you add a minimize button to your dialog, you will need the code below
// to draw the icon. For MFC applications using the document/view model,
// this is automatically done for you by the framework.
void CMFCControlManagementDlg::OnPaint() {
if (IsIconic()) {
CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND,
reinterpret_cast<WPARAM>(dc.GetSafeHdc()), 0);
// Center icon in client rectangle
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// Draw the icon
dc.DrawIcon(x, y, m_hIcon);
}else {
CDialogEx::OnPaint();
}
}
// The system calls this function to obtain the cursor to display while the user drags
// the minimized window.
HCURSOR CMFCControlManagementDlg::OnQueryDragIcon() {
return static_cast<HCURSOR>(m_hIcon);
}
void CMFCControlManagementDlg::OnBnClickedCheck1() {
// TODO: Add your control notification handler code here
UpdateData(TRUE);
if (m_enableDisableVal)
m_myEditControl.EnableWindow(TRUE);
else
m_myEditControl.EnableWindow(FALSE);
}
Step 5 – 编译并执行上述代码后,您将看到以下输出。默认情况下未选中该复选框。这也会禁用编辑控件。

步骤 6 – 检查启用控制复选框。这将自动启用编辑控件。