详解CREATESTRUCT结构体

CREATESTRUCT结构定义了传递给应用程序的窗口过程的初始化参数,它定义了窗口外观相关特性,CREATESTRUCT结构具有如下形式:

typedef struct tagCREATESTRUCT
{
  LPVOID  lpCreateParams;  //指向将被用于创建窗口的数据的指针。  
  HANDLE  hInstance;       //标识了拥有新窗口的模块的模块实例的句柄。  
  HMENU   hMenu;           //标识了要被用于新窗口的菜单。如果是子窗口,则包含整数ID。  
  HWND    hwndParent;      //标识了拥有新窗口的窗口。如果新窗口是一个顶层窗口,这个参数可以为NULL。  
  int     cy;              //指定了新窗口的高。  
  int     cx;              //指定了新窗口的宽。  
  int     y;               //指定了新窗口的左上角的y轴坐标。  
  int     x;               //指定了新窗口的左上角的x轴坐标。 
  LONG    style;           //指定了新窗口的风格。  
  LPCSTR  lpszName;        //指向一个以null结尾的字符串,指定了新窗口的名字。  
  LPCSTR  lpszClass;       //指向一个以null结尾的字符串,指定了新窗口的Windows类名
  DWORD   dwExStyle;       //指定了新窗口的扩展风格。  
} CREATESTRUCT;


在MFC中我们利用MFC向导就可以创建一个单文档和多文档APP,这里主要用单文档应用程序举例。MFC封装了Win32 API使得我们窗口的创建更加简单,利用APP Wizard可以生成具有默认属性的窗口程序。如果我们需要修改应用程序的默认属性,可以调用PreCreateWindow函数和SetWindowLong函数就行自定义,下面分别介绍之。


PreCreateWindow函数


PreCreateWindow函数从字面上看,就知道它是创建窗口有关系,它是在窗口创建之前进行外观修改,通过重载该函数,可以修改CREATESTRUCT结构,从而加入用户自定义的属性,其函数声明如下:

virtual BOOL PreCreateWindow( CREATESTRUCT& cs );
在SDI程序CMainFrame类中,一般都会自带该函数的实现,代码如下:
BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)
{
	if( !CFrameWnd::PreCreateWindow(cs) )
		return FALSE;
	// TODO: 在此处通过修改
	//  CREATESTRUCT cs 来修改窗口类或样式

	return TRUE;
}

由于该函数是虚函数,因此MFC底层代码创创建窗口之前,先会调用该函数,从而实现默认属性修改,这里我们修改宽度和高度,增加水平和垂直的滚动条,以及删除可调边框属性。

例子1 修改外观

BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)
{
    if( !CFrameWnd::PreCreateWindow(cs) )
        return FALSE;
    // TODO: 在此处通过修改
    //  CREATESTRUCT cs 来修改窗口类或样式
    //改变大小
    cs.cx = 500; 
    cs.cy = 400;
    //增加水平和垂直滚动条
    cs.style |= WS_HSCROLL | WS_VSCROLL;
    //去除可调边框属性
    cs.style &= ~WS_THICKFRAME ;

    return TRUE;
}
运行效果对比:


例子2:修改窗口标题

     在默认的单文档和多文档应用程序中,框架窗口stytle风格都包含有FWS_ADDTOTITLE这个属性,其含义是将文档的标题做为窗口的标题,如果需要自定义窗口标题,需要将这个属性删除,具体代码如下:

BOOL CMainFrame::PreCreateWindow(CREATESTRUCT& cs)
{
    if( !CFrameWnd::PreCreateWindow(cs) )
        return FALSE;
    //  CREATESTRUCT cs 来修改窗口类或样式
    //改变大小
    cs.cx = 400; 
    cs.cy = 300;
    //增加水平和垂直滚动条
    cs.style |= WS_HSCROLL | WS_VSCROLL;
    //去除FWS_ADDTOTITLE属性
    cs.style &= ~FWS_ADDTOTITLE ;
    //自定义标题
    cs.lpszName = "HelloWorld";

    return TRUE;
}
运行效果:




SetWindowLong函数



上面介绍的PreCreateWindow函数是在创建之前进行修改的,而SetWinowLong函数是在窗口创建之后进行修改的。

我们在发现框架类(CMainFrame)中有个OnCreate函数,该函数的功能是完成窗口的创建,其部分代码如下:

int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
    if (CFrameWnd::OnCreate(lpCreateStruct) == -1)
    return -1;
    ...

    // TODO: 如果不需要可停靠工具栏,则删除这三行
    m_wndToolBar.EnableDocking(CBRS_ALIGN_ANY);
    EnableDocking(CBRS_ALIGN_ANY);
    DockControlBar(&m_wndToolBar);

    return 0;
}


我们发现该函数调用了基类的OnCreate()函数,就是这个函数完成了窗口的创建,我们可以在该函数返回前调用 SetWindowLong完成指定窗口的属性修改,该函数声明如下:

LONG SetWindowLong(HWND hWnd,int nlndex,LONG dwNewLong)
hWnd:窗口句柄及间接给出的窗口所属的类。
nlndex:指定将设定的大于等于0的偏移值。 要设置其他任何值,可以指定下面值之一:

    GWL_EXISTYLE:设定一个新的扩展风格。
    GWL_STYLE:设定一个新的窗口风格。
    GWL_WNDPROC:为窗口过程设定一个新的地址。GWL_ID:设置一个新的窗口标识符。
     ....
dwNewLong:指定的替换值。

对应的,MFC提供了GetWindowLong函数来获取指定窗口的信息,其函数声明如下:

LONG GetWindowLong(HWND hWnd,int nlndex)
该函数的返回值就是窗口的信息,nIndex指定了要获取的内容,这个为GWL_STYLE,意为获得窗口风格,修改风格的具体代码如下:

int CMainFrame::OnCreate(LPCREATESTRUCT lpCreateStruct)
{
    if (CFrameWnd::OnCreate(lpCreateStruct) == -1)
    return -1;
    ...

    // TODO: 如果不需要可停靠工具栏,则删除这三行
    m_wndToolBar.EnableDocking(CBRS_ALIGN_ANY);
    EnableDocking(CBRS_ALIGN_ANY);
    DockControlBar(&m_wndToolBar);
    SetWindowLong(m_hWnd, 
                  GWL_STYLE, //获取风格
                  GetWindowLong(m_hWnd, GWL_STYLE) & ~WS_MAXIMIZEBOX);//修改风格 去除最大化属性。
    return 0;
}
运行效果对比:



转载于:https://www.cnblogs.com/jinxiang1224/p/8468361.html

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值