---
title: "Sq2 · generative art"
description: "A city of light, seen through a shallow lens. Generative art plate #36 by Theodore Vorillas, drawn live in your browser from its code."
url: "https://vorillaz.com/lab/sq2"
---

![](https://vorillaz.com/_astro/sq2.BDOnBHNt_BE3Rm.webp)

fig. #36 · rendered live in your browser from the code below

# #36 sq2

A city of light, seen through a shallow lens.

- date

  2026.10.13

- tags

  generative-art · javascript

Frames, bars and lamps stand in rows on five decks, drawn in axonometric, and every one of them is dragged back along one axis into a trail. A lens with a shallow depth of field looks at them: one slanted band is sharp, and everything in front of it or behind it spreads into soft light that adds up into haze. Then it all goes onto grainy film. Play it and the trails run on, the focus racks through the decks, and the grain moves. One row of lamps burns in signal.

## The field

```javascript title="sq2.js"
// world axes: u runs down and right, v (travel) up and right, y up
const at = (u, v, y) => [w / 2 + 0.866 * (u + v) * U, h / 2 + (0.5 * (u - v) - y) * U];

// a frame: its outline at the front, its corners dragged back along v, fading out
const trail = gradient(at(u, v, y), at(u, v - len, y), [light, transparent]);
for (const corner of corners) line(at(...corner, v), at(...corner, v - len), trail);
outline(corners.map((c) => at(...c, v)), light);
```

## The lens

```javascript title="sq2.js"
// how far each element sits from the focal plane picks its band; a band is blurred as one,
// and the bands are added together, so light out of focus spreads into haze
const blur = abs(depth(e) - focus) * 1.5;
const band = BANDS.findIndex((edge) => blur <= edge);
draw(e, layers[band], { width: 0.9 + band * 0.9, alpha: e.alpha * (1 - band * 0.08) });

for (const [i, layer] of layers.entries()) composite(layer, { mode: "lighter", filter: `blur(${BLUR[i]}px)` });
composite(layers[0], { mode: "lighter", filter: "blur(5px)", alpha: 0.55 }); // bloom off what is sharp
```

## The film

```javascript title="sq2.js"
// grain in overlay darkens and lightens the light; a sparse dust, added, lifts the black
grain[i] = 128 + gaussian() * 46;
dust[i] = { white, alpha: abs(gaussian()) * 22 };
fill(pattern(grain, offset), "overlay", 0.85);
fill(pattern(dust, offset), "lighter", 0.35); // a fresh offset every frame
```

## References

- [Depth of field](https://en.wikipedia.org/wiki/Depth_of_field)
- [Bokeh](https://en.wikipedia.org/wiki/Bokeh)
- [Axonometric projection](https://en.wikipedia.org/wiki/Axonometric_projection)
- [Film grain](https://en.wikipedia.org/wiki/Film_grain)
