# パーティクルでいろいろな形をつくる

```/**
* morph by particles
*
* @author aa_debdeb
* @date 2016/08/19
*/

int state = 0;
ArrayList<Particle> particles;

void setup(){
size(500, 500, P3D);
particles = new ArrayList<Particle>();
for(int i = 0; i < 5000; i++){
}
}

void draw(){
background(0);
stroke(255, 0, 255);
translate(width / 2, height / 2);
rotateX(frameCount * 0.005);
rotateY(frameCount * 0.010);
rotateZ(frameCount * 0.015);
for(Particle p: particles){
p.display();
p.update();
}
}

void mousePressed(){
state += 1;
if(state == 4){
state = 0;
}
for(Particle p: particles){
p.impact();
p.setPos();
}
}

class Particle{

PVector pos, loc, vel;

Particle(){
float locSize = map(sqrt(random(1)), 0, 1, 0, 500);
float locAng1 = random(PI);
float locAng2 = random(TWO_PI);
float x = locSize * sin(locAng1) * cos(locAng2);
float y = locSize * cos(locAng1);
float z = locSize * sin(locAng1) * sin(locAng2);
loc = new PVector(x, y, z);
impact();
setPos();
}

void impact(){
float velSize = random(5, 10);
float velAng1 = random(PI);
float velAng2 = random(TWO_PI);
float vx = velSize * sin(velAng1) * cos(velAng2);
float vy = velSize * cos(velAng1);
float vz = velSize * sin(velAng1) * sin(velAng2);
vel = new PVector(vx, vy, vz);
}

void setPos(){
float posSize, px, py, pz;
switch(state){
case 0: // sphere
posSize = 100;
float posAng1 = random(PI);
float posAng2 = random(TWO_PI);
px = posSize * sin(posAng1) * cos(posAng2);
py = posSize * cos(posAng1);
pz = posSize * sin(posAng1) * sin(posAng2);
pos = new PVector(px, py, pz);
break;
case 1: // cube
float r = random(1);
float e = 70;
if(r < 0.33){
px = random(1) < 0.5 ? e: -e;
py = random(-e, e);
pz = random(-e, e);
} else if(r < 0.66){
px = random(-e, e);
py = random(1) < 0.5 ? e: -e;
pz = random(-e, e);
} else {
px = random(-e, e);
py = random(-e, e);
pz = random(1) < 0.5 ? e: -e;
}
pos = new PVector(px, py, pz);
break;
case 2: // rectangle
px = random(-70, 70);
py = random(-70, 70);
pz = 0;
pos = new PVector(px, py, pz);
break;
case 3:
posSize = map(sqrt(random(1)), 0, 1, 0, 100);
float posAng = random(TWO_PI);
px = posSize * cos(posAng);
py = posSize * sin(posAng);
pz = 0;
pos = new PVector(px, py, pz);
break;
}
}

void display(){
point(loc.x, loc.y, loc.z);
}

void update(){
PVector acc = PVector.sub(pos, loc);
acc.limit(0.1);