首页 > 其他分享 >使用THREEJS实现一个可调节档位、可摇头的电风扇

使用THREEJS实现一个可调节档位、可摇头的电风扇

时间:2023-06-07 23:33:55浏览次数:79  
标签:THREEJS 档位 shakeDir scene let 电风扇 new btn Math

夏天到了,用Three.js实现一个可以摇头和调节档位的电风扇。主要使用到Blender处理3D模型,用Vite+Typescript搭建项目框架。效果演示:

<iframe allowfullscreen="" height="450" src="https://codesandbox.io/p/sandbox/still-moon-dx6nm6?embed=1" style="border: 1px solid rgba(0, 0, 0, 0.1); border-radius: 2px" width="800"></iframe>

一、处理模型

1、从爱(bai)给(gei)网下载一个风扇的3D模型,在Blender中打开,给模型贴上图
image.png
2、拆解模型。将风扇模型拆解成按钮、底座、扇叶、头部四个部分,其中按钮共五个,包括四个档位和一个摇头的开关。
image.png
3、导出模型。导出GLTF格式模型。
image.png

二、场景搭建

1、初始化场景

this.scene = new THREE.Scene();

/** 摄像机 */
this.camera = new THREE.PerspectiveCamera(75, this.sizes.width / this.sizes.height, 0.1, 100);
this.camera.position.set(0, 0.8, 1.8);

/** 灯光 */
this.lightPoint = new THREE.HemisphereLight(0xffffff, 0xffffff, 1 );
this.lightPoint.position.set(0, 500, 0);
this.scene.add(this.lightPoint);

/** 控制器 */
this.controls = new OrbitControls(this.camera, this.renderer.domElement);
this.controls.enableKeys = false;    // 禁用按键
this.controls.enableZoom = false;    // 禁用缩放
this.controls.enablePan = false;     // 禁用拖拽
this.controls.maxPolarAngle = 1.3;   // 最大垂直旋转角度
this.controls.minPolarAngle = 1.3;   // 最小垂直旋转角度
this.controls.target = new THREE.Vector3(0, 0.8, 0);

2、加载模型

