当前位置:   article > 正文

cesium webgl2.0 shader 各种函数使用_cesium 着色器webgl2

cesium 着色器webgl2

1. 和角度相关的函数

下面是一个和角度相关的函数,他们的用法我们都要熟悉。

函数参数描述
sin(x)弧度正弦函数
cos(x)弧度余弦函数
tan(x)弧度正切函数
asin(x)弧度反正弦函数
acos(x)弧度反余弦函数
atan(x)弧度反正切函数
radians(x)角度角度转换为弧度
degrees(x)弧度弧度转换为角度

2. 数学函数

这类主要是对指数对数幂函数的操作。

函数描述
pow(x,y)x的y次方。如果x小于0,结果是未定义的。同样,如果x=0并且y<=0,结果也是未定义的。
exp(x)e的x次方
log(x)计算满足x等于e的y次方的y的值。如果x的值小于0,结果是未定义的。
exp2(x)计算2的x次方
log2(x)计算满足x等于2的y次方的y的值。如果x的值小于0,结果是未定义的。
sqrt(x)计算x的开方。如果x小于0,结果是未定义的。
inversesqrt(x)计算x的开方之一的值,如果x小于等于0,结果是未定义的。

3. 常用函数

这里是常用函数,和js中的内置函数很像,需要牢记。

函数描述
abs(x)返回x的绝对值
sign(x)如果x>0,返回1.0;如果x=0,返回0,如果x<0,返回-1.0
floor(x)返回小于等于x的最大整数值
ceil(x)返回大于等于x的最小整数值
fract(x)返回x-floor(x),即返回x的小数部分
mod(x, y)返回x和y的模
min(x, y)返回x和y的值较小的那个值。
max(x, y)返回x和y的值较大的那个值。
clamp(x, minVal, maxVal)将x值钳于minVal和maxVal之间,意思就是当x<minVal时返回minVal,当x>maxVal时返回maxVal,当x在minVal和maxVal之间时,返回x
mix(x, y, a)返回线性混合的x和y,如:x*(1−a)+y*a
step(edge, x)如果x < edge,返回0.0,否则返回1.0
smoothstep(edge0, edge1, x)如果x <= edge0,返回0.0 ;如果x >= edge1 返回1.0;如果edge0 < x < edge1,则执行0~1之间的平滑埃尔米特差值。如果edge0 >= edge1,结果是未定义的。

5.内置函数参数常见形式

内置函数参数数据类型常见形式:float、vec2、vec3、vec4

6.使用内置函数实现各种图形

在片元着色器(fragment.glsl)中,通过各种内置函数实现不同效果的图形。
在fragment.glsl的main()函数前声明uv值及数据精度:

precision lowp float;
in vec2 v_st;
  • 1
  • 2

6.1 利用取模函数mod()达到反复渐变效果

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
// 将纹理坐标的y值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
  float strength = mod(v_st.y * 10.0, 1.0);
  out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9

在这里插入图片描述

6.2 利用step(edge, x)实现斑马线条纹效果

1)该step(edge,x)函数中,如果x < edge,返回0.0,否则返回1.0。

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
// 将纹理坐标的y值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
  float strength = mod(v_st.y * 10.0, 1.0);
  // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
  strength = step(.5, strength);
  out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11

在这里插入图片描述
2)更改step中边界值为0.8,当strength大于0.8时返回1,否则返回0,因此黑色宽度占80%,白色占20%。代码如下

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
  // 将纹理坐标的y值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
  float strength = mod(v_st.y * 10.0, 1.0);
  // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
  strength = step(.8, strength);

  out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

在这里插入图片描述
3) 同理,当取vUv的x值时,则生成竖向条纹。

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
  // 将纹理坐标的x值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
  float strength = mod(v_st.x * 10.0, 1.0);
  // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
  strength = step(.8, strength);

  out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12

在这里插入图片描述
4)横竖条纹相加

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
 // 将纹理坐标的x值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
 float strength = mod(v_st.x * 10.0, 1.0);
 // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
 strength = step(.8, strength);
 strength += step(0.8, mod(v_st.y * 10.0, 1.0));

 out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

在这里插入图片描述
5)条纹相乘(相交位置为1,其余为0)

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
 // 将纹理坐标的x值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
 float strength = mod(v_st.x * 10.0, 1.0);
 // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
 strength = step(.8, strength);
 strength *= step(0.8, mod(v_st.y * 10.0, 1.0));

 out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

在这里插入图片描述
6)条纹相减

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
 // 将纹理坐标的x值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
 float strength = mod(v_st.x * 10.0, 1.0);
 // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
 strength = step(.8, strength);
 strength -= step(0.8, mod(v_st.y * 10.0, 1.0));

 out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

在这里插入图片描述
7)方块图形

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;
void main() {
 // 将纹理坐标的x值乘以10.0,然后取余数,得到的值范围是[0, 1] => 实现反复渲染10次横条
 float strength = mod(v_st.x * 10.0, 1.0);
 // 类似于if(strength < 0.5) strength = 0.0; else strength = 1.0;
 strength = step(.2, strength);
 strength *= step(.2, mod(v_st.y * 10.0, 1.0));

 out_FragColor = vec4(strength, strength, strength, 1.0);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

在这里插入图片描述
8)炫彩T字

