@jbrowse/plugin-data-management 2.3.2 → 2.3.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.
Files changed (222) hide show
  1. package/dist/AddConnectionWidget/index.d.ts +3 -2
  2. package/dist/AddConnectionWidget/index.js +38 -4
  3. package/dist/AddConnectionWidget/index.js.map +1 -1
  4. package/dist/AddTrackWidget/components/DefaultAddTrackWorkflow.js +1 -4
  5. package/dist/AddTrackWidget/components/DefaultAddTrackWorkflow.js.map +1 -1
  6. package/dist/AddTrackWidget/components/TrackSourceSelect.js +1 -4
  7. package/dist/AddTrackWidget/components/TrackSourceSelect.js.map +1 -1
  8. package/dist/AddTrackWidget/index.d.ts +3 -2
  9. package/dist/AddTrackWidget/index.js +38 -4
  10. package/dist/AddTrackWidget/index.js.map +1 -1
  11. package/dist/HierarchicalTrackSelectorWidget/components/HierarchicalFab.d.ts +6 -0
  12. package/dist/HierarchicalTrackSelectorWidget/components/HierarchicalFab.js +71 -0
  13. package/dist/HierarchicalTrackSelectorWidget/components/HierarchicalFab.js.map +1 -0
  14. package/dist/HierarchicalTrackSelectorWidget/components/HierarchicalTrackSelector.js +10 -104
  15. package/dist/HierarchicalTrackSelectorWidget/components/HierarchicalTrackSelector.js.map +1 -1
  16. package/dist/HierarchicalTrackSelectorWidget/components/ShoppingCart.d.ts +6 -0
  17. package/dist/HierarchicalTrackSelectorWidget/components/ShoppingCart.js +70 -0
  18. package/dist/HierarchicalTrackSelectorWidget/components/ShoppingCart.js.map +1 -0
  19. package/dist/HierarchicalTrackSelectorWidget/components/{CloseConnectionDialog.d.ts → dialogs/CloseConnectionDialog.d.ts} +0 -0
  20. package/dist/HierarchicalTrackSelectorWidget/components/{CloseConnectionDialog.js → dialogs/CloseConnectionDialog.js} +0 -0
  21. package/dist/HierarchicalTrackSelectorWidget/components/dialogs/CloseConnectionDialog.js.map +1 -0
  22. package/dist/HierarchicalTrackSelectorWidget/components/{DeleteConnectionDialog.d.ts → dialogs/DeleteConnectionDialog.d.ts} +0 -0
  23. package/dist/HierarchicalTrackSelectorWidget/components/{DeleteConnectionDialog.js → dialogs/DeleteConnectionDialog.js} +0 -0
  24. package/dist/HierarchicalTrackSelectorWidget/components/dialogs/DeleteConnectionDialog.js.map +1 -0
  25. package/dist/HierarchicalTrackSelectorWidget/components/{ManageConnectionsDialog.d.ts → dialogs/ManageConnectionsDialog.d.ts} +0 -0
  26. package/dist/HierarchicalTrackSelectorWidget/components/{ManageConnectionsDialog.js → dialogs/ManageConnectionsDialog.js} +0 -0
  27. package/dist/HierarchicalTrackSelectorWidget/components/dialogs/ManageConnectionsDialog.js.map +1 -0
  28. package/dist/HierarchicalTrackSelectorWidget/components/{ToggleConnectionsDialog.d.ts → dialogs/ToggleConnectionsDialog.d.ts} +0 -0
  29. package/dist/HierarchicalTrackSelectorWidget/components/{ToggleConnectionsDialog.js → dialogs/ToggleConnectionsDialog.js} +0 -0
  30. package/dist/HierarchicalTrackSelectorWidget/components/dialogs/ToggleConnectionsDialog.js.map +1 -0
  31. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.d.ts +13 -0
  32. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.js +99 -0
  33. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.js.map +1 -0
  34. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.d.ts +8 -0
  35. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.js +18 -0
  36. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.js.map +1 -0
  37. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.d.ts +11 -0
  38. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.js +71 -0
  39. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.js.map +1 -0
  40. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.d.ts +12 -0
  41. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.js +211 -0
  42. package/dist/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.js.map +1 -0
  43. package/dist/HierarchicalTrackSelectorWidget/components/faceted/util.d.ts +1 -0
  44. package/dist/HierarchicalTrackSelectorWidget/components/faceted/util.js +10 -0
  45. package/dist/HierarchicalTrackSelectorWidget/components/faceted/util.js.map +1 -0
  46. package/dist/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.d.ts +7 -0
  47. package/dist/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.js +136 -0
  48. package/dist/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.js.map +1 -0
  49. package/dist/HierarchicalTrackSelectorWidget/components/{Header.d.ts → tree/HierarchicalHeader.d.ts} +2 -3
  50. package/dist/HierarchicalTrackSelectorWidget/components/tree/HierarchicalHeader.js +65 -0
  51. package/dist/HierarchicalTrackSelectorWidget/components/tree/HierarchicalHeader.js.map +1 -0
  52. package/dist/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.d.ts +8 -0
  53. package/dist/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.js +91 -0
  54. package/dist/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.js.map +1 -0
  55. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.d.ts +7 -0
  56. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.js +89 -0
  57. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.js.map +1 -0
  58. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.d.ts +11 -0
  59. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.js +86 -0
  60. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.js.map +1 -0
  61. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.d.ts +10 -0
  62. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.js +54 -0
  63. package/dist/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.js.map +1 -0
  64. package/dist/HierarchicalTrackSelectorWidget/components/util.d.ts +17 -1
  65. package/dist/HierarchicalTrackSelectorWidget/components/util.js +16 -1
  66. package/dist/HierarchicalTrackSelectorWidget/components/util.js.map +1 -1
  67. package/dist/HierarchicalTrackSelectorWidget/index.d.ts +3 -0
  68. package/dist/HierarchicalTrackSelectorWidget/index.js +36 -0
  69. package/dist/HierarchicalTrackSelectorWidget/index.js.map +1 -1
  70. package/dist/HierarchicalTrackSelectorWidget/model.d.ts +4 -1
  71. package/dist/HierarchicalTrackSelectorWidget/model.js +12 -8
  72. package/dist/HierarchicalTrackSelectorWidget/model.js.map +1 -1
  73. package/dist/PluginStoreWidget/index.d.ts +3 -2
  74. package/dist/PluginStoreWidget/index.js +38 -4
  75. package/dist/PluginStoreWidget/index.js.map +1 -1
  76. package/dist/index.js +10 -51
  77. package/dist/index.js.map +1 -1
  78. package/dist/ucsc-trackhub/index.d.ts +3 -2
  79. package/dist/ucsc-trackhub/index.js +13 -5
  80. package/dist/ucsc-trackhub/index.js.map +1 -1
  81. package/esm/AddConnectionWidget/index.d.ts +3 -2
  82. package/esm/AddConnectionWidget/index.js +15 -2
  83. package/esm/AddConnectionWidget/index.js.map +1 -1
  84. package/esm/AddTrackWidget/components/DefaultAddTrackWorkflow.js +1 -4
  85. package/esm/AddTrackWidget/components/DefaultAddTrackWorkflow.js.map +1 -1
  86. package/esm/AddTrackWidget/components/TrackSourceSelect.js +1 -4
  87. package/esm/AddTrackWidget/components/TrackSourceSelect.js.map +1 -1
  88. package/esm/AddTrackWidget/index.d.ts +3 -2
  89. package/esm/AddTrackWidget/index.js +15 -2
  90. package/esm/AddTrackWidget/index.js.map +1 -1
  91. package/esm/HierarchicalTrackSelectorWidget/components/HierarchicalFab.d.ts +6 -0
  92. package/esm/HierarchicalTrackSelectorWidget/components/HierarchicalFab.js +43 -0
  93. package/esm/HierarchicalTrackSelectorWidget/components/HierarchicalFab.js.map +1 -0
  94. package/esm/HierarchicalTrackSelectorWidget/components/HierarchicalTrackSelector.js +9 -103
  95. package/esm/HierarchicalTrackSelectorWidget/components/HierarchicalTrackSelector.js.map +1 -1
  96. package/esm/HierarchicalTrackSelectorWidget/components/ShoppingCart.d.ts +6 -0
  97. package/esm/HierarchicalTrackSelectorWidget/components/ShoppingCart.js +42 -0
  98. package/esm/HierarchicalTrackSelectorWidget/components/ShoppingCart.js.map +1 -0
  99. package/esm/HierarchicalTrackSelectorWidget/components/{CloseConnectionDialog.d.ts → dialogs/CloseConnectionDialog.d.ts} +0 -0
  100. package/esm/HierarchicalTrackSelectorWidget/components/{CloseConnectionDialog.js → dialogs/CloseConnectionDialog.js} +0 -0
  101. package/esm/HierarchicalTrackSelectorWidget/components/dialogs/CloseConnectionDialog.js.map +1 -0
  102. package/esm/HierarchicalTrackSelectorWidget/components/{DeleteConnectionDialog.d.ts → dialogs/DeleteConnectionDialog.d.ts} +0 -0
  103. package/esm/HierarchicalTrackSelectorWidget/components/{DeleteConnectionDialog.js → dialogs/DeleteConnectionDialog.js} +0 -0
  104. package/esm/HierarchicalTrackSelectorWidget/components/dialogs/DeleteConnectionDialog.js.map +1 -0
  105. package/esm/HierarchicalTrackSelectorWidget/components/{ManageConnectionsDialog.d.ts → dialogs/ManageConnectionsDialog.d.ts} +0 -0
  106. package/esm/HierarchicalTrackSelectorWidget/components/{ManageConnectionsDialog.js → dialogs/ManageConnectionsDialog.js} +0 -0
  107. package/esm/HierarchicalTrackSelectorWidget/components/dialogs/ManageConnectionsDialog.js.map +1 -0
  108. package/esm/HierarchicalTrackSelectorWidget/components/{ToggleConnectionsDialog.d.ts → dialogs/ToggleConnectionsDialog.d.ts} +0 -0
  109. package/esm/HierarchicalTrackSelectorWidget/components/{ToggleConnectionsDialog.js → dialogs/ToggleConnectionsDialog.js} +0 -0
  110. package/esm/HierarchicalTrackSelectorWidget/components/dialogs/ToggleConnectionsDialog.js.map +1 -0
  111. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.d.ts +13 -0
  112. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.js +70 -0
  113. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.js.map +1 -0
  114. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.d.ts +8 -0
  115. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.js +13 -0
  116. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.js.map +1 -0
  117. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.d.ts +11 -0
  118. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.js +42 -0
  119. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.js.map +1 -0
  120. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.d.ts +12 -0
  121. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.js +183 -0
  122. package/esm/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.js.map +1 -0
  123. package/esm/HierarchicalTrackSelectorWidget/components/faceted/util.d.ts +1 -0
  124. package/esm/HierarchicalTrackSelectorWidget/components/faceted/util.js +6 -0
  125. package/esm/HierarchicalTrackSelectorWidget/components/faceted/util.js.map +1 -0
  126. package/esm/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.d.ts +7 -0
  127. package/esm/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.js +108 -0
  128. package/esm/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.js.map +1 -0
  129. package/esm/HierarchicalTrackSelectorWidget/components/{Header.d.ts → tree/HierarchicalHeader.d.ts} +2 -3
  130. package/esm/HierarchicalTrackSelectorWidget/components/tree/HierarchicalHeader.js +37 -0
  131. package/esm/HierarchicalTrackSelectorWidget/components/tree/HierarchicalHeader.js.map +1 -0
  132. package/esm/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.d.ts +8 -0
  133. package/esm/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.js +63 -0
  134. package/esm/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.js.map +1 -0
  135. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.d.ts +7 -0
  136. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.js +60 -0
  137. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.js.map +1 -0
  138. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.d.ts +11 -0
  139. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.js +57 -0
  140. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.js.map +1 -0
  141. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.d.ts +10 -0
  142. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.js +48 -0
  143. package/esm/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.js.map +1 -0
  144. package/esm/HierarchicalTrackSelectorWidget/components/util.d.ts +17 -1
  145. package/esm/HierarchicalTrackSelectorWidget/components/util.js +13 -0
  146. package/esm/HierarchicalTrackSelectorWidget/components/util.js.map +1 -1
  147. package/esm/HierarchicalTrackSelectorWidget/index.d.ts +3 -0
  148. package/esm/HierarchicalTrackSelectorWidget/index.js +13 -0
  149. package/esm/HierarchicalTrackSelectorWidget/index.js.map +1 -1
  150. package/esm/HierarchicalTrackSelectorWidget/model.d.ts +4 -1
  151. package/esm/HierarchicalTrackSelectorWidget/model.js +10 -7
  152. package/esm/HierarchicalTrackSelectorWidget/model.js.map +1 -1
  153. package/esm/PluginStoreWidget/index.d.ts +3 -2
  154. package/esm/PluginStoreWidget/index.js +15 -2
  155. package/esm/PluginStoreWidget/index.js.map +1 -1
  156. package/esm/index.js +10 -51
  157. package/esm/index.js.map +1 -1
  158. package/esm/ucsc-trackhub/index.d.ts +3 -2
  159. package/esm/ucsc-trackhub/index.js +13 -2
  160. package/esm/ucsc-trackhub/index.js.map +1 -1
  161. package/package.json +3 -2
  162. package/src/AddConnectionWidget/components/{AddConnectionWidget.test.js → AddConnectionWidget.test.tsx} +17 -8
  163. package/src/AddConnectionWidget/components/__snapshots__/{AddConnectionWidget.test.js.snap → AddConnectionWidget.test.tsx.snap} +0 -0
  164. package/src/AddConnectionWidget/index.ts +17 -2
  165. package/src/AddTrackWidget/components/DefaultAddTrackWorkflow.tsx +1 -4
  166. package/src/AddTrackWidget/components/TrackSourceSelect.tsx +3 -5
  167. package/src/AddTrackWidget/{index.test.jsx → index.test.tsx} +34 -37
  168. package/src/AddTrackWidget/index.ts +17 -2
  169. package/src/HierarchicalTrackSelectorWidget/components/HierarchicalFab.tsx +94 -0
  170. package/src/HierarchicalTrackSelectorWidget/components/HierarchicalTrackSelector.test.tsx +124 -128
  171. package/src/HierarchicalTrackSelectorWidget/components/HierarchicalTrackSelector.tsx +47 -228
  172. package/src/HierarchicalTrackSelectorWidget/components/ShoppingCart.tsx +73 -0
  173. package/src/HierarchicalTrackSelectorWidget/components/__snapshots__/HierarchicalTrackSelector.test.tsx.snap +25 -43
  174. package/src/HierarchicalTrackSelectorWidget/components/{CloseConnectionDialog.tsx → dialogs/CloseConnectionDialog.tsx} +0 -0
  175. package/src/HierarchicalTrackSelectorWidget/components/{DeleteConnectionDialog.tsx → dialogs/DeleteConnectionDialog.tsx} +0 -0
  176. package/src/HierarchicalTrackSelectorWidget/components/{ManageConnectionsDialog.tsx → dialogs/ManageConnectionsDialog.tsx} +0 -0
  177. package/src/HierarchicalTrackSelectorWidget/components/{ToggleConnectionsDialog.tsx → dialogs/ToggleConnectionsDialog.tsx} +0 -0
  178. package/src/HierarchicalTrackSelectorWidget/components/faceted/FacetFilters.tsx +138 -0
  179. package/src/HierarchicalTrackSelectorWidget/components/faceted/FacetedDialog.tsx +29 -0
  180. package/src/HierarchicalTrackSelectorWidget/components/faceted/FacetedHeader.tsx +86 -0
  181. package/src/HierarchicalTrackSelectorWidget/components/faceted/FacetedSelector.tsx +339 -0
  182. package/src/HierarchicalTrackSelectorWidget/components/faceted/util.ts +5 -0
  183. package/src/HierarchicalTrackSelectorWidget/components/tree/HamburgerMenu.tsx +197 -0
  184. package/src/HierarchicalTrackSelectorWidget/components/tree/HierarchicalHeader.tsx +88 -0
  185. package/src/HierarchicalTrackSelectorWidget/components/tree/HierarchicalTree.tsx +101 -0
  186. package/src/HierarchicalTrackSelectorWidget/components/tree/TrackCategory.tsx +92 -0
  187. package/src/HierarchicalTrackSelectorWidget/components/tree/TrackLabel.tsx +107 -0
  188. package/src/HierarchicalTrackSelectorWidget/components/tree/TrackListNode.tsx +84 -0
  189. package/src/HierarchicalTrackSelectorWidget/components/util.ts +31 -1
  190. package/src/HierarchicalTrackSelectorWidget/index.ts +17 -0
  191. package/src/HierarchicalTrackSelectorWidget/model.ts +12 -9
  192. package/src/PluginStoreWidget/components/PluginStoreWidget.test.tsx +132 -0
  193. package/src/PluginStoreWidget/components/__snapshots__/{PluginStoreWidget.test.js.snap → PluginStoreWidget.test.tsx.snap} +2 -2
  194. package/src/PluginStoreWidget/index.ts +17 -2
  195. package/src/PluginStoreWidget/{model.test.js → model.test.tsx} +0 -0
  196. package/src/__snapshots__/index.test.ts.snap +9 -0
  197. package/src/index.test.ts +54 -0
  198. package/src/index.ts +10 -83
  199. package/src/ucsc-trackhub/index.ts +19 -2
  200. package/dist/HierarchicalTrackSelectorWidget/components/CloseConnectionDialog.js.map +0 -1
  201. package/dist/HierarchicalTrackSelectorWidget/components/DeleteConnectionDialog.js.map +0 -1
  202. package/dist/HierarchicalTrackSelectorWidget/components/Header.js +0 -174
  203. package/dist/HierarchicalTrackSelectorWidget/components/Header.js.map +0 -1
  204. package/dist/HierarchicalTrackSelectorWidget/components/ManageConnectionsDialog.js.map +0 -1
  205. package/dist/HierarchicalTrackSelectorWidget/components/Node.d.ts +0 -29
  206. package/dist/HierarchicalTrackSelectorWidget/components/Node.js +0 -173
  207. package/dist/HierarchicalTrackSelectorWidget/components/Node.js.map +0 -1
  208. package/dist/HierarchicalTrackSelectorWidget/components/ToggleConnectionsDialog.js.map +0 -1
  209. package/esm/HierarchicalTrackSelectorWidget/components/CloseConnectionDialog.js.map +0 -1
  210. package/esm/HierarchicalTrackSelectorWidget/components/DeleteConnectionDialog.js.map +0 -1
  211. package/esm/HierarchicalTrackSelectorWidget/components/Header.js +0 -146
  212. package/esm/HierarchicalTrackSelectorWidget/components/Header.js.map +0 -1
  213. package/esm/HierarchicalTrackSelectorWidget/components/ManageConnectionsDialog.js.map +0 -1
  214. package/esm/HierarchicalTrackSelectorWidget/components/Node.d.ts +0 -29
  215. package/esm/HierarchicalTrackSelectorWidget/components/Node.js +0 -144
  216. package/esm/HierarchicalTrackSelectorWidget/components/Node.js.map +0 -1
  217. package/esm/HierarchicalTrackSelectorWidget/components/ToggleConnectionsDialog.js.map +0 -1
  218. package/src/HierarchicalTrackSelectorWidget/components/Header.tsx +0 -286
  219. package/src/HierarchicalTrackSelectorWidget/components/Node.tsx +0 -282
  220. package/src/PluginStoreWidget/components/PluginStoreWidget.test.js +0 -123
  221. package/src/__snapshots__/index.test.js.snap +0 -9
  222. package/src/index.test.js +0 -61
