blog

枪手亨利

博客园 首页 新随笔 联系 订阅 管理

        在DOC/VIEW结构的应用程序中,要修改主窗口(CMainFrame)的类名,可以利用超类化技术。关于超类化还可以参考浅谈MFC中超类化技术的实现。但是超类化技术对基于对话框基础的应用程序是没有效果。如何修改呢?先看看用超类化改DOC/VIEW结构形式。超类化技术一般有如下几个步骤:
      1.  通过调用 GetClassInfoEx 来获得想要进行超类化操作的窗口类的信息。函数GetClassInfoEx 需要一个指向 WNDCLASSEX 结构的指针,用于当成功返回时填入窗口类的信息。 
      2. 按需要修改 WNDCLASSEX 结构的成员,其中有两个成员必须修改:
              hInstance 存放程序的实例句柄
              lpszClassName 指向一个新类名的指针
              不必修改成员 lpfnWndProc,但大多数情况下还是需要的。但要记住如果要使用函数CallWindowProc
              调用老窗口的过程,那就必须保存成员 lpfnWndProc 的原值。 
      3. 注册修改完的 WNDCLASSEX 结构,得到一个具有旧窗口类某些特性的新窗口类。
      4. 用新窗口类创建窗口

由此修改主窗口类名的可以如下操作:
BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)
{
         if( !CFrameWnd::PreCreateWindow(cs) )
                  return FALSE;
         //修改主窗口类名
         WNDCLASS wndclass;
         //GetClassInfo返回注册窗口类信息
         ::GetClassInfo(AfxGetInstanceHandle(),cs.lpszClass,&wndclass);
         //重新设置窗口类的类名
         wndclass.lpszClassName="New ClassName";
         //重新注册新的窗口类
         VERIFY(AfxRegisterClass(&wndclass));
        // 利用新注册的类名修改主窗口类名
         cs.lpszClass=wndclass.lpszClassName;
 
         return TRUE;
}

同样的方法在基于对话框的应用程序里不起作用,因为对话框在过程根本没有进入这个函数,在MS KB中介绍了另一中修改此类程序类名的方法:
1 修改对话框资源  
   在工作区的资源标签上右键点击最上边的那个“xx  resources”  
         在弹出的对话框中,去掉“Enable  MFC  feature”复选项  
   再打开对话框资源的属性对话框,在右下角的class  name输入你要修改的类名。比如”xxx”   
   再加上“Enable  MFC  feature”复选项  
 
2 在你的InstInstatce()虚函数中:  
  WNDCLASS  wc  =  {0};  
       ::GetClassInfo(AfxGetInstanceHandle(),"#32770",&wc);  
       wc.lpszClassName="xxx";  
       AfxRegisterClass(&wc);  
 然后重新编译即可。
原文参考:Q251059 - HOWTO: Provide Your Own Window Class Name for an MFC Dialog Box





























在MFC中使用自定义窗口类

1、在CYourApp::InitInstance中注册窗口类
WNDCLASS wc;
wc.cbClsExtra = 0;
wc.cbWndExtra = 0;
wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
wc.hCursor = LoadCursor(IDC_ARROW);
wc.hIcon = NULL;
wc.hInstance = AfxGetInstanceHandle();
wc.lpfnWndProc = ::DefWindowProc; // 注意指定窗口过程
wc.lpszClassName = _T("MyWnd_class"); // 指定窗口类
wc.lpszMenuName = NULL;
wc.style = 0;
AfxRegisterClass(&wc);


2、编写.h文件类的定义
#ifndef MY_WND
#define MY_WND


class CMyWnd : public CWnd
{
public:
    // 构造函数、析构函数等公有接口的声明
protected:
    // 各消息处理函数的声明
    DECLARE_MESSAGE_MAP()
};


#endif

3、编写.cpp文件类的实现
#include "stdafx.h"
#include "MyWnd.h"


// 构造函数、析构函数等函数的实现

BEGIN_MESSAGE_MAP(CMyWnd, CWnd)
    // 各消息分流器
END_MESSAGE_MAP()


// 各消息分流器的实现

4、在主程序代码的适当地方调用CreateCreateEx创建窗口。

posted on 2006-01-04 22:07  henry  阅读(1823)  评论(0)    收藏  举报