I am trying to overlay an image on top of my screen with GDI+ and C++. I have successfully drawn an image to a non-transparent window, but I only want the background of my window to be transparent, not the entire window.
Here is my code:
#include <windows.h>
#include <gdiplus.h>
LRESULT CALLBACK WindowProcessMessages(HWND hwnd, UINT msg, WPARAM param, LPARAM lparam);
void draw(HDC hdc);
int WINAPI WinMain(HINSTANCE currentInstance, HINSTANCE previousInstance, PSTR cmdLine, INT cmdCount) {
// Initialize GDI+
Gdiplus::GdiplusStartupInput gdiplusStartupInput;
ULONG_PTR gdiplusToken;
Gdiplus::GdiplusStartup(&gdiplusToken, &gdiplusStartupInput, nullptr);
// Register the window class
const char* CLASS_NAME = "myWin32WindowClass";
WNDCLASS wc{};
wc.hInstance = currentInstance;
wc.lpszClassName = CLASS_NAME;
wc.hCursor = LoadCursor(nullptr, IDC_ARROW);
wc.hbrBackground = (HBRUSH)COLOR_WINDOW;
wc.lpfnWndProc = WindowProcessMessages;
RegisterClass(&wc);
// Create the window
//CreateWindow(CLASS_NAME, "Drawing Image",
// WS_POPUP | WS_VISIBLE, // Window style
// CW_USEDEFAULT, CW_USEDEFAULT, // Window initial position
// 800, 600, // Window size
// nullptr, nullptr, nullptr, nullptr);
CreateWindowEx(WS_EX_LAYERED, // Extended window style
CLASS_NAME, "Drawing Image",
WS_POPUP | WS_VISIBLE, // Window style
CW_USEDEFAULT, CW_USEDEFAULT, // Window position
800, 600, // Window size
nullptr, nullptr, currentInstance,
nullptr);
// Window loop
MSG msg{};
while (GetMessage(&msg, nullptr, 0, 0)) {
TranslateMessage(&msg);
DispatchMessage(&msg);
}
Gdiplus::GdiplusShutdown(gdiplusToken);
return 0;
}
LRESULT CALLBACK WindowProcessMessages(HWND hwnd, UINT msg, WPARAM param, LPARAM lparam) {
HDC hdc;
PAINTSTRUCT ps;
SetLayeredWindowAttributes(hwnd, RGB(0, 0, 0), 255, LWA_COLORKEY | LWA_ALPHA);
switch (msg) {
case WM_PAINT:
SetLayeredWindowAttributes(hwnd, 0, 128, LWA_ALPHA);
hdc = BeginPaint(hwnd, &ps);
draw(hdc);
EndPaint(hwnd, &ps);
return 0;
case WM_DESTROY:
PostQuitMessage(0);
return 0;
default:
return DefWindowProc(hwnd, msg, param, lparam);
}
}
void draw(HDC hdc) {
// MessageBox(nullptr, "Draw function called", "Debug", MB_OK);
Gdiplus::Graphics gf(hdc);
Gdiplus::Bitmap bmp(L"image.png");
gf.DrawImage(&bmp, 430, 10);
}
As far as I can tell, the SetLayeredWindowAttributes
of the window alpha affects the entire window.