Last active
November 27, 2021 20:08
-
-
Save lostfictions/607ab2eccef8385270d3393eb328e246 to your computer and use it in GitHub Desktop.
tiny tiny tracery-like
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const matcher = /\[([^\[\]]+)\]/g | |
function randomInArray(arr) { return arr[Math.floor(Math.random() * arr.length)] } | |
export default function generate(concepts, concept, maxCycles = 10, seen = {}) { | |
if(!concepts[concept]) { | |
return `{error: unknown concept "${concept}"}` | |
} | |
return randomInArray(concepts[concept]) | |
.replace(matcher, (_, nextConcept) => { | |
if(seen[nextConcept] > maxCycles) { | |
return '{error: max cycles exceeded}' | |
} | |
const nextSeen = Object.assign({}, seen) | |
nextSeen[nextConcept] = nextSeen[nextConcept] + 1 || 1 | |
return generate(concepts, nextConcept, maxCycles, nextSeen) | |
}) | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
const concepts = { | |
beings: ['dogs', 'cats', 'humans', 'robots', 'animes'], | |
state: ['harmony', 'misery', 'terror'], | |
howThingsAre: [ | |
'[beings] and [beings], living together in [state]!' | |
], | |
recursive: [ | |
'[beings], but also [recursive]', | |
'[beings]' | |
] | |
} | |
generate(concepts, 'howThingsAre') // => animes and robots, living together in misery! | |
generate(concepts, 'recursive') // => cats, but also humans, but also animes, but also cats, but also robots | |
// You can also use .bind() to partially apply a generator with a set of concepts... | |
const gen = generate.bind(undefined, concepts) | |
// ...and get a function that can be used as a shorthand for that set! | |
gen('howThingsAre') // => dogs and animes, living together in harmony! | |
gen('beings') | |
// You can do the same thing for a single concept, and get a handy zero-argument getter. | |
const getStateOfAffairs = generate.bind(undefined, concepts, 'howThingsAre') | |
getStateOfAffairs() |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment