使用3D引擎threeJS实现星空粒子移动效果


Posted in Javascript onSeptember 13, 2020

three.js是JavaScript编写的WebGL第三方库。提供了非常多的3D显示功能。Three.js 是一款运行在浏览器中的 3D 引擎,你可以用它创建各种三维场景,包括了摄影机、光影、材质等各种对象。

下载地址: http://threejs.org/

首先创建一个HTML文件,引入three.js引擎包.

<!DOCTYPE HTML>
<html>
 <head>
 <meta charset="utf-8">
 <title>Three.js实现3D空间粒子效果</title>
 <style type="text/css">
 body{
 background-color:#000000;
 margin:0px;
 overflow:hidden;
 }
 </style>
 <script src="scripts/three.js"></script>
 </head>
 <body >
 </body>
</html>

声明全局变量

//定义应用所需的组件:相机,场景,渲染器
 var camera, scene, renderer;
 //跟踪鼠标的位置
 var mouseX = 0, mouseY = 0;
 //定义存储粒子的数组
 var particles = [];

相机:

OpenGL(WebGL)中、三维空间中的物体投影到二维空间的方式中,存在透视投影和正投影两种相机。
透视投影就是、从视点开始越近的物体越大、远处的物体绘制的较小的一种方式、和日常生活中我们看物体的方式是一致的。
正投影就是不管物体和视点距离,都按照统一的大小进行绘制、在建筑和设计等领域需要从各个角度来绘制物体,因此这种投影被广泛应用。
在 Three.js 也能够指定透视投影和正投影两种方式的相机。

场景:

场景就是一个三维空间。 用 [Scene] 类声明一个叫 [scene] 的对象。

渲染器:
三维空间里的物体映射到二维平面的过程被称为三维渲染。 一般来说我们都把进行渲染的操作叫做渲染器。

数据初始化

//数据初始化
 function init(){
 //相机参数:
 //四个参数值分别代表:视野角:fov 纵横比:aspect 相机离视体最近的距离:near 相机离视体最远的距离:far
 camera = new THREE.PerspectiveCamera(80, window.innerWidth / window.innerHeight, 1, 4000 );
 //设置相机位置,默认位置为:0,0,0. 
 camera.position.z = 1000;

 //声明场景
 scene = new THREE.Scene();
 //将相机装加载到场景
 scene.add(camera);

 //生成渲染器的对象
 renderer = new THREE.CanvasRenderer();
 //设置渲染器的大小
 renderer.setSize( window.innerWidth, window.innerHeight );
 //追加元素
 document.body.appendChild(renderer.domElement);
 //调用自定义的生成粒子的方法
 makeParticles();
 //添加鼠标移动监听
 document.addEventListener('mousemove',onMouseMove,false);
 //设置间隔调用update函数,间隔次数为每秒30次
 setInterval(update,1000/30);
 }

相机初始化说明:

实例中使用的是透视投影. var camera = new THREE.PerspectiveCamera( fov , aspect , near , far );

透视投影中,会把称为视体积领域中的物体作成投影图。 视体积是通过以下4个参数来指定。

视野角:fov

纵横比:aspect

相机离视体积最近的距离:near

相机离视体积最远的距离:far

设置相机的位置:

相机的位置坐标和视野的中心坐标,按照

 //设置相机的位置坐标

camera.position.x = 100;


camera.position.y = 20;


camera.position.z = 50;

方式进行设置。 和该方式一样,下面这样的方法也可以
 camera.position.set(100,20,50);

此外还可以设置相机的上方向,视野中心等,
设置相机的上方向为正方向: 

camera.up.x = 0;
camera.up.y = 0;
camera.up.z = 1;

设置相机的视野中心 

利用[lookAt]方法来设置相机的视野中心。 「lookAt()」的参数是一个属性包含中心坐标「x」「y」「z」的对象。   

「lookAt()」方法不仅是用来设置视点的中心坐标、 在此之前设置的相机属性要发生实际作用,也需要调用 [lookAt] 方法。

使用3D引擎threeJS实现星空粒子移动效果

其他投影方式

在 Three.js 中、有各种各样的类,用来来实现透视投影、正投影或者复合投影(透视投影和正投影)这样的相机。

var camera = THREE.OrthographicCamera = function ( left, right, top, bottom, near, far ) //正投影
var camera = THREE.CombinedCamera = function ( width, height, fov, near, far, orthonear, orthofar ) //?合投影

渲染器

创建CanvasRenderer对象.这是一个普通的2D画布对象,实例中我们添加到body标签中. 否则我们就不会看到它。我们想让它充满整个浏览器窗口,所以我们设置其大小为window.innerwidth和window.innerheight。

鼠标监听

使用自定义函数makeParticles()创建粒子,并为其添加mousemove侦听器来跟踪鼠标的位置,最后我们建立一个间隔调用update函数一秒30次。
update函数中的定义如下:

function update() {
 updateParticles();
 renderer.render( scene, camera );
 }

产生粒子的函数

