LISP — The Language That Will Not Die
I’ve spent large parts of the last week editing maps for a game
system I’m working on. I’ve been using the GIMP graphics editor, and I’m pretty
impressed with it. I haven’t found anything I can’t easily make it do
— except, oddly enough, draw straight lines between defined
endpoints. (I suspect there’s actually a way to do this using the
path facility.)
I have a requirement to prepare about six different variants of a
base map, using the same topographic map but with different
arrangements of national borders. I’ve handled this by creating a
multi-layered XCF file with the topo map as the background and the
different borders as optional overlays.
OK, so I save the variants to flat PNGs by hand whenever I change the
image, but that’s a pain. What I wanted was a way to put in my makefile
instructions that say, for each variant map, that it depends on the XCF
and the way to make it is to composite a particular selected subset of layers
by running GIMP in batch mode.
Fortunately, GIMP has an embedded Scheme interpreter that’s good
for exactly this kind of thing. Looking at some Python-Fu code by
Carol Spears taught me enough about the API to get started; the fact
that I’m an old LISP head got me the rest of the way.
Here it is.
;; Batch-mode select and save of a layer set as a PNG. ;; Has to be copied into ~/.gimp-2.2/scripts to work ;; ;; Note: This assumes that gimp-drawable-get-name returns a list with ;; the actual string name as its car. This is what gimp-2.2 does, but ;; not what the documentation says it should do! (define (layer-set-saver infile select outfile) (let* ((image (car (gimp-file-load RUN-NONINTERACTIVE infile infile))) (layers (cadr (gimp-image-get-layers image))) (ind 0)) (while (< ind (length layers)) (let* ((layer (aref layers ind)) (layer-name (car (gimp-drawable-get-name layer)))) (gimp-drawable-set-visible layer (if (member layer-name select) 1 0))) (set! ind (+ ind 1))) (file-png-save-defaults RUN-NONINTERACTIVE image (car (gimp-image-flatten image)) outfile outfile) ) (gimp-quit 0) )
Here's one of my makefile productions. The second arg is a list of layer names.
basic.png: basic.xcf gimp -i -b '(layer-set-saver "basic.xcf" (quote ("topographic" "skinny-borders" "grey-switzerland")) "basic.png")'
Apologies for the long line.
LISP truly is The Language That Will Not Die. And that’s a good thing.