• 网络学院
  • IT资讯
  • 操作系统
  • 网络技术
  • 软件应用
  • 办公软件
  • 编程技术
  • 网站架设
  • 数据库类
  • 平面设计
  • 多媒体类
  • 游戏资讯
  • 教学论文
  • 认证考试
MFC类中获得其它类指针
  站点:
  • 首 页
  • 最新软件
  • 文章教程
  • 国内软件
  • 国外软件
  • 绿色软件
  • 源码下载
  • 字体下载
MFC类中获得其它类指针
软件发布 MFC类中获得其它类指针
网络软件 系统工具 应用软件 联络聊天 图形图像 多媒体类 行业软件 游戏娱乐 编程开发 安全相关 教育教学 数码软件 绿软下载
热门软件: QQ 瑞星 pplive e话通 木马克星 千千静听 office2000 五笔字根 Photoshop 视频分割
返回文章教程首页 >> 文章首页 >> 编程技术 >> C/C++教程 >> MFC类中获得其它类指针

MFC类中获得其它类指针

添加时间: 2006-2-15 3:38:25  作者: C++教程  阅读次数:168   来源: http://d9soft.com

       

  当用VC++的Application Wizard生成除了CDialog Basiced以外的应用程序时,将自动产生视图类、文档类、主帧窗口类、应用程序类等等。一般来说,程序的核心数据及操作在文档类中实现。跟界面有关的数据及操作在视图类中实现。当需要在某个类中使用不属于该类的数据时,必须要取得该数据所属类的指针。从视图类获得文档类的指针是很容易的,用GetDocument即可,这在一般的MFC文档中有介绍,也是编程中极为常用的的操作,比如视图类在进行重画等操作时,往往要用到文档类中的数据。然而只能从视图类获得文档类的指针是远远不够的,每个类都有获得其它各个类指针的一套方法,现归纳如下: 为方便说明,现假设已用Application Wizard生成一个SDI应用程序Test,包含如一几个类:CTestApp,CTestDoc,CTestView,CMainFrm.1.从视图类获得文档类的指针 如前所述,在视图类中需要引用文档类的地方之前,使用以下语句:

  CTextDoc *pDoc=(CTestDoc*)GetDocument();

  以后便可使用pDoc指针访问文档类。

  此处的强制类型转换在Test应用程序中并不必需,因为该程序中只有一个视图类,并且在Initstance()中用SDI文档模板进行了装配,你可以在Test.cpp中的Initstance()方法中看到以下语句:

  CSingleDocTemplate *pDocTemplate;

  pDocTemplate=new CSingleDocTemplate(IDR_MAINFRAME,RUNTIME_CLASS(CTestDoc),RUNTIME_CLASS(CMainFrame),

  RUNTIME_CLASS(CTestView));

  AddDocTemplate(pDocTemplate);

  以及TestView.h中的线上定义:

  inline CTestDoc* CTestView::GetDocument()

  { return (CTestDoc*)m_pDocument;}

  简而言之,就是说CTestView的GetDocument()函数自然而然地认为CTestDoc是与它“相配”的,当生成了一个具有多个视图类的应用程序时(如用CSplitterWnd)将窗口分为两栏,但这两栏并非从同一种视图类派生就属于这种情况。具体实现在本文讨论范围之外),只有一个视图类能与唯一的文档类用文档模板进行装配,那么在另外一个未经装配的类中要取得文档类的指针,则需时行强制类型转换。2.从文档类取得视图类的指针 CDocument类提供了两个函数用于视图类的定位:GetFirstViewPosition()和
 GetNextView(),具体语法如下:

  virtual POSITION GetFirstViewPosition() const;

  virtual CView* GetNextView(POSITION& rPosition) const;

  注意:GetNextView()括号中的参数用的是引用方式,因此执行后值可能改变。

  GetFirstViewPosition()用于返回第一个视图位置(返回的并非视图类指针,而是一个POSITION类型值),GetNextView()有两个功能:返回下一个视图类的指针以及用引用调动的方式来改变传入的POSITION类型参数的值。很明显,在Test程序中,只有一个视图类,因此只需将这两个函数调用一次即可得到CTestView的指针如下(需定义一个POSITION结构变量来辅助操作):

  CTestView* pTestView;

  POSITION pos=GetFirstViewPosition();

  pTestView=GetNextView(pos);

  这样,便可到了CTestView类的指针pTestView.执行完成几句后,变量pos=NULL,因为没有下一个视图类,自然也没有下一个视图类的POSITION.但是之几条语句太简单,不具有太强的通用性和安全特征;当象前面说的那样,当要在多个视图为中返回某个指定类的指针时,我们需要遍历所有视图类,直到找到指定类为止。判断一个类指针指向的是否某个类的实例时,可用IsKindOf()成员函数时行检查,如:

  pView->IsKindOf(RUNTIME_CLASS(CTestView));

  即可检查pView所指是否是CTestView类。

  有了以上基础,我们已经可以从文档类取得任何类的指针。为了方便,我们将其作为一个文档类的成员函数,它有一个参数,表示要获得哪个类的指针。实现如下:

  CView* CTestDoc::GetVieww(CRuntimeClass* pClass)

  { CView* pView;

  POSITION pos=GetFirstViewPosition();

  while(pos!=NULL){

  pView=GetNextView(pos);

  if(!pView->IsKindOf(pClass))

  break;}

  if(!pView->IsKindOf(pClass)){

  AfxMessageBox("Connt Locate the View.");

  return NULL;}

  return pView;}

  其中用了两次视图类的成员函数IsKindOf()来判断,是因为退出while循环有三种可能:

  1.pos为NULL,即已经不存在下一个视图类供操作;

  2.pView已符合要求。

  3.1和2同是满足。这是因为GetNextView()的功能是将当前视图指针改变成一个视图的位置同时返回当前视图指针,因此pos是pView的下一个视图类的POSITION,完全有可能既是pos==NULL又是pView符合需要。当所需的视图是最后一个视图是最后一个视图类时就如引。因此需采用两次判断。

  使用该函数应遵循如下格式(以取得CTestView指针为例):

  CTestView* pTestView=(CTestView*)GetView(RUNTIME_CLASS(CTestView));

  RUNTIME_CLASS是一个宏,可以简单地理解它的作用:将类的名字转化为CRuntimeClass为指针。

  至于强制类型转换也是为了安全特性考虑的,因为从同一个基类之间的指针类型是互相兼容的。这种强制类型转换也许并不必要,但能避免一些可能出现的麻烦。3.从一个视图类取得另一视图类的指针 综合1和2,很容易得出视图类之间互相获得指针的方法:就是用文档类作中转,先用1的方法得到文档类的指针,再用2的方法,以文档类的视图定位函数取得另一个视图类。同样,可以实现成一个函数:

  (假设要从CTestAView中取得指向其它视图类的指针)

  CView* CTestAView::GetView(CRuntimeClass* pClass)

  { CTestDoc* pDoc=(CTestDoc*)GetDocument();

  CView* pView;

  POSITION pos=pDoc->GetFirstViewPosition();

  while(pos!=NULL){

  pView=pDoc->GetNextView(pos);

  if(!pView->IsKindOf(pClass))

  break;}

  if(!pView->IsKindOf(pClass)){

  AfxMessageBox("Connt Locate the View.");

  return NULL;}

  return pView;}

  这个函数和2中的GetView()相比,一是多了第一句以取得文档类指针,二是在GetFirstViewPosition()和GetNextView()前加上了文档类指针,以表示它们是文档类成员函数。

  有了此函数;当要从CTestAView中取得CTestBView的指针时,只需如下:

  CTestBView* pTestbView=(CTestView*)GetView(RUNTIME_CLASS(CTestBView));4. 从主帧窗口类获得视图类指针 对本文所举的Test这各SDI程序来说,这是简单的,只需用CFrameWnd类的GetActiveView()成员函数即可。格式如下:

  CFrameWnd::GetActiveView()

  但将此函数应用在MDI应用的CMDIFrameWnd为中时,并不象所想的那样获得当前活动子窗口的视图类,而是返回NULL,这是一个要领性问题。在MDI程序中,CMDIFrameWnd没有和任何视图类发生关系,也就是说没有视图类直接属于它,只有子帧窗口类CMDIChildWnd才是所有子窗口视图类的父窗口。而子帧窗口的父窗口才是CFrameWnd。因此,在MDI程序中获得活动视图类的正确方法应为:先获得活动子帧窗口,再从活动子帧窗口中获得活动视图类:

  //获得活动子帧窗口

  CMDIChildWnd* pChild=(CMDIChildWnd*)GetActiveFrame();

  //或:CMDIChildWnd* pChild=MDIGetActive();

  //获得活动子帧窗口的活动视图

  CMyView* pView=(CMyView*)pChild->GetActiveView();5.从视图类中获得主帧窗口类指针:用函数:CWnd::GetParentFrame()或AfxGetMainWnd();

  可达到目的。GetParentFrame()的工作原理是在父窗口链中搜索,直到找到CFrameWnd或其派生类为止,并返回其指针。用法在InfoViewer中有详细介绍。6.在任何类中获得应用程序类

  用MFC全局函数AfxGetApp()可做到。7.从应用程序类中获得主帧窗口类

  CWinThread类有一个数据成员叫m_pMainWnd,由于CWinApp类由CWinThread派生而来,我们的应用程序为又由CWinApp派生而来,所以我们的CTestApp类也有一个m_pMainWnd成员,它所指南的即是CMainFrame类。(需进行合适的强制类型转换)。总结起来有几点注意:

  A.在类A中获得类B的指针时,类A应包含类B的头文件。

  B.在很多时候要进行强制类型转换,并要注意括号的括法。

  由于派生类和父类指针类型的兼容,使明确区分各个类变得十分重要。在拿不准的时候,最好加上强制类型转换。

 

