// ExifReader.h // Copyright (c) 2009 The Foundry Visionmongers Ltd. All Rights Reserved. #include #include #include #include "DDImage/Reader.h" class ExifReader : public DD::Image::Reader { public: ExifReader(DD::Image::Read * iop); void fetchExifMetaData(DD::Image::MetaData::Bundle& metadata, void* data, int len); }; ExifReader::ExifReader(DD::Image::Read * iop) : DD::Image::Reader(iop) { } void ExifReader::fetchExifMetaData(DD::Image::MetaData::Bundle& metadata, void* rawdata, int size) { ExifData* data = exif_data_new_from_data((const unsigned char*)rawdata, size); if (!data) { return; } ExifByteOrder byteOrder = exif_data_get_byte_order(data); for (int i = 0; i < EXIF_IFD_COUNT; i++) { ExifContent* cont = data->ifd[i]; for (size_t j = 0; j < cont->count; j++) { ExifEntry* entry = cont->entries[j]; std::ostringstream str; switch (entry->format) { case EXIF_FORMAT_ASCII: { std::string asciistring = std::string((char*)entry->data, entry->size); if (asciistring.length() && asciistring[asciistring.length() - 1] == '\0') { asciistring = asciistring.substr(0, asciistring.length() - 1); } str << asciistring; } break; case EXIF_FORMAT_BYTE: str << (int)*entry->data; break; case EXIF_FORMAT_SHORT: str << exif_get_short(entry->data, byteOrder); break; case EXIF_FORMAT_LONG: str << exif_get_long(entry->data, byteOrder); break; case EXIF_FORMAT_SLONG: str << exif_get_slong(entry->data, byteOrder); break; case EXIF_FORMAT_RATIONAL: { ExifRational number = exif_get_rational(entry->data, byteOrder); str << number.numerator << "/" << number.denominator; } break; case EXIF_FORMAT_SRATIONAL: { ExifSRational number = exif_get_srational(entry->data, byteOrder); str << number.numerator << "/" << number.denominator; } break; default: ; } std::ostringstream key; key << DD::Image::MetaData::EXIF::EXIF_PREFIX; key << i; key << "/"; key << exif_tag_get_name(entry->tag); metadata.setData(key.str(), str.str()); } } exif_data_free(data); }