OLD | NEW |
1 // Copyright 2014 PDFium Authors. All rights reserved. | 1 // Copyright 2016 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/fpdfdoc/include/cpdf_occontext.h" | 7 #include "core/fpdfdoc/include/cpdf_occontext.h" |
8 | 8 |
9 #include "core/fpdfapi/fpdf_page/cpdf_contentmarkdata.h" | 9 #include "core/fpdfapi/fpdf_page/cpdf_contentmarkdata.h" |
10 #include "core/fpdfapi/fpdf_page/include/cpdf_pageobject.h" | 10 #include "core/fpdfapi/fpdf_page/include/cpdf_pageobject.h" |
11 #include "core/fpdfapi/fpdf_parser/include/cpdf_array.h" | 11 #include "core/fpdfapi/fpdf_parser/include/cpdf_array.h" |
12 #include "core/fpdfapi/fpdf_parser/include/cpdf_document.h" | 12 #include "core/fpdfapi/fpdf_parser/include/cpdf_document.h" |
13 | 13 |
14 namespace { | 14 namespace { |
15 | 15 |
16 int32_t FPDFDOC_OCG_FindGroup(const CPDF_Array* pArray, | 16 int32_t FindGroup(const CPDF_Array* pArray, const CPDF_Dictionary* pGroupDict) { |
17 const CPDF_Dictionary* pGroupDict) { | |
18 if (!pArray || !pGroupDict) | 17 if (!pArray || !pGroupDict) |
19 return -1; | 18 return -1; |
20 | 19 |
21 for (size_t i = 0; i < pArray->GetCount(); i++) { | 20 for (size_t i = 0; i < pArray->GetCount(); i++) { |
22 if (pArray->GetDictAt(i) == pGroupDict) | 21 if (pArray->GetDictAt(i) == pGroupDict) |
23 return i; | 22 return i; |
24 } | 23 } |
25 return -1; | 24 return -1; |
26 } | 25 } |
27 | 26 |
28 bool FPDFDOC_OCG_HasIntent(const CPDF_Dictionary* pDict, | 27 bool HasIntent(const CPDF_Dictionary* pDict, |
29 const CFX_ByteStringC& csElement, | 28 const CFX_ByteStringC& csElement, |
30 const CFX_ByteStringC& csDef) { | 29 const CFX_ByteStringC& csDef) { |
31 CPDF_Object* pIntent = pDict->GetDirectObjectBy("Intent"); | 30 CPDF_Object* pIntent = pDict->GetDirectObjectBy("Intent"); |
32 if (!pIntent) | 31 if (!pIntent) |
33 return csElement == csDef; | 32 return csElement == csDef; |
34 | 33 |
35 CFX_ByteString bsIntent; | 34 CFX_ByteString bsIntent; |
36 if (CPDF_Array* pArray = pIntent->AsArray()) { | 35 if (CPDF_Array* pArray = pIntent->AsArray()) { |
37 for (size_t i = 0; i < pArray->GetCount(); i++) { | 36 for (size_t i = 0; i < pArray->GetCount(); i++) { |
38 bsIntent = pArray->GetStringAt(i); | 37 bsIntent = pArray->GetStringAt(i); |
39 if (bsIntent == "All" || bsIntent == csElement) | 38 if (bsIntent == "All" || bsIntent == csElement) |
40 return true; | 39 return true; |
41 } | 40 } |
42 return false; | 41 return false; |
43 } | 42 } |
44 bsIntent = pIntent->GetString(); | 43 bsIntent = pIntent->GetString(); |
45 return bsIntent == "All" || bsIntent == csElement; | 44 return bsIntent == "All" || bsIntent == csElement; |
46 } | 45 } |
47 | 46 |
48 CPDF_Dictionary* FPDFDOC_OCG_GetConfig(CPDF_Document* pDoc, | 47 CPDF_Dictionary* GetConfig(CPDF_Document* pDoc, |
49 const CPDF_Dictionary* pOCGDict) { | 48 const CPDF_Dictionary* pOCGDict) { |
50 ASSERT(pOCGDict); | 49 ASSERT(pOCGDict); |
51 CPDF_Dictionary* pOCProperties = pDoc->GetRoot()->GetDictBy("OCProperties"); | 50 CPDF_Dictionary* pOCProperties = pDoc->GetRoot()->GetDictBy("OCProperties"); |
52 if (!pOCProperties) | 51 if (!pOCProperties) |
53 return nullptr; | 52 return nullptr; |
54 | 53 |
55 CPDF_Array* pOCGs = pOCProperties->GetArrayBy("OCGs"); | 54 CPDF_Array* pOCGs = pOCProperties->GetArrayBy("OCGs"); |
56 if (!pOCGs) | 55 if (!pOCGs) |
57 return nullptr; | 56 return nullptr; |
58 | 57 |
59 if (FPDFDOC_OCG_FindGroup(pOCGs, pOCGDict) < 0) | 58 if (FindGroup(pOCGs, pOCGDict) < 0) |
60 return nullptr; | 59 return nullptr; |
61 | 60 |
62 CPDF_Dictionary* pConfig = pOCProperties->GetDictBy("D"); | 61 CPDF_Dictionary* pConfig = pOCProperties->GetDictBy("D"); |
63 CPDF_Array* pConfigs = pOCProperties->GetArrayBy("Configs"); | 62 CPDF_Array* pConfigs = pOCProperties->GetArrayBy("Configs"); |
64 if (!pConfigs) | 63 if (!pConfigs) |
65 return pConfig; | 64 return pConfig; |
66 | 65 |
67 for (size_t i = 0; i < pConfigs->GetCount(); i++) { | 66 for (size_t i = 0; i < pConfigs->GetCount(); i++) { |
68 CPDF_Dictionary* pFind = pConfigs->GetDictAt(i); | 67 CPDF_Dictionary* pFind = pConfigs->GetDictAt(i); |
69 if (pFind && FPDFDOC_OCG_HasIntent(pFind, "View", "View")) | 68 if (pFind && HasIntent(pFind, "View", "View")) |
70 return pFind; | 69 return pFind; |
71 } | 70 } |
72 return pConfig; | 71 return pConfig; |
73 } | 72 } |
74 | 73 |
75 CFX_ByteString FPDFDOC_OCG_GetUsageTypeString(CPDF_OCContext::UsageType eType) { | 74 CFX_ByteString GetUsageTypeString(CPDF_OCContext::UsageType eType) { |
76 CFX_ByteString csState; | 75 CFX_ByteString csState; |
77 switch (eType) { | 76 switch (eType) { |
78 case CPDF_OCContext::Design: | 77 case CPDF_OCContext::Design: |
79 csState = "Design"; | 78 csState = "Design"; |
80 break; | 79 break; |
81 case CPDF_OCContext::Print: | 80 case CPDF_OCContext::Print: |
82 csState = "Print"; | 81 csState = "Print"; |
83 break; | 82 break; |
84 case CPDF_OCContext::Export: | 83 case CPDF_OCContext::Export: |
85 csState = "Export"; | 84 csState = "Export"; |
86 break; | 85 break; |
87 default: | 86 default: |
88 csState = "View"; | 87 csState = "View"; |
89 break; | 88 break; |
90 } | 89 } |
91 return csState; | 90 return csState; |
92 } | 91 } |
93 | 92 |
94 } // namespace | 93 } // namespace |
95 | 94 |
96 CPDF_OCContext::CPDF_OCContext(CPDF_Document* pDoc, UsageType eUsageType) | 95 CPDF_OCContext::CPDF_OCContext(CPDF_Document* pDoc, UsageType eUsageType) |
97 : m_pDocument(pDoc), m_eUsageType(eUsageType) { | 96 : m_pDocument(pDoc), m_eUsageType(eUsageType) { |
98 ASSERT(pDoc); | 97 ASSERT(pDoc); |
99 } | 98 } |
100 | 99 |
101 CPDF_OCContext::~CPDF_OCContext() { | 100 CPDF_OCContext::~CPDF_OCContext() {} |
102 } | |
103 | 101 |
104 bool CPDF_OCContext::LoadOCGStateFromConfig( | 102 bool CPDF_OCContext::LoadOCGStateFromConfig( |
105 const CFX_ByteString& csConfig, | 103 const CFX_ByteString& csConfig, |
106 const CPDF_Dictionary* pOCGDict) const { | 104 const CPDF_Dictionary* pOCGDict) const { |
107 CPDF_Dictionary* pConfig = FPDFDOC_OCG_GetConfig(m_pDocument, pOCGDict); | 105 CPDF_Dictionary* pConfig = GetConfig(m_pDocument, pOCGDict); |
108 if (!pConfig) | 106 if (!pConfig) |
109 return true; | 107 return true; |
110 | 108 |
111 bool bState = pConfig->GetStringBy("BaseState", "ON") != "OFF"; | 109 bool bState = pConfig->GetStringBy("BaseState", "ON") != "OFF"; |
112 CPDF_Array* pArray = pConfig->GetArrayBy("ON"); | 110 CPDF_Array* pArray = pConfig->GetArrayBy("ON"); |
113 if (pArray) { | 111 if (pArray) { |
114 if (FPDFDOC_OCG_FindGroup(pArray, pOCGDict) >= 0) | 112 if (FindGroup(pArray, pOCGDict) >= 0) |
115 bState = true; | 113 bState = true; |
116 } | 114 } |
117 pArray = pConfig->GetArrayBy("OFF"); | 115 pArray = pConfig->GetArrayBy("OFF"); |
118 if (pArray) { | 116 if (pArray) { |
119 if (FPDFDOC_OCG_FindGroup(pArray, pOCGDict) >= 0) | 117 if (FindGroup(pArray, pOCGDict) >= 0) |
120 bState = false; | 118 bState = false; |
121 } | 119 } |
122 pArray = pConfig->GetArrayBy("AS"); | 120 pArray = pConfig->GetArrayBy("AS"); |
123 if (!pArray) | 121 if (!pArray) |
124 return bState; | 122 return bState; |
125 | 123 |
126 CFX_ByteString csFind = csConfig + "State"; | 124 CFX_ByteString csFind = csConfig + "State"; |
127 for (size_t i = 0; i < pArray->GetCount(); i++) { | 125 for (size_t i = 0; i < pArray->GetCount(); i++) { |
128 CPDF_Dictionary* pUsage = pArray->GetDictAt(i); | 126 CPDF_Dictionary* pUsage = pArray->GetDictAt(i); |
129 if (!pUsage) | 127 if (!pUsage) |
130 continue; | 128 continue; |
131 | 129 |
132 if (pUsage->GetStringBy("Event", "View") != csConfig) | 130 if (pUsage->GetStringBy("Event", "View") != csConfig) |
133 continue; | 131 continue; |
134 | 132 |
135 CPDF_Array* pOCGs = pUsage->GetArrayBy("OCGs"); | 133 CPDF_Array* pOCGs = pUsage->GetArrayBy("OCGs"); |
136 if (!pOCGs) | 134 if (!pOCGs) |
137 continue; | 135 continue; |
138 | 136 |
139 if (FPDFDOC_OCG_FindGroup(pOCGs, pOCGDict) < 0) | 137 if (FindGroup(pOCGs, pOCGDict) < 0) |
140 continue; | 138 continue; |
141 | 139 |
142 CPDF_Dictionary* pState = pUsage->GetDictBy(csConfig); | 140 CPDF_Dictionary* pState = pUsage->GetDictBy(csConfig); |
143 if (!pState) | 141 if (!pState) |
144 continue; | 142 continue; |
145 | 143 |
146 bState = pState->GetStringBy(csFind) != "OFF"; | 144 bState = pState->GetStringBy(csFind) != "OFF"; |
147 } | 145 } |
148 return bState; | 146 return bState; |
149 } | 147 } |
150 | 148 |
151 bool CPDF_OCContext::LoadOCGState(const CPDF_Dictionary* pOCGDict) const { | 149 bool CPDF_OCContext::LoadOCGState(const CPDF_Dictionary* pOCGDict) const { |
152 if (!FPDFDOC_OCG_HasIntent(pOCGDict, "View", "View")) | 150 if (!HasIntent(pOCGDict, "View", "View")) |
153 return true; | 151 return true; |
154 | 152 |
155 CFX_ByteString csState = FPDFDOC_OCG_GetUsageTypeString(m_eUsageType); | 153 CFX_ByteString csState = GetUsageTypeString(m_eUsageType); |
156 CPDF_Dictionary* pUsage = pOCGDict->GetDictBy("Usage"); | 154 CPDF_Dictionary* pUsage = pOCGDict->GetDictBy("Usage"); |
157 if (pUsage) { | 155 if (pUsage) { |
158 CPDF_Dictionary* pState = pUsage->GetDictBy(csState); | 156 CPDF_Dictionary* pState = pUsage->GetDictBy(csState); |
159 if (pState) { | 157 if (pState) { |
160 CFX_ByteString csFind = csState + "State"; | 158 CFX_ByteString csFind = csState + "State"; |
161 if (pState->KeyExist(csFind)) { | 159 if (pState->KeyExist(csFind)) |
162 return pState->GetStringBy(csFind) != "OFF"; | 160 return pState->GetStringBy(csFind) != "OFF"; |
163 } | |
164 } | 161 } |
165 if (csState != "View") { | 162 if (csState != "View") { |
166 pState = pUsage->GetDictBy("View"); | 163 pState = pUsage->GetDictBy("View"); |
167 if (pState && pState->KeyExist("ViewState")) { | 164 if (pState && pState->KeyExist("ViewState")) |
168 return pState->GetStringBy("ViewState") != "OFF"; | 165 return pState->GetStringBy("ViewState") != "OFF"; |
169 } | |
170 } | 166 } |
171 } | 167 } |
172 return LoadOCGStateFromConfig(csState, pOCGDict); | 168 return LoadOCGStateFromConfig(csState, pOCGDict); |
173 } | 169 } |
174 | 170 |
175 bool CPDF_OCContext::GetOCGVisible(const CPDF_Dictionary* pOCGDict) { | 171 bool CPDF_OCContext::GetOCGVisible(const CPDF_Dictionary* pOCGDict) { |
176 if (!pOCGDict) | 172 if (!pOCGDict) |
177 return false; | 173 return false; |
178 | 174 |
179 const auto it = m_OCGStates.find(pOCGDict); | 175 const auto it = m_OCGStates.find(pOCGDict); |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
276 | 272 |
277 bool CPDF_OCContext::CheckOCGVisible(const CPDF_Dictionary* pOCGDict) { | 273 bool CPDF_OCContext::CheckOCGVisible(const CPDF_Dictionary* pOCGDict) { |
278 if (!pOCGDict) | 274 if (!pOCGDict) |
279 return true; | 275 return true; |
280 | 276 |
281 CFX_ByteString csType = pOCGDict->GetStringBy("Type", "OCG"); | 277 CFX_ByteString csType = pOCGDict->GetStringBy("Type", "OCG"); |
282 if (csType == "OCG") | 278 if (csType == "OCG") |
283 return GetOCGVisible(pOCGDict); | 279 return GetOCGVisible(pOCGDict); |
284 return LoadOCMDState(pOCGDict); | 280 return LoadOCMDState(pOCGDict); |
285 } | 281 } |
OLD | NEW |