react-msaview 5.4.0 → 5.5.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.
Files changed (94) hide show
  1. package/LICENSE +21 -0
  2. package/bundle/index.js +465 -138
  3. package/bundle/index.js.map +7 -1
  4. package/dist/colorSchemes.js +11 -7
  5. package/dist/colorSchemes.js.map +1 -1
  6. package/dist/components/Checkbox2.js +3 -1
  7. package/dist/components/Checkbox2.js.map +1 -1
  8. package/dist/components/MSAViewer.d.ts +7 -1
  9. package/dist/components/MSAViewer.js +11 -10
  10. package/dist/components/MSAViewer.js.map +1 -1
  11. package/dist/components/Track.js +8 -5
  12. package/dist/components/Track.js.map +1 -1
  13. package/dist/components/dialogs/FeatureDialog.js +27 -23
  14. package/dist/components/dialogs/FeatureDialog.js.map +1 -1
  15. package/dist/components/dialogs/InterProScanDialog.js +2 -1
  16. package/dist/components/dialogs/InterProScanDialog.js.map +1 -1
  17. package/dist/components/header/MultiAlignmentSelector.js +0 -0
  18. package/dist/components/header/MultiAlignmentSelector.js.map +1 -1
  19. package/dist/components/msa/DomainLegend.d.ts +6 -0
  20. package/dist/components/msa/DomainLegend.js +41 -0
  21. package/dist/components/msa/DomainLegend.js.map +1 -0
  22. package/dist/components/msa/MSACanvasBlock.js +17 -5
  23. package/dist/components/msa/MSACanvasBlock.js.map +1 -1
  24. package/dist/components/msa/MSAPanel.js +3 -1
  25. package/dist/components/msa/MSAPanel.js.map +1 -1
  26. package/dist/components/msa/renderBoxFeatureCanvasBlock.js +58 -14
  27. package/dist/components/msa/renderBoxFeatureCanvasBlock.js.map +1 -1
  28. package/dist/components/msa/renderMSABlock.js +7 -9
  29. package/dist/components/msa/renderMSABlock.js.map +1 -1
  30. package/dist/components/msa/renderMSAMouseover.js +32 -4
  31. package/dist/components/msa/renderMSAMouseover.js.map +1 -1
  32. package/dist/components/renderCtx.d.ts +1 -1
  33. package/dist/components/tracks/renderTracksSvg.js +4 -4
  34. package/dist/components/tracks/renderTracksSvg.js.map +1 -1
  35. package/dist/components/tree/renderTreeCanvas.js +3 -0
  36. package/dist/components/tree/renderTreeCanvas.js.map +1 -1
  37. package/dist/constants.d.ts +3 -0
  38. package/dist/constants.js +16 -0
  39. package/dist/constants.js.map +1 -1
  40. package/dist/createPaletteMap.d.ts +5 -2
  41. package/dist/createPaletteMap.js +15 -5
  42. package/dist/createPaletteMap.js.map +1 -1
  43. package/dist/hierarchy.js +4 -1
  44. package/dist/hierarchy.js.map +1 -1
  45. package/dist/launchInterProScan.d.ts +2 -0
  46. package/dist/launchInterProScan.js.map +1 -1
  47. package/dist/model/msaModel.js.map +1 -1
  48. package/dist/model.d.ts +100 -3
  49. package/dist/model.js +121 -19
  50. package/dist/model.js.map +1 -1
  51. package/dist/neighborJoining.js +44 -30
  52. package/dist/neighborJoining.js.map +1 -1
  53. package/dist/renderToSvg.js +104 -74
  54. package/dist/renderToSvg.js.map +1 -1
  55. package/dist/{webpack.js → umd.js} +1 -1
  56. package/dist/umd.js.map +1 -0
  57. package/dist/version.d.ts +1 -1
  58. package/dist/version.js +1 -1
  59. package/package.json +8 -7
  60. package/src/colorSchemes.ts +12 -7
  61. package/src/components/Checkbox2.tsx +7 -1
  62. package/src/components/MSAViewer.tsx +31 -21
  63. package/src/components/Track.tsx +8 -5
  64. package/src/components/dialogs/FeatureDialog.tsx +62 -48
  65. package/src/components/dialogs/InterProScanDialog.tsx +2 -1
  66. package/src/components/header/MultiAlignmentSelector.tsx +0 -0
  67. package/src/components/msa/DomainLegend.tsx +74 -0
  68. package/src/components/msa/MSACanvasBlock.tsx +22 -4
  69. package/src/components/msa/MSAPanel.tsx +2 -0
  70. package/src/components/msa/renderBoxFeatureCanvasBlock.ts +73 -17
  71. package/src/components/msa/renderMSABlock.ts +5 -11
  72. package/src/components/msa/renderMSAMouseover.ts +32 -4
  73. package/src/components/renderCtx.ts +1 -0
  74. package/src/components/tracks/renderTracksSvg.ts +4 -4
  75. package/src/components/tree/renderTreeCanvas.ts +5 -1
  76. package/src/constants.ts +18 -0
  77. package/src/createPaletteMap.ts +18 -5
  78. package/src/hierarchy.ts +4 -1
  79. package/src/launchInterProScan.ts +3 -1
  80. package/src/model/msaModel.ts +3 -1
  81. package/src/model.ts +137 -36
  82. package/src/neighborJoining.ts +44 -31
  83. package/src/renderDomainLegendSvg.test.tsx +134 -0
  84. package/src/renderToSvg.tsx +210 -147
  85. package/src/segmentOverlay.test.ts +70 -0
  86. package/src/version.ts +1 -1
  87. package/bundle/index.js.LICENSE.txt +0 -100
  88. package/dist/components/util.d.ts +0 -1
  89. package/dist/components/util.js +0 -7
  90. package/dist/components/util.js.map +0 -1
  91. package/dist/webpack.js.map +0 -1
  92. package/src/components/util.ts +0 -9
  93. /package/dist/{webpack.d.ts → umd.d.ts} +0 -0
  94. /package/src/{webpack.ts → umd.ts} +0 -0
