代码
#include <windows.h>
#include <Psapi.h>
#include <algorithm>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <iostream>
#include <memory>
#include <string>
#include <thread>
#include <dxgi.h>
#include <d3d11.h>
#include <wrl.h>BOOL SaveBitmapToFile(HBITMAP hBitmap, LPCTSTR filename)
{BITMAP bmp;GetObject(hBitmap, sizeof(BITMAP), &bmp);DWORD dwBmpSize = ((bmp.bmWidth * bmp.bmBitsPixel + 31) / 32) * 4 * bmp.bmHeight;HANDLE hDIB = GlobalAlloc(GHND, dwBmpSize);char *lpbitmap = (char *)GlobalLock(hDIB);BITMAPINFOHEADER bi;bi.biSize = sizeof(BITMAPINFOHEADER);bi.biWidth = bmp.bmWidth;bi.biHeight = bmp.bmHeight;bi.biPlanes = 1;bi.biBitCount = 24;bi.biCompression = BI_RGB;bi.biSizeImage = 0;bi.biXPelsPerMeter = 0;bi.biYPelsPerMeter = 0;bi.biClrImportant = 0;bi.biClrUsed = 0;// 获取位图数据GetDIBits(GetDC(NULL), hBitmap, 0, (UINT)bmp.bmHeight, lpbitmap, (BITMAPINFO *)&bi, DIB_RGB_COLORS);// 创建文件并写入数据HANDLE hf = CreateFile(filename, GENERIC_WRITE, 0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);DWORD dwWritten;BITMAPFILEHEADER bfh;bfh.bfType = 0x4D42; // BMbfh.bfSize = sizeof(BITMAPFILEHEADER) + dwBmpSize;bfh.bfReserved1 = 0;bfh.bfReserved2 = 0;bfh.bfOffBits = (DWORD)sizeof(BITMAPFILEHEADER) + (DWORD)sizeof(BITMAPINFOHEADER);WriteFile(hf, (LPSTR)&bfh, sizeof(BITMAPFILEHEADER), &dwWritten, NULL);WriteFile(hf, (LPSTR)&bi, sizeof(BITMAPINFOHEADER), &dwWritten, NULL);WriteFile(hf, lpbitmap, dwBmpSize, &dwWritten, NULL);// 清理GlobalUnlock(hDIB);GlobalFree(hDIB);CloseHandle(hf);return TRUE;
}bool CaptureScreen(const wchar_t *filePath)
{// 获取屏幕宽高int width = GetSystemMetrics(SM_CXSCREEN);int height = GetSystemMetrics(SM_CYSCREEN);// 创建屏幕DCHDC hScreenDC = GetDC(NULL);if (!hScreenDC){std::cerr << "Failed to get screen DC" << std::endl;return 1;}// 创建一个与屏幕DC兼容的内存DCHDC hMemoryDC = CreateCompatibleDC(hScreenDC);if (!hMemoryDC){std::cerr << "Failed to create memory DC" << std::endl;ReleaseDC(NULL, hScreenDC);return 1;}// 创建一个与屏幕兼容的位图HBITMAP hBitmap = CreateCompatibleBitmap(hScreenDC, width, height);if (!hBitmap){std::cerr << "Failed to create bitmap" << std::endl;DeleteDC(hMemoryDC);ReleaseDC(NULL, hScreenDC);return 1;}// 将位图选入内存DCHGDIOBJ old_obj = SelectObject(hMemoryDC, hBitmap);// 捕获屏幕到内存DCif (!BitBlt(hMemoryDC, 0, 0, width, height, hScreenDC, 0, 0, SRCCOPY)){std::cerr << "Failed to capture screen" << std::endl;SelectObject(hMemoryDC, old_obj);DeleteObject(hBitmap);DeleteDC(hMemoryDC);ReleaseDC(NULL, hScreenDC);return 1;}// 保存位图if (!SaveBitmapToFile(hBitmap, filePath)){std::cerr << "Failed to save bitmap" << std::endl;}// 清理资源SelectObject(hMemoryDC, old_obj);DeleteObject(hBitmap);DeleteDC(hMemoryDC);ReleaseDC(NULL, hScreenDC);return 0;
}