区块链技术博客
www.b2bchain.cn

Cesium 高级主题:自定义fabric材质与着色器初步实践求职学习资料

D0b2wT.gif

本文介绍了Cesium 高级主题:自定义fabric材质与着色器初步实践求职学习资料,有助于帮助完成毕业设计以及求职,是一篇很好的资料。

对技术面试,学习经验等有一些体会,在此分享。

  • 1. 示例代码
  • 2. 修改 fabric 对象
    • 2.1. 必须拥有函数 czm_getMaterial(czm_materialInput materialInput)
    • 2.2. 必须有返回值:不妨返回个默认值
    • 2.3. 顶点着色器与片元着色器
      • 2.3.1. 捕获重点:片元着色器
    • 2.4. 牛刀小试:发个光吧

1. 示例代码

贴到沙盒里就可以运行:

var viewer = new Cesium.Viewer("cesiumContainer"); viewer.scene.globe.depthTestAgainstTerrain = true; viewer.camera.setView({     destination : new Cesium.Cartesian3(-2644963.9889313546, 5763731.142118295, 2199400.7089496767), //世界坐标系下的一个坐标点     orientation : {//旋转角度         heading :6.075,         pitch :-0.727,         roll : 6.283     } });  const extrudedPolygon = new Cesium.PolygonGeometry({   polygonHierarchy : new Cesium.PolygonHierarchy(     Cesium.Cartesian3.fromDegreesArray([       112.41726298378288, 23.290411251106182,       113.67072522399741, 23.560312361463682,       114.09370956893551, 22.590768298743153,       112.83803246418894, 22.285610818885644     ])   ),   extrudedHeight: 3000 });  const instance = new Cesium.GeometryInstance({   geometry: extrudedPolygon,   id: 'box with height' });  const m = new Cesium.Material({   fabric: {     type: 'Color',     uniforms: {       color: new Cesium.Color(216 / 255.0, 170 / 255.0, 208 / 255.0).withAlpha(0.618),     },   } });  const aper =  new Cesium.MaterialAppearance({   material : m, });  var p = viewer.scene.primitives.add(new Cesium.Primitive({   geometryInstances: instance,   appearance: aper,   releaseGeometryInstances: false,   compressVertices: false, }));  // p.readyPromise.then(v => console.log(v));  const vs = aper.vertexShaderSource; const fs = aper.fragmentShaderSource; const fs2 = aper.getFragmentShaderSource();  console.log(`// 顶点着色器: ${vs}`); console.log(`// 片元着色器: ${fs}`); console.log(`// 片元着色器2: ${fs2}`);

2. 修改 fabric 对象

const m = new Cesium.Material({   fabric: {     source: `float a = 12.0;`,   } });

随便定义一个浮点数,发现报错:

Cesium 高级主题:自定义fabric材质与着色器初步实践

加上 uniform 限定字,报错稍微改了一点:

Cesium 高级主题:自定义fabric材质与着色器初步实践

所以,这个 source 是有规则的。

2.1. 必须拥有函数 czm_getMaterial(czm_materialInput materialInput)

我改成这样:

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {  }`,

报错变化了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

大意是指,czm_getMaterial 这个函数没有返回值。这很正常,强类型的 GLSL 规定了这个函数的返回值类型是结构体 czm_material,那么再次修改它。

2.2. 必须有返回值:不妨返回个默认值

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);      return material; }`,

这时,形状有颜色了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

material 这个变量是一个结构体,通过修改其材质因子即可实现材质修改。

修改其漫反射因子:

注意,glsl 中创建结构体 vec3 的默认值是 (0, 0, 0),现在我想要个粉色,rgb色值是:(216 / 255.0, 170 / 255.0, 208 / 255.0),即 (0.8470588235294118, 0.66666666, 0.8156862745098039)

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);     material.diffuse = vec3(0.8470588235294118, 0.66666666, 0.8156862745098039);      return material; }`,

没毛病,颜色出来了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

2.3. 顶点着色器与片元着色器

你可以在很多个地方获取材质、外观的着色器源代码:

  • Material.prototype.shaderSource:可读可写:当前 material 对象的 source 属性,支持实时修改
  • Appearance.prototype.vertexShaderSource:只读:当前外观对象的顶点着色器,仅支持构造时传入
  • Appearance.prototype.fragmentShaderSource:只读:当前外观对象的片元着色器,仅支持构造时传入
  • Appearance.prototype.getFragmentShaderSource():返回最终完全版片元着色器源代码。

上面在 fabric 对象中的 source 属性指定的 glsl 源代码,与 console.log(m.shaderSource) 出来的是完全一样的,所以此处忽略。

当通过 2.2 节中对漫反射属性的设置后,外观对象的 vertexShaderSourcefragmentShaderSource 输出结果如下:

// 顶点着色器: attribute vec3 position3DHigh; attribute vec3 position3DLow; attribute vec3 normal; attribute vec2 st; attribute float batchId;  varying vec3 v_positionEC; varying vec3 v_normalEC; varying vec2 v_st;  void main() {     vec4 p = czm_computePosition();      v_positionEC = (czm_modelViewRelativeToEye * p).xyz;      // position in eye coordinates     v_normalEC = czm_normal * normal;                         // normal in eye coordinates     v_st = st;      gl_Position = czm_modelViewProjectionRelativeToEye * p; }
// 片元着色器: varying vec3 v_positionEC; varying vec3 v_normalEC; varying vec2 v_st;  void main() {     vec3 positionToEyeEC = -v_positionEC;      vec3 normalEC = normalize(v_normalEC); #ifdef FACE_FORWARD     normalEC = faceforward(normalEC, vec3(0.0, 0.0, 1.0), -normalEC); #endif      czm_materialInput materialInput;     materialInput.normalEC = normalEC;     materialInput.positionToEyeEC = positionToEyeEC;     materialInput.st = v_st;     czm_material material = czm_getMaterial(materialInput);  #ifdef FLAT     gl_FragColor = vec4(material.diffuse + material.emission, material.alpha); #else     gl_FragColor = czm_phong(normalize(positionToEyeEC), material, czm_lightDirectionEC); #endif }

2.3.1. 捕获重点:片元着色器

观察片元着色器代码中的主函数,其中有一句调用 czm_material material = czm_getMaterial(materialInput);

这一句便是对我们在 fabric 对象中写入的 glsl 代码的调用。

最终,进入 #ifdef FLAT 分支(才疏学浅,不知道这个 FLAT 宏是什么),对像素着色,使用 material 结构的漫反射因子 + 自发光因子 + 透明度因子进行叠加,生成最终的颜色值。所以,这个时候不妨回到 Material 的 source 中,继续动手脚。

是存在直接修改 Appearance 对象 fragmentShader、vertexShader 的大佬的,后面有机会展开说说。

2.4. 牛刀小试:发个光吧

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);   material.diffuse = vec3(0.8470588235294118, 0.66666666, 0.8156862745098039);   material.specular = 1.0;   material.shininess = 0.8;      return material; }`,

Cesium 高级主题:自定义fabric材质与着色器初步实践

(我偷偷把高度设为了 30000,不然不太明显)

换个地图和参数:

Cesium 高级主题:自定义fabric材质与着色器初步实践

稍微有那么一点感觉了。

`` JS const m = new Cesium.Material({ translucent: false, fabric: { source: czm_material czm_getMaterial(czm_materialInput materialInput)
{
czm_material material = czm_getDefaultMaterial(materialInput);
material.diffuse = vec3(0.24313725490196078, 0.7372549019607844, 0.9333333333333333);
material.specular = 0.5;
material.shininess = 0.8;
material.emission = vec3(0.0, 0.66666666, 0.0);
return material;
}`,

  • 1. 示例代码
  • 2. 修改 fabric 对象
    • 2.1. 必须拥有函数 czm_getMaterial(czm_materialInput materialInput)
    • 2.2. 必须有返回值:不妨返回个默认值
    • 2.3. 顶点着色器与片元着色器
      • 2.3.1. 捕获重点:片元着色器
    • 2.4. 牛刀小试:发个光吧

1. 示例代码

贴到沙盒里就可以运行:

var viewer = new Cesium.Viewer("cesiumContainer"); viewer.scene.globe.depthTestAgainstTerrain = true; viewer.camera.setView({     destination : new Cesium.Cartesian3(-2644963.9889313546, 5763731.142118295, 2199400.7089496767), //世界坐标系下的一个坐标点     orientation : {//旋转角度         heading :6.075,         pitch :-0.727,         roll : 6.283     } });  const extrudedPolygon = new Cesium.PolygonGeometry({   polygonHierarchy : new Cesium.PolygonHierarchy(     Cesium.Cartesian3.fromDegreesArray([       112.41726298378288, 23.290411251106182,       113.67072522399741, 23.560312361463682,       114.09370956893551, 22.590768298743153,       112.83803246418894, 22.285610818885644     ])   ),   extrudedHeight: 3000 });  const instance = new Cesium.GeometryInstance({   geometry: extrudedPolygon,   id: 'box with height' });  const m = new Cesium.Material({   fabric: {     type: 'Color',     uniforms: {       color: new Cesium.Color(216 / 255.0, 170 / 255.0, 208 / 255.0).withAlpha(0.618),     },   } });  const aper =  new Cesium.MaterialAppearance({   material : m, });  var p = viewer.scene.primitives.add(new Cesium.Primitive({   geometryInstances: instance,   appearance: aper,   releaseGeometryInstances: false,   compressVertices: false, }));  // p.readyPromise.then(v => console.log(v));  const vs = aper.vertexShaderSource; const fs = aper.fragmentShaderSource; const fs2 = aper.getFragmentShaderSource();  console.log(`// 顶点着色器: ${vs}`); console.log(`// 片元着色器: ${fs}`); console.log(`// 片元着色器2: ${fs2}`);

2. 修改 fabric 对象

const m = new Cesium.Material({   fabric: {     source: `float a = 12.0;`,   } });

随便定义一个浮点数,发现报错:

Cesium 高级主题:自定义fabric材质与着色器初步实践

加上 uniform 限定字,报错稍微改了一点:

Cesium 高级主题:自定义fabric材质与着色器初步实践

所以,这个 source 是有规则的。

2.1. 必须拥有函数 czm_getMaterial(czm_materialInput materialInput)

我改成这样:

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {  }`,

报错变化了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

大意是指,czm_getMaterial 这个函数没有返回值。这很正常,强类型的 GLSL 规定了这个函数的返回值类型是结构体 czm_material,那么再次修改它。

2.2. 必须有返回值:不妨返回个默认值

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);      return material; }`,

这时,形状有颜色了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

material 这个变量是一个结构体,通过修改其材质因子即可实现材质修改。

修改其漫反射因子:

注意,glsl 中创建结构体 vec3 的默认值是 (0, 0, 0),现在我想要个粉色,rgb色值是:(216 / 255.0, 170 / 255.0, 208 / 255.0),即 (0.8470588235294118, 0.66666666, 0.8156862745098039)

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);     material.diffuse = vec3(0.8470588235294118, 0.66666666, 0.8156862745098039);      return material; }`,

没毛病,颜色出来了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

2.3. 顶点着色器与片元着色器

你可以在很多个地方获取材质、外观的着色器源代码:

  • Material.prototype.shaderSource:可读可写:当前 material 对象的 source 属性,支持实时修改
  • Appearance.prototype.vertexShaderSource:只读:当前外观对象的顶点着色器,仅支持构造时传入
  • Appearance.prototype.fragmentShaderSource:只读:当前外观对象的片元着色器,仅支持构造时传入
  • Appearance.prototype.getFragmentShaderSource():返回最终完全版片元着色器源代码。

上面在 fabric 对象中的 source 属性指定的 glsl 源代码,与 console.log(m.shaderSource) 出来的是完全一样的,所以此处忽略。

当通过 2.2 节中对漫反射属性的设置后,外观对象的 vertexShaderSourcefragmentShaderSource 输出结果如下:

// 顶点着色器: attribute vec3 position3DHigh; attribute vec3 position3DLow; attribute vec3 normal; attribute vec2 st; attribute float batchId;  varying vec3 v_positionEC; varying vec3 v_normalEC; varying vec2 v_st;  void main() {     vec4 p = czm_computePosition();      v_positionEC = (czm_modelViewRelativeToEye * p).xyz;      // position in eye coordinates     v_normalEC = czm_normal * normal;                         // normal in eye coordinates     v_st = st;      gl_Position = czm_modelViewProjectionRelativeToEye * p; }
// 片元着色器: varying vec3 v_positionEC; varying vec3 v_normalEC; varying vec2 v_st;  void main() {     vec3 positionToEyeEC = -v_positionEC;      vec3 normalEC = normalize(v_normalEC); #ifdef FACE_FORWARD     normalEC = faceforward(normalEC, vec3(0.0, 0.0, 1.0), -normalEC); #endif      czm_materialInput materialInput;     materialInput.normalEC = normalEC;     materialInput.positionToEyeEC = positionToEyeEC;     materialInput.st = v_st;     czm_material material = czm_getMaterial(materialInput);  #ifdef FLAT     gl_FragColor = vec4(material.diffuse + material.emission, material.alpha); #else     gl_FragColor = czm_phong(normalize(positionToEyeEC), material, czm_lightDirectionEC); #endif }

2.3.1. 捕获重点:片元着色器

观察片元着色器代码中的主函数,其中有一句调用 czm_material material = czm_getMaterial(materialInput);

这一句便是对我们在 fabric 对象中写入的 glsl 代码的调用。

最终,进入 #ifdef FLAT 分支(才疏学浅,不知道这个 FLAT 宏是什么),对像素着色,使用 material 结构的漫反射因子 + 自发光因子 + 透明度因子进行叠加,生成最终的颜色值。所以,这个时候不妨回到 Material 的 source 中,继续动手脚。

是存在直接修改 Appearance 对象 fragmentShader、vertexShader 的大佬的,后面有机会展开说说。

2.4. 牛刀小试:发个光吧

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);   material.diffuse = vec3(0.8470588235294118, 0.66666666, 0.8156862745098039);   material.specular = 1.0;   material.shininess = 0.8;      return material; }`,

Cesium 高级主题:自定义fabric材质与着色器初步实践

(我偷偷把高度设为了 30000,不然不太明显)

换个地图和参数:

Cesium 高级主题:自定义fabric材质与着色器初步实践

稍微有那么一点感觉了。

`` JS const m = new Cesium.Material({ translucent: false, fabric: { source: czm_material czm_getMaterial(czm_materialInput materialInput)
{
czm_material material = czm_getDefaultMaterial(materialInput);
material.diffuse = vec3(0.24313725490196078, 0.7372549019607844, 0.9333333333333333);
material.specular = 0.5;
material.shininess = 0.8;
material.emission = vec3(0.0, 0.66666666, 0.0);
return material;
}`,

  • 1. 示例代码
  • 2. 修改 fabric 对象
    • 2.1. 必须拥有函数 czm_getMaterial(czm_materialInput materialInput)
    • 2.2. 必须有返回值:不妨返回个默认值
    • 2.3. 顶点着色器与片元着色器
      • 2.3.1. 捕获重点:片元着色器
    • 2.4. 牛刀小试:发个光吧

1. 示例代码

贴到沙盒里就可以运行:

var viewer = new Cesium.Viewer("cesiumContainer"); viewer.scene.globe.depthTestAgainstTerrain = true; viewer.camera.setView({     destination : new Cesium.Cartesian3(-2644963.9889313546, 5763731.142118295, 2199400.7089496767), //世界坐标系下的一个坐标点     orientation : {//旋转角度         heading :6.075,         pitch :-0.727,         roll : 6.283     } });  const extrudedPolygon = new Cesium.PolygonGeometry({   polygonHierarchy : new Cesium.PolygonHierarchy(     Cesium.Cartesian3.fromDegreesArray([       112.41726298378288, 23.290411251106182,       113.67072522399741, 23.560312361463682,       114.09370956893551, 22.590768298743153,       112.83803246418894, 22.285610818885644     ])   ),   extrudedHeight: 3000 });  const instance = new Cesium.GeometryInstance({   geometry: extrudedPolygon,   id: 'box with height' });  const m = new Cesium.Material({   fabric: {     type: 'Color',     uniforms: {       color: new Cesium.Color(216 / 255.0, 170 / 255.0, 208 / 255.0).withAlpha(0.618),     },   } });  const aper =  new Cesium.MaterialAppearance({   material : m, });  var p = viewer.scene.primitives.add(new Cesium.Primitive({   geometryInstances: instance,   appearance: aper,   releaseGeometryInstances: false,   compressVertices: false, }));  // p.readyPromise.then(v => console.log(v));  const vs = aper.vertexShaderSource; const fs = aper.fragmentShaderSource; const fs2 = aper.getFragmentShaderSource();  console.log(`// 顶点着色器: ${vs}`); console.log(`// 片元着色器: ${fs}`); console.log(`// 片元着色器2: ${fs2}`);

2. 修改 fabric 对象

const m = new Cesium.Material({   fabric: {     source: `float a = 12.0;`,   } });

随便定义一个浮点数,发现报错:

Cesium 高级主题:自定义fabric材质与着色器初步实践

加上 uniform 限定字,报错稍微改了一点:

Cesium 高级主题:自定义fabric材质与着色器初步实践

所以,这个 source 是有规则的。

2.1. 必须拥有函数 czm_getMaterial(czm_materialInput materialInput)

我改成这样:

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {  }`,

报错变化了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

大意是指,czm_getMaterial 这个函数没有返回值。这很正常,强类型的 GLSL 规定了这个函数的返回值类型是结构体 czm_material,那么再次修改它。

2.2. 必须有返回值:不妨返回个默认值

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);      return material; }`,

这时,形状有颜色了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

material 这个变量是一个结构体,通过修改其材质因子即可实现材质修改。

修改其漫反射因子:

注意,glsl 中创建结构体 vec3 的默认值是 (0, 0, 0),现在我想要个粉色,rgb色值是:(216 / 255.0, 170 / 255.0, 208 / 255.0),即 (0.8470588235294118, 0.66666666, 0.8156862745098039)

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);     material.diffuse = vec3(0.8470588235294118, 0.66666666, 0.8156862745098039);      return material; }`,

没毛病,颜色出来了:

Cesium 高级主题:自定义fabric材质与着色器初步实践

2.3. 顶点着色器与片元着色器

你可以在很多个地方获取材质、外观的着色器源代码:

  • Material.prototype.shaderSource:可读可写:当前 material 对象的 source 属性,支持实时修改
  • Appearance.prototype.vertexShaderSource:只读:当前外观对象的顶点着色器,仅支持构造时传入
  • Appearance.prototype.fragmentShaderSource:只读:当前外观对象的片元着色器,仅支持构造时传入
  • Appearance.prototype.getFragmentShaderSource():返回最终完全版片元着色器源代码。

上面在 fabric 对象中的 source 属性指定的 glsl 源代码,与 console.log(m.shaderSource) 出来的是完全一样的,所以此处忽略。

当通过 2.2 节中对漫反射属性的设置后,外观对象的 vertexShaderSourcefragmentShaderSource 输出结果如下:

// 顶点着色器: attribute vec3 position3DHigh; attribute vec3 position3DLow; attribute vec3 normal; attribute vec2 st; attribute float batchId;  varying vec3 v_positionEC; varying vec3 v_normalEC; varying vec2 v_st;  void main() {     vec4 p = czm_computePosition();      v_positionEC = (czm_modelViewRelativeToEye * p).xyz;      // position in eye coordinates     v_normalEC = czm_normal * normal;                         // normal in eye coordinates     v_st = st;      gl_Position = czm_modelViewProjectionRelativeToEye * p; }
// 片元着色器: varying vec3 v_positionEC; varying vec3 v_normalEC; varying vec2 v_st;  void main() {     vec3 positionToEyeEC = -v_positionEC;      vec3 normalEC = normalize(v_normalEC); #ifdef FACE_FORWARD     normalEC = faceforward(normalEC, vec3(0.0, 0.0, 1.0), -normalEC); #endif      czm_materialInput materialInput;     materialInput.normalEC = normalEC;     materialInput.positionToEyeEC = positionToEyeEC;     materialInput.st = v_st;     czm_material material = czm_getMaterial(materialInput);  #ifdef FLAT     gl_FragColor = vec4(material.diffuse + material.emission, material.alpha); #else     gl_FragColor = czm_phong(normalize(positionToEyeEC), material, czm_lightDirectionEC); #endif }

2.3.1. 捕获重点:片元着色器

观察片元着色器代码中的主函数,其中有一句调用 czm_material material = czm_getMaterial(materialInput);

这一句便是对我们在 fabric 对象中写入的 glsl 代码的调用。

最终,进入 #ifdef FLAT 分支(才疏学浅,不知道这个 FLAT 宏是什么),对像素着色,使用 material 结构的漫反射因子 + 自发光因子 + 透明度因子进行叠加,生成最终的颜色值。所以,这个时候不妨回到 Material 的 source 中,继续动手脚。

是存在直接修改 Appearance 对象 fragmentShader、vertexShader 的大佬的,后面有机会展开说说。

2.4. 牛刀小试:发个光吧

source:  `czm_material czm_getMaterial(czm_materialInput materialInput) {     czm_material material = czm_getDefaultMaterial(materialInput);   material.diffuse = vec3(0.8470588235294118, 0.66666666, 0.8156862745098039);   material.specular = 1.0;   material.shininess = 0.8;      return material; }`,

Cesium 高级主题:自定义fabric材质与着色器初步实践

(我偷偷把高度设为了 30000,不然不太明显)

换个地图和参数:

Cesium 高级主题:自定义fabric材质与着色器初步实践

稍微有那么一点感觉了。

`` JS const m = new Cesium.Material({ translucent: false, fabric: { source: czm_material czm_getMaterial(czm_materialInput materialInput)
{
czm_material material = czm_getDefaultMaterial(materialInput);
material.diffuse = vec3(0.24313725490196078, 0.7372549019607844, 0.9333333333333333);
material.specular = 0.5;
material.shininess = 0.8;
material.emission = vec3(0.0, 0.66666666, 0.0);
return material;
}`,

部分转自互联网,侵权删除联系

赞(0) 打赏
部分文章转自网络,侵权联系删除b2bchain区块链学习技术社区 » Cesium 高级主题:自定义fabric材质与着色器初步实践求职学习资料
分享到: 更多 (0)

评论 抢沙发

  • 昵称 (必填)
  • 邮箱 (必填)
  • 网址

b2b链

联系我们联系我们