react-msaview 3.1.3 → 3.1.5
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/bundle/index.js +6 -6
- package/dist/DialogQueue.js +2 -4
- package/dist/DialogQueue.js.map +1 -1
- package/dist/UniprotTrack.js +1 -1
- package/dist/UniprotTrack.js.map +1 -1
- package/dist/components/BoxTrackBlock.js +3 -4
- package/dist/components/BoxTrackBlock.js.map +1 -1
- package/dist/components/ImportForm/util.js +1 -0
- package/dist/components/ImportForm/util.js.map +1 -1
- package/dist/components/Loading.d.ts +6 -0
- package/dist/components/Loading.js +12 -0
- package/dist/components/Loading.js.map +1 -0
- package/dist/components/MSAPanel/MSABlock.js +3 -3
- package/dist/components/MSAPanel/MSABlock.js.map +1 -1
- package/dist/components/MSAPanel/MSAMouseoverCanvas.js +7 -9
- package/dist/components/MSAPanel/MSAMouseoverCanvas.js.map +1 -1
- package/dist/components/MSAPanel/index.js +1 -1
- package/dist/components/MSAPanel/index.js.map +1 -1
- package/dist/components/MSAPanel/renderMSABlock.d.ts +3 -1
- package/dist/components/MSAPanel/renderMSABlock.js +9 -9
- package/dist/components/MSAPanel/renderMSABlock.js.map +1 -1
- package/dist/components/MSAPanel/renderMSAMouseover.js +5 -8
- package/dist/components/MSAPanel/renderMSAMouseover.js.map +1 -1
- package/dist/components/MSAView.js +21 -17
- package/dist/components/MSAView.js.map +1 -1
- package/dist/components/TextTrack.js +1 -1
- package/dist/components/TextTrack.js.map +1 -1
- package/dist/components/TreePanel/TreeCanvasBlock.js +11 -13
- package/dist/components/TreePanel/TreeCanvasBlock.js.map +1 -1
- package/dist/components/TreePanel/TreeNodeMenu.js +4 -6
- package/dist/components/TreePanel/TreeNodeMenu.js.map +1 -1
- package/dist/components/TreePanel/renderTreeCanvas.js +19 -20
- package/dist/components/TreePanel/renderTreeCanvas.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +1 -1
- package/dist/layout.js +5 -0
- package/dist/layout.js.map +1 -1
- package/dist/measureTextCanvas.d.ts +1 -0
- package/dist/measureTextCanvas.js +13 -0
- package/dist/measureTextCanvas.js.map +1 -0
- package/dist/model.d.ts +57 -50
- package/dist/model.js +28 -38
- package/dist/model.js.map +1 -1
- package/dist/parseNewick.js +1 -2
- package/dist/parseNewick.js.map +1 -1
- package/dist/parsers/ClustalMSA.d.ts +1 -11
- package/dist/parsers/ClustalMSA.js +3 -18
- package/dist/parsers/ClustalMSA.js.map +1 -1
- package/dist/parsers/FastaMSA.js +3 -4
- package/dist/parsers/FastaMSA.js.map +1 -1
- package/dist/parsers/StockholmMSA.js +13 -19
- package/dist/parsers/StockholmMSA.js.map +1 -1
- package/dist/renderToSvg.js +1 -0
- package/dist/renderToSvg.js.map +1 -1
- package/dist/util.js +7 -4
- package/dist/util.js.map +1 -1
- package/dist/version.d.ts +1 -1
- package/dist/version.js +1 -1
- package/package.json +1 -1
- package/src/components/ImportForm/util.ts +1 -0
- package/src/components/Loading.tsx +27 -0
- package/src/components/MSAPanel/MSABlock.tsx +2 -1
- package/src/components/MSAPanel/MSAMouseoverCanvas.tsx +6 -6
- package/src/components/MSAPanel/index.tsx +2 -2
- package/src/components/MSAPanel/renderMSABlock.ts +9 -1
- package/src/components/MSAPanel/renderMSAMouseover.ts +3 -17
- package/src/components/MSAView.tsx +30 -32
- package/src/components/TreePanel/TreeCanvasBlock.tsx +5 -6
- package/src/components/TreePanel/renderTreeCanvas.ts +20 -13
- package/src/index.ts +1 -1
- package/src/measureTextCanvas.ts +14 -0
- package/src/model.ts +16 -8
- package/src/parsers/ClustalMSA.ts +1 -15
- package/src/renderToSvg.tsx +1 -0
- package/src/version.ts +1 -1
package/dist/util.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"util.js","sourceRoot":"","sources":["../src/util.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,GAAG,EAAE,MAAM,UAAU,CAAA;AAE9B,OAAO,EAAE,MAAM,EAAE,MAAM,EAAE,MAAM,QAAQ,CAAA;AACvC,OAAO,WAAW,MAAM,sBAAsB,CAAA;AAE9C,MAAM,CAAC,CAAC,WAAW,CAAC,CAAC,CAAA;AAErB,MAAM,UAAU,SAAS,CACvB,GAAsB,EACtB,EAAsC;IAEtC,OAAO,MAAM,CAAC,WAAW,CAAC,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,GAAG,CAAC,EAAE,CAAC,CAAC,CAAA;AACxD,CAAC;AAwBD,MAAM,UAAU,eAAe,CAC7B,IAAU,EACV,MAAM,GAAG,MAAM,EACf,KAAK,GAAG,CAAC
|
|
1
|
+
{"version":3,"file":"util.js","sourceRoot":"","sources":["../src/util.ts"],"names":[],"mappings":"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"}
|
package/dist/version.d.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export declare const version = "3.1.
|
|
1
|
+
export declare const version = "3.1.5";
|
package/dist/version.js
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export const version = '3.1.
|
|
1
|
+
export const version = '3.1.5';
|
|
2
2
|
//# sourceMappingURL=version.js.map
|
package/package.json
CHANGED
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
import React from 'react'
|
|
2
|
+
|
|
3
|
+
import { observer } from 'mobx-react'
|
|
4
|
+
import { Typography } from '@mui/material'
|
|
5
|
+
|
|
6
|
+
// locals
|
|
7
|
+
import ImportForm from './ImportForm'
|
|
8
|
+
import MSAView from './MSAView'
|
|
9
|
+
import { MsaViewModel } from '../model'
|
|
10
|
+
|
|
11
|
+
const Loading = observer(function ({ model }: { model: MsaViewModel }) {
|
|
12
|
+
const { done, initialized } = model
|
|
13
|
+
|
|
14
|
+
return (
|
|
15
|
+
<div>
|
|
16
|
+
{!initialized ? (
|
|
17
|
+
<ImportForm model={model} />
|
|
18
|
+
) : !done ? (
|
|
19
|
+
<Typography variant="h4">Loading...</Typography>
|
|
20
|
+
) : (
|
|
21
|
+
<MSAView model={model} />
|
|
22
|
+
)}
|
|
23
|
+
</div>
|
|
24
|
+
)
|
|
25
|
+
})
|
|
26
|
+
|
|
27
|
+
export default Loading
|
|
@@ -42,13 +42,14 @@ const MSABlock = observer(function ({
|
|
|
42
42
|
return autorun(() => {
|
|
43
43
|
renderMSABlock({
|
|
44
44
|
ctx,
|
|
45
|
+
theme,
|
|
45
46
|
offsetX,
|
|
46
47
|
offsetY,
|
|
47
48
|
contrastScheme,
|
|
48
49
|
model,
|
|
49
50
|
})
|
|
50
51
|
})
|
|
51
|
-
}, [model, offsetX, offsetY, contrastScheme])
|
|
52
|
+
}, [model, offsetX, offsetY, theme, contrastScheme])
|
|
52
53
|
return (
|
|
53
54
|
<canvas
|
|
54
55
|
ref={ref}
|
|
@@ -15,17 +15,17 @@ const MSAMouseoverCanvas = observer(function ({
|
|
|
15
15
|
const { height, width } = model
|
|
16
16
|
useEffect(() => {
|
|
17
17
|
const ctx = ref.current?.getContext('2d')
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
})
|
|
18
|
+
return ctx
|
|
19
|
+
? autorun(() => {
|
|
20
|
+
renderMouseover({ ctx, model })
|
|
21
|
+
})
|
|
22
|
+
: undefined
|
|
24
23
|
}, [model])
|
|
25
24
|
|
|
26
25
|
return (
|
|
27
26
|
<canvas
|
|
28
27
|
ref={ref}
|
|
28
|
+
id="mouseover"
|
|
29
29
|
width={width}
|
|
30
30
|
height={height}
|
|
31
31
|
style={{
|
|
@@ -5,9 +5,9 @@ import { MsaViewModel } from '../../model'
|
|
|
5
5
|
|
|
6
6
|
export default function MSAPanel({ model }: { model: MsaViewModel }) {
|
|
7
7
|
return (
|
|
8
|
-
|
|
8
|
+
<div style={{ position: 'relative' }}>
|
|
9
9
|
<MSACanvas model={model} />
|
|
10
10
|
<MSAMouseoverCanvas model={model} />
|
|
11
|
-
|
|
11
|
+
</div>
|
|
12
12
|
)
|
|
13
13
|
}
|
|
@@ -3,6 +3,7 @@ import { MsaViewModel } from '../../model'
|
|
|
3
3
|
import { getClustalXColor, getPercentIdentityColor } from '../../colorSchemes'
|
|
4
4
|
import { NodeWithIdsAndLength } from '../../util'
|
|
5
5
|
import { HierarchyNode } from 'd3-hierarchy'
|
|
6
|
+
import { Theme } from '@mui/material'
|
|
6
7
|
|
|
7
8
|
export function renderMSABlock({
|
|
8
9
|
model,
|
|
@@ -10,12 +11,14 @@ export function renderMSABlock({
|
|
|
10
11
|
offsetY,
|
|
11
12
|
contrastScheme,
|
|
12
13
|
ctx,
|
|
14
|
+
theme,
|
|
13
15
|
highResScaleFactorOverride,
|
|
14
16
|
blockSizeXOverride,
|
|
15
17
|
blockSizeYOverride,
|
|
16
18
|
}: {
|
|
17
19
|
offsetX: number
|
|
18
20
|
offsetY: number
|
|
21
|
+
theme: Theme
|
|
19
22
|
model: MsaViewModel
|
|
20
23
|
contrastScheme: Record<string, string>
|
|
21
24
|
ctx: CanvasRenderingContext2D
|
|
@@ -52,6 +55,7 @@ export function renderMSABlock({
|
|
|
52
55
|
drawTiles({
|
|
53
56
|
model,
|
|
54
57
|
ctx,
|
|
58
|
+
theme,
|
|
55
59
|
offsetX,
|
|
56
60
|
offsetY,
|
|
57
61
|
xStart,
|
|
@@ -63,6 +67,7 @@ export function renderMSABlock({
|
|
|
63
67
|
ctx,
|
|
64
68
|
offsetX,
|
|
65
69
|
contrastScheme,
|
|
70
|
+
theme,
|
|
66
71
|
xStart,
|
|
67
72
|
xEnd,
|
|
68
73
|
visibleLeaves,
|
|
@@ -74,11 +79,13 @@ function drawTiles({
|
|
|
74
79
|
offsetX,
|
|
75
80
|
ctx,
|
|
76
81
|
visibleLeaves,
|
|
82
|
+
theme,
|
|
77
83
|
xStart,
|
|
78
84
|
xEnd,
|
|
79
85
|
}: {
|
|
80
86
|
model: MsaViewModel
|
|
81
87
|
offsetX: number
|
|
88
|
+
theme: Theme
|
|
82
89
|
offsetY: number
|
|
83
90
|
ctx: CanvasRenderingContext2D
|
|
84
91
|
visibleLeaves: HierarchyNode<NodeWithIdsAndLength>[]
|
|
@@ -118,7 +125,7 @@ function drawTiles({
|
|
|
118
125
|
: colorScheme[letter.toUpperCase()]
|
|
119
126
|
if (bgColor) {
|
|
120
127
|
const x = i * colWidth + offsetX - (offsetX % colWidth)
|
|
121
|
-
ctx.fillStyle = color ||
|
|
128
|
+
ctx.fillStyle = color || theme.palette.background.default
|
|
122
129
|
ctx.fillRect(x, y - rowHeight, colWidth, rowHeight)
|
|
123
130
|
}
|
|
124
131
|
}
|
|
@@ -137,6 +144,7 @@ function drawText({
|
|
|
137
144
|
offsetX: number
|
|
138
145
|
model: MsaViewModel
|
|
139
146
|
contrastScheme: Record<string, string>
|
|
147
|
+
theme: Theme
|
|
140
148
|
ctx: CanvasRenderingContext2D
|
|
141
149
|
visibleLeaves: HierarchyNode<NodeWithIdsAndLength>[]
|
|
142
150
|
xStart: number
|
|
@@ -10,8 +10,6 @@ export function renderMouseover({
|
|
|
10
10
|
const {
|
|
11
11
|
mouseCol,
|
|
12
12
|
colWidth,
|
|
13
|
-
treeAreaWidth,
|
|
14
|
-
resizeHandleWidth,
|
|
15
13
|
width,
|
|
16
14
|
height,
|
|
17
15
|
rowHeight,
|
|
@@ -20,31 +18,19 @@ export function renderMouseover({
|
|
|
20
18
|
mouseRow,
|
|
21
19
|
// @ts-expect-error
|
|
22
20
|
mouseCol2,
|
|
23
|
-
minimapHeight,
|
|
24
|
-
totalTrackAreaHeight,
|
|
25
21
|
} = model
|
|
26
22
|
ctx.resetTransform()
|
|
27
23
|
ctx.clearRect(0, 0, width, height)
|
|
28
|
-
|
|
29
24
|
if (mouseCol !== undefined) {
|
|
30
25
|
ctx.fillStyle = 'rgba(0,0,0,0.15)'
|
|
31
|
-
|
|
32
|
-
(mouseCol - 1) * colWidth + scrollX + treeAreaWidth + resizeHandleWidth
|
|
33
|
-
|
|
34
|
-
ctx.fillRect(x, minimapHeight, colWidth, height)
|
|
26
|
+
ctx.fillRect((mouseCol - 1) * colWidth + scrollX, 0, colWidth, height)
|
|
35
27
|
}
|
|
36
|
-
|
|
37
28
|
if (mouseRow !== undefined) {
|
|
38
29
|
ctx.fillStyle = 'rgba(0,0,0,0.15)'
|
|
39
|
-
|
|
40
|
-
mouseRow * rowHeight + scrollY + minimapHeight + totalTrackAreaHeight
|
|
41
|
-
ctx.fillRect(treeAreaWidth + resizeHandleWidth, y, width, rowHeight)
|
|
30
|
+
ctx.fillRect(0, mouseRow * rowHeight + scrollY, width, rowHeight)
|
|
42
31
|
}
|
|
43
32
|
if (mouseCol2 !== undefined) {
|
|
44
33
|
ctx.fillStyle = 'rgba(255,255,0,0.2)'
|
|
45
|
-
|
|
46
|
-
(mouseCol2 - 1) * colWidth + scrollX + treeAreaWidth + resizeHandleWidth
|
|
47
|
-
|
|
48
|
-
ctx.fillRect(x, 0, colWidth, height)
|
|
34
|
+
ctx.fillRect((mouseCol2 - 1) * colWidth + scrollX, 0, colWidth, height)
|
|
49
35
|
}
|
|
50
36
|
}
|
|
@@ -1,56 +1,54 @@
|
|
|
1
1
|
import React, { Suspense } from 'react'
|
|
2
|
-
|
|
3
2
|
import { observer } from 'mobx-react'
|
|
4
|
-
import { Typography } from '@mui/material'
|
|
5
3
|
|
|
6
4
|
// locals
|
|
7
|
-
import
|
|
5
|
+
import { HorizontalResizeHandle, VerticalResizeHandle } from './ResizeHandles'
|
|
6
|
+
import { MsaViewModel } from '../model'
|
|
8
7
|
import TreeRuler from './TreePanel/TreeRuler'
|
|
9
8
|
import Header from './Header'
|
|
10
9
|
import Track from './Track'
|
|
11
|
-
import { HorizontalResizeHandle, VerticalResizeHandle } from './ResizeHandles'
|
|
12
|
-
import { MsaViewModel } from '../model'
|
|
13
10
|
import MSAPanel from './MSAPanel'
|
|
14
11
|
import TreePanel from './TreePanel'
|
|
15
12
|
import Minimap from './Minimap'
|
|
16
13
|
|
|
17
|
-
|
|
18
|
-
|
|
14
|
+
function TopArea({ model }: { model: MsaViewModel }) {
|
|
15
|
+
return (
|
|
16
|
+
<div style={{ display: 'flex' }}>
|
|
17
|
+
<TreeRuler model={model} />
|
|
18
|
+
<Minimap model={model} />
|
|
19
|
+
</div>
|
|
20
|
+
)
|
|
21
|
+
}
|
|
22
|
+
function MainArea({ model }: { model: MsaViewModel }) {
|
|
23
|
+
return (
|
|
24
|
+
<div style={{ display: 'flex' }}>
|
|
25
|
+
<TreePanel model={model} />
|
|
26
|
+
<VerticalResizeHandle model={model} />
|
|
27
|
+
<MSAPanel model={model} />
|
|
28
|
+
</div>
|
|
29
|
+
)
|
|
30
|
+
}
|
|
19
31
|
|
|
32
|
+
const View = observer(function ({ model }: { model: MsaViewModel }) {
|
|
33
|
+
const { turnedOnTracks } = model
|
|
20
34
|
return (
|
|
21
|
-
<div>
|
|
22
|
-
{
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
<MSAView2 model={model} />
|
|
28
|
-
)}
|
|
35
|
+
<div style={{ position: 'relative' }}>
|
|
36
|
+
<TopArea model={model} />
|
|
37
|
+
{turnedOnTracks?.map(track => (
|
|
38
|
+
<Track key={track.model.id} model={model} track={track} />
|
|
39
|
+
))}
|
|
40
|
+
<MainArea model={model} />
|
|
29
41
|
</div>
|
|
30
42
|
)
|
|
31
43
|
})
|
|
32
44
|
|
|
33
|
-
const
|
|
34
|
-
const { height,
|
|
45
|
+
const MSAView = observer(function ({ model }: { model: MsaViewModel }) {
|
|
46
|
+
const { height, DialogComponent, DialogProps } = model
|
|
35
47
|
return (
|
|
36
48
|
<div>
|
|
37
49
|
<div style={{ height, overflow: 'hidden' }}>
|
|
38
50
|
<Header model={model} />
|
|
39
|
-
<
|
|
40
|
-
<div style={{ display: 'flex' }}>
|
|
41
|
-
<TreeRuler model={model} />
|
|
42
|
-
<Minimap model={model} />
|
|
43
|
-
</div>
|
|
44
|
-
{turnedOnTracks?.map(track => (
|
|
45
|
-
<Track key={track.model.id} model={model} track={track} />
|
|
46
|
-
))}
|
|
47
|
-
|
|
48
|
-
<div style={{ display: 'flex' }}>
|
|
49
|
-
<TreePanel model={model} />
|
|
50
|
-
<VerticalResizeHandle model={model} />
|
|
51
|
-
<MSAPanel model={model} />
|
|
52
|
-
</div>
|
|
53
|
-
</div>
|
|
51
|
+
<View model={model} />
|
|
54
52
|
</div>
|
|
55
53
|
<HorizontalResizeHandle model={model} />
|
|
56
54
|
|
|
@@ -42,8 +42,7 @@ const TreeCanvasBlock = observer(function ({
|
|
|
42
42
|
const [toggleNodeMenu, setToggleNodeMenu] = useState<TooltipData>()
|
|
43
43
|
const [hoverElt, setHoverElt] = useState<ClickEntry>()
|
|
44
44
|
|
|
45
|
-
const { scrollY, treeAreaWidth,
|
|
46
|
-
model
|
|
45
|
+
const { scrollY, treeAreaWidth, blockSize, highResScaleFactor } = model
|
|
47
46
|
|
|
48
47
|
const width = treeAreaWidth + padding
|
|
49
48
|
const height = blockSize
|
|
@@ -83,7 +82,7 @@ const TreeCanvasBlock = observer(function ({
|
|
|
83
82
|
|
|
84
83
|
ctx.resetTransform()
|
|
85
84
|
ctx.clearRect(0, 0, treeAreaWidth + padding, blockSize)
|
|
86
|
-
ctx.translate(
|
|
85
|
+
ctx.translate(0, -offsetY)
|
|
87
86
|
|
|
88
87
|
if (hoverElt) {
|
|
89
88
|
const { minX, maxX, minY, maxY } = hoverElt
|
|
@@ -91,10 +90,10 @@ const TreeCanvasBlock = observer(function ({
|
|
|
91
90
|
ctx.fillStyle = 'rgba(0,0,0,0.1)'
|
|
92
91
|
ctx.fillRect(minX, minY, maxX - minX, maxY - minY)
|
|
93
92
|
}
|
|
94
|
-
}, [hoverElt,
|
|
93
|
+
}, [hoverElt, offsetY, blockSize, treeAreaWidth])
|
|
95
94
|
|
|
96
95
|
function hoverBranchClickMap(event: React.MouseEvent) {
|
|
97
|
-
const x = event.nativeEvent.offsetX
|
|
96
|
+
const x = event.nativeEvent.offsetX
|
|
98
97
|
const y = event.nativeEvent.offsetY
|
|
99
98
|
|
|
100
99
|
const [entry] = clickMap.current.search({
|
|
@@ -110,7 +109,7 @@ const TreeCanvasBlock = observer(function ({
|
|
|
110
109
|
}
|
|
111
110
|
|
|
112
111
|
function hoverNameClickMap(event: React.MouseEvent) {
|
|
113
|
-
const x = event.nativeEvent.offsetX
|
|
112
|
+
const x = event.nativeEvent.offsetX
|
|
114
113
|
const y = event.nativeEvent.offsetY
|
|
115
114
|
const [entry] = clickMap.current.search({
|
|
116
115
|
minX: x,
|
|
@@ -71,7 +71,13 @@ export function renderNodeBubbles({
|
|
|
71
71
|
theme: Theme
|
|
72
72
|
blockSizeYOverride?: number
|
|
73
73
|
}) {
|
|
74
|
-
const {
|
|
74
|
+
const {
|
|
75
|
+
hierarchy,
|
|
76
|
+
showBranchLen,
|
|
77
|
+
collapsed,
|
|
78
|
+
blockSize,
|
|
79
|
+
marginLeft: ml,
|
|
80
|
+
} = model
|
|
75
81
|
const by = blockSizeYOverride || blockSize
|
|
76
82
|
for (const node of hierarchy.descendants()) {
|
|
77
83
|
const val = showBranchLen ? 'len' : 'y'
|
|
@@ -96,8 +102,8 @@ export function renderNodeBubbles({
|
|
|
96
102
|
ctx.stroke()
|
|
97
103
|
|
|
98
104
|
clickMap?.insert({
|
|
99
|
-
minX: x - radius,
|
|
100
|
-
maxX: x - radius + d,
|
|
105
|
+
minX: x - radius + ml,
|
|
106
|
+
maxX: x - radius + d + ml,
|
|
101
107
|
minY: y - radius,
|
|
102
108
|
maxY: y - radius + d,
|
|
103
109
|
branch: true,
|
|
@@ -133,7 +139,8 @@ export function renderTreeLabels({
|
|
|
133
139
|
drawTree,
|
|
134
140
|
structures,
|
|
135
141
|
treeAreaWidth,
|
|
136
|
-
|
|
142
|
+
treeAreaWidthMinusMargin,
|
|
143
|
+
marginLeft: ml,
|
|
137
144
|
noTree,
|
|
138
145
|
} = model
|
|
139
146
|
const by = blockSizeYOverride || blockSize
|
|
@@ -170,8 +177,8 @@ export function renderTreeLabels({
|
|
|
170
177
|
if (!drawTree && !labelsAlignRight) {
|
|
171
178
|
ctx.fillText(displayName, 0, yp)
|
|
172
179
|
clickMap?.insert({
|
|
173
|
-
minX: 0,
|
|
174
|
-
maxX: width,
|
|
180
|
+
minX: 0 + ml,
|
|
181
|
+
maxX: width + ml,
|
|
175
182
|
minY: yp - height,
|
|
176
183
|
maxY: yp,
|
|
177
184
|
name,
|
|
@@ -179,7 +186,7 @@ export function renderTreeLabels({
|
|
|
179
186
|
})
|
|
180
187
|
} else if (labelsAlignRight) {
|
|
181
188
|
const smallPadding = 2
|
|
182
|
-
const offset =
|
|
189
|
+
const offset = treeAreaWidthMinusMargin - smallPadding
|
|
183
190
|
if (drawTree && !noTree) {
|
|
184
191
|
const { width } = ctx.measureText(displayName)
|
|
185
192
|
ctx.moveTo(xp + radius + 2, y)
|
|
@@ -188,8 +195,8 @@ export function renderTreeLabels({
|
|
|
188
195
|
}
|
|
189
196
|
ctx.fillText(displayName, offset, yp)
|
|
190
197
|
clickMap?.insert({
|
|
191
|
-
minX: treeAreaWidth -
|
|
192
|
-
maxX: treeAreaWidth
|
|
198
|
+
minX: treeAreaWidth - width + ml,
|
|
199
|
+
maxX: treeAreaWidth + ml,
|
|
193
200
|
minY: yp - height,
|
|
194
201
|
maxY: yp,
|
|
195
202
|
name,
|
|
@@ -198,8 +205,8 @@ export function renderTreeLabels({
|
|
|
198
205
|
} else {
|
|
199
206
|
ctx.fillText(displayName, xp + d, yp)
|
|
200
207
|
clickMap?.insert({
|
|
201
|
-
minX: xp + d,
|
|
202
|
-
maxX: xp + d + width,
|
|
208
|
+
minX: xp + d + ml,
|
|
209
|
+
maxX: xp + d + width + ml,
|
|
203
210
|
minY: yp - height,
|
|
204
211
|
maxY: yp,
|
|
205
212
|
name,
|
|
@@ -235,10 +242,10 @@ export function renderTreeCanvas({
|
|
|
235
242
|
drawNodeBubbles,
|
|
236
243
|
treeWidth,
|
|
237
244
|
highResScaleFactor,
|
|
238
|
-
margin,
|
|
239
245
|
blockSize,
|
|
240
246
|
fontSize,
|
|
241
247
|
rowHeight,
|
|
248
|
+
marginLeft,
|
|
242
249
|
nref,
|
|
243
250
|
} = model
|
|
244
251
|
const by = blockSizeYOverride || blockSize
|
|
@@ -254,7 +261,7 @@ export function renderTreeCanvas({
|
|
|
254
261
|
nref < 0 ? -Infinity : highResScaleFactorOverride || highResScaleFactor
|
|
255
262
|
ctx.scale(k, k)
|
|
256
263
|
ctx.clearRect(0, 0, treeWidth + padding, by)
|
|
257
|
-
ctx.translate(
|
|
264
|
+
ctx.translate(marginLeft, -offsetY)
|
|
258
265
|
|
|
259
266
|
const font = ctx.font
|
|
260
267
|
ctx.font = font.replace(/\d+px/, `${fontSize}px`)
|
package/src/index.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
export { default as MSAView } from './components/
|
|
1
|
+
export { default as MSAView } from './components/Loading'
|
|
2
2
|
export { default as MSAModel, type MsaViewModel } from './model'
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
let canvasHandle: HTMLCanvasElement | undefined
|
|
2
|
+
|
|
3
|
+
export default function measureTextCanvas(text: string, fontSize: number) {
|
|
4
|
+
if (!canvasHandle) {
|
|
5
|
+
canvasHandle = document.createElement('canvas')
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
const ctx = canvasHandle.getContext('2d')
|
|
9
|
+
if (!ctx) {
|
|
10
|
+
throw new Error('no canvas context')
|
|
11
|
+
}
|
|
12
|
+
ctx.font = ctx.font.replace(/\d+px/, `${fontSize}px`)
|
|
13
|
+
return ctx.measureText(text).width
|
|
14
|
+
}
|
package/src/model.ts
CHANGED
|
@@ -9,7 +9,7 @@ import { saveAs } from 'file-saver'
|
|
|
9
9
|
import { FileLocation, ElementId } from '@jbrowse/core/util/types/mst'
|
|
10
10
|
import { FileLocation as FileLocationType } from '@jbrowse/core/util/types'
|
|
11
11
|
import { openLocation } from '@jbrowse/core/util/io'
|
|
12
|
-
import {
|
|
12
|
+
import { notEmpty, sum } from '@jbrowse/core/util'
|
|
13
13
|
import BaseViewModel from '@jbrowse/core/pluggableElementTypes/models/BaseViewModel'
|
|
14
14
|
|
|
15
15
|
// locals
|
|
@@ -37,6 +37,7 @@ import { DialogQueueSessionMixin } from './DialogQueue'
|
|
|
37
37
|
import { renderToSvg } from './renderToSvg'
|
|
38
38
|
import { Theme } from '@mui/material'
|
|
39
39
|
import { blocksX, blocksY } from './calculateBlocks'
|
|
40
|
+
import measureTextCanvas from './measureTextCanvas'
|
|
40
41
|
|
|
41
42
|
export interface RowDetails {
|
|
42
43
|
[key: string]: unknown
|
|
@@ -335,15 +336,12 @@ const model = types
|
|
|
335
336
|
/**
|
|
336
337
|
* #volatile
|
|
337
338
|
*/
|
|
338
|
-
|
|
339
|
+
marginLeft: 20,
|
|
339
340
|
|
|
340
341
|
/**
|
|
341
342
|
* #volatile
|
|
342
343
|
*/
|
|
343
|
-
|
|
344
|
-
left: 20,
|
|
345
|
-
top: 20,
|
|
346
|
-
},
|
|
344
|
+
error: undefined as unknown,
|
|
347
345
|
|
|
348
346
|
/**
|
|
349
347
|
* #volatile
|
|
@@ -765,6 +763,13 @@ const model = types
|
|
|
765
763
|
get msaAreaWidth() {
|
|
766
764
|
return self.width - self.treeAreaWidth
|
|
767
765
|
},
|
|
766
|
+
|
|
767
|
+
/**
|
|
768
|
+
* #getter
|
|
769
|
+
*/
|
|
770
|
+
get treeAreaWidthMinusMargin() {
|
|
771
|
+
return self.treeAreaWidth - self.marginLeft
|
|
772
|
+
},
|
|
768
773
|
/**
|
|
769
774
|
* #getter
|
|
770
775
|
*/
|
|
@@ -1009,7 +1014,7 @@ const model = types
|
|
|
1009
1014
|
if (rowHeight > 5) {
|
|
1010
1015
|
for (const node of hierarchy.leaves()) {
|
|
1011
1016
|
x = Math.max(
|
|
1012
|
-
|
|
1017
|
+
measureTextCanvas(
|
|
1013
1018
|
treeMetadata[node.data.name]?.genome || node.data.name,
|
|
1014
1019
|
fontSize,
|
|
1015
1020
|
),
|
|
@@ -1293,7 +1298,10 @@ const model = types
|
|
|
1293
1298
|
autorun(async () => {
|
|
1294
1299
|
if (self.treeWidthMatchesArea) {
|
|
1295
1300
|
self.setTreeWidth(
|
|
1296
|
-
Math.max(
|
|
1301
|
+
Math.max(
|
|
1302
|
+
50,
|
|
1303
|
+
self.treeAreaWidth - self.labelsWidth - 10 - self.marginLeft,
|
|
1304
|
+
),
|
|
1297
1305
|
)
|
|
1298
1306
|
}
|
|
1299
1307
|
}),
|
|
@@ -60,20 +60,6 @@ export default class ClustalMSA {
|
|
|
60
60
|
}
|
|
61
61
|
|
|
62
62
|
get tracks() {
|
|
63
|
-
return
|
|
64
|
-
? [
|
|
65
|
-
{
|
|
66
|
-
id: 'seqConsensus',
|
|
67
|
-
name: 'Sequence consensus',
|
|
68
|
-
data: this.seqConsensus,
|
|
69
|
-
customColorScheme: {
|
|
70
|
-
'*': 'white',
|
|
71
|
-
':': 'grey',
|
|
72
|
-
'.': 'darkgrey',
|
|
73
|
-
' ': 'black',
|
|
74
|
-
},
|
|
75
|
-
},
|
|
76
|
-
]
|
|
77
|
-
: []
|
|
63
|
+
return []
|
|
78
64
|
}
|
|
79
65
|
}
|
package/src/renderToSvg.tsx
CHANGED
package/src/version.ts
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
export const version = '3.1.
|
|
1
|
+
export const version = '3.1.5'
|