一、实现原理

通过shader,将物体的透明度由下往上,从1到0渐变即可(只需要两圈顶点,底下一圈alpha设为1,上面一圈alpha设为0)

二、实现步骤

1、创建geometry

这个几何体类似于圆柱,只是没有上下两个底面

         /*let bottomPos = [];let topPos = [];let angleOffset = Math.PI*2/segment;for(var i=0;i<segment;i++){let x = Math.cos(angleOffset * i)*radius;let z = Math.sin(angleOffset * i)*radius;bottomPos.push(new Vector3(x,0,z));topPos.push(new Vector3(x,height,z));}bottomPos = bottomPos.concat(topPos);let face = []for(var i=0;i<segment;i++){if(i != segment - 1){face.push(new Face3(i+segment+1,i,i+segment));face.push(new Face3(i,i+segment+1,i+1));}else{face.push(new Face3(segment,i,i+segment));face.push(new Face3(i,segment,0));}}let geo = new Geometry();geo.vertices = bottomPos;geo.faces = face;*///更新为BufferGeometrylet bottomPos = []let topPos = []let angleOffset = (Math.PI * 2) / segmentfor (var i = 0; i < segment; i++) {let x = Math.cos(angleOffset * i) * radiuslet z = Math.sin(angleOffset * i) * radiusbottomPos.push(x, 0, z)topPos.push(x, height, z)}bottomPos = bottomPos.concat(topPos)let face = []for (var i = 0; i < segment; i++) {if (i != segment - 1) {face.push(i + segment + 1, i, i + segment)face.push(i, i + segment + 1, i + 1)} else {face.push(segment, i, i + segment)face.push(i, segment, 0)}}let geo = new BufferGeometry()geo.setAttribute('position', new BufferAttribute(new Float32Array(bottomPos), 3))geo.setIndex(new BufferAttribute(new Uint16Array(face), 1))

