Cesium加载地形

news2025/1/13 6:40:18

Cesium的地形来源大致可以分为两种,一种是由Cesium官方提供的数据源,一种是第三方的数据源,官方源依赖于Cesium Assets,如果设置了AccessToken后,就可以直接使用Cesium的地形静态构造方法来获取数据源CesiumTerrainProvider.fromIonAssetId,AssetId来自于你自己的Assets库中的id。另外一种则可以通过CesiumTerrainProvider.fromUrl 来实现加载第三方的地形服务。

下面的代码是从上一章节中的代码基础上实现的,集成了下拉选择地形服务的功能。

代码中的各个key,不再移除了,方便诸位复现功能,如果需要正式发布,请自行替换,各个key随时可能到期或被清理。

  • 需要注意的是,对于第三方地形服务部分,我是使用了自己发布的地形服务,如何制作发布,网上有很多教程,一般来说发布后的地址是这样的,末尾以layer.json结束,但是在cesium中使用的时候,需要去掉最后的layer.json,因为Cesium会自动补充。
http://127.0.0.1:9004/tile/terrain/2zxJPMEE/layer.json
  • 我使用的是cesiumlab发布的,还有一个labtoken参数,其实完整的是【…2zxJPMEE/layer.json?labtoken=xx】,这种情况,也是要去掉layer.json后再使用。

  • 还需要注意,在cesium 1.104版本后,地形构造器改为了使用静态方法来获取,而且是异步的,具体的可查看代码中的switchTerrain 方法

<template>
  <div>
    <div
        ref="cesiumContainer"
        id="cesiumContainer"
        class="cesium-container"
        style="width: 100%; height: 100vh;"
    >
      
    </div>
    <!--地形切换 -->
    <div class="layer-switcher">
      <label for="baseMap">选择底图:</label>
      <select id="baseMap" v-model="selectedBaseMap" @change="switchBaseMap">
        <option value="cesium">Cesium 默认</option>
        <option value="tianditu">天地图</option>
        <option value="gaode">高德地图</option>
        <option value="baidu">百度地图</option>
      </select>
    </div>

    <!-- 地形切换 -->
    <div class="terrain-switcher">
      <label for="terrain">选择地形:</label>
      <select id="terrain" v-model="selectedTerrain" @change="switchTerrain">
        <option value="none">无地形</option>
        <option value="cesium">Cesium 官方地形</option>
        <option value="custom">第三方/自定义地形</option>
      </select>
    </div>
  </div>
</template>

<script setup>
import { onMounted, ref, reactive } from 'vue';
import {
  BingMapsImageryProvider,
  BingMapsStyle,
  Cartesian3,
  Color,
  HeadingPitchRange,
  Ion,
  Viewer,
  EllipsoidTerrainProvider,
  CesiumTerrainProvider
} from "cesium";
import "cesium/Build/Cesium/Widgets/widgets.css";
import CustomBaiduImageryProvider from "../cesium-extensions/BaiduImageryProvider.js";
import { AMapImageryProvider,BaiduImageryProvider,TdtImageryProvider }  from '@cesium-china/cesium-map'
import * as Cesium from "cesium";

const cesiumContainer = ref(null)
const viewer = ref(null)
const selectedBaseMap = ref('cesium')
// 地形下拉框选项
const selectedTerrain = ref('none');

// 定义各个底图的 ImageryProvider
const imageryProviders = reactive({
  cesium: [new BingMapsImageryProvider({
    url: 'https://dev.virtualearth.net',
    key: 'Rrke5RPh9hmJ32QZoFzP~_KI12m_pz_KbnGoZFmxVFg~Ai7_QidoqYPrWY7Kf1-GR8g9tY5C7BtbjAxOYpeoJNL4Hj66qSgWNOEAZSAlJKFC', // Cesium默认使用Bing Maps,需要替换为你的密钥
    mapStyle: BingMapsStyle.AERIAL,
  })],
  tianditu: [new TdtImageryProvider({
    style: 'vec', //style: vec、cva、img、cia、ter 
    key:'8af054001cff0f120a2e21c69b4f8c00', // 需去天地图申请
  }),new TdtImageryProvider({
    style: 'cva', //style: vec、cva、img、cia、ter 
    key:'8af054001cff0f120a2e21c69b4f8c00', // 需去天地图申请
  })],
  gaode: [new AMapImageryProvider({
    style: 'img', // style: img、elec、cva
    crs: 'WGS84' // 使用84坐标系,默认为:GCJ02
  }),
    new AMapImageryProvider({
    style: 'cva', // style: img、elec、cva
    crs: 'WGS84' // 使用84坐标系,默认为:GCJ02
  })],
  // 使用cesium-map 组件实现
  /*baidu: [new BaiduImageryProvider({
    url:"http://online{s}.map.bdimg.com/onlinelabel/?qt=tile&x={x}&y={y}&z={z}&styles=pl&scaler=1&p=1",
    style: 'normal', // style: img、vec、normal、dark
    crs: 'WGS84' // 使用84坐标系,默认为:BD09
  })],*/
  // 自定义百度地图提供器
  baidu:[new CustomBaiduImageryProvider()]
})


