2
1
mirror of https://github.com/qpdf/qpdf.git synced 2025-02-02 03:48:24 +00:00

Add new QPDFObjectHandle::getValueAs... accessors

This commit is contained in:
m-holger 2022-02-05 14:46:25 +00:00 committed by Jay Berkenbilt
parent cfaa2de804
commit e58b1174c7
4 changed files with 257 additions and 3 deletions

View File

@ -678,6 +678,8 @@ class QPDFObjectHandle
// Methods for bool objects
QPDF_DLL
bool getBoolValue();
QPDF_DLL
bool getValueAsBool(bool&);
// Methods for integer objects. Note: if an integer value is too
// big (too far away from zero in either direction) to fit in the
@ -688,29 +690,46 @@ class QPDFObjectHandle
QPDF_DLL
long long getIntValue();
QPDF_DLL
bool getValueAsInt(long long&);
QPDF_DLL
int getIntValueAsInt();
QPDF_DLL
bool getValueAsInt(int&);
QPDF_DLL
unsigned long long getUIntValue();
QPDF_DLL
bool getValueAsUInt(unsigned long long&);
QPDF_DLL
unsigned int getUIntValueAsUInt();
QPDF_DLL
bool getValueAsUInt(unsigned int&);
// Methods for real objects
QPDF_DLL
std::string getRealValue();
QPDF_DLL
bool getValueAsReal(std::string&);
// Methods that work for both integer and real objects
QPDF_DLL
bool isNumber();
QPDF_DLL
double getNumericValue();
QPDF_DLL
bool getValueAsNumber(double&);
// Methods for name objects; see also name and array objects
QPDF_DLL
std::string getName();
QPDF_DLL
bool getValueAsName(std::string&);
// Methods for string objects
QPDF_DLL
std::string getStringValue();
QPDF_DLL
bool getValueAsString(std::string&);
// If a string starts with the UTF-16 marker, it is converted from
// UTF-16 to UTF-8. Otherwise, it is treated as a string encoded
// with PDF Doc Encoding. PDF Doc Encoding is identical to
@ -720,12 +739,18 @@ class QPDFObjectHandle
// unmapped.
QPDF_DLL
std::string getUTF8Value();
QPDF_DLL
bool getValueAsUTF8(std::string&);
// Methods for content stream objects
QPDF_DLL
std::string getOperatorValue();
QPDF_DLL
bool getValueAsOperator(std::string&);
QPDF_DLL
std::string getInlineImageValue();
QPDF_DLL
bool getValueAsInlineImage(std::string&);
// Methods for array objects; see also name and array objects.

View File

