使用CubeCamera创建反光效果

  • 1.demo效果
  • 2. 实现要点
    • 2.1 创建立方体相机CubeCamera
    • 2.2 使用动态环境贴图材质
    • 2.3 render中更新立方体相机
    • 2.4 创建场景的全景贴图
    • 2.5 创建场景中的模型
  • 3. demo代码

1.demo效果


2. 实现要点

2.1 创建立方体相机CubeCamera

创建立方体的语法如下

const cubeCamera = new THREE.CubeCamera( near, far, cubeRenderTarget)

参数说明

  • near – 远剪切面的距离
  • far – 近剪切面的距离
  • cubeRenderTarget – 立方体渲染器目标对象
    如上参数可知创建CubeCamera对象需要三个参数,其中第三个参数是一个WebGLCubeRenderTarget 类型的对象,所以需要首先创建这样一个对象,然后创建立方体对象,具体代码如下:
//创建立方体渲染器目标对象
this.cubeRenderTarget = new THREE.WebGLCubeRenderTarget(128, {format: THREE.RGBFormat,generateMipmaps: true,minFilter: THREE.LinearMipmapLinearFilter
})//创建立方体相机
this.cubeCamera = new THREE.CubeCamera(1, 100000, this.cubeRenderTarget)
this.scene.add(this.cubeCamera)

2.2 使用动态环境贴图材质

上一步中我们创建完立方体相机后,立方体渲染器目标对象上边生成了有相机获取的图形生成的纹理,并保存在cubeRenderTarget.texture之中,接下来把它当环境贴图创建材质,随后使用这个材质创建一个球体Mesh

//创建球体
this.renderer.renderTarget
const dynamicEnvMapMaterial = new THREE.MeshPhongMaterial({envMap: this.cubeRenderTarget.texture
})
const sphereGeometry = new THREE.SphereGeometry(10, 15, 15)
this.sphere = new THREE.Mesh(sphereGeometry, dynamicEnvMapMaterial)
this.scene.add(this.sphere)

2.3 render中更新立方体相机

this.cubeCamera.update(this.renderer, this.scene) //立方体相机更新

通过以上三步就可以实现将场景中除球体以外的所有模型作为环境贴图添加到球体上,支持动态变化,除此之外还有几点需要说明一下,具体详见以下步骤

2.4 创建场景的全景贴图

这一步与上一篇文章一样,代码如下

// 创建场景
createScene() {this.scene = new THREE.Scene()const publicPath = process.env.BASE_URL//创建全景贴图设置为场景背景this.scene.background = new THREE.CubeTextureLoader().setPath(`${publicPath}textures/cubemap/parliament/`).load(['posx.jpg','negx.jpg','posy.jpg','negy.jpg','posz.jpg','negz.jpg'])
}

2.5 创建场景中的模型

模型包括一个立方体和一个球体,要注意一下几点

  • 创建静态环境贴图材质
    这里就是使用场景的背景创建环境贴图材质,只需要将场景的背景赋值给材质的envMap即可
  • 创建方块和圆环
    这里使用BoxGeometry创建一个立方体模型,使用TorusGeometry创建一个圆环,它们使用的材质都是刚刚创建的环境贴图材质
  • 创建动态环境贴图的球体
    这里文章中 2.2 已有说明,请直接看代码
// 创建模型
createModels() {const material = new THREE.MeshPhongMaterial()material.envMap = this.scene.background //场景背景设置为材质的环境贴图//创建方块const boxGeometry = new THREE.BoxGeometry(15, 15, 15)this.cube = new THREE.Mesh(boxGeometry, material)this.cube.position.set(-22, 0, 0)this.scene.add(this.cube)//构建圆环const torusGeometry = new THREE.TorusGeometry(8, 3, 16, 100)this.torus = new THREE.Mesh(torusGeometry, material)this.torus.position.set(22, 0, 0)this.scene.add(this.torus)//创建球体this.renderer.renderTargetconst dynamicEnvMapMaterial = new THREE.MeshPhongMaterial({envMap: this.cubeRenderTarget.texture})const sphereGeometry = new THREE.SphereGeometry(10, 15, 15)this.sphere = new THREE.Mesh(sphereGeometry, dynamicEnvMapMaterial)this.scene.add(this.sphere)
}

