⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 dibapi.cpp

📁 这个程序是用来实现关于(bmp)文件的读写功能。很简单
💻 CPP
📖 第 1 页 / 共 2 页
字号:
//************************************************************************************************************************
// 文件名:dibapi.cpp
//
//DIB(Independent Bitmap)API函数库:
//
//paintDIB()					-绘制DIB对象
//CreateDIBPAlette()			-创建DIB对象调色板
//FindDIBBits()					-返回DIB图像像素起始位置
//DIBWidth()					-返回DIB的宽度
//DIBHEIGHT()					-返回DIB的高度
//PaletteSize()					-返回DIB调色板的大小
//DIBNumColors()				-计算DIB调色板颜色数目
//CopyHandle()					-拷贝内存块
//
//SaveDIB()						将DIB保存到指定的文件中
//ReadDIBFile()					重指定文件中读取的DIB对象
//
//**************************************************************************************************************************



//#include"stdafx.h"
#include"dibapi.h"
#include"io.h"
#include"errno.h"


#include"math.h"
#include"direct.h"

/*
 *Dib 文件头标志(字符串"BM",写DIB时用到该常数)
 */
#define DIB_HEADER_MARKER     ((WORD)('M'<<8)|'B')





/****************************************************************************************************************************
 *
 *function:
 *  PaintDIB()						  -绘制DIB图像
 *
 *parameter:
 *  HDC				hDC               -输出设备DC
 *  LPRECT			lpDCRECT		  -绘制矩形区域
 *  HDIB			hDIB			  -指向DIB对象的指针
 *  LPRECT			lpDIBRect	      -要输出的DIB区域
 *  CPalette*		pPal		      -指向DIB对象调色板的指针
 *
 *return:
 *  BOLL							  -绘制成功返回TRUE,否则返回FALSE.
 *
 *comments:
 *该函数注意用来绘制DIB对象。其中调用了StretchDIBits()或者
 *SetDIBToDevice()来绘制DIB对象。输出的设备由参数hDC指定;
 *绘制的矩形区域有参数lpDCRect指定;输出DIB的区域由参数
 *lpDIBRect.
 *
 ***************************************************************************************************************************/




BOOL WINAPI PaintDIB(HDC hDC,
					 LPRECT lpDCRect,
					 HDIB   hDIB,
					 LPRECT lpDIBRect,
					 CPalette* pPal)
{
	LPSTR lpDIBHdr;              //BITMAPINFOHEADER 指针
	LPSTR lpDIBBits;			 //DIB像素指针
	BOOL  bSuccess=FALSE;		 //成功的标志
	HPALETTE hPal=NULL;			 //DIB调色板
	HPALETTE hOldPal=NULL;		 //以前的调色板

	//判断DIB对象是否为空
	if(hDIB==NULL)
	{
		//return
		return FALSE;
	}
	//Lock DIB
	lpDIBHdr=(LPSTR)::GlobalLock((HGLOBAL)hDIB);

	//find the section start of DIB image's pixel
	lpDIBBits=::FindDIBBits(lpDIBHdr);

	//Get DIB palette and chose it 
	if(pPal!=NULL)
	{
		hPal=(HPALETTE)pPal->m_hObject;

		//Chose the palette
		hOldPal=::SelectPalette(hDC,hPal,TRUE);
	}

	//Set the palette
	::SetStretchBltMode(hDC,COLORONCOLOR);

	//判断是调用StretchDIBits()还是SetDIBitsToDevice()来绘制DIB对象
	if((RECTWIDTH(lpDCRect)==RECTWIDTH(lpDIBRect))&&(RECTHEIGHT(lpDCRect)==RECTHEIGHT(lpDIBRect)))
	{
		//原始大小,不用拉伸
		bSuccess=::SetDIBitsToDevice(hDC,									//hDC
									 lpDCRect->left,						//DestX
									 lpDCRect->top,							//DestY
									 RECTWIDTH(lpDCRect),					//nDestWidth
									 RECTHEIGHT(lpDCRect),					//nDestHeight
									 lpDIBRect->left,						//SrcX
									 (int)DIBHeight(lpDIBHdr)-				
									 lpDIBRect->top-
									 RECTHEIGHT(lpDIBRect),					//SrcY
									 0,										//nStartScane
									 (WORD)DIBHeight(lpDIBHdr),				//nNumScans
									 lpDIBBits,								//lpBits
									 (LPBITMAPINFO)lpDIBHdr,				//lpBitInfo
									 DIB_RGB_COLORS);						//wUsage
	}
	else
	{
		//非原始大小,拉伸。
		bSuccess=::StretchDIBits(hDC,								//hDC
								 lpDCRect->left,					//DestX
								 lpCDRect->top,						//DestY
								 RECTWIDTH(lpDCRect),				//nDestWidth
								 RECTHEIGHT(lpDCRect),				//nDestHeight
								 lpDIBRect->left,					//SrcX
								 lfDIBRect->top,					//SrcY
								 RECTWIDTH(lpDIBRect),				//wSrcWidth
								 RECTHEIGHT(lpDIBRect),				//wSrcHeight
								 lpDIBBits,							//lpBits
								 (LPBITMAPINFO)lpDIBHdr,			//lpBitsInfo	
								 DIB_RGB_COLORS,					//wUsage
								 SRCCOPY);							//dwROP
	}
	

	//解除锁定
	::GlobalUnlock((HGLOBAL)hDIB);


	//恢复以前的调色板
	if(hOldPal!=NULL)
	{
		::SelectPalette(hDC,hOldPal,TRUE);
	}
	//return
	return bSuccess;

}


