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

📄 image.cpp

📁 卡车运输拉煤中丢煤现象严重,本程序为丢煤视频自动检测系统动态链接库,输出CoalChange函数供其它系统调用。
💻 CPP
字号:
// Image.cpp: implementation of the CImage class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"

#include "Image.h"

// access()
#include "io.h"

#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

CImage::CImage()
{
	hBitmap	= NULL;
	hPal	= NULL;
	hDib	= NULL;

	nImgType = 0;
}

CImage::~CImage()
{
	// 释放资源
	if ( hBitmap ) {
		DeleteObject( hBitmap );
		hBitmap = NULL;
	}
	if ( hPal ) {
		DeleteObject( hPal );
		hPal = NULL;
	}
	if ( hDib ) {
		GlobalFree( hDib );
		hDib = NULL;
	}
}

// 从文件中读取图像
BOOL CImage::LoadFile(HWND hwnd, LPCTSTR lpfilename)
{
	CFile file;
	if ( !file.Open(lpfilename, CFile::modeRead) ) {
		MessageBox(hwnd, "打开文件错误!","警告", 0);
		return FALSE;
	}

	// 得到文件头信息
	memset( &bmfh, 0, sizeof(BITMAPFILEHEADER) );
	file.Read( &bmfh, sizeof(BITMAPFILEHEADER) );

	// 读取图像信息
	BITMAPINFOHEADER bih;
	file.Read( &bih, sizeof(BITMAPINFOHEADER) );
	nBits = bih.biBitCount;
	nWidth = bih.biWidth;
	nHeight = bih.biHeight;
	nWidthBytes = WIDTHBYTES(nBits*nWidth);
	nColors = bih.biClrUsed ? bih.biClrUsed : (1<<nBits);
	if( nBits==24 || nBits==32 )
		nColors=0;
	if( bmfh.bfOffBits != (DWORD)(sizeof(bmfh) + sizeof(bih) + nColors*sizeof(RGBQUAD)))
	{
		MessageBox(hwnd, "打开文件错误!", "警告", 0);
		goto errProc;
	}

	DWORD dwImagesize;
	dwImagesize = nWidthBytes*nHeight;
	hDib = (HDIB)::GlobalAlloc(GHND, sizeof(BITMAPINFOHEADER)
		+ nColors*sizeof(RGBQUAD) + dwImagesize);
	if ( hDib == NULL )
	{
		MessageBox(hwnd, "分配内存错误!", "警告", 0);
		goto errProc;
	}
	LPBYTE lptemp;
	lptemp = (LPBYTE)::GlobalLock((HGLOBAL)hDib);
	if ( lptemp == NULL )
	{
		MessageBox(hwnd, "分配内存错误!", "警告", 0);
		goto errProc;
	}

	file.Seek(sizeof(BITMAPFILEHEADER), CFile::begin);
	if(file.ReadHuge((LPVOID)lptemp,sizeof(bih)+nColors*sizeof(RGBQUAD)
		+dwImagesize) != (sizeof(bih)+nColors*sizeof(RGBQUAD)
		+dwImagesize))
	{
		MessageBox(hwnd,"打开文件错误!","警告",0);
		goto errProc;
	}
	// 关闭文件
	file.Close();
	
	// 读取调色板信息
	if ( nColors != 0 )
	{
		int nPalSize;
		nPalSize = sizeof(LOGPALETTE)+nColors*sizeof(PALETTEENTRY);
		LOGPALETTE *ppal;
		ppal = (LOGPALETTE *)(new BYTE[nPalSize]);
		if ( ppal == NULL )
		{
			MessageBox(hwnd,"分配内存错误!","警告",0);
			goto errProc;
		}

		RGBQUAD * lprgb;
		lprgb = (RGBQUAD *)((LPBYTE)lptemp + (DWORD)sizeof(bih));
		ppal->palVersion = 0x030;
		ppal->palNumEntries = nColors;
		for (int i=0; i<nColors; i++)
		{
			ppal->palPalEntry[i].peBlue = lprgb->rgbBlue;
			ppal->palPalEntry[i].peGreen = lprgb->rgbGreen;
			ppal->palPalEntry[i].peRed = lprgb->rgbRed;
			ppal->palPalEntry[i].peFlags = 0;
			lprgb++;
		}

		hPal = CreatePalette( ppal );
		
		delete [] ppal;
	}

	// 把调色板信息读入设备环境
	{
		HDC hdc = GetDC( hwnd );

		HPALETTE prePal = NULL;
		if ( hPal )
		{
			prePal = SelectPalette(hdc, hPal, FALSE);
			RealizePalette( hdc );
		}

		// 创建BITMAP资源
		hBitmap = CreateDIBitmap(hdc, &bih, (long)CBM_INIT, 
			(LPBYTE)lptemp+sizeof(bih)+sizeof(RGBQUAD)*nColors,
			(LPBITMAPINFO)lptemp, DIB_RGB_COLORS);
	
		// 
		if ( hPal && prePal )
		{
			hPal = SelectPalette(hdc, prePal, FALSE);
			RealizePalette(hdc);
			// ??? 这儿是否要释放资源
			//DeleteObject( prePal );
		}

		ReleaseDC(hwnd, hdc);
	}

	return TRUE;

errProc:
	if ( hBitmap ) {
		DeleteObject( hBitmap );
		hBitmap = NULL;
	}
	if ( hPal ) {
		DeleteObject( hPal );
		hPal = NULL;
	}
	if ( lptemp ) {
		GlobalUnlock( hDib );
		lptemp = NULL;
	}
	if ( hDib ) {
		GlobalFree( hDib );
		hDib = NULL;
	}
	file.Close();
	return FALSE;
}

LPBYTE CImage::FindDibBits()
{
	if ( hDib == NULL )
		return NULL;

	LPBYTE lptemp;
	lptemp = (LPBYTE)GlobalLock( (HGLOBAL)hDib );
	if ( lptemp == NULL )
		return NULL;

	LPBYTE lpret;
	lpret = lptemp + sizeof(BITMAPINFOHEADER) + sizeof(RGBQUAD)*nColors;
	GlobalUnlock( (HGLOBAL)hDib );

	return lpret;
}

BOOL CImage::DrawDIB(HDC hdc, HDIB hdib, CPalette *pPal)
{
	if( hDib == NULL )
		return FALSE;
	
	if ( pPal == NULL )
	{
		if ( hPal == NULL )
			hPal = (HPALETTE)GetStockObject(DEFAULT_PALETTE);		
		
		SelectPalette(hdc, hPal, FALSE);
		RealizePalette(hdc);
	}
	else
	{
		SelectPalette(hdc,(HPALETTE)(pPal->m_hObject),FALSE);
		RealizePalette(hdc);
	}

	LPBYTE lptemp;
	lptemp = (LPBYTE)GlobalLock( (HGLOBAL)hDib );
	if ( lptemp == NULL )
		return FALSE;
	
	SetDIBitsToDevice(hdc, 0, 0, nWidth, nHeight, 0, 0, 0, nHeight,
		(LPBYTE)lptemp+sizeof(BITMAPINFOHEADER)+sizeof(RGBQUAD)*nColors,
		(LPBITMAPINFO)lptemp, DIB_RGB_COLORS);

	GlobalUnlock( (HGLOBAL)hDib );
	return TRUE;
}

BOOL CImage::DrawDDB(HDC hdc, HBITMAP bmp, HPALETTE hpal) 
{
	if ( hBitmap == NULL )
		return FALSE;

	if ( hpal == NULL )
		hPal = (HPALETTE)GetStockObject(DEFAULT_PALETTE);

	HDC hmemdc;
	hmemdc = CreateCompatibleDC( hdc );

	SelectPalette(hdc, hpal, FALSE);
	SelectPalette(hmemdc, hpal, FALSE);
	RealizePalette(hdc);
	
	SelectObject(hmemdc, bmp);
	BitBlt(hdc, 0, 0, nWidth, nHeight, hmemdc, 0, 0, SRCCOPY);
	DeleteDC( hmemdc );
	
	return TRUE;
}

// 从文件中读取图像
BOOL CImage::Load(LPCTSTR lpszPathName)
{
	// 判断文件是否存在
	if ( access(lpszPathName,0) != 0 )
		return FALSE;

	HWND hWnd = (HWND)AfxGetMainWnd()->m_hWnd;

	// 读取文件信息及数据
	HGLOBAL hGlobal = NULL;
	nImgType = FileType( lpszPathName );
	switch ( nImgType )
	{
	case 0:		//NA
		return FALSE;
		break;

	case 1:		//BMP
		GetBMPInfo( lpszPathName, &nWidth, &nHeight, &nPlanes, &nBits, &nColors);
		nWidthBytes = WIDTHBYTES( nBits*nWidth );
		hGlobal = LoadBMP( lpszPathName );
		break;

	case 2:		//GIF
		GetGIFInfo( lpszPathName, &nWidth, &nHeight, &nPlanes, &nBits, &nColors);
		nWidthBytes = WIDTHBYTES( nBits*nWidth );
		hGlobal = LoadGIF( lpszPathName );
		break;

	case 3:		//PCX
		GetPCXInfo( lpszPathName, &nWidth, &nHeight, &nPlanes, &nBits, &nColors);
		nWidthBytes = WIDTHBYTES( nBits*nWidth );
		hGlobal = LoadPCX( lpszPathName );
		break;

	case 4:		//TGA
		GetTGAInfo( lpszPathName, &nWidth, &nHeight, &nPlanes, &nBits, &nColors);
		nWidthBytes = WIDTHBYTES( nBits*nWidth );
		hGlobal = LoadTGA( lpszPathName );
		break;

	case 5:		//JPG
		GetJPGInfo( lpszPathName, &nWidth, &nHeight, &nPlanes, &nBits, &nColors);
		nWidthBytes = WIDTHBYTES( nBits*nWidth );
		hGlobal = LoadJPG( lpszPathName );
		break;

	case 6:		//TIF
		GetTIFInfo( lpszPathName, &nWidth, &nHeight, &nPlanes, &nBits, &nColors);
		nWidthBytes = WIDTHBYTES( nBits*nWidth );
		hGlobal = LoadTIF( lpszPathName );
		break;

	default:
		return FALSE;
	}
	if( hGlobal == NULL )
	{
		MessageBox(hWnd, "读取文件错误!", "警告", 0);
		return FALSE;
	}

	// 24位、32位真彩图像不需要调色板
	if( nBits==24 || nBits==32 )
		nColors=0;

	LPBYTE lpGlobal;
	lpGlobal = (LPBYTE)::GlobalLock( (HGLOBAL)hGlobal );
	if ( lpGlobal == NULL )
	{
		MessageBox(hWnd, "分配内存错误!", "警告", 0);
		goto errProc;
	}

	// 得到文件头信息
	memset( &bmfh, 0, sizeof(BITMAPFILEHEADER) );
	memcpy( &bmfh, lpGlobal, sizeof(BITMAPFILEHEADER) );

	DWORD dwImagesize;
	dwImagesize = nWidthBytes*nHeight;
	dwImagesize += sizeof(BITMAPINFOHEADER);
	dwImagesize += nColors*sizeof(RGBQUAD);
	hDib = (HDIB)::GlobalAlloc(GHND, dwImagesize);
	if ( hDib == NULL )
	{
		MessageBox(hWnd, "分配内存错误!", "警告", 0);
		goto errProc;
	}
	LPBYTE lptemp;
	lptemp = (LPBYTE)::GlobalLock((HGLOBAL)hDib);
	if ( lptemp == NULL )
	{
		MessageBox(hWnd, "分配内存错误!", "警告", 0);
		goto errProc;
	}

	// 拷贝图像数据(不包括文件头信息)
	lpGlobal += sizeof(BITMAPFILEHEADER);
	memcpy( lptemp, lpGlobal, dwImagesize);
	
	// 释放资源
	GlobalUnlock( hGlobal );
	GlobalFree( hGlobal );
	
	BITMAPINFOHEADER bih;
	memcpy( &bih, lptemp, sizeof(BITMAPINFOHEADER) );

	// 读取调色板信息
	if ( nColors != 0 )
	{
		int nPalSize;
		nPalSize = sizeof(LOGPALETTE)+nColors*sizeof(PALETTEENTRY);
		LOGPALETTE *ppal;
		ppal = (LOGPALETTE *)(new BYTE[nPalSize]);
		if ( ppal == NULL )
		{
			MessageBox(hWnd,"分配内存错误!","警告",0);
			goto errProc;
		}
		
		RGBQUAD * lprgb;
		lprgb = (RGBQUAD *)((LPBYTE)lptemp + (DWORD)sizeof(BITMAPINFOHEADER));
		ppal->palVersion = 0x030;
		ppal->palNumEntries = nColors;
		for (int i=0; i<nColors; i++)
		{
			ppal->palPalEntry[i].peBlue = lprgb->rgbBlue;
			ppal->palPalEntry[i].peGreen = lprgb->rgbGreen;
			ppal->palPalEntry[i].peRed = lprgb->rgbRed;
			ppal->palPalEntry[i].peFlags = 0;
			lprgb++;
		}
		
		hPal = CreatePalette( ppal );
		
		delete [] ppal;
	}
	
	// 把调色板信息读入设备环境
	{
		HDC hdc = GetDC( hWnd );
		
		HPALETTE prePal = NULL;
		if ( hPal )
		{
			prePal = SelectPalette(hdc, hPal, FALSE);
			RealizePalette( hdc );
		}
		
		// 创建BITMAP资源
		hBitmap = CreateDIBitmap(hdc, &bih, (long)CBM_INIT, 
			(LPBYTE)lptemp+sizeof(bih)+sizeof(RGBQUAD)*nColors,
			(LPBITMAPINFO)lptemp, DIB_RGB_COLORS);
		
		// 
		if ( hPal && prePal )
		{
			hPal = SelectPalette(hdc, prePal, FALSE);
			RealizePalette(hdc);
			// ??? 这儿是否要释放资源
			//DeleteObject( prePal );
		}
		
		ReleaseDC(hWnd, hdc);
	}

	return TRUE;
	
errProc:
	if ( hBitmap ) {
		DeleteObject( hBitmap );
		hBitmap = NULL;
	}
	if ( hPal ) {
		DeleteObject( hPal );
		hPal = NULL;
	}
	if ( lptemp ) {
		GlobalUnlock( hDib );
		lptemp = NULL;
	}
	if ( hDib ) {
		GlobalFree( hDib );
		hDib = NULL;
	}
	if ( lpGlobal ) {
		GlobalUnlock( hGlobal );
		lpGlobal = NULL;
	}
	if ( hGlobal ) {
		GlobalFree( hGlobal );
		hGlobal = NULL;
	}
	
	return FALSE;
}

// 保存图像
BOOL CImage::Save(LPCTSTR lpszPathName, int nType)
{
	HGLOBAL		hGlobal = NULL;
	LPBYTE		lpNewBuffer = NULL;
	LPBYTE		lpOldBuffer = NULL;
	
	HWND hWnd = (HWND)AfxGetMainWnd()->m_hWnd;

	DWORD dwImagesize;
	dwImagesize = nWidthBytes*nHeight;
	dwImagesize += sizeof(BITMAPFILEHEADER);
	dwImagesize += sizeof(BITMAPINFOHEADER);
	dwImagesize += nColors*sizeof(RGBQUAD);
	hGlobal = (HGLOBAL)::GlobalAlloc(GHND, dwImagesize);
	if ( hGlobal == NULL )
	{
		MessageBox(hWnd, "内存分配错误!", "失败", 0);
		return FALSE;
	}
	lpNewBuffer = (LPBYTE)::GlobalLock( hGlobal );
	if ( lpNewBuffer == NULL )
	{
		MessageBox(hWnd, "内存分配错误!", "失败", 0);
		::GlobalFree( hGlobal );
		return FALSE;
	}

	lpOldBuffer = (LPBYTE)::GlobalLock( hDib );
	if ( lpOldBuffer == NULL )
	{
		MessageBox(hWnd, "内存分配错误!", "失败", 0);
		goto errProc;
	}
	
	// 拷贝文件头信息和图像数据至新分配内存
	memcpy ( lpNewBuffer, &bmfh, sizeof(BITMAPFILEHEADER) );
	dwImagesize =nWidthBytes*nHeight;// nWidthBytes*nHeight;
	dwImagesize += sizeof(BITMAPINFOHEADER);
	dwImagesize += nColors*sizeof(RGBQUAD);
	memcpy (&lpNewBuffer[sizeof(BITMAPFILEHEADER)], lpOldBuffer, dwImagesize );
	
	// 释放资源
	GlobalUnlock( hDib );
	lpOldBuffer = NULL;
	GlobalUnlock( hGlobal );
	lpNewBuffer = NULL;

	switch ( nType )
	{
	case 0:
		MessageBox(hWnd, "不支持此文件格式!", "提示", 0);
		goto errProc;
		break;

	case 1:
		if ( !SaveBMP(lpszPathName, hGlobal) )
		{
			MessageBox(hWnd, "保存BMP图像失败!", "提示", 0);
			goto errProc;
		}
		break;
	case 2:
		if ( !SaveGIF(lpszPathName, hGlobal) )
		{
			MessageBox(hWnd, "保存GIF图像失败!", "提示", 0);
			goto errProc;
		}
		break;
	case 3:
		if ( !SavePCX(lpszPathName, hGlobal) )
		{
			MessageBox(hWnd, "保存PCX图像失败!", "提示", 0);
			goto errProc;
		}
		break;
	case 4:
		if ( !SaveTGA(lpszPathName, hGlobal) )
		{
			MessageBox(hWnd, "保存TGA图像失败!", "提示", 0);
			goto errProc;
		}
		break;
	case 5:
		if ( !SaveJPG(lpszPathName, hGlobal, 50) )
		{
			MessageBox(hWnd, "保存JPEG图像失败!", "提示", 0);
			goto errProc;
		}
		break;
		
	case 6:
		if ( !SaveTIF(lpszPathName, hGlobal) )
		{
			MessageBox(hWnd, "保存TIFF图像失败!", "提示", 0);
			goto errProc;
		}
		break;

	default:
		MessageBox(hWnd, "不支持此文件格式!", "提示", 0);
		goto errProc;
		break;
	}

	// 释放资源
	GlobalFree( hGlobal );
	hGlobal = NULL;

	return TRUE;

errProc:
	if ( lpOldBuffer ) {
		GlobalUnlock( hDib );
		lpOldBuffer = NULL;
	}
	if ( lpNewBuffer ) {
		GlobalUnlock( hGlobal );
		lpNewBuffer = NULL;
	}
	if ( hGlobal ) {
		GlobalFree( hGlobal );
		hGlobal = NULL;
	}

	return FALSE;
}

⌨️ 快捷键说明

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