Perlin噪声生成烟雾
一、实验内容:
和鼠标交互结合生成Perlin Noise的烟雾效果
要求使用p5.js实现烟雾随机生成效果:
- 流场利用Perlin噪声实现;(30分)
- 粒子按照流场运动;(30分)
- 速度、数量等可由参数控制;(15分)(HTML页面交互传递参数8分,代码中变量控制7分)
- 使用类来实现粒子;(15分)
- 文档和注释清楚;(10分)
提交工程目录压缩的zip或者rar,以及一个readme.txt简要说明实现思路和重要参数的功能
二、实验说明:
所有实验是通过 Visual Studio Code引入p5.js包编写,所以首先要去p5.js官网下载相关包,或是在联网状态下把html中引入包的代码改成例如<script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.1.9/p5.js"></script>等。
三、实验代码:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="utf-8"> <title>噪声提交</title> <script src="https://cdnjs.cloudflare.com/ajax/libs/p5.js/1.1.9/p5.js"></script> </head> <body> <input type="text" id="inputBox" placeholder="输入数量1-5000"> <!-- <input type="submit" id="submit"> --> <input type="text" id="inputBox2" placeholder="输入速度1-10"> <!-- <input type="submit" id="submit2"> --> <input type="submit" id="submit" value="确认" > <script src="sketch.js"></script> </body> </html>
var scl=10;//每行每列格子数量 var inc=0.1; var rows,cols; var zoff=0; var particles=[]; var flowfield; var speed=1;//速度 //数量 let input = document.getElementById("inputBox"); //速度 let input_1 = document.getElementById("inputBox2"); //按钮 let submit = document.getElementById("submit"); submit.onmousedown = function (e) { //速度 speed=parseInt(input_1.value); //清空数组 particles.splice(0,particles.length); for(var i=0;i<parseInt(input.value);i++){ particles[i]=new Particle(); } clear(); } function setup() { createCanvas(400,400); cols=floor(width/scl); rows=floor(height/scl); flowfield=new Array(cols*rows); // for(var i=0;i<500;i++){ // particles[i]=new Particle(); // } background(255); } function draw() { var yoff=0; for(var y=0;y<rows;y++){ var xoff=0; for(var x=0;x<cols;x++){ var index=x+y*cols; //乘4是为了放大噪声生成的angle值可以使粒子更加的分散 var angle=noise(xoff,yoff,zoff)*TWO_PI*4; var v=p5.Vector.fromAngle(angle); v.setMag(2); flowfield[index]=v; xoff+=inc; } yoff+=inc; zoff+=0.0005; } for(var i=0;i<particles.length;i++){ particles[i].follow(flowfield); particles[i].update(); particles[i].edges(); particles[i].show(); } } function Particle(){ this.pos=createVector(random(width),random(height));//起始位置 this.vel=createVector(0,0);//初速度 this.acc=createVector(0,0);//初加速度 this.maxspeed=speed;//速度上限 this.prevPos=this.pos.copy(); this.update=function(){ this.vel.add(this.acc); this.vel.limit(this.maxspeed); this.pos.add(this.vel); this.acc.mult(0); } this.follow=function(vectors){ var x=floor(this.pos.x/scl); var y=floor(this.pos.y/scl); var index=x+y*cols; var force=vectors[index]; this.applyForce(force); } this.applyForce=function(force){ this.acc.add(force); } this.show=function(){ stroke(0,5); strokeWeight(1); //用线连接粒子 line(this.pos.x,this.pos.y,this.prevPos.x,this.prevPos.y); this.updataPrev(); } //更新上一粒子位置 this.updataPrev=function(){ this.prevPos.x=this.pos.x; this.prevPos.y=this.pos.y; } //使粒子在画布范围内 this.edges=function(){ if(this.pos.x<0) { this.pos.x=width; this.updataPrev(); } if(this.pos.x>width) { this.pos.x=0; this.updataPrev(); } if(this.pos.y<0) { this.pos.y=height; this.updataPrev(); } if(this.pos.y>height) { this.pos.y=0; this.updataPrev(); } } }
四、实验结果:
编辑
编辑
编辑
根据实验代码,先实现普通随机生成的网格色块,再实现柏林噪声生成的网格色块。
为每个方格绘制方向线,再为绘制方向线变化赋予一个柏林噪声,让方向线动起来。
然后构造Particle类来实现烟雾效果。
根据上个实验思路,添加输入框及按钮,可以赋予不同的数量以及生成烟雾的速度。
添加按钮功能,以及draw函数中使用Particles类中函数的补写。
各个代码的作用在代码中有注释。