3. demo代码

<template><div><div id="container" /><div class="controls-box"><section><el-row><el-checkbox v-model="properties.rotate">rotate</el-checkbox></el-row><el-row><div v-for="(item,key) in properties" :key="key"><div v-if="item&&item.name!=undefined"><el-col :span="8"><span class="vertice-span">{{ item.name }}</span></el-col><el-col :span="13"><el-slider v-model="item.value" :min="item.min" :max="item.max" :step="item.step" :format-tooltip="formatTooltip" @change="propertiesChange" /></el-col><el-col :span="3"><span class="vertice-span">{{ item.value }}</span></el-col></div></div></el-row><el-row><el-col :span="8" class="label-col"><label>texture</label></el-col><el-col :span="16"><el-select v-model="properties.textureType" placeholder="请选择" @change="propertiesChange"><el-option v-for="item in texturesOptions" :key="item.value" :label="item.label" :value="item.value" /></el-select></el-col></el-row></section></div></div>
</template><script>
import * as THREE from 'three'
import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls.js'
export default {data() {return {texturesOptions: [{value: 'bathroom',label: 'bathroom'},{value: 'plaster',label: 'plaster'},{value: 'metal-floor',label: 'metal-floor'},{value: 'none',label: 'none'}],properties: {normalScale: {name: 'normalScale',value: 1,min: -2,max: 2,step: 0.1},reflectivity: {name: 'reflectivity',value: 1,min: 0,max: 2,step: 0.1},textureType: 'none',rotate: false},cube: null,sphere: null,torus: null,camera: null,cubeCamera: null,cubeRenderTarget: null,scene: null,renderer: null,controls: null}},mounted() {this.init()},methods: {formatTooltip(val) {return val},// 初始化async init() {this.createScene() // 创建场景await this.createRender() // 创建渲染器this.createCamera() // 创建相机this.createLight() // 创建光源this.createModels() // 创建模型this.createControls() // 创建控件对象this.render() // 渲染},// 创建场景createScene() {this.scene = new THREE.Scene()const publicPath = process.env.BASE_URL//创建全景贴图设置为场景背景this.scene.background = new THREE.CubeTextureLoader().setPath(`${publicPath}textures/cubemap/parliament/`).load(['posx.jpg','negx.jpg','posy.jpg','negy.jpg','posz.jpg','negz.jpg'])},// 创建模型createModels() {const material = new THREE.MeshPhongMaterial()material.envMap = this.scene.background //场景背景设置为材质的环境贴图//创建方块const boxGeometry = new THREE.BoxGeometry(15, 15, 15)this.cube = new THREE.Mesh(boxGeometry, material)this.cube.position.set(-22, 0, 0)this.scene.add(this.cube)//构建圆环const torusGeometry = new THREE.TorusGeometry(8, 3, 16, 100)this.torus = new THREE.Mesh(torusGeometry, material)this.torus.position.set(22, 0, 0)this.scene.add(this.torus)//创建球体this.renderer.renderTargetconst dynamicEnvMapMaterial = new THREE.MeshPhongMaterial({envMap: this.cubeRenderTarget.texture})const sphereGeometry = new THREE.SphereGeometry(10, 15, 15)this.sphere = new THREE.Mesh(sphereGeometry, dynamicEnvMapMaterial)this.scene.add(this.sphere)},// 创建光源createLight() {// 环境光const ambientLight = new THREE.AmbientLight(0xffffff) // 创建环境光this.scene.add(ambientLight) // 将环境光添加到场景const spotLight = new THREE.SpotLight(0xffffff) // 创建聚光灯spotLight.position.set(0, 50, 50)spotLight.intensity = 2.2this.scene.add(spotLight)},// 创建相机createCamera() {const element = document.getElementById('container')const width = element.clientWidth // 窗口宽度const height = element.clientHeight // 窗口高度const k = width / height // 窗口宽高比// PerspectiveCamera( fov, aspect, near, far )this.camera = new THREE.PerspectiveCamera(45, k, 0.1, 1000)this.camera.position.set(0, 12, 68) // 设置相机位置this.camera.lookAt(new THREE.Vector3(0, 0, 0)) // 设置相机方向this.scene.add(this.camera)const renderTarget = this.renderer.getRenderTarget()//创建立方体渲染器目标对象this.cubeRenderTarget = new THREE.WebGLCubeRenderTarget(128, {format: THREE.RGBFormat,generateMipmaps: true,minFilter: THREE.LinearMipmapLinearFilter})//创建立方体相机this.cubeCamera = new THREE.CubeCamera(1, 100000, this.cubeRenderTarget)this.scene.add(this.cubeCamera)},// 创建渲染器createRender() {const element = document.getElementById('container')this.renderer = new THREE.WebGLRenderer({ antialias: true, alpha: true })this.renderer.setSize(element.clientWidth, element.clientHeight) // 设置渲染区域尺寸this.renderer.shadowMap.enabled = true // 显示阴影// this.renderer.shadowMap.type = THREE.PCFSoftShadowMapthis.renderer.setClearColor(0xeeeeee, 1) // 设置背景颜色element.appendChild(this.renderer.domElement)},propertiesChange() {const publicPath = process.env.BASE_URL//如果不为none为方块加载纹理贴图if (this.properties.textureType !== 'none') {const texture = new THREE.TextureLoader().load(`${publicPath}textures/general/` +this.properties.textureType +'.jpg')this.cube.material.map = textureconst normal = new THREE.TextureLoader().load(`${publicPath}textures/general/` +this.properties.textureType +'-normal.jpg')this.cube.material.normalMap = normal// 更新法线缩放this.cube.material.normalScale.set(this.properties.normalScale.value,this.properties.normalScale.value) // normalScale(x,y)} else {this.cube.material = new THREE.MeshPhongMaterial({envMap: this.scene.background})}// 克隆方块材质赋值给圆环材质this.torus.material = this.cube.material.clone()//更新模型的材质折射率this.cube.material.reflectivity = this.properties.reflectivity.valuethis.torus.material.reflectivity = this.properties.reflectivity.value//更新材质中的纹理this.cube.material.needsUpdate = truethis.torus.material.needsUpdate = true},//模型旋转更新updateRotation() {if (this.properties.rotate) {this.cube.rotation.x += 0.01this.cube.rotation.y += 0.01this.torus.rotation.x += 0.01this.torus.rotation.y += 0.01}},render() {requestAnimationFrame(this.render)this.updateRotation() //模型旋转更新this.cubeCamera.update(this.renderer, this.scene) //立方体相机更新this.renderer.render(this.scene, this.camera)},// 创建控件对象createControls() {this.controls = new OrbitControls(this.camera, this.renderer.domElement)}}
}
</script><style>
#container {position: absolute;width: 100%;height: 100%;
}
.controls-box {position: absolute;right: 5px;top: 5px;width: 300px;padding: 10px;background-color: #fff;border: 1px solid #c3c3c3;
}
.label-col {padding: 8px 5px;
}.vertice-span {line-height: 38px;padding: 0 2px 0 10px;
}
</style>