precision lowp float;
in vec3 v_positionMC;
in vec3 v_positionEC;
in vec2 v_st;

void main() {
  // 基于x渲染取交集
  float barX = step(.4, mod(v_st.x * 10.0 - .2, 1.)) * step(.8, mod(v_st.y * 10.0, 1.));
  // 基于y渲染取交集
  float barY = step(.4, mod(v_st.y * 10.0, 1.)) * step(.8, mod(v_st.x * 10.0, 1.));
  float strength = barX + barY;
  out_FragColor = vec4(v_st, 1.0, strength);
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

在这里插入图片描述

6.3 利用绝对值abs()实现中间向两边渐变

// 取值范围是[-.5,.5]
  float strength = abs(v_st.x - 0.5);
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2
  • 3

在这里插入图片描述

6.4 利用取最小值min()实现渐变

float strength = min(abs(v_st.x - 0.5), abs(v_st.y - 0.5));
 out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述

6.5 利用取最大值max()实现渐变效果

float strength = max(abs(v_st.x - 0.5), abs(v_st.y - 0.5));
out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述

6.6 利用step()、max()、abs()实现小正方形

	float strength = step(.1, max(abs(v_st.x - .5), abs(v_st.y - .5)));
	out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述
反之,若中间正方型为白色,外框为黑色,则:

 float strength = step(.1, max(abs(v_st.y - .5), abs(v_st.x - .5)));
 out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述

6.7 利用向下取整函数floor()实现条纹渐变

1)实现纵向条纹(横向渐变)

float strength = floor(v_st.x * 10.) / 10.;
out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述
2)实现横向条纹(纵向渐变)

float strength = floor(v_st.y * 10.) / 10.;
out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述
3)利用条纹相乘实现渐变格子

float strength = floor(v_st.x * 10.) / 10. * floor(v_st.y * 10.) / 10.;
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述

6.8 利用向上取整函数ceil()实现渐变格子

float strength = ceil(v_st.x * 10.) / 10. * ceil(v_st.y * 10.) / 10.;
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述

6.9 利用随机函数radom()实现随机效果

随机函数虽然内置函数并未提供,但可以通过算法实现类随机效果:
在main()函数前对随机函数进行声明:

// 随机函数
float random(vec2 st) {
  return fract(sin(dot(st.xy, vec2(12.9898, 78.233))) * 43758.5453123);
}
  • 1
  • 2
  • 3
  • 4

1)随机效果

float strength = random(v_st);
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述
2)随机格子效果

float strength = ceil(v_st.y * 10.) / 10. * ceil(v_st.x * 10.) / 10.;
  strength = random(vec2(strength, strength));
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2
  • 3

在这里插入图片描述

6.10 使用length返回向量长度(沿半径计算长度)

float strength = length(v_st);
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述

6.11 使用distance函数计算两个向量之间的距离

1)计算uv向量与(0.5,0.5)中心点之间的距离

float strength = 1. - distance(v_st, vec2(0.5, 0.5));
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述
2)利用相除,实现光点效果

float strength = .5 / distance(v_st, vec2(0.5, 0.5)) - 1.;
  out_FragColor = vec4(strength, strength, strength, 1.0);
  • 1
  • 2

在这里插入图片描述
3)实现十字交叉星星效果

float strength = .15 / distance(vec2(v_st.x, (v_st.y - .5) * 5. + .5), vec2(.5, .5)) - 1.;
  strength += .15 / distance(vec2(v_st.y, (v_st.x - .5) * 5. + .5), vec2(.5, .5)) - 1.;
  out_FragColor = vec4(strength, strength, strength, strength);
  • 1
  • 2
  • 3

在这里插入图片描述

6.12 利用旋转函数rotate()实现旋转飞镖效果

// 旋转函数
//(uv,旋转度数,旋转中心)
vec2 rotate(vec2 uv, float rotation, vec2 mid) {
  return vec2(cos(rotation) * (uv.x - mid.x) + sin(rotation) * (uv.y - mid.y) + mid.x, cos(rotation) * (uv.y - mid.y) - sin(rotation) * (uv.x - mid.x) + mid.y);
}
  • 1
  • 2
  • 3
  • 4
  • 5
vec2 rotateUv = rotate(v_st, -czm_frameNumber * 5.0, vec2(0.5));
  float strength = 0.15 / distance(vec2(rotateUv.x, (rotateUv.y - 0.5) * 5.0 + 0.5), vec2(0.5, 0.5)) - 1.0;
  strength += 0.15 / distance(vec2(rotateUv.y, (rotateUv.x - 0.5) * 5.0 + 0.5), vec2(0.5, 0.5)) - 1.0;
  out_FragColor = vec4(strength, strength, strength, strength);
  • 1
  • 2
  • 3
  • 4

在这里插入图片描述

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/不正经/article/detail/727227
推荐阅读
相关标签
  

闽ICP备14008679号