无论是通过Entity类,还是通过Primitive类添加的空间几何数据,Cesium都提供了对应的方法或材质相关类对材质进行修改。在讲解材质设置之前,首先我们先简单地介绍下什么是材质。比较粗浅的理解是,材质可以是几何对象表面的任意一种着色(Cesium.Color)、可以是贴在其表面的一张图片、也可以是一个纹理或图案,比如下图中的条形或棋盘形的图案。
针对于两种方式(Entity和Primitive)绘制的几何对象,Cesium也提供了Material类和MaterialProperty类,分别对通过Primitive和Entity两种方式生成的几何对象的material属性进行赋值。这里特别要注意,Primitive的appearance(或继承类)的material属性为Material类型,Entity的xxxGraphics的material属性为MaterialProperty或Color类型,请大家不要记混。
Material类
Material类专为Appearance类而生,用于修改Primitive的几何对象材质。同时,Apperance也有自己的继承类,通过修改部分继承类的material属性,也可实现Primitive几何对象材质的修改。Appearance的继承类如下图所示,其中橘黄色背景的子类,能修改其material属性。
通过Material类修改材质相对来说比较复杂,需要对OpenGL以及底层渲染机制进行了解。Cesium中的Material类的内部机制是通过一种json格式的Fabric对象来表达物体的外观特征,而这些外观特征是由漫反射(diffuse)、镜面反射(specular)、法向量(normal)、自发光(emission)以及透明度(alpha)组合(即一个Components)而成。详细可查看Cesium对Fabric的解说https://github.com/CesiumGS/cesium/wiki/Fabric。
Cesium为我们提供了23种现成的Material类型,可通过Material.fromType方法和Fabric两种方式去获取并设置几何对象材质。如下是通过Material类的两种方式实现着色的示例:
// Create a color material with fromType:
polygon.material = Cesium.Material.fromType('Color');
polygon.material.uniforms.color = new Cesium.Color(1.0, 1.0, 0.0, 1.0);
// Create the default material:
polygon.material = new Cesium.Material();
// Create a color material with full Fabric notation:
polygon.material = new Cesium.Material({
fabric : {
type : 'Color',
uniforms : {
color : new Cesium.Color(1.0, 1.0, 0.0, 1.0)
}
}
});
具体可查阅Material类文档说明:http://127.0.0.1:5500/Build/Documentation/Material.html?classFilter=material,以及Material的沙盒示例:https://sandcastle.cesium.com/index.html?src=Materials.html。
从Material的Fabric对象组成来看,要想创建一个新的Material,用户只需要指定type、uniforms、compontents三个属性,构建一个Fabric的JSON对象。如果想写一些自定义的shader,则需要再指定source属性。
MaterialProperty类
MaterialProperty类专为Entity而生,它是一个抽象类,我们无法对它进行实例化。要使用该类对材质进行设置,需要实例化其子类。MaterialProperty类的继承类,如下图所示:
1.ColorMaterialProperty 颜色材质
ColorMaterialProperty类相对来说比较简单,你可以直接使用Cesium.Color替换它,两个类实现的效果最终是一样的,都是给几何对象直接着色。
var color = Cesium.Color.BLUE.withAlpha(0.5);
var colorMaterial = new Cesium.ColorMaterialProperty(color);
viewer.entities.add({
position: Cesium.Cartesian3.fromDegrees(-55.0, 40.0, 100000.0),
ellipse: {
semiMajorAxis: 300000.0, // 长半轴距离
semiMinorAxis: 200000.0, // 短半轴距离
height: 20000.0,
material: colorMaterial,
},
});
2.ImageMaterialProperty 贴图材质
ImageMaterialProperty类可以给几何对象表面贴上一张图片。
var imgUrl = "./images/bumpmap.png";
var imgMaterial = new Cesium.ImageMaterialProperty({
image: imgUrl,
repeat: new Cesium.Cartesian2(4, 4),
color: Cesium.Color.BLUE,
});
viewer.entities.add({
position: Cesium.Cartesian3.fromDegrees(-65.0, 40.0, 100000.0),
ellipse: {
semiMajorAxis: 300000.0, // 长半轴距离
semiMinorAxis: 200000.0, // 短半轴距离
height: 20000.0,
material: imgMaterial,
},
});
3.CheckerboardMaterialProperty 棋盘纹理
var checkerboardMaterial = new Cesium.CheckerboardMaterialProperty({
evenColor: Cesium.Color.WHITE,
oddColor: Cesium.Color.BLACK,
repeat: new Cesium.Cartesian2(4, 4),
});
viewer.entities.add({
position: Cesium.Cartesian3.fromDegrees(-75.0, 40.0, 100000.0),
ellipse: {
semiMajorAxis: 300000.0, // 长半轴距离
semiMinorAxis: 200000.0, // 短半轴距离
height: 20000.0,
material: checkerboardMaterial,
},
});
4.StripeMaterialProperty 条纹纹理
var stripeMaterial = new Cesium.StripeMaterialProperty({
orientation: Cesium.StripeOrientation.VERTICAL,
evenColor: Cesium.Color.WHITE,
oddColor: Cesium.Color.BLACK,
repeat: 16,
});
viewer.entities.add({
position: Cesium.Cartesian3.fromDegrees(-85.0, 40.0, 100000.0),
ellipse: {
semiMajorAxis: 300000.0, // 长半轴距离
semiMinorAxis: 200000.0, // 短半轴距离
height: 20000.0,
material: stripeMaterial,
},
});
5.GridMaterialProperty 网格
var gripMaterial = new Cesium.GridMaterialProperty({
color: Cesium.Color.YELLOW,
cellAlpha: 0.5,
lineCount: new Cesium.Cartesian2(8, 8),
lineThickness: new Cesium.Cartesian2(2.0, 2.0),
lineOffset: new Cesium.Cartesian2(0.0, 0.0),
});
viewer.entities.add({
position: Cesium.Cartesian3.fromDegrees(-95.0, 40.0, 100000.0),
ellipse: {
semiMajorAxis: 300000.0, // 长半轴距离
semiMinorAxis: 200000.0, // 短半轴距离
height: 20000.0,
material: gripMaterial,
},
});
6.PolylineGlowMaterialProperty 发光材质
var glowingLine = viewer.entities.add({
name: "Glowing blue line on the surface",
polyline: {
positions: Cesium.Cartesian3.fromDegreesArray([-75, 37, -125, 37]),
width: 10,
material: new Cesium.PolylineGlowMaterialProperty({
glowPower: 0.8,
taperPower: 0.5,
color: Cesium.Color.CORNFLOWERBLUE,
}),
},
});
7.PolylineOutlineMaterialProperty 外轮廓材质
var orangeOutlined = viewer.entities.add({
name:
"Orange line with black outline at height and following the surface",
polyline: {
positions: Cesium.Cartesian3.fromDegreesArrayHeights([
-75,
39,
250000,
-125,
39,
250000,
]),
width: 5,
material: new Cesium.PolylineOutlineMaterialProperty({
color: Cesium.Color.ORANGE,
outlineWidth: 5,
outlineColor: Cesium.Color.BLACK,
}),
},
});
8.PolylineArrowMaterialProperty 带有箭头的线
var purpleArrow = viewer.entities.add({
name: "Purple straight arrow at height",
polyline: {
positions: Cesium.Cartesian3.fromDegreesArrayHeights([
-75,
43,
500000,
-125,
43,
500000,
]),
width: 10,
arcType: Cesium.ArcType.NONE,
material: new Cesium.PolylineArrowMaterialProperty(Cesium.Color.PURPLE),
},
});
9.PolylineDashMaterialProperty 虚线
var dashedLine = viewer.entities.add({
name: "Blue dashed line",
polyline: {
positions: Cesium.Cartesian3.fromDegreesArrayHeights([
-75,
45,
500000,
-125,
45,
500000,
]),
width: 4,
material: new Cesium.PolylineDashMaterialProperty({
color: Cesium.Color.CYAN,
}),
},
});
上述9种方式生成的效果图如下所示: