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 "core/fpdfapi/parser/cpdf_document.h" | 7 #include "core/fpdfapi/parser/cpdf_document.h" |
8 | 8 |
9 #include <memory> | 9 #include <memory> |
10 #include <set> | 10 #include <set> |
| 11 #include <utility> |
11 #include <vector> | 12 #include <vector> |
12 | 13 |
13 #include "core/fpdfapi/cpdf_modulemgr.h" | 14 #include "core/fpdfapi/cpdf_modulemgr.h" |
14 #include "core/fpdfapi/font/cpdf_fontencoding.h" | 15 #include "core/fpdfapi/font/cpdf_fontencoding.h" |
15 #include "core/fpdfapi/page/cpdf_docpagedata.h" | 16 #include "core/fpdfapi/page/cpdf_docpagedata.h" |
16 #include "core/fpdfapi/page/cpdf_pagemodule.h" | 17 #include "core/fpdfapi/page/cpdf_pagemodule.h" |
17 #include "core/fpdfapi/page/pageint.h" | 18 #include "core/fpdfapi/page/pageint.h" |
18 #include "core/fpdfapi/parser/cpdf_array.h" | 19 #include "core/fpdfapi/parser/cpdf_array.h" |
19 #include "core/fpdfapi/parser/cpdf_dictionary.h" | 20 #include "core/fpdfapi/parser/cpdf_dictionary.h" |
20 #include "core/fpdfapi/parser/cpdf_linearized_header.h" | 21 #include "core/fpdfapi/parser/cpdf_linearized_header.h" |
21 #include "core/fpdfapi/parser/cpdf_name.h" | 22 #include "core/fpdfapi/parser/cpdf_name.h" |
22 #include "core/fpdfapi/parser/cpdf_number.h" | 23 #include "core/fpdfapi/parser/cpdf_number.h" |
23 #include "core/fpdfapi/parser/cpdf_parser.h" | 24 #include "core/fpdfapi/parser/cpdf_parser.h" |
24 #include "core/fpdfapi/parser/cpdf_reference.h" | 25 #include "core/fpdfapi/parser/cpdf_reference.h" |
| 26 #include "core/fpdfapi/parser/cpdf_string.h" |
25 #include "core/fpdfapi/parser/cpdf_stream.h" | 27 #include "core/fpdfapi/parser/cpdf_stream.h" |
26 #include "core/fpdfapi/render/cpdf_docrenderdata.h" | 28 #include "core/fpdfapi/render/cpdf_docrenderdata.h" |
27 #include "core/fpdfapi/render/render_int.h" | 29 #include "core/fpdfapi/render/render_int.h" |
28 #include "core/fxcodec/JBig2_DocumentContext.h" | 30 #include "core/fxcodec/JBig2_DocumentContext.h" |
29 #include "core/fxge/cfx_unicodeencoding.h" | 31 #include "core/fxge/cfx_unicodeencoding.h" |
30 #include "core/fxge/fx_font.h" | 32 #include "core/fxge/fx_font.h" |
31 #include "third_party/base/ptr_util.h" | 33 #include "third_party/base/ptr_util.h" |
32 #include "third_party/base/stl_util.h" | 34 #include "third_party/base/stl_util.h" |
33 | 35 |
34 namespace { | 36 namespace { |
(...skipping 223 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
258 if (pKid->KeyExist("Kids")) { | 260 if (pKid->KeyExist("Kids")) { |
259 // Use |visited_pages| to help detect circular references of pages. | 261 // Use |visited_pages| to help detect circular references of pages. |
260 pdfium::ScopedSetInsertion<CPDF_Dictionary*> local_add(visited_pages, | 262 pdfium::ScopedSetInsertion<CPDF_Dictionary*> local_add(visited_pages, |
261 pKid); | 263 pKid); |
262 count += CountPages(pKid, visited_pages); | 264 count += CountPages(pKid, visited_pages); |
263 } else { | 265 } else { |
264 // This page is a leaf node. | 266 // This page is a leaf node. |
265 count++; | 267 count++; |
266 } | 268 } |
267 } | 269 } |
268 pPages->SetIntegerFor("Count", count); | 270 pPages->SetNewFor<CPDF_Number>("Count", count); |
269 return count; | 271 return count; |
270 } | 272 } |
271 | 273 |
272 int CalculateFlags(bool bold, | 274 int CalculateFlags(bool bold, |
273 bool italic, | 275 bool italic, |
274 bool fixedPitch, | 276 bool fixedPitch, |
275 bool serif, | 277 bool serif, |
276 bool script, | 278 bool script, |
277 bool symbolic) { | 279 bool symbolic) { |
278 int flags = 0; | 280 int flags = 0; |
(...skipping 18 matching lines...) Expand all Loading... |
297 bool bold, | 299 bool bold, |
298 bool italic, | 300 bool italic, |
299 CFX_ByteString basefont, | 301 CFX_ByteString basefont, |
300 CPDF_Array* pWidths) { | 302 CPDF_Array* pWidths) { |
301 if (bold && italic) | 303 if (bold && italic) |
302 basefont += ",BoldItalic"; | 304 basefont += ",BoldItalic"; |
303 else if (bold) | 305 else if (bold) |
304 basefont += ",Bold"; | 306 basefont += ",Bold"; |
305 else if (italic) | 307 else if (italic) |
306 basefont += ",Italic"; | 308 basefont += ",Italic"; |
307 pBaseDict->SetNameFor("Subtype", "TrueType"); | 309 pBaseDict->SetNewFor<CPDF_Name>("Subtype", "TrueType"); |
308 pBaseDict->SetNameFor("BaseFont", basefont); | 310 pBaseDict->SetNewFor<CPDF_Name>("BaseFont", basefont); |
309 pBaseDict->SetNumberFor("FirstChar", 32); | 311 pBaseDict->SetNewFor<CPDF_Number>("FirstChar", 32); |
310 pBaseDict->SetNumberFor("LastChar", 255); | 312 pBaseDict->SetNewFor<CPDF_Number>("LastChar", 255); |
311 pBaseDict->SetFor("Widths", pWidths); | 313 pBaseDict->SetFor("Widths", pdfium::WrapUnique(pWidths)); |
312 } | 314 } |
313 | 315 |
314 std::unique_ptr<CPDF_Dictionary> CalculateFontDesc(CPDF_Document* pDoc, | 316 std::unique_ptr<CPDF_Dictionary> CalculateFontDesc(CPDF_Document* pDoc, |
315 CFX_ByteString basefont, | 317 CFX_ByteString basefont, |
316 int flags, | 318 int flags, |
317 int italicangle, | 319 int italicangle, |
318 int ascend, | 320 int ascend, |
319 int descend, | 321 int descend, |
320 CPDF_Array* bbox, | 322 CPDF_Array* bbox, |
321 int32_t stemV) { | 323 int32_t stemV) { |
322 auto pFontDesc = | 324 auto pFontDesc = |
323 pdfium::MakeUnique<CPDF_Dictionary>(pDoc->GetByteStringPool()); | 325 pdfium::MakeUnique<CPDF_Dictionary>(pDoc->GetByteStringPool()); |
324 pFontDesc->SetNameFor("Type", "FontDescriptor"); | 326 pFontDesc->SetNewFor<CPDF_Name>("Type", "FontDescriptor"); |
325 pFontDesc->SetNameFor("FontName", basefont); | 327 pFontDesc->SetNewFor<CPDF_Name>("FontName", basefont); |
326 pFontDesc->SetIntegerFor("Flags", flags); | 328 pFontDesc->SetNewFor<CPDF_Number>("Flags", flags); |
327 pFontDesc->SetFor("FontBBox", bbox); | 329 pFontDesc->SetFor("FontBBox", pdfium::WrapUnique(bbox)); |
328 pFontDesc->SetIntegerFor("ItalicAngle", italicangle); | 330 pFontDesc->SetNewFor<CPDF_Number>("ItalicAngle", italicangle); |
329 pFontDesc->SetIntegerFor("Ascent", ascend); | 331 pFontDesc->SetNewFor<CPDF_Number>("Ascent", ascend); |
330 pFontDesc->SetIntegerFor("Descent", descend); | 332 pFontDesc->SetNewFor<CPDF_Number>("Descent", descend); |
331 pFontDesc->SetIntegerFor("StemV", stemV); | 333 pFontDesc->SetNewFor<CPDF_Number>("StemV", stemV); |
332 return pFontDesc; | 334 return pFontDesc; |
333 } | 335 } |
334 | 336 |
335 } // namespace | 337 } // namespace |
336 | 338 |
337 CPDF_Document::CPDF_Document(std::unique_ptr<CPDF_Parser> pParser) | 339 CPDF_Document::CPDF_Document(std::unique_ptr<CPDF_Parser> pParser) |
338 : CPDF_IndirectObjectHolder(), | 340 : CPDF_IndirectObjectHolder(), |
339 m_pParser(std::move(pParser)), | 341 m_pParser(std::move(pParser)), |
340 m_pRootDict(nullptr), | 342 m_pRootDict(nullptr), |
341 m_pInfoDict(nullptr), | 343 m_pInfoDict(nullptr), |
(...skipping 300 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
642 } | 644 } |
643 | 645 |
644 CPDF_Image* CPDF_Document::LoadImageFromPageData(uint32_t dwStreamObjNum) { | 646 CPDF_Image* CPDF_Document::LoadImageFromPageData(uint32_t dwStreamObjNum) { |
645 ASSERT(dwStreamObjNum); | 647 ASSERT(dwStreamObjNum); |
646 return m_pDocPage->GetImage(dwStreamObjNum); | 648 return m_pDocPage->GetImage(dwStreamObjNum); |
647 } | 649 } |
648 | 650 |
649 void CPDF_Document::CreateNewDoc() { | 651 void CPDF_Document::CreateNewDoc() { |
650 ASSERT(!m_pRootDict && !m_pInfoDict); | 652 ASSERT(!m_pRootDict && !m_pInfoDict); |
651 m_pRootDict = NewIndirect<CPDF_Dictionary>(); | 653 m_pRootDict = NewIndirect<CPDF_Dictionary>(); |
652 m_pRootDict->SetNameFor("Type", "Catalog"); | 654 m_pRootDict->SetNewFor<CPDF_Name>("Type", "Catalog"); |
653 | 655 |
654 CPDF_Dictionary* pPages = NewIndirect<CPDF_Dictionary>(); | 656 CPDF_Dictionary* pPages = NewIndirect<CPDF_Dictionary>(); |
655 pPages->SetNameFor("Type", "Pages"); | 657 pPages->SetNewFor<CPDF_Name>("Type", "Pages"); |
656 pPages->SetNumberFor("Count", 0); | 658 pPages->SetNewFor<CPDF_Number>("Count", 0); |
657 pPages->SetFor("Kids", new CPDF_Array); | 659 pPages->SetNewFor<CPDF_Array>("Kids"); |
658 m_pRootDict->SetReferenceFor("Pages", this, pPages); | 660 m_pRootDict->SetNewFor<CPDF_Reference>("Pages", this, pPages->GetObjNum()); |
659 m_pInfoDict = NewIndirect<CPDF_Dictionary>(); | 661 m_pInfoDict = NewIndirect<CPDF_Dictionary>(); |
660 } | 662 } |
661 | 663 |
662 CPDF_Dictionary* CPDF_Document::CreateNewPage(int iPage) { | 664 CPDF_Dictionary* CPDF_Document::CreateNewPage(int iPage) { |
663 CPDF_Dictionary* pDict = NewIndirect<CPDF_Dictionary>(); | 665 CPDF_Dictionary* pDict = NewIndirect<CPDF_Dictionary>(); |
664 pDict->SetNameFor("Type", "Page"); | 666 pDict->SetNewFor<CPDF_Name>("Type", "Page"); |
665 uint32_t dwObjNum = pDict->GetObjNum(); | 667 uint32_t dwObjNum = pDict->GetObjNum(); |
666 if (!InsertNewPage(iPage, pDict)) { | 668 if (!InsertNewPage(iPage, pDict)) { |
667 DeleteIndirectObject(dwObjNum); | 669 DeleteIndirectObject(dwObjNum); |
668 return nullptr; | 670 return nullptr; |
669 } | 671 } |
670 return pDict; | 672 return pDict; |
671 } | 673 } |
672 | 674 |
673 bool CPDF_Document::InsertDeletePDFPage(CPDF_Dictionary* pPages, | 675 bool CPDF_Document::InsertDeletePDFPage(CPDF_Dictionary* pPages, |
674 int nPagesToGo, | 676 int nPagesToGo, |
675 CPDF_Dictionary* pPageDict, | 677 CPDF_Dictionary* pPageDict, |
676 bool bInsert, | 678 bool bInsert, |
677 std::set<CPDF_Dictionary*>* pVisited) { | 679 std::set<CPDF_Dictionary*>* pVisited) { |
678 CPDF_Array* pKidList = pPages->GetArrayFor("Kids"); | 680 CPDF_Array* pKidList = pPages->GetArrayFor("Kids"); |
679 if (!pKidList) | 681 if (!pKidList) |
680 return false; | 682 return false; |
681 | 683 |
682 for (size_t i = 0; i < pKidList->GetCount(); i++) { | 684 for (size_t i = 0; i < pKidList->GetCount(); i++) { |
683 CPDF_Dictionary* pKid = pKidList->GetDictAt(i); | 685 CPDF_Dictionary* pKid = pKidList->GetDictAt(i); |
684 if (pKid->GetStringFor("Type") == "Page") { | 686 if (pKid->GetStringFor("Type") == "Page") { |
685 if (nPagesToGo != 0) { | 687 if (nPagesToGo != 0) { |
686 nPagesToGo--; | 688 nPagesToGo--; |
687 continue; | 689 continue; |
688 } | 690 } |
689 if (bInsert) { | 691 if (bInsert) { |
690 pKidList->InsertNewAt<CPDF_Reference>(i, this, pPageDict->GetObjNum()); | 692 pKidList->InsertNewAt<CPDF_Reference>(i, this, pPageDict->GetObjNum()); |
691 pPageDict->SetReferenceFor("Parent", this, pPages->GetObjNum()); | 693 pPageDict->SetNewFor<CPDF_Reference>("Parent", this, |
| 694 pPages->GetObjNum()); |
692 } else { | 695 } else { |
693 pKidList->RemoveAt(i); | 696 pKidList->RemoveAt(i); |
694 } | 697 } |
695 pPages->SetIntegerFor( | 698 pPages->SetNewFor<CPDF_Number>( |
696 "Count", pPages->GetIntegerFor("Count") + (bInsert ? 1 : -1)); | 699 "Count", pPages->GetIntegerFor("Count") + (bInsert ? 1 : -1)); |
697 ResetTraversal(); | 700 ResetTraversal(); |
698 break; | 701 break; |
699 } | 702 } |
700 int nPages = pKid->GetIntegerFor("Count"); | 703 int nPages = pKid->GetIntegerFor("Count"); |
701 if (nPagesToGo >= nPages) { | 704 if (nPagesToGo >= nPages) { |
702 nPagesToGo -= nPages; | 705 nPagesToGo -= nPages; |
703 continue; | 706 continue; |
704 } | 707 } |
705 if (pdfium::ContainsKey(*pVisited, pKid)) | 708 if (pdfium::ContainsKey(*pVisited, pKid)) |
706 return false; | 709 return false; |
707 | 710 |
708 pdfium::ScopedSetInsertion<CPDF_Dictionary*> insertion(pVisited, pKid); | 711 pdfium::ScopedSetInsertion<CPDF_Dictionary*> insertion(pVisited, pKid); |
709 if (!InsertDeletePDFPage(pKid, nPagesToGo, pPageDict, bInsert, pVisited)) | 712 if (!InsertDeletePDFPage(pKid, nPagesToGo, pPageDict, bInsert, pVisited)) |
710 return false; | 713 return false; |
711 | 714 |
712 pPages->SetIntegerFor("Count", | 715 pPages->SetNewFor<CPDF_Number>( |
713 pPages->GetIntegerFor("Count") + (bInsert ? 1 : -1)); | 716 "Count", pPages->GetIntegerFor("Count") + (bInsert ? 1 : -1)); |
714 break; | 717 break; |
715 } | 718 } |
716 return true; | 719 return true; |
717 } | 720 } |
718 | 721 |
719 bool CPDF_Document::InsertNewPage(int iPage, CPDF_Dictionary* pPageDict) { | 722 bool CPDF_Document::InsertNewPage(int iPage, CPDF_Dictionary* pPageDict) { |
720 CPDF_Dictionary* pRoot = GetRoot(); | 723 CPDF_Dictionary* pRoot = GetRoot(); |
721 CPDF_Dictionary* pPages = pRoot ? pRoot->GetDictFor("Pages") : nullptr; | 724 CPDF_Dictionary* pPages = pRoot ? pRoot->GetDictFor("Pages") : nullptr; |
722 if (!pPages) | 725 if (!pPages) |
723 return false; | 726 return false; |
724 | 727 |
725 int nPages = GetPageCount(); | 728 int nPages = GetPageCount(); |
726 if (iPage < 0 || iPage > nPages) | 729 if (iPage < 0 || iPage > nPages) |
727 return false; | 730 return false; |
728 | 731 |
729 if (iPage == nPages) { | 732 if (iPage == nPages) { |
730 CPDF_Array* pPagesList = pPages->GetArrayFor("Kids"); | 733 CPDF_Array* pPagesList = pPages->GetArrayFor("Kids"); |
731 if (!pPagesList) { | 734 if (!pPagesList) |
732 pPagesList = new CPDF_Array; | 735 pPagesList = pPages->SetNewFor<CPDF_Array>("Kids"); |
733 pPages->SetFor("Kids", pPagesList); | |
734 } | |
735 pPagesList->AddNew<CPDF_Reference>(this, pPageDict->GetObjNum()); | 736 pPagesList->AddNew<CPDF_Reference>(this, pPageDict->GetObjNum()); |
736 pPages->SetIntegerFor("Count", nPages + 1); | 737 pPages->SetNewFor<CPDF_Number>("Count", nPages + 1); |
737 pPageDict->SetReferenceFor("Parent", this, pPages->GetObjNum()); | 738 pPageDict->SetNewFor<CPDF_Reference>("Parent", this, pPages->GetObjNum()); |
738 ResetTraversal(); | 739 ResetTraversal(); |
739 } else { | 740 } else { |
740 std::set<CPDF_Dictionary*> stack = {pPages}; | 741 std::set<CPDF_Dictionary*> stack = {pPages}; |
741 if (!InsertDeletePDFPage(pPages, iPage, pPageDict, true, &stack)) | 742 if (!InsertDeletePDFPage(pPages, iPage, pPageDict, true, &stack)) |
742 return false; | 743 return false; |
743 } | 744 } |
744 m_PageList.InsertAt(iPage, pPageDict->GetObjNum()); | 745 m_PageList.InsertAt(iPage, pPageDict->GetObjNum()); |
745 return true; | 746 return true; |
746 } | 747 } |
747 | 748 |
(...skipping 25 matching lines...) Expand all Loading... |
773 CPDF_Dictionary* pBaseDict) { | 774 CPDF_Dictionary* pBaseDict) { |
774 size_t i; | 775 size_t i; |
775 for (i = 0; i < FX_ArraySize(g_FX_CharsetUnicodes); ++i) { | 776 for (i = 0; i < FX_ArraySize(g_FX_CharsetUnicodes); ++i) { |
776 if (g_FX_CharsetUnicodes[i].m_Charset == charset) | 777 if (g_FX_CharsetUnicodes[i].m_Charset == charset) |
777 break; | 778 break; |
778 } | 779 } |
779 if (i == FX_ArraySize(g_FX_CharsetUnicodes)) | 780 if (i == FX_ArraySize(g_FX_CharsetUnicodes)) |
780 return i; | 781 return i; |
781 | 782 |
782 CPDF_Dictionary* pEncodingDict = NewIndirect<CPDF_Dictionary>(); | 783 CPDF_Dictionary* pEncodingDict = NewIndirect<CPDF_Dictionary>(); |
783 pEncodingDict->SetNameFor("BaseEncoding", "WinAnsiEncoding"); | 784 pEncodingDict->SetNewFor<CPDF_Name>("BaseEncoding", "WinAnsiEncoding"); |
784 | 785 |
785 CPDF_Array* pArray = new CPDF_Array; | 786 CPDF_Array* pArray = pEncodingDict->SetNewFor<CPDF_Array>("Differences"); |
786 pArray->AddNew<CPDF_Number>(128); | 787 pArray->AddNew<CPDF_Number>(128); |
787 | 788 |
788 const uint16_t* pUnicodes = g_FX_CharsetUnicodes[i].m_pUnicodes; | 789 const uint16_t* pUnicodes = g_FX_CharsetUnicodes[i].m_pUnicodes; |
789 for (int j = 0; j < 128; j++) { | 790 for (int j = 0; j < 128; j++) { |
790 CFX_ByteString name = PDF_AdobeNameFromUnicode(pUnicodes[j]); | 791 CFX_ByteString name = PDF_AdobeNameFromUnicode(pUnicodes[j]); |
791 pArray->AddNew<CPDF_Name>(name.IsEmpty() ? ".notdef" : name); | 792 pArray->AddNew<CPDF_Name>(name.IsEmpty() ? ".notdef" : name); |
792 } | 793 } |
793 pEncodingDict->SetFor("Differences", pArray); | 794 pBaseDict->SetNewFor<CPDF_Reference>("Encoding", this, |
794 pBaseDict->SetReferenceFor("Encoding", this, pEncodingDict); | 795 pEncodingDict->GetObjNum()); |
795 return i; | 796 return i; |
796 } | 797 } |
797 | 798 |
798 CPDF_Dictionary* CPDF_Document::ProcessbCJK( | 799 CPDF_Dictionary* CPDF_Document::ProcessbCJK( |
799 CPDF_Dictionary* pBaseDict, | 800 CPDF_Dictionary* pBaseDict, |
800 int charset, | 801 int charset, |
801 bool bVert, | 802 bool bVert, |
802 CFX_ByteString basefont, | 803 CFX_ByteString basefont, |
803 std::function<void(FX_WCHAR, FX_WCHAR, CPDF_Array*)> Insert) { | 804 std::function<void(FX_WCHAR, FX_WCHAR, CPDF_Array*)> Insert) { |
804 CPDF_Dictionary* pFontDict = NewIndirect<CPDF_Dictionary>(); | 805 CPDF_Dictionary* pFontDict = NewIndirect<CPDF_Dictionary>(); |
805 CFX_ByteString cmap; | 806 CFX_ByteString cmap; |
806 CFX_ByteString ordering; | 807 CFX_ByteString ordering; |
807 int supplement = 0; | 808 int supplement = 0; |
808 CPDF_Array* pWidthArray = new CPDF_Array; | 809 CPDF_Array* pWidthArray = pFontDict->SetNewFor<CPDF_Array>("W"); |
809 switch (charset) { | 810 switch (charset) { |
810 case FXFONT_CHINESEBIG5_CHARSET: | 811 case FXFONT_CHINESEBIG5_CHARSET: |
811 cmap = bVert ? "ETenms-B5-V" : "ETenms-B5-H"; | 812 cmap = bVert ? "ETenms-B5-V" : "ETenms-B5-H"; |
812 ordering = "CNS1"; | 813 ordering = "CNS1"; |
813 supplement = 4; | 814 supplement = 4; |
814 pWidthArray->AddNew<CPDF_Number>(1); | 815 pWidthArray->AddNew<CPDF_Number>(1); |
815 Insert(0x20, 0x7e, pWidthArray); | 816 Insert(0x20, 0x7e, pWidthArray); |
816 break; | 817 break; |
817 case FXFONT_GB2312_CHARSET: | 818 case FXFONT_GB2312_CHARSET: |
818 cmap = bVert ? "GBK-EUC-V" : "GBK-EUC-H"; | 819 cmap = bVert ? "GBK-EUC-V" : "GBK-EUC-H"; |
(...skipping 18 matching lines...) Expand all Loading... |
837 pWidthArray->AddNew<CPDF_Number>(231); | 838 pWidthArray->AddNew<CPDF_Number>(231); |
838 Insert(0x20, 0x7d, pWidthArray); | 839 Insert(0x20, 0x7d, pWidthArray); |
839 pWidthArray->AddNew<CPDF_Number>(326); | 840 pWidthArray->AddNew<CPDF_Number>(326); |
840 Insert(0xa0, 0xa0, pWidthArray); | 841 Insert(0xa0, 0xa0, pWidthArray); |
841 pWidthArray->AddNew<CPDF_Number>(327); | 842 pWidthArray->AddNew<CPDF_Number>(327); |
842 Insert(0xa1, 0xdf, pWidthArray); | 843 Insert(0xa1, 0xdf, pWidthArray); |
843 pWidthArray->AddNew<CPDF_Number>(631); | 844 pWidthArray->AddNew<CPDF_Number>(631); |
844 Insert(0x7e, 0x7e, pWidthArray); | 845 Insert(0x7e, 0x7e, pWidthArray); |
845 break; | 846 break; |
846 } | 847 } |
847 pBaseDict->SetNameFor("Subtype", "Type0"); | 848 pBaseDict->SetNewFor<CPDF_Name>("Subtype", "Type0"); |
848 pBaseDict->SetNameFor("BaseFont", basefont); | 849 pBaseDict->SetNewFor<CPDF_Name>("BaseFont", basefont); |
849 pBaseDict->SetNameFor("Encoding", cmap); | 850 pBaseDict->SetNewFor<CPDF_Name>("Encoding", cmap); |
850 pFontDict->SetFor("W", pWidthArray); | 851 pFontDict->SetNewFor<CPDF_Name>("Type", "Font"); |
851 pFontDict->SetNameFor("Type", "Font"); | 852 pFontDict->SetNewFor<CPDF_Name>("Subtype", "CIDFontType2"); |
852 pFontDict->SetNameFor("Subtype", "CIDFontType2"); | 853 pFontDict->SetNewFor<CPDF_Name>("BaseFont", basefont); |
853 pFontDict->SetNameFor("BaseFont", basefont); | 854 |
854 CPDF_Dictionary* pCIDSysInfo = new CPDF_Dictionary(GetByteStringPool()); | 855 CPDF_Dictionary* pCIDSysInfo = |
855 pCIDSysInfo->SetStringFor("Registry", "Adobe"); | 856 pFontDict->SetNewFor<CPDF_Dictionary>("CIDSystemInfo"); |
856 pCIDSysInfo->SetStringFor("Ordering", ordering); | 857 pCIDSysInfo->SetNewFor<CPDF_String>("Registry", "Adobe", false); |
857 pCIDSysInfo->SetIntegerFor("Supplement", supplement); | 858 pCIDSysInfo->SetNewFor<CPDF_String>("Ordering", ordering, false); |
858 pFontDict->SetFor("CIDSystemInfo", pCIDSysInfo); | 859 pCIDSysInfo->SetNewFor<CPDF_Number>("Supplement", supplement); |
859 CPDF_Array* pArray = new CPDF_Array; | 860 |
860 pBaseDict->SetFor("DescendantFonts", pArray); | 861 CPDF_Array* pArray = pBaseDict->SetNewFor<CPDF_Array>("DescendantFonts"); |
861 pArray->AddNew<CPDF_Reference>(this, pFontDict->GetObjNum()); | 862 pArray->AddNew<CPDF_Reference>(this, pFontDict->GetObjNum()); |
862 return pFontDict; | 863 return pFontDict; |
863 } | 864 } |
864 | 865 |
865 CPDF_Font* CPDF_Document::AddFont(CFX_Font* pFont, int charset, bool bVert) { | 866 CPDF_Font* CPDF_Document::AddFont(CFX_Font* pFont, int charset, bool bVert) { |
866 if (!pFont) | 867 if (!pFont) |
867 return nullptr; | 868 return nullptr; |
868 | 869 |
869 bool bCJK = charset == FXFONT_CHINESEBIG5_CHARSET || | 870 bool bCJK = charset == FXFONT_CHINESEBIG5_CHARSET || |
870 charset == FXFONT_GB2312_CHARSET || | 871 charset == FXFONT_GB2312_CHARSET || |
871 charset == FXFONT_HANGUL_CHARSET || | 872 charset == FXFONT_HANGUL_CHARSET || |
872 charset == FXFONT_SHIFTJIS_CHARSET; | 873 charset == FXFONT_SHIFTJIS_CHARSET; |
873 CFX_ByteString basefont = pFont->GetFamilyName(); | 874 CFX_ByteString basefont = pFont->GetFamilyName(); |
874 basefont.Replace(" ", ""); | 875 basefont.Replace(" ", ""); |
875 int flags = | 876 int flags = |
876 CalculateFlags(pFont->IsBold(), pFont->IsItalic(), pFont->IsFixedWidth(), | 877 CalculateFlags(pFont->IsBold(), pFont->IsItalic(), pFont->IsFixedWidth(), |
877 false, false, charset == FXFONT_SYMBOL_CHARSET); | 878 false, false, charset == FXFONT_SYMBOL_CHARSET); |
878 | 879 |
879 CPDF_Dictionary* pBaseDict = NewIndirect<CPDF_Dictionary>(); | 880 CPDF_Dictionary* pBaseDict = NewIndirect<CPDF_Dictionary>(); |
880 pBaseDict->SetNameFor("Type", "Font"); | 881 pBaseDict->SetNewFor<CPDF_Name>("Type", "Font"); |
881 std::unique_ptr<CFX_UnicodeEncoding> pEncoding( | 882 std::unique_ptr<CFX_UnicodeEncoding> pEncoding( |
882 new CFX_UnicodeEncoding(pFont)); | 883 new CFX_UnicodeEncoding(pFont)); |
883 CPDF_Dictionary* pFontDict = pBaseDict; | 884 CPDF_Dictionary* pFontDict = pBaseDict; |
884 if (!bCJK) { | 885 if (!bCJK) { |
885 CPDF_Array* pWidths = new CPDF_Array; | 886 CPDF_Array* pWidths = new CPDF_Array; |
886 for (int charcode = 32; charcode < 128; charcode++) { | 887 for (int charcode = 32; charcode < 128; charcode++) { |
887 int glyph_index = pEncoding->GlyphFromCharCode(charcode); | 888 int glyph_index = pEncoding->GlyphFromCharCode(charcode); |
888 int char_width = pFont->GetGlyphWidth(glyph_index); | 889 int char_width = pFont->GetGlyphWidth(glyph_index); |
889 pWidths->AddNew<CPDF_Number>(char_width); | 890 pWidths->AddNew<CPDF_Number>(char_width); |
890 } | 891 } |
891 if (charset == FXFONT_ANSI_CHARSET || charset == FXFONT_DEFAULT_CHARSET || | 892 if (charset == FXFONT_ANSI_CHARSET || charset == FXFONT_DEFAULT_CHARSET || |
892 charset == FXFONT_SYMBOL_CHARSET) { | 893 charset == FXFONT_SYMBOL_CHARSET) { |
893 pBaseDict->SetNameFor("Encoding", "WinAnsiEncoding"); | 894 pBaseDict->SetNewFor<CPDF_Name>("Encoding", "WinAnsiEncoding"); |
894 for (int charcode = 128; charcode <= 255; charcode++) { | 895 for (int charcode = 128; charcode <= 255; charcode++) { |
895 int glyph_index = pEncoding->GlyphFromCharCode(charcode); | 896 int glyph_index = pEncoding->GlyphFromCharCode(charcode); |
896 int char_width = pFont->GetGlyphWidth(glyph_index); | 897 int char_width = pFont->GetGlyphWidth(glyph_index); |
897 pWidths->AddNew<CPDF_Number>(char_width); | 898 pWidths->AddNew<CPDF_Number>(char_width); |
898 } | 899 } |
899 } else { | 900 } else { |
900 size_t i = CalculateEncodingDict(charset, pBaseDict); | 901 size_t i = CalculateEncodingDict(charset, pBaseDict); |
901 if (i < FX_ArraySize(g_FX_CharsetUnicodes)) { | 902 if (i < FX_ArraySize(g_FX_CharsetUnicodes)) { |
902 const uint16_t* pUnicodes = g_FX_CharsetUnicodes[i].m_pUnicodes; | 903 const uint16_t* pUnicodes = g_FX_CharsetUnicodes[i].m_pUnicodes; |
903 for (int j = 0; j < 128; j++) { | 904 for (int j = 0; j < 128; j++) { |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
937 for (size_t i = 1; i < count; i++) { | 938 for (size_t i = 1; i < count; i++) { |
938 glyph = pEncoding->GlyphFromCharCode(stem_chars[i]); | 939 glyph = pEncoding->GlyphFromCharCode(stem_chars[i]); |
939 int width = pFont->GetGlyphWidth(glyph); | 940 int width = pFont->GetGlyphWidth(glyph); |
940 if (width > 0 && width < nStemV) | 941 if (width > 0 && width < nStemV) |
941 nStemV = width; | 942 nStemV = width; |
942 } | 943 } |
943 } | 944 } |
944 CPDF_Dictionary* pFontDesc = ToDictionary(AddIndirectObject( | 945 CPDF_Dictionary* pFontDesc = ToDictionary(AddIndirectObject( |
945 CalculateFontDesc(this, basefont, flags, italicangle, pFont->GetAscent(), | 946 CalculateFontDesc(this, basefont, flags, italicangle, pFont->GetAscent(), |
946 pFont->GetDescent(), pBBox, nStemV))); | 947 pFont->GetDescent(), pBBox, nStemV))); |
947 pFontDict->SetReferenceFor("FontDescriptor", this, pFontDesc); | 948 pFontDict->SetNewFor<CPDF_Reference>("FontDescriptor", this, |
| 949 pFontDesc->GetObjNum()); |
948 return LoadFont(pBaseDict); | 950 return LoadFont(pBaseDict); |
949 } | 951 } |
950 | 952 |
951 #if _FXM_PLATFORM_ == _FXM_PLATFORM_WINDOWS_ | 953 #if _FXM_PLATFORM_ == _FXM_PLATFORM_WINDOWS_ |
952 CPDF_Font* CPDF_Document::AddWindowsFont(LOGFONTW* pLogFont, | 954 CPDF_Font* CPDF_Document::AddWindowsFont(LOGFONTW* pLogFont, |
953 bool bVert, | 955 bool bVert, |
954 bool bTranslateName) { | 956 bool bTranslateName) { |
955 LOGFONTA lfa; | 957 LOGFONTA lfa; |
956 FXSYS_memcpy(&lfa, pLogFont, (char*)lfa.lfFaceName - (char*)&lfa); | 958 FXSYS_memcpy(&lfa, pLogFont, (char*)lfa.lfFaceName - (char*)&lfa); |
957 CFX_ByteString face = CFX_ByteString::FromUnicode(pLogFont->lfFaceName); | 959 CFX_ByteString face = CFX_ByteString::FromUnicode(pLogFont->lfFaceName); |
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1000 | 1002 |
1001 int italicangle = ptm->otmItalicAngle / 10; | 1003 int italicangle = ptm->otmItalicAngle / 10; |
1002 int ascend = ptm->otmrcFontBox.top; | 1004 int ascend = ptm->otmrcFontBox.top; |
1003 int descend = ptm->otmrcFontBox.bottom; | 1005 int descend = ptm->otmrcFontBox.bottom; |
1004 int capheight = ptm->otmsCapEmHeight; | 1006 int capheight = ptm->otmsCapEmHeight; |
1005 int bbox[4] = {ptm->otmrcFontBox.left, ptm->otmrcFontBox.bottom, | 1007 int bbox[4] = {ptm->otmrcFontBox.left, ptm->otmrcFontBox.bottom, |
1006 ptm->otmrcFontBox.right, ptm->otmrcFontBox.top}; | 1008 ptm->otmrcFontBox.right, ptm->otmrcFontBox.top}; |
1007 FX_Free(tm_buf); | 1009 FX_Free(tm_buf); |
1008 basefont.Replace(" ", ""); | 1010 basefont.Replace(" ", ""); |
1009 CPDF_Dictionary* pBaseDict = NewIndirect<CPDF_Dictionary>(); | 1011 CPDF_Dictionary* pBaseDict = NewIndirect<CPDF_Dictionary>(); |
1010 pBaseDict->SetNameFor("Type", "Font"); | 1012 pBaseDict->SetNewFor<CPDF_Name>("Type", "Font"); |
1011 CPDF_Dictionary* pFontDict = pBaseDict; | 1013 CPDF_Dictionary* pFontDict = pBaseDict; |
1012 if (!bCJK) { | 1014 if (!bCJK) { |
1013 if (pLogFont->lfCharSet == FXFONT_ANSI_CHARSET || | 1015 if (pLogFont->lfCharSet == FXFONT_ANSI_CHARSET || |
1014 pLogFont->lfCharSet == FXFONT_DEFAULT_CHARSET || | 1016 pLogFont->lfCharSet == FXFONT_DEFAULT_CHARSET || |
1015 pLogFont->lfCharSet == FXFONT_SYMBOL_CHARSET) { | 1017 pLogFont->lfCharSet == FXFONT_SYMBOL_CHARSET) { |
1016 pBaseDict->SetNameFor("Encoding", "WinAnsiEncoding"); | 1018 pBaseDict->SetNewFor<CPDF_Name>("Encoding", "WinAnsiEncoding"); |
1017 } else { | 1019 } else { |
1018 CalculateEncodingDict(pLogFont->lfCharSet, pBaseDict); | 1020 CalculateEncodingDict(pLogFont->lfCharSet, pBaseDict); |
1019 } | 1021 } |
1020 int char_widths[224]; | 1022 int char_widths[224]; |
1021 GetCharWidth(hDC, 32, 255, char_widths); | 1023 GetCharWidth(hDC, 32, 255, char_widths); |
1022 CPDF_Array* pWidths = new CPDF_Array; | 1024 CPDF_Array* pWidths = new CPDF_Array; |
1023 for (size_t i = 0; i < 224; i++) | 1025 for (size_t i = 0; i < 224; i++) |
1024 pWidths->AddNew<CPDF_Number>(char_widths[i]); | 1026 pWidths->AddNew<CPDF_Number>(char_widths[i]); |
1025 ProcessNonbCJK(pBaseDict, pLogFont->lfWeight > FW_MEDIUM, | 1027 ProcessNonbCJK(pBaseDict, pLogFont->lfWeight > FW_MEDIUM, |
1026 pLogFont->lfItalic != 0, basefont, pWidths); | 1028 pLogFont->lfItalic != 0, basefont, pWidths); |
1027 } else { | 1029 } else { |
1028 pFontDict = | 1030 pFontDict = |
1029 ProcessbCJK(pBaseDict, pLogFont->lfCharSet, bVert, basefont, | 1031 ProcessbCJK(pBaseDict, pLogFont->lfCharSet, bVert, basefont, |
1030 [&hDC](FX_WCHAR start, FX_WCHAR end, CPDF_Array* widthArr) { | 1032 [&hDC](FX_WCHAR start, FX_WCHAR end, CPDF_Array* widthArr) { |
1031 InsertWidthArray(hDC, start, end, widthArr); | 1033 InsertWidthArray(hDC, start, end, widthArr); |
1032 }); | 1034 }); |
1033 } | 1035 } |
1034 CPDF_Array* pBBox = new CPDF_Array; | 1036 CPDF_Array* pBBox = new CPDF_Array; |
1035 for (int i = 0; i < 4; i++) | 1037 for (int i = 0; i < 4; i++) |
1036 pBBox->AddNew<CPDF_Number>(bbox[i]); | 1038 pBBox->AddNew<CPDF_Number>(bbox[i]); |
1037 std::unique_ptr<CPDF_Dictionary> pFontDesc = | 1039 std::unique_ptr<CPDF_Dictionary> pFontDesc = |
1038 CalculateFontDesc(this, basefont, flags, italicangle, ascend, descend, | 1040 CalculateFontDesc(this, basefont, flags, italicangle, ascend, descend, |
1039 pBBox, pLogFont->lfWeight / 5); | 1041 pBBox, pLogFont->lfWeight / 5); |
1040 pFontDesc->SetIntegerFor("CapHeight", capheight); | 1042 pFontDesc->SetNewFor<CPDF_Number>("CapHeight", capheight); |
1041 pFontDict->SetReferenceFor("FontDescriptor", this, | 1043 pFontDict->SetNewFor<CPDF_Reference>( |
1042 AddIndirectObject(std::move(pFontDesc))); | 1044 "FontDescriptor", this, |
| 1045 AddIndirectObject(std::move(pFontDesc))->GetObjNum()); |
1043 hFont = SelectObject(hDC, hFont); | 1046 hFont = SelectObject(hDC, hFont); |
1044 DeleteObject(hFont); | 1047 DeleteObject(hFont); |
1045 DeleteDC(hDC); | 1048 DeleteDC(hDC); |
1046 return LoadFont(pBaseDict); | 1049 return LoadFont(pBaseDict); |
1047 } | 1050 } |
1048 #endif // _FXM_PLATFORM_ == _FXM_PLATFORM_WINDOWS_ | 1051 #endif // _FXM_PLATFORM_ == _FXM_PLATFORM_WINDOWS_ |
OLD | NEW |