multi_exiftool 0.18.1 → 0.19.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,363 +0,0 @@
1
- # Copied from https://exiftool.org/config.html
2
-
3
- #------------------------------------------------------------------------------
4
- # File: example.config
5
- #
6
- # Description: Example user configuration file for Image::ExifTool
7
- #
8
- # Notes: This example file shows how to define your own shortcuts and
9
- # add new EXIF, IPTC, XMP, PNG, MIE and Composite tags, as well
10
- # as how to specify preferred lenses for the LensID tag, and
11
- # define new file types and default ExifTool option values.
12
- #
13
- # Note that unknown tags may be extracted even if they aren't
14
- # defined, but tags must be defined to be written. Also note
15
- # that it is possible to override an existing tag definition
16
- # with a user-defined tag.
17
- #
18
- # To activate this file, rename it to ".ExifTool_config" and
19
- # place it in your home directory or the exiftool application
20
- # directory. (On Mac and some Windows systems this must be done
21
- # via the command line since the GUI's may not allow filenames to
22
- # begin with a dot. Use the "rename" command in Windows or "mv"
23
- # on the Mac.) This causes ExifTool to automatically load the
24
- # file when run. Your home directory is determined by the first
25
- # defined of the following environment variables:
26
- #
27
- # 1. EXIFTOOL_HOME
28
- # 2. HOME
29
- # 3. HOMEDRIVE + HOMEPATH
30
- # 4. (the current directory)
31
- #
32
- # Alternatively, the -config option of the exiftool application
33
- # may be used to load a specific configuration file (note that
34
- # this must be the first option on the command line):
35
- #
36
- # exiftool -config example.config ...
37
- #
38
- # This example file defines the following 16 new tags as well as
39
- # a number of Shortcut and Composite tags:
40
- #
41
- # 1. EXIF:NewEXIFTag
42
- # 2. GPS:GPSPitch
43
- # 3. GPS:GPSRoll
44
- # 4. IPTC:NewIPTCTag
45
- # 5. XMP-xmp:NewXMPxmpTag
46
- # 6. XMP-exif:GPSPitch
47
- # 7. XMP-exif:GPSRoll
48
- # 8. XMP-xxx:NewXMPxxxTag1
49
- # 9. XMP-xxx:NewXMPxxxTag2
50
- # 10. XMP-xxx:NewXMPxxxTag3
51
- # 11. XMP-xxx:NewXMPxxxStruct
52
- # 12. PNG:NewPngTag1
53
- # 13. PNG:NewPngTag2
54
- # 14. PNG:NewPngTag3
55
- # 15. MIE-Meta:NewMieTag1
56
- # 16. MIE-Test:NewMieTag2
57
- #
58
- # For detailed information on the definition of tag tables and
59
- # tag information hashes, see lib/Image/ExifTool/README.
60
- #------------------------------------------------------------------------------
61
-
62
- # Shortcut tags are used when extracting information to simplify
63
- # commonly used commands. They can be used to represent groups
64
- # of tags, or to provide an alias for a tag name.
65
- %Image::ExifTool::UserDefined::Shortcuts = (
66
- MyShortcut => ['exif:createdate','exposuretime','aperture'],
67
- MyAlias => 'FocalLengthIn35mmFormat',
68
- );
69
-
70
- # NOTE: All tag names used in the following tables are case sensitive.
71
-
72
- # The %Image::ExifTool::UserDefined hash defines new tags to be added
73
- # to existing tables.
74
- %Image::ExifTool::UserDefined = (
75
- # All EXIF tags are added to the Main table, and WriteGroup is used to
76
- # specify where the tag is written (default is ExifIFD if not specified):
77
- 'Image::ExifTool::Exif::Main' => {
78
- # Example 1. EXIF:NewEXIFTag
79
- 0xd000 => {
80
- Name => 'NewEXIFTag',
81
- Writable => 'int16u',
82
- WriteGroup => 'IFD0',
83
- },
84
- # add more user-defined EXIF tags here...
85
- },
86
- # the Geotag feature writes these additional GPS tags if available:
87
- 'Image::ExifTool::GPS::Main' => {
88
- # Example 2. GPS:GPSPitch
89
- 0xd000 => {
90
- Name => 'GPSPitch',
91
- Writable => 'rational64s',
92
- },
93
- # Example 3. GPS:GPSRoll
94
- 0xd001 => {
95
- Name => 'GPSRoll',
96
- Writable => 'rational64s',
97
- },
98
- },
99
- # IPTC tags are added to a specific record type (eg. application record):
100
- # (Note: IPTC tag ID's are limited to the range 0-255)
101
- 'Image::ExifTool::IPTC::ApplicationRecord' => {
102
- # Example 4. IPTC:NewIPTCTag
103
- 160 => {
104
- Name => 'NewIPTCTag',
105
- Format => 'string[0,16]',
106
- },
107
- # add more user-defined IPTC ApplicationRecord tags here...
108
- },
109
- # XMP tags may be added to existing namespaces:
110
- 'Image::ExifTool::XMP::xmp' => {
111
- # Example 5. XMP-xmp:NewXMPxmpTag
112
- NewXMPxmpTag => { Groups => { 2 => 'Author' } },
113
- # add more user-defined XMP-xmp tags here...
114
- },
115
- # special Geotag tags for XMP-exif:
116
- 'Image::ExifTool::XMP::exif' => {
117
- # Example 6. XMP-exif:GPSPitch
118
- GPSPitch => { Writable => 'rational', Groups => { 2 => 'Location' } },
119
- # Example 7. XMP-exif:GPSRoll
120
- GPSRoll => { Writable => 'rational', Groups => { 2 => 'Location' } },
121
- },
122
- # new XMP namespaces (eg. xxx) must be added to the Main XMP table:
123
- 'Image::ExifTool::XMP::Main' => {
124
- # namespace definition for examples 8 to 11
125
- xxx => { # <-- must be the same as the NAMESPACE prefix
126
- SubDirectory => {
127
- TagTable => 'Image::ExifTool::UserDefined::xxx',
128
- # (see the definition of this table below)
129
- },
130
- },
131
- # add more user-defined XMP namespaces here...
132
- },
133
- # new PNG tags are added to the PNG::TextualData table:
134
- 'Image::ExifTool::PNG::TextualData' => {
135
- # Example 12. PNG:NewPngTag1
136
- NewPngTag1 => { },
137
- # Example 13. PNG:NewPngTag2
138
- NewPngTag2 => { },
139
- # Example 14. PNG:NewPngTag3
140
- NewPngTag3 => { },
141
- },
142
- # add a new MIE tag (NewMieTag1) and group (MIE-Test) to MIE-Meta
143
- # (Note: MIE group names must NOT end with a number)
144
- 'Image::ExifTool::MIE::Meta' => {
145
- # Example 15. MIE-Meta:NewMieTag1
146
- NewMieTag1 => {
147
- Writable => 'rational64u',
148
- Units => [ 'cm', 'in' ],
149
- },
150
- # new MIE "Test" group for example 16
151
- Test => {
152
- SubDirectory => {
153
- TagTable => 'Image::ExifTool::UserDefined::MIETest',
154
- DirName => 'MIE-Test',
155
- },
156
- },
157
- },
158
- # Composite tags are added to the Composite table:
159
- 'Image::ExifTool::Composite' => {
160
- # Composite tags have values that are derived from the values of
161
- # other tags. The Require/Desire elements below specify constituent
162
- # tags that must/may exist, and the keys of these hashes are used as
163
- # indices in the @val array of the ValueConv expression to access the
164
- # numerical (-n) values of these tags. Print-converted values are
165
- # accessed via the @prt array. All Require'd tags must exist for
166
- # the Composite tag to be evaluated. If no Require'd tags are
167
- # specified, then at least one of the Desire'd tags must exist. See
168
- # the Composite table in Image::ExifTool::Exif for more examples,
169
- # and lib/Image/ExifTool/README for all of the details.
170
- MyBaseName => {
171
- Require => {
172
- 0 => 'FileName',
173
- },
174
- # remove the extension from FileName
175
- ValueConv => '$val[0] =~ /(.*)\./ ? $1 : $val[0]',
176
- },
177
- # the next few examples demonstrate simplifications which may be
178
- # used if only one tag is Require'd or Desire'd:
179
- # 1) the Require lookup may be replaced with a simple tag name
180
- # 2) "$val" may be used to represent "$val[0]" in the expression
181
- FileExtension => {
182
- Require => 'FileName',
183
- ValueConv => '$val=~/\.([^.]*)$/; $1',
184
- },
185
- # override CircleOfConfusion tag to use D/1750 instead of D/1440
186
- CircleOfConfusion => {
187
- Require => 'ScaleFactor35efl',
188
- Groups => { 2 => 'Camera' },
189
- ValueConv => 'sqrt(24*24+36*36) / ($val * 1750)',
190
- # an optional PrintConv may be used to format the value
191
- PrintConv => 'sprintf("%.3f mm",$val)',
192
- },
193
- # generate a description for this file type
194
- FileTypeDescription => {
195
- Require => 'FileType',
196
- ValueConv => 'GetFileType($val,1) || $val',
197
- },
198
- # calculate physical image size based on resolution
199
- PhysicalImageSize => {
200
- Require => {
201
- 0 => 'ImageWidth',
202
- 1 => 'ImageHeight',
203
- 2 => 'XResolution',
204
- 3 => 'YResolution',
205
- 4 => 'ResolutionUnit',
206
- },
207
- ValueConv => '$val[0]/$val[2] . " " . $val[1]/$val[3]',
208
- # (the @prt array contains print-formatted values)
209
- PrintConv => 'sprintf("%.1fx%.1f $prt[4]", split(" ",$val))',
210
- },
211
- # [advanced] select largest JPEG preview image
212
- BigImage => {
213
- Groups => { 2 => 'Preview' },
214
- Desire => {
215
- 0 => 'JpgFromRaw',
216
- 1 => 'PreviewImage',
217
- 2 => 'OtherImage',
218
- # (DNG and A100 ARW may be have 2 PreviewImage's)
219
- 3 => 'PreviewImage (1)',
220
- # (if the MPF has 2 previews, MPImage3 could be the larger one)
221
- 4 => 'MPImage3',
222
- },
223
- # ValueConv may also be a code reference
224
- # Inputs: 0) reference to list of values, 1) ExifTool object
225
- ValueConv => sub {
226
- my $val = shift;
227
- my ($image, $bigImage, $len, $bigLen);
228
- foreach $image (@$val) {
229
- next unless ref $image eq 'SCALAR';
230
- # check for JPEG image (or "Binary data" if -b not used)
231
- next unless $$image =~ /^(\xff\xd8\xff|Binary data (\d+))/;
232
- $len = $2 || length $$image; # get image length
233
- # save largest image
234
- next if defined $bigLen and $bigLen >= $len;
235
- $bigLen = $len;
236
- $bigImage = $image;
237
- }
238
- return $bigImage;
239
- },
240
- },
241
- # **** ADD ADDITIONAL COMPOSITE TAG DEFINITIONS HERE ****
242
- },
243
- );
244
-
245
- # This is a basic example of the definition for a new XMP namespace.
246
- # This table is referenced through a SubDirectory tag definition
247
- # in the %Image::ExifTool::UserDefined definition above.
248
- # The namespace prefix for these tags is 'xxx', which corresponds to
249
- # an ExifTool family 1 group name of 'XMP-xxx'.
250
- %Image::ExifTool::UserDefined::xxx = (
251
- GROUPS => { 0 => 'XMP', 1 => 'XMP-xxx', 2 => 'Image' },
252
- NAMESPACE => { 'xxx' => 'http://ns.myname.com/xxx/1.0/' },
253
- WRITABLE => 'string', # (default to string-type tags)
254
- # Example 8. XMP-xxx:NewXMPxxxTag1 (an alternate-language tag)
255
- # - replace "NewXMPxxxTag1" with your own tag name (eg. "MyTag")
256
- NewXMPxxxTag1 => { Writable => 'lang-alt' },
257
- # Example 9. XMP-xxx:NewXMPxxxTag2 (a string tag in the Author category)
258
- NewXMPxxxTag2 => { Groups => { 2 => 'Author' } },
259
- # Example 10. XMP-xxx:NewXMPxxxTag3 (an unordered List-type tag)
260
- NewXMPxxxTag3 => { List => 'Bag' },
261
- # Example 11. XMP-xxx:NewXMPxxxStruct (a structured tag)
262
- # - example structured XMP tag
263
- NewXMPxxxStruct => {
264
- # the "Struct" entry defines the structure fields
265
- Struct => {
266
- # optional namespace prefix and URI for structure fields
267
- # (required only if different than NAMESPACE above)
268
- # --> multiple entries may exist in this namespace lookup,
269
- # with the last one alphabetically being the default for
270
- # the fields, but each field may have a "Namespace"
271
- # element to specify which prefix to use
272
- NAMESPACE => { 'test' => 'http://x.y.z/test/' },
273
- # optional structure name (used for warning messages only)
274
- STRUCT_NAME => 'MyStruct',
275
- # optional rdf:type property for the structure
276
- TYPE => 'http://x.y.z/test/xystruct',
277
- # structure fields (very similar to tag definitions)
278
- X => { Writable => 'integer' },
279
- Y => { Writable => 'integer' },
280
- # a nested structure...
281
- Things => {
282
- List => 'Bag',
283
- Struct => {
284
- NAMESPACE => { thing => 'http://x.y.z/thing/' },
285
- What => { },
286
- Where => { },
287
- },
288
- },
289
- },
290
- List => 'Seq', # structures may also be elements of a list
291
- },
292
- # Each field in the structure has a corresponding flattened tag that is
293
- # generated automatically with an ID made from a concatenation of the
294
- # original structure tag ID and the field name (after capitalizing the
295
- # first letter of the field name if necessary). The Name and/or
296
- # Description of these flattened tags may be changed if desired, but all
297
- # other tag properties are taken from the structure field definition.
298
- # The "Flat" flag must be used when setting the Name or Description of a
299
- # flattened tag. For example:
300
- NewXMPxxxStructX => { Name => 'SomeOtherName', Flat => 1 },
301
- );
302
-
303
- # Adding a new MIE group requires a few extra definitions
304
- use Image::ExifTool::MIE;
305
- %Image::ExifTool::UserDefined::MIETest = (
306
- %Image::ExifTool::MIE::tableDefaults, # default MIE table entries
307
- GROUPS => { 0 => 'MIE', 1 => 'MIE-Test', 2 => 'Document' },
308
- WRITE_GROUP => 'MIE-Test',
309
- # Example 16. MIE-Test:NewMieTag2
310
- NewMieTag2 => { }, # new user-defined tag in MIE-Test group
311
- );
312
-
313
- # A special 'Lenses' list can be defined to give priority to specific lenses
314
- # in the logic to determine a lens model for the Composite:LensID tag
315
- @Image::ExifTool::UserDefined::Lenses = (
316
- 'Sigma AF 10-20mm F4-5.6 EX DC',
317
- 'Tokina AF193-2 19-35mm f/3.5-4.5',
318
- );
319
-
320
- # User-defined file types to recognize
321
- %Image::ExifTool::UserDefined::FileTypes = (
322
- XXX => { # <-- the extension of the new file type (case insensitive)
323
- # BaseType specifies the format upon which this file is based (case
324
- # sensitive). If BaseType is defined, then the file will be fully
325
- # supported, and in this case the Magic pattern should not be defined
326
- BaseType => 'TIFF',
327
- MIMEType => 'image/x-xxx',
328
- Description => 'My XXX file type',
329
- # if the BaseType is writable by ExifTool, then the new file type
330
- # will also be writable unless otherwise specified, like this:
331
- Writable => 0,
332
- },
333
- YYY => {
334
- # without BaseType, the file will be recognized but not supported
335
- Magic => '0123abcd', # regular expression to match at start of file
336
- MIMEType => 'application/test',
337
- Description => 'My YYY file type',
338
- },
339
- ZZZ => {
340
- # if neither BaseType nor Magic are defined, the file will be
341
- # recognized by extension only. MIMEType will be application/unknown
342
- # unless otherwise specified
343
- Description => 'My ZZZ file type',
344
- },
345
- # if only BaseType is specified, then the following simplified syntax
346
- # may be used. In this example, files with extension "TTT" will be
347
- # processed as JPEG files
348
- TTT => 'JPEG',
349
- );
350
-
351
- # Change default location for writing QuickTime tags so Keys is preferred
352
- # (by default, the PREFERRED levels are: ItemList=2, UserData=1, Keys=0)
353
- use Image::ExifTool::QuickTime;
354
- $Image::ExifTool::QuickTime::Keys{PREFERRED} = 3;
355
-
356
- # Specify default ExifTool option values
357
- # (see the Options function documentation for available options)
358
- %Image::ExifTool::UserDefined::Options = (
359
- CoordFormat => '%.6f', # change default GPS coordinate format
360
- Duplicates => 1, # make -a default for the exiftool app
361
- GeoMaxHDOP => 4, # ignore GPS fixes with HDOP > 4
362
- RequestAll => 3, # request additional tags not normally generated
363
- );
data/test/helper.rb DELETED
@@ -1,27 +0,0 @@
1
- # encoding: utf-8
2
- # frozen_string_literal: true
3
-
4
- require_relative '../lib/multi_exiftool'
5
- require 'contest'
6
- require 'fileutils'
7
- require 'test/unit'
8
- require 'tmpdir'
9
-
10
- module TestHelper
11
-
12
- DATA_FILES = Dir.glob(File.join(File.dirname(__FILE__), 'data/*'))
13
-
14
- def run_in_temp_dir &block
15
- Dir.mktmpdir do |tmpdir|
16
- FileUtils.cp_r DATA_FILES, tmpdir
17
- Dir.chdir tmpdir do
18
- block.call
19
- end
20
- end
21
- end
22
-
23
- end
24
-
25
- class Test::Unit::TestCase
26
- include TestHelper
27
- end
data/test/test_batch.rb DELETED
@@ -1,42 +0,0 @@
1
- # encoding: utf-8
2
- # frozen_string_literal: true
3
-
4
- require_relative 'helper'
5
-
6
- class TestBatch < Test::Unit::TestCase
7
-
8
- MANDATORY_WRITER_ARGS = MultiExiftool::Writer.mandatory_args
9
-
10
- context 'exiftool_args method' do
11
-
12
- setup do
13
- @filenames = %w(a.jpg b.jpg c.jpg)
14
- @multiple_values = @filenames.map do |filename|
15
- {author: 'janfri', comment: "Comment for file #{filename}"}
16
- end
17
- end
18
-
19
- test 'only filenames and values' do
20
- batch = MultiExiftool::Batch.new
21
- @filenames.zip @multiple_values do |filename, values|
22
- batch.write filename, values
23
- end
24
- exiftool_args = @filenames.zip(@multiple_values).map do |filename, values|
25
- [MANDATORY_WRITER_ARGS, '-author=janfri', "-comment=Comment for file #{filename}", filename, '-execute']
26
- end.flatten
27
- assert_equal exiftool_args, batch.exiftool_args
28
- end
29
-
30
- test 'filenames, values and options' do
31
- options = {overwrite_original: true}
32
- batch = MultiExiftool::Batch.new
33
- @filenames.zip @multiple_values do |filename, values|
34
- batch.write filename, values, options
35
- end
36
- exiftool_args = @filenames.zip(@multiple_values).map do |filename, _values|
37
- [MANDATORY_WRITER_ARGS, '-overwrite_original', '-author=janfri', "-comment=Comment for file #{filename}", filename, '-execute']
38
- end.flatten
39
- assert_equal exiftool_args, batch.exiftool_args
40
- end
41
- end
42
- end
@@ -1,26 +0,0 @@
1
- # encoding: utf-8
2
- # frozen_string_literal: true
3
-
4
- require_relative 'helper'
5
-
6
- class TestExecutable < Test::Unit::TestCase
7
-
8
- class Exec
9
- include MultiExiftool::Executable
10
- def initialize
11
- super
12
- end
13
- end
14
-
15
- setup do
16
- @executable = Exec.new
17
- end
18
-
19
- test 'appending to filenames' do
20
- @executable.filenames << 'a.jpg'
21
- assert_equal %w(a.jpg), @executable.filenames
22
- @executable.filenames << 'b.jpg'
23
- assert_equal %W(a.jpg b.jpg), @executable.filenames
24
- end
25
-
26
- end
@@ -1,37 +0,0 @@
1
- # encoding: utf-8
2
- # frozen_string_literal: true
3
-
4
- require_relative 'helper'
5
-
6
- class TestExiftoolStuff < Test::Unit::TestCase
7
-
8
- test 'setting exiftool_command resets exiftool_version' do
9
- MultiExiftool.exiftool_version # ensure @exiftool_version is set
10
- assert_not_nil MultiExiftool.instance_variable_get('@exiftool_version')
11
- MultiExiftool.exiftool_command = MultiExiftool.exiftool_command
12
- assert_nil MultiExiftool.instance_variable_get('@exiftool_version')
13
- end
14
-
15
- test 'attribute exiftool_version is cached' do
16
- MultiExiftool.instance_variable_set '@exiftool_version', nil
17
- t_org = time do
18
- v = MultiExiftool.exiftool_version
19
- assert_not_nil v
20
- end
21
- t_now = time do
22
- v = MultiExiftool.exiftool_version
23
- assert_not_nil v
24
- end
25
- assert t_now * 10 < t_org, 'access to cached version of attribute exiftool_version should be 10 times faster'
26
- end
27
-
28
- protected
29
-
30
- def time
31
- a = Time.now
32
- yield
33
- b = Time.now
34
- b - a
35
- end
36
-
37
- end