2、创建shader材质

            let c = new Color(color);let mat = new ShaderMaterial({uniforms: {targetColor:{value:new Vector3(c.r,c.g,c.b)},height: { value: height},},side: DoubleSide,transparent:true,//depthTest:false,depthWrite:false,vertexShader: ["varying vec3 modelPos;","void main() {","   modelPos = position;"," gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );","}"].join("\n"),fragmentShader: ["uniform vec3 targetColor;","uniform float height;","varying vec3 modelPos;","void main() {","   gl_FragColor = vec4(targetColor.xyz,(1.0 - modelPos.y/height)*(1.0 - modelPos.y/height));","}"].join("\n")});

需要注意的是使用双面渲染、打开透明、关闭深度写入以及alpha的获取(这里使用二次方程,比线性函数过度更自然)

三、完整代码

/*** 生成并返回柱状渐变光环* @param {*} radius 半径* @param {*} height 高度* @param {*} color 颜色* @returns */getAureole(radius,height,color){let geo,mat;let segment = 64;//geo{/*let bottomPos = [];let topPos = [];let angleOffset = Math.PI*2/segment;for(var i=0;i<segment;i++){let x = Math.cos(angleOffset * i)*radius;let z = Math.sin(angleOffset * i)*radius;bottomPos.push(new Vector3(x,0,z));topPos.push(new Vector3(x,height,z));}bottomPos = bottomPos.concat(topPos);let face = []for(var i=0;i<segment;i++){if(i != segment - 1){face.push(new Face3(i+segment+1,i,i+segment));face.push(new Face3(i,i+segment+1,i+1));}else{face.push(new Face3(segment,i,i+segment));face.push(new Face3(i,segment,0));}}geo = new Geometry();geo.vertices = bottomPos;geo.faces = face;*///更新为BufferGeometrylet bottomPos = []let topPos = []let angleOffset = (Math.PI * 2) / segmentfor (var i = 0; i < segment; i++) {let x = Math.cos(angleOffset * i) * radiuslet z = Math.sin(angleOffset * i) * radiusbottomPos.push(x, 0, z)topPos.push(x, height, z)}bottomPos = bottomPos.concat(topPos)let face = []for (var i = 0; i < segment; i++) {if (i != segment - 1) {face.push(i + segment + 1, i, i + segment)face.push(i, i + segment + 1, i + 1)} else {face.push(segment, i, i + segment)face.push(i, segment, 0)}}let geo = new BufferGeometry()geo.setAttribute('position', new BufferAttribute(new Float32Array(bottomPos), 3))geo.setIndex(new BufferAttribute(new Uint16Array(face), 1))}//mat{let c = new Color(color);mat = new ShaderMaterial({uniforms: {targetColor:{value:new Vector3(c.r,c.g,c.b)},height: { value: height},},side: DoubleSide,transparent:true,//depthTest:false,depthWrite:false,vertexShader: ["varying vec3 modelPos;","void main() {","   modelPos = position;","    gl_Position = projectionMatrix * modelViewMatrix * vec4( position, 1.0 );","}"].join("\n"),fragmentShader: ["uniform vec3 targetColor;","uniform float height;","varying vec3 modelPos;","void main() {","   gl_FragColor = vec4(targetColor.xyz,(1.0 - modelPos.y/height)*(1.0 - modelPos.y/height));","}"].join("\n")});}let mesh = new Mesh(geo,mat);mesh.renderOrder = 9999return mesh;}

Threejs渐变光柱效果相关推荐

  1. 悬停渐变特效html,CSS3 transition属性实现hover渐变动画效果

    CSS3 transition属性实现hover渐变动画效果 我们知道许多网页动态特效都是由FLASH或JQUERY之类的JS特效库实现的实际上现在CSS3也能实现很多类似效果了,只是在各种浏览器中兼 ...

  2. ps怎么制作流体_PS教程:制作渐变流体效果海报

    相信大家都看到过一些很酷的使用渐变流体的海报,此类海报一般都充满活力,而且色彩的饱和度都很高,因为这样更能让作品脱颖而出. 看到这些非常有立体感的渐变色彩,大家可能以为只有用很复杂的三维软件才能够做出 ...

  3. python打出由边框包围的_python opencv 图像边框(填充)添加及图像混合的实现方法(末尾实现类似幻灯片渐变的效果)...

    图像边框的实现 图像边框设计的主要函数 cv.copyMakeBorder()--实现边框填充 主要参数如下: 参数一:源图像--如:读取的img 参数二--参数五分别是:上下左右边的宽度--单位:像 ...

  4. jQuery中的渐变动画效果

    jQuery中的渐变动画效果jQuery中的渐变动画效果 转载于:https://www.cnblogs.com/DreamDrive/p/5780292.html

  5. CSS和JS两种颜色渐变文字效果代码

    js实现颜色渐变文字效果代码: <!-- js颜色渐变色文字 --> <div id="moml"> <div style="text-al ...

  6. android 底部tab效果,Android 仿微信底部渐变Tab效果

    先来看一下效果图 除了第三个的发现Tab有所差别外,其他的基本还原了微信的底部Tab渐变效果 每个Tab都是一个自定义View,根据ImageView的tint属性来实现颜色渐变效果,tint属性的使 ...

  7. Flutter SliverAnimatedOpacity 透明渐变动画效果

    志在巅峰的攀登者,不会陶醉在沿途的某个脚印之中,在码农的世界里,优美的应用体验,来源于程序员对细节的处理以及自我要求的境界,年轻人也是忙忙碌碌的码农中一员,每天.每周,都会留下一些脚印,就是这些创作的 ...

  8. Flutter透明度渐变动画Opacity实现透明度渐变动画效果

    题记 -- 执剑天涯,从你的点滴积累开始,所及之处,必精益求精,即是折腾每一天. ** 你可能需要 CSDN 网易云课堂教程 掘金 EDU学院教程 知乎 Flutter系列文章 在Flutter 中实 ...

  9. Flutter透明度渐变动画FadeTransition实现透明度渐变动画效果

    题记 -- 执剑天涯,从你的点滴积累开始,所及之处,必精益求精,即是折腾每一天. ** 你可能需要 CSDN 网易云课堂教程 掘金 EDU学院教程 知乎 Flutter系列文章 在Flutter 中实 ...

最新文章

  1. R语言包_reshape2
  2. hdu 3183 st表
  3. I春秋——web Write up(二)
  4. 数据库四种事务隔离级别详解
  5. 存储过程 传 datatable
  6. 产品经理有哪些类型?
  7. android 键盘遮盖输入框_Android软键盘挡住输入框的终极解决方案
  8. 浅谈C# Socket编程及C#如何使用多线程
  9. Storyboard使用心得
  10. 情侣的网站代码java_GitHub - Mutiantian/lovers-website: 程序员的情侣网站 (programmer's website of lovers)...
  11. hsql转换oracle,Hive系列之HSQL转换成MapReduce过程
  12. A-PDF Watermark
  13. 思科服务器如何进入网站,思科路由器怎么进入设置网站
  14. Failed to list versions for
  15. NYOJ779 兰州烧饼
  16. ei指什么_今天说一下EI是什么
  17. [Windows10]Win10如何获取最高管理员权限
  18. 联想拯救者y9000p和r9000p的区别
  19. Windows批处理脚本(BAT,CMD)简明教程
  20. 格里高利历java_java – 从Hijri日期字符串中获取格里高利日期

热门文章

  1. 如何保证库存数量及时
  2. 黑马--Linux基础学习笔记
  3. 怎么调整图片尺寸大小?快速修改图片大小的方法
  4. 信息收集--域内信息收集
  5. 1995年中国台式计算机价格,大江东去 百舸争流——1995年国内台式PC市场综述
  6. HPE: smart storage: hpssacli:
  7. Python:年月日日历图的显示操作、time模块常用法
  8. 单片机:什么是看门狗?
  9. 【 定义一个长方形Rect类再派生出长方体类Cub】
  10. AI绘画5大免费工具