开源!Cesium视频投射,手把手教你如何让实时视频流“长”在三维地球里!

大家好,我是日拱一卒的攻城师不浪,致力于前沿科技探索,摸索小而美工作室。这是2025年输出的第9/100篇文章。

效果预览

【在线预览地址】:jiawanlong.github.io/Cesium-Exam...

前言

曾经有很多朋友问我:如何在Cesium中做视频投射,能不能讲一讲实现思路?今天它来啦!源码文末自取

可能有的小伙伴还不了解:视频投射是什么东东?我们先来了解一下,这个东东它的应用场景都有啥?

视频投射应用场景

  1. 虚拟现实与增强现实

    通过将视频投射到3D模型地理场景中,可以为用户提供身临其境的沉浸式体验。例如,将实时视频投射到指定道路路口,工作人员可以在虚拟环境中直观感受实时交通情况的变化,并针对突发状况做出及时响应。

  1. 数字孪生与城市建模

    在城市建模中,将实时视频投射到数字孪生模型中,可以展示现实世界中的动态场景。例如,在建筑物或街道模型上叠加实时视频流,用于监控广告旅游展示。

  2. 灾难管理与应急响应

    通过在Cesium场景中投射实时视频,配合地理信息系(GIS),可以帮助应急响应团队实时监控灾难现场,提供更准确的决策支持。比如,地震后的视频数据投射可以帮助救援队伍迅速评估受灾区域。

  1. 文化遗产保护与虚拟博物馆

    视频投射可用于展示历史遗址或文化遗产的数字化复原,用户可以通过Cesium虚拟漫游查看遗址的实时视频或复原视频,增进对历史文化的理解。

其外,视频投射系统还适用于AR导航等地理空间可视化场景等。

原理解析

在做一个功能之前,我们需要先分析其功能,解析出原理,才能对整体做把控。

那么在Cesium中实现视频投射的核心原理主要是通过视锥体几何动态材质绑定技术:

  • 视锥体建模 :基于摄像机参数(位置视角方向)构建一个3D视锥体几何,定义视频投射的空间范围;

  • 视频材质映射 :将HTML5视频元素作为纹理贴图,通过GLSL着色器实时渲染到视锥体表面;

  • 动态坐标转换 :利用Cesium的坐标系(WGS84/Cartesian3)实现地理空间定位,保证视频投射与地球表面的精确对齐。

关键代码解析

视锥体创建

javascript 复制代码
createLightCamera() {
  this.lightCamera = new Cesium.Camera(this.viewer.scene);
  this.lightCamera.frustum.near = this.viewDistance * 0.0001;
  this.lightCamera.frustum.far = this.viewDistance;
  // 计算宽高比和视场角
  const aspectRatio =
      (this.viewDistance * Math.tan(hr / 2) * 2) /
      (this.viewDistance * Math.tan(vr / 2) * 2);
  this.lightCamera.setView({
    orientation: {
      heading: Cesium.Math.toRadians(this.viewHeading),
      pitch: Cesium.Math.toRadians(this.viewPitch)
    }
  });
}
  • 摄像机参数 :通过near/far控制视锥体深度范围;

  • 方向控制heading/pitch确定视锥体朝向;

  • 宽高比计算 :基于水平/垂直视角动态计算投影比例;

通过Cesium.FrustumGeometry生成几何体,使用Cesium.FrustumOutlineGeometry绘制边框。

视频材质绑定

js 复制代码
createAppearance() {
  let source = `czm_material czm_getMaterial(...) {
    vec4 colorImage = texture(image, st);
    material.alpha = colorImage.a * color.a * maskImage.r;
    material.diffuse = colorImage.rgb * color.rgb;
  }`;
  let material = new Cesium.Material({
    fabric: {
      uniforms: {
        image: video_dom, // 绑定视频元素
        tmask: "data:image/jpg;base64,..." // 透明遮罩
      }
    }
  });
  return new Cesium.EllipsoidSurfaceAppearance({ material });
}
  • 动态着色器 :通过自定义GLSL实现视频与遮罩的混合;

  • 实时更新 :将<video>元素作为纹理输入;

  • 透明处理 :通过alpha通道控制视频透明度;

创建包含视频元素的Material实例,通过PerInstanceColorAppearance实现实例化渲染。

地理坐标交互

js 复制代码
getCurrentMousePosition(scene, position) {
  // 通过射线与地球表面求交
  if(scene.mode === Cesium.SceneMode.SCENE3D) {
    const pickRay = scene.camera.getPickRay(position);
    return scene.globe.pick(pickRay, scene);
  }
  return scene.camera.pickEllipsoid(position);
}
  • 三维拾取:在3D模式下通过射线与地球求交;

  • 坐标系转换 :将屏幕坐标转换为WGS84地理坐标;

  • 高程适配 :通过globe.pick自动处理地形高度;

动态更新

监听视频播放事件更新材质,通过requestAnimationFrame实现帧同步。

关键技术点

技术点 实现方式 作用
视锥体参数化 动态计算宽高比/视场角 适配不同视频比例
坐标系转换 Cesium.Transforms.eastNorthUpToFixedFrame 地理空间准确定位
性能优化 使用Primitive替代Entity 提升渲染效率
透明通道处理 GLSL混合视频与遮罩纹理 实现边缘融合效果

如何使用

javascript 复制代码
// 初始化参数
const options = {
  horizontalViewAngle: 60,    // 水平视场角
  verticalViewAngle: 40,      // 垂直视场角
  video: "video_dom",         // 视频DOM ID
  viewPosition: Cartesian3.fromDegrees(85.788705, 45.161394, 900), // 锥体原点
  viewPositionEnd: Cartesian3.fromDegrees(85.788705, 45.167394, 500) // 锥体远点
};

// 创建视频投射实例
const videoProjector = new CesiumVideo(viewer, options);
videoProjector.drawVideo();

// 控制视频播放
document.getElementById('video_dom').play();

最后

源码地址 】:github.com/jiawanlong/...

不浪的【Cesium案例集合源码 】:github.com/tingyuxuan2...

如果开源对您有帮助,也欢迎帮我们点一个免费的star,以鼓励和支持我们开源更多案例!

不会Cesium的基础,也很难做出更高级的效果,所以可以了解下不浪的教程《Cesium从入门到实战》,将Cesium的知识点进行串联,让不了解Cesium的小伙伴拥有一个完整的学习路线,并最终完成一个智慧城市的完整项目,课程也在不断更新迭代中,想了解+作者:brown_7778(备注来意)。
有需要进可视化&Webgis交流群可以加我:brown_7778(备注来意)。

相关推荐
整点可乐6 天前
cesium热力图曲面简单实现,使用heatmap
前端·cesium
不浪brown9 天前
应急指挥&污染扩散模拟 | Cesium 多边形动态扩散墙实战教程(附源码)
前端·cesium
枝上棉蛮13 天前
如何用GISBox将高斯泼溅文件(PLY/Splat)转换为3DTiles?全流程解析
gis·cesium·ply·3dtiles·高斯泼溅·gis软件·splat
白嫖叫上我1 个月前
Ceisum无人机巡检直播视频投射
无人机·cesium·webgis
easyCesium1 个月前
大疆机场及无人机上云
cesium·dji
一嘴一个橘子1 个月前
Entity 的材质(棋盘、条纹、网格)
cesium
一嘴一个橘子1 个月前
primitive 的 Appearance编写着色器材质
cesium
一嘴一个橘子1 个月前
primitive 编写着色器材质
cesium
不浪brown1 个月前
【开源】Cesium中让模型动起来,丝滑又顺畅
前端·cesium