react-msaview 3.1.12 → 3.2.1

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 (233) hide show
  1. package/bundle/index.js +32 -31
  2. package/dist/colorSchemes.d.ts +2 -2
  3. package/dist/colorSchemes.js +5 -6
  4. package/dist/colorSchemes.js.map +1 -1
  5. package/dist/components/Loading.d.ts +1 -1
  6. package/dist/components/Loading.js +7 -5
  7. package/dist/components/Loading.js.map +1 -1
  8. package/dist/components/MSAView.d.ts +1 -1
  9. package/dist/components/MSAView.js +13 -9
  10. package/dist/components/MSAView.js.map +1 -1
  11. package/dist/components/ResizeHandles.d.ts +1 -1
  12. package/dist/components/ResizeHandles.js +8 -4
  13. package/dist/components/ResizeHandles.js.map +1 -1
  14. package/dist/components/SequenceTextArea.js +9 -3
  15. package/dist/components/SequenceTextArea.js.map +1 -1
  16. package/dist/components/TextTrack.d.ts +1 -1
  17. package/dist/components/TextTrack.js +1 -1
  18. package/dist/components/TextTrack.js.map +1 -1
  19. package/dist/components/Track.d.ts +1 -1
  20. package/dist/components/Track.js +6 -2
  21. package/dist/components/Track.js.map +1 -1
  22. package/dist/components/VerticalScrollbar.d.ts +6 -0
  23. package/dist/components/VerticalScrollbar.js +69 -0
  24. package/dist/components/VerticalScrollbar.js.map +1 -0
  25. package/dist/components/dialogs/AboutDialog.js +3 -1
  26. package/dist/components/dialogs/AboutDialog.js.map +1 -1
  27. package/dist/components/dialogs/AddTrackDialog.d.ts +3 -3
  28. package/dist/components/dialogs/AddTrackDialog.js +8 -3
  29. package/dist/components/dialogs/AddTrackDialog.js.map +1 -1
  30. package/dist/components/dialogs/DomainDialog.d.ts +1 -1
  31. package/dist/components/dialogs/DomainDialog.js +8 -4
  32. package/dist/components/dialogs/DomainDialog.js.map +1 -1
  33. package/dist/components/dialogs/ExportSVGDialog.d.ts +1 -1
  34. package/dist/components/dialogs/ExportSVGDialog.js +29 -17
  35. package/dist/components/dialogs/ExportSVGDialog.js.map +1 -1
  36. package/dist/components/dialogs/FeatureDialog.d.ts +1 -1
  37. package/dist/components/dialogs/FeatureDialog.js +8 -4
  38. package/dist/components/dialogs/FeatureDialog.js.map +1 -1
  39. package/dist/components/dialogs/{InterProScanPanel.d.ts → InterProScanDialog.d.ts} +1 -1
  40. package/dist/components/dialogs/{InterProScanPanel.js → InterProScanDialog.js} +26 -11
  41. package/dist/components/dialogs/InterProScanDialog.js.map +1 -0
  42. package/dist/components/dialogs/MetadataDialog.d.ts +1 -1
  43. package/dist/components/dialogs/MetadataDialog.js +3 -1
  44. package/dist/components/dialogs/MetadataDialog.js.map +1 -1
  45. package/dist/components/dialogs/SettingsDialog.d.ts +1 -1
  46. package/dist/components/dialogs/SettingsDialog.js +62 -15
  47. package/dist/components/dialogs/SettingsDialog.js.map +1 -1
  48. package/dist/components/dialogs/TracklistDialog.d.ts +3 -3
  49. package/dist/components/dialogs/TracklistDialog.js +8 -3
  50. package/dist/components/dialogs/TracklistDialog.js.map +1 -1
  51. package/dist/components/dialogs/UserProvidedDomainsDialog.d.ts +7 -0
  52. package/dist/components/dialogs/UserProvidedDomainsDialog.js +64 -0
  53. package/dist/components/dialogs/UserProvidedDomainsDialog.js.map +1 -0
  54. package/dist/components/header/Header.d.ts +1 -1
  55. package/dist/components/header/Header.js +11 -4
  56. package/dist/components/header/Header.js.map +1 -1
  57. package/dist/components/header/HeaderInfoArea.d.ts +1 -1
  58. package/dist/components/header/HeaderInfoArea.js +5 -2
  59. package/dist/components/header/HeaderInfoArea.js.map +1 -1
  60. package/dist/components/header/HeaderMenu.d.ts +1 -1
  61. package/dist/components/header/HeaderMenu.js +12 -4
  62. package/dist/components/header/HeaderMenu.js.map +1 -1
  63. package/dist/components/header/HeaderMenuExtra.d.ts +1 -1
  64. package/dist/components/header/HeaderMenuExtra.js +55 -35
  65. package/dist/components/header/HeaderMenuExtra.js.map +1 -1
  66. package/dist/components/header/HeaderStatusArea.d.ts +2 -2
  67. package/dist/components/header/HeaderStatusArea.js +1 -1
  68. package/dist/components/header/HeaderStatusArea.js.map +1 -1
  69. package/dist/components/header/MultiAlignmentSelector.d.ts +1 -1
  70. package/dist/components/header/ZoomControls.js +45 -3
  71. package/dist/components/header/ZoomControls.js.map +1 -1
  72. package/dist/components/import/ImportForm.d.ts +3 -3
  73. package/dist/components/import/ImportForm.js +15 -2
  74. package/dist/components/import/ImportForm.js.map +1 -1
  75. package/dist/components/import/ImportFormExamples.d.ts +1 -1
  76. package/dist/components/import/ImportFormExamples.js +53 -38
  77. package/dist/components/import/ImportFormExamples.js.map +1 -1
  78. package/dist/components/import/util.d.ts +2 -2
  79. package/dist/components/minimap/Minimap.d.ts +1 -1
  80. package/dist/components/minimap/Minimap.js +24 -17
  81. package/dist/components/minimap/Minimap.js.map +1 -1
  82. package/dist/components/minimap/MinimapSVG.d.ts +1 -1
  83. package/dist/components/minimap/MinimapSVG.js +1 -1
  84. package/dist/components/minimap/MinimapSVG.js.map +1 -1
  85. package/dist/components/msa/MSACanvas.d.ts +1 -1
  86. package/dist/components/msa/MSACanvas.js +3 -3
  87. package/dist/components/msa/MSACanvas.js.map +1 -1
  88. package/dist/components/msa/MSACanvasBlock.d.ts +3 -3
  89. package/dist/components/msa/MSACanvasBlock.js +9 -6
  90. package/dist/components/msa/MSACanvasBlock.js.map +1 -1
  91. package/dist/components/msa/MSAMouseoverCanvas.d.ts +1 -1
  92. package/dist/components/msa/MSAPanel.d.ts +1 -1
  93. package/dist/components/msa/renderBoxFeatureCanvasBlock.d.ts +1 -1
  94. package/dist/components/msa/renderBoxFeatureCanvasBlock.js +3 -4
  95. package/dist/components/msa/renderBoxFeatureCanvasBlock.js.map +1 -1
  96. package/dist/components/msa/renderMSABlock.d.ts +2 -2
  97. package/dist/components/msa/renderMSABlock.js +16 -16
  98. package/dist/components/msa/renderMSABlock.js.map +1 -1
  99. package/dist/components/msa/renderMSAMouseover.d.ts +1 -1
  100. package/dist/components/msa/renderMSAMouseover.js +3 -3
  101. package/dist/components/msa/renderMSAMouseover.js.map +1 -1
  102. package/dist/components/tree/TreeBranchMenu.d.ts +1 -1
  103. package/dist/components/tree/TreeBranchMenu.js +6 -3
  104. package/dist/components/tree/TreeBranchMenu.js.map +1 -1
  105. package/dist/components/tree/TreeCanvas.d.ts +1 -1
  106. package/dist/components/tree/TreeCanvas.js +13 -12
  107. package/dist/components/tree/TreeCanvas.js.map +1 -1
  108. package/dist/components/tree/TreeCanvasBlock.d.ts +1 -1
  109. package/dist/components/tree/TreeCanvasBlock.js +13 -5
  110. package/dist/components/tree/TreeCanvasBlock.js.map +1 -1
  111. package/dist/components/tree/TreeNodeMenu.d.ts +1 -1
  112. package/dist/components/tree/TreeNodeMenu.js +3 -3
  113. package/dist/components/tree/TreeNodeMenu.js.map +1 -1
  114. package/dist/components/tree/TreePanel.d.ts +1 -1
  115. package/dist/components/tree/TreeRuler.d.ts +1 -1
  116. package/dist/components/tree/dialogs/TreeNodeInfoDialog.d.ts +3 -3
  117. package/dist/components/tree/dialogs/TreeNodeInfoDialog.js +5 -2
  118. package/dist/components/tree/dialogs/TreeNodeInfoDialog.js.map +1 -1
  119. package/dist/components/tree/renderTreeCanvas.d.ts +3 -3
  120. package/dist/components/tree/renderTreeCanvas.js +25 -9
  121. package/dist/components/tree/renderTreeCanvas.js.map +1 -1
  122. package/dist/components/util.js +1 -4
  123. package/dist/components/util.js.map +1 -1
  124. package/dist/ggplotPalettes.js.map +1 -1
  125. package/dist/launchInterProScan.d.ts +1 -1
  126. package/dist/launchInterProScan.js +11 -13
  127. package/dist/launchInterProScan.js.map +1 -1
  128. package/dist/model/DataModel.d.ts +5 -1
  129. package/dist/model/DataModel.js +10 -1
  130. package/dist/model/DataModel.js.map +1 -1
  131. package/dist/model/DialogQueue.d.ts +1 -1
  132. package/dist/model/DialogQueue.js +0 -1
  133. package/dist/model/DialogQueue.js.map +1 -1
  134. package/dist/model.d.ts +187 -35
  135. package/dist/model.js +317 -94
  136. package/dist/model.js.map +1 -1
  137. package/dist/parseGFF.js +8 -6
  138. package/dist/parseGFF.js.map +1 -1
  139. package/dist/parseNewick.js +1 -2
  140. package/dist/parseNewick.js.map +1 -1
  141. package/dist/parsers/ClustalMSA.d.ts +2 -2
  142. package/dist/parsers/ClustalMSA.js.map +1 -1
  143. package/dist/parsers/FastaMSA.d.ts +1 -1
  144. package/dist/parsers/FastaMSA.js +3 -3
  145. package/dist/parsers/FastaMSA.js.map +1 -1
  146. package/dist/parsers/StockholmMSA.d.ts +7 -7
  147. package/dist/parsers/StockholmMSA.js +4 -4
  148. package/dist/parsers/StockholmMSA.js.map +1 -1
  149. package/dist/renderToSvg.d.ts +2 -2
  150. package/dist/renderToSvg.js +6 -11
  151. package/dist/renderToSvg.js.map +1 -1
  152. package/dist/reparseTree.d.ts +1 -1
  153. package/dist/rowCoordinateCalculations.d.ts +2 -0
  154. package/dist/rowCoordinateCalculations.js +26 -0
  155. package/dist/rowCoordinateCalculations.js.map +1 -0
  156. package/dist/rowCoordinateCalculations.test.d.ts +1 -0
  157. package/dist/rowCoordinateCalculations.test.js +18 -0
  158. package/dist/rowCoordinateCalculations.test.js.map +1 -0
  159. package/dist/util.d.ts +2 -2
  160. package/dist/util.js +0 -2
  161. package/dist/util.js.map +1 -1
  162. package/dist/version.d.ts +1 -1
  163. package/dist/version.js +1 -1
  164. package/dist/version.js.map +1 -1
  165. package/package.json +10 -3
  166. package/src/colorSchemes.ts +7 -6
  167. package/src/components/Checkbox2.tsx +1 -1
  168. package/src/components/Loading.tsx +18 -6
  169. package/src/components/MSAView.tsx +27 -18
  170. package/src/components/ResizeHandles.tsx +9 -5
  171. package/src/components/SequenceTextArea.tsx +10 -4
  172. package/src/components/TextTrack.tsx +3 -3
  173. package/src/components/Track.tsx +9 -5
  174. package/src/components/VerticalScrollbar.tsx +89 -0
  175. package/src/components/dialogs/AboutDialog.tsx +7 -1
  176. package/src/components/dialogs/AddTrackDialog.tsx +15 -5
  177. package/src/components/dialogs/DomainDialog.tsx +12 -5
  178. package/src/components/dialogs/ExportSVGDialog.tsx +37 -18
  179. package/src/components/dialogs/FeatureDialog.tsx +10 -8
  180. package/src/components/dialogs/{InterProScanPanel.tsx → InterProScanDialog.tsx} +30 -13
  181. package/src/components/dialogs/MetadataDialog.tsx +9 -2
  182. package/src/components/dialogs/SettingsDialog.tsx +98 -19
  183. package/src/components/dialogs/TracklistDialog.tsx +18 -4
  184. package/src/components/dialogs/UserProvidedDomainsDialog.tsx +139 -0
  185. package/src/components/header/Header.tsx +12 -5
  186. package/src/components/header/HeaderInfoArea.tsx +4 -3
  187. package/src/components/header/HeaderMenu.tsx +13 -8
  188. package/src/components/header/HeaderMenuExtra.tsx +59 -43
  189. package/src/components/header/HeaderStatusArea.tsx +2 -6
  190. package/src/components/header/MultiAlignmentSelector.tsx +1 -1
  191. package/src/components/header/ZoomControls.tsx +52 -2
  192. package/src/components/import/ImportForm.tsx +16 -4
  193. package/src/components/import/ImportFormExamples.tsx +77 -64
  194. package/src/components/import/util.ts +2 -2
  195. package/src/components/minimap/Minimap.tsx +34 -29
  196. package/src/components/minimap/MinimapSVG.tsx +2 -2
  197. package/src/components/msa/MSACanvas.tsx +11 -4
  198. package/src/components/msa/MSACanvasBlock.tsx +10 -7
  199. package/src/components/msa/MSAMouseoverCanvas.tsx +1 -1
  200. package/src/components/msa/MSAPanel.tsx +1 -1
  201. package/src/components/msa/renderBoxFeatureCanvasBlock.ts +8 -9
  202. package/src/components/msa/renderMSABlock.ts +44 -24
  203. package/src/components/msa/renderMSAMouseover.ts +4 -4
  204. package/src/components/tree/TreeBranchMenu.tsx +6 -4
  205. package/src/components/tree/TreeCanvas.tsx +15 -16
  206. package/src/components/tree/TreeCanvasBlock.tsx +14 -6
  207. package/src/components/tree/TreeNodeMenu.tsx +4 -4
  208. package/src/components/tree/TreePanel.tsx +1 -1
  209. package/src/components/tree/TreeRuler.tsx +1 -1
  210. package/src/components/tree/dialogs/TreeNodeInfoDialog.tsx +12 -3
  211. package/src/components/tree/renderTreeCanvas.ts +32 -12
  212. package/src/components/util.ts +2 -5
  213. package/src/ggplotPalettes.ts +1 -1
  214. package/src/launchInterProScan.ts +13 -15
  215. package/src/model/DataModel.ts +10 -0
  216. package/src/model/DialogQueue.ts +1 -2
  217. package/src/model.ts +355 -112
  218. package/src/parseGFF.ts +13 -11
  219. package/src/parseNewick.ts +4 -4
  220. package/src/parsers/ClustalMSA.ts +3 -3
  221. package/src/parsers/FastaMSA.ts +5 -5
  222. package/src/parsers/StockholmMSA.ts +11 -11
  223. package/src/renderToSvg.tsx +7 -8
  224. package/src/reparseTree.ts +1 -1
  225. package/src/rowCoordinateCalculations.test.ts +19 -0
  226. package/src/rowCoordinateCalculations.ts +26 -0
  227. package/src/util.ts +2 -4
  228. package/src/version.ts +1 -1
  229. package/dist/components/dialogs/InterProScanPanel.js.map +0 -1
  230. package/dist/components/dialogs/UserProvidedResultPanel.d.ts +0 -7
  231. package/dist/components/dialogs/UserProvidedResultPanel.js +0 -56
  232. package/dist/components/dialogs/UserProvidedResultPanel.js.map +0 -1
  233. package/src/components/dialogs/UserProvidedResultPanel.tsx +0 -119
@@ -2,12 +2,19 @@ import React, { useEffect, useState, useRef } from 'react'
2
2
  import { observer } from 'mobx-react'
3
3
 
4
4
  // locals
5
- import { MsaViewModel } from '../../model'
5
+ import type { MsaViewModel } from '../../model'
6
6
  import MSACanvasBlock from './MSACanvasBlock'
7
7
  import Loading from './Loading'
8
8
 
9
9
  const MSACanvas = observer(function ({ model }: { model: MsaViewModel }) {
10
- const { MSA, msaFilehandle, height, msaAreaWidth, blocks2d } = model
10
+ const {
11
+ MSA,
12
+ verticalScrollbarWidth,
13
+ msaFilehandle,
14
+ height,
15
+ msaAreaWidth,
16
+ blocks2d,
17
+ } = model
11
18
  const ref = useRef<HTMLDivElement>(null)
12
19
  // wheel
13
20
  const scheduled = useRef(false)
@@ -39,7 +46,7 @@ const MSACanvas = observer(function ({ model }: { model: MsaViewModel }) {
39
46
  event.preventDefault()
40
47
  event.stopPropagation()
41
48
  }
42
- curr.addEventListener('wheel', onWheel)
49
+ curr.addEventListener('wheel', onWheel, { passive: false })
43
50
  return () => {
44
51
  curr.removeEventListener('wheel', onWheel)
45
52
  }
@@ -115,7 +122,7 @@ const MSACanvas = observer(function ({ model }: { model: MsaViewModel }) {
115
122
  style={{
116
123
  position: 'relative',
117
124
  height,
118
- width: msaAreaWidth,
125
+ width: msaAreaWidth - verticalScrollbarWidth,
119
126
  overflow: 'hidden',
120
127
  }}
121
128
  >
@@ -5,11 +5,11 @@ import { observer } from 'mobx-react'
5
5
 
6
6
  // locals
7
7
  import { renderMSABlock } from './renderMSABlock'
8
- import { MsaViewModel } from '../../model'
8
+ import type { MsaViewModel } from '../../model'
9
9
  import { colorContrast } from '../../util'
10
10
  import { renderBoxFeatureCanvasBlock } from './renderBoxFeatureCanvasBlock'
11
11
 
12
- const MSABlock = observer(function ({
12
+ const MSACanvasBlock = observer(function ({
13
13
  model,
14
14
  offsetX,
15
15
  offsetY,
@@ -45,7 +45,8 @@ const MSABlock = observer(function ({
45
45
  return autorun(() => {
46
46
  ctx.resetTransform()
47
47
  ctx.clearRect(0, 0, blockSize, blockSize)
48
- if (model.showDomains) {
48
+ const { actuallyShowDomains } = model
49
+ if (actuallyShowDomains) {
49
50
  renderBoxFeatureCanvasBlock({
50
51
  ctx,
51
52
  offsetX,
@@ -74,7 +75,7 @@ const MSABlock = observer(function ({
74
75
  const { left, top } = ref.current.getBoundingClientRect()
75
76
  const mouseX = event.clientX - left + offsetX
76
77
  const mouseY = event.clientY - top + offsetY
77
- const x = Math.floor(mouseX / colWidth) + 1
78
+ const x = Math.floor(mouseX / colWidth)
78
79
  const y = Math.floor(mouseY / rowHeight)
79
80
  model.setMousePos(x, y)
80
81
  }}
@@ -85,7 +86,7 @@ const MSABlock = observer(function ({
85
86
  const { left, top } = ref.current.getBoundingClientRect()
86
87
  const mouseX = event.clientX - left + offsetX
87
88
  const mouseY = event.clientY - top + offsetY
88
- const x = Math.floor(mouseX / colWidth) + 1
89
+ const x = Math.floor(mouseX / colWidth)
89
90
  const y = Math.floor(mouseY / rowHeight)
90
91
  if (x === mouseClickCol && y === mouseClickRow) {
91
92
  model.setMouseClickPos(undefined, undefined)
@@ -93,7 +94,9 @@ const MSABlock = observer(function ({
93
94
  model.setMouseClickPos(x, y)
94
95
  }
95
96
  }}
96
- onMouseLeave={() => model.setMousePos()}
97
+ onMouseLeave={() => {
98
+ model.setMousePos()
99
+ }}
97
100
  width={blockSize * highResScaleFactor}
98
101
  height={blockSize * highResScaleFactor}
99
102
  style={{
@@ -107,4 +110,4 @@ const MSABlock = observer(function ({
107
110
  )
108
111
  })
109
112
 
110
- export default MSABlock
113
+ export default MSACanvasBlock
@@ -3,7 +3,7 @@ import { observer } from 'mobx-react'
3
3
  import { autorun } from 'mobx'
4
4
 
5
5
  // locals
6
- import { MsaViewModel } from '../../model'
6
+ import type { MsaViewModel } from '../../model'
7
7
  import { renderMouseover } from './renderMSAMouseover'
8
8
 
9
9
  const MSAMouseoverCanvas = observer(function ({
@@ -5,7 +5,7 @@ import { observer } from 'mobx-react'
5
5
  import MSACanvas from './MSACanvas'
6
6
  import MSAMouseoverCanvas from './MSAMouseoverCanvas'
7
7
  // types
8
- import { MsaViewModel } from '../../model'
8
+ import type { MsaViewModel } from '../../model'
9
9
 
10
10
  const MSAPanel = observer(function ({ model }: { model: MsaViewModel }) {
11
11
  return (
@@ -1,8 +1,8 @@
1
- import { HierarchyNode } from 'd3-hierarchy'
1
+ import type { HierarchyNode } from 'd3-hierarchy'
2
2
 
3
3
  // locals
4
- import { MsaViewModel } from '../../model'
5
- import { NodeWithIdsAndLength } from '../../util'
4
+ import type { MsaViewModel } from '../../model'
5
+ import type { NodeWithIdsAndLength } from '../../util'
6
6
 
7
7
  export function renderBoxFeatureCanvasBlock({
8
8
  model,
@@ -19,7 +19,7 @@ export function renderBoxFeatureCanvasBlock({
19
19
  highResScaleFactorOverride?: number
20
20
  blockSizeYOverride?: number
21
21
  }) {
22
- const { hierarchy, blockSize, rowHeight, highResScaleFactor, showDomains } =
22
+ const { leaves, blockSize, rowHeight, highResScaleFactor, showDomains } =
23
23
  model
24
24
  if (showDomains) {
25
25
  const k = highResScaleFactorOverride || highResScaleFactor
@@ -28,7 +28,6 @@ export function renderBoxFeatureCanvasBlock({
28
28
  ctx.scale(k, k)
29
29
  ctx.translate(-offsetX, rowHeight / 2 - offsetY)
30
30
 
31
- const leaves = hierarchy.leaves()
32
31
  const yStart = Math.max(0, Math.floor((offsetY - rowHeight) / rowHeight))
33
32
  const yEnd = Math.max(0, Math.ceil((offsetY + by + rowHeight) / rowHeight))
34
33
  const visibleLeaves = leaves.slice(yStart, yEnd)
@@ -56,7 +55,7 @@ function drawTiles({
56
55
  rowHeight,
57
56
  fillPalette,
58
57
  strokePalette,
59
- tidyFilteredGatheredAnnotations,
58
+ tidyFilteredGatheredInterProAnnotations,
60
59
  } = model
61
60
 
62
61
  for (const node of visibleLeaves) {
@@ -66,7 +65,7 @@ function drawTiles({
66
65
  } = node
67
66
  const y = x!
68
67
 
69
- const entry = tidyFilteredGatheredAnnotations?.[name]
68
+ const entry = tidyFilteredGatheredInterProAnnotations[name]
70
69
 
71
70
  let j = 0
72
71
  if (entry) {
@@ -74,8 +73,8 @@ function drawTiles({
74
73
  const m1 = model.seqCoordToRowSpecificGlobalCoord(name, start - 1)
75
74
  const m2 = model.seqCoordToRowSpecificGlobalCoord(name, end)
76
75
  const x = m1 * colWidth
77
- ctx.fillStyle = fillPalette[accession]
78
- ctx.strokeStyle = strokePalette[accession]
76
+ ctx.fillStyle = fillPalette[accession]!
77
+ ctx.strokeStyle = strokePalette[accession]!
79
78
  const h = subFeatureRows ? 4 : rowHeight
80
79
  const t = y - rowHeight + (subFeatureRows ? j * h : 0)
81
80
  const lw = colWidth * (m2 - m1)
@@ -1,10 +1,10 @@
1
- import { HierarchyNode } from 'd3-hierarchy'
2
- import { Theme } from '@mui/material'
1
+ import type { HierarchyNode } from 'd3-hierarchy'
2
+ import type { Theme } from '@mui/material'
3
3
 
4
4
  // locals
5
- import { MsaViewModel } from '../../model'
5
+ import type { MsaViewModel } from '../../model'
6
6
  import { getClustalXColor, getPercentIdentityColor } from '../../colorSchemes'
7
- import { NodeWithIdsAndLength } from '../../util'
7
+ import type { NodeWithIdsAndLength } from '../../util'
8
8
 
9
9
  export function renderMSABlock({
10
10
  model,
@@ -28,13 +28,13 @@ export function renderMSABlock({
28
28
  blockSizeYOverride?: number
29
29
  }) {
30
30
  const {
31
- hierarchy,
32
31
  colWidth,
33
32
  blockSize,
34
33
  rowHeight,
35
34
  fontSize,
36
35
  highResScaleFactor,
37
- showDomains,
36
+ actuallyShowDomains,
37
+ leaves,
38
38
  } = model
39
39
  const k = highResScaleFactorOverride || highResScaleFactor
40
40
  const bx = blockSizeXOverride || blockSize
@@ -45,15 +45,13 @@ export function renderMSABlock({
45
45
  ctx.textAlign = 'center'
46
46
  ctx.font = ctx.font.replace(/\d+px/, `${fontSize}px`)
47
47
 
48
- const leaves = hierarchy.leaves()
49
-
50
48
  const yStart = Math.max(0, Math.floor((offsetY - rowHeight) / rowHeight))
51
49
  const yEnd = Math.max(0, Math.ceil((offsetY + by + rowHeight) / rowHeight))
52
50
  const xStart = Math.max(0, Math.floor(offsetX / colWidth))
53
51
  const xEnd = Math.max(0, Math.ceil((offsetX + bx) / colWidth))
54
52
  const visibleLeaves = leaves.slice(yStart, yEnd)
55
53
 
56
- if (!showDomains) {
54
+ if (!actuallyShowDomains) {
57
55
  drawTiles({
58
56
  model,
59
57
  ctx,
@@ -101,6 +99,7 @@ function drawTiles({
101
99
  colorSchemeName,
102
100
  colorScheme,
103
101
  colStats,
102
+ colStatsSums,
104
103
  columns,
105
104
  colWidth,
106
105
  rowHeight,
@@ -111,24 +110,35 @@ function drawTiles({
111
110
  data: { name },
112
111
  } = node
113
112
  const y = node.x!
114
- const str = columns[name]?.slice(xStart, xEnd)
115
- for (let i = 0; i < str?.length; i++) {
116
- const letter = str[i]
113
+ const str = columns[name]!.slice(xStart, xEnd)
114
+ for (let i = 0; i < str.length; i++) {
115
+ const letter = str[i]!
117
116
  const color =
118
117
  colorSchemeName === 'clustalx_protein_dynamic'
119
- ? getClustalXColor(colStats[xStart + i], model, name, xStart + i)
118
+ ? getClustalXColor(
119
+ colStats[xStart + i]!,
120
+ colStatsSums[xStart + i]!,
121
+ model,
122
+ name,
123
+ xStart + i,
124
+ )
120
125
  : colorSchemeName === 'percent_identity_dynamic'
121
126
  ? getPercentIdentityColor(
122
- colStats[xStart + i],
127
+ colStats[xStart + i]!,
128
+ colStatsSums[xStart + i]!,
123
129
  model,
124
130
  name,
125
131
  xStart + i,
126
132
  )
127
133
  : colorScheme[letter.toUpperCase()]
128
134
  if (bgColor) {
129
- const x = i * colWidth + offsetX - (offsetX % colWidth)
130
135
  ctx.fillStyle = color || theme.palette.background.default
131
- ctx.fillRect(x, y - rowHeight, colWidth, rowHeight)
136
+ ctx.fillRect(
137
+ i * colWidth + offsetX - (offsetX % colWidth),
138
+ y - rowHeight,
139
+ colWidth,
140
+ rowHeight,
141
+ )
132
142
  }
133
143
  }
134
144
  }
@@ -152,23 +162,33 @@ function drawText({
152
162
  xStart: number
153
163
  xEnd: number
154
164
  }) {
155
- const { bgColor, showDomains, colorScheme, columns, colWidth, rowHeight } =
156
- model
157
- if (rowHeight >= 5 && colWidth > rowHeight / 2) {
165
+ const {
166
+ bgColor,
167
+ actuallyShowDomains,
168
+ showMsaLetters,
169
+ colorScheme,
170
+ columns,
171
+ colWidth,
172
+ contrastLettering,
173
+ rowHeight,
174
+ } = model
175
+ if (showMsaLetters) {
158
176
  for (const node of visibleLeaves) {
159
177
  const {
160
178
  data: { name },
161
179
  } = node
162
180
  const y = node.x!
163
- const str = columns[name]?.slice(xStart, xEnd)
164
- for (let i = 0; i < str?.length; i++) {
165
- const letter = str[i]
181
+ const str = columns[name]!.slice(xStart, xEnd)
182
+ for (let i = 0; i < str.length; i++) {
183
+ const letter = str[i]!
166
184
  const color = colorScheme[letter.toUpperCase()]
167
- const contrast = contrastScheme[letter.toUpperCase()] || 'black'
185
+ const contrast = contrastLettering
186
+ ? contrastScheme[letter.toUpperCase()] || 'black'
187
+ : 'black'
168
188
  const x = i * colWidth + offsetX - (offsetX % colWidth)
169
189
 
170
190
  // note: -rowHeight/4 matches +rowHeight/4 in tree
171
- ctx.fillStyle = showDomains
191
+ ctx.fillStyle = actuallyShowDomains
172
192
  ? 'black'
173
193
  : bgColor
174
194
  ? contrast
@@ -1,4 +1,4 @@
1
- import { MsaViewModel } from '../../model'
1
+ import type { MsaViewModel } from '../../model'
2
2
 
3
3
  const hoverColor = 'rgba(0,0,0,0.15)'
4
4
  const highlightColor = 'rgba(128,128,0,0.2)'
@@ -28,7 +28,7 @@ export function renderMouseover({
28
28
  ctx.clearRect(0, 0, width, height)
29
29
  if (mouseCol !== undefined) {
30
30
  ctx.fillStyle = hoverColor
31
- ctx.fillRect((mouseCol - 1) * colWidth + scrollX, 0, colWidth, height)
31
+ ctx.fillRect(mouseCol * colWidth + scrollX, 0, colWidth, height)
32
32
  }
33
33
  if (mouseRow !== undefined) {
34
34
  ctx.fillStyle = hoverColor
@@ -36,7 +36,7 @@ export function renderMouseover({
36
36
  }
37
37
  if (mouseClickCol !== undefined) {
38
38
  ctx.fillStyle = highlightColor
39
- ctx.fillRect((mouseClickCol - 1) * colWidth + scrollX, 0, colWidth, height)
39
+ ctx.fillRect(mouseClickCol * colWidth + scrollX, 0, colWidth, height)
40
40
  }
41
41
  if (mouseClickRow !== undefined) {
42
42
  ctx.fillStyle = highlightColor
@@ -44,6 +44,6 @@ export function renderMouseover({
44
44
  }
45
45
  if (mouseCol2 !== undefined) {
46
46
  ctx.fillStyle = highlightColor
47
- ctx.fillRect((mouseCol2 - 1) * colWidth + scrollX, 0, colWidth, height)
47
+ ctx.fillRect(mouseCol2 * colWidth + scrollX, 0, colWidth, height)
48
48
  }
49
49
  }
@@ -3,7 +3,7 @@ import { Menu, MenuItem } from '@mui/material'
3
3
  import { observer } from 'mobx-react'
4
4
 
5
5
  // locals
6
- import { MsaViewModel } from '../../model'
6
+ import type { MsaViewModel } from '../../model'
7
7
 
8
8
  interface Node {
9
9
  x: number
@@ -50,9 +50,11 @@ const TreeBranchMenu = observer(function ({
50
50
  <MenuItem
51
51
  dense
52
52
  onClick={() => {
53
- model.showOnly === node.id
54
- ? model.setShowOnly(undefined)
55
- : model.setShowOnly(node.id)
53
+ if (model.showOnly === node.id) {
54
+ model.setShowOnly(undefined)
55
+ } else {
56
+ model.setShowOnly(node.id)
57
+ }
56
58
  onClose()
57
59
  }}
58
60
  >
@@ -1,8 +1,9 @@
1
- import React, { useEffect, useRef, useState } from 'react'
1
+ import React from 'react'
2
+ import { useEffect, useRef, useState } from 'react'
2
3
  import { observer } from 'mobx-react'
3
4
 
4
5
  // locals
5
- import { MsaViewModel } from '../../model'
6
+ import type { MsaViewModel } from '../../model'
6
7
  import TreeCanvasBlock from './TreeCanvasBlock'
7
8
  import { padding } from './renderTreeCanvas'
8
9
 
@@ -48,7 +49,8 @@ const TreeCanvas = observer(function ({ model }: { model: MsaViewModel }) {
48
49
  const distanceY = currY - prevY.current
49
50
  if (distanceY) {
50
51
  // use rAF to make it so multiple event handlers aren't fired per-frame
51
- // see https://calendar.perfplanet.com/2013/the-runtime-performance-checklist/
52
+ // see
53
+ // https://calendar.perfplanet.com/2013/the-runtime-performance-checklist/
52
54
  if (!scheduled.current) {
53
55
  scheduled.current = true
54
56
  window.requestAnimationFrame(() => {
@@ -92,23 +94,20 @@ const TreeCanvas = observer(function ({ model }: { model: MsaViewModel }) {
92
94
  }
93
95
  }
94
96
 
95
- // this local mouseup is used in addition to the global because sometimes
96
- // the global add/remove are not called in time, resulting in issue #533
97
- function mouseUp(event: React.MouseEvent) {
98
- event.preventDefault()
99
- setMouseDragging(false)
100
- }
101
-
102
- function mouseLeave(event: React.MouseEvent) {
103
- event.preventDefault()
104
- }
105
-
106
97
  return (
107
98
  <div
108
99
  ref={ref}
109
100
  onMouseDown={mouseDown}
110
- onMouseUp={mouseUp}
111
- onMouseLeave={mouseLeave}
101
+ onMouseUp={event => {
102
+ // this local mouseup is used in addition to the global because
103
+ // sometimes the global add/remove are not called in time, resulting in
104
+ // issue #533
105
+ event.preventDefault()
106
+ setMouseDragging(false)
107
+ }}
108
+ onMouseLeave={event => {
109
+ event.preventDefault()
110
+ }}
112
111
  style={{
113
112
  height,
114
113
  position: 'relative',
@@ -1,11 +1,12 @@
1
- import React, { useCallback, useEffect, useRef, useState } from 'react'
1
+ import React from 'react'
2
+ import { useCallback, useEffect, useRef, useState } from 'react'
2
3
  import { autorun } from 'mobx'
3
4
  import { observer } from 'mobx-react'
4
5
  import { useTheme } from '@mui/material'
5
6
  import RBush from 'rbush'
6
7
 
7
8
  // locals
8
- import { MsaViewModel } from '../../model'
9
+ import type { MsaViewModel } from '../../model'
9
10
  import TreeNodeMenu from './TreeNodeMenu'
10
11
  import TreeBranchMenu from './TreeBranchMenu'
11
12
  import { padding, renderTreeCanvas } from './renderTreeCanvas'
@@ -49,6 +50,7 @@ const TreeCanvasBlock = observer(function ({
49
50
  const w2 = width * highResScaleFactor
50
51
  const h2 = height * highResScaleFactor
51
52
 
53
+ // biome-ignore lint/correctness/useExhaustiveDependencies:
52
54
  const vref = useCallback(
53
55
  (arg: HTMLCanvasElement) => {
54
56
  model.incrementRef()
@@ -135,7 +137,9 @@ const TreeCanvasBlock = observer(function ({
135
137
  <TreeBranchMenu
136
138
  node={branchMenu}
137
139
  model={model}
138
- onClose={() => setBranchMenu(undefined)}
140
+ onClose={() => {
141
+ setBranchMenu(undefined)
142
+ }}
139
143
  />
140
144
  ) : null}
141
145
 
@@ -143,7 +147,9 @@ const TreeCanvasBlock = observer(function ({
143
147
  <TreeNodeMenu
144
148
  node={toggleNodeMenu}
145
149
  model={model}
146
- onClose={() => setToggleNodeMenu(undefined)}
150
+ onClose={() => {
151
+ setToggleNodeMenu(undefined)
152
+ }}
147
153
  />
148
154
  ) : null}
149
155
 
@@ -165,7 +171,7 @@ const TreeCanvasBlock = observer(function ({
165
171
 
166
172
  const data = hoverBranchClickMap(event)
167
173
  if (data?.id) {
168
- setBranchMenu({ ...data, x, y })
174
+ setBranchMenu({ x, y, id: data.id, name: data.name })
169
175
  }
170
176
 
171
177
  const data2 = hoverNameClickMap(event)
@@ -173,7 +179,9 @@ const TreeCanvasBlock = observer(function ({
173
179
  setToggleNodeMenu({ ...data2, x, y })
174
180
  }
175
181
  }}
176
- onMouseLeave={() => setHoverElt(undefined)}
182
+ onMouseLeave={() => {
183
+ setHoverElt(undefined)
184
+ }}
177
185
  ref={vref}
178
186
  />
179
187
  <canvas
@@ -3,7 +3,7 @@ import { Menu, MenuItem } from '@mui/material'
3
3
  import { observer } from 'mobx-react'
4
4
 
5
5
  // locals
6
- import { MsaViewModel } from '../../model'
6
+ import type { MsaViewModel } from '../../model'
7
7
 
8
8
  // lazies
9
9
  const TreeNodeInfoDialog = lazy(() => import('./dialogs/TreeNodeInfoDialog'))
@@ -17,7 +17,7 @@ const TreeMenu = observer(function ({
17
17
  model: MsaViewModel
18
18
  onClose: () => void
19
19
  }) {
20
- const { collapsed, collapsed2 } = model
20
+ const { collapsed, collapsedLeaves } = model
21
21
  return (
22
22
  <Menu
23
23
  anchorReference="anchorPosition"
@@ -58,7 +58,7 @@ const TreeMenu = observer(function ({
58
58
  model.toggleCollapsed(node.id)
59
59
  } else {
60
60
  if (node.id.endsWith('-leafnode')) {
61
- model.toggleCollapsed2(`${node.id}`)
61
+ model.toggleCollapsed2(node.id)
62
62
  } else {
63
63
  model.toggleCollapsed2(`${node.id}-leafnode`)
64
64
  }
@@ -66,7 +66,7 @@ const TreeMenu = observer(function ({
66
66
  onClose()
67
67
  }}
68
68
  >
69
- {collapsed.includes(node.id) || collapsed2.includes(node.id)
69
+ {collapsed.includes(node.id) || collapsedLeaves.includes(node.id)
70
70
  ? 'Show node'
71
71
  : 'Hide node'}
72
72
  </MenuItem>
@@ -1,7 +1,7 @@
1
1
  import React from 'react'
2
2
  import { observer } from 'mobx-react'
3
3
 
4
- import { MsaViewModel } from '../../model'
4
+ import type { MsaViewModel } from '../../model'
5
5
  import TreeCanvas from './TreeCanvas'
6
6
 
7
7
  const TreePanel = observer(function ({ model }: { model: MsaViewModel }) {
@@ -2,7 +2,7 @@ import React from 'react'
2
2
  import { observer } from 'mobx-react'
3
3
 
4
4
  // locals
5
- import { MsaViewModel } from '../../model'
5
+ import type { MsaViewModel } from '../../model'
6
6
 
7
7
  const TreeRuler = observer(({ model }: { model: MsaViewModel }) => {
8
8
  const { treeAreaWidth } = model
@@ -8,10 +8,10 @@ import {
8
8
  } from '@jbrowse/core/BaseFeatureWidget/BaseFeatureDetail'
9
9
 
10
10
  // locals
11
- import { MsaViewModel } from '../../../model'
11
+ import type { MsaViewModel } from '../../../model'
12
12
  import SequenceTextArea from '../../SequenceTextArea'
13
13
 
14
- export default observer(function ({
14
+ const TreeNodeInfoDialog = observer(function ({
15
15
  info,
16
16
  model,
17
17
  nodeName,
@@ -26,7 +26,14 @@ export default observer(function ({
26
26
  const metadata = treeMetadata[nodeName]
27
27
  const [name, sequence] = rows.find(f => f[0] === nodeName)!
28
28
  return (
29
- <Dialog onClose={() => onClose()} open title="Tree node info" maxWidth="xl">
29
+ <Dialog
30
+ onClose={() => {
31
+ onClose()
32
+ }}
33
+ open
34
+ title="Tree node info"
35
+ maxWidth="xl"
36
+ >
30
37
  <DialogContent>
31
38
  <BaseCard title="Attributes">
32
39
  <Attributes attributes={{ nodeName, ...info }} />
@@ -43,3 +50,5 @@ export default observer(function ({
43
50
  </Dialog>
44
51
  )
45
52
  })
53
+
54
+ export default TreeNodeInfoDialog