@vitessce/config 3.0.0 → 3.1.0
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/dist/index.js +589 -83
- package/dist-tsc/VitessceAutoConfig.d.ts +13 -1
- package/dist-tsc/VitessceAutoConfig.d.ts.map +1 -1
- package/dist-tsc/VitessceAutoConfig.js +318 -87
- package/dist-tsc/VitessceAutoConfig.test.js +599 -71
- package/dist-tsc/VitessceConfig.d.ts +46 -0
- package/dist-tsc/VitessceConfig.d.ts.map +1 -1
- package/dist-tsc/VitessceConfig.js +353 -0
- package/dist-tsc/VitessceConfig.test.js +329 -1
- package/dist-tsc/constants.d.ts +247 -0
- package/dist-tsc/constants.d.ts.map +1 -0
- package/dist-tsc/constants.js +87 -0
- package/dist-tsc/index.d.ts +2 -1
- package/dist-tsc/index.js +2 -1
- package/package.json +4 -4
- package/src/VitessceAutoConfig.js +368 -99
- package/src/VitessceAutoConfig.test.js +626 -76
- package/src/VitessceConfig.js +393 -0
- package/src/VitessceConfig.test.js +339 -0
- package/src/constants.js +94 -0
- package/src/index.js +2 -1
package/dist/index.js
CHANGED
|
@@ -93,6 +93,10 @@ const FileType$1 = {
|
|
|
93
93
|
ANNDATA_EXPRESSION_MATRIX_ZARR: "anndata-expression-matrix.zarr"
|
|
94
94
|
};
|
|
95
95
|
const CoordinationType$1 = {
|
|
96
|
+
// Meta coordination scopes
|
|
97
|
+
META_COORDINATION_SCOPES: "metaCoordinationScopes",
|
|
98
|
+
META_COORDINATION_SCOPES_BY: "metaCoordinationScopesBy",
|
|
99
|
+
// Other coordination scopes
|
|
96
100
|
DATASET: "dataset",
|
|
97
101
|
// Entity types
|
|
98
102
|
OBS_TYPE: "obsType",
|
|
@@ -15245,6 +15249,72 @@ class VitessceConfigDataset {
|
|
|
15245
15249
|
};
|
|
15246
15250
|
}
|
|
15247
15251
|
}
|
|
15252
|
+
function useComplexCoordinationHelper(scopes, coordinationScopes, coordinationScopesBy) {
|
|
15253
|
+
function processLevel(parentType, parentScope, levelType, levelVal) {
|
|
15254
|
+
var _a, _b;
|
|
15255
|
+
if (Array.isArray(levelVal)) {
|
|
15256
|
+
coordinationScopesBy[parentType] = {
|
|
15257
|
+
...coordinationScopesBy[parentType] || {},
|
|
15258
|
+
[levelType]: {
|
|
15259
|
+
...((_a = coordinationScopesBy[parentType]) == null ? void 0 : _a[levelType]) || {},
|
|
15260
|
+
[parentScope.cScope]: levelVal.map((childVal) => childVal.scope.cScope)
|
|
15261
|
+
}
|
|
15262
|
+
};
|
|
15263
|
+
levelVal.forEach((childVal) => {
|
|
15264
|
+
if (childVal.children) {
|
|
15265
|
+
Object.entries(childVal.children).forEach(([nextLevelType, nextLevelVal]) => processLevel(
|
|
15266
|
+
levelType,
|
|
15267
|
+
childVal.scope,
|
|
15268
|
+
nextLevelType,
|
|
15269
|
+
nextLevelVal
|
|
15270
|
+
));
|
|
15271
|
+
}
|
|
15272
|
+
});
|
|
15273
|
+
} else {
|
|
15274
|
+
coordinationScopesBy[parentType] = {
|
|
15275
|
+
...coordinationScopesBy[parentType] || {},
|
|
15276
|
+
[levelType]: {
|
|
15277
|
+
...((_b = coordinationScopesBy[parentType]) == null ? void 0 : _b[levelType]) || {},
|
|
15278
|
+
[parentScope.cScope]: levelVal.scope.cScope
|
|
15279
|
+
}
|
|
15280
|
+
};
|
|
15281
|
+
if (levelVal.children) {
|
|
15282
|
+
Object.entries(levelVal.children).forEach(([nextLevelType, nextLevelVal]) => processLevel(
|
|
15283
|
+
levelType,
|
|
15284
|
+
levelVal.scope,
|
|
15285
|
+
nextLevelType,
|
|
15286
|
+
nextLevelVal
|
|
15287
|
+
));
|
|
15288
|
+
}
|
|
15289
|
+
}
|
|
15290
|
+
}
|
|
15291
|
+
Object.entries(scopes).forEach(([topLevelType, topLevelVal]) => {
|
|
15292
|
+
if (Array.isArray(topLevelVal)) {
|
|
15293
|
+
coordinationScopes[topLevelType] = topLevelVal.map((levelVal) => levelVal.scope.cScope);
|
|
15294
|
+
topLevelVal.forEach((levelVal) => {
|
|
15295
|
+
if (levelVal.children) {
|
|
15296
|
+
Object.entries(levelVal.children).forEach(([nextLevelType, nextLevelVal]) => processLevel(
|
|
15297
|
+
topLevelType,
|
|
15298
|
+
levelVal.scope,
|
|
15299
|
+
nextLevelType,
|
|
15300
|
+
nextLevelVal
|
|
15301
|
+
));
|
|
15302
|
+
}
|
|
15303
|
+
});
|
|
15304
|
+
} else {
|
|
15305
|
+
coordinationScopes[topLevelType] = topLevelVal.scope.cScope;
|
|
15306
|
+
if (topLevelVal.children) {
|
|
15307
|
+
Object.entries(topLevelVal.children).forEach(([nextLevelType, nextLevelVal]) => processLevel(
|
|
15308
|
+
topLevelType,
|
|
15309
|
+
topLevelVal.scope,
|
|
15310
|
+
nextLevelType,
|
|
15311
|
+
nextLevelVal
|
|
15312
|
+
));
|
|
15313
|
+
}
|
|
15314
|
+
}
|
|
15315
|
+
});
|
|
15316
|
+
return [coordinationScopes, coordinationScopesBy];
|
|
15317
|
+
}
|
|
15248
15318
|
class VitessceConfigView {
|
|
15249
15319
|
/**
|
|
15250
15320
|
* Construct a new view instance.
|
|
@@ -15260,6 +15330,8 @@ class VitessceConfigView {
|
|
|
15260
15330
|
this.view = {
|
|
15261
15331
|
component,
|
|
15262
15332
|
coordinationScopes,
|
|
15333
|
+
coordinationScopesBy: void 0,
|
|
15334
|
+
// TODO: initialize from parameter?
|
|
15263
15335
|
x,
|
|
15264
15336
|
y,
|
|
15265
15337
|
w,
|
|
@@ -15279,6 +15351,41 @@ class VitessceConfigView {
|
|
|
15279
15351
|
});
|
|
15280
15352
|
return this;
|
|
15281
15353
|
}
|
|
15354
|
+
useComplexCoordination(scopes) {
|
|
15355
|
+
if (!this.view.coordinationScopes) {
|
|
15356
|
+
this.view.coordinationScopes = {};
|
|
15357
|
+
}
|
|
15358
|
+
if (!this.view.coordinationScopesBy) {
|
|
15359
|
+
this.view.coordinationScopesBy = {};
|
|
15360
|
+
}
|
|
15361
|
+
const [nextCoordinationScopes, nextCoordinationScopesBy] = useComplexCoordinationHelper(
|
|
15362
|
+
scopes,
|
|
15363
|
+
this.view.coordinationScopes,
|
|
15364
|
+
this.view.coordinationScopesBy
|
|
15365
|
+
);
|
|
15366
|
+
this.view.coordinationScopes = nextCoordinationScopes;
|
|
15367
|
+
this.view.coordinationScopesBy = nextCoordinationScopesBy;
|
|
15368
|
+
return this;
|
|
15369
|
+
}
|
|
15370
|
+
/**
|
|
15371
|
+
* Attach meta coordination scopes to this view.
|
|
15372
|
+
* @param {VitessceConfigMetaCoordinationScope} metaScope A meta coordination scope instance.
|
|
15373
|
+
* @returns {VitessceConfigView} This, to allow chaining.
|
|
15374
|
+
*/
|
|
15375
|
+
useMetaCoordination(metaScope) {
|
|
15376
|
+
if (!this.view.coordinationScopes) {
|
|
15377
|
+
this.view.coordinationScopes = {};
|
|
15378
|
+
}
|
|
15379
|
+
this.view.coordinationScopes[CoordinationType$1.META_COORDINATION_SCOPES] = [
|
|
15380
|
+
...this.view.coordinationScopes[CoordinationType$1.META_COORDINATION_SCOPES] || [],
|
|
15381
|
+
metaScope.metaScope.cScope
|
|
15382
|
+
];
|
|
15383
|
+
this.view.coordinationScopes[CoordinationType$1.META_COORDINATION_SCOPES_BY] = [
|
|
15384
|
+
...this.view.coordinationScopes[CoordinationType$1.META_COORDINATION_SCOPES_BY] || [],
|
|
15385
|
+
metaScope.metaByScope.cScope
|
|
15386
|
+
];
|
|
15387
|
+
return this;
|
|
15388
|
+
}
|
|
15282
15389
|
/**
|
|
15283
15390
|
* Set the x, y, w, h values for this view.
|
|
15284
15391
|
* @param {number} x The x-coordinate of the view in the layout.
|
|
@@ -15330,6 +15437,11 @@ function vconcat(...views) {
|
|
|
15330
15437
|
const vcvvc = new VitessceConfigViewVConcat(views);
|
|
15331
15438
|
return vcvvc;
|
|
15332
15439
|
}
|
|
15440
|
+
class CoordinationLevel {
|
|
15441
|
+
constructor(value) {
|
|
15442
|
+
this.value = value;
|
|
15443
|
+
}
|
|
15444
|
+
}
|
|
15333
15445
|
class VitessceConfigCoordinationScope {
|
|
15334
15446
|
/**
|
|
15335
15447
|
* Construct a new coordination scope instance.
|
|
@@ -15351,6 +15463,63 @@ class VitessceConfigCoordinationScope {
|
|
|
15351
15463
|
return this;
|
|
15352
15464
|
}
|
|
15353
15465
|
}
|
|
15466
|
+
class VitessceConfigMetaCoordinationScope {
|
|
15467
|
+
/**
|
|
15468
|
+
* Construct a new coordination scope instance.
|
|
15469
|
+
* @param {string} metaScope The name of the coordination scope for metaCoordinationScopes.
|
|
15470
|
+
* @param {string} metaByScope The name of the coordination scope for metaCoordinationScopesBy.
|
|
15471
|
+
*/
|
|
15472
|
+
constructor(metaScope, metaByScope) {
|
|
15473
|
+
this.metaScope = new VitessceConfigCoordinationScope(
|
|
15474
|
+
CoordinationType$1.META_COORDINATION_SCOPES,
|
|
15475
|
+
metaScope
|
|
15476
|
+
);
|
|
15477
|
+
this.metaByScope = new VitessceConfigCoordinationScope(
|
|
15478
|
+
CoordinationType$1.META_COORDINATION_SCOPES_BY,
|
|
15479
|
+
metaByScope
|
|
15480
|
+
);
|
|
15481
|
+
}
|
|
15482
|
+
/**
|
|
15483
|
+
* Attach coordination scopes to this meta scope.
|
|
15484
|
+
* @param {...VitessceConfigCoordinationScope} args A variable number of
|
|
15485
|
+
* coordination scope instances.
|
|
15486
|
+
* @returns {VitessceConfigMetaCoordinationScope} This, to allow chaining.
|
|
15487
|
+
*/
|
|
15488
|
+
useCoordination(...args) {
|
|
15489
|
+
const cScopes = args;
|
|
15490
|
+
const metaScopesVal = this.metaScope.cValue;
|
|
15491
|
+
cScopes.forEach((cScope) => {
|
|
15492
|
+
metaScopesVal[cScope.cType] = cScope.cScope;
|
|
15493
|
+
});
|
|
15494
|
+
this.metaScope.setValue(metaScopesVal);
|
|
15495
|
+
return this;
|
|
15496
|
+
}
|
|
15497
|
+
useComplexCoordination(scopes) {
|
|
15498
|
+
if (!this.metaScope.cValue) {
|
|
15499
|
+
this.metaScope.setValue({});
|
|
15500
|
+
}
|
|
15501
|
+
if (!this.metaByScope.cValue) {
|
|
15502
|
+
this.metaByScope.setValue({});
|
|
15503
|
+
}
|
|
15504
|
+
const [metaScopesVal, metaByScopesVal] = useComplexCoordinationHelper(
|
|
15505
|
+
scopes,
|
|
15506
|
+
this.metaScope.cValue,
|
|
15507
|
+
this.metaByScope.cValue
|
|
15508
|
+
);
|
|
15509
|
+
this.metaScope.setValue(metaScopesVal);
|
|
15510
|
+
this.metaByScope.setValue(metaByScopesVal);
|
|
15511
|
+
return this;
|
|
15512
|
+
}
|
|
15513
|
+
/**
|
|
15514
|
+
* Set the coordination value of the coordination scope.
|
|
15515
|
+
* @param {any} cValue The value to set.
|
|
15516
|
+
* @returns {VitessceConfigCoordinationScope} This, to allow chaining.
|
|
15517
|
+
*/
|
|
15518
|
+
setValue(cValue) {
|
|
15519
|
+
this.cValue = cValue;
|
|
15520
|
+
return this;
|
|
15521
|
+
}
|
|
15522
|
+
}
|
|
15354
15523
|
class VitessceConfig {
|
|
15355
15524
|
/**
|
|
15356
15525
|
* Construct a new view config instance.
|
|
@@ -15472,6 +15641,53 @@ class VitessceConfig {
|
|
|
15472
15641
|
});
|
|
15473
15642
|
return result;
|
|
15474
15643
|
}
|
|
15644
|
+
addMetaCoordination() {
|
|
15645
|
+
const prevMetaScopes = this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES] ? Object.keys(this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES]) : [];
|
|
15646
|
+
const prevMetaByScopes = this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES_BY] ? Object.keys(this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES_BY]) : [];
|
|
15647
|
+
const metaContainer = new VitessceConfigMetaCoordinationScope(
|
|
15648
|
+
getNextScope(prevMetaScopes),
|
|
15649
|
+
getNextScope(prevMetaByScopes)
|
|
15650
|
+
);
|
|
15651
|
+
if (!this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES]) {
|
|
15652
|
+
this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES] = {};
|
|
15653
|
+
}
|
|
15654
|
+
if (!this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES_BY]) {
|
|
15655
|
+
this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES_BY] = {};
|
|
15656
|
+
}
|
|
15657
|
+
this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES][metaContainer.metaScope.cScope] = metaContainer.metaScope;
|
|
15658
|
+
this.config.coordinationSpace[CoordinationType$1.META_COORDINATION_SCOPES_BY][metaContainer.metaByScope.cScope] = metaContainer.metaByScope;
|
|
15659
|
+
return metaContainer;
|
|
15660
|
+
}
|
|
15661
|
+
addComplexCoordination(input) {
|
|
15662
|
+
const processLevel = (level) => {
|
|
15663
|
+
const result = {};
|
|
15664
|
+
Object.entries(level).forEach(([cType, nextLevelOrInitialValue]) => {
|
|
15665
|
+
if (nextLevelOrInitialValue instanceof CoordinationLevel) {
|
|
15666
|
+
const nextLevel = nextLevelOrInitialValue.value;
|
|
15667
|
+
if (Array.isArray(nextLevel)) {
|
|
15668
|
+
result[cType] = nextLevel.map((nextEl) => {
|
|
15669
|
+
const [dummyScope] = this.addCoordination(cType);
|
|
15670
|
+
dummyScope.setValue("__dummy__");
|
|
15671
|
+
return {
|
|
15672
|
+
scope: dummyScope,
|
|
15673
|
+
children: processLevel(nextEl)
|
|
15674
|
+
};
|
|
15675
|
+
});
|
|
15676
|
+
} else {
|
|
15677
|
+
throw new Error("Expected CoordinationLevel.value to be an array.");
|
|
15678
|
+
}
|
|
15679
|
+
} else {
|
|
15680
|
+
const initialValue = nextLevelOrInitialValue;
|
|
15681
|
+
const [scope] = this.addCoordination(cType);
|
|
15682
|
+
scope.setValue(initialValue);
|
|
15683
|
+
result[cType] = { scope };
|
|
15684
|
+
}
|
|
15685
|
+
});
|
|
15686
|
+
return result;
|
|
15687
|
+
};
|
|
15688
|
+
const output = processLevel(input);
|
|
15689
|
+
return output;
|
|
15690
|
+
}
|
|
15475
15691
|
/**
|
|
15476
15692
|
* A convenience function for setting up new coordination scopes across a set of views.
|
|
15477
15693
|
* @param {VitessceConfigView[]} views An array of view objects to link together.
|
|
@@ -15584,6 +15800,109 @@ class VitessceConfig {
|
|
|
15584
15800
|
return vc;
|
|
15585
15801
|
}
|
|
15586
15802
|
}
|
|
15803
|
+
const SINGLE_CELL_WITH_HEATMAP_VIEWS = {
|
|
15804
|
+
obsSets: { x: 4, y: 0, w: 4, h: 4 },
|
|
15805
|
+
obsSetSizes: { x: 8, y: 0, w: 4, h: 4 },
|
|
15806
|
+
scatterplot: { x: 0, y: 0, w: 4, h: 4 },
|
|
15807
|
+
heatmap: { x: 0, y: 4, w: 8, h: 4 },
|
|
15808
|
+
featureList: { x: 8, y: 4, w: 4, h: 4 }
|
|
15809
|
+
};
|
|
15810
|
+
const SINGLE_CELL_WITHOUT_HEATMAP_VIEWS = {
|
|
15811
|
+
obsSets: { x: 10, y: 6, w: 2, h: 6 },
|
|
15812
|
+
obsSetSizes: { x: 8, y: 1, w: 4, h: 6 },
|
|
15813
|
+
scatterplot: { x: 0, y: 0, w: 8, h: 12 },
|
|
15814
|
+
featureList: { x: 8, y: 6, w: 2, h: 6 }
|
|
15815
|
+
};
|
|
15816
|
+
const SPATIAL_TRANSCRIPTOMICS_VIEWS = {
|
|
15817
|
+
scatterplot: { x: 0, y: 0, w: 3, h: 4 },
|
|
15818
|
+
spatial: { x: 3, y: 0, w: 5, h: 4 },
|
|
15819
|
+
obsSets: { x: 8, y: 0, w: 4, h: 2 },
|
|
15820
|
+
featureList: { x: 8, y: 0, w: 4, h: 2 },
|
|
15821
|
+
heatmap: { x: 0, y: 4, w: 6, h: 4 },
|
|
15822
|
+
obsSetFeatureValueDistribution: { x: 6, y: 4, w: 6, h: 4 }
|
|
15823
|
+
};
|
|
15824
|
+
const SPATIAL_TRANSCRIPTOMICS_WITH_HSITOLOGY_VIEWS = {
|
|
15825
|
+
spatial: { x: 0, y: 0, w: 6, h: 6 },
|
|
15826
|
+
heatmap: { x: 0, y: 6, w: 8, h: 6 },
|
|
15827
|
+
layerController: { x: 8, y: 6, w: 4, h: 6 },
|
|
15828
|
+
obsSets: { x: 9, y: 0, w: 3, h: 6 },
|
|
15829
|
+
featureList: { x: 6, y: 0, w: 3, h: 6 }
|
|
15830
|
+
};
|
|
15831
|
+
const IMAGE_VIEWS = {
|
|
15832
|
+
spatial: { x: 0, y: 0, w: 8, h: 12 },
|
|
15833
|
+
layerController: { x: 8, y: 0, w: 4, h: 7 },
|
|
15834
|
+
description: { x: 8, y: 9, w: 4, h: 5 }
|
|
15835
|
+
};
|
|
15836
|
+
const NO_HINTS_CONFIG = {
|
|
15837
|
+
views: {},
|
|
15838
|
+
coordinationValues: {}
|
|
15839
|
+
};
|
|
15840
|
+
const HINTS_CONFIG = {
|
|
15841
|
+
"No hints are available. Generate config with no hints.": NO_HINTS_CONFIG,
|
|
15842
|
+
Basic: NO_HINTS_CONFIG,
|
|
15843
|
+
"Transcriptomics / scRNA-seq (with heatmap)": {
|
|
15844
|
+
views: SINGLE_CELL_WITH_HEATMAP_VIEWS
|
|
15845
|
+
},
|
|
15846
|
+
"Transcriptomics / scRNA-seq (without heatmap)": {
|
|
15847
|
+
views: SINGLE_CELL_WITHOUT_HEATMAP_VIEWS
|
|
15848
|
+
},
|
|
15849
|
+
"Spatial transcriptomics (with polygon cell segmentations)": {
|
|
15850
|
+
views: SPATIAL_TRANSCRIPTOMICS_VIEWS
|
|
15851
|
+
},
|
|
15852
|
+
"Chromatin accessibility / scATAC-seq (with heatmap)": {
|
|
15853
|
+
views: SINGLE_CELL_WITH_HEATMAP_VIEWS,
|
|
15854
|
+
coordinationValues: {
|
|
15855
|
+
featureType: "peak"
|
|
15856
|
+
}
|
|
15857
|
+
},
|
|
15858
|
+
"Chromatin accessibility / scATAC-seq (without heatmap)": {
|
|
15859
|
+
views: SINGLE_CELL_WITHOUT_HEATMAP_VIEWS,
|
|
15860
|
+
coordinationValues: {
|
|
15861
|
+
featureType: "peak"
|
|
15862
|
+
}
|
|
15863
|
+
},
|
|
15864
|
+
"Spatial transcriptomics (with histology image and polygon cell segmentations)": {
|
|
15865
|
+
views: SPATIAL_TRANSCRIPTOMICS_WITH_HSITOLOGY_VIEWS,
|
|
15866
|
+
coordinationSpaceRequired: true
|
|
15867
|
+
},
|
|
15868
|
+
Image: {
|
|
15869
|
+
views: IMAGE_VIEWS
|
|
15870
|
+
}
|
|
15871
|
+
};
|
|
15872
|
+
const HINT_TYPE_TO_FILE_TYPE_MAP = {
|
|
15873
|
+
"AnnData-Zarr": [
|
|
15874
|
+
"Basic",
|
|
15875
|
+
"Transcriptomics / scRNA-seq (with heatmap)",
|
|
15876
|
+
"Transcriptomics / scRNA-seq (without heatmap)",
|
|
15877
|
+
"Spatial transcriptomics (with polygon cell segmentations)",
|
|
15878
|
+
"Chromatin accessibility / scATAC-seq (with heatmap)",
|
|
15879
|
+
"Chromatin accessibility / scATAC-seq (without heatmap)"
|
|
15880
|
+
],
|
|
15881
|
+
"OME-TIFF": [
|
|
15882
|
+
"Basic",
|
|
15883
|
+
"Image"
|
|
15884
|
+
],
|
|
15885
|
+
"AnnData-Zarr,OME-TIFF": [
|
|
15886
|
+
"Basic",
|
|
15887
|
+
"Spatial transcriptomics (with histology image and polygon cell segmentations)"
|
|
15888
|
+
]
|
|
15889
|
+
};
|
|
15890
|
+
const filterViews = (hintsConfig, possibleViews) => {
|
|
15891
|
+
const requiredViews = Object.keys(hintsConfig.views);
|
|
15892
|
+
if (requiredViews.length === 0) {
|
|
15893
|
+
return possibleViews;
|
|
15894
|
+
}
|
|
15895
|
+
const resultViews = [];
|
|
15896
|
+
requiredViews.forEach((requiredView) => {
|
|
15897
|
+
const match = possibleViews.find((possibleView) => possibleView[0] === requiredView);
|
|
15898
|
+
if (match)
|
|
15899
|
+
resultViews.push(match);
|
|
15900
|
+
});
|
|
15901
|
+
if (resultViews.length === 0) {
|
|
15902
|
+
throw new Error("No views found that are compatible with the supplied dataset URLs and hint.");
|
|
15903
|
+
}
|
|
15904
|
+
return resultViews;
|
|
15905
|
+
};
|
|
15587
15906
|
class AbstractAutoConfig {
|
|
15588
15907
|
async composeViewsConfig() {
|
|
15589
15908
|
throw new Error("The composeViewsConfig() method has not been implemented.");
|
|
@@ -15599,12 +15918,11 @@ class OmeTiffAutoConfig extends AbstractAutoConfig {
|
|
|
15599
15918
|
this.fileType = FileType$1.RASTER_JSON;
|
|
15600
15919
|
this.fileName = fileUrl.split("/").at(-1);
|
|
15601
15920
|
}
|
|
15602
|
-
async composeViewsConfig() {
|
|
15603
|
-
return
|
|
15604
|
-
|
|
15605
|
-
["spatial"],
|
|
15606
|
-
|
|
15607
|
-
];
|
|
15921
|
+
async composeViewsConfig(hintsConfig) {
|
|
15922
|
+
return filterViews(
|
|
15923
|
+
hintsConfig,
|
|
15924
|
+
[["description"], ["spatial"], ["layerController"]]
|
|
15925
|
+
);
|
|
15608
15926
|
}
|
|
15609
15927
|
async composeFileConfig() {
|
|
15610
15928
|
return {
|
|
@@ -15633,13 +15951,11 @@ class OmeZarrAutoConfig extends AbstractAutoConfig {
|
|
|
15633
15951
|
this.fileType = FileType$1.RASTER_OME_ZARR;
|
|
15634
15952
|
this.fileName = fileUrl.split("/").at(-1);
|
|
15635
15953
|
}
|
|
15636
|
-
async composeViewsConfig() {
|
|
15637
|
-
return
|
|
15638
|
-
|
|
15639
|
-
["spatial"],
|
|
15640
|
-
|
|
15641
|
-
["status"]
|
|
15642
|
-
];
|
|
15954
|
+
async composeViewsConfig(hintsConfig) {
|
|
15955
|
+
return filterViews(
|
|
15956
|
+
hintsConfig,
|
|
15957
|
+
[["description"], ["spatial"], ["layerController"]]
|
|
15958
|
+
);
|
|
15643
15959
|
}
|
|
15644
15960
|
async composeFileConfig() {
|
|
15645
15961
|
return {
|
|
@@ -15658,6 +15974,7 @@ class AnndataZarrAutoConfig extends AbstractAutoConfig {
|
|
|
15658
15974
|
this.metadataSummary = {};
|
|
15659
15975
|
}
|
|
15660
15976
|
async composeFileConfig() {
|
|
15977
|
+
var _a;
|
|
15661
15978
|
this.metadataSummary = await this.setMetadataSummary();
|
|
15662
15979
|
const options = {
|
|
15663
15980
|
obsEmbedding: [],
|
|
@@ -15684,8 +16001,10 @@ class AnndataZarrAutoConfig extends AbstractAutoConfig {
|
|
|
15684
16001
|
});
|
|
15685
16002
|
const supportedObsSetsKeys = [
|
|
15686
16003
|
"cluster",
|
|
16004
|
+
"clusters",
|
|
15687
16005
|
"subcluster",
|
|
15688
16006
|
"cell_type",
|
|
16007
|
+
"celltype",
|
|
15689
16008
|
"leiden",
|
|
15690
16009
|
"louvain",
|
|
15691
16010
|
"disease",
|
|
@@ -15710,6 +16029,15 @@ class AnndataZarrAutoConfig extends AbstractAutoConfig {
|
|
|
15710
16029
|
}
|
|
15711
16030
|
});
|
|
15712
16031
|
});
|
|
16032
|
+
options.obsSets = (_a = options.obsSets) == null ? void 0 : _a.map((obsSet) => {
|
|
16033
|
+
if (obsSet.path.length === 1) {
|
|
16034
|
+
return {
|
|
16035
|
+
...obsSet,
|
|
16036
|
+
path: obsSet.path[0]
|
|
16037
|
+
};
|
|
16038
|
+
}
|
|
16039
|
+
return obsSet;
|
|
16040
|
+
});
|
|
15713
16041
|
return {
|
|
15714
16042
|
options,
|
|
15715
16043
|
fileType: this.fileType,
|
|
@@ -15721,97 +16049,148 @@ class AnndataZarrAutoConfig extends AbstractAutoConfig {
|
|
|
15721
16049
|
}
|
|
15722
16050
|
};
|
|
15723
16051
|
}
|
|
15724
|
-
async composeViewsConfig() {
|
|
16052
|
+
async composeViewsConfig(hintsConfig) {
|
|
15725
16053
|
this.metadataSummary = await this.setMetadataSummary();
|
|
15726
|
-
const
|
|
15727
|
-
const hasCellSetData = this.metadataSummary.obs.filter((key) => key.toLowerCase().includes("cluster") || key.toLowerCase().includes("cell_type"));
|
|
16054
|
+
const possibleViews = [];
|
|
16055
|
+
const hasCellSetData = this.metadataSummary.obs.filter((key) => key.toLowerCase().includes("cluster") || key.toLowerCase().includes("cell_type") || key.toLowerCase().includes("celltype"));
|
|
15728
16056
|
if (hasCellSetData.length > 0) {
|
|
15729
|
-
|
|
16057
|
+
possibleViews.push(["obsSets"]);
|
|
15730
16058
|
}
|
|
15731
16059
|
this.metadataSummary.obsm.forEach((key) => {
|
|
15732
16060
|
if (key.toLowerCase().includes("obsm/x_umap")) {
|
|
15733
|
-
|
|
16061
|
+
possibleViews.push(["scatterplot", { mapping: "UMAP" }]);
|
|
15734
16062
|
}
|
|
15735
16063
|
if (key.toLowerCase().includes("obsm/x_tsne")) {
|
|
15736
|
-
|
|
16064
|
+
possibleViews.push(["scatterplot", { mapping: "t-SNE" }]);
|
|
15737
16065
|
}
|
|
15738
16066
|
if (key.toLowerCase().includes("obsm/x_pca")) {
|
|
15739
|
-
|
|
16067
|
+
possibleViews.push(["scatterplot", { mapping: "PCA" }]);
|
|
15740
16068
|
}
|
|
15741
16069
|
if (key.toLowerCase().includes("obsm/x_segmentations")) {
|
|
15742
|
-
|
|
16070
|
+
possibleViews.push(["layerController"]);
|
|
15743
16071
|
}
|
|
15744
16072
|
if (key.toLowerCase().includes("obsm/x_spatial")) {
|
|
15745
|
-
|
|
16073
|
+
possibleViews.push(["spatial"]);
|
|
15746
16074
|
}
|
|
15747
16075
|
});
|
|
16076
|
+
possibleViews.push(["obsSetSizes"]);
|
|
16077
|
+
possibleViews.push(["obsSetFeatureValueDistribution"]);
|
|
15748
16078
|
if (this.metadataSummary.X) {
|
|
15749
|
-
|
|
15750
|
-
|
|
16079
|
+
possibleViews.push(["heatmap"]);
|
|
16080
|
+
possibleViews.push(["featureList"]);
|
|
15751
16081
|
}
|
|
16082
|
+
const views = filterViews(hintsConfig, possibleViews);
|
|
15752
16083
|
return views;
|
|
15753
16084
|
}
|
|
16085
|
+
async setMetadataSummaryWithZmetadata(response) {
|
|
16086
|
+
const metadataFile = await response.json();
|
|
16087
|
+
if (!metadataFile.metadata) {
|
|
16088
|
+
throw new Error("Could not generate config: .zmetadata file is not valid.");
|
|
16089
|
+
}
|
|
16090
|
+
const obsmKeys = Object.keys(metadataFile.metadata).filter((key) => key.startsWith("obsm/X_")).map((key) => key.split("/.zarray")[0]);
|
|
16091
|
+
const obsKeysArr = Object.keys(metadataFile.metadata).filter((key) => key.startsWith("obs/")).map((key) => key.split("/.za")[0]);
|
|
16092
|
+
function uniq(a) {
|
|
16093
|
+
return a.sort().filter((item, pos, ary) => !pos || item !== ary[pos - 1]);
|
|
16094
|
+
}
|
|
16095
|
+
const obsKeys = uniq(obsKeysArr);
|
|
16096
|
+
const X = Object.keys(metadataFile.metadata).filter((key) => key.startsWith("X"));
|
|
16097
|
+
return {
|
|
16098
|
+
// Array of keys in obsm that are found by the fetches above
|
|
16099
|
+
obsm: obsmKeys,
|
|
16100
|
+
// Array of keys in obs that are found by the fetches above
|
|
16101
|
+
obs: obsKeys,
|
|
16102
|
+
// Boolean indicating whether the X array was found by the fetches above
|
|
16103
|
+
X: X.length > 0
|
|
16104
|
+
};
|
|
16105
|
+
}
|
|
16106
|
+
async setMetadataSummaryWithoutZmetadata() {
|
|
16107
|
+
const knownMetadataFileSuffixes = [
|
|
16108
|
+
"/obsm/X_pca/.zarray",
|
|
16109
|
+
"/obsm/X_umap/.zarray",
|
|
16110
|
+
"/obsm/X_tsne/.zarray",
|
|
16111
|
+
"/obsm/X_spatial/.zarray",
|
|
16112
|
+
"/obsm/X_segmentations/.zarray",
|
|
16113
|
+
"/obs/.zattrs",
|
|
16114
|
+
"/X/.zarray",
|
|
16115
|
+
"/X/data/.zarray"
|
|
16116
|
+
// for https://s3.amazonaws.com/vitessce-data/0.0.33/main/human-lymph-node-10x-visium/human_lymph_node_10x_visium.h5ad.zarr
|
|
16117
|
+
];
|
|
16118
|
+
const getObsmKey = (url) => {
|
|
16119
|
+
const obsmKeyStartIndex = `${this.fileUrl}/`.length;
|
|
16120
|
+
const obsmKeyEndIndex = url.length - "/.zarray".length;
|
|
16121
|
+
return url.substring(obsmKeyStartIndex, obsmKeyEndIndex);
|
|
16122
|
+
};
|
|
16123
|
+
const promises = knownMetadataFileSuffixes.map((suffix) => fetch(`${this.fileUrl}${suffix}`));
|
|
16124
|
+
const fetchResults = await Promise.all(promises);
|
|
16125
|
+
const okFetchResults = fetchResults.filter((j) => j.ok);
|
|
16126
|
+
const metadataSummary = {
|
|
16127
|
+
// Array of keys in obsm that are found by the fetches above
|
|
16128
|
+
obsm: [],
|
|
16129
|
+
// Array of keys in obs that are found by the fetches above
|
|
16130
|
+
obs: [],
|
|
16131
|
+
// Boolean indicating whether the X array was found by the fetches above
|
|
16132
|
+
X: false
|
|
16133
|
+
};
|
|
16134
|
+
const obsPromiseResult = okFetchResults.find(
|
|
16135
|
+
(r) => r.url === `${this.fileUrl}/obs/.zattrs`
|
|
16136
|
+
);
|
|
16137
|
+
const isObsValid = (obsAttr) => Object.keys(obsAttr).includes("column-order") && Object.keys(obsAttr).includes("encoding-version") && Object.keys(obsAttr).includes("encoding-type") && obsAttr["encoding-type"] === "dataframe" && (obsAttr["encoding-version"] === "0.1.0" || obsAttr["encoding-version"] === "0.2.0");
|
|
16138
|
+
if (obsPromiseResult) {
|
|
16139
|
+
const obsAttrs = await obsPromiseResult.json();
|
|
16140
|
+
if (isObsValid(obsAttrs)) {
|
|
16141
|
+
obsAttrs["column-order"].forEach((key) => metadataSummary.obs.push(`obs/${key}`));
|
|
16142
|
+
} else {
|
|
16143
|
+
throw new Error("Could not generate config: /obs/.zattrs file is not valid.");
|
|
16144
|
+
}
|
|
16145
|
+
}
|
|
16146
|
+
okFetchResults.forEach((r) => {
|
|
16147
|
+
if (r.url.startsWith(`${this.fileUrl}/obsm`)) {
|
|
16148
|
+
const obsmKey = getObsmKey(r.url);
|
|
16149
|
+
if (obsmKey) {
|
|
16150
|
+
metadataSummary.obsm.push(obsmKey);
|
|
16151
|
+
}
|
|
16152
|
+
} else if (r.url.startsWith(`${this.fileUrl}/X`)) {
|
|
16153
|
+
metadataSummary.X = true;
|
|
16154
|
+
}
|
|
16155
|
+
});
|
|
16156
|
+
return metadataSummary;
|
|
16157
|
+
}
|
|
15754
16158
|
async setMetadataSummary() {
|
|
15755
16159
|
if (Object.keys(this.metadataSummary).length > 0) {
|
|
15756
16160
|
return this.metadataSummary;
|
|
15757
16161
|
}
|
|
15758
|
-
const parseMetadataFile = (metadataFile) => {
|
|
15759
|
-
if (!metadataFile.metadata) {
|
|
15760
|
-
throw new Error("Could not generate config: .zmetadata file is not valid.");
|
|
15761
|
-
}
|
|
15762
|
-
const obsmKeys = Object.keys(metadataFile.metadata).filter((key) => key.startsWith("obsm/X_")).map((key) => key.split("/.zarray")[0]);
|
|
15763
|
-
const obsKeysArr = Object.keys(metadataFile.metadata).filter((key) => key.startsWith("obs/")).map((key) => key.split("/.za")[0]);
|
|
15764
|
-
function uniq(a) {
|
|
15765
|
-
return a.sort().filter((item, pos, ary) => !pos || item !== ary[pos - 1]);
|
|
15766
|
-
}
|
|
15767
|
-
const obsKeys = uniq(obsKeysArr);
|
|
15768
|
-
const X = Object.keys(metadataFile.metadata).filter((key) => key.startsWith("X"));
|
|
15769
|
-
const out = {
|
|
15770
|
-
obsm: obsmKeys,
|
|
15771
|
-
obs: obsKeys,
|
|
15772
|
-
X: X.length > 0
|
|
15773
|
-
};
|
|
15774
|
-
return out;
|
|
15775
|
-
};
|
|
15776
16162
|
const metadataExtension = ".zmetadata";
|
|
15777
16163
|
const url = [this.fileUrl, metadataExtension].join("/");
|
|
15778
16164
|
return fetch(url).then((response) => {
|
|
15779
16165
|
if (response.ok) {
|
|
15780
|
-
return
|
|
16166
|
+
return this.setMetadataSummaryWithZmetadata(response);
|
|
15781
16167
|
}
|
|
15782
|
-
|
|
15783
|
-
|
|
15784
|
-
if (error.status === 404) {
|
|
15785
|
-
const errorMssg = `Could not generate config. File ${metadataExtension} not found in supplied file URL. Check docs for more explanation.`;
|
|
15786
|
-
return Promise.reject(new Error(errorMssg));
|
|
16168
|
+
if (response.status === 404) {
|
|
16169
|
+
return this.setMetadataSummaryWithoutZmetadata();
|
|
15787
16170
|
}
|
|
15788
|
-
|
|
16171
|
+
throw new Error(`Could not generate config: ${response.statusText}`);
|
|
16172
|
+
}).catch((error) => {
|
|
16173
|
+
throw new Error(`Could not generate config for URL ${this.fileUrl}: ${error}`);
|
|
15789
16174
|
});
|
|
15790
16175
|
}
|
|
15791
16176
|
}
|
|
15792
16177
|
const configClasses = [
|
|
15793
16178
|
{
|
|
15794
16179
|
extensions: [".ome.tif", ".ome.tiff", ".ome.tf2", ".ome.tf8"],
|
|
15795
|
-
class: OmeTiffAutoConfig
|
|
16180
|
+
class: OmeTiffAutoConfig,
|
|
16181
|
+
name: "OME-TIFF"
|
|
15796
16182
|
},
|
|
15797
16183
|
{
|
|
15798
16184
|
extensions: [".h5ad.zarr", ".adata.zarr", ".anndata.zarr"],
|
|
15799
|
-
class: AnndataZarrAutoConfig
|
|
16185
|
+
class: AnndataZarrAutoConfig,
|
|
16186
|
+
name: "AnnData-Zarr"
|
|
15800
16187
|
},
|
|
15801
16188
|
{
|
|
15802
16189
|
extensions: ["ome.zarr"],
|
|
15803
|
-
class: OmeZarrAutoConfig
|
|
16190
|
+
class: OmeZarrAutoConfig,
|
|
16191
|
+
name: "OME-Zarr"
|
|
15804
16192
|
}
|
|
15805
16193
|
];
|
|
15806
|
-
function getFileType(url) {
|
|
15807
|
-
const match = configClasses.find((obj) => obj.extensions.filter(
|
|
15808
|
-
(ext) => url.endsWith(ext)
|
|
15809
|
-
).length === 1);
|
|
15810
|
-
if (!match) {
|
|
15811
|
-
throw new Error(`Could not generate config for URL: ${url}. This file type is not supported.`);
|
|
15812
|
-
}
|
|
15813
|
-
return match.class;
|
|
15814
|
-
}
|
|
15815
16194
|
function calculateCoordinates(viewsNumb) {
|
|
15816
16195
|
const rows = Math.ceil(Math.sqrt(viewsNumb));
|
|
15817
16196
|
const cols = Math.ceil(viewsNumb / rows);
|
|
@@ -15823,14 +16202,117 @@ function calculateCoordinates(viewsNumb) {
|
|
|
15823
16202
|
const col = i % cols;
|
|
15824
16203
|
const x = col * width;
|
|
15825
16204
|
const y = row * height;
|
|
15826
|
-
coords.push([
|
|
16205
|
+
coords.push([
|
|
16206
|
+
Math.floor(x),
|
|
16207
|
+
Math.floor(y),
|
|
16208
|
+
// Ensure width/height is at least 1.
|
|
16209
|
+
Math.max(1, Math.floor(width)),
|
|
16210
|
+
Math.max(1, Math.floor(height))
|
|
16211
|
+
]);
|
|
15827
16212
|
}
|
|
15828
16213
|
return coords;
|
|
15829
16214
|
}
|
|
15830
|
-
|
|
16215
|
+
const spatialSegmentationLayerValue = {
|
|
16216
|
+
radius: 65,
|
|
16217
|
+
stroked: true,
|
|
16218
|
+
visible: true,
|
|
16219
|
+
opacity: 1
|
|
16220
|
+
};
|
|
16221
|
+
function insertCoordinationSpaceForSpatial(views, vc) {
|
|
16222
|
+
const [
|
|
16223
|
+
spatialSegmentationLayer,
|
|
16224
|
+
spatialImageLayer,
|
|
16225
|
+
spatialZoom,
|
|
16226
|
+
spatialTargetX,
|
|
16227
|
+
spatialTargetY
|
|
16228
|
+
] = vc.addCoordination(
|
|
16229
|
+
CoordinationType$1.SPATIAL_SEGMENTATION_LAYER,
|
|
16230
|
+
CoordinationType$1.SPATIAL_IMAGE_LAYER,
|
|
16231
|
+
CoordinationType$1.SPATIAL_ZOOM,
|
|
16232
|
+
CoordinationType$1.SPATIAL_TARGET_X,
|
|
16233
|
+
CoordinationType$1.SPATIAL_TARGET_Y
|
|
16234
|
+
);
|
|
16235
|
+
spatialSegmentationLayer.setValue(spatialSegmentationLayerValue);
|
|
16236
|
+
spatialImageLayer.setValue([
|
|
16237
|
+
{
|
|
16238
|
+
type: "raster",
|
|
16239
|
+
index: 0,
|
|
16240
|
+
colormap: null,
|
|
16241
|
+
transparentColor: null,
|
|
16242
|
+
opacity: 1,
|
|
16243
|
+
domainType: "Min/Max",
|
|
16244
|
+
channels: [
|
|
16245
|
+
{
|
|
16246
|
+
selection: {
|
|
16247
|
+
c: 0
|
|
16248
|
+
},
|
|
16249
|
+
color: [
|
|
16250
|
+
255,
|
|
16251
|
+
0,
|
|
16252
|
+
0
|
|
16253
|
+
],
|
|
16254
|
+
visible: true,
|
|
16255
|
+
slider: [
|
|
16256
|
+
0,
|
|
16257
|
+
255
|
|
16258
|
+
]
|
|
16259
|
+
},
|
|
16260
|
+
{
|
|
16261
|
+
selection: {
|
|
16262
|
+
c: 1
|
|
16263
|
+
},
|
|
16264
|
+
color: [
|
|
16265
|
+
0,
|
|
16266
|
+
255,
|
|
16267
|
+
0
|
|
16268
|
+
],
|
|
16269
|
+
visible: true,
|
|
16270
|
+
slider: [
|
|
16271
|
+
0,
|
|
16272
|
+
255
|
|
16273
|
+
]
|
|
16274
|
+
},
|
|
16275
|
+
{
|
|
16276
|
+
selection: {
|
|
16277
|
+
c: 2
|
|
16278
|
+
},
|
|
16279
|
+
color: [
|
|
16280
|
+
0,
|
|
16281
|
+
0,
|
|
16282
|
+
255
|
|
16283
|
+
],
|
|
16284
|
+
visible: true,
|
|
16285
|
+
slider: [
|
|
16286
|
+
0,
|
|
16287
|
+
255
|
|
16288
|
+
]
|
|
16289
|
+
}
|
|
16290
|
+
]
|
|
16291
|
+
}
|
|
16292
|
+
]);
|
|
16293
|
+
views.forEach((view) => {
|
|
16294
|
+
if (view.view.component === "spatial" || view.view.component === "layerController") {
|
|
16295
|
+
view.useCoordination(spatialImageLayer);
|
|
16296
|
+
view.useCoordination(spatialSegmentationLayer);
|
|
16297
|
+
view.useCoordination(spatialZoom);
|
|
16298
|
+
view.useCoordination(spatialTargetX);
|
|
16299
|
+
view.useCoordination(spatialTargetY);
|
|
16300
|
+
}
|
|
16301
|
+
});
|
|
16302
|
+
}
|
|
16303
|
+
function getFileType(url) {
|
|
16304
|
+
const match = configClasses.find((obj) => obj.extensions.filter(
|
|
16305
|
+
(ext) => url.endsWith(ext)
|
|
16306
|
+
).length === 1);
|
|
16307
|
+
if (!match) {
|
|
16308
|
+
throw new Error("One or more of the URLs provided point to unsupported file types.");
|
|
16309
|
+
}
|
|
16310
|
+
return match;
|
|
16311
|
+
}
|
|
16312
|
+
async function generateViewDefinition(url, vc, dataset, hintsConfig) {
|
|
15831
16313
|
let ConfigClassName;
|
|
15832
16314
|
try {
|
|
15833
|
-
ConfigClassName = getFileType(url);
|
|
16315
|
+
ConfigClassName = getFileType(url).class;
|
|
15834
16316
|
} catch (err) {
|
|
15835
16317
|
return Promise.reject(err);
|
|
15836
16318
|
}
|
|
@@ -15839,12 +16321,12 @@ async function generateConfig(url, vc) {
|
|
|
15839
16321
|
let viewsConfig;
|
|
15840
16322
|
try {
|
|
15841
16323
|
fileConfig = await configInstance.composeFileConfig();
|
|
15842
|
-
viewsConfig = await configInstance.composeViewsConfig();
|
|
16324
|
+
viewsConfig = await configInstance.composeViewsConfig(hintsConfig);
|
|
15843
16325
|
} catch (error) {
|
|
15844
16326
|
console.error(error);
|
|
15845
16327
|
return Promise.reject(error);
|
|
15846
16328
|
}
|
|
15847
|
-
|
|
16329
|
+
dataset.addFile(fileConfig);
|
|
15848
16330
|
let layerControllerView = false;
|
|
15849
16331
|
let spatialView = false;
|
|
15850
16332
|
const views = [];
|
|
@@ -15856,7 +16338,7 @@ async function generateConfig(url, vc) {
|
|
|
15856
16338
|
if (v[0] === "spatial") {
|
|
15857
16339
|
spatialView = view;
|
|
15858
16340
|
}
|
|
15859
|
-
if (v[0] === "layerController"
|
|
16341
|
+
if (v[0] === "layerController") {
|
|
15860
16342
|
view.setProps({
|
|
15861
16343
|
disable3d: [],
|
|
15862
16344
|
disableChannelsIfRgbDetected: true
|
|
@@ -15868,47 +16350,71 @@ async function generateConfig(url, vc) {
|
|
|
15868
16350
|
views.push(view);
|
|
15869
16351
|
});
|
|
15870
16352
|
if (layerControllerView && spatialView && configInstance instanceof AnndataZarrAutoConfig) {
|
|
15871
|
-
const spatialSegmentationLayerValue = {
|
|
15872
|
-
opacity: 1,
|
|
15873
|
-
radius: 0,
|
|
15874
|
-
visible: true,
|
|
15875
|
-
stroked: false
|
|
15876
|
-
};
|
|
15877
16353
|
vc.linkViews(
|
|
15878
16354
|
[spatialView, layerControllerView],
|
|
15879
16355
|
[
|
|
15880
|
-
CoordinationType$1.SPATIAL_ZOOM,
|
|
15881
|
-
CoordinationType$1.SPATIAL_TARGET_X,
|
|
15882
|
-
CoordinationType$1.SPATIAL_TARGET_Y,
|
|
15883
16356
|
CoordinationType$1.SPATIAL_SEGMENTATION_LAYER
|
|
15884
16357
|
],
|
|
15885
|
-
[
|
|
16358
|
+
[spatialSegmentationLayerValue]
|
|
15886
16359
|
);
|
|
15887
16360
|
}
|
|
15888
16361
|
return views;
|
|
15889
16362
|
}
|
|
15890
|
-
|
|
16363
|
+
function getHintOptions(fileUrls) {
|
|
16364
|
+
const fileTypes = {};
|
|
16365
|
+
fileUrls.forEach((url) => {
|
|
16366
|
+
const match = getFileType(url);
|
|
16367
|
+
if (match.name === "OME-Zarr") {
|
|
16368
|
+
fileTypes["OME-TIFF"] = true;
|
|
16369
|
+
} else {
|
|
16370
|
+
fileTypes[match.name] = true;
|
|
16371
|
+
}
|
|
16372
|
+
});
|
|
16373
|
+
const datasetType = Object.keys(fileTypes).sort().join(",");
|
|
16374
|
+
return (HINT_TYPE_TO_FILE_TYPE_MAP == null ? void 0 : HINT_TYPE_TO_FILE_TYPE_MAP[datasetType]) || [];
|
|
16375
|
+
}
|
|
16376
|
+
async function generateConfig(fileUrls, hintTitle = null) {
|
|
16377
|
+
var _a;
|
|
15891
16378
|
const vc = new VitessceConfig({
|
|
15892
16379
|
schemaVersion: "1.0.15",
|
|
15893
16380
|
name: "An automatically generated config. Adjust values and add layout components if needed.",
|
|
15894
16381
|
description: "Populate with text relevant to this visualisation."
|
|
15895
16382
|
});
|
|
15896
16383
|
const allViews = [];
|
|
16384
|
+
const dataset = vc.addDataset("An automatically generated view config for dataset. Adjust values and add layout components if needed.");
|
|
16385
|
+
const hintsConfig = !hintTitle ? { views: {} } : HINTS_CONFIG == null ? void 0 : HINTS_CONFIG[hintTitle];
|
|
16386
|
+
if (!hintsConfig) {
|
|
16387
|
+
throw new Error(`Hints config not found for the supplied hint: ${hintTitle}.`);
|
|
16388
|
+
}
|
|
16389
|
+
const useHints = ((_a = Object.keys(hintsConfig == null ? void 0 : hintsConfig.views)) == null ? void 0 : _a.length) > 0;
|
|
15897
16390
|
fileUrls.forEach((url) => {
|
|
15898
|
-
allViews.push(
|
|
16391
|
+
allViews.push(generateViewDefinition(url, vc, dataset, hintsConfig));
|
|
15899
16392
|
});
|
|
15900
16393
|
return Promise.all(allViews).then((views) => {
|
|
15901
16394
|
const flattenedViews = views.flat();
|
|
15902
|
-
|
|
15903
|
-
|
|
15904
|
-
|
|
16395
|
+
if (hintsConfig == null ? void 0 : hintsConfig.coordinationSpaceRequired) {
|
|
16396
|
+
insertCoordinationSpaceForSpatial(flattenedViews, vc);
|
|
16397
|
+
}
|
|
16398
|
+
if (!useHints) {
|
|
16399
|
+
const coord = calculateCoordinates(flattenedViews.length);
|
|
16400
|
+
for (let i = 0; i < flattenedViews.length; i++) {
|
|
16401
|
+
flattenedViews[i].setXYWH(...coord[i]);
|
|
16402
|
+
}
|
|
16403
|
+
} else {
|
|
16404
|
+
flattenedViews.forEach((vitessceConfigView) => {
|
|
16405
|
+
const coordinates = Object.values(hintsConfig.views[vitessceConfigView.view.component]);
|
|
16406
|
+
vitessceConfigView.setXYWH(...coordinates);
|
|
16407
|
+
});
|
|
15905
16408
|
}
|
|
15906
16409
|
return vc.toJSON();
|
|
15907
16410
|
});
|
|
15908
16411
|
}
|
|
15909
16412
|
export {
|
|
16413
|
+
HINTS_CONFIG,
|
|
16414
|
+
HINT_TYPE_TO_FILE_TYPE_MAP,
|
|
15910
16415
|
VitessceConfig,
|
|
15911
|
-
|
|
16416
|
+
generateConfig,
|
|
16417
|
+
getHintOptions,
|
|
15912
16418
|
hconcat,
|
|
15913
16419
|
vconcat
|
|
15914
16420
|
};
|