B3DMLoaderBase.js 2.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990
  1. // B3DM File Format
  2. // https://github.com/CesiumGS/3d-tiles/blob/master/specification/TileFormats/Batched3DModel/README.md
  3. import { FeatureTable, BatchTable } from '../utilities/FeatureTable.js';
  4. export class B3DMLoaderBase {
  5. constructor() {
  6. this.fetchOptions = {};
  7. }
  8. load( url ) {
  9. return fetch( url, this.fetchOptions )
  10. .then( res => {
  11. if ( ! res.ok ) {
  12. throw new Error( `Failed to load file "${ url }" with status ${ res.status } : ${ res.statusText }` );
  13. }
  14. return res.arrayBuffer();
  15. } )
  16. .then( buffer => this.parse( buffer ) );
  17. }
  18. parse( buffer ) {
  19. // TODO: this should be able to take a uint8array with an offset and length
  20. const dataView = new DataView( buffer );
  21. // 28-byte header
  22. // 4 bytes
  23. const magic =
  24. String.fromCharCode( dataView.getUint8( 0 ) ) +
  25. String.fromCharCode( dataView.getUint8( 1 ) ) +
  26. String.fromCharCode( dataView.getUint8( 2 ) ) +
  27. String.fromCharCode( dataView.getUint8( 3 ) );
  28. console.assert( magic === 'b3dm' );
  29. // 4 bytes
  30. const version = dataView.getUint32( 4, true );
  31. console.assert( version === 1 );
  32. // 4 bytes
  33. const byteLength = dataView.getUint32( 8, true );
  34. console.assert( byteLength === buffer.byteLength );
  35. // 4 bytes
  36. const featureTableJSONByteLength = dataView.getUint32( 12, true );
  37. // 4 bytes
  38. const featureTableBinaryByteLength = dataView.getUint32( 16, true );
  39. // 4 bytes
  40. const batchTableJSONByteLength = dataView.getUint32( 20, true );
  41. // 4 bytes
  42. const batchTableBinaryByteLength = dataView.getUint32( 24, true );
  43. // Feature Table
  44. const featureTableStart = 28;
  45. const featureTable = new FeatureTable( buffer, featureTableStart, featureTableJSONByteLength, featureTableBinaryByteLength );
  46. // Batch Table
  47. const batchTableStart = featureTableStart + featureTableJSONByteLength + featureTableBinaryByteLength;
  48. const batchTable = new BatchTable( buffer, featureTable.getData( 'BATCH_LENGTH' ), batchTableStart, batchTableJSONByteLength, batchTableBinaryByteLength );
  49. const glbStart = batchTableStart + batchTableJSONByteLength + batchTableBinaryByteLength;
  50. const glbBytes = new Uint8Array( buffer, glbStart, byteLength - glbStart );
  51. return {
  52. version,
  53. featureTable,
  54. batchTable,
  55. glbBytes,
  56. };
  57. }
  58. }