Cesium场景内添加模型

Cesium场景内鼠标添加模型

核心思想

最近在项目中,需要实现在cesium中双击空间内一点添加标识牌模型,其实做法也很简单:

  1. 监听鼠标双击事件
    2.获取当前position的笛卡尔坐标
  2. 根据笛卡尔坐标获取经纬度与高度(高度需要地理高度,保证模型接地)
  3. 根据位置信息在当前位置生成一个弹窗,里面需要去设置添加模型的一些属性
  4. viewer.entities.add添加模型

具体做法

  1. 监听鼠标双击事件
var canvas=viewer.scene.canvas;
let handler = new Cesium.ScreenSpaceEventHandler(canvas);
handler.setInputAction(function (event) {  
//具体功能
}, Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK

2.获取当前position的笛卡尔坐标,然后转化成经纬度高度信息
这一块放在监听事件里

 var lon;
 var lat;
 var height;
 var cartographic;
 var scene = viewer.scene;
 var ellipsoid = scene.globe.ellipsoid;
 var cartesian = viewer.scene.pickPosition(event.position);//笛卡尔坐标
 viewer.scene.globe.depthTestAgainstTerrain = true;
 console.log('笛卡尔坐标 :>> ', cartesian);
   if (cartesian) {
     cartographic = ellipsoid.cartesianToCartographic(cartesian);//地图坐标
     lon = Cesium.Math.toDegrees(cartographic.longitude).toFixed(10);
     lat = Cesium.Math.toDegrees(cartographic.latitude).toFixed(10);
     //地理高度
     height = (cartographic.height+1).toFixed(5);
     //相机高度
     // height=viewer.camera.positionCartographic.height.toFixed(0);
   }
  1. 弹窗样式, 这里使用的是一位老哥写好的popup弹窗类,npm安装后直接用
    整体效果如下
    在这里插入图片描述
npm install cesium_custom_popup

gitee地址也放下面了
链接: https://gitee.com/giser_kangweitao/cesium_custom_popup
5. 弹窗样式

 const listHtml = 
    `<ul style="width: 100%; height: 100%;font-size:22px;text-align: center; color:white;padding-top:30px;z-index: 10;">
    <li>编号: <input type="text"  id="model_id"></li>
    <li>类型:<input type="text" id="model_type"></li>
    <li>公路: <input type="text" id="road" list="appRoadlist">
    <datalist  id="appRoadlist">
    <option >S228</option>
   		<option >S224</option>
   		<option>S101</option>
     </datalist>
     </li>
    <li>标签:<input type="text" id="guidepost_label" list="appLabellist" >
    <datalist  id="appLabellist">
     <option >国/省道标识</option>
     <option >丁字路口</option>
    	<option >服务区</option>
    	<option >目的地距离</option>
    	<option >限速</option>
     <option >收费站</option>
     </datalist>
     </li>
    
    <button style="background-color: #49D182;
    border-radius: 5px; 
    position: absolute;
    top: 55%;
    width: 100px;
   height: 40px;
    color: #FFFFFF;
    "id="btn">添加模型</button>
    </ul>`;
    //放置弹窗
    const putModel = new CustomPopup(
    [lon,lat,height],
    listHtml,
    "interaction",
    {title: "添加模型", lineHeight: 50 }
  );

  putModel.addTo(viewer);

7.点击弹窗事件,点击添加模型后,在当前位置插入模型

 putModel.onClickPopup((e) => {
    if (e.target.id === "btn") {

        var position=Cesium.Cartesian3.fromDegrees(lon,lat,height);//转换为笛卡尔坐标
        viewer.entities.add({  
            position :cartesian,  
            id: document.getElementById("model_id").value,
            model : {  
                uri : './road_gltf/guidepost/20221019140613_parent_directory_路标45.gltf',
                scale:(2,2,2)
           },
            data: {
                        type: document.getElementById("model_type").value,
                        info:{
                        road:document.getElementById("road").value,
                        lat:lat,
                        lng:lon,
                        alt:height,
                        road:document.getElementById("guidepost_label").value
                        }
                       
                    }
        });  
    }
  });

完整代码

import CustomPopup from "./tag.js"; //引入popup弹窗类
var canvas=viewer.scene.canvas;
let handler = new Cesium.ScreenSpaceEventHandler(canvas);
handler.setInputAction(function (event) {
  var lon;
  var lat;
  var height;
  var cartographic;
  var scene = viewer.scene;
  var ellipsoid = scene.globe.ellipsoid;
  var cartesian = viewer.scene.pickPosition(event.position);//笛卡尔坐标
  viewer.scene.globe.depthTestAgainstTerrain = true;
  console.log('笛卡尔坐标 :>> ', cartesian);
    if (cartesian) {
      cartographic = ellipsoid.cartesianToCartographic(cartesian);//地图坐标
      lon = Cesium.Math.toDegrees(cartographic.longitude).toFixed(10);
      lat = Cesium.Math.toDegrees(cartographic.latitude).toFixed(10);
      //地理高度
      height = (cartographic.height+1).toFixed(5);
      //相机高度
      // height=viewer.camera.positionCartographic.height.toFixed(0);
    }
     const listHtml = 
     `<ul style="width: 100%; height: 100%;font-size:22px;text-align: center; color:white;padding-top:30px;z-index: 10;">
     <li>编号: <input type="text"  id="model_id"></li>
     <li>类型:<input type="text" id="model_type"></li>
     <li>公路: <input type="text" id="road" list="appRoadlist">
     <datalist  id="appRoadlist">
     <option >S228</option>
			<option >S224</option>
			<option>S101</option>
      </datalist>
      </li>
     <li>标签:<input type="text" id="guidepost_label" list="appLabellist" >
     <datalist  id="appLabellist">
      <option >国/省道标识</option>
      <option >丁字路口</option>
     	<option >服务区</option>
     	<option >目的地距离</option>
     	<option >限速</option>
      <option >收费站</option>
      </datalist>
      </li>
     
     <button style="background-color: #49D182;
     border-radius: 5px; 
     position: absolute;
     top: 55%;
     width: 100px;
    height: 40px;
     color: #FFFFFF;
     "id="btn">添加模型</button>
     </ul>`;
   const putModel = new CustomPopup(
     [lon,lat,height],
     listHtml,
     "interaction",
     {title: "添加模型", lineHeight: 50 }
   );

   putModel.addTo(viewer);
    
   putModel.onClickPopup((e) => {
    if (e.target.id === "btn") {

        var position=Cesium.Cartesian3.fromDegrees(lon,lat,height);//转换为笛卡尔坐标
        viewer.entities.add({  
            position :cartesian,  
            id: document.getElementById("model_id").value,
            model : {  
                uri : './road_gltf/guidepost/20221019140613_parent_directory_路标45.gltf',
                scale:(2,2,2)
           },
            data: {
                        type: document.getElementById("model_type").value,
                        info:{
                        road:document.getElementById("road").value,
                        lat:lat,
                        lng:lon,
                        alt:height,
                        road:document.getElementById("guidepost_label").value
                        }
                       
                    }
        });  
    }
  });
  }, Cesium.ScreenSpaceEventType.LEFT_DOUBLE_CLICK) 

完成效果

在这里插入图片描述
在这里插入图片描述

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值