这是一篇讲述如何在位图上绘制直线、图形或者文字的文章。尽管这项工作相当简单,但是对一些新手来说,本文将会是一份方便的参考。
用HBITMAP进行操作
作为第一步,我们需要一个关联背景图像的HBitmap句柄。这个句柄可以由之前的操作返回、用CreateBitmap()函数创建、或者从资源中加载,具体操作如下:
view plaincopy to clipboardprint?
HBITMAP hBitmap = ::LoadBitmap(AfxGetInstanceHandle(), MAKEINGRESOURCE(IDC_BITMAP1));
HBITMAP hBitmap = ::LoadBitmap(AfxGetInstanceHandle(), MAKEINGRESOURCE(IDC_BITMAP1));
之后,从hBitmap里面我们可以提取一些基本属性:
view plaincopy to clipboardprint?
BITMAP bm;
GetObject(hBitmap, sizeof(HBITMAP), &bm);
long nWidth = bm.bmWidth;
long nHeight = bm.bmHeight;
BITMAP bm;
GetObject(hBitmap, sizeof(HBITMAP), &bm);
long nWidth = bm.bmWidth;
long nHeight = bm.bmHeight;
现在创建一个位于内存的dc(显示上下文),然后关联一张新的位图。
view plaincopy to clipboardprint?
// 初始化位图属性
BITMAPINFO bmInfo;
memset(&bmInfo.bmiHeader, 0, sizeof(BITMAPINFOHEADER));
bmInfo.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
bmInfo.bmiHeader.biWidth=width;
bmInfo.bmiHeader.biHeight=height;
bmInfo.bmiHeader.biPlanes=1;
bmInfo.bmiHeader.biBitCount=24;
// 创建一个临时dc, 全屏
HDC pDC = ::GetDC(NULL);
HDC TmpDC=CreateCompatibleDC(pDC);
// 创建一个新的位图,然后把它选入上面的临时dc
BYTE *pbase;
HBITMAP TmpBmp=CreateDIBSection(pDC,
&bmInfo,DIB_RGB_COLORS,(void**)&pbase,0,0);
HGDIOBJ TmpObj=SelectObject(TmpDC,TmpBmp);
// 初始化位图属性
BITMAPINFO bmInfo;
memset(&bmInfo.bmiHeader, 0, sizeof(BITMAPINFOHEADER));
bmInfo.bmiHeader.biSize=sizeof(BITMAPINFOHEADER);
bmInfo.bmiHeader.biWidth=width;
bmInfo.bmiHeader.biHeight=height;
bmInfo.bmiHeader.biPlanes=1;
bmInfo.bmiHeader.biBitCount=24;
// 创建一个临时dc, 全屏
HDC pDC = ::GetDC(NULL);
HDC TmpDC=CreateCompatibleDC(pDC);
// 创建一个新的位图,然后把它选入上面的临时dc
BYTE *pbase;
HBITMAP TmpBmp=CreateDIBSection(pDC,
&bmInfo,DIB_RGB_COLORS,(void**)&pbase,0,0);
HGDIOBJ TmpObj=SelectObject(TmpDC,TmpBmp);
TmpDC 就是那个你可以在上面画线、图形或者字体的显示上下文。例如,下面就是绘制一个字符串到背景图像的做法:
view plaincopy to clipboardprint?
//draw the background
HDC dcBmp=CreateCompatibleDC(TmpDC);
HGDIOBJ TmpObj2 = SelectObject(dcBmp,hbitmap);
BitBlt(TmpDC,0,0,width,height,dcBmp,0,0,SRCCOPY);
SelectObject(TmpDC,TmpObj2);
DeleteDC(dcBmp);
//choose the font
CFont m_Font;
LOGFONT* m_pLF;
m_pLF=(LOGFONT*)calloc(1,sizeof(LOGFONT));
strncpy(m_pLF->lfFaceName,"Times New Roman",31);
m_pLF->lfHeight=64;
m_pLF->lfWeight=600;
m_pLF->lfItalic=1;
m_pLF->lfUnderline=0;
m_Font.CreateFontIndirect(m_pLF);
//select the font in the dc
CDC dc;
dc.Attach(TmpDC);
CFont* pOldFont=NULL;
if (m_Font.m_hObject)
pOldFont = dc.SelectObject(&m_Font);
else
dc.SelectObject(GetStockObject(DEFAULT_GUI_FONT));
//Set text color
dc.SetTextColor(RGB(60,120,240));
//Set text position;
RECT pos = {40,40,0,0};
//draw the text
dc.SetBkMode(TRANSPARENT);
dc.DrawText("Test",4,&pos,DT_CALCRECT);
dc.DrawText("Test",4,&pos,0);
//cleanup
if (pOldFont) dc.SelectObject(pOldFont);
m_Font.DeleteObject();
dc.Detach();
free(m_pLF);
//draw the background
HDC dcBmp=CreateCompatibleDC(TmpDC);
HGDIOBJ TmpObj2 = SelectObject(dcBmp,hbitmap);
BitBlt(TmpDC,0,0,width,height,dcBmp,0,0,SRCCOPY);
SelectObject(TmpDC,TmpObj2);
DeleteDC(dcBmp);
//choose the font
CFont m_Font;
LOGFONT* m_pLF;
m_pLF=(LOGFONT*)calloc(1,sizeof(LOGFONT));
strncpy(m_pLF->lfFaceName,"Times New Roman",31);
m_pLF->lfHeight=64;
m_pLF->lfWeight=600;
m_pLF->lfItalic=1;
m_pLF->lfUnderline=0;
m_Font.CreateFontIndirect(m_pLF);
//select the font in the dc
CDC dc;
dc.Attach(TmpDC);
CFont* pOldFont=NULL;
if (m_Font.m_hObject)
pOldFont = dc.SelectObject(&m_Font);
else
dc.SelectObject(GetStockObject(DEFAULT_GUI_FONT));
//Set text color
dc.SetTextColor(RGB(60,120,240));
//Set text position;
RECT pos = {40,40,0,0};
//draw the text
dc.SetBkMode(TRANSPARENT);
dc.DrawText("Test",4,&pos,DT_CALCRECT);
dc.DrawText("Test",4,&pos,0);
//cleanup
if (pOldFont) dc.SelectObject(pOldFont);
m_Font.DeleteObject();
dc.Detach();
free(m_pLF);
在这有两个位图句柄:hBitmap和TmpBmp。你可以绘制新老两张位图,或者用TmpBmp替换hBitmap。
view plaincopy to clipboardprint?
DeleteObject(TmpDC, TmpObj);
DeleteDC(TmpDC);
DeleteObject(TmpDC, TmpObj);
DeleteDC(TmpDC);
最后,要删除临时dc。在这儿不要删除hBitmap和TmpBmp,否者你会失去他们。
view plaincopy to clipboardprint?
//final cleanup
SelectObject(TmpDC,TmpObj);
DeleteDC(TmpDC);
本文来自CSDN博客,转载请标明出处:http://blog.csdn.net/boyzk2008/archive/2009/03/28/4032082.aspx