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

📄 scemfgdiparser.cpp

📁 Source code for EMFexplorer 1.0
💻 CPP
📖 第 1 页 / 共 5 页
字号:
/*
*	This file is part of the EMFexplorer projet.
*	Copyright (C) 2004 Smith Charles.
*
*	This library is free software; you can redistribute it and/or
*	modify it under the terms of the GNU Lesser General Public
*	License as published by the Free Software Foundation; either
*	version 2.1 of the License, or (at your option) any later version.
*
*   This library is distributed in the hope that it will be useful,
*   but WITHOUT ANY WARRANTY; without even the implied warranty of
*   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
*   Lesser General Public License for more details.
*
*   You should have received a copy of the GNU Lesser General Public
*   License along with this library; if not, write to the Free Software
*   Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA.
*
*	Extension: for commercial use, apply the Equity Public License, which
*	adds to the normal terms of the GLPL a condition of donation to the author.
*   If you are interested in support for this source code,
*   contact Smith Charles <smith.charles@free.fr> for more information.
*/


#include "stdafx.h"
#include "SCEMFgdiParser.h"
#include "SCEMFRasterizerDefs.h"

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

#include "SCEMFDefs.h"
#include "SCGenInclude.h"
#include SC_INC_WINLIB(SCDCCloner.h)

// to allow token pasting at the beginig of line
#define SC_TKNPASTE(fake)

