Pattern: Tunnel of Squares 2D

In the library, and source below - a random experiment that evolved into something pretty. It also creates a slightly disturbing optical illusion if you stare at the center for a second or two.

Tunnel of Squares 2D

// Endless tunnel of spiraling squares
// Stare at it long enough and optical illusion makes it seem
// like the background is moving too.
//
// MIT License
// Take this code and make something cool!
// 8.25/2021 ZRanger1

var t2;
export var speed = 5;
export var nSquares = 4;
var cosT = cos(0.1), sinT = sin(0.1);

function signum(a) {
return (a > 0) - (a < 0)
}

export var speed = 5;
var timebase;

export function sliderSpeed(v) {
speed = 1+9* v;
}

export function sliderSquarocity(v) {
nSquares = 1+floor(6*v);
}

translate(-0.5,-0.5);

export function beforeRender(delta) {
timebase = (timebase + delta/1000) % 3600;
t2 = time(0.08);
t1 = speed * timebase;
}

// squared spiral expression adapted from Shader - Shadertoy BETA
export function render2D(index,x,y) {
x1 = signum(x); y1 = signum(y);
sx = x1 * cosT + y1 * sinT;
sy = y1 * cosT - x1 * sinT;

dx = abs(sin(nSquares*log(x * sx + y * sy) + atan2(y,x) - t1))

hsv(t2 + xsx + ysy, 1, dx * dx * dx)
}

5 Likes

You also snuck in CrosstownTraffic into the pattern library, which has a lot of potential (and needs more sliders, IMHO, or at least in my local version… IMLV?)

I tag all the stuff I upload so people know who to complain to. I’m pretty sure @pixie made both Frogger and Crosstown Traffic.

1 Like

Yup, that was me.

Complaints give me indigestion and praise goes straight to my head, so I try to keep my contributions low key…

3 Likes

I don’t want to clog up the pattern library with minor variations, but here’s a quick tweak – thanks to the coordinate transform functions, it only takes one additional line to rotate the squares (and a few more for a UI slider to turn it on and off):

// Endless tunnel of spiraling squares
// Stare at it long enough and optical illusion makes it seem like the background is moving too.  
//
// MIT License
// Take this code and make something cool!
// 8.25/2021 ZRanger1

var cosT = cos(0.1), sinT = sin(0.1);

function signum(a) { return (a > 0) - (a < 0); }

export var speed = 5;     export function sliderSpeed(v) { speed = 1+9* v; }

export var nSquares = 4;  export function sliderSquarocity(v) { nSquares = 1+floor(6*v); }

export var doRotate = 0;  export function sliderRotate(v) { doRotate = trunc(v); }

var timebase = 0;
export function beforeRender(delta) {
  timebase = (timebase + delta/1000) % 3600;
  t2 = time(0.08);
  t1 = speed * timebase;

  resetTransform();
  translate(-0.5,-0.5);
  if (doRotate) rotate(PI2*t2);
}

// squared spiral expression adapted from https://www.shadertoy.com/view/4tlfRB  
export function render2D(index,x,y) {
  x1 = signum(x); y1 = signum(y);
  sx = x1 * cosT + y1 * sinT;
  sy = y1 * cosT - x1 * sinT;

  dx = abs(sin(nSquares*log(x * sx + y * sy) + atan2(y,x) - t1))
  
  hsv(t2 + x*sx + y*sy, 1, dx * dx * dx)
}

Changing the direction and quantum of rotation would also make interesting variations…

3 Likes

Ok… inspired by @pixie, here’s the fun math toy of the day - a function that can give any 2D pattern n-sided kaleidoscopic reflections. I wrote this a couple of days ago for the Line Dancer pattern (now in the library), and have been plugging it in to random patterns to see what would happen ever since.

// Sets up a kaleidoscope effect - makes the image
// repeat over nSides evenly divided polar "slices" about the center.
// To use, just include this code block in your pattern, and add the line:
//      kal(x,y,timebase); x = outx; y = outy;
// to your render2D().  The timebase parameter controls rotation speed.
// you can use any timing value you like.
var outx,outy;
var nSides = 5;
var slice = PI / nSides;
function kal(x,y,timebase) {
  var angle = atan2(y, x);
  angle = mod(angle, 2.0 * slice);
  
  // uncomment to reflect each slice so they can be tiled
  // symmetrically if you like.  ymmv.
  //angle = abs (angle - slice);
  
  // rotate over time - rotation in polar coords is really
  // simple.
  angle += PI*timebase;
  var d = hypot(x,y);
  outx = d * cos(angle);  outy = d * sin(angle);
}

and here’s a version of Tunnel of Squares that uses it, with a “Reflections” slider.

Tunnel of Mirrors
// Endless tunnel of spiraling squares
// Stare at it long enough and optical illusion makes it seem
// like the background is moving too.  
//
// MIT License
// Take this code and make something cool!
// 8.25/2021 ZRanger1

var t2;
export var speed = 5;
export var nSquares = 4;
var cosT = cos(0.1), sinT = sin(0.1);

function signum(a) {
  return (a > 0) - (a < 0)
}

export var speed = 5;
var timebase;

export function sliderSpeed(v) {
  speed = 1+9* v;
}

export function sliderSquarocity(v) {
  nSquares = 1+floor(6*v);
}

export function sliderReflections(v) {
  nSides = 1+floor(v * 15);
  slice = PI / nSides;
}

// This block of code sets up a kaleidoscope effect - makes the image
// repeat over nSides evenly divided polar "slices" about the center.
// To use, just add the line:
//      kal(x,y,timebase / 2); x = outx; y = outy;
// to your render2D().  The timebase parameter controls rotation speed.
// you can use any timing input you like.
var outx,outy;
var nSides = 5;
var slice = PI / nSides;
function kal(x,y,timebase) {
  var angle = atan2(y, x);
  angle = mod(angle, 2.0 * slice);
  
  // uncomment to reflect each slice so they can be tiled
  // symmetrically if you like.  ymmv.
  //angle = abs (angle - slice);
  
  // rotate over time - rotation in polar coords is really
  // simple.
  angle += PI*timebase;
  var d = hypot(x,y);
  outx = d * cos(angle);  outy = d * sin(angle);
}


translate(-0.5,-0.5); 

export function beforeRender(delta) {
  timebase = (timebase + delta/1000) % 3600;
  t2 = time(0.08);
  t1 = speed * timebase;
}

// squared spiral expression adapted from https://www.shadertoy.com/view/4tlfRB  
export function render2D(index,x,y) {
  kal(x,y,timebase / 2); x = outx; y = outy;

  x1 = signum(x); y1 = signum(y);
  sx = x1 * cosT + y1 * sinT;
  sy = y1 * cosT - x1 * sinT;

  dx = abs(sin(nSquares*log(x * sx + y * sy) + atan2(y,x) - t1))
  
  hsv(t2 + x*sx + y*sy, 1, dx * dx * dx)
}
2 Likes