`
hcmfys
  • 浏览: 357611 次
  • 性别: Icon_minigender_1
  • 来自: 广州
社区版块
存档分类
最新评论

duoview1

 
阅读更多
首先在H文件有如下声明:

class CMultiViewApp : public CWinApp

{

public:

CView* m_pFirstView;

CView* m_pOtherView;

int m_currentView;

CView* m_pView2;

CView* m_pView1;

CMultiViewApp();


// Overrides

// ClassWizard generated virtual function overrides

//{{AFX_VIRTUAL(CMultiViewApp)

public:

virtual BOOL InitInstance();

//}}AFX_VIRTUAL


// Implementation

//{{AFX_MSG(CMultiViewApp)

afx_msg void OnAppAbout();

afx_msg void OnViewOtherview();

afx_msg void OnViewFirstview();

//}}AFX_MSG

afx_msg void OnViewChange(UINT nCmdID);

DECLARE_MESSAGE_MAP()

};


其次,在CPP文件有如下消息MAP:

/////////////////////////////////////////////////////////////////////////////

// CMultiViewApp


BEGIN_MESSAGE_MAP(CMultiViewApp, CWinApp)

//{{AFX_MSG_MAP(CMultiViewApp)

ON_COMMAND(ID_APP_ABOUT, OnAppAbout)

ON_COMMAND(ID_VIEW_OTHERVIEW, OnViewOtherview)

ON_COMMAND(ID_VIEW_FIRSTVIEW, OnViewFirstview)

//}}AFX_MSG_MAP

// Standard file based document commands

ON_COMMAND(ID_FILE_NEW, CWinApp::OnFileNew)

ON_COMMAND(ID_FILE_OPEN, CWinApp::OnFileOpen)

// Standard print setup command

ON_COMMAND(ID_FILE_PRINT_SETUP, CWinApp::OnFilePrintSetup)

ON_COMMAND_RANGE( ID_VIEW_VIEW1, ID_VIEW_VIEW2, OnViewChange)

END_MESSAGE_MAP()


说明:SDI程序在CMyApp::InitInstance()已经通过DocTemplate创建一个关联的视图/文档实例,切显示出来.具体实现如下:

BOOL CMultiViewApp::InitInstance()

{

AfxEnableControlContainer();


// Standard initialization

// If you are not using these features and wish to reduce the size

// of your final executable, you should remove from the following

// the specific initialization routines you do not need.


#ifdef _AFXDLL

Enable3dControls(); // Call this when using MFC in a shared DLL

#else

Enable3dControlsStatic(); // Call this when linking to MFC statically

#endif


// Change the registry key under which our settings are stored.

// TODO: You should modify this string to be something appropriate

// such as the name of your company or organization.

SetRegistryKey(_T("Local AppWizard-Generated Applications"));


LoadStdProfileSettings(); // Load standard INI file options (including MRU)


// Register the application's document templates. Document templates

// serve as the connection between documents, frame windows and views.


CSingleDocTemplate* pDocTemplate;

pDocTemplate = new CSingleDocTemplate(

IDR_MAINFRAME,

RUNTIME_CLASS(CMultiViewDoc),

RUNTIME_CLASS(CMainFrame), // main SDI frame window

RUNTIME_CLASS(CMultiViewView));

AddDocTemplate(pDocTemplate);


// Parse command line for standard shell commands, DDE, file open

CCommandLineInfo cmdInfo;

ParseCommandLine(cmdInfo);


// Dispatch commands specified on the command line

if (!ProcessShellCommand(cmdInfo))

return FALSE;


CView* pActiveView = ((CFrameWnd*) m_pMainWnd)->GetActiveView();

m_pFirstView = pActiveView;

m_pOtherView = (CView*) new COtherView;


CDocument* pDoc = ((CFrameWnd*)m_pMainWnd)->GetActiveDocument();

//通过CCreateContext实现第二视图和文档的关联

CCreateContext context;

context.m_pCurrentDoc = pDoc;


UINT m_ID = AFX_IDW_PANE_FIRST + 1;

CRect rect;

//为了演示第一种多视图是实现方法,把Vew的实例创建放在了这里

m_pOtherView->Create(NULL, NULL, WS_CHILD, rect, m_pMainWnd, m_ID, &context);


// The one and only window has been initialized, so show and update it.

m_pMainWnd->ShowWindow(SW_SHOWMAXIMIZED);

m_pMainWnd->UpdateWindow();

m_currentView=1;

return TRUE;

}

1. SDI单文档多视图实现方法1
void CMultiViewApp::OnViewOtherview()

{

// TODO: Add your command handler code here

UINT temp = ::GetWindowLong(m_pOtherView->m_hWnd, GWL_ID);

::SetWindowLong(m_pOtherView->m_hWnd, GWL_ID, ::GetWindowLong(m_pFirstView->m_hWnd, GWL_ID));

::SetWindowLong(m_pFirstView->m_hWnd, GWL_ID, temp);


m_pFirstView->ShowWindow(SW_HIDE);

m_pOtherView->ShowWindow(SW_SHOW);


((CFrameWnd*)m_pMainWnd)->SetActiveView(m_pOtherView);

((CFrameWnd*) m_pMainWnd)->RecalcLayout();

m_pOtherView->Invalidate();


}


void CMultiViewApp::OnViewFirstview()

{

// TODO: Add your command handler code here


UINT temp = ::GetWindowLong(m_pOtherView->m_hWnd, GWL_ID); //GetWindowWord()

::SetWindowLong(m_pOtherView->m_hWnd, GWL_ID, ::GetWindowLong(m_pFirstView->m_hWnd, GWL_ID));//SetWindowWord()

::SetWindowLong(m_pFirstView->m_hWnd, GWL_ID, temp);//SetWindowWord()


m_pOtherView->ShowWindow(SW_HIDE);

m_pFirstView->ShowWindow(SW_SHOW);


((CFrameWnd*)m_pMainWnd)->SetActiveView(m_pFirstView);

((CFrameWnd*)m_pMainWnd)->RecalcLayout();

m_pFirstView->Invalidate();

}

2. SDI单文档多视图实现方法2
void CMultiViewApp::OnViewChange(UINT nCmdID)

{

//另外一种方法实现SDI的多视图切换

CView* pViewAdd;

CView* pViewRemove;

CMainFrame* pMainFrame=(CMainFrame*)AfxGetMainWnd();

CDocument* pDoc = pMainFrame->GetActiveDocument();


if((nCmdID == ID_VIEW_VIEW1) && (m_currentView == 1))

return;

if((nCmdID == ID_VIEW_VIEW2) && (m_currentView == 2))

return;


if (nCmdID == ID_VIEW_VIEW2)

{

if (m_pView2 == NULL)

{

m_pView1 = pMainFrame->GetActiveView();

m_pView2 = new COtherView();


//Note that if OnSize has been overridden in CMyView2

//and GetDocument() is used in this override it can

//cause assertions and, if the assertions are ignored,

//cause access violation.

//使用CCreateContext structure实现view和document的关联

CCreateContext context;

context.m_pCurrentDoc=pDoc;//m_pView1->GetDocument();


m_pView2->Create(NULL, NULL, AFX_WS_DEFAULT_VIEW,

CFrameWnd::rectDefault, AfxGetMainWnd(), AFX_IDW_PANE_FIRST + 1, &context/*NULL*/);

}

pViewAdd = m_pView2;

pViewRemove = m_pView1;

m_currentView= 2;

}

else

{

pViewAdd = m_pView1;

pViewRemove = m_pView2;

m_currentView= 1;

}


// Set the child i.d. of the active view to AFX_IDW_PANE_FIRST,

// so that CFrameWnd::RecalcLayout will allocate to this

// "first pane" that portion of the frame window's client area

// not allocated to control bars. Set the child i.d. of the

// other view to anything other than AFX_IDW_PANE_FIRST; this

// examples switches the child id's of the two views.


int nSwitchChildID = pViewAdd->GetDlgCtrlID();

pViewAdd->SetDlgCtrlID(AFX_IDW_PANE_FIRST);

pViewRemove->SetDlgCtrlID(nSwitchChildID);


// Show the newly active view and hide the inactive view.


pViewAdd->ShowWindow(SW_SHOW);

pViewRemove->ShowWindow(SW_HIDE);


// Connect the newly active view to the document, and

// disconnect the inactive view.

//通过CCreateContext实现视图View和文档Document的关联

//就没有必要手动AddView(),如果需要可以进行手动RemoveView()

//AddView()会在CView::OnCreate()被MFC调用,RemoveView()会在CView::~CView()被调用

//当然可以根据需要手动调用它们,在本例当中,View都是被创建一次,没有被销毁,所以不会自动

//调用RemoveView()

//pDoc->AddView(pViewAdd);

//pDoc->RemoveView(pViewRemove);


pMainFrame->SetActiveView(pViewAdd);

pMainFrame->RecalcLayout();


return ;

}

The code needed to implement view switching depends on the frame window containing the view. There are three common cases: the view is contained within a CFrameWnd (SDI application), the view is contained within a CMDIChildWnd (MDI application) and the view is a pane of a splitter window, either in SDI or MDI applications. In all cases, what we need is a method in our document class to switch to the desired view. This method should receive the new view as a parameter and return the view that was replaced. This returned view is not contained in the document's list anymore. The advantage of having this method in the document class becomes obvious when there are several document types each of which can have different view types. Let's start with an SDI application that doesn't have splitters:

Collapse Copy Code
CView* CMyDocument::SwitchToView ( CView* pNewView )
{
CFrameWnd* pMainWnd = (CFrameWnd*)AfxGetMainWnd();
CView* pOldActiveView = pMainWnd->GetActiveView();
ASSERT(pOldActiveView != NULL);
ASSERT_VALID(pOldActiveView);
ASSERT(pOldActiveView->GetDocument() == this); // must be attached to us

/* Set the child window ID of the active view to AFX_IDW_PANE_FIRST.
This is necessary so that CFrameWnd::RecalcLayout will allocate
this "first pane" to that portion of the frame window's client
area not allocated to control bars. Set the child ID of
the previously active view to some other ID.
*/

::SetWindowLong(pOldActiveView->m_hWnd, GWL_ID, 0);
::SetWindowLong(pNewView->m_hWnd, GWL_ID, AFX_IDW_PANE_FIRST);

// Show the newly active view and hide the inactive view.
pNewView->ShowWindow(SW_SHOW);
pOldActiveView->ShowWindow(SW_HIDE);

// Connect the newly active view to the document,
// and disconnect the inactive view
AddView(pNewView);
RemoveView(pOldActiveView);
pMainWnd->SetActiveView(pNewView);
pMainWnd->RecalcLayout();

return pOldActiveView;
}In the case of an MDI application (again without splitters):

Collapse Copy Code
CView* CMyDocument::SwitchToView ( CView* pNewView )
{
CMDIFrameWnd* pMainWnd = (CMDIFrameWnd*)AfxGetMainWnd();

// Get the active MDI child window.
CMDIChildWnd* pChild = (CMDIChildWnd*)pMainWnd->MDIGetActive();

// Get the active view attached to the active MDI child window.
CView* pOldActiveView = pChild->GetActiveView();

// Set flag so that document will not be deleted when view is dettached.
BOOL bAutoDelete = m_bAutoDelete;
m_bAutoDelete = FALSE;

// Dettach existing view
RemoveView(pOldActiveView);

// restore flag
m_bAutoDelete = bAutoDelete;

// Show the newly active view and hide the inactive view.
pNewView->ShowWindow(SW_SHOW);
pOldActiveView->ShowWindow(SW_HIDE);

// Attach new view
AddView(pNewView);

pChild->RecalcLayout();
pNewView->UpdateWindow();
pChild->SetActiveView(pNewView);
return pOldActiveView;
}When the view to replace is a pane of a splitter window, there is also a small difference between SDI and MDI applications, related to the retrieval of the current active view. In the method below, you must comment out what you don't need depending on your application type:

Collapse Copy Code
CView* CSDISplitDoc::SwitchToView ( CView* pNewView )
{
/* Uncomment this if this is a SDI application
CFrameWnd* pMainWnd = (CFrameWnd*)AfxGetMainWnd();
CView* pOldActiveView = pMainWnd->GetActiveView();
*/

/* Uncomment this if this is a MDI application
CMDIFrameWnd* pMainWnd = (CMDIFrameWnd*)AfxGetMainWnd();

// Get the active MDI child window.
CMDIChildWnd* pChild = (CMDIChildWnd*)pMainWnd->MDIGetActive();

// Get the active view attached to the active MDI child window.
CView* pOldActiveView = pChild->GetActiveView();
*/

CSplitterWnd* pSplitter = (CSplitterWnd *)pOldActiveView->GetParent();
int row, col;
ASSERT(pSplitter->IsChildPane(pOldActiveView, row, col));

// set flag so that document will not be deleted when view is destroyed
m_bAutoDelete = FALSE;

// Dettach existing view
RemoveView(pOldActiveView);

// set flag back to default
m_bAutoDelete = TRUE;
/* Set the child window ID of the active view to the ID of the corresponding
pane. Set the child ID of the previously active view to some other ID.
*/
::SetWindowLong(pOldActiveView->m_hWnd, GWL_ID, 0);
::SetWindowLong(pNewView->m_hWnd, GWL_ID, pSplitter->IdFromRowCol(row, col));

// Show the newly active view and hide the inactive view.
pNewView->ShowWindow(SW_SHOW);
pOldActiveView->ShowWindow(SW_HIDE);

// Attach new view
AddView(pNewView);

// Set active
pSplitter->GetParentFrame()->SetActiveView(pNewView);
pSplitter->RecalcLayout();
pNewView->SendMessage(WM_PAINT);

return pOldActiveView;
}The SwitchToView functions above receive a pointer to an existing view, so a view must have already been created without attaching it to a document. Note that this imposes restrictions on view creation code, which should not make use of the document in any way (for example, the OnInitialUpdate member function). Otherwise, exceptions might occur. The newly activated view is shown before it is attached to the document, so functions in the view that respond to Windows messages such as WM_SIZE or WM_GETMINMAXINFO should not make use of the document either.

The view must be created with correct parent window and window ID. Both parameters depend on the frame windows containing the view, just the same as the SwithToView function. The non-active views could be created the first time the menu to select one of them was selected or somewhere in the document initialization code. Supposing we have a m_pView1 member in the document class that is a pointer to a view, this is how it should be created in a SDI application:

Collapse Copy Code
if (!m_pView1)
{
// create the new view
m_pView1 = new CView1;
m_pView1->Create(NULL, NULL, AFX_WS_DEFAULT_VIEW, CFrameWnd::rectDefault,
AfxGetMainWnd(), AFX_IDW_PANE_FIRST+1, NULL);
}In a MDI application:

Collapse Copy Code
CMDIFrameWnd* pMainWnd = (CMDIFrameWnd*)AfxGetMainWnd();
// Get the active MDI child window.
CMDIChildWnd* pChild = (CMDIChildWnd*)pMainWnd->MDIGetActive();

if (!m_pView1)
{
// create the new view
m_pView1 = new CView1;
m_pView1->Create(NULL, NULL, AFX_WS_DEFAULT_VIEW, CRect(0, 0, 0, 0),
pChild, AFX_IDW_PANE_FIRST, NULL);
}And finally, if the view is a pane of a splitter window (read the comments to difference between SDI and MDI applications):

Collapse Copy Code
/* Uncomment this if this is a SDI application
CFrameWnd* pMainWnd = (CFrameWnd*)AfxGetMainWnd();
CView* pActiveView = pMainWnd->GetActiveView();
CSplitterWnd* pSplitter = (CSplitterWnd *)pActiveView->GetParent();
*/

/* Uncomment this if this is a MDI application
CMDIFrameWnd* pMainWnd = (CMDIFrameWnd*)AfxGetMainWnd();
CMDIChildWnd* pChild = (CMDIChildWnd*)pMainWnd->MDIGetActive();
CView* pActiveView = pChild->GetActiveView();
CSplitterWnd* pSplitter = (CSplitterWnd *)pActiveView->GetParent();
*/

if (!m_pView1)
{
// create the new view
m_pView1 = new CView1;
m_pView1->Create(NULL, NULL, AFX_WS_DEFAULT_VIEW,
CRect(0, 0, 0, 0), pSplitter, 0, NULL);
}When we already have an existing view (m_pView1 in our example), we can make this view active as follows:

Collapse Copy Code
CView* pOldActiveView = SwitchToView(m_pView1);
if (!pOldActiveView)
// there was not an active view
else
// pOldActiveView is a pointer to the now inactive viewNote that inactive views destroy themselves when their parent window is destroyed, so you don't have to worry about destroying them.
分享到:
评论

相关推荐

    威盛 PM880/PM800芯片组产品简介(英文).pdf

    1. 高级内存控制器:支持高速的DDR内存,并具备先进的内存管理能力。 2. 高性能CPU接口:提供了与CPU通信的快速通道,确保了处理器性能的有效发挥。 3. AGP 8X图形接口:支持AGP 8X标准,提供高达2.13Gbps的数据...

    威盛 VX700移动随芯技术简介(英文).pdf

    VIA VX700还具备视频捕捉功能以及DuoView+™,后者是一种先进的双显示器输出技术,能扩展用户的显示体验。 音频方面,VIA VX700集成了VIA Vinyl HD 音频技术,为用户提供高级的音频体验。在内存控制器方面,VIA ...

    威盛电子发布PCI Express芯片组,支持威盛处理器平台

    威盛CN800芯片组内置了威盛UniChrome Pro集成显卡,具备硬件MPEG-2播放能力,这意味着它可以高效地处理视频解码任务,减轻CPU的负担,同时支持DuoView+技术,允许用户在同一时间内实现双屏独立显示,这对于多任务...

    基于微信小程序的社区门诊管理系统php.zip

    基于Php语言设计并实现了微信小程序的社区门诊管理系统。该小程序基于B/S即所谓浏览器/服务器模式,选择MySQL作为后台数据库去开发并实现一个以微信小程序的社区门诊为核心的系统以及对系统的简易介绍。 用户注册,在用户注册页面通过填写账号、密码、确认密码、姓名、性别、手机、等信息进行注册操作; 用户登录,用户通过登录页面输入账号和密码,并点击登录进行小程序登录操作。 用户登陆微信端后,可以对首页、门诊信息、我的等功能进行详细操作 门诊信息,在门诊信息页面可以查看科室名称、科室类型、医生编号、医生姓名、 职称、坐诊时间、科室图片、点击次数、科室介绍等信息进行预约挂号操作 检查信息,在检查信息页面可以查看检查项目、检查地点、检查时间、检查费用、账号、姓名、医生编号、医生姓名、是否支付、审核回复、审核状态等信息进行支付操作

    白色大气风格的设计师作品模板下载.zip

    白色大气风格的设计师作品模板下载.zip

    工程经济学自考必备软件下载

    工程经济学自考必备软件下载

    UML课程设计报告.doc

    UML课程设计报告.doc

    白色大气风格响应式彩绘精品水果网站模板.zip

    白色大气风格响应式彩绘精品水果网站模板.zip

    白色简洁风格的别墅整站网站模板.zip

    白色简洁风格的别墅整站网站模板.zip

    白色简洁风格的APP展示动态源码下载.zip

    白色简洁风格的APP展示动态源码下载.zip

    VB+access电表管理系统(系统+论文+参考文献)(2024qu).7z

    1、资源项目源码均已通过严格测试验证,保证能够正常运行; 2、项目问题、技术讨论,可以给博主私信或留言,博主看到后会第一时间与您进行沟通; 3、本项目比较适合计算机领域相关的毕业设计课题、课程作业等使用,尤其对于计算机科学与技术等相关专业,更为适合;

    白色大气风格的雪山旅游景区CSS3网站模板.zip

    白色大气风格的雪山旅游景区CSS3网站模板.zip

    基于python开发的大模型调用基础框架(源码)

    介绍 基于python开发的大模型调用基础框架(源码) 使用说明 修改配置文件 cd config vim __init__.py # 在配置文件中添加大模型调用地址,模型名称,API_KEY等配置 启动应用 应用启动分为两种模式,命令行模式和web模式 命令行模式 python main.py cli web模式 python main.py api

    基于JavaWeb的小区物业管理系统源代码+数据库

    基于JavaWeb的小区物业管理系统源代码+数据库 负责数据库的设计和界面的设计和实现; 界面使用 BootStrap 框架,页面自适应效果,修改页面后实现各个功能模块的布局; 负责实现用户登录注册,查看小区活动公告、水电费查询、车费查询信息; 采用的技术:采用 MVC 架构,数据库用 MySql;

    白色简单风格的商务企业网站模板下载.zip

    白色简单风格的商务企业网站模板下载.zip

    数据分析-29-260万用户大型家电和电子产品购买分析(包含数据代码)

    1. 平台在家电和电子产品方面的营运情况如何? 2. 哪些品牌和类别销量最高? 3. 用户消费规律 4. 哪些是我们的重点用户? 5. 平台有哪些优势和不足,需要如何改进?

    全平台数据库管理工具MySQL

    全平台数据库管理工具, 支持 ClickHouse, Presto, Trino, MySQL, PostgreSQL, Apache Druid, ElasticSearch...

    白色大气风格的旅游整站网站模板.zip

    白色大气风格的旅游整站网站模板.zip

    STM32F030单片机控制蜂鸣器.zip

    1、嵌入式物联网单片机项目开发例程,简单、方便、好用,节省开发时间。 2、代码使用KEIL 标准库开发,当前在STM32F030C8T6运行,如果是STM32F030其他型号芯片,依然适用,请自行更改KEIL芯片型号以及FLASH容量即可。 3、软件下载时,请注意keil选择项是jlink还是stlink。 4、有偿指导v:wulianjishu666; 5、如果接入其他传感器,请查看账号发布的其他资料。 6、单片机与模块的接线,在代码当中均有定义,请自行对照。 7、若硬件有差异,请根据自身情况调整代码,程序仅供参考学习。 8、代码有注释说明,请耐心阅读。 9、编译时请注意提示,请选择合适的编译器版本。

    【信息融合】基于matlab多维卡尔曼滤波器传感器信息融合(含GPS)【含Matlab源码 9980期】含报告.zip

    Matlab领域上传的视频均有对应的完整代码,皆可运行,亲测可用,适合小白; 1、代码压缩包内容 主函数:main.m; 调用函数:其他m文件;无需运行 运行结果效果图; 2、代码运行版本 Matlab 2019b;若运行有误,根据提示修改;若不会,私信博主; 3、运行操作步骤 步骤一:将所有文件放到Matlab的当前文件夹中; 步骤二:双击打开main.m文件; 步骤三:点击运行,等程序运行完得到结果; 4、仿真咨询 如需其他服务,可私信博主; 4.1 博客或资源的完整代码提供 4.2 期刊或参考文献复现 4.3 Matlab程序定制 4.4 科研合作

Global site tag (gtag.js) - Google Analytics