@jbrowse/plugin-linear-genome-view 2.1.7 → 2.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 (147) hide show
  1. package/dist/BaseLinearDisplay/components/LinearBlocks.d.ts +2 -2
  2. package/dist/BaseLinearDisplay/components/ServerSideRenderedBlockContent.js +2 -22
  3. package/dist/BaseLinearDisplay/components/ServerSideRenderedBlockContent.js.map +1 -1
  4. package/dist/BaseLinearDisplay/components/Tooltip.d.ts +1 -1
  5. package/dist/BaseLinearDisplay/models/BaseLinearDisplayModel.d.ts +149 -4
  6. package/dist/BaseLinearDisplay/models/BaseLinearDisplayModel.js +600 -464
  7. package/dist/BaseLinearDisplay/models/BaseLinearDisplayModel.js.map +1 -1
  8. package/dist/BaseLinearDisplay/models/baseLinearDisplayConfigSchema.js +19 -1
  9. package/dist/BaseLinearDisplay/models/baseLinearDisplayConfigSchema.js.map +1 -1
  10. package/dist/BaseLinearDisplay/models/serverSideRenderedBlock.d.ts +2 -2
  11. package/dist/BasicTrack/configSchema.d.ts +3 -0
  12. package/dist/BasicTrack/configSchema.js +18 -0
  13. package/dist/BasicTrack/configSchema.js.map +1 -0
  14. package/dist/BasicTrack/index.d.ts +3 -0
  15. package/dist/BasicTrack/index.js +18 -0
  16. package/dist/BasicTrack/index.js.map +1 -0
  17. package/dist/FeatureTrack/configSchema.d.ts +3 -0
  18. package/dist/FeatureTrack/configSchema.js +21 -0
  19. package/dist/FeatureTrack/configSchema.js.map +1 -0
  20. package/dist/FeatureTrack/index.d.ts +3 -0
  21. package/dist/FeatureTrack/index.js +18 -0
  22. package/dist/FeatureTrack/index.js.map +1 -0
  23. package/dist/LinearBareDisplay/configSchema.d.ts +5 -1
  24. package/dist/LinearBareDisplay/configSchema.js +12 -1
  25. package/dist/LinearBareDisplay/configSchema.js.map +1 -1
  26. package/dist/LinearBareDisplay/model.d.ts +16 -0
  27. package/dist/LinearBareDisplay/model.js +16 -0
  28. package/dist/LinearBareDisplay/model.js.map +1 -1
  29. package/dist/LinearBasicDisplay/configSchema.d.ts +5 -1
  30. package/dist/LinearBasicDisplay/configSchema.js +16 -1
  31. package/dist/LinearBasicDisplay/configSchema.js.map +1 -1
  32. package/dist/LinearBasicDisplay/model.d.ts +79 -8
  33. package/dist/LinearBasicDisplay/model.js +167 -111
  34. package/dist/LinearBasicDisplay/model.js.map +1 -1
  35. package/dist/LinearGenomeView/components/CenterLine.d.ts +1 -1
  36. package/dist/LinearGenomeView/components/GetSequenceDialog.d.ts +1 -1
  37. package/dist/LinearGenomeView/components/Gridlines.d.ts +1 -1
  38. package/dist/LinearGenomeView/components/Header.d.ts +1 -1
  39. package/dist/LinearGenomeView/components/ImportForm.d.ts +1 -1
  40. package/dist/LinearGenomeView/components/ImportForm.js +38 -31
  41. package/dist/LinearGenomeView/components/ImportForm.js.map +1 -1
  42. package/dist/LinearGenomeView/components/LinearGenomeView.d.ts +1 -1
  43. package/dist/LinearGenomeView/components/LinearGenomeView.js +2 -24
  44. package/dist/LinearGenomeView/components/LinearGenomeView.js.map +1 -1
  45. package/dist/LinearGenomeView/components/LinearGenomeViewSvg.d.ts +1 -1
  46. package/dist/LinearGenomeView/components/LinearGenomeViewSvg.js +7 -5
  47. package/dist/LinearGenomeView/components/LinearGenomeViewSvg.js.map +1 -1
  48. package/dist/LinearGenomeView/components/OverviewRubberBand.d.ts +1 -1
  49. package/dist/LinearGenomeView/components/OverviewScaleBar.d.ts +27 -35
  50. package/dist/LinearGenomeView/components/RubberBand.d.ts +1 -1
  51. package/dist/LinearGenomeView/components/ScaleBar.d.ts +1 -1
  52. package/dist/LinearGenomeView/components/TrackContainer.d.ts +1 -1
  53. package/dist/LinearGenomeView/components/TrackContainer.js +12 -9
  54. package/dist/LinearGenomeView/components/TrackContainer.js.map +1 -1
  55. package/dist/LinearGenomeView/components/TrackLabel.js +9 -1
  56. package/dist/LinearGenomeView/components/TrackLabel.js.map +1 -1
  57. package/dist/LinearGenomeView/components/TracksContainer.d.ts +1 -1
  58. package/dist/LinearGenomeView/index.d.ts +273 -18
  59. package/dist/LinearGenomeView/index.js +409 -90
  60. package/dist/LinearGenomeView/index.js.map +1 -1
  61. package/dist/index.d.ts +30 -90
  62. package/dist/index.js +4 -25
  63. package/dist/index.js.map +1 -1
  64. package/esm/BaseLinearDisplay/components/LinearBlocks.d.ts +2 -2
  65. package/esm/BaseLinearDisplay/components/ServerSideRenderedBlockContent.js +2 -22
  66. package/esm/BaseLinearDisplay/components/ServerSideRenderedBlockContent.js.map +1 -1
  67. package/esm/BaseLinearDisplay/components/Tooltip.d.ts +1 -1
  68. package/esm/BaseLinearDisplay/models/BaseLinearDisplayModel.d.ts +149 -4
  69. package/esm/BaseLinearDisplay/models/BaseLinearDisplayModel.js +600 -464
  70. package/esm/BaseLinearDisplay/models/BaseLinearDisplayModel.js.map +1 -1
  71. package/esm/BaseLinearDisplay/models/baseLinearDisplayConfigSchema.js +19 -1
  72. package/esm/BaseLinearDisplay/models/baseLinearDisplayConfigSchema.js.map +1 -1
  73. package/esm/BaseLinearDisplay/models/serverSideRenderedBlock.d.ts +2 -2
  74. package/esm/BasicTrack/configSchema.d.ts +3 -0
  75. package/esm/BasicTrack/configSchema.js +16 -0
  76. package/esm/BasicTrack/configSchema.js.map +1 -0
  77. package/esm/BasicTrack/index.d.ts +3 -0
  78. package/esm/BasicTrack/index.js +13 -0
  79. package/esm/BasicTrack/index.js.map +1 -0
  80. package/esm/FeatureTrack/configSchema.d.ts +3 -0
  81. package/esm/FeatureTrack/configSchema.js +19 -0
  82. package/esm/FeatureTrack/configSchema.js.map +1 -0
  83. package/esm/FeatureTrack/index.d.ts +3 -0
  84. package/esm/FeatureTrack/index.js +13 -0
  85. package/esm/FeatureTrack/index.js.map +1 -0
  86. package/esm/LinearBareDisplay/configSchema.d.ts +5 -1
  87. package/esm/LinearBareDisplay/configSchema.js +14 -2
  88. package/esm/LinearBareDisplay/configSchema.js.map +1 -1
  89. package/esm/LinearBareDisplay/model.d.ts +16 -0
  90. package/esm/LinearBareDisplay/model.js +16 -0
  91. package/esm/LinearBareDisplay/model.js.map +1 -1
  92. package/esm/LinearBasicDisplay/configSchema.d.ts +5 -1
  93. package/esm/LinearBasicDisplay/configSchema.js +18 -2
  94. package/esm/LinearBasicDisplay/configSchema.js.map +1 -1
  95. package/esm/LinearBasicDisplay/model.d.ts +79 -8
  96. package/esm/LinearBasicDisplay/model.js +167 -111
  97. package/esm/LinearBasicDisplay/model.js.map +1 -1
  98. package/esm/LinearGenomeView/components/CenterLine.d.ts +1 -1
  99. package/esm/LinearGenomeView/components/GetSequenceDialog.d.ts +1 -1
  100. package/esm/LinearGenomeView/components/Gridlines.d.ts +1 -1
  101. package/esm/LinearGenomeView/components/Header.d.ts +1 -1
  102. package/esm/LinearGenomeView/components/ImportForm.d.ts +1 -1
  103. package/esm/LinearGenomeView/components/ImportForm.js +40 -33
  104. package/esm/LinearGenomeView/components/ImportForm.js.map +1 -1
  105. package/esm/LinearGenomeView/components/LinearGenomeView.d.ts +1 -1
  106. package/esm/LinearGenomeView/components/LinearGenomeView.js +3 -25
  107. package/esm/LinearGenomeView/components/LinearGenomeView.js.map +1 -1
  108. package/esm/LinearGenomeView/components/LinearGenomeViewSvg.d.ts +1 -1
  109. package/esm/LinearGenomeView/components/LinearGenomeViewSvg.js +7 -5
  110. package/esm/LinearGenomeView/components/LinearGenomeViewSvg.js.map +1 -1
  111. package/esm/LinearGenomeView/components/OverviewRubberBand.d.ts +1 -1
  112. package/esm/LinearGenomeView/components/OverviewScaleBar.d.ts +27 -35
  113. package/esm/LinearGenomeView/components/RubberBand.d.ts +1 -1
  114. package/esm/LinearGenomeView/components/ScaleBar.d.ts +1 -1
  115. package/esm/LinearGenomeView/components/TrackContainer.d.ts +1 -1
  116. package/esm/LinearGenomeView/components/TrackContainer.js +13 -10
  117. package/esm/LinearGenomeView/components/TrackContainer.js.map +1 -1
  118. package/esm/LinearGenomeView/components/TrackLabel.js +9 -1
  119. package/esm/LinearGenomeView/components/TrackLabel.js.map +1 -1
  120. package/esm/LinearGenomeView/components/TracksContainer.d.ts +1 -1
  121. package/esm/LinearGenomeView/index.d.ts +273 -18
  122. package/esm/LinearGenomeView/index.js +409 -90
  123. package/esm/LinearGenomeView/index.js.map +1 -1
  124. package/esm/index.d.ts +30 -90
  125. package/esm/index.js +4 -25
  126. package/esm/index.js.map +1 -1
  127. package/package.json +2 -2
  128. package/src/BaseLinearDisplay/components/ServerSideRenderedBlockContent.tsx +2 -24
  129. package/src/BaseLinearDisplay/models/BaseLinearDisplayModel.tsx +695 -555
  130. package/src/BaseLinearDisplay/models/baseLinearDisplayConfigSchema.ts +20 -1
  131. package/src/BasicTrack/configSchema.ts +23 -0
  132. package/src/BasicTrack/index.ts +18 -0
  133. package/src/FeatureTrack/configSchema.ts +27 -0
  134. package/src/FeatureTrack/index.ts +21 -0
  135. package/src/LinearBareDisplay/configSchema.ts +15 -2
  136. package/src/LinearBareDisplay/model.ts +16 -0
  137. package/src/LinearBasicDisplay/configSchema.ts +19 -2
  138. package/src/LinearBasicDisplay/model.ts +63 -11
  139. package/src/LinearGenomeView/components/ImportForm.tsx +85 -67
  140. package/src/LinearGenomeView/components/LinearGenomeView.tsx +3 -33
  141. package/src/LinearGenomeView/components/LinearGenomeViewSvg.tsx +21 -18
  142. package/src/LinearGenomeView/components/TrackContainer.tsx +38 -27
  143. package/src/LinearGenomeView/components/TrackLabel.tsx +10 -1
  144. package/src/LinearGenomeView/components/__snapshots__/LinearGenomeView.test.tsx.snap +204 -204
  145. package/src/LinearGenomeView/index.test.ts +33 -26
  146. package/src/LinearGenomeView/index.tsx +471 -133
  147. package/src/index.ts +6 -46
@@ -65,12 +65,13 @@ const ZoomControls_1 = __importDefault(require("./components/ZoomControls"));
65
65
  exports.ZoomControls = ZoomControls_1.default;
66
66
  const LinearGenomeView_1 = __importDefault(require("./components/LinearGenomeView"));
67
67
  exports.LinearGenomeView = LinearGenomeView_1.default;
68
+ // lazies
68
69
  const SequenceSearchDialog = (0, react_1.lazy)(() => Promise.resolve().then(() => __importStar(require('./components/SequenceSearchDialog'))));
69
70
  function calculateVisibleLocStrings(contentBlocks) {
70
71
  if (!contentBlocks.length) {
71
72
  return '';
72
73
  }
73
- const isSingleAssemblyName = contentBlocks.every(block => block.assemblyName === contentBlocks[0].assemblyName);
74
+ const isSingleAssemblyName = contentBlocks.every(b => b.assemblyName === contentBlocks[0].assemblyName);
74
75
  const locs = contentBlocks.map(block => (0, util_1.assembleLocString)({
75
76
  ...block,
76
77
  start: Math.round(block.start),
@@ -91,30 +92,87 @@ function localStorageGetItem(item) {
91
92
  ? localStorage.getItem(item)
92
93
  : undefined;
93
94
  }
95
+ /**
96
+ * #stateModel LinearGenomeView
97
+ */
94
98
  function stateModelFactory(pluginManager) {
95
99
  return mobx_state_tree_1.types
96
100
  .compose(models_1.BaseViewModel, mobx_state_tree_1.types.model('LinearGenomeView', {
101
+ /**
102
+ * #property
103
+ */
97
104
  id: mst_1.ElementId,
105
+ /**
106
+ * #property
107
+ * this is a string instead of the const literal 'LinearGenomeView' to reduce some
108
+ * typescripting strictness, but you should pass the string 'LinearGenomeView' to
109
+ * the model explicitly
110
+ */
98
111
  type: mobx_state_tree_1.types.literal('LinearGenomeView'),
112
+ /**
113
+ * #property
114
+ * corresponds roughly to the horizontal scroll of the LGV
115
+ */
99
116
  offsetPx: 0,
117
+ /**
118
+ * #property
119
+ * corresponds roughly to the zoom level, base-pairs per pixel
120
+ */
100
121
  bpPerPx: 1,
122
+ /**
123
+ * #property
124
+ * currently displayed regions, can be a single chromosome, arbitrary subsections,
125
+ * or the entire set of chromosomes in the genome, but it not advised to use the
126
+ * entire set of chromosomes if your assembly is very fragmented
127
+ */
101
128
  displayedRegions: mobx_state_tree_1.types.array(mst_1.Region),
102
- // we use an array for the tracks because the tracks are displayed in a
103
- // specific order that we need to keep.
129
+ /**
130
+ * #property
131
+ * array of currently displayed tracks state models instances
132
+ */
104
133
  tracks: mobx_state_tree_1.types.array(pluginManager.pluggableMstType('track', 'stateModel')),
134
+ /**
135
+ * #property
136
+ * array of currently displayed tracks state model's
137
+ */
105
138
  hideHeader: false,
139
+ /**
140
+ * #property
141
+ */
106
142
  hideHeaderOverview: false,
143
+ /**
144
+ * #property
145
+ */
107
146
  hideNoTracksActive: false,
147
+ /**
148
+ * #property
149
+ */
108
150
  trackSelectorType: mobx_state_tree_1.types.optional(mobx_state_tree_1.types.enumeration(['hierarchical']), 'hierarchical'),
151
+ /**
152
+ * #property
153
+ * how to display the track labels, can be "overlapping", "offset", or "hidden"
154
+ */
109
155
  trackLabels: mobx_state_tree_1.types.optional(mobx_state_tree_1.types.string, () => localStorageGetItem('lgv-trackLabels') || 'overlapping'),
156
+ /**
157
+ * #property
158
+ * show the "center line"
159
+ */
110
160
  showCenterLine: mobx_state_tree_1.types.optional(mobx_state_tree_1.types.boolean, () => {
111
161
  const setting = localStorageGetItem('lgv-showCenterLine');
112
162
  return setting !== undefined && setting !== null ? !!+setting : false;
113
163
  }),
164
+ /**
165
+ * #property
166
+ * show the "cytobands" in the overview scale bar
167
+ */
114
168
  showCytobandsSetting: mobx_state_tree_1.types.optional(mobx_state_tree_1.types.boolean, () => {
115
169
  const setting = localStorageGetItem('lgv-showCytobands');
116
170
  return setting !== undefined && setting !== null ? !!+setting : true;
117
171
  }),
172
+ /**
173
+ * #property
174
+ * show the "gridlines" in the track area
175
+ */
118
176
  showGridlines: true,
119
177
  }))
120
178
  .volatile(() => ({
@@ -137,15 +195,24 @@ function stateModelFactory(pluginManager) {
137
195
  seqDialogDisplayed: false,
138
196
  }))
139
197
  .views(self => ({
198
+ /**
199
+ * #getter
200
+ */
140
201
  get width() {
141
202
  if (self.volatileWidth === undefined) {
142
203
  throw new Error('width undefined, make sure to check for model.initialized');
143
204
  }
144
205
  return self.volatileWidth;
145
206
  },
207
+ /**
208
+ * #getter
209
+ */
146
210
  get interRegionPaddingWidth() {
147
211
  return exports.INTER_REGION_PADDING_WIDTH;
148
212
  },
213
+ /**
214
+ * #getter
215
+ */
149
216
  get assemblyNames() {
150
217
  return [
151
218
  ...new Set(self.displayedRegions.map(region => region.assemblyName)),
@@ -153,14 +220,23 @@ function stateModelFactory(pluginManager) {
153
220
  },
154
221
  }))
155
222
  .views(self => ({
223
+ /**
224
+ * #method
225
+ */
156
226
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
157
227
  MiniControlsComponent() {
158
228
  return MiniControls_1.default;
159
229
  },
230
+ /**
231
+ * #method
232
+ */
160
233
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
161
234
  HeaderComponent() {
162
235
  return Header_1.default;
163
236
  },
237
+ /**
238
+ * #getter
239
+ */
164
240
  get assemblyErrors() {
165
241
  const { assemblyManager } = (0, util_1.getSession)(self);
166
242
  const { assemblyNames } = self;
@@ -169,23 +245,41 @@ function stateModelFactory(pluginManager) {
169
245
  .filter(f => !!f)
170
246
  .join(', ');
171
247
  },
248
+ /**
249
+ * #getter
250
+ */
172
251
  get assembliesInitialized() {
173
252
  const { assemblyManager } = (0, util_1.getSession)(self);
174
253
  const { assemblyNames } = self;
175
254
  return assemblyNames.every(a => { var _a; return (_a = assemblyManager.get(a)) === null || _a === void 0 ? void 0 : _a.initialized; });
176
255
  },
256
+ /**
257
+ * #getter
258
+ */
177
259
  get initialized() {
178
260
  return self.volatileWidth !== undefined && this.assembliesInitialized;
179
261
  },
262
+ /**
263
+ * #getter
264
+ */
180
265
  get hasDisplayedRegions() {
181
266
  return self.displayedRegions.length > 0;
182
267
  },
268
+ /**
269
+ * #getter
270
+ */
183
271
  get isSearchDialogDisplayed() {
184
272
  return self.searchResults !== undefined;
185
273
  },
274
+ /**
275
+ * #getter
276
+ */
186
277
  get scaleBarHeight() {
187
278
  return exports.SCALE_BAR_HEIGHT + exports.RESIZE_HANDLE_HEIGHT;
188
279
  },
280
+ /**
281
+ * #getter
282
+ */
189
283
  get headerHeight() {
190
284
  if (self.hideHeader) {
191
285
  return 0;
@@ -195,44 +289,77 @@ function stateModelFactory(pluginManager) {
195
289
  }
196
290
  return exports.HEADER_BAR_HEIGHT + exports.HEADER_OVERVIEW_HEIGHT;
197
291
  },
292
+ /**
293
+ * #getter
294
+ */
198
295
  get trackHeights() {
199
296
  return self.tracks
200
297
  .map(t => t.displays[0].height)
201
298
  .reduce((a, b) => a + b, 0);
202
299
  },
300
+ /**
301
+ * #getter
302
+ */
203
303
  get trackHeightsWithResizeHandles() {
204
304
  return this.trackHeights + self.tracks.length * exports.RESIZE_HANDLE_HEIGHT;
205
305
  },
306
+ /**
307
+ * #getter
308
+ */
206
309
  get height() {
207
310
  return (this.trackHeightsWithResizeHandles +
208
311
  this.headerHeight +
209
312
  this.scaleBarHeight);
210
313
  },
314
+ /**
315
+ * #getter
316
+ */
211
317
  get totalBp() {
212
318
  return self.displayedRegions.reduce((a, b) => a + b.end - b.start, 0);
213
319
  },
320
+ /**
321
+ * #getter
322
+ */
214
323
  get maxBpPerPx() {
215
324
  return this.totalBp / (self.width * 0.9);
216
325
  },
326
+ /**
327
+ * #getter
328
+ */
217
329
  get minBpPerPx() {
218
330
  return 1 / 50;
219
331
  },
332
+ /**
333
+ * #getter
334
+ */
220
335
  get error() {
221
336
  return self.volatileError || this.assemblyErrors;
222
337
  },
338
+ /**
339
+ * #getter
340
+ */
223
341
  get maxOffset() {
224
342
  // objectively determined to keep the linear genome on the main screen
225
343
  const leftPadding = 10;
226
344
  return this.displayedRegionsTotalPx - leftPadding;
227
345
  },
346
+ /**
347
+ * #getter
348
+ */
228
349
  get minOffset() {
229
350
  // objectively determined to keep the linear genome on the main screen
230
351
  const rightPadding = 30;
231
352
  return -self.width + rightPadding;
232
353
  },
354
+ /**
355
+ * #getter
356
+ */
233
357
  get displayedRegionsTotalPx() {
234
358
  return this.totalBp / self.bpPerPx;
235
359
  },
360
+ /**
361
+ * #method
362
+ */
236
363
  renderProps() {
237
364
  return {
238
365
  ...(0, tracks_1.getParentRenderProps)(self),
@@ -240,6 +367,9 @@ function stateModelFactory(pluginManager) {
240
367
  highResolutionScaling: (0, configuration_1.getConf)((0, util_1.getSession)(self), 'highResolutionScaling'),
241
368
  };
242
369
  },
370
+ /**
371
+ * #method
372
+ */
243
373
  searchScope(assemblyName) {
244
374
  return {
245
375
  assemblyName,
@@ -247,9 +377,15 @@ function stateModelFactory(pluginManager) {
247
377
  tracks: self.tracks,
248
378
  };
249
379
  },
380
+ /**
381
+ * #method
382
+ */
250
383
  getTrack(id) {
251
384
  return self.tracks.find(t => t.configuration.trackId === id);
252
385
  },
386
+ /**
387
+ * #method
388
+ */
253
389
  rankSearchResults(results) {
254
390
  // order of rank
255
391
  const openTrackIds = self.tracks.map(track => track.configuration.trackId);
@@ -260,7 +396,10 @@ function stateModelFactory(pluginManager) {
260
396
  });
261
397
  return results;
262
398
  },
263
- // modifies view menu action onClick to apply to all tracks of same type
399
+ /**
400
+ * #method
401
+ * modifies view menu action onClick to apply to all tracks of same type
402
+ */
264
403
  rewriteOnClicks(trackType, viewMenuActions) {
265
404
  viewMenuActions.forEach(action => {
266
405
  // go to lowest level menu
@@ -279,6 +418,9 @@ function stateModelFactory(pluginManager) {
279
418
  }
280
419
  });
281
420
  },
421
+ /**
422
+ * #getter
423
+ */
282
424
  get trackTypeActions() {
283
425
  const allActions = new Map();
284
426
  self.tracks.forEach(track => {
@@ -293,33 +435,60 @@ function stateModelFactory(pluginManager) {
293
435
  },
294
436
  }))
295
437
  .actions(self => ({
438
+ /**
439
+ * #action
440
+ */
296
441
  setShowCytobands(flag) {
297
442
  self.showCytobandsSetting = flag;
298
443
  localStorage.setItem('lgv-showCytobands', `${+flag}`);
299
444
  },
445
+ /**
446
+ * #action
447
+ */
300
448
  setWidth(newWidth) {
301
449
  self.volatileWidth = newWidth;
302
450
  },
451
+ /**
452
+ * #action
453
+ */
303
454
  setError(error) {
304
455
  self.volatileError = error;
305
456
  },
457
+ /**
458
+ * #action
459
+ */
306
460
  toggleHeader() {
307
461
  self.hideHeader = !self.hideHeader;
308
462
  },
463
+ /**
464
+ * #action
465
+ */
309
466
  toggleHeaderOverview() {
310
467
  self.hideHeaderOverview = !self.hideHeaderOverview;
311
468
  },
469
+ /**
470
+ * #action
471
+ */
312
472
  toggleNoTracksActive() {
313
473
  self.hideNoTracksActive = !self.hideNoTracksActive;
314
474
  },
475
+ /**
476
+ * #action
477
+ */
315
478
  toggleShowGridlines() {
316
479
  self.showGridlines = !self.showGridlines;
317
480
  },
481
+ /**
482
+ * #action
483
+ */
318
484
  scrollTo(offsetPx) {
319
485
  const newOffsetPx = (0, util_1.clamp)(offsetPx, self.minOffset, self.maxOffset);
320
486
  self.offsetPx = newOffsetPx;
321
487
  return newOffsetPx;
322
488
  },
489
+ /**
490
+ * #action
491
+ */
323
492
  zoomTo(bpPerPx) {
324
493
  const newBpPerPx = (0, util_1.clamp)(bpPerPx, self.minBpPerPx, self.maxBpPerPx);
325
494
  if (newBpPerPx === self.bpPerPx) {
@@ -337,22 +506,37 @@ function stateModelFactory(pluginManager) {
337
506
  viewWidth / 2));
338
507
  return newBpPerPx;
339
508
  },
509
+ /**
510
+ * #action
511
+ * sets offsets used in the get sequence dialog
512
+ */
340
513
  setOffsets(left, right) {
341
- // sets offsets used in the get sequence dialog
342
514
  self.leftOffset = left;
343
515
  self.rightOffset = right;
344
516
  },
517
+ /**
518
+ * #action
519
+ */
345
520
  setSearchResults(results, query) {
346
521
  self.searchResults = results;
347
522
  self.searchQuery = query;
348
523
  },
524
+ /**
525
+ * #action
526
+ */
349
527
  setGetSequenceDialogOpen(open) {
350
528
  self.seqDialogDisplayed = open;
351
529
  },
530
+ /**
531
+ * #action
532
+ */
352
533
  setNewView(bpPerPx, offsetPx) {
353
534
  this.zoomTo(bpPerPx);
354
535
  this.scrollTo(offsetPx);
355
536
  },
537
+ /**
538
+ * #action
539
+ */
356
540
  horizontallyFlip() {
357
541
  self.displayedRegions = (0, mobx_state_tree_1.cast)(self.displayedRegions
358
542
  .slice()
@@ -360,6 +544,9 @@ function stateModelFactory(pluginManager) {
360
544
  .map(region => ({ ...region, reversed: !region.reversed })));
361
545
  this.scrollTo(self.totalBp / self.bpPerPx - self.offsetPx - self.width);
362
546
  },
547
+ /**
548
+ * #action
549
+ */
363
550
  showTrack(trackId, initialSnapshot = {}, displayInitialSnapshot = {}) {
364
551
  const schema = pluginManager.pluggableConfigSchemaType('track');
365
552
  const conf = (0, mobx_state_tree_1.resolveIdentifier)(schema, (0, mobx_state_tree_1.getRoot)(self), trackId);
@@ -395,6 +582,9 @@ function stateModelFactory(pluginManager) {
395
582
  }
396
583
  return t[0];
397
584
  },
585
+ /**
586
+ * #action
587
+ */
398
588
  hideTrack(trackId) {
399
589
  const schema = pluginManager.pluggableConfigSchemaType('track');
400
590
  const conf = (0, mobx_state_tree_1.resolveIdentifier)(schema, (0, mobx_state_tree_1.getRoot)(self), trackId);
@@ -404,6 +594,9 @@ function stateModelFactory(pluginManager) {
404
594
  },
405
595
  }))
406
596
  .actions(self => ({
597
+ /**
598
+ * #action
599
+ */
407
600
  moveTrack(movingId, targetId) {
408
601
  const oldIndex = self.tracks.findIndex(track => track.id === movingId);
409
602
  if (oldIndex === -1) {
@@ -417,6 +610,9 @@ function stateModelFactory(pluginManager) {
417
610
  self.tracks.splice(oldIndex, 1);
418
611
  self.tracks.splice(newIndex, 0, track);
419
612
  },
613
+ /**
614
+ * #action
615
+ */
420
616
  closeView() {
421
617
  const parent = (0, util_1.getContainingView)(self);
422
618
  if (parent) {
@@ -430,6 +626,9 @@ function stateModelFactory(pluginManager) {
430
626
  (0, util_1.getSession)(self).removeView(self);
431
627
  }
432
628
  },
629
+ /**
630
+ * #action
631
+ */
433
632
  toggleTrack(trackId) {
434
633
  // if we have any tracks with that configuration, turn them off
435
634
  const hiddenCount = self.hideTrack(trackId);
@@ -438,18 +637,30 @@ function stateModelFactory(pluginManager) {
438
637
  self.showTrack(trackId);
439
638
  }
440
639
  },
640
+ /**
641
+ * #action
642
+ */
441
643
  setTrackLabels(setting) {
442
644
  self.trackLabels = setting;
443
645
  localStorage.setItem('lgv-trackLabels', setting);
444
646
  },
647
+ /**
648
+ * #action
649
+ */
445
650
  toggleCenterLine() {
446
651
  self.showCenterLine = !self.showCenterLine;
447
652
  localStorage.setItem('lgv-showCenterLine', `${+self.showCenterLine}`);
448
653
  },
654
+ /**
655
+ * #action
656
+ */
449
657
  setDisplayedRegions(regions) {
450
658
  self.displayedRegions = (0, mobx_state_tree_1.cast)(regions);
451
659
  self.zoomTo(self.bpPerPx);
452
660
  },
661
+ /**
662
+ * #action
663
+ */
453
664
  activateTrackSelector() {
454
665
  if (self.trackSelectorType === 'hierarchical') {
455
666
  const session = (0, util_1.getSession)(self);
@@ -462,6 +673,7 @@ function stateModelFactory(pluginManager) {
462
673
  throw new Error(`invalid track selector type ${self.trackSelectorType}`);
463
674
  },
464
675
  /**
676
+ * #method
465
677
  * Helper method for the fetchSequence.
466
678
  * Retrieves the corresponding regions that were selected by the rubberband
467
679
  *
@@ -483,38 +695,51 @@ function stateModelFactory(pluginManager) {
483
695
  end: Math.ceil(region.end),
484
696
  }));
485
697
  },
486
- // schedule something to be run after the next time displayedRegions is set
698
+ /**
699
+ * #action
700
+ * schedule something to be run after the next time displayedRegions is set
701
+ */
487
702
  afterDisplayedRegionsSet(cb) {
488
703
  self.afterDisplayedRegionsSetCallbacks.push(cb);
489
704
  },
705
+ /**
706
+ * #action
707
+ */
490
708
  horizontalScroll(distance) {
491
709
  const oldOffsetPx = self.offsetPx;
492
710
  // newOffsetPx is the actual offset after the scroll is clamped
493
711
  const newOffsetPx = self.scrollTo(self.offsetPx + distance);
494
712
  return newOffsetPx - oldOffsetPx;
495
713
  },
714
+ /**
715
+ * #action
716
+ */
496
717
  center() {
497
718
  const centerBp = self.totalBp / 2;
498
719
  const centerPx = centerBp / self.bpPerPx;
499
720
  self.scrollTo(Math.round(centerPx - self.width / 2));
500
721
  },
722
+ /**
723
+ * #action
724
+ */
501
725
  showAllRegions() {
502
726
  self.zoomTo(self.maxBpPerPx);
503
727
  this.center();
504
728
  },
729
+ /**
730
+ * #action
731
+ */
505
732
  showAllRegionsInAssembly(assemblyName) {
506
733
  const session = (0, util_1.getSession)(self);
507
734
  const { assemblyManager } = session;
508
735
  if (!assemblyName) {
509
- const assemblyNames = [
510
- ...new Set(self.displayedRegions.map(region => region.assemblyName)),
511
- ];
512
- if (assemblyNames.length > 1) {
513
- session.notify(`Can't perform this with multiple assemblies currently`);
736
+ const names = new Set(self.displayedRegions.map(r => r.assemblyName));
737
+ if (names.size > 1) {
738
+ session.notify(`Can't perform operation with multiple assemblies currently`);
514
739
  return;
515
740
  }
516
741
  ;
517
- [assemblyName] = assemblyNames;
742
+ [assemblyName] = [...names];
518
743
  }
519
744
  const assembly = assemblyManager.get(assemblyName);
520
745
  if (assembly) {
@@ -526,15 +751,24 @@ function stateModelFactory(pluginManager) {
526
751
  }
527
752
  }
528
753
  },
754
+ /**
755
+ * #action
756
+ */
529
757
  setDraggingTrackId(idx) {
530
758
  self.draggingTrackId = idx;
531
759
  },
760
+ /**
761
+ * #action
762
+ */
532
763
  setScaleFactor(factor) {
533
764
  self.scaleFactor = factor;
534
765
  },
535
- // this "clears the view" and makes the view return to the import form
766
+ /**
767
+ * #action
768
+ * this "clears the view" and makes the view return to the import form
769
+ */
536
770
  clearView() {
537
- this.setDisplayedRegions([]);
771
+ self.displayedRegions.clear();
538
772
  self.tracks.clear();
539
773
  // it is necessary to run these after setting displayed regions empty
540
774
  // or else model.offsetPx gets set to Infinity and breaks
@@ -542,6 +776,10 @@ function stateModelFactory(pluginManager) {
542
776
  self.scrollTo(0);
543
777
  self.zoomTo(10);
544
778
  },
779
+ /**
780
+ * #action
781
+ * creates an svg export and save using FileSaver
782
+ */
545
783
  async exportSvg(opts = {}) {
546
784
  // eslint-disable-next-line @typescript-eslint/no-explicit-any
547
785
  const html = await (0, LinearGenomeViewSvg_1.renderToSvg)(self, opts);
@@ -551,6 +789,10 @@ function stateModelFactory(pluginManager) {
551
789
  }))
552
790
  .actions(self => {
553
791
  let cancelLastAnimation = () => { };
792
+ /**
793
+ * #action
794
+ * perform animated slide
795
+ */
554
796
  function slide(viewWidths) {
555
797
  const [animate, cancelAnimation] = (0, util_1.springAnimate)(self.offsetPx, self.offsetPx + self.width * viewWidths, self.scrollTo);
556
798
  cancelLastAnimation();
@@ -561,6 +803,10 @@ function stateModelFactory(pluginManager) {
561
803
  })
562
804
  .actions(self => {
563
805
  let cancelLastAnimation = () => { };
806
+ /**
807
+ * #action
808
+ * perform animated zoom
809
+ */
564
810
  function zoom(targetBpPerPx) {
565
811
  self.zoomTo(self.bpPerPx);
566
812
  if (
@@ -582,17 +828,30 @@ function stateModelFactory(pluginManager) {
582
828
  return { zoom };
583
829
  })
584
830
  .views(self => ({
831
+ /**
832
+ * #getter
833
+ */
585
834
  get canShowCytobands() {
586
835
  return self.displayedRegions.length === 1 && this.anyCytobandsExist;
587
836
  },
837
+ /**
838
+ * #getter
839
+ */
588
840
  get showCytobands() {
589
841
  return this.canShowCytobands && self.showCytobandsSetting;
590
842
  },
843
+ /**
844
+ * #getter
845
+ */
591
846
  get anyCytobandsExist() {
592
847
  const { assemblyManager } = (0, util_1.getSession)(self);
593
- const { assemblyNames } = self;
594
- return assemblyNames.some(asm => { var _a, _b; return (_b = (_a = assemblyManager.get(asm)) === null || _a === void 0 ? void 0 : _a.cytobands) === null || _b === void 0 ? void 0 : _b.length; });
848
+ return self.assemblyNames.some(a => { var _a, _b; return (_b = (_a = assemblyManager.get(a)) === null || _a === void 0 ? void 0 : _a.cytobands) === null || _b === void 0 ? void 0 : _b.length; });
595
849
  },
850
+ /**
851
+ * #getter
852
+ * the cytoband is displayed to the right of the chromosome name,
853
+ * and that offset is calculated manually with this method
854
+ */
596
855
  get cytobandOffset() {
597
856
  return this.showCytobands
598
857
  ? (0, util_1.measureText)(self.displayedRegions[0].refName, 12) + 15
@@ -600,6 +859,10 @@ function stateModelFactory(pluginManager) {
600
859
  },
601
860
  }))
602
861
  .views(self => ({
862
+ /**
863
+ * #method
864
+ * return the view menu items
865
+ */
603
866
  menuItems() {
604
867
  const { canShowCytobands, showCytobands } = self;
605
868
  const session = (0, util_1.getSession)(self);
@@ -647,59 +910,57 @@ function stateModelFactory(pluginManager) {
647
910
  icon: SyncAlt_1.default,
648
911
  onClick: self.horizontallyFlip,
649
912
  },
650
- { type: 'divider' },
651
- {
652
- label: 'Show all regions in assembly',
653
- icon: Visibility_1.default,
654
- onClick: self.showAllRegionsInAssembly,
655
- },
656
- {
657
- label: 'Show center line',
658
- icon: Visibility_1.default,
659
- type: 'checkbox',
660
- checked: self.showCenterLine,
661
- onClick: self.toggleCenterLine,
662
- },
663
- {
664
- label: 'Show header',
665
- icon: Visibility_1.default,
666
- type: 'checkbox',
667
- checked: !self.hideHeader,
668
- onClick: self.toggleHeader,
669
- },
670
913
  {
671
- label: 'Show header overview',
914
+ label: 'Show...',
672
915
  icon: Visibility_1.default,
673
- type: 'checkbox',
674
- checked: !self.hideHeaderOverview,
675
- onClick: self.toggleHeaderOverview,
676
- disabled: self.hideHeader,
677
- },
678
- {
679
- label: 'Show no tracks active button',
680
- icon: Visibility_1.default,
681
- type: 'checkbox',
682
- checked: !self.hideNoTracksActive,
683
- onClick: self.toggleNoTracksActive,
684
- },
685
- {
686
- label: 'Show guidelines',
687
- icon: Visibility_1.default,
688
- type: 'checkbox',
689
- checked: self.showGridlines,
690
- onClick: self.toggleShowGridlines,
691
- },
692
- ...(canShowCytobands
693
- ? [
916
+ subMenu: [
694
917
  {
695
- label: 'Show ideogram',
696
- icon: Visibility_1.default,
918
+ label: 'Show all regions in assembly',
919
+ onClick: self.showAllRegionsInAssembly,
920
+ },
921
+ {
922
+ label: 'Show center line',
697
923
  type: 'checkbox',
698
- checked: self.showCytobands,
699
- onClick: () => self.setShowCytobands(!showCytobands),
924
+ checked: self.showCenterLine,
925
+ onClick: self.toggleCenterLine,
700
926
  },
701
- ]
702
- : []),
927
+ {
928
+ label: 'Show header',
929
+ type: 'checkbox',
930
+ checked: !self.hideHeader,
931
+ onClick: self.toggleHeader,
932
+ },
933
+ {
934
+ label: 'Show header overview',
935
+ type: 'checkbox',
936
+ checked: !self.hideHeaderOverview,
937
+ onClick: self.toggleHeaderOverview,
938
+ disabled: self.hideHeader,
939
+ },
940
+ {
941
+ label: 'Show no tracks active button',
942
+ type: 'checkbox',
943
+ checked: !self.hideNoTracksActive,
944
+ onClick: self.toggleNoTracksActive,
945
+ },
946
+ {
947
+ label: 'Show guidelines',
948
+ type: 'checkbox',
949
+ checked: self.showGridlines,
950
+ onClick: self.toggleShowGridlines,
951
+ },
952
+ ...(canShowCytobands
953
+ ? [
954
+ {
955
+ label: 'Show ideogram',
956
+ type: 'checkbox',
957
+ checked: self.showCytobands,
958
+ onClick: () => self.setShowCytobands(!showCytobands),
959
+ },
960
+ ]
961
+ : []),
962
+ ],
963
+ },
703
964
  {
704
965
  label: 'Track labels',
705
966
  icon: Label_1.default,
@@ -742,6 +1003,15 @@ function stateModelFactory(pluginManager) {
742
1003
  let currentlyCalculatedStaticBlocks;
743
1004
  let stringifiedCurrentlyCalculatedStaticBlocks = '';
744
1005
  return {
1006
+ /**
1007
+ * #getter
1008
+ * static blocks are an important concept jbrowse uses to avoid
1009
+ * re-rendering when you scroll to the side. when you horizontally
1010
+ * scroll to the right, old blocks to the left may be removed, and
1011
+ * new blocks may be instantiated on the right. tracks may use the
1012
+ * static blocks to render their data for the region represented by
1013
+ * the block
1014
+ */
745
1015
  get staticBlocks() {
746
1016
  const ret = (0, calculateStaticBlocks_1.default)(self);
747
1017
  const sret = JSON.stringify(ret);
@@ -751,27 +1021,48 @@ function stateModelFactory(pluginManager) {
751
1021
  }
752
1022
  return currentlyCalculatedStaticBlocks;
753
1023
  },
1024
+ /**
1025
+ * #getter
1026
+ * dynamic blocks represent the exact coordinates of the currently
1027
+ * visible genome regions on the screen. they are similar to static
1028
+ * blocks, but statcic blocks can go offscreen while dynamic blocks
1029
+ * represent exactly what is on screen
1030
+ */
754
1031
  get dynamicBlocks() {
755
1032
  return (0, calculateDynamicBlocks_1.default)(self);
756
1033
  },
1034
+ /**
1035
+ * #getter
1036
+ * rounded dynamic blocks are dynamic blocks without fractions of bp
1037
+ */
757
1038
  get roundedDynamicBlocks() {
758
- return this.dynamicBlocks.contentBlocks.map(block => {
759
- return {
760
- ...block,
761
- start: Math.floor(block.start),
762
- end: Math.ceil(block.end),
763
- };
764
- });
1039
+ return this.dynamicBlocks.contentBlocks.map(block => ({
1040
+ ...block,
1041
+ start: Math.floor(block.start),
1042
+ end: Math.ceil(block.end),
1043
+ }));
765
1044
  },
1045
+ /**
1046
+ * #getter
1047
+ * a single "combo-locstring" representing all the regions visible
1048
+ * on the screen
1049
+ */
766
1050
  get visibleLocStrings() {
767
1051
  return calculateVisibleLocStrings(this.dynamicBlocks.contentBlocks);
768
1052
  },
1053
+ /**
1054
+ * #getter
1055
+ * same as visibleLocStrings, but only updated every 300ms
1056
+ */
769
1057
  get coarseVisibleLocStrings() {
770
1058
  return calculateVisibleLocStrings(self.coarseDynamicBlocks);
771
1059
  },
772
1060
  };
773
1061
  })
774
1062
  .actions(self => ({
1063
+ /**
1064
+ * #action
1065
+ */
775
1066
  setCoarseDynamicBlocks(blocks) {
776
1067
  self.coarseDynamicBlocks = blocks.contentBlocks;
777
1068
  self.coarseTotalBp = blocks.totalBp;
@@ -786,6 +1077,7 @@ function stateModelFactory(pluginManager) {
786
1077
  }))
787
1078
  .actions(self => ({
788
1079
  /**
1080
+ * #action
789
1081
  * offset is the base-pair-offset in the displayed region, index is the index of the
790
1082
  * displayed region in the linear genome view
791
1083
  *
@@ -795,7 +1087,14 @@ function stateModelFactory(pluginManager) {
795
1087
  moveTo(start, end) {
796
1088
  (0, Base1DUtils_1.moveTo)(self, start, end);
797
1089
  },
798
- navToLocString(locString, optAssemblyName) {
1090
+ /**
1091
+ * #action
1092
+ * navigate to the given locstring
1093
+ *
1094
+ * @param locString - e.g. "chr1:1-100"
1095
+ * @param optAssemblyName - (optional) the assembly name to use when navigating to the locstring
1096
+ */
1097
+ async navToLocString(locString, optAssemblyName) {
799
1098
  const { assemblyNames } = self;
800
1099
  const { assemblyManager } = (0, util_1.getSession)(self);
801
1100
  const { isValidRefName } = assemblyManager;
@@ -805,6 +1104,9 @@ function stateModelFactory(pluginManager) {
805
1104
  .split(/(\s+)/)
806
1105
  .map(f => f.trim())
807
1106
  .filter(f => !!f);
1107
+ if (assemblyName) {
1108
+ await assemblyManager.waitForAssembly(assemblyName);
1109
+ }
808
1110
  // first try interpreting as a whitespace-separated sequence of
809
1111
  // multiple locstrings
810
1112
  try {
@@ -825,9 +1127,9 @@ function stateModelFactory(pluginManager) {
825
1127
  throw e;
826
1128
  }
827
1129
  }
828
- const locations = parsedLocStrings === null || parsedLocStrings === void 0 ? void 0 : parsedLocStrings.map(region => {
1130
+ const locations = await Promise.all(parsedLocStrings === null || parsedLocStrings === void 0 ? void 0 : parsedLocStrings.map(async (region) => {
829
1131
  const asmName = region.assemblyName || assemblyName;
830
- const asm = assemblyManager.get(asmName);
1132
+ const asm = await assemblyManager.waitForAssembly(asmName);
831
1133
  const { refName } = region;
832
1134
  if (!asm) {
833
1135
  throw new Error(`assembly ${asmName} not found`);
@@ -840,7 +1142,7 @@ function stateModelFactory(pluginManager) {
840
1142
  if (!canonicalRefName) {
841
1143
  throw new Error(`Could not find refName ${refName} in ${asm.name}`);
842
1144
  }
843
- const parentRegion = regions.find(region => region.refName === canonicalRefName);
1145
+ const parentRegion = regions.find(r => r.refName === canonicalRefName);
844
1146
  if (!parentRegion) {
845
1147
  throw new Error(`Could not find refName ${refName} in ${asmName}`);
846
1148
  }
@@ -849,7 +1151,7 @@ function stateModelFactory(pluginManager) {
849
1151
  assemblyName: asmName,
850
1152
  parentRegion,
851
1153
  };
852
- });
1154
+ }));
853
1155
  if (locations.length === 1) {
854
1156
  const loc = locations[0];
855
1157
  self.setDisplayedRegions([
@@ -870,6 +1172,7 @@ function stateModelFactory(pluginManager) {
870
1172
  }
871
1173
  },
872
1174
  /**
1175
+ * #action
873
1176
  * Navigate to a location based on its refName and optionally start, end,
874
1177
  * and assemblyName. Can handle if there are multiple displayedRegions
875
1178
  * from same refName. Only navigates to a location if it is entirely
@@ -878,11 +1181,14 @@ function stateModelFactory(pluginManager) {
878
1181
  *
879
1182
  * Throws an error if navigation was unsuccessful
880
1183
  *
881
- * @param location - a proposed location to navigate to
1184
+ * @param query - a proposed location to navigate to
882
1185
  */
883
1186
  navTo(query) {
884
1187
  this.navToMultiple([query]);
885
1188
  },
1189
+ /**
1190
+ * #action
1191
+ */
886
1192
  navToMultiple(locations) {
887
1193
  const firstLocation = locations[0];
888
1194
  let { refName } = firstLocation;
@@ -947,31 +1253,31 @@ function stateModelFactory(pluginManager) {
947
1253
  this.moveTo({ index, offset: f.reversed ? f.end - e : s - f.start }, { index, offset: f.reversed ? f.end - s : e - f.start });
948
1254
  return;
949
1255
  }
950
- let locationIndex = 0;
951
- let locationStart = 0;
952
- let locationEnd = 0;
953
- for (locationIndex; locationIndex < locations.length; locationIndex++) {
954
- const location = locations[locationIndex];
955
- const region = self.displayedRegions[index + locationIndex];
956
- locationStart = location.start || region.start;
957
- locationEnd = location.end || region.end;
1256
+ let idx = 0;
1257
+ let start = 0;
1258
+ let end = 0;
1259
+ for (idx; idx < locations.length; idx++) {
1260
+ const location = locations[idx];
1261
+ const region = self.displayedRegions[index + idx];
1262
+ start = location.start || region.start;
1263
+ end = location.end || region.end;
958
1264
  if (location.refName !== region.refName) {
959
1265
  throw new Error(`Entered location ${(0, util_1.assembleLocString)(location)} does not match with displayed regions`);
960
1266
  }
961
1267
  }
962
- locationIndex -= 1;
1268
+ idx -= 1;
963
1269
  const startDisplayedRegion = self.displayedRegions[index];
964
- const endDisplayedRegion = self.displayedRegions[index + locationIndex];
1270
+ const endDisplayedRegion = self.displayedRegions[index + idx];
965
1271
  this.moveTo({
966
1272
  index,
967
1273
  offset: startDisplayedRegion.reversed
968
1274
  ? startDisplayedRegion.end - e
969
1275
  : s - startDisplayedRegion.start,
970
1276
  }, {
971
- index: index + locationIndex,
1277
+ index: index + idx,
972
1278
  offset: endDisplayedRegion.reversed
973
- ? endDisplayedRegion.end - locationStart
974
- : locationEnd - endDisplayedRegion.start,
1279
+ ? endDisplayedRegion.end - start
1280
+ : end - endDisplayedRegion.start,
975
1281
  });
976
1282
  return;
977
1283
  }
@@ -984,6 +1290,9 @@ function stateModelFactory(pluginManager) {
984
1290
  },
985
1291
  }))
986
1292
  .views(self => ({
1293
+ /**
1294
+ * #method
1295
+ */
987
1296
  rubberBandMenuItems() {
988
1297
  return [
989
1298
  {
@@ -1001,10 +1310,14 @@ function stateModelFactory(pluginManager) {
1001
1310
  },
1002
1311
  ];
1003
1312
  },
1313
+ /**
1314
+ * #method
1315
+ */
1004
1316
  bpToPx({ refName, coord, regionNumber, }) {
1005
1317
  return (0, Base1DUtils_1.bpToPx)({ refName, coord, regionNumber, self });
1006
1318
  },
1007
1319
  /**
1320
+ * #method
1008
1321
  * scrolls the view to center on the given bp. if that is not in any
1009
1322
  * of the displayed regions, does nothing
1010
1323
  * @param coord - basepair at which you want to center the view
@@ -1021,9 +1334,15 @@ function stateModelFactory(pluginManager) {
1021
1334
  self.scrollTo(Math.round(centerPx.offsetPx - self.width / 2));
1022
1335
  }
1023
1336
  },
1337
+ /**
1338
+ * #method
1339
+ */
1024
1340
  pxToBp(px) {
1025
1341
  return (0, Base1DUtils_1.pxToBp)(self, px);
1026
1342
  },
1343
+ /**
1344
+ * #getter
1345
+ */
1027
1346
  get centerLineInfo() {
1028
1347
  return self.displayedRegions.length
1029
1348
  ? this.pxToBp(self.width / 2)