📄 gfx.cc
字号:
//========================================================================//// Gfx.cc//// Copyright 1996-2003 Glyph & Cog, LLC////========================================================================#include <aconf.h>#ifdef USE_GCC_PRAGMAS#pragma implementation#endif#include <stdlib.h>#include <stdio.h>#include <stddef.h>#include <string.h>#include <math.h>#include "gmem.h"#include "GlobalParams.h"#include "CharTypes.h"#include "Object.h"#include "Array.h"#include "Dict.h"#include "Stream.h"#include "Lexer.h"#include "Parser.h"#include "GfxFont.h"#include "GfxState.h"#include "OutputDev.h"#include "Page.h"#include "Error.h"#include "Gfx.h"// the MSVC math.h doesn't define this#ifndef M_PI#define M_PI 3.14159265358979323846#endif//------------------------------------------------------------------------// constants//------------------------------------------------------------------------// Max recursive depth for a function shading fill.#define functionMaxDepth 6// Max delta allowed in any color component for a function shading fill.#define functionColorDelta (dblToCol(1 / 256.0))// Max number of splits along the t axis for an axial shading fill.#define axialMaxSplits 256// Max delta allowed in any color component for an axial shading fill.#define axialColorDelta (dblToCol(1 / 256.0))// Max number of splits along the t axis for a radial shading fill.#define radialMaxSplits 256// Max delta allowed in any color component for a radial shading fill.#define radialColorDelta (dblToCol(1 / 256.0))// Max recursive depth for a Gouraud triangle shading fill.#define gouraudMaxDepth 4// Max delta allowed in any color component for a Gouraud triangle// shading fill.#define gouraudColorDelta (dblToCol(1 / 256.0))// Max recursive depth for a patch mesh shading fill.#define patchMaxDepth 6// Max delta allowed in any color component for a patch mesh shading// fill.#define patchColorDelta (dblToCol(1 / 256.0))//------------------------------------------------------------------------// Operator table//------------------------------------------------------------------------#ifdef WIN32 // this works around a bug in the VC7 compiler# pragma optimize("",off)#endifOperator Gfx::opTab[] = { {"\"", 3, {tchkNum, tchkNum, tchkString}, &Gfx::opMoveSetShowText}, {"'", 1, {tchkString}, &Gfx::opMoveShowText}, {"B", 0, {tchkNone}, &Gfx::opFillStroke}, {"B*", 0, {tchkNone}, &Gfx::opEOFillStroke}, {"BDC", 2, {tchkName, tchkProps}, &Gfx::opBeginMarkedContent}, {"BI", 0, {tchkNone}, &Gfx::opBeginImage}, {"BMC", 1, {tchkName}, &Gfx::opBeginMarkedContent}, {"BT", 0, {tchkNone}, &Gfx::opBeginText}, {"BX", 0, {tchkNone}, &Gfx::opBeginIgnoreUndef}, {"CS", 1, {tchkName}, &Gfx::opSetStrokeColorSpace}, {"DP", 2, {tchkName, tchkProps}, &Gfx::opMarkPoint}, {"Do", 1, {tchkName}, &Gfx::opXObject}, {"EI", 0, {tchkNone}, &Gfx::opEndImage}, {"EMC", 0, {tchkNone}, &Gfx::opEndMarkedContent}, {"ET", 0, {tchkNone}, &Gfx::opEndText}, {"EX", 0, {tchkNone}, &Gfx::opEndIgnoreUndef}, {"F", 0, {tchkNone}, &Gfx::opFill}, {"G", 1, {tchkNum}, &Gfx::opSetStrokeGray}, {"ID", 0, {tchkNone}, &Gfx::opImageData}, {"J", 1, {tchkInt}, &Gfx::opSetLineCap}, {"K", 4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opSetStrokeCMYKColor}, {"M", 1, {tchkNum}, &Gfx::opSetMiterLimit}, {"MP", 1, {tchkName}, &Gfx::opMarkPoint}, {"Q", 0, {tchkNone}, &Gfx::opRestore}, {"RG", 3, {tchkNum, tchkNum, tchkNum}, &Gfx::opSetStrokeRGBColor}, {"S", 0, {tchkNone}, &Gfx::opStroke}, {"SC", -4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opSetStrokeColor}, {"SCN", -5, {tchkSCN, tchkSCN, tchkSCN, tchkSCN, tchkSCN}, &Gfx::opSetStrokeColorN}, {"T*", 0, {tchkNone}, &Gfx::opTextNextLine}, {"TD", 2, {tchkNum, tchkNum}, &Gfx::opTextMoveSet}, {"TJ", 1, {tchkArray}, &Gfx::opShowSpaceText}, {"TL", 1, {tchkNum}, &Gfx::opSetTextLeading}, {"Tc", 1, {tchkNum}, &Gfx::opSetCharSpacing}, {"Td", 2, {tchkNum, tchkNum}, &Gfx::opTextMove}, {"Tf", 2, {tchkName, tchkNum}, &Gfx::opSetFont}, {"Tj", 1, {tchkString}, &Gfx::opShowText}, {"Tm", 6, {tchkNum, tchkNum, tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opSetTextMatrix}, {"Tr", 1, {tchkInt}, &Gfx::opSetTextRender}, {"Ts", 1, {tchkNum}, &Gfx::opSetTextRise}, {"Tw", 1, {tchkNum}, &Gfx::opSetWordSpacing}, {"Tz", 1, {tchkNum}, &Gfx::opSetHorizScaling}, {"W", 0, {tchkNone}, &Gfx::opClip}, {"W*", 0, {tchkNone}, &Gfx::opEOClip}, {"b", 0, {tchkNone}, &Gfx::opCloseFillStroke}, {"b*", 0, {tchkNone}, &Gfx::opCloseEOFillStroke}, {"c", 6, {tchkNum, tchkNum, tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opCurveTo}, {"cm", 6, {tchkNum, tchkNum, tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opConcat}, {"cs", 1, {tchkName}, &Gfx::opSetFillColorSpace}, {"d", 2, {tchkArray, tchkNum}, &Gfx::opSetDash}, {"d0", 2, {tchkNum, tchkNum}, &Gfx::opSetCharWidth}, {"d1", 6, {tchkNum, tchkNum, tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opSetCacheDevice}, {"f", 0, {tchkNone}, &Gfx::opFill}, {"f*", 0, {tchkNone}, &Gfx::opEOFill}, {"g", 1, {tchkNum}, &Gfx::opSetFillGray}, {"gs", 1, {tchkName}, &Gfx::opSetExtGState}, {"h", 0, {tchkNone}, &Gfx::opClosePath}, {"i", 1, {tchkNum}, &Gfx::opSetFlat}, {"j", 1, {tchkInt}, &Gfx::opSetLineJoin}, {"k", 4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opSetFillCMYKColor}, {"l", 2, {tchkNum, tchkNum}, &Gfx::opLineTo}, {"m", 2, {tchkNum, tchkNum}, &Gfx::opMoveTo}, {"n", 0, {tchkNone}, &Gfx::opEndPath}, {"q", 0, {tchkNone}, &Gfx::opSave}, {"re", 4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opRectangle}, {"rg", 3, {tchkNum, tchkNum, tchkNum}, &Gfx::opSetFillRGBColor}, {"ri", 1, {tchkName}, &Gfx::opSetRenderingIntent}, {"s", 0, {tchkNone}, &Gfx::opCloseStroke}, {"sc", -4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opSetFillColor}, {"scn", -5, {tchkSCN, tchkSCN, tchkSCN, tchkSCN, tchkSCN}, &Gfx::opSetFillColorN}, {"sh", 1, {tchkName}, &Gfx::opShFill}, {"v", 4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opCurveTo1}, {"w", 1, {tchkNum}, &Gfx::opSetLineWidth}, {"y", 4, {tchkNum, tchkNum, tchkNum, tchkNum}, &Gfx::opCurveTo2},};#ifdef WIN32 // this works around a bug in the VC7 compiler# pragma optimize("",on)#endif#define numOps (sizeof(opTab) / sizeof(Operator))//------------------------------------------------------------------------// GfxResources//------------------------------------------------------------------------GfxResources::GfxResources(XRef *xref, Dict *resDict, GfxResources *nextA) { Object obj1, obj2; Ref r; if (resDict) { // build font dictionary fonts = NULL; resDict->lookupNF("Font", &obj1); if (obj1.isRef()) { obj1.fetch(xref, &obj2); if (obj2.isDict()) { r = obj1.getRef(); fonts = new GfxFontDict(xref, &r, obj2.getDict()); } obj2.free(); } else if (obj1.isDict()) { fonts = new GfxFontDict(xref, NULL, obj1.getDict()); } obj1.free(); // get XObject dictionary resDict->lookup("XObject", &xObjDict); // get color space dictionary resDict->lookup("ColorSpace", &colorSpaceDict); // get pattern dictionary resDict->lookup("Pattern", &patternDict); // get shading dictionary resDict->lookup("Shading", &shadingDict); // get graphics state parameter dictionary resDict->lookup("ExtGState", &gStateDict); } else { fonts = NULL; xObjDict.initNull(); colorSpaceDict.initNull(); patternDict.initNull(); shadingDict.initNull(); gStateDict.initNull(); } next = nextA;}GfxResources::~GfxResources() { if (fonts) { delete fonts; } xObjDict.free(); colorSpaceDict.free(); patternDict.free(); shadingDict.free(); gStateDict.free();}GfxFont *GfxResources::lookupFont(char *name) { GfxFont *font; GfxResources *resPtr; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->fonts) { if ((font = resPtr->fonts->lookup(name))) return font; } } error(-1, "Unknown font tag '%s'", name); return NULL;}GBool GfxResources::lookupXObject(char *name, Object *obj) { GfxResources *resPtr; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->xObjDict.isDict()) { if (!resPtr->xObjDict.dictLookup(name, obj)->isNull()) return gTrue; obj->free(); } } error(-1, "XObject '%s' is unknown", name); return gFalse;}GBool GfxResources::lookupXObjectNF(char *name, Object *obj) { GfxResources *resPtr; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->xObjDict.isDict()) { if (!resPtr->xObjDict.dictLookupNF(name, obj)->isNull()) return gTrue; obj->free(); } } error(-1, "XObject '%s' is unknown", name); return gFalse;}void GfxResources::lookupColorSpace(char *name, Object *obj) { GfxResources *resPtr; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->colorSpaceDict.isDict()) { if (!resPtr->colorSpaceDict.dictLookup(name, obj)->isNull()) { return; } obj->free(); } } obj->initNull();}GfxPattern *GfxResources::lookupPattern(char *name) { GfxResources *resPtr; GfxPattern *pattern; Object obj; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->patternDict.isDict()) { if (!resPtr->patternDict.dictLookup(name, &obj)->isNull()) { pattern = GfxPattern::parse(&obj); obj.free(); return pattern; } obj.free(); } } error(-1, "Unknown pattern '%s'", name); return NULL;}GfxShading *GfxResources::lookupShading(char *name) { GfxResources *resPtr; GfxShading *shading; Object obj; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->shadingDict.isDict()) { if (!resPtr->shadingDict.dictLookup(name, &obj)->isNull()) { shading = GfxShading::parse(&obj); obj.free(); return shading; } obj.free(); } } error(-1, "Unknown shading '%s'", name); return NULL;}GBool GfxResources::lookupGState(char *name, Object *obj) { GfxResources *resPtr; for (resPtr = this; resPtr; resPtr = resPtr->next) { if (resPtr->gStateDict.isDict()) { if (!resPtr->gStateDict.dictLookup(name, obj)->isNull()) { return gTrue; } obj->free(); } } error(-1, "ExtGState '%s' is unknown", name); return gFalse;}//------------------------------------------------------------------------// Gfx//------------------------------------------------------------------------Gfx::Gfx(XRef *xrefA, OutputDev *outA, int pageNum, Dict *resDict, double hDPI, double vDPI, PDFRectangle *box, PDFRectangle *cropBox, int rotate, GBool (*abortCheckCbkA)(void *data), void *abortCheckCbkDataA) { int i; xref = xrefA; subPage = gFalse; printCommands = globalParams->getPrintCommands(); // start the resource stack res = new GfxResources(xref, resDict, NULL); // initialize out = outA; state = new GfxState(hDPI, vDPI, box, rotate, out->upsideDown()); fontChanged = gFalse; clip = clipNone; ignoreUndef = 0; out->startPage(pageNum, state); out->setDefaultCTM(state->getCTM()); out->updateAll(state); for (i = 0; i < 6; ++i) { baseMatrix[i] = state->getCTM()[i]; } formDepth = 0; abortCheckCbk = abortCheckCbkA; abortCheckCbkData = abortCheckCbkDataA; // set crop box if (cropBox) { state->moveTo(cropBox->x1, cropBox->y1); state->lineTo(cropBox->x2, cropBox->y1); state->lineTo(cropBox->x2, cropBox->y2); state->lineTo(cropBox->x1, cropBox->y2); state->closePath(); state->clip(); out->clip(state); state->clearPath(); }}Gfx::Gfx(XRef *xrefA, OutputDev *outA, Dict *resDict, PDFRectangle *box, PDFRectangle *cropBox, GBool (*abortCheckCbkA)(void *data), void *abortCheckCbkDataA) { int i; xref = xrefA; subPage = gTrue; printCommands = globalParams->getPrintCommands(); // start the resource stack res = new GfxResources(xref, resDict, NULL); // initialize out = outA; state = new GfxState(72, 72, box, 0, gFalse); fontChanged = gFalse; clip = clipNone; ignoreUndef = 0; for (i = 0; i < 6; ++i) { baseMatrix[i] = state->getCTM()[i]; }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -