# Album Plugin: utils/mv # For info: 'album -plugin_info utils/mv' # For usage: 'album -plugin_usage utils/mv' use strict; my $DESC = < DESC sub usage { my $opt = shift @_; foreach my $msg (@_) { print STDERR "ERROR: $msg\n"; } print STDERR <{PROGNAME} -mv [-gen] $DESC USAGE exit -1; } sub start_plugin { my ($opt,$plugin,$path) = @_; # We actually do this code during -list_plugins and shouldn't, but # right now it doesn't seem to matter. $opt->{mv}{dest} = pop @ARGV; while (my $arg = shift @ARGV) { if ($arg eq "-h") { usage(); } if ($arg eq "-gen") { $opt->{mv}{gen} = 1; next; } push(@{$opt->{mv}{src}}, $arg); } album::add_album_dir($opt, $opt->{mv}{dest}) if $opt->{mv}{gen}; # Don't save the confs if we generate. $opt->{save_conf} = 0; album::hook($opt,'pre_do_albums', \&album_mv); return { author => 'David Ljung Madison', href => 'http://MarginalHacks.com/', version => '1.0', description => $DESC." You can view usage with: % $opt->{PROGNAME} -mv -h", }; } # This should probably be in album (as well as the cache!) my %ALBUM_INFO; # Cache sub album_info { my ($opt,$dir) = @_; unless ($ALBUM_INFO{$dir}) { my $data = album::new_album_data($opt,$dir); album::gather_contents($opt, $data); album::get_captions($opt,$data); album::sort_info($opt,$data); $ALBUM_INFO{$dir} = $data; } return $ALBUM_INFO{$dir}; } sub img_mv { my ($opt, $dir, $img, $dest) = @_; # Move the image rename("$dir/$img","$dest/$img"); # Move the .postfix files foreach my $post (".txt", $opt->{no_album}, $opt->{hide_album}, $opt->{not_img}) { rename("$dir/$img$post","$dest/$img$post"); } # Move the medium/thumbnails my $pre = ($img =~ /^(.+)\.[^\.]+$/) ? $1 : $img; # A bit of a kludge, but we have no easy way to determine # the thumbnail and medium files without either generating # them or else duplicating album code. Will only cause problems # if the album has images like: image.gif and image.hi.gif opendir(TN,"$dir/$opt->{dir}") || return; my @tn = grep(!/^\.{1,2}$/, readdir TN); closedir TN; foreach my $tn ( @tn ) { rename("$dir/$opt->{dir}/$tn", "$dest/$opt->{dir}/$tn") if $tn =~ /^\Q$pre.\E/; } } sub album_mv { my ($opt) = @_; # Check destination my $dest = $opt->{mv}{dest}; usage($opt,"Last argument to -mv must be a destination directory") unless -d $dest; $dest =~ s|/+$||; mkdir("$dest/$opt->{dir}"); # In case it's a new directory. usage($opt,"No files specified for -mv") unless $opt->{mv}{src}; # For each source: my @src = @{$opt->{mv}{src}}; my @gen; while (my $src = shift @src) { usage($opt,"Unknown file to -mv: $src") unless -f $src; my ($dir,@imgs) = album::split_path($opt, $src); push(@gen,$dir); # Find all the files with the same directory so we can move # them in bulk - that way we not only edit the captions.txt once, # but we keep them in order. my @nomatch; foreach my $src2 ( @src ) { my ($dir2,$img2) = album::split_path($opt, $src2); ($dir eq $dir2) ? push(@imgs, $img2) : push(@nomatch, $src2); } @src = @nomatch; # Get the album info. print "Moving from $dir:\n"; my $data = album_info($opt, $dir); foreach my $img ( @imgs ) { print " $img\n"; img_mv($opt,$dir,$img,$dest); } # Update captions.txt if (open(CAP, "<$dir/$opt->{captions}")) { my (@new, @old); while () { # Any plugins that alter the way the first column of captions.txt # might not properly move captions over. Worst case scenario is # that they get left behind. This code is basically stolen from album: my $split_tabs = /\t/ ? 1 : 0; my ($file) = $split_tabs ? split(/\t+/, $_) : split(/\s*::\s*/, $_); $file =~ s/\s$//; # In case it needed to be chomped $file =~ s/^#//; # We move commented out files as well (grep($file eq $_, @imgs)) ? push(@new, $_) : push(@old, $_); } close CAP; # If we fail, perhaps we should move images back? Bah. usage("Can't write destination captions: $dest/$opt->{captions}") unless open(CAP, ">>$dest/$opt->{captions}"); print CAP @new; close CAP; usage("Can't write old captions: $dir/$opt->{captions}") unless open(CAP, ">$dir/$opt->{captions}"); print CAP @old; close CAP; } } # Are we done? album::done() unless $opt->{mv}{gen}; # Done moving! Now regenerate all the albums! $opt->{depth} = 1; map { album::add_album_dir($opt, $_) } @gen; } # Plugins always end with: 1;