@@ -0,0 +1,101 @@
1
+ import React, { useCallback, useMemo, useRef, useEffect } from 'react'
2
+ import { observer } from 'mobx-react'
3
+ import { VariableSizeTree } from 'react-vtree'
4
+ import { getSession } from '@jbrowse/core/util'
5
+ // locals
6
+ import { TreeNode, HierarchicalTrackSelectorModel } from '../../model'
7
+ import Node from './TrackListNode'
8
+
9
+ function getNodeData(
10
+ node: TreeNode,
11
+ nestingLevel: number,
12
+ extra: Record<string, unknown>,
13
+ selection: Record<string, unknown>,
14
+ ) {
15
+ const isLeaf = !!node.conf
16
+ const selected = !!selection[node.id]
17
+ return {
18
+ data: {
19
+ defaultHeight: isLeaf ? 22 : 40,
20
+ isLeaf,
21
+ isOpenByDefault: true,
22
+ nestingLevel,
23
+ selected,
24
+ ...node,
25
+ ...extra,
26
+ },
27
+ nestingLevel,
28
+ node,
29
+ }
30
+ }
31
+
32
+ type NodeData = ReturnType<typeof getNodeData>
33
+
34
+ // this is the main tree component for the hierarchical track selector in note:
35
+ // in jbrowse-web the toolbar is position="sticky" which means the autosizer
36
+ // includes the height of the toolbar, so we subtract the given offsets
37
+ export default observer(function HierarchicalTree({
38
+ height,
39
+ tree,
40
+ model,
41
+ }: {
42
+ height: number
43
+ tree: TreeNode
44
+ model: HierarchicalTrackSelectorModel
45
+ }) {
46
+ const { filterText, selection, view } = model
47
+ const treeRef = useRef<NodeData>(null)
48
+ const session = getSession(model)
49
+ const { drawerPosition } = session
50
+ const obj = useMemo(
51
+ () => Object.fromEntries(selection.map(s => [s.trackId, s])),
52
+ [selection],
53
+ )
54
+
55
+ const extra = useMemo(
56
+ () => ({
57
+ onChange: (trackId: string) => view.toggleTrack(trackId),
58
+ toggleCollapse: (pathName: string) => model.toggleCategory(pathName),
59
+ tree,
60
+ model,
61
+ drawerPosition,
62
+ }),
63
+ [view, model, drawerPosition, tree],
64
+ )
65
+ const treeWalker = useCallback(
66
+ function* treeWalker() {
67
+ for (let i = 0; i < tree.children.length; i++) {
68
+ const r = tree.children[i]
69
+ yield getNodeData(r, 0, extra, obj)
70
+ }
71
+
72
+ while (true) {
73
+ // @ts-ignore
74
+ const parentMeta = yield
75
+
76
+ for (let i = 0; i < parentMeta.node.children.length; i++) {
77
+ const curr = parentMeta.node.children[i]
78
+ yield getNodeData(curr, parentMeta.nestingLevel + 1, extra, obj)
79
+ }
80
+ }
81
+ },
82
+ [tree, extra, obj],
83
+ )
84
+
85
+ useEffect(() => {
86
+ // @ts-ignore
87
+ treeRef.current.recomputeTree({
88
+ refreshNodes: true,
89
+ useDefaultHeight: true,
90
+ })
91
+ }, [tree, filterText])
92
+ return (
93
+ <>
94
+ {/* @ts-ignore */}
95
+ <VariableSizeTree ref={treeRef} treeWalker={treeWalker} height={height}>
96
+ {/* @ts-ignore */}
97
+ {Node}
98
+ </VariableSizeTree>
99
+ </>
100
+ )
101
+ })
@@ -0,0 +1,92 @@
1
+ import React, { useState } from 'react'
2
+ import { IconButton, Typography } from '@mui/material'
3
+ import { makeStyles } from 'tss-react/mui'
4
+ import JBrowseMenu from '@jbrowse/core/ui/Menu'
5
+
6
+ // icons
7
+ import ArrowDropDownIcon from '@mui/icons-material/ArrowDropDown'
8
+ import ArrowRightIcon from '@mui/icons-material/ArrowRight'
9
+ import MoreHorizIcon from '@mui/icons-material/MoreHoriz'
10
+
11
+ // locals
12
+ import { getAllChildren, treeToMap, NodeData } from '../util'
13
+
14
+ const useStyles = makeStyles()(theme => ({
15
+ contrastColor: {
16
+ color: theme.palette.secondary.contrastText,
17
+ },
18
+
19
+ // margin:auto 0 to center text vertically
20
+ accordionText: {
21
+ margin: 'auto 0',
22
+ // width 100 so you can click anywhere on the category bar
23
+ width: '100%',
24
+ },
25
+ }))
26
+
27
+ export default function Category({
28
+ isOpen,
29
+ setOpen,
30
+ data,
31
+ }: {
32
+ isOpen: boolean
33
+ setOpen: (arg: boolean) => void
34
+ data: NodeData
35
+ }) {
36
+ const { classes } = useStyles()
37
+ const [menuEl, setMenuEl] = useState<HTMLElement | null>(null)
38
+ const { name, model, id, tree, toggleCollapse } = data
39
+
40
+ return (
41
+ <div
42
+ className={classes.accordionText}
43
+ onClick={() => {
44
+ if (!menuEl) {
45
+ toggleCollapse(id)
46
+ setOpen(!isOpen)
47
+ }
48
+ }}
49
+ >
50
+ <Typography>
51
+ {isOpen ? <ArrowDropDownIcon /> : <ArrowRightIcon />}
52
+ {name}
53
+ <IconButton
54
+ onClick={event => {
55
+ setMenuEl(event.currentTarget)
56
+ event.stopPropagation()
57
+ }}
58
+ className={classes.contrastColor}
59
+ >
60
+ <MoreHorizIcon />
61
+ </IconButton>
62
+ </Typography>
63
+ {menuEl ? (
64
+ <JBrowseMenu
65
+ anchorEl={menuEl}
66
+ menuItems={[
67
+ {
68
+ label: 'Add to selection',
69
+ onClick: () => {
70
+ const r = treeToMap(tree).get(id)
71
+ model.addToSelection(getAllChildren(r))
72
+ },
73
+ },
74
+ {
75
+ label: 'Remove from selection',
76
+ onClick: () => {
77
+ const r = treeToMap(tree).get(id)
78
+ model.removeFromSelection(getAllChildren(r))
79
+ },
80
+ },
81
+ ]}
82
+ onMenuItemClick={(_event, callback) => {
83
+ callback()
84
+ setMenuEl(null)
85
+ }}
86
+ open={Boolean(menuEl)}
87
+ onClose={() => setMenuEl(null)}
88
+ />
89
+ ) : null}
90
+ </div>
91
+ )
92
+ }
@@ -0,0 +1,107 @@
1
+ import React, { useState } from 'react'
2
+ import { Checkbox, FormControlLabel, IconButton, Tooltip } from '@mui/material'
3
+ import { makeStyles } from 'tss-react/mui'
4
+ import JBrowseMenu from '@jbrowse/core/ui/Menu'
5
+ import { getSession } from '@jbrowse/core/util'
6
+ import {
7
+ AnyConfigurationModel,
8
+ readConfObject,
9
+ } from '@jbrowse/core/configuration'
10
+
11
+ // icons
12
+ import MoreHorizIcon from '@mui/icons-material/MoreHoriz'
13
+
14
+ // locals
15
+ import { isUnsupported, NodeData } from '../util'
16
+ import { SanitizedHTML } from '@jbrowse/core/ui'
17
+
18
+ const useStyles = makeStyles()({
19
+ compactCheckbox: {
20
+ padding: 0,
21
+ },
22
+
23
+ checkboxLabel: {
24
+ marginRight: 0,
25
+ '&:hover': {
26
+ backgroundColor: '#eee',
27
+ },
28
+ },
29
+ })
30
+
31
+ export interface InfoArgs {
32
+ target: HTMLElement
33
+ id: string
34
+ conf: AnyConfigurationModel
35
+ }
36
+
37
+ export default function TrackLabel({ data }: { data: NodeData }) {
38
+ const { classes } = useStyles()
39
+ const { checked, conf, model, drawerPosition, id, name, onChange, selected } =
40
+ data
41
+ const [info, setInfo] = useState<InfoArgs>()
42
+ const description = (conf && readConfObject(conf, ['description'])) || ''
43
+ return (
44
+ <>
45
+ <Tooltip
46
+ title={description + (selected ? ' (in selection)' : '')}
47
+ placement={drawerPosition === 'left' ? 'right' : 'left'}
48
+ >
49
+ <FormControlLabel
50
+ className={classes.checkboxLabel}
51
+ control={
52
+ <Checkbox
53
+ className={classes.compactCheckbox}
54
+ checked={checked}
55
+ onChange={() => onChange(id)}
56
+ disabled={isUnsupported(name)}
57
+ inputProps={{
58
+ // @ts-ignore
59
+ 'data-testid': `htsTrackEntry-${id}`,
60
+ }}
61
+ />
62
+ }
63
+ label={
64
+ <div style={{ background: selected ? '#cccc' : undefined }}>
65
+ <SanitizedHTML html={name} />
66
+ </div>
67
+ }
68
+ />
69
+ </Tooltip>
70
+ <IconButton
71
+ onClick={e => setInfo({ target: e.currentTarget, id, conf })}
72
+ style={{ padding: 0 }}
73
+ color="secondary"
74
+ data-testid={`htsTrackEntryMenu-${id}`}
75
+ >
76
+ <MoreHorizIcon />
77
+ </IconButton>
78
+
79
+ {info ? (
80
+ <JBrowseMenu
81
+ anchorEl={info?.target}
82
+ menuItems={[
83
+ ...(getSession(model).getTrackActionMenuItems?.(info.conf) || []),
84
+ {
85
+ label: 'Add to selection',
86
+ onClick: () => model.addToSelection([info.conf]),
87
+ },
88
+ ...(selected
89
+ ? [
90
+ {
91
+ label: 'Remove from selection',
92
+ onClick: () => model.removeFromSelection([info.conf]),
93
+ },
94
+ ]
95
+ : []),
96
+ ]}
97
+ onMenuItemClick={(_event, callback) => {
98
+ callback()
99
+ setInfo(undefined)
100
+ }}
101
+ open={Boolean(info)}
102
+ onClose={() => setInfo(undefined)}
103
+ />
104
+ ) : null}
105
+ </>
106
+ )
107
+ }
@@ -0,0 +1,84 @@
1
+ import React from 'react'
2
+ import { makeStyles } from 'tss-react/mui'
3
+
4
+ // locals
5
+ import Category from './TrackCategory'
6
+ import TrackLabel from './TrackLabel'
7
+ import { NodeData } from '../util'
8
+
9
+ const useStyles = makeStyles()(theme => ({
10
+ // this accordionBase element's small padding is used to give a margin to
11
+ // accordionColor it a "margin" because the virtualized elements can't really
12
+ // use margin in a conventional way (it doesn't affect layout)
13
+ accordionBase: {
14
+ display: 'flex',
15
+ },
16
+
17
+ accordionCard: {
18
+ padding: 3,
19
+ cursor: 'pointer',
20
+ display: 'flex',
21
+ },
22
+
23
+ nestingLevelMarker: {
24
+ position: 'absolute',
25
+ borderLeft: '1.5px solid #555',
26
+ },
27
+ // accordionColor set's display:flex so that the child accordionText use
28
+ // vertically centered text
29
+ accordionColor: {
30
+ background: theme.palette.tertiary.main,
31
+ color: theme.palette.tertiary.contrastText,
32
+ width: '100%',
33
+ display: 'flex',
34
+ paddingLeft: 5,
35
+ },
36
+ }))
37
+
38
+ // An individual node in the track selector. Note: manually sets cursor:
39
+ // pointer improves usability for what can be clicked
40
+ export default function Node({
41
+ data,
42
+ isOpen,
43
+ style,
44
+ setOpen,
45
+ }: {
46
+ data: NodeData
47
+ isOpen: boolean
48
+ style?: { height: number }
49
+ setOpen: (arg: boolean) => void
50
+ }) {
51
+ const { isLeaf, nestingLevel } = data
52
+
53
+ const { classes } = useStyles()
54
+ const width = 10
55
+ const marginLeft = nestingLevel * width + (isLeaf ? width : 0)
56
+
57
+ return (
58
+ <div style={style} className={!isLeaf ? classes.accordionBase : undefined}>
59
+ {new Array(nestingLevel).fill(0).map((_, idx) => (
60
+ <div
61
+ key={`mark-${idx}`}
62
+ style={{ left: idx * width + 4, height: style?.height }}
63
+ className={classes.nestingLevelMarker}
64
+ />
65
+ ))}
66
+ <div
67
+ className={!isLeaf ? classes.accordionCard : undefined}
68
+ style={{
69
+ marginLeft,
70
+ whiteSpace: 'nowrap',
71
+ width: '100%',
72
+ }}
73
+ >
74
+ <div className={!isLeaf ? classes.accordionColor : undefined}>
75
+ {!isLeaf ? (
76
+ <Category isOpen={isOpen} data={data} setOpen={setOpen} />
77
+ ) : (
78
+ <TrackLabel data={data} />
79
+ )}
80
+ </div>
81
+ </div>
82
+ </div>
83
+ )
84
+ }
@@ -1,5 +1,20 @@
1
1
  import { AnyConfigurationModel } from '@jbrowse/core/configuration'
