zoukankan      html  css  js  c++  java
  • 窗口中显示bmp图片的过程

    创建步骤


    我们首先大致了解下显示位图的基本步骤,主要有5步,如图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;
    }
    运行效果:



    效果分析


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


  • 相关阅读:
    入门练习
    课堂作业补充
    例题作业(9.1-9.7)
    stream — 创建stream(一)
    Lambda表达式的四大内置核心函数式接口
    lambda表达式基础语法及其使用
    java 按照固定大小分割 list 集合的几种方式
    分布式锁相关解决方案
    zabbix3.0 使用详解
    eclipse Memory Analyzer (mat) 安装及使用
  • 原文地址:https://www.cnblogs.com/jinxiang1224/p/8468345.html
Copyright © 2011-2022 走看看