013 - Fractals

The Fractals Module provides L-Systems, escape-time fractals, and IFS.

Why Fractals?

Fractals are mathematically generated patterns with self-similarity. They appear in nature (ferns, coastlines, clouds) and fascinate in art.

Three Approaches:

  1. L-Systems – Grammar-based, generates plants, branches, patterns
  2. Escape-Time – Mandelbrot, Julia – complex number iterations
  3. IFS – Iterated Function Systems – point transformations

L-Systems

Grammar-based fractals.

The Concept

An L-System has:

  • Axiom – Start String (e.g., "F")
  • Rules – Transformations (e.g., "F → F+F-F")
  • Iterations – How often rules are applied

After n iterations, you get a long string of instructions that a "turtle" follows.

TurtleAgent

The TurtleAgent interprets L-System strings:

Symbol Action
F Move Forward + Draw
f Move Forward (no Draw)
+ Rotate Right
- Rotate Left
[ Save State (Push)
] Restore State (Pop)
| Reverse Direction

API

import { TurtleAgent, LSystemRenderer } from '@carstennichte/cc-toolbox';

const turtle = new TurtleAgent({
  startPosition: { x: 0.5, y: 1.0 },
  startAngle: -90,
  stepLength: 10,
  turnAngle: 25,
});

const lsystem = new LSystemRenderer({
  axiom: 'F',
  rules: { 'F': 'F[+F]F[-F]F' },
  iterations: 4,
});

lsystem.generate();
turtle.execute(lsystem.getString(), ctx);

Options

Option Type Default Description
axiom string 'F' Start String
rules Record<string, string> {} Transformation Rules
iterations number 3 Number of Iterations

TurtleAgent Options

Option Type Default Description
startPosition {x, y} (0.5, 1.0) Start Position (normalized)
startAngle number -90 Start Angle (degrees)
stepLength number 10 Step Length
turnAngle number 22.5 Turn Angle
lineWidth number 1 Line Width
color string '#000' Line Color

Presets

Preset Description
plant Simple Plant
tree Branching Tree
koch Koch Curve
sierpinski Sierpinski Triangle
dragon Dragon Curve
hilbert Hilbert Curve
const lsystem = LSystemRenderer.fromPreset('tree', { iterations: 5 });

Color and Width Variations

Extended symbols for visual effect:

Symbol Action
C0-C9 Set Color (from Palette)
W+ Increase Line Width
W- Decrease Line Width
L+ Increase Step Length
L- Decrease Step Length

Escape-Time Fractals

Mandelbrot, Julia, and related sets.

The Concept

For each pixel:

  1. Convert to complex number c
  2. Iterate z = z² + c
  3. If escaped (|z| > 2) → Color based on iterations
  4. If stayed in → Color as "in the set"

FractalRenderer

Unified renderer for all escape-time fractals.

import { FractalRenderer } from '@carstennichte/cc-toolbox';

const fractal = new FractalRenderer({
  type: 'mandelbrot',
  center: { x: -0.5, y: 0 },
  zoom: 1.0,
  maxIterations: 100,
  colorMode: 'smooth',
});

fractal.render(ctx, width, height);

Supported Types

Type Description
mandelbrot Classic Mandelbrot
julia Julia Set
burningship Burning Ship
tricorn Tricorn/Mandelbar

Options

Option Type Default Description
type FractalType 'mandelbrot' Fractal Type
center {x, y} (-0.5, 0) Center Point
zoom number 1.0 Zoom Level
maxIterations number 100 Max Iterations
escapeRadius number 2.0 Escape Threshold

Julia-Specific

Option Type Description
juliaC {x, y} Constant c for Julia Set
const julia = new FractalRenderer({
  type: 'julia',
  juliaC: { x: -0.7, y: 0.27 },
  zoom: 1.5,
});

Coloring Modes

Mode Description
bands Discrete Color Bands
smooth Smooth Gradient
histogram Histogram Equalization
orbit Orbit Trap Coloring

Performance

Feature Description
WebWorkers Render in Background
Progressive Low-Res first, then Refine
Caching Cache Unchanged Areas

IFS (Iterated Function Systems)

Point-based fractals.

The Concept

An IFS has multiple affine transformations. Each iteration:

  1. Select transformation randomly (weighted)
  2. Apply to current point
  3. Plot point
  4. Repeat millions of times

Result: Self-similar structures like ferns, Sierpinski triangles.

IFSRenderer

import { IFSRenderer } from '@carstennichte/cc-toolbox';

const ifs = new IFSRenderer({
  transforms: [
    { a: 0, b: 0, c: 0, d: 0.16, e: 0, f: 0, p: 0.01 },
    { a: 0.85, b: 0.04, c: -0.04, d: 0.85, e: 0, f: 1.6, p: 0.85 },
    { a: 0.2, b: -0.26, c: 0.23, d: 0.22, e: 0, f: 1.6, p: 0.07 },
    { a: -0.15, b: 0.28, c: 0.26, d: 0.24, e: 0, f: 0.44, p: 0.07 },
  ],
  iterations: 100000,
  pointSize: 1,
});

ifs.render(ctx, width, height);

Transform Format

Parameter Description
a, b, c, d 2×2 Rotation/Scale Matrix
e, f Translation
p Probability (must sum to 1)

Presets

Preset Description
fern Barnsley Fern
sierpinski Sierpinski Triangle
vicsek Vicsek Snowflake
tree Fractal Tree
dragon Dragon Curve
const ifs = IFSRenderer.fromPreset('fern', { iterations: 50000 });

Options

Option Type Default Description
transforms Transform[] [] Transformations
iterations number 10000 Number of Points
pointSize number 1 Point Size
color string '#000' Point Color
colorByTransform boolean false Color by Transform

Tweakpane Integration

All fractal renderers have Tweakpane support:

Blade Control
type Dropdown (Mandelbrot/Julia/...)
center 2D Point
zoom Slider (logarithmic)
iterations Slider
colorMode Dropdown
juliaC 2D Point (for Julia)

SVG Export

L-Systems export directly to SVG:

const exporter = new SVGExporter();
exporter.startDocument(800, 600);
turtle.execute(lsystem.getString(), exporter); // SVG instead of Canvas
const svg = exporter.endDocument();

Escape-time and IFS are rasterized and do not export as vector.