I am trying to convert a sketch to use node and bundle a distribution js file. My guess is that some of the function names in p5js must be reserved (to combat this I was going to use a development flag so as not to obfuscate the code at least for testing).
In order to encapsulate the code I am using this method:
let sketch = function(p) {
p.setup = function() {
...
}
let myp5 = new p5(sketch);
Everything seems to work fine except I cannot call the show function from inside my particle Class (ReferenceError: noStroke is not defined
)
Here is the full js:
let canvasBG;
let particles = [];
let audioFile;
let amplitude;
let vol;
let loaded = false;
let x = 0;
let xoff = 0;
let yoff = 0;
let sketch = function(p) {
p.setup = function() {
canvasBG = p.createCanvas(p.windowWidth, p.windowHeight);
audioFile = p.loadSound("audio/mom.mp3", p.audioLoaded);
amplitude = new p5.Amplitude();
p.rectMode(p.CENTER);
p.frameRate(30);
canvasBG.background(255);
}
p.audioLoaded = function() {
audioFile.play();
audioFile.loop();
loaded = true;
}
p.draw = function() {
let nx = p.noise(xoff) * p.windowWidth;
let ny = p.noise(yoff) * p.windowHeight;
xoff = xoff 0.01;
yoff = yoff 0.02;
vol = amplitude.getLevel();
let volumeGate = p.map(vol, 0, 1, p.random(5,12), p.random(80, 550));
if (loaded) {
let b = new Particle(nx, ny, volumeGate);
particles.push(b);
if (volumeGate > 75) {
canvasBG.background(p.random(255), p.random(255), p.random(255));
}
for (let particle of particles) {
particle.show();
}
if (particles.length >= 10) {
particles.splice(0, 1);
}
} else {
x = 0.05;
p.translate (p.windowWidth - 30, 30);
p.rotate(x);
p.noStroke();
p.rect(0, 0, 2, 40, 0.1);
p.fill(0, 0, 0, x * 3);
}
}
}
class Particle {
constructor(x, y, r) {
this.x = x;
this.y = y;
this.r = r;
}
show() {
noStroke(); // this is throwing an error
fill(random(0, 255), random(0, 255), random(0, 255), random(100,255));
ellipse(this.x, this.y, this.r * 2);
}
}
let myp5 = new p5(sketch);
You can run the current full demo here: https://editor.p5js.org/lharby/sketches/wPF908tqX
I've tried converting the class to a function and passing in arguments, similarly an object and then attaching a function to the object, but can't seem to get anything to work plus I would rather keep the Class as it is.
How is the best way to go about this?
CodePudding user response:
You're super close!
Because you're using p5 in instance mode, p5 functions (such as noStroke()
, fill()
, ellipse()
) won't be available in the global scope, but through the p
reference.
In your class you simply need to pass p
as well, similar to how you've already used it with the rest of the code:
class Particle {
constructor(x, y, r) {
this.x = x;
this.y = y;
this.r = r;
}
show(p) {
p.noStroke();
p.fill(p.random(0, 255), p.random(0, 255), p.random(0, 255), p.random(100,255));
p.ellipse(this.x, this.y, this.r * 2);
}
}
and in draw pass the reference to p5:
//...
for (let particle of particles) {
particle.show(p);
}
//...