A Kotlin implementation of evolutionary image generation using genetic algorithms1 to evolve geometric shapes that approximate a target image.
This project uses genetic programming to evolve simple geometric shapes (circles, rectangles, polygons, curves) that gradually approximate a target image through natural selection. Each "individual" consists of a genome of coloured shapes, and evolution occurs through mutation and fitness-based selection.
This implementation is inspired by:
- Roger Johansson's "Genetic Programming: Evolution of Mona Lisa"
- NP Contemplation's "Clojure genetic Mona Lisa problem"
- Initialization: Start with a random collection of zero or more geometric shapes
- Mutation: Randomly modify shape properties (position, colour, size) or add new shapes
- Fitness Evaluation: Compare the rendered image against the target using pixel-by-pixel RGB distance
- Selection: Keep mutations that improve fitness (lower pixel distance)
- Iteration: Repeat the process continuously to evolve better approximations
Evolution parameters can be configured via evolver-settings.json:
maxGenomeSize- Maximum number of shapes per individualnewShapeProbabilityFactor- Likelihood of adding new shapesavgShapesToMutate- Average number of shapes to mutate per generation
The system supports both local evolution; a GUI will show you the latest state if a DISPLAY exists but not if run headless. Shapes can be automatically uploaded to the (appallingly named) dudestore web service.
1 Note that I was later informed that this isn't a true genetic algorithm and is, in fact, a stochastic hill climbing algorithm. I confess I'm no expert on either and continue to call this project "genetic", even if it's inaccurate.