@ifc-lite/pointcloud 0.2.0

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 (87) hide show
  1. package/LICENSE +373 -0
  2. package/README.md +26 -0
  3. package/dist/formats/e57.d.ts +129 -0
  4. package/dist/formats/e57.d.ts.map +1 -0
  5. package/dist/formats/e57.js +495 -0
  6. package/dist/formats/e57.js.map +1 -0
  7. package/dist/formats/ifcx-points.d.ts +26 -0
  8. package/dist/formats/ifcx-points.d.ts.map +1 -0
  9. package/dist/formats/ifcx-points.js +134 -0
  10. package/dist/formats/ifcx-points.js.map +1 -0
  11. package/dist/formats/las.d.ts +54 -0
  12. package/dist/formats/las.d.ts.map +1 -0
  13. package/dist/formats/las.js +203 -0
  14. package/dist/formats/las.js.map +1 -0
  15. package/dist/formats/pcd.d.ts +3 -0
  16. package/dist/formats/pcd.d.ts.map +1 -0
  17. package/dist/formats/pcd.js +302 -0
  18. package/dist/formats/pcd.js.map +1 -0
  19. package/dist/formats/ply.d.ts +40 -0
  20. package/dist/formats/ply.d.ts.map +1 -0
  21. package/dist/formats/ply.js +250 -0
  22. package/dist/formats/ply.js.map +1 -0
  23. package/dist/from-ifcx-attributes.d.ts +10 -0
  24. package/dist/from-ifcx-attributes.d.ts.map +1 -0
  25. package/dist/from-ifcx-attributes.js +49 -0
  26. package/dist/from-ifcx-attributes.js.map +1 -0
  27. package/dist/index.d.ts +26 -0
  28. package/dist/index.d.ts.map +1 -0
  29. package/dist/index.js +21 -0
  30. package/dist/index.js.map +1 -0
  31. package/dist/lzf.d.ts +10 -0
  32. package/dist/lzf.d.ts.map +1 -0
  33. package/dist/lzf.js +64 -0
  34. package/dist/lzf.js.map +1 -0
  35. package/dist/streaming/blob-source.d.ts +15 -0
  36. package/dist/streaming/blob-source.d.ts.map +1 -0
  37. package/dist/streaming/blob-source.js +30 -0
  38. package/dist/streaming/blob-source.js.map +1 -0
  39. package/dist/streaming/decode-worker.d.ts +2 -0
  40. package/dist/streaming/decode-worker.d.ts.map +1 -0
  41. package/dist/streaming/decode-worker.js +131 -0
  42. package/dist/streaming/decode-worker.js.map +1 -0
  43. package/dist/streaming/e57-source.d.ts +17 -0
  44. package/dist/streaming/e57-source.d.ts.map +1 -0
  45. package/dist/streaming/e57-source.js +83 -0
  46. package/dist/streaming/e57-source.js.map +1 -0
  47. package/dist/streaming/host.d.ts +54 -0
  48. package/dist/streaming/host.d.ts.map +1 -0
  49. package/dist/streaming/host.js +120 -0
  50. package/dist/streaming/host.js.map +1 -0
  51. package/dist/streaming/las-source.d.ts +28 -0
  52. package/dist/streaming/las-source.d.ts.map +1 -0
  53. package/dist/streaming/las-source.js +117 -0
  54. package/dist/streaming/las-source.js.map +1 -0
  55. package/dist/streaming/laz-source.d.ts +35 -0
  56. package/dist/streaming/laz-source.d.ts.map +1 -0
  57. package/dist/streaming/laz-source.js +205 -0
  58. package/dist/streaming/laz-source.js.map +1 -0
  59. package/dist/streaming/pcd-source.d.ts +25 -0
  60. package/dist/streaming/pcd-source.d.ts.map +1 -0
  61. package/dist/streaming/pcd-source.js +86 -0
  62. package/dist/streaming/pcd-source.js.map +1 -0
  63. package/dist/streaming/ply-source.d.ts +26 -0
  64. package/dist/streaming/ply-source.d.ts.map +1 -0
  65. package/dist/streaming/ply-source.js +98 -0
  66. package/dist/streaming/ply-source.js.map +1 -0
  67. package/dist/streaming/protocol.d.ts +62 -0
  68. package/dist/streaming/protocol.d.ts.map +1 -0
  69. package/dist/streaming/protocol.js +45 -0
  70. package/dist/streaming/protocol.js.map +1 -0
  71. package/dist/streaming/types.d.ts +41 -0
  72. package/dist/streaming/types.d.ts.map +1 -0
  73. package/dist/streaming/types.js +5 -0
  74. package/dist/streaming/types.js.map +1 -0
  75. package/dist/streaming/worker-client.d.ts +20 -0
  76. package/dist/streaming/worker-client.d.ts.map +1 -0
  77. package/dist/streaming/worker-client.js +152 -0
  78. package/dist/streaming/worker-client.js.map +1 -0
  79. package/dist/types.d.ts +36 -0
  80. package/dist/types.d.ts.map +1 -0
  81. package/dist/types.js +5 -0
  82. package/dist/types.js.map +1 -0
  83. package/dist/xml-mini.d.ts +29 -0
  84. package/dist/xml-mini.d.ts.map +1 -0
  85. package/dist/xml-mini.js +181 -0
  86. package/dist/xml-mini.js.map +1 -0
  87. package/package.json +51 -0