onMounted(() => {
  // 设置 Cesium Ion 访问令牌
  Ion.defaultAccessToken = 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiJhNmQ5NDYyNi1lZTdhLTRiYTItODFiZi1mYzNiYWNjNDFjMzgiLCJpZCI6NTk3MTIsImlhdCI6MTY2MDE4MDAyNX0.bDTaHEah0hRjUyJWz0hyxIL0Fg63awPXV26OmQ5MCdM'; // 替换为你的访问令牌

  viewer.value = new Viewer('cesiumContainer', {
    animation: false, // 移除动画控件
    timeline: false, // 移除时间轴控件
    geocoder: false, // 移除地理编码控件
    homeButton: false, // 移除主页按钮
    sceneModePicker: false, // 移除场景模式选择器
    selectionIndicator: false, // 移除选择指示器
    fullscreenButton: false, // 移除全屏按钮
    vrButton: false, // 移除 VR 按钮
    // 默认不设置 terrainProvider,即使用椭球体
    terrainProvider: new EllipsoidTerrainProvider(),// 默认无地形
  });

  // 添加默认实体或其他初始化操作
  const tiananmenEntity = viewer.value.entities.add({
    position: Cartesian3.fromDegrees(116.397128, 39.916527),
    point: { pixelSize: 10, color: Color.RED },
    name: '天安门',
  })
  viewer.value.flyTo(tiananmenEntity,{
    duration: 3, // 飞行时间,单位秒
    offset: new HeadingPitchRange(
        0, // Heading,航向角,0表示正北方向
        Cesium.Math.toRadians(-80), // Pitch,俯仰角,负值表示向下俯视
        405000 // Range,距离目标的距离,增加此值以提高视角高度
    )
  })
});
const switchBaseMap = () => {
  // 移除当前的底图图层
  if (viewer.value && viewer.value.imageryLayers.length > 0) {
    viewer.value.imageryLayers.removeAll()
  }

  let newProviders = imageryProviders[selectedBaseMap.value] || [];
  
  for (let i = 0; i < newProviders.length; i++) {
    viewer.value.imageryLayers.addImageryProvider(newProviders[i])
  }
  
}

// ------------------ 方法:地形切换 -------------------
const switchTerrain = async () => {
  if (!viewer.value) return;

  if (selectedTerrain.value === 'none') {
    viewer.value.terrainProvider = new EllipsoidTerrainProvider();
  } else if (selectedTerrain.value === 'cesium') {
    // 从 Ion assetId 加载官方地形
    viewer.value.terrainProvider = await CesiumTerrainProvider.fromIonAssetId(1, {
      // requestVertexNormals: true,
      // requestWaterMask: true,
    });
  } else if (selectedTerrain.value === 'custom') {
    // 从自定义 URL 加载
    viewer.value.terrainProvider = await CesiumTerrainProvider.fromUrl(
        'http://127.0.0.1:9004/tile/terrain/2zxJPMEE?labtoken=eyJ0eXAiOiJKV1QiLCJhbGciOiJIUzI1NiJ9.eyJzdWIiOiItMSxUaHUgQXByIDE4IDE1OjMwOjU3IENTVCAyMDI0In0.j_YKsCRsIQtpgOWfFvMwAP65Rlx9uXyVte_xkE95Vdo',
        {
          requestVertexNormals: false,
          // requestWaterMask: true,
        }
    )
  }
};

</script>

<style>
.cesium-container {
  width: 100%;
  height: 100%;
  position: relative;
}
/* 隐藏页面底部的 Cesium logo 和数据归属 */
.cesium-viewer .cesium-widget-credits {
  display: none !important; /* 隐藏整个 Cesium 控件 */
}

/* 隐藏 右上角的 Imagery 和 Navigation instructions */
.cesium-viewer .cesium-viewer-toolbar {
  display: none !important; /* 隐藏工具栏 */
}

