ShutterSploshScatterPlots

Mohammad Ali (mohdali) had made a nice illustration of the socalled rolling shutter effect. He wrote a programm in javascript which uses the library d3 called Rolling shutter.

This program was used by artist Scriptique to program a kind of “paint-by-number recreational occupation for your browser” (as the artist called it). It should display something like “a paint drop dropping”.

The program has a MIT licence and you can see how well your browser paints by numbers by pasting the program into a file and then opening the file in your browser (tested with firefox).

<!DOCTYPE html>
<html>

<head>
 <meta charset="utf-8">
 <title>ShutterSploshScatterPlots</title>
</head>
<style>
 canvas {
  background-color:rgba(50,140,150,0.8)
 }
</style>

<body>
 <script src="https://d3js.org/d3.v4.min.js" type="text/javascript"></script>
 <script type="text/javascript">
  var width = 1000,
   height = 500;
var offset =300;
of=400;

  var canvas = d3.select("body").append("canvas")
   .attr("width", width-60)
   .attr("height", height+offset)
   .node().getContext("2d");

  var shutter = 0;

  var circle = d3.symbol()
   .type(d3.symbolCircle)
   .size(1000)
 .context(canvas);

   
  /*
   Fan Shape definition.
   Modify the parameters to change the shape.
  */
  var numOfPoints = 100;
  var numOfBlades = 5;
  var rotationSpeed = 2; // relative to shutter speed
  var angleDeg = 0;
  var theta = angleDeg / 180 * Math.PI;
var bulge = 20;
var sc=0.7;

  var points = d3.range(numOfPoints);
  var scale = d3.scaleLinear()
   .domain(d3.extent(points))
   .range([0, 2 * Math.PI]);

  var shape = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d); })
   .curve(d3.curveCardinalClosed)
   .context(canvas);

var shape2 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+2/3*Math.PI; })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
 
  canvas.save();

var shape3 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+4/3*Math.PI; })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
 
var shape4 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+2/3*Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape5 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+3.3/3*Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape6 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+0*Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape7 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+0*Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape8 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape9 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape10 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape11 = d3.lineRadial()
   .radius(function (d) { return sc*Math.sin(scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+0*Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

var shape12 = d3.lineRadial()
   .radius(function (d) { return 0.5*sc*Math.sin(Math.PI/2+scale(d))*(200+bulge*Math.sin(25*scale(d))); })
   .angle(function (d) { return scale(d)+0*Math.PI })
   .curve(d3.curveCardinalClosed)
   .context(canvas);
  canvas.save();

  setInterval(function () {
   canvas.beginPath();
   canvas.setTransform(1, 0, 0, 1, 0, 0);
   canvas.clearRect(0, shutter, width, height+offset - shutter);
   canvas.rect(0, shutter, width, height+offset - shutter);
   canvas.clip();

canvas.beginPath();
   canvas.moveTo(0, shutter);
   canvas.lineTo(width, shutter);
canvas.strokeStyle = "rgba(87,207,255,0.8)";
   canvas.stroke();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2+200,height/2+of);
canvas.rotate(rotationSpeed*shutter / 180 *Math.PI);

shape11(points);

canvas.fillStyle = "rgba(159, 170, 200, 0.6)";/**/
   canvas.fill();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2-200,height/2+of);
canvas.rotate(-rotationSpeed*shutter / 180 *Math.PI);

shape10(points);

canvas.fillStyle = "rgba(50, 100, 255, 0.6)";/**/
   canvas.fill();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2+200,height/2+of+30);
canvas.rotate(rotationSpeed*shutter / 180 * Math.PI);

shape9(points);

canvas.fillStyle = "rgba(200, 200, 200, 0.6)";/**/
   canvas.fill();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2+100,height/2+of);
canvas.rotate(rotationSpeed*shutter / 180 * Math.PI);

shape8(points);

canvas.fillStyle = "rgba(0, 10, 130, 0.8)";/**/
   canvas.fill();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2-250,height/2+of);
