p5实现三维细胞粒子生命周期轨迹动画效果代码

代码语言:html

所属分类:粒子

代码描述:p5实现三维细胞粒子生命周期轨迹动画效果代码

代码标签: p5 三维 细胞 粒子 生命 周期 轨迹 动画

下面为部分代码预览,完整代码请点击下载或在bfwstudio webide中打开

<!DOCTYPE html>
<html lang="en" >

<head>
  <meta charset="UTF-8">
  

  
  
  
<style>
* { margin:0; padding:0; } 
html, body { width:100%; height:100%; overflow: hidden; background:black;} 
canvas { display:block; }
#controls {
  z-index: 2;
  margin: 20px;
  position: absolute;
  top: 0; left: 0;
  color: white;
}
</style>

</head>
<body oncontextmenu="return false;">
  <div id="controls"></div>
</body>
<script type="text/javascript" src="//repo.bfw.wiki/bfwrepo/js/p5.0.10.2.js"></script>
      <script  >
let numTypes  = 5;
let goalTypes = 5;
let drag      = .15;
let numPoints = 1000;
let maxTypes  = 20;

let rInt = (b, a=0) => Math.floor(Math.random()*(b-a) + a);

class Vec3{
  constructor(x, y, z, r=10){
    this.x = x;
    this.y = y;
    this.z = z;
    this.r = r;
  }
  op(p, f){
    this.x = f(this.x, p.x != undefined ? p.x : p);
    this.y = f(this.y, p.y != undefined ? p.y : p);
    this.z = f(this.z, p.z != undefined ? p.z : p);
    return this;
  }
  plus  (p){return this.op(p, (a, b) => a + b)}
  minus (p){return this.op(p, (a, b) => a - b)}
  times (p){return this.op(p, (a, b) => a * b)}
  div   (p){return this.op(p, (a, b) => a / b)}
  distTo(p){return Math.hypot(this.x-p.x, this.y-p.y, this.x-p.z)}
  mag    (){return Math.hypot(this.x, this.y, this.z)}
  clone  (){return new Vec3(this.x, this.y, this.z, this.r)}
  rotateX(a){
    let {x, y, z} = this;
    [x, y, z] = [
      x,
      cos(a)*y - sin(a)*z,
      sin(a)*y + cos(a)*z,
    ];
    Object.assign(this, {x, y, z});
  }
  rotateY(a){
    let {x, y, z} = this;
    [x, y, z] = [
      cos(a)*x + sin(a)*z,
      y, 
      cos(a)*z - sin(a)*x,
    ];
    Object.assign(this, {x, y, z});
  }
  rotateZ(a){
    let {x, y, z} = this;
    [x, y, z] = [
      cos(a)*x - sin(a)*y,
      cos(a)*x + sin(a)*y,
      z, 
    ];
    Object.assign(this, {x, y, z});
  }
  updateRotation(){
    let p = this.clone();
    p.rotateY(-rotX);
    p.rotateX(-rotY);
    this.screenCoord = [p.x, p.y];
    this.depth = p.z;
  }
  render(fc=.5, sc = 1){
    fill(fc);
    stroke(sc);
    strokeWeight(1);
    ellipse(...this.screenCoord, this.r);
  }
}

let points = [];
let r = (n) => random(-n, n);
let v3 = (x, y, z) => new Vec3(x, y, z);
let l3 = (p1, p2, c) => new Line(p1, p2, c);
let rPoint = (n) => v3(r(n), r(n), r(n));

let logged = false;
class Particle{
  constructor({pos=v3(0, 0, 0), vel=v3(0, 0, 0), type=random()}){
    Object.assign(this, {pos, vel, type});
  }
  addForce(p){
    let entry = controlGrid[floor(this.type*numTypes)][floor(p.type*numTypes)];
    let dx = this.pos.x-p.pos.x;
    let dy = this.pos.y-p.pos.y;
    let dz = this.pos.z-p.pos.z;
    let d  = dx*dx + dy*dy + dz*dz;
    let f  = ((entry.goalDist*100)**2-d);
    
    let ddx = dx*f*.001/d;
    let ddy = dy*f*.001/d;
    let ddz = dz*f*.001/d;
    
    this.vel.x += ddx + ddx*entry.strafe[0] + ddz*entry.strafe[1] - ddy*entry.strafe[2];
    this.vel.y += ddy - ddz*entry.strafe[0] + ddy*entry.strafe[1] + ddx*entry.strafe[2];
    this.vel.z += ddz + ddy*entry.strafe[0] - ddx*entry.strafe[1] + ddz*entry.strafe[2];
  }
  update(){
    let d = this.vel.mag();
    d = max(d, 3)/3;

    let v = this.vel.clone().div(d);
    this.pos.plus(v);
    this.vel.times(drag);
  }
  render(nd, md){
    let bal = (this.pos.depth+nd)/(md-nd);
    bal = bal+1;
    
    fill(floor(this.type*numTypes)/numTypes, bal*.5 + .5, bal*.5 + .5, bal*.5 + .5);
    ellipse(this.pos.screenCoord[0]*(bal*.5 + .5)*1.2, this.pos.screenCoord[1]*(bal*.5 + .5)*1.2, 5+bal*5);
  }
}

function setup (){
  pixelDensity(1);
  createCanvas();
  colorMode(HSB, 1, 1, 1);
  window.controlGrid = makeControlGrid();
  window.goalGrid    = makeControlGrid();
  windowResized();
  init();
}

let init = () => {
  points = [];
  let size.........完整代码请登录后点击上方下载按钮下载查看

网友评论0