GetDIBits 并使用 X、Y 循环遍历像素

2023-12-10

我抓住屏幕的一部分并扫描像素以获得特定的颜色范围。

我在看MSDN 的捕获图像示例并了解如何使用这些功能。

我可以将这些位放入数组中,但我不确定如何以可以像处理图像一样循环遍历它的方式进行操作。一个伪示例(我确信这是很遥远的):

for ( x = 1; x <= Image.Width; x += 3 )
{
    for ( y = 1; y <= Image.Height; y += 3 )
    {
        red = lpPixels[x];
        green = lpPixels[x + 1];
        blue = lpPixels[x + 2];
    }
}

这基本上就是我想要做的,所以如果红色、蓝色和绿色是某种颜色,我就会知道它在图像中的 (x, y) 处的坐标。

我只是不知道如何以这种方式使用 GetDIBits,以及如何正确设置数组才能完成此任务。


除了已经给出的好的答案之外,这里还有一个例子how得到一个简单的数组结构来行走。 (您可以使用例如戈兹的代码用于迭代。)

GetDIBits 参考@MSDN

你必须选择DIB_RGB_COLORS作为标志uUsage并设置BITMAPINFO结构BITMAPINFOHEADER结构它包含。当你设置biClrUsed and biClrImportant为零,则“无”颜色表,因此您可以读取从中获取的位图的像素GetDIBits作为 RGB 值的序列。使用32作为位数(biBitCount)根据MSDN设置数据结构:

位图最多有 2^32 种颜色。如果biCompression的成员BITMAPINFOHEADER is BI_RGB, the bmiColors成员BITMAPINFO is NULL. Each DWORD位图数组中的 分别表示像素的蓝色、绿色和红色的相对强度。每个中的高字节DWORD未使用。

自从成为 MSLONG正好是 32 位长(a 的大小DWORD),您不必注意填充(如备注部分).

Code:

HDC hdcSource = NULL; // the source device context
HBITMAP hSource = NULL; // the bitmap selected into the device context

BITMAPINFO MyBMInfo = {0};
MyBMInfo.bmiHeader.biSize = sizeof(MyBMInfo.bmiHeader);

// Get the BITMAPINFO structure from the bitmap
if(0 == GetDIBits(hdcSource, hSource, 0, 0, NULL, &MyBMInfo, DIB_RGB_COLORS))
{
    // error handling
}

// create the pixel buffer
BYTE* lpPixels = new BYTE[MyBMInfo.bmiHeader.biSizeImage];

// We'll change the received BITMAPINFOHEADER to request the data in a
// 32 bit RGB format (and not upside-down) so that we can iterate over
// the pixels easily. 

// requesting a 32 bit image means that no stride/padding will be necessary,
// although it always contains an (possibly unused) alpha channel
MyBMInfo.bmiHeader.biBitCount = 32;
MyBMInfo.bmiHeader.biCompression = BI_RGB;  // no compression -> easier to use
// correct the bottom-up ordering of lines (abs is in cstdblib and stdlib.h)
MyBMInfo.bmiHeader.biHeight = abs(MyBMInfo.bmiHeader.biHeight);

// Call GetDIBits a second time, this time to (format and) store the actual
// bitmap data (the "pixels") in the buffer lpPixels
if(0 == GetDIBits(hdcSource, hSource, 0, MyBMInfo.bmiHeader.biHeight,
                  lpPixels, &MyBMInfo, DIB_RGB_COLORS))
{
    // error handling
}
// clean up: deselect bitmap from device context, close handles, delete buffer
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

GetDIBits 并使用 X、Y 循环遍历像素 的相关文章

随机推荐