exiftool_vendored 12.81.0 → 12.83.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/bin/Changes +39 -1
- data/bin/MANIFEST +4 -18
- data/bin/META.json +1 -1
- data/bin/META.yml +1 -1
- data/bin/README +3 -2
- data/bin/build_geolocation +867 -0
- data/bin/exiftool +37 -9
- data/bin/fmt_files/gpx.fmt +2 -1
- data/bin/fmt_files/gpx_wpt.fmt +2 -1
- data/bin/lib/Image/ExifTool/BuildTagLookup.pm +47 -31
- data/bin/lib/Image/ExifTool/CanonVRD.pm +6 -5
- data/bin/lib/Image/ExifTool/DJI.pm +29 -0
- data/bin/lib/Image/ExifTool/Exif.pm +19 -2
- data/bin/lib/Image/ExifTool/FujiFilm.pm +9 -2
- data/bin/lib/Image/ExifTool/GM.pm +552 -0
- data/bin/lib/Image/ExifTool/Geolocation.dat +0 -0
- data/bin/lib/Image/ExifTool/Geolocation.pm +90 -54
- data/bin/lib/Image/ExifTool/Nikon.pm +9 -7
- data/bin/lib/Image/ExifTool/QuickTime.pm +31 -23
- data/bin/lib/Image/ExifTool/QuickTimeStream.pl +66 -30
- data/bin/lib/Image/ExifTool/README +2 -0
- data/bin/lib/Image/ExifTool/Sony.pm +15 -6
- data/bin/lib/Image/ExifTool/TagLookup.pm +37 -6
- data/bin/lib/Image/ExifTool/TagNames.pod +407 -239
- data/bin/lib/Image/ExifTool/WriteQuickTime.pl +5 -2
- data/bin/lib/Image/ExifTool/Writer.pl +165 -133
- data/bin/lib/Image/ExifTool/XMP.pm +3 -2
- data/bin/lib/Image/ExifTool/XMP2.pl +3 -0
- data/bin/lib/Image/ExifTool.pm +38 -9
- data/bin/lib/Image/ExifTool.pod +31 -18
- data/bin/perl-Image-ExifTool.spec +1 -1
- data/lib/exiftool_vendored/version.rb +1 -1
- metadata +4 -20
- data/bin/lib/Image/ExifTool/GeoLang/cs.pm +0 -978
- data/bin/lib/Image/ExifTool/GeoLang/de.pm +0 -1975
- data/bin/lib/Image/ExifTool/GeoLang/en_ca.pm +0 -44
- data/bin/lib/Image/ExifTool/GeoLang/en_gb.pm +0 -124
- data/bin/lib/Image/ExifTool/GeoLang/es.pm +0 -2921
- data/bin/lib/Image/ExifTool/GeoLang/fi.pm +0 -1116
- data/bin/lib/Image/ExifTool/GeoLang/fr.pm +0 -3171
- data/bin/lib/Image/ExifTool/GeoLang/it.pm +0 -2750
- data/bin/lib/Image/ExifTool/GeoLang/ja.pm +0 -10256
- data/bin/lib/Image/ExifTool/GeoLang/ko.pm +0 -4499
- data/bin/lib/Image/ExifTool/GeoLang/nl.pm +0 -1270
- data/bin/lib/Image/ExifTool/GeoLang/pl.pm +0 -3019
- data/bin/lib/Image/ExifTool/GeoLang/ru.pm +0 -18220
- data/bin/lib/Image/ExifTool/GeoLang/sk.pm +0 -441
- data/bin/lib/Image/ExifTool/GeoLang/sv.pm +0 -714
- data/bin/lib/Image/ExifTool/GeoLang/tr.pm +0 -452
- data/bin/lib/Image/ExifTool/GeoLang/zh_cn.pm +0 -2225
- data/bin/lib/Image/ExifTool/GeoLang/zh_tw.pm +0 -72
|
@@ -168,7 +168,8 @@ sub ConvInvISO6709($)
|
|
|
168
168
|
# requires at least 3 digits after the decimal point
|
|
169
169
|
# (and as of Apr 2021, Google Photos doesn't accept coordinats
|
|
170
170
|
# with more than 5 digits after the decimal place:
|
|
171
|
-
# https://exiftool.org/forum/index.php?topic=11055.msg67171#msg67171
|
|
171
|
+
# https://exiftool.org/forum/index.php?topic=11055.msg67171#msg67171
|
|
172
|
+
# still a problem Apr 2024: https://exiftool.org/forum/index.php?msg=85761)
|
|
172
173
|
my @fmt = ('%s%02d.%s%s','%s%03d.%s%s','%s%d.%s%s');
|
|
173
174
|
my @limit = (90,180);
|
|
174
175
|
foreach (@a) {
|
|
@@ -1452,7 +1453,9 @@ sub WriteQuickTime($$$)
|
|
|
1452
1453
|
}
|
|
1453
1454
|
# ($errStr is set if there was an error that could possibly be due to an unknown trailer)
|
|
1454
1455
|
if ($errStr) {
|
|
1455
|
-
if ($lastTag eq 'mdat' and not $dataPt and not $$tagTablePtr{$tag}
|
|
1456
|
+
if (($lastTag eq 'mdat' or $lastTag eq 'moov') and not $dataPt and (not $$tagTablePtr{$tag} or
|
|
1457
|
+
ref $$tagTablePtr{$tag} eq 'HASH' and $$tagTablePtr{$tag}{Unknown}))
|
|
1458
|
+
{
|
|
1456
1459
|
my $nvTrail = $et->GetNewValueHash($Image::ExifTool::Extra{Trailer});
|
|
1457
1460
|
if ($$et{DEL_GROUP}{Trailer} or ($nvTrail and not ($$nvTrail{Value} and $$nvTrail{Value}[0]))) {
|
|
1458
1461
|
$errStr =~ s/ is too large.*//;
|
|
@@ -1234,7 +1234,8 @@ WriteAlso:
|
|
|
1234
1234
|
|
|
1235
1235
|
#------------------------------------------------------------------------------
|
|
1236
1236
|
# set new values from information in specified file
|
|
1237
|
-
# Inputs: 0) ExifTool object reference, 1) source file name or reference, etc
|
|
1237
|
+
# Inputs: 0) ExifTool object reference, 1) source file name or reference, etc,
|
|
1238
|
+
# or ExifTool ref to use already-extracted tags from an ExifTool object,
|
|
1238
1239
|
# 2-N) List of tags to set (or all if none specified), or reference(s) to
|
|
1239
1240
|
# hash for options to pass to SetNewValue. The Replace option defaults
|
|
1240
1241
|
# to 1 for SetNewValuesFromFile -- set this to 0 to allow multiple tags
|
|
@@ -1245,11 +1246,12 @@ WriteAlso:
|
|
|
1245
1246
|
# be used to represent all tags in a group. An optional destination tag
|
|
1246
1247
|
# may be specified with '>DSTTAG' ('DSTTAG<TAG' also works, but in this
|
|
1247
1248
|
# case the source tag may also be an expression involving tag names).
|
|
1249
|
+
# Simple assignments are also allowed: 'DSTTAG[#][+-][^]=[string]'
|
|
1248
1250
|
sub SetNewValuesFromFile($$;@)
|
|
1249
1251
|
{
|
|
1250
1252
|
local $_;
|
|
1251
1253
|
my ($self, $srcFile, @setTags) = @_;
|
|
1252
|
-
my ($key, $tag, @exclude, @reqTags);
|
|
1254
|
+
my ($srcExifTool, $key, $tag, @exclude, @reqTags, $info);
|
|
1253
1255
|
|
|
1254
1256
|
# get initial SetNewValuesFromFile options
|
|
1255
1257
|
my %opts = ( Replace => 1 ); # replace existing list items by default
|
|
@@ -1261,113 +1263,8 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1261
1263
|
}
|
|
1262
1264
|
# expand shortcuts
|
|
1263
1265
|
@setTags and ExpandShortcuts(\@setTags);
|
|
1264
|
-
my $srcExifTool = Image::ExifTool->new;
|
|
1265
|
-
# set flag to indicate we are being called from inside SetNewValuesFromFile()
|
|
1266
|
-
$$srcExifTool{TAGS_FROM_FILE} = 1;
|
|
1267
|
-
# synchronize and increment the file sequence number
|
|
1268
|
-
$$srcExifTool{FILE_SEQUENCE} = $$self{FILE_SEQUENCE}++;
|
|
1269
1266
|
# set options for our extraction tool
|
|
1270
1267
|
my $options = $$self{OPTIONS};
|
|
1271
|
-
# copy both structured and flattened tags by default (but flattened tags are "unsafe")
|
|
1272
|
-
my $structOpt = defined $$options{Struct} ? $$options{Struct} : 2;
|
|
1273
|
-
# copy structures only if no tags specified (since flattened tags are "unsafe")
|
|
1274
|
-
$structOpt = 1 if $structOpt eq '2' and not @setTags;
|
|
1275
|
-
# +------------------------------------------+
|
|
1276
|
-
# ! DON'T FORGET!! Must consider each new !
|
|
1277
|
-
# ! option to decide how it is handled here. !
|
|
1278
|
-
# +------------------------------------------+
|
|
1279
|
-
$srcExifTool->Options(
|
|
1280
|
-
Binary => 1,
|
|
1281
|
-
ByteUnit => $$options{ByteUnit},
|
|
1282
|
-
Charset => $$options{Charset},
|
|
1283
|
-
CharsetEXIF => $$options{CharsetEXIF},
|
|
1284
|
-
CharsetFileName => $$options{CharsetFileName},
|
|
1285
|
-
CharsetID3 => $$options{CharsetID3},
|
|
1286
|
-
CharsetIPTC => $$options{CharsetIPTC},
|
|
1287
|
-
CharsetPhotoshop=> $$options{CharsetPhotoshop},
|
|
1288
|
-
Composite => $$options{Composite},
|
|
1289
|
-
CoordFormat => $$options{CoordFormat} || '%d %d %.8f', # copy coordinates at high resolution unless otherwise specified
|
|
1290
|
-
DateFormat => $$options{DateFormat},
|
|
1291
|
-
Duplicates => 1,
|
|
1292
|
-
Escape => $$options{Escape},
|
|
1293
|
-
# Exclude (set below)
|
|
1294
|
-
ExtendedXMP => $$options{ExtendedXMP},
|
|
1295
|
-
ExtractEmbedded => $$options{ExtractEmbedded},
|
|
1296
|
-
FastScan => $$options{FastScan},
|
|
1297
|
-
Filter => $$options{Filter},
|
|
1298
|
-
FixBase => $$options{FixBase},
|
|
1299
|
-
Geolocation => $$options{Geolocation},
|
|
1300
|
-
GeolocAltNames => $$options{GeolocAltNames},
|
|
1301
|
-
GeolocFeature => $$options{GeolocFeature},
|
|
1302
|
-
GeolocMinPop => $$options{GeolocMinPop},
|
|
1303
|
-
GeolocMaxDist => $$options{GeolocMaxDist},
|
|
1304
|
-
GlobalTimeShift => $$options{GlobalTimeShift},
|
|
1305
|
-
HexTagIDs => $$options{HexTagIDs},
|
|
1306
|
-
IgnoreMinorErrors=>$$options{IgnoreMinorErrors},
|
|
1307
|
-
IgnoreTags => $$options{IgnoreTags},
|
|
1308
|
-
ImageHashType => $$options{ImageHashType},
|
|
1309
|
-
Lang => $$options{Lang},
|
|
1310
|
-
LargeFileSupport=> $$options{LargeFileSupport},
|
|
1311
|
-
LimitLongValues => 10000000, # (10 MB)
|
|
1312
|
-
List => 1,
|
|
1313
|
-
ListItem => $$options{ListItem},
|
|
1314
|
-
ListSep => $$options{ListSep},
|
|
1315
|
-
MakerNotes => $$options{FastScan} && $$options{FastScan} > 1 ? undef : 1,
|
|
1316
|
-
MDItemTags => $$options{MDItemTags},
|
|
1317
|
-
MissingTagValue => $$options{MissingTagValue},
|
|
1318
|
-
NoPDFList => $$options{NoPDFList},
|
|
1319
|
-
NoWarning => $$options{NoWarning},
|
|
1320
|
-
Password => $$options{Password},
|
|
1321
|
-
PrintConv => $$options{PrintConv},
|
|
1322
|
-
QuickTimeUTC => $$options{QuickTimeUTC},
|
|
1323
|
-
RequestAll => $$options{RequestAll} || 1, # (is this still necessary now that RequestTags are being set?)
|
|
1324
|
-
RequestTags => $$options{RequestTags},
|
|
1325
|
-
SaveFormat => $$options{SaveFormat},
|
|
1326
|
-
SavePath => $$options{SavePath},
|
|
1327
|
-
ScanForXMP => $$options{ScanForXMP},
|
|
1328
|
-
StrictDate => defined $$options{StrictDate} ? $$options{StrictDate} : 1,
|
|
1329
|
-
Struct => $structOpt,
|
|
1330
|
-
StructFormat => $$options{StructFormat},
|
|
1331
|
-
SystemTags => $$options{SystemTags},
|
|
1332
|
-
TimeZone => $$options{TimeZone},
|
|
1333
|
-
Unknown => $$options{Unknown},
|
|
1334
|
-
UserParam => $$options{UserParam},
|
|
1335
|
-
Validate => $$options{Validate},
|
|
1336
|
-
WindowsWideFile => $$options{WindowsWideFile},
|
|
1337
|
-
XAttrTags => $$options{XAttrTags},
|
|
1338
|
-
XMPAutoConv => $$options{XMPAutoConv},
|
|
1339
|
-
);
|
|
1340
|
-
# reset Geolocation option if we aren't copying any geolocation tags
|
|
1341
|
-
if ($$options{Geolocation} and not grep /\bGeolocation/i, @setTags) {
|
|
1342
|
-
$self->VPrint(0, '(resetting unnecessary Geolocation option)');
|
|
1343
|
-
$$srcExifTool{OPTIONS}{Geolocation} = undef;
|
|
1344
|
-
}
|
|
1345
|
-
$$srcExifTool{GLOBAL_TIME_OFFSET} = $$self{GLOBAL_TIME_OFFSET};
|
|
1346
|
-
$$srcExifTool{ALT_EXIFTOOL} = $$self{ALT_EXIFTOOL};
|
|
1347
|
-
foreach $tag (@setTags) {
|
|
1348
|
-
next if ref $tag;
|
|
1349
|
-
if ($tag =~ /^-(.*)/) {
|
|
1350
|
-
# avoid extracting tags that are excluded
|
|
1351
|
-
push @exclude, $1;
|
|
1352
|
-
next;
|
|
1353
|
-
}
|
|
1354
|
-
# add specified tags to list of requested tags
|
|
1355
|
-
$_ = $tag;
|
|
1356
|
-
if (/(.+?)\s*(>|<)\s*(.+)/) {
|
|
1357
|
-
if ($2 eq '>') {
|
|
1358
|
-
$_ = $1;
|
|
1359
|
-
} else {
|
|
1360
|
-
$_ = $3;
|
|
1361
|
-
/\$/ and push(@reqTags, /\$\{?(?:[-\w]+:)*([-\w?*]+)/g), next;
|
|
1362
|
-
}
|
|
1363
|
-
}
|
|
1364
|
-
push @reqTags, $2 if /(^|:)([-\w?*]+)#?$/;
|
|
1365
|
-
}
|
|
1366
|
-
if (@exclude) {
|
|
1367
|
-
ExpandShortcuts(\@exclude, 1);
|
|
1368
|
-
$srcExifTool->Options(Exclude => \@exclude);
|
|
1369
|
-
}
|
|
1370
|
-
$srcExifTool->Options(RequestTags => \@reqTags) if @reqTags;
|
|
1371
1268
|
my $printConv = $$options{PrintConv};
|
|
1372
1269
|
if ($opts{Type}) {
|
|
1373
1270
|
# save source type separately because it may be different than dst Type
|
|
@@ -1377,9 +1274,120 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1377
1274
|
$srcExifTool->Options(PrintConv => $printConv);
|
|
1378
1275
|
}
|
|
1379
1276
|
my $srcType = $printConv ? 'PrintConv' : 'ValueConv';
|
|
1277
|
+
my $structOpt = defined $$options{Struct} ? $$options{Struct} : 2;
|
|
1380
1278
|
|
|
1381
|
-
|
|
1382
|
-
|
|
1279
|
+
if (ref $srcFile and UNIVERSAL::isa($srcFile,'Image::ExifTool')) {
|
|
1280
|
+
$srcExifTool = $srcFile;
|
|
1281
|
+
$info = $srcExifTool->GetInfo();
|
|
1282
|
+
} else {
|
|
1283
|
+
$srcExifTool = Image::ExifTool->new;
|
|
1284
|
+
# set flag to indicate we are being called from inside SetNewValuesFromFile()
|
|
1285
|
+
$$srcExifTool{TAGS_FROM_FILE} = 1;
|
|
1286
|
+
# synchronize and increment the file sequence number
|
|
1287
|
+
$$srcExifTool{FILE_SEQUENCE} = $$self{FILE_SEQUENCE}++;
|
|
1288
|
+
# copy both structured and flattened tags by default (but flattened tags are "unsafe")
|
|
1289
|
+
# copy structures only if no tags specified (since flattened tags are "unsafe")
|
|
1290
|
+
$structOpt = 1 if $structOpt eq '2' and not @setTags;
|
|
1291
|
+
# +------------------------------------------+
|
|
1292
|
+
# ! DON'T FORGET!! Must consider each new !
|
|
1293
|
+
# ! option to decide how it is handled here. !
|
|
1294
|
+
# +------------------------------------------+
|
|
1295
|
+
$srcExifTool->Options(
|
|
1296
|
+
Binary => 1,
|
|
1297
|
+
ByteUnit => $$options{ByteUnit},
|
|
1298
|
+
Charset => $$options{Charset},
|
|
1299
|
+
CharsetEXIF => $$options{CharsetEXIF},
|
|
1300
|
+
CharsetFileName => $$options{CharsetFileName},
|
|
1301
|
+
CharsetID3 => $$options{CharsetID3},
|
|
1302
|
+
CharsetIPTC => $$options{CharsetIPTC},
|
|
1303
|
+
CharsetPhotoshop=> $$options{CharsetPhotoshop},
|
|
1304
|
+
Composite => $$options{Composite},
|
|
1305
|
+
CoordFormat => $$options{CoordFormat} || '%d %d %.8f', # copy coordinates at high resolution unless otherwise specified
|
|
1306
|
+
DateFormat => $$options{DateFormat},
|
|
1307
|
+
Duplicates => 1,
|
|
1308
|
+
Escape => $$options{Escape},
|
|
1309
|
+
# Exclude (set below)
|
|
1310
|
+
ExtendedXMP => $$options{ExtendedXMP},
|
|
1311
|
+
ExtractEmbedded => $$options{ExtractEmbedded},
|
|
1312
|
+
FastScan => $$options{FastScan},
|
|
1313
|
+
Filter => $$options{Filter},
|
|
1314
|
+
FixBase => $$options{FixBase},
|
|
1315
|
+
Geolocation => $$options{Geolocation},
|
|
1316
|
+
GeolocAltNames => $$options{GeolocAltNames},
|
|
1317
|
+
GeolocFeature => $$options{GeolocFeature},
|
|
1318
|
+
GeolocMinPop => $$options{GeolocMinPop},
|
|
1319
|
+
GeolocMaxDist => $$options{GeolocMaxDist},
|
|
1320
|
+
GlobalTimeShift => $$options{GlobalTimeShift},
|
|
1321
|
+
HexTagIDs => $$options{HexTagIDs},
|
|
1322
|
+
IgnoreGroups => $$options{IgnoreGroups},
|
|
1323
|
+
IgnoreMinorErrors=>$$options{IgnoreMinorErrors},
|
|
1324
|
+
IgnoreTags => $$options{IgnoreTags},
|
|
1325
|
+
ImageHashType => $$options{ImageHashType},
|
|
1326
|
+
Lang => $$options{Lang},
|
|
1327
|
+
LargeFileSupport=> $$options{LargeFileSupport},
|
|
1328
|
+
LimitLongValues => 10000000, # (10 MB)
|
|
1329
|
+
List => 1,
|
|
1330
|
+
ListItem => $$options{ListItem},
|
|
1331
|
+
ListSep => $$options{ListSep},
|
|
1332
|
+
MakerNotes => $$options{FastScan} && $$options{FastScan} > 1 ? undef : 1,
|
|
1333
|
+
MDItemTags => $$options{MDItemTags},
|
|
1334
|
+
MissingTagValue => $$options{MissingTagValue},
|
|
1335
|
+
NoPDFList => $$options{NoPDFList},
|
|
1336
|
+
NoWarning => $$options{NoWarning},
|
|
1337
|
+
Password => $$options{Password},
|
|
1338
|
+
PrintConv => $$options{PrintConv},
|
|
1339
|
+
QuickTimeUTC => $$options{QuickTimeUTC},
|
|
1340
|
+
RequestAll => $$options{RequestAll} || 1, # (is this still necessary now that RequestTags are being set?)
|
|
1341
|
+
RequestTags => $$options{RequestTags},
|
|
1342
|
+
SaveFormat => $$options{SaveFormat},
|
|
1343
|
+
SavePath => $$options{SavePath},
|
|
1344
|
+
ScanForXMP => $$options{ScanForXMP},
|
|
1345
|
+
StrictDate => defined $$options{StrictDate} ? $$options{StrictDate} : 1,
|
|
1346
|
+
Struct => $structOpt,
|
|
1347
|
+
StructFormat => $$options{StructFormat},
|
|
1348
|
+
SystemTags => $$options{SystemTags},
|
|
1349
|
+
TimeZone => $$options{TimeZone},
|
|
1350
|
+
Unknown => $$options{Unknown},
|
|
1351
|
+
UserParam => $$options{UserParam},
|
|
1352
|
+
Validate => $$options{Validate},
|
|
1353
|
+
WindowsWideFile => $$options{WindowsWideFile},
|
|
1354
|
+
XAttrTags => $$options{XAttrTags},
|
|
1355
|
+
XMPAutoConv => $$options{XMPAutoConv},
|
|
1356
|
+
);
|
|
1357
|
+
# reset Geolocation option if we aren't copying any geolocation tags
|
|
1358
|
+
if ($$options{Geolocation} and not grep /\bGeolocation/i, @setTags) {
|
|
1359
|
+
$self->VPrint(0, '(resetting unnecessary Geolocation option)');
|
|
1360
|
+
$$srcExifTool{OPTIONS}{Geolocation} = undef;
|
|
1361
|
+
}
|
|
1362
|
+
$$srcExifTool{GLOBAL_TIME_OFFSET} = $$self{GLOBAL_TIME_OFFSET};
|
|
1363
|
+
$$srcExifTool{ALT_EXIFTOOL} = $$self{ALT_EXIFTOOL};
|
|
1364
|
+
foreach $tag (@setTags) {
|
|
1365
|
+
next if ref $tag;
|
|
1366
|
+
if ($tag =~ /^-(.*)/) {
|
|
1367
|
+
# avoid extracting tags that are excluded
|
|
1368
|
+
push @exclude, $1;
|
|
1369
|
+
next;
|
|
1370
|
+
}
|
|
1371
|
+
# add specified tags to list of requested tags
|
|
1372
|
+
$_ = $tag;
|
|
1373
|
+
if (/(.+?)\s*(>|<)\s*(.+)/) {
|
|
1374
|
+
if ($2 eq '>') {
|
|
1375
|
+
$_ = $1;
|
|
1376
|
+
} else {
|
|
1377
|
+
$_ = $3;
|
|
1378
|
+
/\$/ and push(@reqTags, /\$\{?(?:[-\w]+:)*([-\w?*]+)/g), next;
|
|
1379
|
+
}
|
|
1380
|
+
}
|
|
1381
|
+
push @reqTags, $2 if /(^|:)([-\w?*]+)#?$/;
|
|
1382
|
+
}
|
|
1383
|
+
if (@exclude) {
|
|
1384
|
+
ExpandShortcuts(\@exclude, 1);
|
|
1385
|
+
$srcExifTool->Options(Exclude => \@exclude);
|
|
1386
|
+
}
|
|
1387
|
+
$srcExifTool->Options(RequestTags => \@reqTags) if @reqTags;
|
|
1388
|
+
# get all tags from source file (including MakerNotes block)
|
|
1389
|
+
$info = $srcExifTool->ImageInfo($srcFile);
|
|
1390
|
+
}
|
|
1383
1391
|
return $info if $$info{Error} and $$info{Error} eq 'Error opening file';
|
|
1384
1392
|
delete $$srcExifTool{VALUE}{Error}; # delete so we can check this later
|
|
1385
1393
|
|
|
@@ -1414,6 +1422,7 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1414
1422
|
#
|
|
1415
1423
|
# 1) loop through input list of tags to set, and build @setList
|
|
1416
1424
|
my (@setList, $set, %setMatches, $t, %altFiles);
|
|
1425
|
+
my $assign = 0;
|
|
1417
1426
|
foreach $t (@setTags) {
|
|
1418
1427
|
if (ref $t eq 'HASH') {
|
|
1419
1428
|
# update current options
|
|
@@ -1428,18 +1437,22 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1428
1437
|
$tag = lc $t; # change tag/group names to all lower case
|
|
1429
1438
|
my (@fg, $grp, $dst, $dstGrp, $dstTag, $isExclude);
|
|
1430
1439
|
# handle redirection to another tag
|
|
1431
|
-
if ($tag =~ /(.+?)\s*(
|
|
1440
|
+
if ($tag =~ /(.+?)\s*(>|<|=)(\s*)(.*)/) {
|
|
1432
1441
|
$dstGrp = '';
|
|
1433
|
-
my $opt;
|
|
1442
|
+
my ($opt, $op, $spc);
|
|
1434
1443
|
if ($2 eq '>') {
|
|
1435
|
-
($tag, $dstTag) = ($1, $
|
|
1444
|
+
($tag, $dstTag) = ($1, $4);
|
|
1436
1445
|
# flag add and delete (eg. '+<' and '-<') redirections
|
|
1437
1446
|
$opt = $1 if $tag =~ s/\s*([-+])$// or $dstTag =~ s/^([-+])\s*//;
|
|
1438
1447
|
} else {
|
|
1439
|
-
($
|
|
1448
|
+
($dstTag, $op, $spc, $tag) = ($1, $2, $3, $4);
|
|
1440
1449
|
$opt = $1 if $dstTag =~ s/\s*([-+])$//;
|
|
1441
|
-
|
|
1442
|
-
|
|
1450
|
+
if ($op eq '=') {
|
|
1451
|
+
# simple assignment ($tag will be the new value)
|
|
1452
|
+
$tag = $spc . $tag;
|
|
1453
|
+
undef $tag unless $dstTag =~ s/\^$// or length $tag;
|
|
1454
|
+
$$opts{ASSIGN} = ++$assign;
|
|
1455
|
+
} elsif ($tag =~ /\$/) { # handle expressions
|
|
1443
1456
|
$tag = $t; # restore original case
|
|
1444
1457
|
# recover leading whitespace (except for initial single space)
|
|
1445
1458
|
$tag =~ s/(.+?)\s*(>|<) ?//;
|
|
@@ -1452,7 +1465,7 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1452
1465
|
}
|
|
1453
1466
|
$$opts{Replace} = 0 if $dstTag =~ s/^\+//;
|
|
1454
1467
|
# validate tag name(s)
|
|
1455
|
-
unless ($$opts{EXPR} or ValidTagName($tag)) {
|
|
1468
|
+
unless ($$opts{EXPR} or $$opts{ASSIGN} or ValidTagName($tag)) {
|
|
1456
1469
|
$self->Warn("Invalid tag name '${tag}'. Use '=' not '<' to assign a tag value");
|
|
1457
1470
|
next;
|
|
1458
1471
|
}
|
|
@@ -1470,7 +1483,7 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1470
1483
|
} else {
|
|
1471
1484
|
$$opts{Replace} = 0 if $tag =~ s/^\+//;
|
|
1472
1485
|
}
|
|
1473
|
-
unless ($$opts{EXPR}) {
|
|
1486
|
+
unless ($$opts{EXPR} or $$opts{ASSIGN}) {
|
|
1474
1487
|
$isExclude = ($tag =~ s/^-//);
|
|
1475
1488
|
if ($tag =~ /(.*):(.+)/) {
|
|
1476
1489
|
($grp, $tag) = ($1, $2);
|
|
@@ -1540,6 +1553,8 @@ sub SetNewValuesFromFile($$;@)
|
|
|
1540
1553
|
foreach $set (@setList) {
|
|
1541
1554
|
$$set[2] and $setMatches{$set} = [ ];
|
|
1542
1555
|
}
|
|
1556
|
+
# no need to search source tags if doing only assignments
|
|
1557
|
+
undef @tags if $assign == @setList;
|
|
1543
1558
|
# 3) loop through all tags in source image and save tags matching each setTag
|
|
1544
1559
|
my (%rtnInfo, $isAlt);
|
|
1545
1560
|
foreach $tag (@tags) {
|
|
@@ -1592,21 +1607,26 @@ SET: foreach $set (@setList) {
|
|
|
1592
1607
|
# get options for SetNewValue
|
|
1593
1608
|
my $opts = $$set[3];
|
|
1594
1609
|
# handle expressions
|
|
1595
|
-
if ($$opts{EXPR}) {
|
|
1596
|
-
my $val
|
|
1597
|
-
|
|
1598
|
-
|
|
1599
|
-
|
|
1600
|
-
|
|
1601
|
-
|
|
1602
|
-
|
|
1603
|
-
($
|
|
1604
|
-
|
|
1605
|
-
|
|
1606
|
-
|
|
1610
|
+
if ($$opts{EXPR} or $$opts{ASSIGN}) {
|
|
1611
|
+
my $val;
|
|
1612
|
+
if ($$opts{EXPR}) {
|
|
1613
|
+
$val = $srcExifTool->InsertTagValues($$set[1], \@tags, 'Error');
|
|
1614
|
+
my $err = $$srcExifTool{VALUE}{Error};
|
|
1615
|
+
if ($err) {
|
|
1616
|
+
# pass on any error as a warning unless it is suppressed
|
|
1617
|
+
my $noWarn = $$srcExifTool{OPTIONS}{NoWarning};
|
|
1618
|
+
unless ($noWarn and (eval { $err =~ /$noWarn/ } or
|
|
1619
|
+
# (also apply expression to warning without "[minor] " prefix)
|
|
1620
|
+
($err =~ s/^\[minor\] //i and eval { $err =~ /$noWarn/ })))
|
|
1621
|
+
{
|
|
1622
|
+
$tag = NextFreeTagKey(\%rtnInfo, 'Warning');
|
|
1623
|
+
$rtnInfo{$tag} = $$srcExifTool{VALUE}{Error};
|
|
1624
|
+
}
|
|
1625
|
+
delete $$srcExifTool{VALUE}{Error};
|
|
1626
|
+
next unless defined $val;
|
|
1607
1627
|
}
|
|
1608
|
-
|
|
1609
|
-
|
|
1628
|
+
} else {
|
|
1629
|
+
$val = $$set[1];
|
|
1610
1630
|
}
|
|
1611
1631
|
my ($dstGrp, $dstTag) = @{$$set[2]};
|
|
1612
1632
|
$$opts{Protected} = 1 unless $dstTag =~ /[?*]/ and $dstTag ne '*';
|
|
@@ -3167,8 +3187,8 @@ sub PushValue($$$;$)
|
|
|
3167
3187
|
# Inputs: 0) ExifTool object ref, 1) string with embedded tag names,
|
|
3168
3188
|
# 2) reference to list of found tags or undef to use FOUND_TAGS, 3) Options:
|
|
3169
3189
|
# undef - set missing tags to ''
|
|
3170
|
-
# 'Error' - issue minor error on missing tag (and return undef)
|
|
3171
|
-
# 'Warn' - issue minor warning on missing tag (and return undef)
|
|
3190
|
+
# 'Error' - issue minor error on missing tag (and return undef if error sent)
|
|
3191
|
+
# 'Warn' - issue minor warning on missing tag (and return undef if warning sent)
|
|
3172
3192
|
# 'Silent' - just return undef on missing tag (no errors/warnings)
|
|
3173
3193
|
# Hash ref - defined to interpolate as variables in string instead of values
|
|
3174
3194
|
# --> receives tag/value pairs for interpolation of the variables
|
|
@@ -3454,6 +3474,18 @@ sub NoDups
|
|
|
3454
3474
|
$_ = ($_[0] and $new eq $_) ? undef : $new;
|
|
3455
3475
|
}
|
|
3456
3476
|
|
|
3477
|
+
#------------------------------------------------------------------------------
|
|
3478
|
+
# Utility routine to set in $_ image from current object
|
|
3479
|
+
# Inputs: 0-N) list of tags to copy
|
|
3480
|
+
# Notes: - for use only in advanced formatting expressions
|
|
3481
|
+
sub SetTags(@)
|
|
3482
|
+
{
|
|
3483
|
+
my $self = $advFmtSelf;
|
|
3484
|
+
my $et = Image::ExifTool->new;
|
|
3485
|
+
$et->SetNewValuesFromFile($self, @_);
|
|
3486
|
+
$et->WriteInfo(\$_);
|
|
3487
|
+
}
|
|
3488
|
+
|
|
3457
3489
|
#------------------------------------------------------------------------------
|
|
3458
3490
|
# Is specified tag writable
|
|
3459
3491
|
# Inputs: 0) tag name, case insensitive (optional group name currently ignored)
|
|
@@ -50,7 +50,7 @@ use Image::ExifTool::Exif;
|
|
|
50
50
|
use Image::ExifTool::GPS;
|
|
51
51
|
require Exporter;
|
|
52
52
|
|
|
53
|
-
$VERSION = '3.
|
|
53
|
+
$VERSION = '3.65';
|
|
54
54
|
@ISA = qw(Exporter);
|
|
55
55
|
@EXPORT_OK = qw(EscapeXML UnescapeXML);
|
|
56
56
|
|
|
@@ -283,11 +283,12 @@ my %recognizedAttrs = (
|
|
|
283
283
|
# NOTE: this lookup is duplicated in TagLookup.pm!!
|
|
284
284
|
%specialStruct = (
|
|
285
285
|
STRUCT_NAME => 1, # [optional] name of structure
|
|
286
|
-
NAMESPACE => 1, # [mandatory] namespace prefix used for fields of this structure
|
|
286
|
+
NAMESPACE => 1, # [mandatory for XMP] namespace prefix used for fields of this structure
|
|
287
287
|
NOTES => 1, # [optional] notes for documentation about this structure
|
|
288
288
|
TYPE => 1, # [optional] rdf:type resource for struct (if used, the StructType flag
|
|
289
289
|
# will be set automatically for all derived flattened tags when writing)
|
|
290
290
|
GROUPS => 1, # [optional] specifies family group 2 name for the structure
|
|
291
|
+
SORT_ORDER => 1, # [optional] order for sorting fields in documentation
|
|
291
292
|
);
|
|
292
293
|
# XMP structures (each structure is similar to a tag table so we can
|
|
293
294
|
# recurse through them in SetPropertyPath() as if they were tag tables)
|
|
@@ -1941,6 +1941,9 @@ my %sACDSeeRegionStruct = (
|
|
|
1941
1941
|
ValueConv => 'Image::ExifTool::XMP::DecodeBase64($val)',
|
|
1942
1942
|
ValueConvInv => 'Image::ExifTool::XMP::EncodeBase64($val)',
|
|
1943
1943
|
},
|
|
1944
|
+
MotionPhoto => { Writable => 'integer' },
|
|
1945
|
+
MotionPhotoVersion => { Writable => 'integer' },
|
|
1946
|
+
MotionPhotoPresentationTimestampUs => { Writable => 'integer' },
|
|
1944
1947
|
);
|
|
1945
1948
|
|
|
1946
1949
|
# Google creations namespace (ref PH)
|
data/bin/lib/Image/ExifTool.pm
CHANGED
|
@@ -29,7 +29,7 @@ use vars qw($VERSION $RELEASE @ISA @EXPORT_OK %EXPORT_TAGS $AUTOLOAD @fileTypes
|
|
|
29
29
|
%jpegMarker %specialTags %fileTypeLookup $testLen $exeDir
|
|
30
30
|
%static_vars);
|
|
31
31
|
|
|
32
|
-
$VERSION = '12.
|
|
32
|
+
$VERSION = '12.83';
|
|
33
33
|
$RELEASE = '';
|
|
34
34
|
@ISA = qw(Exporter);
|
|
35
35
|
%EXPORT_TAGS = (
|
|
@@ -1118,6 +1118,7 @@ my @availableOptions = (
|
|
|
1118
1118
|
[ 'HexTagIDs', 0, 'use hex tag ID\'s in family 7 group names' ],
|
|
1119
1119
|
[ 'HtmlDump', 0, 'HTML dump (0-3, higher # = bigger limit)' ],
|
|
1120
1120
|
[ 'HtmlDumpBase', undef, 'base address for HTML dump' ],
|
|
1121
|
+
[ 'IgnoreGroups', undef, 'list of groups to ignore when extracting' ],
|
|
1121
1122
|
[ 'IgnoreMinorErrors',undef, 'ignore minor errors when reading/writing' ],
|
|
1122
1123
|
[ 'IgnoreTags', undef, 'list of tags to ignore when extracting' ],
|
|
1123
1124
|
[ 'ImageHashType', 'MD5', 'image hash algorithm' ],
|
|
@@ -1137,6 +1138,7 @@ my @availableOptions = (
|
|
|
1137
1138
|
[ 'NoPDFList', undef, 'flag to avoid splitting PDF List-type tag values' ],
|
|
1138
1139
|
[ 'NoWarning', undef, 'regular expression for warnings to suppress' ],
|
|
1139
1140
|
[ 'Password', undef, 'password for password-protected PDF documents' ],
|
|
1141
|
+
[ 'PrintCSV', undef, 'flag to print CSV directly (selected metadata types only)' ],
|
|
1140
1142
|
[ 'PrintConv', 1, 'flag to enable print conversion' ],
|
|
1141
1143
|
[ 'QuickTimeHandler', 1, 'flag to add mdir Handler to newly created Meta box' ],
|
|
1142
1144
|
[ 'QuickTimePad', undef, 'flag to preserve padding of QuickTime CR3 tags' ],
|
|
@@ -2035,8 +2037,8 @@ my %systemTagsNotes = (
|
|
|
2035
2037
|
}
|
|
2036
2038
|
return join(',', @args);
|
|
2037
2039
|
},
|
|
2038
|
-
},
|
|
2039
|
-
GeolocationBearing => { %geoInfo,
|
|
2040
|
+
},
|
|
2041
|
+
GeolocationBearing => { %geoInfo,
|
|
2040
2042
|
Notes => q{
|
|
2041
2043
|
compass bearing to GeolocationCity center. Geolocation tags are
|
|
2042
2044
|
generated only if API L<Geolocation|../ExifTool.html#Geolocation> option is set
|
|
@@ -2469,12 +2471,12 @@ sub Options($$;@)
|
|
|
2469
2471
|
} else {
|
|
2470
2472
|
$$options{$param} = undef; # clear the list
|
|
2471
2473
|
}
|
|
2472
|
-
} elsif ($param
|
|
2474
|
+
} elsif ($param =~ /^(IgnoreTags|IgnoreGroups)$/) {
|
|
2473
2475
|
if (defined $newVal) {
|
|
2474
2476
|
# parse list from delimited string if necessary
|
|
2475
|
-
my @ignoreList = (ref $newVal eq 'ARRAY') ? @$newVal : ($newVal =~ /[-\w
|
|
2476
|
-
ExpandShortcuts(\@ignoreList);
|
|
2477
|
-
# add to existing tags to ignore
|
|
2477
|
+
my @ignoreList = (ref $newVal eq 'ARRAY') ? @$newVal : ($newVal =~ /[-\w?*:#]+/g);
|
|
2478
|
+
ExpandShortcuts(\@ignoreList) if $param eq 'IgnoreTags';
|
|
2479
|
+
# add to existing tags/groups to ignore
|
|
2478
2480
|
$$options{$param} or $$options{$param} = { };
|
|
2479
2481
|
foreach (@ignoreList) {
|
|
2480
2482
|
/^(.*:)?([-\w?*]+)#?$/ or next;
|
|
@@ -2650,7 +2652,6 @@ sub ExtractInfo($;@)
|
|
|
2650
2652
|
$self->Options(Duplicates => 1) if $$options{HtmlDump};
|
|
2651
2653
|
# enable Validate option if Validate tag is requested
|
|
2652
2654
|
$self->Options(Validate => 1) if $$req{validate};
|
|
2653
|
-
|
|
2654
2655
|
if (defined $_[0]) {
|
|
2655
2656
|
# only initialize filename if called with arguments
|
|
2656
2657
|
$$self{FILENAME} = undef; # name of file (or '' if we didn't open it)
|
|
@@ -2659,6 +2660,11 @@ sub ExtractInfo($;@)
|
|
|
2659
2660
|
$self->ParseArguments(@_); # initialize from our arguments
|
|
2660
2661
|
}
|
|
2661
2662
|
}
|
|
2663
|
+
# ignore all tags and set ExtractEmbedded if outputting CSV directly
|
|
2664
|
+
if ($self->Options('PrintCSV')) {
|
|
2665
|
+
$$self{OPTIONS}{IgnoreTags} = { all => 1 };
|
|
2666
|
+
$self->Options(ExtractEmbedded => 1);
|
|
2667
|
+
}
|
|
2662
2668
|
# initialize ExifTool object members
|
|
2663
2669
|
$self->Init();
|
|
2664
2670
|
$$self{InExtract} = 1; # set flag indicating we are inside ExtractInfo
|
|
@@ -2839,6 +2845,7 @@ sub ExtractInfo($;@)
|
|
|
2839
2845
|
$self->FoundTag('FileTypeExtension', '');
|
|
2840
2846
|
$self->DoneExtract();
|
|
2841
2847
|
$raf->Close() if $raf;
|
|
2848
|
+
%saveOptions and $$self{OPTIONS} = \%saveOptions;
|
|
2842
2849
|
delete $$self{InExtract} unless $reEntry;
|
|
2843
2850
|
return 1;
|
|
2844
2851
|
}
|
|
@@ -3070,8 +3077,14 @@ sub ExtractInfo($;@)
|
|
|
3070
3077
|
# restore necessary members when exiting re-entrant code
|
|
3071
3078
|
$$self{$_} = $$reEntry{$_} foreach keys %$reEntry;
|
|
3072
3079
|
SetByteOrder($saveOrder);
|
|
3080
|
+
} else {
|
|
3081
|
+
# call cleanup routines if necessary
|
|
3082
|
+
if ($$self{Cleanup}) {
|
|
3083
|
+
&$_($self) foreach @{$$self{Cleanup}};
|
|
3084
|
+
delete $$self{Cleanup};
|
|
3085
|
+
}
|
|
3086
|
+
delete $$self{InExtract};
|
|
3073
3087
|
}
|
|
3074
|
-
delete $$self{InExtract} unless $reEntry;
|
|
3075
3088
|
|
|
3076
3089
|
# ($type may be undef without an Error when processing sub-documents)
|
|
3077
3090
|
return 0 if not defined $type or exists $$self{VALUE}{Error};
|
|
@@ -5273,6 +5286,16 @@ sub AUTOLOAD
|
|
|
5273
5286
|
return DoAutoLoad($AUTOLOAD, @_);
|
|
5274
5287
|
}
|
|
5275
5288
|
|
|
5289
|
+
#------------------------------------------------------------------------------
|
|
5290
|
+
# Add cleanup routine to call before returning from Extract
|
|
5291
|
+
# Inputs: 0) ExifTool ref, 1) code ref to routine with ExifTool ref as an argument
|
|
5292
|
+
sub AddCleanup($)
|
|
5293
|
+
{
|
|
5294
|
+
my ($self, $sub) = @_;
|
|
5295
|
+
$$self{Cleanup} or $$self{Cleanup} = [ ];
|
|
5296
|
+
push @{$$self{Cleanup}}, $sub;
|
|
5297
|
+
}
|
|
5298
|
+
|
|
5276
5299
|
#------------------------------------------------------------------------------
|
|
5277
5300
|
# Add warning tag
|
|
5278
5301
|
# Inputs: 0) ExifTool object reference, 1) warning message
|
|
@@ -8914,6 +8937,12 @@ sub FoundTag($$$;@)
|
|
|
8914
8937
|
}
|
|
8915
8938
|
$grps[0] or $grps[0] = $$self{SET_GROUP0};
|
|
8916
8939
|
$grps[1] or $grps[1] = $$self{SET_GROUP1};
|
|
8940
|
+
if ($$options{IgnoreGroups}) {
|
|
8941
|
+
foreach (0..1) {
|
|
8942
|
+
my $g = lc($grps[$_] || $$tagInfo{Groups}{$_} || $$tagInfo{Table}{GROUPS}{$_});
|
|
8943
|
+
return undef if $$options{IgnoreGroups}{$g} or $$options{IgnoreGroups}{"$_$g"};
|
|
8944
|
+
}
|
|
8945
|
+
}
|
|
8917
8946
|
my $valueHash = $$self{VALUE};
|
|
8918
8947
|
|
|
8919
8948
|
if ($$tagInfo{RawConv}) {
|