OLD | NEW |
1 // Copyright 2014 PDFium Authors. All rights reserved. | 1 // Copyright 2014 PDFium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com | 5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com |
6 | 6 |
7 #include "public/fpdf_ppo.h" | 7 #include "public/fpdf_ppo.h" |
8 | 8 |
9 #include <memory> | 9 #include <memory> |
10 | 10 |
11 #include "fpdfsdk/include/fsdk_define.h" | 11 #include "fpdfsdk/include/fsdk_define.h" |
| 12 #include "third_party/base/stl_util.h" |
12 | 13 |
13 class CPDF_PageOrganizer { | 14 class CPDF_PageOrganizer { |
14 public: | 15 public: |
15 using ObjectNumberMap = std::map<FX_DWORD, FX_DWORD>; | 16 using ObjectNumberMap = std::map<FX_DWORD, FX_DWORD>; |
16 CPDF_PageOrganizer(); | 17 CPDF_PageOrganizer(); |
17 ~CPDF_PageOrganizer(); | 18 ~CPDF_PageOrganizer(); |
18 | 19 |
19 FX_BOOL PDFDocInit(CPDF_Document* pDestPDFDoc, CPDF_Document* pSrcPDFDoc); | 20 FX_BOOL PDFDocInit(CPDF_Document* pDestPDFDoc, CPDF_Document* pSrcPDFDoc); |
20 FX_BOOL ExportPage(CPDF_Document* pSrcPDFDoc, | 21 FX_BOOL ExportPage(CPDF_Document* pSrcPDFDoc, |
21 CFX_WordArray* nPageNum, | 22 std::vector<FX_WORD>* pPageNums, |
22 CPDF_Document* pDestPDFDoc, | 23 CPDF_Document* pDestPDFDoc, |
23 int nIndex); | 24 int nIndex); |
24 CPDF_Object* PageDictGetInheritableTag(CPDF_Dictionary* pDict, | 25 CPDF_Object* PageDictGetInheritableTag(CPDF_Dictionary* pDict, |
25 CFX_ByteString nSrctag); | 26 CFX_ByteString nSrctag); |
26 FX_BOOL UpdateReference(CPDF_Object* pObj, | 27 FX_BOOL UpdateReference(CPDF_Object* pObj, |
27 CPDF_Document* pDoc, | 28 CPDF_Document* pDoc, |
28 ObjectNumberMap* pObjNumberMap); | 29 ObjectNumberMap* pObjNumberMap); |
29 FX_DWORD GetNewObjId(CPDF_Document* pDoc, | 30 FX_DWORD GetNewObjId(CPDF_Document* pDoc, |
30 ObjectNumberMap* pObjNumberMap, | 31 ObjectNumberMap* pObjNumberMap, |
31 CPDF_Reference* pRef); | 32 CPDF_Reference* pRef); |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
80 Kidsobjnum = pDestPDFDoc->AddIndirectObject(pNewKids); | 81 Kidsobjnum = pDestPDFDoc->AddIndirectObject(pNewKids); |
81 | 82 |
82 pNewPages->SetAt("Kids", new CPDF_Reference(pDestPDFDoc, Kidsobjnum)); | 83 pNewPages->SetAt("Kids", new CPDF_Reference(pDestPDFDoc, Kidsobjnum)); |
83 pNewPages->SetAt("Count", new CPDF_Number(0)); | 84 pNewPages->SetAt("Count", new CPDF_Number(0)); |
84 } | 85 } |
85 | 86 |
86 return TRUE; | 87 return TRUE; |
87 } | 88 } |
88 | 89 |
89 FX_BOOL CPDF_PageOrganizer::ExportPage(CPDF_Document* pSrcPDFDoc, | 90 FX_BOOL CPDF_PageOrganizer::ExportPage(CPDF_Document* pSrcPDFDoc, |
90 CFX_WordArray* nPageNum, | 91 std::vector<FX_WORD>* pPageNums, |
91 CPDF_Document* pDestPDFDoc, | 92 CPDF_Document* pDestPDFDoc, |
92 int nIndex) { | 93 int nIndex) { |
93 int curpage = nIndex; | 94 int curpage = nIndex; |
94 | |
95 std::unique_ptr<ObjectNumberMap> pObjNumberMap(new ObjectNumberMap); | 95 std::unique_ptr<ObjectNumberMap> pObjNumberMap(new ObjectNumberMap); |
96 | 96 int nSize = pdfium::CollectionSize<int>(*pPageNums); |
97 for (int i = 0; i < nPageNum->GetSize(); ++i) { | 97 for (int i = 0; i < nSize; ++i) { |
98 CPDF_Dictionary* pCurPageDict = pDestPDFDoc->CreateNewPage(curpage); | 98 CPDF_Dictionary* pCurPageDict = pDestPDFDoc->CreateNewPage(curpage); |
99 CPDF_Dictionary* pSrcPageDict = pSrcPDFDoc->GetPage(nPageNum->GetAt(i) - 1); | 99 CPDF_Dictionary* pSrcPageDict = pSrcPDFDoc->GetPage(pPageNums->at(i) - 1); |
100 if (!pSrcPageDict || !pCurPageDict) | 100 if (!pSrcPageDict || !pCurPageDict) |
101 return FALSE; | 101 return FALSE; |
102 | 102 |
103 // Clone the page dictionary | 103 // Clone the page dictionary |
104 for (const auto& it : *pSrcPageDict) { | 104 for (const auto& it : *pSrcPageDict) { |
105 const CFX_ByteString& cbSrcKeyStr = it.first; | 105 const CFX_ByteString& cbSrcKeyStr = it.first; |
106 CPDF_Object* pObj = it.second; | 106 CPDF_Object* pObj = it.second; |
107 if (cbSrcKeyStr.Compare(("Type")) && cbSrcKeyStr.Compare(("Parent"))) { | 107 if (cbSrcKeyStr.Compare(("Type")) && cbSrcKeyStr.Compare(("Parent"))) { |
108 if (pCurPageDict->KeyExist(cbSrcKeyStr)) | 108 if (pCurPageDict->KeyExist(cbSrcKeyStr)) |
109 pCurPageDict->RemoveAt(cbSrcKeyStr); | 109 pCurPageDict->RemoveAt(cbSrcKeyStr); |
(...skipping 189 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
299 dwNewObjNum = pDoc->AddIndirectObject(pClone); | 299 dwNewObjNum = pDoc->AddIndirectObject(pClone); |
300 (*pObjNumberMap)[dwObjnum] = dwNewObjNum; | 300 (*pObjNumberMap)[dwObjnum] = dwNewObjNum; |
301 if (!UpdateReference(pClone, pDoc, pObjNumberMap)) { | 301 if (!UpdateReference(pClone, pDoc, pObjNumberMap)) { |
302 pClone->Release(); | 302 pClone->Release(); |
303 return 0; | 303 return 0; |
304 } | 304 } |
305 return dwNewObjNum; | 305 return dwNewObjNum; |
306 } | 306 } |
307 | 307 |
308 FPDF_BOOL ParserPageRangeString(CFX_ByteString rangstring, | 308 FPDF_BOOL ParserPageRangeString(CFX_ByteString rangstring, |
309 CFX_WordArray* pageArray, | 309 std::vector<FX_WORD>* pageArray, |
310 int nCount) { | 310 int nCount) { |
311 if (rangstring.GetLength() != 0) { | 311 if (rangstring.GetLength() != 0) { |
312 rangstring.Remove(' '); | 312 rangstring.Remove(' '); |
313 int nLength = rangstring.GetLength(); | 313 int nLength = rangstring.GetLength(); |
314 CFX_ByteString cbCompareString("0123456789-,"); | 314 CFX_ByteString cbCompareString("0123456789-,"); |
315 for (int i = 0; i < nLength; ++i) { | 315 for (int i = 0; i < nLength; ++i) { |
316 if (cbCompareString.Find(rangstring[i]) == -1) | 316 if (cbCompareString.Find(rangstring[i]) == -1) |
317 return FALSE; | 317 return FALSE; |
318 } | 318 } |
319 CFX_ByteString cbMidRange; | 319 CFX_ByteString cbMidRange; |
320 int nStringFrom = 0; | 320 int nStringFrom = 0; |
321 int nStringTo = 0; | 321 int nStringTo = 0; |
322 while (nStringTo < nLength) { | 322 while (nStringTo < nLength) { |
323 nStringTo = rangstring.Find(',', nStringFrom); | 323 nStringTo = rangstring.Find(',', nStringFrom); |
324 if (nStringTo == -1) | 324 if (nStringTo == -1) |
325 nStringTo = nLength; | 325 nStringTo = nLength; |
326 cbMidRange = rangstring.Mid(nStringFrom, nStringTo - nStringFrom); | 326 cbMidRange = rangstring.Mid(nStringFrom, nStringTo - nStringFrom); |
327 int nMid = cbMidRange.Find('-'); | 327 int nMid = cbMidRange.Find('-'); |
328 if (nMid == -1) { | 328 if (nMid == -1) { |
329 long lPageNum = atol(cbMidRange); | 329 long lPageNum = atol(cbMidRange); |
330 if (lPageNum <= 0 || lPageNum > nCount) | 330 if (lPageNum <= 0 || lPageNum > nCount) |
331 return FALSE; | 331 return FALSE; |
332 pageArray->Add((FX_WORD)lPageNum); | 332 pageArray->push_back((FX_WORD)lPageNum); |
333 } else { | 333 } else { |
334 int nStartPageNum = atol(cbMidRange.Mid(0, nMid)); | 334 int nStartPageNum = atol(cbMidRange.Mid(0, nMid)); |
335 if (nStartPageNum == 0) | 335 if (nStartPageNum == 0) |
336 return FALSE; | 336 return FALSE; |
337 | 337 |
338 ++nMid; | 338 ++nMid; |
339 int nEnd = cbMidRange.GetLength() - nMid; | 339 int nEnd = cbMidRange.GetLength() - nMid; |
340 if (nEnd == 0) | 340 if (nEnd == 0) |
341 return FALSE; | 341 return FALSE; |
342 | 342 |
343 int nEndPageNum = atol(cbMidRange.Mid(nMid, nEnd)); | 343 int nEndPageNum = atol(cbMidRange.Mid(nMid, nEnd)); |
344 if (nStartPageNum < 0 || nStartPageNum > nEndPageNum || | 344 if (nStartPageNum < 0 || nStartPageNum > nEndPageNum || |
345 nEndPageNum > nCount) { | 345 nEndPageNum > nCount) { |
346 return FALSE; | 346 return FALSE; |
347 } | 347 } |
348 for (int i = nStartPageNum; i <= nEndPageNum; ++i) { | 348 for (int i = nStartPageNum; i <= nEndPageNum; ++i) { |
349 pageArray->Add(i); | 349 pageArray->push_back(i); |
350 } | 350 } |
351 } | 351 } |
352 nStringFrom = nStringTo + 1; | 352 nStringFrom = nStringTo + 1; |
353 } | 353 } |
354 } | 354 } |
355 return TRUE; | 355 return TRUE; |
356 } | 356 } |
357 | 357 |
358 DLLEXPORT FPDF_BOOL STDCALL FPDF_ImportPages(FPDF_DOCUMENT dest_doc, | 358 DLLEXPORT FPDF_BOOL STDCALL FPDF_ImportPages(FPDF_DOCUMENT dest_doc, |
359 FPDF_DOCUMENT src_doc, | 359 FPDF_DOCUMENT src_doc, |
360 FPDF_BYTESTRING pagerange, | 360 FPDF_BYTESTRING pagerange, |
361 int index) { | 361 int index) { |
362 CPDF_Document* pDestDoc = CPDFDocumentFromFPDFDocument(dest_doc); | 362 CPDF_Document* pDestDoc = CPDFDocumentFromFPDFDocument(dest_doc); |
363 if (!dest_doc) | 363 if (!dest_doc) |
364 return FALSE; | 364 return FALSE; |
365 | 365 |
366 CPDF_Document* pSrcDoc = CPDFDocumentFromFPDFDocument(src_doc); | 366 CPDF_Document* pSrcDoc = CPDFDocumentFromFPDFDocument(src_doc); |
367 if (!pSrcDoc) | 367 if (!pSrcDoc) |
368 return FALSE; | 368 return FALSE; |
369 | 369 |
370 CFX_WordArray pageArray; | 370 std::vector<FX_WORD> pageArray; |
371 int nCount = pSrcDoc->GetPageCount(); | 371 int nCount = pSrcDoc->GetPageCount(); |
372 if (pagerange) { | 372 if (pagerange) { |
373 if (!ParserPageRangeString(pagerange, &pageArray, nCount)) | 373 if (!ParserPageRangeString(pagerange, &pageArray, nCount)) |
374 return FALSE; | 374 return FALSE; |
375 } else { | 375 } else { |
376 for (int i = 1; i <= nCount; ++i) { | 376 for (int i = 1; i <= nCount; ++i) { |
377 pageArray.Add(i); | 377 pageArray.push_back(i); |
378 } | 378 } |
379 } | 379 } |
380 | 380 |
381 CPDF_PageOrganizer pageOrg; | 381 CPDF_PageOrganizer pageOrg; |
382 pageOrg.PDFDocInit(pDestDoc, pSrcDoc); | 382 pageOrg.PDFDocInit(pDestDoc, pSrcDoc); |
383 return pageOrg.ExportPage(pSrcDoc, &pageArray, pDestDoc, index); | 383 return pageOrg.ExportPage(pSrcDoc, &pageArray, pDestDoc, index); |
384 } | 384 } |
385 | 385 |
386 DLLEXPORT FPDF_BOOL STDCALL FPDF_CopyViewerPreferences(FPDF_DOCUMENT dest_doc, | 386 DLLEXPORT FPDF_BOOL STDCALL FPDF_CopyViewerPreferences(FPDF_DOCUMENT dest_doc, |
387 FPDF_DOCUMENT src_doc) { | 387 FPDF_DOCUMENT src_doc) { |
(...skipping 10 matching lines...) Expand all Loading... |
398 if (!pSrcDict) | 398 if (!pSrcDict) |
399 return FALSE; | 399 return FALSE; |
400 | 400 |
401 CPDF_Dictionary* pDstDict = pDstDoc->GetRoot(); | 401 CPDF_Dictionary* pDstDict = pDstDoc->GetRoot(); |
402 if (!pDstDict) | 402 if (!pDstDict) |
403 return FALSE; | 403 return FALSE; |
404 | 404 |
405 pDstDict->SetAt("ViewerPreferences", pSrcDict->Clone(TRUE)); | 405 pDstDict->SetAt("ViewerPreferences", pSrcDict->Clone(TRUE)); |
406 return TRUE; | 406 return TRUE; |
407 } | 407 } |
OLD | NEW |