Skip to content

Commit a35cb2d

Browse files
committed
replace Node Buffer with ArrayBuffer
1 parent 35ec13f commit a35cb2d

File tree

2 files changed

+53
-39
lines changed

2 files changed

+53
-39
lines changed

src/3d-exporter.ts

+52-38
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,7 @@ export function exportGlb(meshByColor: Map<Color, Mesh>) {
7272
const primitives: Record<string, any>[] = [];
7373
const accessors: Record<string, any>[] = [];
7474
const bufferViews: Record<string, any>[] = [];
75-
const buffers: Buffer[] = [];
75+
const binaryBuffer: ArrayBuffer[] = [];
7676
const materials: Record<string, any>[] = [];
7777
let byteOffset = 0;
7878

@@ -87,10 +87,10 @@ export function exportGlb(meshByColor: Map<Color, Mesh>) {
8787
meshByColor.forEach((mesh, color) => {
8888
const { positions, normals, faces } = mesh;
8989
const accessorOffset = accessors.length;
90-
const faceBuffer = Buffer.from(new Uint32Array(faces).buffer);
91-
const positionBuffer = Buffer.from(flattenVec3s(positions).buffer);
92-
const normalBuffer = Buffer.from(flattenVec3s(normals).buffer);
93-
buffers.push(faceBuffer, positionBuffer, normalBuffer);
90+
const faceBuffer = new Uint32Array(faces).buffer;
91+
const positionBuffer = flattenVec3s(positions).buffer;
92+
const normalBuffer = flattenVec3s(normals).buffer;
93+
binaryBuffer.push(faceBuffer, positionBuffer, normalBuffer);
9494
const materialOffset = materials.length;
9595
const { min: positionMin, max: positionMax } = computeBounding(positions);
9696

@@ -106,36 +106,36 @@ export function exportGlb(meshByColor: Map<Color, Mesh>) {
106106
bufferViews.push({
107107
'buffer': 0,
108108
'byteOffset': byteOffset,
109-
'byteLength': faceBuffer.length,
110-
'target': 34963
109+
'byteLength': faceBuffer.byteLength,
110+
'target': 34963 // ELEMENT_ARRAY_BUFFER
111111
});
112-
byteOffset += faceBuffer.length;
112+
byteOffset += faceBuffer.byteLength;
113113
bufferViews.push({
114114
'buffer': 0,
115115
'byteOffset': byteOffset,
116-
'byteLength': positionBuffer.length,
117-
'target': 34962
116+
'byteLength': positionBuffer.byteLength,
117+
'target': 34962 // ARRAY_BUFFER
118118
});
119-
byteOffset += positionBuffer.length;
119+
byteOffset += positionBuffer.byteLength;
120120
bufferViews.push({
121121
'buffer': 0,
122122
'byteOffset': byteOffset,
123-
'byteLength': normalBuffer.length,
124-
'target': 34962
123+
'byteLength': normalBuffer.byteLength,
124+
'target': 34962 // ARRAY_BUFFER
125125
});
126-
byteOffset += normalBuffer.length;
126+
byteOffset += normalBuffer.byteLength;
127127

128128
accessors.push({
129129
'bufferView': accessorOffset,
130130
'byteOffset': 0,
131-
'componentType': 5125, // unsigned int
131+
'componentType': 5125, // UNSIGNED_INT
132132
'count': faces.length,
133133
'type': 'SCALAR'
134134
});
135135
accessors.push({
136136
'bufferView': accessorOffset + 1,
137137
'byteOffset': 0,
138-
'componentType': 5126, // float
138+
'componentType': 5126, // FLOAT
139139
'count': positions.length,
140140
'type': 'VEC3',
141141
'max': positionMax,
@@ -144,7 +144,7 @@ export function exportGlb(meshByColor: Map<Color, Mesh>) {
144144
accessors.push({
145145
'bufferView': accessorOffset + 2,
146146
'byteOffset': 0,
147-
'componentType': 5126, // float
147+
'componentType': 5126, // FLOAT
148148
'count': normals.length,
149149
'type': 'VEC3'
150150
});
@@ -158,7 +158,7 @@ export function exportGlb(meshByColor: Map<Color, Mesh>) {
158158
}
159159
});
160160
});
161-
const binaryBuffer = Buffer.concat(buffers);
161+
const binaryBufferLength = byteOffset;
162162

163163
const gltf = {
164164
'asset': {
@@ -174,38 +174,52 @@ export function exportGlb(meshByColor: Map<Color, Mesh>) {
174174
'primitives': primitives
175175
}],
176176
'buffers': [{
177-
'byteLength': binaryBuffer.length,
177+
'byteLength': binaryBufferLength,
178178
}],
179179
'bufferViews': bufferViews,
180180
'accessors': accessors,
181181
'materials': materials
182182
};
183183

184-
const createChunk = (chunkType: number, buf: Buffer, padChar: number) => {
185-
let bufBytes = buf.length;
184+
const createChunk = (chunkType: number, buf: ArrayBuffer[], byteLength: number, padChar: number): [ArrayBuffer[], number] => {
186185
let padding = null;
187-
if (bufBytes % 4 !== 0) {
188-
const pad = 4 - (bufBytes % 4);
189-
bufBytes += pad;
190-
padding = Buffer.alloc(pad, padChar);
186+
if (byteLength % 4 !== 0) {
187+
const pad = 4 - (byteLength % 4);
188+
byteLength += pad;
189+
padding = new Uint8Array(pad);
190+
padding.fill(padChar);
191191
}
192-
const tmp = [Buffer.from(new Uint32Array([bufBytes, chunkType]).buffer), buf];
192+
const tmp = [new Uint32Array([byteLength, chunkType]).buffer, ...buf];
193193
if (padding) {
194-
tmp.push(padding);
194+
tmp.push(padding.buffer);
195195
}
196-
return Buffer.concat(tmp);
196+
return [ tmp, byteLength + 8 ];
197197
};
198-
const jsonChunk = createChunk(0x4E4F534A, Buffer.from(JSON.stringify(gltf)), 0x20);
199-
const binaryChunk = createChunk(0x004E4942, binaryBuffer, 0x00);
200-
const glb = Buffer.concat([
201-
Buffer.from(new Uint32Array([
198+
const jsonString = JSON.stringify(gltf);
199+
const jsonBuffer = new Uint8Array(jsonString.length);
200+
for (let i = 0, il = jsonString.length; i < il; ++i) {
201+
jsonBuffer[i] = jsonString.charCodeAt(i);
202+
}
203+
204+
const [ jsonChunk, jsonChunkLength ] = createChunk(0x4E4F534A, [jsonBuffer.buffer], jsonBuffer.length, 0x20);
205+
const [ binaryChunk, binaryChunkLength ] = createChunk(0x004E4942, binaryBuffer, binaryBufferLength, 0x00);
206+
const glbBufferLength = 12 + jsonChunkLength + binaryChunkLength;
207+
const glbBuffer = [
208+
new Uint32Array([
202209
0x46546C67, // magic number "gltf"
203210
0x00000002, // version
204-
12 + jsonChunk.length + binaryChunk.length // total length
205-
]).buffer),
206-
jsonChunk,
207-
binaryChunk
208-
]);
211+
glbBufferLength
212+
]).buffer,
213+
...jsonChunk,
214+
...binaryChunk
215+
];
216+
217+
const glb = new Uint8Array(glbBufferLength);
218+
let offset = 0;
219+
for (const buffer of glbBuffer) {
220+
glb.set(new Uint8Array(buffer), offset);
221+
offset += buffer.byteLength;
222+
}
209223
return glb;
210224
}
211225

@@ -269,5 +283,5 @@ export function exportUsdz(meshByColor: Map<Color, Mesh>) {
269283
const crateFile = new CrateFile();
270284
crateFile.writeUsd(root);
271285
const usdz = crateFile.getUsdz();
272-
return Buffer.from(usdz.buffer);
286+
return usdz;
273287
}

src/render.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ async function writeObjFile(obj: string, objOutPath: string, mtl: string, mtlOut
6767
})
6868
]);
6969
}
70-
async function writeFile(data: Buffer, outPath: string) {
70+
async function writeFile(data: Uint8Array, outPath: string) {
7171
await new Promise<void>(resolve => {
7272
fs.writeFile(outPath, data, () => resolve());
7373
});

0 commit comments

Comments
 (0)