Windows DIB文件操作详解-3.DDB转DIB
来源:互联网 发布:网线端口显示红灯 编辑:程序博客网 时间:2024/05/22 14:13
上一节讲到DIB转换成DDB以提高位图显示性能,那么这里自然想到DDB转DIB。DDB转DIB有什么用呢?最常见的应用场合就是你得到了一个屏幕截图的DDB,现在想把它保存到磁盘上,这时候就要用到DDB转DIB函数GetDIBits。
1.GetDIBits使用方法
函数定义如下
int GetDIBits( HDC hdc, // handle to DC HBITMAP hbmp, // handle to bitmap UINT uStartScan, // first scan line to set UINT cScanLines, // number of scan lines to copy LPVOID lpvBits, // array for bitmap bits LPBITMAPINFO lpbi, // bitmap data buffer UINT uUsage // RGB or palette index);
这个函数获得hbmp的位图信息和数据填充到提前分配好的lpvBits和lpbi指针指向的内存中,完成DDB到DIB转换。
这个函数的使用步骤如下
1.定义BITMAPINFOHEADER bmih结构,设置结构的size,设置bitcount为0。lpvBits参数设为NULL而lpbi参数设为&bmih,如此调用GetDIBits函数,此函数会将hbmp的相关信息(大小、深度等信息)填充到bmih结构。
2.按照步骤1得到的信息分配lpbi和lpvBits结构内存。原则上当lpvBits结构lpvBits不为NULL时,lpbi的前6个参数必须设置,这里直接将bmih内容复制给lpbi。
3.传入分配好的lpbi和lpvBits结构内存地址,调用GetDIBits函数得到位图信息和数据。
一定要注意这里的lpvBits和lpbi内存是自己在调用函数前分配的。
2.屏幕截图保存到文件
这里贴上一个笔者写的截图软件中的屏幕截图DDB转DIB的实例代码,建议下载完整源代码查看
BOOL CScreenBitmap::ExportToFile(CDC *pDC, TCHAR *szBmpName, RECT *pRect/*=NULL*/){HBITMAP hExportBmp;BITMAPFILEHEADER bmfh={0};/************************************************************************//* 获得数据 *//************************************************************************///获得要导出的DDB位图hExportBmp = CopyBitmap(pRect);//获得DDB信息BITMAPINFOHEADER bmih={0};bmih.biSize = sizeof(BITMAPINFOHEADER);bmih.biBitCount = 0;if (0 == GetDIBits(pDC->GetSafeHdc(), hExportBmp, 0, 0, NULL, (BITMAPINFO *)&bmih, DIB_RGB_COLORS)){return FALSE;}//删除已经分配的存储区if (NULL != m_pbmi){free(m_pbmi);m_pbmi = NULL;}if (NULL != m_pBits){free(m_pBits);m_pBits = NULL;}//分配新的存储区DWORD dwInfoSize;DWORD dwBitsSize;if (bmih.biBitCount>=16 && BI_BITFIELDS==bmih.biCompression){dwInfoSize = sizeof(BITMAPINFOHEADER) + 4*4;//字节对齐,RGBQUAD每个成员存储的内存大小为4字节TRACE("%d %d %d\n", sizeof(BITMAPINFO), sizeof(BITMAPINFOHEADER), sizeof(RGBQUAD));}else if (bmih.biBitCount>=16){dwInfoSize = sizeof(BITMAPINFOHEADER);}else{dwInfoSize = sizeof(BITMAPINFOHEADER) + 4*4*bmih.biClrUsed;//字节对齐,RGBQUAD每个成员存储的内存大小为4字节}dwBitsSize = bmih.biHeight * (((bmih.biBitCount*bmih.biPlanes*bmih.biWidth + 31) & ~31) >> 3);//分配对应的内存区m_pbmi = (PBITMAPINFO)malloc(dwInfoSize);if (NULL == m_pbmi){return FALSE;}m_pBits = (PBYTE)malloc(dwBitsSize);if (NULL == m_pBits){free(m_pbmi);return FALSE;}//读入位图信息和位图数据CopyMemory(m_pbmi, &bmih, sizeof(BITMAPINFOHEADER));if (0 == GetDIBits( pDC->GetSafeHdc(), hExportBmp, 0, bmih.biHeight, m_pBits, m_pbmi, DIB_RGB_COLORS)){free(m_pBits);free(m_pbmi);return FALSE;}/************************************************************************//* 保存数据 *//************************************************************************///计算文件头信息bmfh.bfType = *(WORD *)"BM";bmfh.bfSize = sizeof(BITMAPFILEHEADER) + dwInfoSize + dwBitsSize;bmfh.bfOffBits = sizeof(BITMAPFILEHEADER) + dwInfoSize;//写入到对应BMP文件中HANDLE hFile = CreateFile(szBmpName,GENERIC_WRITE, 0,NULL, CREATE_ALWAYS, FILE_ATTRIBUTE_NORMAL, NULL);CFile m_saveFile(hFile);m_saveFile.Write(&bmfh, sizeof(BITMAPFILEHEADER));m_saveFile.Write(m_pbmi, dwInfoSize);m_saveFile.Write(m_pBits, dwBitsSize);m_saveFile.Close();::DeleteObject(hExportBmp);return TRUE;}
最新完整截图软件源代码下载链接,这里CScreenBitmap类中是封装好的截图操作,包括屏幕指定区域截图、复制截图到剪切板上及截图保存到磁盘上,你可以在自己的项目中直接使用它。
原创,转载请注明来自http://blog.csdn.net/wenzhou1219
0 0
- Windows DIB文件操作详解-3.DDB转DIB
- Windows DIB文件操作详解-3.DDB转DIB
- Windows DIB文件操作详解-2.DIB转DDB
- Windows DIB文件操作详解-2.DIB转DDB
- Windows DIB文件操作详解-4.使用DIB Section
- Windows DIB文件操作详解-5.DIB和调色板
- DDB--DIB
- DDB&DIB
- Windows DIB文件操作详解-1.DIB的读入、保存和显示
- Windows DIB文件操作详解-1.DIB的读入、保存和显示
- windows下的DDB和DIB
- windows下的DDB和DIB
- Converting DIB to DDB
- Converting DDB to DIB
- DIB转为DDB
- DDB与DIB
- DDB与DIB
- Converting DDB to DIB
- 三十六计之1之胜战篇—瞒天过海
- opengl编程指南
- tomcat7 安装和环境变量配置
- 初探nodejs创建web服务器
- 关于学习cocos2d-x的计划
- Windows DIB文件操作详解-3.DDB转DIB
- 指针的算术运算
- 对抗赛
- tomcat中StandardContext
- Leetcode中几道二叉树题 II
- 操作系统学习之进程通信(PCI)
- 在iOS开发中使用FMDB
- SQL 授权与回收
- 进程和线程的概念以及如何创造线程