CCustomTabCtrl - MFC 选项卡控件






4.82/5 (99投票s)
2004 年 6 月 14 日
11分钟阅读

583602

14676
一个 MFC 选项卡控件 - Excel 选项卡工作簿控件的克隆。
引言
CCustomTabCtrl
是一个派生自 CWnd
类的 MFC 控件。您可以在 Microsoft 管理控制台服务中找到类似的控件,用于在扩展视图和标准视图之间切换。CCustomTabCtrl
只能创建一种方向 - 底部。如果操作系统是 WinXP 并且启用了 XP 主题,则支持 XP 主题滚动按钮。如果应用程序运行时 XP 主题的启用状态发生更改,CCustomTabCtrl
控件也能正常工作。
在对话框应用程序中使用代码
使用 CCustomTabCtrl
类非常简单。要将其添加到项目中,请按照以下步骤操作:
- 将 ThemeUtil.h、ThemeUtil.cpp、CustomTabCtrl.h、CustomTabCtrl.cpp、Tmschema.h 和 Schemadef.h 添加到您的项目中。
- 在相应的头文件中包含 CustomTabCtrl.h - 通常是使用
CCustomTabCtrl
类的对话框类头文件。//CustomTabCtrlDemoDlg.h : header file #include "CustomTabCtrl.h"
- 在您的对话框头文件中声明类型为
CCustomTabCtrl
的m_ctrlTab
对象。//CustomTabCtrlDemoDlg.h : header file class CCustomTabCtrlDemoDlg : CDialog { ...... private: CCustomTabCtrl m_ctrlTab; };
- 创建控件
- 通过调用
Create
动态创建。在您的对话框的
OnInitDialog
中,添加以下代码://CustomTabCtrlDemoDlg.cpp : definition file m_ctrlTab.Create(WS_VISIBLE|WS_CHILD, CRect(0,0,100,20), this, 1);
- 通过对话框模板。
在对话框资源中创建一个自定义控件,然后在控件的属性中,将类名指定为 "
CCustomTabCtrl
"。要将
m_ctrlTab
与控件关联起来,请在您的对话框的DoDataExchange
中添加以下内容:// CustomTabCtrlDemoDlg.cpp : definition file void CCustomTabCtrlDemoDlg::DoDataExchange(CDataExchange* pDX) { CDialog::DoDataExchange(pDX); //{{AFX_DATA_MAP(CCustomTabCtrlDemoDlg) DDX_Control(pDX, IDC_TAB, m_ctrlTab); //}}AFX_DATA_MAP }
- 通过调用
- 创建选项卡控件后,根据需要添加尽可能多的选项卡。
要添加选项卡项,请在您的对话框的
OnInitDialog
中调用InsertItem
。//CustomTabCtrlDemoDlg.cpp : definition file m_ctrlTab.InsertItem(0,"SS_BLACKRECT"); m_ctrlTab.InsertItem(1,"SS_GRAY"); m_ctrlTab.InsertItem(2,"SS_WHITERECT"); m_ctrlTab.SetCurSel(0);
- 在您的对话框类中处理来自选项卡控件的
WM_NOTIFY
消息。当用户单击选项卡时,选项卡控件(
CCustomTabCtrl
)会向其父窗口发送通知消息(CTCN_SELCHANGE
)。如果要执行任何操作,请处理这些消息。在下面的示例中,我修改了m_ctrlColor
控件(CStatic
)的样式。//CustomTabCtrlDemoDlg.cpp : definition file BEGIN_MESSAGE_MAP(CCustomTabCtrlDemoDlg, CDialog) //{{AFX_MSG_MAP(CCustomTabCtrlDemoDlg) ON_NOTIFY(CTCN_SELCHANGE, IDC_TAB, OnSelchangeTab) //}}AFX_MSG_MAP END_MESSAGE_MAP() .... void CCustomTabCtrlDemoDlg::OnSelchangeTab( NMHDR* pNMHDR, LRESULT* pResult) { switch(m_ctrlTab.GetCurSel()) { case 0: // Black rectangle m_ctrlColor.ModifyStyle( SS_BLACKRECT|SS_GRAYRECT|SS_WHITERECT,SS_BLACKRECT); break; case 1: // Gray rectangle m_ctrlColor.ModifyStyle( SS_BLACKRECT|SS_GRAYRECT|SS_WHITERECT,SS_GRAYRECT); break; default: // White rectangle m_ctrlColor.ModifyStyle( SS_BLACKRECT|SS_GRAYRECT|SS_WHITERECT,SS_WHITERECT); break; } m_ctrlColor.Invalidate(); *pResult = 0; }
- 最后,将选项卡控件移动到对话框上的正确位置。
// CustomTabCtrlDemoDlg.cpp : definition file void CCustomTabCtrlDemoDlg::OnSize(UINT nType, int cx, int cy) { CDialog::OnSize(nType, cx, cy); if(m_ctrlTab.m_hWnd && cx && cy) { CRect r; m_ctrlTab.GetWindowRect(r); ScreenToClient(r); m_ctrlTab.MoveWindow(r.left,cy-r.Height()- r.left,cx-2*r.left,r.Height()); } }
在 SDI/MDI 应用程序中使用代码
创建 SDI/MDI 项目并按照以下步骤操作:
- 将 TabMDIFrameWnd.h 和 TabMDIFrameWnd.cpp 添加到您的 MDI 项目中,将 TabSDIFrameWnd.h 和 TabSDIFrameWnd.cpp 添加到 SDI 项目中。
- 在 MainFrm.h 和 MainFrm.cpp 文件中,将
CFrameWnd
替换为CTabSDIFrameWnd
,将CMDIFrameWnd
替换为CTabMDIFrameWnd
。 - 像这样修改
CMainFrame::OnCreate()
:int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct) { ... if (!m_wndStatusBar.Create(this) || !m_wndStatusBar.SetIndicators(indicators, sizeof(indicators)/sizeof(UINT))) { TRACE0("Failed to create status bar\n"); return -1; // fail to create } if(!m_wndTab.Create( WS_CHILD|WS_VISIBLE|CTCS_FOURBUTTONS|CTCS_DRAGMOVE| CTCS_TOOLTIPS,CRect(0,0,0,m_nHeight),this,IDC_TABCTRL)) { TRACE0("Failed to create tab control\n"); return -1; } m_wndTab.SetDragCursors(AfxGetApp()->LoadCursor( IDC_CURSORMOVE),NULL); m_wndTab.SetItemTooltipText(CTCID_FIRSTBUTTON,"First"); m_wndTab.SetItemTooltipText(CTCID_PREVBUTTON,"Prev"); m_wndTab.SetItemTooltipText(CTCID_NEXTBUTTON,"Next"); m_wndTab.SetItemTooltipText(CTCID_LASTBUTTON,"Last"); m_wndToolBar.EnableDocking(CBRS_ALIGN_ANY); ... }
- 在 MDI 项目中,在
CView::OnInitialUpdate()
中添加pMainFrame->AddView(sLabel,this,sTooltip)
,在CView::OnDestroy()
中添加pMainFrame->DeleteView(this)
,在CView::OnActivateView()
中添加pMainFrame->OnActivateView(pActivateView)
。要编辑视图,请双击选项卡控件项。 - 在 SDI 应用程序中,在
CView::OnInitialUpdate()
中插入pMainFrame->AddView(sLabel,this,sTooltip)
,在CDocument::DeleteContents()
中插入pMainFrame->DeleteContents()
。要添加、删除和编辑视图,请右键单击选项卡控件并使用弹出菜单。
CCustomTabCtrl 类成员
- 然后,当你开始迭代 2(这是构建迭代的开始)时,你可能想要复制测试用例并将它们重新分类到迭代 2。这还允许对测试用例进行粒度跟踪,并允许你说某个测试用例在一个迭代中是准备好的,但在另一个迭代中不是。同样,如何做到这一点取决于你以及你希望如何报告。 “场景”部分提供了更多细节。
- 属性
- 操作
- 通知消息
- 错误代码
然后,当你开始迭代 2(这是构建迭代的开始)时,你可能想要复制测试用例并将它们重新分类到迭代 2。这还允许对测试用例进行粒度跟踪,并允许你说某个测试用例在一个迭代中是准备好的,但在另一个迭代中不是。同样,如何做到这一点取决于你以及你希望如何报告。 “场景”部分提供了更多细节。
CCustomTabCtrl | 构造一个 CCustomTabCtrl 对象。 |
Create | 创建一个选项卡控件并将它附加到 CCustomTabCtrl 对象的一个实例。 |
属性
GetItemCount | 检索选项卡控件中的选项卡数量。 |
GetCurSel | 确定选项卡控件中当前选定的选项卡。 |
SetCurSel | 在选项卡控件中选择一个选项卡。 |
IsItemHighlighted | 检索选项卡项的突出显示状态。 |
HighlightItem | 设置项的突出显示状态。 |
GetItemData | 检索与项关联的应用程序特定值。 |
SetItemData | 设置项的应用程序特定值。 |
GetItemText | 检索选项卡项的文本。 |
SetItemText | 更改选项卡项的文本。 |
GetItemRect | 检索选项卡项的矩形。 |
SetItemTooltipText | 更改选项卡项的工具提示文本。 |
SetDragCursors | 设置选项卡控件的拖动光标。 |
ModifyStyle | 修改选项卡控件的样式。 |
SetControlFont | 设置选项卡控件的当前字体。 |
GetDefaultFont | 检索默认字体的 LOGFONT 结构引用。 |
操作
InsertItem | 在选项卡控件中插入一个新选项卡。 |
DeleteItem | 从选项卡控件中删除一个项。 |
DeleteAllItems | 从选项卡控件中删除所有项。 |
MoveItem | 在当前选项卡控件中移动一个选项卡项。 |
CopyItem | 在当前选项卡控件中复制一个选项卡项。 |
HitTest | 确定位于指定屏幕位置的哪个选项卡或按钮(如果有)。 |
EditLabel | 开始项文本的原位编辑。 |
CCustomTabCtrl::CCustomTabCtrl
CCustomTabCtrl( );
备注
调用此函数构造一个 CCustomTabCtrl
对象。
CCustomTabCtrl::Create
BOOL Create( DWORD dwStyle, const RECT& rect,
CWnd* pParentWnd, UINT nID );
返回值
如果对象的初始化成功,则返回 TRUE
;否则返回 FALSE
。
参数
dwStyle
:指定选项卡控件的样式。可以将任何组合的选项卡控件样式应用于该控件。rect
:指定选项卡控件的大小和位置。它可以是CRect
对象或RECT
结构。pParentWnd
:指定选项卡控件的父窗口,通常是CDialog
。nID
:指定选项卡控件的 ID。
备注
除了 WS_CHILD
、WS_VISIBLE
等窗口样式外,还可以将以下样式应用于选项卡控件:
CTCS_FIXEDWIDTH
:使所有选项卡具有相同的宽度。CTCS_FOURBUTTONS
:创建一个具有四个按钮(第一、上一个、下一个、最后一个)的控件。CTCS_AUTOHIDEBUTTONS
:自动隐藏按钮。如果不指定,按钮将始终显示在顶部。CTCS_TOOLTIPS
:选项卡控件具有关联的 ToolTip 控件。CTCS_MULTIHIGHLIGHT
:按住 CTRL 键单击时可以选择多个选项卡。CTCS_EDITLABELS
:允许在原地编辑项文本。CTCS_DRAGMOVE
:可以通过按住鼠标左键并在选项卡控件上拖动光标来移动项。CTCS_DRAGCOPY
:可以通过按住鼠标左键和 CTRL 键,并在选项卡控件上拖动光标来复制项。
CCustomTabCtrl::GetItemCount
int GetItemCount( ) const;
返回值
选项卡控件中的项数。
备注
调用此函数以检索选项卡控件中的选项卡数量。
CCustomTabCtrl::GetCurSel
int GetCurSel( ) const;
返回值
成功时为选定选项卡的零基索引,如果未选择任何选项卡,则为 – 1。
备注
调用此函数以检索选项卡控件中当前选定的选项卡。
CCustomTabCtrl::SetCurSel
int SetCurSel( int nItem );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要选定的项的零基索引。
备注
在选项卡控件中选择一个选项卡。使用此函数选择选项卡时,选项卡控件不会发送 CTCN_SELCHANGE
通知消息。当用户单击以更改选项卡时,会通过 WM_NOTIFY
发送这些通知。
CCustomTabCtrl::IsItemHighlighted
int IsItemHighlighted( int nItem );
返回值
如果突出显示,则为 1
;否则为 0
;否则为 CTCERR_ERRORCODE
。
参数
nItem
:要检索其突出显示状态的选项卡项的索引。
备注
检索选项卡项的突出显示状态。
CCustomTabCtrl::HighlightItem
int HighlightItem( int nItem, BOOL fHighlight );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要设置其突出显示状态的选项卡项的索引。
fHighlight
:要设置给项的突出显示状态。
备注
此函数设置项的突出显示状态。使用此函数突出显示选项卡时,选项卡控件不会发送 CTCN_HIGHLIGHTCHANGE
通知消息。当用户单击以突出显示选项卡时,会通过 WM_NOTIFY
发送这些通知。
CCustomTabCtrl::GetItemData
int GetItemData( int nItem, DWORD& dwData ) const;
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要检索其数据的选项卡项的索引。
dwData
:指向 DWORD
变量的引用,该变量接收与指定项关联的 32 位应用程序特定值。
备注
此函数检索与 nItem
指定的项关联的 32 位应用程序特定值。
CCustomTabCtrl::SetItemData
int SetItemData( int nItem, DWORD dwData );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要设置其数据的选项卡项的索引。
dwData
:要与该项关联的 32 位值。
备注
此函数设置与 nItem
指定的项关联的 32 位应用程序特定值。
CCustomTabCtrl::GetItemText
int GetItemText( int nItem, CString& sText );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要检索其文本的选项卡项的索引。
sText
:指向 CString
对象的引用,该对象接收项的文本。
备注
此函数检索选项卡项的文本。
CCustomTabCtrl::SetItemText
int SetItemText( int nItem, CString sText );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要设置其文本的选项卡项的索引。
sText
:指向包含新项文本的字符串对象的指针。
备注
此函数更改选项卡项的文本。
CCustomTabCtrl::GetItemRect
int GetItemRect( int nItem, CRect& rect );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要检索其矩形的选项卡项的索引。
rect
:指向 CRect
对象的引用,该对象接收项的矩形。
备注
此函数检索选项卡项的矩形。
CCustomTabCtrl::SetItemTooltipText
int SetItemTooltipText( int nItem, CString sText );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
- 要将工具提示文本设置给该选项卡项的零基索引,其值可以是以下之一:
CTCID_FIRSTBUTTON
:第一个按钮的 ID。CTCID_PREVBUTTON
:上一个按钮的 ID。CTCID_NEXTBUTTON
:下一个按钮的 ID。CTCID_LASTBUTTON
:最后一个按钮的 ID。
sText
:指向包含新项工具提示文本的字符串对象的指针。
备注
此函数更改选项卡项的工具提示文本。
CCustomTabCtrl::SetDragCursors
void SetDragCursors( HCURSOR hCursorMove,
HCURSOR hCursorCopy );
参数
hCursorMove
:移动光标的句柄。
hCursorCopy
:复制光标的句柄。
备注
调用此函数以设置选项卡控件的拖动光标。
CCustomTabCtrl::ModifyStyle
BOOL ModifyStyle( DWORD dwRemove, DWORD dwAdd, UINT nFlags );
返回值
成功时返回 TRUE
,否则返回 FALSE
。
备注
有关帮助,请参阅 CWnd::ModifyStyle()
。调用此函数以设置选项卡控件的样式。(不要使用 SetWindowLong()
来修改 CCustomTabCtrl
样式。)
CCustomTabCtrl::SetControlFont
void SetControlFont( LOGFONTt& lf, BOOL fRedraw = FALSE );
参数
lf
:指定新字体。
fRedraw
:如果为 TRUE
,则重绘 CCustomTabCtrl
对象。
备注
将选项卡控件的当前字体设置为指定的字体。
CCustomTabCtrl::GetDefaultFont
static const LOGFONT& GetDafaultFont();
返回值
默认字体的 LOGFONT
结构的引用。
备注
检索默认字体的 LOGFONT
结构的引用。
CCustomTabCtrl::InsertItem
int InsertItem( int nItem, CString sText, LPARAM lParam = 0 );
返回值
成功时为新选项卡的零基索引;否则为 CTCERR_ERRORCODE
。
参数
nItem
:新选项卡的零基索引。
sText
:指向包含新项文本的字符串对象的指针。
lParam
:与选项卡关联的应用程序定义数据。
备注
调用此函数以在现有选项卡控件中插入一个新选项卡。
CCustomTabCtrl::DeleteItem
int DeleteItem( int nItem );
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
- 要删除的项的零基值。
备注
调用此函数以从选项卡控件中删除指定的项。
CCustomTabCtrl::DeleteAllItems
void DeleteAllItems( );
备注
调用此函数以从选项卡控件中删除所有项。
CCustomTabCtrl::MoveItem
int MoveItem(int nItemSrc, int nItemDst);
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItemSrc
:源项的零基索引。
nItemDst
:目标项的零基索引。
备注
在当前选项卡控件中移动一个选项卡项。使用此函数移动选项卡时,选项卡控件不会发送 CTCN_ITEMMOVE
通知消息。当用户使用鼠标移动项时,会通过 WM_NOTIFY
发送这些通知。
CCustomTabCtrl::CopyItem
int CopyItem(int nItemSrc, int nItemDst);
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItemSrc
:源项的零基索引。
nItemDst
:目标项的零基索引。
备注
在当前选项卡控件中复制一个选项卡项。使用此函数复制选项卡时,选项卡控件不会发送 CTCN_ITEMCOPY
通知消息。当用户使用鼠标复制项时,会通过 WM_NOTIFY
发送这些通知。
CCustomTabCtrl::HitTest
int HitTest( CPoint pt);
返回值
匹配项的零基索引或以下值之一:
CTCHT_ONFIRSTBUTTON
:位置在第一个按钮上。CTCHT_ONPREVBUTTON
:位置在上一个按钮上。CTCHT_ONNEXTBUTTON
:位置在下一个按钮上。CTCHT_ONLASTBUTTON
:位置在最后一个按钮上。CTCHT_NOWHERE
:位置在选项卡控件的客户区窗口内,但不在任何选项卡项或按钮上。
参数
pt
:要在客户端坐标中测试的点。
备注
确定位于指定屏幕位置的哪个选项卡或按钮(如果有)。
CCustomTabCtrl::EditLabel
int EditLabel( int nItem);
返回值
成功时为 CTCERR_NOERROR
,否则为 CTCERR_ERRORCODE
。
参数
nItem
:要编辑的选项卡项的索引。
备注
开始项文本的原位编辑。
通知消息
选项卡控件支持以下通知代码:
CTCN_CLICK
:用户单击了控件的鼠标左键。CTCN_RCLICK
:用户单击了控件的鼠标右键。CTCN_SELCHANGE
:用户更改了当前选择。CTCN_HIGHLIGHTCHANGE
:用户更改了项的突出显示状态。CTCN_ITEMMOVE
:用户移动了该项。CTCN_ITEMCOPY
:用户复制了该项。CTCN_LABELUPDATE
:用户更改了项的文本。CTCN_OUTOFMEMORY
:由于内存不足,控件无法完成操作。
上述通知会传递指向 CTC_NMHDR
结构的指针,该结构将 NMHDR
结构作为其第一个成员,如下所示:
typedef struct _CTC_NMHDR { NMHDR hdr; int nItem; TCHAR pszText[MAX_LABEL_TEXT]; LPARAM lParam; RECT rItem; POINT ptHitTest; BOOL fSelected; BOOL fHighlighted; } CTC_NMHDR;
错误代码
选项卡控件函数可以返回以下错误:
CTCERR_NOERROR
:操作成功。CTCERR_OUTOFMEMORY
:由于内存不足,函数调用失败。CTCERR_INDEXOUTOFRANGE
:函数调用失败,因为选项卡项索引超出范围。CTCERR_NOEDITLABELSTYLE
:函数调用失败,因为未指定CTCS_EDITLABELS
样式。CTCERR_NOMULTIHIGHLIGHTSTYLE
:函数调用失败,因为未指定CTCS_MULTIHIGHLIGHT
样式。CTCERR_ITEMNOTSELECTED
:函数调用失败,因为未选择项。CTCERR_ALREADYINEDITMODE
:函数失败,因为选项卡控件已处于编辑模式。CTCERR_TEXTTOOLONG
:函数失败,因为项文本过长。CTCERR_NOTOOLTIPSSTYLE
:函数调用失败,因为未指定CTCS_TOOLTIPS
样式。CTCERR_CREATETOOLTIPFAILED
:函数调用失败,因为创建工具提示控件失败。
新功能
2006 年 5 月 16 日
- 添加了垂直样式(左和右)
- 备注
- 垂直样式不支持标签编辑。
- 我使用
PlgBlt()
来旋转位图。此函数特定于 NT 及更高版本,在 Windows95 上不起作用。
2006 年 4 月 16 日
- 添加了用于指定样式的按钮
- Bug 修复
- 修正了 RTL 问题。
- 修正了对话框演示应用程序中对“
OnSize
”处理不正确的问题。
2006 年 3 月 25 日
- 添加了关闭按钮和顶部样式
- Bug 修复
- 修正了删除选项卡项时工具提示矩形计算不正确的问题。
- 修正了处于编辑模式时“Alt-F4 点击”的问题。
- 修正了在拖放模式下对“
OnMouseMove
”处理不正确的问题。
2005 年 10 月 10 日
- SDI 和 MDI 演示项目
2004 年 7 月 30 日
- “第一”和“最后一个”按钮
- 项和按钮的内置工具提示
- 多重突出显示项
- 原位编辑
- 用于移动和复制项的拖放功能。
- 按下按钮时自动重复。
- 按钮自动隐藏或始终显示在顶部。