@niivue/niivue 0.67.1-dev.0 → 0.67.1-dev.1
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/build/drawing/index.d.ts +1 -1
- package/build/drawing/index.js.map +1 -1
- package/build/index.min.js +1 -1
- package/build/metafile-esm.json +1 -1
- package/build/niivue/index.d.ts +3 -2
- package/build/niivue/index.js +89 -13
- package/build/niivue/index.js.map +1 -1
- package/build/{nvdocument-CcP6istx.d.ts → nvdocument-B64_4nuJ.d.ts} +18 -1
- package/build/utils/index.d.ts +1 -1
- package/dist/index.d.ts +19 -1
- package/dist/index.js +89 -13
- package/dist/index.js.map +1 -1
- package/dist/index.min.js +1 -1
- package/dist/metafile-esm.json +1 -1
- package/dist/niivue.umd.js +28 -28
- package/package.json +2 -2
- package/src/index_zarr_viewer.html +255 -68
- package/src/niivue/descriptives.ts +1 -1
- package/src/niivue/index.ts +22 -2
- package/src/nvimage/index.ts +1 -1
- package/src/nvimage/zarr/NVZarrHelper.ts +103 -12
- package/src/index_zarr.html +0 -152
package/build/niivue/index.js
CHANGED
|
@@ -19,7 +19,7 @@ import { mat4 as mat418, vec2, vec3 as vec324, vec4 as vec417 } from "gl-matrix"
|
|
|
19
19
|
// package.json
|
|
20
20
|
var package_default = {
|
|
21
21
|
name: "@niivue/niivue",
|
|
22
|
-
version: "0.67.0",
|
|
22
|
+
version: "0.67.1-dev.0",
|
|
23
23
|
description: "minimal webgl2 nifti image viewer",
|
|
24
24
|
types: "./build/niivue/index.d.ts",
|
|
25
25
|
main: "./build/niivue/index.js",
|
|
@@ -22535,9 +22535,11 @@ function createTypedVoxelArray(datatypeCode, size) {
|
|
|
22535
22535
|
case 512 /* DT_UINT16 */:
|
|
22536
22536
|
return new Uint16Array(size);
|
|
22537
22537
|
case 4 /* DT_INT16 */:
|
|
22538
|
-
case 8 /* DT_INT32 */:
|
|
22539
22538
|
return new Int16Array(size);
|
|
22539
|
+
case 8 /* DT_INT32 */:
|
|
22540
|
+
return new Int32Array(size);
|
|
22540
22541
|
case 768 /* DT_UINT32 */:
|
|
22542
|
+
return new Uint32Array(size);
|
|
22541
22543
|
case 16 /* DT_FLOAT32 */:
|
|
22542
22544
|
return new Float32Array(size);
|
|
22543
22545
|
case 64 /* DT_FLOAT64 */:
|
|
@@ -22661,13 +22663,15 @@ var NVZarrHelper = class _NVZarrHelper {
|
|
|
22661
22663
|
const level = Math.max(0, Math.min(options.level, helper.pyramidInfo.levels.length - 1));
|
|
22662
22664
|
helper.pyramidLevel = level;
|
|
22663
22665
|
helper.updateLevelInfo();
|
|
22664
|
-
helper.centerX = helper.
|
|
22665
|
-
helper.centerY = helper.
|
|
22666
|
-
helper.centerZ = helper.
|
|
22666
|
+
helper.centerX = helper.volumeDims.width / 2;
|
|
22667
|
+
helper.centerY = helper.volumeDims.height / 2;
|
|
22668
|
+
helper.centerZ = helper.volumeDims.depth / 2;
|
|
22667
22669
|
helper.configureHostImage();
|
|
22668
|
-
await helper.updateVolume();
|
|
22669
22670
|
return helper;
|
|
22670
22671
|
}
|
|
22672
|
+
async loadInitialChunks() {
|
|
22673
|
+
await this.updateVolume();
|
|
22674
|
+
}
|
|
22671
22675
|
updateLevelInfo() {
|
|
22672
22676
|
const levelInfo = this.pyramidInfo.levels[this.pyramidLevel];
|
|
22673
22677
|
const shape = levelInfo.shape;
|
|
@@ -22739,12 +22743,12 @@ var NVZarrHelper = class _NVZarrHelper {
|
|
|
22739
22743
|
img.img = createTypedVoxelArray(this.datatypeCode, width * height * depth);
|
|
22740
22744
|
this.updateAffine();
|
|
22741
22745
|
img.originalAffine = copyAffine(hdr.affine);
|
|
22742
|
-
img.cal_min =
|
|
22743
|
-
img.cal_max =
|
|
22744
|
-
img.robust_min =
|
|
22745
|
-
img.robust_max =
|
|
22746
|
-
img.global_min =
|
|
22747
|
-
img.global_max =
|
|
22746
|
+
img.cal_min = 0;
|
|
22747
|
+
img.cal_max = 0;
|
|
22748
|
+
img.robust_min = 0;
|
|
22749
|
+
img.robust_max = 0;
|
|
22750
|
+
img.global_min = 0;
|
|
22751
|
+
img.global_max = 0;
|
|
22748
22752
|
}
|
|
22749
22753
|
/** Get unit-converted voxel scales */
|
|
22750
22754
|
getConvertedScales() {
|
|
@@ -22863,6 +22867,9 @@ var NVZarrHelper = class _NVZarrHelper {
|
|
|
22863
22867
|
beginDrag() {
|
|
22864
22868
|
this.centerAtDragStart = { x: this.centerX, y: this.centerY, z: this.centerZ };
|
|
22865
22869
|
}
|
|
22870
|
+
endDrag() {
|
|
22871
|
+
this.centerAtDragStart = null;
|
|
22872
|
+
}
|
|
22866
22873
|
async panBy(dx, dy, dz = 0) {
|
|
22867
22874
|
this.centerX -= dx;
|
|
22868
22875
|
this.centerY -= dy;
|
|
@@ -22872,12 +22879,18 @@ var NVZarrHelper = class _NVZarrHelper {
|
|
|
22872
22879
|
await this.updateVolume();
|
|
22873
22880
|
}
|
|
22874
22881
|
async panTo(newCenterX, newCenterY, newCenterZ) {
|
|
22882
|
+
const prevX = this.centerX;
|
|
22883
|
+
const prevY = this.centerY;
|
|
22884
|
+
const prevZ = this.centerZ;
|
|
22875
22885
|
this.centerX = newCenterX;
|
|
22876
22886
|
this.centerY = newCenterY;
|
|
22877
22887
|
if (newCenterZ !== void 0) {
|
|
22878
22888
|
this.centerZ = newCenterZ;
|
|
22879
22889
|
}
|
|
22880
22890
|
this.clampCenter();
|
|
22891
|
+
if (Math.abs(this.centerX - prevX) < 1e-3 && Math.abs(this.centerY - prevY) < 1e-3 && Math.abs(this.centerZ - prevZ) < 1e-3) {
|
|
22892
|
+
return;
|
|
22893
|
+
}
|
|
22881
22894
|
this.updateAffine();
|
|
22882
22895
|
await this.updateVolume();
|
|
22883
22896
|
}
|
|
@@ -22917,6 +22930,54 @@ var NVZarrHelper = class _NVZarrHelper {
|
|
|
22917
22930
|
getVolumeDims() {
|
|
22918
22931
|
return { ...this.volumeDims };
|
|
22919
22932
|
}
|
|
22933
|
+
/**
|
|
22934
|
+
* Convert physical (mm) coordinates back to real zarr level pixel coordinates.
|
|
22935
|
+
* Inverts the affine: levelPixel = (mm - OME_translation) / scale
|
|
22936
|
+
*/
|
|
22937
|
+
mmToLevelCoords(mmX, mmY, mmZ) {
|
|
22938
|
+
const { scaleW, scaleH, scaleD } = this.getConvertedScales();
|
|
22939
|
+
const axisNames = this.pyramidInfo.axisMapping.spatialAxisNames;
|
|
22940
|
+
const mmByAxis = { x: mmX, y: mmY, z: mmZ };
|
|
22941
|
+
let levelW = 0;
|
|
22942
|
+
let levelH = 0;
|
|
22943
|
+
let levelD = 0;
|
|
22944
|
+
if (axisNames.length >= 2) {
|
|
22945
|
+
const wAxisName = axisNames[axisNames.length - 1];
|
|
22946
|
+
const hAxisName = axisNames[axisNames.length - 2];
|
|
22947
|
+
const dAxisName = axisNames.length >= 3 ? axisNames[axisNames.length - 3] : "z";
|
|
22948
|
+
const mmW = mmByAxis[wAxisName] ?? mmX;
|
|
22949
|
+
const mmH = mmByAxis[hAxisName] ?? mmY;
|
|
22950
|
+
const mmD = mmByAxis[dAxisName] ?? mmZ;
|
|
22951
|
+
if (this.hasTranslations) {
|
|
22952
|
+
const { transW, transH, transD } = this.getConvertedTranslations();
|
|
22953
|
+
levelW = scaleW !== 0 ? (mmW - transW) / scaleW : 0;
|
|
22954
|
+
levelH = scaleH !== 0 ? (mmH - transH) / scaleH : 0;
|
|
22955
|
+
levelD = scaleD !== 0 ? (mmD - transD) / scaleD : 0;
|
|
22956
|
+
} else {
|
|
22957
|
+
levelW = scaleW !== 0 ? mmW / scaleW : 0;
|
|
22958
|
+
levelH = scaleH !== 0 ? mmH / scaleH : 0;
|
|
22959
|
+
levelD = scaleD !== 0 ? mmD / scaleD : 0;
|
|
22960
|
+
}
|
|
22961
|
+
} else {
|
|
22962
|
+
if (this.hasTranslations) {
|
|
22963
|
+
const { transW, transH, transD } = this.getConvertedTranslations();
|
|
22964
|
+
levelW = scaleW !== 0 ? (mmX - transW) / scaleW : 0;
|
|
22965
|
+
levelH = scaleH !== 0 ? (mmY - transH) / scaleH : 0;
|
|
22966
|
+
levelD = scaleD !== 0 ? (mmZ - transD) / scaleD : 0;
|
|
22967
|
+
} else {
|
|
22968
|
+
levelW = scaleW !== 0 ? mmX / scaleW : 0;
|
|
22969
|
+
levelH = scaleH !== 0 ? mmY / scaleH : 0;
|
|
22970
|
+
levelD = scaleD !== 0 ? mmZ / scaleD : 0;
|
|
22971
|
+
}
|
|
22972
|
+
}
|
|
22973
|
+
return {
|
|
22974
|
+
width: Math.round(levelW),
|
|
22975
|
+
height: Math.round(levelH),
|
|
22976
|
+
depth: Math.round(levelD),
|
|
22977
|
+
level: this.pyramidLevel,
|
|
22978
|
+
levelDims: { ...this.levelDims }
|
|
22979
|
+
};
|
|
22980
|
+
}
|
|
22920
22981
|
clampCenter() {
|
|
22921
22982
|
const halfW = this.volumeDims.width / 2;
|
|
22922
22983
|
const halfH = this.volumeDims.height / 2;
|
|
@@ -34659,6 +34720,7 @@ var Niivue = class {
|
|
|
34659
34720
|
crosshair: false
|
|
34660
34721
|
});
|
|
34661
34722
|
__publicField(this, "readyForSync", false);
|
|
34723
|
+
__publicField(this, "_skipDragInDraw", false);
|
|
34662
34724
|
// UI Data
|
|
34663
34725
|
__publicField(this, "uiData", {
|
|
34664
34726
|
mousedown: false,
|
|
@@ -35755,6 +35817,9 @@ var Niivue = class {
|
|
|
35755
35817
|
}
|
|
35756
35818
|
if (this.uiData.isDragging) {
|
|
35757
35819
|
this.uiData.isDragging = false;
|
|
35820
|
+
for (const vol of this.getZarrVolumes()) {
|
|
35821
|
+
vol.zarrHelper?.endDrag();
|
|
35822
|
+
}
|
|
35758
35823
|
if (currentDragMode === 7 /* angle */) {
|
|
35759
35824
|
if (this.uiData.angleState === "drawing_first_line") {
|
|
35760
35825
|
this.uiData.angleFirstLine = [this.uiData.dragStart[0], this.uiData.dragStart[1], this.uiData.dragEnd[0], this.uiData.dragEnd[1]];
|
|
@@ -35900,6 +35965,9 @@ var Niivue = class {
|
|
|
35900
35965
|
}
|
|
35901
35966
|
if (this.uiData.isDragging) {
|
|
35902
35967
|
this.uiData.isDragging = false;
|
|
35968
|
+
for (const vol of this.getZarrVolumes()) {
|
|
35969
|
+
vol.zarrHelper?.endDrag();
|
|
35970
|
+
}
|
|
35903
35971
|
if (this.getCurrentDragMode() === 1 /* contrast */) {
|
|
35904
35972
|
this.calculateNewRange();
|
|
35905
35973
|
this.refreshLayers(this.volumes[0], 0);
|
|
@@ -35959,6 +36027,9 @@ var Niivue = class {
|
|
|
35959
36027
|
if (this.uiData.isDragging || this.uiData.mousedown) {
|
|
35960
36028
|
log.debug("Mouse left canvas during drag, resetting drag state.");
|
|
35961
36029
|
this.uiData.isDragging = false;
|
|
36030
|
+
for (const vol of this.getZarrVolumes()) {
|
|
36031
|
+
vol.zarrHelper?.endDrag();
|
|
36032
|
+
}
|
|
35962
36033
|
const resetState = createResetButtonState();
|
|
35963
36034
|
this.uiData.mouseButtonLeftDown = resetState.mouseButtonLeftDown;
|
|
35964
36035
|
this.uiData.mouseButtonCenterDown = resetState.mouseButtonCenterDown;
|
|
@@ -37111,8 +37182,11 @@ var Niivue = class {
|
|
|
37111
37182
|
if (volume.zarrHelper) {
|
|
37112
37183
|
volume.zarrHelper.onChunksUpdated = () => {
|
|
37113
37184
|
this.updateGLVolume();
|
|
37185
|
+
this._skipDragInDraw = true;
|
|
37114
37186
|
this.drawScene();
|
|
37187
|
+
this._skipDragInDraw = false;
|
|
37115
37188
|
};
|
|
37189
|
+
volume.zarrHelper.loadInitialChunks().catch((err) => log.error("Failed to load initial zarr chunks", err));
|
|
37116
37190
|
}
|
|
37117
37191
|
log.debug("loaded volume", volume.name);
|
|
37118
37192
|
log.debug(volume);
|
|
@@ -41239,7 +41313,9 @@ var Niivue = class {
|
|
|
41239
41313
|
}
|
|
41240
41314
|
if (panPromises.length > 0) {
|
|
41241
41315
|
Promise.all(panPromises).then(() => {
|
|
41316
|
+
this._skipDragInDraw = true;
|
|
41242
41317
|
this.drawScene();
|
|
41318
|
+
this._skipDragInDraw = false;
|
|
41243
41319
|
}).catch((err) => {
|
|
41244
41320
|
log.error("Failed to pan Zarr:", err);
|
|
41245
41321
|
});
|
|
@@ -44516,7 +44592,7 @@ var Niivue = class {
|
|
|
44516
44592
|
this.dragForSlicer3D([this.uiData.dragStart[0], this.uiData.dragStart[1], this.uiData.dragEnd[0], this.uiData.dragEnd[1]]);
|
|
44517
44593
|
return;
|
|
44518
44594
|
}
|
|
44519
|
-
if (this.getCurrentDragMode() === 3 /* pan */) {
|
|
44595
|
+
if (this.getCurrentDragMode() === 3 /* pan */ && !this._skipDragInDraw) {
|
|
44520
44596
|
this.dragForPanZoom([this.uiData.dragStart[0], this.uiData.dragStart[1], this.uiData.dragEnd[0], this.uiData.dragEnd[1]]);
|
|
44521
44597
|
return;
|
|
44522
44598
|
}
|