版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领
文档简介
1、 计算机科学系实验报告(首页) 课程名称计算机图形学班级12网络2实验名称VC存取BMP图像及其几何变换教导教师吴志攀姓名李文森学号1214080613213日期2014 .11.21一、实验目的1. 掌握VC中BMP图像的存取方法;2. 掌握BMP图像平移、旋转、变比等几何变换。二、实验设备与环境TC2.0,Windows XP三、实验内容、程序清单及运行结果1.打开VC+ 6.0,选择File|New进入界面。在Projects中选择MFC AppWinzard(exe),在Project name中输入项目名称,本例为ReadBMP,在Location中输入项目要保存的文件夹。点击“OK
2、”进入下一步。如下图21所示。图212.选择文档类型。在本例中使用的是单文档视图结构,所以这里选择Single document。其余部分设置使用VC+ 6.0的默认设置,点击“Finish”完成项目创建。如下图22所示:图223.为了将BMP中的数据读入到内存中,在项目中导入专门处理BMP文件头和数据的文件:DIBAPI.H和DIBAPI.CPP,在其中实现对BMP文件的大部分处理。在工作区“FileView”选项卡的“Header Files”中点右键,在“添加文件到目录”添加“DIBAPI.H”文件。如下图23所示:图23在工作区“FileView”选项卡的“Source Files”中
3、点右键,在“添加文件到目录”添加“DIBAPI.CPP”文件。并在“ReadBMPDoc.h”添加头文件"dibapi.h",如下所示:#include "dibapi.h"4在CReadBMPDoc类中添加保护成员变量CPalette* m_palDIB,HDIB m_hDIB和CSize m_sizeDoc。m_hDIB用于保存当前BMP图像句柄,m_palDIB用于指向BMP图像对应的调色板。protected:HDIB m_hDIB;CPalette* m_palDIB;CSize m_sizeDoc;5.为了取得保存在当前文档中的HDIB和Pa
4、lette数据,在“ReadBMPDoc.h”的CReadBMPDoc类中添加方法:GetHDIB,GetDocPalette和GDocSize。如下所示:/ Attributespublic:HDIB GetHDIB() const return m_hDIB; CPalette* GetDocPalette() const return m_palDIB; CSize GetDocSize() const return m_sizeDoc; 在CReadBMPDoc.cpp的构造函数中初始化:/ 初始化变量m_hDIB = NULL;m_palDIB = NULL;m_sizeDoc =
5、CSize(1,1);6.响应类CReadBMPDoc OnOpenDocument事件,以实现打开文件的操作。 从View|ClassWizard进入MFC ClassWizard界面,在Message Maps选项中完成消息映射。下图24所示:图24在BOOL CReadBMPDoc:OnOpenDocument(LPCTSTR lpszPathName)函数中添加如下代码:/if (!CDocument:OnOpenDocument(lpszPathName)/return FALSE;/ TODO: Add your specialized creation code here/ret
6、urn TRUE;CFile file;CFileException fe;/ 打开文件if (!file.Open(lpszPathName, CFile:modeRead | CFile:shareDenyWrite, &fe)/ 失败ReportSaveLoadException(lpszPathName, &fe,FALSE, AFX_IDP_FAILED_TO_OPEN_DOC);/ 返回FALSEreturn FALSE;DeleteContents();/ 更改光标形状BeginWaitCursor();/ 尝试调用ReadDIBFile()读取图像TRYm_hD
7、IB = :ReadDIBFile(file);CATCH (CFileException, eLoad)/ 读取失败file.Abort();/ 恢复光标形状EndWaitCursor();/ 报告失败ReportSaveLoadException(lpszPathName, eLoad,FALSE, AFX_IDP_FAILED_TO_OPEN_DOC);/ 设置DIB为空m_hDIB = NULL;/ 返回FALSEreturn FALSE;END_CATCH/ 初始化DIBInitDIBData();/ 恢复光标形状EndWaitCursor();/ 判断读取文件是否成功if (m_h
8、DIB = NULL)/ 失败,可能非BMP格式CString strMsg;strMsg = "读取图像时出错!可能是不支持该类型的图像文件!"/ 提示出错MessageBox(NULL, strMsg, "系统提示", MB_ICONINFORMATION | MB_OK);/ 返回FALSEreturn FALSE;/ 设置文件名称SetPathName(lpszPathName);/ 初始化胀标记为FALSESetModifiedFlag(FALSE);/ 返回TRUEreturn TRUE;并在ReadBMPDoc.cpp添加Public成员函
9、数InitDIBData,并添加如下程序:void CReadBMPDoc:InitDIBData()/ 初始化DIB对象/ 判断调色板是否为空if (m_palDIB != NULL)/ 删除调色板对象delete m_palDIB;/ 重置调色板为空m_palDIB = NULL;/ 如果DIB对象为空,直接返回if (m_hDIB = NULL)/ 返回return;LPSTR lpDIB = (LPSTR) :GlobalLock(HGLOBAL) m_hDIB);/ 判断图像是否过大if (:DIBWidth(lpDIB) > INT_MAX |:DIBHeight(lpDIB
10、) > INT_MAX):GlobalUnlock(HGLOBAL) m_hDIB);/ 释放DIB对象:GlobalFree(HGLOBAL) m_hDIB);/ 设置DIB为空m_hDIB = NULL;CString strMsg;strMsg = "BMP图像太大!"/ 提示用户MessageBox(NULL, strMsg, "系统提示", MB_ICONINFORMATION | MB_OK);/ 返回return;/ 设置文档大小m_sizeDoc = CSize(int) :DIBWidth(lpDIB), (int) :DIBHe
11、ight(lpDIB);:GlobalUnlock(HGLOBAL) m_hDIB);/ 创建新调色板m_palDIB = new CPalette;/ 判断是否创建成功if (m_palDIB = NULL)/ 失败,可能是内存不足:GlobalFree(HGLOBAL) m_hDIB);/ 设置DIB对象为空m_hDIB = NULL;/ 返回return;/ 调用CreateDIBPalette来创建调色板if (:CreateDIBPalette(m_hDIB, m_palDIB) = NULL)/ 返回空,可能该DIB对象没有调色板/ 删除delete m_palDIB;/ 设置为空
12、m_palDIB = NULL;/ 返回return;/ 调用CreateDIBPalette来创建调色板if (:CreateDIBPalette(m_hDIB, m_palDIB) = NULL)/ 返回空,可能该DIB对象没有调色板/ 删除delete m_palDIB;/ 设置为空m_palDIB = NULL;/ 返回return;7.完成图片的打开操作之后,图片的数据就已经被保存在程序中,为了将图片显示出来还需要响应类CReadBMPView的OnDraw事件,在其中完成图像显示。void CReadBMPView:OnDraw(CDC* pDC)/CReadBMPDoc* pDo
13、c = GetDocument();/ASSERT_VALID(pDoc);/ TODO: add draw code for native data here/ 显示等待光标BeginWaitCursor();/ 获取文档CReadBMPDoc* pDoc = GetDocument();ASSERT_VALID(pDoc);/ 获取DIBHDIB hDIB = pDoc->GetHDIB();/ 判断DIB是否为空if (hDIB != NULL)LPSTR lpDIB = (LPSTR) :GlobalLock(HGLOBAL) hDIB);/ 获取DIB宽度int cxDIB =
14、 (int) :DIBWidth(lpDIB);/ 获取DIB高度int cyDIB = (int) :DIBHeight(lpDIB);:GlobalUnlock(HGLOBAL) hDIB);CRect rcDIB;rcDIB.top = rcDIB.left = 0;rcDIB.right = cxDIB;rcDIB.bottom = cyDIB;CRect rcDest;/ 判断是否是打印if (pDC->IsPrinting()/ 是打印,计算输出图像的位置和大小,以便符合页面/ 获取打印页面的水平宽度(象素)int cxPage = pDC->GetDeviceCaps
15、(HORZRES);/ 获取打印页面的垂直高度(象素)int cyPage = pDC->GetDeviceCaps(VERTRES);/ 获取打印机每英寸象素数int cxInch = pDC->GetDeviceCaps(LOGPIXELSX);int cyInch = pDC->GetDeviceCaps(LOGPIXELSY);/ 计算打印图像大小(缩放,根据页面宽度调整图像大小)rcDest.top = rcDest.left = 0;rcDest.bottom = (int)(double)cyDIB * cxPage * cyInch)/ (double)cxD
16、IB * cxInch);rcDest.right = cxPage;/ 计算打印图像位置(垂直居中)int temp = cyPage - (rcDest.bottom - rcDest.top);rcDest.bottom += temp/2;rcDest.top += temp/2;else / 非打印/ 不必缩放图像rcDest = rcDIB;/ 输出DIB:PaintDIB(pDC->m_hDC, &rcDest, pDoc->GetHDIB(),&rcDIB, pDoc->GetDocPalette();/ 恢复正常光标EndWaitCursor
17、();8.编译、调试并运行程序,自此一个用于打开BMP图像的单文档视图结构的程序就完成了。通过修改当前位图句柄m_hDIB中存放像素的数据就可以对图像进行改变了。9. 在项目中导入专门处理BMP几何变换的文件:GeoTrans.H和GeoTrans.CPP。并在ReadBMPView.cpp文件中添加:#include "GeoTrans.h"打开“Resource View”对菜单进行修改,添加“几何变换”菜单项。添加“图像平移”子菜单,ID为“ID_Geo_Trans”。在“CReadBMPView”中建立名为“OnGeoTrans”的“OnCommand”函数。voi
18、d CReadBMPView:OnGeoTrans() / TODO: Add your command handler code here/ 平移位图/ 获取文档CReadBMPDoc* pDoc = GetDocument();/ 平移位图/ 获取文档/CCh1_1Doc* pDoc = GetDocument();/ 指向DIB的指针LPSTRlpDIB;/ 指向DIB象素指针LPSTR lpDIBBits;/ 锁定DIBlpDIB = (LPSTR) :GlobalLock(HGLOBAL) pDoc->GetHDIB();/ 判断是否是8-bpp位图(这里为了方便,只处理8-b
19、pp位图的平移,其它的可以类推)if (:DIBNumColors(lpDIB) != 256)/ 提示用户MessageBox("目前只支持256色位图的平移!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 返回return;LONG lXOffset;LONG lYOffset;/ 创建对话框/CDlgGeoTran dlgPara;/ 初始化变量值/dlgPara.m_XOffset = 100;/dlgPara.m_
20、YOffset = 100;/ 显示对话框,提示用户设定平移量/if (dlgPara.DoModal() != IDOK)/ 返回/return;/ 获取用户设定的平移量lXOffset = 100;lYOffset = 100;/ 删除对话框/delete dlgPara;/ 更改光标形状BeginWaitCursor();/ 找到DIB图像象素起始位置lpDIBBits = :FindDIBBits(lpDIB);/ 调用TranslationDIB()函数平移DIBif (TranslationDIB1(lpDIBBits, :DIBWidth(lpDIB), :DIBHeight(l
21、pDIB), lXOffset, lYOffset)/ 设置脏标记pDoc->SetModifiedFlag(TRUE);/ 更新视图pDoc->UpdateAllViews(NULL);else/ 提示用户MessageBox("分配内存失败!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 恢复光标EndWaitCursor();10. 在“几何变换”菜单项中添加“垂直镜像”子菜单,ID为“ID_Geo_Mir
22、V”。在“CReadBMPView”中建立名为“OnGeoMirV”的“OnCommand”函数。void CReadBMPView:OnGeoMirV() / TODO: Add your command handler code here/ 垂直镜像/ 获取文档CReadBMPDoc* pDoc = GetDocument();/ 指向DIB的指针LPSTR lpDIB;/ 指向DIB象素指针LPSTR lpDIBBits;/ 锁定DIBlpDIB = (LPSTR) :GlobalLock(HGLOBAL) pDoc->GetHDIB();/ 判断是否是8-bpp位图(这里为了方便
23、,只处理8-bpp位图的垂直镜像,其它的可以类推)if (:DIBNumColors(lpDIB) != 256)/ 提示用户MessageBox("目前只支持256色位图的垂直镜像!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 返回return;/ 更改光标形状BeginWaitCursor();/ 找到DIB图像象素起始位置lpDIBBits = :FindDIBBits(lpDIB);/ 调用MirrorDIB()函
24、数垂直镜像DIBif (MirrorDIB(lpDIBBits, :DIBWidth(lpDIB), :DIBHeight(lpDIB), FALSE)/ 设置脏标记pDoc->SetModifiedFlag(TRUE);/ 更新视图pDoc->UpdateAllViews(NULL);else/ 提示用户MessageBox("分配内存失败!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 恢复光标EndWait
25、Cursor();11. 在“几何变换”菜单项中添加“水平镜像”子菜单,ID为“ID_Geo_MirH”。在“CReadBMPView”中建立名为“OnGeoMirH”的“OnCommand”函数。void CReadBMPView:OnGeoMirH() / 水平镜像/ 获取文档CReadBMPDoc* pDoc = GetDocument();/ 指向DIB的指针LPSTR lpDIB;/ 指向DIB象素指针LPSTR lpDIBBits;/ 锁定DIBlpDIB = (LPSTR) :GlobalLock(HGLOBAL) pDoc->GetHDIB();/ 判断是否是8-bpp位
26、图(这里为了方便,只处理8-bpp位图的水平镜像,其它的可以类推)if (:DIBNumColors(lpDIB) != 256)/ 提示用户MessageBox("目前只支持256色位图的水平镜像!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 返回return;/ 更改光标形状BeginWaitCursor();/ 找到DIB图像象素起始位置lpDIBBits = :FindDIBBits(lpDIB);/ 调用Mirr
27、orDIB()函数水平镜像DIBif (MirrorDIB(lpDIBBits, :DIBWidth(lpDIB), :DIBHeight(lpDIB), TRUE)/ 设置脏标记pDoc->SetModifiedFlag(TRUE);/ 更新视图pDoc->UpdateAllViews(NULL);else/ 提示用户MessageBox("分配内存失败!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 恢复光标
28、EndWaitCursor();12. 在“几何变换”菜单项中添加“图像转置”子菜单,ID为“ID_Geo_Transpose”。在“CReadBMPView”中建立名为“OnGeoTranspose”的“OnCommand”函数。void CReadBMPView:OnGeoTranspose() / TODO: Add your command handler code here/ 图像转置/ 获取文档CReadBMPDoc* pDoc = GetDocument();/ 指向DIB的指针LPSTR lpDIB;/ 锁定DIBlpDIB = (LPSTR) :GlobalLock(HGLO
29、BAL) pDoc->GetHDIB();/ 判断是否是8-bpp位图(这里为了方便,只处理8-bpp位图的转置,其它的可以类推)if (:DIBNumColors(lpDIB) != 256)/ 提示用户MessageBox("目前只支持256色位图的转置!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 返回return;/ 更改光标形状BeginWaitCursor();/ 调用TransposeDIB()函数转置
30、DIBif (TransposeDIB(lpDIB)/ 设置脏标记pDoc->SetModifiedFlag(TRUE);/ 更新DIB大小和调色板pDoc->InitDIBData();/ 重新设置滚动视图大小SetScrollSizes(MM_TEXT, pDoc->GetDocSize();/ 更新视图pDoc->UpdateAllViews(NULL);else/ 提示用户MessageBox("分配内存失败!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlo
31、ck(HGLOBAL) pDoc->GetHDIB();/ 恢复光标EndWaitCursor();13. 在“几何变换”菜单项中添加“图像缩放”子菜单,ID为“ID_Geo_Zoom”。在“CReadBMPView”中建立名为“OnGeoZoom”的“OnCommand”响应函数。void CReadBMPView:OnGeoZoom() / TODO: Add your command handler code here/ 图像缩放/ 获取文档CReadBMPDoc* pDoc = GetDocument();/ 指向DIB的指针LPSTR lpDIB;/ 锁定DIBlpDIB =
32、(LPSTR) :GlobalLock(HGLOBAL) pDoc->GetHDIB();/ 判断是否是8-bpp位图(这里为了方便,只处理8-bpp位图的缩放,其它的可以类推)if (:DIBNumColors(lpDIB) != 256)/ 提示用户MessageBox("目前只支持256色位图的缩放!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 返回return;/ 缩放比率float fXZoomRatio;
33、float fYZoomRatio;/ 创建对话框/CDlgGeoZoom dlgPara;/ 初始化变量值/dlgPara.m_XZoom = 0.5;/dlgPara.m_YZoom = 0.5;fXZoomRatio=0.5;fYZoomRatio=0.5;/ 显示对话框,提示用户设定平移量/if (dlgPara.DoModal() != IDOK)/ 返回/return;/ 获取用户设定的平移量/fXZoomRatio = dlgPara.m_XZoom;/fYZoomRatio = dlgPara.m_YZoom;/ 删除对话框/delete dlgPara;/ 创建新DIBHDI
34、B hNewDIB = NULL;/ 更改光标形状BeginWaitCursor();/ 调用ZoomDIB()函数转置DIBhNewDIB = (HDIB) ZoomDIB(lpDIB, fXZoomRatio, fYZoomRatio);/ 判断缩放是否成功if (hNewDIB != NULL)/ 替换DIB,同时释放旧DIB对象pDoc->ReplaceHDIB(hNewDIB);/ 更新DIB大小和调色板pDoc->InitDIBData();/ 设置脏标记pDoc->SetModifiedFlag(TRUE);/ 重新设置滚动视图大小SetScrollSizes(
35、MM_TEXT, pDoc->GetDocSize();/ 更新视图pDoc->UpdateAllViews(NULL);else/ 提示用户MessageBox("分配内存失败!", "系统提示" , MB_ICONINFORMATION | MB_OK);/ 解除锁定:GlobalUnlock(HGLOBAL) pDoc->GetHDIB();/ 恢复光标EndWaitCursor();14.在CReadBMPDoc类中添加一个成员函数,函数类型:void;函数描述:ReplaceHDIB(HDIB hDIB)。void CRead
36、BMPDoc:ReplaceHDIB(HDIB hDIB)/ 替换DIB,在功能粘贴中用到该函数/ 判断DIB是否为空if (m_hDIB != NULL)/ 非空,则清除:GlobalFree(HGLOBAL) m_hDIB);/ 替换成新的DIB对象m_hDIB = hDIB;15.在“几何变换”菜单项中添加“图像缩放”子菜单,ID为“ID_Geo_Rotate”。在“CReadBMPView”中建立名为“OnGeoRotate”的“OnCommand”响应函数。void CReadBMPView:OnGeoRotate() / TODO: Add your command handler code here/ 图像旋转/ 获取文档CReadBMPDoc* pDoc = GetDocument();/ 指向DIB的指针LPSTR lpDIB;/ 锁定DIBlpDIB = (LPSTR) :GlobalLock(HGLOBAL) pDoc->GetHDIB();/ 判断是否是8-bpp位图(这里为了方便,只
温馨提示
- 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
- 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
- 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
- 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
- 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
- 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
- 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。
最新文档
- 2025年度智慧农业管理系统软件产品采购合同范本3篇
- 二零二五年度夫妻离婚房产分割及抚养协议3篇
- 2024年航空货运合同:国际快件运输3篇
- 2024年环境监测行业市场调查与分析合同
- 2024热处理能源管理优化服务合同3篇
- 2024年针对外籍员工专属劳动协议条款版
- 2024年餐饮业合伙人经营权益合同模板一
- 2024版机械产品试用期间买卖协议要点版B版
- 2024版装修维修承包的简单合同范本
- 二零二五年度医疗设备维修保养服务协议
- 过程审核表(产品组评分矩阵评审提问表(评分))-2024年百度过
- 操作手册模板【范本模板】
- 油气管道泄漏事故应急处理方案
- 2025年湖北省武汉市高考数学模拟试卷附答案解析
- DB11∕T 353-2021 城市道路清扫保洁质量与作业要求
- 三方代收款委托协议书范文
- 2023-2024学年全国小学二年级上英语人教版期末考试试卷(含答案解析)
- 2024-2030年中国有机蔬菜市场营销模式建议及供需渠道分析报告
- 江苏省2022年普通高中学业水平合格性考试数学试题(考试版)
- 2023年二轮复习解答题专题三:一次函数的应用方案选取型(原卷版+解析)
- 2024小学语文教学及说课课件:二年级下册《传统节日》
评论
0/150
提交评论