647 lines
18 KiB
C++
647 lines
18 KiB
C++
|
/* DBACKP.CPP
|
||
|
**
|
||
|
** Copyright (C) Microsoft, 1997, All Rights Reserved.
|
||
|
**
|
||
|
** window class to display a preview of the screen background,
|
||
|
** complete with rudimentary palette handling and stretching
|
||
|
** of bitmaps to fit the preview screen.
|
||
|
**
|
||
|
** this can be replaced with a static bitmap control only
|
||
|
** if palettes can also be handled by the control.
|
||
|
**
|
||
|
*/
|
||
|
|
||
|
#include "stdafx.h"
|
||
|
#pragma hdrstop
|
||
|
|
||
|
#define GWW_INFO 0
|
||
|
|
||
|
#define CXYDESKPATTERN 8
|
||
|
|
||
|
BOOL g_bInfoSet = FALSE;
|
||
|
|
||
|
HBITMAP g_hbmPreview = NULL; // the bitmap used for previewing
|
||
|
|
||
|
HBITMAP g_hbmDefault = NULL; // default bitmap
|
||
|
HBITMAP g_hbmWall = NULL; // bitmap image of wallpaper
|
||
|
HDC g_hdcWall = NULL; // memory DC with g_hbmWall selected
|
||
|
HDC g_hdcMemory = NULL; // memory DC
|
||
|
HPALETTE g_hpalWall = NULL; // palette that goes with hbmWall bitmap
|
||
|
HBRUSH g_hbrBack = NULL; // brush for the desktop background
|
||
|
IThumbnail *g_pthumb = NULL; // Html to Bitmap converter
|
||
|
DWORD g_dwWallpaperID = 0; // ID to identify which bitmap we received
|
||
|
|
||
|
#define WM_HTML_BITMAP (WM_USER + 100)
|
||
|
#define WM_ASYNC_BITMAP (WM_HTML_BITMAP + 1)
|
||
|
|
||
|
|
||
|
HPALETTE PaletteFromDS(HDC hdc)
|
||
|
{
|
||
|
DWORD adw[257];
|
||
|
int i,n;
|
||
|
|
||
|
n = GetDIBColorTable(hdc, 0, 256, (LPRGBQUAD)&adw[1]);
|
||
|
adw[0] = MAKELONG(0x300, n);
|
||
|
|
||
|
for (i=1; i<=n; i++)
|
||
|
adw[i] = RGB(GetBValue(adw[i]),GetGValue(adw[i]),GetRValue(adw[i]));
|
||
|
|
||
|
if (n == 0)
|
||
|
return NULL;
|
||
|
else
|
||
|
return CreatePalette((LPLOGPALETTE)&adw[0]);
|
||
|
}
|
||
|
|
||
|
typedef struct{
|
||
|
HWND hwnd;
|
||
|
HBITMAP hbmp;
|
||
|
DWORD id;
|
||
|
WPARAM flags;
|
||
|
TCHAR szFile[MAX_PATH];
|
||
|
} ASYNCWALLPARAM, * PASYNCWALLPARAM;
|
||
|
|
||
|
DWORD CALLBACK UpdateWallProc(LPVOID pv)
|
||
|
{
|
||
|
ASSERT(pv);
|
||
|
PASYNCWALLPARAM pawp = (PASYNCWALLPARAM) pv;
|
||
|
pawp->hbmp = (HBITMAP)LoadImage(NULL, pawp->szFile,
|
||
|
IMAGE_BITMAP, 0, 0,
|
||
|
LR_LOADFROMFILE|LR_CREATEDIBSECTION);
|
||
|
|
||
|
if (pawp->hbmp)
|
||
|
{
|
||
|
// if all is good, then the window will handle cleaning up
|
||
|
if (IsWindow(pawp->hwnd) && PostMessage(pawp->hwnd, WM_ASYNC_BITMAP, 0, (LPARAM)pawp))
|
||
|
return TRUE;
|
||
|
|
||
|
DeleteObject(pawp->hbmp);
|
||
|
}
|
||
|
|
||
|
LocalFree(pawp);
|
||
|
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
const GUID CLSID_HtmlThumbnailExtractor = {0xeab841a0, 0x9550, 0x11cf, 0x8c, 0x16, 0x0, 0x80, 0x5f, 0x14, 0x8, 0xf3};
|
||
|
|
||
|
DWORD CALLBACK UpdateWallProcHTML(LPVOID pv)
|
||
|
{
|
||
|
if (SUCCEEDED(CoInitialize(NULL)))
|
||
|
{
|
||
|
ASSERT(pv);
|
||
|
if (pv)
|
||
|
{
|
||
|
PASYNCWALLPARAM pawp = (PASYNCWALLPARAM) pv;
|
||
|
IPersistFile *ppf;
|
||
|
HRESULT hr = CoCreateInstance(CLSID_HtmlThumbnailExtractor, NULL, CLSCTX_INPROC_SERVER, IID_PPV_ARG(IPersistFile, &ppf));
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
hr = ppf->Load(pawp->szFile, STGM_READ);
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
IExtractImage *pei= NULL;
|
||
|
hr = ppf->QueryInterface(IID_PPV_ARG(IExtractImage, &pei));
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
DWORD dwPriority = 0;
|
||
|
DWORD dwFlags = IEIFLAG_SCREEN | IEIFLAG_OFFLINE;
|
||
|
WCHAR szLocation[MAX_PATH];
|
||
|
SIZEL rgSize = {MON_DX, MON_DY};
|
||
|
|
||
|
hr = pei->GetLocation(szLocation, ARRAYSIZE(szLocation), &dwPriority, &rgSize, SHGetCurColorRes(), &dwFlags);
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
HBITMAP hbm;
|
||
|
hr = pei->Extract(&hbm);
|
||
|
if (SUCCEEDED(hr))
|
||
|
{
|
||
|
if (!SendMessage(pawp->hwnd, WM_HTML_BITMAP, pawp->id, (LPARAM)hbm))
|
||
|
{
|
||
|
DeleteObject(hbm);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
pei->Release();
|
||
|
}
|
||
|
}
|
||
|
ppf->Release();
|
||
|
}
|
||
|
|
||
|
LocalFree(pawp);
|
||
|
}
|
||
|
CoUninitialize();
|
||
|
}
|
||
|
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
void LoadWallpaperAsync(LPCTSTR pszFile, HWND hwnd, DWORD dwID, WPARAM flags, BOOL bHTML)
|
||
|
{
|
||
|
PASYNCWALLPARAM pawp = (PASYNCWALLPARAM) LocalAlloc(LPTR, SIZEOF(ASYNCWALLPARAM));
|
||
|
|
||
|
if (pawp)
|
||
|
{
|
||
|
pawp->hwnd = hwnd;
|
||
|
pawp->flags = flags;
|
||
|
pawp->id = dwID;
|
||
|
StrCpyN(pawp->szFile, pszFile, SIZECHARS(pawp->szFile));
|
||
|
|
||
|
if (!bHTML)
|
||
|
{
|
||
|
if (!SHQueueUserWorkItem(UpdateWallProc, pawp, 0, (DWORD_PTR)0, (DWORD_PTR *)NULL, NULL, 0))
|
||
|
LocalFree(pawp);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
if (!SHQueueUserWorkItem(UpdateWallProcHTML, pawp, 0, (DWORD_PTR)0, (DWORD_PTR *)NULL, NULL, 0))
|
||
|
LocalFree(pawp);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void _InitPreview(void)
|
||
|
{
|
||
|
if( g_hbmPreview )
|
||
|
DeleteObject( g_hbmPreview );
|
||
|
|
||
|
g_hbmPreview = LoadMonitorBitmap();
|
||
|
}
|
||
|
|
||
|
void _BuildPattern(void)
|
||
|
{
|
||
|
WCHAR wszBuf[MAX_PATH];
|
||
|
HBITMAP hbmTemp;
|
||
|
COLORREF clrOldBk, clrOldText;
|
||
|
HBRUSH hbr = NULL;
|
||
|
WORD patbits[CXYDESKPATTERN] = {0, 0, 0, 0, 0, 0, 0, 0};
|
||
|
|
||
|
|
||
|
// get rid of old brush if there was one
|
||
|
if (g_hbrBack)
|
||
|
DeleteObject(g_hbrBack);
|
||
|
|
||
|
g_pActiveDesk->GetPattern(wszBuf, ARRAYSIZE(wszBuf), 0);
|
||
|
if (wszBuf[0] != 0L)
|
||
|
{
|
||
|
LPTSTR pszPatternBuf;
|
||
|
#ifndef UNICODE
|
||
|
CHAR szTemp[MAX_PATH];
|
||
|
SHUnicodeToAnsi(wszBuf, szTemp, ARRAYSIZE(szTemp));
|
||
|
pszPatternBuf = szTemp;
|
||
|
#else
|
||
|
pszPatternBuf = wszBuf;
|
||
|
#endif
|
||
|
PatternToWords(pszPatternBuf, patbits);
|
||
|
hbmTemp = CreateBitmap(8, 8, 1, 1, patbits);
|
||
|
if (hbmTemp)
|
||
|
{
|
||
|
g_hbrBack = CreatePatternBrush(hbmTemp);
|
||
|
DeleteObject(hbmTemp);
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
g_hbrBack = CreateSolidBrush(GetSysColor(COLOR_BACKGROUND));
|
||
|
}
|
||
|
if (!g_hbrBack)
|
||
|
{
|
||
|
g_hbrBack = (HBRUSH)GetStockObject(BLACK_BRUSH);
|
||
|
}
|
||
|
|
||
|
clrOldText = SetTextColor(g_hdcMemory, GetSysColor(COLOR_BACKGROUND));
|
||
|
clrOldBk = SetBkColor(g_hdcMemory, GetSysColor(COLOR_WINDOWTEXT));
|
||
|
|
||
|
hbr = (HBRUSH)SelectObject(g_hdcMemory, g_hbrBack);
|
||
|
PatBlt(g_hdcMemory, MON_X, MON_Y, MON_DX, MON_DY, PATCOPY);
|
||
|
SelectObject(g_hdcMemory, hbr);
|
||
|
|
||
|
SetTextColor(g_hdcMemory, clrOldText);
|
||
|
SetBkColor(g_hdcMemory, clrOldBk);
|
||
|
}
|
||
|
|
||
|
void _InitWall(void)
|
||
|
{
|
||
|
if (g_hbmWall)
|
||
|
{
|
||
|
SelectObject(g_hdcWall, g_hbmDefault);
|
||
|
DeleteObject(g_hbmWall);
|
||
|
g_hbmWall = NULL;
|
||
|
|
||
|
if (g_hpalWall)
|
||
|
{
|
||
|
DeleteObject(g_hpalWall);
|
||
|
g_hpalWall = NULL;
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void _GetWallpaperAsync(HWND hwnd, WPARAM flags)
|
||
|
{
|
||
|
WCHAR wszWallpaper[INTERNET_MAX_URL_LENGTH];
|
||
|
LPTSTR pszWallpaper;
|
||
|
|
||
|
g_pActiveDesk->GetWallpaper(wszWallpaper, ARRAYSIZE(wszWallpaper), 0);
|
||
|
#ifndef UNICODE
|
||
|
CHAR szWallpaper[ARRAYSIZE(wszWallpaper)];
|
||
|
SHUnicodeToAnsi(wszWallpaper, szWallpaper, ARRAYSIZE(szWallpaper));
|
||
|
pszWallpaper = szWallpaper;
|
||
|
#else
|
||
|
pszWallpaper = wszWallpaper;
|
||
|
#endif
|
||
|
|
||
|
g_dwWallpaperID++;
|
||
|
|
||
|
if (!*pszWallpaper || !lstrcmpi(pszWallpaper, g_szNone))
|
||
|
return;
|
||
|
|
||
|
{
|
||
|
if (IsNormalWallpaper(pszWallpaper))
|
||
|
{
|
||
|
LoadWallpaperAsync(pszWallpaper, hwnd, g_dwWallpaperID, flags, FALSE);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
if(IsWallpaperPicture(pszWallpaper))
|
||
|
{
|
||
|
// This is a picture (GIF, JPG etc.,)
|
||
|
// We need to generate a small HTML file that has this picture
|
||
|
// as the background image.
|
||
|
//
|
||
|
// Compute the filename for the Temporary HTML file.
|
||
|
//
|
||
|
GetTempPath(ARRAYSIZE(wszWallpaper), pszWallpaper);
|
||
|
lstrcat(pszWallpaper, PREVIEW_PICTURE_FILENAME);
|
||
|
#ifndef UNICODE
|
||
|
SHAnsiToUnicode(szWallpaper, wszWallpaper, ARRAYSIZE(wszWallpaper));
|
||
|
#endif
|
||
|
//
|
||
|
// Generate the preview picture html file.
|
||
|
//
|
||
|
g_pActiveDesk->GenerateDesktopItemHtml(wszWallpaper, NULL, 0);
|
||
|
}
|
||
|
|
||
|
//
|
||
|
// Will cause a WM_HTML_BITMAP to get sent to us.
|
||
|
//
|
||
|
LoadWallpaperAsync(pszWallpaper, hwnd, g_dwWallpaperID, flags, TRUE);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void _DrawWall(HBITMAP hbm, WPARAM flags)
|
||
|
{
|
||
|
int dxWall; // size of wallpaper
|
||
|
int dyWall;
|
||
|
BITMAP bm;
|
||
|
|
||
|
// init the global
|
||
|
g_hbmWall = hbm;
|
||
|
|
||
|
|
||
|
SelectObject(g_hdcWall, g_hbmWall); // bitmap stays in this DC
|
||
|
GetObject(g_hbmWall, sizeof(bm), &bm);
|
||
|
TraceMsg(TF_ALWAYS, "for bitmap %08X we have bpp=%d and planes=%d", g_hbmWall, bm.bmBitsPixel, bm.bmPlanes);
|
||
|
|
||
|
if (GetDeviceCaps(g_hdcMemory, RASTERCAPS) & RC_PALETTE)
|
||
|
{
|
||
|
if (bm.bmBitsPixel * bm.bmPlanes > 8)
|
||
|
g_hpalWall = CreateHalftonePalette(g_hdcMemory);
|
||
|
else if (bm.bmBitsPixel * bm.bmPlanes == 8)
|
||
|
g_hpalWall = PaletteFromDS(g_hdcWall);
|
||
|
else
|
||
|
g_hpalWall = NULL; //!!! assume 1 or 4bpp images dont have palettes
|
||
|
}
|
||
|
|
||
|
GetObject(g_hbmWall, sizeof(bm), &bm);
|
||
|
|
||
|
if(flags & BP_EXTERNALWALL)
|
||
|
{
|
||
|
//For external wallpapers, we ask the image extractor to generate
|
||
|
// bitmaps the size that we want to show (NOT the screen size).
|
||
|
dxWall = MON_DX;
|
||
|
dyWall = MON_DY;
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
dxWall = MulDiv(bm.bmWidth, MON_DX, GetDeviceCaps(g_hdcMemory, HORZRES));
|
||
|
dyWall = MulDiv(bm.bmHeight, MON_DY, GetDeviceCaps(g_hdcMemory, VERTRES));
|
||
|
}
|
||
|
|
||
|
if (dxWall < 1) dxWall = 1;
|
||
|
if (dyWall < 1) dyWall = 1;
|
||
|
|
||
|
if (g_hpalWall)
|
||
|
{
|
||
|
SelectPalette(g_hdcMemory, g_hpalWall, TRUE);
|
||
|
RealizePalette(g_hdcMemory);
|
||
|
}
|
||
|
|
||
|
IntersectClipRect(g_hdcMemory, MON_X, MON_Y, MON_X + MON_DX, MON_Y + MON_DY);
|
||
|
SetStretchBltMode(g_hdcMemory, COLORONCOLOR);
|
||
|
|
||
|
if (flags & BP_TILE)
|
||
|
{
|
||
|
int i;
|
||
|
StretchBlt(g_hdcMemory, MON_X, MON_Y, dxWall, dyWall,
|
||
|
g_hdcWall, 0, 0, bm.bmWidth, bm.bmHeight, SRCCOPY);
|
||
|
|
||
|
for (i = MON_X+dxWall; i < (MON_X + MON_DX); i+= dxWall)
|
||
|
BitBlt(g_hdcMemory, i, MON_Y, dxWall, dyWall, g_hdcMemory, MON_X, MON_Y, SRCCOPY);
|
||
|
|
||
|
for (i = MON_Y; i < (MON_Y + MON_DY); i += dyWall)
|
||
|
BitBlt(g_hdcMemory, MON_X, i, MON_DX, dyWall, g_hdcMemory, MON_X, MON_Y, SRCCOPY);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
//We want to stretch the Bitmap to the preview monitor size ONLY for new platforms.
|
||
|
if (flags & BP_STRETCH)
|
||
|
{
|
||
|
//Stretch the bitmap to the whole preview monitor.
|
||
|
dxWall = MON_DX;
|
||
|
dyWall = MON_DY;
|
||
|
}
|
||
|
//Center the bitmap in the preview monitor
|
||
|
StretchBlt(g_hdcMemory, MON_X + (MON_DX - dxWall)/2, MON_Y + (MON_DY - dyWall)/2,
|
||
|
dxWall, dyWall, g_hdcWall, 0, 0, bm.bmWidth, bm.bmHeight, SRCCOPY);
|
||
|
}
|
||
|
|
||
|
// restore dc
|
||
|
SelectPalette(g_hdcMemory, (HPALETTE)GetStockObject(DEFAULT_PALETTE), TRUE);
|
||
|
SelectClipRgn(g_hdcMemory, NULL);
|
||
|
}
|
||
|
/*--------------------------------------------------------------------
|
||
|
** Build the preview bitmap.
|
||
|
**
|
||
|
** both the pattern and the bitmap are drawn each time, but
|
||
|
** if the flags dictate the need, new pattern and bitmap
|
||
|
** globals are built as needed.
|
||
|
**--------------------------------------------------------------------*/
|
||
|
void NEAR PASCAL BuildPreviewBitmap(HWND hwnd, HBITMAP hbmp, WPARAM flags)
|
||
|
{
|
||
|
_InitPreview();
|
||
|
|
||
|
HBITMAP hbmOld = (HBITMAP)SelectObject(g_hdcMemory, g_hbmPreview);
|
||
|
|
||
|
_BuildPattern();
|
||
|
|
||
|
_InitWall();
|
||
|
/*
|
||
|
** now, position the wallpaper appropriately
|
||
|
*/
|
||
|
if (hbmp)
|
||
|
{
|
||
|
// use the one that was passed in
|
||
|
_DrawWall(hbmp, flags);
|
||
|
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// this means that we need to set up the stuff
|
||
|
// to get the bmp ASYNC
|
||
|
|
||
|
_GetWallpaperAsync(hwnd, flags);
|
||
|
}
|
||
|
|
||
|
SelectObject(g_hdcMemory, hbmOld);
|
||
|
}
|
||
|
|
||
|
|
||
|
BOOL NEAR PASCAL BP_CreateGlobals(HWND hwnd)
|
||
|
{
|
||
|
HDC hdc;
|
||
|
|
||
|
hdc = GetDC(NULL);
|
||
|
g_hdcWall = CreateCompatibleDC(hdc);
|
||
|
g_hdcMemory = CreateCompatibleDC(hdc);
|
||
|
ReleaseDC(NULL, hdc);
|
||
|
g_hbmPreview = LoadMonitorBitmap();
|
||
|
|
||
|
HBITMAP hbm;
|
||
|
hbm = CreateBitmap(1, 1, 1, 1, NULL);
|
||
|
g_hbmDefault = (HBITMAP)SelectObject(g_hdcMemory, hbm);
|
||
|
SelectObject(g_hdcMemory, g_hbmDefault);
|
||
|
DeleteObject(hbm);
|
||
|
|
||
|
HRESULT hr = E_FAIL;
|
||
|
|
||
|
hr = CoCreateInstance(CLSID_Thumbnail, NULL, CLSCTX_INPROC_SERVER, IID_IThumbnail, (void **)&g_pthumb);
|
||
|
if(SUCCEEDED(hr))
|
||
|
{
|
||
|
g_pthumb->Init(hwnd, WM_HTML_BITMAP);
|
||
|
}
|
||
|
|
||
|
|
||
|
if (!g_hdcWall || !g_hbmPreview || !SUCCEEDED(hr))
|
||
|
return FALSE;
|
||
|
else
|
||
|
return TRUE;
|
||
|
}
|
||
|
|
||
|
void NEAR PASCAL BP_DestroyGlobals(void)
|
||
|
{
|
||
|
if (g_hbmPreview)
|
||
|
{
|
||
|
DeleteObject(g_hbmPreview);
|
||
|
g_hbmPreview = NULL;
|
||
|
}
|
||
|
if (g_hbmWall)
|
||
|
{
|
||
|
SelectObject(g_hdcWall, g_hbmDefault);
|
||
|
DeleteObject(g_hbmWall);
|
||
|
g_hbmWall = NULL;
|
||
|
}
|
||
|
if (g_hpalWall)
|
||
|
{
|
||
|
SelectPalette(g_hdcWall, (HPALETTE)GetStockObject(DEFAULT_PALETTE), TRUE);
|
||
|
DeleteObject(g_hpalWall);
|
||
|
g_hpalWall = NULL;
|
||
|
}
|
||
|
if (g_hdcWall)
|
||
|
{
|
||
|
DeleteDC(g_hdcWall);
|
||
|
g_hdcWall = NULL;
|
||
|
}
|
||
|
if (g_hbrBack)
|
||
|
{
|
||
|
DeleteObject(g_hbrBack);
|
||
|
g_hbrBack = NULL;
|
||
|
}
|
||
|
if (g_hdcMemory)
|
||
|
{
|
||
|
DeleteDC(g_hdcMemory);
|
||
|
g_hdcMemory = NULL;
|
||
|
}
|
||
|
if (g_hbmDefault)
|
||
|
{
|
||
|
DeleteObject(g_hbmDefault);
|
||
|
g_hbmDefault = NULL;
|
||
|
}
|
||
|
if (g_pthumb)
|
||
|
{
|
||
|
g_pthumb->Release();
|
||
|
g_pthumb = NULL;
|
||
|
}
|
||
|
}
|
||
|
|
||
|
void InvalidateBackPrevContents(HWND hwnd)
|
||
|
{
|
||
|
BITMAP bm;
|
||
|
RECT rc;
|
||
|
|
||
|
//
|
||
|
// Only invalidate the "screen" part of the monitor bitmap.
|
||
|
//
|
||
|
GetObject(g_hbmPreview, SIZEOF(bm), &bm);
|
||
|
GetClientRect(hwnd, &rc);
|
||
|
rc.left = ( rc.right - bm.bmWidth ) / 2 + MON_X;
|
||
|
rc.top = ( rc.bottom - bm.bmHeight ) / 2 + MON_Y;
|
||
|
rc.right = rc.left + MON_DX;
|
||
|
rc.bottom = rc.top + MON_DY;
|
||
|
|
||
|
InvalidateRect(hwnd, &rc, FALSE);
|
||
|
}
|
||
|
|
||
|
LRESULT BackPreviewWndProc (HWND hWnd, UINT message, WPARAM wParam, LPARAM lParam)
|
||
|
{
|
||
|
PAINTSTRUCT ps;
|
||
|
BITMAP bm;
|
||
|
RECT rc;
|
||
|
HBITMAP hbmOld;
|
||
|
HPALETTE hpalOld;
|
||
|
|
||
|
switch(message)
|
||
|
{
|
||
|
case WM_CREATE:
|
||
|
if (!BP_CreateGlobals(hWnd))
|
||
|
return -1L;
|
||
|
break;
|
||
|
|
||
|
case WM_DESTROY:
|
||
|
MSG msg;
|
||
|
BP_DestroyGlobals();
|
||
|
while (PeekMessage(&msg, hWnd, WM_HTML_BITMAP, WM_ASYNC_BITMAP, PM_REMOVE))
|
||
|
{
|
||
|
if ( msg.lParam )
|
||
|
{
|
||
|
if (msg.message == WM_ASYNC_BITMAP)
|
||
|
{
|
||
|
// clean up this useless crap
|
||
|
DeleteObject(((PASYNCWALLPARAM)(msg.lParam))->hbmp);
|
||
|
LocalFree((PASYNCWALLPARAM)(msg.lParam));
|
||
|
}
|
||
|
else // WM_HTML_BITMAP
|
||
|
DeleteObject((HBITMAP)msg.lParam);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
break;
|
||
|
|
||
|
case WM_SETBACKINFO:
|
||
|
if (g_hbmPreview)
|
||
|
{
|
||
|
BuildPreviewBitmap(hWnd, NULL, wParam);
|
||
|
g_bInfoSet = TRUE;
|
||
|
|
||
|
InvalidateBackPrevContents(hWnd);
|
||
|
}
|
||
|
break;
|
||
|
|
||
|
case WM_ASYNC_BITMAP:
|
||
|
if (lParam)
|
||
|
{
|
||
|
PASYNCWALLPARAM pawp = (PASYNCWALLPARAM) lParam;
|
||
|
ASSERT(pawp->hbmp);
|
||
|
if (pawp->id == g_dwWallpaperID)
|
||
|
{
|
||
|
BuildPreviewBitmap(hWnd, pawp->hbmp, pawp->flags);
|
||
|
InvalidateBackPrevContents(hWnd);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
// clean up this useless crap
|
||
|
DeleteObject(pawp->hbmp);
|
||
|
LocalFree(pawp);
|
||
|
}
|
||
|
}
|
||
|
break;
|
||
|
|
||
|
|
||
|
case WM_HTML_BITMAP:
|
||
|
{
|
||
|
// may come through with NULL if the image extraction failed....
|
||
|
if (wParam == g_dwWallpaperID && lParam)
|
||
|
{
|
||
|
BuildPreviewBitmap(hWnd, (HBITMAP)lParam, BP_EXTERNALWALL);
|
||
|
InvalidateBackPrevContents(hWnd);
|
||
|
// Take ownership of bitmap
|
||
|
return 1;
|
||
|
}
|
||
|
|
||
|
// Bitmap for something no longer selected
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
case WM_PALETTECHANGED:
|
||
|
if ((HWND)wParam == hWnd)
|
||
|
break;
|
||
|
//fallthru
|
||
|
case WM_QUERYNEWPALETTE:
|
||
|
if (g_hpalWall)
|
||
|
InvalidateRect(hWnd, NULL, FALSE);
|
||
|
break;
|
||
|
|
||
|
case WM_PAINT:
|
||
|
BeginPaint(hWnd,&ps);
|
||
|
if (g_hbmPreview && g_bInfoSet)
|
||
|
{
|
||
|
hbmOld = (HBITMAP)SelectObject(g_hdcMemory, g_hbmPreview);
|
||
|
if (g_hpalWall)
|
||
|
{
|
||
|
hpalOld = SelectPalette(ps.hdc, g_hpalWall, FALSE);
|
||
|
RealizePalette(ps.hdc);
|
||
|
}
|
||
|
|
||
|
GetObject(g_hbmPreview, sizeof(bm), &bm);
|
||
|
GetClientRect(hWnd, &rc);
|
||
|
rc.left = ( rc.right - bm.bmWidth ) / 2;
|
||
|
rc.top = ( rc.bottom - bm.bmHeight ) / 2;
|
||
|
BitBlt(ps.hdc, rc.left, rc.top, bm.bmWidth, bm.bmHeight, g_hdcMemory,
|
||
|
0, 0, SRCCOPY);
|
||
|
|
||
|
if (g_hpalWall)
|
||
|
{
|
||
|
SelectPalette(ps.hdc, hpalOld, TRUE);
|
||
|
RealizePalette(ps.hdc);
|
||
|
}
|
||
|
SelectObject(g_hdcMemory, hbmOld);
|
||
|
}
|
||
|
EndPaint(hWnd,&ps);
|
||
|
return 0;
|
||
|
}
|
||
|
return DefWindowProc(hWnd,message,wParam,lParam);
|
||
|
}
|
||
|
|
||
|
BOOL RegisterBackPreviewClass()
|
||
|
{
|
||
|
WNDCLASS wc;
|
||
|
|
||
|
if (!GetClassInfo(HINST_THISDLL, c_szBackgroundPreview2, &wc))
|
||
|
{
|
||
|
wc.style = 0;
|
||
|
wc.lpfnWndProc = BackPreviewWndProc;
|
||
|
wc.cbClsExtra = 0;
|
||
|
wc.cbWndExtra = 0;
|
||
|
wc.hInstance = HINST_THISDLL;
|
||
|
wc.hIcon = NULL;
|
||
|
wc.hCursor = LoadCursor(NULL, IDC_ARROW);
|
||
|
wc.hbrBackground = (HBRUSH)(COLOR_3DFACE+1);
|
||
|
wc.lpszMenuName = NULL;
|
||
|
wc.lpszClassName = c_szBackgroundPreview2;
|
||
|
|
||
|
if (!RegisterClass(&wc))
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
return TRUE;
|
||
|
}
|