Introduction to Cesium Nine: Cesium loads gltf files

Introduction to glTF files

glTF (Graphics Library Transmission Format) is a format for storing 3D models and scenes. It is an open standard format that can be used to transfer and exchange 3D model and scene data between different 3D engines and software.

The glTF file contains the geometric shape, material, texture, animation and other information of the design scene or model, and has good compatibility and scalability. glTF files are based on the JSON format, which is easy to read and modify, and is also easy to parse and use in programming languages.

glTF supports two file formats: *.glTF and *.glb.

.glTF is a text file based on JSON format, which can contain 3D model elements such as scenes, nodes, mesh information, materials, animations, cameras, etc., and can include external resources such as textures, images, and binary data. .glTF files are easy to read, modify, and edit, and can be compressed with gzip to reduce file size. However, the .glTF file format may become more verbose and slower when processing complex scenes.

.glb is a binary-based file format that contains all glTF data, including all external resources. Since .glb files are binary, file size and load time are greatly reduced while maintaining the flexibility and editability of .glTF files. .glb files can also be compressed using gzip to further reduce file size. However, as a binary file, the .glb file format is difficult to edit and modify directly.

Model coordinate system in Cesium

In Cesium, in order to ensure that all kinds of data can be displayed and interacted correctly in the 3D scene, a specific model coordinate system is defined, that is, the ENU coordinate system, where ENU represents the northeast.

  • East: The X-axis faces east of the earth's surface, in meters.
  • North: The Y-axis faces north on the earth's surface, in meters.
  • Up (Up): The Z axis is toward the center of the earth. In the ENU coordinate system, it usually refers to the upward direction perpendicular to the earth's surface, and the unit is meters.

By default, the origin of the coordinate system of the Cesium scene is located at the center of the earth, outside the atmosphere above the earth's surface, and the coordinate axis is tangent to the earth's surface. Suppose we want to add a 3D model to the Cesium scene, we need to ensure that the model uses the ENU coordinate system and is located tangent to the earth's surface. The model can be transformed from an external coordinate system (such as a Cartesian coordinate system) to an ENU coordinate system by the following steps.

  1. Transforms the model from an external coordinate system to a Cartesian coordinate system.

  2. Convert the coordinate point in the Cartesian coordinate system to the coordinate point in the ENU coordinate system.

  3. Tangent the origin in the ENU coordinate system to the Earth's surface.

To convert the model from the external coordinate system to the ENU coordinate system, we need to use Cesium's coordinate conversion function. Cesium provides a number of functions and objects for converting 3D models from an external coordinate system to the ENU coordinate system.

Related class introduction

Cesium.Cartesian3(x,y,z) function

Cesium.Cartesian3It is a class in the Cesium library used to represent Cartesian coordinates in 3D world space. Each Cartesian3 instance represents a point in space, which can be described by its X, Y, and Z coordinate components.

  • xThe coordinates represent the displacement in the east-west direction in meters.
  • yThe coordinates represent the displacement in the north-south direction in meters.
  • zThe coordinates represent the displacement in the direction perpendicular to the Earth's surface, in meters.

Common methods of Cartesian3

  • Cartesian3.add(left, right, result): Adds two vectors and stores the result in resultan object.
  • Cartesian3.subtract(left, right, result): Subtracts two vectors and stores the result in resultan object.
  • Cartesian3.magnitude(cartesian): Returns the length of the vector.
  • Cartesian3.normalize(cartesian, result): Returns the unit vector of the vector, the result is stored in resultthe object.
  • Cartesian3.dot(left, right): Returns the dot product of two vectors.
  • Cartesian3.cross(left, right, result): Returns the cross product of two vectors, the result is stored in resultan object.
  • Cesium.Cartesian3.fromDegrees(longitude, latitude, height, ellipsoid, result): A function used to convert a given latitude and longitude elevation coordinates into a vector in the Cartesian coordinate system.
    This function accepts five parameters longitude, latitude, height, ellipsoid and result. longitude and latitude are floating-point numbers in degrees, representing the longitude and latitude corresponding to geometric points on the earth's surface. height is the elevation value of this geometric point (with reference to sea level). ellipsoid is an optional parameter indicating the ellipsoid to use, if not provided the WGS84 ellipsoid is used. result is an optional Cartesian3 object representing the vector in the transformed Cartesian coordinate system. If the result parameter is not provided, a new Cartesian3 object is created in which the computed vector is stored, and this object is returned.
    The function first converts longitude and latitude to radians, and calculates the geocentric radius of the geometric point according to the parameters of the ellipsoid. Cartesian coordinates can be calculated using this information, with the height added to the Z component.

