Pointillate
By Will Koeppen
This app uses a reference image to seed a canvas using randomized exclusion sampling. Seeds are iteratively moved to new positions by using Lloyd's algorithm with a density function based on the reference.
Background
Artists have used distributed dots (stippling) for shading since at least 1510 AD. In the late 1800s, the Pointillism movement shed lines altogether and used only dots to create forms.
Computer scientists like Deussen et al. (2000) and Secord (2002) explored algorithms to apply stippling to digital images. Their goal was to use math and CPU power to represent objects with far fewer well-placed dots than you would need for a full resolution image.
As a lover of art and animation, I'm very interested in the idea of visual sufficiency. How little of something can you show and have people recognize what it is? I'm also interested in movement in general and the emotions it can evoke, and this is a way to add movement to static image.
Seeding the canvas
First, we add seeds to a canvas.
The analog version of exclusion sampling would be to use a glue stick on the canvas only in areas where we want seeds to stick. Then we count out 10,000 seeds and throw them at the canvas. Some will stick to the gluey areas. We'll pick up the seeds that didn't stick and throw them again and again until they're all hanging on.
Relaxation
Since we didn't carefully place the seeds, some will be stuck to the canvas close together, and some areas that had glue will still have gaps. We need them to spread out a little.
If you've ever been in a packed subway car when suddenly half of the people get off at a popular stop, you've approximated the movement described by Lloyd's Algorithm. There's a collective sigh of relief from the remaining riders, and we all take a few steps away from the squished person next to us until we reach a new equilibrium.
Weighting
Following the vanilla Lloyd's Algorithm to its mathematical conclusion would lead all of our seeds to be exactly equidistant from each other. Well ordered, but not very interesting if they should be representing an image. Instead, we want seeds to be relaxed, but still grouped (weighted) towards certain areas of the canvas.
What has weight? For humans, we might gravitate towards the fireplace in a cold room, the kitchen at a party, or around a piano player in Grand Central Station. For this project we use a reference image, and we can choose if the dark or the light pixels should have gravity to attract our seeds.
Play
The goal of the “Weighted Voronoi Stippling” of Secord (2002) was to quickly render an image with dots. To do that, use uniformly-sized seeds on a white canvas, start in dark areas, and let the seeds relax over them.
But maybe our goal is the journey rather than the destination. We can seed the canvas in light areas, but gravitate towards dark areas of the image. Or vice versa. We can change the size of the seeds to reflect the weight. Instead of the seeds we can show the boundaries between the seeds (cells). We can swap the colors of the seeds and the canvas, or color the seeds based on the reference image.
The seeding and relaxation are non-deterministic, so your animation will be different every single time.
Tips
- Edit your photo before adding it as a reference (e.g., background removal)
- Images with a high-contrast subject work best
- Most settings can be applied mid-stream
- Try slowing the speed down a lot (e.g., 0.05)
Acknowledgements
Daniel Shiffman's Coding Train Challenge #181 was an excellent resource and well worth watching. Sophie Zhang's response to the challenge was an inspiring seed for my own iteration.