我打算写一个MDI程序北京设置的类,今后自己使用着方便,实现过程中发现程序刚开始运行时图片能正常显示,但刷新后(不论是因为缩放窗口还是因为重新获得焦点)仿佛程序便不起作用了,哪位达人了解这种情况,切盼帮助一下。
#pragma once
///////////////////////////////////////
//设置MDI程序背景的类
///////////////////////////////////////
class CMdiBackground
{
private:
CMDIFrameWnd *m_pMainFrame;public:
static HBITMAP hBmp;//图片句柄
static WNDPROC pfnOldWndProc;//旧函数指针
static int BMPH,BMPW;
CMdiBackground(void);
CMdiBackground(CMDIFrameWnd *pMainFrame);
void SetMainFrame(CMDIFrameWnd *pMainFrame){m_pMainFrame=pMainFrame;};
static LRESULT CALLBACK fnNewWndProc(HWND hwnd, UINT uMsg, WPARAM wParam,LPARAM lParam);
public:
~CMdiBackground(void);
void SetBkFunc(void);
};
===========================================
#include "StdAfx.h"
#include "ElecGridMap.h"
#include "MdiBackground.h"
HBITMAP CMdiBackground::hBmp;//图片句柄
int CMdiBackground::BMPH,CMdiBackground::BMPW;//图片宽度和高度
WNDPROC CMdiBackground::pfnOldWndProc;//旧函数指针
CMdiBackground::CMdiBackground(void)
{
m_pMainFrame=NULL;
}
CMdiBackground::CMdiBackground(CMDIFrameWnd *pMainFrame)
{
m_pMainFrame=pMainFrame;
SetBkFunc();
}
void CMdiBackground::SetBkFunc(void)
{
if(!m_pMainFrame){MessageBox(NULL, L"错误", L"程序错误,应先设置主窗口指针 !!!", MB_OK);return;}
hBmp = LoadBitmap(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_MAINPIC));
if (hBmp == NULL){
MessageBox(NULL, L"错误", L"程序背景图不能调入 !!!", MB_OK);
return;
}
CBitmap bm;
BITMAP bwh; bm.Attach(hBmp);
bm.GetObject(sizeof(BITMAP), &bwh);
bm.Detach();
BMPW=bwh.bmWidth;
BMPH=bwh.bmHeight;
HWND hMain = m_pMainFrame->GetWindow(GW_CHILD)->GetSafeHwnd();
pfnOldWndProc = (WNDPROC)GetWindowLong(hMain, GWL_WNDPROC);
SetWindowLong(hMain, GWL_WNDPROC, (LONG)fnNewWndProc);
}CMdiBackground::~CMdiBackground(void)
{
}
LRESULT CALLBACK CMdiBackground::fnNewWndProc(HWND hwnd, UINT uMsg, WPARAM wParam,LPARAM lParam){
HDC hdc = (HDC)wParam;
HDC hcompdc;
RECT rect;
switch (uMsg) {
case WM_SIZE :
SendMessage(hwnd, WM_ERASEBKGND, (WPARAM)GetDC(hwnd), 0);
return 1;
case WM_ERASEBKGND :
hcompdc = CreateCompatibleDC(hdc);
SelectObject(hcompdc, hBmp);
GetClientRect(hwnd, &rect); if (0 == StretchBlt(hdc, rect.left, rect.top, rect.right, rect.bottom,
hcompdc, 0, 0, BMPW-1, BMPH-1, SRCCOPY))
MessageBox(hwnd, L"错误", L"拉伸绘制图形错误", MB_OK);
return 1;
default :
return CallWindowProc(pfnOldWndProc, hwnd, uMsg, wParam, lParam);
}
}
#pragma once
///////////////////////////////////////
//设置MDI程序背景的类
///////////////////////////////////////
class CMdiBackground
{
private:
CMDIFrameWnd *m_pMainFrame;public:
static HBITMAP hBmp;//图片句柄
static WNDPROC pfnOldWndProc;//旧函数指针
static int BMPH,BMPW;
CMdiBackground(void);
CMdiBackground(CMDIFrameWnd *pMainFrame);
void SetMainFrame(CMDIFrameWnd *pMainFrame){m_pMainFrame=pMainFrame;};
static LRESULT CALLBACK fnNewWndProc(HWND hwnd, UINT uMsg, WPARAM wParam,LPARAM lParam);
public:
~CMdiBackground(void);
void SetBkFunc(void);
};
===========================================
#include "StdAfx.h"
#include "ElecGridMap.h"
#include "MdiBackground.h"
HBITMAP CMdiBackground::hBmp;//图片句柄
int CMdiBackground::BMPH,CMdiBackground::BMPW;//图片宽度和高度
WNDPROC CMdiBackground::pfnOldWndProc;//旧函数指针
CMdiBackground::CMdiBackground(void)
{
m_pMainFrame=NULL;
}
CMdiBackground::CMdiBackground(CMDIFrameWnd *pMainFrame)
{
m_pMainFrame=pMainFrame;
SetBkFunc();
}
void CMdiBackground::SetBkFunc(void)
{
if(!m_pMainFrame){MessageBox(NULL, L"错误", L"程序错误,应先设置主窗口指针 !!!", MB_OK);return;}
hBmp = LoadBitmap(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDB_MAINPIC));
if (hBmp == NULL){
MessageBox(NULL, L"错误", L"程序背景图不能调入 !!!", MB_OK);
return;
}
CBitmap bm;
BITMAP bwh; bm.Attach(hBmp);
bm.GetObject(sizeof(BITMAP), &bwh);
bm.Detach();
BMPW=bwh.bmWidth;
BMPH=bwh.bmHeight;
HWND hMain = m_pMainFrame->GetWindow(GW_CHILD)->GetSafeHwnd();
pfnOldWndProc = (WNDPROC)GetWindowLong(hMain, GWL_WNDPROC);
SetWindowLong(hMain, GWL_WNDPROC, (LONG)fnNewWndProc);
}CMdiBackground::~CMdiBackground(void)
{
}
LRESULT CALLBACK CMdiBackground::fnNewWndProc(HWND hwnd, UINT uMsg, WPARAM wParam,LPARAM lParam){
HDC hdc = (HDC)wParam;
HDC hcompdc;
RECT rect;
switch (uMsg) {
case WM_SIZE :
SendMessage(hwnd, WM_ERASEBKGND, (WPARAM)GetDC(hwnd), 0);
return 1;
case WM_ERASEBKGND :
hcompdc = CreateCompatibleDC(hdc);
SelectObject(hcompdc, hBmp);
GetClientRect(hwnd, &rect); if (0 == StretchBlt(hdc, rect.left, rect.top, rect.right, rect.bottom,
hcompdc, 0, 0, BMPW-1, BMPH-1, SRCCOPY))
MessageBox(hwnd, L"错误", L"拉伸绘制图形错误", MB_OK);
return 1;
default :
return CallWindowProc(pfnOldWndProc, hwnd, uMsg, wParam, lParam);
}
}
SendMessage(hwnd, WM_ERASEBKGND, (WPARAM)GetDC(hwnd), 0);
return 1; -------------
你GetDC之后在哪Release了?没释放后续的GetDC,绘制操作都会失败,且wm_size是会频繁触发的,严重资源泄漏。
case WM_ERASEBKGND:
hcompdc = CreateCompatibleDC(hdc);
HGDIOBJ oldObj = SelectObject(hcompdc, hBmp);
GetClientRect(hwnd, &rect);
if (0 == StretchBlt(hdc, rect.left, rect.top, rect.right, rect.bottom, hcompdc, 0, 0, BMPW-1, BMPH-1, SRCCOPY))
MessageBox(hwnd, L"错误", L"拉伸绘制图形错误", MB_OK);
SelectObject(hcompdc, oldObj);
DeleteDC(hcompdc);
return 1;
f:\vc\elecgridmap\elecgridmap\mdibackground.cpp(59) : error C2361: “default”标签跳过“oldObj”的初始化操作
f:\vc\elecgridmap\elecgridmap\mdibackground.cpp(50) : 参见“oldObj”的声明
LRESULT CALLBACK CMdiBackground::fnNewWndProc(HWND hwnd, UINT uMsg, WPARAM wParam,LPARAM lParam){
HDC hdc = (HDC)wParam;
HDC hcompdc;
RECT rect;
HGDIOBJ oldObj;
HDC tempDC;
switch (uMsg) {
case WM_SIZE :
tempDC=GetDC(hwnd);
SendMessage(hwnd, WM_ERASEBKGND, (WPARAM)tempDC, 0);
ReleaseDC(hwnd,tempDC);
return 1;
case WM_ERASEBKGND :
hcompdc = CreateCompatibleDC(hdc);
oldObj = SelectObject(hcompdc, hBmp);
GetClientRect(hwnd, &rect); if (0 == StretchBlt(hdc, rect.left, rect.top, rect.right, rect.bottom,
hcompdc, 0, 0, BMPW-1, BMPH-1, SRCCOPY))
MessageBox(hwnd, L"错误", L"拉伸绘制图形错误", MB_OK);
SelectObject(hcompdc, oldObj);
DeleteDC(hcompdc);
return 1;
default :
return CallWindowProc(pfnOldWndProc, hwnd, uMsg, wParam, lParam);
}
}