brep-io-kernel 1.0.26 → 1.0.28
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.
- package/README.md +8 -0
- package/dist-kernel/brep-kernel.js +20819 -19752
- package/package.json +6 -5
- package/src/BREP/SolidMethods/fillet copy.js +1532 -0
- package/src/UI/fileManagerWidget.js +1 -10
- package/src/UI/startupTour.js +659 -0
- package/src/UI/toolbarButtons/newButton.js +21 -0
- package/src/UI/toolbarButtons/registerDefaultButtons.js +2 -0
- package/src/UI/toolbarButtons/saveButton.js +1 -1
- package/src/UI/viewer.js +4 -0
- package/src/fs.proxy.js +119 -25
- package/src/generated/licenseBundle.js +2 -0
- package/src/idbStorage.js +275 -105
- package/src/index.js +7 -0
- package/src/licenseInfo.js +71 -0
- package/src/services/componentLibrary.js +1 -1
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
// Registers the default toolbar buttons using the viewer's addToolbarButton API.
|
|
2
2
|
// Each button's logic is implemented in its own module.
|
|
3
3
|
|
|
4
|
+
import { createNewButton } from './newButton.js';
|
|
4
5
|
import { createSaveButton } from './saveButton.js';
|
|
5
6
|
import { createUndoButton, createRedoButton } from './undoRedoButtons.js';
|
|
6
7
|
import { createZoomToFitButton } from './zoomToFitButton.js';
|
|
@@ -17,6 +18,7 @@ export function registerDefaultToolbarButtons(viewer) {
|
|
|
17
18
|
if (!viewer || typeof viewer.addToolbarButton !== 'function') return;
|
|
18
19
|
|
|
19
20
|
const creators = [
|
|
21
|
+
createNewButton,
|
|
20
22
|
createSaveButton,
|
|
21
23
|
createZoomToFitButton,
|
|
22
24
|
createWireframeToggleButton,
|
|
@@ -87,7 +87,7 @@ export function createSaveButton(viewer) {
|
|
|
87
87
|
const b64 = _uint8ToBase64(bytes);
|
|
88
88
|
// Do not persist a separate thumbnail; it's embedded in the 3MF
|
|
89
89
|
const payload = { savedAt: new Date().toISOString(), data3mf: b64 };
|
|
90
|
-
LS.setItem('
|
|
90
|
+
LS.setItem('__BREP_DATA__:autosave', JSON.stringify(payload));
|
|
91
91
|
LS.setItem('__BREP_MODELS_LASTNAME__', 'autosave');
|
|
92
92
|
alert('Saved as "autosave"');
|
|
93
93
|
} catch {
|
package/src/UI/viewer.js
CHANGED
|
@@ -37,6 +37,7 @@ import { PMIMode } from './pmi/PMIMode.js';
|
|
|
37
37
|
import { annotationRegistry } from './pmi/AnnotationRegistry.js';
|
|
38
38
|
import { SchemaForm } from './featureDialogs.js';
|
|
39
39
|
import './dialogs.js';
|
|
40
|
+
import { maybeStartStartupTour } from './startupTour.js';
|
|
40
41
|
import { BREP } from '../BREP/BREP.js';
|
|
41
42
|
import { createAxisHelperGroup, DEFAULT_AXIS_HELPER_PX } from '../utils/axisHelpers.js';
|
|
42
43
|
|
|
@@ -1220,6 +1221,9 @@ export class Viewer {
|
|
|
1220
1221
|
|
|
1221
1222
|
// Ensure toolbar sits above the canvas and doesn't block controls when not hovered
|
|
1222
1223
|
try { this.renderer.domElement.style.marginTop = '0px'; } catch { }
|
|
1224
|
+
|
|
1225
|
+
// Start the startup tour once the core UI is mounted, if not already completed.
|
|
1226
|
+
try { await maybeStartStartupTour(this); } catch { }
|
|
1223
1227
|
}
|
|
1224
1228
|
|
|
1225
1229
|
// Public: allow plugins to add toolbar buttons even before MainToolbar is constructed
|
package/src/fs.proxy.js
CHANGED
|
@@ -78,12 +78,48 @@ async function idbGet(db, key) {
|
|
|
78
78
|
return promisifyRequest(store.get(key));
|
|
79
79
|
}
|
|
80
80
|
|
|
81
|
-
async function
|
|
81
|
+
async function idbDelete(db, key) {
|
|
82
82
|
const tx = db.transaction([VFS_STORE_NAME], 'readwrite');
|
|
83
|
-
tx.objectStore(VFS_STORE_NAME).
|
|
83
|
+
tx.objectStore(VFS_STORE_NAME).delete(key);
|
|
84
84
|
return new Promise((resolve, reject) => {
|
|
85
85
|
tx.oncomplete = () => resolve();
|
|
86
|
-
tx.onerror = () => reject(tx.error || new Error('IDB
|
|
86
|
+
tx.onerror = () => reject(tx.error || new Error('IDB delete failed'));
|
|
87
|
+
});
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
async function idbGetAllEntries(db) {
|
|
91
|
+
const tx = db.transaction([VFS_STORE_NAME], 'readonly');
|
|
92
|
+
const store = tx.objectStore(VFS_STORE_NAME);
|
|
93
|
+
if (store.getAll && store.getAllKeys) {
|
|
94
|
+
const [items, keys] = await Promise.all([promisifyRequest(store.getAll()), promisifyRequest(store.getAllKeys())]);
|
|
95
|
+
const out = new Map();
|
|
96
|
+
for (let i = 0; i < keys.length; i++) out.set(String(keys[i]), items[i]);
|
|
97
|
+
return out;
|
|
98
|
+
}
|
|
99
|
+
return new Promise((resolve, reject) => {
|
|
100
|
+
const out = new Map();
|
|
101
|
+
const req = store.openCursor();
|
|
102
|
+
req.onsuccess = (e) => {
|
|
103
|
+
const cursor = e.target.result;
|
|
104
|
+
if (cursor) {
|
|
105
|
+
out.set(String(cursor.key), cursor.value);
|
|
106
|
+
cursor.continue();
|
|
107
|
+
} else {
|
|
108
|
+
resolve(out);
|
|
109
|
+
}
|
|
110
|
+
};
|
|
111
|
+
req.onerror = () => reject(req.error || new Error('Cursor failed'));
|
|
112
|
+
});
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
async function idbPutDeleteEntries(db, puts, deletes) {
|
|
116
|
+
const tx = db.transaction([VFS_STORE_NAME], 'readwrite');
|
|
117
|
+
const store = tx.objectStore(VFS_STORE_NAME);
|
|
118
|
+
for (const key of deletes || []) store.delete(key);
|
|
119
|
+
for (const [key, value] of puts || []) store.put(value, key);
|
|
120
|
+
return new Promise((resolve, reject) => {
|
|
121
|
+
tx.oncomplete = () => resolve();
|
|
122
|
+
tx.onerror = () => reject(tx.error || new Error('IDB batch failed'));
|
|
87
123
|
});
|
|
88
124
|
}
|
|
89
125
|
|
|
@@ -198,9 +234,27 @@ class IndexedDbFS {
|
|
|
198
234
|
this._dbPromise = openVfsDB();
|
|
199
235
|
try {
|
|
200
236
|
const db = await this._dbPromise;
|
|
201
|
-
const
|
|
202
|
-
|
|
203
|
-
|
|
237
|
+
const legacyRaw = await idbGet(db, VFS_KEY);
|
|
238
|
+
const legacyIndex = coerceIndex(legacyRaw);
|
|
239
|
+
if (legacyIndex) {
|
|
240
|
+
this.index = legacyIndex;
|
|
241
|
+
const puts = Object.entries(this.index.entries);
|
|
242
|
+
await idbPutDeleteEntries(db, puts, [VFS_KEY]);
|
|
243
|
+
} else {
|
|
244
|
+
if (legacyRaw !== undefined && legacyRaw !== null) {
|
|
245
|
+
await idbDelete(db, VFS_KEY);
|
|
246
|
+
}
|
|
247
|
+
const map = await idbGetAllEntries(db);
|
|
248
|
+
if (map.size) {
|
|
249
|
+
const entries = {};
|
|
250
|
+
for (const [key, value] of map.entries()) {
|
|
251
|
+
if (key === VFS_KEY) continue;
|
|
252
|
+
if (value && typeof value === 'object' && typeof value.type === 'string') {
|
|
253
|
+
entries[key] = value;
|
|
254
|
+
}
|
|
255
|
+
}
|
|
256
|
+
if (Object.keys(entries).length) this.index = { entries };
|
|
257
|
+
}
|
|
204
258
|
}
|
|
205
259
|
} catch (err) {
|
|
206
260
|
console.warn('[vfs] IndexedDB unavailable; using in-memory storage only.', err);
|
|
@@ -225,17 +279,25 @@ class IndexedDbFS {
|
|
|
225
279
|
}
|
|
226
280
|
if (!this.index.entries['/']) {
|
|
227
281
|
this.index.entries['/'] = { type: 'dir', children: [], mtimeMs: nowMs(), mode: 0o777 };
|
|
228
|
-
this._save();
|
|
282
|
+
this._save(['/']);
|
|
229
283
|
}
|
|
230
284
|
}
|
|
231
285
|
|
|
232
|
-
_save() {
|
|
286
|
+
_save(puts = [], deletes = []) {
|
|
233
287
|
if (!this._idbEnabled) return;
|
|
234
288
|
if (!this._dbPromise) this._dbPromise = openVfsDB();
|
|
235
|
-
const
|
|
289
|
+
const entries = this.index.entries;
|
|
290
|
+
const putList = Array.isArray(puts) ? puts : [];
|
|
291
|
+
const deleteList = Array.isArray(deletes) ? deletes : [];
|
|
292
|
+
if (!putList.length && !deleteList.length) return;
|
|
293
|
+
const putPairs = [];
|
|
294
|
+
for (const key of putList) {
|
|
295
|
+
const entry = entries[key];
|
|
296
|
+
if (entry) putPairs.push([key, entry]);
|
|
297
|
+
}
|
|
236
298
|
this._persistChain = this._persistChain
|
|
237
299
|
.then(() => this._dbPromise)
|
|
238
|
-
.then((db) =>
|
|
300
|
+
.then((db) => idbPutDeleteEntries(db, putPairs, deleteList))
|
|
239
301
|
.catch((err) => {
|
|
240
302
|
console.warn('[vfs] Persist failed:', err);
|
|
241
303
|
});
|
|
@@ -250,8 +312,10 @@ class IndexedDbFS {
|
|
|
250
312
|
if (!eParent.children.includes(name)) {
|
|
251
313
|
eParent.children.push(name);
|
|
252
314
|
eParent.mtimeMs = nowMs();
|
|
315
|
+
return parent;
|
|
253
316
|
}
|
|
254
317
|
}
|
|
318
|
+
return null;
|
|
255
319
|
}
|
|
256
320
|
_unlinkFromParent(p) {
|
|
257
321
|
const parent = dirname(p);
|
|
@@ -262,8 +326,10 @@ class IndexedDbFS {
|
|
|
262
326
|
if (i >= 0) {
|
|
263
327
|
eParent.children.splice(i, 1);
|
|
264
328
|
eParent.mtimeMs = nowMs();
|
|
329
|
+
return parent;
|
|
265
330
|
}
|
|
266
331
|
}
|
|
332
|
+
return null;
|
|
267
333
|
}
|
|
268
334
|
_resolveEncoding(options) {
|
|
269
335
|
if (!options) return null;
|
|
@@ -303,8 +369,12 @@ class IndexedDbFS {
|
|
|
303
369
|
mtimeMs: nowMs(),
|
|
304
370
|
mode: (options.mode ?? 0o666)
|
|
305
371
|
};
|
|
306
|
-
|
|
307
|
-
|
|
372
|
+
const touched = new Set([path]);
|
|
373
|
+
if (!exists) {
|
|
374
|
+
const p = this._linkIntoParent(path);
|
|
375
|
+
if (p) touched.add(p);
|
|
376
|
+
}
|
|
377
|
+
this._save([...touched]);
|
|
308
378
|
}
|
|
309
379
|
|
|
310
380
|
appendFileSync(path, data, options = {}) {
|
|
@@ -337,7 +407,7 @@ class IndexedDbFS {
|
|
|
337
407
|
existing.data = uint8ToBase64(merged);
|
|
338
408
|
existing.size = merged.length;
|
|
339
409
|
existing.mtimeMs = nowMs();
|
|
340
|
-
this._save();
|
|
410
|
+
this._save([path]);
|
|
341
411
|
}
|
|
342
412
|
|
|
343
413
|
readFileSync(path, options = {}) {
|
|
@@ -368,21 +438,28 @@ class IndexedDbFS {
|
|
|
368
438
|
const eParent = this.index.entries[parent];
|
|
369
439
|
if (!eParent || eParent.type !== 'dir') throw this._enoent('ENOENT', parent);
|
|
370
440
|
this.index.entries[path] = { type: 'dir', children: [], mtimeMs: nowMs(), mode: options.mode ?? 0o777 };
|
|
371
|
-
|
|
441
|
+
const touched = new Set([path]);
|
|
442
|
+
const p = this._linkIntoParent(path);
|
|
443
|
+
if (p) touched.add(p);
|
|
444
|
+
this._save([...touched]);
|
|
445
|
+
return;
|
|
372
446
|
}
|
|
373
447
|
const parts = normalizePath(path).split('/').filter(Boolean);
|
|
374
448
|
let cur = '/';
|
|
449
|
+
const touched = new Set();
|
|
375
450
|
for (const part of parts) {
|
|
376
451
|
const next = normalizePath(cur + '/' + part);
|
|
377
452
|
if (!this.index.entries[next]) {
|
|
378
453
|
this.index.entries[next] = { type: 'dir', children: [], mtimeMs: nowMs(), mode: 0o777 };
|
|
379
|
-
|
|
454
|
+
touched.add(next);
|
|
455
|
+
const p = this._linkIntoParent(next);
|
|
456
|
+
if (p) touched.add(p);
|
|
380
457
|
} else if (this.index.entries[next].type !== 'dir') {
|
|
381
458
|
throw this._eexist('EEXIST', next);
|
|
382
459
|
}
|
|
383
460
|
cur = next;
|
|
384
461
|
}
|
|
385
|
-
this._save();
|
|
462
|
+
if (touched.size) this._save([...touched]);
|
|
386
463
|
}
|
|
387
464
|
|
|
388
465
|
readdirSync(path, options = {}) {
|
|
@@ -411,8 +488,9 @@ class IndexedDbFS {
|
|
|
411
488
|
if (!entry) throw this._enoent('ENOENT', path);
|
|
412
489
|
if (entry.type !== 'file') throw this._enoent('EISDIR', path);
|
|
413
490
|
delete this.index.entries[path];
|
|
414
|
-
this._unlinkFromParent(path);
|
|
415
|
-
|
|
491
|
+
const p = this._unlinkFromParent(path);
|
|
492
|
+
const puts = p ? [p] : [];
|
|
493
|
+
this._save(puts, [path]);
|
|
416
494
|
}
|
|
417
495
|
|
|
418
496
|
rmdirSync(path, options = {}) {
|
|
@@ -425,6 +503,7 @@ class IndexedDbFS {
|
|
|
425
503
|
if (entry.children.length && !recursive) {
|
|
426
504
|
const err = new Error(`ENOTEMPTY: directory not empty, ${path}`); err.code = 'ENOTEMPTY'; throw err;
|
|
427
505
|
}
|
|
506
|
+
const toDelete = [];
|
|
428
507
|
if (recursive) {
|
|
429
508
|
const stack = [path];
|
|
430
509
|
while (stack.length) {
|
|
@@ -434,12 +513,16 @@ class IndexedDbFS {
|
|
|
434
513
|
if (e.type === 'dir') {
|
|
435
514
|
for (const name of e.children) stack.push(normalizePath(cur + '/' + name));
|
|
436
515
|
}
|
|
437
|
-
|
|
516
|
+
delete this.index.entries[cur];
|
|
517
|
+
toDelete.push(cur);
|
|
438
518
|
}
|
|
519
|
+
} else {
|
|
520
|
+
delete this.index.entries[path];
|
|
521
|
+
toDelete.push(path);
|
|
439
522
|
}
|
|
440
|
-
|
|
441
|
-
|
|
442
|
-
this._save();
|
|
523
|
+
const p = this._unlinkFromParent(path);
|
|
524
|
+
const puts = p ? [p] : [];
|
|
525
|
+
this._save(puts, toDelete);
|
|
443
526
|
}
|
|
444
527
|
|
|
445
528
|
renameSync(oldPath, newPath) {
|
|
@@ -453,18 +536,26 @@ class IndexedDbFS {
|
|
|
453
536
|
const pEntry = this.index.entries[newParent];
|
|
454
537
|
if (!pEntry || pEntry.type !== 'dir') throw this._enoent('ENOENT', newParent);
|
|
455
538
|
|
|
539
|
+
const toPut = new Set();
|
|
540
|
+
const toDelete = new Set();
|
|
456
541
|
if (this.index.entries[newPath]) {
|
|
457
542
|
if (this.index.entries[newPath].type === 'dir') {
|
|
458
543
|
const err = new Error(`EISDIR: illegal operation on a directory, ${newPath}`); err.code = 'EISDIR'; throw err;
|
|
459
544
|
}
|
|
545
|
+
toDelete.add(newPath);
|
|
460
546
|
delete this.index.entries[newPath];
|
|
461
547
|
}
|
|
462
548
|
|
|
463
549
|
this.index.entries[newPath] = entry;
|
|
464
550
|
delete this.index.entries[oldPath];
|
|
465
551
|
|
|
466
|
-
|
|
467
|
-
|
|
552
|
+
toDelete.add(oldPath);
|
|
553
|
+
toPut.add(newPath);
|
|
554
|
+
|
|
555
|
+
const oldParent = this._unlinkFromParent(oldPath);
|
|
556
|
+
const newParent2 = this._linkIntoParent(newPath);
|
|
557
|
+
if (oldParent) toPut.add(oldParent);
|
|
558
|
+
if (newParent2) toPut.add(newParent2);
|
|
468
559
|
|
|
469
560
|
if (entry.type === 'dir') {
|
|
470
561
|
const toFix = [];
|
|
@@ -476,11 +567,14 @@ class IndexedDbFS {
|
|
|
476
567
|
const target = normalizePath(newPath + rel);
|
|
477
568
|
this.index.entries[target] = this.index.entries[oldChild];
|
|
478
569
|
delete this.index.entries[oldChild];
|
|
570
|
+
toDelete.add(oldChild);
|
|
571
|
+
toPut.add(target);
|
|
479
572
|
}
|
|
480
573
|
}
|
|
481
574
|
|
|
482
575
|
entry.mtimeMs = nowMs();
|
|
483
|
-
|
|
576
|
+
toPut.add(newPath);
|
|
577
|
+
this._save([...toPut], [...toDelete]);
|
|
484
578
|
}
|
|
485
579
|
|
|
486
580
|
statSync(path) {
|
|
@@ -0,0 +1,2 @@
|
|
|
1
|
+
// Auto-generated by scripts/generateLicenseBundle.js
|
|
2
|
+
export const LICENSE_BUNDLE_TEXT = "brep-io-kernel License\nLicense: SEE LICENSE IN LICENSE.md\n\nCopyright 2025 Autodrop3d LLC\nhttps://autodrop3d.com\n\nPermission is hereby granted, free of charge, to any person obtaining a copy of this software and \nassociated documentation files (the \"Software\"), to deal in the Software without restriction, \nincluding without limitation the rights to use, copy, modify, merge, publish, distribute, \nsublicense, and/or sell copies of the Software, and to permit persons to whom the Software is \nfurnished to do so, subject to the following conditions:\n\n1. Any modifications made to the Software must be submitted to Autodrop3d LLC with an irrevocable \n assignment of the copyright via git pull request. This is intended to allow Autodrop3d LLC to \n sell commercial licenses of the Software for use in proprietary products under a \n dual-licensing strategy. Failure to contribute back modifications without a commercial \n license purchased from Autodrop3d LLC voids all permissions granted by this license.\n\n2. If Autodrop3d LLC is sold, merged, transferred, or otherwise succeeded by any entity or \n individual, all rights and obligations described in this license shall transfer automatically \n to that successor entity or individual.\n\n3. If Autodrop3d LLC ceases operations or dissolves, and no successor entity or individual \n continues to publicly host the Software in a manner that allows the public to obtain the source \n code and submit contributions for a period of at least eighteen (18) consecutive months, then \n Clauses 1 and 2 of this license shall be automatically and irrevocably canceled.\n\nThe above copyright notice and these permission notices shall be included in all copies or \nsubstantial portions of the Software.\n\nTHE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING \nBUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND \nNONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, \nDAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, \nOUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n\nThird-party licenses (production dependencies)\n55 packages • 9 license types\nGenerated from: pnpm licenses list --prod --long --json\n\n(MIT AND Zlib) (1 package)\n- pako@1.0.11 — zlib port to javascript - fast, modularized, with browser support — https://github.com/nodeca/pako\n\n(MIT OR GPL-3.0-or-later) (1 package)\n- jszip@3.10.1 — Create, read and edit .zip files with JavaScript http://stuartk.com/jszip — Author: Stuart Knightley — https://github.com/Stuk/jszip#readme\n\n(MPL-2.0 OR Apache-2.0) (1 package)\n- dompurify@3.2.7 — DOMPurify is a DOM-only, super-fast, uber-tolerant XSS sanitizer for HTML, MathML and SVG. It's written in JavaScript and works in all modern browsers (Safari, Opera (15+), Internet Explorer (10+), Firefox and Chrome - as well as almost anything else using Blink or WebKit). DOMPurify is written by security people who have vast background in web attacks and XSS. Fear not. — Author: Dr.-Ing. Mario Heiderich, Cure53 — https://github.com/cure53/DOMPurify\n\nApache-2.0 (5 packages)\n- @img/sharp-linux-x64@0.34.5 — Prebuilt sharp for use with Linux (glibc) x64 — Author: Lovell Fuller — https://sharp.pixelplumbing.com\n- @img/sharp-linuxmusl-x64@0.34.5 — Prebuilt sharp for use with Linux (musl) x64 — Author: Lovell Fuller — https://sharp.pixelplumbing.com\n- detect-libc@2.1.2 — Node.js module to detect the C standard library (libc) implementation family and version — Author: Lovell Fuller — https://github.com/lovell/detect-libc#readme\n- manifold-3d@3.3.2 — Geometry library for topological robustness — https://github.com/elalish/manifold#readme\n- sharp@0.34.5 — High performance Node.js image processing, the fastest module to resize JPEG, PNG, WebP, GIF, AVIF and TIFF images — Author: Lovell Fuller — https://sharp.pixelplumbing.com\n\nbsd-2-clause (1 package)\n- esbuild-plugin-text-replace@1.3.0 — Replace Text with Regex in files before bundling. — Author: Andreas Heissenberger — https://github.com/aheissenberger/esbuild-plugin-text-replace\n\nISC (2 packages)\n- inherits@2.0.4 — Browser-friendly inheritance fully compatible with standard node.js inherits() — https://github.com/isaacs/inherits#readme\n- semver@7.7.3 — The semantic version parser used by npm. — Author: GitHub Inc. — https://github.com/npm/node-semver#readme\n\nLGPL-3.0-or-later (2 packages)\n- @img/sharp-libvips-linux-x64@1.2.4 — Prebuilt libvips and dependencies for use with sharp on Linux (glibc) x64 — Author: Lovell Fuller — https://sharp.pixelplumbing.com\n- @img/sharp-libvips-linuxmusl-x64@1.2.4 — Prebuilt libvips and dependencies for use with sharp on Linux (musl) x64 — Author: Lovell Fuller — https://sharp.pixelplumbing.com\n\nMIT (41 packages)\n- @gltf-transform/core@4.3.0 — glTF 2.0 SDK for JavaScript and TypeScript, on Web and Node.js. — Author: Don McCurdy — https://gltf-transform.dev/\n- @gltf-transform/extensions@4.3.0 — Adds extension support to @gltf-transform/core — Author: Don McCurdy — https://gltf-transform.dev/extensions.html\n- @gltf-transform/functions@4.3.0 — Functions for common glTF modifications, written using the core API — Author: Don McCurdy — https://gltf-transform.dev/functions.html\n- @img/colour@1.0.0 — The ESM-only 'color' package made compatible for use with CommonJS runtimes — https://github.com/lovell/colour#readme\n- @jridgewell/resolve-uri@3.1.2 — Resolve a URI relative to an optional base URI — Author: Justin Ridgewell — https://github.com/jridgewell/resolve-uri#readme\n- @jridgewell/sourcemap-codec@1.5.5 — Encode/decode sourcemap mappings — Author: Justin Ridgewell — https://github.com/jridgewell/sourcemaps/tree/main/packages/sourcemap-codec\n- @jridgewell/trace-mapping@0.3.31 — Trace the original position through a source map — Author: Justin Ridgewell — https://github.com/jridgewell/sourcemaps/tree/main/packages/trace-mapping\n- @jscadui/3mf-export@0.5.0 — 3mf export\n- @tarikjabiri/dxf@2.8.9 — A JavaScript interface to Dxf written in TypeScript. — Author: Tarik EL JABIRI — https://dxf.vercel.app\n- @types/ndarray@1.0.14 — TypeScript definitions for ndarray — https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/ndarray\n- @types/trusted-types@2.0.7 — TypeScript definitions for trusted-types — https://github.com/DefinitelyTyped/DefinitelyTyped/tree/master/types/trusted-types\n- commander@13.1.0 — the complete solution for node.js command-line programs — Author: TJ Holowaychuk — https://github.com/tj/commander.js#readme\n- convert-source-map@2.0.0 — Converts a source-map from/to different formats and allows adding/changing properties. — Author: Thorsten Lorenz — https://github.com/thlorenz/convert-source-map\n- core-js@3.48.0 — Standard library — Author: Denis Pushkarev — https://core-js.io\n- core-util-is@1.0.3 — The `util.is*` functions introduced in Node v0.12. — Author: Isaac Z. Schlueter — https://github.com/isaacs/core-util-is#readme\n- cwise-compiler@1.1.3 — cwise's internal compiler — Author: Mikola Lysenko — https://github.com/scijs/cwise-compiler#readme\n- esbuild-wasm@0.25.12 — The cross-platform WebAssembly binary for esbuild, a JavaScript bundler. — https://github.com/evanw/esbuild#readme\n- fflate@0.8.2 — High performance (de)compression in an 8kB package — Author: Arjun Barrett — https://101arrowz.github.io/fflate\n- immediate@3.0.6 — A cross browser microtask library — https://github.com/calvinmetcalf/immediate#readme\n- iota-array@1.0.0 — Generates an array of consecutive integers starting at 0 — Author: Mikola Lysenko — https://github.com/mikolalysenko/iota-array#readme\n- is-buffer@1.1.6 — Determine if an object is a Buffer — Author: Feross Aboukhadijeh — https://github.com/feross/is-buffer#readme\n- isarray@1.0.0 — Array#isArray for older browsers — Author: Julian Gruber — https://github.com/juliangruber/isarray\n- ktx-parse@1.1.0 — KTX 2.0 (.ktx2) parser and serializer. — Author: Don McCurdy — https://github.com/donmccurdy/ktx-parse#readme\n- lie@3.3.0 — A basic but performant promise implementation — https://github.com/calvinmetcalf/lie#readme\n- marked@14.0.0 — A markdown parser built for speed — Author: Christopher Jeffrey — https://marked.js.org\n- monaco-editor@0.55.1 — A browser based code editor — Author: Microsoft Corporation — https://github.com/microsoft/monaco-editor\n- ndarray@1.0.19 — Multidimensional Arrays — Author: Mikola Lysenko — https://github.com/mikolalysenko/ndarray#readme\n- ndarray-lanczos@0.3.0 — Resize an ndarray with Lanczos resampling — Author: Don McCurdy — https://github.com/donmccurdy/ndarray-lanczos#readme\n- ndarray-ops@1.2.2 — Common operations for ndarray arrays — Author: Mikola Lysenko — https://github.com/mikolalysenko/ndarray-ops#readme\n- ndarray-pixels@5.0.1 — ndarray-pixels — Author: Don McCurdy — https://github.com/donmccurdy/ndarray-pixels#readme\n- process-nextick-args@2.0.1 — process.nextTick but always with args — https://github.com/calvinmetcalf/process-nextick-args\n- property-graph@4.0.0 — Base for creating objects that behave like a Property Graph. — Author: Don McCurdy — https://github.com/donmccurdy/property-graph#readme\n- readable-stream@2.3.8 — Streams3, a user-land copy of the stream library from Node.js — https://github.com/nodejs/readable-stream#readme\n- safe-buffer@5.1.2 — Safer Node.js Buffer API — Author: Feross Aboukhadijeh — https://github.com/feross/safe-buffer\n- setimmediate@1.0.5 — A shim for the setImmediate efficient script yielding API — Author: YuzuJS — https://github.com/YuzuJS/setImmediate#readme\n- string_decoder@1.1.1 — The string_decoder module from Node core — https://github.com/nodejs/string_decoder\n- three@0.182.0 — JavaScript 3D library — Author: mrdoob — https://threejs.org/\n- three-mesh-bvh@0.9.8 — A BVH implementation to speed up raycasting against three.js meshes. — Author: Garrett Johnson — https://github.com/gkjohnson/three-mesh-bvh#readme\n- ts-replace-all@1.0.0 — https://github.com/LinusU/ts-replace-all#readme\n- uniq@1.0.1 — Removes duplicates from a sorted array in place — Author: Mikola Lysenko — https://github.com/mikolalysenko/uniq#readme\n- util-deprecate@1.0.2 — The Node.js `util.deprecate()` function with browser support — Author: Nathan Rajlich — https://github.com/TooTallNate/util-deprecate\n\nSGI-B-2.0 (1 package)\n- tess2@1.0.0 — GLU tesselator ported to Javascript, performs polygon boolean operations and triangulation — Author: Matt DesLauriers — https://github.com/memononen/tess2.js";
|