Cartesian3 example:
The following code adds two Cartesian3 objects and outputs the result:

var a = new Cesium.Cartesian3(1, 2, 3);
var b = new Cesium.Cartesian3(4, 5, 6);
var result = new Cesium.Cartesian3();
Cesium.Cartesian3.add(a, b, result);
console.log(result); // Cartesian3{x: 5, y: 7, z: 9}

In Cesium's scene, Cartesian3 objects are usually used to represent the position and orientation in the scene. For example, when we select an object in a 3D scene, the returned result is a Cartesian3 object containing position coordinates. They can also be used to perform vector operations and perform transformations on 3D graphics.

Cesium.HeadingPitchRoll(heading, pitch, roll) 类

Cesium.HeadingPitchRollIs a class that defines orientation, pitch and roll angles, which is used to describe the rotation state of 3D objects. The constructor of this class uses three parameters heading, pitchand rollto define the rotation angle of the target object around the Y axis (azimuth), the rotation angle around the X axis (pitch) and the rotation angle around the Z axis (roll), and put them Stored in an instance of the class for use.

All arguments are floating-point numbers in radians, with values ​​between -π and π. headingThe parameter defines the angle of rotation around the Y axis, with true north being 0 degrees. pitchThe parameter defines the angle of rotation of the object around the X axis, with the horizontal position being 0 degrees, upward rotation being positive, and downward rotation being negative. rollThe parameter defines the angle by which the object rotates around the Z axis, and the vertical direction of the input rotation direction is 0 degrees.

For example, the following code creates a rotated state that is rotated 45 degrees around the Y, X, and Z axes:

var heading = Cesium.Math.toRadians(45);
var pitch = Cesium.Math.toRadians(45);
var roll = Cesium.Math.toRadians(45);

var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);

For Cesium.HeadingPitchRollthe rotation state created through the constructor, we can use the instance methods in the following sample code to get and set the specific components of the rotation state object:

var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);

// 获取当前HPR对象的heading、pitch和roll值
var currentHeading = hpr.heading;
var currentPitch = hpr.pitch;
var currentRoll = hpr.roll;

// 设置HPR对象的heading、pitch和roll值
hpr.heading = Cesium.Math.toRadians(90);
hpr.pitch = Cesium.Math.toRadians(-45);
hpr.roll = Cesium.Math.toRadians(0);

It is also possible to create an object with the default rotation (both 0 degrees) using the following sample code Cesium.HeadingPitchRoll:

var hpr = new Cesium.HeadingPitchRoll();

Common conversion functions

Cesium.Transforms.eastNorthUpToFixedFrame(origin, ellipsoid, result) 函数

Cesium.Transforms.eastNorthUpToFixedFrame(origin, ellipsoid, result)It is a method used in Cesium to calculate the transformation matrix of the geocentric coordinate system with a given point as the origin. This method accepts three parameters:

  • origin: A point expressed in the Cartesian coordinate system, that is, the point that is the origin of the geocentric coordinate system.
  • ellipsoid(Optional): Earth Ellipsoid object (default is WGS84 ellipsoid), used to calculate coordinates relative to the geocentric coordinate system.
  • result(optional): A Matrix4 object to store the resulting transformation matrix.

This method returns a Matrix4 object representing the transformation matrix required to convert the ENU coordinate system (northeast up) to a geocentric coordinate system centered at the specified origin. The resulting matrix calculated by this method is related to the unit vector rotation and translation of the ENU coordinate system, which can be used to convert 3D objects from the ENU coordinate system to the geocentric coordinate system.

For example, the following code takes the geographic coordinates of New York (-74.00, 40.71) as the origin and calculates the transformation matrix of the geocentric coordinate system with this point as the origin:

var origin = Cesium.Cartesian3.fromDegrees(-74.00, 40.71, 0);
var enuToFixedFrameTransform = Cesium.Transforms.eastNorthUpToFixedFrame(origin);

If you need to transform a 3D object from a north-east-up ENU coordinate system to a geocentric coordinate system with a specified origin, you can use this matrix to convert it to the desired reference system. For example:

var enuPoint = new Cesium.Cartesian3(10, 10, 0);
var fixedFramePoint = new Cesium.Cartesian3();
Cesium.Matrix4.multiplyByPoint(enuToFixedFrameTransform, enuPoint, fixedFramePoint);

In the above code, enuPointit represents a point in the ENU coordinate system (assuming that the point can be represented as (10,10,0)). Convert the point to a geocentric coordinate system by using a transformation matrix. The result is stored in fixedFramePointa variable, which is a position of this point in the geocentric coordinate system.

Cesium.Transforms.headingPitchRollQuaternion(origin, headingPitchRoll, ellipsoid, fixedFrameTransform, result) 函数

Cesium.Transforms.headingPitchRollQuaternion(origin, headingPitchRoll, ellipsoid, fixedFrameTransform, result)function is a function in the Cesium API used to convert a given origin, azimuth, pitch, and roll into a quaternion. The remaining parameters of the function can be used to specify the ellipsoid, reference frame, and outgoing quaternion for the result.

originThe argument is an Cartesian3object that defines the center point of the rotation. The input headingPitchRollparameters are an object with azimuth, pitch and roll angles HeadingPitchRoll. It should be noted that the three angles entered should be in radians.

The optional parameter ellipsoiddefines the ellipsoid involved in the rotation, if not specified, the standard WGS84 ellipsoid is used. fixedFrameTransformThe parameter can be used to adjust the orientation of the resulting quaternion in case the resulting quaternion is applied to a different device coordinate system. resultThe parameter is an empty object to output the result, if this parameter is omitted, a new quaternion object will be created to store the result. If this argument is provided, the function modifies the object rather than creating a new one.

Here are some example uses of this function:

var origin = Cesium.Cartesian3.fromDegrees(-75.59777, 40.03883);
var heading = Cesium.Math.toRadians(90);
var pitch = 0;
var roll = 0;
var hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll);

// 默认椭球体(WGS84),默认坐标系(惯性坐标系)下的旋转
var quat1 = Cesium.Transforms.headingPitchRollQuaternion(origin, hpr);

// 在一个不同的坐标系下的旋转
var fixedFrameTransform = Cesium.Transforms.northEastDownToFixedFrame(origin);
var quat2 = Cesium.Transforms.headingPitchRollQuaternion(origin, hpr, undefined, fixedFrameTransform);

// 使用不同的椭球体,并使用提供的四元数存储结果
var ellipsoid = Cesium.Ellipsoid.UNIT_SPHERE;
var quat3 = new Cesium.Quaternion();
Cesium.Transforms.headingPitchRollQuaternion(origin, hpr, ellipsoid, undefined, quat3);

originThe above code computes a quaternion rotation based on the given origin, heading, pitch and roll angle. The first example creates a default rotation and stores it in quat1. In the second example, a rotation of the fixed coordinate system is performed using a transformation matrix, and the result is stored in quat2. The third example uses the given ellipsoid and stores the result in the provided quat3quaternion object.

How Cesium loads gltf files

To load the gltf file in Cesium, you can use the viewer.entities.add method to load it. Here you need to pay attention to a detail. When loading the model in the add method, the configuration parameter is uri, not url. You must pay attention here, otherwise it will fail. Load
insert image description here
the detailed code as follows