@ -391,6 +391,17 @@ QPDFObjectHandle::getNumericValue()
return result;
}
bool
QPDFObjectHandle::getValueAsNumber(double& value)
{
if (! isNumber())
{
return false;
}
value = getNumericValue();
return true;
}
bool
QPDFObjectHandle::isName()
{
@ -536,6 +547,17 @@ QPDFObjectHandle::getBoolValue()
}
}
bool
QPDFObjectHandle::getValueAsBool(bool& value)
{
if (! isBool())
{
return false;
}
value = dynamic_cast<QPDF_Bool*>(obj.get())->getVal();
return true;
}
// Integer accessors
long long
@ -553,6 +575,17 @@ QPDFObjectHandle::getIntValue()
}
}
bool
QPDFObjectHandle::getValueAsInt(long long& value)
{
if (! isInteger())
{
return false;
}
value = dynamic_cast<QPDF_Integer*>(obj.get())->getVal();
return true;
}
int
QPDFObjectHandle::getIntValueAsInt()
{
@ -581,6 +614,17 @@ QPDFObjectHandle::getIntValueAsInt()
return result;
}
bool
QPDFObjectHandle::getValueAsInt(int& value)
{
if (! isInteger())
{
return false;
}
value = getIntValueAsInt();
return true;
}
unsigned long long
QPDFObjectHandle::getUIntValue()
{
@ -600,6 +644,17 @@ QPDFObjectHandle::getUIntValue()
return result;
}
bool
QPDFObjectHandle::getValueAsUInt(unsigned long long& value)
{
if (! isInteger())
{
return false;
}
value = getUIntValue();
return true;
}
unsigned int
QPDFObjectHandle::getUIntValueAsUInt()
{
@ -629,6 +684,17 @@ QPDFObjectHandle::getUIntValueAsUInt()
return result;
}
bool
QPDFObjectHandle::getValueAsUInt(unsigned int& value)
{
if (! isInteger())
{
return false;
}
value = getUIntValueAsUInt();
return true;
}
// Real accessors
std::string
@ -646,6 +712,17 @@ QPDFObjectHandle::getRealValue()
}
}
bool
QPDFObjectHandle::getValueAsReal(std::string& value)
{
if (! isReal())
{
return false;
}
value = dynamic_cast<QPDF_Real*>(obj.get())->getVal();
return true;
}
// Name accessors
std::string
@ -663,6 +740,17 @@ QPDFObjectHandle::getName()
}
}
bool
QPDFObjectHandle::getValueAsName(std::string& value)
{
if (! isName())
{
return false;
}
value = dynamic_cast<QPDF_Name*>(obj.get())->getName();
return true;
}
// String accessors
std::string
@ -680,6 +768,17 @@ QPDFObjectHandle::getStringValue()
}
}
bool
QPDFObjectHandle::getValueAsString(std::string& value)
{
if (! isString())
{
return false;
}
value = dynamic_cast<QPDF_String*>(obj.get())->getVal();
return true;
}
std::string
QPDFObjectHandle::getUTF8Value()
{
@ -695,6 +794,17 @@ QPDFObjectHandle::getUTF8Value()
}
}
bool
QPDFObjectHandle::getValueAsUTF8(std::string& value)
{
if (! isString())
{
return false;
}
value = dynamic_cast<QPDF_String*>(obj.get())->getUTF8Val();
return true;
}
// Operator and Inline Image accessors
std::string
@ -712,6 +822,17 @@ QPDFObjectHandle::getOperatorValue()
}
}
bool
QPDFObjectHandle::getValueAsOperator(std::string& value)
{
if (! isOperator())
{
return false;
}
value = dynamic_cast<QPDF_Operator*>(obj.get())->getVal();
return true;
}
std::string
QPDFObjectHandle::getInlineImageValue()
{
@ -727,6 +848,17 @@ QPDFObjectHandle::getInlineImageValue()
}
}
bool
QPDFObjectHandle::getValueAsInlineImage(std::string& value)
{
if (! isInlineImage())
{
return false;
}
value = dynamic_cast<QPDF_InlineImage*>(obj.get())->getVal();
return true;
}
// Array accessors
QPDFObjectHandle::QPDFArrayItems

View File

@ -3285,7 +3285,7 @@ my @badfiles = ("not a PDF file", # 1
"startxref to space then eof", # 38
);
$n_tests += @badfiles + 7;
$n_tests += @badfiles + 8;
# Test 6 contains errors in the free table consistency, but we no
# longer have any consistency check for this since it is not important
@ -3341,6 +3341,10 @@ $td->runtest("integer type checks",
{$td->COMMAND => "test_driver 62 minimal.pdf"},
{$td->STRING => "test 62 done\n", $td->EXIT_STATUS => 0},
$td->NORMALIZE_NEWLINES);
$td->runtest("getValueAs... accessor checks",
{$td->COMMAND => "test_driver 85 -"},
{$td->STRING => "test 85 done\n", $td->EXIT_STATUS => 0},
$td->NORMALIZE_NEWLINES);
show_ntests();
# ----------

View File

