主要介绍 SuperMap iClient3D for WebGL/WebGPU 的入门用法,详细的接口参数请参考 API 页面。
准备
获取 SuperMap iClient3D for WebGL/WebGPU
开发时需要引入 SuperMap iClient3D for WebGL/WebGPU。其中包括必备的 CSS 文件和 JS 文件。你可以通过以下几种方式获取:
SuperMap iClient3D for WebGL/WebGPU
引入
文件方式引入
将获取版本解压缩后,在 examples/Webgl 文件夹下新建 HTML 文件, 在文件中通过<script>
标签将 SuperMap3D.js 文件引入:
| <!DOCTYPE html> |
| <html> |
| <head> |
| <meta charset="UTF-8"> |
| <script type="text/javascript" src="../../Build/SuperMap3D/SuperMap3D.js"></script> |
| </head> |
| </html> |
同时应该根据需要在 标签中引入的其他 css 文件和 js 文件,如下:
| <!DOCTYPE html> |
| <html> |
| <head> |
| <meta charset="utf-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=Edge,chrome=1"> |
| <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no"> |
| <link href="../../Build/SuperMap3D/Widgets/widgets.css" rel="stylesheet"> |
| <link href="./css/pretty.css" rel="stylesheet"> |
| <script src="./js/jquery.min.js"></script> |
| <script src="./js/config.js"></script> |
| <script type="text/javascript" src="../../Build/SuperMap3D/SuperMap3D.js"></script> |
| </head> |
| </html> |
创建三维场景
初始化三维球
在准备章节,已经新建了一个 HTML 页面,在页面中继续添加代码以初始化三维球,如下:
| <!DOCTYPE html> |
| <html> |
| <head> |
| <meta charset="utf-8"> |
| <meta http-equiv="X-UA-Compatible" content="IE=Edge,chrome=1"> |
| <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, minimum-scale=1, user-scalable=no"> |
| <link href="../../Build/SuperMap3D/Widgets/widgets.css" rel="stylesheet"> |
| <link href="./css/pretty.css" rel="stylesheet"> |
| <script src="./js/jquery.min.js"></script> |
| <script src="./js/config.js"></script> |
| <script type="text/javascript" src="../../Build/SuperMap3D/SuperMap3D.js"></script> |
| </head> |
| <body> |
| <div id="Container"></div> |
| <script> |
| function onload(SuperMap3D) { |
| var viewer = new SuperMap3D.Viewer('Container'); |
| } |
| </script> |
| </html> |
设置地图风格
在初始化时,三维球上可以叠加本地图片作为影像:
| <script> |
| function onload(SuperMap3D) { |
| var viewer = new SuperMap3D.Viewer('Container'); |
| |
| viewer.imageryLayers.addImageryProvider(new SuperMap3D.SingleTileImageryProvider({ |
| url : './images/worldimage.jpg' |
| })); |
| } |
| </script> |
运行效果
引用在线地图:SuperMap iClient3D for WebGL 对多种互联网地图信息进行了封装, 例如 BingMap、天地图等,并分别为其提供了影像添加接口 BingMapsImageryProvider
和TiandituImageryProvider
添加 BingMap 影像作为底图:
| <script> |
| function onload(SuperMap3D) { |
| var viewer = new SuperMap3D.Viewer('Container'); |
| viewer.imageryLayers.addImageryProvider(new SuperMap3D.BingMapsImageryProvider({ |
| url : 'https://dev.virtualearth.net', |
| mapStyle : SuperMap3D.BingMapsStyle.AERIAL, |
| key : BING_MAP_KEY |
| })); |
| } |
| </script> |
运行效果
添加天地图作为底图:
| <script> |
| function onload(SuperMap3D) { |
| var viewer = new SuperMap3D.Viewer('Container'); |
| var labelImagery = new SuperMap3D.TiandituImageryProvider({ |
| mapStyle: SuperMap3D.TiandituMapsStyle.CIA_C, |
| token: TOKEN_TIANDITU |
| }); |
| viewer.imageryLayers.addImageryProvider(labelImagery); |
| } |
| </script> |
运行效果
添加图层
SuperMap iClient3D for WebGL/WebGPU 提供多种接口,支持在创建好的三维场景中添加种类丰富的数据图层。在此以添加地形图层为例介绍使用 WebGPU 方式加载的方法
添加地形图层:
(1)选择使用 WebGL 方式加载(默认 WebGL2):
| var viewer = new SuperMap3D.Viewer('Container',{ |
| |
| terrainProvider : new SuperMap3D.SuperMapTerrainProvider({ |
| url : URL_CONFIG.SiChuan_TERRAIN, |
| isSct : true, |
| invisibility:true |
| }), |
| }); |
| viewer.resolutionScale = window.devicePixelRatio; |
| viewer.scene.camera.setView({ |
| destination : new SuperMap3D.Cartesian3(-1206939.1925299785, 5337998.241228442, 3286279.2424502545), |
| orientation : { |
| heading : 1.4059101895600987, |
| pitch : -0.20917672793046682, |
| roll : 2.708944180085382e-13 |
| } |
| }); |
(2)选择使用 WebGPU 方式加载:
| var viewer = new SuperMap3D.Viewer('Container',{ |
| |
| terrainProvider : new SuperMap3D.SuperMapTerrainProvider({ |
| url : URL_CONFIG.SiChuan_TERRAIN, |
| isSct : true, |
| invisibility:true |
| }), |
| |
| contextOptions: { |
| contextType : SuperMap3D.ContextType.WebGPU, |
| } |
| }); |
| viewer.resolutionScale = window.devicePixelRatio; |
| viewer.scenePromise.then(function(scene){ |
| |
| init(SuperMap3D, scene, viewer); |
| }); |
| function init(SuperMap3D, scene, viewer){ |
| viewer.scene.camera.setView({ |
| destination : new SuperMap3D.Cartesian3(-1206939.1925299785, 5337998.241228442, 3286279.2424502545), |
| orientation : { |
| heading : 1.4059101895600987, |
| pitch : -0.20917672793046682, |
| roll : 2.708944180085382e-13 |
| } |
| }); |
| } |
添加影像图层:
| var layer = new SuperMap3D.SuperMapImageryProvider({ |
| url : TEST_IMG |
| }); |
| var imgLayer = viewer.imageryLayers.addImageryProvider(layer) |
添加 S3M 图层:对于在 SuperMap iServer 上发布的 S3M 服务,可以通过以下两种方式打开。
(1).通过 open 接口将整个场景打开,这种方法简单易操作且不易出现遗漏图层的情况
| var scene = viewer.scene; |
| var promise = scene.open("http://localhost:8090/iserver/services/3D-test/rest/realspace"); |
(2).通过 addS3MTilesLayerByScp 接口进行添加,该方式的优势是,可以根据自己的需要选择部分图层添加到场景中,提高加载性能,但需要加载多图层的整个场景时,不如 scene.open 方便。
| var promise = scene.addS3MTilesLayerByScp('http://localhost:8090/iserver/services/3D-test/rest/realspace/datas/zj/config', { |
| name : "base", |
| cacheKey: "123456" |
| }); |
| promise.then(function(layer){ |
| layer.visible = true; |
| }); |
添加 MVT 图层:在 SuperMap 桌面产品中将地图生成好的矢量瓦片地图通过 SuperMap iServer 发布成矢量瓦片或三维服务后, 在 WebGL 中利用接口 addVectorTilesMap 将 MVT 图层服务添加到场景中。
| var mvtMap = scene.addVectorTilesMap({ |
| url: url, //MVT的服务地址 |
| canvasWidth: 512, |
| name: 'testMVT', |
| viewer: viewer |
| }); |
场景设置
SuperMap iClient3D for WebGL 提供了多种接口,方便用户对场景进行个性化设置。
颜色设置
SuperMap iClient3D for WebGL 支持对场景的颜色进行设置:
| viewer.scene.colorCorrection.show = true; |
| viewer.scene.colorCorrection.saturation = $("#saturation").val(); |
| viewer.scene.colorCorrection.brightness = $("#brightness").val(); |
| viewer.scene.colorCorrection.contrast = $("#contrast").val(); |
| viewer.scene.colorCorrection.hue = $("#hue").val(); |
| |
| $("#colorCorrectionShow").on("input change", function() { |
| viewer.scene.colorCorrection.show = this.checked; |
| }); |
| |
| $("#saturation").on("input change", function() { |
| viewer.scene.colorCorrection.saturation = this.value; |
| }); |
| |
| $("#brightness").on("input change", function() { |
| viewer.scene.colorCorrection.brightness = this.value; |
| }); |
| |
| $("#contrast").on("input change", function() { |
| viewer.scene.colorCorrection.contrast = this.value; |
| }); |
| |
| $("#hue").on("input change", function() { |
| viewer.scene.colorCorrection.hue = this.value; |
| }); |
泛光效果设置
SuperMap iClient3D for WebGL 支持在场景中开启泛光,并支持对泛光效果进行设置
| |
| viewer.scene.bloomEffect.show = this.checked; |
| |
| $("#bloom-threshold").on("input change", function() { |
| viewer.scene.bloomEffect.threshold = parseFloat(this.value); |
| }); |
| |
| $("#bloom-intensity").on("input change", function() { |
| viewer.scene.bloomEffect.bloomIntensity = parseFloat(this.value); |
| }); |
分屏显示
支持对场景进行分屏显示,在不同的视口中对场景中的数据进行不同的操作,目前 SuperMap iClient3D for WebGL 支持 设置NONE
、HORIZONTAL
、TRIPLE
、VERTICAL
、VerticalTrisection
和QUAD
等 11 种模式。
| scene.multiViewportMode = SuperMap3D.MultiViewportMode[value] |
场景出图
SuperMap iClient3D for WebGL 支持在浏览器中将指定场景的某一角度作为图片保存至本地。具体方法为:
| |
| function convertImageToCanvas(image) { |
| var canvas = document.createElement("canvas"); |
| canvas.width = image.width; |
| canvas.height = image.height; |
| canvas.getContext("2d").drawImage(image, 0, 0); |
| return canvas; |
| }; |
| |
| function download(base64data) { |
| var image = new Image(); |
| image.src = base64data; |
| image.onload = function() { |
| var canvas = convertImageToCanvas(image); |
| url = canvas.toDataURL("image/jpeg"); |
| var a = document.createElement('a'); |
| var event = new MouseEvent('click'); |
| a.download = (new Date()).getTime() + ".jpg"; |
| a.href = url; |
| a.dispatchEvent(event); |
| } |
| } |
查询
空间查询
SuperMap iClient3D for WebGL 提供了丰富的接口,支持场景模型的空间位置信息查询和 GPU 空间查询等功能。
空间位置信息查询:实时获取鼠标点击位置的空间信息。
| var handler = new SuperMap3D.ScreenSpaceEventHandler(scene.canvas); |
| |
| handler.setInputAction(function(e) { |
| |
| viewer.entities.removeAll(); |
| |
| var position = scene.pickPosition(e.position); |
| |
| var cartographic = SuperMap3D.Cartographic.fromCartesian(position); |
| var longitude = SuperMap3D.Math.toDegrees(cartographic.longitude); |
| var latitude = SuperMap3D.Math.toDegrees(cartographic.latitude); |
| var height = cartographic.height; |
| if (height < 0) { |
| height = 0; |
| } |
| |
| |
| var entity = new SuperMap3D.Entity({ |
| name : "位置信息", |
| description : createDescription(SuperMap3D, [longitude, latitude, height]) |
| }); |
| viewer.selectedEntity = entity; |
| |
| |
| viewer.entities.add(new SuperMap3D.Entity({ |
| point : new SuperMap3D.PointGraphics({ |
| color : new SuperMap3D.Color(1, 1, 0), |
| pixelSize : 10, |
| outlineColor : new SuperMap3D.Color(0, 1, 1) |
| }), |
| position : SuperMap3D.Cartesian3.fromDegrees(longitude, latitude , height + 0.5) |
| })); |
| }, SuperMap3D.ScreenSpaceEventType.LEFT_CLICK); |
GPU 空间查询:在场景中创建查询对象,通过 GPU 空间分析,获取查询对象与模型或模型子对象的空间关系。目前查询对象支持 GeoCone、 GeoBox、GeoCylinder、GeoEllipsoid 和 GeoSphere 等几类。示例代码如下:
| var geometry = undefined; |
| var pos = undefined; |
| var mode = SuperMap3D.PositionMode.Intersects |
| var spatialQuery = new SuperMap3D.SpatialQuery3D(scene); |
| var handler = new SuperMap3D.ScreenSpaceEventHandler(scene.canvas); |
| handler.setInputAction(function (evt) { |
| var length = 100; |
| var width = 100; |
| var height = 100; |
| |
| var cartesian = scene.pickPosition(evt.position); |
| var cartographic = SuperMap3D.Cartographic.fromCartesian(cartesian); |
| pos = new SuperMap3D.Point3D(SuperMap3D.Math.toDegrees(cartographic.longitude), SuperMap3D.Math.toDegrees(cartographic.latitude), cartographic.height); |
| geometry = new SuperMap3D.GeoBox(length, width, height); |
| geometry.geoPosition = pos; |
| spatialQuery.geometry = geometry; |
| spatialQuery.positionMode = mode; |
| spatialQuery.layers = layerSelect; |
| spatialQuery.outlineColor = SuperMap3D.Color.CORNFLOWERBLUE; |
| spatialQuery.fillStyle = SuperMap3D.FillStyle.Fill_And_WireFrame |
| |
| spatialQuery.build(); |
| tooltip.setVisible(false); |
| handler.removeInputAction(SuperMap3D.ScreenSpaceEventType.MOUSE_MOVE) |
| }, SuperMap3D.ScreenSpaceEventType.LEFT_CLICK); |
运行效果
属性查询
属性查询是指在场景中对 S3M 模型的图层或对象属性进行查询
| function doSqlQuery(SQL) { |
| var getFeatureParam; |
| getFeatureParam = new SuperMap.REST.FilterParameter({ |
| attributeFilter: SQL |
| }); |
| } |
量算
SuperMap iClient3D for WebGL 提供了量算功能,支持在前端对地形或 S3M 模型进行距离、面积和高差等指标的实时量算, 并支持贴地距离和贴地面积的量算。
下列代码展示距离量算的方法:
| var handlerDis; |
| |
| handlerDis = new SuperMap3D.MeasureHandler(viewer, SuperMap3D.MeasureMode.Distance, clampMode); |
| |
| handlerDis.measureEvt.addEventListener(function (result) { |
| var dis = Number(result.distance); |
| var selOptV = $("#selOpt").val(); |
| var positions = result.positions; |
| if (selOptV == 3 || selOptV == 4) { |
| dis = Number(calcClampDistance(positions)); |
| } |
| var distance = dis > 1000 ? (dis / 1000).toFixed(2) + 'km' : dis.toFixed(2) + 'm'; |
| handlerDis.disLabel.text = '距离:' + distance; |
| }); |
运行效果
绘制
SuperMap iClient3D for WebGL 支持在前端实时进行点、线、面的绘制。
下列代码展示在前端绘制线的方法:
| var handlerLine = new SuperMap3D.DrawHandler(viewer,SuperMap3D.DrawMode.Line); |
| handlerLine.activeEvt.addEventListener(function(isActive){ |
| if(isActive === true){ |
| viewer.enableCursorStyle = false; |
| viewer._element.style.cursor = ''; |
| $('body').removeClass('drawCur').addClass('drawCur'); |
| } |
| else{ |
| viewer.enableCursorStyle = true; |
| $('body').removeClass('drawCur'); |
| } |
| }); |
| handlerLine.movingEvt.addEventListener(function(windowPosition){ |
| if(handlerLine.isDrawing){ |
| tooltip.showAt(windowPosition,'<p>左键点击确定折线中间点</p><p>右键单击结束绘制</p>'); |
| } else { |
| tooltip.showAt(windowPosition,'<p>点击绘制第一个点</p>'); |
| } |
| }); |
| handlerLine.drawEvt.addEventListener(function(result){ |
| tooltip.setVisible(false); |
| }); |
三维空间分析
SuperMap iClient3D for WebGL 支持对三维场景进行一系列的空间分析。
通视分析
通视分析是指对场景中的指定两个点之间的通视性进行分析,具体步骤如下:
(1).打开三维场景或添加三维图层,此步骤可参考 “添加图层”中的"叠加 S3M 图层。
(2).将获取的点位坐标转为经纬度坐标,进行通视分析。
| var cartographic = SuperMap3D.Cartographic.fromCartesian(position); |
| var longitude = SuperMap3D.Math.toDegrees(cartographic.longitude); |
| var latitude = SuperMap3D.Math.toDegrees(cartographic.latitude); |
| var height = cartographic.height; |
(3).添加观察点和目标点,进行通视分析。
| |
| sightline.viewPosition = [longitude, latitude, height]; |
| |
| sightline.addTargetPoint({ |
| position : [longitude, latitude, height], |
| name : "point" + new Date() |
| }); |
可视域分析
可视域分析是指在三维场景中,基于指定观察点,对一定视域内对象的可见性进行分析。主要步骤有:
(1).打开三维场景。
(2).创建可视域分析对象,并指定可视区域和不可视区域的显示样式:
| var viewshed3D = new SuperMap3D.ViewShed3D(scene); |
| var colorStr1 = viewshed3D.visibleAreaColor.toCssColorString(); |
| var colorStr2 = viewshed3D.hiddenAreaColor.toCssColorString(); |
| $("#colorPicker1").spectrum({ |
| color: colorStr1, |
| showPalette: true, |
| showAlpha: true, |
| localStorageKey: "spectrum.demo", |
| palette: palette |
| }); |
| $('#colorPicker2').spectrum({ |
| color: colorStr2, |
| showPalette: true, |
| showAlpha: true, |
| localStorageKey: "spectrum.demo", |
| palette: palette |
| }); |
(3).设置视口位置:
| var viewPosition; |
| viewshed3D.viewPosition = [longitude, latitude, height]; |
(4).以观察者位置(视口位置点)为球心,在场景中拾取一个点,将以观察者位置与该点的连线为半径绘制三维的可视域:
| |
| var distance = SuperMap3D.Cartesian3.distance(viewPosition, last); |
| if (distance > 0) { |
| |
| var cartographic = SuperMap3D.Cartographic.fromCartesian(last); |
| var longitude = SuperMap3D.Math.toDegrees(cartographic.longitude); |
| var latitude = SuperMap3D.Math.toDegrees(cartographic.latitude); |
| var height = cartographic.height; |
| |
| viewshed3D.setDistDirByPoint([longitude, latitude, height]); |
| } |
(5).进行可视域分析:
阴影分析
阴影分析是指对场景中指定区域在指定时间段内的阴影率进行分析。主要步骤有:
(1).打开三维场景。值得注意的是在创建 Viewer 时,应将阴影开启,确保阴影可用:
| var viewer = new SuperMap3D.Viewer('Container', { |
| shadows : true |
| }); |
(2).创建阴影查询对象,并设置图层的阴影模式:
| |
| var shadowQuery = new SuperMap3D.ShadowQueryPoints(scene); |
| |
| layers[0].shadowType = 2; |
| layers[1].shadowType = 2; |
(3).绘制阴影分析区域:
| var handlerPolygon = new SuperMap3D.DrawHandler(viewer, SuperMap3D.DrawMode.Polygon, 0); |
| handlerPolygon.activeEvt.addEventListener(function(isActive){ |
| if (isActive === true) { |
| viewer.enableCursorStyle = false; |
| viewer._element.style.cursor = ''; |
| $('body').removeClass('drawCur').addClass('drawCur'); |
| } else { |
| viewer.enableCursorStyle = true; |
| $('body').removeClass('drawCur'); |
| } |
| }); |
(4).阴影分析完成后,还可以获取分析区域内空间位置上的阴影率:
| var shadowRadio=shadowQuery.getShadowRadio(cartographic); |
(5).执行阴影分析:
天际线分析
天际线分析是指对三维场景的天际线进行绘制和分析。主要步骤有:
(1).打开三维场景。
(2).创建天际线分析对象:
| var skyline = new SuperMap3D.Skyline(scene); |
(3).为使结果直观,将当前相机位置设置为天际线分析的视口:
| |
| skyline.viewPosition = [longitude, latitude, height]; |
| |
| skyline.pitch = SuperMap3D.Math.toDegrees(scene.camera.pitch); |
| skyline.direction = SuperMap3D.Math.toDegrees(scene.camera.heading); |
| skyline.radius = 10000; |
(4).执行天际线分析:
(5).提取二维天际线:
| var object = skyline.getSkyline2D(); |
(6).此外,SuperMap iClient3D for WebGL 还支持绘制限高体以辅助规划和建设部门的决策。 限高体的含义是在当前视口下,为保持当前的天际线不变,在指定区域内修建的建筑高度不能超过该限高体的高度,其绘制方法如下:
| skyline.addLimitbody({ |
| position: arr, |
| name: "limitBody" |
| }); |
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】凌霞软件回馈社区,博客园 & 1Panel & Halo 联合会员上线
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】博客园社区专享云产品让利特惠,阿里云新客6.5折上折
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· CSnakes vs Python.NET:高效嵌入与灵活互通的跨语言方案对比
· DeepSeek “源神”启动!「GitHub 热点速览」
· 我与微信审核的“相爱相杀”看个人小程序副业
· Plotly.NET 一个为 .NET 打造的强大开源交互式图表库
· 上周热点回顾(2.17-2.23)