本文主要是在一个主窗口下创建一个子窗口。主窗口有一个菜单,菜单下只有设置一个选项,点击设置选项,弹出设置界面,点击设置界面关闭则关闭。我在开发的时候遇到两个问题,第一就是一点设置关闭就整个应用都关了,原来是destroy消息共用了。然后第二个是点击关闭后,设置界面再也显示不出来了,原来是close消息也要分拣。

菜单志愿为IDR_MENU,设置ID选项为ID_SETTING。

文件如下:

Main.cpp

#include "resource.h"
#include<tchar.h>
#include<stdio.h>
#include<windows.h>
#include "SettingMgr.h"
#define ClassName _T("sunxin2006")
HINSTANCE g_hInstance = ;
LRESULT CALLBACK WinSunProc(HWND hwnd,UINT uMsg,WPARAM wParam,LPARAM lParam);
int WINAPI WinMain(HINSTANCE hInstance,
HINSTANCE hPrevInstance,
LPSTR lpCmdLine,
int nCmdShow)
{
WNDCLASS wndcls;
wndcls.cbClsExtra = ;
wndcls.cbWndExtra = ;
wndcls.hbrBackground = (HBRUSH) GetStockObject(WHITE_BRUSH);
wndcls.hCursor = LoadCursor(NULL,IDC_ARROW);
wndcls.hIcon = LoadIcon(NULL,IDI_APPLICATION);
wndcls.hInstance = hInstance;
wndcls.lpfnWndProc = WinSunProc;
wndcls.lpszClassName = _T("sunxin2006");
wndcls.lpszMenuName = NULL;
wndcls.style = CS_HREDRAW | CS_VREDRAW;
RegisterClass(&wndcls);
g_hInstance = hInstance;
HWND hwnd = CreateWindow(ClassName,_T("helloworld"),WS_OVERLAPPEDWINDOW,
,,,,NULL,LoadMenu(hInstance,MAKEINTRESOURCE(IDR_MENU)),hInstance,NULL);
ShowWindow(hwnd,SW_SHOW);
UpdateWindow(hwnd); MSG msg;
while(GetMessage(&msg,NULL,,)>)
{
TranslateMessage(&msg);
DispatchMessage(&msg);
}
return msg.wParam;
}
void OnCreate(HWND hwnd,WPARAM wParam,LPARAM lParam)
{
int scrWidth,scrHeight;
RECT rect;
//获得屏幕尺寸
scrWidth = GetSystemMetrics(SM_CXSCREEN);
scrHeight = GetSystemMetrics(SM_CYSCREEN);
//取得窗口尺寸
GetWindowRect(hwnd,&rect);
//重新设置rect里的值
rect.left = (scrWidth-rect.right)/;
rect.top = (scrHeight-rect.bottom)/;
//移动窗口到指定的位置
SetWindowPos(hwnd,HWND_TOP,rect.left,rect.top,rect.right,rect.bottom,SWP_SHOWWINDOW);
} void OnComand(HWND hwnd,WPARAM wParam,LPARAM lParam)
{
WORD uID = LOWORD(wParam);
switch(uID)
{
case ID_SETTING:
{
if(SettingMgr::GetIntance()->m_SettingWnd)
{
ShowWindow(SettingMgr::GetIntance()->m_SettingWnd,SW_SHOW);
}
else
{
SettingMgr::GetIntance()->m_SettingWnd =
CreateWindow(ClassName, "子窗口",
WS_OVERLAPPEDWINDOW|WS_CHILD|WS_VISIBLE|WS_POPUP, CW_USEDEFAULT, CW_USEDEFAULT, , ,
hwnd, NULL, g_hInstance, NULL);
ShowWindow(SettingMgr::GetIntance()->m_SettingWnd,SW_SHOW);
}
}
break;
}
} VOID OnPaint(HWND hwnd,WPARAM wParam,LPARAM lParam)
{
PAINTSTRUCT ps;
RECT rtClient;
GetClientRect(hwnd,&rtClient);
HDC hdc = BeginPaint(hwnd, &ps);
HDC hMemDC = CreateCompatibleDC(hdc);
HBITMAP hBitmap = CreateCompatibleBitmap(hdc, rtClient.right - rtClient.left, rtClient.bottom - rtClient.top);//rt为RECT变量;
SelectObject(hMemDC, hBitmap);
FillRect(hMemDC, &rtClient,WHITE_BRUSH);
char strText[];
if(hwnd == SettingMgr::GetIntance()->m_SettingWnd)
{
strcpy(strText,_T("我是子窗口!!!"));
}
else
{
strcpy(strText,_T("我是父窗口!!!"));
}
RECT rt={,,,};
DrawText(hMemDC,strText,strlen(strText),&rt,DT_LEFT|DT_TOP);
BitBlt(hdc, , ,rtClient.right - rtClient.left, rtClient.bottom - rtClient.top,
hMemDC, , , SRCCOPY);
DeleteDC(hMemDC);
DeleteObject(hBitmap);
ReleaseDC(hwnd,hdc);
}
LRESULT CALLBACK WinSunProc(HWND hwnd,UINT uMsg,WPARAM wParam,LPARAM lParam)
{
switch(uMsg)
{
case WM_CREATE:
OnCreate(hwnd,wParam,lParam);
break;
case WM_COMMAND:
OnComand(hwnd,wParam,lParam);
break;
case WM_PAINT:
OnPaint(hwnd,wParam,lParam);
break;
case WM_CLOSE:
if(hwnd == SettingMgr::GetIntance()->m_SettingWnd)
{
ShowWindow(SettingMgr::GetIntance()->m_SettingWnd,SW_HIDE);
}
else
{
DefWindowProc(hwnd,uMsg,wParam,lParam);
}
break;
case WM_DESTROY:
if(hwnd == SettingMgr::GetIntance()->m_SettingWnd)
{ }
else
{
PostQuitMessage();
} break;
default:
return DefWindowProc(hwnd,uMsg,wParam,lParam);
}
return ;
}