@@ -1 +1 @@
1
- {"version":3,"file":"renderToSvg.js","sourceRoot":"","sources":["../src/renderToSvg.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"renderToSvg.js","sourceRoot":"","sources":["../src/renderToSvg.tsx"],"names":[],"mappings":"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"}
@@ -3,4 +3,4 @@ export { default as MSAView } from "./components/Loading.js";
3
3
  export { default as MSAModelF } from "./model.js";
4
4
  export * from 'react-dom/client';
5
5
  export { React };
6
- //# sourceMappingURL=webpack.js.map
6
+ //# sourceMappingURL=umd.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"umd.js","sourceRoot":"","sources":["../src/umd.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAE9B,OAAO,EAAE,OAAO,IAAI,OAAO,EAAE,MAAM,yBAA0B,CAAA;AAC7D,OAAO,EAAqB,OAAO,IAAI,SAAS,EAAE,MAAM,YAAY,CAAA;AAEpE,cAAc,kBAAkB,CAAA;AAEhC,OAAO,EAAE,KAAK,EAAE,CAAA"}
package/dist/version.d.ts CHANGED
@@ -1 +1 @@
1
- export declare const version = "5.4.0";
1
+ export declare const version = "5.5.0";
package/dist/version.js CHANGED
@@ -1,2 +1,2 @@
1
- export const version = '5.4.0';
1
+ export const version = '5.5.0';
2
2
  //# sourceMappingURL=version.js.map
package/package.json CHANGED
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "name": "react-msaview",
3
3
  "author": "Colin",
4
- "version": "5.4.0",
4
+ "version": "5.5.0",
5
5
  "license": "MIT",
6
6
  "type": "module",
7
7
  "repository": {
@@ -35,23 +35,24 @@
35
35
  "react-dom": ">=16.8.0"
36
36
  },
37
37
  "devDependencies": {
38
- "@types/node": "^25.9.2"
38
+ "@types/node": "^26.0.1",
39
+ "esbuild": "^0.28.1"
39
40
  },
40
41
  "dependencies": {
41
42
  "@mui/icons-material": "^7.3.11",
42
43
  "@mui/material": "^7.3.11",
43
44
  "colord": "^2.9.3",
44
- "flatbush": "^4.6.1",
45
- "@jbrowse/svgcanvas": "5.4.0",
46
- "msa-parsers": "5.4.0"
45
+ "flatbush": "^4.6.2",
46
+ "@jbrowse/svgcanvas": "5.5.0",
47
+ "msa-parsers": "5.5.0"
47
48
  },
48
49
  "scripts": {
49
50
  "clean": "rimraf dist bundle",
50
51
  "watch": "pnpm build:esm --watch",
51
52
  "format": "prettier --write .",
52
53
  "build:esm": "tsc --project tsconfig.build.json",
53
- "build:bundle": "webpack",
54
- "build": "pnpm clean && pnpm build:esm && pnpm build:bundle",
54
+ "build:umd": "node esbuild.mjs",
55
+ "build": "pnpm clean && pnpm build:esm && pnpm build:umd",
55
56
  "statedocs": "rm -rf apidocs && mkdir apidocs && node --experimental-strip-types docgen/generateStateModelDocs.ts",
56
57
  "poststatedocs": "pnpm format",
57
58
  "test": "vitest"
@@ -6,8 +6,19 @@ import { transform } from './util.ts'
6
6
 
7
7
  extend([namesPlugin])
8
8
 
9
+ // standard A/C/G/T(/U) coloring, shared by the `jbrowse_dna` and `nucleotide`
10
+ // scheme names
11
+ const dna = {
12
+ A: green[500],
13
+ C: blue[500],
14
+ G: orange[500],
15
+ T: red[500],
16
+ U: red[500],
17
+ }
18
+
9
19
  const colorSchemes = {
10
20
  none: {},
21
+ nucleotide: dna,
11
22
  clustal: {
12
23
  G: 'orange',
13
24
  P: 'orange',
@@ -135,13 +146,7 @@ const colorSchemes = {
135
146
  T: '#19cc19',
136
147
  U: '#19cc19',
137
148
  },
138
- jbrowse_dna: {
139
- A: green[500],
140
- C: blue[500],
141
- G: orange[500],
142
- T: red[500],
143
- U: red[500],
144
- },
149
+ jbrowse_dna: dna,
145
150
  jalview_buried: {
146
151
  A: '#00a35c',
147
152
  R: '#00fc03',
@@ -17,7 +17,13 @@ export default function Checkbox2({
17
17
  <div>
18
18
  <FormControlLabel
19
19
  control={
20
- <Checkbox disabled={disabled} checked={checked} onChange={onChange} />
20
+ <Checkbox
21
+ disabled={disabled}
22
+ checked={checked}
23
+ onChange={() => {
24
+ onChange()
25
+ }}
26
+ />
21
27
  }
22
28
  label={label}
23
29
  />
@@ -1,4 +1,4 @@
1
- import React, { useEffect, useMemo } from 'react'
1
+ import React, { useEffect, useState } from 'react'
2
2
 
3
3
  import { createJBrowseTheme } from '@jbrowse/core/ui/theme'
4
4
  import useMeasure from '@jbrowse/core/util/useMeasure'
@@ -9,6 +9,8 @@ import Loading from './Loading.tsx'
9
9
 
10
10
  import type { FileLocation as FileLocationType } from '@jbrowse/core/util/types'
11
11
 
12
+ const theme = createJBrowseTheme()
13
+
12
14
  interface MSAViewerProps {
13
15
  msa?: string
14
16
  tree?: string
@@ -18,6 +20,12 @@ interface MSAViewerProps {
18
20
  gffFilehandle?: FileLocationType
19
21
  colorScheme?: string
20
22
  height?: number
23
+ /** initial per-column pixel width (zoom level) */
24
+ colWidth?: number
25
+ /** initial per-row pixel height */
26
+ rowHeight?: number
27
+ /** alignment columns (0-based) to highlight with a persistent overlay */
28
+ highlightColumns?: number[]
21
29
  /** row name to diff every other row against (matches render as ".") */
22
30
  relativeTo?: string
23
31
  }
@@ -31,33 +39,35 @@ export default function MSAViewer({
31
39
  gffFilehandle,
32
40
  colorScheme,
33
41
  height,
42
+ colWidth,
43
+ rowHeight,
44
+ highlightColumns,
34
45
  relativeTo,
35
46
  }: MSAViewerProps) {
36
- const theme = useMemo(() => createJBrowseTheme(), [])
37
- const model = useMemo(
38
- () =>
39
- MSAModelF().create({
40
- type: 'MsaView',
41
- ...(msa || tree || gff
42
- ? { data: { msa: msa ?? '', tree: tree ?? '', gff } }
43
- : {}),
44
- ...(msaFilehandle ? { msaFilehandle } : {}),
45
- ...(treeFilehandle ? { treeFilehandle } : {}),
46
- ...(gffFilehandle ? { gffFilehandle } : {}),
47
- ...(colorScheme ? { colorSchemeName: colorScheme } : {}),
48
- ...(height ? { height } : {}),
49
- ...(relativeTo ? { relativeTo } : {}),
50
- }),
51
- // eslint-disable-next-line react-hooks/exhaustive-deps
52
- [],
47
+ // lazy initializer: the model is created exactly once from the initial props
48
+ // (a stable MST instance — not a value safe to recompute, so not useMemo)
49
+ const [model] = useState(() =>
50
+ MSAModelF().create({
51
+ type: 'MsaView',
52
+ ...(msa || tree || gff
53
+ ? { data: { msa: msa ?? '', tree: tree ?? '', gff } }
54
+ : {}),
55
+ ...(msaFilehandle ? { msaFilehandle } : {}),
56
+ ...(treeFilehandle ? { treeFilehandle } : {}),
57
+ ...(gffFilehandle ? { gffFilehandle } : {}),
58
+ ...(colorScheme ? { colorSchemeName: colorScheme } : {}),
59
+ ...(height ? { height } : {}),
60
+ ...(colWidth ? { colWidth } : {}),
61
+ ...(rowHeight ? { rowHeight } : {}),
62
+ ...(highlightColumns ? { highlightColumns } : {}),
63
+ ...(relativeTo ? { relativeTo } : {}),
64
+ }),
53
65
  )
54
66
 
55
67
  const [ref, { width }] = useMeasure()
56
68
  useEffect(() => {
57
69
  if (width) {
58
- requestAnimationFrame(() => {
59
- model.setWidth(width)
60
- })
70
+ model.setWidth(width)
61
71
  }
62
72
  }, [model, width])
63
73
 
@@ -26,12 +26,15 @@ const TrackLabel = observer(function TrackLabel({
26
26
  track: BasicTrack
27
27
  }) {
28
28
  const [anchorEl, setAnchorEl] = useState<HTMLButtonElement>()
29
- const { drawLabels, rowHeight, treeAreaWidth: width } = model
29
+ const closeMenu = () => {
30
+ setAnchorEl(undefined)
31
+ }
32
+ const { drawLabels, fontSize, treeAreaWidth: width } = model
30
33
  const {
31
34
  model: { name, height },
32
35
  } = track
33
36
  const { classes } = useStyles()
34
- const trackLabelHeight = Math.min(height, Math.max(8, rowHeight - 8))
37
+ const trackLabelHeight = Math.min(height, fontSize)
35
38
 
36
39
  return (
37
40
  <div
@@ -62,14 +65,14 @@ const TrackLabel = observer(function TrackLabel({
62
65
  transitionDuration={0}
63
66
  open
64
67
  onClose={() => {
65
- setAnchorEl(undefined)
68
+ closeMenu()
66
69
  }}
67
70
  >
68
71
  <MenuItem
69
72
  dense
70
73
  onClick={() => {
71
74
  model.toggleTrack(track.model.id)
72
- setAnchorEl(undefined)
75
+ closeMenu()
73
76
  }}
74
77
  >
75
78
  Close
@@ -81,7 +84,7 @@ const TrackLabel = observer(function TrackLabel({
81
84
  TrackInfoDialog,
82
85
  { onClose, model: track.model },
83
86
  ])
84
- setAnchorEl(undefined)
87
+ closeMenu()
85
88
  }}
86
89
  >
87
90
  Get info
@@ -1,11 +1,18 @@
1
1
  import React from 'react'
2
2
 
3
3
  import { Dialog } from '@jbrowse/core/ui'
4
- import { Button, DialogContent } from '@mui/material'
4
+ import {
5
+ Button,
6
+ Checkbox,
7
+ DialogContent,
8
+ Table,
9
+ TableBody,
10
+ TableCell,
11
+ TableHead,
12
+ TableRow,
13
+ } from '@mui/material'
5
14
  import { observer } from 'mobx-react'
6
15
 
7
- import { getPalette } from '../../ggplotPalettes.ts'
8
-
9
16
  import type { MsaViewModel } from '../../model.ts'
10
17
 
11
18
  const Toggles = observer(function ({ model }: { model: MsaViewModel }) {
@@ -35,53 +42,60 @@ const Toggles = observer(function ({ model }: { model: MsaViewModel }) {
35
42
  )
36
43
  })
37
44
 
38
- const Table = observer(function ({ model }: { model: MsaViewModel }) {
39
- const { tidyInterProAnnotationTypes, featureFilters } = model
40
- const values = [...tidyInterProAnnotationTypes.values()]
41
- const palette = getPalette(values.length - 1)
45
+ const FeatureTable = observer(function ({ model }: { model: MsaViewModel }) {
46
+ const { tidyInterProAnnotationTypes, tidyInterProAnnotations, fillPalette } =
47
+ model
48
+ const counts = new Map<string, number>()
49
+ for (const annot of tidyInterProAnnotations) {
50
+ counts.set(annot.accession, (counts.get(annot.accession) ?? 0) + 1)
51
+ }
42
52
  return (
43
53
  <>
44
54
  <Toggles model={model} />
45
- <table>
46
- <thead>
47
- <tr>
48
- <td />
49
- <td>accession</td>
50
- <td>name</td>
51
- <td>description</td>
52
- </tr>
53
- </thead>
54
- <tbody>
55
- {values.map(({ accession, name, description }, idx) => (
56
- <tr key={accession}>
57
- <td>
58
- <input
59
- type="checkbox"
60
- checked={featureFilters.get(accession) ?? false}
61
- onChange={() => {
62
- model.setFilter(
63
- accession,
64
- !model.featureFilters.get(accession),
65
- )
66
- }}
67
- />
68
- </td>
69
- <td>{accession}</td>
70
- <td>{name}</td>
71
- <td>{description}</td>
72
- <td>
73
- <div
74
- style={{
75
- width: 20,
76
- height: 20,
77
- background: palette[idx] || 'black',
78
- }}
79
- />
80
- </td>
81
- </tr>
82
- ))}
83
- </tbody>
84
- </table>
55
+ <Table size="small">
56
+ <TableHead>
57
+ <TableRow>
58
+ <TableCell padding="checkbox" />
59
+ <TableCell>color</TableCell>
60
+ <TableCell>accession</TableCell>
61
+ <TableCell>name</TableCell>
62
+ <TableCell>count</TableCell>
63
+ <TableCell>description</TableCell>
64
+ </TableRow>
65
+ </TableHead>
66
+ <TableBody>
67
+ {[...tidyInterProAnnotationTypes.values()].map(
68
+ ({ accession, name, description }) => (
69
+ <TableRow key={accession}>
70
+ <TableCell padding="checkbox">
71
+ <Checkbox
72
+ checked={model.featureFilters.get(accession) ?? false}
73
+ onChange={() => {
74
+ model.setFilter(
75
+ accession,
76
+ !model.featureFilters.get(accession),
77
+ )
78
+ }}
79
+ />
80
+ </TableCell>
81
+ <TableCell>
82
+ <div
83
+ style={{
84
+ width: 20,
85
+ height: 20,
86
+ background: fillPalette[accession],
87
+ }}
88
+ />
89
+ </TableCell>
90
+ <TableCell>{accession}</TableCell>
91
+ <TableCell>{name}</TableCell>
92
+ <TableCell>{counts.get(accession)}</TableCell>
93
+ <TableCell>{description}</TableCell>
94
+ </TableRow>
95
+ ),
96
+ )}
97
+ </TableBody>
98
+ </Table>
85
99
  </>
86
100
  )
87
101
  })
@@ -103,7 +117,7 @@ const FeatureTypeDialog = observer(function ({
103
117
  maxWidth="xl"
104
118
  >
105
119
  <DialogContent>
106
- <Table model={model} />
120
+ <FeatureTable model={model} />
107
121
  </DialogContent>
108
122
  </Dialog>
109
123
  )
@@ -4,6 +4,7 @@ import { Dialog } from '@jbrowse/core/ui'
4
4
  import { getSession } from '@jbrowse/core/util'
5
5
  import { Button, DialogActions, DialogContent, Typography } from '@mui/material'
6
6
  import { observer } from 'mobx-react'
7
+ import { getUngappedSequence } from 'msa-parsers'
7
8
 
8
9
  import { launchInterProScan } from '../../launchInterProScan.ts'
9
10
 
@@ -251,7 +252,7 @@ const InterProScanDialog = observer(function ({
251
252
  algorithm: 'interproscan',
252
253
  programs: programs,
253
254
  seq: rows
254
- .map(row => [row[0], row[1].replaceAll('-', '')])
255
+ .map(row => [row[0], getUngappedSequence(row[1])])
255
256
  .filter(f => !!f[1])
256
257
  .map(row => `>${row[0]}\n${row[1]}`)
257
258
  .join('\n'),
@@ -0,0 +1,74 @@
1
+ import React, { useState } from 'react'
2
+
3
+ import ExpandLess from '@mui/icons-material/ExpandLess'
4
+ import ExpandMore from '@mui/icons-material/ExpandMore'
5
+ import { IconButton, Paper, Typography } from '@mui/material'
6
+ import { observer } from 'mobx-react'
7
+
8
+ import type { MsaViewModel } from '../../model.ts'
9
+
10
+ const DomainLegend = observer(function ({ model }: { model: MsaViewModel }) {
11
+ const [expanded, setExpanded] = useState(true)
12
+ const { actuallyShowDomains, visibleDomainTypes: visible, fillPalette } = model
13
+ const ExpandIcon = expanded ? ExpandLess : ExpandMore
14
+
15
+ return actuallyShowDomains && visible.length > 0 ? (
16
+ <Paper
17
+ elevation={3}
18
+ style={{
19
+ position: 'absolute',
20
+ top: 4,
21
+ right: 4,
22
+ zIndex: 100,
23
+ maxWidth: 260,
24
+ maxHeight: '60%',
25
+ display: 'flex',
26
+ flexDirection: 'column',
27
+ opacity: 0.95,
28
+ }}
29
+ >
30
+ <div
31
+ style={{
32
+ display: 'flex',
33
+ alignItems: 'center',
34
+ justifyContent: 'flex-end',
35
+ padding: '2px 4px 2px 8px',
36
+ }}
37
+ >
38
+ <IconButton
39
+ size="small"
40
+ onClick={() => {
41
+ setExpanded(!expanded)
42
+ }}
43
+ >
44
+ <ExpandIcon fontSize="small" />
45
+ </IconButton>
46
+ </div>
47
+ {expanded ? (
48
+ <div style={{ overflow: 'auto', padding: '0 8px 6px' }}>
49
+ {visible.map(({ accession, name }) => (
50
+ <div
51
+ key={accession}
52
+ style={{ display: 'flex', alignItems: 'center', gap: 6 }}
53
+ title={accession}
54
+ >
55
+ <div
56
+ style={{
57
+ width: 12,
58
+ height: 12,
59
+ flexShrink: 0,
60
+ background: fillPalette[accession],
61
+ }}
62
+ />
63
+ <Typography variant="caption" noWrap>
64
+ {name}
65
+ </Typography>
66
+ </div>
67
+ ))}
68
+ </div>
69
+ ) : null}
70
+ </Paper>
71
+ ) : null
72
+ })
73
+
74
+ export default DomainLegend
@@ -89,7 +89,7 @@ const MSACanvasBlock = observer(function ({
89
89
  ])
90
90
 
91
91
  const [mousePosition, setMousePosition] = useState<{ x: number; y: number }>()
92
- const { hoveredInsertion } = model
92
+ const { hoveredInsertion, mouseOverDomains } = model
93
93
 
94
94
  return (
95
95
  <>
@@ -116,10 +116,11 @@ const MSACanvasBlock = observer(function ({
116
116
  } else {
117
117
  model.setMousePos(undefined, undefined)
118
118
  }
119
- // only track client coords when an insertion is hovered (the only
120
- // consumer is the tooltip below); avoids a re-render on every move
119
+ // only track client coords when there's something to show in the
120
+ // tooltip (insertion or a domain under the cursor); avoids a
121
+ // re-render on every move over plain alignment cells
121
122
  setMousePosition(
122
- model.hoveredInsertion
123
+ model.hoveredInsertion || model.mouseOverDomains.length > 0
123
124
  ? { x: event.clientX, y: event.clientY }
124
125
  : undefined,
125
126
  )
@@ -167,6 +168,23 @@ const MSACanvasBlock = observer(function ({
167
168
  : hoveredInsertion.letters}
168
169
  </BaseTooltip>
169
170
  ) : null}
171
+ {!hoveredInsertion && mouseOverDomains.length > 0 && mousePosition ? (
172
+ <BaseTooltip
173
+ clientPoint={{ x: mousePosition.x, y: mousePosition.y + 15 }}
174
+ >
175
+ {mouseOverDomains.map(d => (
176
+ <div key={`${d.accession}-${d.start}-${d.end}`}>
177
+ <b>{d.name}</b> ({d.accession}) {d.start}-{d.end}
178
+ {d.description ? (
179
+ <>
180
+ <br />
181
+ {d.description}
182
+ </>
183
+ ) : null}
184
+ </div>
185
+ ))}
186
+ </BaseTooltip>
187
+ ) : null}
170
188
  </>
171
189
  )
172
190
  })
@@ -2,6 +2,7 @@ import React from 'react'
2
2
 
3
3
  import { observer } from 'mobx-react'
4
4
 
5
+ import DomainLegend from './DomainLegend.tsx'
5
6
  import MSACanvas from './MSACanvas.tsx'
6
7
  import MSAMouseoverCanvas from './MSAMouseoverCanvas.tsx'
7
8
 
@@ -13,6 +14,7 @@ const MSAPanel = observer(function ({ model }: { model: MsaViewModel }) {
13
14
  <div style={{ position: 'relative' }}>
14
15
  <MSACanvas model={model} />
15
16
  <MSAMouseoverCanvas model={model} />
17
+ <DomainLegend model={model} />
16
18
  </div>
17
19
  )
18
20
  })