.layer-switcher {
  position: absolute;
  top: 10px;
  left: 10px;
  background: rgba(42, 42, 42, 0.8);
  padding: 10px;
  border-radius: 4px;
  color: white;
  z-index: 1;
}

.layer-switcher select {
  margin-left: 5px;
  padding: 2px 5px;
  border-radius: 2px;
  border: none;
}

/* 地形切换器样式,可以放在旁边或者下方 */
.terrain-switcher {
  position: absolute;
  top: 60px;
  left: 10px;
  background: rgba(42, 42, 42, 0.8);
  padding: 10px;
  border-radius: 4px;
  color: white;
  z-index: 10;
}

.terrain-switcher select {
  margin-left: 5px;
  padding: 2px 5px;
  border-radius: 2px;
  border: none;
}
</style>

源码

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2275853.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

虚拟文件系统 VFS

目录 虚拟文件系统 VFS 文件系统挂载过程 虚拟文件系统 VFS 统一标准的系统调用接口&#xff1a; VFS定义了一组标准的文件操作API&#xff0c;如open(), read(), write(), close()等&#xff0c;使得用户空间的应用程序无需关心底层文件系统的具体类型。 下层文件系统必须实现…

conda 批量安装requirements.txt文件

通常可以用下面conda命令安装requirements.txt文件 conda install --yes --file requirements.txt 但是&#xff0c;一旦遇到某个包安装失败&#xff0c;就会停止安装后续的包。 下面这条命令能解决上面出现的不执行后续包的问题&#xff0c;需要在CMD窗口执行&#xff1a; 点…

Auto-CoT:自动构建大模型的思维链提示

今天分享的是由上海交通大学发表的一篇文章&#xff1a;Auto-COT 论文题目&#xff1a;AUTOMATIC CHAIN OF THOUGHT PROMPTING IN LARGE LANGUAGE MODELS 论文链接&#xff1a;https://arxiv.org/pdf/2210.03493 代码地址&#xff1a;https://github.com/amazon-science/aut…

算法练习7——拦截导弹的系统数量求解

题目描述 某国为了防御敌国的导弹袭击&#xff0c;发展出一种导弹拦截系统。但是这种导弹拦截系统有一个缺陷&#xff1a;虽然它的第一发炮弹能够到达任意的高度&#xff0c;但是以后每一发炮弹都不能高于前一发的高度。 假设某天雷达捕捉到敌国的导弹来袭。由于该系统还在试用…

命令行中打印二维码

前公司中登录设备时&#xff0c;需要下发密钥&#xff0c;密钥是通过扫描终端中的二维码获得的&#xff0c;终端中的二维码类似这样&#xff1a; 当时没理解原理&#xff0c;现在研究了下如何在命令行中打印二维码。主要介绍其中一些开源工具&#xff1a; 1. qrencode 简介 …

Android车机DIY开发之软件篇(八)单独编译

Android车机DIY开发之软件篇(八)单独编译 1.CarLauncher单独编译 CarLauncher源码位于 packages/apps/Car/Launcher 用Eclipse ADT 谷歌定制版编译而成&#xff0c;.mk .bp编译 Android13目录如下: alientekalientek:~/packages/apps/Car$ ls Calendar …

3 前端: Web开发相关概念 、HTML语法、CSS语法