#define SC_RECORD_DECL0(recType) \
	SC_TKNPASTE(nothing)##recType *pRec = (##recType*)m_pRecord; \
	if (pRec->emr.nSize < sizeof(##recType)) \
		return SC_BRK_NOERROR

#define SC_RECORD_DECL_PLAY(recType) \
	SC_TKNPASTE(nothing)##recType *pRec = (##recType*)m_pRecord; \
	if (pRec->emr.nSize < sizeof(##recType)) \
	{ \
		SCPlayRecord(); \
		return SC_BRK_NOERROR; \
	}

// Reminder
#ifndef SC_RENDERER_CAN_DOROP
// Warning: when m_hPlayDC is not a clone, calling functions like SetMapmode on it may
// perturbate GDI+. This was observed for printer DC.
#pragma message(__FILE__ "(47): SC_RENDERER_CAN_DOROP not defined. Potential printing problems.")
#endif

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

CSCEMFgdiParser::CSCEMFgdiParser():
	SCBrkEMF(),
	m_pRenderer(NULL),
	m_hDestDC(NULL)
#ifdef SC_USE_DCCLONER
	,m_pCloneDC(NULL)
#endif
{
	memset(&m_xformOrig, 0, sizeof(m_xformOrig));
	m_xformOrig.eM11 = m_xformOrig.eM22 = 1;
}

CSCEMFgdiParser::CSCEMFgdiParser(I_EMFRenderer* pRenderer):
	SCBrkEMF(),
	m_pRenderer(pRenderer),
	m_hDestDC(NULL)
#ifdef SC_USE_DCCLONER
	,m_pCloneDC(NULL)
#endif
{
	memset(&m_xformOrig, 0, sizeof(m_xformOrig));
	m_xformOrig.eM11 = m_xformOrig.eM22 = 1;
}


CSCEMFgdiParser::~CSCEMFgdiParser()
{
#ifdef SC_USE_DCCLONER
	// delete temporary DC
	if (m_pCloneDC)
		delete m_pCloneDC;
#endif
}

void CSCEMFgdiParser::SCResetCracker()
{
}

//////////////////////////////////////////////////////////////////////
// Events methods
//////////////////////////////////////////////////////////////////////
SC_BRKRESULT CSCEMFgdiParser::OnEmfHEADER()
{
	// TRACE0("**EMR_HEADER\n");
	ASSERT(m_pRenderer);

	//ENHMETAHEADER *pRec = (ENHMETAHEADER*)m_pRecord;

	SCPlayRecord();
	m_pRenderer->SCBeginRendering(m_hDestDC, m_hPlayDC);

	return SCBrkEMF::OnEmfHEADER();
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYBEZIER()
{
	// TRACE0("**EMR_POLYBEZIER\n");
	ASSERT(m_pRenderer);

	EMRPOLYBEZIER *pRec = (EMRPOLYBEZIER*)m_pRecord;
	m_pRenderer->SCDrawBezier((LPPOINT)pRec->aptl, pRec->cptl);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYGON()
{
	// TRACE0("**EMR_POLYGON\n");
	ASSERT(m_pRenderer);

	EMRPOLYGON *pRec = (EMRPOLYGON*)m_pRecord;
	m_pRenderer->SCDrawPolygon((LPPOINT)pRec->aptl, pRec->cptl);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYLINE()
{
	// TRACE0("**EMR_POLYLINE\n");
	ASSERT(m_pRenderer);

	EMRPOLYLINE *pRec = (EMRPOLYLINE*)m_pRecord;
	m_pRenderer->SCDrawLines((LPPOINT)pRec->aptl, pRec->cptl);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYBEZIERTO()
{
	// TRACE0("**EMR_POLYBEZIERTO\n");
	ASSERT(m_pRenderer);

	EMRPOLYBEZIERTO *pRec = (EMRPOLYBEZIERTO*)m_pRecord;
	m_pRenderer->SCDrawBezierTo((LPPOINT)pRec->aptl, pRec->cptl);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYLINETO()
{
	// TRACE0("**EMR_POLYLINETO\n");
	ASSERT(m_pRenderer);

	EMRPOLYLINETO *pRec = (EMRPOLYLINETO*)m_pRecord;
	m_pRenderer->SCDrawLinesTo((LPPOINT)pRec->aptl, pRec->cptl);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYPOLYLINE()
{
	// TRACE0("**EMR_POLYPOLYLINE\n");
	ASSERT(m_pRenderer);

	EMRPOLYPOLYLINE *pRec = (EMRPOLYPOLYLINE*)m_pRecord;
	LPPOINT pPts = (LPPOINT)((DWORD*)pRec->aPolyCounts + pRec->nPolys);
	m_pRenderer->SCDrawPolyPolyline(pPts, pRec->cptl, (DWORD*)pRec->aPolyCounts, pRec->nPolys);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfPOLYPOLYGON()
{
	// TRACE0("**EMR_POLYPOLYGON\n");
	ASSERT(m_pRenderer);

	EMRPOLYPOLYGON *pRec = (EMRPOLYPOLYGON*)m_pRecord;
	LPPOINT pPts = (LPPOINT)((DWORD*)pRec->aPolyCounts + pRec->nPolys);
	m_pRenderer->SCDrawPolyPolygon(pPts, pRec->cptl, (DWORD*)pRec->aPolyCounts, pRec->nPolys);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETWINDOWEXTEX()
{
	// TRACE0("**EMR_SETWINDOWEXTEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management
#endif

	m_pRenderer->SCSetWindowExtent(((EMRSETWINDOWEXTEX*)m_pRecord)->szlExtent.cx,
									((EMRSETWINDOWEXTEX*)m_pRecord)->szlExtent.cy);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETWINDOWORGEX()
{
	// TRACE0("**EMR_SETWINDOWORGEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management
#endif

	m_pRenderer->SCSetWindowOrg(((EMRSETWINDOWORGEX*)m_pRecord)->ptlOrigin.x,
								((EMRSETWINDOWORGEX*)m_pRecord)->ptlOrigin.y);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETVIEWPORTEXTEX()
{
	// TRACE0("**EMR_SETVIEWPORTEXTEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management
#endif

	m_pRenderer->SCSetViewportExtent(((EMRSETVIEWPORTEXTEX*)m_pRecord)->szlExtent.cx,
									 ((EMRSETVIEWPORTEXTEX*)m_pRecord)->szlExtent.cy);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETVIEWPORTORGEX()
{
	// TRACE0("**EMR_SETVIEWPORTORGEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management
#endif

	m_pRenderer->SCSetViewportOrg(((EMRSETVIEWPORTORGEX*)m_pRecord)->ptlOrigin.x,
								  ((EMRSETVIEWPORTORGEX*)m_pRecord)->ptlOrigin.y);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETBRUSHORGEX()
{
	// TRACE0("**EMR_SETBRUSHORGEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management (via stretchbltmode and halftone)
#endif

	m_pRenderer->SCSetBrushOrg(((EMRSETBRUSHORGEX*)m_pRecord)->ptlOrigin);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfEOF()
{
	// TRACE0("**EMR_EOF\n");
	ASSERT(m_pRenderer);

	// (EMREOF*)m_pRecord;
	SCPlayRecord();
	m_pRenderer->SCEndRendering();
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETPIXELV()
{
	// TRACE0("**EMR_SETPIXELV\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCDrawPixel(((EMRSETPIXELV*)m_pRecord)->ptlPixel,
							 ((EMRSETPIXELV*)m_pRecord)->crColor);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETMAPPERFLAGS()
{
	// TRACE0("**EMR_SETMAPPERFLAGS\n");
	ASSERT(m_pRenderer);

	// (EMRSETMAPPERFLAGS*)m_pRecord;

	// No aspect ratio management, as we only use TT fonts.
	// Anyway let Windows do it.
	SCPlayRecord();		
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETMAPMODE()
{
	// TRACE0("**EMR_SETMAPMODE\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management (via viewport/window settings)
#endif

	m_pRenderer->SCSetMapMode(((EMRSETMAPMODE*)m_pRecord)->iMode);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETBKMODE()
{
	// TRACE0("**EMR_SETBKMODE\n");
	ASSERT(m_pRenderer);
	//SCPlayRecord(); // wait and see

	m_pRenderer->SCSetBkMode(((EMRSETBKMODE*)m_pRecord)->iMode);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETPOLYFILLMODE()
{
	// TRACE0("**EMR_SETPOLYFILLMODE\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCSetPolyFillMode(((EMRSETPOLYFILLMODE*)m_pRecord)->iMode);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETROP2()
{
	// TRACE0("**EMR_SETROP2\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCSetROP2(((EMRSETROP2*)m_pRecord)->iMode);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETSTRETCHBLTMODE()
{
	// TRACE0("**EMR_SETSTRETCHBLTMODE\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management
#endif

	m_pRenderer->SCSetStretchBltMode(((EMRSETSTRETCHBLTMODE*)m_pRecord)->iMode);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETTEXTALIGN()
{
	// TRACE0("**EMR_SETTEXTALIGN\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCSetTextAlign(((EMRSETTEXTALIGN*)m_pRecord)->iMode);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETCOLORADJUSTMENT()
{
	// TRACE0("**EMR_SETCOLORADJUSTMENT\n");
	ASSERT(m_pRenderer);


#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // for ROP (just in case)
#endif
	// "The color adjustment values are used to adjust the input color of the source bitmap
	// for calls to the StretchBlt and StretchDIBits functions when HALFTONE mode is set."
	// But it's NT specific.

	m_pRenderer->SCSetColorAsjustment(&((EMRSETCOLORADJUSTMENT*)m_pRecord)->ColorAdjustment);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETTEXTCOLOR()
{
	// TRACE0("**EMR_SETTEXTCOLOR\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCSetTextColor(((EMRSETTEXTCOLOR*)m_pRecord)->crColor);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETBKCOLOR()
{
	// TRACE0("**EMR_SETBKCOLOR\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCSetBkColor(((EMRSETBKCOLOR*)m_pRecord)->crColor);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfOFFSETCLIPRGN()
{
	// TRACE0("**EMR_OFFSETCLIPRGN\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCOffsetClipRect(((EMROFFSETCLIPRGN*)m_pRecord)->ptlOffset);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfMOVETOEX()
{
	// TRACE0("**EMR_MOVETOEX\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCMoveToEx(((EMRMOVETOEX*)m_pRecord)->ptl);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSETMETARGN()
{
	// TRACE0("**EMR_SETMETARGN\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCOnSetMetaRgn();
	
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfEXCLUDECLIPRECT()
{
	// TRACE0("**EMR_EXCLUDECLIPRECT\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCExcludeClipRect(((EMREXCLUDECLIPRECT*)m_pRecord)->rclClip);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfINTERSECTCLIPRECT()
{
	// TRACE0("**EMR_INTERSECTCLIPRECT\n");
	ASSERT(m_pRenderer);

	m_pRenderer->SCIntersectClipRect(((EMRINTERSECTCLIPRECT*)m_pRecord)->rclClip);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSCALEVIEWPORTEXTEX()
{
	// TRACE0("**EMR_SCALEVIEWPORTEXTEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP
	SCPlayRecord(); // required for ROP management
#endif

	EMRSCALEVIEWPORTEXTEX *pRec = (EMRSCALEVIEWPORTEXTEX*)m_pRecord;
	m_pRenderer->SCScaleViewport(pRec->xNum, pRec->xDenom, pRec->yNum, pRec->yDenom);
	return SC_BRK_NOERROR;
}

SC_BRKRESULT CSCEMFgdiParser::OnEmfSCALEWINDOWEXTEX()
{
	// TRACE0("**EMR_SCALEWINDOWEXTEX\n");
	ASSERT(m_pRenderer);

#ifndef SC_RENDERER_CAN_DOROP

⌨️ 快捷键说明

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