I wanted a screensaver that wrote poetry. Not well, necessarily, but with correct structure and at least a passing resemblance to something a person might say. The result is an ambient haiku generator that produces a new poem every eight seconds, cross-fading between them over a slow-shifting gradient background. You open the page and leave it running. It never stops.
The core problem with generating haiku is the syllable constraint. A haiku is three lines of 5, 7, and 5 syllables. If you just pick random words and try to add them up, you almost never land on exactly the right count. The last word needs to have precisely the right number of syllables to finish the line, and if no word fits, you have to throw out the whole attempt and start over. Brute-force retry works but it's slow and produces a lot of grammatical garbage.
The word data
Instead of counting syllables at runtime, I pre-organized the vocabulary into a JSON file where words are grouped first by part of speech (adjective, noun, verb) and then by syllable count. So when the generator needs a noun with exactly two syllables, it can look that up directly without scanning the whole dictionary. This makes the constraint-solving fast enough to run many times per second.
Backtracking construction
Each line follows a grammatical template. Line one is adjective + noun (5 syllables). Line two is noun + verb + adjective (7 syllables). Line three is verb + noun (5 syllables). The templates give the output a sentence-like quality rather than a word salad feel.
The generator fills each position in the template using a backtracking algorithm. It picks a random word for the first slot, calculates how many syllables remain, then picks a word for the next slot that doesn't exceed the remaining budget. If it reaches a dead end where no word in the dictionary has the exact syllable count needed for the final position, it backs up one step and tries a different word. The recursion continues until all positions are filled and the syllable count is exactly zero.
There's a subtlety in how the budget is managed. When filling position N, the algorithm reserves a minimum of one syllable per remaining position. A three-syllable word can't go in the first slot of a 5-syllable line that has two positions, because that would leave only two syllables for the second word and none for the third. This pruning keeps the search space small.
The ambient part
The background is an animated CSS gradient that cycles through purple, blue, and teal over 30 seconds. The haiku text sits in a frosted-glass card using backdrop-filter: blur. When a new haiku is ready, it fades in over two seconds while the old one fades out. The timing is slow on purpose. This is something you put on a second monitor or a tablet on your desk. It's not an app you interact with.
The whole thing is two files: one HTML page with inline CSS and JavaScript, and one JSON file containing the word data. No build step, no dependencies, no framework.