/*******************************************************************************************************************
 *
 *function:
 *   CreateDIBPalette()					-创建DIB图像的调色板
 *
 *parameter:								
 *   HDIB hDIB					        -指向DIB对象的句柄
 *   CPalette* pPal						-指向DIB对象调色板的指针
 *
 *return:
 *   BOLL								-创建成功返回TRUE,否则返回FALSE
 *
 *comments:
 *  该函数按照DIB创建一个逻辑调色板,从DIB中读取颜色表并保存在调色板中,
 *最后按照逻辑调色板创建一个新的调色板,并返回该调色板的句柄。这样可以
 *用最后的颜色来显示DIB图像。
 *
 **********************************************************************************************************************/



 BOOL WINAPI CreateDIBPalette(HDIB hDIB,CPalette* pPal)
 {
	 //指向逻辑调色板的指针
	 LPLOGPALETTE lpPal;

	 //逻辑调色板的句柄
	 HANDLE hLogPal;

	 //调色板的句柄
	 HPALETTE hPal=NULL;

	 //循环变量
	 int i;

	 //颜色表中的数目
	 WORD wNumColors;

	 //指向DIB的指针
	 LPSTR lpbi;

	 //指向BITMAPINFO结构的指针(Win3.0)
	 LPBITMAPINFO lpbmi;

	 //指向BITMAPCOREINFO结构的指针
	 LPBITMAPCOREINFO lpbmc;

	 //表明是否是Win3.0 DIB的标记
	 BOOL bWinStyleDIB;
	 
	 //创建结果
	 BOOL bResult=FALSE;

	 //判断DIB是否为空
	 if(hDIB=NULL)
	 {
		 //返回FALSE
		 return FALSE;
	 }
	 
	 //锁定DIB
	 lpbi=(LPSTR)::GlobalLock((HGLOBAL)hDIB);

	 //获取指向BITMAPINFO结构的指针(Win3.0)
	 lpbmi=(LPBITMAPINFO)lpbi;

	 //获取指向BITMAPCOREINFO结构的指针
	 lpbmc=(LPBITMAPCOREINFO)lpbi;

	 //获取DIB颜色表中的颜色数目
	 wNumColors=::DIBNumColors(lpmi);

	 if(wNumColors!=0)
	 {
		 //分配为逻辑调色板的内存
		 hLogPal=::GlobalAlloc(GHND,sizeof(LOGPATETTE)+
							        sizeof(PALETTEENTRY)
									*wNumColors);
		 //如果内存不足,退出
		 if(hLogPal==0)
		 {
			 //解除锁定
			 ::GlobalUnlock((HGLOBAL)hDIB);

			 //返回FALSE
			 return FALSE;
		 }

		 lpPal=(LPLOGPALETTE)::GlobalLock((HGLOBAL)hLogPal);//由句柄转向指针

		 // 设置版本号
		 lpPal->palVersion=PALVERSION;

		 //设置颜色的数目
		 lpPal->palNumEntries=(WORD)wNumColors;

		 //判断是否是Win3.0的DIB
		 bWinStyleDIB=IS_WIN30_DIB(lpbi);

		 //读取调色板
		 for(i=0;i<(int)wNumColors;i++)
		 {
			 if(bWinStyleDIB)
			 {
				 //读取红色的分量
				 lpPal->palPalEntry[i].peRed=lpbmi->bmiColors[i].rgbRed;

				 //读取绿色的分量
				 lpPal->palPalEntry[i].peGreen=lpbmi->bmiColors[i].rgbGreen;

				 //读取蓝色的分量
				 lpPal->palPalEntry[i].peBlue=lpbmi->bmiColors[i].grbBlue;

				 //保留位
				 lpPal->palPalEntry[i].peFlags=0;
			 }
			 else
			 {
				 //读取红色的分量
				 lpPal->palPalEntry[i].peRed=lpbmc.bmciColors[i].rgbtRed;

				 //读取绿色的分量
				 lpPal->palPalEntry[i].peGreen=lpbmc.bmciColors[i].rgbtGreen;

				 //读取蓝色的分量
				 lpPal->palPalEntry[i].peBlue=lpbmc.bmciColors[i].rgbtBlue;

				 //保留位
				 lpPal->palPalEntry[i].peFlags=0;
			 }
		 }
		 //按照逻辑调色板创建调色板,并返回指针
		 bResult=pPal->CreatePalette(lpPal);

		 //解除锁定
		 ::GlobalUnlock((HGLOBAL)hLogPal);
		 
		 //释放调色板
		 ::GlobalFree((HGLOBAL)hLogPal);

	 }
	 
	 //解除锁定
	 ::GlobalUnlock((HGLOBAL)hDIB);


	 //返回结果
	 return bResult;

 }


 /**************************************************************************************************************
  *
  *function:
  *		FindDIBBits()				-找到DIB图像像素起始地址				
  *
  *parameter:
  *		LPSTR lpbi					-指向DIB对象的指针
  *
  *return:
  *		LPSTR						-指向DIB图像像素的起始地址
  *
  *comments:
  *		该函数计算DIB中图像像素的起始位置,并返回指向他的起始地址
  *
  ************************************************************************************************************/


  LPSTR WINAPI FindDIBBits(LPSTR lpbi)
  {

	  return (lpbi+*(LPDWORD)lpbi+::PatetteSize(lpsi));

  }



  /***************************************************************************************************************
   *function:
   *	DIBWidth()
   *
   *parameter:
   *	LPSTR lpbi
   *
   *return:
   *	DWORD
   *
   *comments:
   *	该函数返回DIB中图像的宽度。对于Windows 3.0 DIB,返回BITMAPINFOHEADER中的biWidth;
   *对于其他返回BITMAPCOREHEADER中的bcWidth值。
   *
   ************************************************************************************************************/


  DWORD WINAPI DIBWidth(LPSTR lpbi)
  {

	  //指向BITMAPINFO结构的指针(Windows 3.0)
	  LPBITMAPINFOHEADER lpbmi;

	  //指向BITMAPCOREINFO结构的指针
	  LPBITMAPCOREHEADER lpbmc;

	  //获取指针
	  lpbmi=(LPBITMAPINFOHEADER)lpbi;
	  lpbmc=(LPBITMAPCOREHEADER)lpbi;

	  //返回DIB中图像的宽度
	  if(IS_WIN30_DIB(lpbi))
	  {

		  //对于Windows 3.0 DIB 返回lpbmi->biWidth
		  return lpbmi->biWidth;

	  }
	  else
	  {

		  //对于其他格式的DIB,返回lpbmc->bcWidth
		  return lpbmc->bcWidth;

	  }

  }




  /***********************************************************************************************
   *function:
   *	DIBHeight()
   *
   *parameter:
   *	LPSTR lpbi
   *
   *return:
   *	DWORD
   *
   *comments:
   *	该函数返回DIB中的高度。对于Window 3.0 DIB ,返回BITMAPINFOHEADER
   *中的biHeight值;对于其他返回BITMAPCOREHEADER中的bcHeight值。
   *
   *************************************************************************************************/



  DWORD WINAPI DIBHeight(LPSTR lpbi)
  {

	  //指向BITMAPINFO结构的指针(Windows 3.0)
	  LPBITMAPINFOHEADER lpbmi;

	  //指向BITMAPCOREINFO结构的指针
	  LPBITMAPCOREHEADER lpbmc;

	  //获取指针
	  lpbmi=(LPBITMAPINFOHEADER)lpbi;
	  lpbmc=(LPBITMAPCOREHEADER)lpbi;

	  //返回DIB中图像的宽度
	  if(IS_WIN30_DIB(lpbi))
	  {

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -