@loaders.gl/tile-converter 4.0.0-alpha.22 → 4.0.0-alpha.24

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (137) hide show
  1. package/dist/3d-tiles-converter/helpers/load-i3s.d.ts.map +1 -1
  2. package/dist/constants.d.ts +0 -2
  3. package/dist/constants.d.ts.map +1 -1
  4. package/dist/converter.min.js +106 -106
  5. package/dist/dist.min.js +1883 -1241
  6. package/dist/es5/3d-tiles-converter/helpers/load-i3s.js.map +1 -1
  7. package/dist/es5/constants.js +1 -5
  8. package/dist/es5/constants.js.map +1 -1
  9. package/dist/es5/deps-installer/deps-installer.js +1 -1
  10. package/dist/es5/i3s-converter/helpers/batch-ids-extensions.js +26 -11
  11. package/dist/es5/i3s-converter/helpers/batch-ids-extensions.js.map +1 -1
  12. package/dist/es5/i3s-converter/helpers/feature-attributes.js +7 -17
  13. package/dist/es5/i3s-converter/helpers/feature-attributes.js.map +1 -1
  14. package/dist/es5/i3s-converter/helpers/geometry-attributes.js +83 -44
  15. package/dist/es5/i3s-converter/helpers/geometry-attributes.js.map +1 -1
  16. package/dist/es5/i3s-converter/helpers/geometry-converter.js +70 -17
  17. package/dist/es5/i3s-converter/helpers/geometry-converter.js.map +1 -1
  18. package/dist/es5/i3s-converter/helpers/node-index-document.js +3 -2
  19. package/dist/es5/i3s-converter/helpers/node-index-document.js.map +1 -1
  20. package/dist/es5/i3s-converter/helpers/preprocess-3d-tiles.js +1 -2
  21. package/dist/es5/i3s-converter/helpers/preprocess-3d-tiles.js.map +1 -1
  22. package/dist/es5/i3s-converter/i3s-converter.js +36 -26
  23. package/dist/es5/i3s-converter/i3s-converter.js.map +1 -1
  24. package/dist/es5/i3s-converter/types.js.map +1 -1
  25. package/dist/es5/i3s-server/controllers/slpk-controller.js +2 -2
  26. package/dist/es5/i3s-server/controllers/slpk-controller.js.map +1 -1
  27. package/dist/es5/pgm-loader.js +11 -3
  28. package/dist/es5/pgm-loader.js.map +1 -1
  29. package/dist/es5/slpk-extractor/slpk-extractor.js +1 -1
  30. package/dist/es5/slpk-extractor/slpk-extractor.js.map +1 -1
  31. package/dist/esm/3d-tiles-converter/helpers/load-i3s.js.map +1 -1
  32. package/dist/esm/constants.js +0 -2
  33. package/dist/esm/constants.js.map +1 -1
  34. package/dist/esm/deps-installer/deps-installer.js +1 -1
  35. package/dist/esm/i3s-converter/helpers/batch-ids-extensions.js +21 -6
  36. package/dist/esm/i3s-converter/helpers/batch-ids-extensions.js.map +1 -1
  37. package/dist/esm/i3s-converter/helpers/feature-attributes.js +9 -7
  38. package/dist/esm/i3s-converter/helpers/feature-attributes.js.map +1 -1
  39. package/dist/esm/i3s-converter/helpers/geometry-attributes.js +76 -34
  40. package/dist/esm/i3s-converter/helpers/geometry-attributes.js.map +1 -1
  41. package/dist/esm/i3s-converter/helpers/geometry-converter.js +66 -13
  42. package/dist/esm/i3s-converter/helpers/geometry-converter.js.map +1 -1
  43. package/dist/esm/i3s-converter/helpers/node-index-document.js +2 -1
  44. package/dist/esm/i3s-converter/helpers/node-index-document.js.map +1 -1
  45. package/dist/esm/i3s-converter/helpers/preprocess-3d-tiles.js +1 -1
  46. package/dist/esm/i3s-converter/helpers/preprocess-3d-tiles.js.map +1 -1
  47. package/dist/esm/i3s-converter/i3s-converter.js +20 -17
  48. package/dist/esm/i3s-converter/i3s-converter.js.map +1 -1
  49. package/dist/esm/i3s-converter/types.js.map +1 -1
  50. package/dist/esm/i3s-server/bin/i3s-server.min.js +71 -71
  51. package/dist/esm/i3s-server/controllers/slpk-controller.js +1 -1
  52. package/dist/esm/i3s-server/controllers/slpk-controller.js.map +1 -1
  53. package/dist/esm/pgm-loader.js +7 -4
  54. package/dist/esm/pgm-loader.js.map +1 -1
  55. package/dist/esm/slpk-extractor/slpk-extractor.js +2 -1
  56. package/dist/esm/slpk-extractor/slpk-extractor.js.map +1 -1
  57. package/dist/i3s-converter/helpers/batch-ids-extensions.d.ts.map +1 -1
  58. package/dist/i3s-converter/helpers/feature-attributes.d.ts +6 -6
  59. package/dist/i3s-converter/helpers/feature-attributes.d.ts.map +1 -1
  60. package/dist/i3s-converter/helpers/geometry-attributes.d.ts.map +1 -1
  61. package/dist/i3s-converter/helpers/geometry-converter.d.ts +2 -2
  62. package/dist/i3s-converter/helpers/geometry-converter.d.ts.map +1 -1
  63. package/dist/i3s-converter/helpers/node-index-document.d.ts.map +1 -1
  64. package/dist/i3s-converter/i3s-converter.d.ts +1 -1
  65. package/dist/i3s-converter/i3s-converter.d.ts.map +1 -1
  66. package/dist/i3s-converter/types.d.ts +7 -4
  67. package/dist/i3s-converter/types.d.ts.map +1 -1
  68. package/dist/pgm-loader.d.ts +9 -2
  69. package/dist/pgm-loader.d.ts.map +1 -1
  70. package/dist/slpk-extractor/slpk-extractor.d.ts.map +1 -1
  71. package/dist/slpk-extractor.min.js +38 -38
  72. package/package.json +14 -14
  73. package/src/3d-tiles-converter/helpers/load-i3s.ts +1 -0
  74. package/src/constants.ts +0 -3
  75. package/src/i3s-converter/helpers/batch-ids-extensions.ts +53 -14
  76. package/src/i3s-converter/helpers/feature-attributes.ts +20 -15
  77. package/src/i3s-converter/helpers/geometry-attributes.ts +80 -50
  78. package/src/i3s-converter/helpers/geometry-converter.ts +153 -21
  79. package/src/i3s-converter/helpers/node-index-document.ts +5 -1
  80. package/src/i3s-converter/helpers/preprocess-3d-tiles.ts +1 -1
  81. package/src/i3s-converter/i3s-converter.ts +42 -17
  82. package/src/i3s-converter/types.ts +8 -4
  83. package/src/i3s-server/controllers/slpk-controller.ts +1 -1
  84. package/src/pgm-loader.ts +15 -7
  85. package/src/slpk-extractor/slpk-extractor.ts +2 -1
  86. package/dist/3d-tiles-converter/3d-tiles-converter.js +0 -279
  87. package/dist/3d-tiles-converter/helpers/b3dm-converter.js +0 -271
  88. package/dist/3d-tiles-converter/helpers/i3s-obb-to-3d-tiles-obb.js +0 -23
  89. package/dist/3d-tiles-converter/helpers/load-i3s.js +0 -42
  90. package/dist/3d-tiles-converter/helpers/texture-atlas.js +0 -54
  91. package/dist/3d-tiles-converter/json-templates/tileset.js +0 -43
  92. package/dist/bundle.js +0 -5
  93. package/dist/constants.js +0 -6
  94. package/dist/converter-cli.js +0 -222
  95. package/dist/deps-installer/deps-installer.js +0 -89
  96. package/dist/i3s-converter/helpers/batch-ids-extensions.js +0 -158
  97. package/dist/i3s-converter/helpers/coordinate-converter.js +0 -122
  98. package/dist/i3s-converter/helpers/create-scene-server-path.js +0 -28
  99. package/dist/i3s-converter/helpers/feature-attributes.js +0 -216
  100. package/dist/i3s-converter/helpers/geometry-attributes.js +0 -203
  101. package/dist/i3s-converter/helpers/geometry-converter.js +0 -1240
  102. package/dist/i3s-converter/helpers/gltf-attributes.js +0 -129
  103. package/dist/i3s-converter/helpers/load-3d-tiles.js +0 -99
  104. package/dist/i3s-converter/helpers/node-debug.js +0 -120
  105. package/dist/i3s-converter/helpers/node-index-document.js +0 -268
  106. package/dist/i3s-converter/helpers/node-pages.js +0 -316
  107. package/dist/i3s-converter/helpers/preprocess-3d-tiles.js +0 -100
  108. package/dist/i3s-converter/helpers/tileset-traversal.js +0 -29
  109. package/dist/i3s-converter/i3s-converter.js +0 -945
  110. package/dist/i3s-converter/json-templates/geometry-definitions.js +0 -87
  111. package/dist/i3s-converter/json-templates/layers.js +0 -139
  112. package/dist/i3s-converter/json-templates/metadata.js +0 -25
  113. package/dist/i3s-converter/json-templates/node.js +0 -89
  114. package/dist/i3s-converter/json-templates/scene-server.js +0 -31
  115. package/dist/i3s-converter/json-templates/shared-resources.js +0 -129
  116. package/dist/i3s-converter/json-templates/store.js +0 -103
  117. package/dist/i3s-converter/types.js +0 -17
  118. package/dist/i3s-server/app.js +0 -29
  119. package/dist/i3s-server/bin/www.js +0 -37
  120. package/dist/i3s-server/controllers/index-controller.js +0 -31
  121. package/dist/i3s-server/controllers/slpk-controller.js +0 -33
  122. package/dist/i3s-server/routes/index.js +0 -20
  123. package/dist/i3s-server/routes/slpk-router.js +0 -34
  124. package/dist/i3s-server/utils/create-scene-server.js +0 -22
  125. package/dist/i3s-server/utils/server-utils.js +0 -66
  126. package/dist/index.js +0 -10
  127. package/dist/lib/utils/cli-utils.js +0 -82
  128. package/dist/lib/utils/compress-util.js +0 -257
  129. package/dist/lib/utils/file-utils.js +0 -139
  130. package/dist/lib/utils/geometry-utils.js +0 -18
  131. package/dist/lib/utils/lod-conversion-utils.js +0 -76
  132. package/dist/lib/utils/queue.js +0 -18
  133. package/dist/lib/utils/statistic-utills.js +0 -64
  134. package/dist/lib/utils/write-queue.js +0 -80
  135. package/dist/pgm-loader.js +0 -24
  136. package/dist/slpk-extractor/slpk-extractor.js +0 -74
  137. package/dist/slpk-extractor-cli.js +0 -102
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@loaders.gl/tile-converter",
3
- "version": "4.0.0-alpha.22",
3
+ "version": "4.0.0-alpha.24",
4
4
  "description": "Converter",
