aboutsummaryrefslogtreecommitdiffstats
path: root/libqpdf/QPDFFileSpecObjectHelper.cc
diff options
context:
space:
mode:
authorJay Berkenbilt <ejb@ql.org>2021-02-09 00:07:21 +0100
committerJay Berkenbilt <ejb@ql.org>2021-02-10 12:57:37 +0100
commitad34b9c278608dfdcfdbe7402acb3a6dd04c3d0e (patch)
tree5ba96898c85ae2106b44abe5120c49e4cb7b81e5 /libqpdf/QPDFFileSpecObjectHelper.cc
parentbf0e6eb3022bf2fde5623a0a3d151c07f5e82945 (diff)
downloadqpdf-ad34b9c278608dfdcfdbe7402acb3a6dd04c3d0e.tar.zst
Implement helpers for file attachments
Diffstat (limited to 'libqpdf/QPDFFileSpecObjectHelper.cc')
-rw-r--r--libqpdf/QPDFFileSpecObjectHelper.cc157
1 files changed, 157 insertions, 0 deletions
diff --git a/libqpdf/QPDFFileSpecObjectHelper.cc b/libqpdf/QPDFFileSpecObjectHelper.cc
new file mode 100644
index 00000000..ad422d2b
--- /dev/null
+++ b/libqpdf/QPDFFileSpecObjectHelper.cc
@@ -0,0 +1,157 @@
+#include <qpdf/QPDFFileSpecObjectHelper.hh>
+#include <qpdf/QTC.hh>
+#include <qpdf/QPDF.hh>
+#include <qpdf/QUtil.hh>
+
+#include <vector>
+#include <string>
+
+QPDFFileSpecObjectHelper::QPDFFileSpecObjectHelper(
+ QPDFObjectHandle oh) :
+ QPDFObjectHelper(oh)
+{
+ if (! oh.isDictionary())
+ {
+ oh.warnIfPossible("Embedded file object is not a dictionary");
+ return;
+ }
+ auto type = oh.getKey("/Type");
+ if (! (type.isName() && (type.getName() == "/Filespec")))
+ {
+ oh.warnIfPossible("Embedded file object's type is not /Filespec");
+ }
+}
+
+QPDFFileSpecObjectHelper::Members::Members()
+{
+}
+
+static std::vector<std::string> name_keys = {
+ "/UF", "/F", "/Unix", "/DOS", "/Mac"};
+
+std::string
+QPDFFileSpecObjectHelper::getDescription()
+{
+ std::string result;
+ auto desc = this->oh.getKey("/Desc");
+ if (desc.isString())
+ {
+ result = desc.getUTF8Value();
+ }
+ return result;
+}
+
+std::string
+QPDFFileSpecObjectHelper::getFilename()
+{
+ for (auto const& i: name_keys)
+ {
+ auto k = this->oh.getKey(i);
+ if (k.isString())
+ {
+ return k.getUTF8Value();
+ }
+ }
+ return "";
+}
+
+std::map<std::string, std::string>
+QPDFFileSpecObjectHelper::getFilenames()
+{
+ std::map<std::string, std::string> result;
+ for (auto const& i: name_keys)
+ {
+ auto k = this->oh.getKey(i);
+ if (k.isString())
+ {
+ result[i] = k.getUTF8Value();
+ }
+ }
+ return result;
+}
+
+QPDFObjectHandle
+QPDFFileSpecObjectHelper::getEmbeddedFileStream(std::string const& key)
+{
+ auto ef = this->oh.getKey("/EF");
+ if (! ef.isDictionary())
+ {
+ return QPDFObjectHandle::newNull();
+ }
+ if (! key.empty())
+ {
+ return ef.getKey(key);
+ }
+ for (auto const& i: name_keys)
+ {
+ auto k = ef.getKey(i);
+ if (k.isStream())
+ {
+ return k;
+ }
+ }
+ return QPDFObjectHandle::newNull();
+}
+
+QPDFObjectHandle
+QPDFFileSpecObjectHelper::getEmbeddedFileStreams()
+{
+ return this->oh.getKey("/EF");
+}
+
+QPDFFileSpecObjectHelper
+QPDFFileSpecObjectHelper::createFileSpec(
+ QPDF& qpdf,
+ std::string const& filename,
+ std::string const& fullpath)
+{
+ return createFileSpec(
+ qpdf, filename,
+ QPDFEFStreamObjectHelper::createEFStream(
+ qpdf,
+ QUtil::file_provider(fullpath)));
+}
+
+QPDFFileSpecObjectHelper
+QPDFFileSpecObjectHelper::createFileSpec(
+ QPDF& qpdf,
+ std::string const& filename,
+ QPDFEFStreamObjectHelper efsoh)
+{
+ auto oh = qpdf.makeIndirectObject(QPDFObjectHandle::newDictionary());
+ oh.replaceKey("/Type", QPDFObjectHandle::newName("/Filespec"));
+ QPDFFileSpecObjectHelper result(oh);
+ result.setFilename(filename);
+ auto ef = QPDFObjectHandle::newDictionary();
+ ef.replaceKey("/F", efsoh.getObjectHandle());
+ ef.replaceKey("/UF", efsoh.getObjectHandle());
+ oh.replaceKey("/EF", ef);
+ return result;
+}
+
+QPDFFileSpecObjectHelper&
+QPDFFileSpecObjectHelper::setDescription(std::string const& desc)
+{
+ this->oh.replaceKey("/Desc", QPDFObjectHandle::newUnicodeString(desc));
+ return *this;
+}
+
+QPDFFileSpecObjectHelper&
+QPDFFileSpecObjectHelper::setFilename(
+ std::string const& unicode_name,
+ std::string const& compat_name)
+{
+ auto uf = QPDFObjectHandle::newUnicodeString(unicode_name);
+ this->oh.replaceKey("/UF", uf);
+ if (compat_name.empty())
+ {
+ QTC::TC("qpdf", "QPDFFileSpecObjectHelper empty compat_name");
+ this->oh.replaceKey("/F", uf);
+ }
+ else
+ {
+ QTC::TC("qpdf", "QPDFFileSpecObjectHelper non-empty compat_name");
+ this->oh.replaceKey("/F", QPDFObjectHandle::newString(compat_name));
+ }
+ return *this;
+}