three.js使用CubeCamera创建反光效果,动态环境贴图实现,立方体全景贴图(vue中使用three.js83)相关推荐

  1. Three.js - 使用 CubeCamera 创建反光效果

    使用环境贴图可以创建虚假的反光效果,但是是静态的,并且不能实现镜面反射的效果,镜面所反射的物体是动态的,可以通过THREE.CubeCamera来实现镜面反射的效果. 1.示例 示例 https:// ...

  2. 在Simscape中创建虚拟机器人环境(一):组装机器人并从CAD中导入

    在Simscape中创建虚拟机器人环境:组装机器人并从CAD中导入 在接下来的两个博客中,我们希望教授如何在机器人设计和编程中使用动态三维模拟,因此我们与马特·谢弗谁是应用程序支持工程师.他将教你如何 ...

  3. three.js贴图之CubeTextureLoader全景贴图

    学习交流欢迎加群:789723098,博主会将一些demo整理共享 有时候我们在创建地图街景或者地点全景图的时候,会经常用到THREE.CubeTextureLoader来对场景Scene的背景进行贴 ...

  4. THREE.JS 使用CUBECAMERA相机创建反光效果

    THREE.JS 使用CUBECAMERA相机创建反光效果 先看下效果 源码 <!DOCTYPE html> <html lang="en"> <he ...

  5. 96 Three.js 使用cubeCamera相机创建反光效果

    案例查看地址:http://www.wjceo.com/blog/threejs/2018-05-03/159.html 通过案例可以看到,中间的球体不但可以和上一节一样看到环境贴图的相关纹理,连两边 ...

  6. python鱼眼图像识别_一种融合鱼眼图像与深度图像的动态环境视觉里程计方法与流程...

    本发明涉及移动机器人同步定位与地图构建(SLAM)技术领域,尤其是适用于动态环境的基于鱼眼图像与深度图像的视觉里程计方法. 背景技术: 定位技术是移动机器人实现各项复杂任务的技术基础.里程计便是一类简 ...

  7. AWS EKS 创建k8s生产环境实例

    #AWS EKS 创建k8s生产环境实例 在AWS部署海外节点, 图简单使用web控制台创建VPC和k8s集群出错(k8s), 使用cli命令行工具创建成功 本实例为复盘, 记录aws命令行工具创建e ...

  8. vscode新建html运行js,用Visual Studio Code创建JavaScript运行环境

    什么是VSCode Visual Studio Code (简称 VS Code / VSC) 是一款于2015年由微软免费开源的现代化轻量级代码编辑器,支持几乎所有主流的开发语言的语法高亮.智能代码 ...

  9. threeJS 创建反光效果

    参看博客Three.js 使用cubeCamera相机创建反光效果 效果图 总体步骤 ① 创建场景 ② 创建相机 ③ 创建物体 ④ 创建渲染器 html代码 <!DOCTYPE html> ...

