Overview
Prismatica is a J-inspired array language for pixel art. The pixel buffer is a table — X and Y hold every pixel's coordinates at once. All operations map over the entire table automatically. The last expression becomes the image.
sin X computes sin of every x-coordinate at once. X , Y , 0.5 builds an RGB table. No loops needed — that's array programming.Right-to-Left Evaluation
There is no operator precedence. Everything evaluates right-to-left:
Built-in Tables & Values
| Name | Type | Description |
|---|---|---|
X | table | Each pixel's x-coordinate (0–1). A table of scalars. |
Y | table | Each pixel's y-coordinate (0–1). A table of scalars. |
P | table | Position table — each pixel holds [x, y]. Same as p. |
t | scalar | Time in seconds (broadcasts to all pixels) |
m | vec2 | Mouse position over canvas (0–1) |
pi | scalar | π ≈ 3.14159 |
tau | scalar | τ = 2π ≈ 6.28318 |
X and Y are separate scalar tables. P is a 2-channel table. Use P for SDF functions, X/Y for per-axis math.Assignment
name =: expr — assign a table to a name. Also accepts ← and <-.
Strand Arrays
Adjacent number literals form an array automatically — no brackets needed:
Primitive Verbs
| Verb | Monadic (one arg) | Dyadic (two args) |
|---|---|---|
+ | identity | add |
- | negate | subtract |
* | signum (−1/0/1) | multiply |
% | reciprocal (1/y) | divide |
^ | exp (eʸ) | power (xʸ) |
| | abs | modulo |
, | ravel (flatten) | append/concatenate |
<. | floor | min |
>. | ceil | max |
<: | decrement (y−1) | less-or-equal |
>: | increment (y+1) | greater-or-equal |
~: | complement (1−y) | not-equal |
< | — | less-than |
> | — | greater-than |
= | — | equal |
{ | first element | index: i { arr |
# | tally (count) | scale (x * y) |
i. | iota: i. 4 → [0,1,2,3] | — |
Named Verbs
| Name | Monadic | Dyadic x verb y |
|---|---|---|
sin cos tan | trig (component-wise) | sin(x+y) |
sqrt log exp fract | component-wise | — |
wave | sin(y·τ)·0.5+0.5 | — |
noise | 2D value noise → 0–1 | — |
polar | [angle,radius] from center | — |
mirror | 1−2·|y−0.5| | — |
length | Euclidean length | — |
atan2 | atan2(y,0) | atan2(x,y) |
dot_ | dot(y,y) | dot product x·y |
glow | glow(y, 0.05) | d glow k = exp(−max(d,0)/k) |
tile | tile(y, 4) | p tile n = fract(p·n) |
rotate | — | p rotate angle |
hsv | hsv from vec3 [h,s,v] | h hsv s,v |
hsl | hsl from vec3 [h,s,l] | — |
circle | circle at center | p circle cx,cy,r |
box | — | p box cx,cy,w,h |
ring | — | p ring cx,cy,r |
step | step(0.5, y) | edge step x |
smooth | smooth(0,1,y) | lo,hi smooth x |
mix | — | t mix a,b = lerp(a,b,t) |
clamp | clamp(y,0,1) | x clamp lo,hi |
Adverbs
Adverbs modify verbs. They are written after the verb:
| Adverb | Name | Example | Meaning |
|---|---|---|---|
/ | reduce | +/ 0.3 0.3 0.3 | fold array with verb → 0.9 |
~ | reflex | dot_~ v | apply verb to (y, y) → self-dot |
Conjunction @
f @ g creates a new verb meaning "apply g first, then f":
Component Access
Use .x .y .z or .r .g .b to extract components from a vector:
Ternary
condition ? then : else — condition > 0 is truthy.
Comments
NB. comment or ⍝ comment — rest of line ignored.
Widgets
Declare interactive controls that appear below the canvas. Widget values persist while you edit code; load a new example to reset them.
| Syntax | Control | Arguments |
|---|---|---|
name =: @float min max default | Float slider | Range and default. Optional 4th arg: step (default 0.01). |
name =: @int min max default | Integer slider | Integer range and default. |
name =: @color r g b | Color picker | RGB values 0–1. |
name =: @bool default | Toggle | 0 or 1. |