Advance M8-M11 parity workflows
This commit is contained in:
@@ -2,6 +2,10 @@ import type { NanoVDBFloat32TreeLayoutIR, NanoVDBGridIR } from "../../../protoco
|
||||
|
||||
export interface NanoVDBSampleIR { value: number; active: boolean }
|
||||
|
||||
type NanoVDBNearestLocation =
|
||||
| { sample: NanoVDBSampleIR }
|
||||
| { leaf: number; voxel: number };
|
||||
|
||||
export class NanoVDBFloat32Sampler {
|
||||
private readonly view: DataView;
|
||||
private readonly layout: NanoVDBFloat32TreeLayoutIR;
|
||||
@@ -24,6 +28,20 @@ export class NanoVDBFloat32Sampler {
|
||||
}
|
||||
|
||||
nearest(coord: readonly [number, number, number]): NanoVDBSampleIR {
|
||||
const location = this.nearestLocation(coord);
|
||||
if ("sample" in location) return location.sample;
|
||||
return {
|
||||
value: this.f32(location.leaf + this.layout.leafValuesOffset + location.voxel * 4),
|
||||
active: this.mask(location.leaf + this.layout.leafValueMaskOffset, location.voxel),
|
||||
};
|
||||
}
|
||||
|
||||
leafByteOffset(coord: readonly [number, number, number]): number | null {
|
||||
const location = this.nearestLocation(coord);
|
||||
return "leaf" in location ? location.leaf : null;
|
||||
}
|
||||
|
||||
private nearestLocation(coord: readonly [number, number, number]): NanoVDBNearestLocation {
|
||||
if (coord.some((value) => !Number.isSafeInteger(value) || value < -0x8000_0000 || value > 0x7fff_ffff)) throw new Error("NANOVDB_MANIFEST_INVALID: sample coordinate is outside int32");
|
||||
const tableSize = this.u32(this.root + this.layout.rootTableSizeOffset);
|
||||
const key = this.rootKey(coord);
|
||||
@@ -39,20 +57,20 @@ export class NanoVDBFloat32Sampler {
|
||||
if (candidate > key) low = middle + 1;
|
||||
else high = middle - 1;
|
||||
}
|
||||
if (tile < 0) return { value: this.view.getFloat32(this.root + 28, true), active: false };
|
||||
if (tile < 0) return { sample: { value: this.view.getFloat32(this.root + 28, true), active: false } };
|
||||
const child = this.i64(tile + this.layout.rootTileChildOffset);
|
||||
if (child === 0n) return { value: this.f32(tile + this.layout.rootTileValueOffset), active: this.u32(tile + this.layout.rootTileStateOffset) !== 0 };
|
||||
if (child === 0n) return { sample: { value: this.f32(tile + this.layout.rootTileValueOffset), active: this.u32(tile + this.layout.rootTileStateOffset) !== 0 } };
|
||||
const upper = this.child(this.root, child, this.layout.upperNodeBytes);
|
||||
const upperOffset = (((coord[0] >>> 0 & 4095) >>> 7) << 10) | (((coord[1] >>> 0 & 4095) >>> 7) << 5) | ((coord[2] >>> 0 & 4095) >>> 7);
|
||||
const upperSample = this.internal(upper, upperOffset, this.layout.upperValueMaskOffset, this.layout.upperChildMaskOffset, this.layout.upperTableOffset, this.layout.lowerNodeBytes);
|
||||
if ("sample" in upperSample) return upperSample.sample;
|
||||
if ("sample" in upperSample) return upperSample;
|
||||
const lower = upperSample.child;
|
||||
const lowerOffset = (((coord[0] >>> 0 & 127) >>> 3) << 8) | (((coord[1] >>> 0 & 127) >>> 3) << 4) | ((coord[2] >>> 0 & 127) >>> 3);
|
||||
const lowerSample = this.internal(lower, lowerOffset, this.layout.lowerValueMaskOffset, this.layout.lowerChildMaskOffset, this.layout.lowerTableOffset, this.layout.leafNodeBytes);
|
||||
if ("sample" in lowerSample) return lowerSample.sample;
|
||||
if ("sample" in lowerSample) return lowerSample;
|
||||
const leaf = lowerSample.child;
|
||||
const voxel = ((coord[0] >>> 0 & 7) << 6) | ((coord[1] >>> 0 & 7) << 3) | (coord[2] >>> 0 & 7);
|
||||
return { value: this.f32(leaf + this.layout.leafValuesOffset + voxel * 4), active: this.mask(leaf + this.layout.leafValueMaskOffset, voxel) };
|
||||
return { leaf, voxel };
|
||||
}
|
||||
|
||||
linear(coord: readonly [number, number, number]): NanoVDBSampleIR {
|
||||
|
||||
Reference in New Issue
Block a user