filter/source/pdf/impdialog.cxx | 42 ++++++-- filter/source/pdf/impdialog.hxx | 1 vcl/source/gdi/pdfwriter_impl.cxx | 3 vcl/source/pdf/PDFiumLibrary.cxx | 181 +++++++++++--------------------------- 4 files changed, 89 insertions(+), 138 deletions(-)
New commits: commit a1bc9e9d6663b4d0828dd0057968738268bd4181 Author: Tomaž Vajngerl <tomaz.vajng...@collabora.co.uk> AuthorDate: Tue Dec 17 11:58:59 2024 +0900 Commit: Tomaž Vajngerl <qui...@gmail.com> CommitDate: Thu Dec 26 07:52:16 2024 +0100 pdfium: remove duplication of converting a unicode string This adds a universal getUnicodeString function that takes a function call as a parameter, which is only a wrapped PDFium function call that returns a unicode string. The rest of conversion magic to OUString is then done by the function in one place. This reduces a lot of duplication as we had to copy the way how to convert the unicode string to OUString to every method. Change-Id: Id951e2dd0c8b98837ca096cd5f800b8df0449fa0 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/178628 Reviewed-by: Miklos Vajna <vmik...@collabora.com> Tested-by: Jenkins CollaboraOffice <jenkinscollaboraoff...@gmail.com> Reviewed-on: https://gerrit.libreoffice.org/c/core/+/178774 Tested-by: Jenkins Reviewed-by: Tomaž Vajngerl <qui...@gmail.com> diff --git a/vcl/source/pdf/PDFiumLibrary.cxx b/vcl/source/pdf/PDFiumLibrary.cxx index c665ce006d9e..a1552e9ca1bf 100644 --- a/vcl/source/pdf/PDFiumLibrary.cxx +++ b/vcl/source/pdf/PDFiumLibrary.cxx @@ -31,6 +31,7 @@ #include <vcl/BitmapWriteAccess.hxx> #include <vcl/bitmapex.hxx> #include <vcl/dibtools.hxx> +#include <functional> using namespace com::sun::star; @@ -220,6 +221,35 @@ int CompatibleWriterCallback(FPDF_FILEWRITE* pFileWrite, const void* pData, unsi pImpl->m_rStream.WriteBytes(pData, nSize); return 1; } + +OUString getUnicodeString(std::function<int(FPDF_WCHAR*, unsigned long)> aPDFiumFunctionCall) +{ + OUString sReturnText; + + int nBytes = aPDFiumFunctionCall(nullptr, 0); + if (nBytes == 0) + return sReturnText; + assert(nBytes % 2 == 0); + nBytes /= 2; + + std::vector<sal_Unicode> pText(nBytes, 0); + + int nActualBytes = aPDFiumFunctionCall(reinterpret_cast<FPDF_WCHAR*>(pText.data()), nBytes * 2); + assert(nActualBytes % 2 == 0); + nActualBytes /= 2; + if (nActualBytes > 1) + { +#ifdef OSL_BIGENDIAN + for (int i = 0; i != nActualBytes; ++i) + { + pText[i] = OSL_SWAPWORD(pText[i]); + } +#endif + sReturnText = OUString(pText.data()); + } + + return sReturnText; +} } namespace vcl::pdf @@ -910,32 +940,10 @@ PDFiumPageObjectImpl::PDFiumPageObjectImpl(FPDF_PAGEOBJECT pPageObject) OUString PDFiumPageObjectImpl::getText(std::unique_ptr<PDFiumTextPage> const& rTextPage) { - OUString sReturnText; - auto pTextPage = static_cast<PDFiumTextPageImpl*>(rTextPage.get()); - int nBytes = FPDFTextObj_GetText(mpPageObject, pTextPage->getPointer(), nullptr, 0); - assert(nBytes % 2 == 0); - nBytes /= 2; - - std::unique_ptr<sal_Unicode[]> pText(new sal_Unicode[nBytes]); - - int nActualBytes = FPDFTextObj_GetText(mpPageObject, pTextPage->getPointer(), - reinterpret_cast<FPDF_WCHAR*>(pText.get()), nBytes * 2); - assert(nActualBytes % 2 == 0); - nActualBytes /= 2; - if (nActualBytes > 1) - { -#if defined OSL_BIGENDIAN - // The data returned by FPDFTextObj_GetText is documented to always be UTF-16LE: - for (int i = 0; i != nActualBytes; ++i) - { - pText[i] = OSL_SWAPWORD(pText[i]); - } -#endif - sReturnText = OUString(pText.get()); - } - - return sReturnText; + return getUnicodeString([this, pTextPage](FPDF_WCHAR* buffer, unsigned long length) { + return FPDFTextObj_GetText(mpPageObject, pTextPage->getPointer(), buffer, length); + }); } PDFPageObjectType PDFiumPageObjectImpl::getType() @@ -1390,98 +1398,36 @@ Color PDFiumAnnotationImpl::getFontColor(PDFiumDocument* pDoc) OUString PDFiumAnnotationImpl::getFormFieldAlternateName(PDFiumDocument* pDoc) { - auto pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); - OUString aString; - unsigned long nSize = FPDFAnnot_GetFormFieldAlternateName(pDocImpl->getFormHandlePointer(), - mpAnnotation, nullptr, 0); - assert(nSize % 2 == 0); - nSize /= 2; - if (nSize > 1) - { - std::unique_ptr<sal_Unicode[]> pText(new sal_Unicode[nSize]); - unsigned long nStringSize = FPDFAnnot_GetFormFieldAlternateName( - pDocImpl->getFormHandlePointer(), mpAnnotation, - reinterpret_cast<FPDF_WCHAR*>(pText.get()), nSize * 2); - assert(nStringSize % 2 == 0); - nStringSize /= 2; - if (nStringSize > 0) - { -#if defined OSL_BIGENDIAN - for (unsigned long i = 0; i != nStringSize; ++i) - { - pText[i] = OSL_SWAPWORD(pText[i]); - } -#endif - aString = OUString(pText.get()); - } - } - return aString; + auto* pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); + return getUnicodeString([this, pDocImpl](FPDF_WCHAR* buffer, unsigned long length) { + return FPDFAnnot_GetFormFieldAlternateName(pDocImpl->getFormHandlePointer(), mpAnnotation, + buffer, length); + }); } OUString PDFiumAnnotationImpl::getFormFieldValue(PDFiumDocument* pDoc) { - auto pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); - OUString aString; - unsigned long nSize - = FPDFAnnot_GetFormFieldValue(pDocImpl->getFormHandlePointer(), mpAnnotation, nullptr, 0); - assert(nSize % 2 == 0); - nSize /= 2; - if (nSize > 1) - { - std::unique_ptr<sal_Unicode[]> pText(new sal_Unicode[nSize]); - unsigned long nStringSize - = FPDFAnnot_GetFormFieldValue(pDocImpl->getFormHandlePointer(), mpAnnotation, - reinterpret_cast<FPDF_WCHAR*>(pText.get()), nSize * 2); - assert(nStringSize % 2 == 0); - nStringSize /= 2; - if (nStringSize > 0) - { -#if defined OSL_BIGENDIAN - for (unsigned long i = 0; i != nStringSize; ++i) - { - pText[i] = OSL_SWAPWORD(pText[i]); - } -#endif - aString = OUString(pText.get()); - } - } - return aString; + auto* pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); + return getUnicodeString([this, pDocImpl](FPDF_WCHAR* buffer, unsigned long length) { + return FPDFAnnot_GetFormFieldValue(pDocImpl->getFormHandlePointer(), mpAnnotation, buffer, + length); + }); } int PDFiumAnnotationImpl::getOptionCount(PDFiumDocument* pDoc) { - auto pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); + auto* pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); return FPDFAnnot_GetOptionCount(pDocImpl->getFormHandlePointer(), mpAnnotation); } OUString PDFiumAnnotationImpl::getFormAdditionalActionJavaScript(PDFiumDocument* pDoc, PDFAnnotAActionType eEvent) { - auto pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); - OUString aString; - unsigned long nSize = FPDFAnnot_GetFormAdditionalActionJavaScript( - pDocImpl->getFormHandlePointer(), mpAnnotation, static_cast<int>(eEvent), nullptr, 0); - assert(nSize % 2 == 0); - nSize /= 2; - if (nSize > 1) - { - std::unique_ptr<sal_Unicode[]> pText(new sal_Unicode[nSize]); - unsigned long nStringSize = FPDFAnnot_GetFormAdditionalActionJavaScript( - pDocImpl->getFormHandlePointer(), mpAnnotation, static_cast<int>(eEvent), - reinterpret_cast<FPDF_WCHAR*>(pText.get()), nSize * 2); - assert(nStringSize % 2 == 0); - nStringSize /= 2; - if (nStringSize > 0) - { -#if defined OSL_BIGENDIAN - for (unsigned long i = 0; i != nStringSize; ++i) - { - pText[i] = OSL_SWAPWORD(pText[i]); - } -#endif - aString = OUString(pText.get()); - } - } - return aString; + auto* pDocImpl = static_cast<PDFiumDocumentImpl*>(pDoc); + return getUnicodeString([this, pDocImpl, eEvent](FPDF_WCHAR* buffer, unsigned long length) { + return FPDFAnnot_GetFormAdditionalActionJavaScript(pDocImpl->getFormHandlePointer(), + mpAnnotation, static_cast<int>(eEvent), + buffer, length); + }); } namespace @@ -1539,30 +1485,9 @@ PDFObjectType PDFiumAnnotationImpl::getValueType(OString const& rKey) OUString PDFiumAnnotationImpl::getString(OString const& rKey) { - OUString rString; - unsigned long nSize = FPDFAnnot_GetStringValue(mpAnnotation, rKey.getStr(), nullptr, 0); - assert(nSize % 2 == 0); - nSize /= 2; - if (nSize > 1) - { - std::unique_ptr<sal_Unicode[]> pText(new sal_Unicode[nSize]); - unsigned long nStringSize = FPDFAnnot_GetStringValue( - mpAnnotation, rKey.getStr(), reinterpret_cast<FPDF_WCHAR*>(pText.get()), nSize * 2); - assert(nStringSize % 2 == 0); - nStringSize /= 2; - if (nStringSize > 0) - { -#if defined OSL_BIGENDIAN - // The data returned by FPDFAnnot_GetStringValue is documented to always be UTF-16LE: - for (unsigned long i = 0; i != nStringSize; ++i) - { - pText[i] = OSL_SWAPWORD(pText[i]); - } -#endif - rString = OUString(pText.get()); - } - } - return rString; + return getUnicodeString([this, rKey](FPDF_WCHAR* buffer, unsigned long length) { + return FPDFAnnot_GetStringValue(mpAnnotation, rKey.getStr(), buffer, length); + }); } std::vector<std::vector<basegfx::B2DPoint>> PDFiumAnnotationImpl::getInkStrokes() commit 5364b7b663b2be30d802474618dea3db14a2182a Author: Tomaž Vajngerl <tomaz.vajng...@collabora.co.uk> AuthorDate: Thu Dec 12 23:56:29 2024 +0900 Commit: Tomaž Vajngerl <qui...@gmail.com> CommitDate: Thu Dec 26 07:52:05 2024 +0100 tdf#160196 Embedded files are not allowed in PDF/A-1 and PDF/A-2 This disables embedded/attached files in the UI as well as in the export filter for PDF/A-1 and 2. PDF/A-3 is almost identical to PDF/A-2 with the difference that it allows embedded/attached files. Change-Id: If8c3af6ab08ad320cf15618ead9c69fbd490d4f0 Reviewed-on: https://gerrit.libreoffice.org/c/core/+/178413 Tested-by: Jenkins CollaboraOffice <jenkinscollaboraoff...@gmail.com> Reviewed-by: Miklos Vajna <vmik...@collabora.com> Reviewed-on: https://gerrit.libreoffice.org/c/core/+/178769 Reviewed-by: Tomaž Vajngerl <qui...@gmail.com> Tested-by: Jenkins diff --git a/filter/source/pdf/impdialog.cxx b/filter/source/pdf/impdialog.cxx index 03250388c5d6..fa1d634d6192 100644 --- a/filter/source/pdf/impdialog.cxx +++ b/filter/source/pdf/impdialog.cxx @@ -535,6 +535,13 @@ bool ImpPDFTabGeneralPage::IsPdfaSelected() const aVersion == u"4"_ustr; } +bool ImpPDFTabGeneralPage::IsPDFAVersionSelected(sal_Int32 nInputVersion) const +{ + OUString aVersion = mxRbPDFVersion->get_active_id(); + sal_Int32 nSelectedVersion = aVersion.toInt32(); + return nSelectedVersion == nInputVersion; +} + void ImpPDFTabGeneralPage::SetFilterConfigItem(ImpPDFTabDialog* pParent) { mpParent = pParent; @@ -626,6 +633,12 @@ void ImpPDFTabGeneralPage::SetFilterConfigItem(ImpPDFTabDialog* pParent) mbUseTaggedPDFUserSelection = pParent->mbUseTaggedPDFUserSelection; mxCbExportBookmarks->set_active(pParent->mbExportBookmarksUserSelection); + + mxCbAddStream->show(); + mxCbAddStream->set_active(pParent->mbAddStream); + mxCbAddStream->connect_toggled(LINK(this, ImpPDFTabGeneralPage, ToggleAddStreamHdl)); + ToggleAddStreamHdl(*mxCbAddStream); // init addstream dependencies + thePDFVersionChanged(); mxCbExportFormFields->set_active(pParent->mbExportFormFields); @@ -718,13 +731,6 @@ void ImpPDFTabGeneralPage::SetFilterConfigItem(ImpPDFTabDialog* pParent) mxCbExportPlaceholders->set_active(pParent->mbIsExportPlaceholders); mxCbExportPlaceholders->set_sensitive( mbIsWriter && !pParent->maConfigItem.IsReadOnly(u"ExportPlaceholders"_ustr)); - - mxCbAddStream->show(); - mxCbAddStream->set_active(pParent->mbAddStream); - mxCbAddStream->set_sensitive(!pParent->maConfigItem.IsReadOnly(u"IsAddStream"_ustr)); - - mxCbAddStream->connect_toggled(LINK(this, ImpPDFTabGeneralPage, ToggleAddStreamHdl)); - ToggleAddStreamHdl(*mxCbAddStream); // init addstream dependencies } void ImpPDFTabGeneralPage::GetFilterConfigItem( ImpPDFTabDialog* pParent ) @@ -940,9 +946,6 @@ void ImpPDFTabGeneralPage::thePDFVersionChanged() if (pSecPage) pSecPage->ImplPDFASecurityControl(); - mxCbTaggedPDF->set_sensitive( - !bIsPDFA && !bIsPDFUA && !IsReadOnlyProperty(u"UseTaggedPDF"_ustr)); - mxRbPDFVersion->set_sensitive(!IsReadOnlyProperty(u"SelectPdfVersion"_ustr)); if (bIsPDFA || bIsPDFUA) @@ -950,6 +953,7 @@ void ImpPDFTabGeneralPage::thePDFVersionChanged() // store the users selection of subordinate controls and set required PDF/A values mbUseTaggedPDFUserSelection = mxCbTaggedPDF->get_active(); mxCbTaggedPDF->set_active(true); + mxCbTaggedPDF->set_sensitive(false); // if a password was set, inform the user that this will not be used if (bIsPDFA && pSecPage && pSecPage->hasPassword()) @@ -965,6 +969,24 @@ void ImpPDFTabGeneralPage::thePDFVersionChanged() { // restore the users values of subordinate controls mxCbTaggedPDF->set_active(mbUseTaggedPDFUserSelection); + mxCbTaggedPDF->set_sensitive(!IsReadOnlyProperty(u"UseTaggedPDF"_ustr)); + } + + if (IsPDFAVersionSelected(1) || IsPDFAVersionSelected(2)) + { + if (mxCbAddStream->get_sensitive()) + { + if (mpParent) + mpParent->mbAddStream = mxCbAddStream->get_active(); + + mxCbAddStream->set_active(false); + mxCbAddStream->set_sensitive(false); + } + } + else if (mpParent && !mxCbAddStream->get_sensitive()) + { + mxCbAddStream->set_active(mpParent->mbAddStream); + mxCbAddStream->set_sensitive(!mpParent->maConfigItem.IsReadOnly(u"IsAddStream"_ustr)); } if (bIsPDFUA) diff --git a/filter/source/pdf/impdialog.hxx b/filter/source/pdf/impdialog.hxx index 1b697b257ece..fba49c8f0301 100644 --- a/filter/source/pdf/impdialog.hxx +++ b/filter/source/pdf/impdialog.hxx @@ -259,6 +259,7 @@ public: void GetFilterConfigItem(ImpPDFTabDialog* paParent); void SetFilterConfigItem(ImpPDFTabDialog* paParent); bool IsPdfaSelected() const; + bool IsPDFAVersionSelected(sal_Int32 nVersion) const; bool IsPdfUaSelected() const { return mxCbPDFUA->get_active(); } }; diff --git a/vcl/source/gdi/pdfwriter_impl.cxx b/vcl/source/gdi/pdfwriter_impl.cxx index 387edb5e2594..6816fca77bd5 100644 --- a/vcl/source/gdi/pdfwriter_impl.cxx +++ b/vcl/source/gdi/pdfwriter_impl.cxx @@ -3510,6 +3510,9 @@ bool PDFWriterImpl::appendDest( sal_Int32 nDestID, OStringBuffer& rBuffer ) void PDFWriterImpl::addDocumentAttachedFile(OUString const& rFileName, OUString const& rMimeType, OUString const& rDescription, std::unique_ptr<PDFOutputStream> rStream) { + if (m_nPDFA_Version == 1 || m_nPDFA_Version == 2) + return; + sal_Int32 nObjectID = addEmbeddedFile(std::move(rStream), rMimeType); auto& rAttachedFile = m_aDocumentAttachedFiles.emplace_back(); rAttachedFile.maFilename = rFileName;