canvas.rotate(-rotationSpeed*shutter / 180 *Math.PI);
shape6(points);

canvas.fillStyle = "rgba(03, 150, 200, 0.6)";/**/
   canvas.fill();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2+150,height/2+of-30);
canvas.rotate(rotationSpeed*shutter / 180 * Math.PI);

shape7(points);

canvas.fillStyle = "rgba(03, 10, 199, 0.8)";/**/
   canvas.fill();

  canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2-100,height/2+of);
canvas.rotate(-rotationSpeed*shutter / 180 * Math.PI);
shape4(points);
canvas.fillStyle = "#53f6e1";
   canvas.fill();

 canvas.beginPath();
   canvas.setTransform(Math.cos(theta), Math.sin(theta), 0, 1, width / 2, height / 2+of);
   canvas.rotate(rotationSpeed*shutter / 180 *Math.PI);
   
shape2(points);
canvas.fillStyle = "rgba(05, 50, 80, 0.6)";
   canvas.fill();

canvas.beginPath(); /*red ball*/
var heigh=120+shutter-0.16*shutter
if(heigh<height+offset-140){
canvas.setTransform(1,0,0,1,width/2-50,heigh);}
/*canvas.rotate(rotationSpeed*shutter / 180 *Math.PI);*/

shape12(points);

canvas.fillStyle = "rgba(159, 0, 0, 1)";/**/
   canvas.fill();

 canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2-100,height/2+of);
canvas.rotate(-rotationSpeed*shutter / 180 * Math.PI);
shape5(points);
canvas.fillStyle = "rgba(209,237,239,0.6)";
/*"#FFF8DC";*/
   canvas.fill();

  canvas.beginPath();
   canvas.setTransform(Math.cos(theta), Math.sin(theta), 0, 1, width / 2, height / 2+of);
   canvas.rotate(rotationSpeed*shutter / 180 *Math.PI);
   shape(points);

canvas.fillStyle="#42edf7"; /*blue*/
 canvas.fill();

canvas.beginPath();
canvas.setTransform(1,0,0,1,width/2+100,height/2+of);
canvas.rotate(rotationSpeed*shutter / 180 * Math.PI);

shape3(points);

canvas.fillStyle = "rgba(55, 220, 199, 0.8)";/*ehemals rot*/
   canvas.fill();

  /* canvas.beginPath();
   circle();
canvas.fillStyle="blue";
canvas.fill();*/

   shutter = (shutter + 1) % (height+offset);

   if (shutter == 0) {
setInterval(function(){
    canvas.restore();
    canvas.save();
     }, 5000);
/*rotationSpeed=d3.randomUniform(0.1, 5)();*/
   }
  }, 1);
 </script>
</body>
</html>

2 Responses to “ShutterSploshScatterPlots”

  1. inquiry Says:

    Why isn’t there a link to artist “Scriptique” ?

  2. nad Says:

    “Why isn’t there a link to artist “Scriptique” ? “

    As written on randforms about page there are contributors to this blog who use pseudonyms and in particular perform as socalled “sockpuppets” in a “media theatre”. This holds also partially true for nonverbal artistic contributions. But as also said there: not all (art)works are pseudononymous and there are many links to real exisiting artists webpages. Apart from the “media theatre” -it might be interesting for you to know that there are artists which prefer to display their works without their name once in a while. The point being that the artists agents (gallerists etc.) usually put strong restrictions on which artwork shall be sold to whom for what prize, but artists sometimes like to get immediate feedback. So yes there could be some works here, which fall into this category.

Leave a Reply


The below box is for leaving comments. Interesting comments in german, french and russian will eventually be translated into english. If you write a comment you consent to our data protection practices as specified here. If your comment text is not too rude and if your URL is not clearly SPAM then both will be published after moderation. Your email adress will not be published. Moderation is done by hand and might take up to a couple of days.
you can use LaTeX in your math comments, by using the [latex] shortcode:
[latex] E = m c^2 [/latex]