上下文章:

 

上一篇文章: 三维视图绘制与消隐技术 下一篇文章: 强大的语言——C入门

相关文章:

  • 在MySQL中获得更好的全文搜索结果(3)
  • 在MySQL中获得更好的全文搜索结果(4)完
  • 全球获得Oracle认证人数统计
  • 全球获得Oracle认证人数最新统计
  • 如何获得Oracle DBA工作?

相关软件:

 

快速导航

  • 网络学院
  • 精品汇聚
  • 字体下载
  • 教程下载
  • ASP源码
  • PHP源码
  • Net源码
  • JSP 源码

编程技术分类导航

  • ASP & ASP.NET教程
  • PHP教程
  • JSP教程
  • C/C++教程
  • VB & VB.NET教程
  • VC教程
  • Delphi教程
  • BCB教程
  • VFP教程
  • PB教程
  • JAVA教程
  • XML教程
  • C#教程
  • CGI教程

本类经典文章推荐

  • C/C++作用域引申出的编码规范
  • 程序宝典:C++学习感想
  • C语言:黑客学员必修课(一)
  • C语言:黑客学员必修课(二)
  • 使用多线程实现数据实时采集
  • C++编程中的四个调试小技巧
  • C语言程序设计基础之联合
  • 学C++不得不看的一篇文章
  • C,曾经的程序员梦
  • 水滴石穿C语言之可变参数问题

C/C++教程阅读排行

  • 学C++不得不看的一篇文章
  • 水滴石穿C语言之可变参数问题
  • C语言:黑客学员必修课(一)
  • 程序宝典:C++学习感想
  • 我的Visual C++入门之路
  • 初学者学习C++的50条忠告
  • C++中的struct专题研究
  • C++箴言:只要可能就用const
  • 强大的语言——C入门
  • C++编程中的四个调试小技巧

编程技术阅读总排行

  • VB入门教程之一
  • Java连接数据库实例
  • 第二章 PowerBuilder 入门之创建新...
  • VC++之List Box/Check List Box控...
  • 第一章 什么是PowerBuilder
  • VC++ List Ctrl控件
  • VC++ Combo Box/Combo Box Ex控件
  • 学C++不得不看的一篇文章
  • VB入门教程之二
  • VC++之Button控件

广告位置

字母检索 A B C D E F G H I J K L M N O P Q R S T U V W X Y Z 回到顶部

关于我们 | 版权声明 | 免责条款 | 广告联系 | 软件发布 | 下载帮助 | 下载排行 | 网站地图 | 特别鸣谢 | 友情连接

copyright; 2005-2008 D9soft.com 第九软件网 版权所有