Ben Crowder / Blog

Blog: #imagemagick

I’ve occasionally used ImageMagick’s erode and dilate filters to make art look a little less digital. Turns out those filters are also available in Photoshop and Affinity Photo, just under different names: minimum blur and maximum blur. I had no idea. (I should mention that there might still be subtle differences between the algorithms. I didn’t do a deep dive. But from my limited testing they seem to do the same thing.)

Reply via email or office hours

Another scripture poster, this time in English, French, German, Italian, Portuguese, and Spanish:

Go with him twain (Matthew 5:41)

Go with him twain

How I made these:

  • Make a 4000×5000px background texture in Affinity Photo (lots of layers and blending modes) and save to go-with-him-twain-bg.png
  • Lay out the text in Figma (900×1125px frame, bold Asap font at 126px, 150px line height, 6% letter spacing, white text on black background).
  • Export the frame as an SVG, go-with-him-twain.svg
  • Add the following to the beginning of the SVG file (after the opening tag) and change the seed values:
<filter id="filter">
  <feTurbulence seed="4389" type="turbulence" baseFrequency="0.5" numOctaves="2" result="turbulence2"/>
  <feDisplacementMap in2="turbulence2" in="SourceGraphic" scale="2" xChannelSelector="R" yChannelSelector="G" result="disp"/>

  <feTurbulence seed="4378" type="turbulence" baseFrequency="0.05" numOctaves="2" result="turbulence" />
  <feDisplacementMap in2="turbulence" in="disp" scale="3" xChannelSelector="R" yChannelSelector="G" />

<style type="text/css">
  path { filter: url(#filter); }
  • Convert the SVG to a 4000×5000px PNG: /Applications/ go-with-him-twain.svg --export-type=png --export-width=4000
  • Erode/dilate: convert go-with-him-twain.png -morphology erode disk:12 -morphology dilate disk:15 go-with-him-twain-eroded.png
  • Composite: convert go-with-him-twain-bg.png \( go-with-him-twain-eroded.png -normalize +level 0,55% \) -compose screen -composite go-with-him-twain-composite.png (I usually do this in Affinity Photo but I wanted to try using Imagemagick)
  • Upscale to 8000×10000px with Real-ESRGAN: ./realesrgan-ncnn-vulkan -i go-with-him-twain-composite.png -o go-with-him-twain-full.png -s 2
  • Add noise (8% monochromatic) in Affinity Photo and export final PNG (I could do this in Imagemagick, need to port it over)

Reply via email or office hours

New abstract hymn print: Be Still, My Soul.

I’m experimenting with a slightly new style here, masking the notes (after adding noise to the outlines with SVG filters and then eroding/dilating with Imagemagick) and painting inside the mask in Procreate. (And then texturing it in Affinity Photo as usual.)

Be Still, My Soul

Reply via email or office hours

Hymn prints

A new experimental nerdy thing, for people who like hymns, sheet music, and textures:

The first few measures of “Abide with Me!”
The first few measures of “The Spirit of God”

How I make these hymn prints (as I’m calling them):

  • Typeset the first phrase (or so) in MuseScore using the Bravura font, with the spacing trimmed to within an inch of its life
  • Play it out loud to make sure I entered it right (cough) and export an SVG
  • Drag the SVG into a frame in Figma and use the SkewDat plugin to skew it -4°, center it, then export a 4,000px-wide PNG
  • Use ImageMagick to do some erosion and dilation (to simulate age and ink spread): convert input.png -morphology erode disk:18 -morphology dilate disk:16 output.png
  • Texture the image in Affinity Photo and export the PNG
  • Upscale with Real-ESRGAN to 12,000px-wide
  • Downscale a little in Affinity Photo, add 8% monochrome noise, and export the final PNG

I’m still figuring out how I want to do these (full bleed or not, barlines, clefs and key signatures or not, etc.). Also thinking about possibly doing some abstract versions as well, to avoid all these music typesetting issues entirely.

Reply via email or office hours

Scanning journals

I’ve recently begun scanning my journals using my iPhone and the Scanner Pro app, and it’s working out fairly well. My process:

  • Using the built-in iPhone camera app, I long press to lock focus and exposure (this saves time so it doesn’t have to autofocus each time), then photograph each page of the journal. It’s not as high quality as it would be if I used an actual scanner, but it’s much, much faster, and far more portable.
  • After I’m done photographing, I open Scanner Pro and select the images from the camera roll, then use the Black & White Document setting to process them into a PDF.
  • From Scanner Pro, I export the PDF to Dropbox.

The resulting PDF is nice and clean and easy to read, and the files aren’t too big (150 pages is usually between 80 and 200 megs — for me, very much worth the space to preserve important documents).

A concocted example:


That’s before (the image is straight from my iPhone camera, no postprocessing), and this is after Scanner Pro is done with it:


I should add that ordinarily, with actual journals there wouldn’t be as much empty border around the content.

One hitch I’ve run into is that Scanner Pro chokes on anything larger than around 150 pages (it crashes), so I do long journals in chunks.

For that reason and a few other small annoyances, I’ve been looking into replacing Scanner Pro with a desktop-based script that takes a list of photos and processes them into a nice black and white PDF. Imagemagick gets me part of the way there with this command:

convert input.jpg -threshold 50% -blur 1x1 output.jpg

Here’s what it looks like for the above note card scan, at 30%, 50%, and 70% threshold, respectively:


At some point I’ll try writing a Python script that dynamically evaluates each page and adjusts the threshold as necessary to get the best result. Until then, though, I’m still using Scanner Pro.

Reply via email or office hours


Earlier this week I wrote a small Asteroids clone in JavaScript:

Video of the game

Instructions and the link to the game are on the project page.

FYI, here’s how I made the animated GIF: I used Quicktime Player to record a portion of the screen, then used ImageMagick to convert the .mov file to a series of PNGs:

convert png/asteroids_%03d.png

I deleted the extra frames at beginning and end that I didn’t care about (unpausing the game, figuring out how to turn the recording off), then used ImageMagick again to make the GIF:

convert -delay 1x30 png/*.png -layers optimize +dither -colors 32 asteroids.gif

Reply via email or office hours

Some small scripts

Migrating to Day One has resurrected my efforts to scan and transcribe my older paper journals. As I’ve been doing this, I’ve run into the need for a couple small shell scripts to automate things.

On several of these journals I’m scanning the full two-page spread because the whole journal fits on the scanner platen, which means splitting the resulting image out into two (one for each page). Splitimage uses ImageMagick to do that nicely. There’s some overlap, but for a fully automated solution it’s not bad, and it saves me a lot of time cropping.

I prefer taking these split images and renaming them sequentially using something more meaningful (“journal-2009.005.jpg” rather than “IMG_0034.JPG”, for example). I used to do this with OS X’s Automator tool, and it works quite well, but I wanted a quick command-line tool to speed things up. Enter dub, a zsh script that simplifies the batch renaming process. Now I can just type:

dub journal-2009.X.jpg *.JPG

And then it’s just a matter of dumping them into Unbindery and transcribing them.

Reply via email or office hours