需求描述:
使用obj模型和mtl材质绘制地图,为地图边界添加发光边界线。
实现思路:
借助three.js的OutlinePass管道和Raycaster光线投射实现发光线条
实现步骤:
1、引入相关js文件
EffectComposer:用于实现three.js中的后处理效果。EffectComposer可以向其添加多个Pass 对象,处理通道以产生最终的视觉结果。后处理通道按其添加/插入的顺序执行。最后一遍自动渲染到屏幕上。
<!-- EffectComposer(效果组合器)对象 -->
import { EffectComposer } from 'three/examples/jsm/postprocessing/EffectComposer'
RenderPass:它将3D场景渲染带到效果组合器中与后续通道做叠加效果。
<!-- RenderPass/该通道在指定的场景和相机的基础上渲染出一个新场景 -->
import { RenderPass } from 'three/examples/jsm/postprocessing/RenderPass'
ShaderPass:着色器,它需要一个对象,其中包含定义顶点着色器、片段着色器和默认输 入的信息。 它将处理设置从哪个纹理读取以获取上一次传递的结果以及渲染到何处。
<!-- ShaderPass/使用该通道你可以传入一个自定义的着色器,用来生成高级的、自定义的后期处理通道 -->
import { ShaderPass } from 'three/examples/jsm/postprocessing/ShaderPass.js'
OutlinePass:线通道,该通道可以为物体(场景中被添加到通道中的物体)的边缘添加一个发光效果。是本案例中实现发光的管道载体。
import { OutlinePass } from 'three/examples/jsm/postprocessing/OutlinePass'
2、在obj模型实例中选择需要渲染的材质
objLoader.load(objName, function (obj) {
obj.traverse(child => {
if (child.name === '路径.006') {
// 发光材质在此代码块中添加
}
}
}
3、创建通道,设置发光属性,并添加到EffectComposer效果组合器实例中。
// 创建一个EffectComposer(效果组合器)对象,然后在该对象上添加后期处理通道。
const composer = new EffectComposer(renderer)
// 新建一个场景通道 为了覆盖到原理来的场景上
const renderPass = new RenderPass(scene, camera)
composer.addPass(renderPass)
//创建物体边缘发光通道
const outlinePass = new OutlinePass(
new THREE.Vector2(window.innerWidth, window.innerHeight),
scene,
camera,
[intersects[0].object],
)
//定义样式
outlinePass.edgeStrength = 2 // 边框的亮度
outlinePass.edgeGlow = 0 // 光晕
// outlinePass.usePatternTexture = false // 是否使用父级的材质
outlinePass.edgeThickness = 2 // 边框宽度
outlinePass.downSampleRatio = 2 // 边框弯曲度
outlinePass.pulsePeriod = 0 // 呼吸闪烁的速度
outlinePass.visibleEdgeColor.set('#FFE99C') // 呼吸显示的颜色
outlinePass.hiddenEdgeColor = new THREE.Color(0, 0, 0) // 呼吸消失的颜色
composer.addPass(renderPass)
composer.addPass(outlinePass)
const effectColorSpaceConversion = new ShaderPass(GammaCorrectionShader)
composer.addPass(effectColorSpaceConversion)
遇到的衍生问题:
为了是渲染效果更加真实,在渲染器WebGLRenderer创建的时候,将渲染器的输出编码设置为了THREE.sRGBEncoding,让效果比较明亮
未添加发光通道时候的效果:可以明显的看到光比较明亮。
添加发光通道之后的效果明显变暗:
解决办法:修改源码
在我写的这个demo中我主要用的是ShaderPass和ShaderPass通道,所以只需要将ShaderPass.js和 OutlinePass.js文件中的渲染器环境修改为本实例的渲染器环境即可。