//定义粒子生成的方法
 function makeParticles(){
 
 var particle,material;
 //粒子从Z轴产生区间在-1000到1000
 for(var zpos=-1000;zpos<1000;zpos+=20){
 //we make a particle material and pass through the colour and custom particle render function we defined. 
 material = new THREE.ParticleCanvasMaterial( { color: 0xffffff, program: particleRender } );
 //生成粒子
 particle = new THREE.Particle(material);
 //随即产生x轴,y轴,区间值为-500-500
 particle.position.x = Math.random()*1000-500;
 particle.position.y = Math.random()*1000-500;
 //设置z轴
 particle.position.z = zpos;
 //scale it up a bit
 particle.scale.x = particle.scale.y = 10;
 //将产生的粒子添加到场景,否则我们将不会看到它
 scene.add(particle);
 //将粒子位置的值保存到数组
 particles.push(particle);
 }
 }

math . random()返回一个浮点数在0和1之间,我们乘以1000,给了我们一个0到1000之间的数字。然后我们减去500,这给了我们一个号码在-500和500之间.我们也可以这样定义一个生成范围区间内随机值的函数

function randomRange(min, max) { 
 return Math.random()*(max-min) + min; 
}

绘制粒子的函数

//定义粒子绘制函数
 function particleRender( context ) {
 //获取canvas上下文的引用
 context.beginPath();
 // and we just have to draw our shape at 0,0 - in this
 // case an arc from 0 to 2Pi radians or 360º - a full circle!
 context.arc( 0, 0, 1, 0, Math.PI * 2, true );
 //设置原型填充
 context.fill();
 }

定义粒子移动的函数,这里设置成移动速度随着鼠标距离Y轴0点的值越大,粒子移动越快

//移动粒子的函数
 function updateParticles(){
 
 //遍历每个粒子
 for(var i=0; i<particles.length; i++){
 particle = particles[i];
 //设置粒子向前移动的速度依赖于鼠标在平面Y轴上的距离
 particle.position.z += mouseY * 0.1;
 //如果粒子Z轴位置到1000,将z轴位置设置到-1000,即移动到原点,这样就会出现无穷尽的星域效果.
 if(particle.position.z>1000){
  particle.position.z-=2000; 
 }
 }
 }

鼠标移动时函数监听

//鼠标移动时调用
 function onMouseMove(event){
 mouseX = event.clientX;
 mouseY = event.clientY;
 }

至此,空间粒子简单效果学习完毕.

整合代码如下:

<!DOCTYPE HTML>
<html>
 <head>
 <meta charset="utf-8">
 <title>Three.js实现3D空间粒子效果</title>
 <style type="text/css">
 body{
 background-color:#000000;
 margin:0px;
 overflow:hidden;
 }
 </style>
 <script src="scripts/three.js"></script>
 <script>
 //定义应用所需的组件:相机,场景,渲染器
 var camera, scene, renderer;
 //跟踪鼠标的位置
 var mouseX = 0, mouseY = 0;
 //定义存储粒子的数组
 var particles = [];
 
 //数据初始化
 function init(){
 //相机参数:
 //四个参数值分别代表:视野角:fov 纵横比:aspect 相机离视体最近的距离:near 相机离视体最远的距离:far
 camera = new THREE.PerspectiveCamera(80, window.innerWidth / window.innerHeight, 1, 4000 );
 //设置相机位置,默认位置为:0,0,0. 
 camera.position.z = 1000;

 //声明场景
 scene = new THREE.Scene();
 //将相机装加载到场景
 scene.add(camera);
 
 //生成渲染器的对象
 renderer = new THREE.CanvasRenderer();
 //设置渲染器的大小
 renderer.setSize( window.innerWidth, window.innerHeight );
 //追加元素
 document.body.appendChild(renderer.domElement);
 //调用自定义的生成粒子的方法
 makeParticles();
 //添加鼠标移动监听
 document.addEventListener('mousemove',onMouseMove,false);
 //设置间隔调用update函数,间隔次数为每秒30次
 setInterval(update,1000/30);
 }
 
 function update() {
 //调用移动粒子的函数
 updateParticles();
 //重新渲染
 renderer.render( scene, camera );
 }

 //定义粒子生成的方法
 function makeParticles(){
 
 var particle,material;
 //粒子从Z轴产生区间在-1000到1000
 for(var zpos=-1000;zpos<1000;zpos+=20){
  //we make a particle material and pass through the colour and custom particle render function we defined. 
  material = new THREE.ParticleCanvasMaterial( { color: 0xffffff, program: particleRender } );
  //生成粒子
  particle = new THREE.Particle(material);
  //随即产生x轴,y轴,区间值为-500-500
  particle.position.x = Math.random()*1000-500; //math . random()返回一个浮点数在0和1之间
  particle.position.y = Math.random()*1000-500;
  //设置z轴
  particle.position.z = zpos;
  //scale it up a bit
  particle.scale.x = particle.scale.y = 10;
  //将产生的粒子添加到场景
  scene.add(particle);
  //将粒子位置的值保存到数组
  particles.push(particle);
 }
 }

 //定义粒子渲染器
 function particleRender( context ) {
 //获取canvas上下文的引用
 context.beginPath();
 // and we just have to draw our shape at 0,0 - in this
 // case an arc from 0 to 2Pi radians or 360º - a full circle!
 context.arc( 0, 0, 1, 0, Math.PI * 2, true );
 //设置原型填充
 context.fill();
 }

 
 //移动粒子的函数
 function updateParticles(){
 
 //遍历每个粒子
 for(var i=0; i<particles.length; i++){
  particle = particles[i];
  //设置粒子向前移动的速度依赖于鼠标在平面Y轴上的距离
  particle.position.z += mouseY * 0.1;
  //如果粒子Z轴位置到1000,将z轴位置设置到-1000
  if(particle.position.z>1000){
  particle.position.z-=2000; 
  }
 }
 }
 
 //鼠标移动时调用
 function onMouseMove(event){
 mouseX = event.clientX;
 mouseY = event.clientY;
 }
 </script>
 </head>
 <body onload="init()">
 </body>
