VC6.0下bmp位图的读取与显示
VC环境下读取显示.bmp图像方法
VC环境下读取显示.bmp图像方法总结显示bmp图像的方法,列出四种显示方法。
1 通过SetPixel()函数画出每个像素点来显示图像。
2 通过读取位图资源中bmp资源显示图像。
3 通过读取本地文件,利用位图结构信息,定义HGLOBAL,再采用固定的显示方式显示位图。
4 通过读取本地文件,利用位图结构信息,定义buffer,再采用SetDIBitsT oDevice()函数。
下面分别对这四种方法进行详细描述:首先新建VC工程ShowBmpImage->MFC->单文档模式。
将显示的操作都是放在CShowBmpImageView下进行的,并且没有定义成员变量。
1 第一种方法通过SetPixelShow()函数循环画出每个像素点,从而显示图像。
操作如下:增加成员函数SetPixelShow(),编辑代码如下:int x,y; //定义像素位置CClientDC dc(this); //获取dc,也可以用CDC *pDCfor(x=0;x<200;x++)for(y=0;y<200;y++)dc.SetPixel(x,y,RGB(x,y,255)); //画一个像素点,RGB是颜色调用函数后,显示的是一幅彩色图像,可以根据需要改变RGB的值来显示一幅完整的图像。
2 第二种方法通过读取位图资源中的位图显示图像,选择菜单栏->插入->资源,弹出对话框,选择导入按钮,将文件类型改成所有文件,选择想要显示bmp位图,导入。
这样工程的资源位图中,导入的位图默认的ID 是IDB_BITMAP1。
而显示这种位图有一个固定的显示模式,非常方便。
方法如下:a 定义一个CBitmap对象,使其加载位图资源。
b 定义一个CDC对象,用于装载位图;使其创建兼容DC,相当于初始化;与CBitmap对象关联起来,相当于获取位图。
c 定义BITMAP对象,使其与CBitmap对象绑定,可以获取宽度和高度。
C语言实现BMP图像的读写功能
C语⾔实现BMP图像的读写功能C语⾔实现BMP图像的读写对于刚接触数字图像的同学,应该都有⼀个疑问,如何把⼀个BMP格式的图像⽤纯C语⾔读⼊呢,我相信这也是数字图像处理的第⼀步,如果有幸看到这篇⽂档,我就有幸的成为你数字图像处理路上的第⼀盏明灯!了解BMP的构成这就是BMP图像的理论知识,有个⼤概的了解就⾏,最主要的是从理论到实践废话不多说,直接上⼲货。
代码定义头⽂件为“bmp.h”,定义read_bmp函数为读函数,write_bmp函数为写函数读bmp图#include <stdlib.h>#include <math.h>#include <Windows.h>#include "bmp.h"/*存储原图的像素宽度⾼度和位图深度*/FILE* fpbmp;FILE* fpout;unsigned char* fpBmpHeader; //位图头unsigned char* fpFileHeader; //位图信息RGBQUAD* pColorTable; //BMP 调⾊板int read_bmp(const char* path, unsigned char *pBmpBuf,int *Width,int *Height,int * bitCount){fpbmp = fopen(path, "rb");//path为图像路径unsigned short s;fread(&s, 1, 2, fpbmp);//判断读⼊的图像是否为BMP图字符串"BM"=19778if (s == 19778){printf("Open bmp success\n");}else{printf("Open bmp fail\n");return -1;}fseek(fpbmp, 0, SEEK_SET);BITMAPFILEHEADER fileHead;fread(&fileHead, sizeof(BITMAPFILEHEADER), 1, fpbmp);BITMAPINFOHEADER infoHead;fread(&infoHead, sizeof(BITMAPINFOHEADER), 1, fpbmp);*Width = infoHead.biWidth;//图像的宽*Height = infoHead.biHeight;//图像的⾼*bitCount = infoHead.biBitCount;int lineByte = (*Width * *bitCount / 8 + 3) / 4 * 4;fseek(fpbmp, sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) ,SEEK_SET);fread(pBmpBuf, lineByte * *Height, 1, fpbmp);//pBmpBuf为图像的RGB数据,也是我们将要处理的数据return 0;}写BMP图int write_bmp(unsigned char* img, int* Width, int* Height, int* bitCount){fpout = fopen("out.bmp", "wb+");if (fpbmp == NULL){printf("read bmp failed\n");return -1;}int lineByte = (*Width * *bitCount / 8 + 3) / 4 * 4;if (lineByte == 0){printf("err");return -1;}fpFileHeader = new unsigned char[(sizeof(BITMAPFILEHEADER))];fseek(fpbmp, 0, SEEK_SET); //定位原图偏移位置fseek(fpout, 0, SEEK_SET); //定位新图偏移位置fread(fpFileHeader, 1, sizeof(BITMAPFILEHEADER), fpbmp);fwrite(fpFileHeader, 1, sizeof(BITMAPFILEHEADER), fpout);/*复制原图中位图信息到新图像*/fpBmpHeader = new unsigned char[(sizeof(BITMAPINFOHEADER))];fseek(fpbmp, sizeof(BITMAPFILEHEADER), SEEK_SET);fseek(fpout, sizeof(BITMAPFILEHEADER), SEEK_SET);fread(fpBmpHeader, 1, sizeof(BITMAPINFOHEADER), fpbmp);fwrite(fpBmpHeader, 1, sizeof(BITMAPINFOHEADER), fpout);fseek(fpout, sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER) , SEEK_SET);fwrite(img, lineByte * *Height, sizeof(char), fpout);fclose(fpout);fclose(fpbmp);return 0;}main函数调⽤#include <stdio.h>#include <stdlib.h>#include <math.h>#include <Windows.h>#include "bmp.h"int main(){int width, height, bitCount = 0;unsigned char* pBmpBuf = (unsigned char*)malloc(1000 * 1000 * 3);//申请空间const char* path = "D:\\test\\read_bmp_image\\1-B.bmp";//图的路径read_bmp(path, pBmpBuf, &width, &height, &bitCount);write_bmp(pBmpBuf, &width, &height, &bitCount);}总结,将read_bmp函数返回的pBmpBuf参数,赋值给write_bmp函数的img参数,就实现了BMP图从读到写的全部过程,有兴趣的同学动⼿实践下,会有意向不到的收获。
1 怎样读取BMP文件中的像素数据与显示位图
怎样读取BMP位图的数据与显示位图计算机与信息工程系管庶安一 BMP位图文件的结构以24位BMP位图文件为例说明。
BMP位图文件结构如下表所示:位图数据◇逐行逐列记录各像素点的三基色分量。
◇每一像素点占用三个字节,分别表示蓝色分量B、绿色分量G、红色分量R的值。
◇ 设图像有n行、m列像素,行顺序为从下向上分别为第1行、第2行……;列顺序为从左向右分别为第1列、第2列……。
按此顺序将各像素的三基色值记录于BYTE型的一维数组中,如下图所示:注意:当一行占用的字节数不是4的整数倍时,应补充1~3个无效字节,使一行占用的字节数能被4整除。
无效字节可为任意值,不会影响图像内容。
二读取BMP位图数据(1)在MFC工程中的 .H文件中定义如下全局成员变量:BITMAPFILEHEADER FileHead; // 定义存放 .BMP 文件头的结构BITMAPINFOHEADER BmpInfo; // 定义存放 .BMP 信息头的结构LPBYTE lpImage; // 定义存放 .BMP文件中的位图数据的BYTE型指针typedef struct CCC{ // 定义能存放一个像素的3个基色值的结构类型BYTE B;BYTE G;BYTE R;};CCC C3 [480] [640];// 定义能存放一幅480行、640列像素的二维数组,以便图像处理与识别时运算(2)在.CPP文件中的类构造函数中,为lpImage指针申请内存:lpImage=(LPBYTE)new BYTE[640*480*3];在.CPP文件中的类析构函数中,为lpImage指针释放内存:delete[ ] lpImage;(3)在.CPP文件中的适当函数中打开.BMP文件,读取信息头和位图数据。
CFile f;BOOL OK;OK=f.Open( Bmp.PathName,CFile::modeRead|CFile::typeBinary|CFile::shareExcl usive,NULL);if(!OK) return(-1); //不能打开文件,返回失败标志-1f.Read(&FileHead,sizeof(FileHead)); //读文件头if(FileHead.bfType!=0x4d42) {f.Close();return -2; //不是BMP文件,返回失败标志-2 }short x,y,z;z=(BmpInfo.biWidth*3/4)*4+(BmpInfo.biWidth*3%4==0 ? 0 : 4);f.Read(&BmpInfo,sizeof(BmpInfo)); //读信息头f.Seek(FileHead.bfOffBits,0);f.Read(lpImage,BmpInfo.biHeight*z); //读全部位图数据f.Close();for(y=BmpInfo.biHeight-1;y>=0;y--){memcpy(C3[y],lpImage+(BmpInfo.biHeight-1-y)*z,z); //逐行将位图数据填写到C3数组中}return 1; //最后,返回成功标志1三显示位图1 先按上述方法读取位图数据,再将读取数据予以显示。
在vc下用c语言读bmp文件信息并且改写bmp颜色
读者需要的基础: 1.c 语言基础 。 2.会用 vc++ 。 3.了解改 jpg 图像的后缀名来得到 bmp 图像,并不是真正意义的 bmp 图像,这样的图像是不能被 本程序读写的。 5.本程序用的是 24 位的 bmp 图像。
uchar rgbblue; //该颜色的蓝色分量 uchar rgbgreen; //该颜色的绿色分量 uchar rgbred; ////该颜色的红色分量 //uchar rgbReversed; //保留值,这里好像没有。 };
int main() {
struct bmp_header fileheader;//定义一个文件头信息块对象存放读取数据。 struct bmp_information fileinformation;//定义一个图像描述信息块对象存放读取数据。 struct bmp_rgb filergb; //定义一个颜色表(调色板)对象存放读取数据 uchar blue=0;//自定义蓝色分量,用于写进蓝色分量的值,在这里你可以修改三个颜色的分量,改变 bmp 图像的颜色。 uchar green=0;//自定义绿分量,用于写进蓝绿色分量的值 uchar red=255;//自定义红色分量,用于写进红色分量的值 FILE *fp; if((fp=fopen("1.bmp","rb+"))==NULL)//,一定要 rb+,读取并且可写二进制文件。在这里我把我的“1.bmp” 图像放在当前程序下,大家可以自行改变图片的名称和位置,然后在这里自行配置即可。 {
printf("bmp 格式标志:0x%x\n",fileheader.btyde); printf("文件大小: %u\n",fileheader.bsize); printf("保留字 1:%d\n",fileheader.breserved1); printf("保留字 2:%d\n",fileheader.breserved2); printf("位图数据偏移字节数:%u\n",fileheader.bfoffbits); printf("结构体长度: %u\n",fileinformation.bisize); printf("位图宽度: %d\n",fileinformation.bwidth); printf("位图高度: %d\n",fileinformation.bheight); printf("位图平面数: %u\n",fileinformation.bplanes); printf("颜色位数: %u\n",fileinformation.bbitcount); printf("压缩方式:%u\n",fileinformation.bcompression); printf("实际位图数据占用的字节数: %u\n",fileinformation.bmpimagesize); printf("X 方向分辨率:%d\n",fileinformation.bx); printf("Y 方向分辨率: %d\n",fileinformation.by); printf("使用的颜色数:%u\n",fileinformation.bcirused); printf("重要颜色数:%u\n",fileinformation.bcirimportant); printf("红色分量:%u\n",filergb.rgbred); printf("绿色分量:%u\n",filergb.rgbgreen); printf("蓝色分量:%u\n",filergb.rgbblue); fseek(fp,54L,0);//将文件类型指针定位在颜色表(调色板)的开头,便于下面开始写 i=ftell(fp); printf("%d\n",i); for(int j=0;j<fileinformation.bheight;j++)//这里两个循环的意思是保证整个图像的所有像素都被重写 rgb for(int k=0;k<fileinformation.bwidth;k++)
BMP文件的读取与显示
辽宁科技大学新技术专题报告设计题目:BMP文件的读取与显示学院、系:专业班级:学生姓名:指导教师:成绩:2011年7月8 日摘要图像技术在计算机中得到了广泛应用,进而产生了各种各样的图像格式,例如最常用的是Windows下的位图文件(BMP)格式。
BMP(全称Bitmap)是Window操作系统中的标准图像文件格式,可以分成两类:设备相关位图(DDB)和设备无关位图(DIB),使用非常广。
它采用位映射存储格式,除了图像深度可选以外,不采用其他任何压缩,因此,BMP文件所占用的空间很大。
BMP文件的图像深度可选lbit、4bit、8bit及24bit。
BMP文件存储数据时,图像的扫描方式是按从左到右、从下到上的顺序。
由于BMP 文件格式是Windows环境中交换与图有关的数据的一种标准,因此在Windows环境中运行的图形图像软件都支持BMP图像格式。
关键词:BMP;位图;读写;显示;图像媒体目录1绪论................................................................................................................................. - 1 -1.1设计背景. (1)1.2设计目的 (1)1.3设计意义 (1)1.4开发工具简介 (2)2 需求分析........................................................................................................................... - 3 -2.1系统处理信息分析 (3)2.2处理功能分析 (5)3 总体设计........................................................................................................................... - 6 -3.1系统功能模块层次图.. (6)3.2功能简介 (6)3.3主要功能的流程图 (6)4 详细设计与实现............................................................................................................... - 7 -4.1建立单文档工程. (7)4.2添加成员函数和成员变量 (8)4.3重新定义O N F ILE O PEN函数 (13)4.4修改O N D RAW函数 (14)5 测试................................................................................................................................. - 15 -结论..................................................................................................................................... - 16 -致谢..................................................................................................................................... - 17 -参考文献............................................................................................................................. - 18 -1绪论1.1 设计背景随着计算机技术的不断发展,计算机软、硬件都发生了质的飞跃,计算机操作系统从最初支持单一的DOS模式,发展到今天支持多媒体的图形视窗模式。
VC界面显示图片(BMP)
VC界面显示图片(BMP)1、通过点击浏览按钮选择BMP图像文件点击浏览按钮打开文件对话框选择BMP图像文件,得到文件所在的路径目录。
关键代码如下:char szFilter[] = "BMP Files (*.bmp)|*.bmp|All Files (*.*)|*.*||"; CFileDialog dlg( TRUE,"BMP",NULL,OFN_HIDEREADONLY |OFN_OVERWRITEPROMPT,szFilter );if(dlg.DoModal() == IDOK){CString strPathName = dlg.GetPathName();}2、加载BMP文件到内存通过得到的BMP图像文件路径目录,加载BMP图像文件到内存中。
关键代码如下:BOOL CShowBMPDlg::LoadShowBMPFile(const char *pPathname){CFile file;if( !file.Open( pPathname, CFile::modeRead) )return FALSE;DWORD m_nFileLen;m_nFileLen = file.GetLength();m_pBMPBuffer = new char[m_nFileLen + 1];if(!m_pBMPBuffer)return FALSE;if(file.ReadHuge(m_pBMPBuffer,m_nFileLen) != m_nFileLen)return FALSE;return TRUE;}3、将内存中的BMP文件内容转换到HBITMAP将内存中的BMP文件内容转换成位图句柄。
关键代码如下:HBITMAP CShowBMPDlg::BufferToHBITMAP(){HBITMAP hShowBMP;LPSTR hDIB,lpBuffer = m_pBMPBuffer;LPVOID lpDIBBits;BITMAPFILEHEADER bmfHeader;DWORD bmfHeaderLen;bmfHeaderLen = sizeof(bmfHeader);strncpy((LPSTR)&bmfHeader,(LPSTR)lpBuffer,bmfHeaderLen);if (bmfHeader.bfType != (*(WORD*)"BM")) return NULL;hDIB = lpBuffer + bmfHeaderLen;BITMAPINFOHEADER &bmiHeader = *(LPBITMAPINFOHEADER)hDIB ;BITMAPINFO &bmInfo = *(LPBITMAPINFO)hDIB ;lpDIBBits=(lpBuffer)+((BITMAPFILEHEADER *)lpBuffer)->bfOffBits; CClientDC dc(this);hShowBMP =CreateDIBitmap(dc.m_hDC,&bmiHeader,CBM_INIT,lpDIBBits,&bmInfo,DIB_RGB _COLORS);return hShowBMP;}4、在屏幕上显示BMP图像双缓冲实现BMP位图显示在屏幕上。
Vc++打开bmp格式的图像(step by step)
2.在菜单栏上的“查看”上点“建立类向 导”,用类向导ClassWizard在Pp.cpp中 添加消息响应事件OpenDocumentFile
用类向导ClassWizard在PpDoc.cpp中添 加消息响应事件OnOpenDocument,并添 加图像处理函数ReadImage
在// TODO: Add your specialized creation code here后加上
LongToString和 SetInfo需在 BMPDLG.h中进行定义
public: CBMPDLG(CWnd* pParent = NULL); // standard constructor CString LongToString(long data); void SetInfo(CPpDoc * pDoc);
在BMPDLG.h中加PpDoc的头 文件#include “PpDoc.h” 因为有 这个申明void SetInfo(CPpDoc * pDoc);
在PpView.cpp中进行对BMPDLG头文件的定义,添加 #include "BMPDLG.h"
在PpView.cpp中的
void CPpView::OnBaseinfoInfo() {
在ChildFrm.cpp的PreCreateWindow 函数中可初始化子窗口大小
BOOL CChildFrame::PreCreateWindow(CREATESTRUCT& cs) { // TODO: Modify the Window class or styles here by modifying // the CREATESTRUCT cs
ReadImage(lpszPathName); 再在后面加上:
VC++6.0位图的打开显示保存
VC++ 6.0 位图打开、显示和保存操作用到的数据:char *m_pDibData;int m_nBitCount;int m_nHeight;int m_nWidth;CString m_fileName;HGLOBAL m_hDIB;void CBitView::OnFileOpen(){// TODO: Add your command handler code here//打开对话框,并获得要打开的位图的路径,保存在m_fileName中static char szFilter[] = "位图文件(*.bmp;*.dib) | *.bmp;*.dib | All Files(*.*) | *.* ||";CFileDialog dlg(true,"*.bmp",NULL, OFN_HIDEREADONL Y | OFN_OVERWRITEPROMPT,szFilter);if (dlg.DoModal()==IDOK){UpdateData(true);m_fileName = dlg.GetPathName();}//新建CFile类对象dibFile,并用只读的模式打开CFile dibFile;if(!dibFile.Open(m_fileName,CFile::modeRead)){AfxMessageBox("Can not open DIB file...");return;}//接下来读取位图文件的文件头//新建一个位图文件头变量BITMAPFILEHEADER bitmapFileHeader;//从位图文件中读取与位图文件头大小的字节到文件头变量中UINT bitmapFileHeaderSize = dibFile.Read((void*)&bitmapFileHeader,sizeof(BITMAPFILEHEADER));if (bitmapFileHeaderSize != sizeof(BITMAPFILEHEADER)){AfxMessageBox("Failed in reading file");return;}//判断读取的文件是否为位图文件if (bitmapFileHeader.bfType == 0x4d42){//读取整个位图文件长度DWORD dwFileLength = dibFile.GetLength();/***************************************BMP文件的组成结构1 位图文件头(14字节)(BITMAPFILEHEADER)2 位图信息(包含位图信息头和调色板数据)真彩色的位图是没有调色板数据的,而位图信息头为14字节其结构体为BITMAPINFOHEADER,位图信息的结构体为BITMAPINFO3 像素数据*****************************************///获取位图信息头和像素数据的大小(文件总长度- 位图文件头的长度)DWORD dwSize = dwFileLength - sizeof(BITMAPFILEHEADER);//为位图信息头和像素数据分配大小m_hDIB = (HGLOBAL)::GlobalAlloc(GMEM_MOVEABLE,dwSize);//锁定分配的内存,将返回指向此内存的指针BYTE * m_pdib = (BYTE *)::GlobalLock((HGLOBAL)m_hDIB);//将位图信息头和像素数据一起读入到已分配的内存当中DWORD dwReadSize = dibFile.Read((void*)m_pdib,dwSize);//获取位图信息头和位图信息的指针//位图信息头指针用来获取位图的宽度、高度和每个像素所占字节数//位图信息指针用来在StretchDIBits中显示位图时的参数BITMAPINFO *m_pBitmapInfo = (BITMAPINFO *)m_pdib;BITMAPINFOHEADER *m_pBitmapInfoHeader = (BITMAPINFOHEADER *)m_pdib;m_nWidth = m_pBitmapInfoHeader->biWidth;m_nHeight = m_pBitmapInfoHeader->biHeight;m_nBitCount = m_pBitmapInfoHeader->biBitCount;if (m_nBitCount < 24){AfxMessageBox("打开的不是大于24位的真彩色图片,不能处理,只能显示和保存位图!");}//计算像素数据所在的位置(起始位置+位图信息头的大小)m_pDibData = (char *)m_pdib+m_pBitmapInfoHeader->biSize;//显示像素数据的内容CDC *pDC = GetDC(); //得到当前设备的句柄指针::StretchDIBits(pDC->m_hDC,0,0,m_nWidth,m_nHeight,0,0,m_nWidth,m_nHeight,m_pDib Data,m_pBitmapInfo,DIB_RGB_COLORS,SRCCOPY);::GlobalUnlock((HGLOBAL)m_hDIB);}else{AfxMessageBox("非位图文件");return;}}void CBitView::OnSaveBmp(){// TODO: Add your command handler code here//生成图像的信息头(包括位图文件头和位图信息)//位图文件头占14字节,位图信息头占40字节BITMAPFILEHEADER bf;bf.bfOffBits = 54;bf.bfReserved1 = 0;bf.bfReserved2 = 0;//说明文件大小(位图文件头+ 位图信息头+图片像素所占字节数)bf.bfSize = sizeof(BITMAPFILEHEADER) + sizeof(BITMAPINFOHEADER)+m_nHeight*m_nWidth*4;//说明文件类型为BMbf.bfType =((WORD)'M'<<8 | 'B');BITMAPINFOHEADER bi;//说明每个像素所占字节数,其值为1、4、8、16、24、32bi.biBitCount = m_nBitCount;//说明图像显示有重要影响的颜色索引的数目,如果是0,表示都重要bi.biClrImportant = 0;//说明图像数据压缩的类型bi.biCompression = 0L;//说明图像的宽度,以像素为单位bi.biWidth = m_nWidth;//说明图像的高度,以像素为单位bi.biHeight = m_nHeight;//目标设备说明位面数,其值总是被设为1bi.biPlanes = 1;//说明BITMAPINFOHEADER结构所需要的字节数bi.biSize = sizeof(BITMAPINFOHEADER);//说明图像的大小,以字节为单位,当用BI_RGB格式时,可设置为0bi.biSizeImage = 0;//说明图像的水平分辨率,用像素/米来表示bi.biXPelsPerMeter = 0;//说明图像的垂直分辨率,用像素/米来表示bi.biYPelsPerMeter = 0;//打开保存对话框,获取保存路径及文件名static char szFilter[] = "位图文件(*.bmp;*.dib) | *.bmp;*.dib | All Files(*.*) | *.* ||";CFileDialog dlg(false,"*.bmp",NULL,OFN_HIDEREADONL Y | OFN_OVERWRITEPROMPT,szFilter);if (dlg.DoModal() == IDOK){UpdateData(TRUE);m_fileName = dlg.GetPathName();}else{return;}//建立CFile对像准备保存图片CFile file;if(!file.Open(m_fileName,CFile::modeCreate | CFile::modeWrite | CFile::typeBinary)){AfxMessageBox("cant write BMP file");return;}//写入位图文件头file.Write(&bf,14);//写入位图信息头file.Write(&bi,sizeof(BITMAPINFOHEADER));//获得图像每一行所占的字节数long lWidthBytes = (m_nWidth*m_nBitCount +31)/32*4;//写入整个的像素矩阵中的数据file.Write(m_pDibData,m_nHeight*lWidthBytes);//写入完毕file.Close();}void CBitView::OnShowBMP(){// TODO: Add your command handler code hereCDC *pDC = GetDC();BYTE *lpdib = (BYTE *)::GlobalLock((HGLOBAL)m_hDIB);BITMAPINFO *m_pBitmapInfo = (BITMAPINFO *)lpdib;::StretchDIBits(pDC->m_hDC,0,0,m_nWidth,m_nHeight,0,0,m_nWidth,m_nHeight,m_pDib Data,m_pBitmapInfo,DIB_RGB_COLORS,SRCCOPY);::GlobalUnlock((HGLOBAL)m_hDIB);}。
VC++6.0绘制位图
1.1.1.1.绘制位图绘制位图之前需要加载位图。
加载位图有两种方式,从资源中加载位图,以及从外部图片文件中加载位图。
1.1.1.1.1.从资源中加载位图1.1.1.1.1.1.定义位图资源位图资源可以直接使用VC6.0在资源视图中创建或编辑位图资源,也可以在导入外部位图图片作为位图资源。
资源视图中定义位图资源界面如下所示。
定义位图资源1.1.1.1.1.2.加载位图使用MFC提供的CBitmap类可以方便的加载位图资源。
//从资源中加载位图CBitmap bmp;bmp.LoadBitmap(IDB_BITMAP1);//获取位图信息BITMAP bitmap;memset(&bitmap,0,sizeof(bitmap));bmp.GetBitmap(&bitmap);使用CBitmap类的GetBitmap方法获取位图信息,包括宽度和高度以及颜色深度等。
使用BITMAP结构体来描述位图信息。
typedef struct tagBITMAP{LONG bmType;//类型LONG bmWidth;//宽度,像素LONG bmHeight;//高度,像素LONG bmWidthBytes;//位图的每行占用多少字节。
位图是一行行存储的。
WORD bmPlanes;//位面数WORD bmBitsPixel;//颜色深度,每像素使用多少二进制位表示LPVOID bmBits;//指向像素颜色数据存储区域的指针。
}BITMAP1.1.1.1.2.从外部图片文件加载位图此方式比使用位图资源灵活,程序编译之后还可以随时替换成不同的位图文件。
使用全局函数LoadImage可以完成此功能。
//从图片文件加载位图。
HBITMAP hbmp;Hbmp=(HBITMAP)LoadImage(NULL,"bitmap.bmp",IMAGE_BITMAP,0,0,LR_LOADTRANSPARENT|LR_LOADFROMFILE);//将位图句柄转化为CBitmap指针。
实验一bmp位图的读取、显示、放大缩小、二值化和反色
(数字图像处理)实验报告实验名称实验一bmp位图的读取、显示、放大缩小、二值化和反色实验时间专业班级学号姓名成绩教师评语:一、实验目的1、掌握windows BMP格式位图文件的基本格式。
会使用VC++读取图像数据并显示。
2、在读取BMP格式位图的的基础上增加对图像的放大、缩小、二值化和反色的功能。
二、实验内容1、在VC6.0环境下,生成MFC应用程序框架。
2、在已生成的应用程序中,加BMP位图读取与显示的代码,从已有文件中读取bmp格式文件并在视图中显示。
3、在生成的MFC应用程序框架下建立对应的消息响应函数,实现对已在视图中显示的图像的放大、缩小、二值化和反色的具体操作。
三、实验原理具体操作步骤及结果截图基本原理:BMP位图文件格式BMP位图文件中主要由4部分内容组成:1、文件头BITMAPFILEHEADER为一STRUCTURE:typedef struct tagBITMAPFILEHEADER {WORD bfType;//文件类型,必须为“BM”或0x424dDWORD bfSize;//文件大小WORD bfReserved1;//保留WORD bfReserved2;//保留DWORD bfOffBits;//从文件头到实际位图数据的偏移字节数} BITMAPFILEHEADER, FAR *LPBITMAPFILEHEADER, *PBITMAPFILEHEADER;2、位图信息头BITMAPINFOHEADER,定义如下:typedef struct tagBITMAPINFOHEADER{DWORD biSize;//structure sizeLONG biWidth;//image widthLONG biHeight;//image heightWORD biPlanes;//value is 1WORD biBitCount;//color bitsDWORD biCompression;//compression or notDWORD biSizeImage;//Imagesize=width*height( 其中width必须为4的倍数。
用VC实现bmp位图打开和显示
用VC++实现bmp位图打开和显示课程名称:数字图象处理实验名称:用C++实现bimp图片的打开与显示班级:姓名:一试验目地:(1)、学会了解C++是使用;(2)、学会用C++解决图像处理问题二、实验内容:用C++语言编写bimp图像显示;三、实验步骤:1、首先建立一个工程。
打开VC++6.0,单击文件【files】→新建【new】→工程【projects】在打开的projects 下选择MFC App Wizard [exe]→在project name 下输入自己的工程名例如(Showpicture)→单击【ok】→在打开的对话框中选择基于单文档【single document】→在第四步“MFC App Wizard step 4 of 6”面板中删掉【隐藏工具栏】和【打印和打印预览】两个选项,之后的全部选择默认,单击finish,出现一个“New Project Information”窗口,单击【ok】。
一个简单的工程框架就建好了。
这是基于MFC App Wizard 自动生成的应用程序,如果我们自己还没有编译任何代码,现在就按下F7键编译程序,接着按Ctr+F5键运行程序,可以看到出现一个完整的带有标题栏、菜单栏的可调边框的应用程序。
2、现在我们正式开始在新建工程Showpicture中进行编程实现bmp位图的打开和显示。
点击左边框中的【ResourceView】框找到【Menu】点开,双击Menu下的图标,在右面的显示框中创建两个菜单:打开,显示原图。
分别双击这两个菜单修改属性:打开ID: ID_FILE_OPEN显示原图ID: IDM_YUANTU3、给这两个菜单建立类向导。
在右边的窗口中右击“打开”,选择“建立类向导”,然后在打开的对话框中按下图1操作,“Class name”选择“CShowpictureDoc” →”Object IDs”中选择“ID_FILE_OPEN” →“Message”中选择“COMMAND”,点击“Add Function”键就会在“Member functions”中如下显示:然后点击“Edit Code”,在自动生成的OnFileOpen函数中编写代码:void CShowpictureDoc::OnFileOpen(){// TODO: Add your command handler code hereCFileDialog fileDlg(TRUE);fileDlg.m_ofn.lpstrTitle="图片打开对话框";fileDlg.m_ofn.lpstrFilter="BMP Files(*.bmp)\0*.bmp\0\0";if(IDOK==fileDlg.DoModal ())filename.Format ("%s",fileDlg.GetPathName());CDib.LoadFile(filename);}同理,操作“显示原图”,如下图2显示:注意这次的“Class name”选择“CShowpictureView”。
bmp图片加载显示的两种方法
一、图片添加、加载、显示和释放在软件开发过程中,我们经常需要使用到图片,下面我们就来说说图片的加载和使用方法。
我们的SDK平台目前只支持bmp格式的图片,其他格式如jpg、png等压缩格式的图片暂时不支持。
下面我将详细讲解如何添加、加载、显示和释放一个24bit格式的文件名为plane.bmp的图片。
1添加图片资源方法由于我们的程序最终会生成mrp格式文件,因此我们需要把要显示的图片先打包到mrp文件里面。
添加文件的方法,是需要修改mpr格式的工程文件,该工程文件类似我们在Linux开发环境里的 makefile。
例如我们当前的工程文件为demo.mpr,那么我们在files组里面加入名字为plane.bmp的图片,如下图所示:当我们编译mpr工程文件的时候,如果图片被成功打包到mrp文件中,那么在编译完成的时候,会有提示信息,如下图所示:当要添加的图片不存在的时候,编译器报编译错误,如下图所示:当编译通过,并且编译输出有看到图片被成功打包进mrp包里面,说明我们完成了在mpr工程文件里面增加图片的功能。
2从mrp包里面加载图片方法我们这里说的图片加载是指在程序运行过程要显示mrp包里面的bmp图片时候,需要先将bmp加载到内存中的方法。
将bmp图片加载到内存中通常有两种方法,一种是通过调用mrc_readFileFromMrpEx函数;另一种是通过调用mrc_bitmapLoad 函数。
第一种加载图片的具体方法如下面代码所示:T_ICON_MAP* LoadBmp(void){int32 ret;T_ICON_MAP* bmp = NULL;char* bmp_name = "plane.bmp";bmp = (T_ICON_MAP*)malloc(sizeof(T_ICON_MAP));if( NULL == bmp ){return NULL;}memset(bmp,0,sizeof(T_ICON_MAP));bmp->width = 41;bmp->height = 26;ret = mrc_readFileFromMrpEx(NULL,bmp_name,(uint8**)&(bmp->pdata),(int32 *)&(bmp->len),0);if( ret == MR_FAILED){mrc_printf("LoadBmp,load bmp[%s] failed",bmp_name);free(bmp);return NULL;}else{mrc_printf("LoadBmp,load bmp[%s] suc",bmp_name);return bmp;}}在第一种图片加载方法里面,我使用了mrc_readFileFromMrpEx来从mrp中读取先前打包进去的图片。
VC数字图像处理编程之一----BMP图像的基本操作
上一讲我们主要介绍了图像的格式,其中重点说明了BMP文件的存储格式,同时对JEPG和GIF等常用格式作了简单的介绍。
本节主要讲述如何操作BMP文件,如对其读、写和显示等。
在实现数字图象处理的过程中,主要是通过对图像中的每一个像素点运用各种图像处理算法来达到预期的效果,所以进行图像处理的第一步,也是我们最关心的问题,是如何得到图像中每一个像素点的亮度值;为了观察和验证处理的图像效果,另一个需要解决的问题是如何将处理前后的图像正确的显示出来。
我们这章内容就是解决这些问题。
随着科技的发展,图像处理技术已经渗透到人类生活的各个领域并得到越来越多的应用,但是突出的一个矛盾是图像的格式也是越来越多,目前图像处理所涉及的主要的图像格式就有很多种,如TIF、JEMP、BMP等等,一般情况下,为了处理简单方便,进行数字图像处理所采用的都是BMP格式的图像文件(有时也称为DIB格式的图像文件),并且这种格式的文件是没有压缩的。
我们通过操作这种格式的文件,可以获取正确显示图像所需的调色板信息,图像的尺寸信息,图像中各个像素点的亮度信息等等,有了这些数据,开发人员就可以对图像施加各种处理算法,进行相应的处理。
如果特殊情况下需要处理其它某种格式的图像,如GIF、JEMP等格式的图象文件,可以首先将该格式转换为BMP格式,然后再进行相应的处理。
这一点需要读者清楚。
BMP格式的图像文件又可以分为许多种类,如真彩色位图、256色位图,采用RLE(游程编码)压缩格式的BMP位图等等。
由于在实际的工程应用和图像算法效果验证中经常要处理的是256级并且是没有压缩的BMP灰度图像,例如通过黑白采集卡采集得到的图像就是这种格式,所以我们在整个讲座中范例所处理的文件格式都是BMP灰度图像。
如果读者对这种格式的位图能够作到熟练的操作,那么对于其余形式的BMP位图的操作也不会很困难。
BMP灰度图像作为Windows环境下主要的图像格式之一,以其格式简单,适应性强而倍受欢迎。
在VC中加载bmp图片的问题
在VC中加载bmp图片的问题问题:当我 insert-->resource-->选中 -->Bitmap-->import加载图片时出现下面的错误:The bitmap has been imported correctly,howerver beacuse it containsmorethan 256 colors it cannot be loaded in the bitmap editor这是什么错误啊、要怎么改正呢?答:没有错误,你加载的图片高于256色,VC没有提供对高于256色图片的编辑器,所以在VC中不能编辑,只能使用。
而编辑就是对它的修改了,在VC中不能对高于256色的图片进行修改。
但是可以随便用一个图片编辑软件就可以得到低于256色图,比如WINDOWS画图,photoshop等。
打开一个图片,然后另存为,其中有一项选择,256色。
保存就OK了此外对于jpg图片,都可以用windows画图、photoshop来保存成256色的bmp图片,然后在VC中使用。
相关函数为LoadBitmap,具体使用可参见MSDN。
下文可做一定参考。
数字图像处理- MFC教程第一课建立MFC和打开bmp图片第一步:建立MFC工程文件--新建--MFC AppWizardd(exe)工程--单文档—确定。
第二步:设置打开函数查看--建立类导向(Ctrl+W)--CpictureXSView(类名)--ID_FILE_OPEN(IDs列表)--COMMAND(Messages列表)--默认成员函数名为OnFileOpen--Member Functions(成员函数)中双击该函数进入函数编辑。
建立如下函数:打开图片、保存图片为重点。
对象标识符消息函数名所属类ID_FILE_OPENCOMMANDOnFileOpenCpainterViewID_FILE_SAVECOMMANDOnFileSaveCpainterViewID_FILE_NEWUPDATE_COMMAND_UIOnUpdateFileNewCpainterViewID_FILE_MRU_FILE1UPDATE_COMMAND_UIOnUpdateFileMruFile1CpainterView注意:在添加Messages列表中:ON_COMMAND是点了按钮或菜单项后的响应消息;ON_UPDATE_COMMAND_UI是用来表示对应的按钮和菜单项的状态的响应消息,比如你打开这个菜单时,处理这个菜单的状态,比如选中、变灰等。
VC6.0下bmp位图的读取与显示
实验名称实验一、VC6.0下bmp位图的读取与显示一、实验目的掌握windows BMP格式位图文件的基本格式。
会使用VC++读取图像数据并显示。
二、实验原理及内容在VC6.0环境下,生成MFC应用程序框架。
在已生成的应用程序中,加BMP位图读取与显示的代码,从已有文件中读取bmp 格式文件并在视图中显示。
(一)基本知识:BMP位图文件格式BMP位图文件中主要由4部分内容组成:1、文件头BITMAPFILEHEADER为一STRUCTURE:typedef struct tagBITMAPFILEHEADER {WORD bfType;//文件类型,必须为“BM”或0x424dDWORD bfSize;//文件大小WORD bfReserved1;//保留WORD bfReserved2;//保留DWORD bfOffBits;//从文件头到实际位图数据的偏移字节数} BITMAPFILEHEADER, FAR *LPBITMAPFILEHEADER, *PBITMAPFILEHEADER;2、位图信息头BITMAPINFOHEADER,定义如下:typedef struct tagBITMAPINFOHEADER{DWORD biSize;//structure sizeLONG biWidth;//image widthLONG biHeight;//image heightWORD biPlanes;//value is 1WORD biBitCount;//color bitsDWORD biCompression;//compression or notDWORD biSizeImage;//Image size=width*height( 其中width必须为4的倍数。
LONG biXPelsPerMeter;//LONG biYPelsPerMeter;DWORD biClrUsed;//DWORD biClrImportant;} BITMAPINFOHEADER, FAR *LPBITMAPINFOHEADER, *PBITMAPINFOHEADER;3、调色板typedef struct tagRGBQUAD {BYTE rgbBlue;BYTE rgbGreen;BYTE rgbRed;BYTE rgbReserved;} RGBQUAD;用于存放图像的颜色。
VC6绘画BMP位图常用解决方案
CTLCOLOR_STA
到这里其实就可以了,BMP的图片背景实现了,文本框的透明也实现了。 3、补充说明:如果程序运行过程中,需要设置文本框的字体的话,会出现显示"字体重叠不刷新"的 问题 4、这就要对该控件或者对话框处理了,要刷出新字体来。 CWnd* pWnd = GetDlgItem(IDC_STATIC1); pWnd->SetWindowText("");//需要修改的控件标题 //这里可以刷整个对话框,但如果较频繁的话,很明显能看出来,就选择刷显示字体的那块区域就 可以了 pWnd ->GetParent()->InvalidateRect(CRect(0,0,100,50),TRUE); 好了,没有问题了,剩下随便你玩吧,这个解决方法不像网上说的,非要借用人家的自己写的函数 ,现在完全用VC提供的就可以了,免得加这个那个的头文件 4
w组件的绘图都是放在这两个memb是用来画主要对象的举例说明一个按钮是灰色的上面还有文字所做的事就是画上文字既然这两个memb都是用来画出组件的那为何还要分on的要求是快速在里面的绘图程序最好是不要太耗时间因为每当wiw组件有任何小变动都会马上呼叫oner之前呼叫的所以被呼叫一次之前可能会呼叫oner好几次如果我们是一个在做图形化使用者接口的人常会需要把一张美美的图片设为我们d的底图把绘图的程序代码放在on之中可能会常碰到一些问题比方说拖曳一个窗口在我们做的d会变成灰色直到动作停止才恢复这是因为每次需要重绘的时候程序都会马上呼叫oner画成灰色而只有动作停止之后程序才会呼叫on这个问题的解法比较差点的方法是把oner如下所示boolcmydl但是如果我们不呼叫的话程序便不会画上灰色的底色了比较好的做法是直接将绘图的程序从on移到onermpbkgnd为一cbi对象且事先早已加载我们的底图大小一致boolcmydldccrcompmpbkgnd特别要注意的是取得重画大小是使用gevc背景填充位图的几种方法dbbg是位图资源的i设置画刷为希望的背景cdccompdbbg创建位图画刷cbrmemdcbrmemdcbrdbbgbitmapbitmapcompdbbg加载位图cbr创建位图画刷cre使用oner函数实现对话框位图背景boolcxxxdltodo
基于VC6.0的24位真彩色图像读取与显示
基于VC6.0的24位真彩色图像读取与显示
摘要:在图像处理软件的设计中正确认识图像文件的结构至关重要。
对BMP图像的文件结构进行了系统介绍。
通过一个24位真彩色图像的实例,分析了真彩色图像的基本结构,给出了一种在VC6.0环境下读取与显示24位真彩色图像的方法。
关键词:BMP文件;24位真彩色图像;VC6.0
0 引言
随着输入输出设备的发展进步,以及人们对图像清晰度、图像色彩真实感的要求不断提高,针对真彩色图像处理的各类技术也在不断发展,而目前大多数文献以及参考资料都是对256色图像的处理,关于真彩色图像分析和处理的内容较少。
理解24位真彩色图像的结构,正确获得图像的数据信息,对于图像处理来说十分关键。
本文对24位真彩色图像的结构进行了系统的分析,并介绍在Visual C6.0下读取与显示真彩色图像的方法。
1 BMP图像文件结构
BMP格式的图像在Windows系统中比较常见,几乎所有的Windows应用程序都支持这种图像文件。
通常使用的BMP格式文件是一种与设备无关的位图DIB(Device Independnt Bitmap),它使用标准的Windows位图格式,包含颜色信息,并且可以在不同的机器或者系统中显示图像。
BMP图像一般包含文件头(BITMAPFILEHEADER)、信息头(BITMAPINFOHEADER)、调色
板(Palette)、位图数据(Data)四个部分。
BMP图像的文件格式如图1所示。
值得注意的是,24位真彩色图像不需要调色板,图像的信息头之后紧跟着的就是图像数据。
(1)位图文件头。
在wingdi.h中对位图的文件头结构有如下定义:。
对话框MFC中点击按钮打开并显示bmp位图
MFC中对话框的应用以前写的图像处理软件不是从头写的,这次从头写个图像处理软件,遇到的第一个难题竟然是无法在对话框工程中打开一幅新的图片,以前短短的几行代码现在被无限扩展,琢磨N久,终于成功.拿出来和大家分享菜鸟的成果...回去好好补补对话框指针的知识注意:这个程序不是文档视类中实现的,也不是.net实现的中只要用CImage类的方法就可以了,而这是VC6如何在对话框MFC中点击按钮打开并显示bmp位图,关键代码及流程如下:1 在CHuffmanBmpDlg::OnOpenImage() 中打开文件,获取文件路径CFileDialog file_open_dlg(TRUE,NULL,NULL,OFN_HIDEREADONLY,"BMPFiles(*.bmp)|*.bmp|All Files(*.*)|*.*||");file_open_dlg.m_ofn.lpstrTitle = "Open Image File";if(file_open_dlg.DoModal() != IDOK)return;CString file_name = file_open_dlg.GetPathName();2 创建CDialog类的子类CBitmapDialog,注意工程的文件头要包含#include "BitmapDialog.h"3 回到CHuffmanBmpDlg::OnOpenImage()中,添加新对话框类的实例CBitmapDialog *source_dlg = new CBitmapDialog;source_dlg->Create(IDD_Source_Bitmap,NULL);其中IDD_Source_Bitmap是对话框的ID号4 在对话框BitmapDialog类中添加公有成员函数CString image_name;5 回到CHuffmanBmpDlg::OnOpenImage()中,添加如下代码source_dlg->image_name = file_name;source_dlg->ShowWindow(SW_SHOW);6 在对话框BitmapDialog中添加事件响应消息为WM_PAINT,这样MFC会自动添加成员函数void CBitmapDialog::OnPaint(){CPaintDC dc(this); // device context for painting// TODO: Add your message handler code here// Do not call CDialog::OnPaint() for painting messages}7 在OnPaint()中添加如下代码CBitmap SourceImage;HBITMAP OldBitmap;CDC mDC;// SourceImage.LoadBitmap(image_name);SourceImage.Attach((HBITMAP)LoadImage(NULL,image_name,IMAGE_BITMAP,0,0,LR _LOADFROMFILE));CDC dcCompatible;dcCompatible.CreateCompatibleDC(&dc);OldBitmap = (HBITMAP)dcCompatible.SelectObject(&SourceImage);CRect rect;GetClientRect(&rect);dc.BitBlt(0,0,rect.Width(),rect.Height(),&dcCompatible,0,0,SRCCOPY);mDC.SelectObject(&OldBitmap);8 回到CHuffmanBmpDlg::OnOpenImage()中添加Invalidate();重绘窗口(这一步也可不做) 上述过程用文字描述为:1 在父对话框中添加按钮响应函数2 打开文件,获取bmp位图的路径名3 创建子对话框类用于显示bmp位图4 在父对话框中创建子对话框实例,并将bmp位图路径名传递进去5 父对话框发送消息,子对话框接收到消息,响应OnPaint函数6 子对话框中创建CBitmap对象并用Attach和LoadImage函数装载当前位图7 创建一个CDC对象用于在内存中兼容dc8 用CDC的SelectObject方法将CBitmap对象中的位图内容拷贝到内存中9 用BitBlt方法将内存中的信息复制到当前dc中显示出来10 还原mDC对象,并重绘窗口(这一步可不做)注意点:非常重要:不能使用CBitmap::LoadBitmap方法来装载图像,因为MSDN中LoadBitmap的定义为BOOL LoadBitmap (LPCTSTR lpszResourceName );BOOL LoadBitmap (UINT nIDResource );ParameterslpszResourceNamePoints to a null-terminated string that contains the name of the bitmap resource. nIDResourceSpecifies the resource ID number of the bitmap resource.因此,LoadBitmap只能用于装载工程rc中的资源位图ID或其名称.要装载外部图像必须用LoadImage()方法现在几乎所有的书和网上的论坛都是用的LoadBitmap方法,实在是一大误导。
- 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
- 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
- 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
实验名称实验一、VC6.0下bmp位图的读取与显示一、实验目的掌握windows BMP格式位图文件的基本格式。
会使用VC++读取图像数据并显示。
二、实验原理及内容在VC6.0环境下,生成MFC应用程序框架。
在已生成的应用程序中,加BMP位图读取与显示的代码,从已有文件中读取bmp 格式文件并在视图中显示。
(一)基本知识:BMP位图文件格式BMP位图文件中主要由4部分内容组成:1、文件头BITMAPFILEHEADER为一STRUCTURE:typedef struct tagBITMAPFILEHEADER {WORD bfType;//文件类型,必须为“BM”或0x424dDWORD bfSize;//文件大小WORD bfReserved1;//保留WORD bfReserved2;//保留DWORD bfOffBits;//从文件头到实际位图数据的偏移字节数} BITMAPFILEHEADER, FAR *LPBITMAPFILEHEADER, *PBITMAPFILEHEADER;2、位图信息头BITMAPINFOHEADER,定义如下:typedef struct tagBITMAPINFOHEADER{DWORD biSize;//structure sizeLONG biWidth;//image widthLONG biHeight;//image heightWORD biPlanes;//value is 1WORD biBitCount;//color bitsDWORD biCompression;//compression or notDWORD biSizeImage;//Image size=width*height( 其中width必须为4的倍数。
LONG biXPelsPerMeter;//LONG biYPelsPerMeter;DWORD biClrUsed;//DWORD biClrImportant;} BITMAPINFOHEADER, FAR *LPBITMAPINFOHEADER, *PBITMAPINFOHEADER;3、调色板typedef struct tagRGBQUAD {BYTE rgbBlue;BYTE rgbGreen;BYTE rgbRed;BYTE rgbReserved;} RGBQUAD;用于存放图像的颜色。
4、图像的实际数据。
对于2色图,用1位表示像素的值。
对于16色图,用4位表示像素的值。
对于256色图,一个字节刚好表示1个像素。
对于用到调色板的位图,图像数据就是该像素颜色在调色板中索引值,对于真彩色,不用调色板,三个字节的数据分别代表图像的B、G、R。
(二)、基本实验步骤1、打开VC++界面,工程中选择MFC AppWizard(exe),并在project name输入zyf125 ,选择存放project的位置。
2、选择ok,进入下一步。
选择single document,并在最后CdipView类的基类中选择CscrollView,使应用程序视图具有滚动条。
3、在生成的工程中选择CLxyView,对class视图进行操作,添加成员变量跟成员函数到相应现在的zyf125view下int m_x;HBITMAP m_Bmp;LPVOID m_ColorList;LPBYTE m_Image;LPBITMAPINFOHEADER m_DibHead;enum allocate {None, crtallocate, heapallocate};allocate m_nBmpallocate;allocate m_nImageallocate;DWORD m_ImageSize;int m_nPalette;HANDLE m_hFile;HANDLE m_hMap;LPVOID m_lpvFile;HPALETTE m_hPalette;HGLOBAL m_hGlob;利用ClassWizard向ClxyView类中加入如下成员函数。
void SetPaletteSize(int nBitCount);//设置调色板大小void Clear();//清除BOOL ReadFile(CFile *pFile);//读取数据到内存BOOL SetPalette();//当前位图颜色数大于256设置调色板BOOL GetPalette();//创建颜色数不大于256的调色板BOOL DibToDC(CDC* pDC,CSize size);显示位图BOOL MemToDib(LPVOID lmem);//得到内存中位图象素位置CSize GetDibSize();//返回位图尺寸完成以上操作后,在dipView.cpp中找到所添加函数的函数体,copy到自己建立的LxyView.cpp中对应的函数名称的下面。
4、设计一个名为IDB_BITMAP1的位图在resourc下单机右键,选择插入,单击Bitmap,选择新建,然后自己新建一个位图,保存。
5、修改OnDraw和OnInitialUpdate()函数设置滚动条的初始化图形和现实图像,如果不写OnDraw函数体的话图像将被保存在缓冲区而不显示出来6、在Resource下双击Toolbar,打开工具栏编辑器,先对放大缩小工具图标进行绘制,绘制完成后在上面的工具栏中找到所设计的相应的图标,双击图标对图标进行ID的设置,之后在Menu下双击IDR_MAINFRAME进行类向导设计,类向导设计跟上学期的MFC实验中的类向导设计一样,然后添加放大缩小的函数内容到对应的函数下面7、打开Menu资源,双击主菜单,打开菜单资源编辑器喧闹中打开选项,右键单击,选择类向导Class中选择C×××view,单击commond选择AddFunction单击OK,单击Edit code,拷贝Onfileopen函数中代码。
这样就可以打开相应的BMP格式图片8、实验代码:void CZyf125View::OnDraw(CDC* pDC){CZyf125Doc* pDoc = GetDocument();ASSERT_VALID(pDoc);// TODO: add draw code for native data hereBeginWaitCursor();CSize DibSize = GetDibSize();DibSize.cx *= m_x;DibSize.cy *= -m_x;DibToDC(pDC, DibSize);EndWaitCursor();}void CZyf125View::OnInitialUpdate(){CScrollView::OnInitialUpdate();m_x=25;CSize MaxSize(24000,32000);CSize MinSize(MaxSize.cx/100,MaxSize.cy/100);SetScrollSizes(MM_HIMETRIC,MaxSize,MaxSize,MinSize);LPVOID lFirstBMP=(LPVOID)::LoadResource(NULL,::FindResource(NULL,MAKEINTRESOURCE(IDB_BITMAP1),RT_BITMAP);MemToDib(lFirstBMP);;}////////////////////////////////////////////////////////////////////////////// CZyf125View printingBOOL CZyf125View::OnPreparePrinting(CPrintInfo* pInfo){// default preparationreturn DoPreparePrinting(pInfo);}void CZyf125View::OnBeginPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/){// TODO: add extra initialization before printing}void CZyf125View::OnEndPrinting(CDC* /*pDC*/, CPrintInfo* /*pInfo*/){// TODO: add cleanup after printing}/////////////////////////////////////////////////////////////////////////////// CZyf125View diagnostics#ifdef _DEBUGvoid CZyf125View::AssertValid() const{CScrollView::AssertValid();}void CZyf125View::Dump(CDumpContext& dc) const{CScrollView::Dump(dc);}CZyf125Doc* CZyf125View::GetDocument() // non-debug version is inline{ASSERT(m_pDocument->IsKindOf(RUNTIME_CLASS(CZyf125Doc)));return (CZyf125Doc*)m_pDocument;}#endif //_DEBUG/////////////////////////////////////////////////////////////////////////////// CZyf125View message handlersvoid CZyf125View::SetPaletteSize(int nBitCount){if(m_DibHead->biSize != sizeof(BITMAPINFOHEADER)) {throw new CException;}m_ImageSize = m_DibHead->biSizeImage;if(m_ImageSize == 0) {DWORD dwBytes = ((DWORD) m_DibHead->biWidth *m_DibHead->biBitCount) / 32;if(((DWORD) m_DibHead->biWidth * m_DibHead->biBitCount) % 32){dwBytes++;}dwBytes *= 4;m_ImageSize = dwBytes * m_DibHead->biHeight;}m_ColorList = (LPBYTE) m_DibHead + sizeof(BITMAPINFOHEADER);if((m_DibHead == NULL) || (m_DibHead->biClrUsed == 0)) {switch(nBitCount) {case 1:m_nPalette = 2;break;case 4:m_nPalette = 16;break;case 8:m_nPalette = 256;break;case 16:case 24:case 32:m_nPalette = 0;break;default:ASSERT(FALSE);}}else {m_nPalette = m_DibHead->biClrUsed;}ASSERT((m_nPalette >= 0) && (m_nPalette <= 256));}void CZyf125View::Clear(){if(m_hFile == NULL) return;::UnmapViewOfFile(m_lpvFile);::CloseHandle(m_hMap);::CloseHandle(m_hFile);m_hFile = NULL;if(m_nBmpallocate == crtallocate) {delete [] m_DibHead;}else if(m_nBmpallocate == heapallocate) {::GlobalUnlock(m_hGlob);::GlobalFree(m_hGlob);}if(m_nImageallocate == crtallocate) delete [] m_Image;if(m_hPalette != NULL) ::DeleteObject(m_hPalette);if(m_Bmp != NULL) ::DeleteObject(m_Bmp);m_nBmpallocate = m_nImageallocate = None;m_hGlob = NULL;m_DibHead = NULL;m_Image = NULL;m_ColorList = NULL;m_nPalette = 0;m_ImageSize = 0;m_lpvFile = NULL;m_hMap = NULL;m_hFile = NULL;m_Bmp = NULL;m_hPalette = NULL;}BOOL CZyf125View::ReadFile(CFile *pFile){int nCount, nSize;BITMAPFILEHEADER bmfh;Clear();try {nCount = pFile->Read((LPVOID) &bmfh, sizeof(BITMAPFILEHEADER));if(nCount != sizeof(BITMAPFILEHEADER)) {throw new CException;}if(bmfh.bfType != 0x4d42) {throw new CException;}nSize = bmfh.bfOffBits - sizeof(BITMAPFILEHEADER);m_DibHead = (LPBITMAPINFOHEADER) new char[nSize];m_nBmpallocate = m_nImageallocate = crtallocate;nCount = pFile->Read(m_DibHead, nSize);SetPaletteSize(m_DibHead->biBitCount);GetPalette();m_Image = (LPBYTE) new char[m_ImageSize];nCount = pFile->Read(m_Image, m_ImageSize);}catch(CException* tmpc) {AfxMessageBox("文件读取错误");tmpc->Delete();return FALSE;}return TRUE;}BOOL CZyf125View::SetPalette(){if(m_nPalette!=0)return FALSE;CClientDC dc(this);CDC *pDC=&dc;m_hPalette=::CreateHalftonePalette(pDC->GetSafeHdc());return TRUE;}BOOL CZyf125View::GetPalette(){if(m_nPalette==0)return FALSE;if(m_hPalette!=NULL)::DeleteObject(m_hPalette);LPLOGPALETTE pTempPalette=(LPLOGPALETTE) newchar[2*sizeof(WORD)+m_nPalette*sizeof(PALETTEENTRY)];pTempPalette->palVersion=0x30;pTempPalette->palNumEntries=m_nPalette;LPRGBQUAD pRGBQuad=(LPRGBQUAD)m_ColorList;for(int i=0;i<m_nPalette;i++){pTempPalette->palPalEntry[i].peRed=pRGBQuad->rgbRed;pTempPalette->palPalEntry[i].peGreen=pRGBQuad->rgbGreen;pTempPalette->palPalEntry[i].peBlue=pRGBQuad->rgbBlue;pTempPalette->palPalEntry[i].peFlags=0;pRGBQuad++;}m_hPalette=::CreatePalette(pTempPalette);delete pTempPalette;return TRUE;}BOOL CZyf125View::DibToDC(CDC *pDC, CSize size){if(m_DibHead==NULL)return FALSE;if(m_hPalette!=NULL){HDC hdc=pDC->GetSafeHdc();::SelectPalette(hdc,m_hPalette,TRUE);}pDC->SetStretchBltMode(COLORONCOLOR);::StretchDIBits(pDC->GetSafeHdc(),0,0,size.cx,size.cy,0,0,m_DibHead->biWidth,m_DibHead->biHeight,m_Image,(LPBITMAPINFO)m_DibHead,DIB_RGB_COLORS,SRCCOPY);return TRUE;}BOOL CZyf125View::MemToDib(LPVOID lmem){Clear();m_DibHead=(LPBITMAPINFOHEADER)lmem;SetPaletteSize(m_DibHead->biBitCount);m_Image=(LPBYTE)m_ColorList+sizeof(RGBQUAD)*m_nPalette;GetPalette();return TRUE;}CSize CZyf125View::GetDibSize(){if(m_DibHead==NULL)return CSize(0,0);return CSize((int)m_DibHead->biWidth,(int)m_DibHead->biHeight); }void CZyf125View::Onmax(){// TODO: Add your command handler code hereCSize Dibsize = GetDibSize();if ((Dibsize.cx * m_x * 1.2) < 24000){if ((Dibsize.cy * m_x * 1.2) < 32000){m_x = (int)(m_x * 1.2);Invalidate();}}}void CZyf125View::Onmin(){// TODO: Add your command handler code hereif (m_x > 2){m_x = (int)(m_x / 1.2);Invalidate();}}void CZyf125View::OnFileOpen(){// TODO: Add your command handler code hereCFileDialog filedlg(TRUE,"bmp","*.bmp");if(filedlg.DoModal()!=IDOK)return;CFile myfile;myfile.Open(filedlg.GetPathName(),CFile::modeRead);if(ReadFile(&myfile)==TRUE)Invalidate();SetPalette();}9、实验截图位图显示:BMP文件读取。