Wait a few seconds… it’s loading! 🙂

Click to start! (Click mouse to see next visual)

```
//variables to load sound
var sound1;
var sound2;
var sound3;
var sound4;
var sound5;
var sound6;
//variable to switch between shapes and songs
var toggle = 0;
//variable for drawing astroid (toggle 2 shape)
var power = 33;
var r = 255;
function setup() {
createCanvas(500, 500, WEBGL);
amplitude = new p5.Amplitude();
frameRate(40);
}
function preload() {
sound1 = loadSound("https://courses.ideate.cmu.edu/15-104/f2018/wp-content/uploads/2018/12/york.mp3");
sound1.setVolume(1);
sound2 = loadSound("https://courses.ideate.cmu.edu/15-104/f2018/wp-content/uploads/2018/12/prettiestvirgin.mp3");
sound2.setVolume(1);
sound3 = loadSound("https://courses.ideate.cmu.edu/15-104/f2018/wp-content/uploads/2018/12/purity.mp3");
sound3.setVolume(1);
sound4 = loadSound("https://courses.ideate.cmu.edu/15-104/f2018/wp-content/uploads/2018/12/pizza.m4a");
sound4.setVolume(1);
sound5 = loadSound("https://courses.ideate.cmu.edu/15-104/f2018/wp-content/uploads/2018/12/Siamese_Sea.mp3");
sound5.setVolume(1);
sound6 = loadSound("https://courses.ideate.cmu.edu/15-104/f2018/wp-content/uploads/2018/12/perth.mp3");
sound6.setVolume(1);
}
function draw() {
background(0);
noFill();
stroke(255, 0 ,0);
//retrieves amplitude of song playing
var level = amplitude.getLevel();
//maps the amplitudes across values for use in shape later on
var twist = map(level, 0, .6, 0, .3);
var twist2 = twist * 15000;
//adjusts the size of the astroids
var twistSize = map(level, 0, .3, 75, 300);
//sophia's twists
var twisty1 = map(level, 0, 1, 0, .3);
var twisty2 = twisty1 * 5;
var twisty3 = twisty1 * 4;
//MIMI JIAO'S CODE
//first shape - Mimi's code
if (toggle === 1) {
rotateY(frameCount * twist / 100);
rotateX(frameCount * twist / 100);
rotateZ(frameCount * twist / 100);
for (var i = 0; i < twist2; i++) {
fill(i * sin(i), i * cos(i), 255);
beginShape();
vertex(i * cos(i), i, i - 1000);
vertex(i * .01, i * 0.1, i * .01);
vertex(i * sin(i), i * cos(i), i);
endShape(CLOSE);
}
}
//second shape (astroid) - Mimi's code
if (toggle === 2) {
rotateX(twist);
rotateY(twist);
rotateZ(twist);
//randomizes value so astroid will randomly be bright
var randomBright;
randomBright = random(255);
//first astroid
beginShape();
noFill();
for(var i = 0; i < twist2; i++) {
if (randomBright > 250) {
stroke(255, 0, 0);
} else {
stroke(twist * 900 * sin(i), twist * 300, sin(i) * twist * 900);
}
vertex(twistSize * (cos(i) ** power),
twistSize * (sin(i) ** power));
}
endShape();
//second astroid
push();
rotateZ(5);
rotateX(3);
rotateY(4);
beginShape();
noFill();
for(var i = 0; i < twist2; i++) {
stroke(twist * 300, twist * 900 * sin(i), sin(i) * twist * 900);
vertex(twistSize * (cos(i) ** power),
twistSize * (sin(i) ** power));
}
endShape();
pop();
//third astroid
push();
rotateZ(3);
rotateX(4);
rotateY(5);
beginShape();
noFill();
for(var i = 0; i < twist2; i++) {
if (randomBright > 250) {
stroke(255, 0, 0);
} else {
stroke(twist * 900 * sin(i), twist * 300, sin(i) * twist * 900);
}
vertex(twistSize * (cos(i) ** power),
twistSize * (sin(i) ** power));
}
endShape();
pop();
//fourth astroid
push();
rotateZ(4);
rotateX(3);
rotateY(5);
beginShape();
noFill();
for(var i = 0; i < twist2; i++) {
if (randomBright > 250) {
stroke(255, 0, 0);
} else {
stroke(twist * 900 * sin(i), twist * 300, sin(i) * twist * 900);
}
vertex(twistSize * (cos(i) ** power),
twistSize * (sin(i) ** power));
}
endShape();
pop();
//fifth astroid
push();
rotateZ(4);
rotateX(3);
rotateY(5);
beginShape();
noFill();
for (var i = 0; i < 250 * TWO_PI; i++) {
vertex(300 * (cos(i) ** power),
300 * (sin(i) ** power));
}
endShape();
pop();
}
//third shape - Mimi's code
if (toggle === 3) {
beginShape();
noFill();
//x and y coordinates
var x;
var y;
var t = TWO_PI;
var a = map(twist2, 0, width, 2, 10);
var n = map(twist2, 0, height, QUARTER_PI, HALF_PI);
var ma = map(a, 0, 200, 0, QUARTER_PI);
//shape1
push();
beginShape();
for(var i = 0; i < twist2; i++) {
noStroke();
fill(cos(twist2) * 100, cos(twist2) * 100, sin(twist2) * 100);
x = a * sin(ma) * ((n - 1) * cos(t) + cos((n - 1) * t)) / n;
y = a * sin(ma) * ((n - 1) * sin(t) - sin((n - 1) * t)) / n;
vertex(-i * sin(i), i * cos(i), i);
vertex(x, y);
t += QUARTER_PI;
}
endShape();
pop();
//shape2
push();
beginShape();
for(var i = 0; i < twist2; i++) {
noStroke();
fill(sin(twist2) * 100, cos(twist2) * 100, sin(twist2) * 100);
x = a * sin(ma) * ((n - 1) * cos(t) + cos((n - 1) * t)) / n;
rotateZ(-4);
y = a * sin(ma) * ((n - 1) * sin(t) - sin((n - 1) * t)) / n;
vertex(x, y);
vertex(i * sin(i) , i * cos(i), i);
t += HALF_PI;
}
endShape();
pop();
//accent shape3
push();
rotateX(frameCount * .003);
rotateY(frameCount * .004);
rotateZ(frameCount * .005);
beginShape();
for(var i = 0; i < twist2; i++) {
noStroke();
fill(sin(twist2) * 255, cos(twist2) * 255, sin(twist2) * 255);
x = a * sin(ma) * ((n - 1) * cos(t) + cos((n - 1) * t)) / n;
rotateZ(-4);
y = a * sin(ma) * ((n - 1) * sin(t) - sin((n - 1) * t)) / n;
vertex(x, y);
vertex(i * sin(i) , i * cos(i), i);
t += QUARTER_PI;
}
endShape();
pop();
}
//SOPHIA KIM's code below
// first "slide" for Sophia's Code - sphere
push();
if (toggle === 4) {
var radiusSphere1 = twisty2 * 200;
fill(232, 0, 0);
noStroke();
rotateY(frameCount * twisty2 / 1000);
rotateX(frameCount * twisty2 / 1000);
rotateZ(frameCount * twisty2 / 1000);
sphere(radiusSphere1);
var constrainR = constrain(mouseX, radiusSphere1, radiusSphere1);
fill('yellow');
noStroke();
rotateY(frameCount * twisty2 / 500);
rotateX(frameCount * twisty2 / 500);
rotateZ(frameCount * twisty2 / 500);
sphere(constrainR);
}
pop();
//first "slide" - lines behind the sphere
push();
if (toggle === 4) {
for (var i = 0; i < twisty2 * 1000; i++) {
stroke('red');
beginShape();
vertex(i * cos(i), i, i - 2000);
vertex(i * .01, i * 0.09, i * .1);
vertex(i * sin(i) , i * cos(i), i / 100);
endShape(CLOSE);
stroke('orange');
beginShape();
vertex(i * cos(i), i, i - 2000);
vertex(i * .01, i * 0.05, i * .1);
vertex(i * sin(i), i * cos(i), i / 500);
endShape(CLOSE);
}
}
pop();
//2nd "slide" for Sophia's code - lines
push();
if (toggle === 5) {
var Rfor2 = random(twisty2 * 140, 255);
var Gfor2 = random(twisty2 * 140, 255);
for (var i = 0; i < twisty2 * 3000; i++) {
stroke(Rfor2, Gfor2, 230);
strokeWeight(.4);
beginShape();
vertex(i * sin(i / 10), tan(sin(i / 20)) * 10);
vertex(i * sin(i / 20), sin(i / 100) * 20, cos(i / 50));
vertex(tan(i / 10), cos(i / 100), cos(i * 100));
vertex(sin(i / 20), tan(i / 50) * 40, sin(i * 5) / 20);
endShape(CLOSE);
}
}
pop();
//3rd "slide" for Sophia's code -
//multiple circles moving around
push();
if (toggle === 6) {
for(var j = 0; j < 4; j++){
var Rfor3 = random(twisty3 * 200, 255);
stroke(Rfor3, 100, 240);
for(var i = 0; i < twisty3 * 3000; i++){
translate(sin(twisty3 * 0.4 + j) * 20,
sin(twisty3 * 0.1 + j) * 20, i * 3);
rotateX(frameCount * .3 / 5000 / twisty3);
rotateY(frameCount * .2 / twisty3 / 100);
rotateZ(frameCount * .5 / twisty3 / 300);
push();
sphere(14, 7, 5);
pop();
}
}
}
pop();
}
function mousePressed() {
//reset to first shape/song after 6th song
if (toggle < 6) {
toggle ++;
} else {
toggle = 1;
}
//play songs based on mouse click sequence
if (toggle === 1) {
sound1.play();
sound6.stop();
}
if (toggle === 2) {
sound2.play();
sound1.stop();
}
if (toggle === 3) {
sound3.play();
sound2.stop();
}
if (toggle === 4) {
sound4.play();
sound3.stop();
}
if (toggle === 5) {
sound5.play();
sound4.stop();
}
if (toggle === 6) {
sound6.play();
sound5.stop();
}
}
```

For the final project, we created various types of visuals that respond to different songs’ amplitude levels. We were interested in exploring how sound can be translated visually and wanted to challenge ourselves and try something new. So instead of using 2D, we decided to explore the basics of 3D with WEBGL.

We wanted to further explore sound and graphics as one, so we wanted to directly tie the image of the graphics to the amplitude of the music playing. We used shapes like spheres, and beginShape/endShape to create the visuals and played around with implementing trigonometric functions to create curves and other shapes. We wanted to create something that the viewer could flip through, so we made this click-through visual presentation. By clicking on the mouse, the user is able to see different visuals each with its own song.

Have fun and we hope you enjoy it 🙂