Effective Photo Manipulation

Image manipulation is a common tasks for web applications, usually centered around creating and managing thumbnails (of photos, PDFs, videos, whatever).  Photo manipulation is a subset of image manipulation, and has a couple aspects that differentiate it other types.

First and foremost, photo quality is of high importance.  Contrast this with creating a thumbnail of a PDF (especially a text-heavy one); there's no way you can be representative of the original's detail.  A photo's thumbnail, however, must be as representative as possible.  Unfortunately, photos are typically encoded as JPG files, which use a lossy compression algorithm, which means that every time you manipulate them in any way, you're reducing the quality.

Photos are also often subject to user-editing (cropping, annotating, etc.), and while this is commonly done with dedicated photo editing tools (installed on the user's computer), plenty of web apps do it too.  I'm not thinking Photoshop Web, here, I'm talking about your site's photo gallery software that lets you upload originals and rotate them so they're facing the right way.

Between these two things, you (the developer) can get stuck in a bind.  You need to be able to edit photos repeatedly, but at the same time maintain quality.  The trick is to only ever edit a photo once.  Seriously.

This is simpler than it sounds.  The trick is to start thinking about designing your app interms of operations (rotating) instead of states (rotated).

When you get your hands on the original image, put is somewhere safe.  That's the only image you're ever going to deal with.  When your user comes and rotates it, write the specifics of that operation to the database, and then take your original and run all the stored operations on it to create the "current" view.  Then when they crop it, write the operation to the database, and then take your original and run all the stored operations on it to create the "current" view.  You can see where I'm going here.

Same thing goes for thumbnails.  If you need a 150×150 thumbnail of a phote, don't take the "current" view and resize it, take the original, run all the stored operations on it, and tack on a "resize to 150×150″ at the end to create the thumbnail.

This works because you only run through the lossy compression once, so your generated views stay at a noticably higher quality than if you save after each operation.  It might not be apparenty in a 50×50 thumbnail, but if with two operations (rotate then crop) on a full-size image, the difference in quality by doing them together verses encoding in between is quite apparent.

Of course, you can't do this sort of processing on demand, so you have to store the results of the transformations.  The key is to never read those in to do the next step, always start from the original and play back all the manipulations in sequence.  This mechanism fits very nicely with the mod_rewrite-based caching mechanism I wrote about a couple days ago.  When a new operation is saved, wipe out all the cached versions of the photo and let them rebuild as needed.

This isn't a particularly revolutionary idea, and I know many photo tools (e.g. Picasa) do things this way, but I've found that it's worth the extra effort.  Obviously it's utility is predicated on having decent originals, but believe me, your users will notice.

One response to “Effective Photo Manipulation”

  1. andy matthews

    Great idea Barney. It looks like I'm going to be picking up a photo blog development for a friend of mine. He's a professional photographer and would definitely benefit from this sort of approach.