Allow format options for XmpParser::encode (Vladimir Nadvornik), write XMP sidecar files without xpacket.

v0.27.3
Andreas Huggel 18 years ago
parent e4c96433d4
commit 38b1a0fa2c

@ -74,7 +74,7 @@ namespace {
Exiv2::XmpValue::XmpStruct xmpStruct(const XMP_OptionBits& opt);
//! Convert Value::XmpStruct to XMP Toolkit array option bits
XMP_OptionBits xmpOptionBits(Exiv2::XmpValue::XmpStruct xs);
XMP_OptionBits xmpArrayOptionBits(Exiv2::XmpValue::XmpStruct xs);
//! Convert XMP Toolkit array option bits to array TypeId
Exiv2::TypeId arrayValueTypeId(const XMP_OptionBits& opt);
@ -83,7 +83,10 @@ namespace {
Exiv2::XmpValue::XmpArrayType xmpArrayType(const XMP_OptionBits& opt);
//! Convert Value::XmpArrayType to XMP Toolkit array option bits
XMP_OptionBits xmpOptionBits(Exiv2::XmpValue::XmpArrayType xat);
XMP_OptionBits xmpArrayOptionBits(Exiv2::XmpValue::XmpArrayType xat);
//! Convert XmpFormatFlags to XMP Toolkit format option bits
XMP_OptionBits xmpFormatOptionBits(Exiv2::XmpParser::XmpFormatFlags flags);
# ifdef DEBUG
//! Print information about a parsed XMP node
@ -564,7 +567,9 @@ namespace Exiv2 {
#ifdef EXV_HAVE_XMP_TOOLKIT
int XmpParser::encode( std::string& xmpPacket,
const XmpData& xmpData)
const XmpData& xmpData,
uint16_t formatFlags,
uint32_t padding)
{ try {
if (xmpData.empty()) return 0;
@ -609,8 +614,8 @@ namespace Exiv2 {
// Todo: Xmpdatum should have an XmpValue, not a Value
const XmpValue* val = dynamic_cast<const XmpValue*>(&i->value());
assert(val);
options = xmpOptionBits(val->xmpArrayType())
| xmpOptionBits(val->xmpStruct());
options = xmpArrayOptionBits(val->xmpArrayType())
| xmpArrayOptionBits(val->xmpStruct());
if ( i->typeId() == xmpBag
|| i->typeId() == xmpSeq
|| i->typeId() == xmpAlt) {
@ -646,7 +651,7 @@ namespace Exiv2 {
throw Error(38, i->tagName(), TypeInfo::typeName(i->typeId()));
}
std::string tmpPacket;
meta.SerializeToBuffer(&tmpPacket, kXMP_UseCompactFormat); // throws
meta.SerializeToBuffer(&tmpPacket, xmpFormatOptionBits(static_cast<XmpFormatFlags>(formatFlags)), padding); // throws
xmpPacket = tmpPacket;
return 0;
@ -686,7 +691,7 @@ namespace {
return var;
}
XMP_OptionBits xmpOptionBits(Exiv2::XmpValue::XmpStruct xs)
XMP_OptionBits xmpArrayOptionBits(Exiv2::XmpValue::XmpStruct xs)
{
XMP_OptionBits var(0);
switch (xs) {
@ -715,7 +720,7 @@ namespace {
return Exiv2::XmpValue::xmpArrayType(arrayValueTypeId(opt));
}
XMP_OptionBits xmpOptionBits(Exiv2::XmpValue::XmpArrayType xat)
XMP_OptionBits xmpArrayOptionBits(Exiv2::XmpValue::XmpArrayType xat)
{
XMP_OptionBits var(0);
switch (xat) {
@ -736,6 +741,19 @@ namespace {
return var;
}
XMP_OptionBits xmpFormatOptionBits(Exiv2::XmpParser::XmpFormatFlags flags)
{
XMP_OptionBits var(0);
if (flags & Exiv2::XmpParser::omitPacketWrapper) var |= kXMP_OmitPacketWrapper;
if (flags & Exiv2::XmpParser::readOnlyPacket) var |= kXMP_ReadOnlyPacket;
if (flags & Exiv2::XmpParser::useCompactFormat) var |= kXMP_UseCompactFormat;
if (flags & Exiv2::XmpParser::includeThumbnailPad) var |= kXMP_IncludeThumbnailPad;
if (flags & Exiv2::XmpParser::exactPacketLength) var |= kXMP_ExactPacketLength;
if (flags & Exiv2::XmpParser::writeAliasComments) var |= kXMP_WriteAliasComments;
if (flags & Exiv2::XmpParser::omitAllFormatting) var |= kXMP_OmitAllFormatting;
return var;
}
#ifdef DEBUG
void printNode(const std::string& schemaNs,
const std::string& propPath,

@ -254,6 +254,16 @@ namespace Exiv2 {
friend void XmpProperties::registerNs(const std::string&, const std::string&);
friend void XmpProperties::unregisterNs(const std::string&);
public:
//! Options to control the format of the serialized XMP packet.
enum XmpFormatFlags {
omitPacketWrapper = 0x0010UL, //!< Omit the XML packet wrapper.
readOnlyPacket = 0x0020UL, //!< Default is a writeable packet.
useCompactFormat = 0x0040UL, //!< Use a compact form of RDF.
includeThumbnailPad = 0x0100UL, //!< Include a padding allowance for a thumbnail image.
exactPacketLength = 0x0200UL, //!< The padding parameter is the overall packet length.
writeAliasComments = 0x0400UL, //!< Show aliases as XML comments.
omitAllFormatting = 0x0800UL //!< Omit all formatting whitespace.
};
/*!
@brief Decode XMP metadata from an XMP packet \em xmpPacket into
\em xmpData. The format of the XMP packet must follow the
@ -275,16 +285,21 @@ namespace Exiv2 {
follows the XMP specification. This method only modifies
\em xmpPacket if the operations succeeds (return code 0).
@param xmpPacket Reference to a string to hold the encoded XMP
packet.
@param xmpData XMP properties to encode.
@param xmpPacket Reference to a string to hold the encoded XMP
packet.
@param xmpData XMP properties to encode.
@param formatFlags Flags that control the format of the XMP packet,
see enum XmpFormatFlags.
@param padding Padding length.
@return 0 if successful;<BR>
1 if XMP support has not been compiled-in;<BR>
2 if the XMP toolkit failed to initialize;<BR>
3 if the XMP toolkit failed and raised an XMP_Error
*/
static int encode( std::string& xmpPacket,
const XmpData& xmpData);
const XmpData& xmpData,
uint16_t formatFlags =useCompactFormat,
uint32_t padding =0);
/*!
@brief Initialize the XMP Toolkit.

@ -116,13 +116,16 @@ namespace Exiv2 {
IoCloser closer(*io_);
if (writeXmpFromPacket() == false) {
if (XmpParser::encode(xmpPacket_, xmpData_)) {
if (XmpParser::encode(xmpPacket_, xmpData_, XmpParser::omitPacketWrapper|XmpParser::useCompactFormat)) {
#ifndef SUPPRESS_WARNINGS
std::cerr << "Error: Failed to encode XMP metadata.\n";
#endif
}
}
if (xmpPacket_.size() > 0) {
if (xmpPacket_.substr(0, 5) != "<?xml") {
xmpPacket_ = "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n" + xmpPacket_;
}
BasicIo::AutoPtr tempIo(io_->temporary()); // may throw
assert(tempIo.get() != 0);
// Write XMP packet

Loading…
Cancel
Save