1 // Copyright 2014 PDFium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com 6 7 #ifndef CORE_INCLUDE_FPDFAPI_FPDF_PAGEOBJ_H_ 8 #define CORE_INCLUDE_FPDFAPI_FPDF_PAGEOBJ_H_ 9 10 #include "core/include/fxge/fx_ge.h" 11 #include "fpdf_resource.h" 12 13 class CPDF_ClipPath; 14 class CPDF_ClipPathData; 15 class CPDF_ColorState; 16 class CPDF_ColorStateData; 17 class CPDF_ContentMark; 18 class CPDF_ContentMarkItem; 19 class CPDF_FormObject; 20 class CPDF_GeneralState; 21 class CPDF_GeneralStateData; 22 class CPDF_GraphicStates; 23 class CPDF_GraphState; 24 class CPDF_ImageObject; 25 class CPDF_PageObject; 26 class CPDF_Path; 27 class CPDF_PathObject; 28 class CPDF_ShadingObject; 29 class CPDF_TextObject; 30 class CPDF_TextState; 31 class CPDF_TextStateData; 32 class CPDF_TransferFunc; 33 34 typedef CFX_PathData CPDF_PathData; 35 36 class CPDF_Path : public CFX_CountRef<CFX_PathData> { 37 public: GetPointCount()38 int GetPointCount() { return m_pObject->m_PointCount; } 39 GetFlag(int index)40 int GetFlag(int index) { return m_pObject->m_pPoints[index].m_Flag; } 41 GetPointX(int index)42 FX_FLOAT GetPointX(int index) { return m_pObject->m_pPoints[index].m_PointX; } 43 GetPointY(int index)44 FX_FLOAT GetPointY(int index) { return m_pObject->m_pPoints[index].m_PointY; } 45 GetPoints()46 FX_PATHPOINT* GetPoints() { return m_pObject->m_pPoints; } 47 GetBoundingBox()48 CFX_FloatRect GetBoundingBox() const { return m_pObject->GetBoundingBox(); } 49 GetBoundingBox(FX_FLOAT line_width,FX_FLOAT miter_limit)50 CFX_FloatRect GetBoundingBox(FX_FLOAT line_width, 51 FX_FLOAT miter_limit) const { 52 return m_pObject->GetBoundingBox(line_width, miter_limit); 53 } 54 Transform(const CFX_Matrix * pMatrix)55 void Transform(const CFX_Matrix* pMatrix) { GetModify()->Transform(pMatrix); } 56 Append(CPDF_Path src,const CFX_Matrix * pMatrix)57 void Append(CPDF_Path src, const CFX_Matrix* pMatrix) { 58 m_pObject->Append(src.m_pObject, pMatrix); 59 } 60 AppendRect(FX_FLOAT left,FX_FLOAT bottom,FX_FLOAT right,FX_FLOAT top)61 void AppendRect(FX_FLOAT left, 62 FX_FLOAT bottom, 63 FX_FLOAT right, 64 FX_FLOAT top) { 65 m_pObject->AppendRect(left, bottom, right, top); 66 } 67 IsRect()68 FX_BOOL IsRect() const { return m_pObject->IsRect(); } 69 }; 70 class CPDF_ClipPathData { 71 public: 72 CPDF_ClipPathData(); 73 CPDF_ClipPathData(const CPDF_ClipPathData&); 74 ~CPDF_ClipPathData(); 75 76 void SetCount(int path_count, int text_count); 77 78 public: 79 int m_PathCount; 80 81 CPDF_Path* m_pPathList; 82 83 uint8_t* m_pTypeList; 84 85 int m_TextCount; 86 87 CPDF_TextObject** m_pTextList; 88 }; 89 90 class CPDF_ClipPath : public CFX_CountRef<CPDF_ClipPathData> { 91 public: GetPathCount()92 FX_DWORD GetPathCount() const { return m_pObject->m_PathCount; } 93 GetPath(int i)94 CPDF_Path GetPath(int i) const { return m_pObject->m_pPathList[i]; } 95 GetClipType(int i)96 int GetClipType(int i) const { return m_pObject->m_pTypeList[i]; } 97 GetTextCount()98 FX_DWORD GetTextCount() const { return m_pObject->m_TextCount; } 99 GetText(int i)100 CPDF_TextObject* GetText(int i) const { return m_pObject->m_pTextList[i]; } 101 102 CFX_FloatRect GetClipBox() const; 103 104 void AppendPath(CPDF_Path path, int type, FX_BOOL bAutoMerge); 105 106 void DeletePath(int layer_index); 107 108 void AppendTexts(CPDF_TextObject** pTexts, int count); 109 110 void Transform(const CFX_Matrix& matrix); 111 }; 112 class CPDF_ColorStateData { 113 public: CPDF_ColorStateData()114 CPDF_ColorStateData() : m_FillRGB(0), m_StrokeRGB(0) {} 115 116 CPDF_ColorStateData(const CPDF_ColorStateData& src); 117 118 void Default(); 119 120 CPDF_Color m_FillColor; 121 122 FX_DWORD m_FillRGB; 123 124 CPDF_Color m_StrokeColor; 125 126 FX_DWORD m_StrokeRGB; 127 }; 128 class CPDF_ColorState : public CFX_CountRef<CPDF_ColorStateData> { 129 public: GetFillColor()130 CPDF_Color* GetFillColor() const { 131 return m_pObject ? &m_pObject->m_FillColor : NULL; 132 } 133 GetStrokeColor()134 CPDF_Color* GetStrokeColor() const { 135 return m_pObject ? &m_pObject->m_StrokeColor : NULL; 136 } 137 138 void SetFillColor(CPDF_ColorSpace* pCS, FX_FLOAT* pValue, int nValues); 139 140 void SetStrokeColor(CPDF_ColorSpace* pCS, FX_FLOAT* pValue, int nValues); 141 142 void SetFillPattern(CPDF_Pattern* pattern, FX_FLOAT* pValue, int nValues); 143 144 void SetStrokePattern(CPDF_Pattern* pattern, FX_FLOAT* pValue, int nValues); 145 146 private: 147 void SetColor(CPDF_Color& color, 148 FX_DWORD& rgb, 149 CPDF_ColorSpace* pCS, 150 FX_FLOAT* pValue, 151 int nValues); 152 }; 153 typedef CFX_GraphStateData CPDF_GraphStateData; 154 class CPDF_GraphState : public CFX_CountRef<CFX_GraphStateData> { 155 public: 156 }; 157 class CPDF_TextStateData { 158 public: 159 CPDF_TextStateData(); 160 161 CPDF_TextStateData(const CPDF_TextStateData& src); 162 163 ~CPDF_TextStateData(); 164 165 CPDF_Font* m_pFont; 166 167 CPDF_Document* m_pDocument; 168 169 FX_FLOAT m_FontSize; 170 171 FX_FLOAT m_CharSpace; 172 173 FX_FLOAT m_WordSpace; 174 175 FX_FLOAT m_Matrix[4]; 176 177 int m_TextMode; 178 179 FX_FLOAT m_CTM[4]; 180 }; 181 class CPDF_TextState : public CFX_CountRef<CPDF_TextStateData> { 182 public: GetFont()183 CPDF_Font* GetFont() const { return m_pObject->m_pFont; } 184 185 void SetFont(CPDF_Font* pFont); 186 GetFontSize()187 FX_FLOAT GetFontSize() const { return m_pObject->m_FontSize; } 188 GetMatrix()189 FX_FLOAT* GetMatrix() const { return m_pObject->m_Matrix; } 190 191 FX_FLOAT GetFontSizeV() const; 192 193 FX_FLOAT GetFontSizeH() const; 194 195 FX_FLOAT GetBaselineAngle() const; 196 197 FX_FLOAT GetShearAngle() const; 198 }; 199 200 class CPDF_GeneralStateData { 201 public: 202 CPDF_GeneralStateData(); 203 204 CPDF_GeneralStateData(const CPDF_GeneralStateData& src); 205 ~CPDF_GeneralStateData(); 206 207 void SetBlendMode(const CFX_ByteStringC& blend_mode); 208 209 char m_BlendMode[16]; 210 211 int m_BlendType; 212 213 CPDF_Object* m_pSoftMask; 214 215 FX_FLOAT m_SMaskMatrix[6]; 216 217 FX_FLOAT m_StrokeAlpha; 218 219 FX_FLOAT m_FillAlpha; 220 221 CPDF_Object* m_pTR; 222 223 CPDF_TransferFunc* m_pTransferFunc; 224 225 CFX_Matrix m_Matrix; 226 227 int m_RenderIntent; 228 229 FX_BOOL m_StrokeAdjust; 230 231 FX_BOOL m_AlphaSource; 232 233 FX_BOOL m_TextKnockout; 234 235 FX_BOOL m_StrokeOP; 236 237 FX_BOOL m_FillOP; 238 239 int m_OPMode; 240 241 CPDF_Object* m_pBG; 242 243 CPDF_Object* m_pUCR; 244 245 CPDF_Object* m_pHT; 246 247 FX_FLOAT m_Flatness; 248 249 FX_FLOAT m_Smoothness; 250 }; 251 class CPDF_GeneralState : public CFX_CountRef<CPDF_GeneralStateData> { 252 public: 253 void SetRenderIntent(const CFX_ByteString& ri); 254 GetBlendType()255 int GetBlendType() const { 256 return m_pObject ? m_pObject->m_BlendType : FXDIB_BLEND_NORMAL; 257 } 258 GetAlpha(FX_BOOL bStroke)259 int GetAlpha(FX_BOOL bStroke) const { 260 return m_pObject ? FXSYS_round((bStroke ? m_pObject->m_StrokeAlpha 261 : m_pObject->m_FillAlpha) * 262 255) 263 : 255; 264 } 265 }; 266 class CPDF_ContentMarkItem { 267 public: 268 typedef enum { None, PropertiesDict, DirectDict, MCID } ParamType; 269 270 CPDF_ContentMarkItem(); 271 272 CPDF_ContentMarkItem(const CPDF_ContentMarkItem& src); 273 274 ~CPDF_ContentMarkItem(); 275 GetName()276 inline const CFX_ByteString& GetName() const { return m_MarkName; } 277 GetParamType()278 inline ParamType GetParamType() const { return m_ParamType; } 279 GetParam()280 inline void* GetParam() const { return m_pParam; } 281 282 inline FX_BOOL HasMCID() const; 283 SetName(const CFX_ByteString & name)284 inline void SetName(const CFX_ByteString& name) { m_MarkName = name; } 285 SetParam(ParamType type,void * param)286 inline void SetParam(ParamType type, void* param) { 287 m_ParamType = type; 288 m_pParam = param; 289 } 290 291 private: 292 CFX_ByteString m_MarkName; 293 294 ParamType m_ParamType; 295 296 void* m_pParam; 297 }; 298 class CPDF_ContentMarkData { 299 public: CPDF_ContentMarkData()300 CPDF_ContentMarkData() {} 301 302 CPDF_ContentMarkData(const CPDF_ContentMarkData& src); 303 CountItems()304 inline int CountItems() const { return m_Marks.GetSize(); } 305 GetItem(int index)306 inline CPDF_ContentMarkItem& GetItem(int index) const { 307 return m_Marks[index]; 308 } 309 310 int GetMCID() const; 311 312 void AddMark(const CFX_ByteString& name, 313 CPDF_Dictionary* pDict, 314 FX_BOOL bDictNeedClone); 315 316 void DeleteLastMark(); 317 318 private: 319 CFX_ObjectArray<CPDF_ContentMarkItem> m_Marks; 320 }; 321 class CPDF_ContentMark : public CFX_CountRef<CPDF_ContentMarkData> { 322 public: GetMCID()323 int GetMCID() const { return m_pObject ? m_pObject->GetMCID() : -1; } 324 325 FX_BOOL HasMark(const CFX_ByteStringC& mark) const; 326 327 FX_BOOL LookupMark(const CFX_ByteStringC& mark, 328 CPDF_Dictionary*& pDict) const; 329 }; 330 331 #define PDFPAGE_TEXT 1 332 #define PDFPAGE_PATH 2 333 #define PDFPAGE_IMAGE 3 334 #define PDFPAGE_SHADING 4 335 #define PDFPAGE_FORM 5 336 337 class CPDF_GraphicStates { 338 public: 339 void CopyStates(const CPDF_GraphicStates& src); 340 341 void DefaultStates(); 342 343 CPDF_ClipPath m_ClipPath; 344 345 CPDF_GraphState m_GraphState; 346 347 CPDF_ColorState m_ColorState; 348 349 CPDF_TextState m_TextState; 350 351 CPDF_GeneralState m_GeneralState; 352 }; 353 354 class CPDF_PageObject : public CPDF_GraphicStates { 355 public: 356 static CPDF_PageObject* Create(int type); 357 virtual ~CPDF_PageObject(); 358 359 CPDF_PageObject* Clone() const; 360 361 void Copy(const CPDF_PageObject* pSrcObject); 362 363 virtual void Transform(const CFX_Matrix& matrix) = 0; 364 365 void RemoveClipPath(); 366 367 void AppendClipPath(CPDF_Path path, int type, FX_BOOL bAutoMerge); 368 369 void CopyClipPath(CPDF_PageObject* pObj); 370 371 void TransformClipPath(CFX_Matrix& matrix); 372 373 void TransformGeneralState(CFX_Matrix& matrix); 374 SetColorState(CPDF_ColorState state)375 void SetColorState(CPDF_ColorState state) { m_ColorState = state; } 376 377 FX_RECT GetBBox(const CFX_Matrix* pMatrix) const; 378 379 int m_Type; 380 381 FX_FLOAT m_Left; 382 383 FX_FLOAT m_Right; 384 385 FX_FLOAT m_Top; 386 387 FX_FLOAT m_Bottom; 388 389 CPDF_ContentMark m_ContentMark; 390 391 protected: 392 virtual void CopyData(const CPDF_PageObject* pSrcObject) = 0; 393 394 void RecalcBBox(); 395 CPDF_PageObject()396 CPDF_PageObject() {} 397 }; 398 399 struct CPDF_TextObjectItem { 400 FX_DWORD m_CharCode; 401 FX_FLOAT m_OriginX; 402 FX_FLOAT m_OriginY; 403 }; 404 405 class CPDF_TextObject : public CPDF_PageObject { 406 public: 407 CPDF_TextObject(); 408 ~CPDF_TextObject() override; 409 CountItems()410 int CountItems() const { return m_nChars; } 411 412 void GetItemInfo(int index, CPDF_TextObjectItem* pInfo) const; 413 414 int CountChars() const; 415 416 void GetCharInfo(int index, FX_DWORD& charcode, FX_FLOAT& kerning) const; 417 void GetCharInfo(int index, CPDF_TextObjectItem* pInfo) const; 418 419 void GetCharRect(int index, CFX_FloatRect& rect) const; 420 421 FX_FLOAT GetCharWidth(FX_DWORD charcode) const; 422 FX_FLOAT GetSpaceCharWidth() const; 423 GetPosX()424 FX_FLOAT GetPosX() const { return m_PosX; } 425 GetPosY()426 FX_FLOAT GetPosY() const { return m_PosY; } 427 428 void GetTextMatrix(CFX_Matrix* pMatrix) const; 429 GetFont()430 CPDF_Font* GetFont() const { return m_TextState.GetFont(); } 431 GetFontSize()432 FX_FLOAT GetFontSize() const { return m_TextState.GetFontSize(); } 433 434 void SetEmpty(); 435 436 void SetText(const CFX_ByteString& text); 437 438 void SetText(CFX_ByteString* pStrs, FX_FLOAT* pKerning, int nSegs); 439 440 void SetText(int nChars, FX_DWORD* pCharCodes, FX_FLOAT* pKernings); 441 442 void SetPosition(FX_FLOAT x, FX_FLOAT y); 443 444 void SetTextState(CPDF_TextState TextState); 445 446 // CPDF_PageObject: 447 void Transform(const CFX_Matrix& matrix) override; 448 449 void CalcCharPos(FX_FLOAT* pPosArray) const; 450 451 void SetData(int nChars, 452 FX_DWORD* pCharCodes, 453 FX_FLOAT* pCharPos, 454 FX_FLOAT x, 455 FX_FLOAT y); 456 GetData(int & nChars,FX_DWORD * & pCharCodes,FX_FLOAT * & pCharPos)457 void GetData(int& nChars, FX_DWORD*& pCharCodes, FX_FLOAT*& pCharPos) { 458 nChars = m_nChars; 459 pCharCodes = m_pCharCodes; 460 pCharPos = m_pCharPos; 461 } 462 RecalcPositionData()463 void RecalcPositionData() { CalcPositionData(nullptr, nullptr, 1); } 464 465 protected: 466 friend class CPDF_RenderStatus; 467 friend class CPDF_StreamContentParser; 468 friend class CPDF_TextRenderer; 469 friend class CTextPage; 470 471 // CPDF_PageObject: 472 void CopyData(const CPDF_PageObject* pSrcObject) override; 473 474 void SetSegments(const CFX_ByteString* pStrs, FX_FLOAT* pKerning, int nSegs); 475 476 void CalcPositionData(FX_FLOAT* pTextAdvanceX, 477 FX_FLOAT* pTextAdvanceY, 478 FX_FLOAT horz_scale, 479 int level = 0); 480 481 FX_FLOAT m_PosX; 482 FX_FLOAT m_PosY; 483 484 int m_nChars; 485 486 FX_DWORD* m_pCharCodes; 487 488 FX_FLOAT* m_pCharPos; 489 }; 490 491 class CPDF_PathObject : public CPDF_PageObject { 492 public: CPDF_PathObject()493 CPDF_PathObject() { m_Type = PDFPAGE_PATH; } ~CPDF_PathObject()494 ~CPDF_PathObject() override {} 495 496 void Transform(const CFX_Matrix& maxtrix) override; 497 498 void SetGraphState(CPDF_GraphState GraphState); 499 500 void CalcBoundingBox(); 501 502 CPDF_Path m_Path; 503 504 int m_FillType; 505 506 FX_BOOL m_bStroke; 507 508 CFX_Matrix m_Matrix; 509 510 protected: 511 void CopyData(const CPDF_PageObject* pSrcObject) override; 512 }; 513 514 class CPDF_ImageObject : public CPDF_PageObject { 515 public: 516 CPDF_ImageObject(); 517 ~CPDF_ImageObject() override; 518 519 void Transform(const CFX_Matrix& matrix) override; 520 521 CPDF_Image* m_pImage; 522 523 CFX_Matrix m_Matrix; 524 525 void CalcBoundingBox(); 526 527 private: 528 void CopyData(const CPDF_PageObject* pSrcObject) override; 529 }; 530 531 class CPDF_ShadingObject : public CPDF_PageObject { 532 public: 533 CPDF_ShadingObject(); 534 ~CPDF_ShadingObject() override; 535 536 CPDF_ShadingPattern* m_pShading; 537 538 CFX_Matrix m_Matrix; 539 540 void Transform(const CFX_Matrix& matrix) override; 541 542 void CalcBoundingBox(); 543 544 protected: 545 void CopyData(const CPDF_PageObject* pSrcObject) override; 546 }; 547 548 class CPDF_FormObject : public CPDF_PageObject { 549 public: CPDF_FormObject()550 CPDF_FormObject() { 551 m_Type = PDFPAGE_FORM; 552 m_pForm = NULL; 553 } 554 ~CPDF_FormObject() override; 555 556 void Transform(const CFX_Matrix& matrix) override; 557 558 CPDF_Form* m_pForm; 559 560 CFX_Matrix m_FormMatrix; 561 562 void CalcBoundingBox(); 563 564 protected: 565 void CopyData(const CPDF_PageObject* pSrcObject) override; 566 }; 567 568 #endif // CORE_INCLUDE_FPDFAPI_FPDF_PAGEOBJ_H_ 569