three.js之特殊材质效果

 *案例42 创建一个透明的立方体

<template><div ref="container" className="container"></div>
</template><script setup>
import * as THREE from 'three';
import WebGL from 'three/examples/jsm/capabilities/WebGL.js'
// 引入轨道控制器扩展库OrbitControls.js
import {OrbitControls} from 'three/examples/jsm/controls/OrbitControls.js'
import {TransformControls} from 'three/examples/jsm/controls/TransformControls.js'
import { CSS3DRenderer, CSS3DObject } from 'three/examples/jsm/renderers/CSS3DRenderer.js';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import { GUI } from 'three/examples/jsm/libs/lil-gui.module.min.js';
import { RectAreaLightHelper } from 'three/examples/jsm/helpers/RectAreaLightHelper.js';
import { RectAreaLightUniformsLib } from 'three/examples/jsm/lights/RectAreaLightUniformsLib.js';
import {ref, onMounted} from 'vue'let container = ref(null)onMounted(() => {/** * 创建场景(渲染必加代码)*/// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 创建场景const scene = new THREE.Scene();/** * 创建摄像机(渲染必加代码)* */// 创建摄像机(three.js有好几种摄像机,这里用的是透视摄像机)// 参数 1:fov视野角度(注意:这个参数如果调整不好,会导致物体的透视效果看起来怪怪的)//      控制相机能看到的角度范围。//      就像你眼睛睁得越大,看到的范围就越广;睁得越小,看到的范围就越窄// 参数 2:aspect长宽比,控制相机看到的画面的宽高比。//      就像你调整手机屏幕的横屏或竖屏模式,画面的宽高比会变化// 参数 3:near近截面,控制相机能看到的最小距离,默认值是0.1//      1 表示距离相机 1 个单位以内的物体不会被渲染// 参数 4:far远截面,控制相机能看到的最大距离//      1000 表示距离相机 1000 个单位以外的物体不会被渲染const camera = new THREE.PerspectiveCamera(30, containerWidth / containerHeight, 1, 100);// camera.position 和 camera.lookAt 如果不设置可能会导致画面看不到效果// 摄像机的位置camera.position.set(5, 3.5, 4.7);// 摄像机聚焦的位置camera.lookAt(0, 0, 0);// zoom属性可以获取或者设置摄像机的缩放倍数,其默认值为1camera.zoom = 1// 【注意,在大多数属性发生改变之后,需要调用.updateProjectionMatrix来使得这些改变生效】camera.updateProjectionMatrix()/** * 创建渲染器(渲染必加代码)* */// 创建渲染器(three.js有好几种渲染器)const renderer = new THREE.WebGLRenderer();// 设置渲染器尺寸// 第三个参数(选填):false代表以较低分辨率渲染renderer.setSize(containerWidth, containerHeight );// 将渲染器放入文档中container.value.appendChild(renderer.domElement);/** 创建坐标轴对象(用于辅助创建3D场景)* */// AxesHelper() 的参数代表坐标轴的线段长度// 红色代表x轴,绿色代表y轴,蓝色代表z轴const axesHelper = new THREE.AxesHelper(5);scene.add(axesHelper);/** 创建轨道控制器* */const orbitControls = new OrbitControls(camera, renderer.domElement);// 更新控制器orbitControls.update();orbitControls.addEventListener('change', function () {// 输出相机位置//console.log('camera.position', camera.position);});/** 创建一个透明的立方体* (效果不太理想,立方体的背面没有显示)* */// 新建立方体对象const geometry = new THREE.BoxGeometry(1,1,1);// 创建材质// MeshBasicMaterial材质不受光照影响const material = new THREE.MeshBasicMaterial({// 材质颜色color: '#2ccdf1',// 启用透明transparent: true,// 设置透明度opacity: 0.35,// 渲染正面和背面side: THREE.DoubleSide,});// 新建网格(网格包含集合体和作用在几何体上面的材质)const cube = new THREE.Mesh(geometry, material);// 将网格添加到场景scene.add(cube);/** 渲染场景必加代码 (渲染循环)* */// 渲染循环function animate() {// 每秒执行60次requestAnimationFrame(animate);// 更新控制器orbitControls.update();// 渲染场景renderer.render(scene, camera);}// WebGL兼容性检查if (WebGL.isWebGLAvailable()) {animate();} else {const warning = WebGL.getWebGLErrorMessage();container.value.appendChild(warning);}/*** 窗口变化自适应(必加代码)*/const onWindowResize = () => {// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 重置渲染器输出画布canvas尺寸renderer.setSize(containerWidth, containerHeight);// aspect属性 是摄像机视锥体的长宽比,通常设置为,画布的宽/画布的高// 全屏情况下:设置 观察范围长宽比aspect,为窗口宽高比camera.aspect =containerWidth / containerHeight;// 渲染器执行render方法的时候会读取相机对象的投影矩阵属性projectionMatrix// 但是不会每渲染一帧,就通过相机的属性计算投影矩阵(节约计算资源)// 因此如果相机的属性发生了变化,需要执行updateProjectionMatrix ()方法来使得这些属性生效camera.updateProjectionMatrix();}// 监听浏览器窗口大小改变window.addEventListener('resize', onWindowResize);})
</script>
<style></style>
<style scoped>
.container {height: 100vh;box-sizing: border-box;/* overflow属性(必填),否则页面自适应时,偶尔会出现滚动条*/overflow: hidden;
}
</style>

*案例43 创建一个线框球体

<template><div ref="container" className="container"></div>
</template><script setup>
import * as THREE from 'three';
import WebGL from 'three/examples/jsm/capabilities/WebGL.js'
// 引入轨道控制器扩展库OrbitControls.js
import {OrbitControls} from 'three/examples/jsm/controls/OrbitControls.js'
import {TransformControls} from 'three/examples/jsm/controls/TransformControls.js'
import { CSS3DRenderer, CSS3DObject } from 'three/examples/jsm/renderers/CSS3DRenderer.js';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import { GUI } from 'three/examples/jsm/libs/lil-gui.module.min.js';
import { RectAreaLightHelper } from 'three/examples/jsm/helpers/RectAreaLightHelper.js';
import { RectAreaLightUniformsLib } from 'three/examples/jsm/lights/RectAreaLightUniformsLib.js';
import {ref, onMounted} from 'vue'let container = ref(null)onMounted(() => {/** * 创建场景(渲染必加代码)*/// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 创建场景const scene = new THREE.Scene();/** * 创建摄像机(渲染必加代码)* */// 创建摄像机(three.js有好几种摄像机,这里用的是透视摄像机)// 参数 1:fov视野角度(注意:这个参数如果调整不好,会导致物体的透视效果看起来怪怪的)//      控制相机能看到的角度范围。//      就像你眼睛睁得越大,看到的范围就越广;睁得越小,看到的范围就越窄// 参数 2:aspect长宽比,控制相机看到的画面的宽高比。//      就像你调整手机屏幕的横屏或竖屏模式,画面的宽高比会变化// 参数 3:near近截面,控制相机能看到的最小距离,默认值是0.1//      1 表示距离相机 1 个单位以内的物体不会被渲染// 参数 4:far远截面,控制相机能看到的最大距离//      1000 表示距离相机 1000 个单位以外的物体不会被渲染const camera = new THREE.PerspectiveCamera(30, containerWidth / containerHeight, 1, 100);// camera.position 和 camera.lookAt 如果不设置可能会导致画面看不到效果// 摄像机的位置camera.position.set(5, 3.5, 4.7);// 摄像机聚焦的位置camera.lookAt(0, 0, 0);// zoom属性可以获取或者设置摄像机的缩放倍数,其默认值为1camera.zoom = 1// 【注意,在大多数属性发生改变之后,需要调用.updateProjectionMatrix来使得这些改变生效】camera.updateProjectionMatrix()/** * 创建渲染器(渲染必加代码)* */// 创建渲染器(three.js有好几种渲染器)const renderer = new THREE.WebGLRenderer();// 设置渲染器尺寸// 第三个参数(选填):false代表以较低分辨率渲染renderer.setSize(containerWidth, containerHeight );// 将渲染器放入文档中container.value.appendChild(renderer.domElement);/** 创建坐标轴对象(用于辅助创建3D场景)* */// AxesHelper() 的参数代表坐标轴的线段长度// 红色代表x轴,绿色代表y轴,蓝色代表z轴const axesHelper = new THREE.AxesHelper(5);scene.add(axesHelper);/** 创建轨道控制器* */const orbitControls = new OrbitControls(camera, renderer.domElement);// 更新控制器orbitControls.update();orbitControls.addEventListener('change', function () {// 输出相机位置//console.log('camera.position', camera.position);});/** 创建一个线框球体* */// 新建球体const geometry = new THREE.SphereGeometry( 1, 16, 16 );// 创建材质// MeshBasicMaterial材质不受光照影响const material = new THREE.MeshBasicMaterial({// 材质颜色color: '#2ccdf1',// 将几何体渲染为线框。默认值为false(即渲染为平面多边形)wireframe: true,// 控制线框宽度(chrome上不好使)wireframeLinewidth: 5,// 定义线连接节点的样式。可选值为 'round', 'bevel' 和 'miter'。默认值为 'round'wireframeLinejoin: 'round',});// 新建网格(网格包含集合体和作用在几何体上面的材质)const cube = new THREE.Mesh(geometry, material);// 将网格添加到场景scene.add(cube);/** 渲染场景必加代码 (渲染循环)* */// 渲染循环function animate() {// 每秒执行60次requestAnimationFrame(animate);// 更新控制器orbitControls.update();// 渲染场景renderer.render(scene, camera);}// WebGL兼容性检查if (WebGL.isWebGLAvailable()) {animate();} else {const warning = WebGL.getWebGLErrorMessage();container.value.appendChild(warning);}/*** 窗口变化自适应(必加代码)*/const onWindowResize = () => {// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 重置渲染器输出画布canvas尺寸renderer.setSize(containerWidth, containerHeight);// aspect属性 是摄像机视锥体的长宽比,通常设置为,画布的宽/画布的高// 全屏情况下:设置 观察范围长宽比aspect,为窗口宽高比camera.aspect =containerWidth / containerHeight;// 渲染器执行render方法的时候会读取相机对象的投影矩阵属性projectionMatrix// 但是不会每渲染一帧,就通过相机的属性计算投影矩阵(节约计算资源)// 因此如果相机的属性发生了变化,需要执行updateProjectionMatrix ()方法来使得这些属性生效camera.updateProjectionMatrix();}// 监听浏览器窗口大小改变window.addEventListener('resize', onWindowResize);})
</script>
<style></style>
<style scoped>
.container {height: 100vh;box-sizing: border-box;/* overflow属性(必填),否则页面自适应时,偶尔会出现滚动条*/overflow: hidden;
}
</style>

*案例44 用深度网格材质创建一个立方体

<template><div ref="container" className="container"></div>
</template><script setup>
import * as THREE from 'three';
import WebGL from 'three/examples/jsm/capabilities/WebGL.js'
// 引入轨道控制器扩展库OrbitControls.js
import {OrbitControls} from 'three/examples/jsm/controls/OrbitControls.js'
import {TransformControls} from 'three/examples/jsm/controls/TransformControls.js'
import { CSS3DRenderer, CSS3DObject } from 'three/examples/jsm/renderers/CSS3DRenderer.js';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import { GUI } from 'three/examples/jsm/libs/lil-gui.module.min.js';
import { RectAreaLightHelper } from 'three/examples/jsm/helpers/RectAreaLightHelper.js';
import { RectAreaLightUniformsLib } from 'three/examples/jsm/lights/RectAreaLightUniformsLib.js';
import {ref, onMounted} from 'vue'let container = ref(null)onMounted(() => {/** * 创建场景(渲染必加代码)*/// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 创建场景const scene = new THREE.Scene();/** * 创建摄像机(渲染必加代码)* */// 创建摄像机(three.js有好几种摄像机,这里用的是透视摄像机)// 参数 1:fov视野角度(注意:这个参数如果调整不好,会导致物体的透视效果看起来怪怪的,一般为30)//      控制相机能看到的角度范围。//      就像你眼睛睁得越大,看到的范围就越广;睁得越小,看到的范围就越窄// 参数 2:aspect长宽比,控制相机看到的画面的宽高比。//      就像你调整手机屏幕的横屏或竖屏模式,画面的宽高比会变化// 参数 3:near近截面,控制相机能看到的最小距离,默认值是0.1//      1 表示距离相机 1 个单位以内的物体不会被渲染// 参数 4:far远截面,控制相机能看到的最大距离//      1000 表示距离相机 1000 个单位以外的物体不会被渲染const camera = new THREE.PerspectiveCamera(75, containerWidth / containerHeight, 0.1, 1000);// camera.position 和 camera.lookAt 如果不设置可能会导致画面看不到效果// 摄像机的位置camera.position.set(2.35, 2.35, 2.35);// 摄像机聚焦的位置camera.lookAt(0, 0, 0);// zoom属性可以获取或者设置摄像机的缩放倍数,其默认值为1camera.zoom = 1// 【注意,在大多数属性发生改变之后,需要调用.updateProjectionMatrix来使得这些改变生效】camera.updateProjectionMatrix()/** * 创建渲染器(渲染必加代码)* */// 创建渲染器(three.js有好几种渲染器)const renderer = new THREE.WebGLRenderer();// 设置渲染器尺寸// 第三个参数(选填):false代表以较低分辨率渲染renderer.setSize(containerWidth, containerHeight );// 将渲染器放入文档中container.value.appendChild(renderer.domElement);/** 创建坐标轴对象(用于辅助创建3D场景)* */// AxesHelper() 的参数代表坐标轴的线段长度// 红色代表x轴,绿色代表y轴,蓝色代表z轴const axesHelper = new THREE.AxesHelper(5);scene.add(axesHelper);/** 创建轨道控制器* */const orbitControls = new OrbitControls(camera, renderer.domElement);// 更新控制器orbitControls.update();orbitControls.addEventListener('change', function () {// 输出相机位置console.log('camera.position', camera.position);});/** 用深度网格材质创建一个立方体* MeshDepthMaterial 是一种基于深度的材质。* (这种材质不常用)** 它会根据物体与相机的距离,将物体渲染为灰度颜色:*     距离相机近的物体显示为白色。*     距离相机远的物体显示为黑色。*     中间的物体显示为灰色。** MeshDepthMaterial 的特点:*     灰度显示:根据深度渲染为黑白灰颜色。*     无光照:不受场景中灯光的影响。*     简单高效:适合用于深度相关的效果。* */// 创建 深度网格材质 MeshDepthMaterialconst depthMaterial = new THREE.MeshDepthMaterial();// 创建几何体const geometry = new THREE.BoxGeometry(0.5,0.5,0.5);// 创建网格对象const cube1 = new THREE.Mesh(geometry, depthMaterial);cube1.position.set(2, 2, 2);scene.add(cube1);/** 渲染场景必加代码 (渲染循环)* */// 渲染循环function animate() {// 每秒执行60次requestAnimationFrame(animate);// 旋转立方体动画cube1.rotation.x += 0.01;cube1.rotation.y += 0.01;// 更新控制器orbitControls.update();// 渲染场景renderer.render(scene, camera);}// WebGL兼容性检查if (WebGL.isWebGLAvailable()) {animate();} else {const warning = WebGL.getWebGLErrorMessage();container.value.appendChild(warning);}/*** 窗口变化自适应(必加代码)*/const onWindowResize = () => {// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 重置渲染器输出画布canvas尺寸renderer.setSize(containerWidth, containerHeight);// aspect属性 是摄像机视锥体的长宽比,通常设置为,画布的宽/画布的高// 全屏情况下:设置 观察范围长宽比aspect,为窗口宽高比camera.aspect =containerWidth / containerHeight;// 渲染器执行render方法的时候会读取相机对象的投影矩阵属性projectionMatrix// 但是不会每渲染一帧,就通过相机的属性计算投影矩阵(节约计算资源)// 因此如果相机的属性发生了变化,需要执行updateProjectionMatrix ()方法来使得这些属性生效camera.updateProjectionMatrix();}// 监听浏览器窗口大小改变window.addEventListener('resize', onWindowResize);})
</script>
<style></style>
<style scoped>
.container {height: 100vh;box-sizing: border-box;/* overflow属性(必填),否则页面自适应时,偶尔会出现滚动条*/overflow: hidden;
}
</style>

*案例45 创建一个 标准网格材质(MeshStandardMaterial)的透明立方体

<template><div ref="container" className="container"></div>
</template><script setup>
import * as THREE from 'three';
import WebGL from 'three/examples/jsm/capabilities/WebGL.js'
// 引入轨道控制器扩展库OrbitControls.js
import {OrbitControls} from 'three/examples/jsm/controls/OrbitControls.js'
import {TransformControls} from 'three/examples/jsm/controls/TransformControls.js'
import { CSS3DRenderer, CSS3DObject } from 'three/examples/jsm/renderers/CSS3DRenderer.js';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import { GUI } from 'three/examples/jsm/libs/lil-gui.module.min.js';
import { RectAreaLightHelper } from 'three/examples/jsm/helpers/RectAreaLightHelper.js';
import { RectAreaLightUniformsLib } from 'three/examples/jsm/lights/RectAreaLightUniformsLib.js';
import {ref, onMounted} from 'vue'let container = ref(null)onMounted(() => {/** * 创建场景(渲染必加代码)*/// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 创建场景const scene = new THREE.Scene();/** * 创建摄像机(渲染必加代码)* */// 创建摄像机(three.js有好几种摄像机,这里用的是透视摄像机)// 参数 1:fov视野角度(注意:这个参数如果调整不好,会导致物体的透视效果看起来怪怪的,一般为30)//      控制相机能看到的角度范围。//      就像你眼睛睁得越大,看到的范围就越广;睁得越小,看到的范围就越窄// 参数 2:aspect长宽比,控制相机看到的画面的宽高比。//      就像你调整手机屏幕的横屏或竖屏模式,画面的宽高比会变化// 参数 3:near近截面,控制相机能看到的最小距离,默认值是0.1//      1 表示距离相机 1 个单位以内的物体不会被渲染// 参数 4:far远截面,控制相机能看到的最大距离//      1000 表示距离相机 1000 个单位以外的物体不会被渲染const camera = new THREE.PerspectiveCamera(30, containerWidth / containerHeight, 0.1, 1000);// camera.position 和 camera.lookAt 如果不设置可能会导致画面看不到效果// 摄像机的位置camera.position.set(3.9, 3.9, 3.9);// 摄像机聚焦的位置camera.lookAt(0, 0, 0);// zoom属性可以获取或者设置摄像机的缩放倍数,其默认值为1camera.zoom = 1// 【注意,在大多数属性发生改变之后,需要调用.updateProjectionMatrix来使得这些改变生效】camera.updateProjectionMatrix()/** * 创建渲染器(渲染必加代码)* */// 创建渲染器(three.js有好几种渲染器)const renderer = new THREE.WebGLRenderer();// 设置渲染器尺寸// 第三个参数(选填):false代表以较低分辨率渲染renderer.setSize(containerWidth, containerHeight );// 将渲染器放入文档中container.value.appendChild(renderer.domElement);/** 创建轨道控制器* */const orbitControls = new OrbitControls(camera, renderer.domElement);// 更新控制器orbitControls.update();orbitControls.addEventListener('change', function () {// 输出相机位置console.log('camera.position', camera.position);});/** 创建环境光* MeshLambertMaterial材质的物体,没有光源对象是看不清的,所以要创建环境光* */// 第一个参数:环境光颜色// 第二个参数:光照的强度,缺省值为 1const AmbientLight = new THREE.AmbientLight( '#fff',2 ); // soft white lightscene.add( AmbientLight );/** 创建一个 标准网格材质(MeshStandardMaterial)的透明立方体** */// 新建立方体对象const geometry = new THREE.BoxGeometry(1,1,1);// 创建材质// MeshStandardMaterial是一种基于物理的标准材质const material = new THREE.MeshStandardMaterial({// 材质颜色color: '#2ccdf1',// 启用透明transparent: true,// 设置透明度opacity: 0.35,// 渲染正面和背面side: THREE.DoubleSide,});// 新建网格(网格包含集合体和作用在几何体上面的材质)const cube = new THREE.Mesh(geometry, material);// 将网格添加到场景scene.add(cube);/** 创建平行光* 常常用平行光来模拟太阳光* */// 第一个参数:光的颜色// 第二个参数:光照强度const DirectionalLight = new THREE.DirectionalLight( '#ffffff',3 );scene.add( DirectionalLight );// 设置平行光位置DirectionalLight.position.set(1, 1.5, 0)/// 设置平行光的方向,让平行光照射球体// target属性用于设置平行光的目标位置//    平行光默认的目标位置为原点 (0,0,0)//    值可以是场景中的某个对象DirectionalLight.target = cube/** 渲染场景必加代码 (渲染循环)* */// 渲染循环function animate() {// 每秒执行60次requestAnimationFrame(animate);// 更新控制器orbitControls.update();// 渲染场景renderer.render(scene, camera);}// WebGL兼容性检查if (WebGL.isWebGLAvailable()) {animate();} else {const warning = WebGL.getWebGLErrorMessage();container.value.appendChild(warning);}/*** 窗口变化自适应(必加代码)*/const onWindowResize = () => {// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 重置渲染器输出画布canvas尺寸renderer.setSize(containerWidth, containerHeight);// aspect属性 是摄像机视锥体的长宽比,通常设置为,画布的宽/画布的高// 全屏情况下:设置 观察范围长宽比aspect,为窗口宽高比camera.aspect =containerWidth / containerHeight;// 渲染器执行render方法的时候会读取相机对象的投影矩阵属性projectionMatrix// 但是不会每渲染一帧,就通过相机的属性计算投影矩阵(节约计算资源)// 因此如果相机的属性发生了变化,需要执行updateProjectionMatrix ()方法来使得这些属性生效camera.updateProjectionMatrix();}// 监听浏览器窗口大小改变window.addEventListener('resize', onWindowResize);})
</script>
<style></style>
<style scoped>
.container {height: 100vh;box-sizing: border-box;/* overflow属性(必填),否则页面自适应时,偶尔会出现滚动条*/overflow: hidden;
}
</style>

*案例46 创建卡通风格材质的物体

<template><div ref="container" className="container"></div>
</template><script setup>
import * as THREE from 'three';
import WebGL from 'three/examples/jsm/capabilities/WebGL.js'
// 引入轨道控制器扩展库OrbitControls.js
import {OrbitControls} from 'three/examples/jsm/controls/OrbitControls.js'
import {TransformControls} from 'three/examples/jsm/controls/TransformControls.js'
import { CSS3DRenderer, CSS3DObject } from 'three/examples/jsm/renderers/CSS3DRenderer.js';
import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'
import { GUI } from 'three/examples/jsm/libs/lil-gui.module.min.js';
import { RectAreaLightHelper } from 'three/examples/jsm/helpers/RectAreaLightHelper.js';
import { RectAreaLightUniformsLib } from 'three/examples/jsm/lights/RectAreaLightUniformsLib.js';
import {ref, onMounted} from 'vue'let container = ref(null)onMounted(() => {/** * 创建场景(渲染必加代码)*/// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 创建场景const scene = new THREE.Scene();/** * 创建摄像机(渲染必加代码)* */// 创建摄像机(three.js有好几种摄像机,这里用的是透视摄像机)// 参数 1:fov视野角度(注意:这个参数如果调整不好,会导致物体的透视效果看起来怪怪的,一般为30)//      控制相机能看到的角度范围。//      就像你眼睛睁得越大,看到的范围就越广;睁得越小,看到的范围就越窄// 参数 2:aspect长宽比,控制相机看到的画面的宽高比。//      就像你调整手机屏幕的横屏或竖屏模式,画面的宽高比会变化// 参数 3:near近截面,控制相机能看到的最小距离,默认值是0.1//      1 表示距离相机 1 个单位以内的物体不会被渲染// 参数 4:far远截面,控制相机能看到的最大距离//      1000 表示距离相机 1000 个单位以外的物体不会被渲染const camera = new THREE.PerspectiveCamera(30, containerWidth / containerHeight, 0.1, 1000);// camera.position 和 camera.lookAt 如果不设置可能会导致画面看不到效果// 摄像机的位置camera.position.set(3.9, 3.9, 3.9);// 摄像机聚焦的位置camera.lookAt(0, 0, 0);// zoom属性可以获取或者设置摄像机的缩放倍数,其默认值为1camera.zoom = 1// 【注意,在大多数属性发生改变之后,需要调用.updateProjectionMatrix来使得这些改变生效】camera.updateProjectionMatrix()/** * 创建渲染器(渲染必加代码)* */// 创建渲染器(three.js有好几种渲染器)const renderer = new THREE.WebGLRenderer();// 设置渲染器尺寸// 第三个参数(选填):false代表以较低分辨率渲染renderer.setSize(containerWidth, containerHeight );// 将渲染器放入文档中container.value.appendChild(renderer.domElement);/** 创建轨道控制器* */const orbitControls = new OrbitControls(camera, renderer.domElement);// 更新控制器orbitControls.update();orbitControls.addEventListener('change', function () {// 输出相机位置console.log('camera.position', camera.position);});/** 创建坐标轴对象(用于辅助创建3D场景)* */// AxesHelper() 的参数代表坐标轴的线段长度// 红色代表x轴,绿色代表y轴,蓝色代表z轴const axesHelper = new THREE.AxesHelper(5);scene.add(axesHelper);/** 创建环境光* MeshLambertMaterial材质的物体,没有光源对象是看不清的,所以要创建环境光* */// 第一个参数:环境光颜色// 第二个参数:光照的强度,缺省值为 1const AmbientLight = new THREE.AmbientLight( '#fff',1 ); // soft white lightscene.add( AmbientLight );/** * 创建卡通风格材质的物体** MeshToonMaterial 是一种特殊的材质,它可以让 3D 物体看起来像卡通风格的画面* MeshToonMaterial 是一种基于光照的材质,但它不像普通材质那样平滑过渡,而是将颜色分成几个明显的色块。* 这种效果类似于卡通画中的阴影和高光,给人一种手绘的感觉。* 在制作卡通风格的游戏或动画时需要用这种材质** MeshToonMaterial 的特点:*     色块化阴影:将阴影和高光分成明显的色块,而不是平滑过渡。*     支持光照:可以根据场景中的灯光调整颜色。*     简单易用:只需设置颜色和渐变贴图,就能实现卡通效果。* */// 创建 MeshToonMaterial 材质const material = new THREE.MeshToonMaterial({color: '#317fd7', // 设置颜色为绿色gradientMap: null, // 渐变贴图(可选)});// 创建一个立方体和一个球体const sphereGeometry = new THREE.SphereGeometry( 0.5, 32, 16 );const geometry = new THREE.BoxGeometry(0.8,0.8,0.8);// 创建球体网格const sphere = new THREE.Mesh( sphereGeometry, material );sphere.position.set(1.3,0,0)scene.add( sphere );// 创建立方体网格const cube = new THREE.Mesh(geometry, material);scene.add(cube);/** 创建平行光* 常常用平行光来模拟太阳光* */// 第一个参数:光的颜色// 第二个参数:光照强度const DirectionalLight = new THREE.DirectionalLight( '#ffffff',4 );scene.add( DirectionalLight );// 设置平行光位置// .normalize()确保方向向量长度为1,使光照和阴影计算符合物理规律,避免因向量长度导致的意外结果DirectionalLight.position.set(2, 2, 0).normalize()/// 设置平行光的方向,让平行光照射球体// target属性用于设置平行光的目标位置//    平行光默认的目标位置为原点 (0,0,0)//    值可以是场景中的某个对象DirectionalLight.target = cube/** 渲染场景必加代码 (渲染循环)* */// 渲染循环function animate() {// 每秒执行60次requestAnimationFrame(animate);// 更新控制器orbitControls.update();// 渲染场景renderer.render(scene, camera);}// WebGL兼容性检查if (WebGL.isWebGLAvailable()) {animate();} else {const warning = WebGL.getWebGLErrorMessage();container.value.appendChild(warning);}/*** 窗口变化自适应(必加代码)*/const onWindowResize = () => {// 获取容器的实际宽高const containerWidth = container.value.clientWidth;const containerHeight = container.value.clientHeight;// 重置渲染器输出画布canvas尺寸renderer.setSize(containerWidth, containerHeight);// aspect属性 是摄像机视锥体的长宽比,通常设置为,画布的宽/画布的高// 全屏情况下:设置 观察范围长宽比aspect,为窗口宽高比camera.aspect =containerWidth / containerHeight;// 渲染器执行render方法的时候会读取相机对象的投影矩阵属性projectionMatrix// 但是不会每渲染一帧,就通过相机的属性计算投影矩阵(节约计算资源)// 因此如果相机的属性发生了变化,需要执行updateProjectionMatrix ()方法来使得这些属性生效camera.updateProjectionMatrix();}// 监听浏览器窗口大小改变window.addEventListener('resize', onWindowResize);})
</script>
<style></style>
<style scoped>
.container {height: 100vh;box-sizing: border-box;/* overflow属性(必填),否则页面自适应时,偶尔会出现滚动条*/overflow: hidden;
}
</style>

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/22556.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

三格电子上新了——PLC 数据采集网关

型号&#xff1a;SG-PLC-Private 第一章 产品概述 PLC 转 Modbus 网关型号 SG-PLC-Private &#xff08; PLC 私有协议网关&#xff09;&#xff0c;是三格电子推出的工业 级网关&#xff08;以下简称网关&#xff09;&#xff0c;主要用于 在不需要对 PLC 编程的情况…

算法日记25:01背包(DFS->记忆化搜索->倒叙DP->顺序DP->空间优化)

对于01背包这类DP入门的问题&#xff0c;新手应该是去了解如何一步步得出所谓的状态转移方程&#xff0c;而不是直接去看答案所给予的方程过程应该为&#xff1a;DFS->记忆化搜索->倒序递推->循序递推->二维->一维 一、DFS暴力搜索 O ( 2 n ) O(2^n) O(2n) 1…

Spring AutoWired与Resource区别?

大家好&#xff0c;我是锋哥。今天分享关于【Spring AutoWired与Resource区别?】面试题。希望对大家有帮助&#xff1b; Spring AutoWired与Resource区别? 1000道 互联网大厂Java工程师 精选面试题-Java资源分享网 在 Spring 中&#xff0c;Autowired 和 Resource 都是用于…

【知识】深度学习中,应该先zero_grad还是先backward?

转载请注明出处&#xff1a;小锋学长生活大爆炸[xfxuezhagn.cn] 如果本文帮助到了你&#xff0c;欢迎[点赞、收藏、关注]哦~ 目录 抛出问题 各大GPT的回答 ChatGPT-4o ChatGPT-o3-mini-high Kimi-长思考 Deepseek-R1 Grok3 Pytorch官方教程中 抛出问题 以下哪种方式是…

Python----数据结构(哈希表:哈希表组成,哈希冲突)

一、哈希表 哈希表(Hash table)是一种常用、重要、高效的数据结构。 哈希表通过哈希函数,可以快速地将键(Key)映射到值(Value)。从而允许在近常数时间内对键关联的值进行插入、删除和查找操作。 哈希表的主要思想是通过哈希函数将键转换为索引&#xff0c;将索引映射到数组中…

使用excel中的VBA合并多个excel文件

需求是这样的&#xff1a; 在Windows下&#xff0c;用excel文件让多个小组填写了统计信息&#xff0c;现在我需要把收集的多个文件汇总到一个文件中&#xff0c;前三行为标题可以忽略&#xff0c;第四行为收集信息的列名&#xff0c;处理每一行数据的时候&#xff0c;发现某一行…

功能全面的手机壁纸应用,种类齐全、众多高清壁纸

软件介绍 应用亮点&#xff1a;今天给大家分享一款超神奇的手机应用 —— 奇幻壁纸。它作为手机动态壁纸软件&#xff0c;功能超全面&#xff0c;操作还便捷&#xff0c;极具创意&#xff0c;能瞬间将你的手机屏幕变成奇幻世界&#xff0c;带来全新视觉感受。 使用便捷性&…

docker安装kafka,并通过springboot快速集成kafka

目录 一、docker安装和配置Kafka 1.拉取 Zookeeper 的 Docker 镜像 2.运行 Zookeeper 容器 3.拉取 Kafka 的 Docker 镜像 4.运行 Kafka 容器 5.下载 Kafdrop 6.运行 Kafdrop 7.如果docker pull wurstmeister/zookeeper或docker pull wurstmeister/kafka下载很慢&#x…

前端导出word文件,并包含导出Echarts图表等

基础导出模板 const html <html><head><style>body {font-family: Times New Roman;}h1 {text-align: center;}table {border-collapse: collapse;width: 100%;color: #1118FF;font-weight: 600;}th,td {border: 1px solid black;padding: 8px;text-align: …

2024系统编程语言风云变幻:Rust持续领跑,Zig与Ada异军突起

2024年系统编程语言调查报告新鲜出炉&#xff01;这份报告对Rust、Zig、Ada、C、C等主流语言进行了全面评估&#xff0c;结果令人瞩目。Rust凭借其强大的类型系统和内存安全机制继续领跑&#xff0c;而Zig和Ada则展现出巨大的潜力&#xff0c;为系统编程领域带来了新的活力。本…

Jenkins 构建 Unity 打包 .apk 同时生成 .aab

Jenkins 构建 Unity 打包 .apk 同时生成 .aab Android App Bundle简称 AAB&#xff0c;想了解更多关于 AAB 的知识&#xff0c;请看官网 https://developer.android.google.cn/guide/app-bundle/faq?hlzh-cn APK 打包部分在复用上一篇 Jenkins 构建 Unity打包APK 一、新建一…

JAVAweb-标签选择器,盒模型,定位,浮动

<!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><meta name"viewport" content"widthdevice-width, initial-scale1.0"><title>标签</title><style type"text/css&q…

计算机视觉:主流数据集整理

第一章&#xff1a;计算机视觉中图像的基础认知 第二章&#xff1a;计算机视觉&#xff1a;卷积神经网络(CNN)基本概念(一) 第三章&#xff1a;计算机视觉&#xff1a;卷积神经网络(CNN)基本概念(二) 第四章&#xff1a;搭建一个经典的LeNet5神经网络(附代码) 第五章&#xff1…

二级公共基础之数据结构与算法篇(五)树和二叉树

目录 前言 一、树的基本概念 1.父结点和根节点 2.子节点和叶子节点 3.度和深度 4.子树 二、二叉树及其基本性质 1. 二叉树的定义 2. 二叉树的基本性质 性质1 性质2 性质3 性质4 性质5 性质6 三、二叉树的存储结构 四、二叉树的遍历 1.遍历二叉树的概念 1. 前…

自制操作系统学习第七天

今天要做什么&#xff1f; 实现HLT&#xff0c;不让计算机处于HALT&#xff08;HLT&#xff09;.用C语言实现内存写入&#xff08;错误&#xff0c;需要分析&#xff09; 一:使用HLT&#xff0c;让计算机处于睡眠状态 写了下面这个程序&#xff0c;naskfunc.nas 函数名叫io_h…

Python Django系列—入门实例(二)

数据库配置 现在&#xff0c;打开 mysite/settings.py 。这是个包含了 Django 项目设置的 Python 模块。 默认情况下&#xff0c;​ DATABASES 配置使用 SQLite。如果你是数据库新手&#xff0c;或者只是想尝试 Django&#xff0c;这是最简单的选择。SQLite 包含在 Python 中…

DeepSeek接入Siri(已升级支持苹果手表)完整版硅基流动DeepSeek-R1部署

DeepSeek接入Siri&#xff08;已升级支持苹果手表&#xff09;完整版硅基流动DeepSeek-R1部署 **DeepSeek** 是一款专注于深度学习和人工智能的工具或平台&#xff0c;通常与人工智能、机器学习、自动化分析等领域有关。它的主要功能可能包括&#xff1a;深度学习模型搜索&…

抗辐照加固CAN FD芯片的商业航天与车规级应用解析

在工业自动化、智能汽车、航空航天及国防装备等关键领域&#xff0c;数据传输的安全性、可靠性与极端环境适应能力是技术升级的核心挑战。国科安芯推出全新一代CANFD&#xff08;Controller Area Network Flexible Data Rate&#xff09;芯片&#xff0c;以高安全、高可靠、断电…

Java数据结构第十二期:走进二叉树的奇妙世界(一)

专栏&#xff1a;数据结构(Java版) 个人主页&#xff1a;手握风云 目录 一、树型结构 1.1. 树的定义 1.2. 树的基本概念 1.3. 树的表示形式 二、二叉树 2.1. 概念 2.2. 两种特殊的二叉树 2.3. 二叉树的性质 2.4. 二叉树的存储 三、二叉树的基本操作 一、树型结构 1.…

nginx 反向代理 配置请求路由

nginx | 反向代理 | 配置请求路由 nginx简介 Nginx&#xff08;发音为“Engine-X”&#xff09;是一款高性能、开源的 Web 服务器和反向代理服务器&#xff0c;同时也支持邮件代理和负载均衡等功能。它由俄罗斯程序员伊戈尔西索夫&#xff08;Igor Sysoev&#xff09;于 2004…