From b048f791a15f2da781a01eba5b09eb9d389f9c11 Mon Sep 17 00:00:00 2001 From: Nico Weber Date: Tue, 4 Aug 2015 12:19:10 -0700 Subject: clang-format all pdfium code. No behavior change. Generated by: find . -name '*.cpp' -o -name '*.h' | \ grep -E -v 'third_party|thirdparties|lpng_v163' | \ xargs ../../buildtools/mac/clang-format -i See thread "tabs vs spaces" on pdfium@googlegroups.com for discussion. BUG=none R=tsepez@chromium.org Review URL: https://codereview.chromium.org/1265503005 . --- core/src/fpdfapi/fpdf_page/fpdf_page.cpp | 1892 ++++++------ core/src/fpdfapi/fpdf_page/fpdf_page_colors.cpp | 2799 +++++++++--------- core/src/fpdfapi/fpdf_page/fpdf_page_doc.cpp | 1036 ++++--- core/src/fpdfapi/fpdf_page/fpdf_page_func.cpp | 1694 +++++------ .../fpdfapi/fpdf_page/fpdf_page_graph_state.cpp | 1335 +++++---- core/src/fpdfapi/fpdf_page/fpdf_page_image.cpp | 163 +- core/src/fpdfapi/fpdf_page/fpdf_page_parser.cpp | 3007 ++++++++++---------- .../src/fpdfapi/fpdf_page/fpdf_page_parser_old.cpp | 2124 +++++++------- core/src/fpdfapi/fpdf_page/fpdf_page_path.cpp | 72 +- core/src/fpdfapi/fpdf_page/fpdf_page_pattern.cpp | 515 ++-- core/src/fpdfapi/fpdf_page/pageint.h | 947 +++--- 11 files changed, 7852 insertions(+), 7732 deletions(-) (limited to 'core/src/fpdfapi/fpdf_page') diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page.cpp index f404352318..0421aba2d5 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page.cpp @@ -7,92 +7,82 @@ #include "../../../include/fpdfapi/fpdf_page.h" #include "../../../include/fpdfapi/fpdf_module.h" #include "pageint.h" -CPDF_PageObject* CPDF_PageObject::Create(int type) -{ - switch (type) { - case PDFPAGE_TEXT: - return new CPDF_TextObject; - case PDFPAGE_IMAGE: - return new CPDF_ImageObject; - case PDFPAGE_PATH: - return new CPDF_PathObject; - case PDFPAGE_SHADING: - return new CPDF_ShadingObject; - case PDFPAGE_FORM: - return new CPDF_FormObject; - } - return NULL; -} -CPDF_PageObject::~CPDF_PageObject() -{ -} -CPDF_PageObject* CPDF_PageObject::Clone() const -{ - CPDF_PageObject* pObj = Create(m_Type); - pObj->Copy(this); - return pObj; -} -void CPDF_PageObject::Copy(const CPDF_PageObject* pSrc) -{ - if (m_Type != pSrc->m_Type) { - return; - } - CopyData(pSrc); - CopyStates(*pSrc); - m_Left = pSrc->m_Left; - m_Right = pSrc->m_Right; - m_Top = pSrc->m_Top; - m_Bottom = pSrc->m_Bottom; -} -void CPDF_PageObject::AppendClipPath(CPDF_Path path, int type, FX_BOOL bAutoMerge) -{ - m_ClipPath.AppendPath(path, type, bAutoMerge); -} -void CPDF_PageObject::CopyClipPath(CPDF_PageObject* pObj) -{ - m_ClipPath = pObj->m_ClipPath; -} -void CPDF_PageObject::RemoveClipPath() -{ - m_ClipPath.SetNull(); -} -void CPDF_PageObject::RecalcBBox() -{ - switch (m_Type) { - case PDFPAGE_TEXT: - ((CPDF_TextObject*)this)->RecalcPositionData(); - break; - case PDFPAGE_PATH: - ((CPDF_PathObject*)this)->CalcBoundingBox(); - break; - case PDFPAGE_SHADING: - ((CPDF_ShadingObject*)this)->CalcBoundingBox(); - break; - } -} -void CPDF_PageObject::TransformClipPath(CFX_AffineMatrix& matrix) -{ - if (m_ClipPath.IsNull()) { - return; - } - m_ClipPath.GetModify(); - m_ClipPath.Transform(matrix); -} -void CPDF_PageObject::TransformGeneralState(CFX_AffineMatrix& matrix) -{ - if(m_GeneralState.IsNull()) { - return; - } - CPDF_GeneralStateData* pGS = m_GeneralState.GetModify(); - pGS->m_Matrix.Concat(matrix); -} -FX_RECT CPDF_PageObject::GetBBox(const CFX_AffineMatrix* pMatrix) const -{ - CFX_FloatRect rect(m_Left, m_Bottom, m_Right, m_Top); - if (pMatrix) { - pMatrix->TransformRect(rect); - } - return rect.GetOutterRect(); +CPDF_PageObject* CPDF_PageObject::Create(int type) { + switch (type) { + case PDFPAGE_TEXT: + return new CPDF_TextObject; + case PDFPAGE_IMAGE: + return new CPDF_ImageObject; + case PDFPAGE_PATH: + return new CPDF_PathObject; + case PDFPAGE_SHADING: + return new CPDF_ShadingObject; + case PDFPAGE_FORM: + return new CPDF_FormObject; + } + return NULL; +} +CPDF_PageObject::~CPDF_PageObject() {} +CPDF_PageObject* CPDF_PageObject::Clone() const { + CPDF_PageObject* pObj = Create(m_Type); + pObj->Copy(this); + return pObj; +} +void CPDF_PageObject::Copy(const CPDF_PageObject* pSrc) { + if (m_Type != pSrc->m_Type) { + return; + } + CopyData(pSrc); + CopyStates(*pSrc); + m_Left = pSrc->m_Left; + m_Right = pSrc->m_Right; + m_Top = pSrc->m_Top; + m_Bottom = pSrc->m_Bottom; +} +void CPDF_PageObject::AppendClipPath(CPDF_Path path, + int type, + FX_BOOL bAutoMerge) { + m_ClipPath.AppendPath(path, type, bAutoMerge); +} +void CPDF_PageObject::CopyClipPath(CPDF_PageObject* pObj) { + m_ClipPath = pObj->m_ClipPath; +} +void CPDF_PageObject::RemoveClipPath() { + m_ClipPath.SetNull(); +} +void CPDF_PageObject::RecalcBBox() { + switch (m_Type) { + case PDFPAGE_TEXT: + ((CPDF_TextObject*)this)->RecalcPositionData(); + break; + case PDFPAGE_PATH: + ((CPDF_PathObject*)this)->CalcBoundingBox(); + break; + case PDFPAGE_SHADING: + ((CPDF_ShadingObject*)this)->CalcBoundingBox(); + break; + } +} +void CPDF_PageObject::TransformClipPath(CFX_AffineMatrix& matrix) { + if (m_ClipPath.IsNull()) { + return; + } + m_ClipPath.GetModify(); + m_ClipPath.Transform(matrix); +} +void CPDF_PageObject::TransformGeneralState(CFX_AffineMatrix& matrix) { + if (m_GeneralState.IsNull()) { + return; + } + CPDF_GeneralStateData* pGS = m_GeneralState.GetModify(); + pGS->m_Matrix.Concat(matrix); +} +FX_RECT CPDF_PageObject::GetBBox(const CFX_AffineMatrix* pMatrix) const { + CFX_FloatRect rect(m_Left, m_Bottom, m_Right, m_Top); + if (pMatrix) { + pMatrix->TransformRect(rect); + } + return rect.GetOutterRect(); } CPDF_TextObject::CPDF_TextObject() @@ -100,625 +90,587 @@ CPDF_TextObject::CPDF_TextObject() m_PosY(0), m_nChars(0), m_pCharCodes(nullptr), - m_pCharPos(nullptr) -{ - m_Type = PDFPAGE_TEXT; + m_pCharPos(nullptr) { + m_Type = PDFPAGE_TEXT; } -CPDF_TextObject::~CPDF_TextObject() -{ - if (m_nChars > 1 && m_pCharCodes) { - FX_Free(m_pCharCodes); - } - if (m_pCharPos) { - FX_Free(m_pCharPos); - } +CPDF_TextObject::~CPDF_TextObject() { + if (m_nChars > 1 && m_pCharCodes) { + FX_Free(m_pCharCodes); + } + if (m_pCharPos) { + FX_Free(m_pCharPos); + } } -void CPDF_TextObject::GetItemInfo(int index, CPDF_TextObjectItem* pInfo) const -{ - pInfo->m_CharCode = - m_nChars == 1 ? (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[index]; - pInfo->m_OriginX = index ? m_pCharPos[index - 1] : 0; - pInfo->m_OriginY = 0; - if (pInfo->m_CharCode == -1) { - return; - } - CPDF_Font* pFont = m_TextState.GetFont(); - if (pFont->GetFontType() != PDFFONT_CIDFONT) { - return; - } - if (!((CPDF_CIDFont*)pFont)->IsVertWriting()) { - return; - } - FX_WORD CID = ((CPDF_CIDFont*)pFont)->CIDFromCharCode(pInfo->m_CharCode); - pInfo->m_OriginY = pInfo->m_OriginX; - pInfo->m_OriginX = 0; - short vx, vy; - ((CPDF_CIDFont*)pFont)->GetVertOrigin(CID, vx, vy); - FX_FLOAT fontsize = m_TextState.GetFontSize(); - pInfo->m_OriginX -= fontsize * vx / 1000; - pInfo->m_OriginY -= fontsize * vy / 1000; +void CPDF_TextObject::GetItemInfo(int index, CPDF_TextObjectItem* pInfo) const { + pInfo->m_CharCode = + m_nChars == 1 ? (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[index]; + pInfo->m_OriginX = index ? m_pCharPos[index - 1] : 0; + pInfo->m_OriginY = 0; + if (pInfo->m_CharCode == -1) { + return; + } + CPDF_Font* pFont = m_TextState.GetFont(); + if (pFont->GetFontType() != PDFFONT_CIDFONT) { + return; + } + if (!((CPDF_CIDFont*)pFont)->IsVertWriting()) { + return; + } + FX_WORD CID = ((CPDF_CIDFont*)pFont)->CIDFromCharCode(pInfo->m_CharCode); + pInfo->m_OriginY = pInfo->m_OriginX; + pInfo->m_OriginX = 0; + short vx, vy; + ((CPDF_CIDFont*)pFont)->GetVertOrigin(CID, vx, vy); + FX_FLOAT fontsize = m_TextState.GetFontSize(); + pInfo->m_OriginX -= fontsize * vx / 1000; + pInfo->m_OriginY -= fontsize * vy / 1000; } -int CPDF_TextObject::CountChars() const -{ - if (m_nChars == 1) { - return 1; +int CPDF_TextObject::CountChars() const { + if (m_nChars == 1) { + return 1; + } + int count = 0; + for (int i = 0; i < m_nChars; ++i) + if (m_pCharCodes[i] != (FX_DWORD)-1) { + ++count; } - int count = 0; - for (int i = 0; i < m_nChars; ++i) - if (m_pCharCodes[i] != (FX_DWORD) - 1) { - ++count; - } - return count; + return count; } void CPDF_TextObject::GetCharInfo(int index, FX_DWORD& charcode, - FX_FLOAT& kerning) const -{ - if (m_nChars == 1) { - charcode = (FX_DWORD)(uintptr_t)m_pCharCodes; - kerning = 0; - return; - } - int count = 0; - for (int i = 0; i < m_nChars; ++i) { - if (m_pCharCodes[i] != (FX_DWORD) - 1) { - if (count == index) { - charcode = m_pCharCodes[i]; - if (i == m_nChars - 1 || - m_pCharCodes[i + 1] != (FX_DWORD) - 1) { - kerning = 0; - } else { - kerning = m_pCharPos[i]; - } - return; - } - ++count; + FX_FLOAT& kerning) const { + if (m_nChars == 1) { + charcode = (FX_DWORD)(uintptr_t)m_pCharCodes; + kerning = 0; + return; + } + int count = 0; + for (int i = 0; i < m_nChars; ++i) { + if (m_pCharCodes[i] != (FX_DWORD)-1) { + if (count == index) { + charcode = m_pCharCodes[i]; + if (i == m_nChars - 1 || m_pCharCodes[i + 1] != (FX_DWORD)-1) { + kerning = 0; + } else { + kerning = m_pCharPos[i]; } + return; + } + ++count; } + } } -void CPDF_TextObject::GetCharInfo(int index, CPDF_TextObjectItem* pInfo) const -{ - if (m_nChars == 1) { - GetItemInfo(0, pInfo); - return; - } - int count = 0; - for (int i = 0; i < m_nChars; ++i) { - FX_DWORD charcode = m_pCharCodes[i]; - if (charcode == (FX_DWORD) - 1) { - continue; - } - if (count == index) { - GetItemInfo(i, pInfo); - break; - } - ++count; - } +void CPDF_TextObject::GetCharInfo(int index, CPDF_TextObjectItem* pInfo) const { + if (m_nChars == 1) { + GetItemInfo(0, pInfo); + return; + } + int count = 0; + for (int i = 0; i < m_nChars; ++i) { + FX_DWORD charcode = m_pCharCodes[i]; + if (charcode == (FX_DWORD)-1) { + continue; + } + if (count == index) { + GetItemInfo(i, pInfo); + break; + } + ++count; + } } -void CPDF_TextObject::CopyData(const CPDF_PageObject* pSrc) -{ - const CPDF_TextObject* pSrcObj = (const CPDF_TextObject*)pSrc; - if (m_nChars > 1 && m_pCharCodes) { - FX_Free(m_pCharCodes); - m_pCharCodes = nullptr; +void CPDF_TextObject::CopyData(const CPDF_PageObject* pSrc) { + const CPDF_TextObject* pSrcObj = (const CPDF_TextObject*)pSrc; + if (m_nChars > 1 && m_pCharCodes) { + FX_Free(m_pCharCodes); + m_pCharCodes = nullptr; + } + if (m_pCharPos) { + FX_Free(m_pCharPos); + m_pCharPos = nullptr; + } + m_nChars = pSrcObj->m_nChars; + if (m_nChars > 1) { + m_pCharCodes = FX_Alloc(FX_DWORD, m_nChars); + m_pCharPos = FX_Alloc(FX_FLOAT, m_nChars - 1); + for (int i = 0; i < m_nChars; ++i) { + m_pCharCodes[i] = pSrcObj->m_pCharCodes[i]; } - if (m_pCharPos) { - FX_Free(m_pCharPos); - m_pCharPos = nullptr; + for (int i = 0; i < m_nChars - 1; ++i) { + m_pCharPos[i] = pSrcObj->m_pCharPos[i]; } - m_nChars = pSrcObj->m_nChars; - if (m_nChars > 1) { - m_pCharCodes = FX_Alloc(FX_DWORD, m_nChars); - m_pCharPos = FX_Alloc(FX_FLOAT, m_nChars - 1); - for (int i = 0; i < m_nChars; ++i) { - m_pCharCodes[i] = pSrcObj->m_pCharCodes[i]; - } - for (int i = 0; i < m_nChars - 1; ++i) { - m_pCharPos[i] = pSrcObj->m_pCharPos[i]; - } - } else { - m_pCharCodes = pSrcObj->m_pCharCodes; - } - m_PosX = pSrcObj->m_PosX; - m_PosY = pSrcObj->m_PosY; + } else { + m_pCharCodes = pSrcObj->m_pCharCodes; + } + m_PosX = pSrcObj->m_PosX; + m_PosY = pSrcObj->m_PosY; } -void CPDF_TextObject::GetTextMatrix(CFX_AffineMatrix* pMatrix) const -{ - FX_FLOAT* pTextMatrix = m_TextState.GetMatrix(); - pMatrix->Set(pTextMatrix[0], - pTextMatrix[2], - pTextMatrix[1], - pTextMatrix[3], - m_PosX, - m_PosY); +void CPDF_TextObject::GetTextMatrix(CFX_AffineMatrix* pMatrix) const { + FX_FLOAT* pTextMatrix = m_TextState.GetMatrix(); + pMatrix->Set(pTextMatrix[0], pTextMatrix[2], pTextMatrix[1], pTextMatrix[3], + m_PosX, m_PosY); } void CPDF_TextObject::SetSegments(const CFX_ByteString* pStrs, FX_FLOAT* pKerning, - int nsegs) -{ - if (m_nChars > 1 && m_pCharCodes) { - FX_Free(m_pCharCodes); - m_pCharCodes = nullptr; - } - if (m_pCharPos) { - FX_Free(m_pCharPos); - m_pCharPos = nullptr; - } - CPDF_Font* pFont = m_TextState.GetFont(); - m_nChars = 0; + int nsegs) { + if (m_nChars > 1 && m_pCharCodes) { + FX_Free(m_pCharCodes); + m_pCharCodes = nullptr; + } + if (m_pCharPos) { + FX_Free(m_pCharPos); + m_pCharPos = nullptr; + } + CPDF_Font* pFont = m_TextState.GetFont(); + m_nChars = 0; + for (int i = 0; i < nsegs; ++i) { + m_nChars += pFont->CountChar(pStrs[i], pStrs[i].GetLength()); + } + m_nChars += nsegs - 1; + if (m_nChars > 1) { + m_pCharCodes = FX_Alloc(FX_DWORD, m_nChars); + m_pCharPos = FX_Alloc(FX_FLOAT, m_nChars - 1); + int index = 0; for (int i = 0; i < nsegs; ++i) { - m_nChars += pFont->CountChar(pStrs[i], pStrs[i].GetLength()); - } - m_nChars += nsegs - 1; - if (m_nChars > 1) { - m_pCharCodes = FX_Alloc(FX_DWORD, m_nChars); - m_pCharPos = FX_Alloc(FX_FLOAT, m_nChars - 1); - int index = 0; - for (int i = 0; i < nsegs; ++i) { - const FX_CHAR* segment = pStrs[i]; - int offset = 0, len = pStrs[i].GetLength(); - while (offset < len) { - m_pCharCodes[index++] = - pFont->GetNextChar(segment, len, offset); - } - if (i != nsegs - 1) { - m_pCharPos[index - 1] = pKerning[i]; - m_pCharCodes[index++] = (FX_DWORD) - 1; - } - } - } else { - int offset = 0; - m_pCharCodes = - (FX_DWORD*)(uintptr_t)pFont->GetNextChar(pStrs[0], - pStrs[0].GetLength(), - offset); - } + const FX_CHAR* segment = pStrs[i]; + int offset = 0, len = pStrs[i].GetLength(); + while (offset < len) { + m_pCharCodes[index++] = pFont->GetNextChar(segment, len, offset); + } + if (i != nsegs - 1) { + m_pCharPos[index - 1] = pKerning[i]; + m_pCharCodes[index++] = (FX_DWORD)-1; + } + } + } else { + int offset = 0; + m_pCharCodes = (FX_DWORD*)(uintptr_t)pFont->GetNextChar( + pStrs[0], pStrs[0].GetLength(), offset); + } } -void CPDF_TextObject::SetText(const CFX_ByteString& str) -{ - SetSegments(&str, nullptr, 1); - RecalcPositionData(); +void CPDF_TextObject::SetText(const CFX_ByteString& str) { + SetSegments(&str, nullptr, 1); + RecalcPositionData(); } -void CPDF_TextObject::SetEmpty() -{ - if (m_nChars > 1 && m_pCharCodes) { - FX_Free(m_pCharCodes); - } - if (m_nChars > 1 && m_pCharPos) { - FX_Free(m_pCharPos); - } - m_nChars = 0; - m_pCharCodes = nullptr; - m_pCharPos = nullptr; - m_Left = m_Right = m_PosX; - m_Top = m_Bottom = m_PosY; +void CPDF_TextObject::SetEmpty() { + if (m_nChars > 1 && m_pCharCodes) { + FX_Free(m_pCharCodes); + } + if (m_nChars > 1 && m_pCharPos) { + FX_Free(m_pCharPos); + } + m_nChars = 0; + m_pCharCodes = nullptr; + m_pCharPos = nullptr; + m_Left = m_Right = m_PosX; + m_Top = m_Bottom = m_PosY; } void CPDF_TextObject::SetText(CFX_ByteString* pStrs, FX_FLOAT* pKerning, - int nSegs) -{ - SetSegments(pStrs, pKerning, nSegs); - RecalcPositionData(); + int nSegs) { + SetSegments(pStrs, pKerning, nSegs); + RecalcPositionData(); } void CPDF_TextObject::SetText(int nChars, FX_DWORD* pCharCodes, - FX_FLOAT* pKernings) -{ - if (m_nChars > 1 && m_pCharCodes) { - FX_Free(m_pCharCodes); - m_pCharCodes = nullptr; - } - if (m_pCharPos) { - FX_Free(m_pCharPos); - m_pCharPos = nullptr; - } - int nKernings = 0; - int i; - for (i = 0; i < nChars - 1; ++i) { - if (pKernings[i] != 0) { - ++nKernings; - } - } - m_nChars = nChars + nKernings; - if (m_nChars > 1) { - m_pCharCodes = FX_Alloc(FX_DWORD, m_nChars); - m_pCharPos = FX_Alloc(FX_FLOAT, m_nChars - 1); - for (int i = 0, index = 0; i < nChars; ++i) { - m_pCharCodes[index++] = pCharCodes[i]; - if (pKernings[i] != 0 && i != nChars - 1) { - m_pCharCodes[index] = (FX_DWORD) - 1; - m_pCharPos[index - 1] = pKernings[i]; - ++index; - } - } - } else { - m_pCharCodes = (FX_DWORD*)(uintptr_t)pCharCodes[0]; - } - RecalcPositionData(); + FX_FLOAT* pKernings) { + if (m_nChars > 1 && m_pCharCodes) { + FX_Free(m_pCharCodes); + m_pCharCodes = nullptr; + } + if (m_pCharPos) { + FX_Free(m_pCharPos); + m_pCharPos = nullptr; + } + int nKernings = 0; + int i; + for (i = 0; i < nChars - 1; ++i) { + if (pKernings[i] != 0) { + ++nKernings; + } + } + m_nChars = nChars + nKernings; + if (m_nChars > 1) { + m_pCharCodes = FX_Alloc(FX_DWORD, m_nChars); + m_pCharPos = FX_Alloc(FX_FLOAT, m_nChars - 1); + for (int i = 0, index = 0; i < nChars; ++i) { + m_pCharCodes[index++] = pCharCodes[i]; + if (pKernings[i] != 0 && i != nChars - 1) { + m_pCharCodes[index] = (FX_DWORD)-1; + m_pCharPos[index - 1] = pKernings[i]; + ++index; + } + } + } else { + m_pCharCodes = (FX_DWORD*)(uintptr_t)pCharCodes[0]; + } + RecalcPositionData(); } -FX_FLOAT CPDF_TextObject::GetCharWidth(FX_DWORD charcode) const -{ - FX_FLOAT fontsize = m_TextState.GetFontSize() / 1000; - CPDF_Font* pFont = m_TextState.GetFont(); - FX_BOOL bVertWriting = FALSE; - CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); - if (pCIDFont) { - bVertWriting = pCIDFont->IsVertWriting(); - } - if (!bVertWriting) - return pFont->GetCharWidthF(charcode, 0) * fontsize; +FX_FLOAT CPDF_TextObject::GetCharWidth(FX_DWORD charcode) const { + FX_FLOAT fontsize = m_TextState.GetFontSize() / 1000; + CPDF_Font* pFont = m_TextState.GetFont(); + FX_BOOL bVertWriting = FALSE; + CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); + if (pCIDFont) { + bVertWriting = pCIDFont->IsVertWriting(); + } + if (!bVertWriting) + return pFont->GetCharWidthF(charcode, 0) * fontsize; - FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); - return pCIDFont->GetVertWidth(CID) * fontsize; + FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); + return pCIDFont->GetVertWidth(CID) * fontsize; } -FX_FLOAT CPDF_TextObject::GetSpaceCharWidth() const -{ - CPDF_Font* pFont = m_TextState.GetFont(); - FX_DWORD charCode = m_TextState.GetFont()->CharCodeFromUnicode(32); - if (charCode != (FX_DWORD) - 1) { - return GetCharWidth(charCode); - } - FX_FLOAT fontSize = m_TextState.GetFontSize() / 4000.0f; - FX_BOOL bVertWriting = FALSE; - CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); - if (pCIDFont) { - bVertWriting = pCIDFont->IsVertWriting(); - } - FX_RECT fontRect; - pFont->GetFontBBox(fontRect); - fontSize *= bVertWriting ? - (FX_FLOAT)fontRect.Height() : (FX_FLOAT)fontRect.Width(); - return fontSize; +FX_FLOAT CPDF_TextObject::GetSpaceCharWidth() const { + CPDF_Font* pFont = m_TextState.GetFont(); + FX_DWORD charCode = m_TextState.GetFont()->CharCodeFromUnicode(32); + if (charCode != (FX_DWORD)-1) { + return GetCharWidth(charCode); + } + FX_FLOAT fontSize = m_TextState.GetFontSize() / 4000.0f; + FX_BOOL bVertWriting = FALSE; + CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); + if (pCIDFont) { + bVertWriting = pCIDFont->IsVertWriting(); + } + FX_RECT fontRect; + pFont->GetFontBBox(fontRect); + fontSize *= + bVertWriting ? (FX_FLOAT)fontRect.Height() : (FX_FLOAT)fontRect.Width(); + return fontSize; } -void CPDF_TextObject::GetCharRect(int index, CFX_FloatRect& rect) const -{ - CPDF_Font* pFont = m_TextState.GetFont(); - FX_BOOL bVertWriting = FALSE; - CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); - if (pCIDFont) { - bVertWriting = pCIDFont->IsVertWriting(); - } - FX_FLOAT fontsize = m_TextState.GetFontSize() / 1000; - int count = 0; - for (int i = 0; i < m_nChars; ++i) { - FX_DWORD charcode = m_nChars == 1 ? - (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[i]; - if (charcode == (FX_DWORD) - 1) { - continue; - } - if (count != index) { - ++count; - continue; - } - FX_FLOAT curpos = i > 0 ? m_pCharPos[i - 1] : 0; - FX_RECT char_rect; - pFont->GetCharBBox(charcode, char_rect, 0); - if (!bVertWriting) { - rect.left = curpos + char_rect.left * fontsize; - rect.right = curpos + char_rect.right * fontsize; - rect.top = char_rect.top * fontsize; - rect.bottom = char_rect.bottom * fontsize; - } else { - FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); - short vx, vy; - pCIDFont->GetVertOrigin(CID, vx, vy); - char_rect.left -= vx; - char_rect.right -= vx; - char_rect.top -= vy; - char_rect.bottom -= vy; - rect.left = char_rect.left * fontsize; - rect.right = char_rect.right * fontsize; - rect.top = curpos + char_rect.top * fontsize; - rect.bottom = curpos + char_rect.bottom * fontsize; - } - return; - } +void CPDF_TextObject::GetCharRect(int index, CFX_FloatRect& rect) const { + CPDF_Font* pFont = m_TextState.GetFont(); + FX_BOOL bVertWriting = FALSE; + CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); + if (pCIDFont) { + bVertWriting = pCIDFont->IsVertWriting(); + } + FX_FLOAT fontsize = m_TextState.GetFontSize() / 1000; + int count = 0; + for (int i = 0; i < m_nChars; ++i) { + FX_DWORD charcode = + m_nChars == 1 ? (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[i]; + if (charcode == (FX_DWORD)-1) { + continue; + } + if (count != index) { + ++count; + continue; + } + FX_FLOAT curpos = i > 0 ? m_pCharPos[i - 1] : 0; + FX_RECT char_rect; + pFont->GetCharBBox(charcode, char_rect, 0); + if (!bVertWriting) { + rect.left = curpos + char_rect.left * fontsize; + rect.right = curpos + char_rect.right * fontsize; + rect.top = char_rect.top * fontsize; + rect.bottom = char_rect.bottom * fontsize; + } else { + FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); + short vx, vy; + pCIDFont->GetVertOrigin(CID, vx, vy); + char_rect.left -= vx; + char_rect.right -= vx; + char_rect.top -= vy; + char_rect.bottom -= vy; + rect.left = char_rect.left * fontsize; + rect.right = char_rect.right * fontsize; + rect.top = curpos + char_rect.top * fontsize; + rect.bottom = curpos + char_rect.bottom * fontsize; + } + return; + } } void CPDF_TextObject::CalcPositionData(FX_FLOAT* pTextAdvanceX, FX_FLOAT* pTextAdvanceY, FX_FLOAT horz_scale, - int level) -{ - FX_FLOAT curpos = 0; - FX_FLOAT min_x = 10000 * 1.0f; - FX_FLOAT max_x = -10000 * 1.0f; - FX_FLOAT min_y = 10000 * 1.0f; - FX_FLOAT max_y = -10000 * 1.0f; - CPDF_Font* pFont = m_TextState.GetFont(); - FX_BOOL bVertWriting = FALSE; - CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); - if (pCIDFont) { - bVertWriting = pCIDFont->IsVertWriting(); - } - FX_FLOAT fontsize = m_TextState.GetFontSize(); - for (int i = 0; i < m_nChars; ++i) { - FX_DWORD charcode = m_nChars == 1 ? - (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[i]; - if (charcode == (FX_DWORD) - 1) { - curpos -= FXSYS_Mul(m_pCharPos[i - 1], fontsize) / 1000; - continue; - } - if (i) { - m_pCharPos[i - 1] = curpos; - } - FX_RECT char_rect; - pFont->GetCharBBox(charcode, char_rect, level); - FX_FLOAT charwidth; - if (!bVertWriting) { - if (min_y > char_rect.top) { - min_y = (FX_FLOAT)char_rect.top; - } - if (max_y < char_rect.top) { - max_y = (FX_FLOAT)char_rect.top; - } - if (min_y > char_rect.bottom) { - min_y = (FX_FLOAT)char_rect.bottom; - } - if (max_y < char_rect.bottom) { - max_y = (FX_FLOAT)char_rect.bottom; - } - FX_FLOAT char_left = curpos + char_rect.left * fontsize / 1000; - FX_FLOAT char_right = curpos + char_rect.right * fontsize / 1000; - if (min_x > char_left) { - min_x = char_left; - } - if (max_x < char_left) { - max_x = char_left; - } - if (min_x > char_right) { - min_x = char_right; - } - if (max_x < char_right) { - max_x = char_right; - } - charwidth = pFont->GetCharWidthF(charcode, level) * fontsize / 1000; - } else { - FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); - short vx; - short vy; - pCIDFont->GetVertOrigin(CID, vx, vy); - char_rect.left -= vx; - char_rect.right -= vx; - char_rect.top -= vy; - char_rect.bottom -= vy; - if (min_x > char_rect.left) { - min_x = (FX_FLOAT)char_rect.left; - } - if (max_x < char_rect.left) { - max_x = (FX_FLOAT)char_rect.left; - } - if (min_x > char_rect.right) { - min_x = (FX_FLOAT)char_rect.right; - } - if (max_x < char_rect.right) { - max_x = (FX_FLOAT)char_rect.right; - } - FX_FLOAT char_top = curpos + char_rect.top * fontsize / 1000; - FX_FLOAT char_bottom = curpos + char_rect.bottom * fontsize / 1000; - if (min_y > char_top) { - min_y = char_top; - } - if (max_y < char_top) { - max_y = char_top; - } - if (min_y > char_bottom) { - min_y = char_bottom; - } - if (max_y < char_bottom) { - max_y = char_bottom; - } - charwidth = pCIDFont->GetVertWidth(CID) * fontsize / 1000; - } - curpos += charwidth; - if (charcode == ' ' && (!pCIDFont || pCIDFont->GetCharSize(32) == 1)) { - curpos += m_TextState.GetObject()->m_WordSpace; - } - curpos += m_TextState.GetObject()->m_CharSpace; - } - if (bVertWriting) { - if (pTextAdvanceX) { - *pTextAdvanceX = 0; - } - if (pTextAdvanceY) { - *pTextAdvanceY = curpos; - } - min_x = min_x * fontsize / 1000; - max_x = max_x * fontsize / 1000; + int level) { + FX_FLOAT curpos = 0; + FX_FLOAT min_x = 10000 * 1.0f; + FX_FLOAT max_x = -10000 * 1.0f; + FX_FLOAT min_y = 10000 * 1.0f; + FX_FLOAT max_y = -10000 * 1.0f; + CPDF_Font* pFont = m_TextState.GetFont(); + FX_BOOL bVertWriting = FALSE; + CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); + if (pCIDFont) { + bVertWriting = pCIDFont->IsVertWriting(); + } + FX_FLOAT fontsize = m_TextState.GetFontSize(); + for (int i = 0; i < m_nChars; ++i) { + FX_DWORD charcode = + m_nChars == 1 ? (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[i]; + if (charcode == (FX_DWORD)-1) { + curpos -= FXSYS_Mul(m_pCharPos[i - 1], fontsize) / 1000; + continue; + } + if (i) { + m_pCharPos[i - 1] = curpos; + } + FX_RECT char_rect; + pFont->GetCharBBox(charcode, char_rect, level); + FX_FLOAT charwidth; + if (!bVertWriting) { + if (min_y > char_rect.top) { + min_y = (FX_FLOAT)char_rect.top; + } + if (max_y < char_rect.top) { + max_y = (FX_FLOAT)char_rect.top; + } + if (min_y > char_rect.bottom) { + min_y = (FX_FLOAT)char_rect.bottom; + } + if (max_y < char_rect.bottom) { + max_y = (FX_FLOAT)char_rect.bottom; + } + FX_FLOAT char_left = curpos + char_rect.left * fontsize / 1000; + FX_FLOAT char_right = curpos + char_rect.right * fontsize / 1000; + if (min_x > char_left) { + min_x = char_left; + } + if (max_x < char_left) { + max_x = char_left; + } + if (min_x > char_right) { + min_x = char_right; + } + if (max_x < char_right) { + max_x = char_right; + } + charwidth = pFont->GetCharWidthF(charcode, level) * fontsize / 1000; } else { - if (pTextAdvanceX) { - *pTextAdvanceX = FXSYS_Mul(curpos, horz_scale); - } - if (pTextAdvanceY) { - *pTextAdvanceY = 0; - } - min_y = min_y * fontsize / 1000; - max_y = max_y * fontsize / 1000; - } - CFX_AffineMatrix matrix; - GetTextMatrix(&matrix); - m_Left = min_x; - m_Right = max_x; - m_Bottom = min_y; - m_Top = max_y; - matrix.TransformRect(m_Left, m_Right, m_Top, m_Bottom); - int textmode = m_TextState.GetObject()->m_TextMode; - if (textmode == 1 || textmode == 2 || textmode == 5 || textmode == 6) { - FX_FLOAT half_width = m_GraphState.GetObject()->m_LineWidth / 2; - m_Left -= half_width; - m_Right += half_width; - m_Top += half_width; - m_Bottom -= half_width; - } + FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); + short vx; + short vy; + pCIDFont->GetVertOrigin(CID, vx, vy); + char_rect.left -= vx; + char_rect.right -= vx; + char_rect.top -= vy; + char_rect.bottom -= vy; + if (min_x > char_rect.left) { + min_x = (FX_FLOAT)char_rect.left; + } + if (max_x < char_rect.left) { + max_x = (FX_FLOAT)char_rect.left; + } + if (min_x > char_rect.right) { + min_x = (FX_FLOAT)char_rect.right; + } + if (max_x < char_rect.right) { + max_x = (FX_FLOAT)char_rect.right; + } + FX_FLOAT char_top = curpos + char_rect.top * fontsize / 1000; + FX_FLOAT char_bottom = curpos + char_rect.bottom * fontsize / 1000; + if (min_y > char_top) { + min_y = char_top; + } + if (max_y < char_top) { + max_y = char_top; + } + if (min_y > char_bottom) { + min_y = char_bottom; + } + if (max_y < char_bottom) { + max_y = char_bottom; + } + charwidth = pCIDFont->GetVertWidth(CID) * fontsize / 1000; + } + curpos += charwidth; + if (charcode == ' ' && (!pCIDFont || pCIDFont->GetCharSize(32) == 1)) { + curpos += m_TextState.GetObject()->m_WordSpace; + } + curpos += m_TextState.GetObject()->m_CharSpace; + } + if (bVertWriting) { + if (pTextAdvanceX) { + *pTextAdvanceX = 0; + } + if (pTextAdvanceY) { + *pTextAdvanceY = curpos; + } + min_x = min_x * fontsize / 1000; + max_x = max_x * fontsize / 1000; + } else { + if (pTextAdvanceX) { + *pTextAdvanceX = FXSYS_Mul(curpos, horz_scale); + } + if (pTextAdvanceY) { + *pTextAdvanceY = 0; + } + min_y = min_y * fontsize / 1000; + max_y = max_y * fontsize / 1000; + } + CFX_AffineMatrix matrix; + GetTextMatrix(&matrix); + m_Left = min_x; + m_Right = max_x; + m_Bottom = min_y; + m_Top = max_y; + matrix.TransformRect(m_Left, m_Right, m_Top, m_Bottom); + int textmode = m_TextState.GetObject()->m_TextMode; + if (textmode == 1 || textmode == 2 || textmode == 5 || textmode == 6) { + FX_FLOAT half_width = m_GraphState.GetObject()->m_LineWidth / 2; + m_Left -= half_width; + m_Right += half_width; + m_Top += half_width; + m_Bottom -= half_width; + } } -void CPDF_TextObject::CalcCharPos(FX_FLOAT* pPosArray) const -{ - CPDF_Font* pFont = m_TextState.GetFont(); - FX_BOOL bVertWriting = FALSE; - CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); - if (pCIDFont) { - bVertWriting = pCIDFont->IsVertWriting(); - } - FX_FLOAT fontsize = m_TextState.GetFontSize(); - for (int i = 0, index = 0; i < m_nChars; ++i) { - FX_DWORD charcode = m_nChars == 1 ? - (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[i]; - if (charcode == (FX_DWORD) - 1) { - continue; - } - pPosArray[index++] = i ? m_pCharPos[i - 1] : 0; - FX_FLOAT charwidth; - if (bVertWriting) { - FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); - charwidth = pCIDFont->GetVertWidth(CID) * fontsize / 1000; - } else { - charwidth = pFont->GetCharWidthF(charcode) * fontsize / 1000; - } - pPosArray[index] = pPosArray[index - 1] + charwidth; - index++; +void CPDF_TextObject::CalcCharPos(FX_FLOAT* pPosArray) const { + CPDF_Font* pFont = m_TextState.GetFont(); + FX_BOOL bVertWriting = FALSE; + CPDF_CIDFont* pCIDFont = pFont->GetCIDFont(); + if (pCIDFont) { + bVertWriting = pCIDFont->IsVertWriting(); + } + FX_FLOAT fontsize = m_TextState.GetFontSize(); + for (int i = 0, index = 0; i < m_nChars; ++i) { + FX_DWORD charcode = + m_nChars == 1 ? (FX_DWORD)(uintptr_t)m_pCharCodes : m_pCharCodes[i]; + if (charcode == (FX_DWORD)-1) { + continue; + } + pPosArray[index++] = i ? m_pCharPos[i - 1] : 0; + FX_FLOAT charwidth; + if (bVertWriting) { + FX_WORD CID = pCIDFont->CIDFromCharCode(charcode); + charwidth = pCIDFont->GetVertWidth(CID) * fontsize / 1000; + } else { + charwidth = pFont->GetCharWidthF(charcode) * fontsize / 1000; } + pPosArray[index] = pPosArray[index - 1] + charwidth; + index++; + } } -void CPDF_TextObject::Transform(const CFX_AffineMatrix& matrix) -{ - m_TextState.GetModify(); - CFX_AffineMatrix text_matrix; - GetTextMatrix(&text_matrix); - text_matrix.Concat(matrix); - FX_FLOAT* pTextMatrix = m_TextState.GetMatrix(); - pTextMatrix[0] = text_matrix.GetA(); - pTextMatrix[1] = text_matrix.GetC(); - pTextMatrix[2] = text_matrix.GetB(); - pTextMatrix[3] = text_matrix.GetD(); - m_PosX = text_matrix.GetE(); - m_PosY = text_matrix.GetF(); - CalcPositionData(nullptr, nullptr, 0); +void CPDF_TextObject::Transform(const CFX_AffineMatrix& matrix) { + m_TextState.GetModify(); + CFX_AffineMatrix text_matrix; + GetTextMatrix(&text_matrix); + text_matrix.Concat(matrix); + FX_FLOAT* pTextMatrix = m_TextState.GetMatrix(); + pTextMatrix[0] = text_matrix.GetA(); + pTextMatrix[1] = text_matrix.GetC(); + pTextMatrix[2] = text_matrix.GetB(); + pTextMatrix[3] = text_matrix.GetD(); + m_PosX = text_matrix.GetE(); + m_PosY = text_matrix.GetF(); + CalcPositionData(nullptr, nullptr, 0); } -void CPDF_TextObject::SetPosition(FX_FLOAT x, FX_FLOAT y) -{ - FX_FLOAT dx = x - m_PosX; - FX_FLOAT dy = y - m_PosY; - m_PosX = x; - m_PosY = y; - m_Left += dx; - m_Right += dx; - m_Top += dy; - m_Bottom += dy; +void CPDF_TextObject::SetPosition(FX_FLOAT x, FX_FLOAT y) { + FX_FLOAT dx = x - m_PosX; + FX_FLOAT dy = y - m_PosY; + m_PosX = x; + m_PosY = y; + m_Left += dx; + m_Right += dx; + m_Top += dy; + m_Bottom += dy; } void CPDF_TextObject::SetData(int nChars, FX_DWORD* pCharCodes, FX_FLOAT* pCharPos, FX_FLOAT x, - FX_FLOAT y) -{ - ASSERT(m_nChars == 0); - m_nChars = nChars; - m_PosX = x; - m_PosY = y; - if (nChars == 0) { - return; - } - if (nChars == 1) { - m_pCharCodes = (FX_DWORD*)(uintptr_t) * pCharCodes; - } else { - m_pCharCodes = FX_Alloc(FX_DWORD, nChars); - FXSYS_memcpy(m_pCharCodes, pCharCodes, sizeof(FX_DWORD)*nChars); - m_pCharPos = FX_Alloc(FX_FLOAT, nChars - 1); - FXSYS_memcpy(m_pCharPos, pCharPos, sizeof(FX_FLOAT) * (nChars - 1)); - } - RecalcPositionData(); + FX_FLOAT y) { + ASSERT(m_nChars == 0); + m_nChars = nChars; + m_PosX = x; + m_PosY = y; + if (nChars == 0) { + return; + } + if (nChars == 1) { + m_pCharCodes = (FX_DWORD*)(uintptr_t)*pCharCodes; + } else { + m_pCharCodes = FX_Alloc(FX_DWORD, nChars); + FXSYS_memcpy(m_pCharCodes, pCharCodes, sizeof(FX_DWORD) * nChars); + m_pCharPos = FX_Alloc(FX_FLOAT, nChars - 1); + FXSYS_memcpy(m_pCharPos, pCharPos, sizeof(FX_FLOAT) * (nChars - 1)); + } + RecalcPositionData(); } -void CPDF_TextObject::SetTextState(CPDF_TextState TextState) -{ - m_TextState = TextState; - CalcPositionData(nullptr, nullptr, 0); +void CPDF_TextObject::SetTextState(CPDF_TextState TextState) { + m_TextState = TextState; + CalcPositionData(nullptr, nullptr, 0); } -CPDF_ShadingObject::CPDF_ShadingObject() -{ - m_pShading = NULL; - m_Type = PDFPAGE_SHADING; -} -CPDF_ShadingObject::~CPDF_ShadingObject() -{ -} -void CPDF_ShadingObject::CopyData(const CPDF_PageObject* pSrc) -{ - CPDF_ShadingObject* pSrcObj = (CPDF_ShadingObject*)pSrc; - m_pShading = pSrcObj->m_pShading; - if (m_pShading && m_pShading->m_pDocument) { - CPDF_DocPageData* pDocPageData = m_pShading->m_pDocument->GetPageData(); - m_pShading = (CPDF_ShadingPattern*)pDocPageData->GetPattern(m_pShading->m_pShadingObj, m_pShading->m_bShadingObj, &m_pShading->m_ParentMatrix); - } - m_Matrix = pSrcObj->m_Matrix; -} -void CPDF_ShadingObject::Transform(const CFX_AffineMatrix& matrix) -{ - if (!m_ClipPath.IsNull()) { - m_ClipPath.GetModify(); - m_ClipPath.Transform(matrix); - } - m_Matrix.Concat(matrix); - if (!m_ClipPath.IsNull()) { - CalcBoundingBox(); - } else { - matrix.TransformRect(m_Left, m_Right, m_Top, m_Bottom); - } -} -void CPDF_ShadingObject::CalcBoundingBox() -{ - if (m_ClipPath.IsNull()) { - return; - } - CFX_FloatRect rect = m_ClipPath.GetClipBox(); - m_Left = rect.left; - m_Bottom = rect.bottom; - m_Right = rect.right; - m_Top = rect.top; -} -CPDF_FormObject::~CPDF_FormObject() -{ - delete m_pForm; -} -void CPDF_FormObject::Transform(const CFX_AffineMatrix& matrix) -{ - m_FormMatrix.Concat(matrix); +CPDF_ShadingObject::CPDF_ShadingObject() { + m_pShading = NULL; + m_Type = PDFPAGE_SHADING; +} +CPDF_ShadingObject::~CPDF_ShadingObject() {} +void CPDF_ShadingObject::CopyData(const CPDF_PageObject* pSrc) { + CPDF_ShadingObject* pSrcObj = (CPDF_ShadingObject*)pSrc; + m_pShading = pSrcObj->m_pShading; + if (m_pShading && m_pShading->m_pDocument) { + CPDF_DocPageData* pDocPageData = m_pShading->m_pDocument->GetPageData(); + m_pShading = (CPDF_ShadingPattern*)pDocPageData->GetPattern( + m_pShading->m_pShadingObj, m_pShading->m_bShadingObj, + &m_pShading->m_ParentMatrix); + } + m_Matrix = pSrcObj->m_Matrix; +} +void CPDF_ShadingObject::Transform(const CFX_AffineMatrix& matrix) { + if (!m_ClipPath.IsNull()) { + m_ClipPath.GetModify(); + m_ClipPath.Transform(matrix); + } + m_Matrix.Concat(matrix); + if (!m_ClipPath.IsNull()) { CalcBoundingBox(); -} -void CPDF_FormObject::CopyData(const CPDF_PageObject* pSrc) -{ - const CPDF_FormObject* pSrcObj = (const CPDF_FormObject*)pSrc; - delete m_pForm; - m_pForm = pSrcObj->m_pForm->Clone(); - m_FormMatrix = pSrcObj->m_FormMatrix; -} -void CPDF_FormObject::CalcBoundingBox() -{ - CFX_FloatRect form_rect = m_pForm->CalcBoundingBox(); - form_rect.Transform(&m_FormMatrix); - m_Left = form_rect.left; - m_Bottom = form_rect.bottom; - m_Right = form_rect.right; - m_Top = form_rect.top; + } else { + matrix.TransformRect(m_Left, m_Right, m_Top, m_Bottom); + } +} +void CPDF_ShadingObject::CalcBoundingBox() { + if (m_ClipPath.IsNull()) { + return; + } + CFX_FloatRect rect = m_ClipPath.GetClipBox(); + m_Left = rect.left; + m_Bottom = rect.bottom; + m_Right = rect.right; + m_Top = rect.top; +} +CPDF_FormObject::~CPDF_FormObject() { + delete m_pForm; +} +void CPDF_FormObject::Transform(const CFX_AffineMatrix& matrix) { + m_FormMatrix.Concat(matrix); + CalcBoundingBox(); +} +void CPDF_FormObject::CopyData(const CPDF_PageObject* pSrc) { + const CPDF_FormObject* pSrcObj = (const CPDF_FormObject*)pSrc; + delete m_pForm; + m_pForm = pSrcObj->m_pForm->Clone(); + m_FormMatrix = pSrcObj->m_FormMatrix; +} +void CPDF_FormObject::CalcBoundingBox() { + CFX_FloatRect form_rect = m_pForm->CalcBoundingBox(); + form_rect.Transform(&m_FormMatrix); + m_Left = form_rect.left; + m_Bottom = form_rect.bottom; + m_Right = form_rect.right; + m_Top = form_rect.top; } CPDF_PageObjects::CPDF_PageObjects(FX_BOOL bReleaseMembers) : m_pFormDict(nullptr), @@ -731,345 +683,339 @@ CPDF_PageObjects::CPDF_PageObjects(FX_BOOL bReleaseMembers) m_bBackgroundAlphaNeeded(FALSE), m_bReleaseMembers(bReleaseMembers), m_pParser(nullptr), - m_ParseState(CONTENT_NOT_PARSED) -{ -} -CPDF_PageObjects::~CPDF_PageObjects() -{ - delete m_pParser; - if (!m_bReleaseMembers) { - return; - } - FX_POSITION pos = m_ObjectList.GetHeadPosition(); - while (pos) { - delete (CPDF_PageObject*)m_ObjectList.GetNext(pos); - } -} -void CPDF_PageObjects::ContinueParse(IFX_Pause* pPause) -{ - if (m_pParser == NULL) { - return; - } - m_pParser->Continue(pPause); - if (m_pParser->GetStatus() == CPDF_ContentParser::Done) { - m_ParseState = CONTENT_PARSED; - delete m_pParser; - m_pParser = NULL; - } -} -FX_POSITION CPDF_PageObjects::InsertObject(FX_POSITION posInsertAfter, CPDF_PageObject* pNewObject) -{ - if (!posInsertAfter) { - return m_ObjectList.AddHead(pNewObject); - } - return m_ObjectList.InsertAfter(posInsertAfter, pNewObject); -} -int CPDF_PageObjects::GetObjectIndex(CPDF_PageObject* pObj) const -{ - int index = 0; - FX_POSITION pos = m_ObjectList.GetHeadPosition(); - while (pos) { - CPDF_PageObject* pThisObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); - if (pThisObj == pObj) { - return index; - } - index ++; - } - return -1; -} -CPDF_PageObject* CPDF_PageObjects::GetObjectByIndex(int index) const -{ - FX_POSITION pos = m_ObjectList.FindIndex(index); - if (pos == NULL) { - return NULL; - } - return (CPDF_PageObject*)m_ObjectList.GetAt(pos); -} -void CPDF_PageObjects::Transform(const CFX_AffineMatrix& matrix) -{ - FX_POSITION pos = m_ObjectList.GetHeadPosition(); - while (pos) { - CPDF_PageObject* pObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); - pObj->Transform(matrix); - } -} -CFX_FloatRect CPDF_PageObjects::CalcBoundingBox() const -{ - if (m_ObjectList.GetCount() == 0) { - return CFX_FloatRect(0, 0, 0, 0); - } - FX_FLOAT left, right, top, bottom; - left = bottom = 1000000 * 1.0f; - right = top = -1000000 * 1.0f; - FX_POSITION pos = m_ObjectList.GetHeadPosition(); - while (pos) { - CPDF_PageObject* pObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); - if (left > pObj->m_Left) { - left = pObj->m_Left; - } - if (right < pObj->m_Right) { - right = pObj->m_Right; - } - if (top < pObj->m_Top) { - top = pObj->m_Top; - } - if (bottom > pObj->m_Bottom) { - bottom = pObj->m_Bottom; - } - } - return CFX_FloatRect(left, bottom, right, top); -} -void CPDF_PageObjects::LoadTransInfo() -{ - if (m_pFormDict == NULL) { - return; - } - CPDF_Dictionary* pGroup = m_pFormDict->GetDict(FX_BSTRC("Group")); - if (pGroup == NULL) { - return; - } - if (pGroup->GetString(FX_BSTRC("S")) != FX_BSTRC("Transparency")) { - return; - } - m_Transparency |= PDFTRANS_GROUP; - if (pGroup->GetInteger(FX_BSTRC("I"))) { - m_Transparency |= PDFTRANS_ISOLATED; - } - if (pGroup->GetInteger(FX_BSTRC("K"))) { - m_Transparency |= PDFTRANS_KNOCKOUT; - } -} -void CPDF_PageObjects::ClearCacheObjects() -{ - m_ParseState = CONTENT_NOT_PARSED; + m_ParseState(CONTENT_NOT_PARSED) {} +CPDF_PageObjects::~CPDF_PageObjects() { + delete m_pParser; + if (!m_bReleaseMembers) { + return; + } + FX_POSITION pos = m_ObjectList.GetHeadPosition(); + while (pos) { + delete (CPDF_PageObject*)m_ObjectList.GetNext(pos); + } +} +void CPDF_PageObjects::ContinueParse(IFX_Pause* pPause) { + if (m_pParser == NULL) { + return; + } + m_pParser->Continue(pPause); + if (m_pParser->GetStatus() == CPDF_ContentParser::Done) { + m_ParseState = CONTENT_PARSED; delete m_pParser; m_pParser = NULL; - if (m_bReleaseMembers) { - FX_POSITION pos = m_ObjectList.GetHeadPosition(); - while (pos) { - delete (CPDF_PageObject*)m_ObjectList.GetNext(pos); - } - } - m_ObjectList.RemoveAll(); -} -CPDF_Page::CPDF_Page() -{ - m_pPageRender = NULL; -} -void CPDF_Page::Load(CPDF_Document* pDocument, CPDF_Dictionary* pPageDict, FX_BOOL bPageCache) -{ - m_pDocument = (CPDF_Document*)pDocument; - m_pFormDict = pPageDict; - if (bPageCache) { - m_pPageRender = CPDF_ModuleMgr::Get()->GetRenderModule()->CreatePageCache(this); - } - if (pPageDict == NULL) { - m_PageWidth = m_PageHeight = 100 * 1.0f; - m_pPageResources = m_pResources = NULL; - return; - } - CPDF_Object* pageAttr = GetPageAttr(FX_BSTRC("Resources")); - m_pResources = pageAttr ? pageAttr->GetDict() : NULL; - m_pPageResources = m_pResources; - CPDF_Object* pRotate = GetPageAttr(FX_BSTRC("Rotate")); - int rotate = 0; - if (pRotate) { - rotate = pRotate->GetInteger() / 90 % 4; - } - if (rotate < 0) { - rotate += 4; - } - CPDF_Array* pMediaBox, *pCropBox; - pMediaBox = (CPDF_Array*)GetPageAttr(FX_BSTRC("MediaBox")); - CFX_FloatRect mediabox; - if (pMediaBox) { - mediabox = pMediaBox->GetRect(); - mediabox.Normalize(); - } - if (mediabox.IsEmpty()) { - mediabox = CFX_FloatRect(0, 0, 612, 792); - } - pCropBox = (CPDF_Array*)GetPageAttr(FX_BSTRC("CropBox")); - if (pCropBox) { - m_BBox = pCropBox->GetRect(); - m_BBox.Normalize(); - } - if (m_BBox.IsEmpty()) { - m_BBox = mediabox; - } else { - m_BBox.Intersect(mediabox); - } - if (rotate % 2) { - m_PageHeight = m_BBox.right - m_BBox.left; - m_PageWidth = m_BBox.top - m_BBox.bottom; - } else { - m_PageWidth = m_BBox.right - m_BBox.left; - m_PageHeight = m_BBox.top - m_BBox.bottom; - } - switch (rotate) { - case 0: - m_PageMatrix.Set(1.0f, 0, 0, 1.0f, -m_BBox.left, -m_BBox.bottom); - break; - case 1: - m_PageMatrix.Set(0, -1.0f, 1.0f, 0, -m_BBox.bottom, m_BBox.right); - break; - case 2: - m_PageMatrix.Set(-1.0f, 0, 0, -1.0f, m_BBox.right, m_BBox.top); - break; - case 3: - m_PageMatrix.Set(0, 1.0f, -1.0f, 0, m_BBox.top, -m_BBox.left); - break; - } - m_Transparency = PDFTRANS_ISOLATED; - LoadTransInfo(); -} -void CPDF_Page::StartParse(CPDF_ParseOptions* pOptions, FX_BOOL bReParse) -{ - if (bReParse) { - ClearCacheObjects(); - } - if (m_ParseState == CONTENT_PARSED || m_ParseState == CONTENT_PARSING) { - return; - } - m_pParser = new CPDF_ContentParser; - m_pParser->Start(this, pOptions); - m_ParseState = CONTENT_PARSING; -} -void CPDF_Page::ParseContent(CPDF_ParseOptions* pOptions, FX_BOOL bReParse) -{ - StartParse(pOptions, bReParse); - ContinueParse(NULL); -} -CPDF_Page::~CPDF_Page() -{ - if (m_pPageRender) { - IPDF_RenderModule* pModule = CPDF_ModuleMgr::Get()->GetRenderModule(); - pModule->DestroyPageCache(m_pPageRender); - } -} -CPDF_Object* FPDFAPI_GetPageAttr(CPDF_Dictionary* pPageDict, const CFX_ByteStringC& name) -{ - int level = 0; - while (1) { - CPDF_Object* pObj = pPageDict->GetElementValue(name); - if (pObj) { - return pObj; - } - CPDF_Dictionary* pParent = pPageDict->GetDict(FX_BSTRC("Parent")); - if (!pParent || pParent == pPageDict) { - return NULL; - } - pPageDict = pParent; - level ++; - if (level == 1000) { - return NULL; - } - } -} -CPDF_Object* CPDF_Page::GetPageAttr(const CFX_ByteStringC& name) const -{ - return FPDFAPI_GetPageAttr(m_pFormDict, name); -} -CPDF_Form::CPDF_Form(CPDF_Document* pDoc, CPDF_Dictionary* pPageResources, CPDF_Stream* pFormStream, CPDF_Dictionary* pParentResources) -{ - m_pDocument = pDoc; - m_pFormStream = pFormStream; - m_pFormDict = pFormStream ? pFormStream->GetDict() : NULL; - m_pResources = m_pFormDict->GetDict(FX_BSTRC("Resources")); - m_pPageResources = pPageResources; - if (m_pResources == NULL) { - m_pResources = pParentResources; - } - if (m_pResources == NULL) { - m_pResources = pPageResources; - } - m_Transparency = 0; - LoadTransInfo(); -} -CPDF_Form::~CPDF_Form() -{ -} -void CPDF_Form::StartParse(CPDF_AllStates* pGraphicStates, CFX_AffineMatrix* pParentMatrix, - CPDF_Type3Char* pType3Char, CPDF_ParseOptions* pOptions, int level) -{ - if (m_ParseState == CONTENT_PARSED || m_ParseState == CONTENT_PARSING) { - return; - } - m_pParser = new CPDF_ContentParser; - m_pParser->Start(this, pGraphicStates, pParentMatrix, pType3Char, pOptions, level); - m_ParseState = CONTENT_PARSING; -} -void CPDF_Form::ParseContent(CPDF_AllStates* pGraphicStates, CFX_AffineMatrix* pParentMatrix, - CPDF_Type3Char* pType3Char, CPDF_ParseOptions* pOptions, int level) -{ - StartParse(pGraphicStates, pParentMatrix, pType3Char, pOptions, level); - ContinueParse(NULL); -} -CPDF_Form* CPDF_Form::Clone() const -{ - CPDF_Form* pClone = new CPDF_Form(m_pDocument, m_pPageResources, m_pFormStream, m_pResources); + } +} +FX_POSITION CPDF_PageObjects::InsertObject(FX_POSITION posInsertAfter, + CPDF_PageObject* pNewObject) { + if (!posInsertAfter) { + return m_ObjectList.AddHead(pNewObject); + } + return m_ObjectList.InsertAfter(posInsertAfter, pNewObject); +} +int CPDF_PageObjects::GetObjectIndex(CPDF_PageObject* pObj) const { + int index = 0; + FX_POSITION pos = m_ObjectList.GetHeadPosition(); + while (pos) { + CPDF_PageObject* pThisObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); + if (pThisObj == pObj) { + return index; + } + index++; + } + return -1; +} +CPDF_PageObject* CPDF_PageObjects::GetObjectByIndex(int index) const { + FX_POSITION pos = m_ObjectList.FindIndex(index); + if (pos == NULL) { + return NULL; + } + return (CPDF_PageObject*)m_ObjectList.GetAt(pos); +} +void CPDF_PageObjects::Transform(const CFX_AffineMatrix& matrix) { + FX_POSITION pos = m_ObjectList.GetHeadPosition(); + while (pos) { + CPDF_PageObject* pObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); + pObj->Transform(matrix); + } +} +CFX_FloatRect CPDF_PageObjects::CalcBoundingBox() const { + if (m_ObjectList.GetCount() == 0) { + return CFX_FloatRect(0, 0, 0, 0); + } + FX_FLOAT left, right, top, bottom; + left = bottom = 1000000 * 1.0f; + right = top = -1000000 * 1.0f; + FX_POSITION pos = m_ObjectList.GetHeadPosition(); + while (pos) { + CPDF_PageObject* pObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); + if (left > pObj->m_Left) { + left = pObj->m_Left; + } + if (right < pObj->m_Right) { + right = pObj->m_Right; + } + if (top < pObj->m_Top) { + top = pObj->m_Top; + } + if (bottom > pObj->m_Bottom) { + bottom = pObj->m_Bottom; + } + } + return CFX_FloatRect(left, bottom, right, top); +} +void CPDF_PageObjects::LoadTransInfo() { + if (m_pFormDict == NULL) { + return; + } + CPDF_Dictionary* pGroup = m_pFormDict->GetDict(FX_BSTRC("Group")); + if (pGroup == NULL) { + return; + } + if (pGroup->GetString(FX_BSTRC("S")) != FX_BSTRC("Transparency")) { + return; + } + m_Transparency |= PDFTRANS_GROUP; + if (pGroup->GetInteger(FX_BSTRC("I"))) { + m_Transparency |= PDFTRANS_ISOLATED; + } + if (pGroup->GetInteger(FX_BSTRC("K"))) { + m_Transparency |= PDFTRANS_KNOCKOUT; + } +} +void CPDF_PageObjects::ClearCacheObjects() { + m_ParseState = CONTENT_NOT_PARSED; + delete m_pParser; + m_pParser = NULL; + if (m_bReleaseMembers) { FX_POSITION pos = m_ObjectList.GetHeadPosition(); while (pos) { - CPDF_PageObject* pObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); - pClone->m_ObjectList.AddTail(pObj->Clone()); - } - return pClone; -} -void CPDF_Page::GetDisplayMatrix(CFX_AffineMatrix& matrix, int xPos, int yPos, - int xSize, int ySize, int iRotate) const -{ - if (m_PageWidth == 0 || m_PageHeight == 0) { - return; - } - CFX_AffineMatrix display_matrix; - int x0, y0, x1, y1, x2, y2; - iRotate %= 4; - switch (iRotate) { - case 0: - x0 = xPos; - y0 = yPos + ySize; - x1 = xPos; - y1 = yPos; - x2 = xPos + xSize; - y2 = yPos + ySize; - break; - case 1: - x0 = xPos; - y0 = yPos; - x1 = xPos + xSize; - y1 = yPos; - x2 = xPos; - y2 = yPos + ySize; - break; - case 2: - x0 = xPos + xSize; - y0 = yPos; - x1 = xPos + xSize; - y1 = yPos + ySize; - x2 = xPos; - y2 = yPos; - break; - case 3: - x0 = xPos + xSize; - y0 = yPos + ySize; - x1 = xPos; - y1 = yPos + ySize; - x2 = xPos + xSize; - y2 = yPos; - break; - } - display_matrix.Set(FXSYS_Div((FX_FLOAT)(x2 - x0), m_PageWidth), - FXSYS_Div((FX_FLOAT)(y2 - y0), m_PageWidth), - FXSYS_Div((FX_FLOAT)(x1 - x0), m_PageHeight), - FXSYS_Div((FX_FLOAT)(y1 - y0), m_PageHeight), - (FX_FLOAT)x0, (FX_FLOAT)y0); - matrix = m_PageMatrix; - matrix.Concat(display_matrix); -} -CPDF_ParseOptions::CPDF_ParseOptions() -{ - m_bTextOnly = FALSE; - m_bMarkedContent = TRUE; - m_bSeparateForm = TRUE; - m_bDecodeInlineImage = FALSE; + delete (CPDF_PageObject*)m_ObjectList.GetNext(pos); + } + } + m_ObjectList.RemoveAll(); +} +CPDF_Page::CPDF_Page() { + m_pPageRender = NULL; +} +void CPDF_Page::Load(CPDF_Document* pDocument, + CPDF_Dictionary* pPageDict, + FX_BOOL bPageCache) { + m_pDocument = (CPDF_Document*)pDocument; + m_pFormDict = pPageDict; + if (bPageCache) { + m_pPageRender = + CPDF_ModuleMgr::Get()->GetRenderModule()->CreatePageCache(this); + } + if (pPageDict == NULL) { + m_PageWidth = m_PageHeight = 100 * 1.0f; + m_pPageResources = m_pResources = NULL; + return; + } + CPDF_Object* pageAttr = GetPageAttr(FX_BSTRC("Resources")); + m_pResources = pageAttr ? pageAttr->GetDict() : NULL; + m_pPageResources = m_pResources; + CPDF_Object* pRotate = GetPageAttr(FX_BSTRC("Rotate")); + int rotate = 0; + if (pRotate) { + rotate = pRotate->GetInteger() / 90 % 4; + } + if (rotate < 0) { + rotate += 4; + } + CPDF_Array *pMediaBox, *pCropBox; + pMediaBox = (CPDF_Array*)GetPageAttr(FX_BSTRC("MediaBox")); + CFX_FloatRect mediabox; + if (pMediaBox) { + mediabox = pMediaBox->GetRect(); + mediabox.Normalize(); + } + if (mediabox.IsEmpty()) { + mediabox = CFX_FloatRect(0, 0, 612, 792); + } + pCropBox = (CPDF_Array*)GetPageAttr(FX_BSTRC("CropBox")); + if (pCropBox) { + m_BBox = pCropBox->GetRect(); + m_BBox.Normalize(); + } + if (m_BBox.IsEmpty()) { + m_BBox = mediabox; + } else { + m_BBox.Intersect(mediabox); + } + if (rotate % 2) { + m_PageHeight = m_BBox.right - m_BBox.left; + m_PageWidth = m_BBox.top - m_BBox.bottom; + } else { + m_PageWidth = m_BBox.right - m_BBox.left; + m_PageHeight = m_BBox.top - m_BBox.bottom; + } + switch (rotate) { + case 0: + m_PageMatrix.Set(1.0f, 0, 0, 1.0f, -m_BBox.left, -m_BBox.bottom); + break; + case 1: + m_PageMatrix.Set(0, -1.0f, 1.0f, 0, -m_BBox.bottom, m_BBox.right); + break; + case 2: + m_PageMatrix.Set(-1.0f, 0, 0, -1.0f, m_BBox.right, m_BBox.top); + break; + case 3: + m_PageMatrix.Set(0, 1.0f, -1.0f, 0, m_BBox.top, -m_BBox.left); + break; + } + m_Transparency = PDFTRANS_ISOLATED; + LoadTransInfo(); +} +void CPDF_Page::StartParse(CPDF_ParseOptions* pOptions, FX_BOOL bReParse) { + if (bReParse) { + ClearCacheObjects(); + } + if (m_ParseState == CONTENT_PARSED || m_ParseState == CONTENT_PARSING) { + return; + } + m_pParser = new CPDF_ContentParser; + m_pParser->Start(this, pOptions); + m_ParseState = CONTENT_PARSING; +} +void CPDF_Page::ParseContent(CPDF_ParseOptions* pOptions, FX_BOOL bReParse) { + StartParse(pOptions, bReParse); + ContinueParse(NULL); +} +CPDF_Page::~CPDF_Page() { + if (m_pPageRender) { + IPDF_RenderModule* pModule = CPDF_ModuleMgr::Get()->GetRenderModule(); + pModule->DestroyPageCache(m_pPageRender); + } +} +CPDF_Object* FPDFAPI_GetPageAttr(CPDF_Dictionary* pPageDict, + const CFX_ByteStringC& name) { + int level = 0; + while (1) { + CPDF_Object* pObj = pPageDict->GetElementValue(name); + if (pObj) { + return pObj; + } + CPDF_Dictionary* pParent = pPageDict->GetDict(FX_BSTRC("Parent")); + if (!pParent || pParent == pPageDict) { + return NULL; + } + pPageDict = pParent; + level++; + if (level == 1000) { + return NULL; + } + } +} +CPDF_Object* CPDF_Page::GetPageAttr(const CFX_ByteStringC& name) const { + return FPDFAPI_GetPageAttr(m_pFormDict, name); +} +CPDF_Form::CPDF_Form(CPDF_Document* pDoc, + CPDF_Dictionary* pPageResources, + CPDF_Stream* pFormStream, + CPDF_Dictionary* pParentResources) { + m_pDocument = pDoc; + m_pFormStream = pFormStream; + m_pFormDict = pFormStream ? pFormStream->GetDict() : NULL; + m_pResources = m_pFormDict->GetDict(FX_BSTRC("Resources")); + m_pPageResources = pPageResources; + if (m_pResources == NULL) { + m_pResources = pParentResources; + } + if (m_pResources == NULL) { + m_pResources = pPageResources; + } + m_Transparency = 0; + LoadTransInfo(); +} +CPDF_Form::~CPDF_Form() {} +void CPDF_Form::StartParse(CPDF_AllStates* pGraphicStates, + CFX_AffineMatrix* pParentMatrix, + CPDF_Type3Char* pType3Char, + CPDF_ParseOptions* pOptions, + int level) { + if (m_ParseState == CONTENT_PARSED || m_ParseState == CONTENT_PARSING) { + return; + } + m_pParser = new CPDF_ContentParser; + m_pParser->Start(this, pGraphicStates, pParentMatrix, pType3Char, pOptions, + level); + m_ParseState = CONTENT_PARSING; +} +void CPDF_Form::ParseContent(CPDF_AllStates* pGraphicStates, + CFX_AffineMatrix* pParentMatrix, + CPDF_Type3Char* pType3Char, + CPDF_ParseOptions* pOptions, + int level) { + StartParse(pGraphicStates, pParentMatrix, pType3Char, pOptions, level); + ContinueParse(NULL); +} +CPDF_Form* CPDF_Form::Clone() const { + CPDF_Form* pClone = + new CPDF_Form(m_pDocument, m_pPageResources, m_pFormStream, m_pResources); + FX_POSITION pos = m_ObjectList.GetHeadPosition(); + while (pos) { + CPDF_PageObject* pObj = (CPDF_PageObject*)m_ObjectList.GetNext(pos); + pClone->m_ObjectList.AddTail(pObj->Clone()); + } + return pClone; +} +void CPDF_Page::GetDisplayMatrix(CFX_AffineMatrix& matrix, + int xPos, + int yPos, + int xSize, + int ySize, + int iRotate) const { + if (m_PageWidth == 0 || m_PageHeight == 0) { + return; + } + CFX_AffineMatrix display_matrix; + int x0, y0, x1, y1, x2, y2; + iRotate %= 4; + switch (iRotate) { + case 0: + x0 = xPos; + y0 = yPos + ySize; + x1 = xPos; + y1 = yPos; + x2 = xPos + xSize; + y2 = yPos + ySize; + break; + case 1: + x0 = xPos; + y0 = yPos; + x1 = xPos + xSize; + y1 = yPos; + x2 = xPos; + y2 = yPos + ySize; + break; + case 2: + x0 = xPos + xSize; + y0 = yPos; + x1 = xPos + xSize; + y1 = yPos + ySize; + x2 = xPos; + y2 = yPos; + break; + case 3: + x0 = xPos + xSize; + y0 = yPos + ySize; + x1 = xPos; + y1 = yPos + ySize; + x2 = xPos + xSize; + y2 = yPos; + break; + } + display_matrix.Set(FXSYS_Div((FX_FLOAT)(x2 - x0), m_PageWidth), + FXSYS_Div((FX_FLOAT)(y2 - y0), m_PageWidth), + FXSYS_Div((FX_FLOAT)(x1 - x0), m_PageHeight), + FXSYS_Div((FX_FLOAT)(y1 - y0), m_PageHeight), (FX_FLOAT)x0, + (FX_FLOAT)y0); + matrix = m_PageMatrix; + matrix.Concat(display_matrix); +} +CPDF_ParseOptions::CPDF_ParseOptions() { + m_bTextOnly = FALSE; + m_bMarkedContent = TRUE; + m_bSeparateForm = TRUE; + m_bDecodeInlineImage = FALSE; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_colors.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_colors.cpp index 198054ef7e..c07806c994 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_colors.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_colors.cpp @@ -12,1436 +12,1543 @@ namespace { -void sRGB_to_AdobeCMYK(FX_FLOAT R, FX_FLOAT G, FX_FLOAT B, FX_FLOAT& c, FX_FLOAT& m, FX_FLOAT& y, FX_FLOAT& k) -{ - c = 1.0f - R; - m = 1.0f - G; - y = 1.0f - B; - k = c; - if (m < k) { - k = m; - } - if (y < k) { - k = y; - } +void sRGB_to_AdobeCMYK(FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B, + FX_FLOAT& c, + FX_FLOAT& m, + FX_FLOAT& y, + FX_FLOAT& k) { + c = 1.0f - R; + m = 1.0f - G; + y = 1.0f - B; + k = c; + if (m < k) { + k = m; + } + if (y < k) { + k = y; + } } int ComponentsForFamily(int family) { - if (family == PDFCS_DEVICERGB) - return 3; - if (family == PDFCS_DEVICEGRAY) - return 1; - return 4; + if (family == PDFCS_DEVICERGB) + return 3; + if (family == PDFCS_DEVICEGRAY) + return 1; + return 4; } } // namespace CPDF_DeviceCS::CPDF_DeviceCS(CPDF_Document* pDoc, int family) - : CPDF_ColorSpace(pDoc, family, ComponentsForFamily(family)) { -} + : CPDF_ColorSpace(pDoc, family, ComponentsForFamily(family)) {} -FX_BOOL CPDF_DeviceCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - if (m_Family == PDFCS_DEVICERGB) { - R = pBuf[0]; - if (R < 0) { - R = 0; - } else if (R > 1) { - R = 1; - } - G = pBuf[1]; - if (G < 0) { - G = 0; - } else if (G > 1) { - G = 1; - } - B = pBuf[2]; - if (B < 0) { - B = 0; - } else if (B > 1) { - B = 1; - } - } else if (m_Family == PDFCS_DEVICEGRAY) { - R = *pBuf; - if (R < 0) { - R = 0; - } else if (R > 1) { - R = 1; - } - G = B = R; - } else if (m_Family == PDFCS_DEVICECMYK) { - if (!m_dwStdConversion) { - AdobeCMYK_to_sRGB(pBuf[0], pBuf[1], pBuf[2], pBuf[3], R, G, B); - } else { - FX_FLOAT k = pBuf[3]; - R = 1.0f - FX_MIN(1.0f, pBuf[0] + k); - G = 1.0f - FX_MIN(1.0f, pBuf[1] + k); - B = 1.0f - FX_MIN(1.0f, pBuf[2] + k); - } +FX_BOOL CPDF_DeviceCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + if (m_Family == PDFCS_DEVICERGB) { + R = pBuf[0]; + if (R < 0) { + R = 0; + } else if (R > 1) { + R = 1; + } + G = pBuf[1]; + if (G < 0) { + G = 0; + } else if (G > 1) { + G = 1; + } + B = pBuf[2]; + if (B < 0) { + B = 0; + } else if (B > 1) { + B = 1; + } + } else if (m_Family == PDFCS_DEVICEGRAY) { + R = *pBuf; + if (R < 0) { + R = 0; + } else if (R > 1) { + R = 1; + } + G = B = R; + } else if (m_Family == PDFCS_DEVICECMYK) { + if (!m_dwStdConversion) { + AdobeCMYK_to_sRGB(pBuf[0], pBuf[1], pBuf[2], pBuf[3], R, G, B); } else { - ASSERT(m_Family == PDFCS_PATTERN); - R = G = B = 0; - return FALSE; - } - return TRUE; -} -FX_BOOL CPDF_DeviceCS::v_GetCMYK(FX_FLOAT* pBuf, FX_FLOAT& c, FX_FLOAT& m, FX_FLOAT& y, FX_FLOAT& k) const -{ - if (m_Family != PDFCS_DEVICECMYK) { - return FALSE; - } - c = pBuf[0]; - m = pBuf[1]; - y = pBuf[2]; - k = pBuf[3]; - return TRUE; -} -FX_BOOL CPDF_DeviceCS::SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const -{ - if (m_Family == PDFCS_DEVICERGB) { - pBuf[0] = R; - pBuf[1] = G; - pBuf[2] = B; - return TRUE; - } - if (m_Family == PDFCS_DEVICEGRAY) { - if (R == G && R == B) { - *pBuf = R; - return TRUE; - } - return FALSE; - } - if (m_Family == PDFCS_DEVICECMYK) { - sRGB_to_AdobeCMYK(R, G, B, pBuf[0], pBuf[1], pBuf[2], pBuf[3]); - return TRUE; + FX_FLOAT k = pBuf[3]; + R = 1.0f - FX_MIN(1.0f, pBuf[0] + k); + G = 1.0f - FX_MIN(1.0f, pBuf[1] + k); + B = 1.0f - FX_MIN(1.0f, pBuf[2] + k); } + } else { + ASSERT(m_Family == PDFCS_PATTERN); + R = G = B = 0; return FALSE; -} -FX_BOOL CPDF_DeviceCS::v_SetCMYK(FX_FLOAT* pBuf, FX_FLOAT c, FX_FLOAT m, FX_FLOAT y, FX_FLOAT k) const -{ - if (m_Family == PDFCS_DEVICERGB) { - AdobeCMYK_to_sRGB(c, m, y, k, pBuf[0], pBuf[1], pBuf[2]); - return TRUE; - } - if (m_Family == PDFCS_DEVICECMYK) { - pBuf[0] = c; - pBuf[1] = m; - pBuf[2] = y; - pBuf[3] = k; - return TRUE; - } + } + return TRUE; +} +FX_BOOL CPDF_DeviceCS::v_GetCMYK(FX_FLOAT* pBuf, + FX_FLOAT& c, + FX_FLOAT& m, + FX_FLOAT& y, + FX_FLOAT& k) const { + if (m_Family != PDFCS_DEVICECMYK) { return FALSE; -} -static void ReverseRGB(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels) -{ - if (pDestBuf == pSrcBuf) - for (int i = 0; i < pixels; i ++) { - uint8_t temp = pDestBuf[2]; - pDestBuf[2] = pDestBuf[0]; - pDestBuf[0] = temp; - pDestBuf += 3; - } - else - for (int i = 0; i < pixels; i ++) { - *pDestBuf ++ = pSrcBuf[2]; - *pDestBuf ++ = pSrcBuf[1]; - *pDestBuf ++ = pSrcBuf[0]; - pSrcBuf += 3; - } -} -void CPDF_DeviceCS::TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, int image_height, FX_BOOL bTransMask) const -{ - if (bTransMask && m_Family == PDFCS_DEVICECMYK) { - for (int i = 0; i < pixels; i ++) { - int k = 255 - pSrcBuf[3]; - pDestBuf[0] = ((255 - pSrcBuf[0]) * k) / 255; - pDestBuf[1] = ((255 - pSrcBuf[1]) * k) / 255; - pDestBuf[2] = ((255 - pSrcBuf[2]) * k) / 255; - pDestBuf += 3; - pSrcBuf += 4; - } - return; - } - if (m_Family == PDFCS_DEVICERGB) { - ReverseRGB(pDestBuf, pSrcBuf, pixels); - } else if (m_Family == PDFCS_DEVICEGRAY) { - for (int i = 0; i < pixels; i ++) { - *pDestBuf ++ = pSrcBuf[i]; - *pDestBuf ++ = pSrcBuf[i]; - *pDestBuf ++ = pSrcBuf[i]; - } - } else { - for (int i = 0; i < pixels; i ++) { - if (!m_dwStdConversion) { - AdobeCMYK_to_sRGB1(pSrcBuf[0], pSrcBuf[1], pSrcBuf[2], pSrcBuf[3], pDestBuf[2], pDestBuf[1], pDestBuf[0]); - } else { - uint8_t k = pSrcBuf[3]; - pDestBuf[2] = 255 - FX_MIN(255, pSrcBuf[0] + k); - pDestBuf[1] = 255 - FX_MIN(255, pSrcBuf[1] + k); - pDestBuf[0] = 255 - FX_MIN(255, pSrcBuf[2] + k); - } - pSrcBuf += 4; - pDestBuf += 3; - } + } + c = pBuf[0]; + m = pBuf[1]; + y = pBuf[2]; + k = pBuf[3]; + return TRUE; +} +FX_BOOL CPDF_DeviceCS::SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const { + if (m_Family == PDFCS_DEVICERGB) { + pBuf[0] = R; + pBuf[1] = G; + pBuf[2] = B; + return TRUE; + } + if (m_Family == PDFCS_DEVICEGRAY) { + if (R == G && R == B) { + *pBuf = R; + return TRUE; } + return FALSE; + } + if (m_Family == PDFCS_DEVICECMYK) { + sRGB_to_AdobeCMYK(R, G, B, pBuf[0], pBuf[1], pBuf[2], pBuf[3]); + return TRUE; + } + return FALSE; +} +FX_BOOL CPDF_DeviceCS::v_SetCMYK(FX_FLOAT* pBuf, + FX_FLOAT c, + FX_FLOAT m, + FX_FLOAT y, + FX_FLOAT k) const { + if (m_Family == PDFCS_DEVICERGB) { + AdobeCMYK_to_sRGB(c, m, y, k, pBuf[0], pBuf[1], pBuf[2]); + return TRUE; + } + if (m_Family == PDFCS_DEVICECMYK) { + pBuf[0] = c; + pBuf[1] = m; + pBuf[2] = y; + pBuf[3] = k; + return TRUE; + } + return FALSE; +} +static void ReverseRGB(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels) { + if (pDestBuf == pSrcBuf) + for (int i = 0; i < pixels; i++) { + uint8_t temp = pDestBuf[2]; + pDestBuf[2] = pDestBuf[0]; + pDestBuf[0] = temp; + pDestBuf += 3; + } + else + for (int i = 0; i < pixels; i++) { + *pDestBuf++ = pSrcBuf[2]; + *pDestBuf++ = pSrcBuf[1]; + *pDestBuf++ = pSrcBuf[0]; + pSrcBuf += 3; + } +} +void CPDF_DeviceCS::TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask) const { + if (bTransMask && m_Family == PDFCS_DEVICECMYK) { + for (int i = 0; i < pixels; i++) { + int k = 255 - pSrcBuf[3]; + pDestBuf[0] = ((255 - pSrcBuf[0]) * k) / 255; + pDestBuf[1] = ((255 - pSrcBuf[1]) * k) / 255; + pDestBuf[2] = ((255 - pSrcBuf[2]) * k) / 255; + pDestBuf += 3; + pSrcBuf += 4; + } + return; + } + if (m_Family == PDFCS_DEVICERGB) { + ReverseRGB(pDestBuf, pSrcBuf, pixels); + } else if (m_Family == PDFCS_DEVICEGRAY) { + for (int i = 0; i < pixels; i++) { + *pDestBuf++ = pSrcBuf[i]; + *pDestBuf++ = pSrcBuf[i]; + *pDestBuf++ = pSrcBuf[i]; + } + } else { + for (int i = 0; i < pixels; i++) { + if (!m_dwStdConversion) { + AdobeCMYK_to_sRGB1(pSrcBuf[0], pSrcBuf[1], pSrcBuf[2], pSrcBuf[3], + pDestBuf[2], pDestBuf[1], pDestBuf[0]); + } else { + uint8_t k = pSrcBuf[3]; + pDestBuf[2] = 255 - FX_MIN(255, pSrcBuf[0] + k); + pDestBuf[1] = 255 - FX_MIN(255, pSrcBuf[1] + k); + pDestBuf[0] = 255 - FX_MIN(255, pSrcBuf[2] + k); + } + pSrcBuf += 4; + pDestBuf += 3; + } + } } const uint8_t g_sRGBSamples1[] = { - 0, 3, 6, 10, 13, 15, 18, 20, 22, 23, 25, 27, 28, 30, 31, 32, - 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, - 49, 50, 51, 52, 53, 53, 54, 55, 56, 56, 57, 58, 58, 59, 60, 61, - 61, 62, 62, 63, 64, 64, 65, 66, 66, 67, 67, 68, 68, 69, 70, 70, - 71, 71, 72, 72, 73, 73, 74, 74, 75, 76, 76, 77, 77, 78, 78, 79, - 79, 79, 80, 80, 81, 81, 82, 82, 83, 83, 84, 84, 85, 85, 85, 86, - 86, 87, 87, 88, 88, 88, 89, 89, 90, 90, 91, 91, 91, 92, 92, 93, - 93, 93, 94, 94, 95, 95, 95, 96, 96, 97, 97, 97, 98, 98, 98, 99, - 99, 99, 100, 100, 101, 101, 101, 102, 102, 102, 103, 103, 103, 104, 104, 104, - 105, 105, 106, 106, 106, 107, 107, 107, 108, 108, 108, 109, 109, 109, 110, 110, - 110, 110, 111, 111, 111, 112, 112, 112, 113, 113, 113, 114, 114, 114, 115, 115, - 115, 115, 116, 116, 116, 117, 117, 117, 118, 118, 118, 118, 119, 119, 119, 120, + 0, 3, 6, 10, 13, 15, 18, 20, 22, 23, 25, 27, 28, 30, 31, + 32, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, + 48, 49, 49, 50, 51, 52, 53, 53, 54, 55, 56, 56, 57, 58, 58, + 59, 60, 61, 61, 62, 62, 63, 64, 64, 65, 66, 66, 67, 67, 68, + 68, 69, 70, 70, 71, 71, 72, 72, 73, 73, 74, 74, 75, 76, 76, + 77, 77, 78, 78, 79, 79, 79, 80, 80, 81, 81, 82, 82, 83, 83, + 84, 84, 85, 85, 85, 86, 86, 87, 87, 88, 88, 88, 89, 89, 90, + 90, 91, 91, 91, 92, 92, 93, 93, 93, 94, 94, 95, 95, 95, 96, + 96, 97, 97, 97, 98, 98, 98, 99, 99, 99, 100, 100, 101, 101, 101, + 102, 102, 102, 103, 103, 103, 104, 104, 104, 105, 105, 106, 106, 106, 107, + 107, 107, 108, 108, 108, 109, 109, 109, 110, 110, 110, 110, 111, 111, 111, + 112, 112, 112, 113, 113, 113, 114, 114, 114, 115, 115, 115, 115, 116, 116, + 116, 117, 117, 117, 118, 118, 118, 118, 119, 119, 119, 120, }; const uint8_t g_sRGBSamples2[] = { - 120, 121, 122, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, 136, - 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 148, 149, 150, 151, - 152, 153, 154, 155, 155, 156, 157, 158, 159, 159, 160, 161, 162, 163, 163, 164, - 165, 166, 167, 167, 168, 169, 170, 170, 171, 172, 173, 173, 174, 175, 175, 176, - 177, 178, 178, 179, 180, 180, 181, 182, 182, 183, 184, 185, 185, 186, 187, 187, - 188, 189, 189, 190, 190, 191, 192, 192, 193, 194, 194, 195, 196, 196, 197, 197, - 198, 199, 199, 200, 200, 201, 202, 202, 203, 203, 204, 205, 205, 206, 206, 207, - 208, 208, 209, 209, 210, 210, 211, 212, 212, 213, 213, 214, 214, 215, 215, 216, - 216, 217, 218, 218, 219, 219, 220, 220, 221, 221, 222, 222, 223, 223, 224, 224, - 225, 226, 226, 227, 227, 228, 228, 229, 229, 230, 230, 231, 231, 232, 232, 233, - 233, 234, 234, 235, 235, 236, 236, 237, 237, 238, 238, 238, 239, 239, 240, 240, - 241, 241, 242, 242, 243, 243, 244, 244, 245, 245, 246, 246, 246, 247, 247, 248, - 248, 249, 249, 250, 250, 251, 251, 251, 252, 252, 253, 253, 254, 254, 255, 255, + 120, 121, 122, 124, 125, 126, 127, 128, 129, 130, 131, 132, 133, 134, 135, + 136, 137, 138, 139, 140, 141, 142, 143, 144, 145, 146, 147, 148, 148, 149, + 150, 151, 152, 153, 154, 155, 155, 156, 157, 158, 159, 159, 160, 161, 162, + 163, 163, 164, 165, 166, 167, 167, 168, 169, 170, 170, 171, 172, 173, 173, + 174, 175, 175, 176, 177, 178, 178, 179, 180, 180, 181, 182, 182, 183, 184, + 185, 185, 186, 187, 187, 188, 189, 189, 190, 190, 191, 192, 192, 193, 194, + 194, 195, 196, 196, 197, 197, 198, 199, 199, 200, 200, 201, 202, 202, 203, + 203, 204, 205, 205, 206, 206, 207, 208, 208, 209, 209, 210, 210, 211, 212, + 212, 213, 213, 214, 214, 215, 215, 216, 216, 217, 218, 218, 219, 219, 220, + 220, 221, 221, 222, 222, 223, 223, 224, 224, 225, 226, 226, 227, 227, 228, + 228, 229, 229, 230, 230, 231, 231, 232, 232, 233, 233, 234, 234, 235, 235, + 236, 236, 237, 237, 238, 238, 238, 239, 239, 240, 240, 241, 241, 242, 242, + 243, 243, 244, 244, 245, 245, 246, 246, 246, 247, 247, 248, 248, 249, 249, + 250, 250, 251, 251, 251, 252, 252, 253, 253, 254, 254, 255, 255, }; -static FX_FLOAT RGB_Conversion(FX_FLOAT colorComponent) -{ - if (colorComponent > 1) { - colorComponent = 1; - } - if (colorComponent < 0) { - colorComponent = 0; - } - int scale = (int)(colorComponent * 1023); - if (scale < 0) { - scale = 0; - } - if (scale < 192) { - colorComponent = (g_sRGBSamples1[scale] / 255.0f); - } - else { - colorComponent = (g_sRGBSamples2[scale / 4 - 48] / 255.0f); - } - return colorComponent; +static FX_FLOAT RGB_Conversion(FX_FLOAT colorComponent) { + if (colorComponent > 1) { + colorComponent = 1; + } + if (colorComponent < 0) { + colorComponent = 0; + } + int scale = (int)(colorComponent * 1023); + if (scale < 0) { + scale = 0; + } + if (scale < 192) { + colorComponent = (g_sRGBSamples1[scale] / 255.0f); + } else { + colorComponent = (g_sRGBSamples2[scale / 4 - 48] / 255.0f); + } + return colorComponent; } -static void XYZ_to_sRGB(FX_FLOAT X, FX_FLOAT Y, FX_FLOAT Z, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) -{ - FX_FLOAT R1 = 3.2410f * X - 1.5374f * Y - 0.4986f * Z; - FX_FLOAT G1 = -0.9692f * X + 1.8760f * Y + 0.0416f * Z; - FX_FLOAT B1 = 0.0556f * X - 0.2040f * Y + 1.0570f * Z; +static void XYZ_to_sRGB(FX_FLOAT X, + FX_FLOAT Y, + FX_FLOAT Z, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) { + FX_FLOAT R1 = 3.2410f * X - 1.5374f * Y - 0.4986f * Z; + FX_FLOAT G1 = -0.9692f * X + 1.8760f * Y + 0.0416f * Z; + FX_FLOAT B1 = 0.0556f * X - 0.2040f * Y + 1.0570f * Z; - R = RGB_Conversion(R1); - G = RGB_Conversion(G1); - B = RGB_Conversion(B1); + R = RGB_Conversion(R1); + G = RGB_Conversion(G1); + B = RGB_Conversion(B1); } -static void XYZ_to_sRGB_WhitePoint(FX_FLOAT X, FX_FLOAT Y, FX_FLOAT Z, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B, FX_FLOAT Xw, FX_FLOAT Yw, FX_FLOAT Zw) -{ - // The following RGB_xyz is based on - // sRGB value {Rx,Ry}={0.64, 0.33}, {Gx,Gy}={0.30, 0.60}, {Bx,By}={0.15, 0.06} +static void XYZ_to_sRGB_WhitePoint(FX_FLOAT X, + FX_FLOAT Y, + FX_FLOAT Z, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B, + FX_FLOAT Xw, + FX_FLOAT Yw, + FX_FLOAT Zw) { + // The following RGB_xyz is based on + // sRGB value {Rx,Ry}={0.64, 0.33}, {Gx,Gy}={0.30, 0.60}, {Bx,By}={0.15, 0.06} - FX_FLOAT Rx = 0.64f, Ry = 0.33f; - FX_FLOAT Gx = 0.30f, Gy = 0.60f; - FX_FLOAT Bx = 0.15f, By = 0.06f; - CFX_Matrix_3by3 RGB_xyz(Rx, Gx, Bx, Ry, Gy, By, 1 - Rx - Ry, 1 - Gx - Gy, 1 - Bx - By); - CFX_Vector_3by1 whitePoint(Xw, Yw, Zw); - CFX_Vector_3by1 XYZ(X, Y, Z); + FX_FLOAT Rx = 0.64f, Ry = 0.33f; + FX_FLOAT Gx = 0.30f, Gy = 0.60f; + FX_FLOAT Bx = 0.15f, By = 0.06f; + CFX_Matrix_3by3 RGB_xyz(Rx, Gx, Bx, Ry, Gy, By, 1 - Rx - Ry, 1 - Gx - Gy, + 1 - Bx - By); + CFX_Vector_3by1 whitePoint(Xw, Yw, Zw); + CFX_Vector_3by1 XYZ(X, Y, Z); - CFX_Vector_3by1 RGB_Sum_XYZ = RGB_xyz.Inverse().TransformVector(whitePoint); - CFX_Matrix_3by3 RGB_SUM_XYZ_DIAG(RGB_Sum_XYZ.a, 0, 0, 0, RGB_Sum_XYZ.b, 0, 0, 0, RGB_Sum_XYZ.c); - CFX_Matrix_3by3 M = RGB_xyz.Multiply(RGB_SUM_XYZ_DIAG); - CFX_Vector_3by1 RGB = M.Inverse().TransformVector(XYZ); + CFX_Vector_3by1 RGB_Sum_XYZ = RGB_xyz.Inverse().TransformVector(whitePoint); + CFX_Matrix_3by3 RGB_SUM_XYZ_DIAG(RGB_Sum_XYZ.a, 0, 0, 0, RGB_Sum_XYZ.b, 0, 0, + 0, RGB_Sum_XYZ.c); + CFX_Matrix_3by3 M = RGB_xyz.Multiply(RGB_SUM_XYZ_DIAG); + CFX_Vector_3by1 RGB = M.Inverse().TransformVector(XYZ); - R = RGB_Conversion(RGB.a); - G = RGB_Conversion(RGB.b); - B = RGB_Conversion(RGB.c); -} -class CPDF_CalGray : public CPDF_ColorSpace -{ -public: - explicit CPDF_CalGray(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_CALGRAY, 1) { - } - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - FX_BOOL SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const override; - void TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, - int image_height, FX_BOOL bTransMask = FALSE) const override; + R = RGB_Conversion(RGB.a); + G = RGB_Conversion(RGB.b); + B = RGB_Conversion(RGB.c); +} +class CPDF_CalGray : public CPDF_ColorSpace { + public: + explicit CPDF_CalGray(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_CALGRAY, 1) {} + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + FX_BOOL SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const override; + void TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask = FALSE) const override; -private: - FX_FLOAT m_WhitePoint[3]; - FX_FLOAT m_BlackPoint[3]; - FX_FLOAT m_Gamma; + private: + FX_FLOAT m_WhitePoint[3]; + FX_FLOAT m_BlackPoint[3]; + FX_FLOAT m_Gamma; }; -FX_BOOL CPDF_CalGray::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CPDF_Dictionary* pDict = pArray->GetDict(1); - CPDF_Array* pParam = pDict->GetArray(FX_BSTRC("WhitePoint")); - int i; - for (i = 0; i < 3; i ++) { - m_WhitePoint[i] = pParam ? pParam->GetNumber(i) : 0; - } - pParam = pDict->GetArray(FX_BSTRC("BlackPoint")); - for (i = 0; i < 3; i ++) { - m_BlackPoint[i] = pParam ? pParam->GetNumber(i) : 0; - } - m_Gamma = pDict->GetNumber(FX_BSTRC("Gamma")); - if (m_Gamma == 0) { - m_Gamma = 1.0f; - } +FX_BOOL CPDF_CalGray::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CPDF_Dictionary* pDict = pArray->GetDict(1); + CPDF_Array* pParam = pDict->GetArray(FX_BSTRC("WhitePoint")); + int i; + for (i = 0; i < 3; i++) { + m_WhitePoint[i] = pParam ? pParam->GetNumber(i) : 0; + } + pParam = pDict->GetArray(FX_BSTRC("BlackPoint")); + for (i = 0; i < 3; i++) { + m_BlackPoint[i] = pParam ? pParam->GetNumber(i) : 0; + } + m_Gamma = pDict->GetNumber(FX_BSTRC("Gamma")); + if (m_Gamma == 0) { + m_Gamma = 1.0f; + } + return TRUE; +} +FX_BOOL CPDF_CalGray::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + R = G = B = *pBuf; + return TRUE; +} +FX_BOOL CPDF_CalGray::SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const { + if (R == G && R == B) { + *pBuf = R; return TRUE; -} -FX_BOOL CPDF_CalGray::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - R = G = B = *pBuf; - return TRUE; -} -FX_BOOL CPDF_CalGray::SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const -{ - if (R == G && R == B) { - *pBuf = R; - return TRUE; - } - return FALSE; -} -void CPDF_CalGray::TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, int image_height, FX_BOOL bTransMask) const -{ - for (int i = 0; i < pixels; i ++) { - *pDestBuf ++ = pSrcBuf[i]; - *pDestBuf ++ = pSrcBuf[i]; - *pDestBuf ++ = pSrcBuf[i]; - } -} -class CPDF_CalRGB : public CPDF_ColorSpace -{ -public: - explicit CPDF_CalRGB(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_CALRGB, 3) { - } - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - FX_BOOL SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const override; - void TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, - int image_height, FX_BOOL bTransMask = FALSE) const override; + } + return FALSE; +} +void CPDF_CalGray::TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask) const { + for (int i = 0; i < pixels; i++) { + *pDestBuf++ = pSrcBuf[i]; + *pDestBuf++ = pSrcBuf[i]; + *pDestBuf++ = pSrcBuf[i]; + } +} +class CPDF_CalRGB : public CPDF_ColorSpace { + public: + explicit CPDF_CalRGB(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_CALRGB, 3) {} + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + FX_BOOL SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const override; + void TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask = FALSE) const override; - FX_FLOAT m_WhitePoint[3]; - FX_FLOAT m_BlackPoint[3]; - FX_FLOAT m_Gamma[3]; - FX_FLOAT m_Matrix[9]; - FX_BOOL m_bGamma; - FX_BOOL m_bMatrix; + FX_FLOAT m_WhitePoint[3]; + FX_FLOAT m_BlackPoint[3]; + FX_FLOAT m_Gamma[3]; + FX_FLOAT m_Matrix[9]; + FX_BOOL m_bGamma; + FX_BOOL m_bMatrix; }; -FX_BOOL CPDF_CalRGB::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CPDF_Dictionary* pDict = pArray->GetDict(1); - if (!pDict) - return FALSE; +FX_BOOL CPDF_CalRGB::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CPDF_Dictionary* pDict = pArray->GetDict(1); + if (!pDict) + return FALSE; - CPDF_Array* pParam = pDict->GetArray(FX_BSTRC("WhitePoint")); - int i; - for (i = 0; i < 3; i ++) { - m_WhitePoint[i] = pParam ? pParam->GetNumber(i) : 0; - } - pParam = pDict->GetArray(FX_BSTRC("BlackPoint")); - for (i = 0; i < 3; i ++) { - m_BlackPoint[i] = pParam ? pParam->GetNumber(i) : 0; - } - pParam = pDict->GetArray(FX_BSTRC("Gamma")); - if (pParam) { - m_bGamma = TRUE; - for (i = 0; i < 3; i ++) { - m_Gamma[i] = pParam->GetNumber(i); - } - } else { - m_bGamma = FALSE; - } - pParam = pDict->GetArray(FX_BSTRC("Matrix")); - if (pParam) { - m_bMatrix = TRUE; - for (i = 0; i < 9; i ++) { - m_Matrix[i] = pParam->GetNumber(i); - } - } else { - m_bMatrix = FALSE; - } - return TRUE; -} -FX_BOOL CPDF_CalRGB::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - FX_FLOAT A_ = pBuf[0]; - FX_FLOAT B_ = pBuf[1]; - FX_FLOAT C_ = pBuf[2]; - if (m_bGamma) { - A_ = (FX_FLOAT)FXSYS_pow(A_, m_Gamma[0]); - B_ = (FX_FLOAT)FXSYS_pow(B_, m_Gamma[1]); - C_ = (FX_FLOAT)FXSYS_pow(C_, m_Gamma[2]); - } - FX_FLOAT X, Y, Z; - if (m_bMatrix) { - X = m_Matrix[0] * A_ + m_Matrix[3] * B_ + m_Matrix[6] * C_; - Y = m_Matrix[1] * A_ + m_Matrix[4] * B_ + m_Matrix[7] * C_; - Z = m_Matrix[2] * A_ + m_Matrix[5] * B_ + m_Matrix[8] * C_; - } else { - X = A_; - Y = B_; - Z = C_; - } - XYZ_to_sRGB_WhitePoint(X, Y, Z, R, G, B, m_WhitePoint[0], m_WhitePoint[1], m_WhitePoint[2]); - return TRUE; -} -FX_BOOL CPDF_CalRGB::SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const -{ - pBuf[0] = R; - pBuf[1] = G; - pBuf[2] = B; - return TRUE; -} -void CPDF_CalRGB::TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, int image_height, FX_BOOL bTransMask) const -{ - if (bTransMask) { - FX_FLOAT Cal[3]; - FX_FLOAT R, G, B; - for(int i = 0; i < pixels; i ++) { - Cal[0] = ((FX_FLOAT)pSrcBuf[2]) / 255; - Cal[1] = ((FX_FLOAT)pSrcBuf[1]) / 255; - Cal[2] = ((FX_FLOAT)pSrcBuf[0]) / 255; - GetRGB(Cal, R, G, B); - pDestBuf[0] = FXSYS_round(B * 255); - pDestBuf[1] = FXSYS_round(G * 255); - pDestBuf[2] = FXSYS_round(R * 255); - pSrcBuf += 3; - pDestBuf += 3; - } - } - ReverseRGB(pDestBuf, pSrcBuf, pixels); -} -class CPDF_LabCS : public CPDF_ColorSpace -{ -public: - explicit CPDF_LabCS(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_LAB, 3) { - } - void GetDefaultValue(int iComponent, FX_FLOAT& value, FX_FLOAT& min, FX_FLOAT& max) const override; - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - FX_BOOL SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const override; - void TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, - int image_height, FX_BOOL bTransMask = FALSE) const; + CPDF_Array* pParam = pDict->GetArray(FX_BSTRC("WhitePoint")); + int i; + for (i = 0; i < 3; i++) { + m_WhitePoint[i] = pParam ? pParam->GetNumber(i) : 0; + } + pParam = pDict->GetArray(FX_BSTRC("BlackPoint")); + for (i = 0; i < 3; i++) { + m_BlackPoint[i] = pParam ? pParam->GetNumber(i) : 0; + } + pParam = pDict->GetArray(FX_BSTRC("Gamma")); + if (pParam) { + m_bGamma = TRUE; + for (i = 0; i < 3; i++) { + m_Gamma[i] = pParam->GetNumber(i); + } + } else { + m_bGamma = FALSE; + } + pParam = pDict->GetArray(FX_BSTRC("Matrix")); + if (pParam) { + m_bMatrix = TRUE; + for (i = 0; i < 9; i++) { + m_Matrix[i] = pParam->GetNumber(i); + } + } else { + m_bMatrix = FALSE; + } + return TRUE; +} +FX_BOOL CPDF_CalRGB::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + FX_FLOAT A_ = pBuf[0]; + FX_FLOAT B_ = pBuf[1]; + FX_FLOAT C_ = pBuf[2]; + if (m_bGamma) { + A_ = (FX_FLOAT)FXSYS_pow(A_, m_Gamma[0]); + B_ = (FX_FLOAT)FXSYS_pow(B_, m_Gamma[1]); + C_ = (FX_FLOAT)FXSYS_pow(C_, m_Gamma[2]); + } + FX_FLOAT X, Y, Z; + if (m_bMatrix) { + X = m_Matrix[0] * A_ + m_Matrix[3] * B_ + m_Matrix[6] * C_; + Y = m_Matrix[1] * A_ + m_Matrix[4] * B_ + m_Matrix[7] * C_; + Z = m_Matrix[2] * A_ + m_Matrix[5] * B_ + m_Matrix[8] * C_; + } else { + X = A_; + Y = B_; + Z = C_; + } + XYZ_to_sRGB_WhitePoint(X, Y, Z, R, G, B, m_WhitePoint[0], m_WhitePoint[1], + m_WhitePoint[2]); + return TRUE; +} +FX_BOOL CPDF_CalRGB::SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const { + pBuf[0] = R; + pBuf[1] = G; + pBuf[2] = B; + return TRUE; +} +void CPDF_CalRGB::TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask) const { + if (bTransMask) { + FX_FLOAT Cal[3]; + FX_FLOAT R, G, B; + for (int i = 0; i < pixels; i++) { + Cal[0] = ((FX_FLOAT)pSrcBuf[2]) / 255; + Cal[1] = ((FX_FLOAT)pSrcBuf[1]) / 255; + Cal[2] = ((FX_FLOAT)pSrcBuf[0]) / 255; + GetRGB(Cal, R, G, B); + pDestBuf[0] = FXSYS_round(B * 255); + pDestBuf[1] = FXSYS_round(G * 255); + pDestBuf[2] = FXSYS_round(R * 255); + pSrcBuf += 3; + pDestBuf += 3; + } + } + ReverseRGB(pDestBuf, pSrcBuf, pixels); +} +class CPDF_LabCS : public CPDF_ColorSpace { + public: + explicit CPDF_LabCS(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_LAB, 3) {} + void GetDefaultValue(int iComponent, + FX_FLOAT& value, + FX_FLOAT& min, + FX_FLOAT& max) const override; + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + FX_BOOL SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const override; + void TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask = FALSE) const; - FX_FLOAT m_WhitePoint[3]; - FX_FLOAT m_BlackPoint[3]; - FX_FLOAT m_Ranges[4]; + FX_FLOAT m_WhitePoint[3]; + FX_FLOAT m_BlackPoint[3]; + FX_FLOAT m_Ranges[4]; }; -FX_BOOL CPDF_LabCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CPDF_Dictionary* pDict = pArray->GetDict(1); - if (!pDict) { - return FALSE; - } - CPDF_Array* pParam = pDict->GetArray(FX_BSTRC("WhitePoint")); - int i; - for (i = 0; i < 3; i ++) { - m_WhitePoint[i] = pParam ? pParam->GetNumber(i) : 0; - } - pParam = pDict->GetArray(FX_BSTRC("BlackPoint")); - for (i = 0; i < 3; i ++) { - m_BlackPoint[i] = pParam ? pParam->GetNumber(i) : 0; - } - pParam = pDict->GetArray(FX_BSTRC("Range")); - const FX_FLOAT def_ranges[4] = { -100 * 1.0f, 100 * 1.0f, -100 * 1.0f, 100 * 1.0f}; - for (i = 0; i < 4; i ++) { - m_Ranges[i] = pParam ? pParam->GetNumber(i) : def_ranges[i]; - } - return TRUE; -} -void CPDF_LabCS::GetDefaultValue(int iComponent, FX_FLOAT& value, FX_FLOAT& min, FX_FLOAT& max) const -{ - assert(iComponent < 3); - value = 0; - if (iComponent == 0) { - min = 0; - max = 100 * 1.0f; - } else { - min = m_Ranges[iComponent * 2 - 2]; - max = m_Ranges[iComponent * 2 - 1]; - if (value < min) { - value = min; - } else if (value > max) { - value = max; - } - } -} -FX_BOOL CPDF_LabCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - FX_FLOAT Lstar = pBuf[0]; - FX_FLOAT astar = pBuf[1]; - FX_FLOAT bstar = pBuf[2]; - FX_FLOAT M = (Lstar + 16.0f) / 116.0f; - FX_FLOAT L = M + astar / 500.0f; - FX_FLOAT N = M - bstar / 200.0f; - FX_FLOAT X, Y, Z; - if (L < 0.2069f) { - X = 0.957f * 0.12842f * (L - 0.1379f); - } else { - X = 0.957f * L * L * L; - } - if (M < 0.2069f) { - Y = 0.12842f * (M - 0.1379f); - } else { - Y = M * M * M; - } - if (N < 0.2069f) { - Z = 1.0889f * 0.12842f * (N - 0.1379f); - } else { - Z = 1.0889f * N * N * N; - } - XYZ_to_sRGB(X, Y, Z, R, G, B); - return TRUE; -} -FX_BOOL CPDF_LabCS::SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const -{ +FX_BOOL CPDF_LabCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CPDF_Dictionary* pDict = pArray->GetDict(1); + if (!pDict) { return FALSE; -} -void CPDF_LabCS::TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, int image_height, FX_BOOL bTransMask) const -{ - for (int i = 0; i < pixels; i ++) { - FX_FLOAT lab[3]; - FX_FLOAT R, G, B; - lab[0] = (pSrcBuf[0] * 100 / 255.0f); - lab[1] = (FX_FLOAT)(pSrcBuf[1] - 128); - lab[2] = (FX_FLOAT)(pSrcBuf[2] - 128); - GetRGB(lab, R, G, B); - pDestBuf[0] = (int32_t)(B * 255); - pDestBuf[1] = (int32_t)(G * 255); - pDestBuf[2] = (int32_t)(R * 255); - pDestBuf += 3; - pSrcBuf += 3; - } -} -CPDF_IccProfile::CPDF_IccProfile(const uint8_t* pData, FX_DWORD dwSize): - m_bsRGB(FALSE), - m_pTransform(NULL), - m_nSrcComponents(0) -{ - if (dwSize == 3144 && FXSYS_memcmp(pData + 0x190, "sRGB IEC61966-2.1", 17) == 0) { - m_bsRGB = TRUE; - m_nSrcComponents = 3; - } - else if (CPDF_ModuleMgr::Get()->GetIccModule()) { - m_pTransform = CPDF_ModuleMgr::Get()->GetIccModule()->CreateTransform_sRGB(pData, dwSize, m_nSrcComponents); - } -} -CPDF_IccProfile::~CPDF_IccProfile() -{ - if (m_pTransform) { - CPDF_ModuleMgr::Get()->GetIccModule()->DestroyTransform(m_pTransform); - } -} -class CPDF_ICCBasedCS : public CPDF_ColorSpace -{ -public: - explicit CPDF_ICCBasedCS(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_ICCBASED, 0), - m_pAlterCS(nullptr), - m_pProfile(nullptr), - m_pCache(nullptr), - m_pRanges(nullptr), - m_bOwn(FALSE) { - } - ~CPDF_ICCBasedCS() override; + } + CPDF_Array* pParam = pDict->GetArray(FX_BSTRC("WhitePoint")); + int i; + for (i = 0; i < 3; i++) { + m_WhitePoint[i] = pParam ? pParam->GetNumber(i) : 0; + } + pParam = pDict->GetArray(FX_BSTRC("BlackPoint")); + for (i = 0; i < 3; i++) { + m_BlackPoint[i] = pParam ? pParam->GetNumber(i) : 0; + } + pParam = pDict->GetArray(FX_BSTRC("Range")); + const FX_FLOAT def_ranges[4] = {-100 * 1.0f, 100 * 1.0f, -100 * 1.0f, + 100 * 1.0f}; + for (i = 0; i < 4; i++) { + m_Ranges[i] = pParam ? pParam->GetNumber(i) : def_ranges[i]; + } + return TRUE; +} +void CPDF_LabCS::GetDefaultValue(int iComponent, + FX_FLOAT& value, + FX_FLOAT& min, + FX_FLOAT& max) const { + assert(iComponent < 3); + value = 0; + if (iComponent == 0) { + min = 0; + max = 100 * 1.0f; + } else { + min = m_Ranges[iComponent * 2 - 2]; + max = m_Ranges[iComponent * 2 - 1]; + if (value < min) { + value = min; + } else if (value > max) { + value = max; + } + } +} +FX_BOOL CPDF_LabCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + FX_FLOAT Lstar = pBuf[0]; + FX_FLOAT astar = pBuf[1]; + FX_FLOAT bstar = pBuf[2]; + FX_FLOAT M = (Lstar + 16.0f) / 116.0f; + FX_FLOAT L = M + astar / 500.0f; + FX_FLOAT N = M - bstar / 200.0f; + FX_FLOAT X, Y, Z; + if (L < 0.2069f) { + X = 0.957f * 0.12842f * (L - 0.1379f); + } else { + X = 0.957f * L * L * L; + } + if (M < 0.2069f) { + Y = 0.12842f * (M - 0.1379f); + } else { + Y = M * M * M; + } + if (N < 0.2069f) { + Z = 1.0889f * 0.12842f * (N - 0.1379f); + } else { + Z = 1.0889f * N * N * N; + } + XYZ_to_sRGB(X, Y, Z, R, G, B); + return TRUE; +} +FX_BOOL CPDF_LabCS::SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const { + return FALSE; +} +void CPDF_LabCS::TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask) const { + for (int i = 0; i < pixels; i++) { + FX_FLOAT lab[3]; + FX_FLOAT R, G, B; + lab[0] = (pSrcBuf[0] * 100 / 255.0f); + lab[1] = (FX_FLOAT)(pSrcBuf[1] - 128); + lab[2] = (FX_FLOAT)(pSrcBuf[2] - 128); + GetRGB(lab, R, G, B); + pDestBuf[0] = (int32_t)(B * 255); + pDestBuf[1] = (int32_t)(G * 255); + pDestBuf[2] = (int32_t)(R * 255); + pDestBuf += 3; + pSrcBuf += 3; + } +} +CPDF_IccProfile::CPDF_IccProfile(const uint8_t* pData, FX_DWORD dwSize) + : m_bsRGB(FALSE), m_pTransform(NULL), m_nSrcComponents(0) { + if (dwSize == 3144 && + FXSYS_memcmp(pData + 0x190, "sRGB IEC61966-2.1", 17) == 0) { + m_bsRGB = TRUE; + m_nSrcComponents = 3; + } else if (CPDF_ModuleMgr::Get()->GetIccModule()) { + m_pTransform = CPDF_ModuleMgr::Get()->GetIccModule()->CreateTransform_sRGB( + pData, dwSize, m_nSrcComponents); + } +} +CPDF_IccProfile::~CPDF_IccProfile() { + if (m_pTransform) { + CPDF_ModuleMgr::Get()->GetIccModule()->DestroyTransform(m_pTransform); + } +} +class CPDF_ICCBasedCS : public CPDF_ColorSpace { + public: + explicit CPDF_ICCBasedCS(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_ICCBASED, 0), + m_pAlterCS(nullptr), + m_pProfile(nullptr), + m_pCache(nullptr), + m_pRanges(nullptr), + m_bOwn(FALSE) {} + ~CPDF_ICCBasedCS() override; - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - FX_BOOL SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const override; - FX_BOOL v_GetCMYK(FX_FLOAT* pBuf, FX_FLOAT& c, FX_FLOAT& m, FX_FLOAT& y, FX_FLOAT& k) const override; - void EnableStdConversion(FX_BOOL bEnabled) override; - void TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, - int image_height, FX_BOOL bTransMask = FALSE) const override; + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + FX_BOOL SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const override; + FX_BOOL v_GetCMYK(FX_FLOAT* pBuf, + FX_FLOAT& c, + FX_FLOAT& m, + FX_FLOAT& y, + FX_FLOAT& k) const override; + void EnableStdConversion(FX_BOOL bEnabled) override; + void TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask = FALSE) const override; - CPDF_ColorSpace* m_pAlterCS; - CPDF_IccProfile* m_pProfile; - uint8_t* m_pCache; - FX_FLOAT* m_pRanges; - FX_BOOL m_bOwn; + CPDF_ColorSpace* m_pAlterCS; + CPDF_IccProfile* m_pProfile; + uint8_t* m_pCache; + FX_FLOAT* m_pRanges; + FX_BOOL m_bOwn; }; -CPDF_ICCBasedCS::~CPDF_ICCBasedCS() -{ - if (m_pCache) { - FX_Free(m_pCache); - } - if (m_pRanges) { - FX_Free(m_pRanges); - } - if (m_pAlterCS && m_bOwn) { - m_pAlterCS->ReleaseCS(); - } - if (m_pProfile && m_pDocument) { - m_pDocument->GetPageData()->ReleaseIccProfile(m_pProfile); - } +CPDF_ICCBasedCS::~CPDF_ICCBasedCS() { + if (m_pCache) { + FX_Free(m_pCache); + } + if (m_pRanges) { + FX_Free(m_pRanges); + } + if (m_pAlterCS && m_bOwn) { + m_pAlterCS->ReleaseCS(); + } + if (m_pProfile && m_pDocument) { + m_pDocument->GetPageData()->ReleaseIccProfile(m_pProfile); + } } -FX_BOOL CPDF_ICCBasedCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CPDF_Stream* pStream = pArray->GetStream(1); - if (pStream == NULL) { - return FALSE; - } - m_pProfile = pDoc->LoadIccProfile(pStream); - if (!m_pProfile) { - return FALSE; - } - m_nComponents = m_pProfile->GetComponents(); //Try using the nComponents from ICC profile - CPDF_Dictionary* pDict = pStream->GetDict(); - if (m_pProfile->m_pTransform == NULL) { // No valid ICC profile or using sRGB - CPDF_Object* pAlterCSObj = pDict ? pDict->GetElementValue(FX_BSTRC("Alternate")) : NULL; - if (pAlterCSObj) { - CPDF_ColorSpace* pAlterCS = CPDF_ColorSpace::Load(pDoc, pAlterCSObj); - if (pAlterCS) { - if (m_nComponents == 0) { // NO valid ICC profile - if (pAlterCS->CountComponents() > 0) { // Use Alternative colorspace - m_nComponents = pAlterCS->CountComponents(); - m_pAlterCS = pAlterCS; - m_bOwn = TRUE; - } - else { // No valid alternative colorspace - pAlterCS->ReleaseCS(); - int32_t nDictComponents = pDict ? pDict->GetInteger(FX_BSTRC("N")) : 0; - if (nDictComponents != 1 && nDictComponents != 3 && nDictComponents != 4) { - return FALSE; - } - m_nComponents = nDictComponents; - } - - } - else { // Using sRGB - if (pAlterCS->CountComponents() != m_nComponents) { - pAlterCS->ReleaseCS(); - } - else { - m_pAlterCS = pAlterCS; - m_bOwn = TRUE; - } - } - } - } - if (!m_pAlterCS) { - if (m_nComponents == 1) { - m_pAlterCS = GetStockCS(PDFCS_DEVICEGRAY); - } - else if (m_nComponents == 3) { - m_pAlterCS = GetStockCS(PDFCS_DEVICERGB); - } - else if (m_nComponents == 4) { - m_pAlterCS = GetStockCS(PDFCS_DEVICECMYK); +FX_BOOL CPDF_ICCBasedCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CPDF_Stream* pStream = pArray->GetStream(1); + if (pStream == NULL) { + return FALSE; + } + m_pProfile = pDoc->LoadIccProfile(pStream); + if (!m_pProfile) { + return FALSE; + } + m_nComponents = + m_pProfile + ->GetComponents(); // Try using the nComponents from ICC profile + CPDF_Dictionary* pDict = pStream->GetDict(); + if (m_pProfile->m_pTransform == NULL) { // No valid ICC profile or using sRGB + CPDF_Object* pAlterCSObj = + pDict ? pDict->GetElementValue(FX_BSTRC("Alternate")) : NULL; + if (pAlterCSObj) { + CPDF_ColorSpace* pAlterCS = CPDF_ColorSpace::Load(pDoc, pAlterCSObj); + if (pAlterCS) { + if (m_nComponents == 0) { // NO valid ICC profile + if (pAlterCS->CountComponents() > 0) { // Use Alternative colorspace + m_nComponents = pAlterCS->CountComponents(); + m_pAlterCS = pAlterCS; + m_bOwn = TRUE; + } else { // No valid alternative colorspace + pAlterCS->ReleaseCS(); + int32_t nDictComponents = + pDict ? pDict->GetInteger(FX_BSTRC("N")) : 0; + if (nDictComponents != 1 && nDictComponents != 3 && + nDictComponents != 4) { + return FALSE; } + m_nComponents = nDictComponents; + } + + } else { // Using sRGB + if (pAlterCS->CountComponents() != m_nComponents) { + pAlterCS->ReleaseCS(); + } else { + m_pAlterCS = pAlterCS; + m_bOwn = TRUE; + } } - } - CPDF_Array* pRanges = pDict->GetArray(FX_BSTRC("Range")); - m_pRanges = FX_Alloc2D(FX_FLOAT, m_nComponents, 2); - for (int i = 0; i < m_nComponents * 2; i ++) { - if (pRanges) { - m_pRanges[i] = pRanges->GetNumber(i); - } else if (i % 2) { - m_pRanges[i] = 1.0f; - } else { - m_pRanges[i] = 0; - } - } - return TRUE; -} -FX_BOOL CPDF_ICCBasedCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - if (m_pProfile && m_pProfile->m_bsRGB) { - R = pBuf[0]; - G = pBuf[1]; - B = pBuf[2]; - return TRUE; - } - ICodec_IccModule *pIccModule = CPDF_ModuleMgr::Get()->GetIccModule(); - if (m_pProfile->m_pTransform == NULL || pIccModule == NULL) { - if (m_pAlterCS) { - m_pAlterCS->GetRGB(pBuf, R, G, B); - } else { - R = G = B = 0.0f; - } - return TRUE; - } - FX_FLOAT rgb[3]; - pIccModule->SetComponents(m_nComponents); - pIccModule->Translate(m_pProfile->m_pTransform, pBuf, rgb); - R = rgb[0]; - G = rgb[1]; - B = rgb[2]; + } + } + if (!m_pAlterCS) { + if (m_nComponents == 1) { + m_pAlterCS = GetStockCS(PDFCS_DEVICEGRAY); + } else if (m_nComponents == 3) { + m_pAlterCS = GetStockCS(PDFCS_DEVICERGB); + } else if (m_nComponents == 4) { + m_pAlterCS = GetStockCS(PDFCS_DEVICECMYK); + } + } + } + CPDF_Array* pRanges = pDict->GetArray(FX_BSTRC("Range")); + m_pRanges = FX_Alloc2D(FX_FLOAT, m_nComponents, 2); + for (int i = 0; i < m_nComponents * 2; i++) { + if (pRanges) { + m_pRanges[i] = pRanges->GetNumber(i); + } else if (i % 2) { + m_pRanges[i] = 1.0f; + } else { + m_pRanges[i] = 0; + } + } + return TRUE; +} +FX_BOOL CPDF_ICCBasedCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + if (m_pProfile && m_pProfile->m_bsRGB) { + R = pBuf[0]; + G = pBuf[1]; + B = pBuf[2]; return TRUE; -} -FX_BOOL CPDF_ICCBasedCS::v_GetCMYK(FX_FLOAT* pBuf, FX_FLOAT& c, FX_FLOAT& m, FX_FLOAT& y, FX_FLOAT& k) const -{ - if (m_nComponents != 4) { - return FALSE; + } + ICodec_IccModule* pIccModule = CPDF_ModuleMgr::Get()->GetIccModule(); + if (m_pProfile->m_pTransform == NULL || pIccModule == NULL) { + if (m_pAlterCS) { + m_pAlterCS->GetRGB(pBuf, R, G, B); + } else { + R = G = B = 0.0f; } - c = pBuf[0]; - m = pBuf[1]; - y = pBuf[2]; - k = pBuf[3]; return TRUE; -} -FX_BOOL CPDF_ICCBasedCS::SetRGB(FX_FLOAT* pBuf, FX_FLOAT R, FX_FLOAT G, FX_FLOAT B) const -{ + } + FX_FLOAT rgb[3]; + pIccModule->SetComponents(m_nComponents); + pIccModule->Translate(m_pProfile->m_pTransform, pBuf, rgb); + R = rgb[0]; + G = rgb[1]; + B = rgb[2]; + return TRUE; +} +FX_BOOL CPDF_ICCBasedCS::v_GetCMYK(FX_FLOAT* pBuf, + FX_FLOAT& c, + FX_FLOAT& m, + FX_FLOAT& y, + FX_FLOAT& k) const { + if (m_nComponents != 4) { return FALSE; -} -void CPDF_ICCBasedCS::EnableStdConversion(FX_BOOL bEnabled) -{ - CPDF_ColorSpace::EnableStdConversion(bEnabled); - if (m_pAlterCS) { - m_pAlterCS->EnableStdConversion(bEnabled); - } -} -void CPDF_ICCBasedCS::TranslateImageLine(uint8_t* pDestBuf, const uint8_t* pSrcBuf, int pixels, int image_width, int image_height, FX_BOOL bTransMask) const -{ - if (m_pProfile->m_bsRGB) { - ReverseRGB(pDestBuf, pSrcBuf, pixels); - } else if (m_pProfile->m_pTransform) { - int nMaxColors = 1; - for (int i = 0; i < m_nComponents; i ++) { - nMaxColors *= 52; + } + c = pBuf[0]; + m = pBuf[1]; + y = pBuf[2]; + k = pBuf[3]; + return TRUE; +} +FX_BOOL CPDF_ICCBasedCS::SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const { + return FALSE; +} +void CPDF_ICCBasedCS::EnableStdConversion(FX_BOOL bEnabled) { + CPDF_ColorSpace::EnableStdConversion(bEnabled); + if (m_pAlterCS) { + m_pAlterCS->EnableStdConversion(bEnabled); + } +} +void CPDF_ICCBasedCS::TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask) const { + if (m_pProfile->m_bsRGB) { + ReverseRGB(pDestBuf, pSrcBuf, pixels); + } else if (m_pProfile->m_pTransform) { + int nMaxColors = 1; + for (int i = 0; i < m_nComponents; i++) { + nMaxColors *= 52; + } + if (m_nComponents > 3 || image_width * image_height < nMaxColors * 3 / 2) { + CPDF_ModuleMgr::Get()->GetIccModule()->TranslateScanline( + m_pProfile->m_pTransform, pDestBuf, pSrcBuf, pixels); + } else { + if (m_pCache == NULL) { + ((CPDF_ICCBasedCS*)this)->m_pCache = FX_Alloc2D(uint8_t, nMaxColors, 3); + uint8_t* temp_src = FX_Alloc2D(uint8_t, nMaxColors, m_nComponents); + uint8_t* pSrc = temp_src; + for (int i = 0; i < nMaxColors; i++) { + FX_DWORD color = i; + FX_DWORD order = nMaxColors / 52; + for (int c = 0; c < m_nComponents; c++) { + *pSrc++ = (uint8_t)(color / order * 5); + color %= order; + order /= 52; + } } - if (m_nComponents > 3 || image_width * image_height < nMaxColors * 3 / 2) { - CPDF_ModuleMgr::Get()->GetIccModule()->TranslateScanline(m_pProfile->m_pTransform, pDestBuf, pSrcBuf, pixels); - } else { - if (m_pCache == NULL) { - ((CPDF_ICCBasedCS*)this)->m_pCache = FX_Alloc2D(uint8_t, nMaxColors, 3); - uint8_t* temp_src = FX_Alloc2D(uint8_t, nMaxColors, m_nComponents); - uint8_t* pSrc = temp_src; - for (int i = 0; i < nMaxColors; i ++) { - FX_DWORD color = i; - FX_DWORD order = nMaxColors / 52; - for (int c = 0; c < m_nComponents; c ++) { - *pSrc++ = (uint8_t)(color / order * 5); - color %= order; - order /= 52; - } - } - CPDF_ModuleMgr::Get()->GetIccModule()->TranslateScanline(m_pProfile->m_pTransform, m_pCache, temp_src, nMaxColors); - FX_Free(temp_src); - } - for (int i = 0; i < pixels; i ++) { - int index = 0; - for (int c = 0; c < m_nComponents; c ++) { - index = index * 52 + (*pSrcBuf) / 5; - pSrcBuf ++; - } - index *= 3; - *pDestBuf++ = m_pCache[index]; - *pDestBuf++ = m_pCache[index + 1]; - *pDestBuf++ = m_pCache[index + 2]; - } + CPDF_ModuleMgr::Get()->GetIccModule()->TranslateScanline( + m_pProfile->m_pTransform, m_pCache, temp_src, nMaxColors); + FX_Free(temp_src); + } + for (int i = 0; i < pixels; i++) { + int index = 0; + for (int c = 0; c < m_nComponents; c++) { + index = index * 52 + (*pSrcBuf) / 5; + pSrcBuf++; } - } else if (m_pAlterCS) { - m_pAlterCS->TranslateImageLine(pDestBuf, pSrcBuf, pixels, image_width, image_height); - } -} -class CPDF_IndexedCS : public CPDF_ColorSpace -{ -public: - explicit CPDF_IndexedCS(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_INDEXED, 1), - m_pBaseCS(nullptr), - m_pCountedBaseCS(nullptr), - m_pCompMinMax(nullptr) { - } - ~CPDF_IndexedCS() override; + index *= 3; + *pDestBuf++ = m_pCache[index]; + *pDestBuf++ = m_pCache[index + 1]; + *pDestBuf++ = m_pCache[index + 2]; + } + } + } else if (m_pAlterCS) { + m_pAlterCS->TranslateImageLine(pDestBuf, pSrcBuf, pixels, image_width, + image_height); + } +} +class CPDF_IndexedCS : public CPDF_ColorSpace { + public: + explicit CPDF_IndexedCS(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_INDEXED, 1), + m_pBaseCS(nullptr), + m_pCountedBaseCS(nullptr), + m_pCompMinMax(nullptr) {} + ~CPDF_IndexedCS() override; - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - CPDF_ColorSpace* GetBaseCS() const override; - void EnableStdConversion(FX_BOOL bEnabled) override; + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + CPDF_ColorSpace* GetBaseCS() const override; + void EnableStdConversion(FX_BOOL bEnabled) override; - CPDF_ColorSpace* m_pBaseCS; - CPDF_CountedColorSpace* m_pCountedBaseCS; - int m_nBaseComponents; - int m_MaxIndex; - CFX_ByteString m_Table; - FX_FLOAT* m_pCompMinMax; + CPDF_ColorSpace* m_pBaseCS; + CPDF_CountedColorSpace* m_pCountedBaseCS; + int m_nBaseComponents; + int m_MaxIndex; + CFX_ByteString m_Table; + FX_FLOAT* m_pCompMinMax; }; -CPDF_IndexedCS::~CPDF_IndexedCS() -{ - if (m_pCompMinMax) { - FX_Free(m_pCompMinMax); - } - CPDF_ColorSpace* pCS = m_pCountedBaseCS ? m_pCountedBaseCS->get() : NULL; - if (pCS && m_pDocument) { - m_pDocument->GetPageData()->ReleaseColorSpace(pCS->GetArray()); - } -} -FX_BOOL CPDF_IndexedCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - if (pArray->GetCount() < 4) { - return FALSE; - } - CPDF_Object* pBaseObj = pArray->GetElementValue(1); - if (pBaseObj == m_pArray) { - return FALSE; - } - CPDF_DocPageData* pDocPageData = pDoc->GetPageData(); - m_pBaseCS = pDocPageData->GetColorSpace(pBaseObj, NULL); - if (m_pBaseCS == NULL) { - return FALSE; - } - m_pCountedBaseCS = pDocPageData->FindColorSpacePtr(m_pBaseCS->GetArray()); - m_nBaseComponents = m_pBaseCS->CountComponents(); - m_pCompMinMax = FX_Alloc2D(FX_FLOAT, m_nBaseComponents, 2); - FX_FLOAT defvalue; - for (int i = 0; i < m_nBaseComponents; i ++) { - m_pBaseCS->GetDefaultValue(i, defvalue, m_pCompMinMax[i * 2], m_pCompMinMax[i * 2 + 1]); - m_pCompMinMax[i * 2 + 1] -= m_pCompMinMax[i * 2]; - } - m_MaxIndex = pArray->GetInteger(2); - CPDF_Object* pTableObj = pArray->GetElementValue(3); - if (pTableObj == NULL) { - return FALSE; - } - if (pTableObj->GetType() == PDFOBJ_STRING) { - m_Table = ((CPDF_String*)pTableObj)->GetString(); - } else if (pTableObj->GetType() == PDFOBJ_STREAM) { - CPDF_StreamAcc acc; - acc.LoadAllData((CPDF_Stream*)pTableObj, FALSE); - m_Table = CFX_ByteStringC(acc.GetData(), acc.GetSize()); - } - return TRUE; +CPDF_IndexedCS::~CPDF_IndexedCS() { + if (m_pCompMinMax) { + FX_Free(m_pCompMinMax); + } + CPDF_ColorSpace* pCS = m_pCountedBaseCS ? m_pCountedBaseCS->get() : NULL; + if (pCS && m_pDocument) { + m_pDocument->GetPageData()->ReleaseColorSpace(pCS->GetArray()); + } +} +FX_BOOL CPDF_IndexedCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + if (pArray->GetCount() < 4) { + return FALSE; + } + CPDF_Object* pBaseObj = pArray->GetElementValue(1); + if (pBaseObj == m_pArray) { + return FALSE; + } + CPDF_DocPageData* pDocPageData = pDoc->GetPageData(); + m_pBaseCS = pDocPageData->GetColorSpace(pBaseObj, NULL); + if (m_pBaseCS == NULL) { + return FALSE; + } + m_pCountedBaseCS = pDocPageData->FindColorSpacePtr(m_pBaseCS->GetArray()); + m_nBaseComponents = m_pBaseCS->CountComponents(); + m_pCompMinMax = FX_Alloc2D(FX_FLOAT, m_nBaseComponents, 2); + FX_FLOAT defvalue; + for (int i = 0; i < m_nBaseComponents; i++) { + m_pBaseCS->GetDefaultValue(i, defvalue, m_pCompMinMax[i * 2], + m_pCompMinMax[i * 2 + 1]); + m_pCompMinMax[i * 2 + 1] -= m_pCompMinMax[i * 2]; + } + m_MaxIndex = pArray->GetInteger(2); + CPDF_Object* pTableObj = pArray->GetElementValue(3); + if (pTableObj == NULL) { + return FALSE; + } + if (pTableObj->GetType() == PDFOBJ_STRING) { + m_Table = ((CPDF_String*)pTableObj)->GetString(); + } else if (pTableObj->GetType() == PDFOBJ_STREAM) { + CPDF_StreamAcc acc; + acc.LoadAllData((CPDF_Stream*)pTableObj, FALSE); + m_Table = CFX_ByteStringC(acc.GetData(), acc.GetSize()); + } + return TRUE; } -FX_BOOL CPDF_IndexedCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - int index = (int32_t)(*pBuf); - if (index < 0 || index > m_MaxIndex) { - return FALSE; - } - if (m_nBaseComponents) { - if (index == INT_MAX || (index + 1) > INT_MAX / m_nBaseComponents || - (index + 1)*m_nBaseComponents > (int)m_Table.GetLength()) { - R = G = B = 0; - return FALSE; - } - } - CFX_FixedBufGrow Comps(m_nBaseComponents); - FX_FLOAT* comps = Comps; - const uint8_t* pTable = m_Table; - for (int i = 0; i < m_nBaseComponents; i ++) { - comps[i] = m_pCompMinMax[i * 2] + m_pCompMinMax[i * 2 + 1] * pTable[index * m_nBaseComponents + i] / 255; - } - m_pBaseCS->GetRGB(comps, R, G, B); - return TRUE; -} -CPDF_ColorSpace*CPDF_IndexedCS::GetBaseCS() const -{ - return m_pBaseCS; -} -void CPDF_IndexedCS::EnableStdConversion(FX_BOOL bEnabled) -{ - CPDF_ColorSpace::EnableStdConversion(bEnabled); - if (m_pBaseCS) { - m_pBaseCS->EnableStdConversion(bEnabled); - } -} -#define MAX_PATTERN_COLORCOMPS 16 +FX_BOOL CPDF_IndexedCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + int index = (int32_t)(*pBuf); + if (index < 0 || index > m_MaxIndex) { + return FALSE; + } + if (m_nBaseComponents) { + if (index == INT_MAX || (index + 1) > INT_MAX / m_nBaseComponents || + (index + 1) * m_nBaseComponents > (int)m_Table.GetLength()) { + R = G = B = 0; + return FALSE; + } + } + CFX_FixedBufGrow Comps(m_nBaseComponents); + FX_FLOAT* comps = Comps; + const uint8_t* pTable = m_Table; + for (int i = 0; i < m_nBaseComponents; i++) { + comps[i] = + m_pCompMinMax[i * 2] + + m_pCompMinMax[i * 2 + 1] * pTable[index * m_nBaseComponents + i] / 255; + } + m_pBaseCS->GetRGB(comps, R, G, B); + return TRUE; +} +CPDF_ColorSpace* CPDF_IndexedCS::GetBaseCS() const { + return m_pBaseCS; +} +void CPDF_IndexedCS::EnableStdConversion(FX_BOOL bEnabled) { + CPDF_ColorSpace::EnableStdConversion(bEnabled); + if (m_pBaseCS) { + m_pBaseCS->EnableStdConversion(bEnabled); + } +} +#define MAX_PATTERN_COLORCOMPS 16 typedef struct _PatternValue { - CPDF_Pattern* m_pPattern; - CPDF_CountedPattern* m_pCountedPattern; - int m_nComps; - FX_FLOAT m_Comps[MAX_PATTERN_COLORCOMPS]; + CPDF_Pattern* m_pPattern; + CPDF_CountedPattern* m_pCountedPattern; + int m_nComps; + FX_FLOAT m_Comps[MAX_PATTERN_COLORCOMPS]; } PatternValue; -CPDF_PatternCS::~CPDF_PatternCS() -{ - CPDF_ColorSpace* pCS = m_pCountedBaseCS ? m_pCountedBaseCS->get() : NULL; - if (pCS && m_pDocument) { - m_pDocument->GetPageData()->ReleaseColorSpace(pCS->GetArray()); - } -} -FX_BOOL CPDF_PatternCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CPDF_Object* pBaseCS = pArray->GetElementValue(1); - if (pBaseCS == m_pArray) { - return FALSE; - } - CPDF_DocPageData* pDocPageData = pDoc->GetPageData(); - m_pBaseCS = pDocPageData->GetColorSpace(pBaseCS, NULL); - if (m_pBaseCS) { - if (m_pBaseCS->GetFamily() == PDFCS_PATTERN) { - return FALSE; - } - m_pCountedBaseCS = pDocPageData->FindColorSpacePtr(m_pBaseCS->GetArray()); - m_nComponents = m_pBaseCS->CountComponents() + 1; - if (m_pBaseCS->CountComponents() > MAX_PATTERN_COLORCOMPS) { - return FALSE; - } - } else { - m_nComponents = 1; - } - return TRUE; -} -FX_BOOL CPDF_PatternCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - if (m_pBaseCS) { - ASSERT(m_pBaseCS->GetFamily() != PDFCS_PATTERN); - PatternValue* pvalue = (PatternValue*)pBuf; - if (m_pBaseCS->GetRGB(pvalue->m_Comps, R, G, B)) { - return TRUE; - } - } - R = G = B = 0.75f; - return FALSE; -} -CPDF_ColorSpace* CPDF_PatternCS::GetBaseCS() const -{ - return m_pBaseCS; -} -class CPDF_SeparationCS : public CPDF_ColorSpace -{ -public: - CPDF_SeparationCS(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_SEPARATION, 1), - m_pAltCS(nullptr), - m_pFunc(nullptr) { - } - ~CPDF_SeparationCS() override; - void GetDefaultValue(int iComponent, FX_FLOAT& value, FX_FLOAT& min, FX_FLOAT& max) const override; - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - void EnableStdConversion(FX_BOOL bEnabled) override; - - CPDF_ColorSpace* m_pAltCS; - CPDF_Function* m_pFunc; - enum { None, All, Colorant } m_Type; -}; -CPDF_SeparationCS::~CPDF_SeparationCS() -{ - if (m_pAltCS) { - m_pAltCS->ReleaseCS(); - } - delete m_pFunc; -} -void CPDF_SeparationCS::GetDefaultValue(int iComponent, FX_FLOAT& value, FX_FLOAT& min, FX_FLOAT& max) const -{ - value = 1.0f; - min = 0; - max = 1.0f; -} -FX_BOOL CPDF_SeparationCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CFX_ByteString name = pArray->GetString(1); - if (name == FX_BSTRC("None")) { - m_Type = None; - } else { - m_Type = Colorant; - CPDF_Object* pAltCS = pArray->GetElementValue(2); - if (pAltCS == m_pArray) { - return FALSE; - } - m_pAltCS = Load(pDoc, pAltCS); - if (!m_pAltCS) { - return FALSE; - } - CPDF_Object* pFuncObj = pArray->GetElementValue(3); - if (pFuncObj && pFuncObj->GetType() != PDFOBJ_NAME) { - m_pFunc = CPDF_Function::Load(pFuncObj); - } - if (m_pFunc && m_pFunc->CountOutputs() < m_pAltCS->CountComponents()) { - delete m_pFunc; - m_pFunc = NULL; - } - } - return TRUE; -} -FX_BOOL CPDF_SeparationCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - if (m_Type == None) { - return FALSE; - } - if (m_pFunc == NULL) { - if (m_pAltCS == NULL) { - return FALSE; - } - int nComps = m_pAltCS->CountComponents(); - CFX_FixedBufGrow results(nComps); - for (int i = 0; i < nComps; i ++) { - results[i] = *pBuf; - } - m_pAltCS->GetRGB(results, R, G, B); - return TRUE; - } - CFX_FixedBufGrow results(m_pFunc->CountOutputs()); - int nresults = 0; - m_pFunc->Call(pBuf, 1, results, nresults); - if (nresults == 0) { - return FALSE; - } - if (m_pAltCS) { - m_pAltCS->GetRGB(results, R, G, B); - return TRUE; - } - R = G = B = 0; +CPDF_PatternCS::~CPDF_PatternCS() { + CPDF_ColorSpace* pCS = m_pCountedBaseCS ? m_pCountedBaseCS->get() : NULL; + if (pCS && m_pDocument) { + m_pDocument->GetPageData()->ReleaseColorSpace(pCS->GetArray()); + } +} +FX_BOOL CPDF_PatternCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CPDF_Object* pBaseCS = pArray->GetElementValue(1); + if (pBaseCS == m_pArray) { return FALSE; -} -void CPDF_SeparationCS::EnableStdConversion(FX_BOOL bEnabled) -{ - CPDF_ColorSpace::EnableStdConversion(bEnabled); - if (m_pAltCS) { - m_pAltCS->EnableStdConversion(bEnabled); + } + CPDF_DocPageData* pDocPageData = pDoc->GetPageData(); + m_pBaseCS = pDocPageData->GetColorSpace(pBaseCS, NULL); + if (m_pBaseCS) { + if (m_pBaseCS->GetFamily() == PDFCS_PATTERN) { + return FALSE; } -} -class CPDF_DeviceNCS : public CPDF_ColorSpace -{ -public: - CPDF_DeviceNCS(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_DEVICEN, 0), - m_pAltCS(nullptr), - m_pFunc(nullptr) { - } - ~CPDF_DeviceNCS() override; - void GetDefaultValue(int iComponent, FX_FLOAT& value, FX_FLOAT& min, FX_FLOAT& max) const override; - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const override; - void EnableStdConversion(FX_BOOL bEnabled) override; + m_pCountedBaseCS = pDocPageData->FindColorSpacePtr(m_pBaseCS->GetArray()); + m_nComponents = m_pBaseCS->CountComponents() + 1; + if (m_pBaseCS->CountComponents() > MAX_PATTERN_COLORCOMPS) { + return FALSE; + } + } else { + m_nComponents = 1; + } + return TRUE; +} +FX_BOOL CPDF_PatternCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + if (m_pBaseCS) { + ASSERT(m_pBaseCS->GetFamily() != PDFCS_PATTERN); + PatternValue* pvalue = (PatternValue*)pBuf; + if (m_pBaseCS->GetRGB(pvalue->m_Comps, R, G, B)) { + return TRUE; + } + } + R = G = B = 0.75f; + return FALSE; +} +CPDF_ColorSpace* CPDF_PatternCS::GetBaseCS() const { + return m_pBaseCS; +} +class CPDF_SeparationCS : public CPDF_ColorSpace { + public: + CPDF_SeparationCS(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_SEPARATION, 1), + m_pAltCS(nullptr), + m_pFunc(nullptr) {} + ~CPDF_SeparationCS() override; + void GetDefaultValue(int iComponent, + FX_FLOAT& value, + FX_FLOAT& min, + FX_FLOAT& max) const override; + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + void EnableStdConversion(FX_BOOL bEnabled) override; - CPDF_ColorSpace* m_pAltCS; - CPDF_Function* m_pFunc; + CPDF_ColorSpace* m_pAltCS; + CPDF_Function* m_pFunc; + enum { None, All, Colorant } m_Type; }; -CPDF_DeviceNCS::~CPDF_DeviceNCS() -{ - delete m_pFunc; - if (m_pAltCS) { - m_pAltCS->ReleaseCS(); - } -} -void CPDF_DeviceNCS::GetDefaultValue(int iComponent, FX_FLOAT& value, FX_FLOAT& min, FX_FLOAT& max) const -{ - value = 1.0f; - min = 0; - max = 1.0f; -} -FX_BOOL CPDF_DeviceNCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) -{ - CPDF_Object* pObj = pArray->GetElementValue(1); - if (!pObj) { - return FALSE; - } - if (pObj->GetType() != PDFOBJ_ARRAY) { - return FALSE; - } - m_nComponents = ((CPDF_Array*)pObj)->GetCount(); +CPDF_SeparationCS::~CPDF_SeparationCS() { + if (m_pAltCS) { + m_pAltCS->ReleaseCS(); + } + delete m_pFunc; +} +void CPDF_SeparationCS::GetDefaultValue(int iComponent, + FX_FLOAT& value, + FX_FLOAT& min, + FX_FLOAT& max) const { + value = 1.0f; + min = 0; + max = 1.0f; +} +FX_BOOL CPDF_SeparationCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CFX_ByteString name = pArray->GetString(1); + if (name == FX_BSTRC("None")) { + m_Type = None; + } else { + m_Type = Colorant; CPDF_Object* pAltCS = pArray->GetElementValue(2); - if (!pAltCS || pAltCS == m_pArray) { - return FALSE; + if (pAltCS == m_pArray) { + return FALSE; } m_pAltCS = Load(pDoc, pAltCS); - m_pFunc = CPDF_Function::Load(pArray->GetElementValue(3)); - if (m_pAltCS == NULL || m_pFunc == NULL) { - return FALSE; + if (!m_pAltCS) { + return FALSE; } - if (m_pFunc->CountOutputs() < m_pAltCS->CountComponents()) { - return FALSE; + CPDF_Object* pFuncObj = pArray->GetElementValue(3); + if (pFuncObj && pFuncObj->GetType() != PDFOBJ_NAME) { + m_pFunc = CPDF_Function::Load(pFuncObj); } - return TRUE; + if (m_pFunc && m_pFunc->CountOutputs() < m_pAltCS->CountComponents()) { + delete m_pFunc; + m_pFunc = NULL; + } + } + return TRUE; } -FX_BOOL CPDF_DeviceNCS::GetRGB(FX_FLOAT* pBuf, FX_FLOAT& R, FX_FLOAT& G, FX_FLOAT& B) const -{ - if (m_pFunc == NULL) { - return FALSE; +FX_BOOL CPDF_SeparationCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + if (m_Type == None) { + return FALSE; + } + if (m_pFunc == NULL) { + if (m_pAltCS == NULL) { + return FALSE; } - CFX_FixedBufGrow results(m_pFunc->CountOutputs()); - int nresults = 0; - m_pFunc->Call(pBuf, m_nComponents, results, nresults); - if (nresults == 0) { - return FALSE; + int nComps = m_pAltCS->CountComponents(); + CFX_FixedBufGrow results(nComps); + for (int i = 0; i < nComps; i++) { + results[i] = *pBuf; } m_pAltCS->GetRGB(results, R, G, B); return TRUE; -} -void CPDF_DeviceNCS::EnableStdConversion(FX_BOOL bEnabled) -{ - CPDF_ColorSpace::EnableStdConversion(bEnabled); - if (m_pAltCS) { - m_pAltCS->EnableStdConversion(bEnabled); - } -} -CPDF_ColorSpace* CPDF_ColorSpace::GetStockCS(int family) -{ - return CPDF_ModuleMgr::Get()->GetPageModule()->GetStockCS(family);; -} -CPDF_ColorSpace* _CSFromName(const CFX_ByteString& name) -{ - if (name == FX_BSTRC("DeviceRGB") || name == FX_BSTRC("RGB")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); - } - if (name == FX_BSTRC("DeviceGray") || name == FX_BSTRC("G")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); - } - if (name == FX_BSTRC("DeviceCMYK") || name == FX_BSTRC("CMYK")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); - } - if (name == FX_BSTRC("Pattern")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_PATTERN); - } + } + CFX_FixedBufGrow results(m_pFunc->CountOutputs()); + int nresults = 0; + m_pFunc->Call(pBuf, 1, results, nresults); + if (nresults == 0) { + return FALSE; + } + if (m_pAltCS) { + m_pAltCS->GetRGB(results, R, G, B); + return TRUE; + } + R = G = B = 0; + return FALSE; +} +void CPDF_SeparationCS::EnableStdConversion(FX_BOOL bEnabled) { + CPDF_ColorSpace::EnableStdConversion(bEnabled); + if (m_pAltCS) { + m_pAltCS->EnableStdConversion(bEnabled); + } +} +class CPDF_DeviceNCS : public CPDF_ColorSpace { + public: + CPDF_DeviceNCS(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_DEVICEN, 0), + m_pAltCS(nullptr), + m_pFunc(nullptr) {} + ~CPDF_DeviceNCS() override; + void GetDefaultValue(int iComponent, + FX_FLOAT& value, + FX_FLOAT& min, + FX_FLOAT& max) const override; + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + void EnableStdConversion(FX_BOOL bEnabled) override; + + CPDF_ColorSpace* m_pAltCS; + CPDF_Function* m_pFunc; +}; +CPDF_DeviceNCS::~CPDF_DeviceNCS() { + delete m_pFunc; + if (m_pAltCS) { + m_pAltCS->ReleaseCS(); + } +} +void CPDF_DeviceNCS::GetDefaultValue(int iComponent, + FX_FLOAT& value, + FX_FLOAT& min, + FX_FLOAT& max) const { + value = 1.0f; + min = 0; + max = 1.0f; +} +FX_BOOL CPDF_DeviceNCS::v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) { + CPDF_Object* pObj = pArray->GetElementValue(1); + if (!pObj) { + return FALSE; + } + if (pObj->GetType() != PDFOBJ_ARRAY) { + return FALSE; + } + m_nComponents = ((CPDF_Array*)pObj)->GetCount(); + CPDF_Object* pAltCS = pArray->GetElementValue(2); + if (!pAltCS || pAltCS == m_pArray) { + return FALSE; + } + m_pAltCS = Load(pDoc, pAltCS); + m_pFunc = CPDF_Function::Load(pArray->GetElementValue(3)); + if (m_pAltCS == NULL || m_pFunc == NULL) { + return FALSE; + } + if (m_pFunc->CountOutputs() < m_pAltCS->CountComponents()) { + return FALSE; + } + return TRUE; +} +FX_BOOL CPDF_DeviceNCS::GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const { + if (m_pFunc == NULL) { + return FALSE; + } + CFX_FixedBufGrow results(m_pFunc->CountOutputs()); + int nresults = 0; + m_pFunc->Call(pBuf, m_nComponents, results, nresults); + if (nresults == 0) { + return FALSE; + } + m_pAltCS->GetRGB(results, R, G, B); + return TRUE; +} +void CPDF_DeviceNCS::EnableStdConversion(FX_BOOL bEnabled) { + CPDF_ColorSpace::EnableStdConversion(bEnabled); + if (m_pAltCS) { + m_pAltCS->EnableStdConversion(bEnabled); + } +} +CPDF_ColorSpace* CPDF_ColorSpace::GetStockCS(int family) { + return CPDF_ModuleMgr::Get()->GetPageModule()->GetStockCS(family); + ; +} +CPDF_ColorSpace* _CSFromName(const CFX_ByteString& name) { + if (name == FX_BSTRC("DeviceRGB") || name == FX_BSTRC("RGB")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); + } + if (name == FX_BSTRC("DeviceGray") || name == FX_BSTRC("G")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); + } + if (name == FX_BSTRC("DeviceCMYK") || name == FX_BSTRC("CMYK")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); + } + if (name == FX_BSTRC("Pattern")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_PATTERN); + } + return NULL; +} +CPDF_ColorSpace* CPDF_ColorSpace::Load(CPDF_Document* pDoc, CPDF_Object* pObj) { + if (pObj == NULL) { return NULL; -} -CPDF_ColorSpace* CPDF_ColorSpace::Load(CPDF_Document* pDoc, CPDF_Object* pObj) -{ - if (pObj == NULL) { - return NULL; - } - if (pObj->GetType() == PDFOBJ_NAME) { - return _CSFromName(pObj->GetString()); - } - if (pObj->GetType() == PDFOBJ_STREAM) { - CPDF_Dictionary *pDict = ((CPDF_Stream *)pObj)->GetDict(); - if (!pDict) { - return NULL; - } - CPDF_ColorSpace *pRet = NULL; - FX_POSITION pos = pDict->GetStartPos(); - while (pos) { - CFX_ByteString bsKey; - CPDF_Object *pValue = pDict->GetNextElement(pos, bsKey); - if (pValue && pValue->GetType() == PDFOBJ_NAME) { - pRet = _CSFromName(pValue->GetString()); - } - if (pRet) { - return pRet; - } - } - return NULL; - } - if (pObj->GetType() != PDFOBJ_ARRAY) { - return NULL; - } - CPDF_Array* pArray = (CPDF_Array*)pObj; - if (pArray->GetCount() == 0) { - return NULL; - } - CPDF_Object *pFamilyObj = pArray->GetElementValue(0); - if (!pFamilyObj) { - return NULL; - } - CFX_ByteString familyname = pFamilyObj->GetString(); - if (pArray->GetCount() == 1) { - return _CSFromName(familyname); - } - CPDF_ColorSpace* pCS = NULL; - FX_DWORD id = familyname.GetID(); - if (id == FXBSTR_ID('C', 'a', 'l', 'G')) { - pCS = new CPDF_CalGray(pDoc); - } else if (id == FXBSTR_ID('C', 'a', 'l', 'R')) { - pCS = new CPDF_CalRGB(pDoc); - } else if (id == FXBSTR_ID('L', 'a', 'b', 0)) { - pCS = new CPDF_LabCS(pDoc); - } else if (id == FXBSTR_ID('I', 'C', 'C', 'B')) { - pCS = new CPDF_ICCBasedCS(pDoc); - } else if (id == FXBSTR_ID('I', 'n', 'd', 'e') || id == FXBSTR_ID('I', 0, 0, 0)) { - pCS = new CPDF_IndexedCS(pDoc); - } else if (id == FXBSTR_ID('S', 'e', 'p', 'a')) { - pCS = new CPDF_SeparationCS(pDoc); - } else if (id == FXBSTR_ID('D', 'e', 'v', 'i')) { - pCS = new CPDF_DeviceNCS(pDoc); - } else if (id == FXBSTR_ID('P', 'a', 't', 't')) { - pCS = new CPDF_PatternCS(pDoc); - } else { - return NULL; - } - pCS->m_pArray = pArray; - if (!pCS->v_Load(pDoc, pArray)) { - pCS->ReleaseCS(); - return NULL; - } - return pCS; -} -void CPDF_ColorSpace::ReleaseCS() -{ - if (this == GetStockCS(PDFCS_DEVICERGB)) { - return; - } - if (this == GetStockCS(PDFCS_DEVICEGRAY)) { - return; - } - if (this == GetStockCS(PDFCS_DEVICECMYK)) { - return; - } - if (this == GetStockCS(PDFCS_PATTERN)) { - return; - } - delete this; -} -int CPDF_ColorSpace::GetBufSize() const -{ - if (m_Family == PDFCS_PATTERN) { - return sizeof(PatternValue); - } - return m_nComponents * sizeof(FX_FLOAT); -} -FX_FLOAT* CPDF_ColorSpace::CreateBuf() -{ - int size = GetBufSize(); - uint8_t* pBuf = FX_Alloc(uint8_t, size); - return (FX_FLOAT*)pBuf; -} -FX_BOOL CPDF_ColorSpace::sRGB() const -{ - if (m_Family == PDFCS_DEVICERGB) { - return TRUE; - } - if (m_Family != PDFCS_ICCBASED) { - return FALSE; - } - CPDF_ICCBasedCS* pCS = (CPDF_ICCBasedCS*)this; - return pCS->m_pProfile->m_bsRGB; -} -FX_BOOL CPDF_ColorSpace::GetCMYK(FX_FLOAT* pBuf, FX_FLOAT& c, FX_FLOAT& m, FX_FLOAT& y, FX_FLOAT& k) const -{ - if (v_GetCMYK(pBuf, c, m, y, k)) { - return TRUE; - } - FX_FLOAT R, G, B; - if (!GetRGB(pBuf, R, G, B)) { - return FALSE; + } + if (pObj->GetType() == PDFOBJ_NAME) { + return _CSFromName(pObj->GetString()); + } + if (pObj->GetType() == PDFOBJ_STREAM) { + CPDF_Dictionary* pDict = ((CPDF_Stream*)pObj)->GetDict(); + if (!pDict) { + return NULL; + } + CPDF_ColorSpace* pRet = NULL; + FX_POSITION pos = pDict->GetStartPos(); + while (pos) { + CFX_ByteString bsKey; + CPDF_Object* pValue = pDict->GetNextElement(pos, bsKey); + if (pValue && pValue->GetType() == PDFOBJ_NAME) { + pRet = _CSFromName(pValue->GetString()); + } + if (pRet) { + return pRet; + } } - sRGB_to_AdobeCMYK(R, G, B, c, m, y, k); + return NULL; + } + if (pObj->GetType() != PDFOBJ_ARRAY) { + return NULL; + } + CPDF_Array* pArray = (CPDF_Array*)pObj; + if (pArray->GetCount() == 0) { + return NULL; + } + CPDF_Object* pFamilyObj = pArray->GetElementValue(0); + if (!pFamilyObj) { + return NULL; + } + CFX_ByteString familyname = pFamilyObj->GetString(); + if (pArray->GetCount() == 1) { + return _CSFromName(familyname); + } + CPDF_ColorSpace* pCS = NULL; + FX_DWORD id = familyname.GetID(); + if (id == FXBSTR_ID('C', 'a', 'l', 'G')) { + pCS = new CPDF_CalGray(pDoc); + } else if (id == FXBSTR_ID('C', 'a', 'l', 'R')) { + pCS = new CPDF_CalRGB(pDoc); + } else if (id == FXBSTR_ID('L', 'a', 'b', 0)) { + pCS = new CPDF_LabCS(pDoc); + } else if (id == FXBSTR_ID('I', 'C', 'C', 'B')) { + pCS = new CPDF_ICCBasedCS(pDoc); + } else if (id == FXBSTR_ID('I', 'n', 'd', 'e') || + id == FXBSTR_ID('I', 0, 0, 0)) { + pCS = new CPDF_IndexedCS(pDoc); + } else if (id == FXBSTR_ID('S', 'e', 'p', 'a')) { + pCS = new CPDF_SeparationCS(pDoc); + } else if (id == FXBSTR_ID('D', 'e', 'v', 'i')) { + pCS = new CPDF_DeviceNCS(pDoc); + } else if (id == FXBSTR_ID('P', 'a', 't', 't')) { + pCS = new CPDF_PatternCS(pDoc); + } else { + return NULL; + } + pCS->m_pArray = pArray; + if (!pCS->v_Load(pDoc, pArray)) { + pCS->ReleaseCS(); + return NULL; + } + return pCS; +} +void CPDF_ColorSpace::ReleaseCS() { + if (this == GetStockCS(PDFCS_DEVICERGB)) { + return; + } + if (this == GetStockCS(PDFCS_DEVICEGRAY)) { + return; + } + if (this == GetStockCS(PDFCS_DEVICECMYK)) { + return; + } + if (this == GetStockCS(PDFCS_PATTERN)) { + return; + } + delete this; +} +int CPDF_ColorSpace::GetBufSize() const { + if (m_Family == PDFCS_PATTERN) { + return sizeof(PatternValue); + } + return m_nComponents * sizeof(FX_FLOAT); +} +FX_FLOAT* CPDF_ColorSpace::CreateBuf() { + int size = GetBufSize(); + uint8_t* pBuf = FX_Alloc(uint8_t, size); + return (FX_FLOAT*)pBuf; +} +FX_BOOL CPDF_ColorSpace::sRGB() const { + if (m_Family == PDFCS_DEVICERGB) { return TRUE; -} -FX_BOOL CPDF_ColorSpace::SetCMYK(FX_FLOAT* pBuf, FX_FLOAT c, FX_FLOAT m, FX_FLOAT y, FX_FLOAT k) const -{ - if (v_SetCMYK(pBuf, c, m, y, k)) { - return TRUE; - } - FX_FLOAT R, G, B; - AdobeCMYK_to_sRGB(c, m, y, k, R, G, B); - return SetRGB(pBuf, R, G, B); -} -void CPDF_ColorSpace::GetDefaultColor(FX_FLOAT* buf) const -{ - if (buf == NULL || m_Family == PDFCS_PATTERN) { - return; - } - FX_FLOAT min, max; - for (int i = 0; i < m_nComponents; i ++) { - GetDefaultValue(i, buf[i], min, max); - } -} -int CPDF_ColorSpace::GetMaxIndex() const -{ - if (m_Family != PDFCS_INDEXED) { - return 0; - } - CPDF_IndexedCS* pCS = (CPDF_IndexedCS*)this; - return pCS->m_MaxIndex; -} -void CPDF_ColorSpace::TranslateImageLine(uint8_t* dest_buf, const uint8_t* src_buf, int pixels, int image_width, int image_height, FX_BOOL bTransMask) const -{ - CFX_FixedBufGrow srcbuf(m_nComponents); - FX_FLOAT* src = srcbuf; - FX_FLOAT R, G, B; - for (int i = 0; i < pixels; i ++) { - for (int j = 0; j < m_nComponents; j ++) - if (m_Family == PDFCS_INDEXED) { - src[j] = (FX_FLOAT)(*src_buf ++); - } else { - src[j] = (FX_FLOAT)(*src_buf ++) / 255; - } - GetRGB(src, R, G, B); - *dest_buf ++ = (int32_t)(B * 255); - *dest_buf ++ = (int32_t)(G * 255); - *dest_buf ++ = (int32_t)(R * 255); - } -} -void CPDF_ColorSpace::EnableStdConversion(FX_BOOL bEnabled) -{ - if (bEnabled) { - m_dwStdConversion ++; - } else if (m_dwStdConversion) { - m_dwStdConversion --; - } -} -CPDF_Color::CPDF_Color(int family) -{ - m_pCS = CPDF_ColorSpace::GetStockCS(family); - int nComps = 3; - if (family == PDFCS_DEVICEGRAY) { - nComps = 1; - } else if (family == PDFCS_DEVICECMYK) { - nComps = 4; - } - m_pBuffer = FX_Alloc(FX_FLOAT, nComps); - for (int i = 0; i < nComps; i ++) { - m_pBuffer[i] = 0; - } -} -CPDF_Color::~CPDF_Color() -{ - ReleaseBuffer(); - ReleaseColorSpace(); -} -void CPDF_Color::ReleaseBuffer() -{ - if (!m_pBuffer) { - return; - } - if (m_pCS->GetFamily() == PDFCS_PATTERN) { - PatternValue* pvalue = (PatternValue*)m_pBuffer; - CPDF_Pattern* pPattern = pvalue->m_pCountedPattern ? pvalue->m_pCountedPattern->get() : NULL; - if (pPattern && pPattern->m_pDocument) { - CPDF_DocPageData *pPageData = pPattern->m_pDocument->GetPageData(); - if (pPageData) { - pPageData->ReleasePattern(pPattern->m_pPatternObj); - } - } - } - FX_Free(m_pBuffer); - m_pBuffer = NULL; -} -void CPDF_Color::ReleaseColorSpace() -{ - if (m_pCS && m_pCS->m_pDocument && m_pCS->GetArray()) { - m_pCS->m_pDocument->GetPageData()->ReleaseColorSpace(m_pCS->GetArray()); - m_pCS = NULL; - } -} -void CPDF_Color::SetColorSpace(CPDF_ColorSpace* pCS) -{ - if (m_pCS == pCS) { - if (m_pBuffer == NULL) { - m_pBuffer = pCS->CreateBuf(); - } - ReleaseColorSpace(); - m_pCS = pCS; - return; + } + if (m_Family != PDFCS_ICCBASED) { + return FALSE; + } + CPDF_ICCBasedCS* pCS = (CPDF_ICCBasedCS*)this; + return pCS->m_pProfile->m_bsRGB; +} +FX_BOOL CPDF_ColorSpace::GetCMYK(FX_FLOAT* pBuf, + FX_FLOAT& c, + FX_FLOAT& m, + FX_FLOAT& y, + FX_FLOAT& k) const { + if (v_GetCMYK(pBuf, c, m, y, k)) { + return TRUE; + } + FX_FLOAT R, G, B; + if (!GetRGB(pBuf, R, G, B)) { + return FALSE; + } + sRGB_to_AdobeCMYK(R, G, B, c, m, y, k); + return TRUE; +} +FX_BOOL CPDF_ColorSpace::SetCMYK(FX_FLOAT* pBuf, + FX_FLOAT c, + FX_FLOAT m, + FX_FLOAT y, + FX_FLOAT k) const { + if (v_SetCMYK(pBuf, c, m, y, k)) { + return TRUE; + } + FX_FLOAT R, G, B; + AdobeCMYK_to_sRGB(c, m, y, k, R, G, B); + return SetRGB(pBuf, R, G, B); +} +void CPDF_ColorSpace::GetDefaultColor(FX_FLOAT* buf) const { + if (buf == NULL || m_Family == PDFCS_PATTERN) { + return; + } + FX_FLOAT min, max; + for (int i = 0; i < m_nComponents; i++) { + GetDefaultValue(i, buf[i], min, max); + } +} +int CPDF_ColorSpace::GetMaxIndex() const { + if (m_Family != PDFCS_INDEXED) { + return 0; + } + CPDF_IndexedCS* pCS = (CPDF_IndexedCS*)this; + return pCS->m_MaxIndex; +} +void CPDF_ColorSpace::TranslateImageLine(uint8_t* dest_buf, + const uint8_t* src_buf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask) const { + CFX_FixedBufGrow srcbuf(m_nComponents); + FX_FLOAT* src = srcbuf; + FX_FLOAT R, G, B; + for (int i = 0; i < pixels; i++) { + for (int j = 0; j < m_nComponents; j++) + if (m_Family == PDFCS_INDEXED) { + src[j] = (FX_FLOAT)(*src_buf++); + } else { + src[j] = (FX_FLOAT)(*src_buf++) / 255; + } + GetRGB(src, R, G, B); + *dest_buf++ = (int32_t)(B * 255); + *dest_buf++ = (int32_t)(G * 255); + *dest_buf++ = (int32_t)(R * 255); + } +} +void CPDF_ColorSpace::EnableStdConversion(FX_BOOL bEnabled) { + if (bEnabled) { + m_dwStdConversion++; + } else if (m_dwStdConversion) { + m_dwStdConversion--; + } +} +CPDF_Color::CPDF_Color(int family) { + m_pCS = CPDF_ColorSpace::GetStockCS(family); + int nComps = 3; + if (family == PDFCS_DEVICEGRAY) { + nComps = 1; + } else if (family == PDFCS_DEVICECMYK) { + nComps = 4; + } + m_pBuffer = FX_Alloc(FX_FLOAT, nComps); + for (int i = 0; i < nComps; i++) { + m_pBuffer[i] = 0; + } +} +CPDF_Color::~CPDF_Color() { + ReleaseBuffer(); + ReleaseColorSpace(); +} +void CPDF_Color::ReleaseBuffer() { + if (!m_pBuffer) { + return; + } + if (m_pCS->GetFamily() == PDFCS_PATTERN) { + PatternValue* pvalue = (PatternValue*)m_pBuffer; + CPDF_Pattern* pPattern = + pvalue->m_pCountedPattern ? pvalue->m_pCountedPattern->get() : NULL; + if (pPattern && pPattern->m_pDocument) { + CPDF_DocPageData* pPageData = pPattern->m_pDocument->GetPageData(); + if (pPageData) { + pPageData->ReleasePattern(pPattern->m_pPatternObj); + } + } + } + FX_Free(m_pBuffer); + m_pBuffer = NULL; +} +void CPDF_Color::ReleaseColorSpace() { + if (m_pCS && m_pCS->m_pDocument && m_pCS->GetArray()) { + m_pCS->m_pDocument->GetPageData()->ReleaseColorSpace(m_pCS->GetArray()); + m_pCS = NULL; + } +} +void CPDF_Color::SetColorSpace(CPDF_ColorSpace* pCS) { + if (m_pCS == pCS) { + if (m_pBuffer == NULL) { + m_pBuffer = pCS->CreateBuf(); } - ReleaseBuffer(); ReleaseColorSpace(); m_pCS = pCS; - if (m_pCS) { - m_pBuffer = pCS->CreateBuf(); - pCS->GetDefaultColor(m_pBuffer); - } -} -void CPDF_Color::SetValue(FX_FLOAT* comps) -{ - if (m_pBuffer == NULL) { - return; - } - if (m_pCS->GetFamily() != PDFCS_PATTERN) { - FXSYS_memcpy(m_pBuffer, comps, m_pCS->CountComponents() * sizeof(FX_FLOAT)); - } -} -void CPDF_Color::SetValue(CPDF_Pattern* pPattern, FX_FLOAT* comps, int ncomps) -{ - if (ncomps > MAX_PATTERN_COLORCOMPS) { - return; - } - if (m_pCS == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { - if (m_pBuffer) { - FX_Free(m_pBuffer); - } - m_pCS = CPDF_ColorSpace::GetStockCS(PDFCS_PATTERN); - m_pBuffer = m_pCS->CreateBuf(); - } - CPDF_DocPageData *pDocPageData = NULL; + return; + } + ReleaseBuffer(); + ReleaseColorSpace(); + m_pCS = pCS; + if (m_pCS) { + m_pBuffer = pCS->CreateBuf(); + pCS->GetDefaultColor(m_pBuffer); + } +} +void CPDF_Color::SetValue(FX_FLOAT* comps) { + if (m_pBuffer == NULL) { + return; + } + if (m_pCS->GetFamily() != PDFCS_PATTERN) { + FXSYS_memcpy(m_pBuffer, comps, m_pCS->CountComponents() * sizeof(FX_FLOAT)); + } +} +void CPDF_Color::SetValue(CPDF_Pattern* pPattern, FX_FLOAT* comps, int ncomps) { + if (ncomps > MAX_PATTERN_COLORCOMPS) { + return; + } + if (m_pCS == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { + if (m_pBuffer) { + FX_Free(m_pBuffer); + } + m_pCS = CPDF_ColorSpace::GetStockCS(PDFCS_PATTERN); + m_pBuffer = m_pCS->CreateBuf(); + } + CPDF_DocPageData* pDocPageData = NULL; + PatternValue* pvalue = (PatternValue*)m_pBuffer; + if (pvalue->m_pPattern && pvalue->m_pPattern->m_pDocument) { + pDocPageData = pvalue->m_pPattern->m_pDocument->GetPageData(); + if (pDocPageData) { + pDocPageData->ReleasePattern(pvalue->m_pPattern->m_pPatternObj); + } + } + pvalue->m_nComps = ncomps; + pvalue->m_pPattern = pPattern; + if (ncomps) { + FXSYS_memcpy(pvalue->m_Comps, comps, ncomps * sizeof(FX_FLOAT)); + } + pvalue->m_pCountedPattern = NULL; + if (pPattern && pPattern->m_pDocument) { + if (!pDocPageData) { + pDocPageData = pPattern->m_pDocument->GetPageData(); + } + pvalue->m_pCountedPattern = + pDocPageData->FindPatternPtr(pPattern->m_pPatternObj); + } +} +void CPDF_Color::Copy(const CPDF_Color* pSrc) { + ReleaseBuffer(); + ReleaseColorSpace(); + m_pCS = pSrc->m_pCS; + if (m_pCS && m_pCS->m_pDocument) { + CPDF_Array* pArray = m_pCS->GetArray(); + if (pArray) { + m_pCS = m_pCS->m_pDocument->GetPageData()->GetCopiedColorSpace(pArray); + } + } + if (m_pCS == NULL) { + return; + } + m_pBuffer = m_pCS->CreateBuf(); + FXSYS_memcpy(m_pBuffer, pSrc->m_pBuffer, m_pCS->GetBufSize()); + if (m_pCS->GetFamily() == PDFCS_PATTERN) { PatternValue* pvalue = (PatternValue*)m_pBuffer; if (pvalue->m_pPattern && pvalue->m_pPattern->m_pDocument) { - pDocPageData = pvalue->m_pPattern->m_pDocument->GetPageData(); - if (pDocPageData) { - pDocPageData->ReleasePattern(pvalue->m_pPattern->m_pPatternObj); - } - } - pvalue->m_nComps = ncomps; - pvalue->m_pPattern = pPattern; - if (ncomps) { - FXSYS_memcpy(pvalue->m_Comps, comps, ncomps * sizeof(FX_FLOAT)); - } - pvalue->m_pCountedPattern = NULL; - if (pPattern && pPattern->m_pDocument) - { - if (!pDocPageData) { - pDocPageData = pPattern->m_pDocument->GetPageData(); - } - pvalue->m_pCountedPattern = pDocPageData->FindPatternPtr(pPattern->m_pPatternObj); - } -} -void CPDF_Color::Copy(const CPDF_Color* pSrc) -{ - ReleaseBuffer(); - ReleaseColorSpace(); - m_pCS = pSrc->m_pCS; - if (m_pCS && m_pCS->m_pDocument) { - CPDF_Array* pArray = m_pCS->GetArray(); - if (pArray) { - m_pCS = m_pCS->m_pDocument->GetPageData()->GetCopiedColorSpace(pArray); - } - } - if (m_pCS == NULL) { - return; - } - m_pBuffer = m_pCS->CreateBuf(); - FXSYS_memcpy(m_pBuffer, pSrc->m_pBuffer, m_pCS->GetBufSize()); - if (m_pCS->GetFamily() == PDFCS_PATTERN) { - PatternValue* pvalue = (PatternValue*)m_pBuffer; - if (pvalue->m_pPattern && pvalue->m_pPattern->m_pDocument) { - pvalue->m_pPattern = pvalue->m_pPattern->m_pDocument->GetPageData()->GetPattern(pvalue->m_pPattern->m_pPatternObj, FALSE, &pvalue->m_pPattern->m_ParentMatrix); - } + pvalue->m_pPattern = + pvalue->m_pPattern->m_pDocument->GetPageData()->GetPattern( + pvalue->m_pPattern->m_pPatternObj, FALSE, + &pvalue->m_pPattern->m_ParentMatrix); } + } } -FX_BOOL CPDF_Color::GetRGB(int& R, int& G, int& B) const -{ - if (m_pCS == NULL || m_pBuffer == NULL) { - return FALSE; - } - FX_FLOAT r=0.0f, g=0.0f, b=0.0f; - if (!m_pCS->GetRGB(m_pBuffer, r, g, b)) { - return FALSE; - } - R = (int32_t)(r * 255 + 0.5f); - G = (int32_t)(g * 255 + 0.5f); - B = (int32_t)(b * 255 + 0.5f); - return TRUE; -} -CPDF_Pattern* CPDF_Color::GetPattern() const -{ - if (m_pBuffer == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { - return NULL; - } - PatternValue* pvalue = (PatternValue*)m_pBuffer; - return pvalue->m_pPattern; +FX_BOOL CPDF_Color::GetRGB(int& R, int& G, int& B) const { + if (m_pCS == NULL || m_pBuffer == NULL) { + return FALSE; + } + FX_FLOAT r = 0.0f, g = 0.0f, b = 0.0f; + if (!m_pCS->GetRGB(m_pBuffer, r, g, b)) { + return FALSE; + } + R = (int32_t)(r * 255 + 0.5f); + G = (int32_t)(g * 255 + 0.5f); + B = (int32_t)(b * 255 + 0.5f); + return TRUE; +} +CPDF_Pattern* CPDF_Color::GetPattern() const { + if (m_pBuffer == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { + return NULL; + } + PatternValue* pvalue = (PatternValue*)m_pBuffer; + return pvalue->m_pPattern; } -CPDF_ColorSpace* CPDF_Color::GetPatternCS() const -{ - if (m_pBuffer == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { - return NULL; - } - return m_pCS->GetBaseCS(); +CPDF_ColorSpace* CPDF_Color::GetPatternCS() const { + if (m_pBuffer == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { + return NULL; + } + return m_pCS->GetBaseCS(); } -FX_FLOAT* CPDF_Color::GetPatternColor() const -{ - if (m_pBuffer == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { - return NULL; - } - PatternValue* pvalue = (PatternValue*)m_pBuffer; - return pvalue->m_nComps ? pvalue->m_Comps : NULL; +FX_FLOAT* CPDF_Color::GetPatternColor() const { + if (m_pBuffer == NULL || m_pCS->GetFamily() != PDFCS_PATTERN) { + return NULL; + } + PatternValue* pvalue = (PatternValue*)m_pBuffer; + return pvalue->m_nComps ? pvalue->m_Comps : NULL; } -FX_BOOL CPDF_Color::IsEqual(const CPDF_Color& other) const -{ - if (m_pCS != other.m_pCS || m_pCS == NULL) { - return FALSE; - } - return FXSYS_memcmp(m_pBuffer, other.m_pBuffer, m_pCS->GetBufSize()) == 0; +FX_BOOL CPDF_Color::IsEqual(const CPDF_Color& other) const { + if (m_pCS != other.m_pCS || m_pCS == NULL) { + return FALSE; + } + return FXSYS_memcmp(m_pBuffer, other.m_pBuffer, m_pCS->GetBufSize()) == 0; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_doc.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_doc.cpp index 05233a12a4..74e33b56a9 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_doc.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_doc.cpp @@ -10,628 +10,606 @@ #include "../fpdf_font/font_int.h" #include "pageint.h" -class CPDF_PageModule : public IPDF_PageModule -{ -public: - CPDF_PageModule() - : m_StockGrayCS(nullptr, PDFCS_DEVICEGRAY), - m_StockRGBCS(nullptr, PDFCS_DEVICERGB), - m_StockCMYKCS(nullptr, PDFCS_DEVICECMYK), - m_StockPatternCS(nullptr) {} - -private: - ~CPDF_PageModule() override {} - - CPDF_DocPageData* CreateDocData(CPDF_Document* pDoc) override - { - return new CPDF_DocPageData(pDoc); - } - - void ReleaseDoc(CPDF_Document* pDoc) override; - void ClearDoc(CPDF_Document* pDoc) override; - - CPDF_FontGlobals* GetFontGlobals() override - { - return &m_FontGlobals; - } - - void ClearStockFont(CPDF_Document* pDoc) override - { - m_FontGlobals.Clear(pDoc); - } - - CPDF_ColorSpace* GetStockCS(int family) override; - void NotifyCJKAvailable() override; - - CPDF_FontGlobals m_FontGlobals; - CPDF_DeviceCS m_StockGrayCS; - CPDF_DeviceCS m_StockRGBCS; - CPDF_DeviceCS m_StockCMYKCS; - CPDF_PatternCS m_StockPatternCS; +class CPDF_PageModule : public IPDF_PageModule { + public: + CPDF_PageModule() + : m_StockGrayCS(nullptr, PDFCS_DEVICEGRAY), + m_StockRGBCS(nullptr, PDFCS_DEVICERGB), + m_StockCMYKCS(nullptr, PDFCS_DEVICECMYK), + m_StockPatternCS(nullptr) {} + + private: + ~CPDF_PageModule() override {} + + CPDF_DocPageData* CreateDocData(CPDF_Document* pDoc) override { + return new CPDF_DocPageData(pDoc); + } + + void ReleaseDoc(CPDF_Document* pDoc) override; + void ClearDoc(CPDF_Document* pDoc) override; + + CPDF_FontGlobals* GetFontGlobals() override { return &m_FontGlobals; } + + void ClearStockFont(CPDF_Document* pDoc) override { + m_FontGlobals.Clear(pDoc); + } + + CPDF_ColorSpace* GetStockCS(int family) override; + void NotifyCJKAvailable() override; + + CPDF_FontGlobals m_FontGlobals; + CPDF_DeviceCS m_StockGrayCS; + CPDF_DeviceCS m_StockRGBCS; + CPDF_DeviceCS m_StockCMYKCS; + CPDF_PatternCS m_StockPatternCS; }; -CPDF_ColorSpace* CPDF_PageModule::GetStockCS(int family) -{ - if (family == PDFCS_DEVICEGRAY) { - return &m_StockGrayCS; - } - if (family == PDFCS_DEVICERGB) { - return &m_StockRGBCS; - } - if (family == PDFCS_DEVICECMYK) { - return &m_StockCMYKCS; - } - if (family == PDFCS_PATTERN) { - return &m_StockPatternCS; - } - return NULL; +CPDF_ColorSpace* CPDF_PageModule::GetStockCS(int family) { + if (family == PDFCS_DEVICEGRAY) { + return &m_StockGrayCS; + } + if (family == PDFCS_DEVICERGB) { + return &m_StockRGBCS; + } + if (family == PDFCS_DEVICECMYK) { + return &m_StockCMYKCS; + } + if (family == PDFCS_PATTERN) { + return &m_StockPatternCS; + } + return NULL; } -void CPDF_ModuleMgr::InitPageModule() -{ - m_pPageModule.reset(new CPDF_PageModule); +void CPDF_ModuleMgr::InitPageModule() { + m_pPageModule.reset(new CPDF_PageModule); } -void CPDF_PageModule::ReleaseDoc(CPDF_Document* pDoc) -{ - delete pDoc->GetPageData(); +void CPDF_PageModule::ReleaseDoc(CPDF_Document* pDoc) { + delete pDoc->GetPageData(); } -void CPDF_PageModule::ClearDoc(CPDF_Document* pDoc) -{ - pDoc->GetPageData()->Clear(FALSE); +void CPDF_PageModule::ClearDoc(CPDF_Document* pDoc) { + pDoc->GetPageData()->Clear(FALSE); } -void CPDF_PageModule::NotifyCJKAvailable() -{ - m_FontGlobals.m_CMapManager.ReloadAll(); +void CPDF_PageModule::NotifyCJKAvailable() { + m_FontGlobals.m_CMapManager.ReloadAll(); } -CPDF_Font* CPDF_Document::LoadFont(CPDF_Dictionary* pFontDict) -{ - ASSERT(pFontDict); - return GetValidatePageData()->GetFont(pFontDict, FALSE); +CPDF_Font* CPDF_Document::LoadFont(CPDF_Dictionary* pFontDict) { + ASSERT(pFontDict); + return GetValidatePageData()->GetFont(pFontDict, FALSE); } -CPDF_StreamAcc* CPDF_Document::LoadFontFile(CPDF_Stream* pStream) -{ - return GetValidatePageData()->GetFontFileStreamAcc(pStream); +CPDF_StreamAcc* CPDF_Document::LoadFontFile(CPDF_Stream* pStream) { + return GetValidatePageData()->GetFontFileStreamAcc(pStream); } CPDF_ColorSpace* _CSFromName(const CFX_ByteString& name); -CPDF_ColorSpace* CPDF_Document::LoadColorSpace(CPDF_Object* pCSObj, CPDF_Dictionary* pResources) -{ - return GetValidatePageData()->GetColorSpace(pCSObj, pResources); +CPDF_ColorSpace* CPDF_Document::LoadColorSpace(CPDF_Object* pCSObj, + CPDF_Dictionary* pResources) { + return GetValidatePageData()->GetColorSpace(pCSObj, pResources); } -CPDF_Pattern* CPDF_Document::LoadPattern(CPDF_Object* pPatternObj, FX_BOOL bShading, const CFX_AffineMatrix* matrix) -{ - return GetValidatePageData()->GetPattern(pPatternObj, bShading, matrix); +CPDF_Pattern* CPDF_Document::LoadPattern(CPDF_Object* pPatternObj, + FX_BOOL bShading, + const CFX_AffineMatrix* matrix) { + return GetValidatePageData()->GetPattern(pPatternObj, bShading, matrix); } -CPDF_IccProfile* CPDF_Document::LoadIccProfile(CPDF_Stream* pStream) -{ - return GetValidatePageData()->GetIccProfile(pStream); +CPDF_IccProfile* CPDF_Document::LoadIccProfile(CPDF_Stream* pStream) { + return GetValidatePageData()->GetIccProfile(pStream); } -CPDF_Image* CPDF_Document::LoadImageF(CPDF_Object* pObj) -{ - if (!pObj) { - return NULL; - } - FXSYS_assert(pObj->GetObjNum()); - return GetValidatePageData()->GetImage(pObj); +CPDF_Image* CPDF_Document::LoadImageF(CPDF_Object* pObj) { + if (!pObj) { + return NULL; + } + FXSYS_assert(pObj->GetObjNum()); + return GetValidatePageData()->GetImage(pObj); } -void CPDF_Document::RemoveColorSpaceFromPageData(CPDF_Object* pCSObj) -{ - if (!pCSObj) { - return; - } - GetPageData()->ReleaseColorSpace(pCSObj); +void CPDF_Document::RemoveColorSpaceFromPageData(CPDF_Object* pCSObj) { + if (!pCSObj) { + return; + } + GetPageData()->ReleaseColorSpace(pCSObj); } CPDF_DocPageData::CPDF_DocPageData(CPDF_Document* pPDFDoc) - : m_pPDFDoc(pPDFDoc), - m_bForceClear(FALSE) -{ -} + : m_pPDFDoc(pPDFDoc), m_bForceClear(FALSE) {} -CPDF_DocPageData::~CPDF_DocPageData() -{ - Clear(FALSE); - Clear(TRUE); +CPDF_DocPageData::~CPDF_DocPageData() { + Clear(FALSE); + Clear(TRUE); - for (auto& it : m_PatternMap) - delete it.second; - m_PatternMap.clear(); + for (auto& it : m_PatternMap) + delete it.second; + m_PatternMap.clear(); - for (auto& it : m_FontMap) - delete it.second; - m_FontMap.clear(); + for (auto& it : m_FontMap) + delete it.second; + m_FontMap.clear(); - for (auto& it : m_ColorSpaceMap) - delete it.second; - m_ColorSpaceMap.clear(); + for (auto& it : m_ColorSpaceMap) + delete it.second; + m_ColorSpaceMap.clear(); } -void CPDF_DocPageData::Clear(FX_BOOL bForceRelease) -{ - m_bForceClear = bForceRelease; - - for (auto& it : m_PatternMap) { - CPDF_CountedPattern* ptData = it.second; - if (!ptData->get()) - continue; - - if (bForceRelease || ptData->use_count() < 2) { - ptData->get()->SetForceClear(bForceRelease); - ptData->clear(); - } - } - - for (auto& it : m_FontMap) { - CPDF_CountedFont* fontData = it.second; - if (!fontData->get()) - continue; - - if (bForceRelease || fontData->use_count() < 2) { - fontData->clear(); - } - } - - for (auto& it : m_ColorSpaceMap) { - CPDF_CountedColorSpace* csData = it.second; - if (!csData->get()) - continue; - - if (bForceRelease || csData->use_count() < 2) { - csData->get()->ReleaseCS(); - csData->reset(nullptr); +void CPDF_DocPageData::Clear(FX_BOOL bForceRelease) { + m_bForceClear = bForceRelease; + + for (auto& it : m_PatternMap) { + CPDF_CountedPattern* ptData = it.second; + if (!ptData->get()) + continue; + + if (bForceRelease || ptData->use_count() < 2) { + ptData->get()->SetForceClear(bForceRelease); + ptData->clear(); + } + } + + for (auto& it : m_FontMap) { + CPDF_CountedFont* fontData = it.second; + if (!fontData->get()) + continue; + + if (bForceRelease || fontData->use_count() < 2) { + fontData->clear(); + } + } + + for (auto& it : m_ColorSpaceMap) { + CPDF_CountedColorSpace* csData = it.second; + if (!csData->get()) + continue; + + if (bForceRelease || csData->use_count() < 2) { + csData->get()->ReleaseCS(); + csData->reset(nullptr); + } + } + + for (auto it = m_IccProfileMap.begin(); it != m_IccProfileMap.end();) { + auto curr_it = it++; + CPDF_CountedIccProfile* ipData = curr_it->second; + if (!ipData->get()) + continue; + + if (bForceRelease || ipData->use_count() < 2) { + CPDF_Stream* ipKey = curr_it->first; + FX_POSITION pos2 = m_HashProfileMap.GetStartPosition(); + while (pos2) { + CFX_ByteString bsKey; + CPDF_Stream* pFindStream = nullptr; + m_HashProfileMap.GetNextAssoc(pos2, bsKey, (void*&)pFindStream); + if (ipKey == pFindStream) { + m_HashProfileMap.RemoveKey(bsKey); + break; } - } - - for (auto it = m_IccProfileMap.begin(); it != m_IccProfileMap.end();) { - auto curr_it = it++; - CPDF_CountedIccProfile* ipData = curr_it->second; - if (!ipData->get()) - continue; - - if (bForceRelease || ipData->use_count() < 2) { - CPDF_Stream* ipKey = curr_it->first; - FX_POSITION pos2 = m_HashProfileMap.GetStartPosition(); - while (pos2) { - CFX_ByteString bsKey; - CPDF_Stream* pFindStream = nullptr; - m_HashProfileMap.GetNextAssoc(pos2, bsKey, (void*&)pFindStream); - if (ipKey == pFindStream) { - m_HashProfileMap.RemoveKey(bsKey); - break; - } - } - delete ipData->get(); - delete ipData; - m_IccProfileMap.erase(curr_it); - } - } - - for (auto it = m_FontFileMap.begin(); it != m_FontFileMap.end();) { - auto curr_it = it++; - CPDF_CountedStreamAcc* ftData = curr_it->second; - if (!ftData->get()) - continue; - - if (bForceRelease || ftData->use_count() < 2) { - delete ftData->get(); - delete ftData; - m_FontFileMap.erase(curr_it); - } - } - - for (auto it = m_ImageMap.begin(); it != m_ImageMap.end();) { - auto curr_it = it++; - CPDF_CountedImage* imageData = curr_it->second; - if (!imageData->get()) - continue; - - if (bForceRelease || imageData->use_count() < 2) { - delete imageData->get(); - delete imageData; - m_ImageMap.erase(curr_it); - } - } + } + delete ipData->get(); + delete ipData; + m_IccProfileMap.erase(curr_it); + } + } + + for (auto it = m_FontFileMap.begin(); it != m_FontFileMap.end();) { + auto curr_it = it++; + CPDF_CountedStreamAcc* ftData = curr_it->second; + if (!ftData->get()) + continue; + + if (bForceRelease || ftData->use_count() < 2) { + delete ftData->get(); + delete ftData; + m_FontFileMap.erase(curr_it); + } + } + + for (auto it = m_ImageMap.begin(); it != m_ImageMap.end();) { + auto curr_it = it++; + CPDF_CountedImage* imageData = curr_it->second; + if (!imageData->get()) + continue; + + if (bForceRelease || imageData->use_count() < 2) { + delete imageData->get(); + delete imageData; + m_ImageMap.erase(curr_it); + } + } } -CPDF_Font* CPDF_DocPageData::GetFont(CPDF_Dictionary* pFontDict, FX_BOOL findOnly) -{ - if (!pFontDict) { - return NULL; - } - if (findOnly) { - auto it = m_FontMap.find(pFontDict); - if (it != m_FontMap.end() && it->second->get()) { - return it->second->AddRef(); - } - return nullptr; - } - - CPDF_CountedFont* fontData = nullptr; +CPDF_Font* CPDF_DocPageData::GetFont(CPDF_Dictionary* pFontDict, + FX_BOOL findOnly) { + if (!pFontDict) { + return NULL; + } + if (findOnly) { auto it = m_FontMap.find(pFontDict); - if (it != m_FontMap.end()) { - fontData = it->second; - if (fontData->get()) { - return fontData->AddRef(); - } + if (it != m_FontMap.end() && it->second->get()) { + return it->second->AddRef(); } + return nullptr; + } - CPDF_Font* pFont = CPDF_Font::CreateFontF(m_pPDFDoc, pFontDict); - if (!pFont) { - return nullptr; - } - if (!fontData) { - fontData = new CPDF_CountedFont(pFont); - m_FontMap[pFontDict] = fontData; - } else { - fontData->reset(pFont); + CPDF_CountedFont* fontData = nullptr; + auto it = m_FontMap.find(pFontDict); + if (it != m_FontMap.end()) { + fontData = it->second; + if (fontData->get()) { + return fontData->AddRef(); } - return fontData->AddRef(); + } + + CPDF_Font* pFont = CPDF_Font::CreateFontF(m_pPDFDoc, pFontDict); + if (!pFont) { + return nullptr; + } + if (!fontData) { + fontData = new CPDF_CountedFont(pFont); + m_FontMap[pFontDict] = fontData; + } else { + fontData->reset(pFont); + } + return fontData->AddRef(); } -CPDF_Font* CPDF_DocPageData::GetStandardFont(const CFX_ByteStringC& fontName, CPDF_FontEncoding* pEncoding) -{ - if (fontName.IsEmpty()) - return nullptr; - - for (auto& it : m_FontMap) { - CPDF_CountedFont* fontData = it.second; - CPDF_Font* pFont = fontData->get(); - if (!pFont) - continue; - if (pFont->GetBaseFont() != fontName) - continue; - if (pFont->IsEmbedded()) - continue; - if (pFont->GetFontType() != PDFFONT_TYPE1) - continue; - if (pFont->GetFontDict()->KeyExist(FX_BSTRC("Widths"))) - continue; - - CPDF_Type1Font* pT1Font = pFont->GetType1Font(); - if (pEncoding && !pT1Font->GetEncoding()->IsIdentical(pEncoding)) - continue; - - return fontData->AddRef(); - } +CPDF_Font* CPDF_DocPageData::GetStandardFont(const CFX_ByteStringC& fontName, + CPDF_FontEncoding* pEncoding) { + if (fontName.IsEmpty()) + return nullptr; + + for (auto& it : m_FontMap) { + CPDF_CountedFont* fontData = it.second; + CPDF_Font* pFont = fontData->get(); + if (!pFont) + continue; + if (pFont->GetBaseFont() != fontName) + continue; + if (pFont->IsEmbedded()) + continue; + if (pFont->GetFontType() != PDFFONT_TYPE1) + continue; + if (pFont->GetFontDict()->KeyExist(FX_BSTRC("Widths"))) + continue; + + CPDF_Type1Font* pT1Font = pFont->GetType1Font(); + if (pEncoding && !pT1Font->GetEncoding()->IsIdentical(pEncoding)) + continue; - CPDF_Dictionary* pDict = new CPDF_Dictionary; - pDict->SetAtName(FX_BSTRC("Type"), FX_BSTRC("Font")); - pDict->SetAtName(FX_BSTRC("Subtype"), FX_BSTRC("Type1")); - pDict->SetAtName(FX_BSTRC("BaseFont"), fontName); - if (pEncoding) { - pDict->SetAt(FX_BSTRC("Encoding"), pEncoding->Realize()); - } - m_pPDFDoc->AddIndirectObject(pDict); - CPDF_Font* pFont = CPDF_Font::CreateFontF(m_pPDFDoc, pDict); - if (!pFont) { - return nullptr; - } - CPDF_CountedFont* fontData = new CPDF_CountedFont(pFont); - m_FontMap[pDict] = fontData; return fontData->AddRef(); + } + + CPDF_Dictionary* pDict = new CPDF_Dictionary; + pDict->SetAtName(FX_BSTRC("Type"), FX_BSTRC("Font")); + pDict->SetAtName(FX_BSTRC("Subtype"), FX_BSTRC("Type1")); + pDict->SetAtName(FX_BSTRC("BaseFont"), fontName); + if (pEncoding) { + pDict->SetAt(FX_BSTRC("Encoding"), pEncoding->Realize()); + } + m_pPDFDoc->AddIndirectObject(pDict); + CPDF_Font* pFont = CPDF_Font::CreateFontF(m_pPDFDoc, pDict); + if (!pFont) { + return nullptr; + } + CPDF_CountedFont* fontData = new CPDF_CountedFont(pFont); + m_FontMap[pDict] = fontData; + return fontData->AddRef(); } -void CPDF_DocPageData::ReleaseFont(CPDF_Dictionary* pFontDict) -{ - if (!pFontDict) - return; +void CPDF_DocPageData::ReleaseFont(CPDF_Dictionary* pFontDict) { + if (!pFontDict) + return; - auto it = m_FontMap.find(pFontDict); - if (it == m_FontMap.end()) - return; + auto it = m_FontMap.find(pFontDict); + if (it == m_FontMap.end()) + return; - CPDF_CountedFont* fontData = it->second; - if (fontData->get()) { - fontData->RemoveRef(); - if (fontData->use_count() == 0) { - fontData->clear(); - } + CPDF_CountedFont* fontData = it->second; + if (fontData->get()) { + fontData->RemoveRef(); + if (fontData->use_count() == 0) { + fontData->clear(); } + } } -CPDF_ColorSpace* CPDF_DocPageData::GetColorSpace(CPDF_Object* pCSObj, CPDF_Dictionary* pResources) -{ - if (!pCSObj) { - return NULL; - } - if (pCSObj->GetType() == PDFOBJ_NAME) { - CFX_ByteString name = pCSObj->GetConstString(); - CPDF_ColorSpace* pCS = _CSFromName(name); - if (!pCS && pResources) { - CPDF_Dictionary* pList = pResources->GetDict(FX_BSTRC("ColorSpace")); - if (pList) { - pCSObj = pList->GetElementValue(name); - return GetColorSpace(pCSObj, NULL); - } - } - if (pCS == NULL || pResources == NULL) { - return pCS; - } - CPDF_Dictionary* pColorSpaces = pResources->GetDict(FX_BSTRC("ColorSpace")); - if (pColorSpaces == NULL) { - return pCS; - } - CPDF_Object* pDefaultCS = NULL; - switch (pCS->GetFamily()) { - case PDFCS_DEVICERGB: - pDefaultCS = pColorSpaces->GetElementValue(FX_BSTRC("DefaultRGB")); - break; - case PDFCS_DEVICEGRAY: - pDefaultCS = pColorSpaces->GetElementValue(FX_BSTRC("DefaultGray")); - break; - case PDFCS_DEVICECMYK: - pDefaultCS = pColorSpaces->GetElementValue(FX_BSTRC("DefaultCMYK")); - break; - } - if (pDefaultCS == NULL) { - return pCS; - } - return GetColorSpace(pDefaultCS, NULL); - } +CPDF_ColorSpace* CPDF_DocPageData::GetColorSpace(CPDF_Object* pCSObj, + CPDF_Dictionary* pResources) { + if (!pCSObj) { + return NULL; + } + if (pCSObj->GetType() == PDFOBJ_NAME) { + CFX_ByteString name = pCSObj->GetConstString(); + CPDF_ColorSpace* pCS = _CSFromName(name); + if (!pCS && pResources) { + CPDF_Dictionary* pList = pResources->GetDict(FX_BSTRC("ColorSpace")); + if (pList) { + pCSObj = pList->GetElementValue(name); + return GetColorSpace(pCSObj, NULL); + } + } + if (pCS == NULL || pResources == NULL) { + return pCS; + } + CPDF_Dictionary* pColorSpaces = pResources->GetDict(FX_BSTRC("ColorSpace")); + if (pColorSpaces == NULL) { + return pCS; + } + CPDF_Object* pDefaultCS = NULL; + switch (pCS->GetFamily()) { + case PDFCS_DEVICERGB: + pDefaultCS = pColorSpaces->GetElementValue(FX_BSTRC("DefaultRGB")); + break; + case PDFCS_DEVICEGRAY: + pDefaultCS = pColorSpaces->GetElementValue(FX_BSTRC("DefaultGray")); + break; + case PDFCS_DEVICECMYK: + pDefaultCS = pColorSpaces->GetElementValue(FX_BSTRC("DefaultCMYK")); + break; + } + if (pDefaultCS == NULL) { + return pCS; + } + return GetColorSpace(pDefaultCS, NULL); + } + + if (pCSObj->GetType() != PDFOBJ_ARRAY) + return nullptr; + CPDF_Array* pArray = (CPDF_Array*)pCSObj; + if (pArray->GetCount() == 0) + return nullptr; + if (pArray->GetCount() == 1) + return GetColorSpace(pArray->GetElementValue(0), pResources); - if (pCSObj->GetType() != PDFOBJ_ARRAY) - return nullptr; - CPDF_Array* pArray = (CPDF_Array*)pCSObj; - if (pArray->GetCount() == 0) - return nullptr; - if (pArray->GetCount() == 1) - return GetColorSpace(pArray->GetElementValue(0), pResources); - - CPDF_CountedColorSpace* csData = nullptr; - auto it = m_ColorSpaceMap.find(pCSObj); - if (it != m_ColorSpaceMap.end()) { - csData = it->second; - if (csData->get()) { - return csData->AddRef(); - } + CPDF_CountedColorSpace* csData = nullptr; + auto it = m_ColorSpaceMap.find(pCSObj); + if (it != m_ColorSpaceMap.end()) { + csData = it->second; + if (csData->get()) { + return csData->AddRef(); } + } - CPDF_ColorSpace* pCS = CPDF_ColorSpace::Load(m_pPDFDoc, pArray); - if (!pCS) - return nullptr; + CPDF_ColorSpace* pCS = CPDF_ColorSpace::Load(m_pPDFDoc, pArray); + if (!pCS) + return nullptr; - if (!csData) { - csData = new CPDF_CountedColorSpace(pCS); - m_ColorSpaceMap[pCSObj] = csData; - } else { - csData->reset(pCS); - } - return csData->AddRef(); + if (!csData) { + csData = new CPDF_CountedColorSpace(pCS); + m_ColorSpaceMap[pCSObj] = csData; + } else { + csData->reset(pCS); + } + return csData->AddRef(); } -CPDF_ColorSpace* CPDF_DocPageData::GetCopiedColorSpace(CPDF_Object* pCSObj) -{ - if (!pCSObj) - return nullptr; +CPDF_ColorSpace* CPDF_DocPageData::GetCopiedColorSpace(CPDF_Object* pCSObj) { + if (!pCSObj) + return nullptr; - auto it = m_ColorSpaceMap.find(pCSObj); - if (it != m_ColorSpaceMap.end()) - return it->second->AddRef(); + auto it = m_ColorSpaceMap.find(pCSObj); + if (it != m_ColorSpaceMap.end()) + return it->second->AddRef(); - return nullptr; + return nullptr; } -void CPDF_DocPageData::ReleaseColorSpace(CPDF_Object* pColorSpace) -{ - if (!pColorSpace) - return; +void CPDF_DocPageData::ReleaseColorSpace(CPDF_Object* pColorSpace) { + if (!pColorSpace) + return; - auto it = m_ColorSpaceMap.find(pColorSpace); - if (it == m_ColorSpaceMap.end()) - return; + auto it = m_ColorSpaceMap.find(pColorSpace); + if (it == m_ColorSpaceMap.end()) + return; - CPDF_CountedColorSpace* csData = it->second; - if (csData->get()) { - csData->RemoveRef(); - if (csData->use_count() == 0) { - csData->get()->ReleaseCS(); - csData->reset(nullptr); - } + CPDF_CountedColorSpace* csData = it->second; + if (csData->get()) { + csData->RemoveRef(); + if (csData->use_count() == 0) { + csData->get()->ReleaseCS(); + csData->reset(nullptr); } + } } -CPDF_Pattern* CPDF_DocPageData::GetPattern(CPDF_Object* pPatternObj, FX_BOOL bShading, const CFX_AffineMatrix* matrix) -{ - if (!pPatternObj) - return nullptr; - - CPDF_CountedPattern* ptData = nullptr; - auto it = m_PatternMap.find(pPatternObj); - if (it != m_PatternMap.end()) { - ptData = it->second; - if (ptData->get()) { - return ptData->AddRef(); - } - } - CPDF_Pattern* pPattern = nullptr; - if (bShading) { - pPattern = new CPDF_ShadingPattern(m_pPDFDoc, pPatternObj, bShading, matrix); - } else { - CPDF_Dictionary* pDict = pPatternObj ? pPatternObj->GetDict() : nullptr; - if (pDict) { - int type = pDict->GetInteger(FX_BSTRC("PatternType")); - if (type == 1) { - pPattern = new CPDF_TilingPattern(m_pPDFDoc, pPatternObj, matrix); - } else if (type == 2) { - pPattern = new CPDF_ShadingPattern(m_pPDFDoc, pPatternObj, FALSE, matrix); - } - } - } - if (!pPattern) - return nullptr; - - if (!ptData) { - ptData = new CPDF_CountedPattern(pPattern); - m_PatternMap[pPatternObj] = ptData; - } else { - ptData->reset(pPattern); - } - return ptData->AddRef(); +CPDF_Pattern* CPDF_DocPageData::GetPattern(CPDF_Object* pPatternObj, + FX_BOOL bShading, + const CFX_AffineMatrix* matrix) { + if (!pPatternObj) + return nullptr; + + CPDF_CountedPattern* ptData = nullptr; + auto it = m_PatternMap.find(pPatternObj); + if (it != m_PatternMap.end()) { + ptData = it->second; + if (ptData->get()) { + return ptData->AddRef(); + } + } + CPDF_Pattern* pPattern = nullptr; + if (bShading) { + pPattern = + new CPDF_ShadingPattern(m_pPDFDoc, pPatternObj, bShading, matrix); + } else { + CPDF_Dictionary* pDict = pPatternObj ? pPatternObj->GetDict() : nullptr; + if (pDict) { + int type = pDict->GetInteger(FX_BSTRC("PatternType")); + if (type == 1) { + pPattern = new CPDF_TilingPattern(m_pPDFDoc, pPatternObj, matrix); + } else if (type == 2) { + pPattern = + new CPDF_ShadingPattern(m_pPDFDoc, pPatternObj, FALSE, matrix); + } + } + } + if (!pPattern) + return nullptr; + + if (!ptData) { + ptData = new CPDF_CountedPattern(pPattern); + m_PatternMap[pPatternObj] = ptData; + } else { + ptData->reset(pPattern); + } + return ptData->AddRef(); } -void CPDF_DocPageData::ReleasePattern(CPDF_Object* pPatternObj) -{ - if (!pPatternObj) - return; +void CPDF_DocPageData::ReleasePattern(CPDF_Object* pPatternObj) { + if (!pPatternObj) + return; - auto it = m_PatternMap.find(pPatternObj); - if (it == m_PatternMap.end()) - return; + auto it = m_PatternMap.find(pPatternObj); + if (it == m_PatternMap.end()) + return; - CPDF_CountedPattern* ptData = it->second; - if (ptData->get()) { - ptData->RemoveRef(); - if (ptData->use_count() == 0) { - ptData->clear(); - } + CPDF_CountedPattern* ptData = it->second; + if (ptData->get()) { + ptData->RemoveRef(); + if (ptData->use_count() == 0) { + ptData->clear(); } + } } -CPDF_Image* CPDF_DocPageData::GetImage(CPDF_Object* pImageStream) -{ - if (!pImageStream) - return nullptr; +CPDF_Image* CPDF_DocPageData::GetImage(CPDF_Object* pImageStream) { + if (!pImageStream) + return nullptr; - const FX_DWORD dwImageObjNum = pImageStream->GetObjNum(); - auto it = m_ImageMap.find(dwImageObjNum); - if (it != m_ImageMap.end()) { - return it->second->AddRef(); - } + const FX_DWORD dwImageObjNum = pImageStream->GetObjNum(); + auto it = m_ImageMap.find(dwImageObjNum); + if (it != m_ImageMap.end()) { + return it->second->AddRef(); + } - CPDF_Image* pImage = new CPDF_Image(m_pPDFDoc); - pImage->LoadImageF((CPDF_Stream*)pImageStream, FALSE); + CPDF_Image* pImage = new CPDF_Image(m_pPDFDoc); + pImage->LoadImageF((CPDF_Stream*)pImageStream, FALSE); - CPDF_CountedImage* imageData = new CPDF_CountedImage(pImage); - m_ImageMap[dwImageObjNum] = imageData; - return imageData->AddRef(); + CPDF_CountedImage* imageData = new CPDF_CountedImage(pImage); + m_ImageMap[dwImageObjNum] = imageData; + return imageData->AddRef(); } -void CPDF_DocPageData::ReleaseImage(CPDF_Object* pImageStream) -{ - if (!pImageStream || !pImageStream->GetObjNum()) - return; +void CPDF_DocPageData::ReleaseImage(CPDF_Object* pImageStream) { + if (!pImageStream || !pImageStream->GetObjNum()) + return; - auto it = m_ImageMap.find(pImageStream->GetObjNum()); - if (it == m_ImageMap.end()) - return; + auto it = m_ImageMap.find(pImageStream->GetObjNum()); + if (it == m_ImageMap.end()) + return; - CPDF_CountedImage* image = it->second; - if (!image) - return; + CPDF_CountedImage* image = it->second; + if (!image) + return; - image->RemoveRef(); - if (image->use_count() == 0) { - delete image->get(); - delete image; - m_ImageMap.erase(it); - } + image->RemoveRef(); + if (image->use_count() == 0) { + delete image->get(); + delete image; + m_ImageMap.erase(it); + } } -CPDF_IccProfile* CPDF_DocPageData::GetIccProfile(CPDF_Stream* pIccProfileStream) -{ - if (!pIccProfileStream) - return NULL; - - auto it = m_IccProfileMap.find(pIccProfileStream); - if (it != m_IccProfileMap.end()) { - return it->second->AddRef(); - } +CPDF_IccProfile* CPDF_DocPageData::GetIccProfile( + CPDF_Stream* pIccProfileStream) { + if (!pIccProfileStream) + return NULL; - CPDF_StreamAcc stream; - stream.LoadAllData(pIccProfileStream, FALSE); - uint8_t digest[20]; - CPDF_Stream* pCopiedStream = nullptr; - CRYPT_SHA1Generate(stream.GetData(), stream.GetSize(), digest); - if (m_HashProfileMap.Lookup(CFX_ByteStringC(digest, 20), (void*&)pCopiedStream)) { - auto it_copied_stream = m_IccProfileMap.find(pCopiedStream); - return it_copied_stream->second->AddRef(); - } - CPDF_IccProfile* pProfile = new CPDF_IccProfile(stream.GetData(), stream.GetSize()); - CPDF_CountedIccProfile* ipData = new CPDF_CountedIccProfile(pProfile); - m_IccProfileMap[pIccProfileStream] = ipData; - m_HashProfileMap.SetAt(CFX_ByteStringC(digest, 20), pIccProfileStream); - return ipData->AddRef(); + auto it = m_IccProfileMap.find(pIccProfileStream); + if (it != m_IccProfileMap.end()) { + return it->second->AddRef(); + } + + CPDF_StreamAcc stream; + stream.LoadAllData(pIccProfileStream, FALSE); + uint8_t digest[20]; + CPDF_Stream* pCopiedStream = nullptr; + CRYPT_SHA1Generate(stream.GetData(), stream.GetSize(), digest); + if (m_HashProfileMap.Lookup(CFX_ByteStringC(digest, 20), + (void*&)pCopiedStream)) { + auto it_copied_stream = m_IccProfileMap.find(pCopiedStream); + return it_copied_stream->second->AddRef(); + } + CPDF_IccProfile* pProfile = + new CPDF_IccProfile(stream.GetData(), stream.GetSize()); + CPDF_CountedIccProfile* ipData = new CPDF_CountedIccProfile(pProfile); + m_IccProfileMap[pIccProfileStream] = ipData; + m_HashProfileMap.SetAt(CFX_ByteStringC(digest, 20), pIccProfileStream); + return ipData->AddRef(); } -void CPDF_DocPageData::ReleaseIccProfile(CPDF_IccProfile* pIccProfile) -{ - ASSERT(pIccProfile); - - for (auto it = m_IccProfileMap.begin(); it != m_IccProfileMap.end(); ++it) { - CPDF_CountedIccProfile* profile = it->second; - if (profile->get() != pIccProfile) - continue; - - profile->RemoveRef(); - if (profile->use_count() == 0) { - delete profile->get(); - delete profile; - m_IccProfileMap.erase(it); - return; - } +void CPDF_DocPageData::ReleaseIccProfile(CPDF_IccProfile* pIccProfile) { + ASSERT(pIccProfile); + + for (auto it = m_IccProfileMap.begin(); it != m_IccProfileMap.end(); ++it) { + CPDF_CountedIccProfile* profile = it->second; + if (profile->get() != pIccProfile) + continue; + + profile->RemoveRef(); + if (profile->use_count() == 0) { + delete profile->get(); + delete profile; + m_IccProfileMap.erase(it); + return; } + } } -CPDF_StreamAcc* CPDF_DocPageData::GetFontFileStreamAcc(CPDF_Stream* pFontStream) -{ - ASSERT(pFontStream); +CPDF_StreamAcc* CPDF_DocPageData::GetFontFileStreamAcc( + CPDF_Stream* pFontStream) { + ASSERT(pFontStream); - auto it = m_FontFileMap.find(pFontStream); - if (it != m_FontFileMap.end()) - return it->second->AddRef(); + auto it = m_FontFileMap.find(pFontStream); + if (it != m_FontFileMap.end()) + return it->second->AddRef(); - CPDF_Dictionary* pFontDict = pFontStream->GetDict(); - int32_t org_size = pFontDict->GetInteger(FX_BSTRC("Length1")) + - pFontDict->GetInteger(FX_BSTRC("Length2")) + - pFontDict->GetInteger(FX_BSTRC("Length3")); - if (org_size < 0) - org_size = 0; + CPDF_Dictionary* pFontDict = pFontStream->GetDict(); + int32_t org_size = pFontDict->GetInteger(FX_BSTRC("Length1")) + + pFontDict->GetInteger(FX_BSTRC("Length2")) + + pFontDict->GetInteger(FX_BSTRC("Length3")); + if (org_size < 0) + org_size = 0; - CPDF_StreamAcc* pFontFile = new CPDF_StreamAcc; - pFontFile->LoadAllData(pFontStream, FALSE, org_size); + CPDF_StreamAcc* pFontFile = new CPDF_StreamAcc; + pFontFile->LoadAllData(pFontStream, FALSE, org_size); - CPDF_CountedStreamAcc* ftData = new CPDF_CountedStreamAcc(pFontFile); - m_FontFileMap[pFontStream] = ftData; - return ftData->AddRef(); + CPDF_CountedStreamAcc* ftData = new CPDF_CountedStreamAcc(pFontFile); + m_FontFileMap[pFontStream] = ftData; + return ftData->AddRef(); } -void CPDF_DocPageData::ReleaseFontFileStreamAcc(CPDF_Stream* pFontStream, FX_BOOL bForce) -{ - if (!pFontStream) - return; - - auto it = m_FontFileMap.find(pFontStream); - if (it == m_FontFileMap.end()) - return; - - CPDF_CountedStreamAcc* findData = it->second; - if (!findData) - return; - - findData->RemoveRef(); - if (findData->use_count() == 0 || bForce) { - delete findData->get(); - delete findData; - m_FontFileMap.erase(it); - } +void CPDF_DocPageData::ReleaseFontFileStreamAcc(CPDF_Stream* pFontStream, + FX_BOOL bForce) { + if (!pFontStream) + return; + + auto it = m_FontFileMap.find(pFontStream); + if (it == m_FontFileMap.end()) + return; + + CPDF_CountedStreamAcc* findData = it->second; + if (!findData) + return; + + findData->RemoveRef(); + if (findData->use_count() == 0 || bForce) { + delete findData->get(); + delete findData; + m_FontFileMap.erase(it); + } } -CPDF_CountedColorSpace* CPDF_DocPageData::FindColorSpacePtr(CPDF_Object* pCSObj) const -{ - if (!pCSObj) - return nullptr; +CPDF_CountedColorSpace* CPDF_DocPageData::FindColorSpacePtr( + CPDF_Object* pCSObj) const { + if (!pCSObj) + return nullptr; - auto it = m_ColorSpaceMap.find(pCSObj); - return it != m_ColorSpaceMap.end() ? it->second : nullptr; + auto it = m_ColorSpaceMap.find(pCSObj); + return it != m_ColorSpaceMap.end() ? it->second : nullptr; } -CPDF_CountedPattern* CPDF_DocPageData::FindPatternPtr(CPDF_Object* pPatternObj) const -{ - if (!pPatternObj) - return nullptr; +CPDF_CountedPattern* CPDF_DocPageData::FindPatternPtr( + CPDF_Object* pPatternObj) const { + if (!pPatternObj) + return nullptr; - auto it = m_PatternMap.find(pPatternObj); - return it != m_PatternMap.end() ? it->second : nullptr; + auto it = m_PatternMap.find(pPatternObj); + return it != m_PatternMap.end() ? it->second : nullptr; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_func.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_func.cpp index c961f8b20f..87ff0a3b63 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_func.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_func.cpp @@ -13,893 +13,907 @@ #include "pageint.h" class CPDF_PSEngine; -typedef enum {PSOP_ADD, PSOP_SUB, PSOP_MUL, PSOP_DIV, PSOP_IDIV, PSOP_MOD, - PSOP_NEG, PSOP_ABS, PSOP_CEILING, PSOP_FLOOR, PSOP_ROUND, PSOP_TRUNCATE, - PSOP_SQRT, PSOP_SIN, PSOP_COS, PSOP_ATAN, PSOP_EXP, PSOP_LN, PSOP_LOG, - PSOP_CVI, PSOP_CVR, PSOP_EQ, PSOP_NE, PSOP_GT, PSOP_GE, PSOP_LT, PSOP_LE, - PSOP_AND, PSOP_OR, PSOP_XOR, PSOP_NOT, PSOP_BITSHIFT, PSOP_TRUE, PSOP_FALSE, - PSOP_IF, PSOP_IFELSE, PSOP_POP, PSOP_EXCH, PSOP_DUP, PSOP_COPY, - PSOP_INDEX, PSOP_ROLL, PSOP_PROC, PSOP_CONST - } PDF_PSOP; -class CPDF_PSProc -{ -public: - ~CPDF_PSProc(); - FX_BOOL Parse(CPDF_SimpleParser& parser); - FX_BOOL Execute(CPDF_PSEngine* pEngine); - CFX_PtrArray m_Operators; +typedef enum { + PSOP_ADD, + PSOP_SUB, + PSOP_MUL, + PSOP_DIV, + PSOP_IDIV, + PSOP_MOD, + PSOP_NEG, + PSOP_ABS, + PSOP_CEILING, + PSOP_FLOOR, + PSOP_ROUND, + PSOP_TRUNCATE, + PSOP_SQRT, + PSOP_SIN, + PSOP_COS, + PSOP_ATAN, + PSOP_EXP, + PSOP_LN, + PSOP_LOG, + PSOP_CVI, + PSOP_CVR, + PSOP_EQ, + PSOP_NE, + PSOP_GT, + PSOP_GE, + PSOP_LT, + PSOP_LE, + PSOP_AND, + PSOP_OR, + PSOP_XOR, + PSOP_NOT, + PSOP_BITSHIFT, + PSOP_TRUE, + PSOP_FALSE, + PSOP_IF, + PSOP_IFELSE, + PSOP_POP, + PSOP_EXCH, + PSOP_DUP, + PSOP_COPY, + PSOP_INDEX, + PSOP_ROLL, + PSOP_PROC, + PSOP_CONST +} PDF_PSOP; +class CPDF_PSProc { + public: + ~CPDF_PSProc(); + FX_BOOL Parse(CPDF_SimpleParser& parser); + FX_BOOL Execute(CPDF_PSEngine* pEngine); + CFX_PtrArray m_Operators; }; #define PSENGINE_STACKSIZE 100 -class CPDF_PSEngine -{ -public: - CPDF_PSEngine(); - ~CPDF_PSEngine(); - FX_BOOL Parse(const FX_CHAR* string, int size); - FX_BOOL Execute() - { - return m_MainProc.Execute(this); - } - FX_BOOL DoOperator(PDF_PSOP op); - void Reset() - { - m_StackCount = 0; - } - void Push(FX_FLOAT value); - void Push(int value) - { - Push((FX_FLOAT)value); - } - FX_FLOAT Pop(); - int GetStackSize() - { - return m_StackCount; - } -private: - FX_FLOAT m_Stack[PSENGINE_STACKSIZE]; - int m_StackCount; - CPDF_PSProc m_MainProc; +class CPDF_PSEngine { + public: + CPDF_PSEngine(); + ~CPDF_PSEngine(); + FX_BOOL Parse(const FX_CHAR* string, int size); + FX_BOOL Execute() { return m_MainProc.Execute(this); } + FX_BOOL DoOperator(PDF_PSOP op); + void Reset() { m_StackCount = 0; } + void Push(FX_FLOAT value); + void Push(int value) { Push((FX_FLOAT)value); } + FX_FLOAT Pop(); + int GetStackSize() { return m_StackCount; } + + private: + FX_FLOAT m_Stack[PSENGINE_STACKSIZE]; + int m_StackCount; + CPDF_PSProc m_MainProc; }; -CPDF_PSProc::~CPDF_PSProc() -{ - int size = m_Operators.GetSize(); - for (int i = 0; i < size; i ++) { - if (m_Operators[i] == (void*)PSOP_PROC) { - delete (CPDF_PSProc*)m_Operators[i + 1]; - i ++; - } else if (m_Operators[i] == (void*)PSOP_CONST) { - FX_Free((FX_FLOAT*)m_Operators[i + 1]); - i ++; - } - } +CPDF_PSProc::~CPDF_PSProc() { + int size = m_Operators.GetSize(); + for (int i = 0; i < size; i++) { + if (m_Operators[i] == (void*)PSOP_PROC) { + delete (CPDF_PSProc*)m_Operators[i + 1]; + i++; + } else if (m_Operators[i] == (void*)PSOP_CONST) { + FX_Free((FX_FLOAT*)m_Operators[i + 1]); + i++; + } + } } -FX_BOOL CPDF_PSProc::Execute(CPDF_PSEngine* pEngine) -{ - int size = m_Operators.GetSize(); - for (int i = 0; i < size; i ++) { - PDF_PSOP op = (PDF_PSOP)(uintptr_t)m_Operators[i]; - if (op == PSOP_PROC) { - i ++; - } else if (op == PSOP_CONST) { - pEngine->Push(*(FX_FLOAT*)m_Operators[i + 1]); - i ++; - } else if (op == PSOP_IF) { - if (i < 2 || m_Operators[i - 2] != (void*)PSOP_PROC) { - return FALSE; - } - if ((int)pEngine->Pop()) { - ((CPDF_PSProc*)m_Operators[i - 1])->Execute(pEngine); - } - } else if (op == PSOP_IFELSE) { - if (i < 4 || m_Operators[i - 2] != (void*)PSOP_PROC || - m_Operators[i - 4] != (void*)PSOP_PROC) { - return FALSE; - } - if ((int)pEngine->Pop()) { - ((CPDF_PSProc*)m_Operators[i - 3])->Execute(pEngine); - } else { - ((CPDF_PSProc*)m_Operators[i - 1])->Execute(pEngine); - } - } else { - pEngine->DoOperator(op); - } +FX_BOOL CPDF_PSProc::Execute(CPDF_PSEngine* pEngine) { + int size = m_Operators.GetSize(); + for (int i = 0; i < size; i++) { + PDF_PSOP op = (PDF_PSOP)(uintptr_t)m_Operators[i]; + if (op == PSOP_PROC) { + i++; + } else if (op == PSOP_CONST) { + pEngine->Push(*(FX_FLOAT*)m_Operators[i + 1]); + i++; + } else if (op == PSOP_IF) { + if (i < 2 || m_Operators[i - 2] != (void*)PSOP_PROC) { + return FALSE; + } + if ((int)pEngine->Pop()) { + ((CPDF_PSProc*)m_Operators[i - 1])->Execute(pEngine); + } + } else if (op == PSOP_IFELSE) { + if (i < 4 || m_Operators[i - 2] != (void*)PSOP_PROC || + m_Operators[i - 4] != (void*)PSOP_PROC) { + return FALSE; + } + if ((int)pEngine->Pop()) { + ((CPDF_PSProc*)m_Operators[i - 3])->Execute(pEngine); + } else { + ((CPDF_PSProc*)m_Operators[i - 1])->Execute(pEngine); + } + } else { + pEngine->DoOperator(op); } - return TRUE; -} -CPDF_PSEngine::CPDF_PSEngine() -{ - m_StackCount = 0; + } + return TRUE; } -CPDF_PSEngine::~CPDF_PSEngine() -{ +CPDF_PSEngine::CPDF_PSEngine() { + m_StackCount = 0; } -void CPDF_PSEngine::Push(FX_FLOAT v) -{ - if (m_StackCount == 100) { - return; - } - m_Stack[m_StackCount++] = v; +CPDF_PSEngine::~CPDF_PSEngine() {} +void CPDF_PSEngine::Push(FX_FLOAT v) { + if (m_StackCount == 100) { + return; + } + m_Stack[m_StackCount++] = v; } -FX_FLOAT CPDF_PSEngine::Pop() -{ - if (m_StackCount == 0) { - return 0; - } - return m_Stack[--m_StackCount]; +FX_FLOAT CPDF_PSEngine::Pop() { + if (m_StackCount == 0) { + return 0; + } + return m_Stack[--m_StackCount]; } const struct _PDF_PSOpName { - const FX_CHAR* name; - PDF_PSOP op; -} _PDF_PSOpNames[] = { - {"add", PSOP_ADD}, {"sub", PSOP_SUB}, {"mul", PSOP_MUL}, {"div", PSOP_DIV}, - {"idiv", PSOP_IDIV}, {"mod", PSOP_MOD}, {"neg", PSOP_NEG}, {"abs", PSOP_ABS}, - {"ceiling", PSOP_CEILING}, {"floor", PSOP_FLOOR}, {"round", PSOP_ROUND}, - {"truncate", PSOP_TRUNCATE}, {"sqrt", PSOP_SQRT}, {"sin", PSOP_SIN}, - {"cos", PSOP_COS}, {"atan", PSOP_ATAN}, {"exp", PSOP_EXP}, {"ln", PSOP_LN}, - {"log", PSOP_LOG}, {"cvi", PSOP_CVI}, {"cvr", PSOP_CVR}, {"eq", PSOP_EQ}, - {"ne", PSOP_NE}, {"gt", PSOP_GT}, {"ge", PSOP_GE}, {"lt", PSOP_LT}, - {"le", PSOP_LE}, {"and", PSOP_AND}, {"or", PSOP_OR}, {"xor", PSOP_XOR}, - {"not", PSOP_NOT}, {"bitshift", PSOP_BITSHIFT}, {"true", PSOP_TRUE}, - {"false", PSOP_FALSE}, {"if", PSOP_IF}, {"ifelse", PSOP_IFELSE}, - {"pop", PSOP_POP}, {"exch", PSOP_EXCH}, {"dup", PSOP_DUP}, - {"copy", PSOP_COPY}, {"index", PSOP_INDEX}, {"roll", PSOP_ROLL}, - {NULL, PSOP_PROC} -}; -FX_BOOL CPDF_PSEngine::Parse(const FX_CHAR* string, int size) -{ - CPDF_SimpleParser parser((uint8_t*)string, size); + const FX_CHAR* name; + PDF_PSOP op; +} _PDF_PSOpNames[] = {{"add", PSOP_ADD}, {"sub", PSOP_SUB}, + {"mul", PSOP_MUL}, {"div", PSOP_DIV}, + {"idiv", PSOP_IDIV}, {"mod", PSOP_MOD}, + {"neg", PSOP_NEG}, {"abs", PSOP_ABS}, + {"ceiling", PSOP_CEILING}, {"floor", PSOP_FLOOR}, + {"round", PSOP_ROUND}, {"truncate", PSOP_TRUNCATE}, + {"sqrt", PSOP_SQRT}, {"sin", PSOP_SIN}, + {"cos", PSOP_COS}, {"atan", PSOP_ATAN}, + {"exp", PSOP_EXP}, {"ln", PSOP_LN}, + {"log", PSOP_LOG}, {"cvi", PSOP_CVI}, + {"cvr", PSOP_CVR}, {"eq", PSOP_EQ}, + {"ne", PSOP_NE}, {"gt", PSOP_GT}, + {"ge", PSOP_GE}, {"lt", PSOP_LT}, + {"le", PSOP_LE}, {"and", PSOP_AND}, + {"or", PSOP_OR}, {"xor", PSOP_XOR}, + {"not", PSOP_NOT}, {"bitshift", PSOP_BITSHIFT}, + {"true", PSOP_TRUE}, {"false", PSOP_FALSE}, + {"if", PSOP_IF}, {"ifelse", PSOP_IFELSE}, + {"pop", PSOP_POP}, {"exch", PSOP_EXCH}, + {"dup", PSOP_DUP}, {"copy", PSOP_COPY}, + {"index", PSOP_INDEX}, {"roll", PSOP_ROLL}, + {NULL, PSOP_PROC}}; +FX_BOOL CPDF_PSEngine::Parse(const FX_CHAR* string, int size) { + CPDF_SimpleParser parser((uint8_t*)string, size); + CFX_ByteStringC word = parser.GetWord(); + if (word != FX_BSTRC("{")) { + return FALSE; + } + return m_MainProc.Parse(parser); +} +FX_BOOL CPDF_PSProc::Parse(CPDF_SimpleParser& parser) { + while (1) { CFX_ByteStringC word = parser.GetWord(); - if (word != FX_BSTRC("{")) { - return FALSE; + if (word.IsEmpty()) { + return FALSE; } - return m_MainProc.Parse(parser); -} -FX_BOOL CPDF_PSProc::Parse(CPDF_SimpleParser& parser) -{ - while (1) { - CFX_ByteStringC word = parser.GetWord(); - if (word.IsEmpty()) { - return FALSE; - } - if (word == FX_BSTRC("}")) { - return TRUE; - } - if (word == FX_BSTRC("{")) { - CPDF_PSProc* pProc = new CPDF_PSProc; - m_Operators.Add((void*)PSOP_PROC); - m_Operators.Add(pProc); - if (!pProc->Parse(parser)) { - return FALSE; - } - } else { - int i = 0; - while (_PDF_PSOpNames[i].name) { - if (word == CFX_ByteStringC(_PDF_PSOpNames[i].name)) { - m_Operators.Add((void*)_PDF_PSOpNames[i].op); - break; - } - i ++; - } - if (_PDF_PSOpNames[i].name == NULL) { - FX_FLOAT* pd = FX_Alloc(FX_FLOAT, 1); - *pd = FX_atof(word); - m_Operators.Add((void*)PSOP_CONST); - m_Operators.Add(pd); - } - } + if (word == FX_BSTRC("}")) { + return TRUE; } + if (word == FX_BSTRC("{")) { + CPDF_PSProc* pProc = new CPDF_PSProc; + m_Operators.Add((void*)PSOP_PROC); + m_Operators.Add(pProc); + if (!pProc->Parse(parser)) { + return FALSE; + } + } else { + int i = 0; + while (_PDF_PSOpNames[i].name) { + if (word == CFX_ByteStringC(_PDF_PSOpNames[i].name)) { + m_Operators.Add((void*)_PDF_PSOpNames[i].op); + break; + } + i++; + } + if (_PDF_PSOpNames[i].name == NULL) { + FX_FLOAT* pd = FX_Alloc(FX_FLOAT, 1); + *pd = FX_atof(word); + m_Operators.Add((void*)PSOP_CONST); + m_Operators.Add(pd); + } + } + } } #define PI 3.1415926535897932384626433832795f -FX_BOOL CPDF_PSEngine::DoOperator(PDF_PSOP op) -{ - int i1, i2; - FX_FLOAT d1, d2; - switch (op) { - case PSOP_ADD: - d1 = Pop(); - d2 = Pop(); - Push(d1 + d2); - break; - case PSOP_SUB: - d2 = Pop(); - d1 = Pop(); - Push(d1 - d2); - break; - case PSOP_MUL: - d1 = Pop(); - d2 = Pop(); - Push(d1 * d2); - break; - case PSOP_DIV: - d2 = Pop(); - d1 = Pop(); - Push(d1 / d2); - break; - case PSOP_IDIV: - i2 = (int)Pop(); - i1 = (int)Pop(); - Push(i1 / i2); - break; - case PSOP_MOD: - i2 = (int)Pop(); - i1 = (int)Pop(); - Push(i1 % i2); - break; - case PSOP_NEG: - d1 = Pop(); - Push(-d1); - break; - case PSOP_ABS: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_fabs(d1)); - break; - case PSOP_CEILING: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_ceil(d1)); - break; - case PSOP_FLOOR: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_floor(d1)); - break; - case PSOP_ROUND: - d1 = Pop(); - Push(FXSYS_round(d1)); - break; - case PSOP_TRUNCATE: - i1 = (int)Pop(); - Push(i1); - break; - case PSOP_SQRT: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_sqrt(d1)); - break; - case PSOP_SIN: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_sin(d1 * PI / 180.0f)); - break; - case PSOP_COS: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_cos(d1 * PI / 180.0f)); - break; - case PSOP_ATAN: - d2 = Pop(); - d1 = Pop(); - d1 = (FX_FLOAT)(FXSYS_atan2(d1, d2) * 180.0 / PI); - if (d1 < 0) { - d1 += 360; - } - Push(d1); - break; - case PSOP_EXP: - d2 = Pop(); - d1 = Pop(); - Push((FX_FLOAT)FXSYS_pow(d1, d2)); - break; - case PSOP_LN: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_log(d1)); - break; - case PSOP_LOG: - d1 = Pop(); - Push((FX_FLOAT)FXSYS_log10(d1)); - break; - case PSOP_CVI: - i1 = (int)Pop(); - Push(i1); - break; - case PSOP_CVR: - break; - case PSOP_EQ: - d2 = Pop(); - d1 = Pop(); - Push((int)(d1 == d2)); - break; - case PSOP_NE: - d2 = Pop(); - d1 = Pop(); - Push((int)(d1 != d2)); - break; - case PSOP_GT: - d2 = Pop(); - d1 = Pop(); - Push((int)(d1 > d2)); - break; - case PSOP_GE: - d2 = Pop(); - d1 = Pop(); - Push((int)(d1 >= d2)); - break; - case PSOP_LT: - d2 = Pop(); - d1 = Pop(); - Push((int)(d1 < d2)); - break; - case PSOP_LE: - d2 = Pop(); - d1 = Pop(); - Push((int)(d1 <= d2)); - break; - case PSOP_AND: - i1 = (int)Pop(); - i2 = (int)Pop(); - Push(i1 & i2); - break; - case PSOP_OR: - i1 = (int)Pop(); - i2 = (int)Pop(); - Push(i1 | i2); - break; - case PSOP_XOR: - i1 = (int)Pop(); - i2 = (int)Pop(); - Push(i1 ^ i2); - break; - case PSOP_NOT: - i1 = (int)Pop(); - Push((int)!i1); - break; - case PSOP_BITSHIFT: { - int shift = (int)Pop(); - int i = (int)Pop(); - if (shift > 0) { - Push(i << shift); - } else { - Push(i >> -shift); - } - break; - } - case PSOP_TRUE: - Push(1); - break; - case PSOP_FALSE: - Push(0); - break; - case PSOP_POP: - Pop(); - break; - case PSOP_EXCH: - d2 = Pop(); - d1 = Pop(); - Push(d2); - Push(d1); - break; - case PSOP_DUP: - d1 = Pop(); - Push(d1); - Push(d1); - break; - case PSOP_COPY: { - int n = (int)Pop(); - if (n < 0 || n > PSENGINE_STACKSIZE || m_StackCount + n > PSENGINE_STACKSIZE || n > m_StackCount) { - break; - } - for (int i = 0; i < n; i ++) { - m_Stack[m_StackCount + i] = m_Stack[m_StackCount + i - n]; - } - m_StackCount += n; - break; - } - case PSOP_INDEX: { - int n = (int)Pop(); - if (n < 0 || n >= m_StackCount) { - break; - } - Push(m_Stack[m_StackCount - n - 1]); - break; - } - case PSOP_ROLL: { - int j = (int)Pop(); - int n = (int)Pop(); - if (m_StackCount == 0) { - break; - } - if (n < 0 || n > m_StackCount) { - break; - } - if (j < 0) - for (int i = 0; i < -j; i ++) { - FX_FLOAT first = m_Stack[m_StackCount - n]; - for (int ii = 0; ii < n - 1; ii ++) { - m_Stack[m_StackCount - n + ii] = m_Stack[m_StackCount - n + ii + 1]; - } - m_Stack[m_StackCount - 1] = first; - } - else - for (int i = 0; i < j; i ++) { - FX_FLOAT last = m_Stack[m_StackCount - 1]; - int ii; - for (ii = 0; ii < n - 1; ii ++) { - m_Stack[m_StackCount - ii - 1] = m_Stack[m_StackCount - ii - 2]; - } - m_Stack[m_StackCount - ii - 1] = last; - } - break; - } - default: - break; +FX_BOOL CPDF_PSEngine::DoOperator(PDF_PSOP op) { + int i1, i2; + FX_FLOAT d1, d2; + switch (op) { + case PSOP_ADD: + d1 = Pop(); + d2 = Pop(); + Push(d1 + d2); + break; + case PSOP_SUB: + d2 = Pop(); + d1 = Pop(); + Push(d1 - d2); + break; + case PSOP_MUL: + d1 = Pop(); + d2 = Pop(); + Push(d1 * d2); + break; + case PSOP_DIV: + d2 = Pop(); + d1 = Pop(); + Push(d1 / d2); + break; + case PSOP_IDIV: + i2 = (int)Pop(); + i1 = (int)Pop(); + Push(i1 / i2); + break; + case PSOP_MOD: + i2 = (int)Pop(); + i1 = (int)Pop(); + Push(i1 % i2); + break; + case PSOP_NEG: + d1 = Pop(); + Push(-d1); + break; + case PSOP_ABS: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_fabs(d1)); + break; + case PSOP_CEILING: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_ceil(d1)); + break; + case PSOP_FLOOR: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_floor(d1)); + break; + case PSOP_ROUND: + d1 = Pop(); + Push(FXSYS_round(d1)); + break; + case PSOP_TRUNCATE: + i1 = (int)Pop(); + Push(i1); + break; + case PSOP_SQRT: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_sqrt(d1)); + break; + case PSOP_SIN: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_sin(d1 * PI / 180.0f)); + break; + case PSOP_COS: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_cos(d1 * PI / 180.0f)); + break; + case PSOP_ATAN: + d2 = Pop(); + d1 = Pop(); + d1 = (FX_FLOAT)(FXSYS_atan2(d1, d2) * 180.0 / PI); + if (d1 < 0) { + d1 += 360; + } + Push(d1); + break; + case PSOP_EXP: + d2 = Pop(); + d1 = Pop(); + Push((FX_FLOAT)FXSYS_pow(d1, d2)); + break; + case PSOP_LN: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_log(d1)); + break; + case PSOP_LOG: + d1 = Pop(); + Push((FX_FLOAT)FXSYS_log10(d1)); + break; + case PSOP_CVI: + i1 = (int)Pop(); + Push(i1); + break; + case PSOP_CVR: + break; + case PSOP_EQ: + d2 = Pop(); + d1 = Pop(); + Push((int)(d1 == d2)); + break; + case PSOP_NE: + d2 = Pop(); + d1 = Pop(); + Push((int)(d1 != d2)); + break; + case PSOP_GT: + d2 = Pop(); + d1 = Pop(); + Push((int)(d1 > d2)); + break; + case PSOP_GE: + d2 = Pop(); + d1 = Pop(); + Push((int)(d1 >= d2)); + break; + case PSOP_LT: + d2 = Pop(); + d1 = Pop(); + Push((int)(d1 < d2)); + break; + case PSOP_LE: + d2 = Pop(); + d1 = Pop(); + Push((int)(d1 <= d2)); + break; + case PSOP_AND: + i1 = (int)Pop(); + i2 = (int)Pop(); + Push(i1 & i2); + break; + case PSOP_OR: + i1 = (int)Pop(); + i2 = (int)Pop(); + Push(i1 | i2); + break; + case PSOP_XOR: + i1 = (int)Pop(); + i2 = (int)Pop(); + Push(i1 ^ i2); + break; + case PSOP_NOT: + i1 = (int)Pop(); + Push((int)!i1); + break; + case PSOP_BITSHIFT: { + int shift = (int)Pop(); + int i = (int)Pop(); + if (shift > 0) { + Push(i << shift); + } else { + Push(i >> -shift); + } + break; + } + case PSOP_TRUE: + Push(1); + break; + case PSOP_FALSE: + Push(0); + break; + case PSOP_POP: + Pop(); + break; + case PSOP_EXCH: + d2 = Pop(); + d1 = Pop(); + Push(d2); + Push(d1); + break; + case PSOP_DUP: + d1 = Pop(); + Push(d1); + Push(d1); + break; + case PSOP_COPY: { + int n = (int)Pop(); + if (n < 0 || n > PSENGINE_STACKSIZE || + m_StackCount + n > PSENGINE_STACKSIZE || n > m_StackCount) { + break; + } + for (int i = 0; i < n; i++) { + m_Stack[m_StackCount + i] = m_Stack[m_StackCount + i - n]; + } + m_StackCount += n; + break; + } + case PSOP_INDEX: { + int n = (int)Pop(); + if (n < 0 || n >= m_StackCount) { + break; + } + Push(m_Stack[m_StackCount - n - 1]); + break; + } + case PSOP_ROLL: { + int j = (int)Pop(); + int n = (int)Pop(); + if (m_StackCount == 0) { + break; + } + if (n < 0 || n > m_StackCount) { + break; + } + if (j < 0) + for (int i = 0; i < -j; i++) { + FX_FLOAT first = m_Stack[m_StackCount - n]; + for (int ii = 0; ii < n - 1; ii++) { + m_Stack[m_StackCount - n + ii] = m_Stack[m_StackCount - n + ii + 1]; + } + m_Stack[m_StackCount - 1] = first; + } + else + for (int i = 0; i < j; i++) { + FX_FLOAT last = m_Stack[m_StackCount - 1]; + int ii; + for (ii = 0; ii < n - 1; ii++) { + m_Stack[m_StackCount - ii - 1] = m_Stack[m_StackCount - ii - 2]; + } + m_Stack[m_StackCount - ii - 1] = last; + } + break; } - return TRUE; + default: + break; + } + return TRUE; } -static FX_FLOAT PDF_Interpolate(FX_FLOAT x, FX_FLOAT xmin, FX_FLOAT xmax, FX_FLOAT ymin, FX_FLOAT ymax) -{ - return ((x - xmin) * (ymax - ymin) / (xmax - xmin)) + ymin; +static FX_FLOAT PDF_Interpolate(FX_FLOAT x, + FX_FLOAT xmin, + FX_FLOAT xmax, + FX_FLOAT ymin, + FX_FLOAT ymax) { + return ((x - xmin) * (ymax - ymin) / (xmax - xmin)) + ymin; } -static FX_DWORD _GetBits32(const uint8_t* pData, int bitpos, int nbits) -{ - int result = 0; - for (int i = 0; i < nbits; i ++) - if (pData[(bitpos + i) / 8] & (1 << (7 - (bitpos + i) % 8))) { - result |= 1 << (nbits - i - 1); - } - return result; +static FX_DWORD _GetBits32(const uint8_t* pData, int bitpos, int nbits) { + int result = 0; + for (int i = 0; i < nbits; i++) + if (pData[(bitpos + i) / 8] & (1 << (7 - (bitpos + i) % 8))) { + result |= 1 << (nbits - i - 1); + } + return result; } typedef struct { - FX_FLOAT encode_max, encode_min; - int sizes; + FX_FLOAT encode_max, encode_min; + int sizes; } SampleEncodeInfo; -typedef struct { - FX_FLOAT decode_max, decode_min; -} SampleDecodeInfo; -class CPDF_SampledFunc : public CPDF_Function -{ -public: - CPDF_SampledFunc(); - virtual ~CPDF_SampledFunc(); - virtual FX_BOOL v_Init(CPDF_Object* pObj); - virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; - SampleEncodeInfo* m_pEncodeInfo; - SampleDecodeInfo* m_pDecodeInfo; - FX_DWORD m_nBitsPerSample; - FX_DWORD m_SampleMax; - CPDF_StreamAcc* m_pSampleStream; +typedef struct { FX_FLOAT decode_max, decode_min; } SampleDecodeInfo; +class CPDF_SampledFunc : public CPDF_Function { + public: + CPDF_SampledFunc(); + virtual ~CPDF_SampledFunc(); + virtual FX_BOOL v_Init(CPDF_Object* pObj); + virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; + SampleEncodeInfo* m_pEncodeInfo; + SampleDecodeInfo* m_pDecodeInfo; + FX_DWORD m_nBitsPerSample; + FX_DWORD m_SampleMax; + CPDF_StreamAcc* m_pSampleStream; }; -CPDF_SampledFunc::CPDF_SampledFunc() -{ - m_pSampleStream = NULL; - m_pEncodeInfo = NULL; - m_pDecodeInfo = NULL; +CPDF_SampledFunc::CPDF_SampledFunc() { + m_pSampleStream = NULL; + m_pEncodeInfo = NULL; + m_pDecodeInfo = NULL; } -CPDF_SampledFunc::~CPDF_SampledFunc() -{ - delete m_pSampleStream; - if (m_pEncodeInfo) { - FX_Free(m_pEncodeInfo); - } - if (m_pDecodeInfo) { - FX_Free(m_pDecodeInfo); - } +CPDF_SampledFunc::~CPDF_SampledFunc() { + delete m_pSampleStream; + if (m_pEncodeInfo) { + FX_Free(m_pEncodeInfo); + } + if (m_pDecodeInfo) { + FX_Free(m_pDecodeInfo); + } } -FX_BOOL CPDF_SampledFunc::v_Init(CPDF_Object* pObj) -{ - if (pObj->GetType() != PDFOBJ_STREAM) { - return FALSE; - } - CPDF_Stream* pStream = (CPDF_Stream*)pObj; - CPDF_Dictionary* pDict = pStream->GetDict(); - CPDF_Array* pSize = pDict->GetArray(FX_BSTRC("Size")); - CPDF_Array* pEncode = pDict->GetArray(FX_BSTRC("Encode")); - CPDF_Array* pDecode = pDict->GetArray(FX_BSTRC("Decode")); - m_nBitsPerSample = pDict->GetInteger(FX_BSTRC("BitsPerSample")); - if (m_nBitsPerSample > 32) { - return FALSE; - } - m_SampleMax = 0xffffffff >> (32 - m_nBitsPerSample); - m_pSampleStream = new CPDF_StreamAcc; - m_pSampleStream->LoadAllData(pStream, FALSE); - m_pEncodeInfo = FX_Alloc(SampleEncodeInfo, m_nInputs); - FX_SAFE_DWORD nTotalSampleBits = 1; - for (int i = 0; i < m_nInputs; i ++) { - m_pEncodeInfo[i].sizes = pSize ? pSize->GetInteger(i) : 0; - if (!pSize && i == 0) { - m_pEncodeInfo[i].sizes = pDict->GetInteger(FX_BSTRC("Size")); - } - nTotalSampleBits *= m_pEncodeInfo[i].sizes; - if (pEncode) { - m_pEncodeInfo[i].encode_min = pEncode->GetFloat(i * 2); - m_pEncodeInfo[i].encode_max = pEncode->GetFloat(i * 2 + 1); - } else { - m_pEncodeInfo[i].encode_min = 0; - if (m_pEncodeInfo[i].sizes == 1) { - m_pEncodeInfo[i].encode_max = 1; - } else { - m_pEncodeInfo[i].encode_max = (FX_FLOAT)m_pEncodeInfo[i].sizes - 1; - } - } - } - nTotalSampleBits *= m_nBitsPerSample; - nTotalSampleBits *= m_nOutputs; - FX_SAFE_DWORD nTotalSampleBytes = nTotalSampleBits; - nTotalSampleBytes += 7; - nTotalSampleBytes /= 8; - if (!nTotalSampleBytes.IsValid() || - nTotalSampleBytes.ValueOrDie() == 0 || - nTotalSampleBytes.ValueOrDie() > m_pSampleStream->GetSize()) { - return FALSE; - } - m_pDecodeInfo = FX_Alloc(SampleDecodeInfo, m_nOutputs); - for (int i = 0; i < m_nOutputs; i ++) { - if (pDecode) { - m_pDecodeInfo[i].decode_min = pDecode->GetFloat(2 * i); - m_pDecodeInfo[i].decode_max = pDecode->GetFloat(2 * i + 1); - } else { - m_pDecodeInfo[i].decode_min = m_pRanges[i * 2]; - m_pDecodeInfo[i].decode_max = m_pRanges[i * 2 + 1]; - } +FX_BOOL CPDF_SampledFunc::v_Init(CPDF_Object* pObj) { + if (pObj->GetType() != PDFOBJ_STREAM) { + return FALSE; + } + CPDF_Stream* pStream = (CPDF_Stream*)pObj; + CPDF_Dictionary* pDict = pStream->GetDict(); + CPDF_Array* pSize = pDict->GetArray(FX_BSTRC("Size")); + CPDF_Array* pEncode = pDict->GetArray(FX_BSTRC("Encode")); + CPDF_Array* pDecode = pDict->GetArray(FX_BSTRC("Decode")); + m_nBitsPerSample = pDict->GetInteger(FX_BSTRC("BitsPerSample")); + if (m_nBitsPerSample > 32) { + return FALSE; + } + m_SampleMax = 0xffffffff >> (32 - m_nBitsPerSample); + m_pSampleStream = new CPDF_StreamAcc; + m_pSampleStream->LoadAllData(pStream, FALSE); + m_pEncodeInfo = FX_Alloc(SampleEncodeInfo, m_nInputs); + FX_SAFE_DWORD nTotalSampleBits = 1; + for (int i = 0; i < m_nInputs; i++) { + m_pEncodeInfo[i].sizes = pSize ? pSize->GetInteger(i) : 0; + if (!pSize && i == 0) { + m_pEncodeInfo[i].sizes = pDict->GetInteger(FX_BSTRC("Size")); + } + nTotalSampleBits *= m_pEncodeInfo[i].sizes; + if (pEncode) { + m_pEncodeInfo[i].encode_min = pEncode->GetFloat(i * 2); + m_pEncodeInfo[i].encode_max = pEncode->GetFloat(i * 2 + 1); + } else { + m_pEncodeInfo[i].encode_min = 0; + if (m_pEncodeInfo[i].sizes == 1) { + m_pEncodeInfo[i].encode_max = 1; + } else { + m_pEncodeInfo[i].encode_max = (FX_FLOAT)m_pEncodeInfo[i].sizes - 1; + } + } + } + nTotalSampleBits *= m_nBitsPerSample; + nTotalSampleBits *= m_nOutputs; + FX_SAFE_DWORD nTotalSampleBytes = nTotalSampleBits; + nTotalSampleBytes += 7; + nTotalSampleBytes /= 8; + if (!nTotalSampleBytes.IsValid() || nTotalSampleBytes.ValueOrDie() == 0 || + nTotalSampleBytes.ValueOrDie() > m_pSampleStream->GetSize()) { + return FALSE; + } + m_pDecodeInfo = FX_Alloc(SampleDecodeInfo, m_nOutputs); + for (int i = 0; i < m_nOutputs; i++) { + if (pDecode) { + m_pDecodeInfo[i].decode_min = pDecode->GetFloat(2 * i); + m_pDecodeInfo[i].decode_max = pDecode->GetFloat(2 * i + 1); + } else { + m_pDecodeInfo[i].decode_min = m_pRanges[i * 2]; + m_pDecodeInfo[i].decode_max = m_pRanges[i * 2 + 1]; } - return TRUE; + } + return TRUE; } -FX_BOOL CPDF_SampledFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const -{ - int pos = 0; - CFX_FixedBufGrow encoded_input_buf(m_nInputs); - FX_FLOAT* encoded_input = encoded_input_buf; - CFX_FixedBufGrow int_buf(m_nInputs * 2); - int* index = int_buf; - int* blocksize = index + m_nInputs; - for (int i = 0; i < m_nInputs; i ++) { - if (i == 0) { - blocksize[i] = 1; - } else { - blocksize[i] = blocksize[i - 1] * m_pEncodeInfo[i - 1].sizes; - } - encoded_input[i] = PDF_Interpolate(inputs[i], m_pDomains[i * 2], m_pDomains[i * 2 + 1], - m_pEncodeInfo[i].encode_min, m_pEncodeInfo[i].encode_max); - index[i] = (int)encoded_input[i]; - if (index[i] < 0) { - index[i] = 0; - } else if (index[i] > m_pEncodeInfo[i].sizes - 1) { - index[i] = m_pEncodeInfo[i].sizes - 1; +FX_BOOL CPDF_SampledFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const { + int pos = 0; + CFX_FixedBufGrow encoded_input_buf(m_nInputs); + FX_FLOAT* encoded_input = encoded_input_buf; + CFX_FixedBufGrow int_buf(m_nInputs * 2); + int* index = int_buf; + int* blocksize = index + m_nInputs; + for (int i = 0; i < m_nInputs; i++) { + if (i == 0) { + blocksize[i] = 1; + } else { + blocksize[i] = blocksize[i - 1] * m_pEncodeInfo[i - 1].sizes; + } + encoded_input[i] = PDF_Interpolate( + inputs[i], m_pDomains[i * 2], m_pDomains[i * 2 + 1], + m_pEncodeInfo[i].encode_min, m_pEncodeInfo[i].encode_max); + index[i] = (int)encoded_input[i]; + if (index[i] < 0) { + index[i] = 0; + } else if (index[i] > m_pEncodeInfo[i].sizes - 1) { + index[i] = m_pEncodeInfo[i].sizes - 1; + } + pos += index[i] * blocksize[i]; + } + FX_SAFE_INT32 bits_to_output = m_nOutputs; + bits_to_output *= m_nBitsPerSample; + if (!bits_to_output.IsValid()) { + return FALSE; + } + FX_SAFE_INT32 bitpos = pos; + bitpos *= bits_to_output.ValueOrDie(); + if (!bitpos.IsValid()) { + return FALSE; + } + FX_SAFE_INT32 range_check = bitpos; + range_check += bits_to_output.ValueOrDie(); + if (!range_check.IsValid()) { + return FALSE; + } + const uint8_t* pSampleData = m_pSampleStream->GetData(); + if (!pSampleData) { + return FALSE; + } + for (int j = 0; j < m_nOutputs; j++) { + FX_DWORD sample = + _GetBits32(pSampleData, bitpos.ValueOrDie() + j * m_nBitsPerSample, + m_nBitsPerSample); + FX_FLOAT encoded = (FX_FLOAT)sample; + for (int i = 0; i < m_nInputs; i++) { + if (index[i] == m_pEncodeInfo[i].sizes - 1) { + if (index[i] == 0) { + encoded = encoded_input[i] * (FX_FLOAT)sample; } - pos += index[i] * blocksize[i]; - } - FX_SAFE_INT32 bits_to_output = m_nOutputs; - bits_to_output *= m_nBitsPerSample; - if (!bits_to_output.IsValid()) { - return FALSE; - } - FX_SAFE_INT32 bitpos = pos; - bitpos *= bits_to_output.ValueOrDie(); - if (!bitpos.IsValid()) { - return FALSE; - } - FX_SAFE_INT32 range_check = bitpos; - range_check += bits_to_output.ValueOrDie(); - if (!range_check.IsValid()) { - return FALSE; - } - const uint8_t* pSampleData = m_pSampleStream->GetData(); - if (!pSampleData) { - return FALSE; - } - for (int j = 0; j < m_nOutputs; j ++) { - FX_DWORD sample = _GetBits32(pSampleData, bitpos.ValueOrDie() + j * m_nBitsPerSample, m_nBitsPerSample); - FX_FLOAT encoded = (FX_FLOAT)sample; - for (int i = 0; i < m_nInputs; i ++) { - if (index[i] == m_pEncodeInfo[i].sizes - 1) { - if (index[i] == 0) { - encoded = encoded_input[i] * (FX_FLOAT)sample; - } - } else { - FX_SAFE_INT32 bitpos2 = blocksize[i]; - bitpos2 += pos; - bitpos2 *= m_nOutputs; - bitpos2 += j; - bitpos2 *= m_nBitsPerSample; - if (!bitpos2.IsValid()) { - return FALSE; - } - FX_DWORD sample1 = _GetBits32(pSampleData, bitpos2.ValueOrDie(), m_nBitsPerSample); - encoded += (encoded_input[i] - index[i]) * ((FX_FLOAT)sample1 - (FX_FLOAT)sample); - } + } else { + FX_SAFE_INT32 bitpos2 = blocksize[i]; + bitpos2 += pos; + bitpos2 *= m_nOutputs; + bitpos2 += j; + bitpos2 *= m_nBitsPerSample; + if (!bitpos2.IsValid()) { + return FALSE; } - results[j] = PDF_Interpolate(encoded, 0, (FX_FLOAT)m_SampleMax, - m_pDecodeInfo[j].decode_min, m_pDecodeInfo[j].decode_max); - } - return TRUE; + FX_DWORD sample1 = + _GetBits32(pSampleData, bitpos2.ValueOrDie(), m_nBitsPerSample); + encoded += (encoded_input[i] - index[i]) * + ((FX_FLOAT)sample1 - (FX_FLOAT)sample); + } + } + results[j] = PDF_Interpolate(encoded, 0, (FX_FLOAT)m_SampleMax, + m_pDecodeInfo[j].decode_min, + m_pDecodeInfo[j].decode_max); + } + return TRUE; } -class CPDF_PSFunc : public CPDF_Function -{ -public: - virtual FX_BOOL v_Init(CPDF_Object* pObj); - virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; - CPDF_PSEngine m_PS; +class CPDF_PSFunc : public CPDF_Function { + public: + virtual FX_BOOL v_Init(CPDF_Object* pObj); + virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; + CPDF_PSEngine m_PS; }; -FX_BOOL CPDF_PSFunc::v_Init(CPDF_Object* pObj) -{ - CPDF_Stream* pStream = (CPDF_Stream*)pObj; - CPDF_StreamAcc acc; - acc.LoadAllData(pStream, FALSE); - return m_PS.Parse((const FX_CHAR*)acc.GetData(), acc.GetSize()); +FX_BOOL CPDF_PSFunc::v_Init(CPDF_Object* pObj) { + CPDF_Stream* pStream = (CPDF_Stream*)pObj; + CPDF_StreamAcc acc; + acc.LoadAllData(pStream, FALSE); + return m_PS.Parse((const FX_CHAR*)acc.GetData(), acc.GetSize()); } -FX_BOOL CPDF_PSFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const -{ - CPDF_PSEngine& PS = (CPDF_PSEngine&)m_PS; - PS.Reset(); - int i; - for (i = 0; i < m_nInputs; i ++) { - PS.Push(inputs[i]); - } - PS.Execute(); - if (PS.GetStackSize() < m_nOutputs) { - return FALSE; - } - for (i = 0; i < m_nOutputs; i ++) { - results[m_nOutputs - i - 1] = PS.Pop(); - } - return TRUE; +FX_BOOL CPDF_PSFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const { + CPDF_PSEngine& PS = (CPDF_PSEngine&)m_PS; + PS.Reset(); + int i; + for (i = 0; i < m_nInputs; i++) { + PS.Push(inputs[i]); + } + PS.Execute(); + if (PS.GetStackSize() < m_nOutputs) { + return FALSE; + } + for (i = 0; i < m_nOutputs; i++) { + results[m_nOutputs - i - 1] = PS.Pop(); + } + return TRUE; } -class CPDF_ExpIntFunc : public CPDF_Function -{ -public: - CPDF_ExpIntFunc(); - virtual ~CPDF_ExpIntFunc(); - virtual FX_BOOL v_Init(CPDF_Object* pObj); - virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; - FX_FLOAT m_Exponent; - FX_FLOAT* m_pBeginValues; - FX_FLOAT* m_pEndValues; - int m_nOrigOutputs; +class CPDF_ExpIntFunc : public CPDF_Function { + public: + CPDF_ExpIntFunc(); + virtual ~CPDF_ExpIntFunc(); + virtual FX_BOOL v_Init(CPDF_Object* pObj); + virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; + FX_FLOAT m_Exponent; + FX_FLOAT* m_pBeginValues; + FX_FLOAT* m_pEndValues; + int m_nOrigOutputs; }; -CPDF_ExpIntFunc::CPDF_ExpIntFunc() -{ - m_pBeginValues = NULL; - m_pEndValues = NULL; +CPDF_ExpIntFunc::CPDF_ExpIntFunc() { + m_pBeginValues = NULL; + m_pEndValues = NULL; } -CPDF_ExpIntFunc::~CPDF_ExpIntFunc() -{ - if (m_pBeginValues) { - FX_Free(m_pBeginValues); - } - if (m_pEndValues) { - FX_Free(m_pEndValues); - } +CPDF_ExpIntFunc::~CPDF_ExpIntFunc() { + if (m_pBeginValues) { + FX_Free(m_pBeginValues); + } + if (m_pEndValues) { + FX_Free(m_pEndValues); + } } -FX_BOOL CPDF_ExpIntFunc::v_Init(CPDF_Object* pObj) -{ - CPDF_Dictionary* pDict = pObj->GetDict(); - if (pDict == NULL) { - return FALSE; - } - CPDF_Array* pArray0 = pDict->GetArray(FX_BSTRC("C0")); - if (m_nOutputs == 0) { - m_nOutputs = 1; - if (pArray0) { - m_nOutputs = pArray0->GetCount(); - } - } - CPDF_Array* pArray1 = pDict->GetArray(FX_BSTRC("C1")); - m_pBeginValues = FX_Alloc2D(FX_FLOAT, m_nOutputs, 2); - m_pEndValues = FX_Alloc2D(FX_FLOAT, m_nOutputs, 2); - for (int i = 0; i < m_nOutputs; i ++) { - m_pBeginValues[i] = pArray0 ? pArray0->GetFloat(i) : 0.0f; - m_pEndValues[i] = pArray1 ? pArray1->GetFloat(i) : 1.0f; - } - m_Exponent = pDict->GetFloat(FX_BSTRC("N")); - m_nOrigOutputs = m_nOutputs; - if (m_nOutputs && m_nInputs > INT_MAX / m_nOutputs) { - return FALSE; - } - m_nOutputs *= m_nInputs; - return TRUE; +FX_BOOL CPDF_ExpIntFunc::v_Init(CPDF_Object* pObj) { + CPDF_Dictionary* pDict = pObj->GetDict(); + if (pDict == NULL) { + return FALSE; + } + CPDF_Array* pArray0 = pDict->GetArray(FX_BSTRC("C0")); + if (m_nOutputs == 0) { + m_nOutputs = 1; + if (pArray0) { + m_nOutputs = pArray0->GetCount(); + } + } + CPDF_Array* pArray1 = pDict->GetArray(FX_BSTRC("C1")); + m_pBeginValues = FX_Alloc2D(FX_FLOAT, m_nOutputs, 2); + m_pEndValues = FX_Alloc2D(FX_FLOAT, m_nOutputs, 2); + for (int i = 0; i < m_nOutputs; i++) { + m_pBeginValues[i] = pArray0 ? pArray0->GetFloat(i) : 0.0f; + m_pEndValues[i] = pArray1 ? pArray1->GetFloat(i) : 1.0f; + } + m_Exponent = pDict->GetFloat(FX_BSTRC("N")); + m_nOrigOutputs = m_nOutputs; + if (m_nOutputs && m_nInputs > INT_MAX / m_nOutputs) { + return FALSE; + } + m_nOutputs *= m_nInputs; + return TRUE; } -FX_BOOL CPDF_ExpIntFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const -{ - for (int i = 0; i < m_nInputs; i ++) - for (int j = 0; j < m_nOrigOutputs; j ++) { - results[i * m_nOrigOutputs + j] = m_pBeginValues[j] + (FX_FLOAT)FXSYS_pow(inputs[i], m_Exponent) * - (m_pEndValues[j] - m_pBeginValues[j]); - } - return TRUE; +FX_BOOL CPDF_ExpIntFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const { + for (int i = 0; i < m_nInputs; i++) + for (int j = 0; j < m_nOrigOutputs; j++) { + results[i * m_nOrigOutputs + j] = + m_pBeginValues[j] + + (FX_FLOAT)FXSYS_pow(inputs[i], m_Exponent) * + (m_pEndValues[j] - m_pBeginValues[j]); + } + return TRUE; } -class CPDF_StitchFunc : public CPDF_Function -{ -public: - CPDF_StitchFunc(); - virtual ~CPDF_StitchFunc(); - virtual FX_BOOL v_Init(CPDF_Object* pObj); - virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; - int m_nSubs; - CPDF_Function** m_pSubFunctions; - FX_FLOAT* m_pBounds; - FX_FLOAT* m_pEncode; +class CPDF_StitchFunc : public CPDF_Function { + public: + CPDF_StitchFunc(); + virtual ~CPDF_StitchFunc(); + virtual FX_BOOL v_Init(CPDF_Object* pObj); + virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const; + int m_nSubs; + CPDF_Function** m_pSubFunctions; + FX_FLOAT* m_pBounds; + FX_FLOAT* m_pEncode; }; -CPDF_StitchFunc::CPDF_StitchFunc() -{ - m_nSubs = 0; - m_pSubFunctions = NULL; - m_pBounds = NULL; - m_pEncode = NULL; +CPDF_StitchFunc::CPDF_StitchFunc() { + m_nSubs = 0; + m_pSubFunctions = NULL; + m_pBounds = NULL; + m_pEncode = NULL; } -CPDF_StitchFunc::~CPDF_StitchFunc() -{ - for (int i = 0; i < m_nSubs; i ++) - delete m_pSubFunctions[i]; - if (m_pSubFunctions) { - FX_Free(m_pSubFunctions); - } - if (m_pBounds) { - FX_Free(m_pBounds); - } - if (m_pEncode) { - FX_Free(m_pEncode); - } +CPDF_StitchFunc::~CPDF_StitchFunc() { + for (int i = 0; i < m_nSubs; i++) + delete m_pSubFunctions[i]; + if (m_pSubFunctions) { + FX_Free(m_pSubFunctions); + } + if (m_pBounds) { + FX_Free(m_pBounds); + } + if (m_pEncode) { + FX_Free(m_pEncode); + } } -FX_BOOL CPDF_StitchFunc::v_Init(CPDF_Object* pObj) -{ - CPDF_Dictionary* pDict = pObj->GetDict(); - if (pDict == NULL) { - return FALSE; - } - CPDF_Array* pArray = pDict->GetArray(FX_BSTRC("Functions")); - if (pArray == NULL) { - return FALSE; - } - m_nSubs = pArray->GetCount(); - if (m_nSubs == 0) { - return FALSE; - } - m_pSubFunctions = FX_Alloc(CPDF_Function*, m_nSubs); - m_nOutputs = 0; - int i; - for (i = 0; i < m_nSubs; i ++) { - CPDF_Object* pSub = pArray->GetElementValue(i); - if (pSub == pObj) { - return FALSE; - } - m_pSubFunctions[i] = CPDF_Function::Load(pSub); - if (m_pSubFunctions[i] == NULL) { - return FALSE; - } - if (m_pSubFunctions[i]->CountOutputs() > m_nOutputs) { - m_nOutputs = m_pSubFunctions[i]->CountOutputs(); - } - } - m_pBounds = FX_Alloc(FX_FLOAT, m_nSubs + 1); - m_pBounds[0] = m_pDomains[0]; - pArray = pDict->GetArray(FX_BSTRC("Bounds")); - if (pArray == NULL) { - return FALSE; - } - for (i = 0; i < m_nSubs - 1; i ++) { - m_pBounds[i + 1] = pArray->GetFloat(i); - } - m_pBounds[m_nSubs] = m_pDomains[1]; - m_pEncode = FX_Alloc2D(FX_FLOAT, m_nSubs, 2); - pArray = pDict->GetArray(FX_BSTRC("Encode")); - if (pArray == NULL) { - return FALSE; - } - for (i = 0; i < m_nSubs * 2; i ++) { - m_pEncode[i] = pArray->GetFloat(i); - } - return TRUE; -} -FX_BOOL CPDF_StitchFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* outputs) const -{ - FX_FLOAT input = inputs[0]; - int i; - for (i = 0; i < m_nSubs - 1; i ++) - if (input < m_pBounds[i + 1]) { - break; - } +FX_BOOL CPDF_StitchFunc::v_Init(CPDF_Object* pObj) { + CPDF_Dictionary* pDict = pObj->GetDict(); + if (pDict == NULL) { + return FALSE; + } + CPDF_Array* pArray = pDict->GetArray(FX_BSTRC("Functions")); + if (pArray == NULL) { + return FALSE; + } + m_nSubs = pArray->GetCount(); + if (m_nSubs == 0) { + return FALSE; + } + m_pSubFunctions = FX_Alloc(CPDF_Function*, m_nSubs); + m_nOutputs = 0; + int i; + for (i = 0; i < m_nSubs; i++) { + CPDF_Object* pSub = pArray->GetElementValue(i); + if (pSub == pObj) { + return FALSE; + } + m_pSubFunctions[i] = CPDF_Function::Load(pSub); if (m_pSubFunctions[i] == NULL) { - return FALSE; - } - input = PDF_Interpolate(input, m_pBounds[i], m_pBounds[i + 1], m_pEncode[i * 2], m_pEncode[i * 2 + 1]); - int nresults; - m_pSubFunctions[i]->Call(&input, m_nInputs, outputs, nresults); - return TRUE; + return FALSE; + } + if (m_pSubFunctions[i]->CountOutputs() > m_nOutputs) { + m_nOutputs = m_pSubFunctions[i]->CountOutputs(); + } + } + m_pBounds = FX_Alloc(FX_FLOAT, m_nSubs + 1); + m_pBounds[0] = m_pDomains[0]; + pArray = pDict->GetArray(FX_BSTRC("Bounds")); + if (pArray == NULL) { + return FALSE; + } + for (i = 0; i < m_nSubs - 1; i++) { + m_pBounds[i + 1] = pArray->GetFloat(i); + } + m_pBounds[m_nSubs] = m_pDomains[1]; + m_pEncode = FX_Alloc2D(FX_FLOAT, m_nSubs, 2); + pArray = pDict->GetArray(FX_BSTRC("Encode")); + if (pArray == NULL) { + return FALSE; + } + for (i = 0; i < m_nSubs * 2; i++) { + m_pEncode[i] = pArray->GetFloat(i); + } + return TRUE; } -CPDF_Function* CPDF_Function::Load(CPDF_Object* pFuncObj) -{ - if (pFuncObj == NULL) { - return NULL; - } - CPDF_Function* pFunc = NULL; - int type; - if (pFuncObj->GetType() == PDFOBJ_STREAM) { - type = ((CPDF_Stream*)pFuncObj)->GetDict()->GetInteger(FX_BSTRC("FunctionType")); - } else if (pFuncObj->GetType() == PDFOBJ_DICTIONARY) { - type = ((CPDF_Dictionary*)pFuncObj)->GetInteger(FX_BSTRC("FunctionType")); - } else { - return NULL; - } - if (type == 0) { - pFunc = new CPDF_SampledFunc; - } else if (type == 2) { - pFunc = new CPDF_ExpIntFunc; - } else if (type == 3) { - pFunc = new CPDF_StitchFunc; - } else if (type == 4) { - pFunc = new CPDF_PSFunc; - } else { - return NULL; - } - if (!pFunc->Init(pFuncObj)) { - delete pFunc; - return NULL; - } - return pFunc; +FX_BOOL CPDF_StitchFunc::v_Call(FX_FLOAT* inputs, FX_FLOAT* outputs) const { + FX_FLOAT input = inputs[0]; + int i; + for (i = 0; i < m_nSubs - 1; i++) + if (input < m_pBounds[i + 1]) { + break; + } + if (m_pSubFunctions[i] == NULL) { + return FALSE; + } + input = PDF_Interpolate(input, m_pBounds[i], m_pBounds[i + 1], + m_pEncode[i * 2], m_pEncode[i * 2 + 1]); + int nresults; + m_pSubFunctions[i]->Call(&input, m_nInputs, outputs, nresults); + return TRUE; +} +CPDF_Function* CPDF_Function::Load(CPDF_Object* pFuncObj) { + if (pFuncObj == NULL) { + return NULL; + } + CPDF_Function* pFunc = NULL; + int type; + if (pFuncObj->GetType() == PDFOBJ_STREAM) { + type = ((CPDF_Stream*)pFuncObj) + ->GetDict() + ->GetInteger(FX_BSTRC("FunctionType")); + } else if (pFuncObj->GetType() == PDFOBJ_DICTIONARY) { + type = ((CPDF_Dictionary*)pFuncObj)->GetInteger(FX_BSTRC("FunctionType")); + } else { + return NULL; + } + if (type == 0) { + pFunc = new CPDF_SampledFunc; + } else if (type == 2) { + pFunc = new CPDF_ExpIntFunc; + } else if (type == 3) { + pFunc = new CPDF_StitchFunc; + } else if (type == 4) { + pFunc = new CPDF_PSFunc; + } else { + return NULL; + } + if (!pFunc->Init(pFuncObj)) { + delete pFunc; + return NULL; + } + return pFunc; +} +CPDF_Function::CPDF_Function() { + m_pDomains = NULL; + m_pRanges = NULL; } -CPDF_Function::CPDF_Function() -{ +CPDF_Function::~CPDF_Function() { + if (m_pDomains) { + FX_Free(m_pDomains); m_pDomains = NULL; + } + if (m_pRanges) { + FX_Free(m_pRanges); m_pRanges = NULL; + } } -CPDF_Function::~CPDF_Function() -{ - if (m_pDomains) { - FX_Free(m_pDomains); - m_pDomains = NULL; - } +FX_BOOL CPDF_Function::Init(CPDF_Object* pObj) { + CPDF_Dictionary* pDict; + if (pObj->GetType() == PDFOBJ_STREAM) { + pDict = ((CPDF_Stream*)pObj)->GetDict(); + } else { + pDict = (CPDF_Dictionary*)pObj; + } + CPDF_Array* pDomains = pDict->GetArray(FX_BSTRC("Domain")); + if (pDomains == NULL) { + return FALSE; + } + m_nInputs = pDomains->GetCount() / 2; + if (m_nInputs == 0) { + return FALSE; + } + m_pDomains = FX_Alloc2D(FX_FLOAT, m_nInputs, 2); + for (int i = 0; i < m_nInputs * 2; i++) { + m_pDomains[i] = pDomains->GetFloat(i); + } + CPDF_Array* pRanges = pDict->GetArray(FX_BSTRC("Range")); + m_nOutputs = 0; + if (pRanges) { + m_nOutputs = pRanges->GetCount() / 2; + m_pRanges = FX_Alloc2D(FX_FLOAT, m_nOutputs, 2); + for (int i = 0; i < m_nOutputs * 2; i++) { + m_pRanges[i] = pRanges->GetFloat(i); + } + } + FX_DWORD old_outputs = m_nOutputs; + if (!v_Init(pObj)) { + return FALSE; + } + if (m_pRanges && m_nOutputs > (int)old_outputs) { + m_pRanges = FX_Realloc(FX_FLOAT, m_pRanges, m_nOutputs * 2); if (m_pRanges) { - FX_Free(m_pRanges); - m_pRanges = NULL; - } -} -FX_BOOL CPDF_Function::Init(CPDF_Object* pObj) -{ - CPDF_Dictionary* pDict; - if (pObj->GetType() == PDFOBJ_STREAM) { - pDict = ((CPDF_Stream*)pObj)->GetDict(); - } else { - pDict = (CPDF_Dictionary*)pObj; - } - CPDF_Array* pDomains = pDict->GetArray(FX_BSTRC("Domain")); - if (pDomains == NULL) { - return FALSE; - } - m_nInputs = pDomains->GetCount() / 2; - if (m_nInputs == 0) { - return FALSE; - } - m_pDomains = FX_Alloc2D(FX_FLOAT, m_nInputs, 2); - for (int i = 0; i < m_nInputs * 2; i ++) { - m_pDomains[i] = pDomains->GetFloat(i); - } - CPDF_Array* pRanges = pDict->GetArray(FX_BSTRC("Range")); - m_nOutputs = 0; - if (pRanges) { - m_nOutputs = pRanges->GetCount() / 2; - m_pRanges = FX_Alloc2D(FX_FLOAT, m_nOutputs, 2); - for (int i = 0; i < m_nOutputs * 2; i ++) { - m_pRanges[i] = pRanges->GetFloat(i); - } - } - FX_DWORD old_outputs = m_nOutputs; - if (!v_Init(pObj)) { - return FALSE; - } - if (m_pRanges && m_nOutputs > (int)old_outputs) { - m_pRanges = FX_Realloc(FX_FLOAT, m_pRanges, m_nOutputs * 2); - if (m_pRanges) { - FXSYS_memset(m_pRanges + (old_outputs * 2), 0, sizeof(FX_FLOAT) * (m_nOutputs - old_outputs) * 2); - } + FXSYS_memset(m_pRanges + (old_outputs * 2), 0, + sizeof(FX_FLOAT) * (m_nOutputs - old_outputs) * 2); } - return TRUE; + } + return TRUE; } -FX_BOOL CPDF_Function::Call(FX_FLOAT* inputs, int ninputs, FX_FLOAT* results, int& nresults) const -{ - if (m_nInputs != ninputs) { - return FALSE; - } - nresults = m_nOutputs; - for (int i = 0; i < m_nInputs; i ++) { - if (inputs[i] < m_pDomains[i * 2]) { - inputs[i] = m_pDomains[i * 2]; - } else if (inputs[i] > m_pDomains[i * 2 + 1]) { - inputs[i] = m_pDomains[i * 2] + 1; - } - } - v_Call(inputs, results); - if (m_pRanges) { - for (int i = 0; i < m_nOutputs; i ++) { - if (results[i] < m_pRanges[i * 2]) { - results[i] = m_pRanges[i * 2]; - } else if (results[i] > m_pRanges[i * 2 + 1]) { - results[i] = m_pRanges[i * 2 + 1]; - } - } - } - return TRUE; +FX_BOOL CPDF_Function::Call(FX_FLOAT* inputs, + int ninputs, + FX_FLOAT* results, + int& nresults) const { + if (m_nInputs != ninputs) { + return FALSE; + } + nresults = m_nOutputs; + for (int i = 0; i < m_nInputs; i++) { + if (inputs[i] < m_pDomains[i * 2]) { + inputs[i] = m_pDomains[i * 2]; + } else if (inputs[i] > m_pDomains[i * 2 + 1]) { + inputs[i] = m_pDomains[i * 2] + 1; + } + } + v_Call(inputs, results); + if (m_pRanges) { + for (int i = 0; i < m_nOutputs; i++) { + if (results[i] < m_pRanges[i * 2]) { + results[i] = m_pRanges[i * 2]; + } else if (results[i] > m_pRanges[i * 2 + 1]) { + results[i] = m_pRanges[i * 2 + 1]; + } + } + } + return TRUE; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_graph_state.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_graph_state.cpp index b4d030e679..e010a28b02 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_graph_state.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_graph_state.cpp @@ -11,699 +11,682 @@ #include "../fpdf_render/render_int.h" #include "pageint.h" -void CPDF_GraphicStates::DefaultStates() -{ - m_ColorState.New()->Default(); -} -void CPDF_GraphicStates::CopyStates(const CPDF_GraphicStates& src) -{ - m_ClipPath = src.m_ClipPath; - m_GraphState = src.m_GraphState; - m_ColorState = src.m_ColorState; - m_TextState = src.m_TextState; - m_GeneralState = src.m_GeneralState; -} -CPDF_ClipPathData::CPDF_ClipPathData() -{ - m_PathCount = 0; +void CPDF_GraphicStates::DefaultStates() { + m_ColorState.New()->Default(); +} +void CPDF_GraphicStates::CopyStates(const CPDF_GraphicStates& src) { + m_ClipPath = src.m_ClipPath; + m_GraphState = src.m_GraphState; + m_ColorState = src.m_ColorState; + m_TextState = src.m_TextState; + m_GeneralState = src.m_GeneralState; +} +CPDF_ClipPathData::CPDF_ClipPathData() { + m_PathCount = 0; + m_pPathList = NULL; + m_pTypeList = NULL; + m_TextCount = 0; + m_pTextList = NULL; +} +CPDF_ClipPathData::~CPDF_ClipPathData() { + int i; + delete[] m_pPathList; + if (m_pTypeList) { + FX_Free(m_pTypeList); + } + for (i = m_TextCount - 1; i > -1; i--) + delete m_pTextList[i]; + if (m_pTextList) { + FX_Free(m_pTextList); + } +} +CPDF_ClipPathData::CPDF_ClipPathData(const CPDF_ClipPathData& src) { + m_pPathList = NULL; + m_pPathList = NULL; + m_pTextList = NULL; + m_PathCount = src.m_PathCount; + if (m_PathCount) { + int alloc_size = m_PathCount; + if (alloc_size % 8) { + alloc_size += 8 - (alloc_size % 8); + } + m_pPathList = new CPDF_Path[alloc_size]; + for (int i = 0; i < m_PathCount; i++) { + m_pPathList[i] = src.m_pPathList[i]; + } + m_pTypeList = FX_Alloc(uint8_t, alloc_size); + FXSYS_memcpy(m_pTypeList, src.m_pTypeList, m_PathCount); + } else { m_pPathList = NULL; m_pTypeList = NULL; - m_TextCount = 0; + } + m_TextCount = src.m_TextCount; + if (m_TextCount) { + m_pTextList = FX_Alloc(CPDF_TextObject*, m_TextCount); + for (int i = 0; i < m_TextCount; i++) { + if (src.m_pTextList[i]) { + m_pTextList[i] = new CPDF_TextObject; + m_pTextList[i]->Copy(src.m_pTextList[i]); + } else { + m_pTextList[i] = NULL; + } + } + } else { m_pTextList = NULL; -} -CPDF_ClipPathData::~CPDF_ClipPathData() -{ - int i; - delete[] m_pPathList; - if (m_pTypeList) { - FX_Free(m_pTypeList); - } - for (i = m_TextCount - 1; i > -1; i --) - delete m_pTextList[i]; - if (m_pTextList) { - FX_Free(m_pTextList); - } -} -CPDF_ClipPathData::CPDF_ClipPathData(const CPDF_ClipPathData& src) -{ - m_pPathList = NULL; - m_pPathList = NULL; - m_pTextList = NULL; - m_PathCount = src.m_PathCount; - if (m_PathCount) { - int alloc_size = m_PathCount; - if (alloc_size % 8) { - alloc_size += 8 - (alloc_size % 8); + } +} +void CPDF_ClipPathData::SetCount(int path_count, int text_count) { + ASSERT(m_TextCount == 0 && m_PathCount == 0); + if (path_count) { + m_PathCount = path_count; + int alloc_size = (path_count + 7) / 8 * 8; + m_pPathList = new CPDF_Path[alloc_size]; + m_pTypeList = FX_Alloc(uint8_t, alloc_size); + } + if (text_count) { + m_TextCount = text_count; + m_pTextList = FX_Alloc(CPDF_TextObject*, text_count); + } +} +CPDF_Rect CPDF_ClipPath::GetClipBox() const { + CPDF_Rect rect; + FX_BOOL bStarted = FALSE; + int count = GetPathCount(); + if (count) { + rect = GetPath(0).GetBoundingBox(); + for (int i = 1; i < count; i++) { + CPDF_Rect path_rect = GetPath(i).GetBoundingBox(); + rect.Intersect(path_rect); + } + bStarted = TRUE; + } + count = GetTextCount(); + if (count) { + CPDF_Rect layer_rect; + FX_BOOL bLayerStarted = FALSE; + for (int i = 0; i < count; i++) { + CPDF_TextObject* pTextObj = GetText(i); + if (pTextObj == NULL) { + if (!bStarted) { + rect = layer_rect; + bStarted = TRUE; + } else { + rect.Intersect(layer_rect); } - m_pPathList = new CPDF_Path[alloc_size]; - for (int i = 0; i < m_PathCount; i ++) { - m_pPathList[i] = src.m_pPathList[i]; + bLayerStarted = FALSE; + } else { + if (!bLayerStarted) { + layer_rect = pTextObj->GetBBox(NULL); + bLayerStarted = TRUE; + } else { + layer_rect.Union(pTextObj->GetBBox(NULL)); } - m_pTypeList = FX_Alloc(uint8_t, alloc_size); - FXSYS_memcpy(m_pTypeList, src.m_pTypeList, m_PathCount); - } else { - m_pPathList = NULL; - m_pTypeList = NULL; - } - m_TextCount = src.m_TextCount; - if (m_TextCount) { - m_pTextList = FX_Alloc(CPDF_TextObject*, m_TextCount); - for (int i = 0; i < m_TextCount; i ++) { - if (src.m_pTextList[i]) { - m_pTextList[i] = new CPDF_TextObject; - m_pTextList[i]->Copy(src.m_pTextList[i]); - } else { - m_pTextList[i] = NULL; - } - } - } else { - m_pTextList = NULL; - } -} -void CPDF_ClipPathData::SetCount(int path_count, int text_count) -{ - ASSERT(m_TextCount == 0 && m_PathCount == 0); - if (path_count) { - m_PathCount = path_count; - int alloc_size = (path_count + 7) / 8 * 8; - m_pPathList = new CPDF_Path[alloc_size]; - m_pTypeList = FX_Alloc(uint8_t, alloc_size); - } - if (text_count) { - m_TextCount = text_count; - m_pTextList = FX_Alloc(CPDF_TextObject*, text_count); - } -} -CPDF_Rect CPDF_ClipPath::GetClipBox() const -{ - CPDF_Rect rect; - FX_BOOL bStarted = FALSE; - int count = GetPathCount(); - if (count) { - rect = GetPath(0).GetBoundingBox(); - for (int i = 1; i < count; i ++) { - CPDF_Rect path_rect = GetPath(i).GetBoundingBox(); - rect.Intersect(path_rect); - } - bStarted = TRUE; - } - count = GetTextCount(); - if (count) { - CPDF_Rect layer_rect; - FX_BOOL bLayerStarted = FALSE; - for (int i = 0; i < count; i ++) { - CPDF_TextObject* pTextObj = GetText(i); - if (pTextObj == NULL) { - if (!bStarted) { - rect = layer_rect; - bStarted = TRUE; - } else { - rect.Intersect(layer_rect); - } - bLayerStarted = FALSE; - } else { - if (!bLayerStarted) { - layer_rect = pTextObj->GetBBox(NULL); - bLayerStarted = TRUE; - } else { - layer_rect.Union(pTextObj->GetBBox(NULL)); - } - } - } - } - return rect; -} -void CPDF_ClipPath::AppendPath(CPDF_Path path, int type, FX_BOOL bAutoMerge) -{ - CPDF_ClipPathData* pData = GetModify(); - if (pData->m_PathCount && bAutoMerge) { - CPDF_Path old_path = pData->m_pPathList[pData->m_PathCount - 1]; - if (old_path.IsRect()) { - CPDF_Rect old_rect(old_path.GetPointX(0), old_path.GetPointY(0), - old_path.GetPointX(2), old_path.GetPointY(2)); - CPDF_Rect new_rect = path.GetBoundingBox(); - if (old_rect.Contains(new_rect)) { - pData->m_PathCount --; - pData->m_pPathList[pData->m_PathCount].SetNull(); - } - } - } - if (pData->m_PathCount % 8 == 0) { - CPDF_Path* pNewPath = new CPDF_Path[pData->m_PathCount + 8]; - for (int i = 0; i < pData->m_PathCount; i ++) { - pNewPath[i] = pData->m_pPathList[i]; - } - delete[] pData->m_pPathList; - uint8_t* pNewType = FX_Alloc(uint8_t, pData->m_PathCount + 8); - FXSYS_memcpy(pNewType, pData->m_pTypeList, pData->m_PathCount); - if (pData->m_pTypeList) { - FX_Free(pData->m_pTypeList); - } - pData->m_pPathList = pNewPath; - pData->m_pTypeList = pNewType; - } - pData->m_pPathList[pData->m_PathCount] = path; - pData->m_pTypeList[pData->m_PathCount] = (uint8_t)type; - pData->m_PathCount ++; -} -void CPDF_ClipPath::DeletePath(int index) -{ - CPDF_ClipPathData* pData = GetModify(); - if (index >= pData->m_PathCount) { - return; - } - pData->m_pPathList[index].SetNull(); - for (int i = index; i < pData->m_PathCount - 1; i ++) { - pData->m_pPathList[i] = pData->m_pPathList[i + 1]; - } - pData->m_pPathList[pData->m_PathCount - 1].SetNull(); - FXSYS_memmove(pData->m_pTypeList + index, pData->m_pTypeList + index + 1, pData->m_PathCount - index - 1); - pData->m_PathCount --; + } + } + } + return rect; +} +void CPDF_ClipPath::AppendPath(CPDF_Path path, int type, FX_BOOL bAutoMerge) { + CPDF_ClipPathData* pData = GetModify(); + if (pData->m_PathCount && bAutoMerge) { + CPDF_Path old_path = pData->m_pPathList[pData->m_PathCount - 1]; + if (old_path.IsRect()) { + CPDF_Rect old_rect(old_path.GetPointX(0), old_path.GetPointY(0), + old_path.GetPointX(2), old_path.GetPointY(2)); + CPDF_Rect new_rect = path.GetBoundingBox(); + if (old_rect.Contains(new_rect)) { + pData->m_PathCount--; + pData->m_pPathList[pData->m_PathCount].SetNull(); + } + } + } + if (pData->m_PathCount % 8 == 0) { + CPDF_Path* pNewPath = new CPDF_Path[pData->m_PathCount + 8]; + for (int i = 0; i < pData->m_PathCount; i++) { + pNewPath[i] = pData->m_pPathList[i]; + } + delete[] pData->m_pPathList; + uint8_t* pNewType = FX_Alloc(uint8_t, pData->m_PathCount + 8); + FXSYS_memcpy(pNewType, pData->m_pTypeList, pData->m_PathCount); + if (pData->m_pTypeList) { + FX_Free(pData->m_pTypeList); + } + pData->m_pPathList = pNewPath; + pData->m_pTypeList = pNewType; + } + pData->m_pPathList[pData->m_PathCount] = path; + pData->m_pTypeList[pData->m_PathCount] = (uint8_t)type; + pData->m_PathCount++; +} +void CPDF_ClipPath::DeletePath(int index) { + CPDF_ClipPathData* pData = GetModify(); + if (index >= pData->m_PathCount) { + return; + } + pData->m_pPathList[index].SetNull(); + for (int i = index; i < pData->m_PathCount - 1; i++) { + pData->m_pPathList[i] = pData->m_pPathList[i + 1]; + } + pData->m_pPathList[pData->m_PathCount - 1].SetNull(); + FXSYS_memmove(pData->m_pTypeList + index, pData->m_pTypeList + index + 1, + pData->m_PathCount - index - 1); + pData->m_PathCount--; } #define FPDF_CLIPPATH_MAX_TEXTS 1024 -void CPDF_ClipPath::AppendTexts(CPDF_TextObject** pTexts, int count) -{ - CPDF_ClipPathData* pData = GetModify(); - if (pData->m_TextCount + count > FPDF_CLIPPATH_MAX_TEXTS) { - for (int i = 0; i < count; i ++) { - delete pTexts[i]; +void CPDF_ClipPath::AppendTexts(CPDF_TextObject** pTexts, int count) { + CPDF_ClipPathData* pData = GetModify(); + if (pData->m_TextCount + count > FPDF_CLIPPATH_MAX_TEXTS) { + for (int i = 0; i < count; i++) { + delete pTexts[i]; + } + return; + } + CPDF_TextObject** pNewList = + FX_Alloc(CPDF_TextObject*, pData->m_TextCount + count + 1); + if (pData->m_pTextList) { + FXSYS_memcpy(pNewList, pData->m_pTextList, + pData->m_TextCount * sizeof(CPDF_TextObject*)); + FX_Free(pData->m_pTextList); + } + pData->m_pTextList = pNewList; + for (int i = 0; i < count; i++) { + pData->m_pTextList[pData->m_TextCount + i] = pTexts[i]; + } + pData->m_pTextList[pData->m_TextCount + count] = NULL; + pData->m_TextCount += count + 1; +} +void CPDF_ClipPath::Transform(const CPDF_Matrix& matrix) { + CPDF_ClipPathData* pData = GetModify(); + int i; + for (i = 0; i < pData->m_PathCount; i++) { + pData->m_pPathList[i].Transform(&matrix); + } + for (i = 0; i < pData->m_TextCount; i++) + if (pData->m_pTextList[i]) { + pData->m_pTextList[i]->Transform(matrix); + } +} +CPDF_ColorStateData::CPDF_ColorStateData(const CPDF_ColorStateData& src) { + m_FillColor.Copy(&src.m_FillColor); + m_FillRGB = src.m_FillRGB; + m_StrokeColor.Copy(&src.m_StrokeColor); + m_StrokeRGB = src.m_StrokeRGB; +} +void CPDF_ColorStateData::Default() { + m_FillRGB = m_StrokeRGB = 0; + m_FillColor.SetColorSpace(CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY)); + m_StrokeColor.SetColorSpace(CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY)); +} +void CPDF_ColorState::SetFillColor(CPDF_ColorSpace* pCS, + FX_FLOAT* pValue, + int nValues) { + CPDF_ColorStateData* pData = GetModify(); + SetColor(pData->m_FillColor, pData->m_FillRGB, pCS, pValue, nValues); +} +void CPDF_ColorState::SetStrokeColor(CPDF_ColorSpace* pCS, + FX_FLOAT* pValue, + int nValues) { + CPDF_ColorStateData* pData = GetModify(); + SetColor(pData->m_StrokeColor, pData->m_StrokeRGB, pCS, pValue, nValues); +} +void CPDF_ColorState::SetColor(CPDF_Color& color, + FX_DWORD& rgb, + CPDF_ColorSpace* pCS, + FX_FLOAT* pValue, + int nValues) { + if (pCS) { + color.SetColorSpace(pCS); + } else if (color.IsNull()) { + color.SetColorSpace(CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY)); + } + if (color.m_pCS->CountComponents() > nValues) { + return; + } + color.SetValue(pValue); + int R, G, B; + rgb = color.GetRGB(R, G, B) ? FXSYS_RGB(R, G, B) : (FX_DWORD)-1; +} +void CPDF_ColorState::SetFillPattern(CPDF_Pattern* pPattern, + FX_FLOAT* pValue, + int nValues) { + CPDF_ColorStateData* pData = GetModify(); + pData->m_FillColor.SetValue(pPattern, pValue, nValues); + int R, G, B; + FX_BOOL ret = pData->m_FillColor.GetRGB(R, G, B); + if (pPattern->m_PatternType == 1 && + ((CPDF_TilingPattern*)pPattern)->m_bColored && !ret) { + pData->m_FillRGB = 0x00BFBFBF; + return; + } + pData->m_FillRGB = ret ? FXSYS_RGB(R, G, B) : (FX_DWORD)-1; +} +void CPDF_ColorState::SetStrokePattern(CPDF_Pattern* pPattern, + FX_FLOAT* pValue, + int nValues) { + CPDF_ColorStateData* pData = GetModify(); + pData->m_StrokeColor.SetValue(pPattern, pValue, nValues); + int R, G, B; + FX_BOOL ret = pData->m_StrokeColor.GetRGB(R, G, B); + if (pPattern->m_PatternType == 1 && + ((CPDF_TilingPattern*)pPattern)->m_bColored && !ret) { + pData->m_StrokeRGB = 0x00BFBFBF; + return; + } + pData->m_StrokeRGB = + pData->m_StrokeColor.GetRGB(R, G, B) ? FXSYS_RGB(R, G, B) : (FX_DWORD)-1; +} +CPDF_TextStateData::CPDF_TextStateData() { + m_pFont = NULL; + m_pDocument = NULL; + m_FontSize = 1.0f; + m_WordSpace = 0; + m_CharSpace = 0; + m_TextMode = 0; + m_Matrix[0] = m_Matrix[3] = 1.0f; + m_Matrix[1] = m_Matrix[2] = 0; + m_CTM[0] = m_CTM[3] = 1.0f; + m_CTM[1] = m_CTM[2] = 0; +} +CPDF_TextStateData::CPDF_TextStateData(const CPDF_TextStateData& src) { + if (this == &src) { + return; + } + FXSYS_memcpy(this, &src, sizeof(CPDF_TextStateData)); + if (m_pDocument && m_pFont) { + m_pFont = + m_pDocument->GetPageData()->GetFont(m_pFont->GetFontDict(), FALSE); + } +} +CPDF_TextStateData::~CPDF_TextStateData() { + if (m_pDocument && m_pFont) { + CPDF_DocPageData* pPageData = m_pDocument->GetPageData(); + if (pPageData && !pPageData->IsForceClear()) { + pPageData->ReleaseFont(m_pFont->GetFontDict()); + } + } +} +void CPDF_TextState::SetFont(CPDF_Font* pFont) { + CPDF_TextStateData* pStateData = GetModify(); + if (pStateData) { + CPDF_Document* pDoc = pStateData->m_pDocument; + CPDF_DocPageData* pPageData = pDoc ? pDoc->GetPageData() : NULL; + if (pPageData && pStateData->m_pFont && !pPageData->IsForceClear()) { + pPageData->ReleaseFont(pStateData->m_pFont->GetFontDict()); + } + pStateData->m_pDocument = pFont ? pFont->m_pDocument : NULL; + pStateData->m_pFont = pFont; + } +} +FX_FLOAT CPDF_TextState::GetFontSizeV() const { + FX_FLOAT* pMatrix = GetMatrix(); + FX_FLOAT unit = FXSYS_sqrt2(pMatrix[1], pMatrix[3]); + FX_FLOAT size = FXSYS_Mul(unit, GetFontSize()); + return (FX_FLOAT)FXSYS_fabs(size); +} +FX_FLOAT CPDF_TextState::GetFontSizeH() const { + FX_FLOAT* pMatrix = GetMatrix(); + FX_FLOAT unit = FXSYS_sqrt2(pMatrix[0], pMatrix[2]); + FX_FLOAT size = FXSYS_Mul(unit, GetFontSize()); + return (FX_FLOAT)FXSYS_fabs(size); +} +FX_FLOAT CPDF_TextState::GetBaselineAngle() const { + FX_FLOAT* m_Matrix = GetMatrix(); + return FXSYS_atan2(m_Matrix[2], m_Matrix[0]); +} +FX_FLOAT CPDF_TextState::GetShearAngle() const { + FX_FLOAT* m_Matrix = GetMatrix(); + FX_FLOAT shear_angle = FXSYS_atan2(m_Matrix[1], m_Matrix[3]); + return GetBaselineAngle() + shear_angle; +} +CPDF_GeneralStateData::CPDF_GeneralStateData() { + FXSYS_memset(this, 0, sizeof(CPDF_GeneralStateData)); + FXSYS_strcpy((FX_CHAR*)m_BlendMode, "Normal"); + m_StrokeAlpha = 1.0f; + m_FillAlpha = 1.0f; + m_Flatness = 1.0f; + m_Matrix.SetIdentity(); +} +CPDF_GeneralStateData::CPDF_GeneralStateData(const CPDF_GeneralStateData& src) { + FXSYS_memcpy(this, &src, sizeof(CPDF_GeneralStateData)); + if (src.m_pTransferFunc && src.m_pTransferFunc->m_pPDFDoc) { + CPDF_DocRenderData* pDocCache = + src.m_pTransferFunc->m_pPDFDoc->GetRenderData(); + if (!pDocCache) { + return; + } + m_pTransferFunc = pDocCache->GetTransferFunc(m_pTR); + } +} +CPDF_GeneralStateData::~CPDF_GeneralStateData() { + if (m_pTransferFunc && m_pTransferFunc->m_pPDFDoc) { + CPDF_DocRenderData* pDocCache = m_pTransferFunc->m_pPDFDoc->GetRenderData(); + if (!pDocCache) { + return; + } + pDocCache->ReleaseTransferFunc(m_pTR); + } +} +static int GetBlendType(const CFX_ByteStringC& mode) { + switch (mode.GetID()) { + case FXBSTR_ID('N', 'o', 'r', 'm'): + case FXBSTR_ID('C', 'o', 'm', 'p'): + return FXDIB_BLEND_NORMAL; + case FXBSTR_ID('M', 'u', 'l', 't'): + return FXDIB_BLEND_MULTIPLY; + case FXBSTR_ID('S', 'c', 'r', 'e'): + return FXDIB_BLEND_SCREEN; + case FXBSTR_ID('O', 'v', 'e', 'r'): + return FXDIB_BLEND_OVERLAY; + case FXBSTR_ID('D', 'a', 'r', 'k'): + return FXDIB_BLEND_DARKEN; + case FXBSTR_ID('L', 'i', 'g', 'h'): + return FXDIB_BLEND_LIGHTEN; + case FXBSTR_ID('C', 'o', 'l', 'o'): + if (mode.GetLength() == 10) { + return FXDIB_BLEND_COLORDODGE; + } + if (mode.GetLength() == 9) { + return FXDIB_BLEND_COLORBURN; + } + return FXDIB_BLEND_COLOR; + case FXBSTR_ID('H', 'a', 'r', 'd'): + return FXDIB_BLEND_HARDLIGHT; + case FXBSTR_ID('S', 'o', 'f', 't'): + return FXDIB_BLEND_SOFTLIGHT; + case FXBSTR_ID('D', 'i', 'f', 'f'): + return FXDIB_BLEND_DIFFERENCE; + case FXBSTR_ID('E', 'x', 'c', 'l'): + return FXDIB_BLEND_EXCLUSION; + case FXBSTR_ID('H', 'u', 'e', 0): + return FXDIB_BLEND_HUE; + case FXBSTR_ID('S', 'a', 't', 'u'): + return FXDIB_BLEND_SATURATION; + case FXBSTR_ID('L', 'u', 'm', 'i'): + return FXDIB_BLEND_LUMINOSITY; + } + return FXDIB_BLEND_NORMAL; +} +void CPDF_GeneralStateData::SetBlendMode(const CFX_ByteStringC& blend_mode) { + if (blend_mode.GetLength() > 15) { + return; + } + FXSYS_memcpy(m_BlendMode, blend_mode.GetPtr(), blend_mode.GetLength()); + m_BlendMode[blend_mode.GetLength()] = 0; + m_BlendType = ::GetBlendType(blend_mode); +} +int RI_StringToId(const CFX_ByteString& ri) { + FX_DWORD id = ri.GetID(); + if (id == FXBSTR_ID('A', 'b', 's', 'o')) { + return 1; + } + if (id == FXBSTR_ID('S', 'a', 't', 'u')) { + return 2; + } + if (id == FXBSTR_ID('P', 'e', 'r', 'c')) { + return 3; + } + return 0; +} +void CPDF_GeneralState::SetRenderIntent(const CFX_ByteString& ri) { + GetModify()->m_RenderIntent = RI_StringToId(ri); +} +CPDF_AllStates::CPDF_AllStates() { + m_TextX = m_TextY = m_TextLineX = m_TextLineY = 0; + m_TextLeading = 0; + m_TextRise = 0; + m_TextHorzScale = 1.0f; +} +CPDF_AllStates::~CPDF_AllStates() {} +void CPDF_AllStates::Copy(const CPDF_AllStates& src) { + CopyStates(src); + m_TextMatrix.Copy(src.m_TextMatrix); + m_ParentMatrix.Copy(src.m_ParentMatrix); + m_CTM.Copy(src.m_CTM); + m_TextX = src.m_TextX; + m_TextY = src.m_TextY; + m_TextLineX = src.m_TextLineX; + m_TextLineY = src.m_TextLineY; + m_TextLeading = src.m_TextLeading; + m_TextRise = src.m_TextRise; + m_TextHorzScale = src.m_TextHorzScale; +} +void CPDF_AllStates::SetLineDash(CPDF_Array* pArray, + FX_FLOAT phase, + FX_FLOAT scale) { + CFX_GraphStateData* pData = m_GraphState.GetModify(); + pData->m_DashPhase = FXSYS_Mul(phase, scale); + pData->SetDashCount(pArray->GetCount()); + for (FX_DWORD i = 0; i < pArray->GetCount(); i++) { + pData->m_DashArray[i] = FXSYS_Mul(pArray->GetNumber(i), scale); + } +} +void CPDF_AllStates::ProcessExtGS(CPDF_Dictionary* pGS, + CPDF_StreamContentParser* pParser) { + CPDF_GeneralStateData* pGeneralState = m_GeneralState.GetModify(); + FX_POSITION pos = pGS->GetStartPos(); + while (pos) { + CFX_ByteString key_str; + CPDF_Object* pElement = pGS->GetNextElement(pos, key_str); + CPDF_Object* pObject = pElement ? pElement->GetDirect() : NULL; + if (pObject == NULL) { + continue; + } + FX_DWORD key = key_str.GetID(); + switch (key) { + case FXBSTR_ID('L', 'W', 0, 0): + m_GraphState.GetModify()->m_LineWidth = pObject->GetNumber(); + break; + case FXBSTR_ID('L', 'C', 0, 0): + m_GraphState.GetModify()->m_LineCap = + (CFX_GraphStateData::LineCap)pObject->GetInteger(); + break; + case FXBSTR_ID('L', 'J', 0, 0): + m_GraphState.GetModify()->m_LineJoin = + (CFX_GraphStateData::LineJoin)pObject->GetInteger(); + break; + case FXBSTR_ID('M', 'L', 0, 0): + m_GraphState.GetModify()->m_MiterLimit = pObject->GetNumber(); + break; + case FXBSTR_ID('D', 0, 0, 0): { + if (pObject->GetType() != PDFOBJ_ARRAY) { + break; } - return; - } - CPDF_TextObject** pNewList = FX_Alloc(CPDF_TextObject*, pData->m_TextCount + count + 1); - if (pData->m_pTextList) { - FXSYS_memcpy(pNewList, pData->m_pTextList, pData->m_TextCount * sizeof(CPDF_TextObject*)); - FX_Free(pData->m_pTextList); - } - pData->m_pTextList = pNewList; - for (int i = 0; i < count; i ++) { - pData->m_pTextList[pData->m_TextCount + i] = pTexts[i]; - } - pData->m_pTextList[pData->m_TextCount + count] = NULL; - pData->m_TextCount += count + 1; -} -void CPDF_ClipPath::Transform(const CPDF_Matrix& matrix) -{ - CPDF_ClipPathData* pData = GetModify(); - int i; - for (i = 0; i < pData->m_PathCount; i ++) { - pData->m_pPathList[i].Transform(&matrix); - } - for (i = 0; i < pData->m_TextCount; i ++) - if (pData->m_pTextList[i]) { - pData->m_pTextList[i]->Transform(matrix); + CPDF_Array* pDash = (CPDF_Array*)pObject; + CPDF_Array* pArray = pDash->GetArray(0); + if (pArray == NULL) { + break; } -} -CPDF_ColorStateData::CPDF_ColorStateData(const CPDF_ColorStateData& src) -{ - m_FillColor.Copy(&src.m_FillColor); - m_FillRGB = src.m_FillRGB; - m_StrokeColor.Copy(&src.m_StrokeColor); - m_StrokeRGB = src.m_StrokeRGB; -} -void CPDF_ColorStateData::Default() -{ - m_FillRGB = m_StrokeRGB = 0; - m_FillColor.SetColorSpace(CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY)); - m_StrokeColor.SetColorSpace(CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY)); -} -void CPDF_ColorState::SetFillColor(CPDF_ColorSpace* pCS, FX_FLOAT* pValue, int nValues) -{ - CPDF_ColorStateData* pData = GetModify(); - SetColor(pData->m_FillColor, pData->m_FillRGB, pCS, pValue, nValues); -} -void CPDF_ColorState::SetStrokeColor(CPDF_ColorSpace* pCS, FX_FLOAT* pValue, int nValues) -{ - CPDF_ColorStateData* pData = GetModify(); - SetColor(pData->m_StrokeColor, pData->m_StrokeRGB, pCS, pValue, nValues); -} -void CPDF_ColorState::SetColor(CPDF_Color& color, FX_DWORD& rgb, CPDF_ColorSpace* pCS, FX_FLOAT* pValue, int nValues) -{ - if (pCS) { - color.SetColorSpace(pCS); - } else if (color.IsNull()) { - color.SetColorSpace(CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY)); - } - if (color.m_pCS->CountComponents() > nValues) { - return; - } - color.SetValue(pValue); - int R, G, B; - rgb = color.GetRGB(R, G, B) ? FXSYS_RGB(R, G, B) : (FX_DWORD) - 1; -} -void CPDF_ColorState::SetFillPattern(CPDF_Pattern* pPattern, FX_FLOAT* pValue, int nValues) -{ - CPDF_ColorStateData* pData = GetModify(); - pData->m_FillColor.SetValue(pPattern, pValue, nValues); - int R, G, B; - FX_BOOL ret = pData->m_FillColor.GetRGB(R, G, B); - if (pPattern->m_PatternType == 1 && ((CPDF_TilingPattern*)pPattern)->m_bColored && !ret) { - pData->m_FillRGB = 0x00BFBFBF; - return; - } - pData->m_FillRGB = ret ? FXSYS_RGB(R, G, B) : (FX_DWORD) - 1; -} -void CPDF_ColorState::SetStrokePattern(CPDF_Pattern* pPattern, FX_FLOAT* pValue, int nValues) -{ - CPDF_ColorStateData* pData = GetModify(); - pData->m_StrokeColor.SetValue(pPattern, pValue, nValues); - int R, G, B; - FX_BOOL ret = pData->m_StrokeColor.GetRGB(R, G, B); - if (pPattern->m_PatternType == 1 && ((CPDF_TilingPattern*)pPattern)->m_bColored && !ret) { - pData->m_StrokeRGB = 0x00BFBFBF; - return; - } - pData->m_StrokeRGB = pData->m_StrokeColor.GetRGB(R, G, B) ? FXSYS_RGB(R, G, B) : (FX_DWORD) - 1; -} -CPDF_TextStateData::CPDF_TextStateData() -{ - m_pFont = NULL; - m_pDocument = NULL; - m_FontSize = 1.0f; - m_WordSpace = 0; - m_CharSpace = 0; - m_TextMode = 0; - m_Matrix[0] = m_Matrix[3] = 1.0f; - m_Matrix[1] = m_Matrix[2] = 0; - m_CTM[0] = m_CTM[3] = 1.0f; - m_CTM[1] = m_CTM[2] = 0; -} -CPDF_TextStateData::CPDF_TextStateData(const CPDF_TextStateData& src) -{ - if (this == &src) { - return; - } - FXSYS_memcpy(this, &src, sizeof(CPDF_TextStateData)); - if (m_pDocument && m_pFont) { - m_pFont = m_pDocument->GetPageData()->GetFont(m_pFont->GetFontDict(), FALSE); - } -} -CPDF_TextStateData::~CPDF_TextStateData() -{ - if (m_pDocument && m_pFont) { - CPDF_DocPageData *pPageData = m_pDocument->GetPageData(); - if (pPageData && !pPageData->IsForceClear()) { - pPageData->ReleaseFont(m_pFont->GetFontDict()); + SetLineDash(pArray, pDash->GetNumber(1), 1.0f); + break; + } + case FXBSTR_ID('R', 'I', 0, 0): + m_GeneralState.SetRenderIntent(pObject->GetString()); + break; + case FXBSTR_ID('F', 'o', 'n', 't'): { + if (pObject->GetType() != PDFOBJ_ARRAY) { + break; } - } -} -void CPDF_TextState::SetFont(CPDF_Font* pFont) -{ - CPDF_TextStateData* pStateData = GetModify(); - if (pStateData) { - CPDF_Document* pDoc = pStateData->m_pDocument; - CPDF_DocPageData *pPageData = pDoc ? pDoc->GetPageData() : NULL; - if (pPageData && pStateData->m_pFont && !pPageData->IsForceClear()) { - pPageData->ReleaseFont(pStateData->m_pFont->GetFontDict()); + CPDF_Array* pFont = (CPDF_Array*)pObject; + m_TextState.GetModify()->m_FontSize = pFont->GetNumber(1); + m_TextState.SetFont(pParser->FindFont(pFont->GetString(0))); + break; + } + case FXBSTR_ID('T', 'R', 0, 0): + if (pGS->KeyExist(FX_BSTRC("TR2"))) { + continue; } - pStateData->m_pDocument = pFont ? pFont->m_pDocument : NULL; - pStateData->m_pFont = pFont; - } -} -FX_FLOAT CPDF_TextState::GetFontSizeV() const -{ - FX_FLOAT* pMatrix = GetMatrix(); - FX_FLOAT unit = FXSYS_sqrt2(pMatrix[1], pMatrix[3]); - FX_FLOAT size = FXSYS_Mul(unit, GetFontSize()); - return (FX_FLOAT)FXSYS_fabs(size); -} -FX_FLOAT CPDF_TextState::GetFontSizeH() const -{ - FX_FLOAT* pMatrix = GetMatrix(); - FX_FLOAT unit = FXSYS_sqrt2(pMatrix[0], pMatrix[2]); - FX_FLOAT size = FXSYS_Mul(unit, GetFontSize()); - return (FX_FLOAT)FXSYS_fabs(size); -} -FX_FLOAT CPDF_TextState::GetBaselineAngle() const -{ - FX_FLOAT* m_Matrix = GetMatrix(); - return FXSYS_atan2(m_Matrix[2], m_Matrix[0]); -} -FX_FLOAT CPDF_TextState::GetShearAngle() const -{ - FX_FLOAT* m_Matrix = GetMatrix(); - FX_FLOAT shear_angle = FXSYS_atan2(m_Matrix[1], m_Matrix[3]); - return GetBaselineAngle() + shear_angle; -} -CPDF_GeneralStateData::CPDF_GeneralStateData() -{ - FXSYS_memset(this, 0, sizeof(CPDF_GeneralStateData)); - FXSYS_strcpy((FX_CHAR*)m_BlendMode, "Normal"); - m_StrokeAlpha = 1.0f; - m_FillAlpha = 1.0f; - m_Flatness = 1.0f; - m_Matrix.SetIdentity(); -} -CPDF_GeneralStateData::CPDF_GeneralStateData(const CPDF_GeneralStateData& src) -{ - FXSYS_memcpy(this, &src, sizeof(CPDF_GeneralStateData)); - if (src.m_pTransferFunc && src.m_pTransferFunc->m_pPDFDoc) { - CPDF_DocRenderData* pDocCache = src.m_pTransferFunc->m_pPDFDoc->GetRenderData(); - if (!pDocCache) { - return; + case FXBSTR_ID('T', 'R', '2', 0): + if (pObject && pObject->GetType() != PDFOBJ_NAME) { + pGeneralState->m_pTR = pObject; + } else { + pGeneralState->m_pTR = NULL; } - m_pTransferFunc = pDocCache->GetTransferFunc(m_pTR); - } -} -CPDF_GeneralStateData::~CPDF_GeneralStateData() -{ - if (m_pTransferFunc && m_pTransferFunc->m_pPDFDoc) { - CPDF_DocRenderData* pDocCache = m_pTransferFunc->m_pPDFDoc->GetRenderData(); - if (!pDocCache) { - return; + break; + case FXBSTR_ID('B', 'M', 0, 0): { + CFX_ByteString mode; + if (pObject->GetType() == PDFOBJ_ARRAY) { + mode = ((CPDF_Array*)pObject)->GetString(0); + } else { + mode = pObject->GetString(); } - pDocCache->ReleaseTransferFunc(m_pTR); - } -} -static int GetBlendType(const CFX_ByteStringC& mode) -{ - switch (mode.GetID()) { - case FXBSTR_ID('N', 'o', 'r', 'm'): - case FXBSTR_ID('C', 'o', 'm', 'p'): - return FXDIB_BLEND_NORMAL; - case FXBSTR_ID('M', 'u', 'l', 't'): - return FXDIB_BLEND_MULTIPLY; - case FXBSTR_ID('S', 'c', 'r', 'e'): - return FXDIB_BLEND_SCREEN; - case FXBSTR_ID('O', 'v', 'e', 'r'): - return FXDIB_BLEND_OVERLAY; - case FXBSTR_ID('D', 'a', 'r', 'k'): - return FXDIB_BLEND_DARKEN; - case FXBSTR_ID('L', 'i', 'g', 'h'): - return FXDIB_BLEND_LIGHTEN; - case FXBSTR_ID('C', 'o', 'l', 'o'): - if (mode.GetLength() == 10) { - return FXDIB_BLEND_COLORDODGE; - } - if (mode.GetLength() == 9) { - return FXDIB_BLEND_COLORBURN; - } - return FXDIB_BLEND_COLOR; - case FXBSTR_ID('H', 'a', 'r', 'd'): - return FXDIB_BLEND_HARDLIGHT; - case FXBSTR_ID('S', 'o', 'f', 't'): - return FXDIB_BLEND_SOFTLIGHT; - case FXBSTR_ID('D', 'i', 'f', 'f'): - return FXDIB_BLEND_DIFFERENCE; - case FXBSTR_ID('E', 'x', 'c', 'l'): - return FXDIB_BLEND_EXCLUSION; - case FXBSTR_ID('H', 'u', 'e', 0): - return FXDIB_BLEND_HUE; - case FXBSTR_ID('S', 'a', 't', 'u'): - return FXDIB_BLEND_SATURATION; - case FXBSTR_ID('L', 'u', 'm', 'i'): - return FXDIB_BLEND_LUMINOSITY; - } - return FXDIB_BLEND_NORMAL; -} -void CPDF_GeneralStateData::SetBlendMode(const CFX_ByteStringC& blend_mode) -{ - if (blend_mode.GetLength() > 15) { - return; - } - FXSYS_memcpy(m_BlendMode, blend_mode.GetPtr(), blend_mode.GetLength()); - m_BlendMode[blend_mode.GetLength()] = 0; - m_BlendType = ::GetBlendType(blend_mode); -} -int RI_StringToId(const CFX_ByteString& ri) -{ - FX_DWORD id = ri.GetID(); - if (id == FXBSTR_ID('A', 'b', 's', 'o')) { - return 1; - } - if (id == FXBSTR_ID('S', 'a', 't', 'u')) { - return 2; - } - if (id == FXBSTR_ID('P', 'e', 'r', 'c')) { - return 3; - } - return 0; -} -void CPDF_GeneralState::SetRenderIntent(const CFX_ByteString& ri) -{ - GetModify()->m_RenderIntent = RI_StringToId(ri); -} -CPDF_AllStates::CPDF_AllStates() -{ - m_TextX = m_TextY = m_TextLineX = m_TextLineY = 0; - m_TextLeading = 0; - m_TextRise = 0; - m_TextHorzScale = 1.0f; -} -CPDF_AllStates::~CPDF_AllStates() -{ -} -void CPDF_AllStates::Copy(const CPDF_AllStates& src) -{ - CopyStates(src); - m_TextMatrix.Copy(src.m_TextMatrix); - m_ParentMatrix.Copy(src.m_ParentMatrix); - m_CTM.Copy(src.m_CTM); - m_TextX = src.m_TextX; - m_TextY = src.m_TextY; - m_TextLineX = src.m_TextLineX; - m_TextLineY = src.m_TextLineY; - m_TextLeading = src.m_TextLeading; - m_TextRise = src.m_TextRise; - m_TextHorzScale = src.m_TextHorzScale; -} -void CPDF_AllStates::SetLineDash(CPDF_Array* pArray, FX_FLOAT phase, FX_FLOAT scale) -{ - CFX_GraphStateData* pData = m_GraphState.GetModify(); - pData->m_DashPhase = FXSYS_Mul(phase, scale); - pData->SetDashCount(pArray->GetCount()); - for (FX_DWORD i = 0; i < pArray->GetCount(); i ++) { - pData->m_DashArray[i] = FXSYS_Mul(pArray->GetNumber(i), scale); - } -} -void CPDF_AllStates::ProcessExtGS(CPDF_Dictionary* pGS, CPDF_StreamContentParser* pParser) -{ - CPDF_GeneralStateData* pGeneralState = m_GeneralState.GetModify(); - FX_POSITION pos = pGS->GetStartPos(); - while (pos) { - CFX_ByteString key_str; - CPDF_Object* pElement = pGS->GetNextElement(pos, key_str); - CPDF_Object* pObject = pElement ? pElement->GetDirect() : NULL; - if (pObject == NULL) { - continue; + pGeneralState->SetBlendMode(mode); + if (pGeneralState->m_BlendType > FXDIB_BLEND_MULTIPLY) { + pParser->GetObjectList()->m_bBackgroundAlphaNeeded = TRUE; } - FX_DWORD key = key_str.GetID(); - switch (key) { - case FXBSTR_ID('L', 'W', 0, 0): - m_GraphState.GetModify()->m_LineWidth = pObject->GetNumber(); - break; - case FXBSTR_ID('L', 'C', 0, 0): - m_GraphState.GetModify()->m_LineCap = (CFX_GraphStateData::LineCap)pObject->GetInteger(); - break; - case FXBSTR_ID('L', 'J', 0, 0): - m_GraphState.GetModify()->m_LineJoin = (CFX_GraphStateData::LineJoin)pObject->GetInteger(); - break; - case FXBSTR_ID('M', 'L', 0, 0): - m_GraphState.GetModify()->m_MiterLimit = pObject->GetNumber(); - break; - case FXBSTR_ID('D', 0, 0, 0): { - if (pObject->GetType() != PDFOBJ_ARRAY) { - break; - } - CPDF_Array* pDash = (CPDF_Array*)pObject; - CPDF_Array* pArray = pDash->GetArray(0); - if (pArray == NULL) { - break; - } - SetLineDash(pArray, pDash->GetNumber(1), 1.0f); - break; - } - case FXBSTR_ID('R', 'I', 0, 0): - m_GeneralState.SetRenderIntent(pObject->GetString()); - break; - case FXBSTR_ID('F', 'o', 'n', 't'): { - if (pObject->GetType() != PDFOBJ_ARRAY) { - break; - } - CPDF_Array* pFont = (CPDF_Array*)pObject; - m_TextState.GetModify()->m_FontSize = pFont->GetNumber(1); - m_TextState.SetFont(pParser->FindFont(pFont->GetString(0))); - break; - } - case FXBSTR_ID('T', 'R', 0, 0): - if (pGS->KeyExist(FX_BSTRC("TR2"))) { - continue; - } - case FXBSTR_ID('T', 'R', '2', 0): - if (pObject && pObject->GetType() != PDFOBJ_NAME) { - pGeneralState->m_pTR = pObject; - } else { - pGeneralState->m_pTR = NULL; - } - break; - case FXBSTR_ID('B', 'M', 0, 0): { - CFX_ByteString mode; - if (pObject->GetType() == PDFOBJ_ARRAY) { - mode = ((CPDF_Array*)pObject)->GetString(0); - } else { - mode = pObject->GetString(); - } - pGeneralState->SetBlendMode(mode); - if (pGeneralState->m_BlendType > FXDIB_BLEND_MULTIPLY) { - pParser->GetObjectList()->m_bBackgroundAlphaNeeded = TRUE; - } - break; - } - case FXBSTR_ID('S', 'M', 'a', 's'): - if (pObject && pObject->GetType() == PDFOBJ_DICTIONARY) { - pGeneralState->m_pSoftMask = pObject; - FXSYS_memcpy(pGeneralState->m_SMaskMatrix, &pParser->GetCurStates()->m_CTM, sizeof(CPDF_Matrix)); - } else { - pGeneralState->m_pSoftMask = NULL; - } - break; - case FXBSTR_ID('C', 'A', 0, 0): - pGeneralState->m_StrokeAlpha = PDF_ClipFloat(pObject->GetNumber()); - break; - case FXBSTR_ID('c', 'a', 0, 0): - pGeneralState->m_FillAlpha = PDF_ClipFloat(pObject->GetNumber()); - break; - case FXBSTR_ID('O', 'P', 0, 0): - pGeneralState->m_StrokeOP = pObject->GetInteger(); - if (!pGS->KeyExist(FX_BSTRC("op"))) { - pGeneralState->m_FillOP = pObject->GetInteger(); - } - break; - case FXBSTR_ID('o', 'p', 0, 0): - pGeneralState->m_FillOP = pObject->GetInteger(); - break; - case FXBSTR_ID('O', 'P', 'M', 0): - pGeneralState->m_OPMode = pObject->GetInteger(); - break; - case FXBSTR_ID('B', 'G', 0, 0): - if (pGS->KeyExist(FX_BSTRC("BG2"))) { - continue; - } - case FXBSTR_ID('B', 'G', '2', 0): - pGeneralState->m_pBG = pObject; - break; - case FXBSTR_ID('U', 'C', 'R', 0): - if (pGS->KeyExist(FX_BSTRC("UCR2"))) { - continue; - } - case FXBSTR_ID('U', 'C', 'R', '2'): - pGeneralState->m_pUCR = pObject; - break; - case FXBSTR_ID('H', 'T', 0, 0): - pGeneralState->m_pHT = pObject; - break; - case FXBSTR_ID('F', 'L', 0, 0): - pGeneralState->m_Flatness = pObject->GetNumber(); - break; - case FXBSTR_ID('S', 'M', 0, 0): - pGeneralState->m_Smoothness = pObject->GetNumber(); - break; - case FXBSTR_ID('S', 'A', 0, 0): - pGeneralState->m_StrokeAdjust = pObject->GetInteger(); - break; - case FXBSTR_ID('A', 'I', 'S', 0): - pGeneralState->m_AlphaSource = pObject->GetInteger(); - break; - case FXBSTR_ID('T', 'K', 0, 0): - pGeneralState->m_TextKnockout = pObject->GetInteger(); - break; + break; + } + case FXBSTR_ID('S', 'M', 'a', 's'): + if (pObject && pObject->GetType() == PDFOBJ_DICTIONARY) { + pGeneralState->m_pSoftMask = pObject; + FXSYS_memcpy(pGeneralState->m_SMaskMatrix, + &pParser->GetCurStates()->m_CTM, sizeof(CPDF_Matrix)); + } else { + pGeneralState->m_pSoftMask = NULL; } - } - pGeneralState->m_Matrix = m_CTM; -} -CPDF_ContentMarkItem::CPDF_ContentMarkItem() -{ - m_ParamType = None; -} -CPDF_ContentMarkItem::CPDF_ContentMarkItem(const CPDF_ContentMarkItem& src) -{ - m_MarkName = src.m_MarkName; - m_ParamType = src.m_ParamType; - if (m_ParamType == DirectDict) { - m_pParam = ((CPDF_Dictionary*)src.m_pParam)->Clone(); - } else { - m_pParam = src.m_pParam; - } -} -CPDF_ContentMarkItem::~CPDF_ContentMarkItem() -{ - if (m_ParamType == DirectDict && m_pParam) { - ((CPDF_Dictionary*)m_pParam)->Release(); - } -} -FX_BOOL CPDF_ContentMarkItem::HasMCID() const -{ - if (m_pParam && (m_ParamType == DirectDict || m_ParamType == PropertiesDict)) { - return ((CPDF_Dictionary *)m_pParam)->KeyExist(FX_BSTRC("MCID")); - } - return FALSE; -} -CPDF_ContentMarkData::CPDF_ContentMarkData(const CPDF_ContentMarkData& src) -{ - for (int i = 0; i < src.m_Marks.GetSize(); i ++) { - m_Marks.Add(src.m_Marks[i]); - } -} -int CPDF_ContentMarkData::GetMCID() const -{ - CPDF_ContentMarkItem::ParamType type = CPDF_ContentMarkItem::None; - for (int i = 0; i < m_Marks.GetSize(); i ++) { - type = m_Marks[i].GetParamType(); - if (type == CPDF_ContentMarkItem::PropertiesDict || type == CPDF_ContentMarkItem::DirectDict) { - CPDF_Dictionary *pDict = (CPDF_Dictionary *)m_Marks[i].GetParam(); - if (pDict->KeyExist(FX_BSTRC("MCID"))) { - return pDict->GetInteger(FX_BSTRC("MCID")); - } + break; + case FXBSTR_ID('C', 'A', 0, 0): + pGeneralState->m_StrokeAlpha = PDF_ClipFloat(pObject->GetNumber()); + break; + case FXBSTR_ID('c', 'a', 0, 0): + pGeneralState->m_FillAlpha = PDF_ClipFloat(pObject->GetNumber()); + break; + case FXBSTR_ID('O', 'P', 0, 0): + pGeneralState->m_StrokeOP = pObject->GetInteger(); + if (!pGS->KeyExist(FX_BSTRC("op"))) { + pGeneralState->m_FillOP = pObject->GetInteger(); } - } - return -1; -} -void CPDF_ContentMarkData::AddMark(const CFX_ByteString& name, CPDF_Dictionary* pDict, FX_BOOL bDirect) -{ - CPDF_ContentMarkItem& item = m_Marks.Add(); - item.SetName(name); - if (pDict == NULL) { - return; - } - item.SetParam(bDirect ? CPDF_ContentMarkItem::DirectDict : CPDF_ContentMarkItem::PropertiesDict, - bDirect ? pDict->Clone() : pDict); -} -void CPDF_ContentMarkData::DeleteLastMark() -{ - int size = m_Marks.GetSize(); - if (size == 0) { - return; - } - m_Marks.RemoveAt(size - 1); -} -FX_BOOL CPDF_ContentMark::HasMark(const CFX_ByteStringC& mark) const -{ - if (m_pObject == NULL) { - return FALSE; - } - for (int i = 0; i < m_pObject->CountItems(); i ++) { - CPDF_ContentMarkItem& item = m_pObject->GetItem(i); - if (item.GetName() == mark) { - return TRUE; + break; + case FXBSTR_ID('o', 'p', 0, 0): + pGeneralState->m_FillOP = pObject->GetInteger(); + break; + case FXBSTR_ID('O', 'P', 'M', 0): + pGeneralState->m_OPMode = pObject->GetInteger(); + break; + case FXBSTR_ID('B', 'G', 0, 0): + if (pGS->KeyExist(FX_BSTRC("BG2"))) { + continue; } - } - return FALSE; -} -FX_BOOL CPDF_ContentMark::LookupMark(const CFX_ByteStringC& mark, CPDF_Dictionary*& pDict) const -{ - if (m_pObject == NULL) { - return FALSE; - } - for (int i = 0; i < m_pObject->CountItems(); i ++) { - CPDF_ContentMarkItem& item = m_pObject->GetItem(i); - if (item.GetName() == mark) { - pDict = NULL; - if (item.GetParamType() == CPDF_ContentMarkItem::PropertiesDict || - item.GetParamType() == CPDF_ContentMarkItem::DirectDict) { - pDict = (CPDF_Dictionary*)item.GetParam(); - } - return TRUE; + case FXBSTR_ID('B', 'G', '2', 0): + pGeneralState->m_pBG = pObject; + break; + case FXBSTR_ID('U', 'C', 'R', 0): + if (pGS->KeyExist(FX_BSTRC("UCR2"))) { + continue; } - } + case FXBSTR_ID('U', 'C', 'R', '2'): + pGeneralState->m_pUCR = pObject; + break; + case FXBSTR_ID('H', 'T', 0, 0): + pGeneralState->m_pHT = pObject; + break; + case FXBSTR_ID('F', 'L', 0, 0): + pGeneralState->m_Flatness = pObject->GetNumber(); + break; + case FXBSTR_ID('S', 'M', 0, 0): + pGeneralState->m_Smoothness = pObject->GetNumber(); + break; + case FXBSTR_ID('S', 'A', 0, 0): + pGeneralState->m_StrokeAdjust = pObject->GetInteger(); + break; + case FXBSTR_ID('A', 'I', 'S', 0): + pGeneralState->m_AlphaSource = pObject->GetInteger(); + break; + case FXBSTR_ID('T', 'K', 0, 0): + pGeneralState->m_TextKnockout = pObject->GetInteger(); + break; + } + } + pGeneralState->m_Matrix = m_CTM; +} +CPDF_ContentMarkItem::CPDF_ContentMarkItem() { + m_ParamType = None; +} +CPDF_ContentMarkItem::CPDF_ContentMarkItem(const CPDF_ContentMarkItem& src) { + m_MarkName = src.m_MarkName; + m_ParamType = src.m_ParamType; + if (m_ParamType == DirectDict) { + m_pParam = ((CPDF_Dictionary*)src.m_pParam)->Clone(); + } else { + m_pParam = src.m_pParam; + } +} +CPDF_ContentMarkItem::~CPDF_ContentMarkItem() { + if (m_ParamType == DirectDict && m_pParam) { + ((CPDF_Dictionary*)m_pParam)->Release(); + } +} +FX_BOOL CPDF_ContentMarkItem::HasMCID() const { + if (m_pParam && + (m_ParamType == DirectDict || m_ParamType == PropertiesDict)) { + return ((CPDF_Dictionary*)m_pParam)->KeyExist(FX_BSTRC("MCID")); + } + return FALSE; +} +CPDF_ContentMarkData::CPDF_ContentMarkData(const CPDF_ContentMarkData& src) { + for (int i = 0; i < src.m_Marks.GetSize(); i++) { + m_Marks.Add(src.m_Marks[i]); + } +} +int CPDF_ContentMarkData::GetMCID() const { + CPDF_ContentMarkItem::ParamType type = CPDF_ContentMarkItem::None; + for (int i = 0; i < m_Marks.GetSize(); i++) { + type = m_Marks[i].GetParamType(); + if (type == CPDF_ContentMarkItem::PropertiesDict || + type == CPDF_ContentMarkItem::DirectDict) { + CPDF_Dictionary* pDict = (CPDF_Dictionary*)m_Marks[i].GetParam(); + if (pDict->KeyExist(FX_BSTRC("MCID"))) { + return pDict->GetInteger(FX_BSTRC("MCID")); + } + } + } + return -1; +} +void CPDF_ContentMarkData::AddMark(const CFX_ByteString& name, + CPDF_Dictionary* pDict, + FX_BOOL bDirect) { + CPDF_ContentMarkItem& item = m_Marks.Add(); + item.SetName(name); + if (pDict == NULL) { + return; + } + item.SetParam(bDirect ? CPDF_ContentMarkItem::DirectDict + : CPDF_ContentMarkItem::PropertiesDict, + bDirect ? pDict->Clone() : pDict); +} +void CPDF_ContentMarkData::DeleteLastMark() { + int size = m_Marks.GetSize(); + if (size == 0) { + return; + } + m_Marks.RemoveAt(size - 1); +} +FX_BOOL CPDF_ContentMark::HasMark(const CFX_ByteStringC& mark) const { + if (m_pObject == NULL) { + return FALSE; + } + for (int i = 0; i < m_pObject->CountItems(); i++) { + CPDF_ContentMarkItem& item = m_pObject->GetItem(i); + if (item.GetName() == mark) { + return TRUE; + } + } + return FALSE; +} +FX_BOOL CPDF_ContentMark::LookupMark(const CFX_ByteStringC& mark, + CPDF_Dictionary*& pDict) const { + if (m_pObject == NULL) { return FALSE; + } + for (int i = 0; i < m_pObject->CountItems(); i++) { + CPDF_ContentMarkItem& item = m_pObject->GetItem(i); + if (item.GetName() == mark) { + pDict = NULL; + if (item.GetParamType() == CPDF_ContentMarkItem::PropertiesDict || + item.GetParamType() == CPDF_ContentMarkItem::DirectDict) { + pDict = (CPDF_Dictionary*)item.GetParam(); + } + return TRUE; + } + } + return FALSE; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_image.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_image.cpp index aabfd141d6..e9f70c14db 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_image.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_image.cpp @@ -7,99 +7,92 @@ #include "../../../include/fpdfapi/fpdf_page.h" #include "../../../include/fpdfapi/fpdf_pageobj.h" #include "pageint.h" -CPDF_ImageObject::CPDF_ImageObject() -{ - m_pImage = NULL; - m_Type = PDFPAGE_IMAGE; +CPDF_ImageObject::CPDF_ImageObject() { + m_pImage = NULL; + m_Type = PDFPAGE_IMAGE; } -CPDF_ImageObject::~CPDF_ImageObject() -{ - if (!m_pImage) { - return; - } - if (m_pImage->IsInline() || (m_pImage->GetStream() && m_pImage->GetStream()->GetObjNum() == 0)) { - delete m_pImage; - } else { - m_pImage->GetDocument()->GetPageData()->ReleaseImage(m_pImage->GetStream()); - } +CPDF_ImageObject::~CPDF_ImageObject() { + if (!m_pImage) { + return; + } + if (m_pImage->IsInline() || + (m_pImage->GetStream() && m_pImage->GetStream()->GetObjNum() == 0)) { + delete m_pImage; + } else { + m_pImage->GetDocument()->GetPageData()->ReleaseImage(m_pImage->GetStream()); + } } -void CPDF_ImageObject::CopyData(const CPDF_PageObject* pSrc) -{ - const CPDF_ImageObject* pSrcObj = (const CPDF_ImageObject*)pSrc; - if (m_pImage) { - m_pImage->Release(); - } - m_pImage = pSrcObj->m_pImage->Clone(); - m_Matrix = pSrcObj->m_Matrix; +void CPDF_ImageObject::CopyData(const CPDF_PageObject* pSrc) { + const CPDF_ImageObject* pSrcObj = (const CPDF_ImageObject*)pSrc; + if (m_pImage) { + m_pImage->Release(); + } + m_pImage = pSrcObj->m_pImage->Clone(); + m_Matrix = pSrcObj->m_Matrix; } -void CPDF_ImageObject::Transform(const CFX_AffineMatrix& matrix) -{ - m_Matrix.Concat(matrix); - CalcBoundingBox(); +void CPDF_ImageObject::Transform(const CFX_AffineMatrix& matrix) { + m_Matrix.Concat(matrix); + CalcBoundingBox(); } -void CPDF_ImageObject::CalcBoundingBox() -{ - m_Left = m_Bottom = 0; - m_Right = m_Top = 1.0f; - m_Matrix.TransformRect(m_Left, m_Right, m_Top, m_Bottom); +void CPDF_ImageObject::CalcBoundingBox() { + m_Left = m_Bottom = 0; + m_Right = m_Top = 1.0f; + m_Matrix.TransformRect(m_Left, m_Right, m_Top, m_Bottom); } -void CPDF_Image::Release() -{ - if (m_bInline || (m_pStream && m_pStream->GetObjNum() == 0)) { - delete this; - } +void CPDF_Image::Release() { + if (m_bInline || (m_pStream && m_pStream->GetObjNum() == 0)) { + delete this; + } } -CPDF_Image* CPDF_Image::Clone() -{ - if (m_pStream->GetObjNum()) { - return m_pDocument->GetPageData()->GetImage(m_pStream); - } - CPDF_Image* pImage = new CPDF_Image(m_pDocument); - pImage->LoadImageF((CPDF_Stream*)((CPDF_Object*)m_pStream)->Clone(), m_bInline); - if (m_bInline) { - CPDF_Dictionary *pInlineDict = (CPDF_Dictionary*)m_pInlineDict->Clone(TRUE); - pImage->SetInlineDict(pInlineDict); - } - return pImage; +CPDF_Image* CPDF_Image::Clone() { + if (m_pStream->GetObjNum()) { + return m_pDocument->GetPageData()->GetImage(m_pStream); + } + CPDF_Image* pImage = new CPDF_Image(m_pDocument); + pImage->LoadImageF((CPDF_Stream*)((CPDF_Object*)m_pStream)->Clone(), + m_bInline); + if (m_bInline) { + CPDF_Dictionary* pInlineDict = (CPDF_Dictionary*)m_pInlineDict->Clone(TRUE); + pImage->SetInlineDict(pInlineDict); + } + return pImage; } -CPDF_Image::CPDF_Image(CPDF_Document* pDoc) -{ - m_pDocument = pDoc; - m_pStream = NULL; - m_pOC = NULL; - m_bInline = FALSE; - m_pInlineDict = NULL; - m_pDIBSource = NULL; - m_pMask = NULL; - m_MatteColor = 0; -} -CPDF_Image::~CPDF_Image() -{ - if (m_bInline) { - if (m_pStream) { - m_pStream->Release(); - } - if (m_pInlineDict) { - m_pInlineDict->Release(); - } - } +CPDF_Image::CPDF_Image(CPDF_Document* pDoc) { + m_pDocument = pDoc; + m_pStream = NULL; + m_pOC = NULL; + m_bInline = FALSE; + m_pInlineDict = NULL; + m_pDIBSource = NULL; + m_pMask = NULL; + m_MatteColor = 0; } -FX_BOOL CPDF_Image::LoadImageF(CPDF_Stream* pStream, FX_BOOL bInline) -{ - m_pStream = pStream; - if (m_bInline && m_pInlineDict) { - m_pInlineDict->Release(); - m_pInlineDict = NULL; +CPDF_Image::~CPDF_Image() { + if (m_bInline) { + if (m_pStream) { + m_pStream->Release(); } - m_bInline = bInline; - CPDF_Dictionary* pDict = pStream->GetDict(); - if (m_bInline) { - m_pInlineDict = (CPDF_Dictionary*)pDict->Clone(); + if (m_pInlineDict) { + m_pInlineDict->Release(); } - m_pOC = pDict->GetDict(FX_BSTRC("OC")); - m_bIsMask = !pDict->KeyExist(FX_BSTRC("ColorSpace")) || pDict->GetInteger(FX_BSTRC("ImageMask")); - m_bInterpolate = pDict->GetInteger(FX_BSTRC("Interpolate")); - m_Height = pDict->GetInteger(FX_BSTRC("Height")); - m_Width = pDict->GetInteger(FX_BSTRC("Width")); - return TRUE; + } +} +FX_BOOL CPDF_Image::LoadImageF(CPDF_Stream* pStream, FX_BOOL bInline) { + m_pStream = pStream; + if (m_bInline && m_pInlineDict) { + m_pInlineDict->Release(); + m_pInlineDict = NULL; + } + m_bInline = bInline; + CPDF_Dictionary* pDict = pStream->GetDict(); + if (m_bInline) { + m_pInlineDict = (CPDF_Dictionary*)pDict->Clone(); + } + m_pOC = pDict->GetDict(FX_BSTRC("OC")); + m_bIsMask = !pDict->KeyExist(FX_BSTRC("ColorSpace")) || + pDict->GetInteger(FX_BSTRC("ImageMask")); + m_bInterpolate = pDict->GetInteger(FX_BSTRC("Interpolate")); + m_Height = pDict->GetInteger(FX_BSTRC("Height")); + m_Width = pDict->GetInteger(FX_BSTRC("Width")); + return TRUE; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_parser.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_parser.cpp index 892e2153b7..47ba46a0f3 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_parser.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_parser.cpp @@ -9,7 +9,11 @@ #include "../../../include/fpdfapi/fpdf_serial.h" #include "pageint.h" -#define REQUIRE_PARAMS(count) if (m_ParamCount != count) { m_bAbort = TRUE; return; } +#define REQUIRE_PARAMS(count) \ + if (m_ParamCount != count) { \ + m_bAbort = TRUE; \ + return; \ + } CPDF_StreamContentParser::CPDF_StreamContentParser( CPDF_Document* pDocument, @@ -45,1539 +49,1556 @@ CPDF_StreamContentParser::CPDF_StreamContentParser( m_pLastCloneImageDict(nullptr), m_bReleaseLastDict(TRUE), m_bColored(FALSE), - m_bResourceMissing(FALSE) -{ - if (pmtContentToUser) { - m_mtContentToUser = *pmtContentToUser; - } - if (pOptions) { - m_Options = *pOptions; - } - if (!m_pResources) { - m_pResources = m_pParentResources; - } - if (!m_pResources) { - m_pResources = m_pPageResources; - } - if (pBBox) { - m_BBox = *pBBox; - } - if (pStates) { - m_pCurStates->Copy(*pStates); - } else { - m_pCurStates->m_GeneralState.New(); - m_pCurStates->m_GraphState.New(); - m_pCurStates->m_TextState.New(); - m_pCurStates->m_ColorState.New(); - } - for (int i = 0; i < FX_ArraySize(m_Type3Data); ++i) { - m_Type3Data[i] = 0.0; - } + m_bResourceMissing(FALSE) { + if (pmtContentToUser) { + m_mtContentToUser = *pmtContentToUser; + } + if (pOptions) { + m_Options = *pOptions; + } + if (!m_pResources) { + m_pResources = m_pParentResources; + } + if (!m_pResources) { + m_pResources = m_pPageResources; + } + if (pBBox) { + m_BBox = *pBBox; + } + if (pStates) { + m_pCurStates->Copy(*pStates); + } else { + m_pCurStates->m_GeneralState.New(); + m_pCurStates->m_GraphState.New(); + m_pCurStates->m_TextState.New(); + m_pCurStates->m_ColorState.New(); + } + for (int i = 0; i < FX_ArraySize(m_Type3Data); ++i) { + m_Type3Data[i] = 0.0; + } } -CPDF_StreamContentParser::~CPDF_StreamContentParser() -{ - ClearAllParams(); - for (int i = 0; i < m_StateStack.GetSize(); ++i) { - delete (CPDF_AllStates*)m_StateStack[i]; - } - if (m_pPathPoints) { - FX_Free(m_pPathPoints); - } - if (m_pLastImageDict) { - m_pLastImageDict->Release(); - } - if (m_pLastCloneImageDict) { - m_pLastCloneImageDict->Release(); - } -} -int CPDF_StreamContentParser::GetNextParamPos() -{ - if (m_ParamCount == PARAM_BUF_SIZE) { - m_ParamStartPos ++; - if (m_ParamStartPos == PARAM_BUF_SIZE) { - m_ParamStartPos = 0; - } - if (m_ParamBuf1[m_ParamStartPos].m_Type == 0) { - if (CPDF_Object* pObject = m_ParamBuf1[m_ParamStartPos].m_pObject) - pObject->Release(); - } - return m_ParamStartPos; - } - int index = m_ParamStartPos + m_ParamCount; - if (index >= PARAM_BUF_SIZE) { - index -= PARAM_BUF_SIZE; - } - m_ParamCount ++; - return index; -} -void CPDF_StreamContentParser::AddNameParam(const FX_CHAR* name, int len) -{ - int index = GetNextParamPos(); - if (len > 32) { - m_ParamBuf1[index].m_Type = 0; - m_ParamBuf1[index].m_pObject = CPDF_Name::Create(PDF_NameDecode(CFX_ByteStringC(name, len))); - } else { - m_ParamBuf1[index].m_Type = PDFOBJ_NAME; - if (FXSYS_memchr(name, '#', len) == NULL) { - FXSYS_memcpy(m_ParamBuf1[index].m_Name.m_Buffer, name, len); - m_ParamBuf1[index].m_Name.m_Len = len; - } else { - CFX_ByteString str = PDF_NameDecode(CFX_ByteStringC(name, len)); - FXSYS_memcpy(m_ParamBuf1[index].m_Name.m_Buffer, str.c_str(), str.GetLength()); - m_ParamBuf1[index].m_Name.m_Len = str.GetLength(); - } - } -} -void CPDF_StreamContentParser::AddNumberParam(const FX_CHAR* str, int len) -{ - int index = GetNextParamPos(); - m_ParamBuf1[index].m_Type = PDFOBJ_NUMBER; - FX_atonum(CFX_ByteStringC(str, len), m_ParamBuf1[index].m_Number.m_bInteger, - &m_ParamBuf1[index].m_Number.m_Integer); -} -void CPDF_StreamContentParser::AddObjectParam(CPDF_Object* pObj) -{ - int index = GetNextParamPos(); +CPDF_StreamContentParser::~CPDF_StreamContentParser() { + ClearAllParams(); + for (int i = 0; i < m_StateStack.GetSize(); ++i) { + delete (CPDF_AllStates*)m_StateStack[i]; + } + if (m_pPathPoints) { + FX_Free(m_pPathPoints); + } + if (m_pLastImageDict) { + m_pLastImageDict->Release(); + } + if (m_pLastCloneImageDict) { + m_pLastCloneImageDict->Release(); + } +} +int CPDF_StreamContentParser::GetNextParamPos() { + if (m_ParamCount == PARAM_BUF_SIZE) { + m_ParamStartPos++; + if (m_ParamStartPos == PARAM_BUF_SIZE) { + m_ParamStartPos = 0; + } + if (m_ParamBuf1[m_ParamStartPos].m_Type == 0) { + if (CPDF_Object* pObject = m_ParamBuf1[m_ParamStartPos].m_pObject) + pObject->Release(); + } + return m_ParamStartPos; + } + int index = m_ParamStartPos + m_ParamCount; + if (index >= PARAM_BUF_SIZE) { + index -= PARAM_BUF_SIZE; + } + m_ParamCount++; + return index; +} +void CPDF_StreamContentParser::AddNameParam(const FX_CHAR* name, int len) { + int index = GetNextParamPos(); + if (len > 32) { m_ParamBuf1[index].m_Type = 0; - m_ParamBuf1[index].m_pObject = pObj; -} -void CPDF_StreamContentParser::ClearAllParams() -{ - FX_DWORD index = m_ParamStartPos; - for (FX_DWORD i = 0; i < m_ParamCount; i ++) { - if (m_ParamBuf1[index].m_Type == 0) { - if (CPDF_Object* pObject = m_ParamBuf1[index].m_pObject) - pObject->Release(); - } - index ++; - if (index == PARAM_BUF_SIZE) { - index = 0; - } - } - m_ParamStartPos = 0; - m_ParamCount = 0; -} -CPDF_Object* CPDF_StreamContentParser::GetObject(FX_DWORD index) -{ - if (index >= m_ParamCount) { - return NULL; - } - int real_index = m_ParamStartPos + m_ParamCount - index - 1; - if (real_index >= PARAM_BUF_SIZE) { - real_index -= PARAM_BUF_SIZE; - } - _ContentParam& param = m_ParamBuf1[real_index]; - if (param.m_Type == PDFOBJ_NUMBER) { - CPDF_Number* pNumber = CPDF_Number::Create(param.m_Number.m_bInteger, ¶m.m_Number.m_Integer); - param.m_Type = 0; - param.m_pObject = pNumber; - return pNumber; - } - if (param.m_Type == PDFOBJ_NAME) { - CPDF_Name* pName = CPDF_Name::Create(CFX_ByteString(param.m_Name.m_Buffer, param.m_Name.m_Len)); - param.m_Type = 0; - param.m_pObject = pName; - return pName; - } - if (param.m_Type == 0) { - return param.m_pObject; - } - ASSERT(FALSE); + m_ParamBuf1[index].m_pObject = + CPDF_Name::Create(PDF_NameDecode(CFX_ByteStringC(name, len))); + } else { + m_ParamBuf1[index].m_Type = PDFOBJ_NAME; + if (FXSYS_memchr(name, '#', len) == NULL) { + FXSYS_memcpy(m_ParamBuf1[index].m_Name.m_Buffer, name, len); + m_ParamBuf1[index].m_Name.m_Len = len; + } else { + CFX_ByteString str = PDF_NameDecode(CFX_ByteStringC(name, len)); + FXSYS_memcpy(m_ParamBuf1[index].m_Name.m_Buffer, str.c_str(), + str.GetLength()); + m_ParamBuf1[index].m_Name.m_Len = str.GetLength(); + } + } +} +void CPDF_StreamContentParser::AddNumberParam(const FX_CHAR* str, int len) { + int index = GetNextParamPos(); + m_ParamBuf1[index].m_Type = PDFOBJ_NUMBER; + FX_atonum(CFX_ByteStringC(str, len), m_ParamBuf1[index].m_Number.m_bInteger, + &m_ParamBuf1[index].m_Number.m_Integer); +} +void CPDF_StreamContentParser::AddObjectParam(CPDF_Object* pObj) { + int index = GetNextParamPos(); + m_ParamBuf1[index].m_Type = 0; + m_ParamBuf1[index].m_pObject = pObj; +} +void CPDF_StreamContentParser::ClearAllParams() { + FX_DWORD index = m_ParamStartPos; + for (FX_DWORD i = 0; i < m_ParamCount; i++) { + if (m_ParamBuf1[index].m_Type == 0) { + if (CPDF_Object* pObject = m_ParamBuf1[index].m_pObject) + pObject->Release(); + } + index++; + if (index == PARAM_BUF_SIZE) { + index = 0; + } + } + m_ParamStartPos = 0; + m_ParamCount = 0; +} +CPDF_Object* CPDF_StreamContentParser::GetObject(FX_DWORD index) { + if (index >= m_ParamCount) { return NULL; -} -CFX_ByteString CPDF_StreamContentParser::GetString(FX_DWORD index) -{ - if (index >= m_ParamCount) { - return CFX_ByteString(); - } - int real_index = m_ParamStartPos + m_ParamCount - index - 1; - if (real_index >= PARAM_BUF_SIZE) { - real_index -= PARAM_BUF_SIZE; - } - _ContentParam& param = m_ParamBuf1[real_index]; - if (param.m_Type == PDFOBJ_NAME) { - return CFX_ByteString(param.m_Name.m_Buffer, param.m_Name.m_Len); - } - if (param.m_Type == 0 && param.m_pObject) { - return param.m_pObject->GetString(); - } + } + int real_index = m_ParamStartPos + m_ParamCount - index - 1; + if (real_index >= PARAM_BUF_SIZE) { + real_index -= PARAM_BUF_SIZE; + } + _ContentParam& param = m_ParamBuf1[real_index]; + if (param.m_Type == PDFOBJ_NUMBER) { + CPDF_Number* pNumber = CPDF_Number::Create(param.m_Number.m_bInteger, + ¶m.m_Number.m_Integer); + param.m_Type = 0; + param.m_pObject = pNumber; + return pNumber; + } + if (param.m_Type == PDFOBJ_NAME) { + CPDF_Name* pName = CPDF_Name::Create( + CFX_ByteString(param.m_Name.m_Buffer, param.m_Name.m_Len)); + param.m_Type = 0; + param.m_pObject = pName; + return pName; + } + if (param.m_Type == 0) { + return param.m_pObject; + } + ASSERT(FALSE); + return NULL; +} +CFX_ByteString CPDF_StreamContentParser::GetString(FX_DWORD index) { + if (index >= m_ParamCount) { return CFX_ByteString(); -} -FX_FLOAT CPDF_StreamContentParser::GetNumber(FX_DWORD index) -{ - if (index >= m_ParamCount) { - return 0; - } - int real_index = m_ParamStartPos + m_ParamCount - index - 1; - if (real_index >= PARAM_BUF_SIZE) { - real_index -= PARAM_BUF_SIZE; - } - _ContentParam& param = m_ParamBuf1[real_index]; - if (param.m_Type == PDFOBJ_NUMBER) { - return param.m_Number.m_bInteger ? (FX_FLOAT)param.m_Number.m_Integer : param.m_Number.m_Float; - } - if (param.m_Type == 0 && param.m_pObject) { - return param.m_pObject->GetNumber(); - } + } + int real_index = m_ParamStartPos + m_ParamCount - index - 1; + if (real_index >= PARAM_BUF_SIZE) { + real_index -= PARAM_BUF_SIZE; + } + _ContentParam& param = m_ParamBuf1[real_index]; + if (param.m_Type == PDFOBJ_NAME) { + return CFX_ByteString(param.m_Name.m_Buffer, param.m_Name.m_Len); + } + if (param.m_Type == 0 && param.m_pObject) { + return param.m_pObject->GetString(); + } + return CFX_ByteString(); +} +FX_FLOAT CPDF_StreamContentParser::GetNumber(FX_DWORD index) { + if (index >= m_ParamCount) { return 0; -} -FX_FLOAT CPDF_StreamContentParser::GetNumber16(FX_DWORD index) -{ - return GetNumber(index); -} -void CPDF_StreamContentParser::SetGraphicStates(CPDF_PageObject* pObj, FX_BOOL bColor, FX_BOOL bText, FX_BOOL bGraph) -{ - pObj->m_GeneralState = m_pCurStates->m_GeneralState; - pObj->m_ClipPath = m_pCurStates->m_ClipPath; - pObj->m_ContentMark = m_CurContentMark; - if (bColor) { - pObj->m_ColorState = m_pCurStates->m_ColorState; - } - if (bGraph) { - pObj->m_GraphState = m_pCurStates->m_GraphState; - } - if (bText) { - pObj->m_TextState = m_pCurStates->m_TextState; - } + } + int real_index = m_ParamStartPos + m_ParamCount - index - 1; + if (real_index >= PARAM_BUF_SIZE) { + real_index -= PARAM_BUF_SIZE; + } + _ContentParam& param = m_ParamBuf1[real_index]; + if (param.m_Type == PDFOBJ_NUMBER) { + return param.m_Number.m_bInteger ? (FX_FLOAT)param.m_Number.m_Integer + : param.m_Number.m_Float; + } + if (param.m_Type == 0 && param.m_pObject) { + return param.m_pObject->GetNumber(); + } + return 0; +} +FX_FLOAT CPDF_StreamContentParser::GetNumber16(FX_DWORD index) { + return GetNumber(index); +} +void CPDF_StreamContentParser::SetGraphicStates(CPDF_PageObject* pObj, + FX_BOOL bColor, + FX_BOOL bText, + FX_BOOL bGraph) { + pObj->m_GeneralState = m_pCurStates->m_GeneralState; + pObj->m_ClipPath = m_pCurStates->m_ClipPath; + pObj->m_ContentMark = m_CurContentMark; + if (bColor) { + pObj->m_ColorState = m_pCurStates->m_ColorState; + } + if (bGraph) { + pObj->m_GraphState = m_pCurStates->m_GraphState; + } + if (bText) { + pObj->m_TextState = m_pCurStates->m_TextState; + } } -const CPDF_StreamContentParser::OpCode CPDF_StreamContentParser::g_OpCodes[] = -{ - {FXBSTR_ID('"', 0, 0, 0), &CPDF_StreamContentParser::Handle_NextLineShowText_Space}, - {FXBSTR_ID('\'', 0, 0, 0), &CPDF_StreamContentParser::Handle_NextLineShowText}, - {FXBSTR_ID('B', 0, 0, 0), &CPDF_StreamContentParser::Handle_FillStrokePath}, - {FXBSTR_ID('B', '*', 0, 0), &CPDF_StreamContentParser::Handle_EOFillStrokePath}, - {FXBSTR_ID('B', 'D', 'C', 0), &CPDF_StreamContentParser::Handle_BeginMarkedContent_Dictionary}, - {FXBSTR_ID('B', 'I', 0, 0), &CPDF_StreamContentParser::Handle_BeginImage}, - {FXBSTR_ID('B', 'M', 'C', 0), &CPDF_StreamContentParser::Handle_BeginMarkedContent}, - {FXBSTR_ID('B', 'T', 0, 0), &CPDF_StreamContentParser::Handle_BeginText}, - {FXBSTR_ID('B', 'X', 0, 0), &CPDF_StreamContentParser::Handle_BeginSectionUndefined}, - {FXBSTR_ID('C', 'S', 0, 0), &CPDF_StreamContentParser::Handle_SetColorSpace_Stroke}, - {FXBSTR_ID('D', 'P', 0, 0), &CPDF_StreamContentParser::Handle_MarkPlace_Dictionary}, - {FXBSTR_ID('D', 'o', 0, 0), &CPDF_StreamContentParser::Handle_ExecuteXObject}, - {FXBSTR_ID('E', 'I', 0, 0), &CPDF_StreamContentParser::Handle_EndImage}, - {FXBSTR_ID('E', 'M', 'C', 0), &CPDF_StreamContentParser::Handle_EndMarkedContent}, - {FXBSTR_ID('E', 'T', 0, 0), &CPDF_StreamContentParser::Handle_EndText}, - {FXBSTR_ID('E', 'X', 0, 0), &CPDF_StreamContentParser::Handle_EndSectionUndefined}, - {FXBSTR_ID('F', 0, 0, 0), &CPDF_StreamContentParser::Handle_FillPathOld}, - {FXBSTR_ID('G', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetGray_Stroke}, - {FXBSTR_ID('I', 'D', 0, 0), &CPDF_StreamContentParser::Handle_BeginImageData}, - {FXBSTR_ID('J', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetLineCap}, - {FXBSTR_ID('K', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetCMYKColor_Stroke}, - {FXBSTR_ID('M', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetMiterLimit}, - {FXBSTR_ID('M', 'P', 0, 0), &CPDF_StreamContentParser::Handle_MarkPlace}, - {FXBSTR_ID('Q', 0, 0, 0), &CPDF_StreamContentParser::Handle_RestoreGraphState}, - {FXBSTR_ID('R', 'G', 0, 0), &CPDF_StreamContentParser::Handle_SetRGBColor_Stroke}, - {FXBSTR_ID('S', 0, 0, 0), &CPDF_StreamContentParser::Handle_StrokePath}, - {FXBSTR_ID('S', 'C', 0, 0), &CPDF_StreamContentParser::Handle_SetColor_Stroke}, - {FXBSTR_ID('S', 'C', 'N', 0), &CPDF_StreamContentParser::Handle_SetColorPS_Stroke}, - {FXBSTR_ID('T', '*', 0, 0), &CPDF_StreamContentParser::Handle_MoveToNextLine}, - {FXBSTR_ID('T', 'D', 0, 0), &CPDF_StreamContentParser::Handle_MoveTextPoint_SetLeading}, - {FXBSTR_ID('T', 'J', 0, 0), &CPDF_StreamContentParser::Handle_ShowText_Positioning}, - {FXBSTR_ID('T', 'L', 0, 0), &CPDF_StreamContentParser::Handle_SetTextLeading}, - {FXBSTR_ID('T', 'c', 0, 0), &CPDF_StreamContentParser::Handle_SetCharSpace}, - {FXBSTR_ID('T', 'd', 0, 0), &CPDF_StreamContentParser::Handle_MoveTextPoint}, - {FXBSTR_ID('T', 'f', 0, 0), &CPDF_StreamContentParser::Handle_SetFont}, - {FXBSTR_ID('T', 'j', 0, 0), &CPDF_StreamContentParser::Handle_ShowText}, - {FXBSTR_ID('T', 'm', 0, 0), &CPDF_StreamContentParser::Handle_SetTextMatrix}, - {FXBSTR_ID('T', 'r', 0, 0), &CPDF_StreamContentParser::Handle_SetTextRenderMode}, - {FXBSTR_ID('T', 's', 0, 0), &CPDF_StreamContentParser::Handle_SetTextRise}, - {FXBSTR_ID('T', 'w', 0, 0), &CPDF_StreamContentParser::Handle_SetWordSpace}, - {FXBSTR_ID('T', 'z', 0, 0), &CPDF_StreamContentParser::Handle_SetHorzScale}, - {FXBSTR_ID('W', 0, 0, 0), &CPDF_StreamContentParser::Handle_Clip}, - {FXBSTR_ID('W', '*', 0, 0), &CPDF_StreamContentParser::Handle_EOClip}, - {FXBSTR_ID('b', 0, 0, 0), &CPDF_StreamContentParser::Handle_CloseFillStrokePath}, - {FXBSTR_ID('b', '*', 0, 0), &CPDF_StreamContentParser::Handle_CloseEOFillStrokePath}, - {FXBSTR_ID('c', 0, 0, 0), &CPDF_StreamContentParser::Handle_CurveTo_123}, - {FXBSTR_ID('c', 'm', 0, 0), &CPDF_StreamContentParser::Handle_ConcatMatrix}, - {FXBSTR_ID('c', 's', 0, 0), &CPDF_StreamContentParser::Handle_SetColorSpace_Fill}, - {FXBSTR_ID('d', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetDash}, - {FXBSTR_ID('d', '0', 0, 0), &CPDF_StreamContentParser::Handle_SetCharWidth}, - {FXBSTR_ID('d', '1', 0, 0), &CPDF_StreamContentParser::Handle_SetCachedDevice}, - {FXBSTR_ID('f', 0, 0, 0), &CPDF_StreamContentParser::Handle_FillPath}, - {FXBSTR_ID('f', '*', 0, 0), &CPDF_StreamContentParser::Handle_EOFillPath}, - {FXBSTR_ID('g', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetGray_Fill}, - {FXBSTR_ID('g', 's', 0, 0), &CPDF_StreamContentParser::Handle_SetExtendGraphState}, - {FXBSTR_ID('h', 0, 0, 0), &CPDF_StreamContentParser::Handle_ClosePath}, - {FXBSTR_ID('i', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetFlat}, - {FXBSTR_ID('j', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetLineJoin}, - {FXBSTR_ID('k', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetCMYKColor_Fill}, - {FXBSTR_ID('l', 0, 0, 0), &CPDF_StreamContentParser::Handle_LineTo}, - {FXBSTR_ID('m', 0, 0, 0), &CPDF_StreamContentParser::Handle_MoveTo}, - {FXBSTR_ID('n', 0, 0, 0), &CPDF_StreamContentParser::Handle_EndPath}, - {FXBSTR_ID('q', 0, 0, 0), &CPDF_StreamContentParser::Handle_SaveGraphState}, - {FXBSTR_ID('r', 'e', 0, 0), &CPDF_StreamContentParser::Handle_Rectangle}, - {FXBSTR_ID('r', 'g', 0, 0), &CPDF_StreamContentParser::Handle_SetRGBColor_Fill}, - {FXBSTR_ID('r', 'i', 0, 0), &CPDF_StreamContentParser::Handle_SetRenderIntent}, - {FXBSTR_ID('s', 0, 0, 0), &CPDF_StreamContentParser::Handle_CloseStrokePath}, - {FXBSTR_ID('s', 'c', 0, 0), &CPDF_StreamContentParser::Handle_SetColor_Fill}, - {FXBSTR_ID('s', 'c', 'n', 0), &CPDF_StreamContentParser::Handle_SetColorPS_Fill}, - {FXBSTR_ID('s', 'h', 0, 0), &CPDF_StreamContentParser::Handle_ShadeFill}, - {FXBSTR_ID('v', 0, 0, 0), &CPDF_StreamContentParser::Handle_CurveTo_23}, - {FXBSTR_ID('w', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetLineWidth}, - {FXBSTR_ID('y', 0, 0, 0), &CPDF_StreamContentParser::Handle_CurveTo_13}, +const CPDF_StreamContentParser::OpCode CPDF_StreamContentParser::g_OpCodes[] = { + {FXBSTR_ID('"', 0, 0, 0), + &CPDF_StreamContentParser::Handle_NextLineShowText_Space}, + {FXBSTR_ID('\'', 0, 0, 0), + &CPDF_StreamContentParser::Handle_NextLineShowText}, + {FXBSTR_ID('B', 0, 0, 0), &CPDF_StreamContentParser::Handle_FillStrokePath}, + {FXBSTR_ID('B', '*', 0, 0), + &CPDF_StreamContentParser::Handle_EOFillStrokePath}, + {FXBSTR_ID('B', 'D', 'C', 0), + &CPDF_StreamContentParser::Handle_BeginMarkedContent_Dictionary}, + {FXBSTR_ID('B', 'I', 0, 0), &CPDF_StreamContentParser::Handle_BeginImage}, + {FXBSTR_ID('B', 'M', 'C', 0), + &CPDF_StreamContentParser::Handle_BeginMarkedContent}, + {FXBSTR_ID('B', 'T', 0, 0), &CPDF_StreamContentParser::Handle_BeginText}, + {FXBSTR_ID('B', 'X', 0, 0), + &CPDF_StreamContentParser::Handle_BeginSectionUndefined}, + {FXBSTR_ID('C', 'S', 0, 0), + &CPDF_StreamContentParser::Handle_SetColorSpace_Stroke}, + {FXBSTR_ID('D', 'P', 0, 0), + &CPDF_StreamContentParser::Handle_MarkPlace_Dictionary}, + {FXBSTR_ID('D', 'o', 0, 0), + &CPDF_StreamContentParser::Handle_ExecuteXObject}, + {FXBSTR_ID('E', 'I', 0, 0), &CPDF_StreamContentParser::Handle_EndImage}, + {FXBSTR_ID('E', 'M', 'C', 0), + &CPDF_StreamContentParser::Handle_EndMarkedContent}, + {FXBSTR_ID('E', 'T', 0, 0), &CPDF_StreamContentParser::Handle_EndText}, + {FXBSTR_ID('E', 'X', 0, 0), + &CPDF_StreamContentParser::Handle_EndSectionUndefined}, + {FXBSTR_ID('F', 0, 0, 0), &CPDF_StreamContentParser::Handle_FillPathOld}, + {FXBSTR_ID('G', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetGray_Stroke}, + {FXBSTR_ID('I', 'D', 0, 0), + &CPDF_StreamContentParser::Handle_BeginImageData}, + {FXBSTR_ID('J', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetLineCap}, + {FXBSTR_ID('K', 0, 0, 0), + &CPDF_StreamContentParser::Handle_SetCMYKColor_Stroke}, + {FXBSTR_ID('M', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetMiterLimit}, + {FXBSTR_ID('M', 'P', 0, 0), &CPDF_StreamContentParser::Handle_MarkPlace}, + {FXBSTR_ID('Q', 0, 0, 0), + &CPDF_StreamContentParser::Handle_RestoreGraphState}, + {FXBSTR_ID('R', 'G', 0, 0), + &CPDF_StreamContentParser::Handle_SetRGBColor_Stroke}, + {FXBSTR_ID('S', 0, 0, 0), &CPDF_StreamContentParser::Handle_StrokePath}, + {FXBSTR_ID('S', 'C', 0, 0), + &CPDF_StreamContentParser::Handle_SetColor_Stroke}, + {FXBSTR_ID('S', 'C', 'N', 0), + &CPDF_StreamContentParser::Handle_SetColorPS_Stroke}, + {FXBSTR_ID('T', '*', 0, 0), + &CPDF_StreamContentParser::Handle_MoveToNextLine}, + {FXBSTR_ID('T', 'D', 0, 0), + &CPDF_StreamContentParser::Handle_MoveTextPoint_SetLeading}, + {FXBSTR_ID('T', 'J', 0, 0), + &CPDF_StreamContentParser::Handle_ShowText_Positioning}, + {FXBSTR_ID('T', 'L', 0, 0), + &CPDF_StreamContentParser::Handle_SetTextLeading}, + {FXBSTR_ID('T', 'c', 0, 0), &CPDF_StreamContentParser::Handle_SetCharSpace}, + {FXBSTR_ID('T', 'd', 0, 0), + &CPDF_StreamContentParser::Handle_MoveTextPoint}, + {FXBSTR_ID('T', 'f', 0, 0), &CPDF_StreamContentParser::Handle_SetFont}, + {FXBSTR_ID('T', 'j', 0, 0), &CPDF_StreamContentParser::Handle_ShowText}, + {FXBSTR_ID('T', 'm', 0, 0), + &CPDF_StreamContentParser::Handle_SetTextMatrix}, + {FXBSTR_ID('T', 'r', 0, 0), + &CPDF_StreamContentParser::Handle_SetTextRenderMode}, + {FXBSTR_ID('T', 's', 0, 0), &CPDF_StreamContentParser::Handle_SetTextRise}, + {FXBSTR_ID('T', 'w', 0, 0), &CPDF_StreamContentParser::Handle_SetWordSpace}, + {FXBSTR_ID('T', 'z', 0, 0), &CPDF_StreamContentParser::Handle_SetHorzScale}, + {FXBSTR_ID('W', 0, 0, 0), &CPDF_StreamContentParser::Handle_Clip}, + {FXBSTR_ID('W', '*', 0, 0), &CPDF_StreamContentParser::Handle_EOClip}, + {FXBSTR_ID('b', 0, 0, 0), + &CPDF_StreamContentParser::Handle_CloseFillStrokePath}, + {FXBSTR_ID('b', '*', 0, 0), + &CPDF_StreamContentParser::Handle_CloseEOFillStrokePath}, + {FXBSTR_ID('c', 0, 0, 0), &CPDF_StreamContentParser::Handle_CurveTo_123}, + {FXBSTR_ID('c', 'm', 0, 0), &CPDF_StreamContentParser::Handle_ConcatMatrix}, + {FXBSTR_ID('c', 's', 0, 0), + &CPDF_StreamContentParser::Handle_SetColorSpace_Fill}, + {FXBSTR_ID('d', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetDash}, + {FXBSTR_ID('d', '0', 0, 0), &CPDF_StreamContentParser::Handle_SetCharWidth}, + {FXBSTR_ID('d', '1', 0, 0), + &CPDF_StreamContentParser::Handle_SetCachedDevice}, + {FXBSTR_ID('f', 0, 0, 0), &CPDF_StreamContentParser::Handle_FillPath}, + {FXBSTR_ID('f', '*', 0, 0), &CPDF_StreamContentParser::Handle_EOFillPath}, + {FXBSTR_ID('g', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetGray_Fill}, + {FXBSTR_ID('g', 's', 0, 0), + &CPDF_StreamContentParser::Handle_SetExtendGraphState}, + {FXBSTR_ID('h', 0, 0, 0), &CPDF_StreamContentParser::Handle_ClosePath}, + {FXBSTR_ID('i', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetFlat}, + {FXBSTR_ID('j', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetLineJoin}, + {FXBSTR_ID('k', 0, 0, 0), + &CPDF_StreamContentParser::Handle_SetCMYKColor_Fill}, + {FXBSTR_ID('l', 0, 0, 0), &CPDF_StreamContentParser::Handle_LineTo}, + {FXBSTR_ID('m', 0, 0, 0), &CPDF_StreamContentParser::Handle_MoveTo}, + {FXBSTR_ID('n', 0, 0, 0), &CPDF_StreamContentParser::Handle_EndPath}, + {FXBSTR_ID('q', 0, 0, 0), &CPDF_StreamContentParser::Handle_SaveGraphState}, + {FXBSTR_ID('r', 'e', 0, 0), &CPDF_StreamContentParser::Handle_Rectangle}, + {FXBSTR_ID('r', 'g', 0, 0), + &CPDF_StreamContentParser::Handle_SetRGBColor_Fill}, + {FXBSTR_ID('r', 'i', 0, 0), + &CPDF_StreamContentParser::Handle_SetRenderIntent}, + {FXBSTR_ID('s', 0, 0, 0), + &CPDF_StreamContentParser::Handle_CloseStrokePath}, + {FXBSTR_ID('s', 'c', 0, 0), + &CPDF_StreamContentParser::Handle_SetColor_Fill}, + {FXBSTR_ID('s', 'c', 'n', 0), + &CPDF_StreamContentParser::Handle_SetColorPS_Fill}, + {FXBSTR_ID('s', 'h', 0, 0), &CPDF_StreamContentParser::Handle_ShadeFill}, + {FXBSTR_ID('v', 0, 0, 0), &CPDF_StreamContentParser::Handle_CurveTo_23}, + {FXBSTR_ID('w', 0, 0, 0), &CPDF_StreamContentParser::Handle_SetLineWidth}, + {FXBSTR_ID('y', 0, 0, 0), &CPDF_StreamContentParser::Handle_CurveTo_13}, }; -FX_BOOL CPDF_StreamContentParser::OnOperator(const FX_CHAR* op) -{ - int i = 0; - FX_DWORD opid = 0; - while (i < 4 && op[i]) { - opid = (opid << 8) + op[i]; - i ++; - } - while (i < 4) { - opid <<= 8; - i ++; - }; - int low = 0, high = sizeof g_OpCodes / sizeof(OpCode) - 1; - while (low <= high) { - int middle = (low + high) / 2; - int compare = opid - g_OpCodes[middle].m_OpId; - if (compare == 0) { - (this->*g_OpCodes[middle].m_OpHandler)(); - return TRUE; - } - if (compare < 0) { - high = middle - 1; - } else { - low = middle + 1; - } - } - return m_CompatCount != 0; -} -void CPDF_StreamContentParser::Handle_CloseFillStrokePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - Handle_ClosePath(); - AddPathObject(FXFILL_WINDING, TRUE); -} -void CPDF_StreamContentParser::Handle_FillStrokePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(FXFILL_WINDING, TRUE); -} -void CPDF_StreamContentParser::Handle_CloseEOFillStrokePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathPoint(m_PathStartX, m_PathStartY, FXPT_LINETO | FXPT_CLOSEFIGURE); - AddPathObject(FXFILL_ALTERNATE, TRUE); -} -void CPDF_StreamContentParser::Handle_EOFillStrokePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(FXFILL_ALTERNATE, TRUE); -} -void CPDF_StreamContentParser::Handle_BeginMarkedContent_Dictionary() -{ - if (!m_Options.m_bMarkedContent) { - return; - } - CFX_ByteString tag = GetString(1); - CPDF_Object* pProperty = GetObject(0); +FX_BOOL CPDF_StreamContentParser::OnOperator(const FX_CHAR* op) { + int i = 0; + FX_DWORD opid = 0; + while (i < 4 && op[i]) { + opid = (opid << 8) + op[i]; + i++; + } + while (i < 4) { + opid <<= 8; + i++; + }; + int low = 0, high = sizeof g_OpCodes / sizeof(OpCode) - 1; + while (low <= high) { + int middle = (low + high) / 2; + int compare = opid - g_OpCodes[middle].m_OpId; + if (compare == 0) { + (this->*g_OpCodes[middle].m_OpHandler)(); + return TRUE; + } + if (compare < 0) { + high = middle - 1; + } else { + low = middle + 1; + } + } + return m_CompatCount != 0; +} +void CPDF_StreamContentParser::Handle_CloseFillStrokePath() { + if (m_Options.m_bTextOnly) { + return; + } + Handle_ClosePath(); + AddPathObject(FXFILL_WINDING, TRUE); +} +void CPDF_StreamContentParser::Handle_FillStrokePath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(FXFILL_WINDING, TRUE); +} +void CPDF_StreamContentParser::Handle_CloseEOFillStrokePath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathPoint(m_PathStartX, m_PathStartY, FXPT_LINETO | FXPT_CLOSEFIGURE); + AddPathObject(FXFILL_ALTERNATE, TRUE); +} +void CPDF_StreamContentParser::Handle_EOFillStrokePath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(FXFILL_ALTERNATE, TRUE); +} +void CPDF_StreamContentParser::Handle_BeginMarkedContent_Dictionary() { + if (!m_Options.m_bMarkedContent) { + return; + } + CFX_ByteString tag = GetString(1); + CPDF_Object* pProperty = GetObject(0); + if (pProperty == NULL) { + return; + } + FX_BOOL bDirect = TRUE; + if (pProperty->GetType() == PDFOBJ_NAME) { + pProperty = FindResourceObj(FX_BSTRC("Properties"), pProperty->GetString()); if (pProperty == NULL) { - return; - } - FX_BOOL bDirect = TRUE; - if (pProperty->GetType() == PDFOBJ_NAME) { - pProperty = FindResourceObj(FX_BSTRC("Properties"), pProperty->GetString()); - if (pProperty == NULL) { - return; - } - bDirect = FALSE; - } - if (pProperty->GetType() != PDFOBJ_DICTIONARY) { - return; - } - m_CurContentMark.GetModify()->AddMark(tag, (CPDF_Dictionary*)pProperty, bDirect); -} -void CPDF_StreamContentParser::Handle_BeginMarkedContent() -{ - if (!m_Options.m_bMarkedContent) { - return; - } - CFX_ByteString tag = GetString(0); - m_CurContentMark.GetModify()->AddMark(tag, NULL, FALSE); + return; + } + bDirect = FALSE; + } + if (pProperty->GetType() != PDFOBJ_DICTIONARY) { + return; + } + m_CurContentMark.GetModify()->AddMark(tag, (CPDF_Dictionary*)pProperty, + bDirect); +} +void CPDF_StreamContentParser::Handle_BeginMarkedContent() { + if (!m_Options.m_bMarkedContent) { + return; + } + CFX_ByteString tag = GetString(0); + m_CurContentMark.GetModify()->AddMark(tag, NULL, FALSE); } struct _FX_BSTR { - const FX_CHAR* m_Ptr; - int m_Size; + const FX_CHAR* m_Ptr; + int m_Size; }; -#define _FX_BSTRC(str) {str, sizeof(str)-1} +#define _FX_BSTRC(str) \ + { str, sizeof(str) - 1 } const _FX_BSTR _PDF_InlineKeyAbbr[] = { - _FX_BSTRC("BitsPerComponent"), _FX_BSTRC("BPC"), - _FX_BSTRC("ColorSpace"), _FX_BSTRC("CS"), - _FX_BSTRC("Decode"), _FX_BSTRC("D"), - _FX_BSTRC("DecodeParms"), _FX_BSTRC("DP"), - _FX_BSTRC("Filter"), _FX_BSTRC("F"), - _FX_BSTRC("Height"), _FX_BSTRC("H"), - _FX_BSTRC("ImageMask"), _FX_BSTRC("IM"), - _FX_BSTRC("Interpolate"), _FX_BSTRC("I"), - _FX_BSTRC("Width"), _FX_BSTRC("W"), + _FX_BSTRC("BitsPerComponent"), + _FX_BSTRC("BPC"), + _FX_BSTRC("ColorSpace"), + _FX_BSTRC("CS"), + _FX_BSTRC("Decode"), + _FX_BSTRC("D"), + _FX_BSTRC("DecodeParms"), + _FX_BSTRC("DP"), + _FX_BSTRC("Filter"), + _FX_BSTRC("F"), + _FX_BSTRC("Height"), + _FX_BSTRC("H"), + _FX_BSTRC("ImageMask"), + _FX_BSTRC("IM"), + _FX_BSTRC("Interpolate"), + _FX_BSTRC("I"), + _FX_BSTRC("Width"), + _FX_BSTRC("W"), }; const _FX_BSTR _PDF_InlineValueAbbr[] = { - _FX_BSTRC("DeviceGray"), _FX_BSTRC("G"), - _FX_BSTRC("DeviceRGB"), _FX_BSTRC("RGB"), - _FX_BSTRC("DeviceCMYK"), _FX_BSTRC("CMYK"), - _FX_BSTRC("Indexed"), _FX_BSTRC("I"), - _FX_BSTRC("ASCIIHexDecode"), _FX_BSTRC("AHx"), - _FX_BSTRC("ASCII85Decode"), _FX_BSTRC("A85"), - _FX_BSTRC("LZWDecode"), _FX_BSTRC("LZW"), - _FX_BSTRC("FlateDecode"), _FX_BSTRC("Fl"), + _FX_BSTRC("DeviceGray"), _FX_BSTRC("G"), + _FX_BSTRC("DeviceRGB"), _FX_BSTRC("RGB"), + _FX_BSTRC("DeviceCMYK"), _FX_BSTRC("CMYK"), + _FX_BSTRC("Indexed"), _FX_BSTRC("I"), + _FX_BSTRC("ASCIIHexDecode"), _FX_BSTRC("AHx"), + _FX_BSTRC("ASCII85Decode"), _FX_BSTRC("A85"), + _FX_BSTRC("LZWDecode"), _FX_BSTRC("LZW"), + _FX_BSTRC("FlateDecode"), _FX_BSTRC("Fl"), _FX_BSTRC("RunLengthDecode"), _FX_BSTRC("RL"), - _FX_BSTRC("CCITTFaxDecode"), _FX_BSTRC("CCF"), - _FX_BSTRC("DCTDecode"), _FX_BSTRC("DCT"), + _FX_BSTRC("CCITTFaxDecode"), _FX_BSTRC("CCF"), + _FX_BSTRC("DCTDecode"), _FX_BSTRC("DCT"), }; -static CFX_ByteStringC _PDF_FindFullName(const _FX_BSTR* table, int count, const CFX_ByteStringC& abbr) -{ - int i = 0; - while (i < count) { - if (abbr.GetLength() == table[i + 1].m_Size && FXSYS_memcmp(abbr.GetPtr(), table[i + 1].m_Ptr, abbr.GetLength()) == 0) { - return CFX_ByteStringC(table[i].m_Ptr, table[i].m_Size); - } - i += 2; - } - return CFX_ByteStringC(); -} -void _PDF_ReplaceAbbr(CPDF_Object* pObj) -{ - switch (pObj->GetType()) { - case PDFOBJ_DICTIONARY: { - CPDF_Dictionary* pDict = (CPDF_Dictionary*)pObj; - FX_POSITION pos = pDict->GetStartPos(); - while (pos) { - CFX_ByteString key; - CPDF_Object* value = pDict->GetNextElement(pos, key); - CFX_ByteStringC fullname = _PDF_FindFullName(_PDF_InlineKeyAbbr, - sizeof _PDF_InlineKeyAbbr / sizeof(_FX_BSTR), key); - if (!fullname.IsEmpty()) { - pDict->ReplaceKey(key, fullname); - key = fullname; - } - if (value->GetType() == PDFOBJ_NAME) { - CFX_ByteString name = value->GetString(); - fullname = _PDF_FindFullName(_PDF_InlineValueAbbr, - sizeof _PDF_InlineValueAbbr / sizeof(_FX_BSTR), name); - if (!fullname.IsEmpty()) { - pDict->SetAtName(key, fullname); - } - } else { - _PDF_ReplaceAbbr(value); - } - } - break; - } - case PDFOBJ_ARRAY: { - CPDF_Array* pArray = (CPDF_Array*)pObj; - for (FX_DWORD i = 0; i < pArray->GetCount(); i ++) { - CPDF_Object* pElement = pArray->GetElement(i); - if (pElement->GetType() == PDFOBJ_NAME) { - CFX_ByteString name = pElement->GetString(); - CFX_ByteStringC fullname = _PDF_FindFullName(_PDF_InlineValueAbbr, - sizeof _PDF_InlineValueAbbr / sizeof(_FX_BSTR), name); - if (!fullname.IsEmpty()) { - pArray->SetAt(i, CPDF_Name::Create(fullname)); - } - } else { - _PDF_ReplaceAbbr(pElement); - } - } - break; - } - } -} -static CFX_ByteStringC _PDF_FindAbbrName(const _FX_BSTR* table, int count, const CFX_ByteStringC& fullName) -{ - int i = 0; - while (i < count) { - if (fullName.GetLength() == table[i].m_Size && FXSYS_memcmp(fullName.GetPtr(), table[i].m_Ptr, fullName.GetLength()) == 0) { - return CFX_ByteStringC(table[i + 1].m_Ptr, table[i + 1].m_Size); +static CFX_ByteStringC _PDF_FindFullName(const _FX_BSTR* table, + int count, + const CFX_ByteStringC& abbr) { + int i = 0; + while (i < count) { + if (abbr.GetLength() == table[i + 1].m_Size && + FXSYS_memcmp(abbr.GetPtr(), table[i + 1].m_Ptr, abbr.GetLength()) == + 0) { + return CFX_ByteStringC(table[i].m_Ptr, table[i].m_Size); + } + i += 2; + } + return CFX_ByteStringC(); +} +void _PDF_ReplaceAbbr(CPDF_Object* pObj) { + switch (pObj->GetType()) { + case PDFOBJ_DICTIONARY: { + CPDF_Dictionary* pDict = (CPDF_Dictionary*)pObj; + FX_POSITION pos = pDict->GetStartPos(); + while (pos) { + CFX_ByteString key; + CPDF_Object* value = pDict->GetNextElement(pos, key); + CFX_ByteStringC fullname = _PDF_FindFullName( + _PDF_InlineKeyAbbr, sizeof _PDF_InlineKeyAbbr / sizeof(_FX_BSTR), + key); + if (!fullname.IsEmpty()) { + pDict->ReplaceKey(key, fullname); + key = fullname; } - i += 2; - } - return CFX_ByteStringC(); -} -void _PDF_ReplaceFull(CPDF_Object* pObj) -{ - switch (pObj->GetType()) { - case PDFOBJ_DICTIONARY: { - CPDF_Dictionary* pDict = (CPDF_Dictionary*)pObj; - FX_POSITION pos = pDict->GetStartPos(); - while (pos) { - CFX_ByteString key; - CPDF_Object* value = pDict->GetNextElement(pos, key); - CFX_ByteStringC abbrName = _PDF_FindAbbrName(_PDF_InlineKeyAbbr, - sizeof(_PDF_InlineKeyAbbr) / sizeof(_FX_BSTR), key); - if (!abbrName.IsEmpty()) { - pDict->ReplaceKey(key, abbrName); - key = abbrName; - } - if (value->GetType() == PDFOBJ_NAME) { - CFX_ByteString name = value->GetString(); - abbrName = _PDF_FindAbbrName(_PDF_InlineValueAbbr, - sizeof(_PDF_InlineValueAbbr) / sizeof(_FX_BSTR), name); - if (!abbrName.IsEmpty()) { - pDict->SetAtName(key, abbrName); - } - } else { - _PDF_ReplaceFull(value); - } - } - break; - } - case PDFOBJ_ARRAY: { - CPDF_Array* pArray = (CPDF_Array*)pObj; - for (FX_DWORD i = 0; i < pArray->GetCount(); i ++) { - CPDF_Object* pElement = pArray->GetElement(i); - if (pElement->GetType() == PDFOBJ_NAME) { - CFX_ByteString name = pElement->GetString(); - CFX_ByteStringC abbrName = _PDF_FindAbbrName(_PDF_InlineValueAbbr, - sizeof _PDF_InlineValueAbbr / sizeof(_FX_BSTR), name); - if (!abbrName.IsEmpty()) { - pArray->SetAt(i, CPDF_Name::Create(abbrName)); - } - } else { - _PDF_ReplaceFull(pElement); - } - } - break; - } - } -} -void CPDF_StreamContentParser::Handle_BeginText() -{ - m_pCurStates->m_TextMatrix.Set(1.0f, 0, 0, 1.0f, 0, 0); - OnChangeTextMatrix(); - m_pCurStates->m_TextX = 0; - m_pCurStates->m_TextY = 0; - m_pCurStates->m_TextLineX = 0; - m_pCurStates->m_TextLineY = 0; -} -void CPDF_StreamContentParser::Handle_BeginSectionUndefined() -{ - m_CompatCount ++; -} -void CPDF_StreamContentParser::Handle_CurveTo_123() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathPoint(GetNumber(5), GetNumber(4), FXPT_BEZIERTO); - AddPathPoint(GetNumber(3), GetNumber(2), FXPT_BEZIERTO); - AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); -} -void CPDF_StreamContentParser::Handle_ConcatMatrix() -{ - FX_FLOAT a2 = GetNumber16(5), b2 = GetNumber16(4), c2 = GetNumber16(3), d2 = GetNumber16(2); - FX_FLOAT e2 = GetNumber(1), f2 = GetNumber(0); - CFX_AffineMatrix new_matrix(a2, b2, c2, d2, e2, f2); - new_matrix.Concat(m_pCurStates->m_CTM); - m_pCurStates->m_CTM = new_matrix; - OnChangeTextMatrix(); -} -void CPDF_StreamContentParser::Handle_SetColorSpace_Fill() -{ - if (m_Options.m_bTextOnly) { - return; - } - CFX_ByteString csname = GetString(0); - CPDF_ColorSpace* pCS = FindColorSpace(csname); - if (pCS == NULL) { - return; - } - m_pCurStates->m_ColorState.GetModify()->m_FillColor.SetColorSpace(pCS); -} -void CPDF_StreamContentParser::Handle_SetColorSpace_Stroke() -{ - if (m_Options.m_bTextOnly) { - return; - } - CFX_ByteString csname = GetString(0); - CPDF_ColorSpace* pCS = FindColorSpace(csname); - if (pCS == NULL) { - return; - } - m_pCurStates->m_ColorState.GetModify()->m_StrokeColor.SetColorSpace(pCS); -} -void CPDF_StreamContentParser::Handle_SetDash() -{ - if (m_Options.m_bTextOnly) { - return; - } - CPDF_Array* pArray = GetObject(1) ? GetObject(1)->GetArray() : NULL; - if (pArray == NULL) { - return; - } - m_pCurStates->SetLineDash(pArray, GetNumber(0), 1.0f); -} -void CPDF_StreamContentParser::Handle_SetCharWidth() -{ - m_Type3Data[0] = GetNumber(1); - m_Type3Data[1] = GetNumber(0); - m_bColored = TRUE; -} -void CPDF_StreamContentParser::Handle_SetCachedDevice() -{ - for (int i = 0; i < 6; i ++) { - m_Type3Data[i] = GetNumber(5 - i); - } - m_bColored = FALSE; -} -void CPDF_StreamContentParser::Handle_ExecuteXObject() -{ - CFX_ByteString name = GetString(0); - if (name == m_LastImageName && m_pLastImage && m_pLastImage->GetStream() && m_pLastImage->GetStream()->GetObjNum()) { - AddImage(NULL, m_pLastImage, FALSE); - return; - } - if (m_Options.m_bTextOnly) { - CPDF_Object* pRes = NULL; - if (m_pResources == NULL) { - return; - } - if (m_pResources == m_pPageResources) { - CPDF_Dictionary* pList = m_pResources->GetDict(FX_BSTRC("XObject")); - if (pList == NULL) { - return; - } - pRes = pList->GetElement(name); - if (pRes == NULL || pRes->GetType() != PDFOBJ_REFERENCE) { - return; - } + if (value->GetType() == PDFOBJ_NAME) { + CFX_ByteString name = value->GetString(); + fullname = _PDF_FindFullName( + _PDF_InlineValueAbbr, + sizeof _PDF_InlineValueAbbr / sizeof(_FX_BSTR), name); + if (!fullname.IsEmpty()) { + pDict->SetAtName(key, fullname); + } } else { - CPDF_Dictionary* pList = m_pResources->GetDict(FX_BSTRC("XObject")); - if (pList == NULL) { - if (m_pPageResources == NULL) { - return; - } - CPDF_Dictionary* pList = m_pPageResources->GetDict(FX_BSTRC("XObject")); - if (pList == NULL) { - return; - } - pRes = pList->GetElement(name); - if (pRes == NULL || pRes->GetType() != PDFOBJ_REFERENCE) { - return; - } - } else { - pRes = pList->GetElement(name); - if (pRes == NULL || pRes->GetType() != PDFOBJ_REFERENCE) { - return; - } - } + _PDF_ReplaceAbbr(value); } - FX_BOOL bForm; - if (m_pDocument->IsFormStream(((CPDF_Reference*)pRes)->GetRefObjNum(), bForm) && !bForm) { - return; - } - } - CPDF_Stream* pXObject = (CPDF_Stream*)FindResourceObj(FX_BSTRC("XObject"), name); - if (pXObject == NULL || pXObject->GetType() != PDFOBJ_STREAM) { - m_bResourceMissing = TRUE; - return; - } - CFX_ByteStringC type = pXObject->GetDict() ? pXObject->GetDict()->GetConstString(FX_BSTRC("Subtype")) : CFX_ByteStringC(); - if (type == FX_BSTRC("Image")) { - if (m_Options.m_bTextOnly) { - return; + } + break; + } + case PDFOBJ_ARRAY: { + CPDF_Array* pArray = (CPDF_Array*)pObj; + for (FX_DWORD i = 0; i < pArray->GetCount(); i++) { + CPDF_Object* pElement = pArray->GetElement(i); + if (pElement->GetType() == PDFOBJ_NAME) { + CFX_ByteString name = pElement->GetString(); + CFX_ByteStringC fullname = _PDF_FindFullName( + _PDF_InlineValueAbbr, + sizeof _PDF_InlineValueAbbr / sizeof(_FX_BSTR), name); + if (!fullname.IsEmpty()) { + pArray->SetAt(i, CPDF_Name::Create(fullname)); + } + } else { + _PDF_ReplaceAbbr(pElement); } - CPDF_ImageObject* pObj = AddImage(pXObject, NULL, FALSE); - m_LastImageName = name; - m_pLastImage = pObj->m_pImage; - } else if (type == FX_BSTRC("Form")) { - AddForm(pXObject); - } else { - return; - } -} -void CPDF_StreamContentParser::AddForm(CPDF_Stream* pStream) -{ - if (!m_Options.m_bSeparateForm) { - CPDF_Dictionary* pResources = pStream->GetDict()->GetDict(FX_BSTRC("Resources")); - CFX_AffineMatrix form_matrix = pStream->GetDict()->GetMatrix(FX_BSTRC("Matrix")); - form_matrix.Concat(m_pCurStates->m_CTM); - CPDF_Array* pBBox = pStream->GetDict()->GetArray(FX_BSTRC("BBox")); - CFX_FloatRect form_bbox; - CPDF_Path ClipPath; - if (pBBox) { - form_bbox = pStream->GetDict()->GetRect(FX_BSTRC("BBox")); - ClipPath.New(); - ClipPath.AppendRect(form_bbox.left, form_bbox.bottom, form_bbox.right, form_bbox.top); - ClipPath.Transform(&form_matrix); - form_bbox.Transform(&form_matrix); + } + break; + } + } +} +static CFX_ByteStringC _PDF_FindAbbrName(const _FX_BSTR* table, + int count, + const CFX_ByteStringC& fullName) { + int i = 0; + while (i < count) { + if (fullName.GetLength() == table[i].m_Size && + FXSYS_memcmp(fullName.GetPtr(), table[i].m_Ptr, fullName.GetLength()) == + 0) { + return CFX_ByteStringC(table[i + 1].m_Ptr, table[i + 1].m_Size); + } + i += 2; + } + return CFX_ByteStringC(); +} +void _PDF_ReplaceFull(CPDF_Object* pObj) { + switch (pObj->GetType()) { + case PDFOBJ_DICTIONARY: { + CPDF_Dictionary* pDict = (CPDF_Dictionary*)pObj; + FX_POSITION pos = pDict->GetStartPos(); + while (pos) { + CFX_ByteString key; + CPDF_Object* value = pDict->GetNextElement(pos, key); + CFX_ByteStringC abbrName = _PDF_FindAbbrName( + _PDF_InlineKeyAbbr, sizeof(_PDF_InlineKeyAbbr) / sizeof(_FX_BSTR), + key); + if (!abbrName.IsEmpty()) { + pDict->ReplaceKey(key, abbrName); + key = abbrName; } - CPDF_StreamContentParser parser( - m_pDocument, m_pPageResources, m_pResources, &m_mtContentToUser, - m_pObjectList, pResources, &form_bbox, &m_Options, - m_pCurStates.get(), m_Level + 1); - parser.m_pCurStates->m_CTM = form_matrix; - if (ClipPath.NotNull()) { - parser.m_pCurStates->m_ClipPath.AppendPath(ClipPath, FXFILL_WINDING, TRUE); + if (value->GetType() == PDFOBJ_NAME) { + CFX_ByteString name = value->GetString(); + abbrName = _PDF_FindAbbrName( + _PDF_InlineValueAbbr, + sizeof(_PDF_InlineValueAbbr) / sizeof(_FX_BSTR), name); + if (!abbrName.IsEmpty()) { + pDict->SetAtName(key, abbrName); + } + } else { + _PDF_ReplaceFull(value); } - CPDF_StreamAcc stream; - stream.LoadAllData(pStream, FALSE); - if (stream.GetSize() == 0) { - return; + } + break; + } + case PDFOBJ_ARRAY: { + CPDF_Array* pArray = (CPDF_Array*)pObj; + for (FX_DWORD i = 0; i < pArray->GetCount(); i++) { + CPDF_Object* pElement = pArray->GetElement(i); + if (pElement->GetType() == PDFOBJ_NAME) { + CFX_ByteString name = pElement->GetString(); + CFX_ByteStringC abbrName = _PDF_FindAbbrName( + _PDF_InlineValueAbbr, + sizeof _PDF_InlineValueAbbr / sizeof(_FX_BSTR), name); + if (!abbrName.IsEmpty()) { + pArray->SetAt(i, CPDF_Name::Create(abbrName)); + } + } else { + _PDF_ReplaceFull(pElement); } - parser.Parse(stream.GetData(), stream.GetSize(), 0); - return; - } - CPDF_FormObject* pFormObj = new CPDF_FormObject; - pFormObj->m_pForm = new CPDF_Form(m_pDocument, m_pPageResources, pStream, m_pResources); - pFormObj->m_FormMatrix = m_pCurStates->m_CTM; - pFormObj->m_FormMatrix.Concat(m_mtContentToUser); - CPDF_AllStates status; - status.m_GeneralState = m_pCurStates->m_GeneralState; - status.m_GraphState = m_pCurStates->m_GraphState; - status.m_ColorState = m_pCurStates->m_ColorState; - status.m_TextState = m_pCurStates->m_TextState; - pFormObj->m_pForm->ParseContent(&status, NULL, NULL, &m_Options, m_Level + 1); - if (!m_pObjectList->m_bBackgroundAlphaNeeded && pFormObj->m_pForm->m_bBackgroundAlphaNeeded) { - m_pObjectList->m_bBackgroundAlphaNeeded = TRUE; - } - pFormObj->CalcBoundingBox(); - SetGraphicStates(pFormObj, TRUE, TRUE, TRUE); - m_pObjectList->m_ObjectList.AddTail(pFormObj); -} -CPDF_ImageObject* CPDF_StreamContentParser::AddImage(CPDF_Stream* pStream, CPDF_Image* pImage, FX_BOOL bInline) -{ - if (pStream == NULL && pImage == NULL) { - return NULL; - } - CFX_AffineMatrix ImageMatrix; - ImageMatrix.Copy(m_pCurStates->m_CTM); - ImageMatrix.Concat(m_mtContentToUser); - CPDF_ImageObject* pImageObj = new CPDF_ImageObject; - if (pImage) { - pImageObj->m_pImage = m_pDocument->GetPageData()->GetImage(pImage->GetStream()); - } else if (pStream->GetObjNum()) { - pImageObj->m_pImage = m_pDocument->LoadImageF(pStream); - } else { - pImageObj->m_pImage = new CPDF_Image(m_pDocument); - pImageObj->m_pImage->LoadImageF(pStream, bInline); - } - SetGraphicStates(pImageObj, pImageObj->m_pImage->IsMask(), FALSE, FALSE); - pImageObj->m_Matrix = ImageMatrix; - pImageObj->CalcBoundingBox(); - m_pObjectList->m_ObjectList.AddTail(pImageObj); - return pImageObj; -} -void CPDF_StreamContentParser::Handle_MarkPlace_Dictionary() -{ -} -void CPDF_StreamContentParser::Handle_EndImage() -{ -} -void CPDF_StreamContentParser::Handle_EndMarkedContent() -{ - if (!m_Options.m_bMarkedContent) { - return; - } - if (m_CurContentMark.IsNull()) { - return; + } + break; + } + } +} +void CPDF_StreamContentParser::Handle_BeginText() { + m_pCurStates->m_TextMatrix.Set(1.0f, 0, 0, 1.0f, 0, 0); + OnChangeTextMatrix(); + m_pCurStates->m_TextX = 0; + m_pCurStates->m_TextY = 0; + m_pCurStates->m_TextLineX = 0; + m_pCurStates->m_TextLineY = 0; +} +void CPDF_StreamContentParser::Handle_BeginSectionUndefined() { + m_CompatCount++; +} +void CPDF_StreamContentParser::Handle_CurveTo_123() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathPoint(GetNumber(5), GetNumber(4), FXPT_BEZIERTO); + AddPathPoint(GetNumber(3), GetNumber(2), FXPT_BEZIERTO); + AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); +} +void CPDF_StreamContentParser::Handle_ConcatMatrix() { + FX_FLOAT a2 = GetNumber16(5), b2 = GetNumber16(4), c2 = GetNumber16(3), + d2 = GetNumber16(2); + FX_FLOAT e2 = GetNumber(1), f2 = GetNumber(0); + CFX_AffineMatrix new_matrix(a2, b2, c2, d2, e2, f2); + new_matrix.Concat(m_pCurStates->m_CTM); + m_pCurStates->m_CTM = new_matrix; + OnChangeTextMatrix(); +} +void CPDF_StreamContentParser::Handle_SetColorSpace_Fill() { + if (m_Options.m_bTextOnly) { + return; + } + CFX_ByteString csname = GetString(0); + CPDF_ColorSpace* pCS = FindColorSpace(csname); + if (pCS == NULL) { + return; + } + m_pCurStates->m_ColorState.GetModify()->m_FillColor.SetColorSpace(pCS); +} +void CPDF_StreamContentParser::Handle_SetColorSpace_Stroke() { + if (m_Options.m_bTextOnly) { + return; + } + CFX_ByteString csname = GetString(0); + CPDF_ColorSpace* pCS = FindColorSpace(csname); + if (pCS == NULL) { + return; + } + m_pCurStates->m_ColorState.GetModify()->m_StrokeColor.SetColorSpace(pCS); +} +void CPDF_StreamContentParser::Handle_SetDash() { + if (m_Options.m_bTextOnly) { + return; + } + CPDF_Array* pArray = GetObject(1) ? GetObject(1)->GetArray() : NULL; + if (pArray == NULL) { + return; + } + m_pCurStates->SetLineDash(pArray, GetNumber(0), 1.0f); +} +void CPDF_StreamContentParser::Handle_SetCharWidth() { + m_Type3Data[0] = GetNumber(1); + m_Type3Data[1] = GetNumber(0); + m_bColored = TRUE; +} +void CPDF_StreamContentParser::Handle_SetCachedDevice() { + for (int i = 0; i < 6; i++) { + m_Type3Data[i] = GetNumber(5 - i); + } + m_bColored = FALSE; +} +void CPDF_StreamContentParser::Handle_ExecuteXObject() { + CFX_ByteString name = GetString(0); + if (name == m_LastImageName && m_pLastImage && m_pLastImage->GetStream() && + m_pLastImage->GetStream()->GetObjNum()) { + AddImage(NULL, m_pLastImage, FALSE); + return; + } + if (m_Options.m_bTextOnly) { + CPDF_Object* pRes = NULL; + if (m_pResources == NULL) { + return; } - int count = m_CurContentMark.GetObject()->CountItems(); - if (count == 1) { - m_CurContentMark.SetNull(); + if (m_pResources == m_pPageResources) { + CPDF_Dictionary* pList = m_pResources->GetDict(FX_BSTRC("XObject")); + if (pList == NULL) { return; - } - m_CurContentMark.GetModify()->DeleteLastMark(); -} -void CPDF_StreamContentParser::Handle_EndText() -{ - int count = m_ClipTextList.GetSize(); - if (count == 0) { + } + pRes = pList->GetElement(name); + if (pRes == NULL || pRes->GetType() != PDFOBJ_REFERENCE) { return; - } - if (m_pCurStates->m_TextState.GetObject()->m_TextMode < 4) { - for (int i = 0; i < count; i ++) { - CPDF_TextObject* pText = (CPDF_TextObject*)m_ClipTextList.GetAt(i); - delete pText; - } + } } else { - m_pCurStates->m_ClipPath.AppendTexts((CPDF_TextObject**)m_ClipTextList.GetData(), count); - } - m_ClipTextList.RemoveAll(); -} -void CPDF_StreamContentParser::Handle_EndSectionUndefined() -{ - if (m_CompatCount) { - m_CompatCount --; - } -} -void CPDF_StreamContentParser::Handle_FillPath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(FXFILL_WINDING, FALSE); -} -void CPDF_StreamContentParser::Handle_FillPathOld() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(FXFILL_WINDING, FALSE); -} -void CPDF_StreamContentParser::Handle_EOFillPath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(FXFILL_ALTERNATE, FALSE); -} -void CPDF_StreamContentParser::Handle_SetGray_Fill() -{ - FX_FLOAT value = GetNumber(0); - CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); - m_pCurStates->m_ColorState.SetFillColor(pCS, &value, 1); -} -void CPDF_StreamContentParser::Handle_SetGray_Stroke() -{ - FX_FLOAT value = GetNumber(0); - CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); - m_pCurStates->m_ColorState.SetStrokeColor(pCS, &value, 1); -} -void CPDF_StreamContentParser::Handle_SetExtendGraphState() -{ - CFX_ByteString name = GetString(0); - CPDF_Dictionary* pGS = (CPDF_Dictionary*)FindResourceObj(FX_BSTRC("ExtGState"), name); - if (pGS == NULL || pGS->GetType() != PDFOBJ_DICTIONARY) { - m_bResourceMissing = TRUE; - return; - } - m_pCurStates->ProcessExtGS(pGS, this); -} -void CPDF_StreamContentParser::Handle_ClosePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - if (m_PathPointCount == 0) { - return; - } - if (m_PathStartX != m_PathCurrentX || m_PathStartY != m_PathCurrentY) { - AddPathPoint(m_PathStartX, m_PathStartY, FXPT_LINETO | FXPT_CLOSEFIGURE); - } else if (m_pPathPoints[m_PathPointCount - 1].m_Flag != FXPT_MOVETO) { - m_pPathPoints[m_PathPointCount - 1].m_Flag |= FXPT_CLOSEFIGURE; - } -} -void CPDF_StreamContentParser::Handle_SetFlat() -{ - m_pCurStates->m_GeneralState.GetModify()->m_Flatness = GetNumber(0); -} -void CPDF_StreamContentParser::Handle_BeginImageData() -{ -} -void CPDF_StreamContentParser::Handle_SetLineJoin() -{ - m_pCurStates->m_GraphState.GetModify()->m_LineJoin = (CFX_GraphStateData::LineJoin)GetInteger(0); -} -void CPDF_StreamContentParser::Handle_SetLineCap() -{ - m_pCurStates->m_GraphState.GetModify()->m_LineCap = (CFX_GraphStateData::LineCap)GetInteger(0); -} -void CPDF_StreamContentParser::Handle_SetCMYKColor_Fill() -{ - REQUIRE_PARAMS(4); - FX_FLOAT values[4]; - for (int i = 0; i < 4; i ++) { - values[i] = GetNumber(3 - i); - } - CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); - m_pCurStates->m_ColorState.SetFillColor(pCS, values, 4); -} -void CPDF_StreamContentParser::Handle_SetCMYKColor_Stroke() -{ - REQUIRE_PARAMS(4); - FX_FLOAT values[4]; - for (int i = 0; i < 4; i ++) { - values[i] = GetNumber(3 - i); - } - CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); - m_pCurStates->m_ColorState.SetStrokeColor(pCS, values, 4); -} -void CPDF_StreamContentParser::Handle_LineTo() -{ - REQUIRE_PARAMS(2); - if (m_Options.m_bTextOnly) { - return; - } - AddPathPoint(GetNumber(1), GetNumber(0), FXPT_LINETO); -} -void CPDF_StreamContentParser::Handle_MoveTo() -{ - REQUIRE_PARAMS(2); - if (m_Options.m_bTextOnly) { - m_pSyntax->SkipPathObject(); - return; - } - AddPathPoint(GetNumber(1), GetNumber(0), FXPT_MOVETO); - ParsePathObject(); -} -void CPDF_StreamContentParser::Handle_SetMiterLimit() -{ - m_pCurStates->m_GraphState.GetModify()->m_MiterLimit = GetNumber(0); -} -void CPDF_StreamContentParser::Handle_MarkPlace() -{ -} -void CPDF_StreamContentParser::Handle_EndPath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(0, FALSE); -} -void CPDF_StreamContentParser::Handle_SaveGraphState() -{ - CPDF_AllStates* pStates = new CPDF_AllStates; - pStates->Copy(*m_pCurStates); - m_StateStack.Add(pStates); -} -void CPDF_StreamContentParser::Handle_RestoreGraphState() -{ - int size = m_StateStack.GetSize(); - if (size == 0) { - return; - } - CPDF_AllStates* pStates = (CPDF_AllStates*)m_StateStack.GetAt(size - 1); - m_pCurStates->Copy(*pStates); - delete pStates; - m_StateStack.RemoveAt(size - 1); -} -void CPDF_StreamContentParser::Handle_Rectangle() -{ - if (m_Options.m_bTextOnly) { - return; - } - FX_FLOAT x = GetNumber(3), y = GetNumber(2); - FX_FLOAT w = GetNumber(1), h = GetNumber(0); - AddPathRect(x, y, w, h); -} -void CPDF_StreamContentParser::AddPathRect(FX_FLOAT x, FX_FLOAT y, FX_FLOAT w, FX_FLOAT h) -{ - AddPathPoint(x, y, FXPT_MOVETO); - AddPathPoint(x + w, y, FXPT_LINETO); - AddPathPoint(x + w, y + h, FXPT_LINETO); - AddPathPoint(x, y + h, FXPT_LINETO); - AddPathPoint(x, y, FXPT_LINETO | FXPT_CLOSEFIGURE); -} -void CPDF_StreamContentParser::Handle_SetRGBColor_Fill() -{ - REQUIRE_PARAMS(3); - FX_FLOAT values[3]; - for (int i = 0; i < 3; i ++) { - values[i] = GetNumber(2 - i); - } - CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); - m_pCurStates->m_ColorState.SetFillColor(pCS, values, 3); -} -void CPDF_StreamContentParser::Handle_SetRGBColor_Stroke() -{ - REQUIRE_PARAMS(3); - FX_FLOAT values[3]; - for (int i = 0; i < 3; i ++) { - values[i] = GetNumber(2 - i); - } - CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); - m_pCurStates->m_ColorState.SetStrokeColor(pCS, values, 3); -} -void CPDF_StreamContentParser::Handle_SetRenderIntent() -{ -} -void CPDF_StreamContentParser::Handle_CloseStrokePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - Handle_ClosePath(); - AddPathObject(0, TRUE); -} -void CPDF_StreamContentParser::Handle_StrokePath() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathObject(0, TRUE); -} -void CPDF_StreamContentParser::Handle_SetColor_Fill() -{ - if (m_Options.m_bTextOnly) { - return; - } - FX_FLOAT values[4]; - int nargs = m_ParamCount; - if (nargs > 4) { - nargs = 4; - } - for (int i = 0; i < nargs; i ++) { - values[i] = GetNumber(nargs - i - 1); - } - m_pCurStates->m_ColorState.SetFillColor(NULL, values, nargs); -} -void CPDF_StreamContentParser::Handle_SetColor_Stroke() -{ - if (m_Options.m_bTextOnly) { - return; - } - FX_FLOAT values[4]; - int nargs = m_ParamCount; - if (nargs > 4) { - nargs = 4; - } - for (int i = 0; i < nargs; i ++) { - values[i] = GetNumber(nargs - i - 1); - } - m_pCurStates->m_ColorState.SetStrokeColor(NULL, values, nargs); -} -void CPDF_StreamContentParser::Handle_SetColorPS_Fill() -{ - if (m_Options.m_bTextOnly) { - return; - } - CPDF_Object* pLastParam = GetObject(0); - if (pLastParam == NULL) { - return; - } - int nargs = m_ParamCount; - int nvalues = nargs; - if (pLastParam->GetType() == PDFOBJ_NAME) { - nvalues --; - } - FX_FLOAT* values = NULL; - if (nvalues) { - values = FX_Alloc(FX_FLOAT, nvalues); - for (int i = 0; i < nvalues; i ++) { - values[i] = GetNumber(nargs - i - 1); + CPDF_Dictionary* pList = m_pResources->GetDict(FX_BSTRC("XObject")); + if (pList == NULL) { + if (m_pPageResources == NULL) { + return; } - } - if (nvalues != nargs) { - CPDF_Pattern* pPattern = FindPattern(GetString(0), FALSE); - if (pPattern) { - m_pCurStates->m_ColorState.SetFillPattern(pPattern, values, nvalues); + CPDF_Dictionary* pList = m_pPageResources->GetDict(FX_BSTRC("XObject")); + if (pList == NULL) { + return; } - } else { - m_pCurStates->m_ColorState.SetFillColor(NULL, values, nvalues); - } - if (values) { - FX_Free(values); - } -} -void CPDF_StreamContentParser::Handle_SetColorPS_Stroke() -{ - if (m_Options.m_bTextOnly) { - return; - } - CPDF_Object* pLastParam = GetObject(0); - if (pLastParam == NULL) { - return; - } - int nargs = m_ParamCount; - int nvalues = nargs; - if (pLastParam->GetType() == PDFOBJ_NAME) { - nvalues --; - } - FX_FLOAT* values = NULL; - if (nvalues) { - values = FX_Alloc(FX_FLOAT, nvalues); - for (int i = 0; i < nvalues; i ++) { - values[i] = GetNumber(nargs - i - 1); + pRes = pList->GetElement(name); + if (pRes == NULL || pRes->GetType() != PDFOBJ_REFERENCE) { + return; } - } - if (nvalues != nargs) { - CPDF_Pattern* pPattern = FindPattern(GetString(0), FALSE); - if (pPattern) { - m_pCurStates->m_ColorState.SetStrokePattern(pPattern, values, nvalues); + } else { + pRes = pList->GetElement(name); + if (pRes == NULL || pRes->GetType() != PDFOBJ_REFERENCE) { + return; } - } else { - m_pCurStates->m_ColorState.SetStrokeColor(NULL, values, nvalues); - } - if (values) { - FX_Free(values); - } -} -CFX_FloatRect _GetShadingBBox(CPDF_Stream* pStream, int type, const CFX_AffineMatrix* pMatrix, - CPDF_Function** pFuncs, int nFuncs, CPDF_ColorSpace* pCS); -void CPDF_StreamContentParser::Handle_ShadeFill() -{ + } + } + FX_BOOL bForm; + if (m_pDocument->IsFormStream(((CPDF_Reference*)pRes)->GetRefObjNum(), + bForm) && + !bForm) { + return; + } + } + CPDF_Stream* pXObject = + (CPDF_Stream*)FindResourceObj(FX_BSTRC("XObject"), name); + if (pXObject == NULL || pXObject->GetType() != PDFOBJ_STREAM) { + m_bResourceMissing = TRUE; + return; + } + CFX_ByteStringC type = + pXObject->GetDict() + ? pXObject->GetDict()->GetConstString(FX_BSTRC("Subtype")) + : CFX_ByteStringC(); + if (type == FX_BSTRC("Image")) { if (m_Options.m_bTextOnly) { - return; - } - CPDF_Pattern* pPattern = FindPattern(GetString(0), TRUE); - if (pPattern == NULL) { - return; - } - if (pPattern->m_PatternType != PATTERN_SHADING) { - return; - } - CPDF_ShadingPattern* pShading = (CPDF_ShadingPattern*)pPattern; - if (!pShading->m_bShadingObj) { - return; - } - if (!pShading->Load()) { - return; - } - CPDF_ShadingObject* pObj = new CPDF_ShadingObject; - pObj->m_pShading = pShading; - SetGraphicStates(pObj, FALSE, FALSE, FALSE); - pObj->m_Matrix = m_pCurStates->m_CTM; - pObj->m_Matrix.Concat(m_mtContentToUser); - CFX_FloatRect bbox; - if (!pObj->m_ClipPath.IsNull()) { - bbox = pObj->m_ClipPath.GetClipBox(); - } else { - bbox = m_BBox; - } - if (pShading->m_ShadingType >= 4) { - bbox.Intersect(_GetShadingBBox((CPDF_Stream*)pShading->m_pShadingObj, pShading->m_ShadingType, &pObj->m_Matrix, - pShading->m_pFunctions, pShading->m_nFuncs, pShading->m_pCS)); - } - pObj->m_Left = bbox.left; - pObj->m_Right = bbox.right; - pObj->m_Top = bbox.top; - pObj->m_Bottom = bbox.bottom; - m_pObjectList->m_ObjectList.AddTail(pObj); -} -void CPDF_StreamContentParser::Handle_SetCharSpace() -{ - m_pCurStates->m_TextState.GetModify()->m_CharSpace = GetNumber(0); -} -void CPDF_StreamContentParser::Handle_MoveTextPoint() -{ - m_pCurStates->m_TextLineX += GetNumber(1); - m_pCurStates->m_TextLineY += GetNumber(0); - m_pCurStates->m_TextX = m_pCurStates->m_TextLineX; - m_pCurStates->m_TextY = m_pCurStates->m_TextLineY; -} -void CPDF_StreamContentParser::Handle_MoveTextPoint_SetLeading() -{ - Handle_MoveTextPoint(); - m_pCurStates->m_TextLeading = -GetNumber(0); -} -void CPDF_StreamContentParser::Handle_SetFont() -{ - FX_FLOAT fs = GetNumber(0); - if (fs == 0) { - fs = m_DefFontSize; - } - m_pCurStates->m_TextState.GetModify()->m_FontSize = fs; - CPDF_Font* pFont = FindFont(GetString(1)); - if (pFont) { - m_pCurStates->m_TextState.SetFont(pFont); - } -} -CPDF_Object* CPDF_StreamContentParser::FindResourceObj(const CFX_ByteStringC& type, const CFX_ByteString& name) -{ - if (m_pResources == NULL) { - return NULL; - } - if (m_pResources == m_pPageResources) { - CPDF_Dictionary* pList = m_pResources->GetDict(type); - if (pList == NULL) { - return NULL; - } - CPDF_Object* pRes = pList->GetElementValue(name); - return pRes; - } + return; + } + CPDF_ImageObject* pObj = AddImage(pXObject, NULL, FALSE); + m_LastImageName = name; + m_pLastImage = pObj->m_pImage; + } else if (type == FX_BSTRC("Form")) { + AddForm(pXObject); + } else { + return; + } +} +void CPDF_StreamContentParser::AddForm(CPDF_Stream* pStream) { + if (!m_Options.m_bSeparateForm) { + CPDF_Dictionary* pResources = + pStream->GetDict()->GetDict(FX_BSTRC("Resources")); + CFX_AffineMatrix form_matrix = + pStream->GetDict()->GetMatrix(FX_BSTRC("Matrix")); + form_matrix.Concat(m_pCurStates->m_CTM); + CPDF_Array* pBBox = pStream->GetDict()->GetArray(FX_BSTRC("BBox")); + CFX_FloatRect form_bbox; + CPDF_Path ClipPath; + if (pBBox) { + form_bbox = pStream->GetDict()->GetRect(FX_BSTRC("BBox")); + ClipPath.New(); + ClipPath.AppendRect(form_bbox.left, form_bbox.bottom, form_bbox.right, + form_bbox.top); + ClipPath.Transform(&form_matrix); + form_bbox.Transform(&form_matrix); + } + CPDF_StreamContentParser parser(m_pDocument, m_pPageResources, m_pResources, + &m_mtContentToUser, m_pObjectList, + pResources, &form_bbox, &m_Options, + m_pCurStates.get(), m_Level + 1); + parser.m_pCurStates->m_CTM = form_matrix; + if (ClipPath.NotNull()) { + parser.m_pCurStates->m_ClipPath.AppendPath(ClipPath, FXFILL_WINDING, + TRUE); + } + CPDF_StreamAcc stream; + stream.LoadAllData(pStream, FALSE); + if (stream.GetSize() == 0) { + return; + } + parser.Parse(stream.GetData(), stream.GetSize(), 0); + return; + } + CPDF_FormObject* pFormObj = new CPDF_FormObject; + pFormObj->m_pForm = + new CPDF_Form(m_pDocument, m_pPageResources, pStream, m_pResources); + pFormObj->m_FormMatrix = m_pCurStates->m_CTM; + pFormObj->m_FormMatrix.Concat(m_mtContentToUser); + CPDF_AllStates status; + status.m_GeneralState = m_pCurStates->m_GeneralState; + status.m_GraphState = m_pCurStates->m_GraphState; + status.m_ColorState = m_pCurStates->m_ColorState; + status.m_TextState = m_pCurStates->m_TextState; + pFormObj->m_pForm->ParseContent(&status, NULL, NULL, &m_Options, m_Level + 1); + if (!m_pObjectList->m_bBackgroundAlphaNeeded && + pFormObj->m_pForm->m_bBackgroundAlphaNeeded) { + m_pObjectList->m_bBackgroundAlphaNeeded = TRUE; + } + pFormObj->CalcBoundingBox(); + SetGraphicStates(pFormObj, TRUE, TRUE, TRUE); + m_pObjectList->m_ObjectList.AddTail(pFormObj); +} +CPDF_ImageObject* CPDF_StreamContentParser::AddImage(CPDF_Stream* pStream, + CPDF_Image* pImage, + FX_BOOL bInline) { + if (pStream == NULL && pImage == NULL) { + return NULL; + } + CFX_AffineMatrix ImageMatrix; + ImageMatrix.Copy(m_pCurStates->m_CTM); + ImageMatrix.Concat(m_mtContentToUser); + CPDF_ImageObject* pImageObj = new CPDF_ImageObject; + if (pImage) { + pImageObj->m_pImage = + m_pDocument->GetPageData()->GetImage(pImage->GetStream()); + } else if (pStream->GetObjNum()) { + pImageObj->m_pImage = m_pDocument->LoadImageF(pStream); + } else { + pImageObj->m_pImage = new CPDF_Image(m_pDocument); + pImageObj->m_pImage->LoadImageF(pStream, bInline); + } + SetGraphicStates(pImageObj, pImageObj->m_pImage->IsMask(), FALSE, FALSE); + pImageObj->m_Matrix = ImageMatrix; + pImageObj->CalcBoundingBox(); + m_pObjectList->m_ObjectList.AddTail(pImageObj); + return pImageObj; +} +void CPDF_StreamContentParser::Handle_MarkPlace_Dictionary() {} +void CPDF_StreamContentParser::Handle_EndImage() {} +void CPDF_StreamContentParser::Handle_EndMarkedContent() { + if (!m_Options.m_bMarkedContent) { + return; + } + if (m_CurContentMark.IsNull()) { + return; + } + int count = m_CurContentMark.GetObject()->CountItems(); + if (count == 1) { + m_CurContentMark.SetNull(); + return; + } + m_CurContentMark.GetModify()->DeleteLastMark(); +} +void CPDF_StreamContentParser::Handle_EndText() { + int count = m_ClipTextList.GetSize(); + if (count == 0) { + return; + } + if (m_pCurStates->m_TextState.GetObject()->m_TextMode < 4) { + for (int i = 0; i < count; i++) { + CPDF_TextObject* pText = (CPDF_TextObject*)m_ClipTextList.GetAt(i); + delete pText; + } + } else { + m_pCurStates->m_ClipPath.AppendTexts( + (CPDF_TextObject**)m_ClipTextList.GetData(), count); + } + m_ClipTextList.RemoveAll(); +} +void CPDF_StreamContentParser::Handle_EndSectionUndefined() { + if (m_CompatCount) { + m_CompatCount--; + } +} +void CPDF_StreamContentParser::Handle_FillPath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(FXFILL_WINDING, FALSE); +} +void CPDF_StreamContentParser::Handle_FillPathOld() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(FXFILL_WINDING, FALSE); +} +void CPDF_StreamContentParser::Handle_EOFillPath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(FXFILL_ALTERNATE, FALSE); +} +void CPDF_StreamContentParser::Handle_SetGray_Fill() { + FX_FLOAT value = GetNumber(0); + CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); + m_pCurStates->m_ColorState.SetFillColor(pCS, &value, 1); +} +void CPDF_StreamContentParser::Handle_SetGray_Stroke() { + FX_FLOAT value = GetNumber(0); + CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); + m_pCurStates->m_ColorState.SetStrokeColor(pCS, &value, 1); +} +void CPDF_StreamContentParser::Handle_SetExtendGraphState() { + CFX_ByteString name = GetString(0); + CPDF_Dictionary* pGS = + (CPDF_Dictionary*)FindResourceObj(FX_BSTRC("ExtGState"), name); + if (pGS == NULL || pGS->GetType() != PDFOBJ_DICTIONARY) { + m_bResourceMissing = TRUE; + return; + } + m_pCurStates->ProcessExtGS(pGS, this); +} +void CPDF_StreamContentParser::Handle_ClosePath() { + if (m_Options.m_bTextOnly) { + return; + } + if (m_PathPointCount == 0) { + return; + } + if (m_PathStartX != m_PathCurrentX || m_PathStartY != m_PathCurrentY) { + AddPathPoint(m_PathStartX, m_PathStartY, FXPT_LINETO | FXPT_CLOSEFIGURE); + } else if (m_pPathPoints[m_PathPointCount - 1].m_Flag != FXPT_MOVETO) { + m_pPathPoints[m_PathPointCount - 1].m_Flag |= FXPT_CLOSEFIGURE; + } +} +void CPDF_StreamContentParser::Handle_SetFlat() { + m_pCurStates->m_GeneralState.GetModify()->m_Flatness = GetNumber(0); +} +void CPDF_StreamContentParser::Handle_BeginImageData() {} +void CPDF_StreamContentParser::Handle_SetLineJoin() { + m_pCurStates->m_GraphState.GetModify()->m_LineJoin = + (CFX_GraphStateData::LineJoin)GetInteger(0); +} +void CPDF_StreamContentParser::Handle_SetLineCap() { + m_pCurStates->m_GraphState.GetModify()->m_LineCap = + (CFX_GraphStateData::LineCap)GetInteger(0); +} +void CPDF_StreamContentParser::Handle_SetCMYKColor_Fill() { + REQUIRE_PARAMS(4); + FX_FLOAT values[4]; + for (int i = 0; i < 4; i++) { + values[i] = GetNumber(3 - i); + } + CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); + m_pCurStates->m_ColorState.SetFillColor(pCS, values, 4); +} +void CPDF_StreamContentParser::Handle_SetCMYKColor_Stroke() { + REQUIRE_PARAMS(4); + FX_FLOAT values[4]; + for (int i = 0; i < 4; i++) { + values[i] = GetNumber(3 - i); + } + CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); + m_pCurStates->m_ColorState.SetStrokeColor(pCS, values, 4); +} +void CPDF_StreamContentParser::Handle_LineTo() { + REQUIRE_PARAMS(2); + if (m_Options.m_bTextOnly) { + return; + } + AddPathPoint(GetNumber(1), GetNumber(0), FXPT_LINETO); +} +void CPDF_StreamContentParser::Handle_MoveTo() { + REQUIRE_PARAMS(2); + if (m_Options.m_bTextOnly) { + m_pSyntax->SkipPathObject(); + return; + } + AddPathPoint(GetNumber(1), GetNumber(0), FXPT_MOVETO); + ParsePathObject(); +} +void CPDF_StreamContentParser::Handle_SetMiterLimit() { + m_pCurStates->m_GraphState.GetModify()->m_MiterLimit = GetNumber(0); +} +void CPDF_StreamContentParser::Handle_MarkPlace() {} +void CPDF_StreamContentParser::Handle_EndPath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(0, FALSE); +} +void CPDF_StreamContentParser::Handle_SaveGraphState() { + CPDF_AllStates* pStates = new CPDF_AllStates; + pStates->Copy(*m_pCurStates); + m_StateStack.Add(pStates); +} +void CPDF_StreamContentParser::Handle_RestoreGraphState() { + int size = m_StateStack.GetSize(); + if (size == 0) { + return; + } + CPDF_AllStates* pStates = (CPDF_AllStates*)m_StateStack.GetAt(size - 1); + m_pCurStates->Copy(*pStates); + delete pStates; + m_StateStack.RemoveAt(size - 1); +} +void CPDF_StreamContentParser::Handle_Rectangle() { + if (m_Options.m_bTextOnly) { + return; + } + FX_FLOAT x = GetNumber(3), y = GetNumber(2); + FX_FLOAT w = GetNumber(1), h = GetNumber(0); + AddPathRect(x, y, w, h); +} +void CPDF_StreamContentParser::AddPathRect(FX_FLOAT x, + FX_FLOAT y, + FX_FLOAT w, + FX_FLOAT h) { + AddPathPoint(x, y, FXPT_MOVETO); + AddPathPoint(x + w, y, FXPT_LINETO); + AddPathPoint(x + w, y + h, FXPT_LINETO); + AddPathPoint(x, y + h, FXPT_LINETO); + AddPathPoint(x, y, FXPT_LINETO | FXPT_CLOSEFIGURE); +} +void CPDF_StreamContentParser::Handle_SetRGBColor_Fill() { + REQUIRE_PARAMS(3); + FX_FLOAT values[3]; + for (int i = 0; i < 3; i++) { + values[i] = GetNumber(2 - i); + } + CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); + m_pCurStates->m_ColorState.SetFillColor(pCS, values, 3); +} +void CPDF_StreamContentParser::Handle_SetRGBColor_Stroke() { + REQUIRE_PARAMS(3); + FX_FLOAT values[3]; + for (int i = 0; i < 3; i++) { + values[i] = GetNumber(2 - i); + } + CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); + m_pCurStates->m_ColorState.SetStrokeColor(pCS, values, 3); +} +void CPDF_StreamContentParser::Handle_SetRenderIntent() {} +void CPDF_StreamContentParser::Handle_CloseStrokePath() { + if (m_Options.m_bTextOnly) { + return; + } + Handle_ClosePath(); + AddPathObject(0, TRUE); +} +void CPDF_StreamContentParser::Handle_StrokePath() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathObject(0, TRUE); +} +void CPDF_StreamContentParser::Handle_SetColor_Fill() { + if (m_Options.m_bTextOnly) { + return; + } + FX_FLOAT values[4]; + int nargs = m_ParamCount; + if (nargs > 4) { + nargs = 4; + } + for (int i = 0; i < nargs; i++) { + values[i] = GetNumber(nargs - i - 1); + } + m_pCurStates->m_ColorState.SetFillColor(NULL, values, nargs); +} +void CPDF_StreamContentParser::Handle_SetColor_Stroke() { + if (m_Options.m_bTextOnly) { + return; + } + FX_FLOAT values[4]; + int nargs = m_ParamCount; + if (nargs > 4) { + nargs = 4; + } + for (int i = 0; i < nargs; i++) { + values[i] = GetNumber(nargs - i - 1); + } + m_pCurStates->m_ColorState.SetStrokeColor(NULL, values, nargs); +} +void CPDF_StreamContentParser::Handle_SetColorPS_Fill() { + if (m_Options.m_bTextOnly) { + return; + } + CPDF_Object* pLastParam = GetObject(0); + if (pLastParam == NULL) { + return; + } + int nargs = m_ParamCount; + int nvalues = nargs; + if (pLastParam->GetType() == PDFOBJ_NAME) { + nvalues--; + } + FX_FLOAT* values = NULL; + if (nvalues) { + values = FX_Alloc(FX_FLOAT, nvalues); + for (int i = 0; i < nvalues; i++) { + values[i] = GetNumber(nargs - i - 1); + } + } + if (nvalues != nargs) { + CPDF_Pattern* pPattern = FindPattern(GetString(0), FALSE); + if (pPattern) { + m_pCurStates->m_ColorState.SetFillPattern(pPattern, values, nvalues); + } + } else { + m_pCurStates->m_ColorState.SetFillColor(NULL, values, nvalues); + } + if (values) { + FX_Free(values); + } +} +void CPDF_StreamContentParser::Handle_SetColorPS_Stroke() { + if (m_Options.m_bTextOnly) { + return; + } + CPDF_Object* pLastParam = GetObject(0); + if (pLastParam == NULL) { + return; + } + int nargs = m_ParamCount; + int nvalues = nargs; + if (pLastParam->GetType() == PDFOBJ_NAME) { + nvalues--; + } + FX_FLOAT* values = NULL; + if (nvalues) { + values = FX_Alloc(FX_FLOAT, nvalues); + for (int i = 0; i < nvalues; i++) { + values[i] = GetNumber(nargs - i - 1); + } + } + if (nvalues != nargs) { + CPDF_Pattern* pPattern = FindPattern(GetString(0), FALSE); + if (pPattern) { + m_pCurStates->m_ColorState.SetStrokePattern(pPattern, values, nvalues); + } + } else { + m_pCurStates->m_ColorState.SetStrokeColor(NULL, values, nvalues); + } + if (values) { + FX_Free(values); + } +} +CFX_FloatRect _GetShadingBBox(CPDF_Stream* pStream, + int type, + const CFX_AffineMatrix* pMatrix, + CPDF_Function** pFuncs, + int nFuncs, + CPDF_ColorSpace* pCS); +void CPDF_StreamContentParser::Handle_ShadeFill() { + if (m_Options.m_bTextOnly) { + return; + } + CPDF_Pattern* pPattern = FindPattern(GetString(0), TRUE); + if (pPattern == NULL) { + return; + } + if (pPattern->m_PatternType != PATTERN_SHADING) { + return; + } + CPDF_ShadingPattern* pShading = (CPDF_ShadingPattern*)pPattern; + if (!pShading->m_bShadingObj) { + return; + } + if (!pShading->Load()) { + return; + } + CPDF_ShadingObject* pObj = new CPDF_ShadingObject; + pObj->m_pShading = pShading; + SetGraphicStates(pObj, FALSE, FALSE, FALSE); + pObj->m_Matrix = m_pCurStates->m_CTM; + pObj->m_Matrix.Concat(m_mtContentToUser); + CFX_FloatRect bbox; + if (!pObj->m_ClipPath.IsNull()) { + bbox = pObj->m_ClipPath.GetClipBox(); + } else { + bbox = m_BBox; + } + if (pShading->m_ShadingType >= 4) { + bbox.Intersect(_GetShadingBBox((CPDF_Stream*)pShading->m_pShadingObj, + pShading->m_ShadingType, &pObj->m_Matrix, + pShading->m_pFunctions, pShading->m_nFuncs, + pShading->m_pCS)); + } + pObj->m_Left = bbox.left; + pObj->m_Right = bbox.right; + pObj->m_Top = bbox.top; + pObj->m_Bottom = bbox.bottom; + m_pObjectList->m_ObjectList.AddTail(pObj); +} +void CPDF_StreamContentParser::Handle_SetCharSpace() { + m_pCurStates->m_TextState.GetModify()->m_CharSpace = GetNumber(0); +} +void CPDF_StreamContentParser::Handle_MoveTextPoint() { + m_pCurStates->m_TextLineX += GetNumber(1); + m_pCurStates->m_TextLineY += GetNumber(0); + m_pCurStates->m_TextX = m_pCurStates->m_TextLineX; + m_pCurStates->m_TextY = m_pCurStates->m_TextLineY; +} +void CPDF_StreamContentParser::Handle_MoveTextPoint_SetLeading() { + Handle_MoveTextPoint(); + m_pCurStates->m_TextLeading = -GetNumber(0); +} +void CPDF_StreamContentParser::Handle_SetFont() { + FX_FLOAT fs = GetNumber(0); + if (fs == 0) { + fs = m_DefFontSize; + } + m_pCurStates->m_TextState.GetModify()->m_FontSize = fs; + CPDF_Font* pFont = FindFont(GetString(1)); + if (pFont) { + m_pCurStates->m_TextState.SetFont(pFont); + } +} +CPDF_Object* CPDF_StreamContentParser::FindResourceObj( + const CFX_ByteStringC& type, + const CFX_ByteString& name) { + if (m_pResources == NULL) { + return NULL; + } + if (m_pResources == m_pPageResources) { CPDF_Dictionary* pList = m_pResources->GetDict(type); if (pList == NULL) { - if (m_pPageResources == NULL) { - return NULL; - } - CPDF_Dictionary* pList = m_pPageResources->GetDict(type); - if (pList == NULL) { - return NULL; - } - CPDF_Object* pRes = pList->GetElementValue(name); - return pRes; + return NULL; } CPDF_Object* pRes = pList->GetElementValue(name); return pRes; -} -CPDF_Font* CPDF_StreamContentParser::FindFont(const CFX_ByteString& name) -{ - CPDF_Dictionary* pFontDict = (CPDF_Dictionary*)FindResourceObj(FX_BSTRC("Font"), name); - if (pFontDict == NULL || pFontDict->GetType() != PDFOBJ_DICTIONARY) { - m_bResourceMissing = TRUE; - return CPDF_Font::GetStockFont(m_pDocument, FX_BSTRC("Helvetica")); - } - CPDF_Font* pFont = m_pDocument->LoadFont(pFontDict); - if (pFont && pFont->GetType3Font()) { - pFont->GetType3Font()->SetPageResources(m_pResources); - pFont->GetType3Font()->CheckType3FontMetrics(); - } - return pFont; -} -CPDF_ColorSpace* CPDF_StreamContentParser::FindColorSpace(const CFX_ByteString& name) -{ - if (name == FX_BSTRC("Pattern")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_PATTERN); - } - if (name == FX_BSTRC("DeviceGray") || name == FX_BSTRC("DeviceCMYK") || name == FX_BSTRC("DeviceRGB")) { - CFX_ByteString defname = "Default"; - defname += name.Mid(7); - CPDF_Object* pDefObj = FindResourceObj(FX_BSTRC("ColorSpace"), defname); - if (pDefObj == NULL) { - if (name == FX_BSTRC("DeviceGray")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); - } - if (name == FX_BSTRC("DeviceRGB")) { - return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); - } - return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); - } - return m_pDocument->LoadColorSpace(pDefObj); - } - CPDF_Object* pCSObj = FindResourceObj(FX_BSTRC("ColorSpace"), name); - if (pCSObj == NULL) { - m_bResourceMissing = TRUE; - return NULL; - } - return m_pDocument->LoadColorSpace(pCSObj); -} -CPDF_Pattern* CPDF_StreamContentParser::FindPattern(const CFX_ByteString& name, FX_BOOL bShading) -{ - CPDF_Object* pPattern = FindResourceObj(bShading ? FX_BSTRC("Shading") : FX_BSTRC("Pattern"), name); - if (pPattern == NULL || (pPattern->GetType() != PDFOBJ_DICTIONARY && - pPattern->GetType() != PDFOBJ_STREAM)) { - m_bResourceMissing = TRUE; - return NULL; - } - return m_pDocument->LoadPattern(pPattern, bShading, &m_pCurStates->m_ParentMatrix); -} -void CPDF_StreamContentParser::ConvertTextSpace(FX_FLOAT& x, FX_FLOAT& y) -{ - m_pCurStates->m_TextMatrix.Transform(x, y, x, y); - ConvertUserSpace(x, y); -} -void CPDF_StreamContentParser::ConvertUserSpace(FX_FLOAT& x, FX_FLOAT& y) -{ - m_pCurStates->m_CTM.Transform(x, y, x, y); - m_mtContentToUser.Transform(x, y, x, y); -} -void CPDF_StreamContentParser::AddTextObject(CFX_ByteString* pStrs, FX_FLOAT fInitKerning, FX_FLOAT* pKerning, int nsegs) -{ - CPDF_Font* pFont = m_pCurStates->m_TextState.GetFont(); - if (pFont == NULL) { - return; - } - if (fInitKerning != 0) { - if (!pFont->IsVertWriting()) { - m_pCurStates->m_TextX -= FXSYS_Mul(fInitKerning, m_pCurStates->m_TextState.GetFontSize()) / 1000; - } else { - m_pCurStates->m_TextY -= FXSYS_Mul(fInitKerning, m_pCurStates->m_TextState.GetFontSize()) / 1000; - } + } + CPDF_Dictionary* pList = m_pResources->GetDict(type); + if (pList == NULL) { + if (m_pPageResources == NULL) { + return NULL; } - if (nsegs == 0) { - return; + CPDF_Dictionary* pList = m_pPageResources->GetDict(type); + if (pList == NULL) { + return NULL; } - int textmode; - if (pFont->GetFontType() == PDFFONT_TYPE3) { - textmode = 0; + CPDF_Object* pRes = pList->GetElementValue(name); + return pRes; + } + CPDF_Object* pRes = pList->GetElementValue(name); + return pRes; +} +CPDF_Font* CPDF_StreamContentParser::FindFont(const CFX_ByteString& name) { + CPDF_Dictionary* pFontDict = + (CPDF_Dictionary*)FindResourceObj(FX_BSTRC("Font"), name); + if (pFontDict == NULL || pFontDict->GetType() != PDFOBJ_DICTIONARY) { + m_bResourceMissing = TRUE; + return CPDF_Font::GetStockFont(m_pDocument, FX_BSTRC("Helvetica")); + } + CPDF_Font* pFont = m_pDocument->LoadFont(pFontDict); + if (pFont && pFont->GetType3Font()) { + pFont->GetType3Font()->SetPageResources(m_pResources); + pFont->GetType3Font()->CheckType3FontMetrics(); + } + return pFont; +} +CPDF_ColorSpace* CPDF_StreamContentParser::FindColorSpace( + const CFX_ByteString& name) { + if (name == FX_BSTRC("Pattern")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_PATTERN); + } + if (name == FX_BSTRC("DeviceGray") || name == FX_BSTRC("DeviceCMYK") || + name == FX_BSTRC("DeviceRGB")) { + CFX_ByteString defname = "Default"; + defname += name.Mid(7); + CPDF_Object* pDefObj = FindResourceObj(FX_BSTRC("ColorSpace"), defname); + if (pDefObj == NULL) { + if (name == FX_BSTRC("DeviceGray")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICEGRAY); + } + if (name == FX_BSTRC("DeviceRGB")) { + return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); + } + return CPDF_ColorSpace::GetStockCS(PDFCS_DEVICECMYK); + } + return m_pDocument->LoadColorSpace(pDefObj); + } + CPDF_Object* pCSObj = FindResourceObj(FX_BSTRC("ColorSpace"), name); + if (pCSObj == NULL) { + m_bResourceMissing = TRUE; + return NULL; + } + return m_pDocument->LoadColorSpace(pCSObj); +} +CPDF_Pattern* CPDF_StreamContentParser::FindPattern(const CFX_ByteString& name, + FX_BOOL bShading) { + CPDF_Object* pPattern = FindResourceObj( + bShading ? FX_BSTRC("Shading") : FX_BSTRC("Pattern"), name); + if (pPattern == NULL || (pPattern->GetType() != PDFOBJ_DICTIONARY && + pPattern->GetType() != PDFOBJ_STREAM)) { + m_bResourceMissing = TRUE; + return NULL; + } + return m_pDocument->LoadPattern(pPattern, bShading, + &m_pCurStates->m_ParentMatrix); +} +void CPDF_StreamContentParser::ConvertTextSpace(FX_FLOAT& x, FX_FLOAT& y) { + m_pCurStates->m_TextMatrix.Transform(x, y, x, y); + ConvertUserSpace(x, y); +} +void CPDF_StreamContentParser::ConvertUserSpace(FX_FLOAT& x, FX_FLOAT& y) { + m_pCurStates->m_CTM.Transform(x, y, x, y); + m_mtContentToUser.Transform(x, y, x, y); +} +void CPDF_StreamContentParser::AddTextObject(CFX_ByteString* pStrs, + FX_FLOAT fInitKerning, + FX_FLOAT* pKerning, + int nsegs) { + CPDF_Font* pFont = m_pCurStates->m_TextState.GetFont(); + if (pFont == NULL) { + return; + } + if (fInitKerning != 0) { + if (!pFont->IsVertWriting()) { + m_pCurStates->m_TextX -= + FXSYS_Mul(fInitKerning, m_pCurStates->m_TextState.GetFontSize()) / + 1000; } else { - textmode = m_pCurStates->m_TextState.GetObject()->m_TextMode; - } - CPDF_TextObject* pText = new CPDF_TextObject; - m_pLastTextObject = pText; - SetGraphicStates(pText, TRUE, TRUE, TRUE); - if (textmode && textmode != 3 && textmode != 4 && textmode != 7) { - FX_FLOAT* pCTM = pText->m_TextState.GetModify()->m_CTM; - pCTM[0] = m_pCurStates->m_CTM.a; - pCTM[1] = m_pCurStates->m_CTM.c; - pCTM[2] = m_pCurStates->m_CTM.b; - pCTM[3] = m_pCurStates->m_CTM.d; - } - pText->SetSegments(pStrs, pKerning, nsegs); - pText->m_PosX = m_pCurStates->m_TextX; - pText->m_PosY = m_pCurStates->m_TextY + m_pCurStates->m_TextRise; - ConvertTextSpace(pText->m_PosX, pText->m_PosY); - FX_FLOAT x_advance, y_advance; - pText->CalcPositionData(&x_advance, &y_advance, m_pCurStates->m_TextHorzScale, m_Level); - m_pCurStates->m_TextX += x_advance; - m_pCurStates->m_TextY += y_advance; - if (textmode > 3) { - CPDF_TextObject* pCopy = new CPDF_TextObject; - pCopy->Copy(pText); - m_ClipTextList.Add(pCopy); - } - m_pObjectList->m_ObjectList.AddTail(pText); - if (pKerning && pKerning[nsegs - 1] != 0) { - if (!pFont->IsVertWriting()) { - m_pCurStates->m_TextX -= FXSYS_Mul(pKerning[nsegs - 1], m_pCurStates->m_TextState.GetFontSize()) / 1000; - } else { - m_pCurStates->m_TextY -= FXSYS_Mul(pKerning[nsegs - 1], m_pCurStates->m_TextState.GetFontSize()) / 1000; - } - } -} -void CPDF_StreamContentParser::Handle_ShowText() -{ - CFX_ByteString str = GetString(0); - if (str.IsEmpty()) { - return; - } - AddTextObject(&str, 0, NULL, 1); -} -void CPDF_StreamContentParser::Handle_ShowText_Positioning() -{ - CPDF_Array* pArray = GetObject(0) ? GetObject(0)->GetArray() : NULL; - if (pArray == NULL) { - return; - } - int n = pArray->GetCount(), nsegs = 0, i; - for (i = 0; i < n; i ++) { - CPDF_Object* pObj = pArray->GetElementValue(i); - if (pObj->GetType() == PDFOBJ_STRING) { - nsegs ++; - } - } - if (nsegs == 0) { - for (i = 0; i < n; i ++) { - m_pCurStates->m_TextX -= FXSYS_Mul(pArray->GetNumber(i), m_pCurStates->m_TextState.GetFontSize()) / 1000; - }; - return; - } - CFX_ByteString* pStrs = new CFX_ByteString[nsegs]; - FX_FLOAT* pKerning = FX_Alloc(FX_FLOAT, nsegs); - int iSegment = 0; - FX_FLOAT fInitKerning = 0; - for (i = 0; i < n; i ++) { - CPDF_Object* pObj = pArray->GetElementValue(i); - if (pObj->GetType() == PDFOBJ_STRING) { - CFX_ByteString str = pObj->GetString(); - if (str.IsEmpty()) { - continue; - } - pStrs[iSegment] = str; - pKerning[iSegment ++] = 0; - } else { - FX_FLOAT num = pObj ? pObj->GetNumber() : 0; - if (iSegment == 0) { - fInitKerning += num; - } else { - pKerning[iSegment - 1] += num; - } - } - } - AddTextObject(pStrs, fInitKerning, pKerning, iSegment); - delete[] pStrs; - FX_Free(pKerning); -} -void CPDF_StreamContentParser::Handle_SetTextLeading() -{ - m_pCurStates->m_TextLeading = GetNumber(0); -} -void CPDF_StreamContentParser::Handle_SetTextMatrix() -{ - m_pCurStates->m_TextMatrix.Set(GetNumber16(5), GetNumber16(4), GetNumber16(3), - GetNumber16(2), GetNumber(1), GetNumber(0)); - OnChangeTextMatrix(); - m_pCurStates->m_TextX = 0; - m_pCurStates->m_TextY = 0; - m_pCurStates->m_TextLineX = 0; - m_pCurStates->m_TextLineY = 0; -} -void CPDF_StreamContentParser::OnChangeTextMatrix() -{ - CFX_AffineMatrix text_matrix(m_pCurStates->m_TextHorzScale, 0.0f, 0.0f, 1.0f, 0.0f, 0.0f); - text_matrix.Concat(m_pCurStates->m_TextMatrix); - text_matrix.Concat(m_pCurStates->m_CTM); - text_matrix.Concat(m_mtContentToUser); - FX_FLOAT* pTextMatrix = m_pCurStates->m_TextState.GetModify()->m_Matrix; - pTextMatrix[0] = text_matrix.a; - pTextMatrix[1] = text_matrix.c; - pTextMatrix[2] = text_matrix.b; - pTextMatrix[3] = text_matrix.d; -} -void CPDF_StreamContentParser::Handle_SetTextRenderMode() -{ - int mode = GetInteger(0); - if (mode < 0 || mode > 7) { - return; - } - m_pCurStates->m_TextState.GetModify()->m_TextMode = mode; -} -void CPDF_StreamContentParser::Handle_SetTextRise() -{ - m_pCurStates->m_TextRise = GetNumber(0); -} -void CPDF_StreamContentParser::Handle_SetWordSpace() -{ - m_pCurStates->m_TextState.GetModify()->m_WordSpace = GetNumber(0); -} -void CPDF_StreamContentParser::Handle_SetHorzScale() -{ - if (m_ParamCount != 1) { - return; - } - m_pCurStates->m_TextHorzScale = GetNumber(0) / 100; - OnChangeTextMatrix(); -} -void CPDF_StreamContentParser::Handle_MoveToNextLine() -{ - m_pCurStates->m_TextLineY -= m_pCurStates->m_TextLeading; - m_pCurStates->m_TextX = m_pCurStates->m_TextLineX; - m_pCurStates->m_TextY = m_pCurStates->m_TextLineY; -} -void CPDF_StreamContentParser::Handle_CurveTo_23() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathPoint(m_PathCurrentX, m_PathCurrentY, FXPT_BEZIERTO); - AddPathPoint(GetNumber(3), GetNumber(2), FXPT_BEZIERTO); - AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); -} -void CPDF_StreamContentParser::Handle_SetLineWidth() -{ - FX_FLOAT width = GetNumber(0); - m_pCurStates->m_GraphState.GetModify()->m_LineWidth = width; -} -void CPDF_StreamContentParser::Handle_Clip() -{ - m_PathClipType = FXFILL_WINDING; -} -void CPDF_StreamContentParser::Handle_EOClip() -{ - m_PathClipType = FXFILL_ALTERNATE; -} -void CPDF_StreamContentParser::Handle_CurveTo_13() -{ - if (m_Options.m_bTextOnly) { - return; - } - AddPathPoint(GetNumber(3), GetNumber(2), FXPT_BEZIERTO); - AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); - AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); -} -void CPDF_StreamContentParser::Handle_NextLineShowText() -{ - Handle_MoveToNextLine(); - Handle_ShowText(); -} -void CPDF_StreamContentParser::Handle_NextLineShowText_Space() -{ - m_pCurStates->m_TextState.GetModify()->m_WordSpace = GetNumber(2); - m_pCurStates->m_TextState.GetModify()->m_CharSpace = GetNumber(1); - Handle_NextLineShowText(); -} -void CPDF_StreamContentParser::Handle_Invalid() -{ -} -void CPDF_StreamContentParser::AddPathPoint(FX_FLOAT x, FX_FLOAT y, int flag) -{ - m_PathCurrentX = x; - m_PathCurrentY = y; - if (flag == FXPT_MOVETO) { - m_PathStartX = x; - m_PathStartY = y; - if (m_PathPointCount && m_pPathPoints[m_PathPointCount - 1].m_Flag == FXPT_MOVETO) { - m_pPathPoints[m_PathPointCount - 1].m_PointX = x; - m_pPathPoints[m_PathPointCount - 1].m_PointY = y; - return; - } - } else if (m_PathPointCount == 0) { - return; - } - m_PathPointCount ++; - if (m_PathPointCount > m_PathAllocSize) { - int newsize = m_PathPointCount + 256; - FX_PATHPOINT* pNewPoints = FX_Alloc(FX_PATHPOINT, newsize); - if (m_PathAllocSize) { - FXSYS_memcpy(pNewPoints, m_pPathPoints, m_PathAllocSize * sizeof(FX_PATHPOINT)); - FX_Free(m_pPathPoints); - } - m_pPathPoints = pNewPoints; - m_PathAllocSize = newsize; - } - m_pPathPoints[m_PathPointCount - 1].m_Flag = flag; - m_pPathPoints[m_PathPointCount - 1].m_PointX = x; - m_pPathPoints[m_PathPointCount - 1].m_PointY = y; -} -void CPDF_StreamContentParser::AddPathObject(int FillType, FX_BOOL bStroke) -{ - int PathPointCount = m_PathPointCount, PathClipType = m_PathClipType; - m_PathPointCount = 0; - m_PathClipType = 0; - if (PathPointCount <= 1) { - if (PathPointCount && PathClipType) { - CPDF_Path path; - path.New()->AppendRect(0, 0, 0, 0); - m_pCurStates->m_ClipPath.AppendPath(path, FXFILL_WINDING, TRUE); - } - return; - } - if (PathPointCount && m_pPathPoints[PathPointCount - 1].m_Flag == FXPT_MOVETO) { - PathPointCount --; - } - CPDF_Path Path; - CFX_PathData* pPathData = Path.New(); - pPathData->SetPointCount(PathPointCount); - FXSYS_memcpy(pPathData->GetPoints(), m_pPathPoints, sizeof(FX_PATHPOINT) * PathPointCount); - CFX_AffineMatrix matrix = m_pCurStates->m_CTM; - matrix.Concat(m_mtContentToUser); - if (bStroke || FillType) { - CPDF_PathObject* pPathObj = new CPDF_PathObject; - pPathObj->m_bStroke = bStroke; - pPathObj->m_FillType = FillType; - pPathObj->m_Path = Path; - pPathObj->m_Matrix = matrix; - SetGraphicStates(pPathObj, TRUE, FALSE, TRUE); - pPathObj->CalcBoundingBox(); - m_pObjectList->m_ObjectList.AddTail(pPathObj); - } - if (PathClipType) { - if (!matrix.IsIdentity()) { - Path.Transform(&matrix); - matrix.SetIdentity(); - } - m_pCurStates->m_ClipPath.AppendPath(Path, PathClipType, TRUE); - } -} -CFX_ByteString _FPDF_ByteStringFromHex(CFX_BinaryBuf& src_buf) -{ - CFX_ByteTextBuf buf; - FX_BOOL bFirst = TRUE; - int code = 0; - const uint8_t* str = src_buf.GetBuffer(); - FX_DWORD size = src_buf.GetSize(); - for (FX_DWORD i = 0; i < size; i ++) { - uint8_t ch = str[i]; - if (ch >= '0' && ch <= '9') { - if (bFirst) { - code = (ch - '0') * 16; - } else { - code += ch - '0'; - buf.AppendChar((char)code); - } - bFirst = !bFirst; - } else if (ch >= 'A' && ch <= 'F') { - if (bFirst) { - code = (ch - 'A' + 10) * 16; - } else { - code += ch - 'A' + 10; - buf.AppendChar((char)code); - } - bFirst = !bFirst; - } else if (ch >= 'a' && ch <= 'f') { - if (bFirst) { - code = (ch - 'a' + 10) * 16; - } else { - code += ch - 'a' + 10; - buf.AppendChar((char)code); - } - bFirst = !bFirst; - } - } - if (!bFirst) { + m_pCurStates->m_TextY -= + FXSYS_Mul(fInitKerning, m_pCurStates->m_TextState.GetFontSize()) / + 1000; + } + } + if (nsegs == 0) { + return; + } + int textmode; + if (pFont->GetFontType() == PDFFONT_TYPE3) { + textmode = 0; + } else { + textmode = m_pCurStates->m_TextState.GetObject()->m_TextMode; + } + CPDF_TextObject* pText = new CPDF_TextObject; + m_pLastTextObject = pText; + SetGraphicStates(pText, TRUE, TRUE, TRUE); + if (textmode && textmode != 3 && textmode != 4 && textmode != 7) { + FX_FLOAT* pCTM = pText->m_TextState.GetModify()->m_CTM; + pCTM[0] = m_pCurStates->m_CTM.a; + pCTM[1] = m_pCurStates->m_CTM.c; + pCTM[2] = m_pCurStates->m_CTM.b; + pCTM[3] = m_pCurStates->m_CTM.d; + } + pText->SetSegments(pStrs, pKerning, nsegs); + pText->m_PosX = m_pCurStates->m_TextX; + pText->m_PosY = m_pCurStates->m_TextY + m_pCurStates->m_TextRise; + ConvertTextSpace(pText->m_PosX, pText->m_PosY); + FX_FLOAT x_advance, y_advance; + pText->CalcPositionData(&x_advance, &y_advance, m_pCurStates->m_TextHorzScale, + m_Level); + m_pCurStates->m_TextX += x_advance; + m_pCurStates->m_TextY += y_advance; + if (textmode > 3) { + CPDF_TextObject* pCopy = new CPDF_TextObject; + pCopy->Copy(pText); + m_ClipTextList.Add(pCopy); + } + m_pObjectList->m_ObjectList.AddTail(pText); + if (pKerning && pKerning[nsegs - 1] != 0) { + if (!pFont->IsVertWriting()) { + m_pCurStates->m_TextX -= + FXSYS_Mul(pKerning[nsegs - 1], + m_pCurStates->m_TextState.GetFontSize()) / + 1000; + } else { + m_pCurStates->m_TextY -= + FXSYS_Mul(pKerning[nsegs - 1], + m_pCurStates->m_TextState.GetFontSize()) / + 1000; + } + } +} +void CPDF_StreamContentParser::Handle_ShowText() { + CFX_ByteString str = GetString(0); + if (str.IsEmpty()) { + return; + } + AddTextObject(&str, 0, NULL, 1); +} +void CPDF_StreamContentParser::Handle_ShowText_Positioning() { + CPDF_Array* pArray = GetObject(0) ? GetObject(0)->GetArray() : NULL; + if (pArray == NULL) { + return; + } + int n = pArray->GetCount(), nsegs = 0, i; + for (i = 0; i < n; i++) { + CPDF_Object* pObj = pArray->GetElementValue(i); + if (pObj->GetType() == PDFOBJ_STRING) { + nsegs++; + } + } + if (nsegs == 0) { + for (i = 0; i < n; i++) { + m_pCurStates->m_TextX -= + FXSYS_Mul(pArray->GetNumber(i), + m_pCurStates->m_TextState.GetFontSize()) / + 1000; + }; + return; + } + CFX_ByteString* pStrs = new CFX_ByteString[nsegs]; + FX_FLOAT* pKerning = FX_Alloc(FX_FLOAT, nsegs); + int iSegment = 0; + FX_FLOAT fInitKerning = 0; + for (i = 0; i < n; i++) { + CPDF_Object* pObj = pArray->GetElementValue(i); + if (pObj->GetType() == PDFOBJ_STRING) { + CFX_ByteString str = pObj->GetString(); + if (str.IsEmpty()) { + continue; + } + pStrs[iSegment] = str; + pKerning[iSegment++] = 0; + } else { + FX_FLOAT num = pObj ? pObj->GetNumber() : 0; + if (iSegment == 0) { + fInitKerning += num; + } else { + pKerning[iSegment - 1] += num; + } + } + } + AddTextObject(pStrs, fInitKerning, pKerning, iSegment); + delete[] pStrs; + FX_Free(pKerning); +} +void CPDF_StreamContentParser::Handle_SetTextLeading() { + m_pCurStates->m_TextLeading = GetNumber(0); +} +void CPDF_StreamContentParser::Handle_SetTextMatrix() { + m_pCurStates->m_TextMatrix.Set(GetNumber16(5), GetNumber16(4), GetNumber16(3), + GetNumber16(2), GetNumber(1), GetNumber(0)); + OnChangeTextMatrix(); + m_pCurStates->m_TextX = 0; + m_pCurStates->m_TextY = 0; + m_pCurStates->m_TextLineX = 0; + m_pCurStates->m_TextLineY = 0; +} +void CPDF_StreamContentParser::OnChangeTextMatrix() { + CFX_AffineMatrix text_matrix(m_pCurStates->m_TextHorzScale, 0.0f, 0.0f, 1.0f, + 0.0f, 0.0f); + text_matrix.Concat(m_pCurStates->m_TextMatrix); + text_matrix.Concat(m_pCurStates->m_CTM); + text_matrix.Concat(m_mtContentToUser); + FX_FLOAT* pTextMatrix = m_pCurStates->m_TextState.GetModify()->m_Matrix; + pTextMatrix[0] = text_matrix.a; + pTextMatrix[1] = text_matrix.c; + pTextMatrix[2] = text_matrix.b; + pTextMatrix[3] = text_matrix.d; +} +void CPDF_StreamContentParser::Handle_SetTextRenderMode() { + int mode = GetInteger(0); + if (mode < 0 || mode > 7) { + return; + } + m_pCurStates->m_TextState.GetModify()->m_TextMode = mode; +} +void CPDF_StreamContentParser::Handle_SetTextRise() { + m_pCurStates->m_TextRise = GetNumber(0); +} +void CPDF_StreamContentParser::Handle_SetWordSpace() { + m_pCurStates->m_TextState.GetModify()->m_WordSpace = GetNumber(0); +} +void CPDF_StreamContentParser::Handle_SetHorzScale() { + if (m_ParamCount != 1) { + return; + } + m_pCurStates->m_TextHorzScale = GetNumber(0) / 100; + OnChangeTextMatrix(); +} +void CPDF_StreamContentParser::Handle_MoveToNextLine() { + m_pCurStates->m_TextLineY -= m_pCurStates->m_TextLeading; + m_pCurStates->m_TextX = m_pCurStates->m_TextLineX; + m_pCurStates->m_TextY = m_pCurStates->m_TextLineY; +} +void CPDF_StreamContentParser::Handle_CurveTo_23() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathPoint(m_PathCurrentX, m_PathCurrentY, FXPT_BEZIERTO); + AddPathPoint(GetNumber(3), GetNumber(2), FXPT_BEZIERTO); + AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); +} +void CPDF_StreamContentParser::Handle_SetLineWidth() { + FX_FLOAT width = GetNumber(0); + m_pCurStates->m_GraphState.GetModify()->m_LineWidth = width; +} +void CPDF_StreamContentParser::Handle_Clip() { + m_PathClipType = FXFILL_WINDING; +} +void CPDF_StreamContentParser::Handle_EOClip() { + m_PathClipType = FXFILL_ALTERNATE; +} +void CPDF_StreamContentParser::Handle_CurveTo_13() { + if (m_Options.m_bTextOnly) { + return; + } + AddPathPoint(GetNumber(3), GetNumber(2), FXPT_BEZIERTO); + AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); + AddPathPoint(GetNumber(1), GetNumber(0), FXPT_BEZIERTO); +} +void CPDF_StreamContentParser::Handle_NextLineShowText() { + Handle_MoveToNextLine(); + Handle_ShowText(); +} +void CPDF_StreamContentParser::Handle_NextLineShowText_Space() { + m_pCurStates->m_TextState.GetModify()->m_WordSpace = GetNumber(2); + m_pCurStates->m_TextState.GetModify()->m_CharSpace = GetNumber(1); + Handle_NextLineShowText(); +} +void CPDF_StreamContentParser::Handle_Invalid() {} +void CPDF_StreamContentParser::AddPathPoint(FX_FLOAT x, FX_FLOAT y, int flag) { + m_PathCurrentX = x; + m_PathCurrentY = y; + if (flag == FXPT_MOVETO) { + m_PathStartX = x; + m_PathStartY = y; + if (m_PathPointCount && + m_pPathPoints[m_PathPointCount - 1].m_Flag == FXPT_MOVETO) { + m_pPathPoints[m_PathPointCount - 1].m_PointX = x; + m_pPathPoints[m_PathPointCount - 1].m_PointY = y; + return; + } + } else if (m_PathPointCount == 0) { + return; + } + m_PathPointCount++; + if (m_PathPointCount > m_PathAllocSize) { + int newsize = m_PathPointCount + 256; + FX_PATHPOINT* pNewPoints = FX_Alloc(FX_PATHPOINT, newsize); + if (m_PathAllocSize) { + FXSYS_memcpy(pNewPoints, m_pPathPoints, + m_PathAllocSize * sizeof(FX_PATHPOINT)); + FX_Free(m_pPathPoints); + } + m_pPathPoints = pNewPoints; + m_PathAllocSize = newsize; + } + m_pPathPoints[m_PathPointCount - 1].m_Flag = flag; + m_pPathPoints[m_PathPointCount - 1].m_PointX = x; + m_pPathPoints[m_PathPointCount - 1].m_PointY = y; +} +void CPDF_StreamContentParser::AddPathObject(int FillType, FX_BOOL bStroke) { + int PathPointCount = m_PathPointCount, PathClipType = m_PathClipType; + m_PathPointCount = 0; + m_PathClipType = 0; + if (PathPointCount <= 1) { + if (PathPointCount && PathClipType) { + CPDF_Path path; + path.New()->AppendRect(0, 0, 0, 0); + m_pCurStates->m_ClipPath.AppendPath(path, FXFILL_WINDING, TRUE); + } + return; + } + if (PathPointCount && + m_pPathPoints[PathPointCount - 1].m_Flag == FXPT_MOVETO) { + PathPointCount--; + } + CPDF_Path Path; + CFX_PathData* pPathData = Path.New(); + pPathData->SetPointCount(PathPointCount); + FXSYS_memcpy(pPathData->GetPoints(), m_pPathPoints, + sizeof(FX_PATHPOINT) * PathPointCount); + CFX_AffineMatrix matrix = m_pCurStates->m_CTM; + matrix.Concat(m_mtContentToUser); + if (bStroke || FillType) { + CPDF_PathObject* pPathObj = new CPDF_PathObject; + pPathObj->m_bStroke = bStroke; + pPathObj->m_FillType = FillType; + pPathObj->m_Path = Path; + pPathObj->m_Matrix = matrix; + SetGraphicStates(pPathObj, TRUE, FALSE, TRUE); + pPathObj->CalcBoundingBox(); + m_pObjectList->m_ObjectList.AddTail(pPathObj); + } + if (PathClipType) { + if (!matrix.IsIdentity()) { + Path.Transform(&matrix); + matrix.SetIdentity(); + } + m_pCurStates->m_ClipPath.AppendPath(Path, PathClipType, TRUE); + } +} +CFX_ByteString _FPDF_ByteStringFromHex(CFX_BinaryBuf& src_buf) { + CFX_ByteTextBuf buf; + FX_BOOL bFirst = TRUE; + int code = 0; + const uint8_t* str = src_buf.GetBuffer(); + FX_DWORD size = src_buf.GetSize(); + for (FX_DWORD i = 0; i < size; i++) { + uint8_t ch = str[i]; + if (ch >= '0' && ch <= '9') { + if (bFirst) { + code = (ch - '0') * 16; + } else { + code += ch - '0'; buf.AppendChar((char)code); - } - return buf.GetByteString(); + } + bFirst = !bFirst; + } else if (ch >= 'A' && ch <= 'F') { + if (bFirst) { + code = (ch - 'A' + 10) * 16; + } else { + code += ch - 'A' + 10; + buf.AppendChar((char)code); + } + bFirst = !bFirst; + } else if (ch >= 'a' && ch <= 'f') { + if (bFirst) { + code = (ch - 'a' + 10) * 16; + } else { + code += ch - 'a' + 10; + buf.AppendChar((char)code); + } + bFirst = !bFirst; + } + } + if (!bFirst) { + buf.AppendChar((char)code); + } + return buf.GetByteString(); } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_parser_old.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_parser_old.cpp index b2cfce73d9..78169614bd 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_parser_old.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_parser_old.cpp @@ -18,1118 +18,1168 @@ const FX_CHAR* const _PDF_OpCharType = "IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII" "IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII" "IIIIIIIIIIIIIIIIIIIIIIIIIIIIIIII"; -FX_BOOL _PDF_HasInvalidOpChar(const FX_CHAR* op) -{ - if(!op) { - return FALSE; - } - uint8_t ch; - while((ch = *op++)) { - if(_PDF_OpCharType[ch] == 'I') { - return TRUE; - } - } +FX_BOOL _PDF_HasInvalidOpChar(const FX_CHAR* op) { + if (!op) { return FALSE; + } + uint8_t ch; + while ((ch = *op++)) { + if (_PDF_OpCharType[ch] == 'I') { + return TRUE; + } + } + return FALSE; } class CPDF_StreamParserAutoClearer { - public: - CPDF_StreamParserAutoClearer(CPDF_StreamParser** scoped_variable, CPDF_StreamParser* new_parser) - : scoped_variable_(scoped_variable) { - *scoped_variable_ = new_parser; - } - ~CPDF_StreamParserAutoClearer() { *scoped_variable_ = NULL; } - private: - CPDF_StreamParser** scoped_variable_; + public: + CPDF_StreamParserAutoClearer(CPDF_StreamParser** scoped_variable, + CPDF_StreamParser* new_parser) + : scoped_variable_(scoped_variable) { + *scoped_variable_ = new_parser; + } + ~CPDF_StreamParserAutoClearer() { *scoped_variable_ = NULL; } + + private: + CPDF_StreamParser** scoped_variable_; }; -FX_DWORD CPDF_StreamContentParser::Parse(const uint8_t* pData, FX_DWORD dwSize, FX_DWORD max_cost) -{ - if (m_Level > _FPDF_MAX_FORM_LEVEL_) { - return dwSize; - } - FX_DWORD InitObjCount = m_pObjectList->CountObjects(); - CPDF_StreamParser syntax(pData, dwSize); - CPDF_StreamParserAutoClearer auto_clearer(&m_pSyntax, &syntax); - m_CompatCount = 0; - while (1) { - FX_DWORD cost = m_pObjectList->CountObjects() - InitObjCount; - if (max_cost && cost >= max_cost) { - break; - } - switch (syntax.ParseNextElement()) { - case CPDF_StreamParser::EndOfData: - return m_pSyntax->GetPos(); - case CPDF_StreamParser::Keyword: - if(!OnOperator((char*)syntax.GetWordBuf()) && _PDF_HasInvalidOpChar((char*)syntax.GetWordBuf())) { - m_bAbort = TRUE; - } - if (m_bAbort) { - return m_pSyntax->GetPos(); - } - ClearAllParams(); - break; - case CPDF_StreamParser::Number: - AddNumberParam((char*)syntax.GetWordBuf(), syntax.GetWordSize()); - break; - case CPDF_StreamParser::Name: - AddNameParam((const FX_CHAR*)syntax.GetWordBuf() + 1, syntax.GetWordSize() - 1); - break; - default: - AddObjectParam(syntax.GetObject()); - } - } - return m_pSyntax->GetPos(); +FX_DWORD CPDF_StreamContentParser::Parse(const uint8_t* pData, + FX_DWORD dwSize, + FX_DWORD max_cost) { + if (m_Level > _FPDF_MAX_FORM_LEVEL_) { + return dwSize; + } + FX_DWORD InitObjCount = m_pObjectList->CountObjects(); + CPDF_StreamParser syntax(pData, dwSize); + CPDF_StreamParserAutoClearer auto_clearer(&m_pSyntax, &syntax); + m_CompatCount = 0; + while (1) { + FX_DWORD cost = m_pObjectList->CountObjects() - InitObjCount; + if (max_cost && cost >= max_cost) { + break; + } + switch (syntax.ParseNextElement()) { + case CPDF_StreamParser::EndOfData: + return m_pSyntax->GetPos(); + case CPDF_StreamParser::Keyword: + if (!OnOperator((char*)syntax.GetWordBuf()) && + _PDF_HasInvalidOpChar((char*)syntax.GetWordBuf())) { + m_bAbort = TRUE; + } + if (m_bAbort) { + return m_pSyntax->GetPos(); + } + ClearAllParams(); + break; + case CPDF_StreamParser::Number: + AddNumberParam((char*)syntax.GetWordBuf(), syntax.GetWordSize()); + break; + case CPDF_StreamParser::Name: + AddNameParam((const FX_CHAR*)syntax.GetWordBuf() + 1, + syntax.GetWordSize() - 1); + break; + default: + AddObjectParam(syntax.GetObject()); + } + } + return m_pSyntax->GetPos(); } void _PDF_ReplaceAbbr(CPDF_Object* pObj); -void CPDF_StreamContentParser::Handle_BeginImage() -{ - FX_FILESIZE savePos = m_pSyntax->GetPos(); - CPDF_Dictionary* pDict = CPDF_Dictionary::Create(); - while (1) { - CPDF_StreamParser::SyntaxType type = m_pSyntax->ParseNextElement(); - if (type == CPDF_StreamParser::Keyword) { - CFX_ByteString bsKeyword(m_pSyntax->GetWordBuf(), m_pSyntax->GetWordSize()); - if (bsKeyword != FX_BSTRC("ID")) { - m_pSyntax->SetPos(savePos); - pDict->Release(); - return; - } - } - if (type != CPDF_StreamParser::Name) { - break; - } - CFX_ByteString key((const FX_CHAR*)m_pSyntax->GetWordBuf() + 1, m_pSyntax->GetWordSize() - 1); - CPDF_Object* pObj = m_pSyntax->ReadNextObject(); - if (!key.IsEmpty()) { - pDict->SetAt(key, pObj, m_pDocument); - } else if (pObj) { - pObj->Release(); - } - } - _PDF_ReplaceAbbr(pDict); - CPDF_Object* pCSObj = NULL; - if (pDict->KeyExist(FX_BSTRC("ColorSpace"))) { - pCSObj = pDict->GetElementValue(FX_BSTRC("ColorSpace")); - if (pCSObj->GetType() == PDFOBJ_NAME) { - CFX_ByteString name = pCSObj->GetString(); - if (name != FX_BSTRC("DeviceRGB") && name != FX_BSTRC("DeviceGray") && name != FX_BSTRC("DeviceCMYK")) { - pCSObj = FindResourceObj(FX_BSTRC("ColorSpace"), name); - if (pCSObj && !pCSObj->GetObjNum()) { - pCSObj = pCSObj->Clone(); - pDict->SetAt(FX_BSTRC("ColorSpace"), pCSObj, m_pDocument); - } - } - } - } - CPDF_Stream* pStream = m_pSyntax->ReadInlineStream(m_pDocument, pDict, pCSObj, m_Options.m_bDecodeInlineImage); - while (1) { - CPDF_StreamParser::SyntaxType type = m_pSyntax->ParseNextElement(); - if (type == CPDF_StreamParser::EndOfData) { - break; - } - if (type != CPDF_StreamParser::Keyword) { - continue; - } - if (m_pSyntax->GetWordSize() == 2 && m_pSyntax->GetWordBuf()[0] == 'E' && - m_pSyntax->GetWordBuf()[1] == 'I') { - break; - } - } - if (m_Options.m_bTextOnly) { - if (pStream) { - pStream->Release(); - } else { - pDict->Release(); - } +void CPDF_StreamContentParser::Handle_BeginImage() { + FX_FILESIZE savePos = m_pSyntax->GetPos(); + CPDF_Dictionary* pDict = CPDF_Dictionary::Create(); + while (1) { + CPDF_StreamParser::SyntaxType type = m_pSyntax->ParseNextElement(); + if (type == CPDF_StreamParser::Keyword) { + CFX_ByteString bsKeyword(m_pSyntax->GetWordBuf(), + m_pSyntax->GetWordSize()); + if (bsKeyword != FX_BSTRC("ID")) { + m_pSyntax->SetPos(savePos); + pDict->Release(); return; + } + } + if (type != CPDF_StreamParser::Name) { + break; + } + CFX_ByteString key((const FX_CHAR*)m_pSyntax->GetWordBuf() + 1, + m_pSyntax->GetWordSize() - 1); + CPDF_Object* pObj = m_pSyntax->ReadNextObject(); + if (!key.IsEmpty()) { + pDict->SetAt(key, pObj, m_pDocument); + } else if (pObj) { + pObj->Release(); + } + } + _PDF_ReplaceAbbr(pDict); + CPDF_Object* pCSObj = NULL; + if (pDict->KeyExist(FX_BSTRC("ColorSpace"))) { + pCSObj = pDict->GetElementValue(FX_BSTRC("ColorSpace")); + if (pCSObj->GetType() == PDFOBJ_NAME) { + CFX_ByteString name = pCSObj->GetString(); + if (name != FX_BSTRC("DeviceRGB") && name != FX_BSTRC("DeviceGray") && + name != FX_BSTRC("DeviceCMYK")) { + pCSObj = FindResourceObj(FX_BSTRC("ColorSpace"), name); + if (pCSObj && !pCSObj->GetObjNum()) { + pCSObj = pCSObj->Clone(); + pDict->SetAt(FX_BSTRC("ColorSpace"), pCSObj, m_pDocument); + } + } + } + } + CPDF_Stream* pStream = m_pSyntax->ReadInlineStream( + m_pDocument, pDict, pCSObj, m_Options.m_bDecodeInlineImage); + while (1) { + CPDF_StreamParser::SyntaxType type = m_pSyntax->ParseNextElement(); + if (type == CPDF_StreamParser::EndOfData) { + break; + } + if (type != CPDF_StreamParser::Keyword) { + continue; + } + if (m_pSyntax->GetWordSize() == 2 && m_pSyntax->GetWordBuf()[0] == 'E' && + m_pSyntax->GetWordBuf()[1] == 'I') { + break; + } + } + if (m_Options.m_bTextOnly) { + if (pStream) { + pStream->Release(); + } else { + pDict->Release(); + } + return; + } + pDict->SetAtName(FX_BSTRC("Subtype"), FX_BSTRC("Image")); + CPDF_ImageObject* pImgObj = AddImage(pStream, NULL, TRUE); + if (!pImgObj) { + if (pStream) { + pStream->Release(); + } else { + pDict->Release(); } - pDict->SetAtName(FX_BSTRC("Subtype"), FX_BSTRC("Image")); - CPDF_ImageObject *pImgObj = AddImage(pStream, NULL, TRUE); - if (!pImgObj) { - if (pStream) { - pStream->Release(); - } else { - pDict->Release(); - } - } + } } -void CPDF_StreamContentParser::ParsePathObject() -{ - FX_FLOAT params[6] = {}; - int nParams = 0; - int last_pos = m_pSyntax->GetPos(); - while (1) { - CPDF_StreamParser::SyntaxType type = m_pSyntax->ParseNextElement(); - FX_BOOL bProcessed = TRUE; - switch (type) { - case CPDF_StreamParser::EndOfData: - return; - case CPDF_StreamParser::Keyword: { - int len = m_pSyntax->GetWordSize(); - if (len == 1) { - switch (m_pSyntax->GetWordBuf()[0]) { - case 'm': - AddPathPoint(params[0], params[1], FXPT_MOVETO); - nParams = 0; - break; - case 'l': - AddPathPoint(params[0], params[1], FXPT_LINETO); - nParams = 0; - break; - case 'c': - AddPathPoint(params[0], params[1], FXPT_BEZIERTO); - AddPathPoint(params[2], params[3], FXPT_BEZIERTO); - AddPathPoint(params[4], params[5], FXPT_BEZIERTO); - nParams = 0; - break; - case 'v': - AddPathPoint(m_PathCurrentX, m_PathCurrentY, FXPT_BEZIERTO); - AddPathPoint(params[0], params[1], FXPT_BEZIERTO); - AddPathPoint(params[2], params[3], FXPT_BEZIERTO); - nParams = 0; - break; - case 'y': - AddPathPoint(params[0], params[1], FXPT_BEZIERTO); - AddPathPoint(params[2], params[3], FXPT_BEZIERTO); - AddPathPoint(params[2], params[3], FXPT_BEZIERTO); - nParams = 0; - break; - case 'h': - Handle_ClosePath(); - nParams = 0; - break; - default: - bProcessed = FALSE; - break; - } - } else if (len == 2) { - if (m_pSyntax->GetWordBuf()[0] == 'r' && m_pSyntax->GetWordBuf()[1] == 'e') { - AddPathRect(params[0], params[1], params[2], params[3]); - nParams = 0; - } else { - bProcessed = FALSE; - } - } else { - bProcessed = FALSE; - } - if (bProcessed) { - last_pos = m_pSyntax->GetPos(); - } - break; - } - case CPDF_StreamParser::Number: { - if (nParams == 6) { - break; - } - FX_BOOL bInteger; - int value; - FX_atonum(CFX_ByteStringC(m_pSyntax->GetWordBuf(), m_pSyntax->GetWordSize()), bInteger, &value); - params[nParams++] = bInteger ? (FX_FLOAT)value : *(FX_FLOAT*)&value; - break; - } +void CPDF_StreamContentParser::ParsePathObject() { + FX_FLOAT params[6] = {}; + int nParams = 0; + int last_pos = m_pSyntax->GetPos(); + while (1) { + CPDF_StreamParser::SyntaxType type = m_pSyntax->ParseNextElement(); + FX_BOOL bProcessed = TRUE; + switch (type) { + case CPDF_StreamParser::EndOfData: + return; + case CPDF_StreamParser::Keyword: { + int len = m_pSyntax->GetWordSize(); + if (len == 1) { + switch (m_pSyntax->GetWordBuf()[0]) { + case 'm': + AddPathPoint(params[0], params[1], FXPT_MOVETO); + nParams = 0; + break; + case 'l': + AddPathPoint(params[0], params[1], FXPT_LINETO); + nParams = 0; + break; + case 'c': + AddPathPoint(params[0], params[1], FXPT_BEZIERTO); + AddPathPoint(params[2], params[3], FXPT_BEZIERTO); + AddPathPoint(params[4], params[5], FXPT_BEZIERTO); + nParams = 0; + break; + case 'v': + AddPathPoint(m_PathCurrentX, m_PathCurrentY, FXPT_BEZIERTO); + AddPathPoint(params[0], params[1], FXPT_BEZIERTO); + AddPathPoint(params[2], params[3], FXPT_BEZIERTO); + nParams = 0; + break; + case 'y': + AddPathPoint(params[0], params[1], FXPT_BEZIERTO); + AddPathPoint(params[2], params[3], FXPT_BEZIERTO); + AddPathPoint(params[2], params[3], FXPT_BEZIERTO); + nParams = 0; + break; + case 'h': + Handle_ClosePath(); + nParams = 0; + break; default: - bProcessed = FALSE; - } - if (!bProcessed) { - m_pSyntax->SetPos(last_pos); - return; - } - } + bProcessed = FALSE; + break; + } + } else if (len == 2) { + if (m_pSyntax->GetWordBuf()[0] == 'r' && + m_pSyntax->GetWordBuf()[1] == 'e') { + AddPathRect(params[0], params[1], params[2], params[3]); + nParams = 0; + } else { + bProcessed = FALSE; + } + } else { + bProcessed = FALSE; + } + if (bProcessed) { + last_pos = m_pSyntax->GetPos(); + } + break; + } + case CPDF_StreamParser::Number: { + if (nParams == 6) { + break; + } + FX_BOOL bInteger; + int value; + FX_atonum( + CFX_ByteStringC(m_pSyntax->GetWordBuf(), m_pSyntax->GetWordSize()), + bInteger, &value); + params[nParams++] = bInteger ? (FX_FLOAT)value : *(FX_FLOAT*)&value; + break; + } + default: + bProcessed = FALSE; + } + if (!bProcessed) { + m_pSyntax->SetPos(last_pos); + return; + } + } } -CPDF_StreamParser::CPDF_StreamParser(const uint8_t* pData, FX_DWORD dwSize) -{ - m_pBuf = pData; - m_Size = dwSize; - m_Pos = 0; - m_pLastObj = NULL; +CPDF_StreamParser::CPDF_StreamParser(const uint8_t* pData, FX_DWORD dwSize) { + m_pBuf = pData; + m_Size = dwSize; + m_Pos = 0; + m_pLastObj = NULL; } -CPDF_StreamParser::~CPDF_StreamParser() -{ - if (m_pLastObj) { - m_pLastObj->Release(); - } +CPDF_StreamParser::~CPDF_StreamParser() { + if (m_pLastObj) { + m_pLastObj->Release(); + } } -FX_DWORD _DecodeAllScanlines(ICodec_ScanlineDecoder* pDecoder, uint8_t*& dest_buf, FX_DWORD& dest_size) -{ - if (pDecoder == NULL) { - return (FX_DWORD) - 1; - } - int ncomps = pDecoder->CountComps(); - int bpc = pDecoder->GetBPC(); - int width = pDecoder->GetWidth(); - int height = pDecoder->GetHeight(); - int pitch = (width * ncomps * bpc + 7) / 8; - if (height == 0 || pitch > (1 << 30) / height) { - delete pDecoder; - return -1; - } - dest_buf = FX_Alloc2D(uint8_t, pitch, height); - dest_size = pitch * height; // Safe since checked alloc returned. - for (int row = 0; row < height; row ++) { - uint8_t* pLine = pDecoder->GetScanline(row); - if (pLine == NULL) { - break; - } - FXSYS_memcpy(dest_buf + row * pitch, pLine, pitch); - } - FX_DWORD srcoff = pDecoder->GetSrcOffset(); +FX_DWORD _DecodeAllScanlines(ICodec_ScanlineDecoder* pDecoder, + uint8_t*& dest_buf, + FX_DWORD& dest_size) { + if (pDecoder == NULL) { + return (FX_DWORD)-1; + } + int ncomps = pDecoder->CountComps(); + int bpc = pDecoder->GetBPC(); + int width = pDecoder->GetWidth(); + int height = pDecoder->GetHeight(); + int pitch = (width * ncomps * bpc + 7) / 8; + if (height == 0 || pitch > (1 << 30) / height) { delete pDecoder; - return srcoff; + return -1; + } + dest_buf = FX_Alloc2D(uint8_t, pitch, height); + dest_size = pitch * height; // Safe since checked alloc returned. + for (int row = 0; row < height; row++) { + uint8_t* pLine = pDecoder->GetScanline(row); + if (pLine == NULL) { + break; + } + FXSYS_memcpy(dest_buf + row * pitch, pLine, pitch); + } + FX_DWORD srcoff = pDecoder->GetSrcOffset(); + delete pDecoder; + return srcoff; } -ICodec_ScanlineDecoder* FPDFAPI_CreateFaxDecoder(const uint8_t* src_buf, FX_DWORD src_size, int width, int height, - const CPDF_Dictionary* pParams); -FX_DWORD _A85Decode(const uint8_t* src_buf, FX_DWORD src_size, uint8_t*& dest_buf, FX_DWORD& dest_size); -FX_DWORD _HexDecode(const uint8_t* src_buf, FX_DWORD src_size, uint8_t*& dest_buf, FX_DWORD& dest_size); -FX_DWORD FPDFAPI_FlateOrLZWDecode(FX_BOOL bLZW, const uint8_t* src_buf, FX_DWORD src_size, CPDF_Dictionary* pParams, - FX_DWORD estimated_size, uint8_t*& dest_buf, FX_DWORD& dest_size); -FX_DWORD PDF_DecodeInlineStream(const uint8_t* src_buf, FX_DWORD limit, - int width, int height, CFX_ByteString& decoder, - CPDF_Dictionary* pParam, uint8_t*& dest_buf, FX_DWORD& dest_size) -{ - if (decoder == FX_BSTRC("CCITTFaxDecode") || decoder == FX_BSTRC("CCF")) { - ICodec_ScanlineDecoder* pDecoder = FPDFAPI_CreateFaxDecoder(src_buf, limit, width, height, pParam); - return _DecodeAllScanlines(pDecoder, dest_buf, dest_size); - } - if (decoder == FX_BSTRC("ASCII85Decode") || decoder == FX_BSTRC("A85")) { - return _A85Decode(src_buf, limit, dest_buf, dest_size); - } - if (decoder == FX_BSTRC("ASCIIHexDecode") || decoder == FX_BSTRC("AHx")) { - return _HexDecode(src_buf, limit, dest_buf, dest_size); - } - if (decoder == FX_BSTRC("FlateDecode") || decoder == FX_BSTRC("Fl")) { - return FPDFAPI_FlateOrLZWDecode(FALSE, src_buf, limit, pParam, dest_size, dest_buf, dest_size); - } - if (decoder == FX_BSTRC("LZWDecode") || decoder == FX_BSTRC("LZW")) { - return FPDFAPI_FlateOrLZWDecode(TRUE, src_buf, limit, pParam, 0, dest_buf, dest_size); - } - if (decoder == FX_BSTRC("DCTDecode") || decoder == FX_BSTRC("DCT")) { - ICodec_ScanlineDecoder* pDecoder = CPDF_ModuleMgr::Get()->GetJpegModule()->CreateDecoder( - src_buf, limit, width, height, 0, pParam ? pParam->GetInteger(FX_BSTRC("ColorTransform"), 1) : 1); - return _DecodeAllScanlines(pDecoder, dest_buf, dest_size); - } - if (decoder == FX_BSTRC("RunLengthDecode") || decoder == FX_BSTRC("RL")) { - return RunLengthDecode(src_buf, limit, dest_buf, dest_size); - } - dest_size = 0; - dest_buf = 0; - return (FX_DWORD) - 1; +ICodec_ScanlineDecoder* FPDFAPI_CreateFaxDecoder( + const uint8_t* src_buf, + FX_DWORD src_size, + int width, + int height, + const CPDF_Dictionary* pParams); +FX_DWORD _A85Decode(const uint8_t* src_buf, + FX_DWORD src_size, + uint8_t*& dest_buf, + FX_DWORD& dest_size); +FX_DWORD _HexDecode(const uint8_t* src_buf, + FX_DWORD src_size, + uint8_t*& dest_buf, + FX_DWORD& dest_size); +FX_DWORD FPDFAPI_FlateOrLZWDecode(FX_BOOL bLZW, + const uint8_t* src_buf, + FX_DWORD src_size, + CPDF_Dictionary* pParams, + FX_DWORD estimated_size, + uint8_t*& dest_buf, + FX_DWORD& dest_size); +FX_DWORD PDF_DecodeInlineStream(const uint8_t* src_buf, + FX_DWORD limit, + int width, + int height, + CFX_ByteString& decoder, + CPDF_Dictionary* pParam, + uint8_t*& dest_buf, + FX_DWORD& dest_size) { + if (decoder == FX_BSTRC("CCITTFaxDecode") || decoder == FX_BSTRC("CCF")) { + ICodec_ScanlineDecoder* pDecoder = + FPDFAPI_CreateFaxDecoder(src_buf, limit, width, height, pParam); + return _DecodeAllScanlines(pDecoder, dest_buf, dest_size); + } + if (decoder == FX_BSTRC("ASCII85Decode") || decoder == FX_BSTRC("A85")) { + return _A85Decode(src_buf, limit, dest_buf, dest_size); + } + if (decoder == FX_BSTRC("ASCIIHexDecode") || decoder == FX_BSTRC("AHx")) { + return _HexDecode(src_buf, limit, dest_buf, dest_size); + } + if (decoder == FX_BSTRC("FlateDecode") || decoder == FX_BSTRC("Fl")) { + return FPDFAPI_FlateOrLZWDecode(FALSE, src_buf, limit, pParam, dest_size, + dest_buf, dest_size); + } + if (decoder == FX_BSTRC("LZWDecode") || decoder == FX_BSTRC("LZW")) { + return FPDFAPI_FlateOrLZWDecode(TRUE, src_buf, limit, pParam, 0, dest_buf, + dest_size); + } + if (decoder == FX_BSTRC("DCTDecode") || decoder == FX_BSTRC("DCT")) { + ICodec_ScanlineDecoder* pDecoder = + CPDF_ModuleMgr::Get()->GetJpegModule()->CreateDecoder( + src_buf, limit, width, height, 0, + pParam ? pParam->GetInteger(FX_BSTRC("ColorTransform"), 1) : 1); + return _DecodeAllScanlines(pDecoder, dest_buf, dest_size); + } + if (decoder == FX_BSTRC("RunLengthDecode") || decoder == FX_BSTRC("RL")) { + return RunLengthDecode(src_buf, limit, dest_buf, dest_size); + } + dest_size = 0; + dest_buf = 0; + return (FX_DWORD)-1; } -CPDF_Stream* CPDF_StreamParser::ReadInlineStream(CPDF_Document* pDoc, CPDF_Dictionary* pDict, CPDF_Object* pCSObj, FX_BOOL bDecode) -{ - if (m_Pos == m_Size) { - return NULL; - } - if (PDF_CharType[m_pBuf[m_Pos]] == 'W') { - m_Pos ++; - } - CFX_ByteString Decoder; - CPDF_Dictionary* pParam = NULL; - CPDF_Object* pFilter = pDict->GetElementValue(FX_BSTRC("Filter")); - if (pFilter == NULL) { - } else if (pFilter->GetType() == PDFOBJ_ARRAY) { - Decoder = ((CPDF_Array*)pFilter)->GetString(0); +CPDF_Stream* CPDF_StreamParser::ReadInlineStream(CPDF_Document* pDoc, + CPDF_Dictionary* pDict, + CPDF_Object* pCSObj, + FX_BOOL bDecode) { + if (m_Pos == m_Size) { + return NULL; + } + if (PDF_CharType[m_pBuf[m_Pos]] == 'W') { + m_Pos++; + } + CFX_ByteString Decoder; + CPDF_Dictionary* pParam = NULL; + CPDF_Object* pFilter = pDict->GetElementValue(FX_BSTRC("Filter")); + if (pFilter == NULL) { + } else if (pFilter->GetType() == PDFOBJ_ARRAY) { + Decoder = ((CPDF_Array*)pFilter)->GetString(0); + CPDF_Array* pParams = pDict->GetArray(FX_BSTRC("DecodeParms")); + if (pParams) { + pParam = pParams->GetDict(0); + } + } else { + Decoder = pFilter->GetString(); + pParam = pDict->GetDict(FX_BSTRC("DecodeParms")); + } + FX_DWORD width = pDict->GetInteger(FX_BSTRC("Width")); + FX_DWORD height = pDict->GetInteger(FX_BSTRC("Height")); + FX_DWORD OrigSize = 0; + if (pCSObj != NULL) { + FX_DWORD bpc = pDict->GetInteger(FX_BSTRC("BitsPerComponent")); + FX_DWORD nComponents = 1; + CPDF_ColorSpace* pCS = pDoc->LoadColorSpace(pCSObj); + if (pCS == NULL) { + nComponents = 3; + } else { + nComponents = pCS->CountComponents(); + pDoc->GetPageData()->ReleaseColorSpace(pCSObj); + } + FX_DWORD pitch = width; + if (bpc && pitch > INT_MAX / bpc) { + return NULL; + } + pitch *= bpc; + if (nComponents && pitch > INT_MAX / nComponents) { + return NULL; + } + pitch *= nComponents; + if (pitch > INT_MAX - 7) { + return NULL; + } + pitch += 7; + pitch /= 8; + OrigSize = pitch; + } else { + if (width > INT_MAX - 7) { + return NULL; + } + OrigSize = ((width + 7) / 8); + } + if (height && OrigSize > INT_MAX / height) { + return NULL; + } + OrigSize *= height; + uint8_t* pData = NULL; + FX_DWORD dwStreamSize; + if (Decoder.IsEmpty()) { + if (OrigSize > m_Size - m_Pos) { + OrigSize = m_Size - m_Pos; + } + pData = FX_Alloc(uint8_t, OrigSize); + FXSYS_memcpy(pData, m_pBuf + m_Pos, OrigSize); + dwStreamSize = OrigSize; + m_Pos += OrigSize; + } else { + FX_DWORD dwDestSize = OrigSize; + dwStreamSize = + PDF_DecodeInlineStream(m_pBuf + m_Pos, m_Size - m_Pos, width, height, + Decoder, pParam, pData, dwDestSize); + if ((int)dwStreamSize < 0) { + return NULL; + } + if (bDecode) { + m_Pos += dwStreamSize; + dwStreamSize = dwDestSize; + if (pFilter->GetType() == PDFOBJ_ARRAY) { + ((CPDF_Array*)pFilter)->RemoveAt(0); CPDF_Array* pParams = pDict->GetArray(FX_BSTRC("DecodeParms")); if (pParams) { - pParam = pParams->GetDict(0); + pParams->RemoveAt(0); } + } else { + pDict->RemoveAt(FX_BSTRC("Filter")); + pDict->RemoveAt(FX_BSTRC("DecodeParms")); + } } else { - Decoder = pFilter->GetString(); - pParam = pDict->GetDict(FX_BSTRC("DecodeParms")); - } - FX_DWORD width = pDict->GetInteger(FX_BSTRC("Width")); - FX_DWORD height = pDict->GetInteger(FX_BSTRC("Height")); - FX_DWORD OrigSize = 0; - if (pCSObj != NULL) { - FX_DWORD bpc = pDict->GetInteger(FX_BSTRC("BitsPerComponent")); - FX_DWORD nComponents = 1; - CPDF_ColorSpace* pCS = pDoc->LoadColorSpace(pCSObj); - if (pCS == NULL) { - nComponents = 3; - } else { - nComponents = pCS->CountComponents(); - pDoc->GetPageData()->ReleaseColorSpace(pCSObj); - } - FX_DWORD pitch = width; - if (bpc && pitch > INT_MAX / bpc) { - return NULL; - } - pitch *= bpc; - if (nComponents && pitch > INT_MAX / nComponents) { - return NULL; - } - pitch *= nComponents; - if (pitch > INT_MAX - 7) { - return NULL; - } - pitch += 7; - pitch /= 8; - OrigSize = pitch; - } else { - if (width > INT_MAX - 7) { - return NULL; - } - OrigSize = ((width + 7) / 8); - } - if (height && OrigSize > INT_MAX / height) { - return NULL; - } - OrigSize *= height; - uint8_t* pData = NULL; - FX_DWORD dwStreamSize; - if (Decoder.IsEmpty()) { - if (OrigSize > m_Size - m_Pos) { - OrigSize = m_Size - m_Pos; - } - pData = FX_Alloc(uint8_t, OrigSize); - FXSYS_memcpy(pData, m_pBuf + m_Pos, OrigSize); - dwStreamSize = OrigSize; - m_Pos += OrigSize; - } else { - FX_DWORD dwDestSize = OrigSize; - dwStreamSize = PDF_DecodeInlineStream(m_pBuf + m_Pos, m_Size - m_Pos, width, height, Decoder, pParam, - pData, dwDestSize); - if ((int)dwStreamSize < 0) { - return NULL; - } - if (bDecode) { - m_Pos += dwStreamSize; - dwStreamSize = dwDestSize; - if (pFilter->GetType() == PDFOBJ_ARRAY) { - ((CPDF_Array*)pFilter)->RemoveAt(0); - CPDF_Array* pParams = pDict->GetArray(FX_BSTRC("DecodeParms")); - if (pParams) { - pParams->RemoveAt(0); - } - } else { - pDict->RemoveAt(FX_BSTRC("Filter")); - pDict->RemoveAt(FX_BSTRC("DecodeParms")); - } - } else { - if (pData) { - FX_Free(pData); - } - FX_DWORD dwSavePos = m_Pos; - m_Pos += dwStreamSize; - while (1) { - FX_DWORD dwPrevPos = m_Pos; - CPDF_StreamParser::SyntaxType type = ParseNextElement(); - if (type == CPDF_StreamParser::EndOfData) { - break; - } - if (type != CPDF_StreamParser::Keyword) { - dwStreamSize += m_Pos - dwPrevPos; - continue; - } - if (GetWordSize() == 2 && GetWordBuf()[0] == 'E' && - GetWordBuf()[1] == 'I') { - m_Pos = dwPrevPos; - break; - } - dwStreamSize += m_Pos - dwPrevPos; - } - m_Pos = dwSavePos; - pData = FX_Alloc(uint8_t, dwStreamSize); - FXSYS_memcpy(pData, m_pBuf + m_Pos, dwStreamSize); - m_Pos += dwStreamSize; + if (pData) { + FX_Free(pData); + } + FX_DWORD dwSavePos = m_Pos; + m_Pos += dwStreamSize; + while (1) { + FX_DWORD dwPrevPos = m_Pos; + CPDF_StreamParser::SyntaxType type = ParseNextElement(); + if (type == CPDF_StreamParser::EndOfData) { + break; } - } - pDict->SetAtInteger(FX_BSTRC("Length"), (int)dwStreamSize); - return CPDF_Stream::Create(pData, dwStreamSize, pDict); + if (type != CPDF_StreamParser::Keyword) { + dwStreamSize += m_Pos - dwPrevPos; + continue; + } + if (GetWordSize() == 2 && GetWordBuf()[0] == 'E' && + GetWordBuf()[1] == 'I') { + m_Pos = dwPrevPos; + break; + } + dwStreamSize += m_Pos - dwPrevPos; + } + m_Pos = dwSavePos; + pData = FX_Alloc(uint8_t, dwStreamSize); + FXSYS_memcpy(pData, m_pBuf + m_Pos, dwStreamSize); + m_Pos += dwStreamSize; + } + } + pDict->SetAtInteger(FX_BSTRC("Length"), (int)dwStreamSize); + return CPDF_Stream::Create(pData, dwStreamSize, pDict); } #define MAX_WORD_BUFFER 256 -#define MAX_STRING_LENGTH 32767 +#define MAX_STRING_LENGTH 32767 #define FXDWORD_TRUE FXDWORD_FROM_LSBFIRST(0x65757274) #define FXDWORD_NULL FXDWORD_FROM_LSBFIRST(0x6c6c756e) #define FXDWORD_FALS FXDWORD_FROM_LSBFIRST(0x736c6166) -CPDF_StreamParser::SyntaxType CPDF_StreamParser::ParseNextElement() -{ - if (m_pLastObj) { - m_pLastObj->Release(); - m_pLastObj = NULL; - } - m_WordSize = 0; - FX_BOOL bIsNumber = TRUE; - if (m_Pos >= m_Size) { +CPDF_StreamParser::SyntaxType CPDF_StreamParser::ParseNextElement() { + if (m_pLastObj) { + m_pLastObj->Release(); + m_pLastObj = NULL; + } + m_WordSize = 0; + FX_BOOL bIsNumber = TRUE; + if (m_Pos >= m_Size) { + return EndOfData; + } + int ch = m_pBuf[m_Pos++]; + int type = PDF_CharType[ch]; + while (1) { + while (type == 'W') { + if (m_Size <= m_Pos) { return EndOfData; + } + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; + } + if (ch != '%') { + break; } - int ch = m_pBuf[m_Pos++]; - int type = PDF_CharType[ch]; while (1) { - while (type == 'W') { - if (m_Size <= m_Pos) { - return EndOfData; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - } - if (ch != '%') { - break; - } - while (1) { - if (m_Size <= m_Pos) { - return EndOfData; - } - ch = m_pBuf[m_Pos++]; - if (ch == '\r' || ch == '\n') { - break; - } - } - type = PDF_CharType[ch]; + if (m_Size <= m_Pos) { + return EndOfData; + } + ch = m_pBuf[m_Pos++]; + if (ch == '\r' || ch == '\n') { + break; + } + } + type = PDF_CharType[ch]; + } + if (type == 'D' && ch != '/') { + m_Pos--; + m_pLastObj = ReadNextObject(); + return Others; + } + while (1) { + if (m_WordSize < MAX_WORD_BUFFER) { + m_WordBuffer[m_WordSize++] = ch; + } + if (type != 'N') { + bIsNumber = FALSE; + } + if (m_Size <= m_Pos) { + break; + } + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; + if (type == 'D' || type == 'W') { + m_Pos--; + break; + } + } + m_WordBuffer[m_WordSize] = 0; + if (bIsNumber) { + return Number; + } + if (m_WordBuffer[0] == '/') { + return Name; + } + if (m_WordSize == 4) { + if (*(FX_DWORD*)m_WordBuffer == FXDWORD_TRUE) { + m_pLastObj = CPDF_Boolean::Create(TRUE); + return Others; + } + if (*(FX_DWORD*)m_WordBuffer == FXDWORD_NULL) { + m_pLastObj = CPDF_Null::Create(); + return Others; + } + } else if (m_WordSize == 5) { + if (*(FX_DWORD*)m_WordBuffer == FXDWORD_FALS && m_WordBuffer[4] == 'e') { + m_pLastObj = CPDF_Boolean::Create(FALSE); + return Others; + } + } + return Keyword; +} +void CPDF_StreamParser::SkipPathObject() { + FX_DWORD command_startpos = m_Pos; + if (m_Pos >= m_Size) { + return; + } + int ch = m_pBuf[m_Pos++]; + int type = PDF_CharType[ch]; + while (1) { + while (type == 'W') { + if (m_Pos >= m_Size) { + return; + } + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; } - if (type == 'D' && ch != '/') { - m_Pos --; - m_pLastObj = ReadNextObject(); - return Others; + if (type != 'N') { + m_Pos = command_startpos; + return; } while (1) { - if (m_WordSize < MAX_WORD_BUFFER) { - m_WordBuffer[m_WordSize++] = ch; - } - if (type != 'N') { - bIsNumber = FALSE; - } - if (m_Size <= m_Pos) { - break; + while (type != 'W') { + if (m_Pos >= m_Size) { + return; } ch = m_pBuf[m_Pos++]; type = PDF_CharType[ch]; - if (type == 'D' || type == 'W') { - m_Pos --; - break; - } - } - m_WordBuffer[m_WordSize] = 0; - if (bIsNumber) { - return Number; - } - if (m_WordBuffer[0] == '/') { - return Name; - } - if (m_WordSize == 4) { - if (*(FX_DWORD*)m_WordBuffer == FXDWORD_TRUE) { - m_pLastObj = CPDF_Boolean::Create(TRUE); - return Others; + } + while (type == 'W') { + if (m_Pos >= m_Size) { + return; } - if (*(FX_DWORD*)m_WordBuffer == FXDWORD_NULL) { - m_pLastObj = CPDF_Null::Create(); - return Others; - } - } else if (m_WordSize == 5) { - if (*(FX_DWORD*)m_WordBuffer == FXDWORD_FALS && m_WordBuffer[4] == 'e') { - m_pLastObj = CPDF_Boolean::Create(FALSE); - return Others; + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; + } + if (type == 'N') { + continue; + } + FX_DWORD op_startpos = m_Pos - 1; + while (type != 'W' && type != 'D') { + if (m_Pos >= m_Size) { + return; } - } - return Keyword; + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; + } + if (m_Pos - op_startpos == 2) { + int op = m_pBuf[op_startpos]; + if (op == 'm' || op == 'l' || op == 'c' || op == 'v' || op == 'y') { + command_startpos = m_Pos; + break; + } + } else if (m_Pos - op_startpos == 3) { + if (m_pBuf[op_startpos] == 'r' && m_pBuf[op_startpos + 1] == 'e') { + command_startpos = m_Pos; + break; + } + } + m_Pos = command_startpos; + return; + } + } } -void CPDF_StreamParser::SkipPathObject() -{ - FX_DWORD command_startpos = m_Pos; - if (m_Pos >= m_Size) { - return; +CPDF_Object* CPDF_StreamParser::ReadNextObject(FX_BOOL bAllowNestedArray, + FX_BOOL bInArray) { + FX_BOOL bIsNumber; + GetNextWord(bIsNumber); + if (m_WordSize == 0) { + return NULL; + } + if (bIsNumber) { + m_WordBuffer[m_WordSize] = 0; + return CPDF_Number::Create(CFX_ByteStringC(m_WordBuffer, m_WordSize)); + } + int first_char = m_WordBuffer[0]; + if (first_char == '/') { + return CPDF_Name::Create( + PDF_NameDecode(CFX_ByteStringC(m_WordBuffer + 1, m_WordSize - 1))); + } + if (first_char == '(') { + return CPDF_String::Create(ReadString()); + } + if (first_char == '<') { + if (m_WordSize == 1) { + return CPDF_String::Create(ReadHexString(), TRUE); } - int ch = m_pBuf[m_Pos++]; - int type = PDF_CharType[ch]; + CPDF_Dictionary* pDict = CPDF_Dictionary::Create(); while (1) { - while (type == 'W') { - if (m_Pos >= m_Size) { - return; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - } - if (type != 'N') { - m_Pos = command_startpos; - return; - } - while (1) { - while (type != 'W') { - if (m_Pos >= m_Size) { - return; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - } - while (type == 'W') { - if (m_Pos >= m_Size) { - return; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - } - if (type == 'N') { - continue; - } - FX_DWORD op_startpos = m_Pos - 1; - while (type != 'W' && type != 'D') { - if (m_Pos >= m_Size) { - return; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - } - if (m_Pos - op_startpos == 2) { - int op = m_pBuf[op_startpos]; - if (op == 'm' || op == 'l' || op == 'c' || op == 'v' || op == 'y') { - command_startpos = m_Pos; - break; - } - } else if (m_Pos - op_startpos == 3) { - if (m_pBuf[op_startpos] == 'r' && m_pBuf[op_startpos + 1] == 'e') { - command_startpos = m_Pos; - break; - } - } - m_Pos = command_startpos; - return; + GetNextWord(bIsNumber); + if (m_WordSize == 0) { + pDict->Release(); + return NULL; + } + if (m_WordSize == 2 && m_WordBuffer[0] == '>') { + break; + } + if (m_WordBuffer[0] != '/') { + pDict->Release(); + return NULL; + } + CFX_ByteString key = + PDF_NameDecode(CFX_ByteStringC(m_WordBuffer + 1, m_WordSize - 1)); + CPDF_Object* pObj = ReadNextObject(TRUE); + if (pObj == NULL) { + if (pDict) { + pDict->Release(); } - } -} -CPDF_Object* CPDF_StreamParser::ReadNextObject(FX_BOOL bAllowNestedArray, FX_BOOL bInArray) -{ - FX_BOOL bIsNumber; - GetNextWord(bIsNumber); - if (m_WordSize == 0) { return NULL; - } - if (bIsNumber) { - m_WordBuffer[m_WordSize] = 0; - return CPDF_Number::Create(CFX_ByteStringC(m_WordBuffer, m_WordSize)); - } - int first_char = m_WordBuffer[0]; - if (first_char == '/') { - return CPDF_Name::Create(PDF_NameDecode(CFX_ByteStringC(m_WordBuffer + 1, m_WordSize - 1))); - } - if (first_char == '(') { - return CPDF_String::Create(ReadString()); - } - if (first_char == '<') { - if (m_WordSize == 1) { - return CPDF_String::Create(ReadHexString(), TRUE); + } + if (!key.IsEmpty()) { + pDict->SetAt(key, pObj); + } else { + pObj->Release(); + } + } + return pDict; + } + if (first_char == '[') { + if (!bAllowNestedArray && bInArray) { + return NULL; + } + CPDF_Array* pArray = CPDF_Array::Create(); + while (1) { + CPDF_Object* pObj = ReadNextObject(bAllowNestedArray, TRUE); + if (pObj == NULL) { + if (m_WordSize == 0 || m_WordBuffer[0] == ']') { + return pArray; } - CPDF_Dictionary* pDict = CPDF_Dictionary::Create(); - while (1) { - GetNextWord(bIsNumber); - if (m_WordSize == 0) { - pDict->Release(); - return NULL; - } - if (m_WordSize == 2 && m_WordBuffer[0] == '>') { - break; - } - if (m_WordBuffer[0] != '/') { - pDict->Release(); - return NULL; - } - CFX_ByteString key = PDF_NameDecode(CFX_ByteStringC(m_WordBuffer + 1, m_WordSize - 1)); - CPDF_Object* pObj = ReadNextObject(TRUE); - if (pObj == NULL) { - if (pDict) { - pDict->Release(); - } - return NULL; - } - if (!key.IsEmpty()) { - pDict->SetAt(key, pObj); - } else { - pObj->Release(); - } + if (m_WordBuffer[0] == '[') { + continue; } - return pDict; + } else { + pArray->Add(pObj); + } } - if (first_char == '[') { - if (!bAllowNestedArray && bInArray) { - return NULL; - } - CPDF_Array* pArray = CPDF_Array::Create(); - while (1) { - CPDF_Object* pObj = ReadNextObject(bAllowNestedArray, TRUE); - if (pObj == NULL) { - if (m_WordSize == 0 || m_WordBuffer[0] == ']') { - return pArray; - } - if (m_WordBuffer[0] == '[') { - continue; - } - } else { - pArray->Add(pObj); - } - } + } + if (m_WordSize == 4) { + if (*(FX_DWORD*)m_WordBuffer == FXDWORD_TRUE) { + return CPDF_Boolean::Create(TRUE); } - if (m_WordSize == 4) { - if (*(FX_DWORD*)m_WordBuffer == FXDWORD_TRUE) { - return CPDF_Boolean::Create(TRUE); - } - if (*(FX_DWORD*)m_WordBuffer == FXDWORD_NULL) { - return CPDF_Null::Create(); - } - } else if (m_WordSize == 5) { - if (*(FX_DWORD*)m_WordBuffer == FXDWORD_FALS && m_WordBuffer[4] == 'e') { - return CPDF_Boolean::Create(FALSE); - } + if (*(FX_DWORD*)m_WordBuffer == FXDWORD_NULL) { + return CPDF_Null::Create(); } - return NULL; + } else if (m_WordSize == 5) { + if (*(FX_DWORD*)m_WordBuffer == FXDWORD_FALS && m_WordBuffer[4] == 'e') { + return CPDF_Boolean::Create(FALSE); + } + } + return NULL; } -void CPDF_StreamParser::GetNextWord(FX_BOOL& bIsNumber) -{ - m_WordSize = 0; - bIsNumber = TRUE; - if (m_Size <= m_Pos) { +void CPDF_StreamParser::GetNextWord(FX_BOOL& bIsNumber) { + m_WordSize = 0; + bIsNumber = TRUE; + if (m_Size <= m_Pos) { + return; + } + int ch = m_pBuf[m_Pos++]; + int type = PDF_CharType[ch]; + while (1) { + while (type == 'W') { + if (m_Size <= m_Pos) { return; + } + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; } - int ch = m_pBuf[m_Pos++]; - int type = PDF_CharType[ch]; - while (1) { - while (type == 'W') { - if (m_Size <= m_Pos) { - return; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - } - if (ch != '%') { - break; - } - while (1) { - if (m_Size <= m_Pos) { - return; - } - ch = m_pBuf[m_Pos++]; - if (ch == '\r' || ch == '\n') { - break; - } - } - type = PDF_CharType[ch]; - } - if (type == 'D') { - bIsNumber = FALSE; - m_WordBuffer[m_WordSize++] = ch; - if (ch == '/') { - while (1) { - if (m_Size <= m_Pos) { - return; - } - ch = m_pBuf[m_Pos++]; - type = PDF_CharType[ch]; - if (type != 'R' && type != 'N') { - m_Pos --; - return; - } - if (m_WordSize < MAX_WORD_BUFFER) { - m_WordBuffer[m_WordSize++] = ch; - } - } - } else if (ch == '<') { - if (m_Size <= m_Pos) { - return; - } - ch = m_pBuf[m_Pos++]; - if (ch == '<') { - m_WordBuffer[m_WordSize++] = ch; - } else { - m_Pos --; - } - } else if (ch == '>') { - if (m_Size <= m_Pos) { - return; - } - ch = m_pBuf[m_Pos++]; - if (ch == '>') { - m_WordBuffer[m_WordSize++] = ch; - } else { - m_Pos --; - } - } - return; + if (ch != '%') { + break; } while (1) { - if (m_WordSize < MAX_WORD_BUFFER) { - m_WordBuffer[m_WordSize++] = ch; - } - if (type != 'N') { - bIsNumber = FALSE; - } + if (m_Size <= m_Pos) { + return; + } + ch = m_pBuf[m_Pos++]; + if (ch == '\r' || ch == '\n') { + break; + } + } + type = PDF_CharType[ch]; + } + if (type == 'D') { + bIsNumber = FALSE; + m_WordBuffer[m_WordSize++] = ch; + if (ch == '/') { + while (1) { if (m_Size <= m_Pos) { - return; + return; } ch = m_pBuf[m_Pos++]; type = PDF_CharType[ch]; - if (type == 'D' || type == 'W') { - m_Pos --; - break; + if (type != 'R' && type != 'N') { + m_Pos--; + return; } - } -} -CFX_ByteString CPDF_StreamParser::ReadString() -{ - if (m_Size <= m_Pos) { - return CFX_ByteString(); - } - int ch = m_pBuf[m_Pos++]; - CFX_ByteTextBuf buf; - int parlevel = 0; - int status = 0, iEscCode = 0; - while (1) { - switch (status) { - case 0: - if (ch == ')') { - if (parlevel == 0) { - if (buf.GetLength() > MAX_STRING_LENGTH) { - return CFX_ByteString(buf.GetBuffer(), MAX_STRING_LENGTH); - } - return buf.GetByteString(); - } - parlevel --; - buf.AppendChar(')'); - } else if (ch == '(') { - parlevel ++; - buf.AppendChar('('); - } else if (ch == '\\') { - status = 1; - } else { - buf.AppendChar((char)ch); - } - break; - case 1: - if (ch >= '0' && ch <= '7') { - iEscCode = ch - '0'; - status = 2; - break; - } - if (ch == 'n') { - buf.AppendChar('\n'); - } else if (ch == 'r') { - buf.AppendChar('\r'); - } else if (ch == 't') { - buf.AppendChar('\t'); - } else if (ch == 'b') { - buf.AppendChar('\b'); - } else if (ch == 'f') { - buf.AppendChar('\f'); - } else if (ch == '\r') { - status = 4; - break; - } else if (ch == '\n') { - } else { - buf.AppendChar(ch); - } - status = 0; - break; - case 2: - if (ch >= '0' && ch <= '7') { - iEscCode = iEscCode * 8 + ch - '0'; - status = 3; - } else { - buf.AppendChar(iEscCode); - status = 0; - continue; - } - break; - case 3: - if (ch >= '0' && ch <= '7') { - iEscCode = iEscCode * 8 + ch - '0'; - buf.AppendChar(iEscCode); - status = 0; - } else { - buf.AppendChar(iEscCode); - status = 0; - continue; - } - break; - case 4: - status = 0; - if (ch != '\n') { - continue; - } - break; - } - if (m_Size <= m_Pos) { - break; + if (m_WordSize < MAX_WORD_BUFFER) { + m_WordBuffer[m_WordSize++] = ch; } - ch = m_pBuf[m_Pos++]; + } + } else if (ch == '<') { + if (m_Size <= m_Pos) { + return; + } + ch = m_pBuf[m_Pos++]; + if (ch == '<') { + m_WordBuffer[m_WordSize++] = ch; + } else { + m_Pos--; + } + } else if (ch == '>') { + if (m_Size <= m_Pos) { + return; + } + ch = m_pBuf[m_Pos++]; + if (ch == '>') { + m_WordBuffer[m_WordSize++] = ch; + } else { + m_Pos--; + } } - if (m_Size > m_Pos) { - ch = m_pBuf[m_Pos++]; + return; + } + while (1) { + if (m_WordSize < MAX_WORD_BUFFER) { + m_WordBuffer[m_WordSize++] = ch; } - if (buf.GetLength() > MAX_STRING_LENGTH) { - return CFX_ByteString(buf.GetBuffer(), MAX_STRING_LENGTH); + if (type != 'N') { + bIsNumber = FALSE; } - return buf.GetByteString(); -} -CFX_ByteString CPDF_StreamParser::ReadHexString() -{ if (m_Size <= m_Pos) { - return CFX_ByteString(); + return; } - int ch = m_pBuf[m_Pos++]; - CFX_ByteTextBuf buf; - FX_BOOL bFirst = TRUE; - int code = 0; - while (1) { - if (ch == '>') { - break; - } - if (ch >= '0' && ch <= '9') { - if (bFirst) { - code = (ch - '0') * 16; - } else { - code += ch - '0'; - buf.AppendChar((char)code); - } - bFirst = !bFirst; - } else if (ch >= 'A' && ch <= 'F') { - if (bFirst) { - code = (ch - 'A' + 10) * 16; - } else { - code += ch - 'A' + 10; - buf.AppendChar((char)code); - } - bFirst = !bFirst; - } else if (ch >= 'a' && ch <= 'f') { - if (bFirst) { - code = (ch - 'a' + 10) * 16; - } else { - code += ch - 'a' + 10; - buf.AppendChar((char)code); + ch = m_pBuf[m_Pos++]; + type = PDF_CharType[ch]; + if (type == 'D' || type == 'W') { + m_Pos--; + break; + } + } +} +CFX_ByteString CPDF_StreamParser::ReadString() { + if (m_Size <= m_Pos) { + return CFX_ByteString(); + } + int ch = m_pBuf[m_Pos++]; + CFX_ByteTextBuf buf; + int parlevel = 0; + int status = 0, iEscCode = 0; + while (1) { + switch (status) { + case 0: + if (ch == ')') { + if (parlevel == 0) { + if (buf.GetLength() > MAX_STRING_LENGTH) { + return CFX_ByteString(buf.GetBuffer(), MAX_STRING_LENGTH); } - bFirst = !bFirst; + return buf.GetByteString(); + } + parlevel--; + buf.AppendChar(')'); + } else if (ch == '(') { + parlevel++; + buf.AppendChar('('); + } else if (ch == '\\') { + status = 1; + } else { + buf.AppendChar((char)ch); + } + break; + case 1: + if (ch >= '0' && ch <= '7') { + iEscCode = ch - '0'; + status = 2; + break; + } + if (ch == 'n') { + buf.AppendChar('\n'); + } else if (ch == 'r') { + buf.AppendChar('\r'); + } else if (ch == 't') { + buf.AppendChar('\t'); + } else if (ch == 'b') { + buf.AppendChar('\b'); + } else if (ch == 'f') { + buf.AppendChar('\f'); + } else if (ch == '\r') { + status = 4; + break; + } else if (ch == '\n') { + } else { + buf.AppendChar(ch); + } + status = 0; + break; + case 2: + if (ch >= '0' && ch <= '7') { + iEscCode = iEscCode * 8 + ch - '0'; + status = 3; + } else { + buf.AppendChar(iEscCode); + status = 0; + continue; + } + break; + case 3: + if (ch >= '0' && ch <= '7') { + iEscCode = iEscCode * 8 + ch - '0'; + buf.AppendChar(iEscCode); + status = 0; + } else { + buf.AppendChar(iEscCode); + status = 0; + continue; } - if (m_Size <= m_Pos) { - break; + break; + case 4: + status = 0; + if (ch != '\n') { + continue; } - ch = m_pBuf[m_Pos++]; + break; } - if (!bFirst) { + if (m_Size <= m_Pos) { + break; + } + ch = m_pBuf[m_Pos++]; + } + if (m_Size > m_Pos) { + ch = m_pBuf[m_Pos++]; + } + if (buf.GetLength() > MAX_STRING_LENGTH) { + return CFX_ByteString(buf.GetBuffer(), MAX_STRING_LENGTH); + } + return buf.GetByteString(); +} +CFX_ByteString CPDF_StreamParser::ReadHexString() { + if (m_Size <= m_Pos) { + return CFX_ByteString(); + } + int ch = m_pBuf[m_Pos++]; + CFX_ByteTextBuf buf; + FX_BOOL bFirst = TRUE; + int code = 0; + while (1) { + if (ch == '>') { + break; + } + if (ch >= '0' && ch <= '9') { + if (bFirst) { + code = (ch - '0') * 16; + } else { + code += ch - '0'; buf.AppendChar((char)code); + } + bFirst = !bFirst; + } else if (ch >= 'A' && ch <= 'F') { + if (bFirst) { + code = (ch - 'A' + 10) * 16; + } else { + code += ch - 'A' + 10; + buf.AppendChar((char)code); + } + bFirst = !bFirst; + } else if (ch >= 'a' && ch <= 'f') { + if (bFirst) { + code = (ch - 'a' + 10) * 16; + } else { + code += ch - 'a' + 10; + buf.AppendChar((char)code); + } + bFirst = !bFirst; } - if (buf.GetLength() > MAX_STRING_LENGTH) { - return CFX_ByteString(buf.GetBuffer(), MAX_STRING_LENGTH); - } - return buf.GetByteString(); -} -#define PAGEPARSE_STAGE_GETCONTENT 1 -#define PAGEPARSE_STAGE_PARSE 2 -#define PAGEPARSE_STAGE_CHECKCLIP 3 -CPDF_ContentParser::CPDF_ContentParser() -{ - m_pParser = NULL; - m_pStreamArray = NULL; - m_pSingleStream = NULL; - m_pData = NULL; - m_Status = Ready; - m_pType3Char = NULL; + if (m_Size <= m_Pos) { + break; + } + ch = m_pBuf[m_Pos++]; + } + if (!bFirst) { + buf.AppendChar((char)code); + } + if (buf.GetLength() > MAX_STRING_LENGTH) { + return CFX_ByteString(buf.GetBuffer(), MAX_STRING_LENGTH); + } + return buf.GetByteString(); } -CPDF_ContentParser::~CPDF_ContentParser() -{ - Clear(); +#define PAGEPARSE_STAGE_GETCONTENT 1 +#define PAGEPARSE_STAGE_PARSE 2 +#define PAGEPARSE_STAGE_CHECKCLIP 3 +CPDF_ContentParser::CPDF_ContentParser() { + m_pParser = NULL; + m_pStreamArray = NULL; + m_pSingleStream = NULL; + m_pData = NULL; + m_Status = Ready; + m_pType3Char = NULL; } -void CPDF_ContentParser::Clear() -{ - delete m_pParser; - delete m_pSingleStream; - if (m_pStreamArray) { - for (FX_DWORD i = 0; i < m_nStreams; i ++) - delete m_pStreamArray[i]; - FX_Free(m_pStreamArray); - } - if (m_pData && m_pSingleStream == NULL) { - FX_Free((void*)m_pData); - } - m_pParser = NULL; - m_pStreamArray = NULL; - m_pSingleStream = NULL; - m_pData = NULL; - m_Status = Ready; +CPDF_ContentParser::~CPDF_ContentParser() { + Clear(); } -void CPDF_ContentParser::Start(CPDF_Page* pPage, CPDF_ParseOptions* pOptions) -{ - if (m_Status != Ready || pPage == NULL || pPage->m_pDocument == NULL || pPage->m_pFormDict == NULL) { - m_Status = Done; - return; - } - m_pObjects = pPage; - m_bForm = FALSE; - if (pOptions) { - m_Options = *pOptions; - } - m_Status = ToBeContinued; - m_InternalStage = PAGEPARSE_STAGE_GETCONTENT; - m_CurrentOffset = 0; - CPDF_Object* pContent = pPage->m_pFormDict->GetElementValue(FX_BSTRC("Contents")); - if (pContent == NULL) { - m_Status = Done; - return; - } - if (pContent->GetType() == PDFOBJ_STREAM) { - m_nStreams = 0; - m_pSingleStream = new CPDF_StreamAcc; - m_pSingleStream->LoadAllData((CPDF_Stream*)pContent, FALSE); - } else if (pContent->GetType() == PDFOBJ_ARRAY) { - CPDF_Array* pArray = (CPDF_Array*)pContent; - m_nStreams = pArray->GetCount(); - if (m_nStreams == 0) { - m_Status = Done; - return; - } - m_pStreamArray = FX_Alloc(CPDF_StreamAcc*, m_nStreams); - } else { - m_Status = Done; - return; - } +void CPDF_ContentParser::Clear() { + delete m_pParser; + delete m_pSingleStream; + if (m_pStreamArray) { + for (FX_DWORD i = 0; i < m_nStreams; i++) + delete m_pStreamArray[i]; + FX_Free(m_pStreamArray); + } + if (m_pData && m_pSingleStream == NULL) { + FX_Free((void*)m_pData); + } + m_pParser = NULL; + m_pStreamArray = NULL; + m_pSingleStream = NULL; + m_pData = NULL; + m_Status = Ready; } -void CPDF_ContentParser::Start(CPDF_Form* pForm, CPDF_AllStates* pGraphicStates, - CFX_AffineMatrix* pParentMatrix, CPDF_Type3Char* pType3Char, CPDF_ParseOptions* pOptions, int level) -{ - m_pType3Char = pType3Char; - m_pObjects = pForm; - m_bForm = TRUE; - CFX_AffineMatrix form_matrix = pForm->m_pFormDict->GetMatrix(FX_BSTRC("Matrix")); - if (pGraphicStates) { - form_matrix.Concat(pGraphicStates->m_CTM); - } - CPDF_Array* pBBox = pForm->m_pFormDict->GetArray(FX_BSTRC("BBox")); - CFX_FloatRect form_bbox; - CPDF_Path ClipPath; - if (pBBox) { - form_bbox = pBBox->GetRect(); - ClipPath.New(); - ClipPath.AppendRect(form_bbox.left, form_bbox.bottom, form_bbox.right, form_bbox.top); - ClipPath.Transform(&form_matrix); - if (pParentMatrix) { - ClipPath.Transform(pParentMatrix); - } - form_bbox.Transform(&form_matrix); - if (pParentMatrix) { - form_bbox.Transform(pParentMatrix); - } - } - CPDF_Dictionary* pResources = pForm->m_pFormDict->GetDict(FX_BSTRC("Resources")); - m_pParser = new CPDF_StreamContentParser( - pForm->m_pDocument, pForm->m_pPageResources, pForm->m_pResources, - pParentMatrix, pForm, pResources, &form_bbox, pOptions, pGraphicStates, - level); - - m_pParser->GetCurStates()->m_CTM = form_matrix; - m_pParser->GetCurStates()->m_ParentMatrix = form_matrix; - if (ClipPath.NotNull()) { - m_pParser->GetCurStates()->m_ClipPath.AppendPath(ClipPath, FXFILL_WINDING, TRUE); - } - if (pForm->m_Transparency & PDFTRANS_GROUP) { - CPDF_GeneralStateData* pData = m_pParser->GetCurStates()->m_GeneralState.GetModify(); - pData->m_BlendType = FXDIB_BLEND_NORMAL; - pData->m_StrokeAlpha = 1.0f; - pData->m_FillAlpha = 1.0f; - pData->m_pSoftMask = NULL; - } +void CPDF_ContentParser::Start(CPDF_Page* pPage, CPDF_ParseOptions* pOptions) { + if (m_Status != Ready || pPage == NULL || pPage->m_pDocument == NULL || + pPage->m_pFormDict == NULL) { + m_Status = Done; + return; + } + m_pObjects = pPage; + m_bForm = FALSE; + if (pOptions) { + m_Options = *pOptions; + } + m_Status = ToBeContinued; + m_InternalStage = PAGEPARSE_STAGE_GETCONTENT; + m_CurrentOffset = 0; + CPDF_Object* pContent = + pPage->m_pFormDict->GetElementValue(FX_BSTRC("Contents")); + if (pContent == NULL) { + m_Status = Done; + return; + } + if (pContent->GetType() == PDFOBJ_STREAM) { m_nStreams = 0; m_pSingleStream = new CPDF_StreamAcc; - if (pForm->m_pDocument) { - m_pSingleStream->LoadAllData(pForm->m_pFormStream, FALSE); - } else { - m_pSingleStream->LoadAllData(pForm->m_pFormStream, FALSE); - } - m_pData = (uint8_t*)m_pSingleStream->GetData(); - m_Size = m_pSingleStream->GetSize(); - m_Status = ToBeContinued; - m_InternalStage = PAGEPARSE_STAGE_PARSE; - m_CurrentOffset = 0; + m_pSingleStream->LoadAllData((CPDF_Stream*)pContent, FALSE); + } else if (pContent->GetType() == PDFOBJ_ARRAY) { + CPDF_Array* pArray = (CPDF_Array*)pContent; + m_nStreams = pArray->GetCount(); + if (m_nStreams == 0) { + m_Status = Done; + return; + } + m_pStreamArray = FX_Alloc(CPDF_StreamAcc*, m_nStreams); + } else { + m_Status = Done; + return; + } } -void CPDF_ContentParser::Continue(IFX_Pause* pPause) -{ - int steps = 0; - while (m_Status == ToBeContinued) { - if (m_InternalStage == PAGEPARSE_STAGE_GETCONTENT) { - if (m_CurrentOffset == m_nStreams) { - if (m_pStreamArray) { - m_Size = 0; - FX_DWORD i; - for (i = 0; i < m_nStreams; i ++) { - FX_DWORD size = m_pStreamArray[i]->GetSize(); - if (m_Size + size + 1 <= m_Size) { - m_Status = Done; - return; - } - m_Size += size + 1; - } - m_pData = FX_Alloc(uint8_t, m_Size); - FX_DWORD pos = 0; - for (i = 0; i < m_nStreams; i ++) { - FXSYS_memcpy(m_pData + pos, m_pStreamArray[i]->GetData(), m_pStreamArray[i]->GetSize()); - pos += m_pStreamArray[i]->GetSize() + 1; - m_pData[pos - 1] = ' '; - delete m_pStreamArray[i]; - } - FX_Free(m_pStreamArray); - m_pStreamArray = NULL; - } else { - m_pData = (uint8_t*)m_pSingleStream->GetData(); - m_Size = m_pSingleStream->GetSize(); - } - m_InternalStage = PAGEPARSE_STAGE_PARSE; - m_CurrentOffset = 0; - } else { - CPDF_Array* pContent = m_pObjects->m_pFormDict->GetArray(FX_BSTRC("Contents")); - m_pStreamArray[m_CurrentOffset] = new CPDF_StreamAcc; - CPDF_Stream* pStreamObj = (CPDF_Stream*)(pContent ? pContent->GetElementValue(m_CurrentOffset) : NULL); - m_pStreamArray[m_CurrentOffset]->LoadAllData(pStreamObj, FALSE); - m_CurrentOffset ++; - } - } - if (m_InternalStage == PAGEPARSE_STAGE_PARSE) { - if (!m_pParser) { - m_pParser = new CPDF_StreamContentParser( - m_pObjects->m_pDocument, m_pObjects->m_pPageResources, - nullptr, nullptr, m_pObjects, m_pObjects->m_pResources, - &m_pObjects->m_BBox, &m_Options, nullptr, 0); - m_pParser->GetCurStates()->m_ColorState.GetModify()->Default(); - } - if (m_CurrentOffset >= m_Size) { - m_InternalStage = PAGEPARSE_STAGE_CHECKCLIP; - } else { - m_CurrentOffset += m_pParser->Parse(m_pData + m_CurrentOffset, m_Size - m_CurrentOffset, PARSE_STEP_LIMIT); - if (m_pParser->ShouldAbort()) { - m_InternalStage = PAGEPARSE_STAGE_CHECKCLIP; - continue; - } - } - } - if (m_InternalStage == PAGEPARSE_STAGE_CHECKCLIP) { - if (m_pType3Char) { - m_pType3Char->m_bColored = m_pParser->IsColored(); - m_pType3Char->m_Width = FXSYS_round(m_pParser->GetType3Data()[0] * 1000); - m_pType3Char->m_BBox.left = FXSYS_round(m_pParser->GetType3Data()[2] * 1000); - m_pType3Char->m_BBox.bottom = FXSYS_round(m_pParser->GetType3Data()[3] * 1000); - m_pType3Char->m_BBox.right = FXSYS_round(m_pParser->GetType3Data()[4] * 1000); - m_pType3Char->m_BBox.top = FXSYS_round(m_pParser->GetType3Data()[5] * 1000); - } - FX_POSITION pos = m_pObjects->m_ObjectList.GetHeadPosition(); - while (pos) { - CPDF_PageObject* pObj = (CPDF_PageObject*)m_pObjects->m_ObjectList.GetNext(pos); - if (pObj->m_ClipPath.IsNull()) { - continue; - } - if (pObj->m_ClipPath.GetPathCount() != 1) { - continue; - } - if (pObj->m_ClipPath.GetTextCount()) { - continue; - } - CPDF_Path ClipPath = pObj->m_ClipPath.GetPath(0); - if (!ClipPath.IsRect() || pObj->m_Type == PDFPAGE_SHADING) { - continue; - } - CFX_FloatRect old_rect(ClipPath.GetPointX(0), ClipPath.GetPointY(0), - ClipPath.GetPointX(2), ClipPath.GetPointY(2)); - CFX_FloatRect obj_rect(pObj->m_Left, pObj->m_Bottom, pObj->m_Right, pObj->m_Top); - if (old_rect.Contains(obj_rect)) { - pObj->m_ClipPath.SetNull(); - } +void CPDF_ContentParser::Start(CPDF_Form* pForm, + CPDF_AllStates* pGraphicStates, + CFX_AffineMatrix* pParentMatrix, + CPDF_Type3Char* pType3Char, + CPDF_ParseOptions* pOptions, + int level) { + m_pType3Char = pType3Char; + m_pObjects = pForm; + m_bForm = TRUE; + CFX_AffineMatrix form_matrix = + pForm->m_pFormDict->GetMatrix(FX_BSTRC("Matrix")); + if (pGraphicStates) { + form_matrix.Concat(pGraphicStates->m_CTM); + } + CPDF_Array* pBBox = pForm->m_pFormDict->GetArray(FX_BSTRC("BBox")); + CFX_FloatRect form_bbox; + CPDF_Path ClipPath; + if (pBBox) { + form_bbox = pBBox->GetRect(); + ClipPath.New(); + ClipPath.AppendRect(form_bbox.left, form_bbox.bottom, form_bbox.right, + form_bbox.top); + ClipPath.Transform(&form_matrix); + if (pParentMatrix) { + ClipPath.Transform(pParentMatrix); + } + form_bbox.Transform(&form_matrix); + if (pParentMatrix) { + form_bbox.Transform(pParentMatrix); + } + } + CPDF_Dictionary* pResources = + pForm->m_pFormDict->GetDict(FX_BSTRC("Resources")); + m_pParser = new CPDF_StreamContentParser( + pForm->m_pDocument, pForm->m_pPageResources, pForm->m_pResources, + pParentMatrix, pForm, pResources, &form_bbox, pOptions, pGraphicStates, + level); + + m_pParser->GetCurStates()->m_CTM = form_matrix; + m_pParser->GetCurStates()->m_ParentMatrix = form_matrix; + if (ClipPath.NotNull()) { + m_pParser->GetCurStates()->m_ClipPath.AppendPath(ClipPath, FXFILL_WINDING, + TRUE); + } + if (pForm->m_Transparency & PDFTRANS_GROUP) { + CPDF_GeneralStateData* pData = + m_pParser->GetCurStates()->m_GeneralState.GetModify(); + pData->m_BlendType = FXDIB_BLEND_NORMAL; + pData->m_StrokeAlpha = 1.0f; + pData->m_FillAlpha = 1.0f; + pData->m_pSoftMask = NULL; + } + m_nStreams = 0; + m_pSingleStream = new CPDF_StreamAcc; + if (pForm->m_pDocument) { + m_pSingleStream->LoadAllData(pForm->m_pFormStream, FALSE); + } else { + m_pSingleStream->LoadAllData(pForm->m_pFormStream, FALSE); + } + m_pData = (uint8_t*)m_pSingleStream->GetData(); + m_Size = m_pSingleStream->GetSize(); + m_Status = ToBeContinued; + m_InternalStage = PAGEPARSE_STAGE_PARSE; + m_CurrentOffset = 0; +} +void CPDF_ContentParser::Continue(IFX_Pause* pPause) { + int steps = 0; + while (m_Status == ToBeContinued) { + if (m_InternalStage == PAGEPARSE_STAGE_GETCONTENT) { + if (m_CurrentOffset == m_nStreams) { + if (m_pStreamArray) { + m_Size = 0; + FX_DWORD i; + for (i = 0; i < m_nStreams; i++) { + FX_DWORD size = m_pStreamArray[i]->GetSize(); + if (m_Size + size + 1 <= m_Size) { + m_Status = Done; + return; } - m_Status = Done; - return; - } - steps ++; - if (pPause && pPause->NeedToPauseNow()) { - break; - } - } + m_Size += size + 1; + } + m_pData = FX_Alloc(uint8_t, m_Size); + FX_DWORD pos = 0; + for (i = 0; i < m_nStreams; i++) { + FXSYS_memcpy(m_pData + pos, m_pStreamArray[i]->GetData(), + m_pStreamArray[i]->GetSize()); + pos += m_pStreamArray[i]->GetSize() + 1; + m_pData[pos - 1] = ' '; + delete m_pStreamArray[i]; + } + FX_Free(m_pStreamArray); + m_pStreamArray = NULL; + } else { + m_pData = (uint8_t*)m_pSingleStream->GetData(); + m_Size = m_pSingleStream->GetSize(); + } + m_InternalStage = PAGEPARSE_STAGE_PARSE; + m_CurrentOffset = 0; + } else { + CPDF_Array* pContent = + m_pObjects->m_pFormDict->GetArray(FX_BSTRC("Contents")); + m_pStreamArray[m_CurrentOffset] = new CPDF_StreamAcc; + CPDF_Stream* pStreamObj = + (CPDF_Stream*)(pContent ? pContent->GetElementValue(m_CurrentOffset) + : NULL); + m_pStreamArray[m_CurrentOffset]->LoadAllData(pStreamObj, FALSE); + m_CurrentOffset++; + } + } + if (m_InternalStage == PAGEPARSE_STAGE_PARSE) { + if (!m_pParser) { + m_pParser = new CPDF_StreamContentParser( + m_pObjects->m_pDocument, m_pObjects->m_pPageResources, nullptr, + nullptr, m_pObjects, m_pObjects->m_pResources, &m_pObjects->m_BBox, + &m_Options, nullptr, 0); + m_pParser->GetCurStates()->m_ColorState.GetModify()->Default(); + } + if (m_CurrentOffset >= m_Size) { + m_InternalStage = PAGEPARSE_STAGE_CHECKCLIP; + } else { + m_CurrentOffset += + m_pParser->Parse(m_pData + m_CurrentOffset, + m_Size - m_CurrentOffset, PARSE_STEP_LIMIT); + if (m_pParser->ShouldAbort()) { + m_InternalStage = PAGEPARSE_STAGE_CHECKCLIP; + continue; + } + } + } + if (m_InternalStage == PAGEPARSE_STAGE_CHECKCLIP) { + if (m_pType3Char) { + m_pType3Char->m_bColored = m_pParser->IsColored(); + m_pType3Char->m_Width = + FXSYS_round(m_pParser->GetType3Data()[0] * 1000); + m_pType3Char->m_BBox.left = + FXSYS_round(m_pParser->GetType3Data()[2] * 1000); + m_pType3Char->m_BBox.bottom = + FXSYS_round(m_pParser->GetType3Data()[3] * 1000); + m_pType3Char->m_BBox.right = + FXSYS_round(m_pParser->GetType3Data()[4] * 1000); + m_pType3Char->m_BBox.top = + FXSYS_round(m_pParser->GetType3Data()[5] * 1000); + } + FX_POSITION pos = m_pObjects->m_ObjectList.GetHeadPosition(); + while (pos) { + CPDF_PageObject* pObj = + (CPDF_PageObject*)m_pObjects->m_ObjectList.GetNext(pos); + if (pObj->m_ClipPath.IsNull()) { + continue; + } + if (pObj->m_ClipPath.GetPathCount() != 1) { + continue; + } + if (pObj->m_ClipPath.GetTextCount()) { + continue; + } + CPDF_Path ClipPath = pObj->m_ClipPath.GetPath(0); + if (!ClipPath.IsRect() || pObj->m_Type == PDFPAGE_SHADING) { + continue; + } + CFX_FloatRect old_rect(ClipPath.GetPointX(0), ClipPath.GetPointY(0), + ClipPath.GetPointX(2), ClipPath.GetPointY(2)); + CFX_FloatRect obj_rect(pObj->m_Left, pObj->m_Bottom, pObj->m_Right, + pObj->m_Top); + if (old_rect.Contains(obj_rect)) { + pObj->m_ClipPath.SetNull(); + } + } + m_Status = Done; + return; + } + steps++; + if (pPause && pPause->NeedToPauseNow()) { + break; + } + } } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_path.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_path.cpp index 90a508eab3..81b69bcb24 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_path.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_path.cpp @@ -8,45 +8,41 @@ #include "../../../include/fpdfapi/fpdf_pageobj.h" #include "../../../include/fpdfapi/fpdf_module.h" #include "pageint.h" -void CPDF_PathObject::CopyData(const CPDF_PageObject* pSrc) -{ - const CPDF_PathObject* pSrcObj = (const CPDF_PathObject*)pSrc; - m_Path = pSrcObj->m_Path; - m_FillType = pSrcObj->m_FillType; - m_bStroke = pSrcObj->m_bStroke; - m_Matrix = pSrcObj->m_Matrix; +void CPDF_PathObject::CopyData(const CPDF_PageObject* pSrc) { + const CPDF_PathObject* pSrcObj = (const CPDF_PathObject*)pSrc; + m_Path = pSrcObj->m_Path; + m_FillType = pSrcObj->m_FillType; + m_bStroke = pSrcObj->m_bStroke; + m_Matrix = pSrcObj->m_Matrix; } -void CPDF_PathObject::Transform(const CPDF_Matrix& matrix) -{ - m_Matrix.Concat(matrix); - CalcBoundingBox(); +void CPDF_PathObject::Transform(const CPDF_Matrix& matrix) { + m_Matrix.Concat(matrix); + CalcBoundingBox(); } -void CPDF_PathObject::SetGraphState(CPDF_GraphState GraphState) -{ - m_GraphState = GraphState; - CalcBoundingBox(); +void CPDF_PathObject::SetGraphState(CPDF_GraphState GraphState) { + m_GraphState = GraphState; + CalcBoundingBox(); } -void CPDF_PathObject::CalcBoundingBox() -{ - if (m_Path.IsNull()) { - return; - } - CFX_FloatRect rect; - FX_FLOAT width = m_GraphState.GetObject()->m_LineWidth; - if (m_bStroke && width != 0) { - rect = m_Path.GetBoundingBox(width, m_GraphState.GetObject()->m_MiterLimit); - } else { - rect = m_Path.GetBoundingBox(); - } - rect.Transform(&m_Matrix); - if (width == 0 && m_bStroke) { - rect.left += -0.5f; - rect.right += 0.5f; - rect.bottom += -0.5f; - rect.top += 0.5f; - } - m_Left = rect.left; - m_Right = rect.right; - m_Top = rect.top; - m_Bottom = rect.bottom; +void CPDF_PathObject::CalcBoundingBox() { + if (m_Path.IsNull()) { + return; + } + CFX_FloatRect rect; + FX_FLOAT width = m_GraphState.GetObject()->m_LineWidth; + if (m_bStroke && width != 0) { + rect = m_Path.GetBoundingBox(width, m_GraphState.GetObject()->m_MiterLimit); + } else { + rect = m_Path.GetBoundingBox(); + } + rect.Transform(&m_Matrix); + if (width == 0 && m_bStroke) { + rect.left += -0.5f; + rect.right += 0.5f; + rect.bottom += -0.5f; + rect.top += 0.5f; + } + m_Left = rect.left; + m_Right = rect.right; + m_Top = rect.top; + m_Bottom = rect.bottom; } diff --git a/core/src/fpdfapi/fpdf_page/fpdf_page_pattern.cpp b/core/src/fpdfapi/fpdf_page/fpdf_page_pattern.cpp index 48b3a40495..3f915a7b79 100644 --- a/core/src/fpdfapi/fpdf_page/fpdf_page_pattern.cpp +++ b/core/src/fpdfapi/fpdf_page/fpdf_page_pattern.cpp @@ -7,283 +7,294 @@ #include "../../../include/fpdfapi/fpdf_page.h" #include "pageint.h" -CPDF_Pattern::CPDF_Pattern(const CFX_AffineMatrix* pParentMatrix) : - m_pPatternObj(NULL), m_PatternType(PATTERN_TILING), m_pDocument(NULL), m_bForceClear(FALSE) -{ - if (pParentMatrix) { - m_ParentMatrix = *pParentMatrix; - } +CPDF_Pattern::CPDF_Pattern(const CFX_AffineMatrix* pParentMatrix) + : m_pPatternObj(NULL), + m_PatternType(PATTERN_TILING), + m_pDocument(NULL), + m_bForceClear(FALSE) { + if (pParentMatrix) { + m_ParentMatrix = *pParentMatrix; + } +} +CPDF_Pattern::~CPDF_Pattern() {} +CPDF_TilingPattern::CPDF_TilingPattern(CPDF_Document* pDoc, + CPDF_Object* pPatternObj, + const CFX_AffineMatrix* parentMatrix) + : CPDF_Pattern(parentMatrix) { + m_PatternType = PATTERN_TILING; + m_pPatternObj = pPatternObj; + m_pDocument = pDoc; + CPDF_Dictionary* pDict = m_pPatternObj->GetDict(); + ASSERT(pDict != NULL); + m_Pattern2Form = pDict->GetMatrix(FX_BSTRC("Matrix")); + m_bColored = pDict->GetInteger(FX_BSTRC("PaintType")) == 1; + if (parentMatrix) { + m_Pattern2Form.Concat(*parentMatrix); + } + m_pForm = NULL; } -CPDF_Pattern::~CPDF_Pattern() -{ +CPDF_TilingPattern::~CPDF_TilingPattern() { + delete m_pForm; + m_pForm = NULL; } -CPDF_TilingPattern::CPDF_TilingPattern(CPDF_Document* pDoc, CPDF_Object* pPatternObj, const CFX_AffineMatrix* parentMatrix) : - CPDF_Pattern(parentMatrix) -{ - m_PatternType = PATTERN_TILING; - m_pPatternObj = pPatternObj; - m_pDocument = pDoc; +FX_BOOL CPDF_TilingPattern::Load() { + if (m_pForm != NULL) { + return TRUE; + } + CPDF_Dictionary* pDict = m_pPatternObj->GetDict(); + if (pDict == NULL) { + return FALSE; + } + m_bColored = pDict->GetInteger(FX_BSTRC("PaintType")) == 1; + m_XStep = (FX_FLOAT)FXSYS_fabs(pDict->GetNumber(FX_BSTRC("XStep"))); + m_YStep = (FX_FLOAT)FXSYS_fabs(pDict->GetNumber(FX_BSTRC("YStep"))); + if (m_pPatternObj->GetType() != PDFOBJ_STREAM) { + return FALSE; + } + CPDF_Stream* pStream = (CPDF_Stream*)m_pPatternObj; + m_pForm = new CPDF_Form(m_pDocument, NULL, pStream); + m_pForm->ParseContent(NULL, &m_ParentMatrix, NULL, NULL); + m_BBox = pDict->GetRect(FX_BSTRC("BBox")); + return TRUE; +} +CPDF_ShadingPattern::CPDF_ShadingPattern(CPDF_Document* pDoc, + CPDF_Object* pPatternObj, + FX_BOOL bShading, + const CFX_AffineMatrix* parentMatrix) + : CPDF_Pattern(parentMatrix) { + m_PatternType = PATTERN_SHADING; + m_pPatternObj = bShading ? NULL : pPatternObj; + m_pDocument = pDoc; + m_bShadingObj = bShading; + if (!bShading) { CPDF_Dictionary* pDict = m_pPatternObj->GetDict(); ASSERT(pDict != NULL); m_Pattern2Form = pDict->GetMatrix(FX_BSTRC("Matrix")); - m_bColored = pDict->GetInteger(FX_BSTRC("PaintType")) == 1; + m_pShadingObj = pDict->GetElementValue(FX_BSTRC("Shading")); if (parentMatrix) { - m_Pattern2Form.Concat(*parentMatrix); + m_Pattern2Form.Concat(*parentMatrix); } - m_pForm = NULL; + } else { + m_pShadingObj = pPatternObj; + } + m_ShadingType = 0; + m_pCS = NULL; + m_nFuncs = 0; + for (int i = 0; i < 4; i++) { + m_pFunctions[i] = NULL; + } + m_pCountedCS = NULL; } -CPDF_TilingPattern::~CPDF_TilingPattern() -{ - delete m_pForm; - m_pForm = NULL; +CPDF_ShadingPattern::~CPDF_ShadingPattern() { + Clear(); } -FX_BOOL CPDF_TilingPattern::Load() -{ - if (m_pForm != NULL) { - return TRUE; - } - CPDF_Dictionary* pDict = m_pPatternObj->GetDict(); - if (pDict == NULL) { - return FALSE; - } - m_bColored = pDict->GetInteger(FX_BSTRC("PaintType")) == 1; - m_XStep = (FX_FLOAT)FXSYS_fabs(pDict->GetNumber(FX_BSTRC("XStep"))); - m_YStep = (FX_FLOAT)FXSYS_fabs(pDict->GetNumber(FX_BSTRC("YStep"))); - if (m_pPatternObj->GetType() != PDFOBJ_STREAM) { - return FALSE; - } - CPDF_Stream* pStream = (CPDF_Stream*)m_pPatternObj; - m_pForm = new CPDF_Form(m_pDocument, NULL, pStream); - m_pForm->ParseContent(NULL, &m_ParentMatrix, NULL, NULL); - m_BBox = pDict->GetRect(FX_BSTRC("BBox")); - return TRUE; +void CPDF_ShadingPattern::Clear() { + for (int i = 0; i < m_nFuncs; i++) { + delete m_pFunctions[i]; + m_pFunctions[i] = NULL; + } + CPDF_ColorSpace* pCS = m_pCountedCS ? m_pCountedCS->get() : NULL; + if (pCS && m_pDocument) { + m_pDocument->GetPageData()->ReleaseColorSpace(pCS->GetArray()); + } + m_ShadingType = 0; + m_pCS = NULL; + m_pCountedCS = NULL; + m_nFuncs = 0; } -CPDF_ShadingPattern::CPDF_ShadingPattern(CPDF_Document* pDoc, CPDF_Object* pPatternObj, FX_BOOL bShading, const CFX_AffineMatrix* parentMatrix) : CPDF_Pattern(parentMatrix) -{ - m_PatternType = PATTERN_SHADING; - m_pPatternObj = bShading ? NULL : pPatternObj; - m_pDocument = pDoc; - m_bShadingObj = bShading; - if (!bShading) { - CPDF_Dictionary* pDict = m_pPatternObj->GetDict(); - ASSERT(pDict != NULL); - m_Pattern2Form = pDict->GetMatrix(FX_BSTRC("Matrix")); - m_pShadingObj = pDict->GetElementValue(FX_BSTRC("Shading")); - if (parentMatrix) { - m_Pattern2Form.Concat(*parentMatrix); - } - } else { - m_pShadingObj = pPatternObj; - } - m_ShadingType = 0; - m_pCS = NULL; +FX_BOOL CPDF_ShadingPattern::Load() { + if (m_ShadingType != 0) { + return TRUE; + } + CPDF_Dictionary* pShadingDict = + m_pShadingObj ? m_pShadingObj->GetDict() : NULL; + if (pShadingDict == NULL) { + return FALSE; + } + if (m_nFuncs) { + for (int i = 0; i < m_nFuncs; i++) + delete m_pFunctions[i]; m_nFuncs = 0; - for (int i = 0; i < 4; i ++) { - m_pFunctions[i] = NULL; + } + CPDF_Object* pFunc = pShadingDict->GetElementValue(FX_BSTRC("Function")); + if (pFunc) { + if (pFunc->GetType() == PDFOBJ_ARRAY) { + m_nFuncs = ((CPDF_Array*)pFunc)->GetCount(); + if (m_nFuncs > 4) { + m_nFuncs = 4; + } + for (int i = 0; i < m_nFuncs; i++) { + m_pFunctions[i] = + CPDF_Function::Load(((CPDF_Array*)pFunc)->GetElementValue(i)); + } + } else { + m_pFunctions[0] = CPDF_Function::Load(pFunc); + m_nFuncs = 1; } - m_pCountedCS = NULL; + } + CPDF_Object* pCSObj = pShadingDict->GetElementValue(FX_BSTRC("ColorSpace")); + if (pCSObj == NULL) { + return FALSE; + } + CPDF_DocPageData* pDocPageData = m_pDocument->GetPageData(); + m_pCS = pDocPageData->GetColorSpace(pCSObj, NULL); + if (m_pCS) { + m_pCountedCS = pDocPageData->FindColorSpacePtr(m_pCS->GetArray()); + } + m_ShadingType = pShadingDict->GetInteger(FX_BSTRC("ShadingType")); + return TRUE; } -CPDF_ShadingPattern::~CPDF_ShadingPattern() -{ - Clear(); +FX_BOOL CPDF_ShadingPattern::Reload() { + Clear(); + return Load(); } -void CPDF_ShadingPattern::Clear() -{ - for (int i = 0; i < m_nFuncs; i ++) { - delete m_pFunctions[i]; - m_pFunctions[i] = NULL; - } - CPDF_ColorSpace* pCS = m_pCountedCS ? m_pCountedCS->get() : NULL; - if (pCS && m_pDocument) { - m_pDocument->GetPageData()->ReleaseColorSpace(pCS->GetArray()); - } - m_ShadingType = 0; - m_pCS = NULL; - m_pCountedCS = NULL; - m_nFuncs = 0; +FX_BOOL CPDF_MeshStream::Load(CPDF_Stream* pShadingStream, + CPDF_Function** pFuncs, + int nFuncs, + CPDF_ColorSpace* pCS) { + m_Stream.LoadAllData(pShadingStream); + m_BitStream.Init(m_Stream.GetData(), m_Stream.GetSize()); + m_pFuncs = pFuncs; + m_nFuncs = nFuncs; + m_pCS = pCS; + CPDF_Dictionary* pDict = pShadingStream->GetDict(); + m_nCoordBits = pDict->GetInteger(FX_BSTRC("BitsPerCoordinate")); + m_nCompBits = pDict->GetInteger(FX_BSTRC("BitsPerComponent")); + m_nFlagBits = pDict->GetInteger(FX_BSTRC("BitsPerFlag")); + if (!m_nCoordBits || !m_nCompBits) { + return FALSE; + } + int nComps = pCS->CountComponents(); + if (nComps > 8) { + return FALSE; + } + m_nComps = nFuncs ? 1 : nComps; + if (((int)m_nComps < 0) || m_nComps > 8) { + return FALSE; + } + m_CoordMax = m_nCoordBits == 32 ? -1 : (1 << m_nCoordBits) - 1; + m_CompMax = (1 << m_nCompBits) - 1; + CPDF_Array* pDecode = pDict->GetArray(FX_BSTRC("Decode")); + if (pDecode == NULL || pDecode->GetCount() != 4 + m_nComps * 2) { + return FALSE; + } + m_xmin = pDecode->GetNumber(0); + m_xmax = pDecode->GetNumber(1); + m_ymin = pDecode->GetNumber(2); + m_ymax = pDecode->GetNumber(3); + for (FX_DWORD i = 0; i < m_nComps; i++) { + m_ColorMin[i] = pDecode->GetNumber(i * 2 + 4); + m_ColorMax[i] = pDecode->GetNumber(i * 2 + 5); + } + return TRUE; } -FX_BOOL CPDF_ShadingPattern::Load() -{ - if (m_ShadingType != 0) { - return TRUE; - } - CPDF_Dictionary* pShadingDict = m_pShadingObj ? m_pShadingObj->GetDict() : NULL; - if (pShadingDict == NULL) { - return FALSE; - } - if (m_nFuncs) { - for (int i = 0; i < m_nFuncs; i ++) - delete m_pFunctions[i]; - m_nFuncs = 0; - } - CPDF_Object* pFunc = pShadingDict->GetElementValue(FX_BSTRC("Function")); - if (pFunc) { - if (pFunc->GetType() == PDFOBJ_ARRAY) { - m_nFuncs = ((CPDF_Array*)pFunc)->GetCount(); - if (m_nFuncs > 4) { - m_nFuncs = 4; - } - for (int i = 0; i < m_nFuncs; i ++) { - m_pFunctions[i] = CPDF_Function::Load(((CPDF_Array*)pFunc)->GetElementValue(i)); - } - } else { - m_pFunctions[0] = CPDF_Function::Load(pFunc); - m_nFuncs = 1; - } - } - CPDF_Object* pCSObj = pShadingDict->GetElementValue(FX_BSTRC("ColorSpace")); - if (pCSObj == NULL) { - return FALSE; - } - CPDF_DocPageData* pDocPageData = m_pDocument->GetPageData(); - m_pCS = pDocPageData->GetColorSpace(pCSObj, NULL); - if (m_pCS) { - m_pCountedCS = pDocPageData->FindColorSpacePtr(m_pCS->GetArray()); - } - m_ShadingType = pShadingDict->GetInteger(FX_BSTRC("ShadingType")); - return TRUE; +FX_DWORD CPDF_MeshStream::GetFlag() { + return m_BitStream.GetBits(m_nFlagBits) & 0x03; } -FX_BOOL CPDF_ShadingPattern::Reload() -{ - Clear(); - return Load(); +void CPDF_MeshStream::GetCoords(FX_FLOAT& x, FX_FLOAT& y) { + if (m_nCoordBits == 32) { + x = m_xmin + (FX_FLOAT)(m_BitStream.GetBits(m_nCoordBits) * + (m_xmax - m_xmin) / (double)m_CoordMax); + y = m_ymin + (FX_FLOAT)(m_BitStream.GetBits(m_nCoordBits) * + (m_ymax - m_ymin) / (double)m_CoordMax); + } else { + x = m_xmin + + m_BitStream.GetBits(m_nCoordBits) * (m_xmax - m_xmin) / m_CoordMax; + y = m_ymin + + m_BitStream.GetBits(m_nCoordBits) * (m_ymax - m_ymin) / m_CoordMax; + } } -FX_BOOL CPDF_MeshStream::Load(CPDF_Stream* pShadingStream, CPDF_Function** pFuncs, int nFuncs, CPDF_ColorSpace* pCS) -{ - m_Stream.LoadAllData(pShadingStream); - m_BitStream.Init(m_Stream.GetData(), m_Stream.GetSize()); - m_pFuncs = pFuncs; - m_nFuncs = nFuncs; - m_pCS = pCS; - CPDF_Dictionary* pDict = pShadingStream->GetDict(); - m_nCoordBits = pDict->GetInteger(FX_BSTRC("BitsPerCoordinate")); - m_nCompBits = pDict->GetInteger(FX_BSTRC("BitsPerComponent")); - m_nFlagBits = pDict->GetInteger(FX_BSTRC("BitsPerFlag")); - if (!m_nCoordBits || !m_nCompBits) { - return FALSE; - } - int nComps = pCS->CountComponents(); - if (nComps > 8) { - return FALSE; - } - m_nComps = nFuncs ? 1 : nComps; - if (((int)m_nComps < 0) || m_nComps > 8) { - return FALSE; - } - m_CoordMax = m_nCoordBits == 32 ? -1 : (1 << m_nCoordBits) - 1; - m_CompMax = (1 << m_nCompBits) - 1; - CPDF_Array* pDecode = pDict->GetArray(FX_BSTRC("Decode")); - if (pDecode == NULL || pDecode->GetCount() != 4 + m_nComps * 2) { - return FALSE; - } - m_xmin = pDecode->GetNumber(0); - m_xmax = pDecode->GetNumber(1); - m_ymin = pDecode->GetNumber(2); - m_ymax = pDecode->GetNumber(3); - for (FX_DWORD i = 0; i < m_nComps; i ++) { - m_ColorMin[i] = pDecode->GetNumber(i * 2 + 4); - m_ColorMax[i] = pDecode->GetNumber(i * 2 + 5); +void CPDF_MeshStream::GetColor(FX_FLOAT& r, FX_FLOAT& g, FX_FLOAT& b) { + FX_DWORD i; + FX_FLOAT color_value[8]; + for (i = 0; i < m_nComps; i++) { + color_value[i] = m_ColorMin[i] + + m_BitStream.GetBits(m_nCompBits) * + (m_ColorMax[i] - m_ColorMin[i]) / m_CompMax; + } + if (m_nFuncs) { + static const int kMaxResults = 8; + FX_FLOAT result[kMaxResults]; + int nResults; + FXSYS_memset(result, 0, sizeof(result)); + for (FX_DWORD i = 0; i < m_nFuncs; i++) { + if (m_pFuncs[i] && m_pFuncs[i]->CountOutputs() <= kMaxResults) { + m_pFuncs[i]->Call(color_value, 1, result, nResults); + } } - return TRUE; + m_pCS->GetRGB(result, r, g, b); + } else { + m_pCS->GetRGB(color_value, r, g, b); + } } -FX_DWORD CPDF_MeshStream::GetFlag() -{ - return m_BitStream.GetBits(m_nFlagBits) & 0x03; +FX_DWORD CPDF_MeshStream::GetVertex(CPDF_MeshVertex& vertex, + CFX_AffineMatrix* pObject2Bitmap) { + FX_DWORD flag = GetFlag(); + GetCoords(vertex.x, vertex.y); + pObject2Bitmap->Transform(vertex.x, vertex.y); + GetColor(vertex.r, vertex.g, vertex.b); + m_BitStream.ByteAlign(); + return flag; } -void CPDF_MeshStream::GetCoords(FX_FLOAT& x, FX_FLOAT& y) -{ - if (m_nCoordBits == 32) { - x = m_xmin + (FX_FLOAT)(m_BitStream.GetBits(m_nCoordBits) * (m_xmax - m_xmin) / (double)m_CoordMax); - y = m_ymin + (FX_FLOAT)(m_BitStream.GetBits(m_nCoordBits) * (m_ymax - m_ymin) / (double)m_CoordMax); - } else { - x = m_xmin + m_BitStream.GetBits(m_nCoordBits) * (m_xmax - m_xmin) / m_CoordMax; - y = m_ymin + m_BitStream.GetBits(m_nCoordBits) * (m_ymax - m_ymin) / m_CoordMax; +FX_BOOL CPDF_MeshStream::GetVertexRow(CPDF_MeshVertex* vertex, + int count, + CFX_AffineMatrix* pObject2Bitmap) { + for (int i = 0; i < count; i++) { + if (m_BitStream.IsEOF()) { + return FALSE; } -} -void CPDF_MeshStream::GetColor(FX_FLOAT& r, FX_FLOAT& g, FX_FLOAT& b) -{ - FX_DWORD i; - FX_FLOAT color_value[8]; - for (i = 0; i < m_nComps; i ++) { - color_value[i] = m_ColorMin[i] + m_BitStream.GetBits(m_nCompBits) * (m_ColorMax[i] - m_ColorMin[i]) / m_CompMax; - } - if (m_nFuncs) { - static const int kMaxResults = 8; - FX_FLOAT result[kMaxResults]; - int nResults; - FXSYS_memset(result, 0, sizeof(result)); - for (FX_DWORD i = 0; i < m_nFuncs; i ++) { - if (m_pFuncs[i] && m_pFuncs[i]->CountOutputs() <= kMaxResults) { - m_pFuncs[i]->Call(color_value, 1, result, nResults); - } - } - m_pCS->GetRGB(result, r, g, b); - } else { - m_pCS->GetRGB(color_value, r, g, b); - } -} -FX_DWORD CPDF_MeshStream::GetVertex(CPDF_MeshVertex& vertex, CFX_AffineMatrix* pObject2Bitmap) -{ - FX_DWORD flag = GetFlag(); - GetCoords(vertex.x, vertex.y); - pObject2Bitmap->Transform(vertex.x, vertex.y); - GetColor(vertex.r, vertex.g, vertex.b); + GetCoords(vertex[i].x, vertex[i].y); + pObject2Bitmap->Transform(vertex[i].x, vertex[i].y); + GetColor(vertex[i].r, vertex[i].g, vertex[i].b); m_BitStream.ByteAlign(); - return flag; + } + return TRUE; } -FX_BOOL CPDF_MeshStream::GetVertexRow(CPDF_MeshVertex* vertex, int count, CFX_AffineMatrix* pObject2Bitmap) -{ - for (int i = 0; i < count; i ++) { - if (m_BitStream.IsEOF()) { - return FALSE; - } - GetCoords(vertex[i].x, vertex[i].y); - pObject2Bitmap->Transform(vertex[i].x, vertex[i].y); - GetColor(vertex[i].r, vertex[i].g, vertex[i].b); - m_BitStream.ByteAlign(); +CFX_FloatRect _GetShadingBBox(CPDF_Stream* pStream, + int type, + const CFX_AffineMatrix* pMatrix, + CPDF_Function** pFuncs, + int nFuncs, + CPDF_ColorSpace* pCS) { + if (pStream == NULL || pStream->GetType() != PDFOBJ_STREAM || + pFuncs == NULL || pCS == NULL) { + return CFX_FloatRect(0, 0, 0, 0); + } + CPDF_MeshStream stream; + if (!stream.Load(pStream, pFuncs, nFuncs, pCS)) { + return CFX_FloatRect(0, 0, 0, 0); + } + CFX_FloatRect rect; + FX_BOOL bStarted = FALSE; + FX_BOOL bGouraud = type == 4 || type == 5; + int full_point_count = type == 7 ? 16 : (type == 6 ? 12 : 1); + int full_color_count = (type == 6 || type == 7) ? 4 : 1; + while (!stream.m_BitStream.IsEOF()) { + FX_DWORD flag = 0; + if (type != 5) { + flag = stream.GetFlag(); } - return TRUE; -} -CFX_FloatRect _GetShadingBBox(CPDF_Stream* pStream, int type, const CFX_AffineMatrix* pMatrix, - CPDF_Function** pFuncs, int nFuncs, CPDF_ColorSpace* pCS) -{ - if (pStream == NULL || pStream->GetType() != PDFOBJ_STREAM || pFuncs == NULL || pCS == NULL) { - return CFX_FloatRect(0, 0, 0, 0); + int point_count = full_point_count, color_count = full_color_count; + if (!bGouraud && flag) { + point_count -= 4; + color_count -= 2; } - CPDF_MeshStream stream; - if (!stream.Load(pStream, pFuncs, nFuncs, pCS)) { - return CFX_FloatRect(0, 0, 0, 0); + for (int i = 0; i < point_count; i++) { + FX_FLOAT x, y; + stream.GetCoords(x, y); + if (bStarted) { + rect.UpdateRect(x, y); + } else { + rect.InitRect(x, y); + bStarted = TRUE; + } } - CFX_FloatRect rect; - FX_BOOL bStarted = FALSE; - FX_BOOL bGouraud = type == 4 || type == 5; - int full_point_count = type == 7 ? 16 : (type == 6 ? 12 : 1); - int full_color_count = (type == 6 || type == 7) ? 4 : 1; - while (!stream.m_BitStream.IsEOF()) { - FX_DWORD flag = 0; - if (type != 5) { - flag = stream.GetFlag(); - } - int point_count = full_point_count, color_count = full_color_count; - if (!bGouraud && flag) { - point_count -= 4; - color_count -= 2; - } - for (int i = 0; i < point_count; i ++) { - FX_FLOAT x, y; - stream.GetCoords(x, y); - if (bStarted) { - rect.UpdateRect(x, y); - } else { - rect.InitRect(x, y); - bStarted = TRUE; - } - } - stream.m_BitStream.SkipBits(stream.m_nComps * stream.m_nCompBits * color_count); - if (bGouraud) { - stream.m_BitStream.ByteAlign(); - } + stream.m_BitStream.SkipBits(stream.m_nComps * stream.m_nCompBits * + color_count); + if (bGouraud) { + stream.m_BitStream.ByteAlign(); } - rect.Transform(pMatrix); - return rect; + } + rect.Transform(pMatrix); + return rect; } diff --git a/core/src/fpdfapi/fpdf_page/pageint.h b/core/src/fpdfapi/fpdf_page/pageint.h index 8cd393cf32..c931af7eb2 100644 --- a/core/src/fpdfapi/fpdf_page/pageint.h +++ b/core/src/fpdfapi/fpdf_page/pageint.h @@ -12,486 +12,507 @@ #include "../../../../third_party/base/nonstd_unique_ptr.h" #include "../../../include/fpdfapi/fpdf_pageobj.h" -#define PARSE_STEP_LIMIT 100 - -class CPDF_StreamParser -{ -public: - - CPDF_StreamParser(const uint8_t* pData, FX_DWORD dwSize); - ~CPDF_StreamParser(); - - CPDF_Stream* ReadInlineStream(CPDF_Document* pDoc, CPDF_Dictionary* pDict, CPDF_Object* pCSObj, FX_BOOL bDecode); - typedef enum { EndOfData, Number, Keyword, Name, Others } SyntaxType; - - SyntaxType ParseNextElement(); - uint8_t* GetWordBuf() - { - return m_WordBuffer; - } - FX_DWORD GetWordSize() - { - return m_WordSize; - } - CPDF_Object* GetObject() - { - CPDF_Object* pObj = m_pLastObj; - m_pLastObj = NULL; - return pObj; - } - FX_DWORD GetPos() - { - return m_Pos; - } - void SetPos(FX_DWORD pos) - { - m_Pos = pos; - } - - CPDF_Object* ReadNextObject(FX_BOOL bAllowNestedArray = FALSE, FX_BOOL bInArray = FALSE); - void SkipPathObject(); -protected: - void GetNextWord(FX_BOOL& bIsNumber); - CFX_ByteString ReadString(); - CFX_ByteString ReadHexString(); - const uint8_t* m_pBuf; - FX_DWORD m_Size; - FX_DWORD m_Pos; - uint8_t m_WordBuffer[256]; - FX_DWORD m_WordSize; - CPDF_Object* m_pLastObj; +#define PARSE_STEP_LIMIT 100 + +class CPDF_StreamParser { + public: + CPDF_StreamParser(const uint8_t* pData, FX_DWORD dwSize); + ~CPDF_StreamParser(); + + CPDF_Stream* ReadInlineStream(CPDF_Document* pDoc, + CPDF_Dictionary* pDict, + CPDF_Object* pCSObj, + FX_BOOL bDecode); + typedef enum { EndOfData, Number, Keyword, Name, Others } SyntaxType; + + SyntaxType ParseNextElement(); + uint8_t* GetWordBuf() { return m_WordBuffer; } + FX_DWORD GetWordSize() { return m_WordSize; } + CPDF_Object* GetObject() { + CPDF_Object* pObj = m_pLastObj; + m_pLastObj = NULL; + return pObj; + } + FX_DWORD GetPos() { return m_Pos; } + void SetPos(FX_DWORD pos) { m_Pos = pos; } + + CPDF_Object* ReadNextObject(FX_BOOL bAllowNestedArray = FALSE, + FX_BOOL bInArray = FALSE); + void SkipPathObject(); + + protected: + void GetNextWord(FX_BOOL& bIsNumber); + CFX_ByteString ReadString(); + CFX_ByteString ReadHexString(); + const uint8_t* m_pBuf; + FX_DWORD m_Size; + FX_DWORD m_Pos; + uint8_t m_WordBuffer[256]; + FX_DWORD m_WordSize; + CPDF_Object* m_pLastObj; }; typedef enum { - PDFOP_CloseFillStrokePath = 0, PDFOP_FillStrokePath, - PDFOP_CloseEOFillStrokePath, PDFOP_EOFillStrokePath, - PDFOP_BeginMarkedContent_Dictionary, PDFOP_BeginImage, - PDFOP_BeginMarkedContent, PDFOP_BeginText, - PDFOP_BeginSectionUndefined, PDFOP_CurveTo_123, - PDFOP_ConcatMatrix, PDFOP_SetColorSpace_Fill, - PDFOP_SetColorSpace_Stroke, PDFOP_SetDash, - PDFOP_SetCharWidth, PDFOP_SetCachedDevice, - PDFOP_ExecuteXObject, PDFOP_MarkPlace_Dictionary, - PDFOP_EndImage, PDFOP_EndMarkedContent, - PDFOP_EndText, PDFOP_EndSectionUndefined, - PDFOP_FillPath, PDFOP_FillPathOld, - PDFOP_EOFillPath, PDFOP_SetGray_Fill, - PDFOP_SetGray_Stroke, PDFOP_SetExtendGraphState, - PDFOP_ClosePath, PDFOP_SetFlat, - PDFOP_BeginImageData, PDFOP_SetLineJoin, - PDFOP_SetLineCap, PDFOP_SetCMYKColor_Fill, - PDFOP_SetCMYKColor_Stroke, PDFOP_LineTo, - PDFOP_MoveTo, PDFOP_SetMiterLimit, - PDFOP_MarkPlace, PDFOP_EndPath, - PDFOP_SaveGraphState, PDFOP_RestoreGraphState, - PDFOP_Rectangle, PDFOP_SetRGBColor_Fill, - PDFOP_SetRGBColor_Stroke, PDFOP_SetRenderIntent, - PDFOP_CloseStrokePath, PDFOP_StrokePath, - PDFOP_SetColor_Fill, PDFOP_SetColor_Stroke, - PDFOP_SetColorPS_Fill, PDFOP_SetColorPS_Stroke, - PDFOP_ShadeFill, PDFOP_SetCharSpace, - PDFOP_MoveTextPoint, PDFOP_MoveTextPoint_SetLeading, - PDFOP_SetFont, PDFOP_ShowText, - PDFOP_ShowText_Positioning, PDFOP_SetTextLeading, - PDFOP_SetTextMatrix, PDFOP_SetTextRenderMode, - PDFOP_SetTextRise, PDFOP_SetWordSpace, - PDFOP_SetHorzScale, PDFOP_MoveToNextLine, - PDFOP_CurveTo_23, PDFOP_SetLineWidth, - PDFOP_Clip, PDFOP_EOClip, - PDFOP_CurveTo_13, PDFOP_NextLineShowText, - PDFOP_NextLineShowText_Space, PDFOP_Invalid + PDFOP_CloseFillStrokePath = 0, + PDFOP_FillStrokePath, + PDFOP_CloseEOFillStrokePath, + PDFOP_EOFillStrokePath, + PDFOP_BeginMarkedContent_Dictionary, + PDFOP_BeginImage, + PDFOP_BeginMarkedContent, + PDFOP_BeginText, + PDFOP_BeginSectionUndefined, + PDFOP_CurveTo_123, + PDFOP_ConcatMatrix, + PDFOP_SetColorSpace_Fill, + PDFOP_SetColorSpace_Stroke, + PDFOP_SetDash, + PDFOP_SetCharWidth, + PDFOP_SetCachedDevice, + PDFOP_ExecuteXObject, + PDFOP_MarkPlace_Dictionary, + PDFOP_EndImage, + PDFOP_EndMarkedContent, + PDFOP_EndText, + PDFOP_EndSectionUndefined, + PDFOP_FillPath, + PDFOP_FillPathOld, + PDFOP_EOFillPath, + PDFOP_SetGray_Fill, + PDFOP_SetGray_Stroke, + PDFOP_SetExtendGraphState, + PDFOP_ClosePath, + PDFOP_SetFlat, + PDFOP_BeginImageData, + PDFOP_SetLineJoin, + PDFOP_SetLineCap, + PDFOP_SetCMYKColor_Fill, + PDFOP_SetCMYKColor_Stroke, + PDFOP_LineTo, + PDFOP_MoveTo, + PDFOP_SetMiterLimit, + PDFOP_MarkPlace, + PDFOP_EndPath, + PDFOP_SaveGraphState, + PDFOP_RestoreGraphState, + PDFOP_Rectangle, + PDFOP_SetRGBColor_Fill, + PDFOP_SetRGBColor_Stroke, + PDFOP_SetRenderIntent, + PDFOP_CloseStrokePath, + PDFOP_StrokePath, + PDFOP_SetColor_Fill, + PDFOP_SetColor_Stroke, + PDFOP_SetColorPS_Fill, + PDFOP_SetColorPS_Stroke, + PDFOP_ShadeFill, + PDFOP_SetCharSpace, + PDFOP_MoveTextPoint, + PDFOP_MoveTextPoint_SetLeading, + PDFOP_SetFont, + PDFOP_ShowText, + PDFOP_ShowText_Positioning, + PDFOP_SetTextLeading, + PDFOP_SetTextMatrix, + PDFOP_SetTextRenderMode, + PDFOP_SetTextRise, + PDFOP_SetWordSpace, + PDFOP_SetHorzScale, + PDFOP_MoveToNextLine, + PDFOP_CurveTo_23, + PDFOP_SetLineWidth, + PDFOP_Clip, + PDFOP_EOClip, + PDFOP_CurveTo_13, + PDFOP_NextLineShowText, + PDFOP_NextLineShowText_Space, + PDFOP_Invalid } PDFOP; -#define PARAM_BUF_SIZE 16 +#define PARAM_BUF_SIZE 16 typedef struct { - int m_Type; - union { - struct { - FX_BOOL m_bInteger; - union { - int m_Integer; - FX_FLOAT m_Float; - }; - } m_Number; - CPDF_Object* m_pObject; - struct { - int m_Len; - char m_Buffer[32]; - } m_Name; - }; + int m_Type; + union { + struct { + FX_BOOL m_bInteger; + union { + int m_Integer; + FX_FLOAT m_Float; + }; + } m_Number; + CPDF_Object* m_pObject; + struct { + int m_Len; + char m_Buffer[32]; + } m_Name; + }; } _ContentParam; -#define _FPDF_MAX_FORM_LEVEL_ 30 -#define _FPDF_MAX_TYPE3_FORM_LEVEL_ 4 +#define _FPDF_MAX_FORM_LEVEL_ 30 +#define _FPDF_MAX_TYPE3_FORM_LEVEL_ 4 #define _FPDF_MAX_OBJECT_STACK_SIZE_ 512 -class CPDF_StreamContentParser -{ -public: - CPDF_StreamContentParser( - CPDF_Document* pDoc, - CPDF_Dictionary* pPageResources, - CPDF_Dictionary* pParentResources, - CFX_AffineMatrix* pmtContentToUser, - CPDF_PageObjects* pObjList, - CPDF_Dictionary* pResources, - CFX_FloatRect* pBBox, - CPDF_ParseOptions* pOptions, - CPDF_AllStates* pAllStates, - int level); - ~CPDF_StreamContentParser(); - - FX_BOOL ShouldAbort() const { return m_bAbort; } - CPDF_PageObjects* GetObjectList() const { return m_pObjectList; } - CPDF_AllStates* GetCurStates() const { return m_pCurStates.get(); } - FX_BOOL IsColored() const { return m_bColored; } - const FX_FLOAT* GetType3Data() const { return m_Type3Data; } - - void AddNumberParam(const FX_CHAR* str, int len); - void AddObjectParam(CPDF_Object* pObj); - void AddNameParam(const FX_CHAR* name, int size); - int GetNextParamPos(); - void ClearAllParams(); - CPDF_Object* GetObject(FX_DWORD index); - CFX_ByteString GetString(FX_DWORD index); - FX_FLOAT GetNumber(FX_DWORD index); - FX_FLOAT GetNumber16(FX_DWORD index); - int GetInteger(FX_DWORD index) - { - return (int32_t)(GetNumber(index)); - } - FX_BOOL OnOperator(const FX_CHAR* op); - void BigCaseCaller(int index); - FX_DWORD GetParsePos() - { - return m_pSyntax->GetPos(); - } - void AddTextObject(CFX_ByteString* pText, FX_FLOAT fInitKerning, FX_FLOAT* pKerning, int count); - - void ConvertUserSpace(FX_FLOAT& x, FX_FLOAT& y); - void ConvertTextSpace(FX_FLOAT& x, FX_FLOAT& y); - void OnChangeTextMatrix(); - FX_DWORD Parse(const uint8_t* pData, FX_DWORD dwSize, FX_DWORD max_cost); - void ParsePathObject(); - void AddPathPoint(FX_FLOAT x, FX_FLOAT y, int flag); - void AddPathRect(FX_FLOAT x, FX_FLOAT y, FX_FLOAT w, FX_FLOAT h); - void AddPathObject(int FillType, FX_BOOL bStroke); - CPDF_ImageObject* AddImage(CPDF_Stream* pStream, CPDF_Image* pImage, FX_BOOL bInline); - void AddDuplicateImage(); - void AddForm(CPDF_Stream*); - void SetGraphicStates(CPDF_PageObject* pObj, FX_BOOL bColor, FX_BOOL bText, FX_BOOL bGraph); - void SaveStates(CPDF_AllStates*); - void RestoreStates(CPDF_AllStates*); - CPDF_Font* FindFont(const CFX_ByteString& name); - CPDF_ColorSpace* FindColorSpace(const CFX_ByteString& name); - CPDF_Pattern* FindPattern(const CFX_ByteString& name, FX_BOOL bShading); - CPDF_Object* FindResourceObj(const CFX_ByteStringC& type, const CFX_ByteString& name); - -protected: - struct OpCode { - FX_DWORD m_OpId; - void (CPDF_StreamContentParser::*m_OpHandler)(); - }; - static const OpCode g_OpCodes[]; - - void Handle_CloseFillStrokePath(); - void Handle_FillStrokePath(); - void Handle_CloseEOFillStrokePath(); - void Handle_EOFillStrokePath(); - void Handle_BeginMarkedContent_Dictionary(); - void Handle_BeginImage(); - void Handle_BeginMarkedContent(); - void Handle_BeginText(); - void Handle_BeginSectionUndefined(); - void Handle_CurveTo_123(); - void Handle_ConcatMatrix(); - void Handle_SetColorSpace_Fill(); - void Handle_SetColorSpace_Stroke(); - void Handle_SetDash(); - void Handle_SetCharWidth(); - void Handle_SetCachedDevice(); - void Handle_ExecuteXObject(); - void Handle_MarkPlace_Dictionary(); - void Handle_EndImage(); - void Handle_EndMarkedContent(); - void Handle_EndText(); - void Handle_EndSectionUndefined(); - void Handle_FillPath(); - void Handle_FillPathOld(); - void Handle_EOFillPath(); - void Handle_SetGray_Fill(); - void Handle_SetGray_Stroke(); - void Handle_SetExtendGraphState(); - void Handle_ClosePath(); - void Handle_SetFlat(); - void Handle_BeginImageData(); - void Handle_SetLineJoin(); - void Handle_SetLineCap(); - void Handle_SetCMYKColor_Fill(); - void Handle_SetCMYKColor_Stroke(); - void Handle_LineTo(); - void Handle_MoveTo(); - void Handle_SetMiterLimit(); - void Handle_MarkPlace(); - void Handle_EndPath(); - void Handle_SaveGraphState(); - void Handle_RestoreGraphState(); - void Handle_Rectangle(); - void Handle_SetRGBColor_Fill(); - void Handle_SetRGBColor_Stroke(); - void Handle_SetRenderIntent(); - void Handle_CloseStrokePath(); - void Handle_StrokePath(); - void Handle_SetColor_Fill(); - void Handle_SetColor_Stroke(); - void Handle_SetColorPS_Fill(); - void Handle_SetColorPS_Stroke(); - void Handle_ShadeFill(); - void Handle_SetCharSpace(); - void Handle_MoveTextPoint(); - void Handle_MoveTextPoint_SetLeading(); - void Handle_SetFont(); - void Handle_ShowText(); - void Handle_ShowText_Positioning(); - void Handle_SetTextLeading(); - void Handle_SetTextMatrix(); - void Handle_SetTextRenderMode(); - void Handle_SetTextRise(); - void Handle_SetWordSpace(); - void Handle_SetHorzScale(); - void Handle_MoveToNextLine(); - void Handle_CurveTo_23(); - void Handle_SetLineWidth(); - void Handle_Clip(); - void Handle_EOClip(); - void Handle_CurveTo_13(); - void Handle_NextLineShowText(); - void Handle_NextLineShowText_Space(); - void Handle_Invalid(); - - CPDF_Document* const m_pDocument; - CPDF_Dictionary* m_pPageResources; - CPDF_Dictionary* m_pParentResources; - CPDF_Dictionary* m_pResources; - CPDF_PageObjects* m_pObjectList; - int m_Level; - CFX_AffineMatrix m_mtContentToUser; - CFX_FloatRect m_BBox; - CPDF_ParseOptions m_Options; - _ContentParam m_ParamBuf1[PARAM_BUF_SIZE]; - FX_DWORD m_ParamStartPos; - FX_DWORD m_ParamCount; - FX_BOOL m_bAbort; - CPDF_StreamParser* m_pSyntax; - nonstd::unique_ptr m_pCurStates; - CPDF_ContentMark m_CurContentMark; - CFX_PtrArray m_ClipTextList; - CPDF_TextObject* m_pLastTextObject; - FX_FLOAT m_DefFontSize; - int m_CompatCount; - FX_PATHPOINT* m_pPathPoints; - int m_PathPointCount; - int m_PathAllocSize; - FX_FLOAT m_PathStartX; - FX_FLOAT m_PathStartY; - FX_FLOAT m_PathCurrentX; - FX_FLOAT m_PathCurrentY; - int m_PathClipType; - CFX_ByteString m_LastImageName; - CPDF_Image* m_pLastImage; - CFX_BinaryBuf m_LastImageDict; - CFX_BinaryBuf m_LastImageData; - CPDF_Dictionary* m_pLastImageDict; - CPDF_Dictionary* m_pLastCloneImageDict; - FX_BOOL m_bReleaseLastDict; - FX_BOOL m_bSameLastDict; - FX_BOOL m_bColored; - FX_FLOAT m_Type3Data[6]; - FX_BOOL m_bResourceMissing; - CFX_PtrArray m_StateStack; +class CPDF_StreamContentParser { + public: + CPDF_StreamContentParser(CPDF_Document* pDoc, + CPDF_Dictionary* pPageResources, + CPDF_Dictionary* pParentResources, + CFX_AffineMatrix* pmtContentToUser, + CPDF_PageObjects* pObjList, + CPDF_Dictionary* pResources, + CFX_FloatRect* pBBox, + CPDF_ParseOptions* pOptions, + CPDF_AllStates* pAllStates, + int level); + ~CPDF_StreamContentParser(); + + FX_BOOL ShouldAbort() const { return m_bAbort; } + CPDF_PageObjects* GetObjectList() const { return m_pObjectList; } + CPDF_AllStates* GetCurStates() const { return m_pCurStates.get(); } + FX_BOOL IsColored() const { return m_bColored; } + const FX_FLOAT* GetType3Data() const { return m_Type3Data; } + + void AddNumberParam(const FX_CHAR* str, int len); + void AddObjectParam(CPDF_Object* pObj); + void AddNameParam(const FX_CHAR* name, int size); + int GetNextParamPos(); + void ClearAllParams(); + CPDF_Object* GetObject(FX_DWORD index); + CFX_ByteString GetString(FX_DWORD index); + FX_FLOAT GetNumber(FX_DWORD index); + FX_FLOAT GetNumber16(FX_DWORD index); + int GetInteger(FX_DWORD index) { return (int32_t)(GetNumber(index)); } + FX_BOOL OnOperator(const FX_CHAR* op); + void BigCaseCaller(int index); + FX_DWORD GetParsePos() { return m_pSyntax->GetPos(); } + void AddTextObject(CFX_ByteString* pText, + FX_FLOAT fInitKerning, + FX_FLOAT* pKerning, + int count); + + void ConvertUserSpace(FX_FLOAT& x, FX_FLOAT& y); + void ConvertTextSpace(FX_FLOAT& x, FX_FLOAT& y); + void OnChangeTextMatrix(); + FX_DWORD Parse(const uint8_t* pData, FX_DWORD dwSize, FX_DWORD max_cost); + void ParsePathObject(); + void AddPathPoint(FX_FLOAT x, FX_FLOAT y, int flag); + void AddPathRect(FX_FLOAT x, FX_FLOAT y, FX_FLOAT w, FX_FLOAT h); + void AddPathObject(int FillType, FX_BOOL bStroke); + CPDF_ImageObject* AddImage(CPDF_Stream* pStream, + CPDF_Image* pImage, + FX_BOOL bInline); + void AddDuplicateImage(); + void AddForm(CPDF_Stream*); + void SetGraphicStates(CPDF_PageObject* pObj, + FX_BOOL bColor, + FX_BOOL bText, + FX_BOOL bGraph); + void SaveStates(CPDF_AllStates*); + void RestoreStates(CPDF_AllStates*); + CPDF_Font* FindFont(const CFX_ByteString& name); + CPDF_ColorSpace* FindColorSpace(const CFX_ByteString& name); + CPDF_Pattern* FindPattern(const CFX_ByteString& name, FX_BOOL bShading); + CPDF_Object* FindResourceObj(const CFX_ByteStringC& type, + const CFX_ByteString& name); + + protected: + struct OpCode { + FX_DWORD m_OpId; + void (CPDF_StreamContentParser::*m_OpHandler)(); + }; + static const OpCode g_OpCodes[]; + + void Handle_CloseFillStrokePath(); + void Handle_FillStrokePath(); + void Handle_CloseEOFillStrokePath(); + void Handle_EOFillStrokePath(); + void Handle_BeginMarkedContent_Dictionary(); + void Handle_BeginImage(); + void Handle_BeginMarkedContent(); + void Handle_BeginText(); + void Handle_BeginSectionUndefined(); + void Handle_CurveTo_123(); + void Handle_ConcatMatrix(); + void Handle_SetColorSpace_Fill(); + void Handle_SetColorSpace_Stroke(); + void Handle_SetDash(); + void Handle_SetCharWidth(); + void Handle_SetCachedDevice(); + void Handle_ExecuteXObject(); + void Handle_MarkPlace_Dictionary(); + void Handle_EndImage(); + void Handle_EndMarkedContent(); + void Handle_EndText(); + void Handle_EndSectionUndefined(); + void Handle_FillPath(); + void Handle_FillPathOld(); + void Handle_EOFillPath(); + void Handle_SetGray_Fill(); + void Handle_SetGray_Stroke(); + void Handle_SetExtendGraphState(); + void Handle_ClosePath(); + void Handle_SetFlat(); + void Handle_BeginImageData(); + void Handle_SetLineJoin(); + void Handle_SetLineCap(); + void Handle_SetCMYKColor_Fill(); + void Handle_SetCMYKColor_Stroke(); + void Handle_LineTo(); + void Handle_MoveTo(); + void Handle_SetMiterLimit(); + void Handle_MarkPlace(); + void Handle_EndPath(); + void Handle_SaveGraphState(); + void Handle_RestoreGraphState(); + void Handle_Rectangle(); + void Handle_SetRGBColor_Fill(); + void Handle_SetRGBColor_Stroke(); + void Handle_SetRenderIntent(); + void Handle_CloseStrokePath(); + void Handle_StrokePath(); + void Handle_SetColor_Fill(); + void Handle_SetColor_Stroke(); + void Handle_SetColorPS_Fill(); + void Handle_SetColorPS_Stroke(); + void Handle_ShadeFill(); + void Handle_SetCharSpace(); + void Handle_MoveTextPoint(); + void Handle_MoveTextPoint_SetLeading(); + void Handle_SetFont(); + void Handle_ShowText(); + void Handle_ShowText_Positioning(); + void Handle_SetTextLeading(); + void Handle_SetTextMatrix(); + void Handle_SetTextRenderMode(); + void Handle_SetTextRise(); + void Handle_SetWordSpace(); + void Handle_SetHorzScale(); + void Handle_MoveToNextLine(); + void Handle_CurveTo_23(); + void Handle_SetLineWidth(); + void Handle_Clip(); + void Handle_EOClip(); + void Handle_CurveTo_13(); + void Handle_NextLineShowText(); + void Handle_NextLineShowText_Space(); + void Handle_Invalid(); + + CPDF_Document* const m_pDocument; + CPDF_Dictionary* m_pPageResources; + CPDF_Dictionary* m_pParentResources; + CPDF_Dictionary* m_pResources; + CPDF_PageObjects* m_pObjectList; + int m_Level; + CFX_AffineMatrix m_mtContentToUser; + CFX_FloatRect m_BBox; + CPDF_ParseOptions m_Options; + _ContentParam m_ParamBuf1[PARAM_BUF_SIZE]; + FX_DWORD m_ParamStartPos; + FX_DWORD m_ParamCount; + FX_BOOL m_bAbort; + CPDF_StreamParser* m_pSyntax; + nonstd::unique_ptr m_pCurStates; + CPDF_ContentMark m_CurContentMark; + CFX_PtrArray m_ClipTextList; + CPDF_TextObject* m_pLastTextObject; + FX_FLOAT m_DefFontSize; + int m_CompatCount; + FX_PATHPOINT* m_pPathPoints; + int m_PathPointCount; + int m_PathAllocSize; + FX_FLOAT m_PathStartX; + FX_FLOAT m_PathStartY; + FX_FLOAT m_PathCurrentX; + FX_FLOAT m_PathCurrentY; + int m_PathClipType; + CFX_ByteString m_LastImageName; + CPDF_Image* m_pLastImage; + CFX_BinaryBuf m_LastImageDict; + CFX_BinaryBuf m_LastImageData; + CPDF_Dictionary* m_pLastImageDict; + CPDF_Dictionary* m_pLastCloneImageDict; + FX_BOOL m_bReleaseLastDict; + FX_BOOL m_bSameLastDict; + FX_BOOL m_bColored; + FX_FLOAT m_Type3Data[6]; + FX_BOOL m_bResourceMissing; + CFX_PtrArray m_StateStack; }; -class CPDF_ContentParser -{ -public: - enum ParseStatus { - Ready, - ToBeContinued, - Done - }; - - CPDF_ContentParser(); - ~CPDF_ContentParser(); - - ParseStatus GetStatus() - { - return m_Status; - } - void Start(CPDF_Page* pPage, CPDF_ParseOptions* pOptions); - void Start(CPDF_Form* pForm, CPDF_AllStates* pGraphicStates, CFX_AffineMatrix* pParentMatrix, - CPDF_Type3Char* pType3Char, CPDF_ParseOptions* pOptions, int level); - void Continue(IFX_Pause* pPause); - -protected: - void Clear(); - ParseStatus m_Status; - CPDF_PageObjects* m_pObjects; - FX_BOOL m_bForm; - CPDF_ParseOptions m_Options; - CPDF_Type3Char* m_pType3Char; - int m_InternalStage; - CPDF_StreamAcc* m_pSingleStream; - CPDF_StreamAcc** m_pStreamArray; - FX_DWORD m_nStreams; - uint8_t* m_pData; - FX_DWORD m_Size; - class CPDF_StreamContentParser* m_pParser; - FX_DWORD m_CurrentOffset; - CPDF_StreamFilter* m_pStreamFilter; +class CPDF_ContentParser { + public: + enum ParseStatus { Ready, ToBeContinued, Done }; + + CPDF_ContentParser(); + ~CPDF_ContentParser(); + + ParseStatus GetStatus() { return m_Status; } + void Start(CPDF_Page* pPage, CPDF_ParseOptions* pOptions); + void Start(CPDF_Form* pForm, + CPDF_AllStates* pGraphicStates, + CFX_AffineMatrix* pParentMatrix, + CPDF_Type3Char* pType3Char, + CPDF_ParseOptions* pOptions, + int level); + void Continue(IFX_Pause* pPause); + + protected: + void Clear(); + ParseStatus m_Status; + CPDF_PageObjects* m_pObjects; + FX_BOOL m_bForm; + CPDF_ParseOptions m_Options; + CPDF_Type3Char* m_pType3Char; + int m_InternalStage; + CPDF_StreamAcc* m_pSingleStream; + CPDF_StreamAcc** m_pStreamArray; + FX_DWORD m_nStreams; + uint8_t* m_pData; + FX_DWORD m_Size; + class CPDF_StreamContentParser* m_pParser; + FX_DWORD m_CurrentOffset; + CPDF_StreamFilter* m_pStreamFilter; }; -class CPDF_AllStates : public CPDF_GraphicStates -{ -public: - CPDF_AllStates(); - ~CPDF_AllStates(); - void Copy(const CPDF_AllStates& src); - void ProcessExtGS(CPDF_Dictionary* pGS, CPDF_StreamContentParser* pParser); - void SetLineDash(CPDF_Array*, FX_FLOAT, FX_FLOAT scale); - CFX_AffineMatrix m_TextMatrix, m_CTM, m_ParentMatrix; - FX_FLOAT m_TextX, m_TextY, m_TextLineX, m_TextLineY; - FX_FLOAT m_TextLeading, m_TextRise, m_TextHorzScale; +class CPDF_AllStates : public CPDF_GraphicStates { + public: + CPDF_AllStates(); + ~CPDF_AllStates(); + void Copy(const CPDF_AllStates& src); + void ProcessExtGS(CPDF_Dictionary* pGS, CPDF_StreamContentParser* pParser); + void SetLineDash(CPDF_Array*, FX_FLOAT, FX_FLOAT scale); + CFX_AffineMatrix m_TextMatrix, m_CTM, m_ParentMatrix; + FX_FLOAT m_TextX, m_TextY, m_TextLineX, m_TextLineY; + FX_FLOAT m_TextLeading, m_TextRise, m_TextHorzScale; }; -class CPDF_DocPageData -{ - public: - explicit CPDF_DocPageData(CPDF_Document *pPDFDoc); - ~CPDF_DocPageData(); - - void Clear(FX_BOOL bRelease = FALSE); - CPDF_Font* GetFont(CPDF_Dictionary* pFontDict, FX_BOOL findOnly); - CPDF_Font* GetStandardFont(const CFX_ByteStringC& fontName, CPDF_FontEncoding* pEncoding); - void ReleaseFont(CPDF_Dictionary* pFontDict); - CPDF_ColorSpace* GetColorSpace(CPDF_Object* pCSObj, CPDF_Dictionary* pResources); - CPDF_ColorSpace* GetCopiedColorSpace(CPDF_Object* pCSObj); - void ReleaseColorSpace(CPDF_Object* pColorSpace); - CPDF_Pattern* GetPattern(CPDF_Object* pPatternObj, FX_BOOL bShading, const CFX_AffineMatrix* matrix); - void ReleasePattern(CPDF_Object* pPatternObj); - CPDF_Image* GetImage(CPDF_Object* pImageStream); - void ReleaseImage(CPDF_Object* pImageStream); - CPDF_IccProfile* GetIccProfile(CPDF_Stream* pIccProfileStream); - void ReleaseIccProfile(CPDF_IccProfile* pIccProfile); - CPDF_StreamAcc* GetFontFileStreamAcc(CPDF_Stream* pFontStream); - void ReleaseFontFileStreamAcc(CPDF_Stream* pFontStream, FX_BOOL bForce = FALSE); - FX_BOOL IsForceClear() const {return m_bForceClear;} - CPDF_CountedColorSpace* FindColorSpacePtr(CPDF_Object* pCSObj) const; - CPDF_CountedPattern* FindPatternPtr(CPDF_Object* pPatternObj) const; - - private: - using CPDF_CountedFont = CPDF_CountedObject; - using CPDF_CountedIccProfile = CPDF_CountedObject; - using CPDF_CountedImage = CPDF_CountedObject; - using CPDF_CountedStreamAcc = CPDF_CountedObject; - - using CPDF_ColorSpaceMap = std::map; - using CPDF_FontFileMap = std::map; - using CPDF_FontMap = std::map; - using CPDF_IccProfileMap = std::map; - using CPDF_ImageMap = std::map; - using CPDF_PatternMap = std::map; - - CPDF_Document* const m_pPDFDoc; - CFX_MapByteStringToPtr m_HashProfileMap; - FX_BOOL m_bForceClear; - - CPDF_ColorSpaceMap m_ColorSpaceMap; - CPDF_FontFileMap m_FontFileMap; - CPDF_FontMap m_FontMap; - CPDF_IccProfileMap m_IccProfileMap; - CPDF_ImageMap m_ImageMap; - CPDF_PatternMap m_PatternMap; +class CPDF_DocPageData { + public: + explicit CPDF_DocPageData(CPDF_Document* pPDFDoc); + ~CPDF_DocPageData(); + + void Clear(FX_BOOL bRelease = FALSE); + CPDF_Font* GetFont(CPDF_Dictionary* pFontDict, FX_BOOL findOnly); + CPDF_Font* GetStandardFont(const CFX_ByteStringC& fontName, + CPDF_FontEncoding* pEncoding); + void ReleaseFont(CPDF_Dictionary* pFontDict); + CPDF_ColorSpace* GetColorSpace(CPDF_Object* pCSObj, + CPDF_Dictionary* pResources); + CPDF_ColorSpace* GetCopiedColorSpace(CPDF_Object* pCSObj); + void ReleaseColorSpace(CPDF_Object* pColorSpace); + CPDF_Pattern* GetPattern(CPDF_Object* pPatternObj, + FX_BOOL bShading, + const CFX_AffineMatrix* matrix); + void ReleasePattern(CPDF_Object* pPatternObj); + CPDF_Image* GetImage(CPDF_Object* pImageStream); + void ReleaseImage(CPDF_Object* pImageStream); + CPDF_IccProfile* GetIccProfile(CPDF_Stream* pIccProfileStream); + void ReleaseIccProfile(CPDF_IccProfile* pIccProfile); + CPDF_StreamAcc* GetFontFileStreamAcc(CPDF_Stream* pFontStream); + void ReleaseFontFileStreamAcc(CPDF_Stream* pFontStream, + FX_BOOL bForce = FALSE); + FX_BOOL IsForceClear() const { return m_bForceClear; } + CPDF_CountedColorSpace* FindColorSpacePtr(CPDF_Object* pCSObj) const; + CPDF_CountedPattern* FindPatternPtr(CPDF_Object* pPatternObj) const; + + private: + using CPDF_CountedFont = CPDF_CountedObject; + using CPDF_CountedIccProfile = CPDF_CountedObject; + using CPDF_CountedImage = CPDF_CountedObject; + using CPDF_CountedStreamAcc = CPDF_CountedObject; + + using CPDF_ColorSpaceMap = std::map; + using CPDF_FontFileMap = std::map; + using CPDF_FontMap = std::map; + using CPDF_IccProfileMap = std::map; + using CPDF_ImageMap = std::map; + using CPDF_PatternMap = std::map; + + CPDF_Document* const m_pPDFDoc; + CFX_MapByteStringToPtr m_HashProfileMap; + FX_BOOL m_bForceClear; + + CPDF_ColorSpaceMap m_ColorSpaceMap; + CPDF_FontFileMap m_FontFileMap; + CPDF_FontMap m_FontMap; + CPDF_IccProfileMap m_IccProfileMap; + CPDF_ImageMap m_ImageMap; + CPDF_PatternMap m_PatternMap; }; -class CPDF_Function -{ -public: - static CPDF_Function* Load(CPDF_Object* pFuncObj); - virtual ~CPDF_Function(); - FX_BOOL Call(FX_FLOAT* inputs, int ninputs, FX_FLOAT* results, int& nresults) const; - int CountInputs() - { - return m_nInputs; - } - int CountOutputs() - { - return m_nOutputs; - } -protected: - CPDF_Function(); - int m_nInputs, m_nOutputs; - FX_FLOAT* m_pDomains; - FX_FLOAT* m_pRanges; - FX_BOOL Init(CPDF_Object* pObj); - virtual FX_BOOL v_Init(CPDF_Object* pObj) = 0; - virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const = 0; +class CPDF_Function { + public: + static CPDF_Function* Load(CPDF_Object* pFuncObj); + virtual ~CPDF_Function(); + FX_BOOL Call(FX_FLOAT* inputs, + int ninputs, + FX_FLOAT* results, + int& nresults) const; + int CountInputs() { return m_nInputs; } + int CountOutputs() { return m_nOutputs; } + + protected: + CPDF_Function(); + int m_nInputs, m_nOutputs; + FX_FLOAT* m_pDomains; + FX_FLOAT* m_pRanges; + FX_BOOL Init(CPDF_Object* pObj); + virtual FX_BOOL v_Init(CPDF_Object* pObj) = 0; + virtual FX_BOOL v_Call(FX_FLOAT* inputs, FX_FLOAT* results) const = 0; }; -class CPDF_IccProfile -{ -public: - CPDF_IccProfile(const uint8_t* pData, FX_DWORD dwSize); - ~CPDF_IccProfile(); - int32_t GetComponents() const { return m_nSrcComponents; } - FX_BOOL m_bsRGB; - void* m_pTransform; -private: - int32_t m_nSrcComponents; +class CPDF_IccProfile { + public: + CPDF_IccProfile(const uint8_t* pData, FX_DWORD dwSize); + ~CPDF_IccProfile(); + int32_t GetComponents() const { return m_nSrcComponents; } + FX_BOOL m_bsRGB; + void* m_pTransform; + + private: + int32_t m_nSrcComponents; }; -class CPDF_DeviceCS : public CPDF_ColorSpace -{ -public: - CPDF_DeviceCS(CPDF_Document* pDoc, int family); - - FX_BOOL GetRGB(FX_FLOAT* pBuf, - FX_FLOAT& R, - FX_FLOAT& G, - FX_FLOAT& B) const override; - FX_BOOL SetRGB(FX_FLOAT* pBuf, - FX_FLOAT R, - FX_FLOAT G, - FX_FLOAT B) const override; - FX_BOOL v_GetCMYK(FX_FLOAT* pBuf, - FX_FLOAT& c, - FX_FLOAT& m, - FX_FLOAT& y, - FX_FLOAT& k) const override; - FX_BOOL v_SetCMYK(FX_FLOAT* pBuf, - FX_FLOAT c, - FX_FLOAT m, - FX_FLOAT y, - FX_FLOAT k) const override; - void TranslateImageLine(uint8_t* pDestBuf, - const uint8_t* pSrcBuf, - int pixels, - int image_width, - int image_height, - FX_BOOL bTransMask = FALSE) const override; +class CPDF_DeviceCS : public CPDF_ColorSpace { + public: + CPDF_DeviceCS(CPDF_Document* pDoc, int family); + + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + FX_BOOL SetRGB(FX_FLOAT* pBuf, + FX_FLOAT R, + FX_FLOAT G, + FX_FLOAT B) const override; + FX_BOOL v_GetCMYK(FX_FLOAT* pBuf, + FX_FLOAT& c, + FX_FLOAT& m, + FX_FLOAT& y, + FX_FLOAT& k) const override; + FX_BOOL v_SetCMYK(FX_FLOAT* pBuf, + FX_FLOAT c, + FX_FLOAT m, + FX_FLOAT y, + FX_FLOAT k) const override; + void TranslateImageLine(uint8_t* pDestBuf, + const uint8_t* pSrcBuf, + int pixels, + int image_width, + int image_height, + FX_BOOL bTransMask = FALSE) const override; }; -class CPDF_PatternCS : public CPDF_ColorSpace -{ -public: - explicit CPDF_PatternCS(CPDF_Document* pDoc) - : CPDF_ColorSpace(pDoc, PDFCS_PATTERN, 1), - m_pBaseCS(nullptr), - m_pCountedBaseCS(nullptr) { - } - ~CPDF_PatternCS() override; - FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; - FX_BOOL GetRGB(FX_FLOAT* pBuf, - FX_FLOAT& R, - FX_FLOAT& G, - FX_FLOAT& B) const override; - CPDF_ColorSpace* GetBaseCS() const override; - -private: - CPDF_ColorSpace* m_pBaseCS; - CPDF_CountedColorSpace* m_pCountedBaseCS; +class CPDF_PatternCS : public CPDF_ColorSpace { + public: + explicit CPDF_PatternCS(CPDF_Document* pDoc) + : CPDF_ColorSpace(pDoc, PDFCS_PATTERN, 1), + m_pBaseCS(nullptr), + m_pCountedBaseCS(nullptr) {} + ~CPDF_PatternCS() override; + FX_BOOL v_Load(CPDF_Document* pDoc, CPDF_Array* pArray) override; + FX_BOOL GetRGB(FX_FLOAT* pBuf, + FX_FLOAT& R, + FX_FLOAT& G, + FX_FLOAT& B) const override; + CPDF_ColorSpace* GetBaseCS() const override; + + private: + CPDF_ColorSpace* m_pBaseCS; + CPDF_CountedColorSpace* m_pCountedBaseCS; }; #endif // CORE_SRC_FPDFAPI_FPDF_PAGE_PAGEINT_H_ -- cgit v1.2.3