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

📄 avitools.cpp

📁 超声影像工作站系统可与各种型号的B超、彩超连接
💻 CPP
📖 第 1 页 / 共 2 页
字号:
	if (1 != fread(&bfh,sizeof(BITMAPFILEHEADER),1,fp))
	{
		fclose(fp);

		m_iLastErrorNumber	= ERR_READ_FILE_ERROR;
		m_sLastErrorDescribe.Format("读取文件头出错:%s",sBmpFile);
		return ERR_READ_FILE_ERROR;
	}

	//	验证文件格式 'BM'
	if (0x4d42 != bfh.bfType)
	{
		fclose(fp);

		m_iLastErrorNumber	= ERR_BAD_FORMAT;
		m_sLastErrorDescribe.Format("文件格式错误:没有 'BM' 标志:%s",sBmpFile);
		return ERR_BAD_FORMAT;
	}

	//	读取信息头数据
	if (1 != fread(&bih,sizeof(BITMAPINFOHEADER),1,fp))
	{
		fclose(fp);

		m_iLastErrorNumber	= ERR_READ_FILE_ERROR;
		m_sLastErrorDescribe.Format("读取信息头数据:%s",sBmpFile);
		return ERR_READ_FILE_ERROR;
	}
	
	// 8 bits bitmap
	if (8 == bih.biBitCount)
	{
		pattlelength	= bih.biClrUsed * sizeof(RGBQUAD);
	}

	//	16 or 24 bits bitmap
	else if (16 == bih.biBitCount || 24 == bih.biBitCount)
	{
		pattlelength	= 0;
	}
	
	//	other
	else
	{
		fclose(fp);

		m_iLastErrorNumber	= ERR_BAD_FORMAT;
		m_sLastErrorDescribe.Format("不能处理该图象,颜色错误:%s",sBmpFile);
		return ERR_BAD_FORMAT;
	}
	needlength	= sizeof(BITMAPINFOHEADER) + pattlelength;

	if (0 < pattlelength)
	{
		pattlebuf	= new CHAR[pattlelength];
		if (NULL == pattlebuf)
		{
			fclose(fp);

			m_iLastErrorNumber	= ERR_OUT_OF_MEMORY;
			m_sLastErrorDescribe.Format("内存溢出");
			return ERR_OUT_OF_MEMORY;
		}

		if (1 != fread(pattlebuf,pattlelength,1,fp))
		{
			delete pattlebuf;
			fclose(fp);

			m_iLastErrorNumber	= ERR_READ_FILE_ERROR;
			m_sLastErrorDescribe.Format("读取调色板出错:%s",sBmpFile);
			return ERR_READ_FILE_ERROR;
		}
	}
	fclose(fp);

	//	为流格式分配空间,包括信息头和可选调色板
	m_pFormat	= (BITMAPINFOHEADER *)(new CHAR[needlength]);
	if (NULL == m_pFormat)
	{
		delete pattlebuf;

		m_iLastErrorNumber	= ERR_OUT_OF_MEMORY;
		m_sLastErrorDescribe.Format("内存溢出");
		return ERR_OUT_OF_MEMORY;
	}

	//	复制格式内容
	memcpy(m_pFormat,&bih,sizeof(BITMAPINFOHEADER));
	if (0 < pattlelength)
	{
		memcpy((CHAR *)m_pFormat + sizeof(BITMAPINFOHEADER),pattlebuf,pattlelength);
		delete pattlebuf;
	}
	
	m_iFormatLength	= needlength;
	m_iFrameSize	= bih.biSizeImage;

	m_iLastErrorNumber	= ERR_OK;
	m_sLastErrorDescribe.Empty();
	return ERR_OK;
}

//	Unfinished
HRESULT
CAVITools::SetStreamFormatFromMemory(BITMAPINFOHEADER *pData,BOOL bHasPattle)
{
	INT	needlength;

	if (NULL != m_pFormat)
	{
		delete m_pFormat;
		m_pFormat	= NULL;
	}

	if (8 == pData->biBitCount)
	{
		needlength	= sizeof(BITMAPINFOHEADER) + pData->biClrUsed * sizeof(RGBQUAD);
	}
	else if (16 == pData->biBitCount || 24 == pData->biBitCount)
	{
		if (FALSE != bHasPattle)
			return FALSE;
		needlength	= sizeof(BITMAPINFOHEADER);
	}
	else
	{
		return FALSE;
	}

	m_pFormat	= (BITMAPINFOHEADER *)(new CHAR[needlength]);
	if (NULL == m_pFormat)
	{
		return FALSE;
	}

	memcpy(m_pFormat,pData,needlength);

	m_iFormatLength	= needlength;
	m_iFrameSize	= pData->biSizeImage;

	return TRUE;
}

/*
	分解 AVI 文件为位图文件
	输入参数:
		sAviFileName			-	需要分解的 AVI 文件位置
		sTargetPath				-	目标路径
		iCount					-	分解的位图文件数目
	返回值:
		ERR_OK					-	分解成功
*/
HRESULT
CAVITools::SplitAvi(CHAR *sAviFileName, CHAR *sTargetPath, INT *iCount)
{
//	long			lBytes,lSamples;					//	Samples And Bytes That Read From Stream
	AVIFILEINFO		AviFileInfo;						//	Avi File Info
	AVISTREAMINFO	AviStreamInfo;						//	Avi Stream Info
	PAVIFILE		pAviFile		= NULL;
	PAVISTREAM		pAviStream		= NULL;
	PGETFRAME		pGetFrame		= NULL;
	HDRAWDIB		hDrawDib		= NULL;
	FILE			*fp				= NULL;
	CHAR			*sBmpFileName	= NULL;
	HRESULT			hr				= NULL;				// Common Var, The Function's Result Handle
	HRESULT			hReturnValue	= ERR_OK;
	LPVOID			lpFrameBuffer	= NULL;
	
	//	Open An Avi File, Get It's Handle Pointer
	hr	= ::AVIFileOpen(&pAviFile,sAviFileName,OF_READ,NULL);
	if (hr)
	{
		hReturnValue	= ERR_AVI_OPEN_ERROR;
		goto _ReleaseMemory;
	}

	//	Get Avi File Info
	hr	= ::AVIFileInfo(pAviFile,&AviFileInfo,sizeof(AVIFILEINFO));
	if (hr)
	{
		hReturnValue	= ERR_AVI_INFO_ERROR;
		goto _ReleaseMemory;
	}

	// Open A Stream From An Opened File, Get It's Handle Pointer
	hr	= ::AVIFileGetStream(pAviFile,&pAviStream,streamtypeVIDEO,0);
	if (hr)
	{
		if (AVIERR_NODATA == hr)
		{
		}
		else if (AVIERR_MEMORY == hr)
		{
		}
		hReturnValue	= ERR_AVI_GETSTREAM_ERROR;
		goto _ReleaseMemory;
	}

	// Get Stream Information
	hr	= ::AVIStreamInfo(pAviStream,&AviStreamInfo,sizeof(AVISTREAMINFO));
	if (hr)
	{
		hReturnValue	= ERR_AVI_STREAMINFO_ERROR;
		goto _ReleaseMemory;
	}

	// Get Frame Open
	pGetFrame	= ::AVIStreamGetFrameOpen(pAviStream,(LPBITMAPINFOHEADER)AVIGETFRAMEF_BESTDISPLAYFMT);
	if (!pGetFrame)
	{
		hReturnValue	= ERR_AVI_GETFRAME_ERROR;
		goto _ReleaseMemory;
	}

	sBmpFileName	= new CHAR[strlen(sTargetPath) + 12];
	if (NULL == sBmpFileName)
	{
		hReturnValue	= ERR_OUT_OF_MEMORY;
		goto _ReleaseMemory;
	}

	strcpy(sBmpFileName,sTargetPath);
	if ('\\' != sBmpFileName[strlen(sBmpFileName) - 1])
	{
		strcat(sBmpFileName,"\\");
	}
	strcat(sBmpFileName,"00000.bmp");
//////////////////////////////
 	INT		n,i;

	n	= strlen(sBmpFileName) - 5;

	for (i = 0;; i++)
	{
		if ((INT)AviStreamInfo.dwLength <= i)
		{
			*iCount	= i;
			hReturnValue	= ERR_OK;
			goto _ReleaseMemory;
		}

		sBmpFileName[n - 4] = '0' + i % 100000	/ 10000;
		sBmpFileName[n - 3] = '0' + i % 10000	/ 1000;
		sBmpFileName[n - 2] = '0' + i % 1000	/ 100;
		sBmpFileName[n - 1] = '0' + i % 100		/ 10;
		sBmpFileName[n - 0] = '0' + i % 10		/ 1;

		lpFrameBuffer	= ::AVIStreamGetFrame(pGetFrame,i);
		if (NULL == lpFrameBuffer)
		{
			hReturnValue	= ERR_AVI_GETFRAME_ERROR;
			goto _ReleaseMemory;
		}

		// Save The Memory Frame To A Specified File
//		SaveDib(fn,framebuffer,width,height,colorbits);
	}

	hReturnValue	= ERR_OK;

_ReleaseMemory:
	if (NULL != sBmpFileName)	delete sBmpFileName;
	if (NULL != pGetFrame)		::AVIStreamGetFrameClose(pGetFrame);
	if (NULL != pAviStream)		::AVIStreamRelease(pAviStream);
	if (NULL != pAviFile)		::AVIFileRelease(pAviFile);
	return hReturnValue;
}

/*
	SAVE BITMAP FILE TO DISK
	ARGUMENTS:
		sFileName				-	THE PATHNAME OF BITMAP THAT YOU WANT TO SAVE
		pData					-	ADDRESS OF BITMAP BUFFER, INCLUDE INFOHEADER, 
									OPTIONAL PATTLE AND BITSDATA
	RETURN VALUE:
		ERR_OK					-	SUCCESS
		ERR_BAD_FORMAT			-	BUFFER HAS BAD OR UNKNOWN FORMAT
		ERR_CANNOT_OPEN_FILE	-	CANNOT OPEN FILE TO WRITE
		ERR_WRITE_FILE_ERROR	-	AN ERROR OCCUR WHILE WRITING FILE
*/
HRESULT
CAVITools::SaveBMP(CHAR *sFileName, BITMAPINFOHEADER *pData)
{
	BITMAPFILEHEADER	bfh;
	FILE				*fp		= NULL;

	//	SUPPORT ONLY 8 bits, 16 bits AND 24 bits FORMAT
	if (8 != pData->biBitCount && 16 != pData->biBitCount && 24 != pData->biBitCount)
	{
		m_iLastErrorNumber		= ERR_BAD_FORMAT;
		m_sLastErrorDescribe	= "不支持该图象的颜色数目";
		return ERR_BAD_FORMAT;
	}

	bfh.bfType	= 0x4d42; // "BM";
	bfh.bfReserved1	= 0;
	bfh.bfReserved2	= 0;

	//	CALCULATE FILE SIZE AND BITSDATA OFFSET ADDRESS
	bfh.bfSize	= sizeof(bfh);
	bfh.bfSize	+= pData->biSize;
	if (8 == pData->biBitCount)
		bfh.bfSize	+= pData->biClrUsed * sizeof(RGBQUAD);

	bfh.bfOffBits	= bfh.bfSize;

	bfh.bfSize	+= pData->biSizeImage;

	//	OPEN FILE FOR BINARY WRITE
	if (NULL == (fp = fopen(sFileName,"wb")))
	{
		m_iLastErrorNumber	= ERR_CANNOT_OPEN_FILE;
		m_sLastErrorDescribe.Format("无法打开文件 %s",sFileName);
		return ERR_CANNOT_OPEN_FILE;
	}
	
	//	WRITE DATA
	if (1 != fwrite(&bfh,sizeof(BITMAPFILEHEADER),1,fp) ||
		1 != fwrite((CHAR *)pData,bfh.bfSize - sizeof(BITMAPFILEHEADER),1,fp))
	{
		fclose(fp);
		m_iLastErrorNumber	= ERR_WRITE_FILE_ERROR;
		m_sLastErrorDescribe.Format("无法写入文件 %s",sFileName);
		return ERR_WRITE_FILE_ERROR;
	}
	fclose(fp);

	//	SUCCESS, RETURN OK
	m_iLastErrorNumber	= ERR_OK;
	m_sLastErrorDescribe.Empty();
	return ERR_OK;
}

/*
	RETURN THE ERROR NUMBER AND DESCRIBE OF THE LAST ERROR
	ARGUMENTS:
		sDescribe		-	REFERS TO A CSTRING VARIABLE TO RETURN ERROR DESCRIBE
		iErrorNumber	-	REFERS TO A INTEGER VARIABLE TO RETURN ERROR NUMBER
	RETURN VALUE:
		TRUE			-	HAS ERROR
		FALSE			-	THERE ISN'T ANY ERROR
*/
BOOL
CAVITools::GetLastError(CString &sDescribe, INT &iErrorNumber)
{
	sDescribe		= m_sLastErrorDescribe;
	iErrorNumber	= m_iLastErrorNumber;
	return	(ERR_OK	== m_iLastErrorNumber) ? (FALSE) : (TRUE);
}

BOOL
CAVITools::GetLastError(CString &sDescribe)
{
	sDescribe		= m_sLastErrorDescribe;
	return	(ERR_OK	== m_iLastErrorNumber) ? (FALSE) : (TRUE);
}

/*
	在指定的设备上显示 AVI 图象
	参数:
	sFileName			-	AVI 文件名
	hWnd				-	指定的设备
*/
BOOL
CAVITools::ShowAvi(CHAR *sFileName, HWND hWnd, 
				   INT iVideoID, INT iDelay,
				   INT iBeginFrame, INT iEndFrame,
				   int xDst, int yDst, int dxDst, int dyDst,
				   int xSrc, int ySrc, int dxSrc, int dySrc)
{
	memset(&m_ShowAviArg, 0, sizeof(SHOW_AVI_ARG));
	
	strcpy(m_ShowAviArg.sFileName, sFileName);
	SHOW_AVI_ARG	*p	= &m_ShowAviArg;
	p->xDst				= xDst;
	p->yDst				= yDst;
	p->dxDst			= dxDst;
	p->dyDst			= dyDst;
	p->xSrc				= xSrc;
	p->ySrc				= ySrc;
	p->dxSrc			= dxSrc;
	p->dySrc			= dySrc;
	p->hWnd				= hWnd;
	p->iDelay			= iDelay;
	p->bLoop			= TRUE;
	p->iVideoID			= iVideoID;
	p->iBeginFrame		= iBeginFrame;
	p->iEndFrame		= iEndFrame;
	p->iControl			= CONTROL_PLAY;

	::AfxBeginThread(ShowAviThread, (LPVOID)p);

	return	TRUE;
}

UINT
ShowAviThread(LPVOID lParam)
{
	SHOW_AVI_ARG*	pArg			= (SHOW_AVI_ARG *)lParam;
	HDRAWDIB		hDrawDib		= NULL;
	HDC				hDC				= NULL;
	PAVIFILE		pAviFile		= NULL;
	PAVISTREAM		pAviStream		= NULL;
	PGETFRAME		pGetFrame		= NULL;
	LPVOID			lpFrameBuf		= NULL;
	HRESULT			hr				= NULL;
	BOOL			bReturnValue	= FALSE;
	INT				iCurrentFrame	= -1;
	AVISTREAMINFO	AviStreamInfo;

	hr			= ::AVIFileOpen(&pAviFile, pArg->sFileName, OF_READ, NULL);
	if	(AVIERR_OK	!= hr)			goto	_ReleaseMemory;

	hr			= ::AVIFileGetStream(pAviFile, &pAviStream, streamtypeVIDEO, pArg->iVideoID);
	if	(AVIERR_OK	!= hr)			goto	_ReleaseMemory;

	hr			= ::AVIStreamInfo(pAviStream, &AviStreamInfo, sizeof(AVISTREAMINFO));
	if	(AVIERR_OK	!= hr)			goto	_ReleaseMemory;

	pGetFrame	= ::AVIStreamGetFrameOpen(pAviStream, NULL);
	if	(NULL		== pGetFrame)	goto	_ReleaseMemory;

	hDrawDib	= ::DrawDibOpen();
	if	(NULL		== hDrawDib)	goto	_ReleaseMemory;

	hDC			= ::GetDC(pArg->hWnd);
	if	(NULL		== hDC)			goto	_ReleaseMemory;

	if	((INT)AviStreamInfo.dwLength <= 0)	goto	_ReleaseMemory;

	if	(pArg->iBeginFrame < 0)
		pArg->iBeginFrame	= 0;
	else if	(pArg->iBeginFrame >= (INT)AviStreamInfo.dwLength)
		pArg->iBeginFrame	= (INT)AviStreamInfo.dwLength - 1;

	if	(pArg->iEndFrame < 0)
		pArg->iEndFrame		= (INT)AviStreamInfo.dwLength - 1;
	else if	(pArg->iEndFrame >= (INT)AviStreamInfo.dwLength)
		pArg->iEndFrame		= (INT)AviStreamInfo.dwLength - 1;

	if	(pArg->iEndFrame < pArg->iBeginFrame)
		goto	_ReleaseMemory;

	iCurrentFrame	= pArg->iBeginFrame;
	for	(;;)
	{
		if	(CONTROL_PLAY	!= pArg->iControl)
		{
			if	(CONTROL_PAUSE	== pArg->iControl)
			{
				while	(CONTROL_PAUSE	== pArg->iControl)	::Sleep(100);
				if		(CONTROL_STOP	== pArg->iControl)	goto	_ReleaseMemory;
			}
			else if	(CONTROL_STOP	== pArg->iControl)
			{
				goto	_ReleaseMemory;
			}
		}

		if	(iCurrentFrame >= (INT)AviStreamInfo.dwLength)
		{
			if	(FALSE	== pArg->bLoop)		break;
			else							iCurrentFrame	= pArg->iBeginFrame;
		}
		lpFrameBuf		= ::AVIStreamGetFrame(pGetFrame, iCurrentFrame);
		if	(NULL		== lpFrameBuf)	goto	_ReleaseMemory;
	
		::DrawDibDraw(hDrawDib, hDC,
			pArg->xDst, pArg->yDst, pArg->dxDst, pArg->dyDst,
			(BITMAPINFOHEADER *)lpFrameBuf, NULL,
			pArg->xSrc, pArg->ySrc, pArg->dxSrc, pArg->dySrc,
			0);

		::Sleep(pArg->iDelay);
		iCurrentFrame++;
	}
	bReturnValue	= TRUE;

_ReleaseMemory:
	if	(NULL	!= hDC)			::ReleaseDC(pArg->hWnd, hDC);
	if	(NULL	!= hDrawDib)	::DrawDibClose(hDrawDib);
	if	(NULL	!= pGetFrame)	::AVIStreamGetFrameClose(pGetFrame);
	if	(NULL	!= pAviStream)	::AVIStreamRelease(pAviStream);
	if	(NULL	!= pAviFile)	::AVIFileRelease(pAviFile);

	return	UINT(bReturnValue);
}

⌨️ 快捷键说明

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