aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndy Shevchenko <andy@smile.org.ua>2006-10-06 11:54:08 +0000
committerAndy Shevchenko <andy@smile.org.ua>2006-10-06 11:54:08 +0000
commit03cc05032e79823648523bdd434d4f1b3d86a41b (patch)
tree29a13765f37f045b12b945d0a40877e76ae3aaa8
parent32b6758f8688e0aea2210eb335bd9be6c8c79ff8 (diff)
downloadrenrot-03cc05032e79823648523bdd434d4f1b3d86a41b.tar.gz
renrot-03cc05032e79823648523bdd434d4f1b3d86a41b.tar.bz2
Move main() to the end of file. Refactoring: configOptions -> cfgOpts.
Remove --color. Add 'use color' to configuration file ("use color = Yes" is default). Processing message look tunned, now it shows '(m of n)' file processed. Fix tag target in the Makefile. Possible fix bug with clearing EXIFs when --no-backup is given git-svn-id: file:///svnroot/renrot/branches/RENROT_STABLE@268 fe2816f4-e837-0410-b10a-f608c9d244a1
-rw-r--r--ChangeLog8
-rw-r--r--Makefile.PL2
-rw-r--r--README39
-rw-r--r--TODO10
-rw-r--r--etc/colors.conf3
-rw-r--r--etc/renrot.conf2
-rwxr-xr-xrenrot435
7 files changed, 263 insertions, 236 deletions
diff --git a/ChangeLog b/ChangeLog
index 1c46ef5..f8cb281 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,2 +1,9 @@
$Log$
+Revision 1.148.2.7 2006/10/06 11:54:08 andy
+Move main() to the end of file. Refactoring: configOptions -> cfgOpts.
+Remove --color. Add 'use color' to configuration file ("use color = Yes" is default).
+Processing message look tunned, now it shows '(m of n)' file processed.
+Fix tag target in the Makefile.
+Possible fix bug with clearing EXIFs when --no-backup is given
+
Revision 1.148.2.6 2006/09/02 19:03:17 andy
@@ -619,2 +626 @@ Revision 1.1 2005/10/17 13:39:38 zeus
ChangeLog file is added. Its the very begining.
-
diff --git a/Makefile.PL b/Makefile.PL
index 4579c16..9e3262e 100644
--- a/Makefile.PL
+++ b/Makefile.PL
@@ -24,3 +24,3 @@ rpm : tardist
tag :
- cvs tag "renrot_$(shell date +'%Y%m%d%H%M%S')"
+ $(PERLRUN) -e 'use POSIX qw(strftime); $$date = strftime("%Y%m%d%H%M%S", localtime()); system("cvs tag $(NAME)_$$date");'
END
diff --git a/README b/README
index a8d985f..05daca3 100644
--- a/README
+++ b/README
@@ -98,16 +98,22 @@ the script:
-RESTRICTIONS
-------------
+RESTRICTIONS AND BUGS
+------------ --- ----
+
+RenRot has some restrictions and known bugs at runtime.
+
+1. Script handles a whole directory without recursion and only with one
+extension of files.
+
+2. Algorithm treat each file with given extension as the image. Otherwise,
+file will be renamed to the current time stamp when --no-rename option is
+omitted.
-RenRot has some restrictions at runtime. First off, script handles a whole
-directory without recursion and only with one extension of files. Second,
-algorithm treat each file with given extension as the image. Otherwise, file
-will be renamed to the current time stamp when --no-rename option is omitted.
-Third, rename operation is not permited between different partitions due to
-hard link technology used (this will be avoided in future). Rotation process
-is available only on JPEG files.
+3. Rename operation is not permited between different partitions due to hard
+link technology used (this will be avoided in future).
-It seems that for Perl v.5.8.7 and 5.8.8, at least on FreeBSD 6 the bug, which
-cause crash of the renrot, exists. In case when total amount of the files size
-to process is bigger than RAM amount, the renrot falls with error:
+4. Rotation process is available only on JPEG files.
+
+5. It seems that for Perl v.5.8.7 and 5.8.8, at least on FreeBSD 6 the bug,
+which cause crash of the renrot, exists. In case when total amount of the
+files size to process is bigger than RAM amount, the renrot falls with error:
@@ -117,2 +123,11 @@ This doesn't occure for Perl v.5.6.1.
+6. Still no way to set the tags with the same name but located in the
+different groups.
+
+7. The colorization is started after the configuration files were parsed.
+While that is not happened the messages will be colorized by default color
+scheme.
+
+8. The colorization is not working under Windows platform.
+
diff --git a/TODO b/TODO
index 29b68b0..c96e996 100644
--- a/TODO
+++ b/TODO
@@ -9,2 +9,9 @@ q optional feature
+BUGS
+
+- fix cleaning EXIFs when --no-backup is given
+
+- make possible to use same EXIF tags in different groups
+
+
EXIF tags
@@ -47,2 +54,5 @@ User interface
+- to implement help output by topics (sole -h outputs list of topics like
+ rename,rotate,keyword e.t.c. and -h keyword outputs help for keyword related
+
diff --git a/etc/colors.conf b/etc/colors.conf
index 73297ce..2ac6e60 100644
--- a/etc/colors.conf
+++ b/etc/colors.conf
@@ -5,2 +5,5 @@
+# Use colorized output. This NOT works under Win32.
+#Use color = No
+
# Setup colors for different facilities
diff --git a/etc/renrot.conf b/etc/renrot.conf
index 3b564e7..9c478c0 100644
--- a/etc/renrot.conf
+++ b/etc/renrot.conf
@@ -77 +77,3 @@
+# Use colorized output (not works under MS Windows)
+#use color = Yes
diff --git a/renrot b/renrot
index 67f12f8..dab4ccc 100755
--- a/renrot
+++ b/renrot
@@ -59,3 +59,3 @@ if (defined %Image::ExifTool::UserDefined::RenRot) {
#
-my %configOptions = (
+my %cfgOpts = (
'aggregation delta' => 900,
@@ -72,4 +72,5 @@ my %configOptions = (
'trim' => 1,
+ 'use color' => 1,
'use ipc' => 0,
- );
+ );
@@ -86,3 +87,2 @@ my $aggrVirtDir; # directory name for virtual aggregation
my $backup = 1; # make or not a backup of the original files
-my %colorsFromCli; # colors are got from CLI
my $comfile; # file with commentary
@@ -188,2 +188,5 @@ my @multOpts = (
+my @files; # array of the sorted filenames to process
+my %filenameshash; # hash for old file names
+
########################################################################################
@@ -205,3 +208,3 @@ sub printColored {
- if (defined $useColor and $useColor != 0) {
+ if ($cfgOpts{'use color'} != 0) {
if (defined $facility and defined $colors{$facility}) {
@@ -219,3 +222,3 @@ sub procmsg {
- if (defined $useColor and $useColor != 0) {
+ if ($cfgOpts{'use color'} != 0) {
if (defined $colors{'process'}) {
@@ -291,3 +294,2 @@ sub getOptions {
my $showHelp = 0; # need help
- my @tmpColors;
my @tmpTags;
@@ -301,3 +303,2 @@ sub getOptions {
"backup!" => \$backup,
- "color=s" => \@tmpColors,
"comment-file=s" => \$comfile,
@@ -342,3 +343,2 @@ sub getOptions {
dbgmsg (3, " --backup: ", boolConv($backup), "\n");
- dbgmsg (3, " --color:\n", join("\n", @tmpColors), "\n") if (scalar(@tmpColors) > 0);
dbgmsg (3, " --comment-file: $comfile\n") if (defined $comfile);
@@ -397,10 +397,2 @@ sub getOptions {
- # Convert multiple color parameters to colors hash
- foreach my $colorStr (@tmpColors) {
- my %color = strToHash($colorStr, 'reset');
- foreach my $key (keys %color) {
- $colorsFromCli{$key} = $color{$key};
- }
- }
-
# Convert multiple tag parameters to tags hash
@@ -408,5 +400,3 @@ sub getOptions {
my %tag = strToHash($tagStr);
- foreach my $key (keys %tag) {
- $tagsFromCli{$key} = $tag{$key};
- }
+ map { $tagsFromCli{$_} = $tag{$_} } keys %tag;
}
@@ -521,5 +511,3 @@ sub parseConfigFile {
my %tmpConfig = getConfig($fc + 1, $file);
- foreach my $key (keys %tmpConfig) {
- $hConfig{$key} = $tmpConfig{$key};
- }
+ map { $hConfig{$_} = $tmpConfig{$_} } keys %tmpConfig;
}
@@ -558,5 +546,3 @@ sub parseConfig {
- foreach my $rcfile (@rcFiles) {
- %configOptions = parseConfigFile(0, $rcfile, %configOptions);
- }
+ map { %cfgOpts = parseConfigFile(0, $_, %cfgOpts) } @rcFiles;
}
@@ -595,154 +581,12 @@ sub dirValidator {
sub switchColor {
- dbgmsg (1, "Switch to user defined color scheme.\n");
-
# Parse configuration file color set
- foreach my $cKey (keys %configOptions) {
+ foreach my $cKey (keys %cfgOpts) {
next if ($cKey !~ m/^color#\d+#\d+$/); # skip not a color
- my %color = strToHash($configOptions{$cKey}, 'reset');
- foreach my $key (keys %color) {
- $colors{$key} = $color{$key};
- }
- }
-
- # Merge colors from configuration file with command line arguments
- map { $colors{$_} = $colorsFromCli{$_} } keys %colorsFromCli;
-}
-
-########################################################################################
-#
-# MAIN() renames and rotates given files
-#
-
-# parse command line options
-getOptions();
-
-parseConfig($configFile);
-
-switchColor();
-
-# redefining options set in configuration file with set via CLI ones
-$configOptions{'aggregation delta'} = $aggrDelta if (defined $aggrDelta);
-$configOptions{'aggregation directory'} = $aggrDir if (defined $aggrDir);
-$configOptions{'aggregation mode'} = $aggrMode if (defined $aggrMode);
-$configOptions{'aggregation template'} = $aggrTemplate if (defined $aggrTemplate);
-$configOptions{'aggregation virtual'} = $aggrVirtual if (defined $aggrVirtual);
-$configOptions{'aggregation virtual directory'} = $aggrVirtDir if (defined $aggrVirtDir);
-$configOptions{'keywordize'} = $keywordize if (defined $keywordize);
-$configOptions{'keywords file'} = $keywordsFile if (defined $keywordsFile);
-$configOptions{'keywords replace'} = $keywordsReplace if (defined $keywordsReplace);
-$configOptions{'mtime'} = $mtime if (defined $mtime);
-$configOptions{'name template'} = $nameTemplate if (defined $nameTemplate);
-$configOptions{'trim'} = $trim if (defined $trim);
-$configOptions{'use ipc'} = $useIPC if (defined $useIPC);
-
-dbgmsg (1, "main(): Show what would have been happened (no real actions).\n") if ($dryRun != 0);
-
-# Validate aggregation mode possible values
-if (not grep (/^$configOptions{'aggregation mode'}$/, ('none', 'delta', 'template'))) {
- warnmsg ("Aggregation mode isn't correct!\n");
-}
-
-$configOptions{'aggregation directory'} = dirConv($configOptions{'aggregation directory'});
-$configOptions{'aggregation virtual directory'} = dirConv($configOptions{'aggregation virtual directory'});
-
-fatalmsg ("Current or multilevel directory isn't possible now, sorry. Check aggregation arguments.\n"), die
- if ($configOptions{'aggregation mode'} ne "none" and
- (dirValidator($configOptions{'aggregation directory'}) == 0 or
- dirValidator($configOptions{'aggregation virtual directory'}) == 0));
-
-# Calculate ExifTool's verbosity
-my $exiftoolVerbose = ($verbose > $maxVerbosity) ? ($verbose - $maxVerbosity) : 0;
-
-# ExifTool object configuration
-my $exifTool = new Image::ExifTool;
-$exifTool->Options(Binary => 1, Unknown => 1, DateFormat => '%Y%m%d%H%M%S', Verbose => $exiftoolVerbose);
-
-my $file; # file in the directory
-my @files; # array of the sorted filenames to process
-my @filenames; # array of the filenames to process
-my $angleSuffix; # suffix to add to the end of the rotated files
-my $counterSize;
-my %filenameshash; # hash for old file names
-
-chdir ($workDir) || ( fatalmsg ("Can't enter to $workDir!\n"), die );
-
-# All things in ARGV will be treated as file names to process
-@files = @ARGV;
-
-# if no file is given
-if (scalar(@files) == 0) {
- opendir(DIR, "./") || ( fatalmsg ("Can't open $workDir!\n"), die );
- while ( defined ( $file = readdir DIR )) {
- next if (! -f $file); # skip absent file or not a file
- push (@files, $file) if (substr($file, length($file) - length($extToProcess)) eq $extToProcess);
+ my %color = strToHash($cfgOpts{$cKey}, 'reset');
+ map { $colors{$_} = $color{$_} } keys %color;
}
- closedir(DIR);
-}
-
-# independently of @files initialization doing this
-foreach $file ( @files ) {
- next if (! -f $file); # skip absent file or not a file
- next if (grep {/^$file$/} @excludeList); # skip excluded file
- push (@filenames, $file);
-}
-
-# No file to process?
-if (scalar(@filenames) == 0) {
- fatalmsg ("No files to process!\n");
- exit 1;
-}
-
-# Parse configuration file tag set
-foreach my $cKey (keys %configOptions) {
- next if ($cKey !~ m/^tag(file)?#\d+#\d+$/); # skip not a tag or tagfile
- my %tag = strToHash($configOptions{$cKey});
- foreach my $key (keys %tag) {
- $tags{$key} = $tag{$key};
- if ($cKey =~ m/^tagfile/) {
- dbgmsg (4, "main(): Read data from '$tags{$key}{value}' for '$key'\n");
- $tags{$key}{value} = getFileData($tags{$key}{value});
- }
- }
-}
-
-# Put command line arguments to appropriate tags
-$tags{'Comment'} = {value => getFileData($comfile)} if (defined $comfile);
-$tags{'UserComment'} = {value => $userComment} if (defined $userComment);
-# Merge tags from configuration file with command line arguments
-foreach my $key (keys %tagsFromCli) {
- $tags{$key} = $tagsFromCli{$key};
-}
-
-# Print parsed tags at debug level
-my @dbgTags;
-foreach my $key (sort (keys %tags)) {
- my $group = defined $tags{$key}{group} ? $tags{$key}{group} : "";
- my $value = defined $tags{$key}{value} ? $tags{$key}{value} : "";
- push (@dbgTags, "$key [$group] = $value");
-}
-dbgmsg (4, "Tags:\n", join("\n", @dbgTags), "\n") if (scalar(@dbgTags) > 0);
-
-# Preparing the variable, which contains the format of the counter output
-if ($countFF != 0) {
- my $size = length((scalar(@filenames) - 1) * $countStep + $countStart);
- $counterSize = "%." . $size . "d";
- dbgmsg (1, "main(): Counter size: $size (amount files in cache: ", scalar(@filenames), ")\n");
-} else {
- $counterSize = "%d";
-}
-
-# Validate angle value
-if ((defined $rotateAngle and not grep(/^$rotateAngle$/, keys %rotangles)) or
- (defined $rotateThumbnail and not grep(/^$rotateThumbnail$/, keys %rotangles))) {
- fatalmsg ("Angle should be 90, 180 or 270!\n");
- exit 1;
+ dbgmsg (1, "Switch to user defined color scheme.\n");
}
-@files = sort @filenames;
-dbgmsg (4, "main(): Pushed files(", scalar(@files), "):\n", join("\n", @files), "\n");
-
-renRotProcess();
-aggregationProcess();
-
########################################################################################
@@ -773,2 +617,4 @@ sub keywordizer {
sub renRotProcess {
+ my $exifToolObj = shift;
+ my $counterSize = shift;
my $fileCounter = $countStart; # file counter
@@ -779,5 +625,5 @@ sub renRotProcess {
- if ($configOptions{'keywordize'} != 0) {
- @keywordArr = keywordizer ($configOptions{'keywords file'});
- errmsg ("Keywords file doesn't exist!\n") if (not -e $configOptions{'keywords file'});
+ if ($cfgOpts{'keywordize'} != 0) {
+ @keywordArr = keywordizer ($cfgOpts{'keywords file'});
+ errmsg ("Keywords file doesn't exist!\n") if (not -e $cfgOpts{'keywords file'});
}
@@ -786,6 +632,6 @@ sub renRotProcess {
dbgmsg (2, "Keywords count: ", scalar(@keywordArr), "\n");
- if ($configOptions{'keywords replace'} != 0) {
- $exifTool->SetNewValue(Keywords => \@keywordArr);
+ if ($cfgOpts{'keywords replace'} != 0) {
+ $exifToolObj->SetNewValue(Keywords => \@keywordArr);
} else {
- $exifTool->SetNewValue(Keywords => \@keywordArr, AddValue => 1);
+ $exifToolObj->SetNewValue(Keywords => \@keywordArr, AddValue => 1);
}
@@ -794,3 +640,3 @@ sub renRotProcess {
# Convert trim boolean value to string
- my $trimStr = (not defined $configOptions{'trim'} or $configOptions{'trim'}) ? '-trim' : '';
+ my $trimStr = (not defined $cfgOpts{'trim'} or $cfgOpts{'trim'}) ? '-trim' : '';
dbgmsg (1, "renRotProcess(): Trim string: '$trimStr'\n");
@@ -799,3 +645,3 @@ sub renRotProcess {
foreach my $key (sort (keys %tags)) {
- $exifTool->SetNewValue($key, $tags{$key}{value}, Group => $tags{$key}{group});
+ $exifToolObj->SetNewValue($key, $tags{$key}{value}, Group => $tags{$key}{group});
}
@@ -805,19 +651,22 @@ sub renRotProcess {
+ my $file_num = scalar(@files);
+ my $file_rem = 0;
foreach my $file (@files) {
- procmsg ("Processing file: $file ...\n");
+ $file_rem++;
+ procmsg ("Processing file: ($file_rem of $file_num) $file ...\n");
# Setup defaults
- $info = $exifTool->ImageInfo($file);
+ $info = $exifToolObj->ImageInfo($file);
# analyzing whether to rotate
- $angleSuffix = rotateFile($exifTool, $info, $file, $trimStr);
+ my $angleSuffix = rotateFile($exifToolObj, $info, $file, $trimStr);
# analyzing whether and how to rename file
- $newFileName = renameFile($exifTool, $info, $file, $fileCounter);
+ $newFileName = renameFile($exifToolObj, $info, $file, $fileCounter, $counterSize, $angleSuffix);
# Writing tags.
- tagWriter($exifTool, $newFileName) if ($noTags == 0);
+ tagWriter($exifToolObj, $newFileName) if ($noTags == 0);
# seting mtime for the file if been asked for
- mtimeSet($exifTool, $info, $newFileName);
+ mtimeSet($exifToolObj, $info, $newFileName);
@@ -887,2 +736,4 @@ sub renameFile {
my $fileCounter = shift;
+ my $counterSize = shift;
+ my $angleSuffix = shift;
@@ -899,5 +750,7 @@ sub renameFile {
$tags{'RenRotFileNameOriginal'} = {value => $file, group => 'RenRot'};
- $exifTool->SetNewValue("RenRotFileNameOriginal",
- $tags{'RenRotFileNameOriginal'}{value},
- Group => $tags{'RenRotFileNameOriginal'}{group});
+ $exifToolObj->SetNewValue(
+ "RenRotFileNameOriginal",
+ $tags{'RenRotFileNameOriginal'}{value},
+ Group => $tags{'RenRotFileNameOriginal'}{group}
+ );
dbgmsg (2, "renameFile(): set RenRotFileNameOriginal to $file.\n");
@@ -912,5 +765,7 @@ sub renameFile {
$infoObj,
- $configOptions{'name template'},
+ $cfgOpts{'name template'},
$fileCounter,
- $file);
+ $file,
+ $counterSize,
+ $angleSuffix);
if ($filenameshash{$newFileName . $ext}) {
@@ -979,3 +834,3 @@ sub mtimeSet {
my $file = shift;
- if ($configOptions{'mtime'} != 0) {
+ if ($cfgOpts{'mtime'} != 0) {
my $mTime = getUnixTime(getTimestamp($exifToolObj, $infoObj));
@@ -1028,4 +883,6 @@ sub exifWriter {
sub aggregationProcess {
- return if ($configOptions{'aggregation mode'} eq "none");
+ return if ($cfgOpts{'aggregation mode'} eq "none");
+ my $exifToolObj = shift;
+ my $counterSize = shift;
my $file;
@@ -1033,2 +890,4 @@ sub aggregationProcess {
my $NewDir;
+ my $file_num = scalar(keys(%filenameshash));
+ my $file_rem = 0;
@@ -1037,4 +896,4 @@ sub aggregationProcess {
- if ($configOptions{'aggregation mode'} eq "template") {
- dbgmsg (1, "aggregationProcess(): Template: $configOptions{'aggregation template'}\n");
+ if ($cfgOpts{'aggregation mode'} eq "template") {
+ dbgmsg (1, "aggregationProcess(): Template: $cfgOpts{'aggregation template'}\n");
my $fileCounter = $countStart;
@@ -1042,15 +901,18 @@ sub aggregationProcess {
foreach $file (sort (keys %filenameshash)) {
- dbgmsg (4, "aggregationProcess(): Processing file: $file\n");
- $info = $exifTool->ImageInfo($file);
- $NewDir = template2name($exifTool,
+ $file_rem++;
+ dbgmsg (4, "aggregationProcess(): Processing ($file_rem of $file_num) file: $file\n");
+ $info = $exifToolObj->ImageInfo($file);
+ $NewDir = template2name($exifToolObj,
$info,
- $configOptions{'aggregation template'},
+ $cfgOpts{'aggregation template'},
$fileCounter,
- $file);
+ $file,
+ $counterSize,
+ "0cw");
aggregateFile($file, $NewDir) if ($dryRun == 0);
- procmsg ("Aggregate: $file -> $NewDir\n", "\n");
+ procmsg ("Aggregate: ($file_rem of $file_num) $file -> $NewDir\n", "\n");
$fileCounter += $countStep;
}
- } elsif ($configOptions{'aggregation mode'} eq "delta") {
+ } elsif ($cfgOpts{'aggregation mode'} eq "delta") {
my $DirCounter = 1;
@@ -1062,3 +924,4 @@ sub aggregationProcess {
$filetmp = $file;
- dbgmsg (4, "aggregationProcess(): Processing file: $file\n");
+ $file_rem++;
+ dbgmsg (4, "aggregationProcess(): Processing ($file_rem of $file_num) file: $file\n");
@@ -1067,3 +930,3 @@ sub aggregationProcess {
$filePrev = $filetmp;
- $NewDir = $configOptions{'aggregation directory'} . "." . sprintf($counterSize, $DirCounter);
+ $NewDir = $cfgOpts{'aggregation directory'} . "." . sprintf($counterSize, $DirCounter);
$DirCounter++;
@@ -1072,4 +935,4 @@ sub aggregationProcess {
# Check for new direcroty creation
- if (($filenameshash{$filetmp} - $timestampPrev) > $configOptions{'aggregation delta'}) {
- $NewDir = $configOptions{'aggregation directory'} . "." . sprintf($counterSize, $DirCounter);
+ if (($filenameshash{$filetmp} - $timestampPrev) > $cfgOpts{'aggregation delta'}) {
+ $NewDir = $cfgOpts{'aggregation directory'} . "." . sprintf($counterSize, $DirCounter);
$DirCounter++;
@@ -1079,6 +942,6 @@ sub aggregationProcess {
}
- procmsg ("Aggregate: $file -> $NewDir\n", "\n");
+ procmsg ("Aggregate: ($file_rem of $file_num) $file -> $NewDir\n", "\n");
}
} else {
- errmsg ("Aggregation mode $configOptions{'aggregation mode'} isn't implemented!\n");
+ errmsg ("Aggregation mode $cfgOpts{'aggregation mode'} isn't implemented!\n");
}
@@ -1105,3 +968,3 @@ sub aggregateFile {
- if ($configOptions{'aggregation virtual'} == 0) {
+ if ($cfgOpts{'aggregation virtual'} == 0) {
makeDir($NewDir);
@@ -1110,4 +973,4 @@ sub aggregateFile {
} else {
- makeDir($configOptions{'aggregation virtual directory'});
- $NewDir = $configOptions{'aggregation virtual directory'} . "/" . $NewDir;
+ makeDir($cfgOpts{'aggregation virtual directory'});
+ $NewDir = $cfgOpts{'aggregation virtual directory'} . "/" . $NewDir;
makeDir($NewDir);
@@ -1248,2 +1111,8 @@ sub rotateImg {
+ # preparing to write tags to the just rotated file
+ my $exifAfterRot = new Image::ExifTool;
+ $exifAfterRot->Options(Binary => 1);
+ $exifAfterRot->SetNewValuesFromFile($oldfile, '*:*');
+ $exifAfterRot->SetNewValue("Orientation", 1, Type => 'ValueConv');
+
if ($backup != 0) {
@@ -1253,8 +1122,2 @@ sub rotateImg {
- # preparing to write Orientation tag to the just rotated file
- my $exifAfterRot = new Image::ExifTool;
- $exifAfterRot->Options(Binary => 1);
- $exifAfterRot->SetNewValuesFromFile($origfile, '*:*');
- $exifAfterRot->SetNewValue("Orientation", 1, Type => 'ValueConv');
-
# writing the changes to the EXIFs
@@ -1297,3 +1160,3 @@ sub rotateThumbnail {
- if ($configOptions{'use ipc'} == 0) {
+ if ($cfgOpts{'use ipc'} == 0) {
# extracting the thumbnail image
@@ -1408,3 +1271,2 @@ Colorizing options:
--use-color (*) colorized output
- --color <COLOR> ... setup color(s)
@@ -1431,2 +1293,4 @@ sub template2name {
my $fileName = shift; # file name for %n and %e
+ my $counterSize = shift;
+ my $angleSuffix = shift;# suffix to add to the end of the rotated files
my ($base, $ext); # file name %n and extension %e
@@ -1535,2 +1399,133 @@ sub template2name {
+########################################################################################
+#
+# MAIN() renames and rotates given files
+#
+
+getOptions();
+parseConfig($configFile);
+switchColor();
+
+# redefining options set in configuration file with set via CLI ones
+$cfgOpts{'aggregation delta'} = $aggrDelta if (defined $aggrDelta);
+$cfgOpts{'aggregation directory'} = $aggrDir if (defined $aggrDir);
+$cfgOpts{'aggregation mode'} = $aggrMode if (defined $aggrMode);
+$cfgOpts{'aggregation template'} = $aggrTemplate if (defined $aggrTemplate);
+$cfgOpts{'aggregation virtual'} = $aggrVirtual if (defined $aggrVirtual);
+$cfgOpts{'aggregation virtual directory'} = $aggrVirtDir if (defined $aggrVirtDir);
+$cfgOpts{'keywordize'} = $keywordize if (defined $keywordize);
+$cfgOpts{'keywords file'} = $keywordsFile if (defined $keywordsFile);
+$cfgOpts{'keywords replace'} = $keywordsReplace if (defined $keywordsReplace);
+$cfgOpts{'mtime'} = $mtime if (defined $mtime);
+$cfgOpts{'name template'} = $nameTemplate if (defined $nameTemplate);
+$cfgOpts{'trim'} = $trim if (defined $trim);
+$cfgOpts{'use color'} = $useColor if (defined $useColor);
+$cfgOpts{'use ipc'} = $useIPC if (defined $useIPC);
+
+dbgmsg (1, "main(): Show what would have been happened (no real actions).\n") if ($dryRun != 0);
+
+# Validate aggregation mode possible values
+if (not grep (/^$cfgOpts{'aggregation mode'}$/, ('none', 'delta', 'template'))) {
+ warnmsg ("Aggregation mode isn't correct!\n");
+}
+
+$cfgOpts{'aggregation directory'} = dirConv($cfgOpts{'aggregation directory'});
+$cfgOpts{'aggregation virtual directory'} = dirConv($cfgOpts{'aggregation virtual directory'});
+
+fatalmsg ("Current or multilevel directory isn't possible now, sorry. Check aggregation arguments.\n"), die
+ if ($cfgOpts{'aggregation mode'} ne "none" and
+ (dirValidator($cfgOpts{'aggregation directory'}) == 0 or
+ dirValidator($cfgOpts{'aggregation virtual directory'}) == 0));
+
+# Calculate ExifTool's verbosity
+my $exiftoolVerbose = ($verbose > $maxVerbosity) ? ($verbose - $maxVerbosity) : 0;
+
+# ExifTool object configuration
+my $exifTool = new Image::ExifTool;
+$exifTool->Options(Binary => 1, Unknown => 1, DateFormat => '%Y%m%d%H%M%S', Verbose => $exiftoolVerbose);
+
+chdir ($workDir) || ( fatalmsg ("Can't enter to $workDir!\n"), die );
+
+# All things in ARGV will be treated as file names to process
+@files = @ARGV;
+
+# if no file is given
+if (scalar(@files) == 0) {
+ opendir(DIR, "./") || ( fatalmsg ("Can't open $workDir!\n"), die );
+ my $file;
+ while ( defined ( $file = readdir DIR )) {
+ next if (not -f $file); # skip absent file or not a file
+ push (@files, $file) if (substr($file, length($file) - length($extToProcess)) eq $extToProcess);
+ }
+ closedir(DIR);
+}
+
+# independently of @files initialization doing this
+my @filenames;
+
+foreach my $file ( @files ) {
+ next if (not -f $file); # skip absent file or not a file
+ next if (grep {/^$file$/} @excludeList); # skip excluded file
+ push (@filenames, $file);
+}
+
+# No file to process?
+if (scalar(@filenames) == 0) {
+ fatalmsg ("No files to process!\n");
+ exit 1;
+}
+
+# Parse configuration file tag set
+foreach my $cKey (keys %cfgOpts) {
+ next if ($cKey !~ m/^tag(file)?#\d+#\d+$/); # skip not a tag or tagfile
+ my %tag = strToHash($cfgOpts{$cKey});
+ foreach my $key (keys %tag) {
+ $tags{$key} = $tag{$key};
+ if ($cKey =~ m/^tagfile/) {
+ dbgmsg (4, "main(): Read data from '$tags{$key}{value}' for '$key'\n");
+ $tags{$key}{value} = getFileData($tags{$key}{value});
+ }
+ }
+}
+
+# Put command line arguments to appropriate tags
+$tags{'Comment'} = {value => getFileData($comfile)} if (defined $comfile);
+$tags{'UserComment'} = {value => $userComment} if (defined $userComment);
+
+# Merge tags from configuration file with command line arguments
+map { $tags{$_} = $tagsFromCli{$_} } keys %tagsFromCli;
+
+# Print parsed tags at debug level
+my @dbgTags;
+foreach my $key (sort (keys %tags)) {
+ my $group = defined $tags{$key}{group} ? $tags{$key}{group} : "";
+ my $value = defined $tags{$key}{value} ? $tags{$key}{value} : "";
+ push (@dbgTags, "$key [$group] = $value");
+}
+dbgmsg (4, "Tags:\n", join("\n", @dbgTags), "\n") if (scalar(@dbgTags) > 0);
+
+# Validate angle value
+if ((defined $rotateAngle and not grep(/^$rotateAngle$/, keys %rotangles)) or
+ (defined $rotateThumbnail and not grep(/^$rotateThumbnail$/, keys %rotangles))) {
+ fatalmsg ("Angle should be 90, 180 or 270!\n");
+ exit 1;
+}
+
+@files = sort @filenames;
+dbgmsg (4, "main(): Pushed files(", scalar(@files), "):\n", join("\n", @files), "\n");
+
+# Preparing the variable, which contains the format of the counter output
+my $counterSize;
+
+if ($countFF != 0) {
+ my $size = length((scalar(@filenames) - 1) * $countStep + $countStart);
+ $counterSize = "%." . $size . "d";
+ dbgmsg (1, "main(): Counter size: $size (amount files in cache: ", scalar(@filenames), ")\n");
+} else {
+ $counterSize = "%d";
+}
+
+renRotProcess($exifTool, $counterSize);
+aggregationProcess($exifTool, $counterSize);
+
__END__
@@ -1788,6 +1783,2 @@ colorized output. This NOT works under Win32.
-=item B<--color> I<COLOR>
-
-setup color for choosen facility
-
=item B<--dry-run>

Return to:

Send suggestions and report system problems to the System administrator.