5
5
  "license": "MIT",
6
6
  "publishConfig": {
@@ -45,18 +45,18 @@
45
45
  "build-i3s-server-bundle": "esbuild src/i3s-server/bin/www.ts --outfile=dist/esm/i3s-server/bin/i3s-server.min.js --platform=node --target=esnext,node14 --external:join-images --minify --bundle --define:__VERSION__=\\\"$npm_package_version\\\""
46
46
  },
47
47
  "dependencies": {
48
- "@loaders.gl/3d-tiles": "4.0.0-alpha.22",
49
- "@loaders.gl/crypto": "4.0.0-alpha.22",
50
- "@loaders.gl/draco": "4.0.0-alpha.22",
51
- "@loaders.gl/gltf": "4.0.0-alpha.22",
52
- "@loaders.gl/i3s": "4.0.0-alpha.22",
53
- "@loaders.gl/images": "4.0.0-alpha.22",
54
- "@loaders.gl/loader-utils": "4.0.0-alpha.22",
55
- "@loaders.gl/polyfills": "4.0.0-alpha.22",
56
- "@loaders.gl/textures": "4.0.0-alpha.22",
57
- "@loaders.gl/tiles": "4.0.0-alpha.22",
58
- "@loaders.gl/worker-utils": "4.0.0-alpha.22",
59
- "@loaders.gl/zip": "4.0.0-alpha.22",
48
+ "@loaders.gl/3d-tiles": "4.0.0-alpha.24",
49
+ "@loaders.gl/crypto": "4.0.0-alpha.24",
50
+ "@loaders.gl/draco": "4.0.0-alpha.24",
51
+ "@loaders.gl/gltf": "4.0.0-alpha.24",
52
+ "@loaders.gl/i3s": "4.0.0-alpha.24",
53
+ "@loaders.gl/images": "4.0.0-alpha.24",
54
+ "@loaders.gl/loader-utils": "4.0.0-alpha.24",
55
+ "@loaders.gl/polyfills": "4.0.0-alpha.24",
56
+ "@loaders.gl/textures": "4.0.0-alpha.24",
57
+ "@loaders.gl/tiles": "4.0.0-alpha.24",
58
+ "@loaders.gl/worker-utils": "4.0.0-alpha.24",
59
+ "@loaders.gl/zip": "4.0.0-alpha.24",
60
60
  "@math.gl/core": "^3.5.1",
61
61
  "@math.gl/culling": "^3.5.1",
62
62
  "@math.gl/geoid": "^3.5.1",
@@ -80,7 +80,7 @@
80
80
  "join-images": "^1.1.3",
81
81
  "sharp": "^0.31.3"
82
82
  },