import { GLTF, GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader';

var gltf: GLTF = await new Promise((resolve, _) => new GLTFLoader().load('./fan.glb', gltf => resolve(gltf)));
this.scene.add(gltf.scene);

3、绑定风扇按钮

this.fan = new Fan(gltf);

/** 档位调节按钮 */
let btns: Array<[string, Level]> = [
	['Btn_1', Level.one],
	['Btn_2', Level.two],
	['Btn_3', Level.three],
	['Btn_4', Level.zero],
];
btns.forEach(([name, level]) => {
	let btn = gltf.scene.getObjectByName(name);
	if (btn) this.fan.btns.push(new LevelBtn(btn, level));
});

/** 摇头按钮 */
let btn = gltf.scene.getObjectByName("Shake");
if (btn) this.fan.btns.push(new ShakeBtn(btn));

三、功能实现

1、扇叶旋转

function update() {
	let leaf = this.obj.scene.getObjectByName("Leaf");
	let rotationY = leaf!.rotation.y + Math.PI/10 * this.speed;
	while(rotationY > Math.PI * 2) rotationY = rotationY - Math.PI * 2;
	leaf!.rotation.y = rotationY;
	requestAnimationFrame(() => update());
}

2、档位调节

import { gsap } from 'gsap';

function turnLevel(btn: LevelBtn) {
	if(btn.state == BtnState.down) return;
	this.btns.filter(item => item instanceof LevelBtn).forEach(item => item.up());
	btn.down();
	if(btn.level !== Level.zero) this.state = State.on;
	this.level = btn.level;
	gsap.to(this, 3, { speed: this.level });
}

3、左右摇头

let head = this.obj.scene.getObjectByName("Head");
let shake = this.obj.scene.getObjectByName("Shake");
let leaf = this.obj.scene.getObjectByName("Leaf");
let rotationZ = head!.rotation.z + Math.PI / 1000 * this.shakeDir;
if(Math.abs(rotationZ) > Math.abs(this.shakeRange)) {
	let shakeDir = this.shakeDir;
	setTimeout(() => {
		if(shakeDir == ShakeDir.left) this.shakeDir = ShakeDir.right;
		else if(shakeDir == ShakeDir.right) this.shakeDir = ShakeDir.left;
	}, 1000)
	this.shakeDir = ShakeDir.wait;
	rotationZ = Math.abs(this.shakeRange) * Math.abs(rotationZ) / rotationZ;
}
head!.rotation.z = rotationZ;
leaf!.rotation.y = rotationZ;
shake!.rotation.z = rotationZ;

四、最后

项目代码和演示地址:https://codesandbox.io/p/sandbox/threejs-mini-fans-dx6nm6

标签:THREEJS,档位,shakeDir,scene,let,电风扇,new,btn,Math
From: https://www.cnblogs.com/one-yutian/p/17461954.html

相关文章

  • threejs绘制多边形几何体
    threejs绘制多边形 //创建一个立方体几何体varcubeGeometry=newTHREE.BoxGeometry(0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5);//创建一个多边形几何体varpolygonGeometry=newTHREE.Geometry();//创建多边形的顶点数......
  • 电风扇倾倒时为什么能自动停转?
    夏天来了,很多家庭都会开电风扇,电风扇是一种利用电动机驱动扇叶旋转,来达到使空气加速流通的家用电器,主要用于清凉解暑和流通空气。一般的家用电风扇在工作时发生倾倒,电风扇就停止工作,是什么原因呢?其实电风扇的内部安装了一个防倾倒开关,它的作用就是当主机发生倾斜或跌倒时,防倾倒开关......
  • 电风扇倾倒时为什么能自动停转?
    夏天来了,很多家庭都会开电风扇,电风扇是一种利用电动机驱动扇叶旋转,来达到使空气加速流通的家用电器,主要用于清凉解暑和流通空气。一般的家用电风扇在工作时发生倾倒,电风扇就停止工作,是什么原因呢?其实电风扇的内部安装了一个防倾倒开关,它的作用就是当主机发生倾斜或跌倒时,防倾倒开关......
  • threejs绘制平面多边形
    在Three.js中,可以使用geometry对象和geometryMaterial对象来创建和渲染多边形几何体。下面是一个绘制多边形平面的示例代码: //创建一个立方体几何体varcubeGeometry=newTHREE.BoxGeometry(0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5);......
  • webgl 渲染带透明通道的视频(threeJS)
    首先,你需要一个这样的视频 或者一个这样的视频 webgl渲染可以用three.js,上下叠加的代码如下:import*asTHREEfrom'three';letvideoWidth=540;//视频实际的宽度letvideoHeight=540;//原视频实际的高度的一般//定义渲染器varrenderer=new......
  • threejs绘制球体
    threejs绘制球体在Three.js中,可以使用geometry对象和geometryMaterial对象来创建和渲染球体几何体。下面是一个绘制球体的示例代码://创建一个立方体几何体varcubeGeometry=newTHREE.BoxGeometry(0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5,0.5);......
  • threejs创建圆柱体
    threejs创建圆柱体 创建一个几何体(geometry):使用Three.js的几何体类创建一个几何体,该类将定义您的几何体的形状和大小。例如,您可以使用以下代码创建一个圆柱体:vargeometry=newTHREE.CylinderGeometry(5,32,32); 这将创建一个高度为5、半径为32的圆柱体。创建......
  • threejs webgl性能优化
    threejswebgl性能优化WEBGL性能优化的方法有很多,以下是一些常见的方法:减少渲染次数:在WEBGL中,渲染次数越少,性能越好。因此,您可以通过减少渲染次数来提高性能。例如,使用批处理技术将多个对象合并为一个批处理对象进行渲染。降低纹理分辨率:纹理分辨率越高,渲染的时间就越长。......
  • threejs相机动画
    threejs相机动画import*asdatfrom"dat.gui";import{GUI}from"../../utils/lil-gui.module.min.js";importTWEENfrom"@tweenjs/tween.js";constgui=newGUI();gui.domElement.style.right="0px";......
  • # vue 使用 threejs 实现实景看房效果 demo
    vue使用threejs实现实景看房效果demo关于这个threejs实现VR看房效果也超级简单,只需要提供一个思路的话就可以了其实,首先需要一个房间结构的贴图,这个贴图网上有,当然找个合适的也不好找,我找了一上午在别人的demo里面扣了一张出来,代码都是一样的,稍微说一下思路。一张全景......