source: trunk/gsdl/perllib/plugins/ImagePlug.pm@ 2882

Last change on this file since 2882 was 2882, checked in by paynter, 22 years ago

Compensate for change to "convert" output (size data goes to STDERR
instead of STDOUT).

  • Property svn:keywords set to Author Date Id Revision
File size: 10.7 KB
RevLine 
[1733]1###########################################################################
2#
3# ImagePlug.pm -- simple text plugin
4# A component of the Greenstone digital library software
5# from the New Zealand Digital Library Project at the
6# University of Waikato, New Zealand.
7#
8# Copyright (C) 1999 New Zealand Digital Library Project
9#
10# This program is free software; you can redistribute it and/or modify
11# it under the terms of the GNU General Public License as published by
12# the Free Software Foundation; either version 2 of the License, or
13# (at your option) any later version.
14#
15# This program is distributed in the hope that it will be useful,
16# but WITHOUT ANY WARRANTY; without even the implied warranty of
17# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18# GNU General Public License for more details.
19#
20# You should have received a copy of the GNU General Public License
21# along with this program; if not, write to the Free Software
22# Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
23#
24###########################################################################
25
26package ImagePlug;
27
28use BasPlug;
29
30sub BEGIN {
31 @ISA = ('BasPlug');
32}
33
[1758]34
[2207]35sub print_usage {
[1744]36 my ($plugin_name) = @_;
37
[2207]38 print STDERR "
39 usage: plugin ImagePlug [options]
40
[2230]41 -noscaleup Don't scale up small images when making thumbnails
[2207]42
[2230]43 -thumbnailsize n Make thumbnails of size nxn
[2207]44
[2230]45 -thumbnailtype s Make thumbnails in format 's'
[2207]46
[2230]47 -screenviewsize n If set, makes an image of size n for screen display
48 and sets Screen, ScreenSize, ScrrenWidth and Screeneight
49 metadata. By default it is not set.
[2207]50
[2230]51 -screenviewtype s If -screenviewsize is set, this sets the screen display
52 image type. Defaults to jpg.
[2207]53
[2230]54 -convertto s Convert main inage to (gif|png|jpg)
55
56 -minimumsize n Ignore images smaller than n bytes
57
[2207]58"
[1744]59}
60
[1733]61sub new {
62 my ($class) = @_;
[1744]63 my $plugin_name = shift (@_);
[1733]64 my $self = new BasPlug ("ImagePlug", @_);
65
[1744]66 if (!parsargv::parse(\@_,
67 q^noscaleup^, \$self->{'noscaleup'},
68 q^converttotype/.*/^, \$self->{'converttotype'},
[2230]69 q^minimumsize/[0-9]*/100^, \$self->{'minimumsize'},
70
[1744]71 q^thumbnailsize/[0-9]*/100^, \$self->{'thumbnailsize'},
[2230]72 q^thumbnailtype/.*/gif^, \$self->{'thumbnailtype'},
73 q^screenviewsize/[0-9]*/0^, \$self->{'screenviewsize'},
74 q^screenviewtype/.*/jpg^, \$self->{'screenviewtype'},
[1744]75 "allow_extra_options")) {
76
[2207]77 print STDERR "\nImagePlug uses an incorrect option.\n";
78 print STDERR "Check your collect.cfg configuration file.\n";
79 &print_usage($plugin_name);
[1744]80 die "\n";
81 }
82
[1733]83 return bless $self, $class;
84}
85
86sub get_default_process_exp {
87 my $self = shift (@_);
88
[1758]89 return q^(?i)(\.jpe?g|\.gif|\.png|\.bmp|\.xbm|\.tif?f)$^;
[1733]90}
91
[2230]92
93# Create the thumbnail and screenview images, and discover the Image's
94# size, width, and height using the convert utility.
95
[1733]96sub run_convert {
97 my $self = shift (@_);
[2230]98 my $filename = shift (@_); # filename with full path
99 my $file = shift (@_); # filename without path
[1733]100 my $doc_obj = shift (@_);
[1744]101 my $section = $doc_obj->get_top_section();
[2230]102
103 my $verbosity = $self->{'verbosity'};
104 my $outhandle = $self->{'outhandle'};
[1733]105
[2230]106 # check the filename is okay
107 return 0 if ($file eq "" || $filename eq "");
108
[1758]109 if ($filename =~ m/ /) {
[2230]110 print $outhandle "ImagePlug: \"$filename\" contains a space. choking.\n";
111 return undef;
[1744]112 }
113
[1758]114 my $minimumsize = $self->{'minimumsize'};
[2230]115 if (defined $minimumsize && (-s $filename < $minimumsize)) {
116 print $outhandle "ImagePlug: \"$filename\" too small, skipping\n"
117 if ($verbosity > 1);
118 }
119
120
121 # Convert the image to a new type (if required).
[1744]122 my $converttotype = $self->{'converttotype'};
[2230]123 my $originalfilename = ""; # only set if we do a conversion
[1733]124 my $type = "unknown";
[1758]125
126 if ($converttotype ne "" && $filename =~ m/$converttotype$/) {
[2230]127
[1744]128 $originalfilename = $filename;
[2230]129 $filename = &util::get_tmp_filename() . ".$converttotype";
[1744]130 $self->{'tmp_filename'} = $filename;
[2230]131
[1744]132 my $command = "convert -verbose $originalfilename $filename";
[2230]133 print $outhandle "$command\n" if ($verbosity > 2);
134 my $result = '';
[1744]135 $result = `$command`;
[2230]136 print $outhandle "$result\n" if ($verbosity > 3);
137
[1744]138 $type = $converttotype;
[1733]139 }
[1744]140
[2230]141
142 # Make the thumbnail image
143 my $thumbnailsize = $self->{'thumbnailsize'} || 100;
144 my $thumbnailtype = $self->{'thumbnailtype'} || 'gif';
145
146 my $thumbnailfilename = &util::get_tmp_filename() . ".$thumbnailtype";
[1744]147 $self->{'tmp_filename2'} = $thumbnailfilename;
[1733]148
[2230]149 # Generate the thumbnail with convert
150 my $command = "convert -verbose -geometry $thumbnailsize"
151 . "x$thumbnailsize $filename $thumbnailfilename";
152 print $outhandle "$command\n" if ($verbosity > 2);
153 my $result = '';
[2882]154 $result = `$command 2>&1` ;
[2230]155 print $outhandle "$result\n" if ($verbosity > 3);
156
157 # Add the thumbnail as an associated file ...
158 if (-e "$thumbnailfilename") {
159 $doc_obj->associate_file("$thumbnailfilename", "thumbnail.$thumbnailtype",
160 "image/$thumbnailtype",$section);
161 $doc_obj->add_metadata ($section, "ThumbType", $thumbnailtype);
162 $doc_obj->add_metadata ($section, "Thumb", "thumbnail.$thumbnailtype");
163 }
164
165
166 # Extract Image metadata from convert output
[1758]167 if ($result =~ m/([0-9]+)x([0-9]+)=>([0-9]+)x([0-9]+)/) {
[2226]168 $doc_obj->add_metadata ($section, "ImageWidth", $1);
169 $doc_obj->add_metadata ($section, "ImageHeight", $2);
170 $doc_obj->add_metadata ($section, "ThumbWidth", $3);
171 $doc_obj->add_metadata ($section, "ThumbHeight", $4);
[1733]172 }
[1744]173
174 my $size = "unknown";
[1735]175 if ($result =~ m/^[^\n]* ([0-9]+)b/) {
176 $size = $1;
[2230]177 } elsif ($result =~ m/^[^\n]* ([0-9]+)kb/) {
[1735]178 $size = 1024 * $1;
179 }
[1744]180
181 if ($result =~ m/^[^\n]*JPE?G/i) {
[1735]182 $type = "jpeg";
[2230]183 } elsif ($result =~ m/^[^\n]*GIF/i) {
[1733]184 $type = "gif";
[2230]185 } elsif ($result =~ m/^[^\n]*PNG/i) {
[1733]186 $type = "png";
[2230]187 } elsif ($result =~ m/^[^\n]*TIF?F/i) {
[1733]188 $type = "tiff";
[2230]189 } elsif ($result =~ m/^[^\n]*BMP/i) {
[1744]190 $type = "bmp";
[2230]191 } elsif ($result =~ m/^[^\n]*XBM?F/i) {
[1758]192 $type = "xbm";
193 }
194
[1744]195 $doc_obj->add_metadata ($section, "ImageType", $type);
[1733]196 $doc_obj->add_metadata ($section, "Image", "$file");
[1744]197 $doc_obj->add_metadata ($section, "ImageSize", $size);
198
[2230]199 # Add the image as an associated file ...
[1744]200 $doc_obj->associate_file($filename,$file,"image/$type",$section);
201
[2230]202
203 # Make a screen-sized version of the picture if requested
204 if ($self->{'screenviewsize'}) {
205
206 my $screenviewsize = $self->{'screenviewsize'};
207 my $screenviewtype = $self->{'screenviewtype'} || 'jpeg';
208 my $screenviewfilename = &util::get_tmp_filename() . ".$screenviewtype";
209 $self->{'tmp_filename3'} = $screenviewfilename;
210
211 # make the screenview image
212 my $command = "convert -verbose -geometry $screenviewsize"
213 . "x$screenviewsize $filename $screenviewfilename";
214 print $outhandle "$command\n" if ($verbosity > 2);
215 my $result = "";
[2882]216 $result = `$command 2>&1` ;
[2230]217 print $outhandle "$result\n" if ($verbosity > 3);
218
219 # get screenview dimensions, size and type
220 if ($result =~ m/[0-9]+x[0-9]+=>([0-9]+)x([0-9]+)/) {
221 $doc_obj->add_metadata ($section, "ScreenWidth", $1);
222 $doc_obj->add_metadata ($section, "ScreenHeight", $2);
223 }
224
225 #add the screenview as an associated file ...
226 if (-e "$screenviewfilename") {
227 $doc_obj->associate_file("$screenviewfilename", "screenview.$screenviewtype",
228 "image/$screenviewtype",$section);
229 $doc_obj->add_metadata ($section, "ScreenType", $screenviewtype);
230 $doc_obj->add_metadata ($section, "Screen", "screenview.$screenviewtype");
231 } else {
232 print $outhandle "ImagePlug: couldn't find \"$screenviewfilename\"\n";
233 }
234 }
235
[1733]236 return $type;
[2230]237
238
[1733]239}
240
241
242# The ImagePlug read() function. This function does all the right things
243# to make general options work for a given plugin. It calls the process()
244# function which does all the work specific to a plugin (like the old
245# read functions used to do). Most plugins should define their own
246# process() function and let this read() function keep control.
247#
248# ImagePlug overrides read() because there is no need to read the actual
249# text of the file in, because the contents of the file is not text...
250#
251# Return number of files processed, undef if can't process
252# Note that $base_dir might be "" and that $file might
253# include directories
254
255sub read {
256 my $self = shift (@_);
257 my ($pluginfo, $base_dir, $file, $metadata, $processor, $maxdocs) = @_;
258
[2230]259 my $outhandle = $self->{'outhandle'};
260
[1733]261 my $filename = &util::filename_cat($base_dir, $file);
262 return 0 if $self->{'block_exp'} ne "" && $filename =~ /$self->{'block_exp'}/;
263 if ($filename !~ /$self->{'process_exp'}/ || !-f $filename) {
264 return undef;
265 }
[2230]266 print $outhandle "ImagePlug processing \"$filename\"\n"
[1758]267 if $self->{'verbosity'} > 1;
268
[2230]269 #if there's a leading directory name, eat it...
270 $file =~ s/^.*[\/\\]//;
[1733]271
272 # create a new document
273 my $doc_obj = new doc ($filename, "indexed_doc");
[2327]274 $doc_obj->set_OIDtype ($processor->{'OIDtype'});
275
[1733]276 #run convert to get the thumbnail and extract size and type info
[1758]277 my $result = run_convert($self, $filename, $file, $doc_obj);
[1744]278
[1758]279 if (!defined $result)
[1744]280 {
281 print "ImagePlug: couldn't process \"$filename\"\n";
282 return 0;
[1733]283 }
284
285 #create an empty text string so we don't break downstream plugins
[2226]286 my $text = "Dummy text to sidestep display bug.";
[1733]287
288 # include any metadata passed in from previous plugins
289 # note that this metadata is associated with the top level section
[1744]290 my $section = $doc_obj->get_top_section();
[1733]291 $self->extra_metadata ($doc_obj, $section, $metadata);
292
293 # do plugin specific processing of doc_obj
[2226]294 return undef unless defined ($self->process (\$text, $pluginfo, $base_dir,
295 $file, $metadata, $doc_obj));
[1733]296
297 # do any automatic metadata extraction
298 $self->auto_extract_metadata ($doc_obj);
299
300 # add an OID
301 $doc_obj->set_OID();
[2226]302 $doc_obj->add_text($section, $text);
[1733]303
304 # process the document
305 $processor->process($doc_obj);
306
[2230]307 # clean up temporary files - we do this here instead of in
308 # run_convert becuase associated files aren't actually copied
309 # until after process has been run.
[1744]310 if (defined $self->{'tmp_filename'} &&
311 -e $self->{'tmp_filename'}) {
[2230]312 &util::rm($self->{'tmp_filename'})
[1733]313 }
[1744]314 if (defined $self->{'tmp_filename2'} &&
315 -e $self->{'tmp_filename2'}) {
[2230]316 &util::rm($self->{'tmp_filename2'})
[1744]317 }
[2230]318 if (defined $self->{'tmp_filename3'} &&
319 -e $self->{'tmp_filename3'}) {
320 &util::rm($self->{'tmp_filename3'})
321 }
[1733]322
[2207]323 return 1;
[1733]324}
325
326# do plugin specific processing of doc_obj
327sub process {
328 my $self = shift (@_);
329 my ($textref, $pluginfo, $base_dir, $file, $metadata, $doc_obj) = @_;
330 my $outhandle = $self->{'outhandle'};
331
332 return 1;
333}
334
3351;
336
337
338
339
340
341
342
343
344
345
346
Note: See TracBrowser for help on using the repository browser.