-
Notifications
You must be signed in to change notification settings - Fork 81
/
sketch.js
120 lines (96 loc) · 3.08 KB
/
sketch.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
/*
Analyze the frequency spectrum with FFT (Fast Fourier Transform)
Draw a 1024 particles system that represents bins of the FFT frequency spectrum.
Example by Jason Sigal
*/
var mic, soundFile; // input sources, press T to toggleInput()
var fft;
var smoothing = 0.8; // play with this, between 0 and .99
var binCount = 1024; // size of resulting FFT array. Must be a power of 2 between 16 an 1024
var particles = new Array(binCount);
function setup() {
c = createCanvas(windowWidth, windowHeight);
noStroke();
soundFile = createAudio('../../music/Broke_For_Free_-_01_-_As_Colorful_As_Ever.mp3');
mic = new p5.AudioIn();
mic.start();
// initialize the FFT, plug in our variables for smoothing and binCount
fft = new p5.FFT(smoothing, binCount);
fft.setInput(mic);
// instantiate the particles.
for (var i = 0; i < particles.length; i++) {
var x = map(i, 0, binCount, 0, width * 2);
var y = random(0, height);
var position = createVector(x, y);
particles[i] = new Particle(position);
}
}
function draw() {
background(0, 0, 0, 100);
// returns an array with [binCount] amplitude readings from lowest to highest frequencies
var spectrum = fft.analyze(binCount);
// update and draw all [binCount] particles!
// Each particle gets a level that corresponds to
// the level at one bin of the FFT spectrum.
// This level is like amplitude, often called "energy."
// It will be a number between 0-255.
for (var i = 0; i < binCount; i++) {
var thisLevel = map(spectrum[i], 0, 255, 0, 1);
// update values based on amplitude at this part of the frequency spectrum
particles[i].update( thisLevel );
// draw the particle
particles[i].draw();
// update x position (in case we change the bin count while live coding)
particles[i].position.x = map(i, 0, binCount, 0, width * 2);
}
}
// ===============
// Particle class
// ===============
var Particle = function(position) {
this.position = position;
this.scale = random(0, 1);
this.speed = createVector(0, random(0, 10) );
this.color = [random(0, 255), random(0,255), random(0,255)];
}
var theyExpand = 1;
// use FFT bin level to change speed and diameter
Particle.prototype.update = function(someLevel) {
this.position.y += this.speed.y / (someLevel*2);
if (this.position.y > height) {
this.position.y = 0;
}
this.diameter = map(someLevel, 0, 1, 0, 100) * this.scale * theyExpand;
}
Particle.prototype.draw = function() {
fill(this.color);
ellipse(
this.position.x, this.position.y,
this.diameter, this.diameter
);
}
// ================
// Helper Functions
// ================
function windowResized() {
resizeCanvas(windowWidth, windowHeight);
background(0);
}
function keyPressed() {
if (key == 'T') {
toggleInput();
}
}
// To prevent feedback, mic doesnt send its output.
// So we need to tell fft to listen to the mic, and then switch back.
function toggleInput() {
if (soundFile.isPlaying() ) {
soundFile.pause();
mic.start();
fft.setInput(mic);
} else {
soundFile.play();
mic.stop();
fft.setInput(soundFile);
}
}