Skip to main content
Version: v0.1.0

usePointFlow

The core hook that manages the ring buffer, ingest pipeline, and policy engine. StreamedPointCloud is built on top of it.

Use usePointFlow when you need direct access to the buffer — for example, to drive a custom renderer, to integrate with a non-React-three-fiber canvas, or to share buffer state across multiple scenes.

import { usePointFlow } from "pointflow";

Usage

const state = usePointFlow({
maxPoints: 100_000,
workerMode: true,
importanceField: "intensity",
});

// Push a chunk:
state.pushChunk({ points: [...] });

// Read buffer state:
console.log(state.totalPoints, state.droppedPoints, state.isUnderPressure);

// For custom rendering:
const count = state.renderIntoBuffers(positions, colors, 1, "intensity", isVisible);

Options

OptionTypeDefaultDescription
maxPointsnumberRing buffer ceiling.
lodLevelsnumber3Number of LOD levels to build.
modeBackpressurePolicy["mode"]"drop-oldest"Eviction mode.
reactivePushbooleantrueWhen true, pushChunk triggers a React state update. Set to false when you're driving render from a loop.
workerModebooleanfalseOff-thread ingest.
tierTierLevelautoHardware capability tier.
runtimeModeRuntimeMode"balanced"Operating mode.
constraintsUserConstraintsundefinedHard budget ceilings.
legacyModebooleanfalseDisable policy and use maxPoints directly.
dynamicAllocDynamicAllocOptionsundefinedDynamic buffer growth.
importanceFieldstring | "auto"undefinedImportance attribute key.
maxStalenessMsnumber0Recency half-life in ms.
timeWindowMsnumber0Render window filter in ms.
spatialCullingbooleantrueUniform-grid spatial index.
workerCullingbooleanfalseIngest-time frustum filter.
adaptiveIngestbooleanfalseThin chunks under pressure.
onRawIngest(xyz, attributes, count) => voidundefinedCalled after each chunk ingests.
configPointFlowConfigundefinedShared config object.

Returned state

FieldTypeDescription
pointsPointRecord[]Current buffer contents. Updated on each pushChunk when reactivePush is true.
lodBucketsPointRecord[][]Points organized by LOD level.
totalPointsnumberCurrent buffer fill.
droppedPointsnumberCumulative dropped count since last reset.
isUnderPressurebooleanTrue when buffer is full and dropping.
activePolicyActivePolicyCurrent tier, mode, and effective budgets.
pushChunk(chunk: PointChunk) => voidIngest a chunk.
reset() => voidClear the buffer.
refresh() => voidPull latest buffer state into React.
refreshStats() => voidPull stats only, without rebuilding the points array.
getSnapshot() => PointRecord[]Read buffer contents without a React update.
renderIntoBuffers(positions, colors, lodStep, colorBy, isVisible?) => numberWrite buffer directly into typed arrays. Returns point count written.
getBufferCapacity() => numberCurrent allocated capacity.
setWorkerFrustum(planes: Float32Array) => voidUpdate the frustum used by worker-side culling.
resetVersionnumberIncrements each time reset() is called.
_bufferRefMutableRefObject<PointBuffer | null>Direct buffer access for advanced use.

usePointCloud

For file loading, use usePointCloud instead:

import { usePointCloud } from "pointflow";

const { status, progress, detectedPointCount, onSceneReady, abort } =
usePointCloud("/scan.ply", {
maxPoints: 1_000_000,
colorBy: "intensity",
});

The first argument is the source (string, URL, File, or Blob). The second is an options object. Returns status ("idle" | "loading" | "ready" | "error" | "aborted"), progress (0–1), detectedPointCount, an onSceneReady callback setter, and abort.