region-metadata.mjs 1.6 KB

123456789101112131415161718
  1. // Per-content region metadata for public Cesium feature.show masking.
  2. import assert from 'node:assert/strict'
  3. import {parseGlb,packGlb} from './instance-repeated-meshes.mjs'
  4. export function addRegionMetadata(bytes,region){
  5. const {json,bin}=parseGlb(bytes);assert.ok(Number.isInteger(region)&&region>=0&&region<65536)
  6. const chunks=[bin];let offset=bin.length
  7. function append(data){const pad=(-offset)&3;if(pad){chunks.push(Buffer.alloc(pad));offset+=pad}const view=json.bufferViews.length;json.bufferViews.push({buffer:0,byteOffset:offset,byteLength:data.length});chunks.push(data);offset+=data.length;return view}
  8. const value=Buffer.alloc(2);value.writeUInt16LE(region);const view=append(value)
  9. const schema={id:'city-building-regions',classes:{BuildingRegion:{properties:{region:{type:'SCALAR',componentType:'UINT16'}}}}}
  10. json.extensions={...(json.extensions||{}),EXT_structural_metadata:{schema,propertyTables:[{class:'BuildingRegion',count:1,properties:{region:{values:view}}}]}}
  11. for(const mesh of json.meshes)for(const p of mesh.primitives){const count=json.accessors[p.attributes.POSITION].count,index=json.accessors.length
  12. json.accessors.push({bufferView:append(Buffer.alloc(count*4)),componentType:5125,type:'SCALAR',count,min:[0],max:[0]})
  13. p.attributes._FEATURE_ID_0=index
  14. p.extensions={...(p.extensions||{}),EXT_mesh_features:{featureIds:[{featureCount:1,attribute:0,propertyTable:0}]}}
  15. }
  16. json.extensionsUsed=[...new Set([...(json.extensionsUsed||[]),'EXT_mesh_features','EXT_structural_metadata'])]
  17. json.buffers=[{byteLength:offset}];return packGlb(json,Buffer.concat(chunks))
  18. }