Cesium-Examples/examples/cesiumEx/5.1.1、雾Webgl2.html
2025-06-12 14:10:21 +08:00

125 lines
4.9 KiB
HTML
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

<!--********************************************************************
* by jiawanlong
*********************************************************************-->
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8" />
<link
rel="stylesheet"
href="./../../libs/cesium/Cesium1.98/Widgets/widgets.css"
/>
<script
type="text/javascript"
src="./../../libs/cesium/Cesium1.98/Cesium.js"
></script>
</head>
<body
style="
margin: 0;
overflow: hidden;
background: #fff;
width: 100%;
height: 100%;
position: absolute;
top: 0;
"
>
<div id="map" style="margin: 0 auto; width: 100%; height: 100%"></div>
<script type="text/javascript">
Cesium.Ion.defaultAccessToken =
"eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiIyMjBhMzcxMC0wNjBiLTRmYjItYjY1MC0wMzAwMzMyMGUyMmEiLCJpZCI6MzAzNzc3LCJpYXQiOjE3NDc2Mzk0NTV9.E_90aKtVdzRGlU2z48VwJ4mWvl-uuDkfQBCOO6zbzn4";
const viewer = new Cesium.Viewer("map", {});
// 开启帧率
viewer.scene.debugShowFramesPerSecond = true;
const tileset = new Cesium.Cesium3DTileset({
url: "./data/tileset.json",
});
tileset.readyPromise
.then(function (tileset) {
viewer.scene.primitives.add(tileset);
viewer.zoomTo(tileset);
})
.catch(function (error) {
console.log(error);
});
// 模型删除
// viewer.scene.primitives.remove(tileset)
// viewer.scene.primitives.removeAll()
function setFogEffect1(viewer) {
const fs = `
float getDistance(sampler2D depthTexture, vec2 texCoords)
{
//它用于将从深度纹理中读取到的深度值进行解压缩,以便在着色器中进行深度测试和深度值比较等操作。
//深度纹理通常用于实现阴影效果、深度检测等功能。
//在Cesium中深度值通常被存储在一个16位的纹理单元中这个值被压缩成0到1之间的浮点数以便节省显存空间。
float depth = czm_unpackDepth(texture(depthTexture, texCoords));
//若深度值为0则返回无穷远
if (depth == 0.0) {
return czm_infinity;
}
//将窗口坐标系(即屏幕坐标系)下的像素坐标转换为相机坐标系下的坐标
vec4 eyeCoordinate = czm_windowToEyeCoordinates(gl_FragCoord.xy, depth);
//返回物体离相机的距离
return -eyeCoordinate.z / eyeCoordinate.w;
}
//根据距离,在中间进行插值
float interpolateByDistance(vec4 nearFarScalar, float distance)
{
//根据常识,雾应该是距离远,越看不清,近距离内的物体可以看清
//因此近距离alpha=0远距离的alpha=1.0
//本例中设置可见度为200米
//雾特效的起始距离
float startDistance = nearFarScalar.x;
//雾特效的起始alpha值
float startValue = nearFarScalar.y;
//雾特效的结束距离
float endDistance = nearFarScalar.z;
//雾特效的结束alpha值
float endValue = nearFarScalar.w;
//根据每段距离占总长度的占比插值alpha距离越远alpha值越大。插值范围0,1。
float t = clamp((distance - startDistance) / (endDistance - startDistance), 0.0, 1.0);
return mix(startValue, endValue, t);
}
vec4 alphaBlend(vec4 sourceColor, vec4 destinationColor)
{
return sourceColor * vec4(sourceColor.aaa, 1.0) + destinationColor * (1.0 - sourceColor.a);
}
uniform sampler2D colorTexture;
uniform sampler2D depthTexture;
uniform vec4 fogByDistance;
uniform vec4 fogColor;
in vec2 v_textureCoordinates;
void main(void)
{
//获取地物距相机的距离
float distance = getDistance(depthTexture, v_textureCoordinates);
//获取场景原本的纹理颜色
vec4 sceneColor = texture(colorTexture, v_textureCoordinates);
//根据距离对alpha进行插值
float blendAmount = interpolateByDistance(fogByDistance, distance);
//将alpha变化值代入雾的原始颜色中并将雾与场景原始纹理进行融合
vec4 finalFogColor = vec4(fogColor.rgb, fogColor.a * blendAmount);
out_FragColor = alphaBlend(finalFogColor, sceneColor);
}`;
viewer.scene.postProcessStages.add(
new Cesium.PostProcessStage({
name: "test",
fragmentShader: fs,
uniforms: {
fogByDistance: new Cesium.Cartesian4(10, 0.0, 200, 0.7),
fogColor: Cesium.Color.WHITE,
},
})
);
}
setFogEffect1(viewer);
</script>
</body>
</html>