<template>
  <div id="cesiumContainer"></div>
</template>
<script setup>
import * as Cesium from 'cesium' 
import {
    
     onMounted } from 'vue'; 
// import modelFile from '/feiji.glb'
let viewer, imageLayers
onMounted(async () => {
    
     
  // 初始化Cesium
  initViewer()
  // 加载影像数据
  addImageLayers()
  // 加载gltf数据
  addGLTFModel('/feiji.glb', 4000)
})

function initViewer() {
    
    
  viewer = new Cesium.Viewer('cesiumContainer', {
    
    
    animation: false,//动画小部件
    baseLayerPicker: false,//地图图层组件
    fullscreenButton: false,//全屏组件
    geocoder: false,//地理编码搜索组件
    homeButton: false,//首页组件
    infoBox: false,//信息框
    sceneModePicker: false,//场景模式
    selectionIndicator: false,//选取指示器组件
    timeline: false,//时间轴
    navigationHelpButton: false,//帮助按钮
    navigationInstructionsInitiallyVisible: false,
  })
  // console.log(viewer);
  // 隐藏logo信息
  viewer._cesiumWidget._creditContainer.style.display = 'none'
  // 隐藏地球
  // viewer.scene.globe.show = false
  imageLayers = viewer.imageryLayers
  viewer.scene.globe.depthTestAgainstTerrain = true;// 随着地图缩放深度增加会导致数据获取不到,所以需要进行开启深度监测
  // console.log(imageLayers);
}
async function addImageLayers() {
    
    
  imageLayers.remove(imageLayers.get(0)) //清楚Cesium默认加载的影像地图数据(默认是加载的bing地图) 
  // Bing地图
  const bing = await Cesium.BingMapsImageryProvider.fromUrl(
    "https://dev.virtualearth.net", {
    
    
    key: "AodxPjHCueIzbuOPovDaDba7D6qpNMPdJ8nt96KsDjKIs0yz5j4jTuNMdMdO6tJZ",
    mapStyle: Cesium.BingMapsStyle.AERIAL//可选参数,指定地图样式
  })
  imageLayers.addImageryProvider(bing) 
}
async function addGLTFModel(url, height) {
    
       
  // Entity方法加载gltf
  viewer.entities.removeAll() //加载之前先清楚所有entity
  const position = Cesium.Cartesian3.fromDegrees(-123.0744619, 44.0503706, height)
  const heading = Cesium.Math.toRadians(135) //135度转弧度
  const pitch = Cesium.Math.toRadians(0);
  const roll = 0
  const hpr = new Cesium.HeadingPitchRoll(heading, pitch, roll)
  const orientation = Cesium.Transforms.headingPitchRollQuaternion(
    position,
    hpr
  )  
  const entity = await viewer.entities.add({
    
    
    name: 'feiji',
    position: position,
    orientation: orientation,
    model: {
    
     
      uri: url,//注意entitits.add方式加载gltf文件时,这里是uri,不是url,并且这种方式只能加载.glb格式的文件
      scale: 1.0,//缩放比例
      minimumPixelSize: 128,//最小像素大小,可以避免太小看不见
      maximumScale: 20000,//模型的最大比例尺大小。minimumPixelSize的上限  
      incrementallyLoadTextures: true,//加载模型后纹理是否可以继续流入
      runAnimations: true,//是否启动模型中制定的gltf动画
      clampAnimations: true,//制定gltf动画是否在没有关键帧的持续时间内保持最后一个姿势
      shadows: Cesium.ShadowMode.ENABLED,
      heightReference: Cesium.HeightReference.NONE
    }
  }) 
  viewer.trackedEntity = entity; // 聚焦模型
  viewer.zoomTo(entity)
}
</script>
<style  scoped></style>

Run the code, refresh the browser, and you can see that the gltf model has been loaded into the page.
insert image description here
Okay, that’s it for today. If you have any questions, leave a message in the comment area. If you like it, please follow, like and bookmark

Guess you like

Origin blog.csdn.net/w137160164/article/details/130788090