|
|
|
@ -372,46 +372,43 @@ void TiffDecoder::decodeCanonAFInfo(const TiffEntryBase* object) {
|
|
|
|
|
const uint16_t nMasks = (nPoints + 15) / (sizeof(uint16_t) * 8);
|
|
|
|
|
int nStart = 0;
|
|
|
|
|
|
|
|
|
|
static const struct {
|
|
|
|
|
uint16_t tag;
|
|
|
|
|
uint16_t size;
|
|
|
|
|
bool bSigned;
|
|
|
|
|
} records[] = {
|
|
|
|
|
{0x2600, 1, true}, // AFInfoSize
|
|
|
|
|
{0x2601, 1, true}, // AFAreaMode
|
|
|
|
|
{0x2602, 1, true}, // AFNumPoints
|
|
|
|
|
{0x2603, 1, true}, // AFValidPoints
|
|
|
|
|
{0x2604, 1, true}, // AFCanonImageWidth
|
|
|
|
|
{0x2605, 1, true}, // AFCanonImageHeight
|
|
|
|
|
{0x2606, 1, true}, // AFImageWidth"
|
|
|
|
|
{0x2607, 1, true}, // AFImageHeight
|
|
|
|
|
{0x2608, nPoints, true}, // AFAreaWidths
|
|
|
|
|
{0x2609, nPoints, true}, // AFAreaHeights
|
|
|
|
|
{0x260a, nPoints, true}, // AFXPositions
|
|
|
|
|
{0x260b, nPoints, true}, // AFYPositions
|
|
|
|
|
{0x260c, nMasks, false}, // AFPointsInFocus
|
|
|
|
|
{0x260d, nMasks, false}, // AFPointsSelected
|
|
|
|
|
{0x260e, nMasks, false}, // AFPointsUnusable
|
|
|
|
|
using record = std::tuple<uint16_t, uint16_t, bool>;
|
|
|
|
|
static const auto records = std::array{
|
|
|
|
|
record(0x2600, 1, true), // AFInfoSize
|
|
|
|
|
record(0x2601, 1, true), // AFAreaMode
|
|
|
|
|
record(0x2602, 1, true), // AFNumPoints
|
|
|
|
|
record(0x2603, 1, true), // AFValidPoints
|
|
|
|
|
record(0x2604, 1, true), // AFCanonImageWidth
|
|
|
|
|
record(0x2605, 1, true), // AFCanonImageHeight
|
|
|
|
|
record(0x2606, 1, true), // AFImageWidth"
|
|
|
|
|
record(0x2607, 1, true), // AFImageHeight
|
|
|
|
|
record(0x2608, nPoints, true), // AFAreaWidths
|
|
|
|
|
record(0x2609, nPoints, true), // AFAreaHeights
|
|
|
|
|
record(0x260a, nPoints, true), // AFXPositions
|
|
|
|
|
record(0x260b, nPoints, true), // AFYPositions
|
|
|
|
|
record(0x260c, nMasks, false), // AFPointsInFocus
|
|
|
|
|
record(0x260d, nMasks, false), // AFPointsSelected
|
|
|
|
|
record(0x260e, nMasks, false), // AFPointsUnusable
|
|
|
|
|
};
|
|
|
|
|
// check we have enough data!
|
|
|
|
|
uint16_t count = 0;
|
|
|
|
|
for (auto&& record : records) {
|
|
|
|
|
count += record.size;
|
|
|
|
|
for (auto&& [tag, size, bSigned] : records) {
|
|
|
|
|
count += size;
|
|
|
|
|
if (count > ints.size())
|
|
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
for (auto&& record : records) {
|
|
|
|
|
for (auto&& [tag, size, bSigned] : records) {
|
|
|
|
|
const TagInfo* pTags = ExifTags::tagList("Canon");
|
|
|
|
|
const TagInfo* pTag = findTag(pTags, record.tag);
|
|
|
|
|
const TagInfo* pTag = findTag(pTags, tag);
|
|
|
|
|
if (pTag) {
|
|
|
|
|
auto v = Exiv2::Value::create(record.bSigned ? Exiv2::signedShort : Exiv2::unsignedShort);
|
|
|
|
|
auto v = Exiv2::Value::create(bSigned ? Exiv2::signedShort : Exiv2::unsignedShort);
|
|
|
|
|
std::ostringstream s;
|
|
|
|
|
if (record.bSigned) {
|
|
|
|
|
for (uint16_t k = 0; k < record.size; k++)
|
|
|
|
|
if (bSigned) {
|
|
|
|
|
for (uint16_t k = 0; k < size; k++)
|
|
|
|
|
s << " " << ints.at(nStart++);
|
|
|
|
|
} else {
|
|
|
|
|
for (uint16_t k = 0; k < record.size; k++)
|
|
|
|
|
for (uint16_t k = 0; k < size; k++)
|
|
|
|
|
s << " " << uint.at(nStart++);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|