牛骨文教育服务平台(让学习变的简单)

VC++中Ribbon编程架构及SDI架构多视图切换介绍

在MS Visual Studio 2008 MFC中Ribbon界面风格出现了,这种界面风格给人带来耳目一新的感觉。Ribbon界面风格出现,可以说改革了传统的菜单式界面风格,常见的应用就是MS Office 2007中的Word、Excel、PowerPoint等组件中,Ribbon不仅使得功能有组织的存放,而且可以更加方便快捷地找到各个功能。但是MS Visual Studio 2008 MFC中还未加入Ribbon编程的相关组件,这意味着不会是那种想要什么控件就托到相应的位置就可以了,而是要完全通过代码来生成和控制相关的组件。值得然人欣喜的是,在MS Visual Studio 2010 MFC中,Ribbon编程相关的组件已经被添加了进来,这样一来Ribbon编程就变得容易了起来,可以达到“所见即所得”的效果了。

下面结合MS Visual Studio 2008 MFC中Ribbon编程的一个实例,详细讲述Ribbon编程的具体步骤和注意事项,同时还将提出一种SDI(单文档界面)架构程序中进行多个视图切换的方法。(完整的实例可在我的CSDN资源中下载:http://download.csdn.net/detail/margin1988/6408275):

⑴  MS Visual Studio 2008 MFC中创建SDIRibbon应用程序的步骤:

1)“新建”一个Visual C++ MFC应用程序项目:

2)“确定”后进入MFC应用程序向导,单击“下一步”:

3)进入到应用程序类型界面,选择“单文档”、“Office”、“Office 2007(黑色主题)”,单击“下一步”:

4)进入复合文档支持,选择“无”,单击“下一步”:

5)进入文档模板字符串,单击“下一步”:

6)进入数据库支持,选择“无”,单击“下一步”:

7)进入用户界面功能,按下图所示选择后,单击“下一步”:

8)进入高级功能,勾去所有的高级功能,如下图,单击“下一步”:

9)进入生成的类,选择基类“CFormView”,单击“完成”:

10)完成后,直接编译运行程序,得到的界面如下入:

(2)Ribbon界面风格的主要构成分析:

Ribbon应用程序的主体框架构成从大到小包含如上图中所示的三大块:分类(CMFCRibbonCategory)、面板(CMFCRibbonPanel)、元素(包括:CMFCRibbonButton、CMFCRibbonEdit等)。

(3)如何创建属于自己的Ribbon界面表现形式:

1)使用绘图、PS等工具绘制自己的按钮图标(PNG),并放在工程的res目录下,然后将其导入工程资源:

2)在MainFrm.cpp文件的InitializeRibbon()函数中,仿照默认生成的代码编写自己的Ribbon界面表现形式,删除自动生成的你不需要的代码:

A.添加资源符号:

在String Table中添加分类和面板资源符号:

在Accelerator中添加元素资源快捷键:

B.依次创建“分类->面板->元素”:

//创建“分类”-模块1
bNameValid = strTemp.LoadString(IDS_RIBBON_MODULAR1);
ASSERT(bNameValid);
CMFCRibbonCategory* pCategoryHomeMod1 = m_wndRibbonBar.AddCategory(strTemp,IDB_PNG3,IDB_PNG2,CSize(28,25),CSize(56,50));

//创建“面板”-用户管理和“元素”-按钮
bNameValid = strTemp.LoadString(IDS_RIBBON_USERMANAGER);
ASSERT(bNameValid);
CMFCRibbonPanel* pPanelUserManager = pCategoryHomeMod1->AddPanel(strTemp, m_PanelImages.ExtractIcon(7));//有个子图标(索引~)
CMFCRibbonButton* pBtnUserManager = new CMFCRibbonButton(ID_EDIT_USERMANAGER,_T(""), 0,0);//加载的第一个(索引)
pPanelUserManager->Add(pBtnUserManager);

3)添加相应消息响应函数,使面板元素激活可用:

BEGIN_MESSAGE_MAP(CMainFrame, CFrameWndEx)
   ON_COMMAND(ID_EDIT_USERMANAGER, OnUserManagerCommand)
   ON_COMMAND(ID_EDIT_PARAMCONFIG, OnParamConfigCommand)
//消息响应宏
END_MESSAGE_MAP()

4)最终自定义的Ribbon界面表现形式如下图:

(4)SDI(单文档界面)架构想要实现多个视图之间的切换,需要定义一个切换视图的函数——void SwitchToForm(int nForm);该函数的实现体如下:

★声明全局变量frmID:

在stdafx.h中添加声明:extern int frmID;

在stdafx.cpp中添加定义:int frmID;

在C工程名.cpp中的InitInstance()中初始化:frmID = 0;

void CMainFrame::SwitchToForm(int nForm) {//进行视图切换的代码函数
if (nForm!=frmID)
{
frmID=nForm;//避免多次点击同一按钮时出现的错误,一按钮点击一次后,第二次点击不做任何处理。
CDocument* pDoc = GetActiveDocument();
CView *pOldActiveView=GetActiveView();//保存旧视图
CView *pNewActiveView=(CView*)GetDlgItem(nForm);//取得新视图
if(pNewActiveView==NULL)
{
switch(nForm){
case IDD_USERMANAGER_FORM ://视图资源符号
pNewActiveView=(CView*)new CPoint19View;
break;
case IDD_PARAMCONFIG_FORM ://视图资源符号
pNewActiveView=(CView*)new CParamConfig;
break;
}
CCreateContext context; //将文挡和视图相连
context.m_pCurrentDoc=pOldActiveView->GetDocument();
pNewActiveView->Create(NULL, NULL, WS_BORDER|WS_CHILD, CFrameWnd::rectDefault, this, nForm, &context);

pNewActiveView->OnInitialUpdate();
}
SetActiveView(pNewActiveView); //改变活动的视图
pNewActiveView->ShowWindow(SW_SHOW); //显示新的视图
pOldActiveView->ShowWindow(SW_HIDE); //隐藏旧的视图

if(pOldActiveView->GetRuntimeClass() ==RUNTIME_CLASS(CPoint19View))
pOldActiveView->SetDlgCtrlID(IDD_USERMANAGER_FORM);
else if(pOldActiveView->GetRuntimeClass() ==RUNTIME_CLASS(CParamConfig))
pOldActiveView->SetDlgCtrlID(IDD_PARAMCONFIG_FORM);

pNewActiveView->SetDlgCtrlID(AFX_IDW_PANE_FIRST);
delete pOldActiveView; //删除旧视图
RecalcLayout();//调整框架窗口
}
}

调用方式如下:

void CMainFrame::OnUserManagerCommand(){
	SwitchToForm(IDD_USERMANAGER_FORM);
}
void CMainFrame::OnParamConfigCommand(){
	SwitchToForm(IDD_PARAMCONFIG_FORM);
}