2
- import { TreeNode } from '../model'
2
+ import { HierarchicalTrackSelectorModel, TreeNode } from '../model'
3
+
4
+ export interface NodeData {
5
+ nestingLevel: number
6
+ checked: boolean
7
+ conf: AnyConfigurationModel
8
+ drawerPosition: unknown
9
+ id: string
10
+ isLeaf: boolean
11
+ name: string
12
+ onChange: Function
13
+ toggleCollapse: (arg: string) => void
14
+ tree: TreeNode
15
+ selected: boolean
16
+ model: HierarchicalTrackSelectorModel
17
+ }
3
18
 
4
19
  export function getAllChildren(subtree?: TreeNode): AnyConfigurationModel[] {
5
20
  // @ts-ignore
@@ -9,3 +24,18 @@ export function getAllChildren(subtree?: TreeNode): AnyConfigurationModel[] {
9
24
  ) || []
10
25
  ).flat(Infinity)
11
26
  }
27
+
28
+ export function treeToMap(tree: TreeNode, map = new Map<string, TreeNode>()) {
29
+ if (tree.id && tree.children.length) {
30
+ map.set(tree.id, tree)
31
+ }
32
+ for (let i = 0; i < tree.children.length; i++) {
33
+ const node = tree.children[i]
34
+ treeToMap(node, map)
35
+ }
36
+ return map
37
+ }
38
+
39
+ export function isUnsupported(name = '') {
40
+ return name.endsWith('(Unsupported)') || name.endsWith('(Unknown)')
41
+ }
@@ -1,5 +1,22 @@
1
1
  import stateModelFactory, { HierarchicalTrackSelectorModel } from './model'
