csPDFiumDest csPDFiumDocument::createDest(const void *_dest, const void *_action) const { FPDF_DEST dest = (FPDF_DEST)_dest; const FPDF_ACTION action = (const FPDF_ACTION)_action; if( action != NULL ) { if( FPDFAction_GetType(action) == PDFACTION_GOTO && dest == NULL ) { dest = FPDFAction_GetDest(impl->document, action); } else if( FPDFAction_GetType(action) == PDFACTION_REMOTEGOTO ) { const int size = FPDFAction_GetFilePath(action, NULL, 0); if( size < 1 ) { return csPDFiumDest(); } QByteArray destFilename(size, '\0'); FPDFAction_GetFilePath(action, destFilename.data(), destFilename.size()); return csPDFiumDest(impl->fileName, QString::fromUtf8(destFilename)); } } if( dest == NULL ) { return csPDFiumDest(); } return csPDFiumDest(FPDFDest_GetPageIndex(impl->document, dest), FPDFDest_GetZoomMode(dest) == FPDF_ZOOM_XYZ ? QPointF(FPDFDest_GetZoomParam(dest, 0), FPDFDest_GetZoomParam(dest, 1)) : QPointF()); }
TEST_F(FPDFDocEmbedderTest, ActionURI) { EXPECT_TRUE(OpenDocument("uri_action.pdf")); FPDF_PAGE page = LoadPage(0); ASSERT_TRUE(page); // The target action is nearly the size of the whole page. FPDF_LINK link = FPDFLink_GetLinkAtPoint(page, 100, 100); ASSERT_TRUE(link); FPDF_ACTION action = FPDFLink_GetAction(link); ASSERT_TRUE(action); EXPECT_EQ(static_cast<unsigned long>(PDFACTION_URI), FPDFAction_GetType(action)); const char kExpectedResult[] = "https://example.com/page.html"; const unsigned long kExpectedLength = sizeof(kExpectedResult); unsigned long bufsize = FPDFAction_GetURIPath(document(), action, nullptr, 0); ASSERT_EQ(kExpectedLength, bufsize); char buf[1024]; EXPECT_EQ(bufsize, FPDFAction_GetURIPath(document(), action, buf, bufsize)); EXPECT_STREQ(kExpectedResult, buf); // Other public methods are not appropriate for URI actions EXPECT_EQ(nullptr, FPDFAction_GetDest(document(), action)); EXPECT_EQ(0u, FPDFAction_GetFilePath(action, buf, sizeof(buf))); UnloadPage(page); }
TEST_F(FPDFDocEmbedderTest, ActionBadArguments) { EXPECT_TRUE(OpenDocument("launch_action.pdf")); EXPECT_EQ(static_cast<unsigned long>(PDFACTION_UNSUPPORTED), FPDFAction_GetType(nullptr)); EXPECT_EQ(nullptr, FPDFAction_GetDest(nullptr, nullptr)); EXPECT_EQ(nullptr, FPDFAction_GetDest(document(), nullptr)); EXPECT_EQ(0u, FPDFAction_GetFilePath(nullptr, nullptr, 0)); EXPECT_EQ(0u, FPDFAction_GetURIPath(nullptr, nullptr, nullptr, 0)); EXPECT_EQ(0u, FPDFAction_GetURIPath(document(), nullptr, nullptr, 0)); }
FPDF_EXPORT unsigned long FPDF_CALLCONV FPDFAction_GetFilePath(FPDF_ACTION pDict, void* buffer, unsigned long buflen) { unsigned long type = FPDFAction_GetType(pDict); if (type != PDFACTION_REMOTEGOTO && type != PDFACTION_LAUNCH) return 0; CPDF_Action action(CPDFDictionaryFromFPDFAction(pDict)); ByteString path = action.GetFilePath().ToUTF8(); unsigned long len = path.GetLength() + 1; if (buffer && len <= buflen) memcpy(buffer, path.c_str(), len); return len; }
FPDF_EXPORT FPDF_DEST FPDF_CALLCONV FPDFAction_GetDest(FPDF_DOCUMENT document, FPDF_ACTION pDict) { CPDF_Document* pDoc = CPDFDocumentFromFPDFDocument(document); if (!pDoc) return nullptr; unsigned long type = FPDFAction_GetType(pDict); if (type != PDFACTION_GOTO && type != PDFACTION_REMOTEGOTO) return nullptr; CPDF_Action action(CPDFDictionaryFromFPDFAction(pDict)); return FPDFDestFromCPDFArray(action.GetDest(pDoc).GetArray()); }
DLLEXPORT unsigned long STDCALL FPDFAction_GetFilePath(FPDF_ACTION pDict, void* buffer, unsigned long buflen) { unsigned long type = FPDFAction_GetType(pDict); if (type != PDFACTION_REMOTEGOTO && type != PDFACTION_LAUNCH) return 0; CPDF_Action action(ToDictionary(static_cast<CPDF_Object*>(pDict))); CFX_ByteString path = action.GetFilePath().UTF8Encode(); unsigned long len = path.GetLength() + 1; if (buffer && buflen >= len) FXSYS_memcpy(buffer, path.c_str(), len); return len; }
FPDF_EXPORT unsigned long FPDF_CALLCONV FPDFAction_GetURIPath(FPDF_DOCUMENT document, FPDF_ACTION pDict, void* buffer, unsigned long buflen) { CPDF_Document* pDoc = CPDFDocumentFromFPDFDocument(document); if (!pDoc) return 0; unsigned long type = FPDFAction_GetType(pDict); if (type != PDFACTION_URI) return 0; CPDF_Action action(CPDFDictionaryFromFPDFAction(pDict)); ByteString path = action.GetURI(pDoc); unsigned long len = path.GetLength() + 1; if (buffer && len <= buflen) memcpy(buffer, path.c_str(), len); return len; }
TEST_F(FPDFDocEmbedderTest, ActionNonesuch) { EXPECT_TRUE(OpenDocument("nonesuch_action.pdf")); FPDF_PAGE page = LoadPage(0); ASSERT_TRUE(page); // The target action is nearly the size of the whole page. FPDF_LINK link = FPDFLink_GetLinkAtPoint(page, 100, 100); ASSERT_TRUE(link); FPDF_ACTION action = FPDFLink_GetAction(link); ASSERT_TRUE(action); EXPECT_EQ(static_cast<unsigned long>(PDFACTION_UNSUPPORTED), FPDFAction_GetType(action)); // No public methods are appropriate for unsupported actions. char buf[1024]; EXPECT_FALSE(FPDFAction_GetDest(document(), action)); EXPECT_EQ(0u, FPDFAction_GetFilePath(action, buf, sizeof(buf))); EXPECT_EQ(0u, FPDFAction_GetURIPath(document(), action, buf, sizeof(buf))); UnloadPage(page); }