使用位图 (C) 仅捕获部分屏幕
Capture only part of the screen with Bitmap (C)
我在使用 BitBlt()
尝试捕获位于屏幕正中央的全宽和 1 像素高的图像时遇到问题。
HDC hdcTemp;
BYTE* bitPointer;
int x, y;
int red, green, blue, alpha;
HDC desktopWindow = GetDC(HWND_DESKTOP);
//GetWindowRect(hWND_Desktop, &rect);
int screenWidth = GetSystemMetrics(SM_CXSCREEN);
int screenHeight = GetSystemMetrics(SM_CYSCREEN);
int wPos = screenWidth / 2;
int hPos = screenHeight / 2;
int screenShotWidth = screenWidth;
int screenShotHeight = 1;
while (true)
{
hdcTemp = CreateCompatibleDC(desktopWindow);
BITMAPINFO bitmap;
bitmap.bmiHeader.biSize = sizeof(bitmap.bmiHeader);
bitmap.bmiHeader.biWidth = screenShotWidth;
bitmap.bmiHeader.biHeight = screenShotHeight;
bitmap.bmiHeader.biPlanes = 1;
bitmap.bmiHeader.biBitCount = 24;
bitmap.bmiHeader.biCompression = BI_RGB;
bitmap.bmiHeader.biSizeImage = screenShotWidth * 4 * screenShotHeight;
bitmap.bmiHeader.biClrUsed = 0;
bitmap.bmiHeader.biClrImportant = 0;
HBITMAP hBitmap2 = CreateDIBSection(hdcTemp, &bitmap, DIB_RGB_COLORS, (void**)(&bitPointer), NULL, NULL);
SelectObject(hdcTemp, hBitmap2);
BitBlt(hdcTemp, 0, 0, screenShotWidth, screenShotHeight, desktopWindow, 0, hPos-1 ,SRCCOPY);
for (int i = 0; i < (screenShotWidth * 4 * screenShotHeight); i += 4)
{
red = (int)bitPointer[i];
green = (int)bitPointer[i + 1];
blue = (int)bitPointer[i + 2];
x = i / (4 * screenShotHeight);
y = i / (4 * screenShotWidth);
std::cout << "r : " << red << " x: " << x << " y: " << y << "\n";
}
std::this_thread::sleep_for(std::chrono::milliseconds(2));
}
我知道在拍摄全屏时 BitBlt() 需要看起来像这样:
BitBlt(hdcTemp, 0, 0, screenWidth, screenHeight, desktopWindow, 0, 0 ,SRCCOPY);
我只是不知道要改变什么才能让它只捕获我想捕获的位于屏幕中间的部分...
bitmap.bmiHeader.biSizeImage = screenShotWidth * 4 * screenShotHeight;
对于 24 位位图大小应计算如下:
int size = ((screenShotWidth * 24 + 31) / 32) * 4 * screenShotHeight;
请注意,24 位位图没有 Alpha 通道,每个像素 3 个字节。将增量更改为以下内容:
for(int i = 0; i < (screenShotWidth * 3 * screenShotHeight); i += 3)
{
red = (int)bitPointer[i];
green = (int)bitPointer[i + 1];
blue = (int)bitPointer[i + 2];
...
}
为了方便起见,您还可以使用 32 位位图。
我在使用 BitBlt()
尝试捕获位于屏幕正中央的全宽和 1 像素高的图像时遇到问题。
HDC hdcTemp;
BYTE* bitPointer;
int x, y;
int red, green, blue, alpha;
HDC desktopWindow = GetDC(HWND_DESKTOP);
//GetWindowRect(hWND_Desktop, &rect);
int screenWidth = GetSystemMetrics(SM_CXSCREEN);
int screenHeight = GetSystemMetrics(SM_CYSCREEN);
int wPos = screenWidth / 2;
int hPos = screenHeight / 2;
int screenShotWidth = screenWidth;
int screenShotHeight = 1;
while (true)
{
hdcTemp = CreateCompatibleDC(desktopWindow);
BITMAPINFO bitmap;
bitmap.bmiHeader.biSize = sizeof(bitmap.bmiHeader);
bitmap.bmiHeader.biWidth = screenShotWidth;
bitmap.bmiHeader.biHeight = screenShotHeight;
bitmap.bmiHeader.biPlanes = 1;
bitmap.bmiHeader.biBitCount = 24;
bitmap.bmiHeader.biCompression = BI_RGB;
bitmap.bmiHeader.biSizeImage = screenShotWidth * 4 * screenShotHeight;
bitmap.bmiHeader.biClrUsed = 0;
bitmap.bmiHeader.biClrImportant = 0;
HBITMAP hBitmap2 = CreateDIBSection(hdcTemp, &bitmap, DIB_RGB_COLORS, (void**)(&bitPointer), NULL, NULL);
SelectObject(hdcTemp, hBitmap2);
BitBlt(hdcTemp, 0, 0, screenShotWidth, screenShotHeight, desktopWindow, 0, hPos-1 ,SRCCOPY);
for (int i = 0; i < (screenShotWidth * 4 * screenShotHeight); i += 4)
{
red = (int)bitPointer[i];
green = (int)bitPointer[i + 1];
blue = (int)bitPointer[i + 2];
x = i / (4 * screenShotHeight);
y = i / (4 * screenShotWidth);
std::cout << "r : " << red << " x: " << x << " y: " << y << "\n";
}
std::this_thread::sleep_for(std::chrono::milliseconds(2));
}
我知道在拍摄全屏时 BitBlt() 需要看起来像这样:
BitBlt(hdcTemp, 0, 0, screenWidth, screenHeight, desktopWindow, 0, 0 ,SRCCOPY);
我只是不知道要改变什么才能让它只捕获我想捕获的位于屏幕中间的部分...
bitmap.bmiHeader.biSizeImage = screenShotWidth * 4 * screenShotHeight;
对于 24 位位图大小应计算如下:
int size = ((screenShotWidth * 24 + 31) / 32) * 4 * screenShotHeight;
请注意,24 位位图没有 Alpha 通道,每个像素 3 个字节。将增量更改为以下内容:
for(int i = 0; i < (screenShotWidth * 3 * screenShotHeight); i += 3)
{
red = (int)bitPointer[i];
green = (int)bitPointer[i + 1];
blue = (int)bitPointer[i + 2];
...
}
为了方便起见,您还可以使用 32 位位图。