最新文章

  1. java快递下单模块,Java开发快递物流项目(7)
  2. android入门学习-天气预报app(一)
  3. 【一】Windows API 零门槛编程指南——MessageBox 基本使用及基础讲解
  4. native下拉图片放大 react_RN下拉图片放大 - Chason-洪的个人空间 - OSCHINA - 中文开源技术交流社区...
  5. winscp普通用户向linux根目录中上传文件无法建立远程文件
  6. 经纬度5位数和6位数差多少_经度和纬度的最大长度是多少?
  7. 20.4.26工作感想
  8. 提问的价值,你了解多少?
  9. QQ空间花匠免费代码
  10. 收藏:不错的数据中台建设方法论
  11. oracle ora 3136,oracle中ORA-3136,ORA-609
  12. 51单片机仿真——中断系统(2)
  13. 计算机c程序题孔融让梨,幼儿园大班语言游戏教案《孔融让梨》含PPT课件.doc
  14. php7.4 源码安装
  15. C#特性——Description
  16. 在调试器里看LINUX内核态栈溢出
  17. LyX 发布撑持 CJK 的 1.5 正式版
  18. 给定两个整数,被除数 dividend 和除数 divisor。将两数相除,要求不使用乘法、除法和 mod 运算符。
  19. json数组字符串转list集合
  20. mysql身份证号校验函数

热门文章

  1. cellpadding 和cellspacing区别
  2. Apache 配置禁止IP地址访问,只允许使用域名的方式访问
  3. 2023新型智慧城市解决方案(ppt可编辑)
  4. 1 access中iif函数中的_Access中IIF,SWITCH,CHOOSE的使用
  5. 基于80s电影下载网的电影信息爬虫
  6. 了解websocket是什么
  7. SpringBoot 启动时的运行方法
  8. Neural Radiance Caching
  9. 计算机系统:数据表示与运算实验
  10. i9-13900H参数 酷睿i913900H性能怎么样 相当于什么水平