窗口中显示bmp图片的过程

创建步骤


我们首先大致了解下显示位图的基本步骤,主要有5步,如图1所示:

窗口中显示bmp图片的过程_第1张图片

                                                            图1 位图显示步骤

对每个过程的解释如下:

1.创建位图

   利用CBitmap类构造一个位图对象,然后利用LoadBitmap函数完成实际位图资源和对象的关联.

2.创建兼容DC

   在OnDraw或OnEraseBkgnd函数的入参是CDC对象指针,指示了当前实际显示设备的相关信息;我们利用CreateCompatible函数创建一个内存设备上下文,和参数pDC所指定的DC相兼容。内存设备上下文实际上是一个内存块,表示一个显示的表面,可以认为是虚拟的设备显示环境

3.将位图选人兼容DC中

   当兼容的内存设备上下文被创建时,它的表面是标准的一个单色像素宽和一个单色像素高,我们需要将具有有正确的宽度和高度的位图选人兼容DC,才能正确的显示。

4.将兼容DC中的位图粘贴到当前DC

    我们可以利用BitBlt函数或者StrechBlt函数完成兼容DC中的图像到实际DC的搬移和显示。

5.位图显示

     利用窗口绘制过程的两个时机完成位图显示,一个窗口绘制过程包括两个步骤:首先是利用画刷擦除窗口背景,其次是再对窗口重新进行重绘;擦除是调用OnEraseBkgnd函数,重绘是调用OnDraw函数


函数说明


BitBlt函数是以1:1的比例完成拷贝,而StrechBlt函数则可以进行图片的压缩或者扩展,它们的函数声明和参数函数如下所示,更加具体的信息参数MSDN:

BitBlt函数声明如下:

BOOL BitBlt( int x, int y, int nWidth, int nHeight, CDC* pSrcDC, int xSrc, int ySrc, DWORD dwRop );

返回值:函数成功,返回非零值,否则为0。
参数: 
x       指定目标矩形左上角的逻辑x坐标。  
y       指定目标矩形左上角的逻辑y坐标。  
nWidth  指定目标矩形和源位图的宽度(逻辑单位)。  
nHeight 指定目标矩形和源位图的高度(逻辑单位)。  
pSrcDC  指向CDC对象的指针,标识待拷贝位图的设备上下文。  
xSrc    指定源位图左上角的逻辑X坐标。  
ySrc    指定源位图左上角的逻辑Y坐标。  
dwRop   指定要执行的光栅操作 

StrechBlt函数声明如下:

BOOL StretchBlt(
     int x,
     int y,
     int nWidth,
     int nHeight,
     CDC* pSrcDC,
     intxSrc,
     int ySrc,
     int nSrcWidth,
     int nSrcHeight,
     DWORD dwRop
     )

返回值:如果位图已经绘制,则返回非零值,否则为0。
参数: 
x           目标矩形左上角的X逻辑坐标。  
y           目标矩形左上角的Y逻辑坐标。  
nWidth      目标矩形的宽度(逻辑单位)。  
nHeight     目标矩形的高度(逻辑单位)。  
pSrcDC      指定源设备上下文。  
xSrc        源矩形左上角的X逻辑坐标。  
ySrc        源矩形左上角的Y逻辑坐标。  
nSrcWidth   源矩形的宽度(逻辑单位)。  
nSrcHeight  源矩形的高度(逻辑单位)。  
dwRop       指定光栅操作。

功能代码


我们这里以OnEraseBKgnd消息响应函数完成整个显示功能,该函数在视类中进行响应,具体代码如下:

BOOL CCBmpViewView::OnEraseBkgnd(CDC* pDC)
{
    // TODO: 在此添加消息处理程序代码和/或调用默认值

    //创建位图对象
    CBitmap bitmap;
    bitmap.LoadBitmap(IDB_BITMAP1);

    //获取位图信息
    BITMAP bmp;
    bitmap.GetBitmap(&bmp);

    //创建兼容DC
    CDC dcCompatible;
    dcCompatible.CreateCompatibleDC(pDC);

    //将位图选入兼容DC
    dcCompatible.SelectObject(&bitmap);

    //向实际DC输出图片
    CRect rect;
    GetClientRect(&rect);
    //1比1格式输出图片
    //pDC->BitBlt(0,0,rect.Width(), rect.Height(),&dcCompatible,0,0,SRCCOPY);
    //适应实际窗口大小进行图片压缩或者拉伸输出
    pDC->StretchBlt(0,0,rect.Width(), rect.Height(),&dcCompatible,0,0,bmp.bmWidth,bmp.bmHeight,SRCCOPY);
   
    return TRUE;
}
运行效果:

窗口中显示bmp图片的过程_第2张图片


效果分析


通过两种方式进行对比发现,若我们的位图大小比窗口小,以OnEraseBkgnd函数和BitBlt函数进行输出图片,改变窗口大小会有窗口的残留痕迹;若以OnDraw函数和BitBlt函数进行输出则没有这样的问题,但是会带来视觉上的闪烁;StrechBlt函数由于有压缩或者拉伸造成图片失真。


转载于:https://www.cnblogs.com/jinxiang1224/p/8468345.html

你可能感兴趣的:(窗口中显示bmp图片的过程)