学习ThreeJs

325 阅读2分钟

学习ThreeJs

Three.js是基于原生WebGL封装运行的三维引擎,在所有WebGL引擎中,Three.js是国内文资料最多、使用最广泛的三维引擎。

本文章为记录,若有大佬看到请不吝指点。

首先先安装引入ThreeJs

安装: `npm install three --save `,注意这里使用`import`引入会报错,发现控制台报错 `default export is not declared in imported module` 说明three.js没有默认的导出对象,下面列出了三种写法,这里看个人爱好了。(webpack的配置与package.json的生成不多做赘述了)
import * as THREE from 'three'
import { Scene, WebGLRenderer} from 'three'
const THREE = require('three')

定义一些需要的变量

let camera, scene, renderer; // 相机, 场景, WebGLRenderer实列
let geometry, materail, mesh; // 集合体, 材质, 网格

初始化渲染场景

function initRenderer() {
  // true/false表示是否开启反锯齿
  renderer = new THREE.WebGLRenderer({ antialias: true })
  // 设置宽高
  renderer.setSize(window.innerWidth, window.innerHeight)
  // 放到body里面
  document.body.appendChild(renderer.domElement)
}

初始化相机

关于PerspectiveCamera (透视投影相机)的参数,
fov 可视角度,
aspect 实际窗口的纵横比,一般是 width / height
near 照相机到视景体最近的距离,
远照相机到视景体最远的距离,far 应大于near
一张图来感受一下


只有离相机的距离大于near值,小于far值,且在相机的可视角度之内,才能被相机投影到。透视图中,粉色到青色的部分是视景体,是可能被渲染的物体所在的区域

function initCamera() {
  // 透视投影相机 
 
  camera = new THREE.PerspectiveCamera(70, window.innerWidth / window.innerHeight, 0.01, 100);
  camera.position.z = 1 // z轴为1
}

初始化场景

一行代码

function initScene() {
  scene = new THREE.Scene()
}

初始化物体

geometry: 这里是一个长宽高都为0.4的正方体。
materail: 是默认的普通材质
mesh:
function initObj() {
  geometry = new THREE.BoxGeometry(0.4, 0.4, 0.4);
  materail = new THREE.MeshNormalMaterial();
  mesh = new THREE.Mesh(geometry, materail);
  scene.add(mesh)
}

初始化动画

首先请求动画帧,再把动画放进去,每一帧都会发生变化,每次发生变化x、y轴加0.01从而达到动画的效果,再把场景和相机放到渲染器里面。

function render() {
  animate()
}

function animate() {
  requestAnimationFrame(animate);
  mesh.rotation.x += 0.01;
  mesh.rotation.y += 0.01;
  renderer.render(scene, camera); 
}

下面是完整的代码,最终的效果就是封面图了。

// var THREE = require('three')
// import THREE from 'three
import * as THREE from 'three'

let camera, scene, renderer;
let geometry, materail, mesh;

// 渲染场景
function initRenderer() {
  renderer = new THREE.WebGLRenderer({ antialias: true })
  renderer.setSize(window.innerWidth, window.innerHeight)
  document.body.appendChild(renderer.domElement)
}

// 相机
function initCamera() {
  // 透视投影相机 https://www.cnblogs.com/xulei1992/p/5709677.html
  camera = new THREE.PerspectiveCamera(80, window.innerWidth / window.innerHeight, 0.1, 100);
  camera.position.z = 1
}

// 场景
function initScene() {
  scene = new THREE.Scene()
}

// 物体
function initObj() {
  geometry = new THREE.BoxGeometry(0.4, 0.4, 0.4);
  materail = new THREE.MeshNormalMaterial();
  mesh = new THREE.Mesh(geometry, materail);
  scene.add(mesh)
}


// 渲染动画
function render() {
  animate()
}

function animate() {
  requestAnimationFrame(animate);
  mesh.rotation.x += 0.01;
  mesh.rotation.y += 0.05;
  renderer.render(scene, camera);
}

// 初始化
function init() {
  initRenderer()
  initCamera()
  initScene()
  initObj()
  render()
}

window.onload = init

源代码: github.com/cn0379/Thre…