Building more Simutrans tools: the Perl Imager package

Tags:

In building some new tools to support Simutrans development, I found this bit of sage advice dated 2005 from Tony Cook, the developer of the Imager module. From that I revised this example to translate the "transparent" cyan that Simutrans wants in its pakfile images, to actual transparency.

Note the use of new function signatures, and hash slices.

use v5.20;
use feature 'signatures';
no warnings 'experimental::signatures';

use Imager;

sub replace_color ($img, $from_color, $to_color) {
    # Inspired by http://www.perlmonks.org/?node_id=497355
    my $rpnexpr = <<'EOS';
x y getp1 !pix
@pix red from_red eq
@pix green from_green eq
@pix blue from_blue eq
and and
@pix alpha from_alpha eq
and
to_red to_green to_blue to_alpha rgba @pix ifp
EOS

    my %constants;
    # Load values via hash slices
    @constants{map {"from_$_"} qw{red green blue alpha}} = 
        $from_color->rgba;
    @constants{map {"to_$_"  } qw{red green blue alpha}} =
        $to_color  ->rgba;
    return Imager::transform2({ rpnexpr => $rpnexpr,
                                constants => \%constants,
                                channels => 4},
                              $img);
}

my %special_colors = (
    'transparent_cyan' => [231,255,255],
    );

my $image = Imager->new(file => $filename);
$image = $image->convert(preset => 'addalpha');
#
# Replace visible color with transparency
#
my $color = Imager::Color->new( @{$special_color{transparent_cyan}} );

# make a work image the same size as our input; add an alpha channel
my $work = Imager->new(xsize => $image->getwidth,
                       ysize => $image->getheight, channels => 4);
# fill it with the color we want transparent
$work->box(filled => 1, color => $color);

# get an image with that color replaced with transparent black
my $out = $work->difference(other => $image);

$out->write(file => 'example-output.png');

Further examples of the little Transform script language could change from more-standard "real" transparent PNGs to what Simutrans wants, or help highlight unwanted special colors that can result from anti-aliasing, or do all kinds of color or shape transforms.