</html>

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持三水点靠木。

Javascript 相关文章推荐
多选列表框动态添加,移动,删除,全选等操作的简单实例
Jan 13 Javascript
jquery五角星评分插件示例分享
Feb 21 Javascript
javascript实现类似超链接的效果
Dec 26 Javascript
jquery通过closest选择器修改上级元素的方法
Mar 17 Javascript
js实现点击按钮后给Div图层设置随机背景颜色的方法
May 06 Javascript
js性能优化技巧
Nov 29 Javascript
js 判断一个数字是不是2的n次方幂的实例
Nov 26 Javascript
仿淘宝JSsearch搜索下拉深度用法
Jan 15 Javascript
jquery 实现拖动文件上传加载进度条功能
Mar 18 jQuery
javascript、php关键字搜索函数的使用方法
May 29 Javascript
jQuery常见的遍历DOM操作详解
Sep 05 jQuery
highcharts.js数据绑定方式代码实例
Nov 13 Javascript
vue.js项目打包上线的图文教程
Nov 16 #Javascript
Three.js基础学习教程
Nov 16 #Javascript
three.js实现3D视野缩放效果
Nov 16 #Javascript
three.js中3D视野的缩放实现代码
Nov 16 #Javascript
js的函数的按值传递参数(实例讲解)
Nov 16 #Javascript
React/Redux应用使用Async/Await的方法
Nov 16 #Javascript
详谈DOM简介及节点、属性、查找节点的方法
Nov 16 #Javascript
You might like
全国FM电台频率大全 - 8 黑龙江省
2020/03/11 无线电
MOTOROLA 摩托罗拉 MODEL 66-XI五灯中波收音机
2021/03/02 无线电
在命令行下运行PHP脚本[带参数]的方法
2010/01/22 PHP
php实现网站顶踩功能的完整前端代码
2015/07/19 PHP
thinkphp3.2框架中where条件查询用法总结
2019/08/13 PHP
高性能Javascript笔记 数据的存储与访问性能优化
2012/08/02 Javascript
javascript:window.open弹出窗口的位置问题
2014/03/18 Javascript
node.js中的fs.fsyncSync方法使用说明
2014/12/15 Javascript
js实现简单的可切换选项卡效果
2015/04/10 Javascript
深入浅析search 搜索框的写法
2016/08/02 Javascript
Vue+Element使用富文本编辑器的示例代码
2017/08/14 Javascript
vue与vue-i18n结合实现后台数据的多语言切换方法
2018/03/08 Javascript
vue全局组件与局部组件使用方法详解
2018/03/29 Javascript
vue轮播组件实现$children和$parent 附带好用的gif录制工具
2019/09/26 Javascript
jQuery操作元素的内容和样式完整实例分析
2020/01/10 jQuery
动态实现element ui的el-table某列数据不同样式的示例
2021/01/22 Javascript
从零学Python之入门(二)基本数据类型
2014/05/25 Python
python在linux系统下获取系统内存使用情况的方法
2015/05/11 Python
用Python删除本地目录下某一时间点之前创建的所有文件的实例
2017/12/14 Python
python实现泊松图像融合
2018/07/26 Python
解决Django layui {{}}冲突的问题
2019/08/29 Python
python3 pillow模块实现简单验证码
2019/10/31 Python
Pytorch 实现权重初始化
2019/12/31 Python
python实现吃苹果小游戏
2020/03/21 Python
浅谈Python描述数据结构之KMP篇
2020/09/06 Python
python对批量WAV音频进行等长分割的方法实现
2020/09/25 Python
李维斯德国官方网上商店:Levi’s德国
2016/09/10 全球购物
怎样在程序里获得一个空指针
2015/01/24 面试题
应届毕业生求职信范文分享
2013/12/26 职场文书
致铅球运动员加油稿
2014/02/13 职场文书
商务日语专业的自荐信
2014/05/23 职场文书
优秀班主任经验交流材料
2014/06/02 职场文书
新教师个人工作总结
2015/02/06 职场文书
2015年街道办事处团委工作总结
2015/10/14 职场文书
大学生干部培训心得体会
2016/01/06 职场文书
新手入门Mysql--sql执行过程
2021/06/20 MySQL