Add some experimental float API variants in public/fpdfview.h.
These new API variants listed below use floats instead of doubles. They
are better because they work more seamlessly with the underlying
implementation, which uses floats. The original non-F variants have
notes that the they will be deprecated soon.
The new APIs in this CL are:
- FPDF_GetPageHeightF()
- FPDF_GetPageSizeByIndexF()
- FPDF_GetPageWidthF()
This CL also introduces a size struct, FS_SIZEF, so APIs like
FPDF_GetPageSizeByIndexF() can take a single size out parameter instead
of two.
Some callers have been switched to them to show they work.
Bug: pdfium:996
Change-Id: Id9b4edbcdb2b429d8ea7e49bd2faf1e0bfc9e7e4
Reviewed-on: https://pdfium-review.googlesource.com/c/pdfium/+/61872
Commit-Queue: Lei Zhang <thestig@chromium.org>
Reviewed-by: Tom Sepez <tsepez@chromium.org>
diff --git a/fpdfsdk/fpdf_view.cpp b/fpdfsdk/fpdf_view.cpp
index e897274..40e13b8 100644
--- a/fpdfsdk/fpdf_view.cpp
+++ b/fpdfsdk/fpdf_view.cpp
@@ -355,14 +355,22 @@
return FPDFPageFromIPDFPage(pPage.Leak());
}
-FPDF_EXPORT double FPDF_CALLCONV FPDF_GetPageWidth(FPDF_PAGE page) {
+FPDF_EXPORT float FPDF_CALLCONV FPDF_GetPageWidthF(FPDF_PAGE page) {
IPDF_Page* pPage = IPDFPageFromFPDFPage(page);
- return pPage ? pPage->GetPageWidth() : 0.0;
+ return pPage ? pPage->GetPageWidth() : 0.0f;
+}
+
+FPDF_EXPORT double FPDF_CALLCONV FPDF_GetPageWidth(FPDF_PAGE page) {
+ return FPDF_GetPageWidthF(page);
+}
+
+FPDF_EXPORT float FPDF_CALLCONV FPDF_GetPageHeightF(FPDF_PAGE page) {
+ IPDF_Page* pPage = IPDFPageFromFPDFPage(page);
+ return pPage ? pPage->GetPageHeight() : 0.0f;
}
FPDF_EXPORT double FPDF_CALLCONV FPDF_GetPageHeight(FPDF_PAGE page) {
- IPDF_Page* pPage = IPDFPageFromFPDFPage(page);
- return pPage ? pPage->GetPageHeight() : 0.0;
+ return FPDF_GetPageHeightF(page);
}
FPDF_EXPORT FPDF_BOOL FPDF_CALLCONV FPDF_GetPageBoundingBox(FPDF_PAGE page,
@@ -914,11 +922,11 @@
flags, bNeedToRestore, pause);
}
-FPDF_EXPORT int FPDF_CALLCONV FPDF_GetPageSizeByIndex(FPDF_DOCUMENT document,
- int page_index,
- double* width,
- double* height) {
- if (!width || !height)
+FPDF_EXPORT FPDF_BOOL FPDF_CALLCONV
+FPDF_GetPageSizeByIndexF(FPDF_DOCUMENT document,
+ int page_index,
+ FS_SIZEF* size) {
+ if (!size)
return false;
auto* pDoc = CPDFDocumentFromFPDFDocument(document);
@@ -935,8 +943,8 @@
if (!pPage)
return false;
- *width = pPage->GetPageWidth();
- *height = pPage->GetPageHeight();
+ size->width = pPage->GetPageWidth();
+ size->height = pPage->GetPageHeight();
return true;
}
#endif // PDF_ENABLE_XFA
@@ -947,8 +955,24 @@
auto page = pdfium::MakeRetain<CPDF_Page>(pDoc, pDict);
page->SetRenderCache(pdfium::MakeUnique<CPDF_PageRenderCache>(page.Get()));
- *width = page->GetPageWidth();
- *height = page->GetPageHeight();
+ size->width = page->GetPageWidth();
+ size->height = page->GetPageHeight();
+ return true;
+}
+
+FPDF_EXPORT int FPDF_CALLCONV FPDF_GetPageSizeByIndex(FPDF_DOCUMENT document,
+ int page_index,
+ double* width,
+ double* height) {
+ if (!width || !height)
+ return false;
+
+ FS_SIZEF size;
+ if (!FPDF_GetPageSizeByIndexF(document, page_index, &size))
+ return false;
+
+ *width = size.width;
+ *height = size.height;
return true;
}
diff --git a/fpdfsdk/fpdf_view_c_api_test.c b/fpdfsdk/fpdf_view_c_api_test.c
index 2b888e4..dce7a23 100644
--- a/fpdfsdk/fpdf_view_c_api_test.c
+++ b/fpdfsdk/fpdf_view_c_api_test.c
@@ -401,8 +401,11 @@
CHK(FPDF_GetPageBoundingBox);
CHK(FPDF_GetPageCount);
CHK(FPDF_GetPageHeight);
+ CHK(FPDF_GetPageHeightF);
CHK(FPDF_GetPageSizeByIndex);
+ CHK(FPDF_GetPageSizeByIndexF);
CHK(FPDF_GetPageWidth);
+ CHK(FPDF_GetPageWidthF);
#ifdef PDF_ENABLE_V8
CHK(FPDF_GetRecommendedV8Flags);
#endif
diff --git a/fpdfsdk/fpdf_view_embeddertest.cpp b/fpdfsdk/fpdf_view_embeddertest.cpp
index a74e8f3..fbf3897 100644
--- a/fpdfsdk/fpdf_view_embeddertest.cpp
+++ b/fpdfsdk/fpdf_view_embeddertest.cpp
@@ -397,8 +397,8 @@
// Now try to access |doc| and make sure it still works.
ScopedFPDFPage page(FPDF_LoadPage(doc.get(), 0));
ASSERT_TRUE(page);
- EXPECT_DOUBLE_EQ(200, FPDF_GetPageWidth(page.get()));
- EXPECT_DOUBLE_EQ(300, FPDF_GetPageHeight(page.get()));
+ EXPECT_FLOAT_EQ(200.0f, FPDF_GetPageWidthF(page.get()));
+ EXPECT_FLOAT_EQ(300.0f, FPDF_GetPageHeightF(page.get()));
}
TEST_F(FPDFViewEmbedderTest, Page) {
@@ -406,8 +406,8 @@
FPDF_PAGE page = LoadPage(0);
EXPECT_TRUE(page);
- EXPECT_EQ(612.0, FPDF_GetPageWidth(page));
- EXPECT_EQ(792.0, FPDF_GetPageHeight(page));
+ EXPECT_FLOAT_EQ(612.0f, FPDF_GetPageWidthF(page));
+ EXPECT_FLOAT_EQ(792.0f, FPDF_GetPageHeightF(page));
FS_RECTF rect;
EXPECT_TRUE(FPDF_GetPageBoundingBox(page, &rect));
@@ -773,8 +773,8 @@
EXPECT_TRUE(OpenDocument("rectangles.pdf"));
FPDF_PAGE page = LoadPage(0);
ASSERT_TRUE(page);
- const int page_width = static_cast<int>(FPDF_GetPageWidth(page));
- const int page_height = static_cast<int>(FPDF_GetPageHeight(page));
+ const int page_width = static_cast<int>(FPDF_GetPageWidthF(page));
+ const int page_height = static_cast<int>(FPDF_GetPageHeightF(page));
EXPECT_EQ(200, page_width);
EXPECT_EQ(300, page_height);
@@ -912,6 +912,41 @@
UnloadPage(page);
}
+TEST_F(FPDFViewEmbedderTest, FPDF_GetPageSizeByIndexF) {
+ EXPECT_TRUE(OpenDocument("rectangles.pdf"));
+
+ FS_SIZEF size;
+ EXPECT_FALSE(FPDF_GetPageSizeByIndexF(nullptr, 0, &size));
+ EXPECT_FALSE(FPDF_GetPageSizeByIndexF(document(), 0, nullptr));
+
+ // Page -1 doesn't exist.
+ EXPECT_FALSE(FPDF_GetPageSizeByIndexF(document(), -1, &size));
+
+ // Page 1 doesn't exist.
+ EXPECT_FALSE(FPDF_GetPageSizeByIndexF(document(), 1, &size));
+
+ // Page 0 exists.
+ EXPECT_TRUE(FPDF_GetPageSizeByIndexF(document(), 0, &size));
+ EXPECT_FLOAT_EQ(200.0f, size.width);
+ EXPECT_FLOAT_EQ(300.0f, size.height);
+
+ CPDF_Document* pDoc = CPDFDocumentFromFPDFDocument(document());
+#ifdef PDF_ENABLE_XFA
+ // TODO(tsepez): XFA must obtain this size without parsing.
+ EXPECT_EQ(1u, pDoc->GetParsedPageCountForTesting());
+#else // PDF_ENABLE_XFA
+ EXPECT_EQ(0u, pDoc->GetParsedPageCountForTesting());
+#endif // PDF_ENABLE_XFA
+
+ // Double-check against values from when page is actually parsed.
+ FPDF_PAGE page = LoadPage(0);
+ ASSERT_TRUE(page);
+ EXPECT_FLOAT_EQ(size.width, FPDF_GetPageWidthF(page));
+ EXPECT_FLOAT_EQ(size.height, FPDF_GetPageHeightF(page));
+ EXPECT_EQ(1u, pDoc->GetParsedPageCountForTesting());
+ UnloadPage(page);
+}
+
TEST_F(FPDFViewEmbedderTest, FPDF_GetPageSizeByIndex) {
EXPECT_TRUE(OpenDocument("rectangles.pdf"));
diff --git a/public/fpdfview.h b/public/fpdfview.h
index f7b99f4..e3eb65e 100644
--- a/public/fpdfview.h
+++ b/public/fpdfview.h
@@ -157,6 +157,15 @@
// Const Pointer to FS_RECTF structure.
typedef const FS_RECTF* FS_LPCRECTF;
+// Rectangle size. Coordinate system agnostic.
+typedef struct FS_SIZEF_ {
+ float width;
+ float height;
+} * FS_LPSIZEF, FS_SIZEF;
+
+// Const Pointer to FS_SIZEF structure.
+typedef const FS_SIZEF* FS_LPCSIZEF;
+
// Annotation enums.
typedef int FPDF_ANNOTATION_SUBTYPE;
typedef int FPDF_ANNOT_APPEARANCEMODE;
@@ -593,6 +602,16 @@
FPDF_EXPORT FPDF_PAGE FPDF_CALLCONV FPDF_LoadPage(FPDF_DOCUMENT document,
int page_index);
+// Experimental API
+// Function: FPDF_GetPageWidthF
+// Get page width.
+// Parameters:
+// page - Handle to the page. Returned by FPDF_LoadPage().
+// Return value:
+// Page width (excluding non-displayable area) measured in points.
+// One point is 1/72 inch (around 0.3528 mm).
+FPDF_EXPORT float FPDF_CALLCONV FPDF_GetPageWidthF(FPDF_PAGE page);
+
// Function: FPDF_GetPageWidth
// Get page width.
// Parameters:
@@ -600,8 +619,21 @@
// Return value:
// Page width (excluding non-displayable area) measured in points.
// One point is 1/72 inch (around 0.3528 mm).
+// Note:
+// Prefer FPDF_GetPageWidthF() above. This will be deprecated in the
+// future.
FPDF_EXPORT double FPDF_CALLCONV FPDF_GetPageWidth(FPDF_PAGE page);
+// Experimental API
+// Function: FPDF_GetPageHeightF
+// Get page height.
+// Parameters:
+// page - Handle to the page. Returned by FPDF_LoadPage().
+// Return value:
+// Page height (excluding non-displayable area) measured in points.
+// One point is 1/72 inch (around 0.3528 mm)
+FPDF_EXPORT float FPDF_CALLCONV FPDF_GetPageHeightF(FPDF_PAGE page);
+
// Function: FPDF_GetPageHeight
// Get page height.
// Parameters:
@@ -609,6 +641,9 @@
// Return value:
// Page height (excluding non-displayable area) measured in points.
// One point is 1/72 inch (around 0.3528 mm)
+// Note:
+// Prefer FPDF_GetPageHeightF() above. This will be deprecated in the
+// future.
FPDF_EXPORT double FPDF_CALLCONV FPDF_GetPageHeight(FPDF_PAGE page);
// Experimental API.
@@ -624,6 +659,21 @@
FPDF_EXPORT FPDF_BOOL FPDF_CALLCONV FPDF_GetPageBoundingBox(FPDF_PAGE page,
FS_RECTF* rect);
+// Experimental API.
+// Function: FPDF_GetPageSizeByIndexF
+// Get the size of the page at the given index.
+// Parameters:
+// document - Handle to document. Returned by FPDF_LoadDocument().
+// page_index - Page index, zero for the first page.
+// size - Pointer to a FS_SIZEF to receive the page size.
+// (in points).
+// Return value:
+// Non-zero for success. 0 for error (document or page not found).
+FPDF_EXPORT FPDF_BOOL FPDF_CALLCONV
+FPDF_GetPageSizeByIndexF(FPDF_DOCUMENT document,
+ int page_index,
+ FS_SIZEF* size);
+
// Function: FPDF_GetPageSizeByIndex
// Get the size of the page at the given index.
// Parameters:
@@ -635,6 +685,9 @@
// (in points).
// Return value:
// Non-zero for success. 0 for error (document or page not found).
+// Note:
+// Prefer FPDF_GetPageSizeByIndexF() above. This will be deprecated in
+// the future.
FPDF_EXPORT int FPDF_CALLCONV FPDF_GetPageSizeByIndex(FPDF_DOCUMENT document,
int page_index,
double* width,
diff --git a/samples/pdfium_test.cc b/samples/pdfium_test.cc
index 3eb62ca..eb7db5b 100644
--- a/samples/pdfium_test.cc
+++ b/samples/pdfium_test.cc
@@ -694,8 +694,8 @@
if (!options.scale_factor_as_string.empty())
std::stringstream(options.scale_factor_as_string) >> scale;
- auto width = static_cast<int>(FPDF_GetPageWidth(page) * scale);
- auto height = static_cast<int>(FPDF_GetPageHeight(page) * scale);
+ auto width = static_cast<int>(FPDF_GetPageWidthF(page) * scale);
+ auto height = static_cast<int>(FPDF_GetPageHeightF(page) * scale);
int alpha = FPDFPage_HasTransparency(page) ? 1 : 0;
ScopedFPDFBitmap bitmap(FPDFBitmap_Create(width, height, alpha));
diff --git a/samples/pdfium_test_write_helper.cc b/samples/pdfium_test_write_helper.cc
index 7c1f782..356bb08 100644
--- a/samples/pdfium_test_write_helper.cc
+++ b/samples/pdfium_test_write_helper.cc
@@ -466,8 +466,8 @@
HDC dc = CreateEnhMetaFileA(nullptr, filename, nullptr, nullptr);
- int width = static_cast<int>(FPDF_GetPageWidth(page));
- int height = static_cast<int>(FPDF_GetPageHeight(page));
+ int width = static_cast<int>(FPDF_GetPageWidthF(page));
+ int height = static_cast<int>(FPDF_GetPageHeightF(page));
HRGN rgn = CreateRectRgn(0, 0, width, height);
SelectClipRgn(dc, rgn);
DeleteObject(rgn);
@@ -491,8 +491,8 @@
HDC dc = CreateEnhMetaFileA(nullptr, nullptr, nullptr, nullptr);
- int width = static_cast<int>(FPDF_GetPageWidth(page));
- int height = static_cast<int>(FPDF_GetPageHeight(page));
+ int width = static_cast<int>(FPDF_GetPageWidthF(page));
+ int height = static_cast<int>(FPDF_GetPageHeightF(page));
FPDF_RenderPage(dc, page, 0, 0, width, height, 0, FPDF_ANNOT | FPDF_PRINTING);
HENHMETAFILE emf = CloseEnhMetaFile(dc);
diff --git a/testing/embedder_test.cpp b/testing/embedder_test.cpp
index c999732..265b33f 100644
--- a/testing/embedder_test.cpp
+++ b/testing/embedder_test.cpp
@@ -379,8 +379,8 @@
ScopedFPDFBitmap EmbedderTest::RenderPageWithFlags(FPDF_PAGE page,
FPDF_FORMHANDLE handle,
int flags) {
- int width = static_cast<int>(FPDF_GetPageWidth(page));
- int height = static_cast<int>(FPDF_GetPageHeight(page));
+ int width = static_cast<int>(FPDF_GetPageWidthF(page));
+ int height = static_cast<int>(FPDF_GetPageHeightF(page));
int alpha = FPDFPage_HasTransparency(page) ? 1 : 0;
ScopedFPDFBitmap bitmap(FPDFBitmap_Create(width, height, alpha));
FPDF_DWORD fill_color = alpha ? 0x00000000 : 0xFFFFFFFF;
@@ -401,8 +401,8 @@
int flags) {
HDC dc = CreateEnhMetaFileA(nullptr, nullptr, nullptr, nullptr);
- int width = static_cast<int>(FPDF_GetPageWidth(page));
- int height = static_cast<int>(FPDF_GetPageHeight(page));
+ int width = static_cast<int>(FPDF_GetPageWidthF(page));
+ int height = static_cast<int>(FPDF_GetPageHeightF(page));
HRGN rgn = CreateRectRgn(0, 0, width, height);
SelectClipRgn(dc, rgn);
DeleteObject(rgn);
diff --git a/testing/fuzzers/pdfium_fuzzer_helper.cc b/testing/fuzzers/pdfium_fuzzer_helper.cc
index 27e0292..266666d 100644
--- a/testing/fuzzers/pdfium_fuzzer_helper.cc
+++ b/testing/fuzzers/pdfium_fuzzer_helper.cc
@@ -219,8 +219,8 @@
FORM_DoPageAAction(page.get(), form, FPDFPAGE_AACTION_OPEN);
const double scale = 1.0;
- int width = static_cast<int>(FPDF_GetPageWidth(page.get()) * scale);
- int height = static_cast<int>(FPDF_GetPageHeight(page.get()) * scale);
+ int width = static_cast<int>(FPDF_GetPageWidthF(page.get()) * scale);
+ int height = static_cast<int>(FPDF_GetPageHeightF(page.get()) * scale);
ScopedFPDFBitmap bitmap(FPDFBitmap_Create(width, height, 0));
if (bitmap) {
FPDFBitmap_FillRect(bitmap.get(), 0, 0, width, height, 0xFFFFFFFF);