




版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、 HYPERLINK /zhmxy555/article/details/7422922 【Visual C+】游戏开发笔记十四 游戏画面绘图(四) 华丽的CImage类本系列文章由zhmxy555编写,转载请注明出处。 HYPERLINK /zhmxy555/article/details/7422922 /zhmxy555/article/details/7422922作者:毛星云邮箱: HYPERLINK mailto:happylifemxy happylifemxy欢迎邮件交流编程心得我们知道,VisualC+中的CBitmap类的功能简直太弱小了,这曾经让Visual C+在图像处
2、理方面的功能比较尴尬。之前笔记里面,我们采用的CBitmap配合GDI进行透明图像的处理有些晦涩繁琐,而且受到图像素材的限制,可以说是有些落后,不是太实用。为了解决这个问题,这节笔记我们将系统的学习MFC和ATL中新增一个图像处理的类,它就是华丽而强大的CImage类。由于本节笔记是对CImage类的一个非常系统近乎完全的介绍,我尽量让它涵盖到了CImage类的所有的属性和类成员,所以篇幅也许比以往的笔记内容都长,里面的不少内容是用到的时候才需要掌握或者查阅的,并不用强行记忆。一,概念讲解部分1.CImage类的定位和概述首先,我们简单介绍一下CImage类的定位。CImage是MFC和ATL
3、共享的新类,它提供了增强的位图支持,包括加载、保存和转换JPEG,BMP,GIF,PNG图像格式的能力。可以说是微软意识到了CBitmap的不足,然后推出了一个CBitmap的增强版。使用CImage类,需在代码头部加入包含atlimage.h文件,即添加代码#includeatlimage.h。由于CImage拥有功能强大的类成员函数的支持,它便具有了下列四个比较出彩的特性:1、AlphaBlend支持像素级的颜色混合,从而实现透明和半透明的效果。2、PlgBlt能使一个矩形区域的位图映射到一个平行四边形区域中,而且还可能使用位屏蔽操作。3、TransparentBlt在目标区域中产生透明图
4、像4、MaskBlt在目标区域中产生源位图与屏蔽位图合成的效果。2.以CImage类做媒,让CBitmap类也能处理丰富的图片格式解决的思路比较明朗,我们采用CImage类的Load函数加载图片,之后用Detch取得HBITMAP的句柄,然后再将此句柄附加给CBitmap的对象就行了。这样就实现了让CBitmap类也可以操作JPG/JPEG/GIF/PNG格式的图片。具体代码如下:cpp HYPERLINK /zhmxy555/article/details/7422922 o view plain view plain HYPERLINK /zhmxy555/article/details/
5、7422922 o copy copy HYPERLINK /zhmxy555/article/details/7422922 o print print HYPERLINK /zhmxy555/article/details/7422922 o ? ?#includeatlimage.hCImageimage;/定义一个CBitmap类image.Load(“filename”);/filename为要加载的文件地址HBITMAPhBitmap=image.Detach();/返回被分离的图片的句柄CBitmapbmp;/定义一个bitmapbmp.Attach(hBitmap);/进行句柄
6、的附加然后就可以用CBitmap进行余下的操作了。3.CImage额外的一些性质CImage类对于DIB(device-independentbitmap)设备无关位图文件和非DIB都可以处理。我们可以通过Create函数或者CImage:Load来处理DIB部分,用Attach函数来将非DIB部分附加到一个CImage对象上。对于以下函数,只支持DIB部分的位图文件,他们是:GetBitsGetColorTable,GetMaxColorTableEntries,GetPitch,GetPixelAddress,IsIndexed,SetColorTable。我们可以通过CImage类中的I
7、sDIBSection()函数来帮助我们判断一个位图文件是否为DIB部分,其定义如下:cpp HYPERLINK /zhmxy555/article/details/7422922 o view plain view plain HYPERLINK /zhmxy555/article/details/7422922 o copy copy HYPERLINK /zhmxy555/article/details/7422922 o print print HYPERLINK /zhmxy555/article/details/7422922 o ? ?boolIsDIBSection()cons
8、tthrow();/如果返回值为true,则该文件为DIB;返回flase则不是DIB文件我们需要注意的是,CImage不能被选到一个新的CDC(classofdevice-context设备描述表的类),CImage会为图像创建自己的HDC(设备描述表DC的句柄)。因为一个HBITMAP只能被选入到一个HDC中一次,也就是说这个与CImage相关的HBITMAP不能被选到一个其他的HDC中。如果需要一个CDC,我们可以从CImage中获取HDC,然后使用CDC::FromHandle函数。4.CImage兼容性的说明在CImage中,有如下兼容性的要求:只支持WindowsNT4.0以上系统
9、的成员函数:PlgBlt,MaskBlt,AlphaBlend。只支持Windows2000,98以上系统的成员函数:TransparentBlt,Draw其实由于目前都是WindowsXP以上的操作系统,这个知识点了解一下就行。5.CImage类用于贴图的一般的使用方法使用方法不唯一,最常用的方法如下,该方法大致分为三部分:在源文件中添加CImage类的包含文件:#includeatlimage.h定义一个CImage类对象,然后调用CImage:Load方法装载一个外部图像文件。Load方法有如下两种重载:cpp HYPERLINK /zhmxy555/article/details/74
10、22922 o view plain view plain HYPERLINK /zhmxy555/article/details/7422922 o copy copy HYPERLINK /zhmxy555/article/details/7422922 o print print HYPERLINK /zhmxy555/article/details/7422922 o ? ?HRESULTLoad(LPCTSTRpszFileName/包含加载文件名的字符串指针)throw();HRESULTLoad(IStream*pStream/指向包含加载文件名的流的指针)throw();调用C
11、Image:Draw方法绘制图像。下面重点介绍一下Draw方法。CImage:Draw将一个位图文件从源设备描述表复制到当前设备描述表该函数有如下六种重载:cpp HYPERLINK /zhmxy555/article/details/7422922 o view plain view plain HYPERLINK /zhmxy555/article/details/7422922 o copy copy HYPERLINK /zhmxy555/article/details/7422922 o print print HYPERLINK /zhmxy555/article/details/
12、7422922 o ? ?BOOLDraw(HDChDestDC,/目标设备环境DC的句柄intxDest,/目的矩形的左上角X坐标(逻辑单位)intyDest,/目的矩形的左上角Y坐标(逻辑单位)intnDestWidth,/目标矩形的宽度(就是设定贴过去的图片的宽度)intnDestHeight,/目标矩形的高度(就是设定铁锅的图片的高度)intxSrc,/源矩形的左上角X坐标intySrc,/源矩形的左上角Y坐标intnSrcWidth,/源矩形的宽度intnSrcHeight/源矩形的高度)constthrow();BOOLDraw(HDChDestDC,/目标环境DC的句柄const
13、RECT&rectDest,/一个RECT结构的引用,用来确定目标图像。constRECT&rectSrc/一个RECT结构体的引用,用来确定源图像)constthrow();BOOLDraw(HDChDestDC,/目标环境DC的句柄intxDest,/目标矩形的左上角X坐标intyDest/目标矩形的左上角Y坐标)constthrow();/BOOLDraw(HDChDestDC,/目标环境DC的句柄constPOINT&pointDest/一个POINT结构体,用来确定目的矩形的左上角坐标)constthrow();BOOLDraw(HDChDestDC,/目标环境DC的句柄intxDe
14、st,/目标矩形的左上角X坐标intyDest,/目标矩形的左上角Y坐标intnDestWidth,/目标矩形的宽度intnDestHeight/目标矩形的宽度)constthrow();BOOLDraw(HDChDestDC,/目标环境DC的句柄constRECT&rectDest/一个RECT结构的引用,用来确定目标图像。)constthrow();在上面的Draw函数的各种重载中,对于没有指定源矩形的版本,则整个源图像就是默认的源矩形。对于没有指定目的矩形尺寸的,则源图片的尺寸就是默认的目的矩形尺寸。需要注意的是,Draw方法综合了StretchBlt、TransparentBlt和Al
15、phaBlend函数的功能。通常情况下,Draw()函数作用和StretchBlt()函数一致。但是当我们的图像中存在透明的颜色和alpha通道的时候,Draw()函数作用和TransparentBlt()或者AlphaBlend()函数一致。所以,在一般情况下,我们都尽量调用Draw方法来绘制图像。6.对CImage所有类成员的介绍我将CImage类的所有类函数按功能分为了四大类,可以更方面的了解各函数的定位和作用,也方便大家查阅:功能为创建与连接,释放的函数Attach附加一个HBITMAP到CImage对象,位图类型DIB与否都可以Create创建一个DIB部分的位图,并将其附加到之前创
16、建的CImage对象CreateEX创建一个DIB部分的位图(拥有额外的参数),并将其附加到之前 创建的CImage对象Destroy从CImage类上分离该位图并进行删除Detach从CImage类里分离该位图ReleaseDC 释放设备描述表中的数据ReleaseGDIPlus释放GDI+使用的源功能为输入与输出的函数GetExporterFilterString返回系统支持的输入文件格式类型及其描述GetImporterFilterString返回系统支持的输出文件格式类型及其描述LoadFromResource从指定的源处加载一个图像资源Load从指定文件处加载一个图像资源IsInde
17、xed判断一个位图颜色映射到了一个索引调色盘IsNull判断一个源位图是否被当前载入Save以指定的类型来保存图像关于位图类型与参数的函数GetBits返回一个指向该位图实际像素值指针GetBPP返回该位图每个像素的位GetColorTable返回颜色表中RGB值的范围条目GetDC返回目前被选择的设备描述表GetExporterFilterString返回系统支持的输入文件格式类型及其描述GetImporterFilterString返回系统支持的输出文件格式类型及其描述GetHeight返回当前图像的像素高度GetMaxColorTableEntries返回颜色表条目中的最大值GetPit
18、ch返回当前图片的间距(单位为字节),用来决定像素格式的GetTransparentColor返回颜色表中透明色的位置GetWidth返回当前图片的宽度(单位为像素)功能为图形绘制与位图块传输相关的函数AlphaBlend显示一个半透明或者透明像素的位图BitBlt从源设备描述表复制一个位图文件到当前设备描述表Draw从源矩形复制一个位图到目的矩形,该函数伸缩或者拉伸位图来适应目标矩 形的尺寸,如果有必要,会处理Alpha值和透明颜色。MaskBlt用指定的掩码和光栅操作来结合颜色数据和目的位图PlgBlt执行一个从源设备描述表的矩形到目标设备描述表的平行 四边形的块状位图转换SetColor
19、Tabel在DIB的颜色表中设定一系列条目的RGB颜色的值SetPixelIndexed设置在指定坐标处的像素(使用索调色板的索引值)。SetPixelRGB设置在指定坐标处的像素(使用RGB值)SetPixel在指定坐标处设置像素的颜色SetTransparentColor设置将被视为透明色的颜色的索引值(只能选取调色板中的 一种颜色)StretchBlt从源矩形复制一个位图到目的矩形,如果有必要,该函数会 伸缩或者拉伸位图来适应目标矩形的尺寸,TransparentBlt从源设备描述表中复制一个带有透明色的位图到当前设备 描述表二,实例运用部分运用CImage完成透明贴图的一个完整实例介绍
20、了这么多了,下面我们依然用一个实例来巩固本节笔记的知识。我们知道,CImage支持透明PNG的贴图,下面我们就运用透明PNG的贴图,来代替之前的掩码操作贴图。准备两张素材图,一张背景图,一张需要进行透明操作的人物图。这次的选材就很广了,没有之前透明操作需要自己一定的美工功底或者美工童鞋支持的诸多限制了。我选的两张图片素材如下:背景图bg.bmp640 x444人物图onion.bmp130 x130(呵呵,可爱的洋葱头)将人物图onion.bmp用photoshop等图像处理软件进行抠图操作,除去红黄相间的背景图,并将背景图用透明图层代替,再将图片大小调节成85x113,用png格式输出,效果
21、如下:处理好的人物图onion.png85x113将bg.bmp以及onion.png放到工程目录下,并在源文件写入代码并运行。该代码和笔记六中代码的思路基本相同,只不过,将笔记六中使用掩码操作进行透明化处理的方式换成了png透明贴图的方式,更加的直观和易懂易用。详细注释的源代码如下cpp HYPERLINK /zhmxy555/article/details/7422922 o view plain view plain HYPERLINK /zhmxy555/article/details/7422922 o copy copy HYPERLINK /zhmxy555/article/de
22、tails/7422922 o print print HYPERLINK /zhmxy555/article/details/7422922 o ? ?#includestdafx.h#includeatlimage.h/全局变量声明HINSTANCEhInst;HBITMAPbg;/声明一个位图对象,用于存储背景图HDCmdc;/声明一个内存DCmdc,用来暂存位图/全局函数声明ATOMMyRegisterClass(HINSTANCEhInstance);BOOLInitInstance(HINSTANCE,int);LRESULTCALLBACKWndProc(HWND,UINT,WP
23、ARAM,LPARAM);voidMyPaint(HDChdc);/*Winmain函数,程序入口点函数*intAPIENTRYWinMain(HINSTANCEhInstance,HINSTANCEhPrevInstance,LPSTRlpCmdLine,intnCmdShow)MSGmsg;MyRegisterClass(hInstance);if(!InitInstance(hInstance,nCmdShow)returnFALSE;/消息循环while(GetMessage(&msg,NULL,0,0)TranslateMessage(&msg);DispatchMessage(&m
24、sg);returnmsg.wParam;/*设计一个窗口类,类似填空题,使用窗口结构体*ATOMMyRegisterClass(HINSTANCEhInstance)WNDCLASSEXwcex;wcex.cbSize=sizeof(WNDCLASSEX);wcex.style=CS_HREDRAW|CS_VREDRAW;wcex.lpfnWndProc=(WNDPROC)WndProc;wcex.cbClsExtra=0;wcex.cbWndExtra=0;wcex.hInstance=hInstance;wcex.hIcon=LoadIcon(NULL,IDI_APPLICATION);
25、wcex.hCursor=NULL;wcex.hCursor=LoadCursor(NULL,IDC_ARROW);wcex.hbrBackground=(HBRUSH)(COLOR_WINDOW+1);wcex.lpszMenuName=NULL;wcex.lpszClassName=canvas;wcex.hIconSm=NULL;returnRegisterClassEx(&wcex);/*初始化函数*/1.建立与窗口DC兼容的内存DC/2.从文件加载背景图及透明的洋葱头BOOLInitInstance(HINSTANCEhInstance,intnCmdShow)HWNDhWnd;HD
26、Chdc;hInst=hInstance;hWnd=CreateWindow(canvas,浅墨的绘图窗口,WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,0,CW_USEDEFAULT,0,NULL,NULL,hInstance,NULL);if(!hWnd)returnFALSE;MoveWindow(hWnd,10,10,600,444,true);ShowWindow(hWnd,nCmdShow);UpdateWindow(hWnd);hdc=GetDC(hWnd);/获得窗口DCmdc=CreateCompatibleDC(hdc);/创建与窗口兼容的内存DC(m
27、dc)bg=(HBITMAP)LoadImage(NULL,bg.bmp,IMAGE_BITMAP,600,444,LR_LOADFROMFILE);MyPaint(hdc);ReleaseDC(hWnd,hdc);returnTRUE;/*自定义绘图函数*/透明贴图voidMyPaint(HDChdc)SelectObject(mdc,bg);BitBlt(hdc,0,0,600,450,mdc,0,0,SRCCOPY);/先将背景图贴到显示窗口中CImageimage;/定义一个CImage对象,用于透明贴图CStringstr;/定义一个CString对象,用于存放文件名字符串str=onion.png;/将字符串赋值为文件名image.Load(str);/在image中载入图像文件image.Draw(hdc,120,180,85,113,0,0,85,113);/调用D
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 四川省主要粮油作物重大病虫害防治常用药剂、施药情况记录表
- 高效备考:CPSM2024试题及答案
- 提升CPMM应试能力的试题及答案
- 供应链管理师应对竞争策略试题及答案
- 供应链管理师人际沟通能力试题及答案
- 2024年SCMP考试预测及试题答案
- 采购管理师市场分析试题及答案
- 保健急救知识培训课件
- 2024年注册安全工程师笔试实战试题及答案
- SCMP考试变化与试题答案应对
- 静脉输液治疗护理质量管理查检表
- 员工聘用合同聘用合同
- 八年级上册语文全品作业本电子版
- CATIA-零件实体设计模块Part-Desi课件
- 中考地理易错题
- 职称专家推荐意见表
- 文学作品与名著勾连阅读专题复习-中考语文二轮专题
- 认证咨询机构设立审批须知
- 部编版道德与法治六年级下册第三单元《多样文明 多彩生活》大单元作业设计
- 设备安装施工方案与调试方案
- GB/T 34938-2017平面型电磁屏蔽材料通用技术要求
评论
0/150
提交评论