xxxxxxxxxx
182
flock = [];
let sizeX = 100;
let sizeY = 100;
let sizeZ = 100;
let gap = 20;
let num = 120;
let timer = 800;
let count = 0;
let alignSlider, cohesionSlider, separationSlider;
function setup() {
createCanvas(windowWidth, windowHeight, WEBGL);
alignSlider = createSlider(0, 5, 1, 0.1);
cohesionSlider = createSlider(0, 5, 1, 0.1);
separationSlider = createSlider(0, 5, 1, 0.1);
for(let i = 0; i < num; i++){
flock.push(new Boid());
}
}
function draw() {
background(20);
push();
rotateY(frameCount*0.01);
noFill();
stroke(225);
strokeWeight(1);
box(sizeX, sizeY, sizeZ);
strokeWeight(1);
box(sizeX+gap, sizeY+gap, sizeZ+gap);
for (let boid of flock){
boid.flock(flock);
boid.border();
boid.update();
boid.show();
}
pop();
if(count%timer == 0){
reset();
}
count = count + 1;
}
function reset(){
flock = [];
for(let i = 0; i < num; i++){
flock.push(new Boid());
}
}
class Boid{
constructor(){
this.position = createVector(random(-sizeX/2,sizeX/2), random(-sizeY/2, sizeY/2), random(-sizeZ/2,sizeZ/2));
this.velocity = p5.Vector.random3D();
this.velocity.setMag(random(0.1,0.3));
this.acceleration = createVector();
this.maxForce = 0.1;
this.maxSpeed = 0.5;
this.coloring = p5.Vector.random3D().setMag(255);
this.sizing = random(10,30);
}
align(boids){
let perceptionRadius = 10;
let steering = createVector();
let total = 0;
for(let other of boids){
let d = dist(this.position.x, this.position.y, this.position.z, other.position.x, other.position.y,other.position.z);
if(other != this && d < perceptionRadius){
steering.add(other.velocity);
total++;
}
}
if(total > 0){
steering.div(total);
steering.setMag(this.maxSpeed);
steering.sub(this.velocity);
steering.limit(this.maxForce);
}
return steering;
}
cohesion(boids){
let perceptionRadius = 20;
let steering = createVector();
let total = 0;
for(let other of boids){
let d = dist(this.position.x, this.position.y, this.position.z, other.position.x, other.position.y,other.position.z);
if(other != this && d < perceptionRadius){
steering.add(other.position);
total++;
}
}
if(total > 0){
steering.div(total);
steering.sub(this.position);
steering.setMag(this.maxSpeed);
steering.sub(this.velocity);
steering.limit(this.maxForce);
}
return steering;
}
separation(boids){
let perceptionRadius = 10;
let steering = createVector();
let total = 0;
for(let other of boids){
let d = dist(this.position.x, this.position.y, this.position.z, other.position.x, other.position.y,other.position.z);
if(other != this && d < perceptionRadius){
let diff = p5.Vector.sub(this.position, other.position);
diff.div(d);
steering.add(diff);
total++;
}
}
if(total > 0){
steering.div(total);
steering.setMag(this.maxSpeed);
steering.sub(this.velocity);
steering.limit(this.maxForce);
}
return steering;
}
flock(boids){
let alignment = this.align(boids);
let cohesion = this.cohesion(boids);
let separation = this.separation(boids);
alignment.mult(alignSlider.value());
cohesion.mult(cohesionSlider.value());
separation.mult(separationSlider.value());
this.acceleration.add(alignment);
this.acceleration.add(cohesion);
this.acceleration.add(separation);
}
update(){
this.position.add(this.velocity);
this.velocity.add(this.acceleration);
this.velocity.limit(this.maxSpeed);
this.acceleration.mult(0);
}
border(){
if(this.position.x > sizeX/2) this.position.x = -sizeX/2;
if(this.position.x < -sizeX/2) this.position.x = sizeX/2;
if(this.position.y > sizeY/2) this.position.y = -sizeY/2;
if(this.position.y < -sizeY/2) this.position.y = sizeY/2;
if(this.position.z > sizeZ/2) this.position.z = -sizeZ/2;
if(this.position.z < -sizeZ/2) this.position.z = sizeZ/2;
}
show(){
strokeWeight(this.sizing);
stroke(this.coloring.x, this.coloring.y, this.coloring.z,200);
point(this.position.x, this.position.y, this.position.z);
}
}