文章目录 前言:导学1 Web开发相关概念2 Web标准(网页标准)3 软件架构(CS/BS)(1)C/S: Client/Server 客户端 / 服务器端(2)B/S: Browser/Server 浏览器 / 服务器端VSCode配置前段开发环境一、HTML概念1 概念2 HTML快速入门(1)语法快速入门(2)VSCode一个 !(快捷键…

Redis:内存管理

1. 最大内存限制 (maxmemory) 简介 概念:maxmemory 参数用于设置 Redis 实例允许使用的最大内存量。作用:当 Redis 使用的内存达到这个限制时,它会根据配置的淘汰策略来决定如何处理新的写入请求或移除现有数据。示例 # 设置最大内存为2GB maxmemory 2gb注意事项 合理规划…

C语言进阶——1数据的存储

目录 1. 数据类型介绍1.1 类型的基本归类&#xff1a;1.1.1 整形家族1.1.2 浮点型家族1.1.3 构造类型&#xff1a;1.1.4.指针类型1.1.5 void 表示空类型&#xff08;无类型&#xff09; 2. 整形在内存中的存储2.1 原码、反码、补码2.1.1 示例 20在计算机中的存储 2.2 大小端2.2…

OpenAI 故障复盘 - 阿里云容器服务与可观测产品如何保障大规模 K8s 集群稳定性

本文作者&#xff1a; 容器服务团队&#xff1a;刘佳旭、冯诗淳 可观测团队&#xff1a;竺夏栋、麻嘉豪、隋吉智 一、前言 Kubernetes(K8s)架构已经是当今 IT 架构的主流与事实标准&#xff08;CNCF Survey[1]&#xff09;。随着承接的业务规模越来越大&#xff0c;用户也在使…

【微服务】面试 1、概述和服务发现

微服务面试题 课程内容架构 Spring Cloud 部分 服务注册&#xff1a;重点讲解&#xff08;Nacos&#xff09;和&#xff08;Eureka&#xff09;&#xff0c;这是微服务架构中实现服务发现与注册的关键组件&#xff0c;确保服务间能够相互定位与通信。负载均衡&#xff1a;涵盖…

Mybatis冲冲冲00(含如何配置模版文件)

官方网站:mybatis – MyBatis 3 | 入门 mybatis安装方式1.下jar包(网址在上),2.Maven(代码也由上可找) 两个核心配置文件 1.核心主配置文件:configuration.xml(文件名自定义),通常设置为mybatis-config.xml 2.SQL映射文件:mapper.xml(文件名自定义),通常设置为:实体类名.xml…

【Rust】引用与借用

目录 思维导图 1. 引用与借用的基本概念 1.1. 引用示例 2. 借用的规则 2.1. 可变借用示例 2.2. 借用的限制 3. 引用的生命周期 思维导图 1. 引用与借用的基本概念 引用的定义&#xff1a;引用是一种指向数据的指针&#xff0c;但与裸指针不同&#xff0c;Rust的引用在编…

django网上商城系统

Django网上商城系统是一种基于Django框架构建的电子商务解决方案&#xff0c;它充分利用了Django框架的强大功能&#xff0c;为开发者提供了一个快速构建在线商店的平台。 一、系统架构与技术栈 Django网上商城系统采用MVC&#xff08;模型-视图-控制器&#xff09;架构&…

Node.js - 模块化与包管理工具

1. 前言 模块化是代码组织的方式&#xff0c;而包管理工具是管理模块的工具。在现代项目开发中&#xff0c;模块化和包管理工具几乎是不可分割的一部分&#xff0c;它们一起构成了高效的开发工作流。 包代表了一组特定功能的源码集合&#xff0c;包管理工具可以对包进行下载安…

贪心算法汇总

1.贪心算法 贪心的本质是选择每一阶段的局部最优&#xff0c;从而达到全局最优。 如何能看出局部最优是否能推出整体最优 靠自己手动模拟&#xff0c;如果模拟可行&#xff0c;就可以试一试贪心策略&#xff0c;如果不可行&#xff0c;可能需要动态规划。 如何验证可不可以…

leetcode-最长递增子序列

300. 最长递增子序列 - 力扣&#xff08;LeetCode&#xff09; 动态规划的题目我真的不想看题解&#xff0c;题解都是直接推出来动态转移方程&#xff0c;我就很纳闷&#xff0c;到底是怎么推出来的呢&#xff1f;什么样的智慧&#xff0c;上来分析问题就是那么的清晰有条理。我…

Qt 5.14.2 学习记录 —— 십일 QLCDNumber、ProgressBar、QCalendarWidget

文章目录 1、QLCDNumber2、ProgressBar3、QCalendarWidget 1、QLCDNumber 写一个倒计时程序。拖一个LCD Number到界面&#xff1a; 定时器用Qt的QTimer类&#xff0c;这个类的对象会产生一个timeout信号&#xff0c;通过start方法来开启定时器&#xff0c;并且参数中设定触发ti…

VDN 微服务架构搭建篇(二)服务注册与配置中心Nacos

VDN 微服务架构搭建篇&#xff08;二&#xff09;&#xff1a;服务注册与配置中心 Nacos 本文将介绍如何使用 Spring Cloud Alibaba 和 Nacos 搭建服务注册与配置中心&#xff0c;重点讲解如何实现微服务架构中的服务发现、自动注册、配置管理以及动态配置刷新等功能。通过整合…

高等数学学习笔记 ☞ 单调性、凸凹性、极值、最值、曲率

1. 单调性 1. 单调性定义&#xff1a;设函数在区间上有定义&#xff0c;对于区间上任意两点&#xff0c;若&#xff1a; ①&#xff1a;当时&#xff0c;恒有&#xff0c;则称函数在区间上单调递增。 ②&#xff1a;当时&#xff0c;恒有&#xff0c;则称函数在区间上单调递减…