VC++常用功能详解.docx
- 文档编号:7331366
- 上传时间:2023-01-23
- 格式:DOCX
- 页数:13
- 大小:20.70KB
VC++常用功能详解.docx
《VC++常用功能详解.docx》由会员分享,可在线阅读,更多相关《VC++常用功能详解.docx(13页珍藏版)》请在冰豆网上搜索。
VC++常用功能详解
常用功能代码目录
在View中如何得到Doc中的数据?
在Doc中如何通知相关的View更新显示?
在Doc中如何得到与它相关的视图Views?
怎样得到应用程序类?
怎样得到应用程序的主框架类Frame?
怎样在自定义类中得到当前视图View类?
怎样在框架类中得到当前文档Doc类?
怎样在自定义类中得到当前文档Doc类?
获取所有菜单项的数目。
设置菜单的风格。
SDI单文档状态栏编程
VC++头文件的包含顺序问题。
几种DC之间的区别
在绘图之前擦除屏幕
CSocket类网络通信编程步骤
在View中如何得到Doc中的数据?
在Doc中如何通知相关的View更新显示?
在Doc中如何得到与它相关的视图Views?
怎样得到应用程序类?
怎样得到应用程序的主框架类Frame?
怎样在自定义类中得到当前视图View类?
怎样在框架类中得到当前文档Doc类?
怎样在自定义类中得到当前文档Doc类?
获取所有菜单项的数目。
设置菜单的风格。
SDI单文档状态栏编程
VC++头文件的包含顺序问题。
几种DC之间的区别
在绘图之前擦除屏幕
CSocket类网络通信编程步骤
在View中如何得到Doc中的数据?
为了显示和修改文档类的数据,在CView类中有一指向相应文档类对象的指针变量m_pDocument。
m_pDocument在CView中被说明为指向CDocument类的指针,而在具体的应用中文档类一般都是CDocument类的派生类,必须对m_pDocument指针进行强制类型转换才能利用它检索CDocument派生类的特有数据。
为此AppWizard在CView的派生类中专门生成了一成员函数GetDocument()来完成这一转换。
A、首先,使用下面的语句得到DOC的对象指针:
CC501WriterDoc*pDoc=GetDocument();
B、如果所用数据是DOC中的public类型的成员,则可直接访问如下:
pDoc->data;
但是按照C++的编程风格,一个类中的数据要尽量使用private型,同时给出两个访问的成员函数Get()和Set()。
这样得到数据就要用如下形式:
CStringtext=pDoc->GetData();
在Doc中如何通知相关的View更新显示?
在CDocument的派生类中调用以下语句:
UpdateAllViews();
在Doc中如何得到与它相关的视图Views?
在CDocument的派生类中,要得到与它相关的用于显示的视图可调用以下语句:
POSITIONpos=GetFirstViewPosition();//取得第一个视图
CC501WriterView*pv=(CC501WriterView*)GetNextView(pos);//下一个视图
怎样得到应用程序类?
在任何地方可使用以下形式得到:
CC501WriterApp*pApp=(CC501WriterApp*)AfxGetApp();
或者直接使用全局变量theApp。
MFC为我们提供了一个全局函数AfxGetInstanceHandle(),可以用来获取当前应用程序的实例句柄。
怎样得到应用程序的主框架类Frame?
在任何地方可使用以下形式得到:
CMainFrame*pFrm=(CMainFrame*)AfxGetMainWnd();
或者CMainFrame*pFrm=(CMainFrame*)AfxGetApp()->m_pMainWnd;
如果当前类是在App中,则还可以用以下方法得到:
CMainFrame*pFrm=(CMainFrame*)m_pMainWnd;
或者CMainFrame*pFrm=(CMainFrame*)GetMainWnd;
怎样在自定义类中得到当前视图View类?
程序中往往有程序员自已增加的类,例如用户生成的一个对话框类。
在这些自定义类中要得到当前的视图View类时,可以使用以下方法:
CMainFame*pFrm=(CMainFame*)AfxGetMainWnd();
CC501WriterView*pv=(CC501WriterView*)pFrm->GetActiveView();
怎样在框架类中得到当前文档Doc类?
CSDISplitterDoc*pDoc=(CSDISplitterDoc*)GetActiveDocument();
怎样在自定义类中得到当前文档Doc类?
在自定义类中要得到当前的文档DOC类时,可以按标题五的步骤做,然后:
CC501WriterDoc*pDoc=(CC501WriterDoc*)pv->GetDocument();
或者:
CMainFrame*pFrm=(CMainFrame*)AfxGetMainWnd();
CC501WriterDoc*pDoc=(CC501WriterDoc*)pFrm->GetActiveDocument();
获取所有菜单项的数目。
A、以CMenu类为基类派生一个CCustomMenu类,CCustomMenu类常用于菜单的绘制。
B、在CCustomMenu类的头文件中声明变量或函数,代码如下:
staticintGetAllItemCount(HMENUhMenu,int&ItemCount,BOOLFirstFind=TRUE);
intm_ItemCount;
intAttatchMenu(HMENUhMenu);
C、添加AttatchMenu方法,该方法将当前窗口的菜单与自定义的菜单关联,代码如下:
intCCustomMenu:
:
AttatchMenu(HMENUhMenu)
{
Attach(hMenu);
intcount=GetAllItemCount(hMenu,m_ItemCount);
returncount;
}
D、添加静态GetAllItemCount方法,该方法用于得到所有菜单项的数目,代码如下:
intCCustomMenu:
:
GetAllItemCount(HMENUhMenu,int&ItemCount,BOOLFirstFind)
{
CMenu*pMenu=CMenu:
:
FromHandle(hMenu);//获得菜单的句柄
if(pMenu)
{
if(FirstFind)
{
ItemCount=0;
}
intcount=pMenu->GetMenuItemCount();
ItemCount+=count;
CMenu*pSubMenu=NULL;
for(inti=0;i { pSubMenu=pMenu->GetSubMenu(i); if(pSubMenu! =NULL) { GetAllItemCount(pSubMenu->m_hMenu,ItemCount,FALSE); } } } returnItemCount; } E、然后在框架类或对话框类的OnCreate()函数或OnInitDialog()函数中调用AttatchMenu函数,代码如下: HMENUhMenu=GetMenu()->GetSafeHmenu(); if(hMenu! =NULL) { //CCustomMenum_Menu; intcount=m_Menu.AttatchMenu(hMenu); } 设置菜单的风格。 A、以CMenu类为基类派生一个CCustomMenu类,CCustomMenu类常用于菜单的绘制。 B、在CCustomMenu类的头文件中定义一个CMenuItem结构体,代码如下: structCMenuItem { CStringm_MenuText;//菜单项的文本 UINTm_ImageIndex;//菜单项图像索引 intm_MenuType;//菜单项的类型,-2顶层菜单,-1弹出式菜单,0分隔条,其他普通菜单 }; C、在CCustomMenu类的头文件中声明变量或函数,代码如下: BOOLSetMenuItemInfo(CMenu*pMenu,BOOLToped=TRUE); intm_ItemCount; intm_Index;//遍历菜单时使用的索引 CMenuItem*m_MenuList; intAttatchMenu(HMENUhMenu); D、添加AttatchMenu方法,该方法将当前窗口的菜单与自定义的菜单关联,代码如下: intCCustomMenu: : AttatchMenu(HMENUhMenu) { Attach(hMenu); intcount=GetAllItemCount(hMenu,m_ItemCount); if(m_ItemCount>0) m_MenuList=newCMenuItem[m_ItemCount]; returncount; } E、添加SetMenuItemInfo方法,该方法用于设置菜单风格,代码如下: BOOLCCustomMenu: : SetMenuItemInfo(CMenu*pMenu,BOOLToped) { if(pMenu! =NULL) { intMenuCount=pMenu->GetMenuItemCount(); for(inti=0;i { //获得菜单文本 pMenu->GetMenuString(i,m_MenuList[m_Index].m_MenuText,MF_BYPOSITION); UINTMenuID=pMenu->GetMenuItemID(i);//获得菜单ID //MenuID=-1,Toped=FALSE;表示弹出式菜单 if((MenuID=-1||MenuID==65535)&&Toped==TRUE) { MenuID=-2; } m_MenuList[m_Index].m_MenuType=MenuID;//设置菜单列表 //修改菜单风格 pMenu->ModifyMenu(i,MF_OWNERDRAW|MF_BYPOSITION|MF_STRING,m_MenuList[m_Index].m_MenuType,(LPSTR)&(m_MenuList[m_Index])); m_Index+=1; CMenu*pSubMenu=pMenu->GetSubMenu(i);//获得子菜单句柄 if(pSubMenu) { SetMenuItemInfo(pSubMenu,FALSE);//递归调用SetMenuItemInfo } } } returnTRUE; } F、然后在框架类或对话框类的OnCreate()函数或OnInitDialog()函数中调用SetMenuItemInfo函数,代码如下: HMENUhMenu=GetMenu()->GetSafeHmenu(); if(hMenu! =NULL) { //CCustomMenum_Menu; intcount=m_Menu.AttatchMenu(hMenu); m_Menu.SetMenuItemInfo(&m_Menu);//设置菜单项 } SDI单文档状态栏编程 A、自定义状态栏指示器。 在资源的StringTable中添加: IDS_STATE颜色 在MainFram.cpp中添加IDS_STATE staticUINTindicators[]= { ID_SEPARATOR,//statuslineindicator IDS_STATE,//添加的内容 ID_INDICATOR_CAPS, ID_INDICATOR_NUM, ID_INDICATOR_SCRL, }; B、在MainFrm.h中修改: public: CStatusBarm_wndStatusBar;//默认为私有,这里改为公有 C、在CmyTestView.cpp中加入#include“MainFrm.h” D、在视类中的消息响应函数中添加: CSizesz=dc.GetTextExtent(str); CMainFrame*pFrame=(CMainFrame*)AfxGetMainWnd(); pFrame->m_wndStatusBar.SetPaneInfo(1,IDS_STATE,SBPS_NORMAL,sz.cx); pFrame->m_wndStatusBar.SetPaneText(1,str); VC++头文件的包含顺序问题。 如果顺序不对会有以下错误: errorC2143: syntaxerror: missing';'before'*' errorC2501: 'CMyTestView': missingstorage-classortypespecifiers errorC2501: 'pv': missingstorage-classortypespecifiers 在任何cpp文件的开头都应该以这样的顺序: #include"MyTestDoc.h" #include"MyTestView.h" #include"MainFrm.h" 注意,Doc的头文件一定要在最前面。 这样你的CDemoView和CMyView也可以共享一个CDemoDoc。 一般在Cpp中包含文件是要注意类的包含关系,被包含的类定义应该在前面。 如果实在有冲突,可以在一个类的头文件中加: classCXXXDoc;之类的空定义。 这样定义过的头文件中可以用CXXXDoc申明指针,但是不能申明实际对象。 几种DC之间的区别 CDC及其派生类的继承视图: Cobject public|------CDC public|------|------CClientDC public|------|------CpaintDC public|------|------CwindowDC public|------|------CMetaFileDC CClientDC: (客户区设备上下文)用于客户区的输出,与特定窗口关联,可以让开发者访问目标窗口中客户区,其构造函数中包含了GetDC,析构函数中包含了ReleaseDC: 用法是: CClientDCdc(this);//this一般指向本窗口或当前活动视图 dc.TextOut(10,10,str,str.GetLength());//利用dc输出文本,如果是在CScrollView中使用,还要注意调用OnPrepareDC(&dc)调整设备上下文的坐标。 CPaintDC用于响应窗口重绘消息(WM_PAINT)是的绘图输出。 CPaintDC在构造函数中调用BeginPaint()取得设备上下文,在析构函数中调用EndPaint()释放设备上下文。 EndPaint()除了释放设备上下文外,还负责从消息队列中清除WM_PAINT消息。 因此,在处理窗口重画时,必须使用CPaintDC,否则WM_PAINT消息无法从消息队列中清除,将引起不断的窗口重画。 CPaintDC也只能用在WM_PAINT消息处理之中。 CPaintDC: : CPaintDC(CWnd*pWnd) { ... if(! Attach(: : BeginPaint(m_hWnd=pWnd->m_hWnd,&m_ps))) AfxThrowResourceException(); } CPaintDC: : ~CPaintDC() { ... : : EndPaint(m_hWnd,&m_ps); Detach(); } CWindowDC: 关联一特定窗口,允许开发者在目标窗口的任何一部分进行绘图,包含边界与标题,这种DC同WM_NCPAINT消息一起发送 CWindowDC与CClientDC,CPaintDC的区别: CWindowDC可在非客户区绘制图形,而CClientDC,CPaintDC只能在客户区绘制图形。 CWindowDC下坐标原点是在屏幕的左上角,CClientDC,CPaintDC下坐标原点是在客户区的左上角。 //CWindowDCdc(this);//this代表只能在view区域绘画 //CWindowDCdc(GetParent());//在整个frame区域绘画 CWindowDCdc(GetDesktopWindow());//可在整个桌面区域绘画 dc.MoveTo(m_ptOrigin); dc.LineTo(point); CClientDC与CPaintDC的区别: CPaintDC的对象一般用在OnPaint内以响应Windows消息WM_PAINT,自动完成绘制,在整个窗口内进行重画,维持原有窗口完整性。 CClientDC应用在非响应Windows消息WM_PAINT的情况下,进行实时绘制,绘制的区域内被重画。 另外CDC和HDC都要手动释放。 HDChDC; hDC=: : GetDC(m_hWnd); MoveToEx(hDC,m_ptOrigin.x,m_ptOrigin.y,NULL); LineTo(hDC,point.x,point.y); : : ReleaseDC(m_hWnd,hDC); CDC*pDC=GetDC(); pDC->MoveTo(m_ptOrigin); pDC->LineTo(point); ReleaseDC(pDC); 方法一: 此方法在设备结束时不会销毁原来的资源(即: hDC,hBitmap) CDC*pDC=CDC: : FromHandle(hDC); 方法二: 此方法在设备结束时会销毁原来的资源(即: hDC,hBitmap) CDCdc; dc.Attach(hDC); 在绘图之前擦除屏幕 CClientDCdc(this); RECTrc; GetClientRect(&rc); PatBlt(dc,rc.left,rc.top,rc.right,rc.bottom,WHITENESS);//刷上白色 CSocket类网络通信编程步骤 1.构造CSocket对象,如以下的形式: CSocketServersocket; 2.利用CSocket对象的Create()函数创建WindowsSocket,Create()函数会调用Bind()函数将此Socket绑定到指定的地址上,其原型为: BOOLCreate(UINTnSocketPort=0,intnSocketType=SOCK_STREAM,LPCTSTRlpszSocketAddress=NULL); 其中nSocketPort参数指定通信连接的端口号,端口号可以任意指定,但最好不要使用系统默认的一些端口号,例如21是FTP文件传输使用的端口号; 3.Socket创建完毕之后,在服务器端进行监听客户的连接请求,使用如下的代码: ServerSocket.Listen(); 紧接着对于客户端而言,将会调用Connect()函数向服务器发送连接请求,而对于服务器而言,则会调用Accept()函数对客户端发送过来的请求连接进行接受和处理,Accept()函数可以创建一个和监听Socket相同的连接Socket来处理客户的请求,二原来的Socket仍然处于监听状态,使用的形式如下。 客户端: ClientSocket.Connect(服务器的地址,服务器的端口号); 服务器端: CSocketReceiveSocket; ServerSocket.Accept(连接Socket,客户的地址结构,客户地址结构的长度) 4.对于数据流服务器类型而言,服务器和客户各自通过调用函数来完成数据的发送和接受,使用如下的语句: ServerReceive.Receive(缓冲区,缓冲区的长度,接受标志位); Client.Send(缓冲区,缓冲区的长度,发送标志位); 5.在客户端与服务器端的数据传输完成之后,调用下述语句,释放Socket所占有的资源。 ServerSocket.Close(); ReceiveSocket.Close(); ClientSocket.Close();
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- VC 常用 功能 详解