@@ -0,0 +1,302 @@
1
+ /* This Source Code Form is subject to the terms of the Mozilla Public
2
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
3
+ * file, You can obtain one at https://mozilla.org/MPL/2.0/. */
4
+ /**
5
+ * PCD (Point Cloud Data, PCL library format) decoder.
6
+ *
7
+ * Supports DATA ascii / binary / binary_compressed (LZF). Extracts at minimum
8
+ * x/y/z (required) and optionally rgb (PCL packs RGB as a bit-reinterpreted
9
+ * 32-bit field — we read the bits regardless of the declared TYPE).
10
+ *
11
+ * binary_compressed payload layout: u32-LE compressedSize, u32-LE
12
+ * uncompressedSize, then LZF-compressed data. The decompressed body is
13
+ * COLUMN-major (SoA), unlike `binary` which is row-major (AoS).
14
+ */
15
+ import { decompressLZF } from '../lzf.js';
16
+ const TEXT_DECODER = new TextDecoder();
17
+ export function decodePcd(buffer) {
18
+ const header = parseHeader(buffer);
19
+ let positions;
20
+ let colors;
21
+ if (header.data === 'ascii') {
22
+ ({ positions, colors } = decodeAscii(buffer, header));
23
+ }
24
+ else if (header.data === 'binary') {
25
+ ({ positions, colors } = decodeBinary(buffer, header));
26
+ }
27
+ else {
28
+ ({ positions, colors } = decodeBinaryCompressed(buffer, header));
29
+ }
30
+ return {
31
+ positions,
32
+ colors,
33
+ pointCount: header.pointCount,
34
+ bbox: computeBBox(positions),
35
+ };
36
+ }
37
+ // ─── header parser ──────────────────────────────────────────────────────────
38
+ function parseHeader(buffer) {
39
+ // Header is ASCII, terminated by the line beginning with "DATA ".
40
+ // 64 KB covers files with long comments / metadata while still bounding
41
+ // the worst-case scan; larger headers are unrealistic in practice and
42
+ // rejecting them is preferable to scanning a multi-GB body.
43
+ const probeLen = Math.min(65536, buffer.length);
44
+ const probe = TEXT_DECODER.decode(buffer.subarray(0, probeLen));
45
+ const dataIdx = probe.search(/^DATA\s+(\S+)/m);
46
+ if (dataIdx < 0) {
47
+ throw new Error('PCD: missing DATA line in header (scanned first ' + probeLen + ' bytes)');
48
+ }
49
+ const headerText = probe.slice(0, dataIdx);
50
+ const dataLineMatch = probe.slice(dataIdx).match(/^DATA\s+(\S+)\s*\n/);
51
+ if (!dataLineMatch) {
52
+ throw new Error('PCD: malformed DATA line');
53
+ }
54
+ const dataKind = dataLineMatch[1].toLowerCase();
55
+ if (dataKind !== 'ascii' && dataKind !== 'binary' && dataKind !== 'binary_compressed') {
56
+ throw new Error(`PCD: unsupported DATA kind "${dataKind}"`);
57
+ }
58
+ const bodyOffset = dataIdx + dataLineMatch[0].length;
59
+ // Parse named tokens out of the header.
60
+ const tokens = new Map();
61
+ for (const rawLine of headerText.split('\n')) {
62
+ const line = rawLine.replace(/#.*$/, '').trim();
63
+ if (!line)
64
+ continue;
65
+ const parts = line.split(/\s+/);
66
+ const key = parts[0].toUpperCase();
67
+ tokens.set(key, parts.slice(1));
68
+ }
69
+ const fieldNames = tokens.get('FIELDS') ?? [];
70
+ const sizes = (tokens.get('SIZE') ?? []).map(Number);
71
+ const types = (tokens.get('TYPE') ?? []);
72
+ const counts = (tokens.get('COUNT') ?? []).map(Number);
73
+ const widthRaw = tokens.get('WIDTH')?.[0];
74
+ const heightRaw = tokens.get('HEIGHT')?.[0];
75
+ const pointsRaw = tokens.get('POINTS')?.[0];
76
+ if (fieldNames.length === 0)
77
+ throw new Error('PCD: missing FIELDS');
78
+ if (sizes.length !== fieldNames.length)
79
+ throw new Error('PCD: SIZE/FIELDS length mismatch');
80
+ if (types.length !== fieldNames.length)
81
+ throw new Error('PCD: TYPE/FIELDS length mismatch');
82
+ const fields = [];
83
+ let stride = 0;
84
+ for (let i = 0; i < fieldNames.length; i++) {
85
+ const count = counts[i] ?? 1;
86
+ const size = sizes[i];
87
+ const type = types[i];
88
+ if (type !== 'F' && type !== 'I' && type !== 'U') {
89
+ throw new Error(`PCD: unsupported field TYPE "${type}"`);
90
+ }
91
+ fields.push({ name: fieldNames[i], size, type, count, offset: stride });
92
+ stride += size * count;
93
+ }
94
+ const width = widthRaw !== undefined ? parseInt(widthRaw, 10) : 0;
95
+ const height = heightRaw !== undefined ? parseInt(heightRaw, 10) : 1;
96
+ const pointCount = pointsRaw !== undefined ? parseInt(pointsRaw, 10) : width * height;
97
+ if (!Number.isFinite(pointCount) || pointCount <= 0) {
98
+ throw new Error('PCD: invalid point count');
99
+ }
100
+ return {
101
+ version: tokens.get('VERSION')?.[0] ?? '0.7',
102
+ fields,
103
+ width,
104
+ height,
105
+ pointCount,
106
+ pointStride: stride,
107
+ data: dataKind,
108
+ bodyOffset,
109
+ };
110
+ }
111
+ function planChannels(header) {
112
+ const plan = {};
113
+ for (const field of header.fields) {
114
+ const name = field.name.toLowerCase();
115
+ if (name === 'x')
116
+ plan.xField = field;
117
+ else if (name === 'y')
118
+ plan.yField = field;
119
+ else if (name === 'z')
120
+ plan.zField = field;
121
+ else if (name === 'rgb' || name === 'rgba')
122
+ plan.rgbField = field;
123
+ }
124
+ if (!plan.xField || !plan.yField || !plan.zField) {
125
+ throw new Error('PCD: x/y/z fields are required');
126
+ }
127
+ return plan;
128
+ }
129
+ function decodeAscii(buffer, header) {
130
+ const plan = planChannels(header);
131
+ const text = TEXT_DECODER.decode(buffer.subarray(header.bodyOffset));
132
+ const positions = new Float32Array(header.pointCount * 3);
133
+ const colors = plan.rgbField ? new Float32Array(header.pointCount * 3) : undefined;
134
+ // Column index of x/y/z/rgb in the ascii row order (ascii rows preserve
135
+ // FIELDS order; multi-count fields are flattened).
136
+ const colMap = buildAsciiColumnMap(header, plan);
137
+ let writeIdx = 0;
138
+ let lineStart = 0;
139
+ let pointsRead = 0;
140
+ while (pointsRead < header.pointCount && lineStart < text.length) {
141
+ let lineEnd = text.indexOf('\n', lineStart);
142
+ if (lineEnd < 0)
143
+ lineEnd = text.length;
144
+ const line = text.slice(lineStart, lineEnd).trim();
145
+ lineStart = lineEnd + 1;
146
+ if (!line)
147
+ continue;
148
+ const parts = line.split(/\s+/);
149
+ positions[writeIdx * 3] = Number(parts[colMap.xCol]);
150
+ positions[writeIdx * 3 + 1] = Number(parts[colMap.yCol]);
151
+ positions[writeIdx * 3 + 2] = Number(parts[colMap.zCol]);
152
+ if (colors && colMap.rgbCol >= 0) {
153
+ const packed = parsePackedRgb(parts[colMap.rgbCol], plan.rgbField);
154
+ colors[writeIdx * 3] = ((packed >> 16) & 0xff) / 255;
155
+ colors[writeIdx * 3 + 1] = ((packed >> 8) & 0xff) / 255;
156
+ colors[writeIdx * 3 + 2] = (packed & 0xff) / 255;
157
+ }
158
+ writeIdx++;
159
+ pointsRead++;
160
+ }
161
+ if (pointsRead !== header.pointCount) {
162
+ throw new Error(`PCD ascii: expected ${header.pointCount} points, got ${pointsRead}`);
163
+ }
164
+ return { positions, colors };
165
+ }
166
+ function buildAsciiColumnMap(header, plan) {
167
+ let col = 0;
168
+ let xCol = -1;
169
+ let yCol = -1;
170
+ let zCol = -1;
171
+ let rgbCol = -1;
172
+ for (const field of header.fields) {
173
+ if (field === plan.xField)
174
+ xCol = col;
175
+ if (field === plan.yField)
176
+ yCol = col;
177
+ if (field === plan.zField)
178
+ zCol = col;
179
+ if (field === plan.rgbField)
180
+ rgbCol = col;
181
+ col += field.count;
182
+ }
183
+ return { xCol, yCol, zCol, rgbCol };
184
+ }
185
+ function decodeBinary(buffer, header) {
186
+ const plan = planChannels(header);
187
+ const view = new DataView(buffer.buffer, buffer.byteOffset + header.bodyOffset, header.pointCount * header.pointStride);
188
+ const positions = new Float32Array(header.pointCount * 3);
189
+ const colors = plan.rgbField ? new Float32Array(header.pointCount * 3) : undefined;
190
+ for (let i = 0; i < header.pointCount; i++) {
191
+ const base = i * header.pointStride;
192
+ positions[i * 3] = readScalar(view, base + plan.xField.offset, plan.xField);
193
+ positions[i * 3 + 1] = readScalar(view, base + plan.yField.offset, plan.yField);
194
+ positions[i * 3 + 2] = readScalar(view, base + plan.zField.offset, plan.zField);
195
+ if (colors && plan.rgbField) {
196
+ const packed = view.getUint32(base + plan.rgbField.offset, true);
197
+ colors[i * 3] = ((packed >> 16) & 0xff) / 255;
198
+ colors[i * 3 + 1] = ((packed >> 8) & 0xff) / 255;
199
+ colors[i * 3 + 2] = (packed & 0xff) / 255;
200
+ }
201
+ }
202
+ return { positions, colors };
203
+ }
204
+ function decodeBinaryCompressed(buffer, header) {
205
+ if (buffer.length < header.bodyOffset + 8) {
206
+ throw new Error('PCD binary_compressed: truncated size header');
207
+ }
208
+ const sizeView = new DataView(buffer.buffer, buffer.byteOffset + header.bodyOffset, 8);
209
+ const compressedSize = sizeView.getUint32(0, true);
210
+ const uncompressedSize = sizeView.getUint32(4, true);
211
+ const expectedUncompressed = header.pointCount * header.pointStride;
212
+ if (uncompressedSize !== expectedUncompressed) {
213
+ throw new Error(`PCD binary_compressed: declared uncompressed=${uncompressedSize} ` +
214
+ `does not match fields*points=${expectedUncompressed}`);
215
+ }
216
+ const compressed = buffer.subarray(header.bodyOffset + 8, header.bodyOffset + 8 + compressedSize);
217
+ const raw = decompressLZF(compressed, uncompressedSize);
218
+ // SoA layout: contiguous block per field. Compute each field's start.
219
+ const plan = planChannels(header);
220
+ const fieldStart = new Map();
221
+ let cursor = 0;
222
+ for (const field of header.fields) {
223
+ fieldStart.set(field, cursor);
224
+ cursor += header.pointCount * field.size * field.count;
225
+ }
226
+ const view = new DataView(raw.buffer, raw.byteOffset, raw.byteLength);
227
+ const positions = new Float32Array(header.pointCount * 3);
228
+ const colors = plan.rgbField ? new Float32Array(header.pointCount * 3) : undefined;
229
+ const xBase = fieldStart.get(plan.xField);
230
+ const yBase = fieldStart.get(plan.yField);
231
+ const zBase = fieldStart.get(plan.zField);
232
+ const rgbBase = plan.rgbField ? fieldStart.get(plan.rgbField) : 0;
233
+ for (let i = 0; i < header.pointCount; i++) {
234
+ positions[i * 3] = readScalar(view, xBase + i * plan.xField.size, plan.xField);
235
+ positions[i * 3 + 1] = readScalar(view, yBase + i * plan.yField.size, plan.yField);
236
+ positions[i * 3 + 2] = readScalar(view, zBase + i * plan.zField.size, plan.zField);
237
+ if (colors && plan.rgbField) {
238
+ const packed = view.getUint32(rgbBase + i * plan.rgbField.size, true);
239
+ colors[i * 3] = ((packed >> 16) & 0xff) / 255;
240
+ colors[i * 3 + 1] = ((packed >> 8) & 0xff) / 255;
241
+ colors[i * 3 + 2] = (packed & 0xff) / 255;
242
+ }
243
+ }
244
+ return { positions, colors };
245
+ }
246
+ // ─── helpers ────────────────────────────────────────────────────────────────
247
+ function readScalar(view, offset, field) {
248
+ if (field.type === 'F') {
249
+ return field.size === 8 ? view.getFloat64(offset, true) : view.getFloat32(offset, true);
250
+ }
251
+ if (field.type === 'U') {
252
+ if (field.size === 1)
253
+ return view.getUint8(offset);
254
+ if (field.size === 2)
255
+ return view.getUint16(offset, true);
256
+ if (field.size === 4)
257
+ return view.getUint32(offset, true);
258
+ }
259
+ else {
260
+ if (field.size === 1)
261
+ return view.getInt8(offset);
262
+ if (field.size === 2)
263
+ return view.getInt16(offset, true);
264
+ if (field.size === 4)
265
+ return view.getInt32(offset, true);
266
+ }
267
+ throw new Error(`PCD: unsupported field width ${field.size} for type ${field.type}`);
268
+ }
269
+ const PARSE_BUFFER = new ArrayBuffer(4);
270
+ const PARSE_F32 = new Float32Array(PARSE_BUFFER);
271
+ const PARSE_U32 = new Uint32Array(PARSE_BUFFER);
272
+ function parsePackedRgb(token, field) {
273
+ // PCL stores RGB as a uint32 (0x00RRGGBB) bit-reinterpreted to float and
274
+ // emitted via printf("%g"). We have to round-trip the float bits back to
275
+ // an integer to recover the channel bytes.
276
+ if (field.type === 'F') {
277
+ PARSE_F32[0] = Number(token);
278
+ return PARSE_U32[0];
279
+ }
280
+ return Number(token) >>> 0;
281
+ }
282
+ function computeBBox(positions) {
283
+ let minX = Infinity, minY = Infinity, minZ = Infinity;
284
+ let maxX = -Infinity, maxY = -Infinity, maxZ = -Infinity;
285
+ for (let i = 0; i < positions.length; i += 3) {
286
+ const x = positions[i], y = positions[i + 1], z = positions[i + 2];
287
+ if (x < minX)
288
+ minX = x;
289
+ if (x > maxX)
290
+ maxX = x;
291
+ if (y < minY)
292
+ minY = y;
293
+ if (y > maxY)
294
+ maxY = y;
295
+ if (z < minZ)
296
+ minZ = z;
297
+ if (z > maxZ)
298
+ maxZ = z;
299
+ }
300
+ return { min: [minX, minY, minZ], max: [maxX, maxY, maxZ] };
301
+ }
302
+ //# sourceMappingURL=pcd.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"pcd.js","sourceRoot":"","sources":["../../src/formats/pcd.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,40 @@
1
+ /**
2
+ * PLY (Stanford Polygon) reader — point clouds only.
3
+ *
4
+ * Supports `format ascii 1.0`, `format binary_little_endian 1.0`, and
5
+ * `format binary_big_endian 1.0`. Reads the `vertex` element exclusively;
6
+ * `face` and other elements are skipped (they're meaningful for surface
7
+ * meshes but not for the scan-style files this viewer ingests).
8
+ *
9
+ * Position fields (x/y/z) are required. RGB (r/g/b or red/green/blue,
10
+ * uchar) and intensity (intensity, uchar/ushort/float) are optional and
11
+ * surfaced when present. Returns a single `DecodedPointChunk` — large
12
+ * .ply files (>25M points) get bounded by `streamPointCloud`'s memory
13
+ * cap which downsamples upstream.
14
+ */
15
+ import type { DecodedPointChunk } from '../types.js';
16
+ interface PropertyDecl {
17
+ name: string;
18
+ type: string;
19
+ size: number;
20
+ /** Byte offset within a single vertex record (binary mode only). */
21
+ offset: number;
22
+ }
23
+ interface ElementDecl {
24
+ name: string;
25
+ count: number;
26
+ properties: PropertyDecl[];
27
+ /** Bytes per record (binary mode); unused for ascii. */
28
+ recordSize: number;
29
+ }
30
+ export interface PlyHeader {
31
+ format: 'ascii' | 'binary_little_endian' | 'binary_big_endian';
32
+ version: string;
33
+ elements: ElementDecl[];
34
+ /** Byte offset where the body data starts. */
35
+ bodyOffset: number;
36
+ }
37
+ export declare function parsePlyHeader(buffer: Uint8Array): PlyHeader;
38
+ export declare function decodePly(buffer: Uint8Array): DecodedPointChunk;
39
+ export {};
40
+ //# sourceMappingURL=ply.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ply.d.ts","sourceRoot":"","sources":["../../src/formats/ply.ts"],"names":[],"mappings":"AAIA;;;;;;;;;;;;;GAaG;AAEH,OAAO,KAAK,EAAE,iBAAiB,EAAkB,MAAM,aAAa,CAAC;AAUrE,UAAU,YAAY;IACpB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,oEAAoE;IACpE,MAAM,EAAE,MAAM,CAAC;CAChB;AAED,UAAU,WAAW;IACnB,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;IACd,UAAU,EAAE,YAAY,EAAE,CAAC;IAC3B,wDAAwD;IACxD,UAAU,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,WAAW,SAAS;IACxB,MAAM,EAAE,OAAO,GAAG,sBAAsB,GAAG,mBAAmB,CAAC;IAC/D,OAAO,EAAE,MAAM,CAAC;IAChB,QAAQ,EAAE,WAAW,EAAE,CAAC;IACxB,8CAA8C;IAC9C,UAAU,EAAE,MAAM,CAAC;CACpB;AAID,wBAAgB,cAAc,CAAC,MAAM,EAAE,UAAU,GAAG,SAAS,CA6E5D;AAED,wBAAgB,SAAS,CAAC,MAAM,EAAE,UAAU,GAAG,iBAAiB,CAqD/D"}
@@ -0,0 +1,250 @@
1
+ /* This Source Code Form is subject to the terms of the Mozilla Public
2
+ * License, v. 2.0. If a copy of the MPL was not distributed with this
3
+ * file, You can obtain one at https://mozilla.org/MPL/2.0/. */
4
+ /** Name → byte size for the PLY-defined scalar types. */
5
+ const TYPE_SIZES = {
6
+ char: 1, int8: 1, uchar: 1, uint8: 1,
7
+ short: 2, int16: 2, ushort: 2, uint16: 2,
8
+ int: 4, int32: 4, uint: 4, uint32: 4,
9
+ float: 4, float32: 4, double: 8, float64: 8,
10
+ };
11
+ const TEXT_DECODER = new TextDecoder();
12
+ export function parsePlyHeader(buffer) {
13
+ // The header is ASCII. Find the line that says `end_header`. PLY files
14
+ // never have headers larger than a few KB even with many properties;
15
+ // 64 KB is a generous probe.
16
+ const probeLen = Math.min(65536, buffer.length);
17
+ const probe = TEXT_DECODER.decode(buffer.subarray(0, probeLen));
18
+ if (!probe.startsWith('ply')) {
19
+ throw new Error('PLY: missing magic — file does not start with "ply"');
20
+ }
21
+ const endIdx = probe.indexOf('end_header');
22
+ if (endIdx < 0) {
23
+ throw new Error('PLY: missing end_header line in first ' + probeLen + ' bytes');
24
+ }
25
+ // Body starts after the next newline that follows end_header.
26
+ const newline = probe.indexOf('\n', endIdx);
27
+ if (newline < 0) {
28
+ throw new Error('PLY: end_header line not terminated by newline');
29
+ }
30
+ const headerText = probe.slice(0, newline + 1);
31
+ const bodyOffset = newline + 1;
32
+ const lines = headerText.split('\n').map((l) => l.trim()).filter((l) => l.length > 0);
33
+ let format = null;
34
+ let version = '1.0';
35
+ const elements = [];
36
+ let current = null;
37
+ for (const line of lines) {
38
+ if (line === 'ply' || line === 'end_header')
39
+ continue;
40
+ if (line.startsWith('comment'))
41
+ continue;
42
+ if (line.startsWith('obj_info'))
43
+ continue;
44
+ if (line.startsWith('format ')) {
45
+ const parts = line.split(/\s+/);
46
+ const f = parts[1];
47
+ version = parts[2] ?? '1.0';
48
+ if (f === 'ascii' || f === 'binary_little_endian' || f === 'binary_big_endian') {
49
+ format = f;
50
+ }
51
+ else {
52
+ throw new Error(`PLY: unsupported format "${f}"`);
53
+ }
54
+ continue;
55
+ }
56
+ if (line.startsWith('element ')) {
57
+ const parts = line.split(/\s+/);
58
+ current = {
59
+ name: parts[1],
60
+ count: parseInt(parts[2], 10),
61
+ properties: [],
62
+ recordSize: 0,
63
+ };
64
+ elements.push(current);
65
+ continue;
66
+ }
67
+ if (line.startsWith('property ')) {
68
+ if (!current) {
69
+ throw new Error(`PLY: property declared before any element: "${line}"`);
70
+ }
71
+ const parts = line.split(/\s+/);
72
+ // Skip list properties (face indices etc.) — we don't render meshes.
73
+ if (parts[1] === 'list')
74
+ continue;
75
+ const type = parts[1];
76
+ const name = parts[2];
77
+ const size = TYPE_SIZES[type];
78
+ if (size === undefined) {
79
+ throw new Error(`PLY: unknown property type "${type}"`);
80
+ }
81
+ current.properties.push({ name, type, size, offset: current.recordSize });
82
+ current.recordSize += size;
83
+ continue;
84
+ }
85
+ }
86
+ if (!format)
87
+ throw new Error('PLY: missing `format` line in header');
88
+ if (!elements.some((e) => e.name === 'vertex')) {
89
+ throw new Error('PLY: missing `vertex` element');
90
+ }
91
+ return { format, version, elements, bodyOffset };
92
+ }
93
+ export function decodePly(buffer) {
94
+ const header = parsePlyHeader(buffer);
95
+ const vertex = header.elements.find((e) => e.name === 'vertex');
96
+ if (!vertex)
97
+ throw new Error('PLY: no vertex element');
98
+ // Both decoders start at header.bodyOffset, so vertex MUST be the first
99
+ // element. Files that declare another element first would silently
100
+ // produce garbage point data otherwise. Reject deterministically.
101
+ if (header.elements[0] !== vertex) {
102
+ throw new Error(`PLY: vertex element must appear first; saw "${header.elements[0]?.name}" first`);
103
+ }
104
+ const xProp = vertex.properties.find((p) => p.name === 'x');
105
+ const yProp = vertex.properties.find((p) => p.name === 'y');
106
+ const zProp = vertex.properties.find((p) => p.name === 'z');
107
+ if (!xProp || !yProp || !zProp) {
108
+ throw new Error('PLY: vertex element must define x, y, z properties');
109
+ }
110
+ const rProp = vertex.properties.find((p) => p.name === 'red' || p.name === 'r');
111
+ const gProp = vertex.properties.find((p) => p.name === 'green' || p.name === 'g');
112
+ const bProp = vertex.properties.find((p) => p.name === 'blue' || p.name === 'b');
113
+ const hasRgb = !!(rProp && gProp && bProp);
114
+ const intensityProp = vertex.properties.find((p) => p.name === 'intensity' || p.name === 'scalar_Intensity');
115
+ const count = vertex.count;
116
+ const positions = new Float32Array(count * 3);
117
+ const colors = hasRgb ? new Float32Array(count * 3) : undefined;
118
+ const intensities = intensityProp ? new Uint16Array(count) : undefined;
119
+ if (header.format === 'ascii') {
120
+ decodeAsciiBody(buffer, header, vertex, positions, colors, intensities);
121
+ }
122
+ else {
123
+ decodeBinaryBody(buffer, header, vertex, positions, colors, intensities, header.format === 'binary_little_endian');
124
+ }
125
+ return {
126
+ positions,
127
+ colors,
128
+ intensities,
129
+ pointCount: count,
130
+ bbox: computeBBox(positions),
131
+ };
132
+ }
133
+ // ─── ascii body ─────────────────────────────────────────────────────────────
134
+ function decodeAsciiBody(buffer, header, vertex, positions, colors, intensities) {
135
+ // Decode just the vertex part of the body (other elements come after).
136
+ // For ascii, each line = one vertex (in the order properties were
137
+ // declared).
138
+ const text = TEXT_DECODER.decode(buffer.subarray(header.bodyOffset));
139
+ const xCol = vertex.properties.findIndex((p) => p.name === 'x');
140
+ const yCol = vertex.properties.findIndex((p) => p.name === 'y');
141
+ const zCol = vertex.properties.findIndex((p) => p.name === 'z');
142
+ const rCol = vertex.properties.findIndex((p) => p.name === 'red' || p.name === 'r');
143
+ const gCol = vertex.properties.findIndex((p) => p.name === 'green' || p.name === 'g');
144
+ const bCol = vertex.properties.findIndex((p) => p.name === 'blue' || p.name === 'b');
145
+ const iCol = vertex.properties.findIndex((p) => p.name === 'intensity' || p.name === 'scalar_Intensity');
146
+ let lineStart = 0;
147
+ let written = 0;
148
+ while (written < vertex.count && lineStart < text.length) {
149
+ let lineEnd = text.indexOf('\n', lineStart);
150
+ if (lineEnd < 0)
151
+ lineEnd = text.length;
152
+ const line = text.slice(lineStart, lineEnd).trim();
153
+ lineStart = lineEnd + 1;
154
+ if (!line)
155
+ continue;
156
+ const parts = line.split(/\s+/);
157
+ positions[written * 3] = Number(parts[xCol]);
158
+ positions[written * 3 + 1] = Number(parts[yCol]);
159
+ positions[written * 3 + 2] = Number(parts[zCol]);
160
+ if (colors && rCol >= 0 && gCol >= 0 && bCol >= 0) {
161
+ colors[written * 3] = clamp01(Number(parts[rCol]) / 255);
162
+ colors[written * 3 + 1] = clamp01(Number(parts[gCol]) / 255);
163
+ colors[written * 3 + 2] = clamp01(Number(parts[bCol]) / 255);
164
+ }
165
+ if (intensities && iCol >= 0) {
166
+ intensities[written] = Math.min(65535, Math.max(0, Number(parts[iCol]) | 0));
167
+ }
168
+ written++;
169
+ }
170
+ if (written !== vertex.count) {
171
+ throw new Error(`PLY ascii: expected ${vertex.count} vertex lines, got ${written}`);
172
+ }
173
+ }
174
+ // ─── binary body ────────────────────────────────────────────────────────────
175
+ function decodeBinaryBody(buffer, header, vertex, positions, colors, intensities, littleEndian) {
176
+ const stride = vertex.recordSize;
177
+ const need = vertex.count * stride;
178
+ if (buffer.length < header.bodyOffset + need) {
179
+ throw new Error(`PLY binary: expected ${need} body bytes, got ${buffer.length - header.bodyOffset}`);
180
+ }
181
+ const view = new DataView(buffer.buffer, buffer.byteOffset + header.bodyOffset, need);
182
+ const xProp = vertex.properties.find((p) => p.name === 'x');
183
+ const yProp = vertex.properties.find((p) => p.name === 'y');
184
+ const zProp = vertex.properties.find((p) => p.name === 'z');
185
+ const rProp = colors ? vertex.properties.find((p) => p.name === 'red' || p.name === 'r') : undefined;
186
+ const gProp = colors ? vertex.properties.find((p) => p.name === 'green' || p.name === 'g') : undefined;
187
+ const bProp = colors ? vertex.properties.find((p) => p.name === 'blue' || p.name === 'b') : undefined;
188
+ const iProp = intensities
189
+ ? vertex.properties.find((p) => p.name === 'intensity' || p.name === 'scalar_Intensity')
190
+ : undefined;
191
+ for (let i = 0; i < vertex.count; i++) {
192
+ const base = i * stride;
193
+ positions[i * 3] = readScalar(view, base + xProp.offset, xProp, littleEndian);
194
+ positions[i * 3 + 1] = readScalar(view, base + yProp.offset, yProp, littleEndian);
195
+ positions[i * 3 + 2] = readScalar(view, base + zProp.offset, zProp, littleEndian);
196
+ if (colors && rProp && gProp && bProp) {
197
+ colors[i * 3] = clamp01(readScalar(view, base + rProp.offset, rProp, littleEndian) / 255);
198
+ colors[i * 3 + 1] = clamp01(readScalar(view, base + gProp.offset, gProp, littleEndian) / 255);
199
+ colors[i * 3 + 2] = clamp01(readScalar(view, base + bProp.offset, bProp, littleEndian) / 255);
200
+ }
201
+ if (intensities && iProp) {
202
+ intensities[i] = Math.min(65535, Math.max(0, readScalar(view, base + iProp.offset, iProp, littleEndian) | 0));
203
+ }
204
+ }
205
+ }
206
+ function readScalar(view, offset, prop, le) {
207
+ switch (prop.type) {
208
+ case 'char':
209
+ case 'int8': return view.getInt8(offset);
210
+ case 'uchar':
211
+ case 'uint8': return view.getUint8(offset);
212
+ case 'short':
213
+ case 'int16': return view.getInt16(offset, le);
214
+ case 'ushort':
215
+ case 'uint16': return view.getUint16(offset, le);
216
+ case 'int':
217
+ case 'int32': return view.getInt32(offset, le);
218
+ case 'uint':
219
+ case 'uint32': return view.getUint32(offset, le);
220
+ case 'float':
221
+ case 'float32': return view.getFloat32(offset, le);
222
+ case 'double':
223
+ case 'float64': return view.getFloat64(offset, le);
224
+ default: throw new Error(`PLY: cannot read scalar of type "${prop.type}"`);
225
+ }
226
+ }
227
+ function clamp01(v) {
228
+ return v < 0 ? 0 : v > 1 ? 1 : v;
229
+ }
230
+ function computeBBox(positions) {
231
+ let minX = Infinity, minY = Infinity, minZ = Infinity;
232
+ let maxX = -Infinity, maxY = -Infinity, maxZ = -Infinity;
233
+ for (let i = 0; i < positions.length; i += 3) {
234
+ const x = positions[i], y = positions[i + 1], z = positions[i + 2];
235
+ if (x < minX)
236
+ minX = x;
237
+ if (x > maxX)
238
+ maxX = x;
239
+ if (y < minY)
240
+ minY = y;
241
+ if (y > maxY)
242
+ maxY = y;
243
+ if (z < minZ)
244
+ minZ = z;
245
+ if (z > maxZ)
246
+ maxZ = z;
247
+ }
248
+ return { min: [minX, minY, minZ], max: [maxX, maxY, maxZ] };
249
+ }
250
+ //# sourceMappingURL=ply.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ply.js","sourceRoot":"","sources":["../../src/formats/ply.ts"],"names":[],"mappings":"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"}