threejs+shader 曲线点运动,飞线运动

这篇博客详细介绍了使用Three.js和shader在3D地球场景中实现自定义飞线样式的多种方法,包括从开始到结束的显示、点的大小变化、透明度过渡以及点在线上的运动等效果,展示了代码实现的细节和关键参数设置。
摘要由CSDN通过智能技术生成

公司大屏维护,产品要求自定义线路样式,UI一天一个脑洞,以下是开发中所更改过的飞线样式,3d地球起始点飞跃由threejs+shader完成,
成品点这里

飞线-从开始到结束都显示

别忘了设置
transparent: true,
depthWrite: false,
blending: THREE.AdditiveBlending,

vertexShader: `
      attribute float aIndex;
      uniform float uTime;
      uniform float uLength;
      uniform float uScale;
      varying float vSize;
      void main() {
        vec4 viewPosition = viewMatrix * modelMatrix * vec4(position,1);
        gl_Position = projectionMatrix *  viewPosition;
        vSize = aIndex- uTime;
        if(vSize<=0.0){
            vSize = vSize + uLength; 
        }else{
          vSize = 0.0;
        }
        gl_PointSize = vSize * uScale;
      }
`,
 fragmentShader: `
      varying float vSize;
      uniform vec3 uColor;
      void main(){
        float distanceToCenter = distance(gl_PointCoord,vec2(0.5));
        float alpha = 1.0 - (distanceToCenter*2.0);
        gl_FragColor = vec4(1,0,0,alpha);
        if(vSize<=0.0){
            gl_FragColor = vec4(1,0,0,0);
        }else{
         	// // gl_FragColor = vec4(uColor,1.0); 
            gl_FragColor = vec4(uColor,alpha); // 圆点点
        }
      }
`

在这里插入图片描述

## 飞线-从开始到结束都显示 uTime*2

代码同上一个案例,设置 vSize = aIndex- uTime * 2

vertexShader: `
     	...代码同上一个案例...
        vSize = aIndex- uTime * 2;
        ...代码同上一个案例...
`,
 fragmentShader: 代码同上一个案例

在这里插入图片描述

飞线-快结束的时候淡出

fragmentShader: `
varying float vSize;
uniform float uTime;
uniform float uLength;
uniform vec3 uColor;
void main(){
  float distanceToCenter = distance(gl_PointCoord,vec2(0.5));
  float alpha = 1.0 - (distanceToCenter*2.0);
  if(vSize<=0.0){
      gl_FragColor = vec4(1,0,0,0);
  }else{
    float s = 0.9;
    if(uTime > uLength *s){
      gl_FragColor = vec4(uColor, alpha - ((uTime - uLength * s) / (uLength * (1.0-s)))); // 圆点
    }else{
      gl_FragColor = vec4(uColor,alpha); // 圆点
    }
  }
}
`,

在这里插入图片描述

飞线- 显示部分点,前面的点大,后面的点小

      vertexShader: `
      attribute float aIndex;
      uniform float uTime;
      uniform float uLength;
      uniform float uScale;
      varying float vSize;
      void main() {
        vec4 modelPosition = modelMatrix * vec4( position, 1.0 ); // 顶点坐标
        gl_Position =  projectionMatrix * viewMatrix * modelPosition;
        float size = aIndex  - uTime; 
        if(size < 0.0) {
          size = size + uLength;
        }
        vSize = (size - uLength / 2.0) * uScale; // 设置二分之一的点为不可见
        gl_PointSize = vSize;
      }
`,
      fragmentShader: `
      varying float vSize;
      uniform vec3 uColor;
      void main(){
        float distanceToCenter = distance(gl_PointCoord,vec2(0.5,0.5));
        float alpha = 1.0 - (distanceToCenter*2.0);
    
        if(vSize<=0.0){
            gl_FragColor = vec4(1,0,0,0);
        }else{
            gl_FragColor = vec4(uColor,alpha);
        }
      }
`,

在这里插入图片描述

飞线- 点越小越透明,形成一个小尾巴

vertexShader: `
 attribute float aIndex;
 uniform float uTime;
 uniform float uLength;
 uniform float uScale;
 varying float vSize;
 void main() {
   vec4 modelPosition = modelMatrix * vec4( position, 1.0 ); // 顶点坐标
   gl_Position =  projectionMatrix * viewMatrix * modelPosition;
   float size = aIndex  - uTime; 
   if(size < 0.0) {
     size = size + uLength;
   }
   vSize = (size - uLength / 2.0) * uScale; // 设置二分之一的点为不可见
   gl_PointSize = vSize;
 }
 `,
 fragmentShader: `
 varying float vSize;
   uniform float uLength;
   uniform float uScale;
   void main(){
     if(vSize <= 0.0){
       gl_FragColor = vec4(1,1,0,0);      
     }else{
       // 根据点的大小设置透明度,点越小越透明
       float opacity = uLength / 2.0 * uScale;
       gl_FragColor = vec4(1,1,0,vSize / opacity);      
     }
   }
 `,

在这里插入图片描述

保留曲线路径

 vertexShader: `
      attribute float aIndex;
      uniform float uTime;
      uniform float uLength;
      uniform float uScale;
      varying float vSize;
      void main() {
        vec4 modelPosition = modelMatrix * vec4( position, 1.0 ); // 顶点坐标
        gl_Position =  projectionMatrix * viewMatrix * modelPosition;
        float size = aIndex  - uTime; 
        if(size < 0.0) {
          size = size + uLength;
        }
        vSize = (size - uLength / 2.0) * uScale; // 设置二分之一的点为不可见
        gl_PointSize = vSize<=2.0?2.0:vSize;
      }
`,
  fragmentShader: `
  varying float vSize;
  uniform vec3 uColor;
  void main(){
    float distanceToCenter = distance(gl_PointCoord,vec2(0.5,0.5));
    float alpha = 1.0 - (distanceToCenter*2.0);
    if(vSize<=2.0){
      gl_FragColor = vec4(1,0,1,alpha);
    }else{
      gl_FragColor = vec4(uColor,alpha);
    }
  }
`,

在这里插入图片描述

点在线上运行

      vertexShader: `
      attribute float aIndex;
      uniform float uTime;
      uniform float uLength;
      uniform float uScale;
      varying float vSize;
      void main() {
        vec4 modelPosition = modelMatrix * vec4( position, 1.0 ); // 顶点坐标
        gl_Position =  projectionMatrix * viewMatrix * modelPosition;
        float size = aIndex  - uTime; 
        if(size < 0.0) {
          size = size + uLength;
        }
        vSize = (size - (uLength * 0.99)); // 只显示0.01的点
        gl_PointSize = vSize<=2.0?2.0:vSize;
      }
`,
      fragmentShader: `
      varying float vSize;
      uniform vec3 uColor;
      void main(){
        float distanceToCenter = distance(gl_PointCoord,vec2(0.5,0.5));
        float alpha = 1.0 - (distanceToCenter*2.0);
        if(vSize<=2.0){
          gl_FragColor = vec4(1,0,1,alpha);
        }else{
          gl_FragColor = vec4(uColor,alpha);
        }
      }
`,

在这里插入图片描述

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值