Files
PozzettiAndrea a342f20402 Serve frontend JS from javascript/, keep vendor bundles out of the main realm
Move web/ to javascript/ and declare it via [tool.comfy] web.

Rename the seven third-party bundles (playcanvas, spark, three.js, gsplat,
OrbitControls, TrackballControls) to .mjs. Every reference to them is inside the
HTML viewers, but ComfyUI auto-imports **/*.js under the web dir into the shared
browser realm, so ~8MB of vendor code was being evaluated in the main page on
every startup -- and with it 36 collision errors: document.body injection,
document-level listeners, unguarded message listeners and self.onmessage writes.
The importmap values, script srcs and three.module's internal ./three.core ref
are rewritten to match.

DisplayName becomes "GaussianPack": the namespace enforced on
registerExtension names is derived from it, and "ComfyUI-GaussianPack" made
that prefix invalid. The analysis extension is renamed to match.

js/gaussian_preview.js hooked "PlyPreviewLoadGaussianPLYEnhance", a node id
that appears nowhere in this repo, so the PLY dropdown auto-refresh had never
run; it now targets LoadPLY and LoadPLYOutput, the two nodes that actually carry
the ply_file widget. Guard its message listener on event.source.

Asset seeding resolves the input directory through
folder_paths.get_input_directory(), so it follows ComfyUI Desktop and
--input-directory instead of writing into the code tree.

comfy-test.toml moves to the current schema: [test.workflows] cuda (there is
no "gpu" key -- the accelerator is named by backend, and the old spelling parsed
to an empty list, so CUDA runners silently ran the full unfiltered set), an
explicit [test.platforms] platforms allowlist (per-platform booleans are no
longer supported), and the javascript level.
2026-08-22 20:56:09 +02:00

1.7 KiB

Library to convert gaussian splats between PLY and SPZ formats

Based on the original C++ library.

Installation

NPM

npm install spz-js

Example (Node.js)

import {
    createReadStream,
    readFileSync,
    writeFileSync,
    unlinkSync
} from 'fs';
import { Readable } from 'stream';
import path from 'path';

import {
    loadPly,
    loadSpz,
    serializePly,
    serializeSpz
} from 'spz-js';

// Helper function to load either SPZ or PLY files
const loadFile = async (file) => {
    const extension = path.extname(file);
    if (extension === '.spz') {
        const fileBuffer = readFileSync(file);
        return await loadSpz(fileBuffer);
    } else if (extension === '.ply') {
        const fileStream = createReadStream(file);
        const webStream = Readable.toWeb(fileStream);
        return await loadPly(webStream);
    }
    throw new Error(`Unsupported file extension: ${extension}`);
};

const gs = await loadFile("gs.ply"); // or gs.spz

const plyData = serializePly(gs);
writeFileSync("gs.ply", Buffer.from(plyData));

const spzData = await serializeSpz(gs);
writeFileSync("gs.spz", Buffer.from(spzData));

Example (Browser)

import {
    loadPly,
    loadSpz
} from 'spz-js';

const loadFile = async (url) => {
    const response = await fetch(url);
    const extension = url.split('.').pop();
    
    if (extension === 'spz') {
        const buffer = await response.arrayBuffer();
        return await loadSpz(buffer);
    } else if (extension === 'ply') {
        return await loadPly(response.body);
    }
    throw new Error(`Unsupported file extension: ${extension}`);
};