EMF文件结构
Emf
主要由
Emf
头记录、描述和记录构成:
Emf头
typedef struct tagENHMETAHEADER {
DWORD iType; 应该为1(EMR_HEADER)
DWORD nSize; Header大小,不包括描述
RECTL rclBounds; 图像的边框尺寸(设备单位)
RECTL rclFrame; 图像的边框尺寸(0.01 mm为单位)
DWORD dSignature; 0x464d4520(EMF标志)
DWORD nVersion; 0x10000
DWORD nBytes; 元文件的尺寸(整个文件大小)
DWORD nRecords; Emf记录数(包括头,描述数据头记录)
WORD nHandles;
WORD sReserved;
DWORD nDescription; 描述长度,以byte为单位
DWORD offDescription; 描述存放地方,文件开始为0开始计算
DWORD nPalEntries;
SIZEL szlDevice; 原始设备分辩率(像素单位)
SIZEL szlMillimeters;原始设备分辩率(mm单位)
#if (WINVER >= 0x0400)
DWORD cbPixelFormat;
DWORD offPixelFormat;
DWORD bOpenGL;
#endif /* WINVER >= 0x0400 */
#if (WINVER >= 0x0500)
SIZEL szlMicrometers; szlMillimeters*1000
#endif /* WINVER >= 0x0500 */
} ENHMETAHEADER, *PENHMETAHEADER;
EMF描述
如果头记录的
nDescription
大于
0
则表示有内容,否则为空,一般紧接在
EMR_HEADER
后面
EMF记录
记录格式:
DWORD iType; 类型,如EMR_HEADER, EMR_EOF
DWORD nSize;长度,包括iType,nSize,内容
具体内容
EMF最后记录
EMR emr;EMF记录(iType和nSize)
DWORD nPalEntries; 调色板数
DWORD offPalEntries; 调色板位置,从iType开始计算
DWORD nSizeLast; nSize大小,如果有调色板,则调色版在nSizeLast前面
例子
//打开Emf文件
if
(!m_File.Open(strFileName ,CFile::modeRead , &m_FileException))
{
TCHAR szError[1024];
m_FileException.GetErrorMessage(szError, 1024);
TRACE(L"Couldn't open source file::%s,errormsg:s/n",strFileName,szError) ;
return ;
}
DWORD dwReaded ;
//
读取Emf Header
dwReaded = m_File.Read( &m_EnhMetaHeader , sizeof( ENHMETAHEADER ) ) ;
if( dwReaded < sizeof( ENHMETAHEADER ) )
{
TRACE("Read meta header error!/n") ;
m_File.Close() ;
return ;
}
if( m_EnhMetaHeader.dSignature!=0x464d4520)
{
TRACE("This file is not emf file./n");
m_File.Close() ;
return;
}
//
读取描述
if ( m_EnhMetaHeader.nDescription > 0 )
{
//file.Seek(eh.offDescription,CFile::begin);
TCHAR *szDesciption ;
szDesciption = new TCHAR[m_EnhMetaHeader.nDescription+1] ;
memset( szDesciption , 0 , sizeof( TCHAR) * (m_EnhMetaHeader.nDescription+1));
dwReaded = m_File.Read(szDesciption , m_EnhMetaHeader.nDescription * sizeof( TCHAR) ) ;
if( dwReaded == m_EnhMetaHeader.nDescription * sizeof( TCHAR) )
{
TRACE(L"description:%s/n",szDesciption);
}
//file.Seek( sizeof( ENHMETAHEADER ) , CFile::begin) ;
delete szDesciption ;
}
m_dwEmfRecord = 0 ;
//
读取记录
DWORD
dwReaded = m_File.Read( &iType , 4 ) ;
if( dwReaded < 4 )
return ;
dwReaded = m_File.Read( &nSize , 4 ) ;
if( dwReaded < 4 )
return ;
lpParam = new BYTE[nSize ];
memset( lpParam , 0 , nSize ) ;
memcpy( lpParam , &iType , 4 ) ;
memcpy( lpParam + 4 , &nSize , 4 ) ;
if( lpParam == NULL )
return ;
if( nSize > 8 )
{
dwReaded = m_File.Read(lpParam + 8, nSize - 8 ) ;
if( dwReaded < nSize - 8 )
return ;
}