KidLisp Chaos Mode 🌀#
A playful fallback evaluator for invalid/random input
Status: ✅ Phase 1 & 2 Implemented#
- Detection:
isChaoticSource()function analyzes input for validity - Evaluation:
evaluateChaos()generates 6 visual modes from chaotic input - Integration: Hooks into
module()before parsing, routes to chaos evaluator
Problem Statement#
When the KidLisp editor receives scrambled or random text (e.g., during decryption animations, or when users experiment with random characters), the interpreter throws many confusing errors:
❌ Unknown KidLisp word: s7a
❌ Unknown KidLisp word: _f
❗ Invalid `<`. Wrong number of arguments.
... (repeated many times)
This is:
- Scary for new users experimenting
- Noisy in the console
- Missed opportunity for creative play
Solution: Chaos Mode#
Instead of failing loudly, detect "chaotic" input and route it through a Chaos Evaluator that produces visual output from any input.
Implementation#
Phase 1: Detection ✅#
Located in kidlisp.mjs at module level:
// Exported for testing and external use
export { isChaoticSource, KIDLISP_VOCABULARY, KIDLISP_FUNCTIONS, KIDLISP_COLORS };
function isChaoticSource(source) {
// Returns: { isChaotic: boolean, confidence: number, reason: string, stats: object }
// Detection criteria:
// 1. Low word recognition ratio (< 30% known KidLisp words/colors)
// 2. High special character ratio (> 50% non-alphanumeric)
// 3. Severely unbalanced parentheses (ratio > 3:1)
// 4. Very short invalid inputs (< 3 chars)
}
Phase 2: Chaos Evaluator ✅#
The evaluateChaos(source, api) method in the KidLisp class generates one of 6 visual modes:
| Mode | Name | Description |
|---|---|---|
| 0 | Rainbow Static | Each character becomes a colored pixel |
| 1 | Pulsing Circles | Concentric circles based on text length |
| 2 | Wave Interference | Animated sine wave pattern |
| 3 | DNA Helix | Two strands based on character values |
| 4 | Matrix Rain | Falling green columns |
| 5 | Kaleidoscope | Rotating symmetric pattern |
The mode is deterministically chosen from the source hash, so the same input always produces the same visual.
Integration Point#
In module() method, before calling parse():
const chaosResult = isChaoticSource(source);
if (chaosResult.isChaotic) {
console.log(`🌀 Chaos mode detected (${Math.round(chaosResult.confidence * 100)}% confidence)`);
this.chaosMode = { active: true, source, ...chaosResult };
return [['__chaos__', source]]; // Special AST that triggers chaos evaluator
}
In evaluate() method, at the top:
if (Array.isArray(parsed) && parsed[0]?.[0] === '__chaos__') {
return this.evaluateChaos(parsed[0][1], api);
}
Phase 3: Console Integration (TODO)#
Goal: Turn chaotic input into visual output.
// New module: kidlisp/chaos.mjs
export function evaluateChaos(source, api) {
const { wipe, ink, line, box, write, screen } = api;
// Use source as seed for deterministic randomness
const seed = hashString(source);
const rng = seededRandom(seed);
// Extract visual properties from source
const colors = extractColors(source);
const shapes = extractShapes(source);
const intensity = source.length;
// Generate visual based on source characteristics
wipe(colors.background);
// Draw based on character distribution
for (let i = 0; i < source.length; i++) {
const char = source[i];
const charCode = char.charCodeAt(0);
// Map character to visual element
const x = (charCode * 7 + i * 13) % screen.width;
const y = (charCode * 11 + i * 17) % screen.height;
const size = (charCode % 20) + 5;
// Color from character
const hue = (charCode * 137) % 360;
ink(hslToRgb(hue, 80, 60));
// Shape from character type
if (/[a-z]/i.test(char)) {
box(x, y, size, size); // Letters = boxes
} else if (/\d/.test(char)) {
// Numbers = circles (if we have circle, else box)
box(x - size/2, y - size/2, size, size);
} else if (/[()[\]{}]/.test(char)) {
// Brackets = lines connecting
line(x, y, screen.width - x, screen.height - y);
} else {
// Special chars = scattered pixels
for (let j = 0; j < 5; j++) {
const px = x + (rng() * 20 - 10);
const py = y + (rng() * 20 - 10);
box(px, py, 2, 2);
}
}
}
// Optional: Display the source text itself
ink(colors.foreground);
write(source.slice(0, 50), 10, screen.height - 20);
return { chaosMode: true, seed };
}
function hashString(str) {
let hash = 0;
for (let i = 0; i < str.length; i++) {
hash = ((hash << 5) - hash) + str.charCodeAt(i);
hash |= 0;
}
return hash;
}
function seededRandom(seed) {
return function() {
seed = (seed * 1103515245 + 12345) & 0x7fffffff;
return seed / 0x7fffffff;
};
}
Phase 3: Integration Points#
3.1 In kidlisp.mjs module function#
export function module(source, api) {
// Early chaos detection
if (isChaoticSource(source)) {
console.log('🌀 Chaos mode activated');
return {
paint: () => evaluateChaos(source, api),
sim: () => {},
act: () => {},
chaosMode: true
};
}
// Normal parsing continues...
const parsed = parse(source);
// ...
}
3.2 In kidlisp.com/index.html#
// Before sending to iframe, check for chaos
import { isChaoticSource } from './kidlisp/chaos.mjs';
// In updatePreview():
if (isChaoticSource(code)) {
// Show chaos indicator in UI
showChaosIndicator();
// Don't suppress - let it run through chaos evaluator
}
3.3 Console Output#
Instead of error spam, show:
🌀 Chaos mode: interpreting "8dk6:i` b*|o s7a~g" as visual noise
Phase 4: Chaos Visual Modes#
Different chaos styles based on input characteristics:
| Input Pattern | Visual Style |
|---|---|
| Mostly letters | Text scatter / waterfall |
| Mostly numbers | Numeric grid / matrix rain |
| Heavy punctuation | Line art / connections |
| Mixed/random | Noise field / static |
| Repeating patterns | Tiles / fractals |
Phase 5: Educational Hooks#
When in chaos mode, occasionally surface hints:
const CHAOS_HINTS = [
"Try: ink red, box 50 50 100 100",
"Tip: Commands are separated by commas",
"Start simple: wipe blue",
"Colors: red, blue, green, yellow, purple...",
];
// Show hint after 3 seconds of chaos
setTimeout(() => {
if (stillInChaosMode) {
showHint(CHAOS_HINTS[Math.floor(Math.random() * CHAOS_HINTS.length)]);
}
}, 3000);
API Surface#
// kidlisp.mjs exports
export {
isChaoticSource, // (source: string) => boolean
evaluateChaos, // (source: string, api: API) => ChaosResult
CHAOS_THRESHOLD, // Configurable detection sensitivity
};
// Types
interface ChaosResult {
chaosMode: true;
seed: number;
visualStyle: 'scatter' | 'matrix' | 'lines' | 'noise' | 'tiles';
}
Benefits#
- No scary errors for beginners experimenting
- Always produces output - encourages play
- Deterministic - same input = same visual (good for sharing)
- Educational - hints guide users toward valid syntax
- Fun - turns mistakes into art
- Performance - skips expensive parsing for obvious chaos
Future Ideas#
- Chaos → Valid: Offer to "fix" chaotic input into similar valid code
- Chaos Gallery: Save interesting chaos outputs
- Chaos Remix: Let users intentionally trigger chaos mode
- Sound: Chaos mode could also produce audio from input
- Animation: Chaos visuals could animate based on character sequence
Implementation Order#
- ✅
isChaoticSource()detector - Implemented with confidence scoring - ✅ Basic
evaluateChaos()visual generator - 6 visual modes - ✅ Integration in
kidlisp.mjsmodule - Before parsing - ✅ Console message cleanup - Shows
🌀 Chaos modeinstead of errors - ✅ Multiple visual styles - Rainbow, circles, waves, DNA, matrix, kaleidoscope
- 🔲 Educational hints (Phase 3)
- 🔲 kidlisp.com UI indicator (Phase 3)
- 🔲 Chaos gallery/sharing (Future)
"Every input is valid. Some are just more chaotic than others."