diff options
Diffstat (limited to 'core/fpdfapi')
-rw-r--r-- | core/fpdfapi/edit/cpdf_pagecontentgenerator.cpp | 7 | ||||
-rw-r--r-- | core/fpdfapi/edit/cpdf_pagecontentgenerator_unittest.cpp | 99 | ||||
-rw-r--r-- | core/fpdfapi/page/cpdf_path.cpp | 17 | ||||
-rw-r--r-- | core/fpdfapi/page/cpdf_path.h | 8 | ||||
-rw-r--r-- | core/fpdfapi/page/cpdf_streamcontentparser.cpp | 10 | ||||
-rw-r--r-- | core/fpdfapi/render/cpdf_renderstatus.cpp | 59 |
6 files changed, 74 insertions, 126 deletions
diff --git a/core/fpdfapi/edit/cpdf_pagecontentgenerator.cpp b/core/fpdfapi/edit/cpdf_pagecontentgenerator.cpp index 4de89a47de..ff8b676de1 100644 --- a/core/fpdfapi/edit/cpdf_pagecontentgenerator.cpp +++ b/core/fpdfapi/edit/cpdf_pagecontentgenerator.cpp @@ -148,14 +148,13 @@ void CPDF_PageContentGenerator::ProcessImage(CFX_ByteTextBuf* buf, void CPDF_PageContentGenerator::ProcessPath(CFX_ByteTextBuf* buf, CPDF_PathObject* pPathObj) { ProcessGraphics(buf, pPathObj); - const FX_PATHPOINT* pPoints = pPathObj->m_Path.GetPoints(); + auto& pPoints = pPathObj->m_Path.GetPoints(); if (pPathObj->m_Path.IsRect()) { *buf << pPoints[0].m_PointX << " " << pPoints[0].m_PointY << " " << (pPoints[2].m_PointX - pPoints[0].m_PointX) << " " << (pPoints[2].m_PointY - pPoints[0].m_PointY) << " re"; } else { - int numPoints = pPathObj->m_Path.GetPointCount(); - for (int i = 0; i < numPoints; i++) { + for (size_t i = 0; i < pPoints.size(); i++) { if (i > 0) *buf << " "; *buf << pPoints[i].m_PointX << " " << pPoints[i].m_PointY; @@ -165,7 +164,7 @@ void CPDF_PageContentGenerator::ProcessPath(CFX_ByteTextBuf* buf, } else if (pointType == FXPT_TYPE::LineTo) { *buf << " l"; } else if (pointType == FXPT_TYPE::BezierTo) { - if (i + 2 >= numPoints || + if (i + 2 >= pPoints.size() || !pPoints[i].IsTypeAndOpen(FXPT_TYPE::BezierTo) || !pPoints[i + 1].IsTypeAndOpen(FXPT_TYPE::BezierTo) || pPoints[i + 2].m_Type != FXPT_TYPE::BezierTo) { diff --git a/core/fpdfapi/edit/cpdf_pagecontentgenerator_unittest.cpp b/core/fpdfapi/edit/cpdf_pagecontentgenerator_unittest.cpp index 0a636a1888..42e6e2d843 100644 --- a/core/fpdfapi/edit/cpdf_pagecontentgenerator_unittest.cpp +++ b/core/fpdfapi/edit/cpdf_pagecontentgenerator_unittest.cpp @@ -44,6 +44,7 @@ TEST_F(CPDF_PageContentGeneratorTest, ProcessRect) { pPathObj->m_Path.AppendRect(10, 5, 13, 30); pPathObj->m_FillType = FXFILL_ALTERNATE; pPathObj->m_bStroke = true; + auto pTestPage = pdfium::MakeUnique<CPDF_Page>(nullptr, nullptr, false); CPDF_PageContentGenerator generator(pTestPage.get()); CFX_ByteTextBuf buf; @@ -51,77 +52,33 @@ TEST_F(CPDF_PageContentGeneratorTest, ProcessRect) { EXPECT_EQ("q 10 5 3 25 re B* Q\n", buf.MakeString()); pPathObj = pdfium::MakeUnique<CPDF_PathObject>(); - pPathObj->m_Path.SetPointCount(4); - FX_PATHPOINT* pPoints = pPathObj->m_Path.GetMutablePoints(); - pPoints[0].m_PointX = 0; - pPoints[0].m_PointY = 0; - pPoints[0].m_Type = FXPT_TYPE::MoveTo; - pPoints[0].m_CloseFigure = false; - pPoints[1].m_PointX = 5.2f; - pPoints[1].m_PointY = 0; - pPoints[1].m_Type = FXPT_TYPE::LineTo; - pPoints[1].m_CloseFigure = false; - pPoints[2].m_PointX = 5.2f; - pPoints[2].m_PointY = 3.78f; - pPoints[2].m_Type = FXPT_TYPE::LineTo; - pPoints[2].m_CloseFigure = false; - pPoints[3].m_PointX = 0; - pPoints[3].m_PointY = 3.78f; - pPoints[3].m_Type = FXPT_TYPE::LineTo; - pPoints[3].m_CloseFigure = true; + pPathObj->m_Path.AppendPoint(0, 0, FXPT_TYPE::MoveTo, false); + pPathObj->m_Path.AppendPoint(5.2f, 0, FXPT_TYPE::LineTo, false); + pPathObj->m_Path.AppendPoint(5.2f, 3.78f, FXPT_TYPE::LineTo, false); + pPathObj->m_Path.AppendPoint(0, 3.78f, FXPT_TYPE::LineTo, true); pPathObj->m_FillType = 0; pPathObj->m_bStroke = false; buf.Clear(); + TestProcessPath(&generator, &buf, pPathObj.get()); EXPECT_EQ("q 0 0 5.2 3.78 re n Q\n", buf.MakeString()); } TEST_F(CPDF_PageContentGeneratorTest, ProcessPath) { auto pPathObj = pdfium::MakeUnique<CPDF_PathObject>(); - pPathObj->m_Path.SetPointCount(10); - FX_PATHPOINT* pPoints = pPathObj->m_Path.GetMutablePoints(); - pPoints[0].m_PointX = 3.102f; - pPoints[0].m_PointY = 4.67f; - pPoints[0].m_Type = FXPT_TYPE::MoveTo; - pPoints[0].m_CloseFigure = false; - pPoints[1].m_PointX = 5.45f; - pPoints[1].m_PointY = 0.29f; - pPoints[1].m_Type = FXPT_TYPE::LineTo; - pPoints[1].m_CloseFigure = false; - pPoints[2].m_PointX = 4.24f; - pPoints[2].m_PointY = 3.15f; - pPoints[2].m_Type = FXPT_TYPE::BezierTo; - pPoints[2].m_CloseFigure = false; - pPoints[3].m_PointX = 4.65f; - pPoints[3].m_PointY = 2.98f; - pPoints[3].m_Type = FXPT_TYPE::BezierTo; - pPoints[3].m_CloseFigure = false; - pPoints[4].m_PointX = 3.456f; - pPoints[4].m_PointY = 0.24f; - pPoints[4].m_Type = FXPT_TYPE::BezierTo; - pPoints[4].m_CloseFigure = false; - pPoints[5].m_PointX = 10.6f; - pPoints[5].m_PointY = 11.15f; - pPoints[5].m_Type = FXPT_TYPE::LineTo; - pPoints[5].m_CloseFigure = false; - pPoints[6].m_PointX = 11; - pPoints[6].m_PointY = 12.5f; - pPoints[6].m_Type = FXPT_TYPE::LineTo; - pPoints[6].m_CloseFigure = false; - pPoints[7].m_PointX = 11.46f; - pPoints[7].m_PointY = 12.67f; - pPoints[7].m_Type = FXPT_TYPE::BezierTo; - pPoints[7].m_CloseFigure = false; - pPoints[8].m_PointX = 11.84f; - pPoints[8].m_PointY = 12.96f; - pPoints[8].m_Type = FXPT_TYPE::BezierTo; - pPoints[8].m_CloseFigure = false; - pPoints[9].m_PointX = 12; - pPoints[9].m_PointY = 13.64f; - pPoints[9].m_Type = FXPT_TYPE::BezierTo; - pPoints[9].m_CloseFigure = true; + pPathObj->m_Path.AppendPoint(3.102f, 4.67f, FXPT_TYPE::MoveTo, false); + pPathObj->m_Path.AppendPoint(5.45f, 0.29f, FXPT_TYPE::LineTo, false); + pPathObj->m_Path.AppendPoint(4.24f, 3.15f, FXPT_TYPE::BezierTo, false); + pPathObj->m_Path.AppendPoint(4.65f, 2.98f, FXPT_TYPE::BezierTo, false); + pPathObj->m_Path.AppendPoint(3.456f, 0.24f, FXPT_TYPE::BezierTo, false); + pPathObj->m_Path.AppendPoint(10.6f, 11.15f, FXPT_TYPE::LineTo, false); + pPathObj->m_Path.AppendPoint(11, 12.5f, FXPT_TYPE::LineTo, false); + pPathObj->m_Path.AppendPoint(11.46f, 12.67f, FXPT_TYPE::BezierTo, false); + pPathObj->m_Path.AppendPoint(11.84f, 12.96f, FXPT_TYPE::BezierTo, false); + pPathObj->m_Path.AppendPoint(12, 13.64f, FXPT_TYPE::BezierTo, true); pPathObj->m_FillType = FXFILL_WINDING; pPathObj->m_bStroke = false; + auto pTestPage = pdfium::MakeUnique<CPDF_Page>(nullptr, nullptr, false); CPDF_PageContentGenerator generator(pTestPage.get()); CFX_ByteTextBuf buf; @@ -134,29 +91,21 @@ TEST_F(CPDF_PageContentGeneratorTest, ProcessPath) { TEST_F(CPDF_PageContentGeneratorTest, ProcessGraphics) { auto pPathObj = pdfium::MakeUnique<CPDF_PathObject>(); - pPathObj->m_Path.SetPointCount(3); - FX_PATHPOINT* pPoints = pPathObj->m_Path.GetMutablePoints(); - pPoints[0].m_PointX = 1; - pPoints[0].m_PointY = 2; - pPoints[0].m_Type = FXPT_TYPE::MoveTo; - pPoints[0].m_CloseFigure = false; - pPoints[1].m_PointX = 3; - pPoints[1].m_PointY = 4; - pPoints[1].m_Type = FXPT_TYPE::LineTo; - pPoints[1].m_CloseFigure = false; - pPoints[2].m_PointX = 5; - pPoints[2].m_PointY = 6; - pPoints[2].m_Type = FXPT_TYPE::LineTo; - pPoints[2].m_CloseFigure = true; + pPathObj->m_Path.AppendPoint(1, 2, FXPT_TYPE::MoveTo, false); + pPathObj->m_Path.AppendPoint(3, 4, FXPT_TYPE::LineTo, false); + pPathObj->m_Path.AppendPoint(5, 6, FXPT_TYPE::LineTo, true); pPathObj->m_FillType = FXFILL_WINDING; pPathObj->m_bStroke = true; + FX_FLOAT rgb[3] = {0.5f, 0.7f, 0.35f}; CPDF_ColorSpace* pCS = CPDF_ColorSpace::GetStockCS(PDFCS_DEVICERGB); pPathObj->m_ColorState.SetFillColor(pCS, rgb, 3); + FX_FLOAT rgb2[3] = {1, 0.9f, 0}; pPathObj->m_ColorState.SetStrokeColor(pCS, rgb2, 3); pPathObj->m_GeneralState.SetFillAlpha(0.5f); pPathObj->m_GeneralState.SetStrokeAlpha(0.8f); + auto pDoc = pdfium::MakeUnique<CPDF_Document>(nullptr); pDoc->CreateNewDoc(); CPDF_Dictionary* pPageDict = pDoc->CreateNewPage(0); @@ -165,6 +114,7 @@ TEST_F(CPDF_PageContentGeneratorTest, ProcessGraphics) { CFX_ByteTextBuf buf; TestProcessPath(&generator, &buf, pPathObj.get()); CFX_ByteString pathString = buf.MakeString(); + // Color RGB values used are integers divided by 255. EXPECT_EQ("q 0.501961 0.701961 0.34902 rg 1 0.901961 0 RG /", pathString.Left(48)); @@ -184,6 +134,7 @@ TEST_F(CPDF_PageContentGeneratorTest, ProcessGraphics) { EXPECT_EQ("q 0.501961 0.701961 0.34902 rg 1 0.901961 0 RG 10.5 w /", pathString2.Left(55)); EXPECT_EQ(" gs 1 2 m 3 4 l 5 6 l h B Q\n", pathString2.Right(28)); + // Compare with the previous (should use same dictionary for gs) EXPECT_EQ(pathString.GetLength() + 7, pathString2.GetLength()); EXPECT_EQ(pathString.Mid(48, pathString.GetLength() - 76), diff --git a/core/fpdfapi/page/cpdf_path.cpp b/core/fpdfapi/page/cpdf_path.cpp index 96d6b72abb..a95ce1e5bc 100644 --- a/core/fpdfapi/page/cpdf_path.cpp +++ b/core/fpdfapi/page/cpdf_path.cpp @@ -12,20 +12,12 @@ CPDF_Path::CPDF_Path(const CPDF_Path& that) : m_Ref(that.m_Ref) {} CPDF_Path::~CPDF_Path() {} -int CPDF_Path::GetPointCount() const { - return m_Ref.GetObject()->GetPointCount(); -} - -void CPDF_Path::SetPointCount(int count) { - m_Ref.GetPrivateCopy()->SetPointCount(count); -} - -const FX_PATHPOINT* CPDF_Path::GetPoints() const { +const std::vector<FX_PATHPOINT>& CPDF_Path::GetPoints() const { return m_Ref.GetObject()->GetPoints(); } -FX_PATHPOINT* CPDF_Path::GetMutablePoints() { - return m_Ref.GetPrivateCopy()->GetPoints(); +void CPDF_Path::ClosePath() { + m_Ref.GetPrivateCopy()->ClosePath(); } FX_FLOAT CPDF_Path::GetPointX(int index) const { @@ -73,7 +65,6 @@ void CPDF_Path::AppendPoint(FX_FLOAT x, FXPT_TYPE type, bool close) { CFX_PathData data; - data.SetPointCount(1); - data.SetPoint(0, x, y, type, close); + data.AppendPoint(x, y, type, close); Append(&data, nullptr); } diff --git a/core/fpdfapi/page/cpdf_path.h b/core/fpdfapi/page/cpdf_path.h index 21a94becac..97dd8fd8a9 100644 --- a/core/fpdfapi/page/cpdf_path.h +++ b/core/fpdfapi/page/cpdf_path.h @@ -7,6 +7,8 @@ #ifndef CORE_FPDFAPI_PAGE_CPDF_PATH_H_ #define CORE_FPDFAPI_PAGE_CPDF_PATH_H_ +#include <vector> + #include "core/fxcrt/cfx_shared_copy_on_write.h" #include "core/fxcrt/fx_system.h" #include "core/fxge/cfx_fxgedevice.h" @@ -22,10 +24,8 @@ class CPDF_Path { void Emplace() { m_Ref.Emplace(); } explicit operator bool() const { return !!m_Ref; } - int GetPointCount() const; - void SetPointCount(int count); - const FX_PATHPOINT* GetPoints() const; - FX_PATHPOINT* GetMutablePoints(); + const std::vector<FX_PATHPOINT>& GetPoints() const; + void ClosePath(); FX_FLOAT GetPointX(int index) const; FX_FLOAT GetPointY(int index) const; diff --git a/core/fpdfapi/page/cpdf_streamcontentparser.cpp b/core/fpdfapi/page/cpdf_streamcontentparser.cpp index 0af43d08b2..e991e456b7 100644 --- a/core/fpdfapi/page/cpdf_streamcontentparser.cpp +++ b/core/fpdfapi/page/cpdf_streamcontentparser.cpp @@ -1506,10 +1506,14 @@ void CPDF_StreamContentParser::AddPathObject(int FillType, bool bStroke) { m_pPathPoints[PathPointCount - 1].IsTypeAndOpen(FXPT_TYPE::MoveTo)) { PathPointCount--; } + CPDF_Path Path; - Path.SetPointCount(PathPointCount); - FXSYS_memcpy(Path.GetMutablePoints(), m_pPathPoints, - sizeof(FX_PATHPOINT) * PathPointCount); + for (int i = 0; i < PathPointCount; i++) { + FX_PATHPOINT& point = m_pPathPoints[i]; + Path.AppendPoint(point.m_PointX, point.m_PointY, point.m_Type, + point.m_CloseFigure); + } + CFX_Matrix matrix = m_pCurStates->m_CTM; matrix.Concat(m_mtContentToUser); if (bStroke || FillType) { diff --git a/core/fpdfapi/render/cpdf_renderstatus.cpp b/core/fpdfapi/render/cpdf_renderstatus.cpp index 4f2638f276..60b57600c2 100644 --- a/core/fpdfapi/render/cpdf_renderstatus.cpp +++ b/core/fpdfapi/render/cpdf_renderstatus.cpp @@ -611,18 +611,21 @@ struct Coon_Bezier { x.FromPoints(x0, x1, x2, x3); y.FromPoints(y0, y1, y2, y3); } + Coon_Bezier first_half() { Coon_Bezier result; result.x = x.first_half(); result.y = y.first_half(); return result; } + Coon_Bezier second_half() { Coon_Bezier result; result.x = x.second_half(); result.y = y.second_half(); return result; } + void BezierInterpol(Coon_Bezier& C1, Coon_Bezier& C2, Coon_Bezier& D1, @@ -630,30 +633,31 @@ struct Coon_Bezier { x.BezierInterpol(C1.x, C2.x, D1.x, D2.x); y.BezierInterpol(C1.y, C2.y, D1.y, D2.y); } - void GetPoints(FX_PATHPOINT* pPoints) { + + void GetPoints(std::vector<FX_PATHPOINT>& pPoints, size_t start_idx) { float p[4]; int i; x.GetPoints(p); - for (i = 0; i < 4; i++) { - pPoints[i].m_PointX = p[i]; - } + for (i = 0; i < 4; i++) + pPoints[start_idx + i].m_PointX = p[i]; + y.GetPoints(p); - for (i = 0; i < 4; i++) { - pPoints[i].m_PointY = p[i]; - } + for (i = 0; i < 4; i++) + pPoints[start_idx + i].m_PointY = p[i]; } - void GetPointsReverse(FX_PATHPOINT* pPoints) { + + void GetPointsReverse(std::vector<FX_PATHPOINT>& pPoints, size_t start_idx) { float p[4]; int i; x.GetPointsReverse(p); - for (i = 0; i < 4; i++) { - pPoints[i].m_PointX = p[i]; - } + for (i = 0; i < 4; i++) + pPoints[i + start_idx].m_PointX = p[i]; + y.GetPointsReverse(p); - for (i = 0; i < 4; i++) { - pPoints[i].m_PointY = p[i]; - } + for (i = 0; i < 4; i++) + pPoints[i + start_idx].m_PointY = p[i]; } + float Distance() { return x.Distance() + y.Distance(); } }; @@ -693,6 +697,7 @@ struct Coon_Color { } }; +#define COONCOLOR_THRESHOLD 4 struct CPDF_PatchDrawer { Coon_Color patch_colors[4]; int max_delta; @@ -728,15 +733,15 @@ struct CPDF_PatchDrawer { d_top = div_colors[1].Distance(div_colors[2]); d_right = div_colors[2].Distance(div_colors[3]); } -#define COONCOLOR_THRESHOLD 4 + if (bSmall || (d_bottom < COONCOLOR_THRESHOLD && d_left < COONCOLOR_THRESHOLD && d_top < COONCOLOR_THRESHOLD && d_right < COONCOLOR_THRESHOLD)) { - FX_PATHPOINT* pPoints = path.GetPoints(); - C1.GetPoints(pPoints); - D2.GetPoints(pPoints + 3); - C2.GetPointsReverse(pPoints + 6); - D1.GetPointsReverse(pPoints + 9); + std::vector<FX_PATHPOINT>& pPoints = path.GetPoints(); + C1.GetPoints(pPoints, 0); + D2.GetPoints(pPoints, 3); + C2.GetPointsReverse(pPoints, 6); + D1.GetPointsReverse(pPoints, 9); int fillFlags = FXFILL_WINDING | FXFILL_FULLCOVER; if (fill_mode & RENDER_NOPATHSMOOTH) { fillFlags |= FXFILL_NOPATHSMOOTH; @@ -814,14 +819,12 @@ void DrawCoonPatchMeshes( patch.alpha = alpha; patch.pDevice = &device; patch.fill_mode = fill_mode; - patch.path.SetPointCount(13); - FX_PATHPOINT* pPoints = patch.path.GetPoints(); - pPoints[0].m_Type = FXPT_TYPE::MoveTo; - pPoints[0].m_CloseFigure = false; - for (int i = 1; i < 13; i++) { - pPoints[i].m_Type = FXPT_TYPE::BezierTo; - pPoints[i].m_CloseFigure = false; + + for (int i = 0; i < 13; i++) { + patch.path.AppendPoint( + 0, 0, i == 0 ? FXPT_TYPE::MoveTo : FXPT_TYPE::BezierTo, false); } + CFX_PointF coords[16]; int point_count = type == kTensorProductPatchMeshShading ? 16 : 12; while (!stream.BitStream()->IsEOF()) { @@ -1368,7 +1371,7 @@ void CPDF_RenderStatus::ProcessClipPath(CPDF_ClipPath ClipPath, if (!pPathData) continue; - if (pPathData->GetPointCount() == 0) { + if (pPathData->GetPoints().empty()) { CFX_PathData EmptyPath; EmptyPath.AppendRect(-1, -1, 0, 0); int fill_mode = FXFILL_WINDING; |