A million integers on Ulam and Sacks spirals, where prime-rich polynomials glow as rays.
A segmented sieve of Eratosthenes finds the 78,498 primes below a million a slice at a time, after the opening plays the sieve itself on the first few hundred cells. Each prime gets two homes: Ulam's square spiral, computed in closed form from its ring, and Sacks' Archimedean spiral, where n sits at radius sqrt(n / pi) and angle 2 pi sqrt(n) so perfect squares line up due east. Switching layouts interpolates radius and unwound angle together, so every ring of the square swirls into the circle like a galaxy. Zoomed out, primes are splatted into an accumulation buffer with area-weighted coverage, tone mapped and bloomed; zoomed in they become labelled cells. Highlighted quadratics such as Euler's n^2 + n + 41 show why the patterns exist: on Ulam's spiral any 4j^2 + bj + c runs along a diagonal, and some are several times richer in primes than average.
Try it. Drag to pan, scroll or pinch to zoom from single numbers out to the whole million, and hover any cell to see its factorization or its rank among the primes. Click a number to light the ray through it and measure its share of primes. Switch Ulam and Sacks with the buttons or Space, step through the polynomials with the arrows, and use plus, minus and 0 to zoom or fit.
Paste this into Claude Code, Codex or any coding agent to get a simple version running, then take it wherever you like.
Build an interactive prime number spiral with JavaScript and the HTML canvas element. Put everything in a single index.html file with no libraries or build step, so I can open it directly in a browser.
Start simple:
- Make a canvas that fills the window, stays sharp on high-DPI screens (scale by devicePixelRatio), and resizes with the window. Paint it a deep navy background.
- Write a sieve of Eratosthenes for the numbers up to about 250,000, stored in a Uint8Array.
- Write a function that returns the (x, y) position of n on Ulam's square spiral: 1 at the center, then 2, 3, 4 and so on winding counterclockwise in square rings. Ring k holds the numbers from (2k - 1)^2 + 1 to (2k + 1)^2, which gives you a closed form without walking the spiral.
- Draw every prime as a small square, one pixel or a little more, centered on the canvas. Diagonal streaks should appear right away.
Once that works, make it beautiful:
- Add Robert Sacks' version as a second layout: put n at radius sqrt(n) and angle 2 pi sqrt(n), so perfect squares line up on one ray. Press Space to animate every point from one layout to the other with an eased interpolation.
- Highlight the values of Euler's polynomial n^2 + n + 41 in a second color, and show what fraction of them are prime compared with all numbers of that size.
- Add zoom with the mouse wheel around the cursor and drag to pan. When zoomed in far enough, draw each integer as a cell with its number in it, primes filled and composites faint.
- Give primes a warm color near the center that cools toward the edge.
Explain the key ideas in short code comments. When you're done, tell me how to open it and suggest three directions I could take it next, such as clicking any number to highlight the diagonal through it and fit its quadratic, a polar morph that swirls the square into the circle, or rendering a million primes into an ImageData buffer for speed.