SettingMgr.h

#pragma once
#include<Windows.h>
class SettingMgr
{
protected:
static SettingMgr* _Intance;
public:
HWND m_SettingWnd;
public:
SettingMgr(void);
~SettingMgr(void);
static SettingMgr* GetIntance();
};

SettingMgr.cpp

#include "SettingMgr.h"
SettingMgr* SettingMgr::_Intance = new SettingMgr();
SettingMgr::SettingMgr(void):m_SettingWnd(NULL)
{
} SettingMgr::~SettingMgr(void)
{ } SettingMgr* SettingMgr::GetIntance()
{
return _Intance;
}

由于例子很简单,所以用没用SettingMgr类效果不明显,如果结果比较麻烦,最好使用管理类。

注:修正一下错误,释放BeginPaint,需要调用EndPaint(hwnd,&ps),而不是ReleaseDC,失误了。。。抱歉。。。。

2、第二种方法,比较简单。创建时可以用不同的窗口类,注册时写一个另外的窗口函数。

Win32子窗口的创建的更多相关文章

  1. WIN32进阶必备:跟随鼠标移动的子窗口

    上两张Demo的图,方便朋友们选择是否继续看文章. 在子窗口的白色区域按下鼠标左键不放并移动鼠标可以拖拽子窗口跟随鼠标移动. 选择继续看下去的朋友不要担心,接下来就是正文了. PART 1:Demo功 ...

  2. win32程序之子窗口编程

    win32程序之子窗口编程 一丶简介.什么是子窗口 在前边我们已经讲解了窗口的本质.以及如何注册窗口类跟创建窗口. 还讲了消息循环. 那么有很多窗口其实Windows已经帮我们创建出来了.我们直接使用 ...

  3. System.InvalidOperationException:“寄宿 HWND 必须是子窗口。”

    原文:System.InvalidOperationException:"寄宿 HWND 必须是子窗口." 当试图在 WPF 窗口中嵌套显示 Win32 子窗口的时候,你有可能出现 ...

  4. 12 Windows编程——子窗口和系统内置窗口类“BUTTON”

    创建子窗口类,使得子窗口有自己的处理过程. 子窗口类型WS_CHILD不能和WS_POPUP一起使用!为什么子窗口要有自己的处理过程?如果使用主窗口类来创建子窗口,那么子窗口和主窗口将公用窗口处理过程 ...

  5. 转-JS子窗口创建父窗口操作父窗口

    Javascript弹出子窗口  可以通过多种方式实现,下面介绍几种方法 (1) 通过window对象的open()方法,open()方法将会产生一个新的window窗口对象 其用法为: window ...

  6. IE 中创建 子窗口 传值 与接收值 【window.showModalDialog】

    父窗口 创建一个窗口 var backinfo = window.showModalDialog('UserSelect.aspx', '', 'dialogHeight=600px; dialogW ...

  7. Win32 程序开发:创建一个应用程序窗口

    一.创建一个应用程序窗口 代码如下: // 头文件 #include <windows.h> // 全局变量 WCHAR g_lpszClassName[] = L"CLASSN ...

  8. 使用CreateWindowEx创建子窗口的注意事项

    比如: 使用 HWND child = CreateWindowEx(0,L"childclass",NULL,WS_CHILD | WS_VISIBLE | WS_CLIPSIB ...

  9. MFC在子线程中创建窗口(PostMessage方法)

    1.创建子线程 C++创建线程的方式比较多 1)最简单易用的<thread>头文件,但是这种方法创建的子线程中无法给主线程PostMessage消息(也可能是我操作有误,总之没成功) 2) ...

