此例向导为使用Visual Studio 6.0 应用程序向导制作具有可停靠面板的MDI程序. 对于最新版本的 Visual Studio . NET这种技巧同样生效.
使用MFC AppWizard制作简单的MDI程序:
- Visual Studio中选择文件(File) |新建(New) 选择项目(Projects) tab.
- 选择 项目类型为MFC Appwizard(exe) ,输入 ‘MDISample’ 作为项目名称.
Visual Studio 新建工程对话框...
- 第一步, 确定多文档(Multiple documents) 被选中,单击'完成(Finish)’ 按钮.
添加空白停靠面板:
- 在
StdAfx.h
文件中加入下面一行:Xtreme Toolkit Pro:
#define _XTP_STATICLINK //此处为译者修改 using mfc in static link lib #include <XTToolkitPro.h> //在rc2文件中添加 #include "xttoolkitpro.rc"
- 给CMainFrame class添加成员变量 CXTPDockingPaneManager :
// Attributes public: CXTPDockingPaneManager m_paneManager;
- 给将要使用的面板标题添加字符串资源:
IDR_PANE_OPTIONS 61446 Options IDR_PANE_PROPERTIES 61447 Properties
此图为译者所加
- 在CMainFrame::OnCreate中添加如下代码:
// 只有在所有控制栏对象被创建和停靠以后,初始化停靠面板管理器并设置面板的初始值. m_paneManager.InstallDockingPanes(this); m_paneManager.SetTheme(xtpPaneThemeOffice); //CXTPDockingPane* pwndPane1 = m_paneManager.CreatePane( // IDR_PANE_OPTIONS, CRect(0, 0,200, 120), dockLeftOf); //CXTPDockingPane* pwndPane2 = m_paneManager.CreatePane( // IDR_PANE_PROPERTIES, CRect(0, 0,200, 120), dockBottomOf, pwndPane1) // 创建停靠面板,注意dockLeftOf改为xtpPaneDockLeft xtpPaneDockBottom 译者修改 CXTPDockingPane* pwndPane1 = m_paneManager.CreatePane( IDR_PANE_OPTIONS, CRect(0, 0,200, 120), xtpPaneDockLeft); CXTPDockingPane* pwndPane2 = m_paneManager.CreatePane( IDR_PANE_PROPERTIES, CRect(0, 0,200, 120), xtpPaneDockBottom, pwndPane1); return 0;
带有停靠面板的MDI 示例程序...
由 CWnd 类派生面板:
- 为CMainFrame添加CWnd 派生类成员变量
// Attributes public: CStatic m_wndOptions; CEdit m_wndProperties;
- MainFrm.cpp添加
OnDockingPaneNotify
面板停靠通知消息句柄.BEGIN_MESSAGE_MAP(CMainFrame, CMDIFrameWnd) //{{AFX_MSG_MAP(CMainFrame) ON_WM_CREATE() //}}AFX_MSG_MAP ON_MESSAGE(XTPWM_DOCKINGPANE_NOTIFY, OnDockingPaneNotify) END_MESSAGE_MAP() //{{AFX_MSG(CMainFrame) afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct); // NOTE - the ClassWizard will add and remove member functions here. // DO NOT EDIT what you see in these blocks of generated code! //}}AFX_MSG afx_msg LRESULT OnDockingPaneNotify(WPARAM wParam,LPARAM lParam); DECLARE_MESSAGE_MAP() LRESULT CMainFrame::OnDockingPaneNotify(WPARAM wParam,LPARAM lParam) { //wParam消息 LPARAM 对象 if (wParam ==XTP_DPN_SHOWWINDOW) { CXTPDockingPane* pPane=(CXTPDockingPane*)lParam; if (!pPane->IsValid()) { switch(pPane->GetID()) { case IDR_PANE_PROPERTIES: { if (m_wndProperties.GetSafeHwnd()==0) { //子窗口,垂直滚动,多行编辑 m_wndProperties.Create(WS_CHILD| ES_AUTOVSCROLL|ES_MULTILINE, CRect(0,0,0,0),this,0); } pPane->Attach((&m_wndProperties)); break; } case IDR_PANE_OPTIONS: { if (m_wndOptions.GetSafeHwnd()==0) { m_wndOptions.Create(_T("\n\nOptions"), WS_CHILD|WS_CLIPCHILDREN| WS_CLIPSIBLINGS|SS_CENTER, CRect(0,0,0,0),this,0); } pPane->Attach(&m_wndOptions); break; } } } return TRUE; } return FALSE; }
MDI Sample Application With CWnd Objects Attached to Docking Panes...
给停靠面板选项页添加图像:
- 为创建好的面板制作Bitmap 图标
Visual Studio 资源编辑器...
- 在
CMainFrame::OnCreate 中添加如下代码
int nIDIcons[] = {IDR_PANE_OPTIONS, IDR_PANE_PROPERTIES}; m_paneManager.SetIcons(IDB_BITMAP_ICONS, nIDIcons, _countof(nIDIcons), RGB(0, 255, 0)); return 0;
Visual Studio 资源编辑器... (图标仅为示例,与原文并不一致)
添加保存和装载状态句柄:
- CMainFrame中添加如下代码在
OnCreate
函数. 恢复先前停靠栏状态:int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct) { ... // 加载先前停靠栏状态. CXTPDockingPaneLayout layoutNormal(&m_paneManager); if (layoutNormal.Load(_T("NormalLayout"))) { m_paneManager.SetLayout(&layoutNormal); } return 0; }
- 在CMainFrame 类添加
OnClose
消息句柄,调用基类前添加如下代码. 将保存最近停靠栏状态:void CMainFrame::OnClose() { // TODO: Add your message handler code here and/or call default CXTPDockingPaneLayout layoutNormal(&m_paneManager); m_paneManager.GetLayout(&layoutNormal); layoutNormal.Save(_T("NormalLayout")); CMDIFrameWnd::OnClose(); }
------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------
原文
Chapter 4: Tutorials for Using Xtreme Toolkit Pro v13.2 |
How to Add a Docking Pane to Your Application
The following is a tutorial on how to create an MDI application with Docking Panes using the Visual Studio 6.0 Application Wizard. The same technique can be used for later versions of Visual Studio . NET as well.
Create a simple MDI application using the MFC AppWizard:
- From Visual Studio select File thenNew and select theProjects tab.
- Choose MFC Appwizard(exe) as your project type and enter ‘MDISample’ as the project name.
Visual Studio New Project Dialog...
- For the first step, make sure that Multiple documents is selected then press the ‘Finish’ button.
Add Empty Docking Panes:
- Add the following line to your
StdAfx.h
file:Xtreme Toolkit Pro:
#include <XTToolkitPro.h> // Xtreme Toolkit Pro component library
- Add CXTPDockingPaneManager member to CMainFrame class:
// Attributes public: CXTPDockingPaneManager m_paneManager;
- Add string resources for the titles of the future panes:
IDR_PANE_OPTIONS 61446 Options IDR_PANE_PROPERTIES 61447 Properties
- Add following to CMainFrame::OnCreate:
// Initialize the docking pane manager and set the // initial them for the docking panes. Do this only after all // control bars objects have been created and docked. m_paneManager.InstallDockingPanes(this); m_paneManager.SetTheme(xtpPaneThemeOffice); // Create docking panes. CXTPDockingPane* pwndPane1 = m_paneManager.CreatePane( IDR_PANE_OPTIONS, CRect(0, 0,200, 120), dockLeftOf); CXTPDockingPane* pwndPane2 = m_paneManager.CreatePane( IDR_PANE_PROPERTIES, CRect(0, 0,200, 120), dockBottomOf, pwndPane1)
MDI Sample Application With Docking Panes...
Attach CWnd derived class to the panes:
- Add a CWnd derived class as member ofCMainFrame:
// Attributes public: CStatic m_wndOptions; CEdit m_wndProperties;
- Add
OnDockingPaneNotify
handler.BEGIN_MESSAGE_MAP(CMainFrame, CMDIFrameWnd) //{{AFX_MSG_MAP(CMainFrame) ON_WM_CREATE() //}}AFX_MSG_MAP ON_MESSAGE(XTPWM_DOCKINGPANE_NOTIFY, OnDockingPaneNotify) END_MESSAGE_MAP() LRESULT CMainFrame::OnDockingPaneNotify(WPARAM wParam, LPARAM lParam) { if (wParam == XTP_DPN_SHOWWINDOW) { CXTPDockingPane* pPane = (CXTPDockingPane*)lParam; if (!pPane->IsValid()) { switch (pPane->GetID()) { case IDR_PANE_PROPERTIES: { if (m_wndProperties.GetSafeHwnd() == 0) { m_wndProperties.Create(WS_CHILD| ES_AUTOVSCROLL|ES_MULTILINE, CRect(0, 0, 0, 0), this, 0); } pPane->Attach(&m_wndProperties); break; } case IDR_PANE_OPTIONS: { if (m_wndOptions.GetSafeHwnd() == 0) { m_wndOptions.Create(_T("\n\nOptions"), WS_CHILD|WS_CLIPCHILDREN| WS_CLIPSIBLINGS|SS_CENTER, CRect(0, 0, 0, 0), this, 0); } pPane->Attach(&m_wndOptions); break; } } } return TRUE; } return FALSE; }
MDI Sample Application With CWnd Objects Attached to Docking Panes...
- Create Bitmap with icons for created panes
Visual Studio Resource Editor...
- Add to
CMainFrame::OnCreate
int nIDIcons[] = {IDR_PANE_OPTIONS, IDR_PANE_PROPERTIES}; m_paneManager.SetIcons(IDB_BITMAP_ICONS, nIDIcons, _countof(nIDIcons), RGB(0, 255, 0));
Visual Studio Resource Editor...
Add Save and Load State Handlers:
- Add following to the
OnCreate
function forCMainFrame. This will restore the previous state of docking panes:int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct) { ... // Load the previous state for docking panes. CXTPDockingPaneLayout layoutNormal(&m_paneManager); if (layoutNormal.Load(_T("NormalLayout"))) { m_paneManager.SetLayout(&layoutNormal); } return 0; }
- Add the
OnClose
message handler to CMainFrame and the following before the call to the base class. This will save the current state of your docking pane:void CMainFrame::OnClose() { // Save the current state for docking panes. CXTPDockingPaneLayout layoutNormal(&m_paneManager); m_paneManager.GetLayout(&layoutNormal); layoutNormal.Save(_T("NormalLayout")); CMDIFrameWnd::OnClose(); }