83
- "gitHead": "0da838c506d1275383f2fd3d244d9c72b25397d2",
83
+ "gitHead": "97a8990595c132fb14e3445a8768d9f4cb98ff05",
84
84
  "devDependencies": {
85
85
  "@types/express": "^4.17.17",
86
86
  "@types/node": "^20.4.2"
@@ -47,5 +47,6 @@ export const loadI3SContent = async (
47
47
  };
48
48
  const tileContent = await load(sourceTile.contentUrl, I3SLoader, loadOptions);
49
49
 
50
+ // @ts-expect-error
50
51
  return tileContent;
51
52
  };
package/src/constants.ts CHANGED
@@ -1,5 +1,2 @@
1
1
  export const BROWSER_ERROR_MESSAGE =
2
2
  'Tile converter does not work in browser, only in node js environment';
3
-
4
- export const EXT_MESH_FEATURES = 'EXT_mesh_features';
5
- export const EXT_FEATURE_METADATA = 'EXT_feature_metadata';
@@ -3,11 +3,16 @@ import type {NumericArray} from '@loaders.gl/loader-utils';
3
3
  import type {
4
4
  GLTF_EXT_feature_metadata_FeatureIdTexture,
5
5
  GLTF_EXT_feature_metadata_GLTF,
6
- GLTF_EXT_feature_metadata_Primitive
6
+ GLTF_EXT_feature_metadata_Primitive,
7
+ GLTF_EXT_structural_metadata
7
8
  } from '@loaders.gl/gltf';
9
+
10
+ import type {GLTF_EXT_mesh_features} from '@loaders.gl/gltf';
11
+
8
12
  import {TypedArray} from '@math.gl/core';
9
13
  import {TextureImageProperties} from '../types';
10
- import {EXT_FEATURE_METADATA, EXT_MESH_FEATURES} from '../../constants';
14
+ import {emod} from '@loaders.gl/math';
15
+ import {EXT_STRUCTURAL_METADATA, EXT_MESH_FEATURES, EXT_FEATURE_METADATA} from '@loaders.gl/gltf';
11
16
  import {Tiles3DTileContent} from '@loaders.gl/3d-tiles';
12
17
 
13
18
  /**
@@ -52,7 +57,6 @@ export function handleBatchIdsExtensions(
52
57
  featureTexture: string | null
53
58
  ): NumericArray {
54
59
  const extensions = primitive?.extensions;
55
-
56
60
  if (!extensions) {
57
61
  return [];
58
62
  }
@@ -67,8 +71,13 @@ export function handleBatchIdsExtensions(
67
71
  featureTexture
68
72
  );
69
73
  case EXT_MESH_FEATURES:
70
- console.warn('EXT_mesh_features extension is not supported yet');
71
- return [];
74
+ return handleExtMeshFeaturesExtension(attributes, extensionData as GLTF_EXT_mesh_features);
75
+ case EXT_STRUCTURAL_METADATA:
76
+ return handleExtStructuralMetadataExtension(
77
+ attributes,
78
+ extensionData as GLTF_EXT_structural_metadata
79
+ );
80
+
72
81
  default:
73
82
  return [];
74
83
  }
@@ -77,6 +86,45 @@ export function handleBatchIdsExtensions(
77
86
  return [];
78
87
  }
79
88
 
89
+ function handleExtStructuralMetadataExtension(
90
+ attributes: {
91
+ [key: string]: GLTFAccessorPostprocessed;
92
+ },
93
+ extStructuralMetadata: GLTF_EXT_structural_metadata
94
+ ): NumericArray {
95
+ // Take only first extension object to get batchIds attribute name.
96
+ const dataAttributeNames = extStructuralMetadata?.dataAttributeNames;
97
+ if (dataAttributeNames?.length) {
98
+ // Let's use the first element of the array
99
+ // TODO: What to do with others if any?
100
+ const batchIdsAttribute = attributes[dataAttributeNames[0]];
101
+ return batchIdsAttribute.value;
102
+ }
103
+ return [];
104
+ }
105
+
106
+ /**
107
+ * Getting batchIds from EXT_mesh_features extensions.
108
+ * @param attributes - gltf accessors
109
+ * @param extMeshFeatures - EXT_mesh_features extension
110
+ * @returns an array of attribute values
111
+ */
112
+ function handleExtMeshFeaturesExtension(
113
+ attributes: {
114
+ [key: string]: GLTFAccessorPostprocessed;
115
+ },
116
+ extMeshFeatures: GLTF_EXT_mesh_features
117
+ ): NumericArray {
118
+ const dataAttributeNames = extMeshFeatures?.dataAttributeNames;
119
+ if (dataAttributeNames?.length) {
120
+ // Let's use the first element of the array
121
+ // TODO: What to do with others if any?
122
+ const batchIdsAttribute = attributes[dataAttributeNames[0]];
123
+ return batchIdsAttribute.value;
124
+ }
125
+ return [];
126
+ }
127
+
80
128
  /**
81
129
  * Get batchIds from EXT_feature_metadata extension.
82
130
  * Docs - https://github.com/CesiumGS/glTF/tree/3d-tiles-next/extensions/2.0/Vendor/EXT_feature_metadata
@@ -218,12 +266,3 @@ function generateBatchIdsFromTexture(
218
266
 
219
267
  return batchIds;
220
268
  }
221
-
222
- /**
223
- * Handle UVs if they are out of range [0,1].
224
- * @param n
225
- * @param m
226
- */
227
- function emod(n: number): number {
228
- return ((n % 1) + 1) % 1;
229
- }
@@ -9,26 +9,26 @@ import {
9
9
  } from '@loaders.gl/i3s';
10
10
 
11
11
  /**
12
- * Takes attributes from property table based on featureIds.
12
+ * Takes attributes from property table based on featureIdsMap.
13
13
  * If there is no property value for particular featureId (index) the property will be null.
14
14
  * Example:
15
15
  * Initial data:
16
- * OBJECTID: [0, 1, 5]
16
+ * OBJECTID: {0: 0, 3: 33, 4: 333}
17
17
  * component: ['Windows', 'Frames', 'Wall', 'Roof', 'Skylight']
18
18
  * Result:
19
- * OBJECTID: [0, 1, 5]
20
- * component: ['Windows', 'Frames', 'null']
21
- * @param featureIds
19
+ * OBJECTID: [0, 33, 333]
20
+ * component: ['Windows', 'Roof', 'Skylight']
21
+ * @param featureIdsMap
22
22
  * @param propertyTable
23
23
  */
24
24
  export function flattenPropertyTableByFeatureIds(
25
- featureIds: number[],
25
+ featureIdsMap: Record<string, number>,
26
26
  propertyTable: FeatureTableJson
27
27
  ): FeatureTableJson {
28
28
  const resultPropertyTable: FeatureTableJson = {};
29
29
  for (const propertyName in propertyTable) {
30
30
  const properties = propertyTable[propertyName];
31
- resultPropertyTable[propertyName] = getPropertiesByFeatureIds(properties, featureIds);
31
+ resultPropertyTable[propertyName] = getPropertiesByFeatureIds(properties, featureIdsMap);
32
32
  }
33
33
 
34
34
  return resultPropertyTable;
@@ -37,14 +37,19 @@ export function flattenPropertyTableByFeatureIds(
37
37
  /**
38
38
  * Getting properties by featureId index
39
39
  * @param properties
40
- * @param featureIds
40
+ * @param featureIdsMap
41
41
  */
42
- function getPropertiesByFeatureIds(properties: any[], featureIds: number[]): any[] {
43
- const resultProperties: any = [];
44
-
45
- for (const featureId of featureIds) {
46
- const property = properties[featureId] || null;
47
- resultProperties.push(property);
42
+ function getPropertiesByFeatureIds(
43
+ properties: unknown[],
44
+ featureIdsMap: Record<string, number>
45
+ ): unknown[] {
46
+ const resultProperties: unknown[] = [];
47
+
48
+ if (properties) {
49
+ for (const featureIdKey in featureIdsMap) {
50
+ const property = properties[featureIdKey] || null;
51
+ resultProperties.push(property);
52
+ }
48
53
  }
49
54
 
50
55
  return resultProperties;
@@ -64,7 +69,7 @@ export function checkPropertiesLength(
64
69
  let needFlatten = false;
65
70
 
66
71
  for (const attribute of Object.values(propertyTable)) {
67
- if (featureIds.length !== attribute.length) {
72
+ if (!featureIds || !attribute || featureIds.length !== attribute.length) {
68
73
  needFlatten = true;
69
74
  }
70
75
  }
@@ -1,4 +1,9 @@
1
- import type {GeometryAttributes, ConvertedAttributes, GroupedByFeatureIdAttributes} from '../types';
1
+ import type {
2
+ GeometryAttributes,
3
+ ConvertedAttributes,
4
+ GroupedByFeatureIdAttributes,
5
+ GroupedAttributes
6
+ } from '../types';
2
7
  import {concatenateTypedArrays} from '@loaders.gl/loader-utils';
3
8
 
4
9
  const VALUES_PER_VERTEX = 3;
@@ -125,6 +130,11 @@ function makeAttributeObjects(attributes: GeometryAttributes): GroupedByFeatureI
125
130
  let colorsList = new Uint8Array(colors);
126
131
  let texCoordsList = new Float32Array(texCoords);
127
132
  let uvRegionsList = new Uint16Array(uvRegions);
133
+ let positionsOffset = 0;
134
+ let normalsOffset = 0;
135
+ let colorsOffset = 0;
136
+ let uvRegionsOffset = 0;
137
+ let texCoordsOffset = 0;
128
138
 
129
139
  for (let index = 0; index < featureIds.length; index++) {
130
140
  const startIndex = faceRange[index * 2];
@@ -138,21 +148,21 @@ function makeAttributeObjects(attributes: GeometryAttributes): GroupedByFeatureI
138
148
 
139
149
  groupedData.push({
140
150
  featureId: featureIds[index],
141
- positions: positionsList.slice(0, positionsCount),
142
- normals: normalsList.slice(0, normalsCount),
143
- colors: colorsList.slice(0, colorsCount),
144
- uvRegions: uvRegionsList.slice(0, uvRegionsCount),
145
- texCoords: texCoordsList.slice(0, texCoordsCount)
151
+ positions: positionsList.subarray(positionsOffset, positionsOffset + positionsCount),
152
+ normals: normalsList.subarray(normalsOffset, normalsOffset + normalsCount),
153
+ colors: colorsList.subarray(colorsOffset, colorsOffset + colorsCount),
154
+ uvRegions: uvRegionsList.subarray(uvRegionsOffset, uvRegionsOffset + uvRegionsCount),
155
+ texCoords: texCoordsList.subarray(texCoordsOffset, texCoordsOffset + texCoordsCount)
146
156
  });
147
157
 
148
- positionsList = positionsList.slice(positionsCount);
149
- normalsList = normalsList.slice(normalsCount);
150
- colorsList = colorsList.slice(colorsCount);
151
- uvRegionsList = uvRegionsList.slice(uvRegionsCount);
152
- texCoordsList = texCoordsList.slice(texCoordsCount);
158
+ positionsOffset += positionsCount;
159
+ normalsOffset += normalsCount;
160
+ colorsOffset += colorsCount;
161
+ uvRegionsOffset += uvRegionsCount;
162
+ texCoordsOffset += texCoordsCount;
153
163
  }
154
164
 
155
- return groupedData.sort((first, second) => first.featureId - second.featureId);
165
+ return groupedData;
156
166
  }
157
167
 
158
168
  /**
@@ -195,35 +205,32 @@ function getSliceAttributeCount(
195
205
  function unifyObjectsByFeatureId(
196
206
  sortedData: GroupedByFeatureIdAttributes[]
197
207
  ): GroupedByFeatureIdAttributes[] {
198
- const uniqueObjects: GroupedByFeatureIdAttributes[] = [];
199
-
200
- for (let index = 0; index < sortedData.length; index++) {
201
- const currentObject = sortedData[index];
202
- const existingObject = uniqueObjects.find((obj) => obj.featureId === currentObject.featureId);
203
-
208
+ const groupedMetadata: {
209
+ featureId: number;
210
+ attributes: GroupedByFeatureIdAttributes[];
211
+ }[] = [];
212
+ for (const data of sortedData) {
213
+ const existingObject = groupedMetadata.find((obj) => obj.featureId === data.featureId);
204
214
  if (existingObject) {
205
- existingObject.positions = concatenateTypedArrays(
206
- existingObject.positions,
207
- currentObject.positions
208
- );
209
- existingObject.normals = concatenateTypedArrays(
210
- existingObject.normals,
211
- currentObject.normals
212
- );
213
- existingObject.colors = concatenateTypedArrays(existingObject.colors, currentObject.colors);
214
- existingObject.texCoords = concatenateTypedArrays(
215
- existingObject.texCoords,
216
- currentObject.texCoords
217
- );
218
- existingObject.uvRegions = concatenateTypedArrays(
219
- existingObject.uvRegions,
220
- currentObject.uvRegions
221
- );
215
+ existingObject.attributes.push(data);
222
216
  } else {
223
- uniqueObjects.push(currentObject);
217
+ groupedMetadata.push({
218
+ featureId: data.featureId,
219
+ attributes: [data]
220
+ });
224
221
  }
225
222
  }
226
223
 
224
+ const uniqueObjects: GroupedByFeatureIdAttributes[] = [];
225
+ for (const metatada of groupedMetadata) {
226
+ const attributes = concatenateAttributes(metatada.attributes);
227
+
228
+ uniqueObjects.push({
229
+ featureId: metatada.featureId,
230
+ ...attributes
231
+ });
232
+ }
233
+
227
234
  return uniqueObjects;
228
235
  }
229
236
 
@@ -238,12 +245,6 @@ function groupAttributesAndRangesByFeatureId(
238
245
  ): GeometryAttributes {
239
246
  const firstAttributeObject = unifiedObjects[0];
240
247
  const featureIds = [firstAttributeObject.featureId || 0];
241
-
242
- let positions = new Float32Array(firstAttributeObject.positions);
243
- let normals = new Float32Array(firstAttributeObject.normals);
244
- let colors = new Uint8Array(firstAttributeObject.colors);
245
- let uvRegions = new Uint16Array(firstAttributeObject.uvRegions);
246
- let texCoords = new Float32Array(firstAttributeObject.texCoords);
247
248
  const range = [0];
248
249
 
249
250
  let objIndex = 0;
@@ -253,12 +254,6 @@ function groupAttributesAndRangesByFeatureId(
253
254
  const currentAttributesObject = unifiedObjects[index];
254
255
  featureIds.push(currentAttributesObject.featureId || 0);
255
256
 
256
- positions = concatenateTypedArrays(positions, currentAttributesObject.positions);
257
- normals = concatenateTypedArrays(normals, currentAttributesObject.normals);
258
- colors = concatenateTypedArrays(colors, currentAttributesObject.colors);
259
- uvRegions = concatenateTypedArrays(uvRegions, currentAttributesObject.uvRegions);
260
- texCoords = concatenateTypedArrays(texCoords, currentAttributesObject.texCoords);
261
-
262
257
  const groupedObject = unifiedObjects[objIndex];
263
258
  range.push(groupedObject.positions.length / POSITIONS_AND_NORMALS_PER_TRIANGLE - 1 + sum);
264
259
  range.push(groupedObject.positions.length / POSITIONS_AND_NORMALS_PER_TRIANGLE + sum);
@@ -267,8 +262,43 @@ function groupAttributesAndRangesByFeatureId(
267
262
  objIndex += 1;
268
263
  }
269
264
 
270
- range.push(positions.length / POSITIONS_AND_NORMALS_PER_TRIANGLE - 1);
265
+ const attributes = concatenateAttributes(unifiedObjects);
266
+
267
+ range.push(attributes.positions.length / POSITIONS_AND_NORMALS_PER_TRIANGLE - 1);
271
268
 
272
269
  const faceRange = new Uint32Array(range);
273
- return {faceRange, featureIds, positions, normals, colors, uvRegions, texCoords, featureCount};
270
+ return {faceRange, featureIds, featureCount, ...attributes};
271
+ }
272
+
273
+ /**
274
+ * Concatenate attributes typed arrays
275
+ * @param attributes - grouped by featureId typed arrays
276
+ * @returns - concatenated typed array list
277
+ */
278
+ function concatenateAttributes(attributes: GroupedByFeatureIdAttributes[]): GroupedAttributes {
279
+ const positionGroups = attributes.map(({positions}) => positions);
280
+ const positions =
281
+ positionGroups.length > 1 ? concatenateTypedArrays(...positionGroups) : positionGroups[0];
282
+
283
+ const normalGroups = attributes.map(({normals}) => normals);
284
+ const normals =
285
+ normalGroups.length > 1 ? concatenateTypedArrays(...normalGroups) : normalGroups[0];
286
+
287
+ const colorGroups = attributes.map(({colors}) => colors);
288
+ const colors = colorGroups.length > 1 ? concatenateTypedArrays(...colorGroups) : colorGroups[0];
289
+
290
+ const texCoordGroups = attributes.map(({texCoords}) => texCoords);
291
+ const texCoords =
292
+ texCoordGroups.length > 1 ? concatenateTypedArrays(...texCoordGroups) : texCoordGroups[0];
293
+
294
+ const uvRegionGroups = attributes.map(({uvRegions}) => uvRegions);
295
+ const uvRegions =
296
+ uvRegionGroups.length > 1 ? concatenateTypedArrays(...uvRegionGroups) : uvRegionGroups[0];
297
+ return {
298
+ positions,
299
+ normals,
300
+ colors,
301
+ texCoords,
302
+ uvRegions
303
+ };
274
304
  }