Jacob Mulquin

Simple Perl Image Gallery Generator (spigg)

No bells or whistles

✍️ Jacob Mulquin
📅 22/01/2022

My wife gave birth to a beautiful baby boy last week. Neither my wife or I had newborn photoshoots when we were babies so this is something we wanted to do for our children.

We went to the wonderful Silke at Love and Dream Photography to have our photos taken. She advised us of a 2 week turn-around for photo editing but to our delight, she had sent us the set the very next day. We highly recommend her services, excellent value!

In order to show our family in our sons' Facebook group, I needed to generate a gallery for them to view. Well, we could have just uploaded them all directly to the group and let Facebook take care of the thumbnailing, but where's the fun in that??

Let's be masochistic and do this in Perl, even though I'm terrible at the language. What could possibly go wrong?

Now there are literally bajillions of scripts out there to generate static image galleries but I want one with no bells or whistles at all. I want this gallery to make no sound what-so-ever; I'm not interested in displaying EXIF and I'm not interested in captions or comments. I just want a series of thumbnails on a single page that link to fullsize pictures.

Here's how I envision the flow of the program:

  1. Take in a directory as a script argument, defaulting to current directory
  2. Iterate through the directory looking for image files
  3. Generate thumbnail files and save into thumbnail directory
  4. Append a HTML string and save it into index.html

Surprisingly, it only took a couple hours to hack together something bareful functional. What possibly could have went wrong just... Didn't. Still, I stand alert and full of suspicion.

Here is the code in it's entirety:

#!/usr/bin/perl
use strict;
use warnings;
use 5.010;

my $directory;
if (@ARGV && -e $ARGV[0]) {
    $directory = $ARGV[0];
    $directory .= '/' if $directory !~ m|/$|; # Add trailing slash
} else {
    $directory = './';
}
my $thumbs_directory = $directory . 'thumbs/';
my $thumbs_scale = '10%';

my $index_file = "index.html";
my $title = "Image Gallery";

sub get_image_files
{
    my @images;
    opendir DIR, "$_[0]" || die "can't open dir '$_[0]'\n";
        @images = grep { /\.(?:png|gif|jpg|jpeg)$/i } readdir DIR;
    closedir DIR;
    return @images;
}

sub create_thumbnail
{
    my $image = $_[0];
    my $thumbs_directory = $_[1];
    my $scale = $_[2];

    system ("convert \"$image\" -resize $scale \"$thumbs_directory\/$image\"");
}

my @images = get_image_files($directory);

unless (@images) {
    die "dir $directory is empty\n";
}

if (! -e $thumbs_directory) {
    mkdir($thumbs_directory) || die "can't make path '$thumbs_directory' ($!)<\n";
}

open (HTML, ">", $directory."/".$index_file) || die $!;
print HTML "<!doctype html>
<html>
<head><title>".$title."</title><style>img { margin: 2px; border:2px solid blue; }</style></head>
<body><h1>".$title."</h1>";
foreach my $image (@images) {
    create_thumbnail($image, $thumbs_directory, $thumbs_scale);
    print HTML "<a href='".$directory.$image."'><img src='".$thumbs_directory.$image."'></a>";
}
print HTML "</body></html>";
close(HTML);

Like most things this is still a work in progress but it met my needs right here, right now. If you are a Perl programmer and want to laugh at me for the above code, email me.

I will eventually come back to this and improve things, including:

You can see the script in action here, where I took photos from a recent data recovery attempt at a couple of old hard drives: Random images from some old hard drives