随机推荐

  1. 武大OJ 622. Symmetrical

    Description          Cyy likes something symmetrical, and Han Move likes something circular. Han Mov ...

  2. JVM内存分布和垃圾回收

    内存区域划分   程序计数器(Program counter Register) 描述  程序计数器(Program Counter Register)是一块较小的内存空间.它可以看作是当前线程执行的 ...

  3. Spring Cloud简介/版本选择/ZooKeeper例子搭建简单说明

    一.什么是Spring Cloud 官方的说法就是Spring Cloud 给开发者提供一套按照一定套路快速开发分布式系统的工具. 具体点就是Spring Boot实现的微服务架构开发工具.它为微服务 ...

  4. activeMQ启动失败61616port被占用问题

    Failed t bind to server socket:tcp://localhost:61616 due to : java.net.BindException 通过netstat -aon ...

  5. dhtmlx中添加一列(将相似button、下拉列表、输入框显示在一行上)

    { type: "label", list: [ { { type: "label", labelWidth: 55 }, { type: "newc ...

  6. protobuf-net precompile

    之前游戏为了解决在ios自动更新的问题,想到使用了将游戏代码打包成dll,使用反射加载执行的办法.办法想好了以后,一直没有做测试.上周不知道什么原因,终于有人去测试了,结果发现报错了.我当时觉得有点意 ...

  7. Java 实现的断点下载

    该断点下载可应用于浏览器或者迅雷等下载工具的下载,实现方式有多种多样的,本文仅仅研究了单线程的下载.迅雷等下载工具会自己主动将下载资源分块并记录每块的起始位置,然后依据系统性能.起多线程下载. 1. ...

  8. 利用rman自己主动备份转储spfile

    利用rman自己主动备份转储spfile [情景简单介绍] 生产环境丢失了server的參数文件,rman已开启自己主动备份设置. [操作过程简述] ----启动rman $rman target / ...

  9. luogu2346 四子连棋

    题目大意 在一个4*4的棋盘上摆放了14颗棋子,其中有7颗白色棋子,7颗黑色棋子,有两个空白地带,任何一颗黑白棋子都可以向上下左右四个方向移动到相邻的空格,这叫行棋一步,黑白双方交替走棋,任意一方可以 ...

  10. charts柱状图,定时刷新

    option: var dataoptionone = { title : { text: '数据存储情况', subtext: '数据表', x:'center' }, tooltip: { sho ...