
作者ZLF在三维GIS可视化中动态日照阴影能够极大提升场景的真实感和沉浸感。如何模拟太阳轨迹变化实现随时间流动的光影效果让场景更具表现力让我们一起看看吧一、数据制作对于上述视频中的三维缓存数据制作此处不做讲述如有需要可参考 iDesktopX 帮助文档https://help.supermap.com/iDesktopX/zh/二、实现思路基本实现思路如下图所示三、示例完整代码!DOCTYPE html html langen head meta charsetutf-8 meta http-equivX-UA-Compatible contentIEEdge,chrome1 meta nameviewport contentwidthdevice-width, initial-scale1, maximum-scale1, minimum-scale1, user-scalableno title日照动画/title link href../../Build/SuperMap3D/Widgets/widgets.css relstylesheet link href./css/bootstrap.min.css relstylesheet link href./css/pretty.css relstylesheet link href./style/shadowQuery.css relstylesheet script src./js/jquery.min.js/script script src./js/bootstrap.min.js/script script src./js/tooltip.js/script script src./js/config.js/script script typetext/javascript src../../Build/SuperMap3D/SuperMap3D.js/script style #animationControls { margin-top: 10px; padding: 10px; background: rgba(255,255,255,0.8); border-radius: 5px; } #currentTimeDisplay { font-weight: bold; color: #333; margin: 5px 0; } .speed-control { width: 100%; margin: 5px 0; } /style /head body div idContainer/div div idloadingbar classspinner div classspinner-container container1 div classcircle1/div div classcircle2/div div classcircle3/div div classcircle4/div /div div classspinner-container container2 div classcircle1/div div classcircle2/div div classcircle3/div div classcircle4/div /div div classspinner-container container3 div classcircle1/div div classcircle2/div div classcircle3/div div classcircle4/div /div /div div idtoolbar classparam-container tool-bar div classparam-item b日期选择/b input idselDate typedate value2026-03-20/ /div div classparam-item b开始时间/b select idstartTime classform-control option value66:00/option option value77:00/option option value88:00/option option value99:00/option option value10 selected10:00/option option value1111:00/option option value1212:00/option /select /div div classparam-item b结束时间/b select idendTime classform-control option value1212:00/option option value1313:00/option option value1414:00/option option value1515:00/option option value1616:00/option option value1717:00/option option value18 selected18:00/option /select /div div classparam-item button typebutton idsunlight classbutton black日照阴影动画/button button typebutton idclear classbutton black清除/button /div div idanimationControls styledisplay:none; div idcurrentTimeDisplay当前时间: 10:00:00/div button typebutton idplayAnimation classbutton black播放/button button typebutton idpauseAnimation classbutton black暂停/button button typebutton idstopAnimation classbutton black停止/button div label播放速度:/label input typerange idspeedControl classspeed-control min1 max100 value50 span idspeedValue50x/span /div /div /div script typetext/javascript // 页面加载完成后执行SuperMap3D 为传入的全局对象 function onload(SuperMap3D) { // 获取引擎类型可能用于 WebGL 上下文配置 var EngineType getEngineType(); // 创建三维视图器配置阴影、时间轴、动画等 var viewer new SuperMap3D.Viewer(Container, { shadows: true, // 开启阴影 shouldAnimate: true, // 允许动画 contextOptions: { contextType: Number(EngineType), // 设置 WebGL 上下文类型 } }); // 等待场景加载完成后执行初始化 viewer.scenePromise.then(function(scene){ init(SuperMap3D, scene, viewer); }); } // 初始化函数设置场景、加载图层、绑定事件 function init(SuperMap3D, scene, viewer) { // 设置分辨率适应设备像素比 viewer.resolutionScale window.devicePixelRatio; var scene viewer.scene; // 设置阴影暗度 scene.shadowMap.darkness 0.4; // 关闭 HDR scene.hdrEnabled false; // 显示太阳 scene.sun.show true; // 开启地球光照 scene.globe.enableLighting true; // 显示工具栏 $(#toolbar).show(); // 移除加载动画 $(#loadingbar).remove(); // 如果不支持深度纹理拾取弹出警告 if(!scene.pickPositionSupported){ alert(不支持深度纹理,阴影分析功能无法使用); } // 获取 Widget 对象用于错误处理等 var widget viewer.Widget; try{ // 打开三维场景SCP 服务返回一个 Promise 数组 var buildPromise scene.open(http://localhost:8090/iserver/services/3D-building/rest/realspace); // 等待所有图层加载完成 SuperMap3D.when.all(buildPromise,function(layers){ // 遍历图层设置不可选中并开启阴影 for(var i 0; i layers.length; i){ layers[i].selectEnabled false; layers[i].shadowType 2; } setCurrentTime(); function setCurrentTime() { viewer.clock.multiplier 1; // 重置速度倍率 viewer.clock.shouldAnimate false; // 停止动画 } // 更新当前时间显示的函数 function updateCurrentTimeDisplay() { var currentTime SuperMap3D.JulianDate.toDate(viewer.clock.currentTime); var timeString currentTime.toLocaleTimeString(); // 格式化为本地时间字符串 $(#currentTimeDisplay).text(当前时间: timeString); } // 监听时钟 tick 事件每次更新显示当前时间 viewer.clock.onTick.addEventListener(function() { updateCurrentTimeDisplay(); }); // 点击“日照阴影动画”按钮设置动画开始、结束时间并启动动画 $(#sunlight).click(function(){ var dateVal $(#selDate).val(); var startTime new Date(dateVal); var endTime new Date(dateVal); var shour Number($(#startTime :selected).val()); // 开始小时 var ehour Number($(#endTime :selected).val()); // 结束小时 // 检查结束时间是否大于开始时间 if(shour ehour) { alert(结束时间必须大于开始时间); return; } // 设置开始和结束的完整日期时间 startTime.setHours(shour); endTime.setHours(ehour); // 配置时钟范围 viewer.clock.startTime SuperMap3D.JulianDate.fromDate(startTime); viewer.clock.stopTime SuperMap3D.JulianDate.fromDate(endTime); viewer.clock.currentTime viewer.clock.startTime.clone(); // 当前时间设为开始时间 // 设置时钟范围为播放完成后重新从时间轴起点开始循环播放 viewer.clock.clockRange SuperMap3D.ClockRange.LOOP_STOP; // 设置播放速度倍率 viewer.clock.multiplier 3600; // 开始动画 viewer.clock.shouldAnimate true; // 显示动画控制面板 $(#animationControls).show(); }); // 播放按钮继续动画 $(#playAnimation).click(function() { viewer.clock.shouldAnimate true; }); // 暂停按钮暂停动画 $(#pauseAnimation).click(function() { viewer.clock.shouldAnimate false; }); // 停止按钮暂停并重置到开始时间 $(#stopAnimation).click(function() { viewer.clock.shouldAnimate false; viewer.clock.currentTime viewer.clock.startTime.clone(); updateCurrentTimeDisplay(); // 更新显示 }); // 速度控制滑动条 $(#speedControl).on(input, function() { var speed parseInt($(this).val()); var actualSpeed 60 (speed * 360); // 自定义速度计算公式 viewer.clock.multiplier actualSpeed; $(#speedValue).text(speed x); }); // 清除按钮隐藏动画控制面板并停止动画 $(#clear).click(function(){ $(#animationControls).hide(); viewer.clock.shouldAnimate false; }); // 当开始时间、结束时间或日期改变时重新设置当前时间但不启动动画 $(#startTime, #endTime, #selDate).change(function(){ setCurrentTime(); }); }, function(e){ // 图层加载失败的处理如果允许显示渲染错误则显示错误面板 if (widget._showRenderLoopErrors) { var title 加载SCP失败请检查网络连接状态或者url地址是否正确; widget.showErrorPanel(title, undefined, e); } }); } catch(e){ // 捕获渲染或其他异常显示错误面板 if (widget._showRenderLoopErrors) { var title 渲染时发生错误已停止渲染。; widget.showErrorPanel(title, undefined, e); } } } // 如果 SuperMap3D 对象已定义则直接调用 onload if (typeof SuperMap3D ! undefined) { window.startupCalled true; onload(SuperMap3D); } /script /body /html