2
2
  import configSchema from './configSchema'
3
+ import PluginManager from '@jbrowse/core/PluginManager'
4
+ import { WidgetType } from '@jbrowse/core/pluggableElementTypes'
5
+ import { lazy } from 'react'
3
6
 
4
7
  export { stateModelFactory, configSchema }
5
8
  export type { HierarchicalTrackSelectorModel }
9
+
10
+ export default (pluginManager: PluginManager) => {
11
+ pluginManager.addWidgetType(() => {
12
+ return new WidgetType({
13
+ name: 'HierarchicalTrackSelectorWidget',
14
+ heading: 'Available tracks',
15
+ configSchema,
16
+ stateModel: stateModelFactory(pluginManager),
17
+ ReactComponent: lazy(
18
+ () => import('./components/HierarchicalTrackSelector'),
19
+ ),
20
+ })
21
+ })
22
+ }
@@ -18,16 +18,16 @@ function hasAnyOverlap<T>(a1: T[] = [], a2: T[] = []) {
18
18
  return !!a1.find(value => a2.includes(value))
19
19
  }
20
20
 
21
- function passesFilter(
22
- filter: string,
23
- config: AnyConfigurationModel,
21
+ export function matches(
22
+ query: string,
23
+ conf: AnyConfigurationModel,
24
24
  session: AbstractSessionModel,
25
25
  ) {
26
- const categories = readConfObject(config, 'category') as string[] | undefined
27
- const filterLower = filter.toLowerCase()
26
+ const categories = readConfObject(conf, 'category') as string[] | undefined
27
+ const queryLower = query.toLowerCase()
28
28
  return (
29
- getTrackName(config, session).toLowerCase().includes(filterLower) ||
30
- !!categories?.filter(c => c.toLowerCase().includes(filterLower)).length
29
+ getTrackName(conf, session).toLowerCase().includes(queryLower) ||
30
+ !!categories?.filter(c => c.toLowerCase().includes(queryLower)).length
31
31
  )
32
32
  }
33
33
 
@@ -74,7 +74,7 @@ export function generateHierarchy(
74
74
  const session = getSession(model)
75
75
 
76
76
  trackConfigurations
77
- .filter(conf => passesFilter(filterText, conf, session))
77
+ .filter(conf => matches(filterText, conf, session))
78
78
  .forEach(conf => {
79
79
  // copy the categories since this array can be mutated downstream
80
80
  const categories = [...(readConfObject(conf, 'category') || [])]
@@ -131,15 +131,18 @@ export default function stateTreeFactory(pluginManager: PluginManager) {
131
131
  id: ElementId,
132
132
  type: types.literal('HierarchicalTrackSelectorWidget'),
133
133
  collapsed: types.map(types.boolean),
134
- filterText: '',
135
134
  view: types.safeReference(
136
135
  pluginManager.pluggableMstType('view', 'stateModel'),
137
136
  ),
138
137
  })
139
138
  .volatile(() => ({
140
139
  selection: [] as AnyConfigurationModel[],
140
+ filterText: '',
141
141
  }))
142
142
  .actions(self => ({
143
+ setSelection(elt: AnyConfigurationModel[]) {
144
+ self.selection = elt
145
+ },
143
146
  addToSelection(elt: AnyConfigurationModel[]) {
144
147
  self.selection = dedupe([...self.selection, ...elt], e => e.trackId)
145
148
  },
@@ -0,0 +1,132 @@
1
+ import React from 'react'
2
+ import { getSnapshot, getParent } from 'mobx-state-tree'
3
+ import { ThemeProvider } from '@mui/material/styles'
4
+ import { render, cleanup, fireEvent, waitFor } from '@testing-library/react'
5
+ import { createJBrowseTheme } from '@jbrowse/core/ui'
6
+ import { createTestSession } from '@jbrowse/web/src/rootModel'
7
+
8
+ // locals
9
+ import PluginStoreWidget from './PluginStoreWidget'
10
+ import { PluginStoreModel } from '../model'
11
+
12
+ jest.mock('@jbrowse/web/src/makeWorkerInstance', () => () => {})
13
+
14
+ const plugins = {
15
+ plugins: [
16
+ {
17
+ name: 'MsaView',
18
+ authors: ['Colin Diesh'],
19
+ description: 'multiple sequence alignment browser plugin for JBrowse 2',
20
+ location: 'https://github.com/GMOD/jbrowse-plugin-msaview',
21
+ url: 'https://unpkg.com/jbrowse-plugin-msaview/dist/jbrowse-plugin-msaview.umd.production.min.js',
22
+ license: 'Apache License 2.0',
23
+ image:
24
+ 'https://raw.githubusercontent.com/GMOD/jbrowse-plugin-list/main/img/msaview-screenshot-fs8.png',
25
+ },
26
+ ],
27
+ }
28
+
29
+ let session: ReturnType<typeof createTestSession>
30
+ let model: PluginStoreModel
31
+
32
+ beforeEach(() => {
33
+ session = createTestSession()
34
+ model = session.addWidget('PluginStoreWidget', 'pluginStoreWidget')
35
+ const { location } = window
36
+
37
+ // @ts-ignore
38
+ delete window.location
39
+ window.location = {
40
+ ...location,
41
+ reload: jest.fn(),
42
+ }
43
+
44
+ // @ts-ignore
45
+ fetch.resetMocks()
46
+
47
+ // @ts-ignore
48
+ fetch.mockResponse(JSON.stringify(plugins))
49
+ })
50
+
51
+ afterEach(cleanup)
52
+
53
+ test('renders with the available plugins', async () => {
54
+ const { container, findByText } = render(
55
+ <ThemeProvider theme={createJBrowseTheme()}>
56
+ <PluginStoreWidget model={model} />
57
+ </ThemeProvider>,
58
+ )
59
+ await findByText('multiple sequence alignment browser plugin for JBrowse 2')
60
+ expect(container.firstChild).toMatchSnapshot()
61
+ })
62
+
63
+ test('Installs a session plugin', async () => {
64
+ const { findByText } = render(
65
+ <ThemeProvider theme={createJBrowseTheme()}>
66
+ <PluginStoreWidget model={model} />
67
+ </ThemeProvider>,
68
+ )
69
+ await findByText('multiple sequence alignment browser plugin for JBrowse 2')
70
+ fireEvent.click(await findByText('Install'))
71
+ await waitFor(() => {
72
+ expect(window.location.reload).toHaveBeenCalled()
73
+ })
74
+ expect(getSnapshot(session.sessionPlugins)[0]).toEqual(plugins.plugins[0])
75
+ })
76
+
77
+ test('plugin store admin - adds a custom plugin correctly', async () => {
78
+ session = createTestSession({}, true)
79
+ model = session.addWidget('PluginStoreWidget', 'pluginStoreWidget')
80
+ const { findByText, getByText, getByLabelText } = render(
81
+ <ThemeProvider theme={createJBrowseTheme()}>
82
+ <PluginStoreWidget model={model} />
83
+ </ThemeProvider>,
84
+ )
85
+ await findByText('multiple sequence alignment browser plugin for JBrowse 2')
86
+ fireEvent.click(getByText('Add custom plugin'))
87
+ fireEvent.change(getByLabelText('Plugin URL'), {
88
+ target: {
89
+ value:
90
+ 'https://unpkg.com/jbrowse-plugin-msaview/dist/jbrowse-plugin-msaview.esm.js',
91
+ },
92
+ })
93
+ fireEvent.change(getByLabelText('Plugin name'), {
94
+ target: {
95
+ value: 'MsaView',
96
+ },
97
+ })
98
+ fireEvent.click(getByText('Submit'))
99
+
100
+ await waitFor(() => {
101
+ expect(window.location.reload).toHaveBeenCalled()
102
+ })
103
+
104
+ expect(getSnapshot(getParent(session)).jbrowse.plugins).toEqual([
105
+ {
106
+ name: 'MsaView',
107
+ umdUrl:
108
+ 'https://unpkg.com/jbrowse-plugin-msaview/dist/jbrowse-plugin-msaview.esm.js',
109
+ },
110
+ ])
111
+ })
112
+
113
+ test('plugin store admin - removes a custom plugin correctly', async () => {
114
+ session = createTestSession({}, true)
115
+ model = session.addWidget('PluginStoreWidget', 'pluginStoreWidget')
116
+
117
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
118
+ const rootModel = getParent<any>(session)
119
+ const { jbrowse } = rootModel
120
+ jbrowse.addPlugin(plugins.plugins[0])
121
+ const { findByText, getByText, getByTestId } = render(
122
+ <ThemeProvider theme={createJBrowseTheme()}>
123
+ <PluginStoreWidget model={model} />
124
+ </ThemeProvider>,
125
+ )
126
+ await findByText('multiple sequence alignment browser plugin for JBrowse 2')
127
+ fireEvent.click(getByTestId('removePlugin-SVGPlugin'))
128
+ fireEvent.click(getByText('Confirm'))
129
+ await waitFor(() => {
130
+ expect(window.location.reload).toHaveBeenCalled()
131
+ })
132
+ })
@@ -1,6 +1,6 @@
1
1
  // Jest Snapshot v1, https://goo.gl/fbAQLP
2
2
 
3
- exports[`<PluginStoreWidget /> renders with the available plugins 1`] = `
3
+ exports[`renders with the available plugins 1`] = `
4
4
  <div
5
5
  class="css-1kq0gb6-root"
6
6
  >
@@ -16,7 +16,7 @@ exports[`<PluginStoreWidget /> renders with the available plugins 1`] = `
16
16
  Filter plugins
17
17
  </label>
18
18
  <div
19
- class="MuiInputBase-root MuiInput-root MuiInput-underline MuiInputBase-colorPrimary MuiInputBase-fullWidth MuiInputBase-formControl MuiInputBase-sizeSmall MuiInputBase-adornedEnd css-1wz39fi-MuiInputBase-root-MuiInput-root"
19
+ class="MuiInputBase-root MuiInput-root MuiInput-underline MuiInputBase-colorPrimary MuiInputBase-fullWidth MuiInputBase-formControl MuiInputBase-sizeSmall MuiInputBase-adornedEnd css-1blad95-MuiInputBase-root-MuiInput-root"
20
20
  >
21
21
  <input
22
22
  aria-invalid="false"
@@ -1,4 +1,19 @@
1
1
  import { ConfigurationSchema } from '@jbrowse/core/configuration'
2
+ import { WidgetType } from '@jbrowse/core/pluggableElementTypes'
3
+ import PluginManager from '@jbrowse/core/PluginManager'
4
+ import { lazy } from 'react'
2
5
 
3
- export { default as stateModelFactory } from './model'
4
- export const configSchema = ConfigurationSchema('PluginStoreWidget', {})
6
+ import stateModelFactory from './model'
7
+ const configSchema = ConfigurationSchema('PluginStoreWidget', {})
8
+
9
+ export default (pluginManager: PluginManager) => {
10
+ pluginManager.addWidgetType(() => {
11
+ return new WidgetType({
12
+ name: 'PluginStoreWidget',
13
+ heading: 'Plugin store',
14
+ configSchema,
15
+ stateModel: stateModelFactory(pluginManager),
16
+ ReactComponent: lazy(() => import('./components/PluginStoreWidget')),
17
+ })
18
+ })
19
+ }
@@ -0,0 +1,9 @@
1
+ // Jest Snapshot v1, https://goo.gl/fbAQLP
2
+
3
+ exports[`adds config editor widget 1`] = `{}`;
4
+
5
+ exports[`adds connection add widget 1`] = `{}`;
6
+
7
+ exports[`adds hierarchical track selector 1`] = `{}`;
8
+
9
+ exports[`adds track add widget 1`] = `{}`;