xref: /aosp_15_r20/external/pdfium/fpdfsdk/fpdf_thumbnail.cpp (revision 3ac0a46f773bac49fa9476ec2b1cf3f8da5ec3a4)
1 // Copyright 2019 The PDFium Authors
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "public/fpdf_thumbnail.h"
6 
7 #include <utility>
8 
9 #include "core/fpdfapi/page/cpdf_dib.h"
10 #include "core/fpdfapi/page/cpdf_page.h"
11 #include "core/fpdfapi/parser/cpdf_dictionary.h"
12 #include "core/fpdfapi/parser/cpdf_stream.h"
13 #include "core/fpdfapi/parser/cpdf_stream_acc.h"
14 #include "core/fxge/dib/cfx_dibitmap.h"
15 #include "fpdfsdk/cpdfsdk_helpers.h"
16 #include "public/fpdfview.h"
17 
18 namespace {
19 
CPDFStreamForThumbnailFromPage(FPDF_PAGE page)20 RetainPtr<const CPDF_Stream> CPDFStreamForThumbnailFromPage(FPDF_PAGE page) {
21   const CPDF_Page* pdf_page = CPDFPageFromFPDFPage(page);
22   if (!pdf_page)
23     return nullptr;
24 
25   RetainPtr<const CPDF_Dictionary> page_dict = pdf_page->GetDict();
26   if (!page_dict->KeyExist("Type"))
27     return nullptr;
28 
29   return page_dict->GetStreamFor("Thumb");
30 }
31 
32 }  // namespace
33 
34 FPDF_EXPORT unsigned long FPDF_CALLCONV
FPDFPage_GetDecodedThumbnailData(FPDF_PAGE page,void * buffer,unsigned long buflen)35 FPDFPage_GetDecodedThumbnailData(FPDF_PAGE page,
36                                  void* buffer,
37                                  unsigned long buflen) {
38   RetainPtr<const CPDF_Stream> thumb_stream =
39       CPDFStreamForThumbnailFromPage(page);
40   if (!thumb_stream)
41     return 0u;
42 
43   return DecodeStreamMaybeCopyAndReturnLength(
44       std::move(thumb_stream),
45       {static_cast<uint8_t*>(buffer), static_cast<size_t>(buflen)});
46 }
47 
48 FPDF_EXPORT unsigned long FPDF_CALLCONV
FPDFPage_GetRawThumbnailData(FPDF_PAGE page,void * buffer,unsigned long buflen)49 FPDFPage_GetRawThumbnailData(FPDF_PAGE page,
50                              void* buffer,
51                              unsigned long buflen) {
52   RetainPtr<const CPDF_Stream> thumb_stream =
53       CPDFStreamForThumbnailFromPage(page);
54   if (!thumb_stream)
55     return 0u;
56 
57   return GetRawStreamMaybeCopyAndReturnLength(
58       std::move(thumb_stream),
59       {static_cast<uint8_t*>(buffer), static_cast<size_t>(buflen)});
60 }
61 
62 FPDF_EXPORT FPDF_BITMAP FPDF_CALLCONV
FPDFPage_GetThumbnailAsBitmap(FPDF_PAGE page)63 FPDFPage_GetThumbnailAsBitmap(FPDF_PAGE page) {
64   RetainPtr<const CPDF_Stream> thumb_stream =
65       CPDFStreamForThumbnailFromPage(page);
66   if (!thumb_stream)
67     return nullptr;
68 
69   const CPDF_Page* pdf_page = CPDFPageFromFPDFPage(page);
70   auto dib_source = pdfium::MakeRetain<CPDF_DIB>(pdf_page->GetDocument(),
71                                                  std::move(thumb_stream));
72   const CPDF_DIB::LoadState start_status = dib_source->StartLoadDIBBase(
73       false, nullptr, pdf_page->GetPageResources().Get(), false,
74       CPDF_ColorSpace::Family::kUnknown, false, {0, 0});
75   if (start_status == CPDF_DIB::LoadState::kFail)
76     return nullptr;
77 
78   auto thumb_bitmap = pdfium::MakeRetain<CFX_DIBitmap>();
79   if (!thumb_bitmap->Copy(dib_source))
80     return nullptr;
81 
82   return FPDFBitmapFromCFXDIBitmap(thumb_bitmap.Leak());
83 }
84