设为首页 加入收藏

TOP

MFC程序员的WTL指南之分隔窗口(三)
2012-11-04 15:05:14 来源: 作者: 【 】 浏览:1985
Tags:MFC 程序员 WTL 指南 分隔 窗口
  创建一个窗格内的窗口

  既然已经有了分隔窗口和子窗口的成员变量,填充分隔窗口就是一件简单的事情了。先创建分隔窗口,然后创建两个子窗口,使用分隔窗口作为它们的父窗口:

LRESULT CMainFrame::OnCreate ( LPCREATESTRUCT lpcs )
{
 //...
 // Create the splitter window
 const DWORD dwSplitStyle = WS_CHILD | WS_VISIBLE | WS_CLIPCHILDREN | WS_CLIPSIBLINGS,dwSplitExStyle = WS_EX_CLIENTEDGE;

 m_wndVertSplit.Create ( *this, rcDefault, NULL,dwSplitStyle, dwSplitExStyle );

 // Create the left pane (list of clip formats)
 m_wndFormatList.Create ( m_wndVertSplit, rcDefault );

 // Create the right pane (rich edit ctrl)
 const DWORD dwRichEditStyle =
  WS_CHILD | WS_VISIBLE | WS_HSCROLL | WS_VSCROLL |
  ES_READONLY | ES_AUTOHSCROLL | ES_AUTOVSCROLL | ES_MULTILINE;

 m_wndDataViewer.Create ( m_wndVertSplit, rcDefault,NULL, dwRichEditStyle );
 m_wndDataViewer.SetFont ( AtlGetStockFont(ANSI_FIXED_FONT) );


 // Set the splitter as the client area window, and resize
 // the splitter to match the frame size.
 m_hWndClient = m_wndVertSplit;
 UpdateLayout();

 m_wndVertSplit.SetSplitterPos ( 200 );

 return 0;
}

  注意两个类的Create()函数都用m_wndVertSplit作为父窗口,RECT参数无关紧要,因为分隔窗口会重新调整它们的大小,所以可以使用CWindow::rcDefault。

  最后就是将窗口的句柄传递给分隔窗口的窗格,这一步也需要在UpdateLayout()调用之前完成,这样最终所有的窗口都有正确的大小。

LRESULT CMainFrame::OnCreate ( LPCREATESTRUCT lpcs )
{
 //...
 m_wndDataViewer.SetFont ( AtlGetStockFont(ANSI_FIXED_FONT) );

 // Set up the splitter panes
 m_wndVertSplit.SetSplitterPanes ( m_wndFormatList, m_wndDataViewer );


 // Set the splitter as the client area window, and resize
 // the splitter to match the frame size.
 m_hWndClient = m_wndVertSplit;
 UpdateLayout();

 m_wndVertSplit.SetSplitterPos ( 200 );

 return 0;
}

  现在,list控件上增加了几栏,结果看起来是这个样子:


  需要注意的是分隔窗口对放进窗格的窗口类型没有限制,不像MFC那样必须是CView的派生类。窗格窗口只要有WS_CHILD样式就行了,没有任何其他限制。

  消息处理

  由于在主框架窗口和我们的窗格窗口之间加了一个分隔窗口,你可能想知道现在通知消息是如何工作的,比如,主框架窗口是如何收到NM_CUSTOMDRAW通知消息并将它反射给list控件的?答案就在CSplitterWindowImpl的消息链中:

BEGIN_MSG_MAP(thisClass)
 MESSAGE_HANDLER(WM_ERASEBKGND, OnEraseBackground)
 MESSAGE_HANDLER(WM_SIZE, OnSize)
 CHAIN_MSG_MAP(baseClass)
 FORWARD_NOTIFICATIONS()
END_MSG_MAP()

  最后的哪个FORWARD_NOTIFICATIONS()宏最重要,回忆一下第四章,有一些通知消息总是被发送的子窗口的父窗口,FORWARD_NOTIFICATIONS()就是做了这些工作,它将这些消息转发给分隔窗口的父窗口。也就是说,当list窗口发送一个WM_NOTIFY消息给分隔窗口时(它是list的父窗口),分隔窗口就将这个WM_NOTIFY消息转发给主框架窗口(它是分隔窗口的父窗口)。当主框架窗口反射回消息时会将消息反射给WM_NOTIFY消息的最初发送者,也就是list窗口,所以分隔窗口并没有参与消息反射。

  在list窗口和主框架窗口之间的这些消息传递并不影响分隔窗口的工作,这使得在程序中添加和移除分隔窗口非常容易,因为子窗口不需要做任何改变就可以继续工作。

首页 上一页 1 2 3 4 5 6 7 下一页 尾页 3/11/11
】【打印繁体】【投稿】【收藏】 【推荐】【举报】【评论】 【关闭】 【返回顶部
分享到: 
上一篇VC程序中实现控件的动态生成与响应 下一篇制作一个基于MFC对话框的OpenGL类

评论

帐  号: 密码: (新用户注册)
验 证 码:
表  情:
内  容: