I'm creating a non-intrusive popup window to notify the user when processing a time-consuming operation. At the moment I'm setting its transparency by calling SetLayeredWindowAttributes
which gives me a reasonable result:
alt text http://img6.imageshack.us/img6/3144/transparentn.jpg
However I'd like the text and close button to appear opaque (it doesn't quite look right with white text) while keeping the background transparent - is there a way of doing this?
In order to do "proper" alpha in a layered window you need to supply the window manager with a PARGB bitmap by a call to UpdateLayeredWindow
.
The cleanest way to achieve this that I know of is the following:
- Create a GDI+
Bitmap
object with the PixelFormat32bppPARGB
pixel format.
- Create a
Graphics
object to draw in this Bitmap
object.
- Do all your drawing into this object using GDI+.
- Destroy the
Graphics
object created in step 2.
- Call the
GetHBITMAP
method on the Bitmap
object to get a Windows HBITMAP
.
- Destroy the
Bitmap
object.
- Create a memory DC using
CreateCompatibleDC
and select the HBITMAP
from step 5 into it.
- Call UpdateLayeredWindow using the memory DC as a source.
- Select previous bitmap and delete the memory DC.
- Destroy the
HBITMAP
created in step 5.
This method should allow you to control the alpha channel of everything that is drawn: transparent for the background, opaque for the text and button.
Also, since you are going to be outputting text, I recommend that you call SystemParametersInfo
to get the default antialiasing setting (SPI_GETFONTSMOOTHING
), and then the SetTextRenderingHint
on the Graphics object to set the antialiasing type to the same type that is configured by the user, for a nicer look.
I suspect you'll need two top level windows rather than one - one that has the alpha blend and a second that is display above the first with the opaque text and button but with a transparent background. To accomplish this with a single window you'll need to use the UpdateLayeredWindow API call, but using this will cause your buttons to not redraw when they are interacted with (hover highlights, focus etc.)
It is possible that if this application is for Vista only there is a new API call that you can use, but I do not believe it is available in XP or earlier.
I can't say for sure, you'll need to try it, but since everything is a window, you could try setting the layered attributes for your button to make it opaque.
As for the text, you may be able to put that in its own frame with a set background and foreground color, and modify its layered attributes to make the background color transparent...
But since these are child windows and not the top-level window, I really don't know that it'll work.