@ -3220,6 +3220,99 @@ static void test_84(QPDF& pdf, char const* arg2)
}
}
static void test_85(QPDF& pdf, char const* arg2)
{
// Test QPDFObjectHandle::getValueAs... accessors
auto oh_b = QPDFObjectHandle::newBool(false);
auto oh_i = QPDFObjectHandle::newInteger(1);
auto oh_i_maxplus =
QPDFObjectHandle::newInteger(QIntC::to_longlong(INT_MAX) + 1LL);
auto oh_i_umaxplus =
QPDFObjectHandle::newInteger(QIntC::to_longlong(UINT_MAX) + 1LL);
auto oh_i_minminus =
QPDFObjectHandle::newInteger(QIntC::to_longlong(INT_MIN) - 1LL);
auto oh_i_neg = QPDFObjectHandle::newInteger(-1);
auto oh_r = QPDFObjectHandle::newReal("42.0");
auto oh_n = QPDFObjectHandle::newName("/Test");
auto oh_s = QPDFObjectHandle::newString("/Test");
auto oh_o = QPDFObjectHandle::newOperator("/Test");
auto oh_ii = QPDFObjectHandle::newInlineImage("/Test");
bool b = true;
assert(oh_b.getValueAsBool(b));
assert(! b);
assert(! oh_i.getValueAsBool(b));
assert(! b);
long long li = 0LL;
assert(oh_i.getValueAsInt(li));
assert(li == 1LL);
assert(! oh_b.getValueAsInt(li));
assert(li == 1LL);
int i = 0;
assert(oh_i.getValueAsInt(i));
assert(i == 1);
assert(! oh_b.getValueAsInt(i));
assert(i == 1);
assert(oh_i_maxplus.getValueAsInt(i));
assert(i == INT_MAX);
assert(oh_i_minminus.getValueAsInt(i));
assert(i == INT_MIN);
unsigned long long uli = 0U;
assert(oh_i.getValueAsUInt(uli));
assert(uli == 1u);
assert(! oh_b.getValueAsUInt(uli));
assert(uli == 1u);
assert(oh_i_neg.getValueAsUInt(uli));
assert(uli == 0u);
unsigned int ui = 0U;
assert(oh_i.getValueAsUInt(ui));
assert(ui == 1u);
assert(! oh_b.getValueAsUInt(ui));
assert(ui == 1u);
assert(oh_i_neg.getValueAsUInt(ui));
assert(ui == 0u);
assert(oh_i_umaxplus.getValueAsUInt(ui));
assert(ui == UINT_MAX);
std::string s = "0";
assert(oh_r.getValueAsReal(s));
assert(s == "42.0");
assert(! oh_i.getValueAsReal(s));
assert(s == "42.0");
double num = 0.0;
assert(oh_i.getValueAsNumber(num));
assert(abs(num - 1.0) < 1e-100);
assert(oh_r.getValueAsNumber(num));
assert(abs(num - 42.0) < 1e-100);
assert(! oh_b.getValueAsNumber(num));
assert(abs(num - 42.0) < 1e-100);
s = "";
assert(oh_n.getValueAsName(s));
assert(s == "/Test") ;
assert(! oh_r.getValueAsName(s));
assert(s == "/Test");
s = "";
assert(oh_s.getValueAsUTF8(s));
assert(s == "/Test");
assert(! oh_r.getValueAsUTF8(s));
assert(s == "/Test");
s = "";
assert(oh_s.getValueAsUTF8(s));
assert(s == "/Test");
assert(! oh_r.getValueAsUTF8(s));
assert(s == "/Test");
s = "";
assert(oh_o.getValueAsOperator(s));
assert(s == "/Test");
assert(! oh_r.getValueAsOperator(s));
assert(s == "/Test");
s = "";
assert(oh_ii.getValueAsInlineImage(s));
assert(s == "/Test");
assert(! oh_r.getValueAsInlineImage(s));
assert(s == "/Test");
}
void runtest(int n, char const* filename1, char const* arg2)
{
// Most tests here are crafted to work on specific files. Look at
@ -3286,7 +3379,7 @@ void runtest(int n, char const* filename1, char const* arg2)
pdf.processMemoryFile((std::string(filename1) + ".pdf").c_str(),
p, size);
}
else if ((n == 61) || (n == 81) || (n == 83) || (n == 84))
else if ((n == 61) || (n == 81) || (n == 83) || (n == 84) || (n == 85))
{
// Ignore filename argument entirely
}
@ -3334,7 +3427,7 @@ void runtest(int n, char const* filename1, char const* arg2)
{72, test_72}, {73, test_73}, {74, test_74}, {75, test_75},
{76, test_76}, {77, test_77}, {78, test_78}, {79, test_79},
{80, test_80}, {81, test_81}, {82, test_82}, {83, test_83},
{84, test_84},
{84, test_84}, {85, test_85},
};
auto fn = test_functions.find(n);