/*Vicky Zhou
vzhou@andrew.cmu.edu
Project 12 - Final
Section E*/
var particles; //number of particles in sphere system
var spacing; //spacing of particles
var waveRipple; //manipulates ripple in sphere system
var points; //array for compiling all sphere points
var speed; // speed variable for ripple sphere wave effect
var amplitude; //amplitude of wave
//variables for new toruses
var myx = [];
var myy = [];
var myz = [];
//variables for existing, old toruses
var total = 5;
var locations = new Array(total);
var bool = new Array(total);
var oldpart = [];
var oldpartsize = 12;
//to change displays
var changescene = true;
function setup() {
createCanvas(600, 600, WEBGL);
particles = 2000;
spacing = 200;
points = [];
speed = 0.01;
amplitude = 0.8;
wavecol = 0;
if (changescene) {
//array of random points for wave of spheres
for (var i = 0; i < particles; i++) {
points[i] = createVector(random(-5, 5),
random(-5, 5),
random(-5, 5));
}
} else {
//array for generated toruses
for (var i = 0; i < myx.length; i++) {
myx[i];
myy[i];
myz[i];
}
//array for already existing toruses
for (var i = 0; i < locations.length; i++) {
locations[i] = new Array(total);
bool[i] = new Array(total);
for (var j = 0; j < locations[i].length; j++) {
locations[i][j] = new Array(total);
bool[i][j] = new Array(total);
for (var k = 0; k < locations[i][j].length; k++) {
locations[i][j][k] = createVector(i * oldpartsize,
j * oldpartsize,
k * oldpartsize);
bool[i][j][k] = false;
}
}
}
var thres = 2; //threshold for state of Torus
for (var i = 0; i < total; i++) {
for (var j = 0; j < total; j++) {
for (var k = 0; k < total; k++) {
stateofTorus = random(15); //random number for state
if (stateofTorus <= thres) {
st = 1;
bool[i][j][k] = true;
} else {
st = 0;
}
oldpart.push(new myTorus(i * oldpartsize,
j * oldpartsize,
k * oldpartsize,
st));
}
}
}
}
}
//create and push new coordinates for toruses when any key is pressed
function keyPressed() {
myx.push(random(-10, 10));
myy.push(random(-300, 300));
myz.push(random(-300, 300));
}
function draw() {
background(30, 30, 50);
wavecol += 1;
//light that is emiited
directionalLight(wavecol/2, 200, 200, 50);
ambientLight(80, wavecol/5, 170);
//manipulates wave of spheres
waveRipple = mouseX * speed;
//center rotating cube
push();
rotateX(frameCount/100);
rotateY(frameCount/100);
noStroke();
box(150);
pop();
if (changescene) {
//array of random points to plot each sphere
for (var i = 0; i < particles; i++) {
var dot = points[i];
doty = sin(dot.x + waveRipple) * amplitude;
push();
translate(dot.x * spacing, doty * spacing, dot.z * spacing);
noStroke();
sphere(10);
pop();
}
} else {
//array of existing toruses
push();
for (var i = 0; i < oldpart.length; i++) {
oldpart[i].display();
}
pop();
//create new toruses
for (var i = 0; i < myx.length; i++) {
rotateY(frameCount/500);
push();
if (keyIsPressed === true) {
updatez = myz[i];
} else {
updatez = 100;
}
thenewy = cos(waveRipple) * amplitude + myy[i];
thenewz = 0;
directionalLight(wavecol/2, 200, 200, 50);
translate(myx[i], thenewy, thenewz + updatez);
var gradred = map(mouseX, 0, width, 0, 255);
var gradgreen = map(mouseX, 0, width, 0, 200);
fill(gradred, gradgreen, 200);
strokeWeight(0.2);
stroke("blue");
torus(12, 5);
pop();
}
}
}
//function to create existing toruses
function myTorus(x, y, z, st) {
this.x = x;
this.y = y;
this.z = z;
this.st = st;
this.display = function() {
if (this.st == 1) {
rotateY(frameCount/350);
push();
directionalLight(wavecol/2, 200, 200, 250);
translate(this.x, this.y, this.z * 3.5);
strokeWeight(0.2);
stroke("blue");
torus(oldpartsize, 5);
pop();
}
}
}
//click mouse to toggle between scenes
function mousePressed() {
changescene =! (changescene);
setup();
}
Instructions
Mouse Click: toggle between screens
Mouse move: manipulate wave; manipulate color of toruses
Press any key: add a new torus
Hold down any key: explode toruses
Statement
“Re:current” is a project utilizing 3D graphics from WEBGL in order to manipulate arrays and variables to create interactive cyclical experiences — 1. a “current” like nature of manipulating a wave of spheres using curves to mimic ocean-like wave that changes color over time and 2. a looping interaction of adding toruses which rotate around a 3. perennially rotating cube. My greatest struggle was working and adapting to the 3D landscape and nuances of WEBGL, and being able to translate the 2D elements we learned thus far onto my canvas. For my beginning prototypes, the biggest challenge I faced with creating an interactive project was being able to manipulate factors utilizing the mouse press and mouse pressed feature, because of how a mouse inherently creates an output of 2D, whereas my project would call for 3D. I resolved this issue to the best of my ability in this short term by opting to toggle between screens and making basic interactions using the mouse, and then for more detailed engagement I utilized the key pressed feature to generate random x, y, and z coordinates. For further exploration, I would love to explore with more dynamic ways of altering the canvas, ideally in ways to can imitate biomimicry, seeing that WEBGL is able to produce interestingly rendered outcomes with its different textures, lighting, and other attributes.
Screenshots
Some screenshots of my work!