Make Friends With ImageMagick
Like many artists, my wife Luann has increasingly been using the Web to showcase her work. When we first launched her site, we had just a handful of scanned images to work with, and it was straightforward to incorporate them into her pages. Recently, she's been having her work photographed professionally, and accumulating CDs full of images she wants to present on the Web. At the same time, I've taken a lot of pictures with my digital camera, an Olympus D-460, and have posted some of these on the Web.
All this photo activity has required me to think about how to manage images on the Web, and to find ways to automate things that were formerly manual chores: producing thumbnails, linking them to their enlargements, framing and titling the images. I'll share some techniques here partly because they may be useful to you, and partly because they may prompt you to share related techniques with me -- preferably, by way of my newsgroup.
For the first incarnation of my wife's site, I used scanned images. This was feasible because Luann's work -- jewelry and decorative wall hangings -- generally lies flat, and doesn't spill over the edges my flatbed scanner. During this era, I made heavy use of the retouching software that came with the scanner, Kai's PhotoSoap. Because the jewelry wasn't really flat, the scanner often produced shadows and defects that needed to be cleaned up. Sporting the same radical interface that first wowed me when I saw Kai's Power Tools, PhotoSoap is an amazing piece of software with a deep feature set that I'll probably never fully plumb.
What PhotoSoap isn't, though -- at least in my Windows version of the product -- is scriptable. And when you start dealing with more than a handful of images, fixing up lousy scans quickly becomes a huge waste of time. The same holds true for digital pictures. In theory, my wife doesn't need to use a professional photographer for her work. She could photograph everything herself with the digital camera. In practice, there's more to it than meets the eye. The 1.3-megapixel limit of my Olympus D-460 isn't even really the bottleneck, I don't think, since that's plenty of resolution for the Web.
It's the lighting that really matters: both the equipment, and the know-how. So Luann hires a pro (Jeff Baird, in Brattleboro, VT), and he produces CD-ROMs full of images that don't really need any retouching. What they do need is conversion, into pairs of thumbnails and enlargements suitable for Web display. Somebody mentioned ImageMagick in one of my newsgroups long ago. It's a remarkable open source product that I can now, after just a few weeks, no longer imagine not having. It's available in source and binary form for many systems, including Windows and Linux, and I use it on both of these. It's really a suite of programs sharing a set of core libraries. One of these, display, requires X and so runs most conveniently on Unix/Linux. It's an interactive image editor that you can use to view, crop, resize, color-adjust, and otherwise mangle your images.
Windows users who may be avoiding ImageMagick because of its X orientation: don't worry. Capabilities similar to ImageMagick's display are included in the software bundled with most scanners and digital cameras. What's you won't get, but what ImageMagick provides, are the command-line-driven tools convert, mogrify, and montage. And these run just as happily on the Windows command line as the Unix command line.
Here's an example from a documentation project I recently worked on. In this
case, my source images were Windows .BMP files -- screenshots that I'd used
Windows Paint to crop. (Paint never has learned to save as GIF or JPG, a
deficiency that ImageMagick corrects.) Given a set of files named Help_01.bmp,
Help_02.bmp, etc., I invoked a
for %f in (Help_01 Help_02 Help_03 Help_04) do process %f
Here's the command file:
1 copy %1.bmp s_%1.bmp
Line one copies the image to the same filename prefixed with "s_" -- that's my convention for naming thumbnails.
Line two reads the thumbnail BMP and writes out an equivalent JPG. In this case, the image is a screenshot, and the text isn't going to be readable no matter what format is used. So JPG compression is indicated, to ensure quick loading of the many thumbnails that will appear in the help file.
Line three transforms the "s_" version of the image, in place, to a thumbnail-sized image that's at most 200 pixels wide or high.
Line four reads the full-sized BMP and writes an equivalent GIF.
Line five transforms the full-sized GIF, in place, adding a 2-pixel black border.
Back when I ran the Byte Magazine website, my associate Joy Blake used Debabelizer to do these chores. It's a great program too, and probably does some things better than ImageMagick does. For $400, it should. But Debabelizer's built-in scripting, while incredibly useful, doesn't offer the ultimate flexibility of ImageMagick's command-line-driven tools. Managing collections of images comes down to managing namespaces. For that, I tend to favor Perl, which I use to automate the writing of command files that use the ImageMagick tools.
function openWindow ( doc, win, width, height, title )
This routine expects the absolute width and height of the image. It adds 20 pixels to each dimension for two reasons. First, I've found that Netscape displays a lone image awkwardly without some extra padding around it. Second, the padding can be used to frame the image.
Rather than just display the raw image, the routine writes an HTML wrapper for it -- a table, with a black background and a border. True, you could use ImageMagick to produce these effects, but I like the HTML effect, and changing it doesn't require any image reprocessing.
The routine also expects a title, and we'll want to use a meaningful title, not just a numeric image name. All in all, calls to this routine need to marshall a fair amount of information. Here's an example from Luann's jewelry page:
The names and dimensions of the thumbnail and enlargement.
Text for the ALT tag, and for the pop-up window's title.
This strategy lets me focus on the macro-design of the page that will contain and describe the images.
Next, I capture the essential information about each image -- in this case, the filename, a description, and a price -- in a little database. A Perl hashtable does this handily:
my $images =
Now, templatize the HTML chunk that you want to substitute for each placeholder:
my $template = <<"EOT";
Finally, read the layout file and replace the markers with HTML chunks:
open (F, "jewelry.tmpl") or die $!;
The jpegsize routine, which I found at htp://www.nihongo.org/snowhare/utilities/, extracts the dimensions of both images.
There's nothing revolutionary here, but it all adds up to a huge productivity boost. As a result, it's feasible to include niceties -- like descriptive titles for pop-up windows -- which would otherwise require way too much time and effort. The underlying pattern of templates and substitution, used here at two levels (the main page and each image chunk), is one that I find endlessly useful.
Byte Newsgroups:Join Jon and the others in various, ongoing discussions in the newsgroups.
Jon Udell (http://udell.roninhouse.com/) was Byte Magazine's executive editor for new media, the architect of the original www.byte.com, and author of Byte's Web Project column. He's now an independent Web/Internet consultant, and is the author of Practical Internet Groupware, from O'Reilly and Associates.
Here's what Willem van Schaik
I liked the pop-up window method Jon developed for his wife's Web pages. But
This was, of course, easily fixed by replacing the "width += 20" with an
If you want to see the result, give it a try at:
(It also shows some cool satellite images.)
The script now becomes:
and to use this in your HTML code:
Here, you should replace everything in the form of imgXxxxx, and, of
Just my $0.02. I hope it is useful to some people,
Questions or problems regarding this web site should be directed to firstname.lastname@example.org.
Copyright © 2008 Art Beckman. All rights reserved.
Last Modified: March 9, 2008