Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How does Bitblt() work with SRCAND?

Tags:

winapi

After reading theForger's "Transparent Bitmaps" tutorial for Windows API, I'm having trouble understanding the Bitblt() function with SRCAND, at a bitwise level.

Part of the code I have for drawing a single black and white bitmap with SRCAND looks like this, based from the tutorial.

BITMAP bm;
RECT rcClient;
PAINTSTRUCT ps;

HDC hdc = BeginPaint(hwnd, &ps); //hwnd = handle to current window
HDC hdcMem = CreateCompatibleDC(hdc);

GetObject(g_hbmBall, sizeof(bm), &bm); //g_hbmBall = handle to bitmap object

GetClientRect(hwnd, &rcClient);
FillRect(hdc, &rcClient, (HBRUSH)GetStockObject(LTGRAY_BRUSH));

SelectObject(hdcMem, g_hbmBall);
BitBlt(hdc, 0, 0, bm.bmWidth, bm.bmHeight, hdcMem, 0, 0, SRCAND);

What I'm confused about is the last line, how with bitwise AND, the white color of a bitmap image disappears in the result while the black color stays there. (The docs for SRCAND say it "Combines the colors of the source and destination rectangles by using the Boolean AND operator.")

This is what I see visually: enter image description here

Overall, I'm wondering, at the bitwise level, what's being compared between the handle to device context in the window and the white/black image to cause the white color to disappear in the result and the black color to stay?

What I thought would happen was that, at the start, the handle to device context contains only 0s. So no matter what color would be AND'd, doing AND with 0s always results in 0s, so everything would be black in the end, resulting in a black square.

like image 932
DragonautX Avatar asked Dec 15 '25 05:12

DragonautX


1 Answers

The docs for SRCAND say it "Combines the colors of the source and destination rectangles by using the Boolean AND operator."

More exactly, the bitwise AND operator is used.

Destination pixel is always grey (let's assume an RGB value of 0x7F7F7F). For white pixels in source image, the pixel value would be 0xFFFFFF, for black pixels 0x000000.

This results in the following equation if source pixel is black:

DWORD result = 0x000000 & 0x7F7F7F;

The result is 0x000000 (black), because AND only keeps bits which are 1 in both operands.

If the source pixel is white we have the following equation:

DWORD result = 0xFFFFFF & 0x7F7F7F;

The result is 0x7F7F7F (grey) because these are the bits that are 1 in both operands.

like image 134
zett42 Avatar answered Dec 16 '25 22:12

zett42



Donate For Us

If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!