@genome-spy/core 0.66.1 → 0.68.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/bundle/index.es.js +7669 -6115
- package/dist/bundle/index.js +114 -133
- package/dist/schema.json +534 -132
- package/dist/src/data/collector.d.ts +20 -0
- package/dist/src/data/collector.d.ts.map +1 -1
- package/dist/src/data/collector.js +148 -0
- package/dist/src/data/dataFlow.d.ts +6 -0
- package/dist/src/data/dataFlow.d.ts.map +1 -1
- package/dist/src/data/dataFlow.js +10 -0
- package/dist/src/data/flowHandle.d.ts +2 -0
- package/dist/src/data/flowHandle.d.ts.map +1 -1
- package/dist/src/data/flowHandle.js +1 -0
- package/dist/src/data/flowInit.d.ts +12 -4
- package/dist/src/data/flowInit.d.ts.map +1 -1
- package/dist/src/data/flowInit.js +115 -17
- package/dist/src/data/flowNode.d.ts +8 -0
- package/dist/src/data/flowNode.d.ts.map +1 -1
- package/dist/src/data/flowNode.js +18 -0
- package/dist/src/data/keyIndex.d.ts +18 -0
- package/dist/src/data/keyIndex.d.ts.map +1 -0
- package/dist/src/data/keyIndex.js +241 -0
- package/dist/src/data/keyIndex.test.d.ts +2 -0
- package/dist/src/data/keyIndex.test.d.ts.map +1 -0
- package/dist/src/data/sources/dataSource.d.ts.map +1 -1
- package/dist/src/data/sources/dataSource.js +5 -1
- package/dist/src/data/sources/dataSourceFactory.d.ts +14 -12
- package/dist/src/data/sources/dataSourceFactory.d.ts.map +1 -1
- package/dist/src/data/sources/dataSourceFactory.js +52 -16
- package/dist/src/data/sources/lazy/mockLazySource.d.ts +29 -0
- package/dist/src/data/sources/lazy/mockLazySource.d.ts.map +1 -0
- package/dist/src/data/sources/lazy/mockLazySource.js +44 -0
- package/dist/src/data/sources/lazy/singleAxisLazySource.d.ts +22 -1
- package/dist/src/data/sources/lazy/singleAxisLazySource.d.ts.map +1 -1
- package/dist/src/data/sources/lazy/singleAxisLazySource.js +34 -2
- package/dist/src/data/sources/lazy/singleAxisWindowedSource.d.ts.map +1 -1
- package/dist/src/data/sources/lazy/singleAxisWindowedSource.js +15 -0
- package/dist/src/data/sources/lazy/tabixSource.d.ts.map +1 -1
- package/dist/src/data/sources/lazy/tabixSource.js +15 -5
- package/dist/src/data/transforms/stack.d.ts.map +1 -1
- package/dist/src/data/transforms/stack.js +1 -0
- package/dist/src/encoder/accessor.d.ts +43 -0
- package/dist/src/encoder/accessor.d.ts.map +1 -1
- package/dist/src/encoder/accessor.js +164 -0
- package/dist/src/encoder/encoder.d.ts +11 -2
- package/dist/src/encoder/encoder.d.ts.map +1 -1
- package/dist/src/encoder/encoder.js +24 -4
- package/dist/src/encoder/metadataChannels.d.ts +15 -0
- package/dist/src/encoder/metadataChannels.d.ts.map +1 -0
- package/dist/src/encoder/metadataChannels.js +65 -0
- package/dist/src/encoder/metadataChannels.test.d.ts +2 -0
- package/dist/src/encoder/metadataChannels.test.d.ts.map +1 -0
- package/dist/src/genome/scaleLocus.d.ts.map +1 -1
- package/dist/src/genome/scaleLocus.js +14 -1
- package/dist/src/genomeSpy/containerUi.d.ts +0 -1
- package/dist/src/genomeSpy/containerUi.d.ts.map +1 -1
- package/dist/src/genomeSpy/containerUi.js +0 -14
- package/dist/src/genomeSpy/loadingIndicatorManager.d.ts +3 -7
- package/dist/src/genomeSpy/loadingIndicatorManager.d.ts.map +1 -1
- package/dist/src/genomeSpy/loadingIndicatorManager.js +68 -20
- package/dist/src/genomeSpy/loadingStatusRegistry.d.ts +52 -0
- package/dist/src/genomeSpy/loadingStatusRegistry.d.ts.map +1 -0
- package/dist/src/genomeSpy/loadingStatusRegistry.js +86 -0
- package/dist/src/genomeSpy/viewContextFactory.d.ts.map +1 -1
- package/dist/src/genomeSpy/viewContextFactory.js +0 -1
- package/dist/src/genomeSpy/viewDataInit.d.ts +10 -0
- package/dist/src/genomeSpy/viewDataInit.d.ts.map +1 -1
- package/dist/src/genomeSpy/viewDataInit.js +166 -2
- package/dist/src/genomeSpy/viewDataInit.test.d.ts +2 -0
- package/dist/src/genomeSpy/viewDataInit.test.d.ts.map +1 -0
- package/dist/src/genomeSpy.d.ts +1 -2
- package/dist/src/genomeSpy.d.ts.map +1 -1
- package/dist/src/genomeSpy.js +69 -27
- package/dist/src/gl/dataToVertices.d.ts.map +1 -1
- package/dist/src/gl/dataToVertices.js +16 -4
- package/dist/src/marks/mark.d.ts.map +1 -1
- package/dist/src/marks/mark.js +18 -11
- package/dist/src/marks/markUtils.js +1 -1
- package/dist/src/scale/scale.d.ts +6 -1
- package/dist/src/scale/scale.d.ts.map +1 -1
- package/dist/src/scale/scale.js +83 -23
- package/dist/src/scales/axisResolution.d.ts.map +1 -1
- package/dist/src/scales/axisResolution.js +10 -0
- package/dist/src/scales/{scaleDomainAggregator.d.ts → domainPlanner.d.ts} +8 -5
- package/dist/src/scales/domainPlanner.d.ts.map +1 -0
- package/dist/src/scales/domainPlanner.js +285 -0
- package/dist/src/scales/domainPlanner.test.d.ts +2 -0
- package/dist/src/scales/domainPlanner.test.d.ts.map +1 -0
- package/dist/src/scales/scaleInstanceManager.d.ts.map +1 -1
- package/dist/src/scales/scaleInstanceManager.js +8 -4
- package/dist/src/scales/scaleInteractionController.d.ts +6 -0
- package/dist/src/scales/scaleInteractionController.d.ts.map +1 -1
- package/dist/src/scales/scaleInteractionController.js +41 -3
- package/dist/src/scales/scaleResolution.d.ts +19 -16
- package/dist/src/scales/scaleResolution.d.ts.map +1 -1
- package/dist/src/scales/scaleResolution.js +255 -70
- package/dist/src/scales/scaleResolution.test.d.ts.map +1 -1
- package/dist/src/selection/selection.d.ts +21 -0
- package/dist/src/selection/selection.d.ts.map +1 -1
- package/dist/src/selection/selection.js +82 -0
- package/dist/src/spec/channel.d.ts +52 -15
- package/dist/src/spec/data.d.ts +4 -0
- package/dist/src/spec/parameter.d.ts +16 -11
- package/dist/src/spec/testing.d.ts +12 -0
- package/dist/src/spec/testing.d.ts.map +1 -0
- package/dist/src/spec/testing.js +20 -0
- package/dist/src/spec/view.d.ts +45 -10
- package/dist/src/styles/genome-spy.css +3 -31
- package/dist/src/styles/genome-spy.css.d.ts +1 -1
- package/dist/src/styles/genome-spy.css.d.ts.map +1 -1
- package/dist/src/styles/genome-spy.css.js +0 -29
- package/dist/src/types/encoder.d.ts +37 -2
- package/dist/src/types/rendering.d.ts +4 -3
- package/dist/src/types/viewContext.d.ts +0 -14
- package/dist/src/utils/domainArray.d.ts.map +1 -1
- package/dist/src/utils/domainArray.js +3 -0
- package/dist/src/utils/indexer.d.ts +3 -0
- package/dist/src/utils/indexer.d.ts.map +1 -1
- package/dist/src/utils/indexer.js +3 -0
- package/dist/src/utils/throttle.d.ts +4 -1
- package/dist/src/utils/throttle.d.ts.map +1 -1
- package/dist/src/utils/throttle.js +54 -23
- package/dist/src/utils/throttle.test.d.ts +2 -0
- package/dist/src/utils/throttle.test.d.ts.map +1 -0
- package/dist/src/utils/transition.d.ts +21 -0
- package/dist/src/utils/transition.d.ts.map +1 -1
- package/dist/src/utils/transition.js +28 -0
- package/dist/src/utils/ui/tooltip.d.ts.map +1 -1
- package/dist/src/utils/ui/tooltip.js +7 -1
- package/dist/src/utils/ui/tooltip.test.d.ts +2 -0
- package/dist/src/utils/ui/tooltip.test.d.ts.map +1 -0
- package/dist/src/view/axisGridView.d.ts.map +1 -1
- package/dist/src/view/axisGridView.js +22 -5
- package/dist/src/view/axisView.d.ts.map +1 -1
- package/dist/src/view/axisView.js +20 -5
- package/dist/src/view/concatView.js +3 -3
- package/dist/src/view/containerMutationHelper.d.ts.map +1 -1
- package/dist/src/view/containerMutationHelper.js +6 -2
- package/dist/src/view/containerView.d.ts +9 -5
- package/dist/src/view/containerView.d.ts.map +1 -1
- package/dist/src/view/containerView.js +34 -9
- package/dist/src/view/dataReadiness.d.ts +46 -0
- package/dist/src/view/dataReadiness.d.ts.map +1 -0
- package/dist/src/view/dataReadiness.js +267 -0
- package/dist/src/view/dataReadiness.test.d.ts +2 -0
- package/dist/src/view/dataReadiness.test.d.ts.map +1 -0
- package/dist/src/view/facetView.d.ts.map +1 -1
- package/dist/src/view/facetView.js +7 -5
- package/dist/src/view/flowBuilder.d.ts +5 -3
- package/dist/src/view/flowBuilder.d.ts.map +1 -1
- package/dist/src/view/flowBuilder.js +74 -7
- package/dist/src/view/gridView/gridChild.d.ts.map +1 -1
- package/dist/src/view/gridView/gridChild.js +8 -0
- package/dist/src/view/gridView/gridView.d.ts.map +1 -1
- package/dist/src/view/gridView/gridView.js +119 -2
- package/dist/src/view/gridView/scrollbar.d.ts.map +1 -1
- package/dist/src/view/gridView/scrollbar.js +3 -0
- package/dist/src/view/gridView/selectionRect.d.ts.map +1 -1
- package/dist/src/view/gridView/selectionRect.js +20 -5
- package/dist/src/view/gridView/separatorView.d.ts +51 -0
- package/dist/src/view/gridView/separatorView.d.ts.map +1 -0
- package/dist/src/view/gridView/separatorView.js +275 -0
- package/dist/src/view/layerView.js +3 -3
- package/dist/src/view/layout/flexLayout.d.ts +0 -30
- package/dist/src/view/layout/flexLayout.d.ts.map +1 -1
- package/dist/src/view/layout/flexLayout.js +0 -86
- package/dist/src/view/paramMediator.d.ts +19 -0
- package/dist/src/view/paramMediator.d.ts.map +1 -1
- package/dist/src/view/paramMediator.js +86 -19
- package/dist/src/view/testUtils.d.ts.map +1 -1
- package/dist/src/view/testUtils.js +11 -1
- package/dist/src/view/unitView.d.ts +8 -13
- package/dist/src/view/unitView.d.ts.map +1 -1
- package/dist/src/view/unitView.js +127 -43
- package/dist/src/view/view.d.ts +34 -14
- package/dist/src/view/view.d.ts.map +1 -1
- package/dist/src/view/view.js +119 -9
- package/dist/src/view/viewFactory.d.ts.map +1 -1
- package/dist/src/view/viewFactory.js +20 -1
- package/dist/src/view/viewSelectors.d.ts +148 -0
- package/dist/src/view/viewSelectors.d.ts.map +1 -0
- package/dist/src/view/viewSelectors.js +773 -0
- package/dist/src/view/viewSelectors.test.d.ts +2 -0
- package/dist/src/view/viewSelectors.test.d.ts.map +1 -0
- package/dist/src/view/viewUtils.d.ts +0 -8
- package/dist/src/view/viewUtils.d.ts.map +1 -1
- package/dist/src/view/viewUtils.js +1 -21
- package/package.json +3 -3
- package/dist/src/scales/scaleDomainAggregator.d.ts.map +0 -1
- package/dist/src/scales/scaleDomainAggregator.js +0 -162
- package/dist/src/scales/scaleDomainAggregator.test.d.ts +0 -2
- package/dist/src/scales/scaleDomainAggregator.test.d.ts.map +0 -1
|
@@ -5,45 +5,67 @@ import SPINNER from "../img/90-ring-with-bg.svg";
|
|
|
5
5
|
export default class LoadingIndicatorManager {
|
|
6
6
|
/** @type {HTMLElement} */
|
|
7
7
|
#loadingIndicatorsElement;
|
|
8
|
+
|
|
8
9
|
/**
|
|
9
|
-
* @type {
|
|
10
|
+
* @type {import("./loadingStatusRegistry.js").default}
|
|
10
11
|
*/
|
|
11
|
-
#
|
|
12
|
+
#loadingStatusRegistry;
|
|
13
|
+
|
|
14
|
+
/** @type {(() => void) | null} */
|
|
15
|
+
#unsubscribe = null;
|
|
12
16
|
|
|
13
17
|
/**
|
|
14
18
|
* @param {HTMLElement} loadingIndicatorsElement
|
|
19
|
+
* @param {import("./loadingStatusRegistry.js").default} loadingStatusRegistry
|
|
15
20
|
*/
|
|
16
|
-
constructor(loadingIndicatorsElement) {
|
|
21
|
+
constructor(loadingIndicatorsElement, loadingStatusRegistry) {
|
|
17
22
|
this.#loadingIndicatorsElement = loadingIndicatorsElement;
|
|
18
23
|
|
|
19
|
-
|
|
20
|
-
* @type {Map<import("../view/view.js").default, { status: import("../types/viewContext.js").DataLoadingStatus, detail?: string }>}
|
|
21
|
-
*/
|
|
22
|
-
this.#loadingViews = new Map();
|
|
23
|
-
}
|
|
24
|
+
this.#loadingStatusRegistry = loadingStatusRegistry;
|
|
24
25
|
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
* @param {string} [detail]
|
|
29
|
-
*/
|
|
30
|
-
setDataLoadingStatus(view, status, detail) {
|
|
31
|
-
this.#loadingViews.set(view, { status, detail });
|
|
26
|
+
this.#unsubscribe = this.#loadingStatusRegistry.subscribe(() =>
|
|
27
|
+
this.updateLayout()
|
|
28
|
+
);
|
|
32
29
|
this.updateLayout();
|
|
33
30
|
}
|
|
34
31
|
|
|
32
|
+
destroy() {
|
|
33
|
+
if (this.#unsubscribe) {
|
|
34
|
+
this.#unsubscribe();
|
|
35
|
+
this.#unsubscribe = null;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
|
|
35
39
|
updateLayout() {
|
|
36
40
|
/** @type {import("lit").TemplateResult[]} */
|
|
37
41
|
const indicators = [];
|
|
38
42
|
|
|
39
|
-
const isSomethingVisible = () =>
|
|
40
|
-
[
|
|
41
|
-
(
|
|
42
|
-
|
|
43
|
+
const isSomethingVisible = () => {
|
|
44
|
+
for (const [, status] of this.#loadingStatusRegistry.entries()) {
|
|
45
|
+
if (status.status == "loading" || status.status == "error") {
|
|
46
|
+
return true;
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
return false;
|
|
50
|
+
};
|
|
51
|
+
|
|
52
|
+
/** @type {{ status: import("../types/viewContext.js").DataLoadingStatus, detail?: string } | undefined} */
|
|
53
|
+
let fallbackStatus;
|
|
54
|
+
let hasVisibleWithCoords = false;
|
|
55
|
+
|
|
56
|
+
for (const [view, status] of this.#loadingStatusRegistry.entries()) {
|
|
57
|
+
const isVisible =
|
|
58
|
+
status.status == "loading" || status.status == "error";
|
|
43
59
|
|
|
44
|
-
for (const [view, status] of this.#loadingViews) {
|
|
45
60
|
const c = view.coords;
|
|
61
|
+
if (!c && isVisible && !fallbackStatus) {
|
|
62
|
+
fallbackStatus = status;
|
|
63
|
+
}
|
|
46
64
|
if (c) {
|
|
65
|
+
if (isVisible) {
|
|
66
|
+
hasVisibleWithCoords = true;
|
|
67
|
+
}
|
|
68
|
+
|
|
47
69
|
const style = {
|
|
48
70
|
left: `${c.x}px`,
|
|
49
71
|
top: `${c.y}px`,
|
|
@@ -70,6 +92,32 @@ export default class LoadingIndicatorManager {
|
|
|
70
92
|
}
|
|
71
93
|
}
|
|
72
94
|
|
|
95
|
+
if (fallbackStatus && !hasVisibleWithCoords) {
|
|
96
|
+
const style = {
|
|
97
|
+
left: "0px",
|
|
98
|
+
top: "0px",
|
|
99
|
+
width: "100%",
|
|
100
|
+
height: "100%",
|
|
101
|
+
};
|
|
102
|
+
indicators.push(
|
|
103
|
+
html`<div style=${styleMap(style)}>
|
|
104
|
+
<div class=${fallbackStatus.status}>
|
|
105
|
+
${fallbackStatus.status == "error"
|
|
106
|
+
? html`<span
|
|
107
|
+
>Loading
|
|
108
|
+
failed${fallbackStatus.detail
|
|
109
|
+
? html`: ${fallbackStatus.detail}`
|
|
110
|
+
: nothing}</span
|
|
111
|
+
>`
|
|
112
|
+
: html`
|
|
113
|
+
<img src="${SPINNER}" alt="" />
|
|
114
|
+
<span>Loading...</span>
|
|
115
|
+
`}
|
|
116
|
+
</div>
|
|
117
|
+
</div>`
|
|
118
|
+
);
|
|
119
|
+
}
|
|
120
|
+
|
|
73
121
|
// Do some hacks to stop css animations of the loading indicators.
|
|
74
122
|
// Otherwise they fire animation frames even when their opacity is zero.
|
|
75
123
|
// TODO: Instead of this, replace the animated spinners with static images.
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @typedef {import("../view/view.js").default} View
|
|
3
|
+
* @typedef {import("../types/viewContext.js").DataLoadingStatus} DataLoadingStatus
|
|
4
|
+
* @typedef {{ status: DataLoadingStatus, detail?: string }} LoadingStatus
|
|
5
|
+
* @typedef {{ view: View, status: DataLoadingStatus, detail?: string }} LoadingStatusChange
|
|
6
|
+
*/
|
|
7
|
+
/**
|
|
8
|
+
* Central registry for per-view loading status that decouples data sources
|
|
9
|
+
* from UI rendering. Consumers can subscribe to changes and query the current
|
|
10
|
+
* status map when needed (e.g., for overlay rendering).
|
|
11
|
+
*/
|
|
12
|
+
export default class LoadingStatusRegistry {
|
|
13
|
+
/**
|
|
14
|
+
* @param {View} view
|
|
15
|
+
* @param {DataLoadingStatus} status
|
|
16
|
+
* @param {string} [detail]
|
|
17
|
+
*/
|
|
18
|
+
set(view: View, status: DataLoadingStatus, detail?: string): void;
|
|
19
|
+
/**
|
|
20
|
+
* @param {View} view
|
|
21
|
+
*/
|
|
22
|
+
delete(view: View): void;
|
|
23
|
+
/**
|
|
24
|
+
* @param {View} view
|
|
25
|
+
* @returns {LoadingStatus | undefined}
|
|
26
|
+
*/
|
|
27
|
+
get(view: View): LoadingStatus | undefined;
|
|
28
|
+
/**
|
|
29
|
+
* @returns {IterableIterator<[View, LoadingStatus]>}
|
|
30
|
+
*/
|
|
31
|
+
entries(): IterableIterator<[View, LoadingStatus]>;
|
|
32
|
+
/**
|
|
33
|
+
* Subscribe to status changes.
|
|
34
|
+
*
|
|
35
|
+
* @param {(change: LoadingStatusChange) => void} listener
|
|
36
|
+
* @returns {() => void} Unsubscribe callback
|
|
37
|
+
*/
|
|
38
|
+
subscribe(listener: (change: LoadingStatusChange) => void): () => void;
|
|
39
|
+
#private;
|
|
40
|
+
}
|
|
41
|
+
export type View = import("../view/view.js").default;
|
|
42
|
+
export type DataLoadingStatus = import("../types/viewContext.js").DataLoadingStatus;
|
|
43
|
+
export type LoadingStatus = {
|
|
44
|
+
status: DataLoadingStatus;
|
|
45
|
+
detail?: string;
|
|
46
|
+
};
|
|
47
|
+
export type LoadingStatusChange = {
|
|
48
|
+
view: View;
|
|
49
|
+
status: DataLoadingStatus;
|
|
50
|
+
detail?: string;
|
|
51
|
+
};
|
|
52
|
+
//# sourceMappingURL=loadingStatusRegistry.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"loadingStatusRegistry.d.ts","sourceRoot":"","sources":["../../../src/genomeSpy/loadingStatusRegistry.js"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH;;;;GAIG;AACH;IAOI;;;;OAIG;IACH,UAJW,IAAI,UACJ,iBAAiB,WACjB,MAAM,QAahB;IAED;;OAEG;IACH,aAFW,IAAI,QAkBd;IAED;;;OAGG;IACH,UAHW,IAAI,GACF,aAAa,GAAG,SAAS,CAIrC;IAED;;OAEG;IACH,WAFa,gBAAgB,CAAC,CAAC,IAAI,EAAE,aAAa,CAAC,CAAC,CAInD;IAED;;;;;OAKG;IACH,oBAHW,CAAC,MAAM,EAAE,mBAAmB,KAAK,IAAI,GACnC,MAAM,IAAI,CAOtB;;CACJ;mBApFY,OAAO,iBAAiB,EAAE,OAAO;gCACjC,OAAO,yBAAyB,EAAE,iBAAiB;4BACnD;IAAE,MAAM,EAAE,iBAAiB,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE;kCAC9C;IAAE,IAAI,EAAE,IAAI,CAAC;IAAC,MAAM,EAAE,iBAAiB,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE"}
|
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* @typedef {import("../view/view.js").default} View
|
|
3
|
+
* @typedef {import("../types/viewContext.js").DataLoadingStatus} DataLoadingStatus
|
|
4
|
+
* @typedef {{ status: DataLoadingStatus, detail?: string }} LoadingStatus
|
|
5
|
+
* @typedef {{ view: View, status: DataLoadingStatus, detail?: string }} LoadingStatusChange
|
|
6
|
+
*/
|
|
7
|
+
|
|
8
|
+
/**
|
|
9
|
+
* Central registry for per-view loading status that decouples data sources
|
|
10
|
+
* from UI rendering. Consumers can subscribe to changes and query the current
|
|
11
|
+
* status map when needed (e.g., for overlay rendering).
|
|
12
|
+
*/
|
|
13
|
+
export default class LoadingStatusRegistry {
|
|
14
|
+
/** @type {Map<View, LoadingStatus>} */
|
|
15
|
+
#statuses = new Map();
|
|
16
|
+
|
|
17
|
+
/** @type {Set<(change: LoadingStatusChange) => void>} */
|
|
18
|
+
#listeners = new Set();
|
|
19
|
+
|
|
20
|
+
/**
|
|
21
|
+
* @param {View} view
|
|
22
|
+
* @param {DataLoadingStatus} status
|
|
23
|
+
* @param {string} [detail]
|
|
24
|
+
*/
|
|
25
|
+
set(view, status, detail) {
|
|
26
|
+
if (!view) {
|
|
27
|
+
throw new Error("LoadingStatusRegistry.set requires a view.");
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
this.#statuses.set(view, { status, detail });
|
|
31
|
+
|
|
32
|
+
const change = { view, status, detail };
|
|
33
|
+
for (const listener of this.#listeners) {
|
|
34
|
+
listener(change);
|
|
35
|
+
}
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/**
|
|
39
|
+
* @param {View} view
|
|
40
|
+
*/
|
|
41
|
+
delete(view) {
|
|
42
|
+
const previous = this.#statuses.get(view);
|
|
43
|
+
if (!previous) {
|
|
44
|
+
return;
|
|
45
|
+
}
|
|
46
|
+
|
|
47
|
+
this.#statuses.delete(view);
|
|
48
|
+
|
|
49
|
+
const change = {
|
|
50
|
+
view,
|
|
51
|
+
status: previous.status,
|
|
52
|
+
detail: previous.detail,
|
|
53
|
+
};
|
|
54
|
+
for (const listener of this.#listeners) {
|
|
55
|
+
listener(change);
|
|
56
|
+
}
|
|
57
|
+
}
|
|
58
|
+
|
|
59
|
+
/**
|
|
60
|
+
* @param {View} view
|
|
61
|
+
* @returns {LoadingStatus | undefined}
|
|
62
|
+
*/
|
|
63
|
+
get(view) {
|
|
64
|
+
return this.#statuses.get(view);
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* @returns {IterableIterator<[View, LoadingStatus]>}
|
|
69
|
+
*/
|
|
70
|
+
entries() {
|
|
71
|
+
return this.#statuses.entries();
|
|
72
|
+
}
|
|
73
|
+
|
|
74
|
+
/**
|
|
75
|
+
* Subscribe to status changes.
|
|
76
|
+
*
|
|
77
|
+
* @param {(change: LoadingStatusChange) => void} listener
|
|
78
|
+
* @returns {() => void} Unsubscribe callback
|
|
79
|
+
*/
|
|
80
|
+
subscribe(listener) {
|
|
81
|
+
this.#listeners.add(listener);
|
|
82
|
+
return () => {
|
|
83
|
+
this.#listeners.delete(listener);
|
|
84
|
+
};
|
|
85
|
+
}
|
|
86
|
+
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"viewContextFactory.d.ts","sourceRoot":"","sources":["../../../src/genomeSpy/viewContextFactory.js"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;;;;;;;;GASG;AACH,2CALW,OAAO,CAAC,WAAW,CAAC,GAAG;IAC7B,6BAA6B,CAAC,EAAE,CAAC,OAAO,EAAE,WAAW,EAAE,IAAI,EAAE,OAAO,iBAAiB,EAAE,QAAQ,GAAG,OAAO,iBAAiB,EAAE,UAAU,EAAE,YAAY,CAAC,EAAE,OAAO,0BAA0B,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,OAAO,iBAAiB,EAAE,OAAO,EAAE,WAAW,CAAC,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,CAAC,IAAI,EAAE,OAAO,iBAAiB,EAAE,QAAQ,KAAK,IAAI,KAAK,OAAO,CAAC,OAAO,iBAAiB,EAAE,OAAO,CAAC,CAAA;CACvX,GACS,WAAW,
|
|
1
|
+
{"version":3,"file":"viewContextFactory.d.ts","sourceRoot":"","sources":["../../../src/genomeSpy/viewContextFactory.js"],"names":[],"mappings":"AAAA;;GAEG;AAEH;;;;;;;;;GASG;AACH,2CALW,OAAO,CAAC,WAAW,CAAC,GAAG;IAC7B,6BAA6B,CAAC,EAAE,CAAC,OAAO,EAAE,WAAW,EAAE,IAAI,EAAE,OAAO,iBAAiB,EAAE,QAAQ,GAAG,OAAO,iBAAiB,EAAE,UAAU,EAAE,YAAY,CAAC,EAAE,OAAO,0BAA0B,EAAE,OAAO,EAAE,UAAU,CAAC,EAAE,OAAO,iBAAiB,EAAE,OAAO,EAAE,WAAW,CAAC,EAAE,MAAM,EAAE,SAAS,CAAC,EAAE,CAAC,IAAI,EAAE,OAAO,iBAAiB,EAAE,QAAQ,KAAK,IAAI,KAAK,OAAO,CAAC,OAAO,iBAAiB,EAAE,OAAO,CAAC,CAAA;CACvX,GACS,WAAW,CAiEvB;0BA5EY,OAAO,yBAAyB,EAAE,OAAO"}
|
|
@@ -9,4 +9,14 @@
|
|
|
9
9
|
* @returns {Promise<import("../data/dataFlow.js").default>}
|
|
10
10
|
*/
|
|
11
11
|
export function initializeViewData(viewRoot: import("../view/view.js").default, dataFlow: import("../data/dataFlow.js").default, fontManager: import("../fonts/bmFontManager.js").default, onDataFlowBuilt: (dataFlow: import("../data/dataFlow.js").default) => void): Promise<import("../data/dataFlow.js").default>;
|
|
12
|
+
/**
|
|
13
|
+
* Initializes data flow and graphics for visible views that were previously
|
|
14
|
+
* skipped. Intended for view-visibility toggles.
|
|
15
|
+
*
|
|
16
|
+
* @param {import("../view/view.js").default} viewRoot
|
|
17
|
+
* @param {import("../data/dataFlow.js").default} dataFlow
|
|
18
|
+
* @param {import("../fonts/bmFontManager.js").default} fontManager
|
|
19
|
+
* @returns {Promise<import("../data/dataFlow.js").default>}
|
|
20
|
+
*/
|
|
21
|
+
export function initializeVisibleViewData(viewRoot: import("../view/view.js").default, dataFlow: import("../data/dataFlow.js").default, fontManager: import("../fonts/bmFontManager.js").default): Promise<import("../data/dataFlow.js").default>;
|
|
12
22
|
//# sourceMappingURL=viewDataInit.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"viewDataInit.d.ts","sourceRoot":"","sources":["../../../src/genomeSpy/viewDataInit.js"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"viewDataInit.d.ts","sourceRoot":"","sources":["../../../src/genomeSpy/viewDataInit.js"],"names":[],"mappings":"AAOA;;;;;;;;;GASG;AACH,6CANW,OAAO,iBAAiB,EAAE,OAAO,YACjC,OAAO,qBAAqB,EAAE,OAAO,eACrC,OAAO,2BAA2B,EAAE,OAAO,mBAC3C,CAAC,QAAQ,EAAE,OAAO,qBAAqB,EAAE,OAAO,KAAK,IAAI,GACvD,OAAO,CAAC,OAAO,qBAAqB,EAAE,OAAO,CAAC,CAkC1D;AAED;;;;;;;;GAQG;AACH,oDALW,OAAO,iBAAiB,EAAE,OAAO,YACjC,OAAO,qBAAqB,EAAE,OAAO,eACrC,OAAO,2BAA2B,EAAE,OAAO,GACzC,OAAO,CAAC,OAAO,qBAAqB,EAAE,OAAO,CAAC,CA2E1D"}
|
|
@@ -3,6 +3,7 @@ import {
|
|
|
3
3
|
loadViewSubtreeData,
|
|
4
4
|
} from "../data/flowInit.js";
|
|
5
5
|
import { finalizeSubtreeGraphics } from "../view/viewUtils.js";
|
|
6
|
+
import { VISIT_SKIP } from "../view/view.js";
|
|
6
7
|
|
|
7
8
|
/**
|
|
8
9
|
* Initializes the view data pipeline: builds the flow graph, awaits fonts,
|
|
@@ -20,9 +21,13 @@ export async function initializeViewData(
|
|
|
20
21
|
fontManager,
|
|
21
22
|
onDataFlowBuilt
|
|
22
23
|
) {
|
|
24
|
+
const visibilityPredicate = (
|
|
25
|
+
/** @type {import("../view/view.js").default} */ view
|
|
26
|
+
) => view.isConfiguredVisible();
|
|
23
27
|
const { dataFlow: builtDataFlow, graphicsPromises } = initializeViewSubtree(
|
|
24
28
|
viewRoot,
|
|
25
|
-
dataFlow
|
|
29
|
+
dataFlow,
|
|
30
|
+
visibilityPredicate
|
|
26
31
|
);
|
|
27
32
|
onDataFlowBuilt(builtDataFlow);
|
|
28
33
|
|
|
@@ -33,9 +38,168 @@ export async function initializeViewData(
|
|
|
33
38
|
await fontManager.waitUntilReady();
|
|
34
39
|
|
|
35
40
|
// Find all data sources and initiate loading.
|
|
36
|
-
await loadViewSubtreeData(
|
|
41
|
+
await loadViewSubtreeData(
|
|
42
|
+
viewRoot,
|
|
43
|
+
new Set(builtDataFlow.dataSources),
|
|
44
|
+
visibilityPredicate
|
|
45
|
+
);
|
|
46
|
+
|
|
47
|
+
await finalizeSubtreeGraphics(graphicsPromises);
|
|
48
|
+
|
|
49
|
+
return builtDataFlow;
|
|
50
|
+
}
|
|
51
|
+
|
|
52
|
+
/**
|
|
53
|
+
* Initializes data flow and graphics for visible views that were previously
|
|
54
|
+
* skipped. Intended for view-visibility toggles.
|
|
55
|
+
*
|
|
56
|
+
* @param {import("../view/view.js").default} viewRoot
|
|
57
|
+
* @param {import("../data/dataFlow.js").default} dataFlow
|
|
58
|
+
* @param {import("../fonts/bmFontManager.js").default} fontManager
|
|
59
|
+
* @returns {Promise<import("../data/dataFlow.js").default>}
|
|
60
|
+
*/
|
|
61
|
+
export async function initializeVisibleViewData(
|
|
62
|
+
viewRoot,
|
|
63
|
+
dataFlow,
|
|
64
|
+
fontManager
|
|
65
|
+
) {
|
|
66
|
+
// Initialize dataflow/graphics for views that have become visible since the
|
|
67
|
+
// initial load, while avoiding unnecessary data source reloads. If a view
|
|
68
|
+
// attaches downstream of an already completed collector, repropagate that
|
|
69
|
+
// collector instead of reloading the source.
|
|
70
|
+
const visibilityPredicate = (
|
|
71
|
+
/** @type {import("../view/view.js").default} */ view
|
|
72
|
+
) => view.isConfiguredVisible();
|
|
73
|
+
const visibleViews = collectVisibleViews(viewRoot, visibilityPredicate);
|
|
74
|
+
const viewsToInitialize = visibleViews.filter(
|
|
75
|
+
(view) => view.getDataInitializationState() === "none"
|
|
76
|
+
);
|
|
77
|
+
|
|
78
|
+
if (viewsToInitialize.length === 0) {
|
|
79
|
+
return dataFlow;
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
const viewsToInitializeSet = new Set(viewsToInitialize);
|
|
83
|
+
const viewInitializationPredicate = (
|
|
84
|
+
/** @type {import("../view/view.js").default} */ view
|
|
85
|
+
) => viewsToInitializeSet.has(view);
|
|
86
|
+
|
|
87
|
+
/** @type {Set<import("../data/collector.js").default>} */
|
|
88
|
+
const collectorsToRepropagate = new Set();
|
|
89
|
+
/** @type {import("../view/view.js").default[]} */
|
|
90
|
+
const viewsNeedingLoad = [];
|
|
91
|
+
for (const view of viewsToInitialize) {
|
|
92
|
+
if (view.spec.data) {
|
|
93
|
+
viewsNeedingLoad.push(view);
|
|
94
|
+
continue;
|
|
95
|
+
}
|
|
96
|
+
const collector = findCompletedAncestorCollector(view);
|
|
97
|
+
if (collector) {
|
|
98
|
+
collectorsToRepropagate.add(collector);
|
|
99
|
+
} else {
|
|
100
|
+
viewsNeedingLoad.push(view);
|
|
101
|
+
}
|
|
102
|
+
}
|
|
103
|
+
|
|
104
|
+
const { dataFlow: builtDataFlow, graphicsPromises } = initializeViewSubtree(
|
|
105
|
+
viewRoot,
|
|
106
|
+
dataFlow,
|
|
107
|
+
visibilityPredicate,
|
|
108
|
+
viewInitializationPredicate
|
|
109
|
+
);
|
|
110
|
+
|
|
111
|
+
await fontManager.waitUntilReady();
|
|
112
|
+
|
|
113
|
+
for (const collector of collectorsToRepropagate) {
|
|
114
|
+
collector.repropagate();
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
if (viewsNeedingLoad.length) {
|
|
118
|
+
const dataSourceRoots = collectDataSourceRoots(viewsNeedingLoad);
|
|
119
|
+
await Promise.all(
|
|
120
|
+
Array.from(dataSourceRoots.entries()).map(
|
|
121
|
+
([subtreeRoot, dataSources]) =>
|
|
122
|
+
loadViewSubtreeData(subtreeRoot, dataSources, undefined, {
|
|
123
|
+
// If a source is already loading, schedule a reload so new branches
|
|
124
|
+
// added during lazy init receive a complete data propagation.
|
|
125
|
+
queueReload: true,
|
|
126
|
+
})
|
|
127
|
+
)
|
|
128
|
+
);
|
|
129
|
+
}
|
|
37
130
|
|
|
38
131
|
await finalizeSubtreeGraphics(graphicsPromises);
|
|
39
132
|
|
|
40
133
|
return builtDataFlow;
|
|
41
134
|
}
|
|
135
|
+
|
|
136
|
+
/**
|
|
137
|
+
* @param {import("../view/view.js").default} viewRoot
|
|
138
|
+
* @param {(view: import("../view/view.js").default) => boolean} viewFilter
|
|
139
|
+
* @returns {import("../view/view.js").default[]}
|
|
140
|
+
*/
|
|
141
|
+
function collectVisibleViews(viewRoot, viewFilter) {
|
|
142
|
+
/** @type {import("../view/view.js").default[]} */
|
|
143
|
+
const views = [];
|
|
144
|
+
viewRoot.visit((view) => {
|
|
145
|
+
if (!viewFilter(view)) {
|
|
146
|
+
return VISIT_SKIP;
|
|
147
|
+
}
|
|
148
|
+
views.push(view);
|
|
149
|
+
});
|
|
150
|
+
return views;
|
|
151
|
+
}
|
|
152
|
+
|
|
153
|
+
/**
|
|
154
|
+
* @param {import("../view/view.js").default[]} views
|
|
155
|
+
* @returns {Map<import("../view/view.js").default, Set<import("../data/sources/dataSource.js").default>>}
|
|
156
|
+
*/
|
|
157
|
+
function collectDataSourceRoots(views) {
|
|
158
|
+
/** @type {Map<import("../view/view.js").default, Set<import("../data/sources/dataSource.js").default>>} */
|
|
159
|
+
const roots = new Map();
|
|
160
|
+
|
|
161
|
+
for (const view of views) {
|
|
162
|
+
let current = view;
|
|
163
|
+
while (current && !current.flowHandle?.dataSource) {
|
|
164
|
+
current = current.dataParent;
|
|
165
|
+
}
|
|
166
|
+
|
|
167
|
+
if (!current?.flowHandle?.dataSource) {
|
|
168
|
+
if (view.spec.data) {
|
|
169
|
+
throw new Error(
|
|
170
|
+
"No data source found for view " + view.getPathString()
|
|
171
|
+
);
|
|
172
|
+
}
|
|
173
|
+
// Some views are data-less (constants or references); they don't
|
|
174
|
+
// participate in data loading but still need graphics init.
|
|
175
|
+
continue;
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
let dataSources = roots.get(current);
|
|
179
|
+
if (!dataSources) {
|
|
180
|
+
dataSources = new Set();
|
|
181
|
+
roots.set(current, dataSources);
|
|
182
|
+
}
|
|
183
|
+
dataSources.add(current.flowHandle.dataSource);
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
return roots;
|
|
187
|
+
}
|
|
188
|
+
|
|
189
|
+
/**
|
|
190
|
+
* Finds the nearest completed collector in the dataParent chain.
|
|
191
|
+
*
|
|
192
|
+
* @param {import("../view/view.js").default} view
|
|
193
|
+
* @returns {import("../data/collector.js").default | undefined}
|
|
194
|
+
*/
|
|
195
|
+
function findCompletedAncestorCollector(view) {
|
|
196
|
+
let current = view.dataParent;
|
|
197
|
+
while (current) {
|
|
198
|
+
const collector = current.flowHandle?.collector;
|
|
199
|
+
if (collector) {
|
|
200
|
+
return collector.completed ? collector : undefined;
|
|
201
|
+
}
|
|
202
|
+
current = current.dataParent;
|
|
203
|
+
}
|
|
204
|
+
return undefined;
|
|
205
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"viewDataInit.test.d.ts","sourceRoot":"","sources":["../../../src/genomeSpy/viewDataInit.test.js"],"names":[],"mappings":""}
|
package/dist/src/genomeSpy.d.ts
CHANGED
|
@@ -66,8 +66,6 @@ export default class GenomeSpy {
|
|
|
66
66
|
* @param {any} [payload]
|
|
67
67
|
*/
|
|
68
68
|
broadcast(type: BroadcastEventType, payload?: any): void;
|
|
69
|
-
loadingMessageElement: HTMLElement;
|
|
70
|
-
loadingIndicatorsElement: HTMLElement;
|
|
71
69
|
tooltip: import("./utils/ui/tooltip.js").default;
|
|
72
70
|
/**
|
|
73
71
|
* Unregisters all listeners, removes all created dom elements, removes all css classes from the container
|
|
@@ -78,6 +76,7 @@ export default class GenomeSpy {
|
|
|
78
76
|
* @returns {Promise<boolean>} true if the launch was successful
|
|
79
77
|
*/
|
|
80
78
|
launch(): Promise<boolean>;
|
|
79
|
+
initializeVisibleViewData(): Promise<void>;
|
|
81
80
|
registerMouseEvents(): void;
|
|
82
81
|
/**
|
|
83
82
|
* This method should be called in a mouseMove handler. If not called, the
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"genomeSpy.d.ts","sourceRoot":"","sources":["../../src/genomeSpy.js"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"genomeSpy.d.ts","sourceRoot":"","sources":["../../src/genomeSpy.js"],"names":[],"mappings":"AA+CA;IAoBI;;;;;OAKG;IAEH;;;;;OAKG;IACH,uBAJW,WAAW,qDAEX,OAAO,qBAAqB,EAAE,YAAY,EA0CpD;IAvCG,uBAA0B;IAC1B,oDAAsB;IAItB,sCAAsC;IACtC,wCAAgB;IAEhB,yBAAoC;IAEpC,4CAA4C;IAC5C,oBADW,CAAC,CAAS,IAAM,EAAN,MAAM,KAAE,MAAM,EAAE,CAAC,EAAE,CACZ;IAE5B,mBAAoD;IAEpD,0BAA0B;IAC1B,aADW,WAAW,CACM;IAE5B;;;;;OAKG;IACH,yBAFU,CAAC,IAAI,kCAAM,KAAK,OAAO,CAE8B;IAE/D,oFAAoF;IACpF,iBADW,MAAM,CAAC,MAAM,EAAE,OAAO,6BAA6B,EAAE,cAAc,CAAC,CAK9E;IAED,mBAAmB;IACnB,2CAAyB;IAIzB,YAAkC;IAatC;;;OAGG;IACH,oCAFW,CAAC,IAAI,EAAE,MAAM,KAAK,GAAG,EAAE,QAIjC;IAED;;OAEG;IACH,+BAFW,MAAM,YAShB;IAED;;;;OAIG;IACH,sBAHW,MAAM,QACN,GAAG,EAAE,QAYf;IAED;;;OAGG;IACH,uBAHW,MAAM,YACN,CAAC,KAAK,EAAE,GAAG,KAAK,IAAI,QAI9B;IAED;;;OAGG;IACH,0BAHW,MAAM,YACN,CAAC,KAAK,EAAE,GAAG,KAAK,IAAI,QAI9B;IAED;;;;;OAKG;IACH,gBAHW,kBAAkB,YAClB,GAAG,QAMb;IA4DG,iDAAsB;IAQ1B;;OAEG;IACH,gBAqBC;IAyJD;;;OAGG;IACH,UAFa,OAAO,CAAC,OAAO,CAAC,CAyC5B;IAED,2CAiBC;IAED,4BAEC;IAED;;;;;;;OAOG;IACH,cAFa,CAAC,SAFH,CAAC,cACD,CAAS,IAAC,EAAD,CAAC,KAAE,OAAO,CAAC,MAAM,GAAG,WAAW,GAAG,OAAO,KAAK,EAAE,cAAc,CAAC,QAKlF;IAED;;;;;;;;OAQG;IACH,4BANW,MAAM,kBACN,MAAM,qBACN,MAAM,eACN,MAAM,UAuBhB;IAED;;;MAEC;IAED,sBAEC;IAED,kBAEC;IAED,iCAEC;IAED,iCAYC;IAED,uFAWC;;CACJ;;;;iCAviBY,eAAe,GAAG,QAAQ,GAAG,gBAAgB,GAAG,kBAAkB;4BAbnC,uBAAuB;qBAR9C,qBAAqB;wBAElB,yBAAyB;qBAL5B,oBAAoB"}
|