Discussion:
Bitmap shown "transparent" in static control due to Common Controls 6?
(too old to reply)
Carl Colijn
2010-04-03 20:57:48 UTC
Permalink
Hi group,

I hit upon a problem I can't explain. I have a dialog on which I
placed a static control with the SS_BITMAP style. On run-time I load a
bitmap with the LoadImage function and show it in the control with the
STM_SETIMAGE message. I also include a manifest file to make the app
use Common Controls version 6, thus enabling Windows XP themes. I run
this app on a Windows XP SP3 machine.

When I save the bitmap with a full palette all shows OK, but when I
only add the needed colors in the bitmap's palette (say e.g. a palette
of only 3 colors) one of the colors in the bitmap shows
"transparent"...?! By removing the manifest the bitmap with the
reduced palette will also show OK. To remove unused colors from the
palette I used the Gimp.

What could be the cause of this? Is it the theme support in XP that
acts wrong / "special" with these bitmaps, or is the saved bitmap
corrupt in some way? (corrupt being either really corrupt or not
conforming to some Windows UI guidelines I'm unaware of.)

I have created a very simple app in C++ (with Code::Blocks) showing
this effect; see below for the sources. The zipped up project includes
all source files, the final .exe and both images. It can download (6.3
KB) from my website at:
http://www.twologs.com/auto_transparent_image.zip

I'd really appreciate some insight / help on this!

Kind regards,
Carl Colijn

TwoLogs - IT Services and Product Development
A natural choice!
http://www.twologs.com
TimeTraces: the powerful and versatile time registration system!
http://timetraces.twologs.com


==================
= Resource.h:
==================
#ifndef INCLUDE_RESOURCE_H
#define INCLUDE_RESOURCE_H

#define IDD_DIALOG 1
#define IDC_IMAGE 2
#define IDI_IMAGE1 3
#define IDI_IMAGE2 4

#endif // INCLUDE_RESOURCE_H


==================
= Main.cpp:
==================
#define _WIN32_IE 0x0400
#include <windows.h>
#include <commctrl.h>
#include "Resource.h"

HINSTANCE g_hInstance;
DWORD g_nBitmapID;

LRESULT CALLBACK DlgProc(HWND hDlg, UINT nMsg, WPARAM nWParam, LPARAM
nLParam) {
if (nMsg == WM_CLOSE) {
EndDialog(hDlg, 0);
SetWindowLong(hDlg, DWL_MSGRESULT, 0);
return true;
} else if (nMsg == WM_INITDIALOG) {
HBITMAP hBitmap = (HBITMAP)LoadImage(g_hInstance,
MAKEINTRESOURCE(g_nBitmapID), IMAGE_BITMAP, 0, 0, LR_CREATEDIBSECTION);
SendDlgItemMessage(hDlg, IDC_IMAGE, STM_SETIMAGE, IMAGE_BITMAP,
(LPARAM)hBitmap);
SetWindowLong(hDlg, DWL_MSGRESULT, TRUE);
return true;
} else {
return false;
}
}

int WINAPI WinMain(HINSTANCE hThisInstance, HINSTANCE hPrevInstance,
LPSTR csArgument, int nFunsterStil) {
INITCOMMONCONTROLSEX oInit;
oInit.dwSize = sizeof(INITCOMMONCONTROLSEX);
oInit.dwICC = ICC_DATE_CLASSES;
InitCommonControlsEx(&oInit);
g_hInstance = hThisInstance;
g_nBitmapID = IDI_IMAGE1;
DialogBoxParam(hThisInstance, MAKEINTRESOURCE(IDD_DIALOG), NULL,
(DLGPROC)DlgProc, 0);
g_nBitmapID = IDI_IMAGE2;
DialogBoxParam(hThisInstance, MAKEINTRESOURCE(IDD_DIALOG), NULL,
(DLGPROC)DlgProc, 0);
return 0;
}


==================
= Resource.rc:
==================
#include <windows.h>
#include "Resource.h"

CREATEPROCESS_MANIFEST_RESOURCE_ID RT_MANIFEST "Manifest.txt"

IDI_IMAGE1 BITMAP "Image1.bmp"
IDI_IMAGE2 BITMAP "Image2.bmp"

IDD_DIALOG DIALOGEX 0, 0, 160, 80
CAPTION "Color Test"
BEGIN
CONTROL "", IDC_IMAGE, WC_STATIC, SS_BITMAP | SS_SUNKEN, 7, 7, 21,
18
END


==================
= Manifest.txt:
==================
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<assembly xmlns="urn:schemas-microsoft-com:asm.v1"
manifestVersion="1.0">
<assemblyIdentity
version="1.0.0.0"
processorArchitecture="X86"
name="Test"
type="win32"
/>
<description></description>
<dependency>
<dependentAssembly>
<assemblyIdentity
type="win32"
name="Microsoft.Windows.Common-Controls"
version="6.0.0.0"
processorArchitecture="X86"
publicKeyToken="6595b64144ccf1df"
language="*"
/>
</dependentAssembly>
</dependency>
</assembly>


==================
= Project set-up instructions:
==================
- Link in Comctl32.lib
- Set optimizations to max
Carl Colijn
2010-04-04 15:17:25 UTC
Permalink
Post by Carl Colijn
Hi group,
I hit upon a problem I can't explain. I have a dialog on which I
placed a static control with the SS_BITMAP style. On run-time I load
a bitmap with the LoadImage function and show it in the control with
the STM_SETIMAGE message. I also include a manifest file to make the
app use Common Controls version 6, thus enabling Windows XP themes.
I run this app on a Windows XP SP3 machine.
When I save the bitmap with a full palette all shows OK, but when I
only add the needed colors in the bitmap's palette (say e.g. a palette
of only 3 colors) one of the colors in the bitmap shows
"transparent"...?! By removing the manifest the bitmap with the
reduced palette will also show OK. To remove unused colors from the
palette I used the Gimp.
What could be the cause of this? Is it the theme support in XP that
acts wrong / "special" with these bitmaps, or is the saved bitmap
corrupt in some way? (corrupt being either really corrupt or not
conforming to some Windows UI guidelines I'm unaware of.)
To answer my own post: the bitmap was loaded via LoadImage with the
flag LR_CREATEDIBSECTION. When the flag LR_DEFAULTCOLOR is used, the
problem goes away. Appearantly the bitmaps with the special behavior
didn't result in a compatible bitmap of sorts? I'm still interested in
the exact reason for this if someone wants to elaborate on it, but the
problem has been resolved.
--
Kind regards,
Carl Colijn

TwoLogs - IT Services and Product Development
A natural choice!
http://www.twologs.com
TimeTraces: the powerful and versatile time registration system!
http://timetraces.twologs.com
Chris Becke
2010-04-06 08:36:12 UTC
Permalink
Post by Carl Colijn
Post by Carl Colijn
Hi group,
I hit upon a problem I can't explain. I have a dialog on which I
placed a static control with the SS_BITMAP style. On run-time I load
a bitmap with the LoadImage function and show it in the control with
the STM_SETIMAGE message. I also include a manifest file to make the
app use Common Controls version 6, thus enabling Windows XP themes.
I run this app on a Windows XP SP3 machine.
When I save the bitmap with a full palette all shows OK, but when I
only add the needed colors in the bitmap's palette (say e.g. a palette
of only 3 colors) one of the colors in the bitmap shows
"transparent"...?! By removing the manifest the bitmap with the
reduced palette will also show OK. To remove unused colors from the
palette I used the Gimp.
What could be the cause of this? Is it the theme support in XP that
acts wrong / "special" with these bitmaps, or is the saved bitmap
corrupt in some way? (corrupt being either really corrupt or not
conforming to some Windows UI guidelines I'm unaware of.)
To answer my own post: the bitmap was loaded via LoadImage with the
flag LR_CREATEDIBSECTION. When the flag LR_DEFAULTCOLOR is used, the
problem goes away. Appearantly the bitmaps with the special behavior
didn't result in a compatible bitmap of sorts? I'm still interested in
the exact reason for this if someone wants to elaborate on it, but the
problem has been resolved.
Looking at the bitmaps bits, they both seem to 100% legitimate bitmaps.

I can only imagine that the static control for version 6 common controls
has a bug in its transparency detection logic - rather than checking the
number of bits of color depth they do an explicit number_of_colors == 16
check.

At any rate, the version 6 static control is meant (per comments in
MSDN) check and process images with alpha to draw them correctly. This
would seem to be failing when passed a bitmap with a relatively novel
structure.

Loading...