OLD | NEW |
1 // Copyright 2016 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/fpdfapi/page/cpdf_image.h" | 7 #include "core/fpdfapi/page/cpdf_image.h" |
8 | 8 |
9 #include <algorithm> | 9 #include <algorithm> |
| 10 #include <memory> |
10 #include <utility> | 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/page/cpdf_page.h" | 15 #include "core/fpdfapi/page/cpdf_page.h" |
15 #include "core/fpdfapi/parser/cpdf_array.h" | 16 #include "core/fpdfapi/parser/cpdf_array.h" |
16 #include "core/fpdfapi/parser/cpdf_boolean.h" | 17 #include "core/fpdfapi/parser/cpdf_boolean.h" |
17 #include "core/fpdfapi/parser/cpdf_dictionary.h" | 18 #include "core/fpdfapi/parser/cpdf_dictionary.h" |
18 #include "core/fpdfapi/parser/cpdf_document.h" | 19 #include "core/fpdfapi/parser/cpdf_document.h" |
19 #include "core/fpdfapi/parser/cpdf_name.h" | 20 #include "core/fpdfapi/parser/cpdf_name.h" |
20 #include "core/fpdfapi/parser/cpdf_number.h" | 21 #include "core/fpdfapi/parser/cpdf_number.h" |
21 #include "core/fpdfapi/parser/cpdf_reference.h" | 22 #include "core/fpdfapi/parser/cpdf_reference.h" |
| 23 #include "core/fpdfapi/parser/cpdf_stream.h" |
22 #include "core/fpdfapi/parser/cpdf_string.h" | 24 #include "core/fpdfapi/parser/cpdf_string.h" |
23 #include "core/fpdfapi/render/cpdf_pagerendercache.h" | 25 #include "core/fpdfapi/render/cpdf_pagerendercache.h" |
24 #include "core/fpdfapi/render/render_int.h" | 26 #include "core/fpdfapi/render/render_int.h" |
25 #include "core/fxcodec/fx_codec.h" | 27 #include "core/fxcodec/fx_codec.h" |
26 #include "core/fxge/fx_dib.h" | 28 #include "core/fxge/fx_dib.h" |
| 29 #include "third_party/base/ptr_util.h" |
27 | 30 |
28 CPDF_Image::CPDF_Image(CPDF_Document* pDoc) : m_pDocument(pDoc) {} | 31 CPDF_Image::CPDF_Image(CPDF_Document* pDoc) : m_pDocument(pDoc) {} |
29 | 32 |
30 CPDF_Image::CPDF_Image(CPDF_Document* pDoc, | 33 CPDF_Image::CPDF_Image(CPDF_Document* pDoc, |
31 std::unique_ptr<CPDF_Stream> pStream) | 34 std::unique_ptr<CPDF_Stream> pStream) |
32 : m_bIsInline(true), | 35 : m_bIsInline(true), |
33 m_pDocument(pDoc), | 36 m_pDocument(pDoc), |
34 m_pStream(pStream.get()), | 37 m_pStream(pStream.get()), |
35 m_pOwnedStream(std::move(pStream)) { | 38 m_pOwnedStream(std::move(pStream)) { |
36 m_pOwnedDict = | 39 m_pOwnedDict = |
(...skipping 103 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
140 pFile->ReadBlock(data.data(), 0, dwEstimateSize); | 143 pFile->ReadBlock(data.data(), 0, dwEstimateSize); |
141 CPDF_Dictionary* pDict = InitJPEG(data.data(), dwEstimateSize); | 144 CPDF_Dictionary* pDict = InitJPEG(data.data(), dwEstimateSize); |
142 if (!pDict && size > dwEstimateSize) { | 145 if (!pDict && size > dwEstimateSize) { |
143 data.resize(size); | 146 data.resize(size); |
144 pFile->ReadBlock(data.data(), 0, size); | 147 pFile->ReadBlock(data.data(), 0, size); |
145 pDict = InitJPEG(data.data(), size); | 148 pDict = InitJPEG(data.data(), size); |
146 } | 149 } |
147 if (!pDict) | 150 if (!pDict) |
148 return; | 151 return; |
149 | 152 |
150 m_pStream->InitStreamFromFile(pFile, pDict); | 153 m_pStream->InitStreamFromFile(pFile, pdfium::WrapUnique(pDict)); |
151 } | 154 } |
152 | 155 |
153 void CPDF_Image::SetImage(const CFX_DIBitmap* pBitmap, int32_t iCompress) { | 156 void CPDF_Image::SetImage(const CFX_DIBitmap* pBitmap, int32_t iCompress) { |
154 int32_t BitmapWidth = pBitmap->GetWidth(); | 157 int32_t BitmapWidth = pBitmap->GetWidth(); |
155 int32_t BitmapHeight = pBitmap->GetHeight(); | 158 int32_t BitmapHeight = pBitmap->GetHeight(); |
156 if (BitmapWidth < 1 || BitmapHeight < 1) { | 159 if (BitmapWidth < 1 || BitmapHeight < 1) { |
157 return; | 160 return; |
158 } | 161 } |
159 uint8_t* src_buf = pBitmap->GetBuffer(); | 162 uint8_t* src_buf = pBitmap->GetBuffer(); |
160 int32_t src_pitch = pBitmap->GetPitch(); | 163 int32_t src_pitch = pBitmap->GetPitch(); |
161 int32_t bpp = pBitmap->GetBPP(); | 164 int32_t bpp = pBitmap->GetBPP(); |
162 | 165 |
163 CPDF_Dictionary* pDict = | 166 auto pDict = |
164 new CPDF_Dictionary(m_pDocument->GetByteStringPool()); | 167 pdfium::MakeUnique<CPDF_Dictionary>(m_pDocument->GetByteStringPool()); |
165 pDict->SetNewFor<CPDF_Name>("Type", "XObject"); | 168 pDict->SetNewFor<CPDF_Name>("Type", "XObject"); |
166 pDict->SetNewFor<CPDF_Name>("Subtype", "Image"); | 169 pDict->SetNewFor<CPDF_Name>("Subtype", "Image"); |
167 pDict->SetNewFor<CPDF_Number>("Width", BitmapWidth); | 170 pDict->SetNewFor<CPDF_Number>("Width", BitmapWidth); |
168 pDict->SetNewFor<CPDF_Number>("Height", BitmapHeight); | 171 pDict->SetNewFor<CPDF_Number>("Height", BitmapHeight); |
169 uint8_t* dest_buf = nullptr; | 172 uint8_t* dest_buf = nullptr; |
170 FX_STRSIZE dest_pitch = 0, dest_size = 0, opType = -1; | 173 FX_STRSIZE dest_pitch = 0, dest_size = 0, opType = -1; |
171 if (bpp == 1) { | 174 if (bpp == 1) { |
172 int32_t reset_a = 0, reset_r = 0, reset_g = 0, reset_b = 0; | 175 int32_t reset_a = 0, reset_r = 0, reset_g = 0, reset_b = 0; |
173 int32_t set_a = 0, set_r = 0, set_g = 0, set_b = 0; | 176 int32_t set_a = 0, set_r = 0, set_g = 0, set_b = 0; |
174 if (!pBitmap->IsAlphaMask()) { | 177 if (!pBitmap->IsAlphaMask()) { |
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
215 pCS->AddNew<CPDF_Number>(iPalette - 1); | 218 pCS->AddNew<CPDF_Number>(iPalette - 1); |
216 uint8_t* pColorTable = FX_Alloc2D(uint8_t, iPalette, 3); | 219 uint8_t* pColorTable = FX_Alloc2D(uint8_t, iPalette, 3); |
217 uint8_t* ptr = pColorTable; | 220 uint8_t* ptr = pColorTable; |
218 for (int32_t i = 0; i < iPalette; i++) { | 221 for (int32_t i = 0; i < iPalette; i++) { |
219 uint32_t argb = pBitmap->GetPaletteArgb(i); | 222 uint32_t argb = pBitmap->GetPaletteArgb(i); |
220 ptr[0] = (uint8_t)(argb >> 16); | 223 ptr[0] = (uint8_t)(argb >> 16); |
221 ptr[1] = (uint8_t)(argb >> 8); | 224 ptr[1] = (uint8_t)(argb >> 8); |
222 ptr[2] = (uint8_t)argb; | 225 ptr[2] = (uint8_t)argb; |
223 ptr += 3; | 226 ptr += 3; |
224 } | 227 } |
| 228 auto pNewDict = |
| 229 pdfium::MakeUnique<CPDF_Dictionary>(m_pDocument->GetByteStringPool()); |
225 CPDF_Stream* pCTS = m_pDocument->NewIndirect<CPDF_Stream>( | 230 CPDF_Stream* pCTS = m_pDocument->NewIndirect<CPDF_Stream>( |
226 pColorTable, iPalette * 3, | 231 pColorTable, iPalette * 3, std::move(pNewDict)); |
227 new CPDF_Dictionary(m_pDocument->GetByteStringPool())); | |
228 pCS->AddNew<CPDF_Reference>(m_pDocument, pCTS->GetObjNum()); | 232 pCS->AddNew<CPDF_Reference>(m_pDocument, pCTS->GetObjNum()); |
229 pDict->SetNewFor<CPDF_Reference>("ColorSpace", m_pDocument, | 233 pDict->SetNewFor<CPDF_Reference>("ColorSpace", m_pDocument, |
230 pCS->GetObjNum()); | 234 pCS->GetObjNum()); |
231 } else { | 235 } else { |
232 pDict->SetNewFor<CPDF_Name>("ColorSpace", "DeviceGray"); | 236 pDict->SetNewFor<CPDF_Name>("ColorSpace", "DeviceGray"); |
233 } | 237 } |
234 pDict->SetNewFor<CPDF_Number>("BitsPerComponent", 8); | 238 pDict->SetNewFor<CPDF_Number>("BitsPerComponent", 8); |
235 if ((iCompress & 0x03) == PDF_IMAGE_NO_COMPRESS) { | 239 if ((iCompress & 0x03) == PDF_IMAGE_NO_COMPRESS) { |
236 dest_pitch = BitmapWidth; | 240 dest_pitch = BitmapWidth; |
237 opType = 1; | 241 opType = 1; |
(...skipping 14 matching lines...) Expand all Loading... |
252 bool bDeleteMask = false; | 256 bool bDeleteMask = false; |
253 if (pBitmap->HasAlpha()) { | 257 if (pBitmap->HasAlpha()) { |
254 pMaskBitmap = pBitmap->GetAlphaMask(); | 258 pMaskBitmap = pBitmap->GetAlphaMask(); |
255 bDeleteMask = true; | 259 bDeleteMask = true; |
256 } | 260 } |
257 if (pMaskBitmap) { | 261 if (pMaskBitmap) { |
258 int32_t maskWidth = pMaskBitmap->GetWidth(); | 262 int32_t maskWidth = pMaskBitmap->GetWidth(); |
259 int32_t maskHeight = pMaskBitmap->GetHeight(); | 263 int32_t maskHeight = pMaskBitmap->GetHeight(); |
260 uint8_t* mask_buf = nullptr; | 264 uint8_t* mask_buf = nullptr; |
261 FX_STRSIZE mask_size = 0; | 265 FX_STRSIZE mask_size = 0; |
262 CPDF_Dictionary* pMaskDict = | 266 auto pMaskDict = |
263 new CPDF_Dictionary(m_pDocument->GetByteStringPool()); | 267 pdfium::MakeUnique<CPDF_Dictionary>(m_pDocument->GetByteStringPool()); |
264 pMaskDict->SetNewFor<CPDF_Name>("Type", "XObject"); | 268 pMaskDict->SetNewFor<CPDF_Name>("Type", "XObject"); |
265 pMaskDict->SetNewFor<CPDF_Name>("Subtype", "Image"); | 269 pMaskDict->SetNewFor<CPDF_Name>("Subtype", "Image"); |
266 pMaskDict->SetNewFor<CPDF_Number>("Width", maskWidth); | 270 pMaskDict->SetNewFor<CPDF_Number>("Width", maskWidth); |
267 pMaskDict->SetNewFor<CPDF_Number>("Height", maskHeight); | 271 pMaskDict->SetNewFor<CPDF_Number>("Height", maskHeight); |
268 pMaskDict->SetNewFor<CPDF_Name>("ColorSpace", "DeviceGray"); | 272 pMaskDict->SetNewFor<CPDF_Name>("ColorSpace", "DeviceGray"); |
269 pMaskDict->SetNewFor<CPDF_Number>("BitsPerComponent", 8); | 273 pMaskDict->SetNewFor<CPDF_Number>("BitsPerComponent", 8); |
270 if (pMaskBitmap->GetBPP() == 8 && | 274 if (pMaskBitmap->GetBPP() == 8 && |
271 (iCompress & PDF_IMAGE_MASK_LOSSY_COMPRESS) != 0) { | 275 (iCompress & PDF_IMAGE_MASK_LOSSY_COMPRESS) != 0) { |
272 } else if (pMaskBitmap->GetFormat() == FXDIB_1bppMask) { | 276 } else if (pMaskBitmap->GetFormat() == FXDIB_1bppMask) { |
273 } else { | 277 } else { |
274 mask_buf = FX_Alloc2D(uint8_t, maskHeight, maskWidth); | 278 mask_buf = FX_Alloc2D(uint8_t, maskHeight, maskWidth); |
275 mask_size = maskHeight * maskWidth; // Safe since checked alloc returned. | 279 mask_size = maskHeight * maskWidth; // Safe since checked alloc returned. |
276 for (int32_t a = 0; a < maskHeight; a++) { | 280 for (int32_t a = 0; a < maskHeight; a++) { |
277 FXSYS_memcpy(mask_buf + a * maskWidth, pMaskBitmap->GetScanline(a), | 281 FXSYS_memcpy(mask_buf + a * maskWidth, pMaskBitmap->GetScanline(a), |
278 maskWidth); | 282 maskWidth); |
279 } | 283 } |
280 } | 284 } |
281 pMaskDict->SetNewFor<CPDF_Number>("Length", mask_size); | 285 pMaskDict->SetNewFor<CPDF_Number>("Length", mask_size); |
282 pDict->SetNewFor<CPDF_Reference>( | 286 CPDF_Stream* pNewStream = m_pDocument->NewIndirect<CPDF_Stream>( |
283 "SMask", m_pDocument, | 287 mask_buf, mask_size, std::move(pMaskDict)); |
284 m_pDocument->NewIndirect<CPDF_Stream>(mask_buf, mask_size, pMaskDict) | 288 pDict->SetNewFor<CPDF_Reference>("SMask", m_pDocument, |
285 ->GetObjNum()); | 289 pNewStream->GetObjNum()); |
286 if (bDeleteMask) | 290 if (bDeleteMask) |
287 delete pMaskBitmap; | 291 delete pMaskBitmap; |
288 } | 292 } |
289 if (opType == 0) { | 293 if (opType == 0) { |
290 if (iCompress & PDF_IMAGE_LOSSLESS_COMPRESS) { | 294 if (iCompress & PDF_IMAGE_LOSSLESS_COMPRESS) { |
291 } else { | 295 } else { |
292 if (pBitmap->GetBPP() == 1) { | 296 if (pBitmap->GetBPP() == 1) { |
293 } else if (pBitmap->GetBPP() >= 8 && pBitmap->GetPalette()) { | 297 } else if (pBitmap->GetBPP() >= 8 && pBitmap->GetPalette()) { |
294 CFX_DIBitmap* pNewBitmap = new CFX_DIBitmap(); | 298 CFX_DIBitmap* pNewBitmap = new CFX_DIBitmap(); |
295 pNewBitmap->Copy(pBitmap); | 299 pNewBitmap->Copy(pBitmap); |
296 pNewBitmap->ConvertFormat(FXDIB_Rgb); | 300 pNewBitmap->ConvertFormat(FXDIB_Rgb); |
297 SetImage(pNewBitmap, iCompress); | 301 SetImage(pNewBitmap, iCompress); |
298 delete pDict; | |
299 pDict = nullptr; | |
300 FX_Free(dest_buf); | 302 FX_Free(dest_buf); |
301 dest_buf = nullptr; | 303 dest_buf = nullptr; |
302 dest_size = 0; | 304 dest_size = 0; |
303 delete pNewBitmap; | 305 delete pNewBitmap; |
304 return; | 306 return; |
305 } | 307 } |
306 } | 308 } |
307 } else if (opType == 1) { | 309 } else if (opType == 1) { |
308 dest_buf = FX_Alloc2D(uint8_t, dest_pitch, BitmapHeight); | 310 dest_buf = FX_Alloc2D(uint8_t, dest_pitch, BitmapHeight); |
309 dest_size = dest_pitch * BitmapHeight; // Safe as checked alloc returned. | 311 dest_size = dest_pitch * BitmapHeight; // Safe as checked alloc returned. |
(...skipping 23 matching lines...) Expand all Loading... |
333 } | 335 } |
334 | 336 |
335 pDest += dest_pitch; | 337 pDest += dest_pitch; |
336 dest_offset = 0; | 338 dest_offset = 0; |
337 } | 339 } |
338 } | 340 } |
339 if (!m_pStream) { | 341 if (!m_pStream) { |
340 m_pOwnedStream = pdfium::MakeUnique<CPDF_Stream>(); | 342 m_pOwnedStream = pdfium::MakeUnique<CPDF_Stream>(); |
341 m_pStream = m_pOwnedStream.get(); | 343 m_pStream = m_pOwnedStream.get(); |
342 } | 344 } |
343 m_pStream->InitStream(dest_buf, dest_size, pDict); | 345 m_pStream->InitStream(dest_buf, dest_size, std::move(pDict)); |
344 m_bIsMask = pBitmap->IsAlphaMask(); | 346 m_bIsMask = pBitmap->IsAlphaMask(); |
345 m_Width = BitmapWidth; | 347 m_Width = BitmapWidth; |
346 m_Height = BitmapHeight; | 348 m_Height = BitmapHeight; |
347 FX_Free(dest_buf); | 349 FX_Free(dest_buf); |
348 } | 350 } |
349 | 351 |
350 void CPDF_Image::ResetCache(CPDF_Page* pPage, const CFX_DIBitmap* pBitmap) { | 352 void CPDF_Image::ResetCache(CPDF_Page* pPage, const CFX_DIBitmap* pBitmap) { |
351 pPage->GetRenderCache()->ResetBitmap(m_pStream, pBitmap); | 353 pPage->GetRenderCache()->ResetBitmap(m_pStream, pBitmap); |
352 } | 354 } |
353 | 355 |
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
408 } | 410 } |
409 if (!ret) { | 411 if (!ret) { |
410 delete m_pDIBSource; | 412 delete m_pDIBSource; |
411 m_pDIBSource = nullptr; | 413 m_pDIBSource = nullptr; |
412 return false; | 414 return false; |
413 } | 415 } |
414 m_pMask = pSource->DetachMask(); | 416 m_pMask = pSource->DetachMask(); |
415 m_MatteColor = pSource->GetMatteColor(); | 417 m_MatteColor = pSource->GetMatteColor(); |
416 return false; | 418 return false; |
417 } | 419 } |
OLD | NEW |