21.VC(ui)-DIB段

 1.CreateDIBSection?

HBITMAP CreateDIBSection(
  HDC hdc,                   // 参考设备上下文句柄 
  CONST BITMAPINFO *pbmi,  //指向包含位图信息头,位屏蔽和颜色表的BITMAPINFO结构
  UINT iUsage,             // iUsage指明颜色表内是否包含的是调色板索引的RGB值,如果它是DIB_PAL_COLORS,则使用hdc当前选用的逻辑调色板,
  VOID **ppvBits,          //【out】 指向DIB段像素阵列的地址
  HANDLE hSection,         //由CreateFileMapping返回的文件映射对象(段对象)的句柄,
  DWORD dwOffset           // offset to bitmap bit values
);

GDI不在DIB段中支持所有有效的DIB格式,因为DIB段需要既可读又可写(可在其上绘制),因此GDI只在DIB段中支持不压缩的DIB格式,你无法创建压缩类型为BI_RLE4,BI_RLE8,BI_PNG和BI_JPEG的DIB段。
由GDI分配管理DIB段所需的内存,包括位图信息头信屏蔽和颜色表,这些数据由GDI维护,应用程序不能直接存取,GDI确实在GDI句柄表中保留了一项用于链向GDI内部和DIB相关的数据结构,这类似于DDB而不同于不由GDI管理的DIB
如果不是从内存映射文件对象创建DIB段,GDI从应用程序的虚拟内存空间为像素阵列分配存储空间,然后将其指针返回给调用者,

2.DDB和DIB像素阵列内存分配方式的不同点?
DDB像素阵列是从内核模式页面池中分配的,它们使用了有限的共享的系统资源,而应用程序不能直接存取像素阵列,相反,DIB的像素阵列由虚拟内存地址空间分配的,而不是系统堆分配的,虽然说系统堆是从虚拟内存地址空间分配的,它提供了一种再分配的机值,可以实现大量小对象的分配,而从虚拟内存空间分配必须以页面为单位,对于DIB段,GDI以64KB大小的块为单位分配内存,

3.GetDIBColorTable/SetDIBColorTable?
DIB段不是真正的DIB,因为应用程序不能像控制DIB颜色表那样直接访问其颜色表,  相反,DIB段的颜色表由GDI控制,应用程序只能通过严格受控的GetDIBColorTable/SetDIBColorTable函数对其进行存取。
为什么要存取DIB段的颜色表?调用CreateDIBSection函数创建DIB段的时候不是提供了颜色缚吗?这样做至少有两个合法的理由,第一:如果调用CreateDIBSection函数的iUsage参数是DIB_PAL_COLORS,应用程序只有逻辑调色板的相对调色板索引,不是真正的RGB颜色表,如果应用程序想要把DIB段保存为BMP文件,它必须有RGB颜色表,第二,通过控制基于调色板的图像的颜色表可以实现很多图像算法,比如,调整位图的色度,亮度和饱和度,或是将位图转换为灰度图像,要实现这些算法,应用程序必须控制RGB颜色表并报告颜色表的变化。

4.使用DIB段与DIB以及DDB相比,有哪些优势?
(1)用GDI进行设备无关的绘制,创建DIB时GDI没有什么帮助,对于DDB,唯一支持的颜色格式是与当前显示模式兼容的格式,如果图形应用程序想在8-bpp显示模式下用GDI实现24bpp绘制,DIB段是唯一的解决方案。
(2)结合GDI绘制和直接像素阵列操作,只有DIB段支持应用程序同时进行GDI绘制和直接像素操作,没有DIB段的话,你必须创建DIB和DDB,并在两者之间用GetDIBits和SetDIBits函数传递像素
 (3)灵活的内存管理,和从系统内存分配的DDB相比,DIB段的内存是从虚拟内存空间或内存映射文件分配的,只受虚拟内存空间和空闲磁盘空间的限制,比如,你可以创建8192*8192,32bpp的DIB段,它的大小是256MB,面是DDB在NT的系统下限制为48M, DIB段还允许同时创建更多的大位图,

5.24位DIB段的像素阵列是以BGR三位顺序排列的,而32位则以BGRA四位排列的

了解了您的问题,您是想通过获取窗口的句柄来实现截屏功能。在 Windows 平台上,可以使用以下方式来实现: ```c++ #include <Windows.h> bool CaptureScreen(HWND hWnd, const char* filename) { HDC hDc = GetDC(hWnd); HDC hMemDc = CreateCompatibleDC(hDc); RECT rcClient; GetClientRect(hWnd, &rcClient); int nWidth = rcClient.right - rcClient.left; int nHeight = rcClient.bottom - rcClient.top; HBITMAP hBitmap = CreateCompatibleBitmap(hDc, nWidth, nHeight); HBITMAP hOldBitmap = (HBITMAP)SelectObject(hMemDc, hBitmap); BitBlt(hMemDc, 0, 0, nWidth, nHeight, hDc, 0, 0, SRCCOPY); SelectObject(hMemDc, hOldBitmap); DeleteDC(hMemDc); ReleaseDC(hWnd, hDc); PBITMAPINFO pbi; pbi = CreateBitmapInfoStruct(hWnd, hBitmap); LPBYTE lpBits; lpBits = (LPBYTE)GlobalAlloc(GMEM_FIXED, pbi->bmiHeader.biSizeImage); GetDIBits(hMemDc, hBitmap, 0, (UINT)pbi->bmiHeader.biHeight, lpBits, pbi, DIB_RGB_COLORS); HANDLE hf; BITMAPFILEHEADER hdr; PBITMAPINFOHEADER pbih; LPBYTE lpData; DWORD dwTotal; DWORD cb; BYTE* hp; DWORD dwTmp; pbih = (PBITMAPINFOHEADER)pbi; lpData = (LPBYTE)(lpBits + pbih->biSize + pbi->bmiHeader.biClrUsed * sizeof(RGBQUAD)); dwTotal = ((DWORD)(pbih->biSizeImage + sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER))); hdr.bfType = 0x4d42; hdr.bfSize = dwTotal; hdr.bfReserved1 = 0; hdr.bfReserved2 = 0; hdr.bfOffBits = (DWORD)sizeof(BITMAPFILEHEADER) + (DWORD)sizeof(BITMAPINFOHEADER) + pbi->bmiHeader.biClrUsed * sizeof(RGBQUAD); hf = CreateFile(filename, GENERIC_READ | GENERIC_WRITE, (DWORD)0, NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, (HANDLE)NULL); if (hf == INVALID_HANDLE_VALUE) return false; WriteFile(hf, (LPVOID)&hdr, sizeof(BITMAPFILEHEADER), (LPDWORD)&dwTmp, NULL); WriteFile(hf, (LPVOID)pbih, sizeof(BITMAPINFOHEADER) + pbi->bmiHeader.biClrUsed * sizeof(RGBQUAD), (LPDWORD)&dwTmp, (NULL)); WriteFile(hf, (LPVOID)lpData, (DWORD)pbih->biSizeImage, (LPDWORD)&dwTmp, NULL); CloseHandle(hf); GlobalFree((HGLOBAL)lpBits); DeleteObject(hBitmap); return true; } ``` 上面的代码中,`CaptureScreen` 函数接收两个参数:`hWnd` 表示窗口句柄,`filename` 表示截图保存的文件名。该函数实现了从指定窗口截图,并将截图保存到指定文件中的功能。 注:上述代码中使用了一些辅助函数,如 `CreateBitmapInfoStruct`,请根据实际情况进行实现。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值