@jbrowse/bandage-core 10.2.2 → 10.2.4
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/README.md +8 -7
- package/dist/bubbles/bubbleHalos.js +7 -3
- package/dist/bubbles/bubblesFromGraph.js +4 -2
- package/dist/bubbles/classifyBubble.js +10 -5
- package/dist/bubbles/superbubbles.js +10 -6
- package/dist/chunks/{chunk-N6FECAXP.js → chunk-24WITXQY.js} +17 -8
- package/dist/chunks/{chunk-EYK7DJZV.js → chunk-2CHS5LMM.js} +1 -1
- package/dist/chunks/{chunk-XTCNEKO5.js → chunk-2QLLQJ72.js} +15 -13
- package/dist/chunks/{chunk-TWRLC3KK.js → chunk-3XSM4OZU.js} +1 -1
- package/dist/chunks/{chunk-WEDZ76AK.js → chunk-4DRQTBBE.js} +1 -1
- package/dist/chunks/{chunk-2LQ5BWT7.js → chunk-4ETPXDO6.js} +1 -1
- package/dist/chunks/{chunk-FP4H7SFT.js → chunk-4HWM3FNK.js} +2 -2
- package/dist/chunks/{chunk-C7MZJSPT.js → chunk-54POIBVC.js} +2 -8
- package/dist/chunks/{chunk-PKFMP65V.js → chunk-5GMFEPWR.js} +1 -1
- package/dist/chunks/{chunk-CDLPYR5O.js → chunk-5I3K4R2G.js} +7 -6
- package/dist/chunks/{chunk-2CVHXFK7.js → chunk-7SRWJLSC.js} +19 -22
- package/dist/chunks/{chunk-SBMJNRTV.js → chunk-A4PFFC4Q.js} +37 -27
- package/dist/chunks/{chunk-FNGIQF43.js → chunk-ABUIN5AK.js} +6 -14
- package/dist/chunks/{chunk-IW6CYVX2.js → chunk-AR4BUBMU.js} +6 -1
- package/dist/chunks/{chunk-IUDJKOLB.js → chunk-B6IW3IRE.js} +15 -33
- package/dist/chunks/{chunk-JUIJI7RC.js → chunk-BAETMD3J.js} +9 -4
- package/dist/chunks/{chunk-L5WF4ZPS.js → chunk-BS4UZ44I.js} +1 -1
- package/dist/chunks/{chunk-HNQPEMYE.js → chunk-CM6LO6OC.js} +0 -1
- package/dist/chunks/{chunk-CLOP7UVD.js → chunk-CQHUZHET.js} +11 -8
- package/dist/chunks/{chunk-R456ME6J.js → chunk-CU6P5RUG.js} +17 -6
- package/dist/chunks/chunk-D5D36ZF6.js +107 -0
- package/dist/chunks/{chunk-AFP3NWSL.js → chunk-DY3JCAMX.js} +1 -1
- package/dist/chunks/{chunk-NRV7R36Q.js → chunk-EFQLEGWM.js} +3 -3
- package/dist/chunks/{chunk-BXEPA4KS.js → chunk-G6UIYQZR.js} +5 -2
- package/dist/chunks/{chunk-ASSNZXCF.js → chunk-GINYTQ43.js} +44 -103
- package/dist/chunks/{chunk-NNODIW4U.js → chunk-H2H4Y3TV.js} +1 -0
- package/dist/chunks/{chunk-MVFDSFV2.js → chunk-HNCXR2VS.js} +1 -1
- package/dist/chunks/chunk-JA2HJIYS.js +71 -0
- package/dist/chunks/{chunk-PBENCR5L.js → chunk-JBCZIBFC.js} +0 -2
- package/dist/chunks/{chunk-5BGP5Z64.js → chunk-JLSJMCDJ.js} +1 -1
- package/dist/chunks/{chunk-DT2GGH4D.js → chunk-JMABOQWL.js} +2 -6
- package/dist/chunks/{chunk-3S3YVOJ7.js → chunk-JSUCGZ6K.js} +1 -1
- package/dist/chunks/{chunk-MLSWIMZO.js → chunk-KBEP7VYK.js} +2 -2
- package/dist/chunks/{chunk-DRG4236Y.js → chunk-KC7T5RWG.js} +2 -20
- package/dist/chunks/{chunk-TAMCZHLW.js → chunk-N73TI3VG.js} +2 -2
- package/dist/chunks/chunk-O4EGE27I.js +10 -0
- package/dist/chunks/{chunk-3ZZSX5HN.js → chunk-PTABFYQ7.js} +10 -6
- package/dist/chunks/{chunk-WBCOREDZ.js → chunk-QLWI2PZ3.js} +16 -7
- package/dist/chunks/chunk-RBCE2OQH.js +32 -0
- package/dist/chunks/{chunk-BUBZ32IC.js → chunk-RPRHR56C.js} +4 -8
- package/dist/chunks/{chunk-47DYCZOK.js → chunk-RUCH6ZFL.js} +4 -0
- package/dist/chunks/{chunk-GNTTI6LA.js → chunk-T2PCSAFY.js} +1 -1
- package/dist/chunks/{chunk-XKWD2RY3.js → chunk-URZ3CH2R.js} +3 -10
- package/dist/chunks/{chunk-ALDGONEI.js → chunk-VQC7KELB.js} +1 -1
- package/dist/chunks/{chunk-FLFBYSJO.js → chunk-VQWHMWLF.js} +5 -1
- package/dist/chunks/{chunk-4R6QNG23.js → chunk-WL6ZKUVC.js} +3 -3
- package/dist/chunks/{chunk-CRTD2SBP.js → chunk-WZNPX7Q6.js} +6 -2
- package/dist/chunks/{chunk-TICYLD5F.js → chunk-XAWLIU54.js} +35 -78
- package/dist/chunks/{chunk-DK5P2YOL.js → chunk-XI3ZUTWF.js} +2 -2
- package/dist/chunks/{chunk-ZIUKZUPJ.js → chunk-XL472HHD.js} +1 -1
- package/dist/chunks/{chunk-BPRXQ2SS.js → chunk-XMW266WS.js} +1 -1
- package/dist/chunks/{chunk-WFB5TXRA.js → chunk-ZY2AFL4Y.js} +13 -31
- package/dist/cli/decodeText.js +6 -0
- package/dist/cli/figure.js +59 -60
- package/dist/cli/fold.js +13 -13
- package/dist/deletionEdges.js +6 -4
- package/dist/el.js +3 -1
- package/dist/figure.js +33 -31
- package/dist/figureData.js +32 -27
- package/dist/figureScene.js +43 -0
- package/dist/figureSettings.js +8 -8
- package/dist/foldVariants.js +2 -2
- package/dist/gbzCut.js +1 -1
- package/dist/genes/exonOutline.js +2 -2
- package/dist/genes/geneFiles.js +1 -1
- package/dist/genes/genePins.js +3 -3
- package/dist/gfa/gfaConverter.js +2 -2
- package/dist/gfa-core/gfaParser.js +1 -1
- package/dist/gfa-core/index.js +1 -1
- package/dist/graphLabels.js +4 -4
- package/dist/index.js +72 -73
- package/dist/labelLayout.js +8 -8
- package/dist/layout/forceCache.js +8 -8
- package/dist/layout/mergeRuns.js +2 -2
- package/dist/layout/orderedLayout.js +1 -3
- package/dist/layout/tubeMapLayout.js +6 -6
- package/dist/layout/walkRowDraw.js +11 -11
- package/dist/layout/walkRowLayout.js +3 -1
- package/dist/layout/walkStrip.js +14 -12
- package/dist/layoutEngines.js +1 -2
- package/dist/layoutModes.js +9 -9
- package/dist/nodeWidths.js +1 -3
- package/dist/pathColors.js +5 -5
- package/dist/pipeline.js +7 -7
- package/dist/referenceRampCss.js +9 -9
- package/dist/referenceStrip.js +9 -9
- package/dist/renderer/Canvas2DRenderer.js +2 -2
- package/dist/renderer/GeometryBuilder.js +8 -8
- package/dist/renderer/canvas.js +1 -1
- package/dist/renderer/svgCanvas.js +1 -1
- package/dist/tubeMap/axis.js +5 -5
- package/dist/tubeMap/bundle.js +7 -7
- package/dist/tubeMap/coarsen.js +6 -6
- package/dist/tubeMap/deviations.js +5 -5
- package/dist/tubeMap/draw.js +1 -1
- package/dist/tubeMap/genes.js +6 -6
- package/dist/tubeMap/nodeColors.js +9 -9
- package/dist/types/bubbles/bubbleHalos.d.ts +2 -8
- package/dist/types/bubbles/bubblesFromGraph.d.ts +1 -0
- package/dist/types/bubbles/classifyBubble.d.ts +0 -1
- package/dist/types/cli/decodeText.d.ts +1 -0
- package/dist/types/cli/figure.d.ts +4 -15
- package/dist/types/deletionEdges.d.ts +3 -5
- package/dist/types/el.d.ts +1 -0
- package/dist/types/figureData.d.ts +7 -26
- package/dist/types/figureScene.d.ts +31 -0
- package/dist/types/genes/geneFiles.d.ts +2 -1
- package/dist/types/index.d.ts +1 -1
- package/dist/types/labelLayout.d.ts +1 -5
- package/dist/types/layout/deletionRoutes.d.ts +1 -1
- package/dist/types/layout/orderedLayout.d.ts +0 -6
- package/dist/types/layout/walkRowLayout.d.ts +1 -0
- package/dist/types/nodeWidths.d.ts +0 -1
- package/dist/types/renderer/Canvas2DRenderer.d.ts +1 -0
- package/dist/types/renderer/canvas.d.ts +2 -2
- package/dist/types/tubeMap/draw.d.ts +1 -0
- package/dist/types/util/geometry.d.ts +3 -3
- package/dist/types/version.d.ts +1 -1
- package/dist/util/SpatialIndex.js +4 -4
- package/dist/util/edgeCurves.js +3 -3
- package/dist/util/geometry.js +3 -3
- package/dist/util/hitDetection.js +5 -5
- package/dist/version.js +1 -1
- package/dist/viewport.js +8 -8
- package/dist/walkEncoding.js +9 -9
- package/dist/walkHighlight.js +10 -10
- package/dist/walkKey.js +5 -5
- package/package.json +3 -6
- package/dist/chunks/bandage-layout-3AR6BCUD.js +0 -4694
- package/dist/chunks/chunk-4BYTEJGW.js +0 -44
- package/dist/chunks/chunk-7XHHVYG7.js +0 -13
- package/dist/chunks/chunk-EHUBJDDB.js +0 -135
- package/dist/loadBandage.js +0 -6
- package/dist/types/bandage/bandage-layout.d.ts +0 -14
- package/dist/types/loadBandage.d.ts +0 -3
package/README.md
CHANGED
|
@@ -10,8 +10,10 @@ npm install @jbrowse/bandage-core
|
|
|
10
10
|
|
|
11
11
|
- GFA and rGFA text in (`loadGraph`), or the same graph as typed arrays a worker
|
|
12
12
|
can transfer (`GraphTables`)
|
|
13
|
-
- Layouts: Bandage's FMMM engine as WASM
|
|
14
|
-
|
|
13
|
+
- Layouts: Bandage's FMMM engine as WASM from
|
|
14
|
+
[@jbrowse/graph-fmmm-layout](https://github.com/GMOD/graph-fmmm-layout)
|
|
15
|
+
(`loadBandage`, `forceLayout`), ordered, anchored, sample rows, walk rows,
|
|
16
|
+
tube map
|
|
15
17
|
- A Canvas2D renderer (`buildGeometry`, `Canvas2DRenderer`), hit testing and
|
|
16
18
|
label placement
|
|
17
19
|
- Bubbles, deletion edges, path colors, gbz-base windows cut to GFA
|
|
@@ -42,13 +44,10 @@ the worked example.
|
|
|
42
44
|
pnpm install
|
|
43
45
|
pnpm test # unit tests
|
|
44
46
|
pnpm build # dist/ with declarations
|
|
45
|
-
pnpm test:wasm # the committed layout engine still loads
|
|
46
47
|
```
|
|
47
48
|
|
|
48
|
-
The
|
|
49
|
-
|
|
50
|
-
says how to rebuild it from `src/bandage/native` and the vendored `vendor/ogdf`.
|
|
51
|
-
A weekly workflow proves the committed artifact still reproduces.
|
|
49
|
+
The FMMM engine and its wasm build live in
|
|
50
|
+
[graph-fmmm-layout](https://github.com/GMOD/graph-fmmm-layout).
|
|
52
51
|
|
|
53
52
|
CI also packs the core and runs
|
|
54
53
|
[BandageJS](https://github.com/cmdcolin/BandageJS) and
|
|
@@ -66,6 +65,8 @@ publishes to npm with trusted publishing.
|
|
|
66
65
|
JBrowse 2 plugin that browses these graphs by locus
|
|
67
66
|
- [BandageJS](https://github.com/cmdcolin/BandageJS) - standalone page for GFA
|
|
68
67
|
and gbz-base graphs
|
|
68
|
+
- [@jbrowse/graph-fmmm-layout](https://github.com/GMOD/graph-fmmm-layout) -
|
|
69
|
+
Bandage's FMMM layout as wasm
|
|
69
70
|
- [@jbrowse/graph-stress-layout](https://github.com/GMOD/graph-stress-layout) -
|
|
70
71
|
stress layout that keeps the reference straight
|
|
71
72
|
- [@gmod/gbz-base](https://github.com/GMOD/gbz-base-js) - range-request reader
|
|
@@ -3,10 +3,14 @@ import {
|
|
|
3
3
|
WHOLE_FRACTION,
|
|
4
4
|
bubbleHalos,
|
|
5
5
|
coversGraph
|
|
6
|
-
} from "../chunks/chunk-
|
|
7
|
-
import "../chunks/chunk-
|
|
6
|
+
} from "../chunks/chunk-JA2HJIYS.js";
|
|
7
|
+
import "../chunks/chunk-URZ3CH2R.js";
|
|
8
8
|
import "../chunks/chunk-FX4RDMDN.js";
|
|
9
|
-
import "../chunks/chunk-
|
|
9
|
+
import "../chunks/chunk-PTABFYQ7.js";
|
|
10
|
+
import "../chunks/chunk-AB35TJST.js";
|
|
11
|
+
import "../chunks/chunk-N73TI3VG.js";
|
|
12
|
+
import "../chunks/chunk-24WITXQY.js";
|
|
13
|
+
import "../chunks/chunk-7SRWJLSC.js";
|
|
10
14
|
import "../chunks/chunk-CPMHA4W5.js";
|
|
11
15
|
import "../chunks/chunk-FYQWPEEY.js";
|
|
12
16
|
export {
|
|
@@ -1,14 +1,16 @@
|
|
|
1
1
|
import {
|
|
2
2
|
bubblesFromGraph,
|
|
3
|
+
relax,
|
|
3
4
|
walkIndexOf,
|
|
4
5
|
walkRoutes
|
|
5
|
-
} from "../chunks/chunk-
|
|
6
|
+
} from "../chunks/chunk-CQHUZHET.js";
|
|
6
7
|
import "../chunks/chunk-FX4RDMDN.js";
|
|
7
|
-
import "../chunks/chunk-
|
|
8
|
+
import "../chunks/chunk-CM6LO6OC.js";
|
|
8
9
|
import "../chunks/chunk-CPMHA4W5.js";
|
|
9
10
|
import "../chunks/chunk-FYQWPEEY.js";
|
|
10
11
|
export {
|
|
11
12
|
bubblesFromGraph,
|
|
13
|
+
relax,
|
|
12
14
|
walkIndexOf,
|
|
13
15
|
walkRoutes
|
|
14
16
|
};
|
|
@@ -2,14 +2,19 @@ import {
|
|
|
2
2
|
BUBBLE_KIND_COLORS,
|
|
3
3
|
BUBBLE_KIND_NAMES,
|
|
4
4
|
bubbleSegmentIds,
|
|
5
|
-
classifyBubble
|
|
6
|
-
|
|
7
|
-
} from "../chunks/chunk-XKWD2RY3.js";
|
|
5
|
+
classifyBubble
|
|
6
|
+
} from "../chunks/chunk-URZ3CH2R.js";
|
|
8
7
|
import "../chunks/chunk-FX4RDMDN.js";
|
|
8
|
+
import "../chunks/chunk-PTABFYQ7.js";
|
|
9
|
+
import "../chunks/chunk-AB35TJST.js";
|
|
10
|
+
import "../chunks/chunk-N73TI3VG.js";
|
|
11
|
+
import "../chunks/chunk-24WITXQY.js";
|
|
12
|
+
import "../chunks/chunk-7SRWJLSC.js";
|
|
13
|
+
import "../chunks/chunk-CPMHA4W5.js";
|
|
14
|
+
import "../chunks/chunk-FYQWPEEY.js";
|
|
9
15
|
export {
|
|
10
16
|
BUBBLE_KIND_COLORS,
|
|
11
17
|
BUBBLE_KIND_NAMES,
|
|
12
18
|
bubbleSegmentIds,
|
|
13
|
-
classifyBubble
|
|
14
|
-
formatBp
|
|
19
|
+
classifyBubble
|
|
15
20
|
};
|
|
@@ -1,17 +1,21 @@
|
|
|
1
1
|
import {
|
|
2
2
|
graphBubbles,
|
|
3
3
|
superbubblesFromGraph
|
|
4
|
-
} from "../chunks/chunk-
|
|
5
|
-
import "../chunks/chunk-
|
|
4
|
+
} from "../chunks/chunk-ABUIN5AK.js";
|
|
5
|
+
import "../chunks/chunk-CQHUZHET.js";
|
|
6
6
|
import "../chunks/chunk-T6V4KI2L.js";
|
|
7
|
-
import "../chunks/chunk-
|
|
8
|
-
import "../chunks/chunk-
|
|
7
|
+
import "../chunks/chunk-JA2HJIYS.js";
|
|
8
|
+
import "../chunks/chunk-URZ3CH2R.js";
|
|
9
9
|
import "../chunks/chunk-FX4RDMDN.js";
|
|
10
|
-
import "../chunks/chunk-
|
|
10
|
+
import "../chunks/chunk-CM6LO6OC.js";
|
|
11
11
|
import "../chunks/chunk-M6LK4GII.js";
|
|
12
12
|
import "../chunks/chunk-RAEABQNW.js";
|
|
13
13
|
import "../chunks/chunk-BPLIXMH7.js";
|
|
14
|
-
import "../chunks/chunk-
|
|
14
|
+
import "../chunks/chunk-PTABFYQ7.js";
|
|
15
|
+
import "../chunks/chunk-AB35TJST.js";
|
|
16
|
+
import "../chunks/chunk-N73TI3VG.js";
|
|
17
|
+
import "../chunks/chunk-24WITXQY.js";
|
|
18
|
+
import "../chunks/chunk-7SRWJLSC.js";
|
|
15
19
|
import "../chunks/chunk-CPMHA4W5.js";
|
|
16
20
|
import "../chunks/chunk-FYQWPEEY.js";
|
|
17
21
|
export {
|
|
@@ -3,7 +3,7 @@ import {
|
|
|
3
3
|
edgeJoinOf,
|
|
4
4
|
routedEdgeCurves,
|
|
5
5
|
strandSides
|
|
6
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-7SRWJLSC.js";
|
|
7
7
|
import {
|
|
8
8
|
firstNodeAtOrAfter,
|
|
9
9
|
isBackbone
|
|
@@ -15,8 +15,18 @@ function bypassedPoints(nodePositions, bypassed) {
|
|
|
15
15
|
return bypassed.flatMap((id) => nodePositions[id] ?? []);
|
|
16
16
|
}
|
|
17
17
|
function deletionArcCurves(nodePositions, deletion, axis, route, stranded = false) {
|
|
18
|
-
|
|
19
|
-
|
|
18
|
+
return edgeCurvesOf(
|
|
19
|
+
nodePositions,
|
|
20
|
+
deletion,
|
|
21
|
+
axis,
|
|
22
|
+
deletion.bypassed,
|
|
23
|
+
route,
|
|
24
|
+
stranded
|
|
25
|
+
);
|
|
26
|
+
}
|
|
27
|
+
function edgeCurvesOf(nodePositions, edge, axis, bypassed, route, stranded) {
|
|
28
|
+
const from = nodePositions[edge.from];
|
|
29
|
+
const to = nodePositions[edge.to];
|
|
20
30
|
if (!from?.length || !to?.length) {
|
|
21
31
|
return void 0;
|
|
22
32
|
}
|
|
@@ -24,15 +34,13 @@ function deletionArcCurves(nodePositions, deletion, axis, route, stranded = fals
|
|
|
24
34
|
from,
|
|
25
35
|
to,
|
|
26
36
|
route,
|
|
27
|
-
stranded ? strandSides(
|
|
37
|
+
stranded ? strandSides(edge) : void 0
|
|
28
38
|
) : computeEdgeCurves(
|
|
29
39
|
from,
|
|
30
40
|
to,
|
|
31
|
-
edgeJoinOf(
|
|
32
|
-
0,
|
|
33
|
-
0,
|
|
41
|
+
edgeJoinOf(edge, stranded),
|
|
34
42
|
axis,
|
|
35
|
-
bypassedPoints(nodePositions,
|
|
43
|
+
bypassed ? bypassedPoints(nodePositions, bypassed) : []
|
|
36
44
|
);
|
|
37
45
|
}
|
|
38
46
|
function backboneBySequence(graph) {
|
|
@@ -161,6 +169,7 @@ function deletionDrawing(graph, deletions, show = true) {
|
|
|
161
169
|
export {
|
|
162
170
|
bypassedPoints,
|
|
163
171
|
deletionArcCurves,
|
|
172
|
+
edgeCurvesOf,
|
|
164
173
|
deletionEdges,
|
|
165
174
|
closableDeletions,
|
|
166
175
|
deletionDrawing
|
|
@@ -1,3 +1,6 @@
|
|
|
1
|
+
import {
|
|
2
|
+
orientToReference
|
|
3
|
+
} from "./chunk-PUG7LXDF.js";
|
|
1
4
|
import {
|
|
2
5
|
seededNodes
|
|
3
6
|
} from "./chunk-IGVV37VI.js";
|
|
@@ -9,18 +12,15 @@ import {
|
|
|
9
12
|
takeRoutes,
|
|
10
13
|
withDeletionRoutes
|
|
11
14
|
} from "./chunk-VPE4AYP7.js";
|
|
12
|
-
import {
|
|
13
|
-
orientToReference
|
|
14
|
-
} from "./chunk-PUG7LXDF.js";
|
|
15
15
|
import {
|
|
16
16
|
convertGFAToGraph
|
|
17
|
-
} from "./chunk-
|
|
17
|
+
} from "./chunk-AR4BUBMU.js";
|
|
18
|
+
import {
|
|
19
|
+
parseGFA
|
|
20
|
+
} from "./chunk-5I3K4R2G.js";
|
|
18
21
|
import {
|
|
19
22
|
graphFromTables
|
|
20
23
|
} from "./chunk-PSMKPSO4.js";
|
|
21
|
-
import {
|
|
22
|
-
parseGFA
|
|
23
|
-
} from "./chunk-CDLPYR5O.js";
|
|
24
24
|
import {
|
|
25
25
|
anchorGraph
|
|
26
26
|
} from "./chunk-M6LK4GII.js";
|
|
@@ -30,7 +30,7 @@ import {
|
|
|
30
30
|
import {
|
|
31
31
|
mergeRuns,
|
|
32
32
|
splitRuns
|
|
33
|
-
} from "./chunk-
|
|
33
|
+
} from "./chunk-N73TI3VG.js";
|
|
34
34
|
import {
|
|
35
35
|
spreadFor
|
|
36
36
|
} from "./chunk-UVBGRJQX.js";
|
|
@@ -40,9 +40,9 @@ import {
|
|
|
40
40
|
layoutScaling
|
|
41
41
|
} from "./chunk-6JEWNXCQ.js";
|
|
42
42
|
import {
|
|
43
|
-
|
|
43
|
+
deletionDrawing,
|
|
44
44
|
deletionEdges
|
|
45
|
-
} from "./chunk-
|
|
45
|
+
} from "./chunk-24WITXQY.js";
|
|
46
46
|
import {
|
|
47
47
|
isBackbone
|
|
48
48
|
} from "./chunk-FYQWPEEY.js";
|
|
@@ -118,9 +118,11 @@ function engineKey(graph, settings) {
|
|
|
118
118
|
}
|
|
119
119
|
async function forceLayout(graph, settings, engine) {
|
|
120
120
|
const spread = spreadFor(settings.bubbleSpread);
|
|
121
|
-
const
|
|
122
|
-
|
|
123
|
-
|
|
121
|
+
const { shown: deletions, hidden: dropped } = deletionDrawing(
|
|
122
|
+
graph,
|
|
123
|
+
deletionEdges(graph),
|
|
124
|
+
settings.showDeletionEdges !== false
|
|
125
|
+
);
|
|
124
126
|
const routed = withDeletionRoutes(graph, deletions, dropped);
|
|
125
127
|
const merged = mergeRuns(routed.graph, routed.ids);
|
|
126
128
|
const runs = {
|
|
@@ -1,12 +1,12 @@
|
|
|
1
1
|
import {
|
|
2
2
|
EdgeSpatialIndex,
|
|
3
3
|
SpatialIndex
|
|
4
|
-
} from "./chunk-
|
|
4
|
+
} from "./chunk-KBEP7VYK.js";
|
|
5
5
|
import {
|
|
6
6
|
pathRibbonOffsets,
|
|
7
7
|
translateCurves,
|
|
8
8
|
yToXOf
|
|
9
|
-
} from "./chunk-
|
|
9
|
+
} from "./chunk-7SRWJLSC.js";
|
|
10
10
|
|
|
11
11
|
// src/util/hitDetection.ts
|
|
12
12
|
function distanceToSegment(px, py, x1, y1, x2, y2) {
|
|
@@ -47,16 +47,9 @@ function walkRowLayout(graph, region) {
|
|
|
47
47
|
const nodePositions = backbonePositions(
|
|
48
48
|
overWindow.length > 0 ? overWindow : backbone
|
|
49
49
|
);
|
|
50
|
-
const rowLabels = [
|
|
51
|
-
{ label: walks.reference.label, y: 0 },
|
|
52
|
-
...walks.rows.map((row, i) => ({
|
|
53
|
-
label: row.label,
|
|
54
|
-
y: (i + 1) * ROW_HEIGHT_PX
|
|
55
|
-
}))
|
|
56
|
-
];
|
|
57
50
|
return {
|
|
58
51
|
nodePositions,
|
|
59
|
-
rowLabels,
|
|
52
|
+
rowLabels: walkRowLabels(walks),
|
|
60
53
|
referenceAxis: true,
|
|
61
54
|
pixelRows: true,
|
|
62
55
|
extent: walkRowsExtent(walks)
|
|
@@ -64,6 +57,7 @@ function walkRowLayout(graph, region) {
|
|
|
64
57
|
}
|
|
65
58
|
|
|
66
59
|
export {
|
|
60
|
+
READOUT_ROOM,
|
|
67
61
|
walkRowsExtent,
|
|
68
62
|
walkRowLabels,
|
|
69
63
|
walkRowLayout
|
|
@@ -57,10 +57,11 @@ function parseGFA(file) {
|
|
|
57
57
|
};
|
|
58
58
|
for (const rawLine of file.split("\n")) {
|
|
59
59
|
const line = rawLine.endsWith("\r") ? rawLine.slice(0, -1) : rawLine;
|
|
60
|
-
|
|
60
|
+
const type = line.split(" ", 1)[0];
|
|
61
|
+
if (type === "H") {
|
|
61
62
|
const [, ...rest] = line.split(" ");
|
|
62
63
|
graph.header.push(parseTags(rest));
|
|
63
|
-
} else if (
|
|
64
|
+
} else if (type === "S") {
|
|
64
65
|
const [, name, ...rest] = line.split(" ");
|
|
65
66
|
let len;
|
|
66
67
|
let seq;
|
|
@@ -82,7 +83,7 @@ function parseGFA(file) {
|
|
|
82
83
|
len = +tags.LN;
|
|
83
84
|
}
|
|
84
85
|
graph.nodes.push({ id: name, length: len, sequence: seq, tags });
|
|
85
|
-
} else if (
|
|
86
|
+
} else if (type === "E") {
|
|
86
87
|
const [, , source, target, , , , , cigar, ...rest] = line.split(" ");
|
|
87
88
|
if (source && target) {
|
|
88
89
|
graph.links.push({
|
|
@@ -94,7 +95,7 @@ function parseGFA(file) {
|
|
|
94
95
|
tags: parseTags(rest)
|
|
95
96
|
});
|
|
96
97
|
}
|
|
97
|
-
} else if (
|
|
98
|
+
} else if (type === "L") {
|
|
98
99
|
const [, source, strand1, target, strand2, cigar, ...rest] = line.split(" ");
|
|
99
100
|
if (source && target && strand2) {
|
|
100
101
|
graph.links.push({
|
|
@@ -106,7 +107,7 @@ function parseGFA(file) {
|
|
|
106
107
|
tags: parseTags(rest)
|
|
107
108
|
});
|
|
108
109
|
}
|
|
109
|
-
} else if (
|
|
110
|
+
} else if (type === "W") {
|
|
110
111
|
const [, sample, hap, contig, start, end, body, ...rest] = line.split(" ");
|
|
111
112
|
if (sample && hap && contig && start && end && body) {
|
|
112
113
|
graph.walks.push({
|
|
@@ -119,7 +120,7 @@ function parseGFA(file) {
|
|
|
119
120
|
tags: parseTags(rest)
|
|
120
121
|
});
|
|
121
122
|
}
|
|
122
|
-
} else if (
|
|
123
|
+
} else if (type === "P") {
|
|
123
124
|
const [, name, path, ...rest] = line.split(" ");
|
|
124
125
|
if (name && path) {
|
|
125
126
|
graph.paths.push({ name, path, rest });
|
|
@@ -206,15 +206,16 @@ function bowAround(p1x, p1y, p2x, p2y, toward, maxBow) {
|
|
|
206
206
|
function yToXOf({ scaleX, scaleY }) {
|
|
207
207
|
return scaleY / scaleX;
|
|
208
208
|
}
|
|
209
|
-
var
|
|
209
|
+
var PATH_RIBBON_SPACING_PX = 3;
|
|
210
210
|
function drawnDirection(a, b, yToX) {
|
|
211
211
|
const dx = b.x - a.x;
|
|
212
212
|
const dy = (b.y - a.y) * yToX;
|
|
213
213
|
const len = Math.hypot(dx, dy);
|
|
214
214
|
return len === 0 ? void 0 : { x: dx / len, y: dy / len };
|
|
215
215
|
}
|
|
216
|
-
function pathRibbonOffsets(fromSegments, toSegments, count, axis
|
|
216
|
+
function pathRibbonOffsets(fromSegments, toSegments, count, axis) {
|
|
217
217
|
const yToX = yToXOf(axis);
|
|
218
|
+
const spacing = PATH_RIBBON_SPACING_PX / Math.max(axis.scaleX, 1e-6);
|
|
218
219
|
const dir = drawnDirection(
|
|
219
220
|
fromSegments[fromSegments.length - 1],
|
|
220
221
|
toSegments[0],
|
|
@@ -270,15 +271,15 @@ function edgeJoinOf(edge, stranded = false) {
|
|
|
270
271
|
const sides = strandSides(edge);
|
|
271
272
|
return self === false ? sides : sides.from === sides.to ? sides.from : true;
|
|
272
273
|
}
|
|
273
|
-
function hairpinCurves(attach, reach
|
|
274
|
+
function hairpinCurves(attach, reach) {
|
|
274
275
|
const { at, inward } = attach;
|
|
275
276
|
const dx = inward ? at.x - inward.x : 1;
|
|
276
277
|
const dy = inward ? at.y - inward.y : 0;
|
|
277
278
|
const len = Math.hypot(dx, dy) || 1;
|
|
278
279
|
const ux = dx / len;
|
|
279
280
|
const uy = dy / len;
|
|
280
|
-
const px = at.x
|
|
281
|
-
const py = at.y
|
|
281
|
+
const px = at.x;
|
|
282
|
+
const py = at.y;
|
|
282
283
|
const nearX = px + ux * reach / 3;
|
|
283
284
|
const nearY = py + uy * reach / 3;
|
|
284
285
|
const apexX = px + ux * reach;
|
|
@@ -308,7 +309,7 @@ function hairpinCurves(attach, reach, offsetX, offsetY) {
|
|
|
308
309
|
}
|
|
309
310
|
];
|
|
310
311
|
}
|
|
311
|
-
function computeEdgeCurves(fromSegments, toSegments, join,
|
|
312
|
+
function computeEdgeCurves(fromSegments, toSegments, join, axis, bypassed = [], maxBowIn) {
|
|
312
313
|
const scale = axis.scaleX;
|
|
313
314
|
const yToX = yToXOf(axis);
|
|
314
315
|
const maxBow = maxBowIn ?? (axis.pixelRows ? MAX_ROW_BOW_PX : void 0);
|
|
@@ -321,8 +322,6 @@ function computeEdgeCurves(fromSegments, toSegments, join, offsetX, offsetY, axi
|
|
|
321
322
|
scaleYOf(fromSegments, yToX),
|
|
322
323
|
scaleYOf(toSegments, yToX),
|
|
323
324
|
join,
|
|
324
|
-
offsetX,
|
|
325
|
-
offsetY * yToX,
|
|
326
325
|
{ scaleX: scale, scaleY: scale },
|
|
327
326
|
scaleYOf(bypassed, yToX),
|
|
328
327
|
// the cap is a y measure and the body works in x units, so it converts
|
|
@@ -335,9 +334,7 @@ function computeEdgeCurves(fromSegments, toSegments, join, offsetX, offsetY, axi
|
|
|
335
334
|
if (typeof join === "string") {
|
|
336
335
|
return hairpinCurves(
|
|
337
336
|
attachment(fromSegments, join),
|
|
338
|
-
selfLoopReach(fromSegments, scale)
|
|
339
|
-
offsetX,
|
|
340
|
-
offsetY
|
|
337
|
+
selfLoopReach(fromSegments, scale)
|
|
341
338
|
);
|
|
342
339
|
}
|
|
343
340
|
const loop = join === true;
|
|
@@ -346,10 +343,10 @@ function computeEdgeCurves(fromSegments, toSegments, join, offsetX, offsetY, axi
|
|
|
346
343
|
const toAttach = attachment(toSegments, sides.to);
|
|
347
344
|
const fromEnd = fromAttach.at;
|
|
348
345
|
const toStart = toAttach.at;
|
|
349
|
-
const p1x = fromEnd.x
|
|
350
|
-
const p1y = fromEnd.y
|
|
351
|
-
const p2x = toStart.x
|
|
352
|
-
const p2y = toStart.y
|
|
346
|
+
const p1x = fromEnd.x;
|
|
347
|
+
const p1y = fromEnd.y;
|
|
348
|
+
const p2x = toStart.x;
|
|
349
|
+
const p2y = toStart.y;
|
|
353
350
|
if (loop) {
|
|
354
351
|
let segDirX = 1;
|
|
355
352
|
let segDirY = 0;
|
|
@@ -365,8 +362,8 @@ function computeEdgeCurves(fromSegments, toSegments, join, offsetX, offsetY, axi
|
|
|
365
362
|
const ext = selfLoopReach(fromSegments, scale);
|
|
366
363
|
const perpX = -segDirY;
|
|
367
364
|
const perpY = segDirX;
|
|
368
|
-
const midX = (fromEnd.x + toStart.x) / 2 +
|
|
369
|
-
const midY = (fromEnd.y + toStart.y) / 2 +
|
|
365
|
+
const midX = (fromEnd.x + toStart.x) / 2 + perpX * ext;
|
|
366
|
+
const midY = (fromEnd.y + toStart.y) / 2 + perpY * ext;
|
|
370
367
|
const cp1x = p1x + segDirX * ext;
|
|
371
368
|
const cp1y = p1y + segDirY * ext;
|
|
372
369
|
const cp2x = p2x - segDirX * ext;
|
|
@@ -441,10 +438,10 @@ function computeEdgeCurves(fromSegments, toSegments, join, offsetX, offsetY, axi
|
|
|
441
438
|
{
|
|
442
439
|
x0: p1x,
|
|
443
440
|
y0: p1y,
|
|
444
|
-
cx0: cx1 +
|
|
445
|
-
cy0: cy1 +
|
|
446
|
-
cx1: cx2 +
|
|
447
|
-
cy1: cy2 +
|
|
441
|
+
cx0: cx1 + bulgeX - spreadX,
|
|
442
|
+
cy0: cy1 + bulgeY - spreadY,
|
|
443
|
+
cx1: cx2 + bulgeX + spreadX,
|
|
444
|
+
cy1: cy2 + bulgeY + spreadY,
|
|
448
445
|
x1: p2x,
|
|
449
446
|
y1: p2y
|
|
450
447
|
}
|
|
@@ -521,7 +518,7 @@ export {
|
|
|
521
518
|
strandSides,
|
|
522
519
|
bowAround,
|
|
523
520
|
yToXOf,
|
|
524
|
-
|
|
521
|
+
PATH_RIBBON_SPACING_PX,
|
|
525
522
|
pathRibbonOffsets,
|
|
526
523
|
selfLinkOf,
|
|
527
524
|
edgeJoinOf,
|
|
@@ -5,17 +5,17 @@ import {
|
|
|
5
5
|
} from "./chunk-G2FD7S3C.js";
|
|
6
6
|
import {
|
|
7
7
|
baseEdgeCurves
|
|
8
|
-
} from "./chunk-
|
|
8
|
+
} from "./chunk-ZY2AFL4Y.js";
|
|
9
9
|
import {
|
|
10
10
|
PATH_LIGHTNESS,
|
|
11
11
|
PATH_SATURATION,
|
|
12
12
|
nameHue,
|
|
13
13
|
pathHueAt
|
|
14
|
-
} from "./chunk-
|
|
14
|
+
} from "./chunk-3XSM4OZU.js";
|
|
15
15
|
import {
|
|
16
16
|
meanDepth,
|
|
17
17
|
nodeWidthPx
|
|
18
|
-
} from "./chunk-
|
|
18
|
+
} from "./chunk-JBCZIBFC.js";
|
|
19
19
|
import {
|
|
20
20
|
referenceMidpoints
|
|
21
21
|
} from "./chunk-ES2N6V56.js";
|
|
@@ -25,7 +25,7 @@ import {
|
|
|
25
25
|
strandSides,
|
|
26
26
|
translateCurves,
|
|
27
27
|
yToXOf
|
|
28
|
-
} from "./chunk-
|
|
28
|
+
} from "./chunk-7SRWJLSC.js";
|
|
29
29
|
|
|
30
30
|
// src/renderer/GeometryBuilder.ts
|
|
31
31
|
var EDGE_DEFAULT_COLOR = packAbgr(119, 119, 119, 217);
|
|
@@ -551,25 +551,24 @@ function buildGeometry(options) {
|
|
|
551
551
|
const edgeColor = !highlight || onWalk ? plainEdgeColor : fadeAbgr(plainEdgeColor, FADED_ALPHA);
|
|
552
552
|
const toNode = nodeById.get(edge.to);
|
|
553
553
|
const intoHalfWidth = (toNode ? nodeWidthPx(toNode, contigThickness, nodeWidth, depthNorm) : contigThickness) / 2;
|
|
554
|
-
const
|
|
555
|
-
|
|
556
|
-
if (viewportBounds && !isBezierInBounds(curves, viewportBounds)) {
|
|
557
|
-
return;
|
|
558
|
-
}
|
|
554
|
+
const inView = (curves) => !viewportBounds || isBezierInBounds(curves, viewportBounds);
|
|
555
|
+
const stroke = (curves, thickness, color) => {
|
|
559
556
|
if (isDeletion) {
|
|
560
557
|
for (const dash of dashCurves(curves, DELETION_DASH_PX / scale)) {
|
|
561
|
-
edgeCurves.push({ curves: dash, thickness
|
|
558
|
+
edgeCurves.push({ curves: dash, thickness, color });
|
|
562
559
|
}
|
|
563
560
|
} else {
|
|
564
|
-
edgeCurves.push({ curves, thickness
|
|
561
|
+
edgeCurves.push({ curves, thickness, color });
|
|
565
562
|
}
|
|
566
|
-
|
|
563
|
+
};
|
|
564
|
+
const arrowOn = (curves) => {
|
|
565
|
+
const head = showArrows ? arrowheadFor({
|
|
567
566
|
curves,
|
|
568
567
|
edgeHalfWidth: connectorThickness / 2,
|
|
569
568
|
nodeHalfWidth: intoHalfWidth,
|
|
570
569
|
scale,
|
|
571
570
|
yToX,
|
|
572
|
-
color:
|
|
571
|
+
color: edgeColor,
|
|
573
572
|
fromSegments,
|
|
574
573
|
toSegments
|
|
575
574
|
}) : void 0;
|
|
@@ -602,17 +601,22 @@ function buildGeometry(options) {
|
|
|
602
601
|
}
|
|
603
602
|
const offset = (lane - (laneWalks.length - 1) / 2) * laneWidth * worldPerScreenPx;
|
|
604
603
|
const curves = offset === 0 ? baseCurves : translateCurves(baseCurves, nx * offset, ny * offset / yToX);
|
|
605
|
-
if (
|
|
606
|
-
|
|
604
|
+
if (inView(curves)) {
|
|
605
|
+
stroke(
|
|
606
|
+
curves,
|
|
607
|
+
laneWidth / 2,
|
|
608
|
+
walk.colors.get(edge.from) ?? walk.colors.get(edge.to) ?? plainEdgeColor
|
|
609
|
+
);
|
|
607
610
|
}
|
|
608
|
-
edgeCurves.push({
|
|
609
|
-
curves,
|
|
610
|
-
thickness: laneWidth / 2,
|
|
611
|
-
color: walk.colors.get(edge.from) ?? walk.colors.get(edge.to) ?? plainEdgeColor
|
|
612
|
-
});
|
|
613
611
|
});
|
|
612
|
+
if (edgeCurves.length > edgeCurveStart) {
|
|
613
|
+
arrowOn(baseCurves);
|
|
614
|
+
}
|
|
614
615
|
} else if (!ribbons) {
|
|
615
|
-
|
|
616
|
+
if (inView(baseCurves)) {
|
|
617
|
+
stroke(baseCurves, edgeThickness, edgeColor);
|
|
618
|
+
arrowOn(baseCurves);
|
|
619
|
+
}
|
|
616
620
|
} else {
|
|
617
621
|
const offsets = pathRibbonOffsets(
|
|
618
622
|
fromSegments,
|
|
@@ -622,14 +626,20 @@ function buildGeometry(options) {
|
|
|
622
626
|
);
|
|
623
627
|
const arrowRibbon = Math.floor((numPaths - 1) / 2);
|
|
624
628
|
for (let pathIdx = 0; pathIdx < numPaths; pathIdx++) {
|
|
625
|
-
const
|
|
629
|
+
const { x, y } = offsets[pathIdx];
|
|
630
|
+
const curves = x === 0 && y === 0 ? baseCurves : translateCurves(baseCurves, x, y);
|
|
631
|
+
if (!inView(curves)) {
|
|
632
|
+
continue;
|
|
633
|
+
}
|
|
626
634
|
const ribbonColor = pathColorByName(edge.pathIds[pathIdx]);
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
highlight && (highlight.walks.length ? !highlight.names.has(edge.pathIds[pathIdx]) : !onWalk) ? fadeAbgr(ribbonColor, FADED_ALPHA) : ribbonColor
|
|
631
|
-
pathIdx === arrowRibbon ? edgeColor : void 0
|
|
635
|
+
stroke(
|
|
636
|
+
curves,
|
|
637
|
+
edgeThickness,
|
|
638
|
+
highlight && (highlight.walks.length ? !highlight.names.has(edge.pathIds[pathIdx]) : !onWalk) ? fadeAbgr(ribbonColor, FADED_ALPHA) : ribbonColor
|
|
632
639
|
);
|
|
640
|
+
if (pathIdx === arrowRibbon) {
|
|
641
|
+
arrowOn(curves);
|
|
642
|
+
}
|
|
633
643
|
}
|
|
634
644
|
}
|
|
635
645
|
const edgeCurveCount = edgeCurves.length - edgeCurveStart;
|
|
@@ -1,23 +1,21 @@
|
|
|
1
1
|
import {
|
|
2
2
|
bubblesFromGraph,
|
|
3
|
+
relax,
|
|
3
4
|
walkIndexOf,
|
|
4
5
|
walkRoutes
|
|
5
|
-
} from "./chunk-
|
|
6
|
+
} from "./chunk-CQHUZHET.js";
|
|
6
7
|
import {
|
|
7
8
|
bubbleSubgraph
|
|
8
9
|
} from "./chunk-T6V4KI2L.js";
|
|
9
10
|
import {
|
|
10
11
|
coversGraph
|
|
11
|
-
} from "./chunk-
|
|
12
|
+
} from "./chunk-JA2HJIYS.js";
|
|
12
13
|
import {
|
|
13
14
|
bubbleSegmentIds
|
|
14
|
-
} from "./chunk-
|
|
15
|
-
import {
|
|
16
|
-
SATURATED_PATH_COUNT
|
|
17
|
-
} from "./chunk-FX4RDMDN.js";
|
|
15
|
+
} from "./chunk-URZ3CH2R.js";
|
|
18
16
|
import {
|
|
19
17
|
strandSides
|
|
20
|
-
} from "./chunk-
|
|
18
|
+
} from "./chunk-7SRWJLSC.js";
|
|
21
19
|
import {
|
|
22
20
|
isBackbone
|
|
23
21
|
} from "./chunk-FYQWPEEY.js";
|
|
@@ -196,13 +194,7 @@ function routesThrough(nodes, offset, next, f) {
|
|
|
196
194
|
}
|
|
197
195
|
for (let p = offset[k]; p < offset[k + 1]; p++) {
|
|
198
196
|
const u = next[p] >> 1;
|
|
199
|
-
|
|
200
|
-
const prev = best.get(u);
|
|
201
|
-
best.set(u, {
|
|
202
|
-
min: Math.min(prev?.min ?? Infinity, cur.min + add),
|
|
203
|
-
max: Math.max(prev?.max ?? -Infinity, cur.max + add),
|
|
204
|
-
n: Math.min(SATURATED_PATH_COUNT, cur.n + (prev?.n ?? 0))
|
|
205
|
-
});
|
|
197
|
+
relax(best, u, cur, u === sink ? 0 : nodes[u].length);
|
|
206
198
|
}
|
|
207
199
|
}
|
|
208
200
|
return best.get(sink) ?? { min: 0, max: 0, n: 0 };
|