@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
@@ -1,6 +1,5 @@
1
1
  /* eslint-disable @typescript-eslint/no-explicit-any */
2
2
  import React from 'react';
3
- import TooLargeMessage from './TooLargeMessage';
4
3
  import { BaseDisplay } from '@jbrowse/core/pluggableElementTypes/models';
5
4
  import { getConf } from '@jbrowse/core/configuration';
6
5
  import { isAbortException, getContainingView, getContainingTrack, getSession, getViewParams, isSelectionContainer, isSessionModelWithWidgets, } from '@jbrowse/core/util';
@@ -11,6 +10,8 @@ import { autorun } from 'mobx';
11
10
  import { addDisposer, isAlive, types } from 'mobx-state-tree';
12
11
  // icons
13
12
  import MenuOpenIcon from '@mui/icons-material/MenuOpen';
13
+ // locals
14
+ import TooLargeMessage from './TooLargeMessage';
14
15
  import { Tooltip } from '../components/BaseLinearDisplay';
15
16
  import BlockState, { renderBlockData } from './serverSideRenderedBlock';
16
17
  // stabilize clipid under test for snapshot
@@ -33,492 +34,627 @@ function getDisplayStr(totalBytes) {
33
34
  }
34
35
  const minDisplayHeight = 20;
35
36
  const defaultDisplayHeight = 100;
36
- export const BaseLinearDisplay = types
37
- .compose('BaseLinearDisplay', BaseDisplay, types.model({
38
- height: types.optional(types.refinement('displayHeight', types.number, n => n >= minDisplayHeight), defaultDisplayHeight),
39
- blockState: types.map(BlockState),
40
- userBpPerPxLimit: types.maybe(types.number),
41
- userByteSizeLimit: types.maybe(types.number),
42
- }))
43
- .volatile(() => ({
44
- currBpPerPx: 0,
45
- message: '',
46
- featureIdUnderMouse: undefined,
47
- contextMenuFeature: undefined,
48
- scrollTop: 0,
49
- estimatedRegionStatsP: undefined,
50
- estimatedRegionStats: undefined,
51
- }))
52
- .views(self => ({
53
- get blockType() {
54
- return 'staticBlocks';
55
- },
56
- get blockDefinitions() {
57
- const { blockType } = this;
58
- const view = getContainingView(self);
59
- if (!view.initialized) {
60
- throw new Error('view not initialized yet');
61
- }
62
- return view[blockType];
63
- },
64
- }))
65
- .views(self => ({
66
- /**
67
- * how many milliseconds to wait for the display to
68
- * "settle" before re-rendering a block
69
- */
70
- get renderDelay() {
71
- return 50;
72
- },
73
- get TooltipComponent() {
74
- return Tooltip;
75
- },
76
- /**
77
- * returns a string feature ID if the globally-selected object
78
- * is probably a feature
79
- */
80
- get selectedFeatureId() {
81
- if (isAlive(self)) {
82
- const { selection } = getSession(self);
83
- // does it quack like a feature?
84
- if (isFeature(selection)) {
85
- return selection.id();
37
+ /**
38
+ * #stateModel BaseLinearDisplay
39
+ * extends `BaseDisplay`
40
+ */
41
+ function stateModelFactory() {
42
+ return types
43
+ .compose('BaseLinearDisplay', BaseDisplay, types.model({
44
+ /**
45
+ * #property
46
+ */
47
+ height: types.optional(types.refinement('displayHeight', types.number, n => n >= minDisplayHeight), defaultDisplayHeight),
48
+ /**
49
+ * #property
50
+ * updated via autorun
51
+ */
52
+ blockState: types.map(BlockState),
53
+ /**
54
+ * #property
55
+ */
56
+ userBpPerPxLimit: types.maybe(types.number),
57
+ /**
58
+ * #property
59
+ */
60
+ userByteSizeLimit: types.maybe(types.number),
61
+ }))
62
+ .volatile(() => ({
63
+ currBpPerPx: 0,
64
+ message: '',
65
+ featureIdUnderMouse: undefined,
66
+ contextMenuFeature: undefined,
67
+ scrollTop: 0,
68
+ estimatedRegionStatsP: undefined,
69
+ estimatedRegionStats: undefined,
70
+ }))
71
+ .views(self => ({
72
+ /**
73
+ * #getter
74
+ */
75
+ get blockType() {
76
+ return 'staticBlocks';
77
+ },
78
+ /**
79
+ * #getter
80
+ */
81
+ get blockDefinitions() {
82
+ const { blockType } = this;
83
+ const view = getContainingView(self);
84
+ if (!view.initialized) {
85
+ throw new Error('view not initialized yet');
86
86
  }
87
- }
88
- return undefined;
89
- },
90
- /**
91
- * if a display-level message should be displayed instead of the blocks,
92
- * make this return a react component
93
- */
94
- get DisplayMessageComponent() {
95
- return undefined;
96
- },
97
- }))
98
- .views(self => ({
99
- /**
100
- * a CompositeMap of `featureId -> feature obj` that
101
- * just looks in all the block data for that feature
102
- */
103
- get features() {
104
- const featureMaps = [];
105
- for (const block of self.blockState.values()) {
106
- if (block && block.features) {
107
- featureMaps.push(block.features);
87
+ return view[blockType];
88
+ },
89
+ }))
90
+ .views(self => ({
91
+ /**
92
+ * #getter
93
+ * how many milliseconds to wait for the display to
94
+ * "settle" before re-rendering a block
95
+ */
96
+ get renderDelay() {
97
+ return 50;
98
+ },
99
+ /**
100
+ * #getter
101
+ */
102
+ get TooltipComponent() {
103
+ return Tooltip;
104
+ },
105
+ /**
106
+ * #getter
107
+ * returns a string feature ID if the globally-selected object
108
+ * is probably a feature
109
+ */
110
+ get selectedFeatureId() {
111
+ if (isAlive(self)) {
112
+ const { selection } = getSession(self);
113
+ // does it quack like a feature?
114
+ if (isFeature(selection)) {
115
+ return selection.id();
116
+ }
108
117
  }
109
- }
110
- return new CompositeMap(featureMaps);
111
- },
112
- get featureUnderMouse() {
113
- const feat = self.featureIdUnderMouse;
114
- return feat ? this.features.get(feat) : undefined;
115
- },
116
- getFeatureOverlapping(blockKey, x, y) {
117
- var _a, _b;
118
- return (_b = (_a = self.blockState.get(blockKey)) === null || _a === void 0 ? void 0 : _a.layout) === null || _b === void 0 ? void 0 : _b.getByCoord(x, y);
119
- },
120
- getFeatureByID(blockKey, id) {
121
- var _a, _b;
122
- return (_b = (_a = self.blockState.get(blockKey)) === null || _a === void 0 ? void 0 : _a.layout) === null || _b === void 0 ? void 0 : _b.getByID(id);
123
- },
124
- // if block key is not supplied, can look at all blocks
125
- searchFeatureByID(id) {
126
- let ret;
127
- self.blockState.forEach(block => {
128
- var _a;
129
- const val = (_a = block === null || block === void 0 ? void 0 : block.layout) === null || _a === void 0 ? void 0 : _a.getByID(id);
130
- if (val) {
131
- ret = val;
118
+ return undefined;
119
+ },
120
+ /**
121
+ * #getter
122
+ * if a display-level message should be displayed instead of the blocks,
123
+ * make this return a react component
124
+ */
125
+ get DisplayMessageComponent() {
126
+ return undefined;
127
+ },
128
+ }))
129
+ .views(self => ({
130
+ /**
131
+ * #getter
132
+ * a CompositeMap of `featureId -> feature obj` that
133
+ * just looks in all the block data for that feature
134
+ */
135
+ get features() {
136
+ const featureMaps = [];
137
+ for (const block of self.blockState.values()) {
138
+ if (block && block.features) {
139
+ featureMaps.push(block.features);
140
+ }
132
141
  }
133
- });
134
- return ret;
135
- },
136
- get currentBytesRequested() {
137
- var _a;
138
- return ((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.bytes) || 0;
139
- },
140
- get currentFeatureScreenDensity() {
141
- var _a;
142
- const view = getContainingView(self);
143
- return (((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.featureDensity) || 0) * view.bpPerPx;
144
- },
145
- get maxFeatureScreenDensity() {
146
- return getConf(self, 'maxFeatureScreenDensity');
147
- },
148
- get estimatedStatsReady() {
149
- return !!self.estimatedRegionStats;
150
- },
151
- get maxAllowableBytes() {
152
- var _a;
153
- return (self.userByteSizeLimit ||
154
- ((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.fetchSizeLimit) ||
155
- getConf(self, 'fetchSizeLimit'));
156
- },
157
- }))
158
- .actions(self => ({
159
- // base display reload does nothing, see specialized displays for details
160
- setMessage(message) {
161
- self.message = message;
162
- },
163
- afterAttach() {
164
- // watch the parent's blocks to update our block state when they change,
165
- // then we recreate the blocks on our own model (creating and deleting to
166
- // match the parent blocks)
167
- const blockWatchDisposer = autorun(() => {
168
- const blocksPresent = {};
142
+ return new CompositeMap(featureMaps);
143
+ },
144
+ /**
145
+ * #getter
146
+ */
147
+ get featureUnderMouse() {
148
+ const feat = self.featureIdUnderMouse;
149
+ return feat ? this.features.get(feat) : undefined;
150
+ },
151
+ /**
152
+ * #getter
153
+ */
154
+ getFeatureOverlapping(blockKey, x, y) {
155
+ var _a, _b;
156
+ return (_b = (_a = self.blockState.get(blockKey)) === null || _a === void 0 ? void 0 : _a.layout) === null || _b === void 0 ? void 0 : _b.getByCoord(x, y);
157
+ },
158
+ /**
159
+ * #getter
160
+ */
161
+ getFeatureByID(blockKey, id) {
162
+ var _a, _b;
163
+ return (_b = (_a = self.blockState.get(blockKey)) === null || _a === void 0 ? void 0 : _a.layout) === null || _b === void 0 ? void 0 : _b.getByID(id);
164
+ },
165
+ /**
166
+ * #getter
167
+ */
168
+ searchFeatureByID(id) {
169
+ let ret;
170
+ self.blockState.forEach(block => {
171
+ var _a;
172
+ const val = (_a = block === null || block === void 0 ? void 0 : block.layout) === null || _a === void 0 ? void 0 : _a.getByID(id);
173
+ if (val) {
174
+ ret = val;
175
+ }
176
+ });
177
+ return ret;
178
+ },
179
+ /**
180
+ * #getter
181
+ */
182
+ get currentBytesRequested() {
183
+ var _a;
184
+ return ((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.bytes) || 0;
185
+ },
186
+ /**
187
+ * #getter
188
+ */
189
+ get currentFeatureScreenDensity() {
190
+ var _a;
169
191
  const view = getContainingView(self);
170
- if (view.initialized) {
171
- self.blockDefinitions.contentBlocks.forEach(block => {
172
- blocksPresent[block.key] = true;
173
- if (!self.blockState.has(block.key)) {
174
- this.addBlock(block.key, block);
175
- }
176
- });
177
- self.blockState.forEach((_, key) => {
178
- if (!blocksPresent[key]) {
179
- this.deleteBlock(key);
180
- }
181
- });
182
- }
183
- });
184
- addDisposer(self, blockWatchDisposer);
185
- },
186
- estimateRegionsStats(regions, opts) {
187
- if (self.estimatedRegionStatsP) {
188
- return self.estimatedRegionStatsP;
189
- }
190
- const { rpcManager } = getSession(self);
191
- const { adapterConfig } = self;
192
- if (!adapterConfig) {
193
- // A track extending the base track might not have an adapter config
194
- // e.g. Apollo tracks don't use adapters
195
- return Promise.resolve({});
196
- }
197
- const sessionId = getRpcSessionId(self);
198
- const params = {
199
- sessionId,
200
- regions,
201
- adapterConfig,
202
- statusCallback: (message) => {
203
- if (isAlive(self)) {
204
- this.setMessage(message);
192
+ return (((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.featureDensity) || 0) * view.bpPerPx;
193
+ },
194
+ /**
195
+ * #getter
196
+ */
197
+ get maxFeatureScreenDensity() {
198
+ return getConf(self, 'maxFeatureScreenDensity');
199
+ },
200
+ /**
201
+ * #getter
202
+ */
203
+ get estimatedStatsReady() {
204
+ return !!self.estimatedRegionStats;
205
+ },
206
+ /**
207
+ * #getter
208
+ */
209
+ get maxAllowableBytes() {
210
+ var _a;
211
+ return (self.userByteSizeLimit ||
212
+ ((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.fetchSizeLimit) ||
213
+ getConf(self, 'fetchSizeLimit'));
214
+ },
215
+ }))
216
+ .actions(self => ({
217
+ /**
218
+ * #action
219
+ */
220
+ setMessage(message) {
221
+ self.message = message;
222
+ },
223
+ afterAttach() {
224
+ // watch the parent's blocks to update our block state when they change,
225
+ // then we recreate the blocks on our own model (creating and deleting to
226
+ // match the parent blocks)
227
+ const blockWatchDisposer = autorun(() => {
228
+ const blocksPresent = {};
229
+ const view = getContainingView(self);
230
+ if (view.initialized) {
231
+ self.blockDefinitions.contentBlocks.forEach(block => {
232
+ blocksPresent[block.key] = true;
233
+ if (!self.blockState.has(block.key)) {
234
+ this.addBlock(block.key, block);
235
+ }
236
+ });
237
+ self.blockState.forEach((_, key) => {
238
+ if (!blocksPresent[key]) {
239
+ this.deleteBlock(key);
240
+ }
241
+ });
205
242
  }
206
- },
207
- ...opts,
208
- };
209
- self.estimatedRegionStatsP = rpcManager
210
- .call(sessionId, 'CoreEstimateRegionStats', params)
211
- .catch(e => {
212
- this.setRegionStatsP(undefined);
213
- throw e;
214
- });
215
- return self.estimatedRegionStatsP;
216
- },
217
- setRegionStatsP(p) {
218
- self.estimatedRegionStatsP = p;
219
- },
220
- setRegionStats(estimatedRegionStats) {
221
- self.estimatedRegionStats = estimatedRegionStats;
222
- },
223
- clearRegionStats() {
224
- self.estimatedRegionStatsP = undefined;
225
- self.estimatedRegionStats = undefined;
226
- },
227
- setHeight(displayHeight) {
228
- if (displayHeight > minDisplayHeight) {
229
- self.height = displayHeight;
230
- }
231
- else {
232
- self.height = minDisplayHeight;
233
- }
234
- return self.height;
235
- },
236
- resizeHeight(distance) {
237
- const oldHeight = self.height;
238
- const newHeight = this.setHeight(self.height + distance);
239
- return newHeight - oldHeight;
240
- },
241
- setScrollTop(scrollTop) {
242
- self.scrollTop = scrollTop;
243
- },
244
- updateStatsLimit(stats) {
245
- const view = getContainingView(self);
246
- if (stats.bytes) {
247
- self.userByteSizeLimit = stats.bytes;
248
- }
249
- else {
250
- self.userBpPerPxLimit = view.bpPerPx;
251
- }
252
- },
253
- addBlock(key, block) {
254
- self.blockState.set(key, BlockState.create({
255
- key,
256
- region: block.toRegion(),
257
- }));
258
- },
259
- setCurrBpPerPx(n) {
260
- self.currBpPerPx = n;
261
- },
262
- deleteBlock(key) {
263
- self.blockState.delete(key);
264
- },
265
- selectFeature(feature) {
266
- const session = getSession(self);
267
- if (isSessionModelWithWidgets(session)) {
268
- const featureWidget = session.addWidget('BaseFeatureWidget', 'baseFeature', {
269
- view: getContainingView(self),
270
- track: getContainingTrack(self),
271
- featureData: feature.toJSON(),
272
243
  });
273
- session.showWidget(featureWidget);
274
- }
275
- if (isSelectionContainer(session)) {
276
- session.setSelection(feature);
277
- }
278
- },
279
- clearFeatureSelection() {
280
- const session = getSession(self);
281
- session.clearSelection();
282
- },
283
- setFeatureIdUnderMouse(feature) {
284
- self.featureIdUnderMouse = feature;
285
- },
286
- reload() {
287
- ;
288
- [...self.blockState.values()].map(val => val.doReload());
289
- },
290
- setContextMenuFeature(feature) {
291
- self.contextMenuFeature = feature;
292
- },
293
- }))
294
- .views(self => ({
295
- // region is too large if:
296
- // - stats are ready
297
- // - region is greater than 20kb (don't warn when zoomed in less than that)
298
- // - and bytes > max allowed bytes || curr density>max density
299
- get regionTooLarge() {
300
- const view = getContainingView(self);
301
- if (!self.estimatedStatsReady || view.dynamicBlocks.totalBp < 20000) {
302
- return false;
303
- }
304
- const bpLimitOrDensity = self.userBpPerPxLimit
305
- ? view.bpPerPx > self.userBpPerPxLimit
306
- : self.currentFeatureScreenDensity > self.maxFeatureScreenDensity;
307
- return (self.currentBytesRequested > self.maxAllowableBytes || bpLimitOrDensity);
308
- },
309
- // only shows a message of bytes requested is defined, the feature density
310
- // based stats don't produce any helpful message besides to zoom in
311
- get regionTooLargeReason() {
312
- const req = self.currentBytesRequested;
313
- const max = self.maxAllowableBytes;
314
- return req && req > max
315
- ? `Requested too much data (${getDisplayStr(req)})`
316
- : '';
317
- },
318
- }))
319
- .actions(self => {
320
- const { reload: superReload } = self;
321
- return {
322
- async reload() {
323
- self.setError();
324
- const aborter = new AbortController();
244
+ addDisposer(self, blockWatchDisposer);
245
+ },
246
+ /**
247
+ * #action
248
+ */
249
+ estimateRegionsStats(regions, opts) {
250
+ if (self.estimatedRegionStatsP) {
251
+ return self.estimatedRegionStatsP;
252
+ }
253
+ const { rpcManager } = getSession(self);
254
+ const { adapterConfig } = self;
255
+ if (!adapterConfig) {
256
+ // A track extending the base track might not have an adapter config
257
+ // e.g. Apollo tracks don't use adapters
258
+ return Promise.resolve({});
259
+ }
260
+ const sessionId = getRpcSessionId(self);
261
+ const params = {
262
+ sessionId,
263
+ regions,
264
+ adapterConfig,
265
+ statusCallback: (message) => {
266
+ if (isAlive(self)) {
267
+ this.setMessage(message);
268
+ }
269
+ },
270
+ ...opts,
271
+ };
272
+ self.estimatedRegionStatsP = rpcManager
273
+ .call(sessionId, 'CoreEstimateRegionStats', params)
274
+ .catch(e => {
275
+ this.setRegionStatsP(undefined);
276
+ throw e;
277
+ });
278
+ return self.estimatedRegionStatsP;
279
+ },
280
+ /**
281
+ * #action
282
+ */
283
+ setRegionStatsP(p) {
284
+ self.estimatedRegionStatsP = p;
285
+ },
286
+ /**
287
+ * #action
288
+ */
289
+ setRegionStats(estimatedRegionStats) {
290
+ self.estimatedRegionStats = estimatedRegionStats;
291
+ },
292
+ /**
293
+ * #action
294
+ */
295
+ clearRegionStats() {
296
+ self.estimatedRegionStatsP = undefined;
297
+ self.estimatedRegionStats = undefined;
298
+ },
299
+ /**
300
+ * #action
301
+ */
302
+ setHeight(displayHeight) {
303
+ if (displayHeight > minDisplayHeight) {
304
+ self.height = displayHeight;
305
+ }
306
+ else {
307
+ self.height = minDisplayHeight;
308
+ }
309
+ return self.height;
310
+ },
311
+ /**
312
+ * #action
313
+ */
314
+ resizeHeight(distance) {
315
+ const oldHeight = self.height;
316
+ const newHeight = this.setHeight(self.height + distance);
317
+ return newHeight - oldHeight;
318
+ },
319
+ /**
320
+ * #action
321
+ */
322
+ setScrollTop(scrollTop) {
323
+ self.scrollTop = scrollTop;
324
+ },
325
+ /**
326
+ * #action
327
+ */
328
+ updateStatsLimit(stats) {
325
329
  const view = getContainingView(self);
326
- // extra check for contentBlocks.length
327
- // https://github.com/GMOD/jbrowse-components/issues/2694
328
- if (!view.initialized || !view.staticBlocks.contentBlocks.length) {
329
- return;
330
+ if (stats.bytes) {
331
+ self.userByteSizeLimit = stats.bytes;
330
332
  }
331
- try {
332
- self.estimatedRegionStatsP = self.estimateRegionsStats(view.staticBlocks.contentBlocks, { signal: aborter.signal });
333
- const estimatedRegionStats = await self.estimatedRegionStatsP;
334
- if (isAlive(self)) {
335
- self.setRegionStats(estimatedRegionStats);
336
- superReload();
337
- }
338
- else {
339
- return;
340
- }
333
+ else {
334
+ self.userBpPerPxLimit = view.bpPerPx;
335
+ }
336
+ },
337
+ /**
338
+ * #action
339
+ */
340
+ addBlock(key, block) {
341
+ self.blockState.set(key, BlockState.create({
342
+ key,
343
+ region: block.toRegion(),
344
+ }));
345
+ },
346
+ /**
347
+ * #action
348
+ */
349
+ setCurrBpPerPx(n) {
350
+ self.currBpPerPx = n;
351
+ },
352
+ /**
353
+ * #action
354
+ */
355
+ deleteBlock(key) {
356
+ self.blockState.delete(key);
357
+ },
358
+ /**
359
+ * #action
360
+ */
361
+ selectFeature(feature) {
362
+ const session = getSession(self);
363
+ if (isSessionModelWithWidgets(session)) {
364
+ const featureWidget = session.addWidget('BaseFeatureWidget', 'baseFeature', {
365
+ view: getContainingView(self),
366
+ track: getContainingTrack(self),
367
+ featureData: feature.toJSON(),
368
+ });
369
+ session.showWidget(featureWidget);
341
370
  }
342
- catch (e) {
343
- console.error(e);
344
- self.setError(e);
371
+ if (isSelectionContainer(session)) {
372
+ session.setSelection(feature);
345
373
  }
346
374
  },
347
- afterAttach() {
348
- // this autorun performs stats estimation
349
- //
350
- // the chain of events calls estimateRegionsStats against the data
351
- // adapter which by default uses featureDensity, but can also respond
352
- // with a byte size estimate and fetch size limit (data adapter can
353
- // define what is too much data)
354
- addDisposer(self, autorun(async () => {
355
- var _a;
375
+ /**
376
+ * #action
377
+ */
378
+ clearFeatureSelection() {
379
+ const session = getSession(self);
380
+ session.clearSelection();
381
+ },
382
+ /**
383
+ * #action
384
+ */
385
+ setFeatureIdUnderMouse(feature) {
386
+ self.featureIdUnderMouse = feature;
387
+ },
388
+ /**
389
+ * #action
390
+ */
391
+ reload() {
392
+ ;
393
+ [...self.blockState.values()].map(val => val.doReload());
394
+ },
395
+ /**
396
+ * #action
397
+ */
398
+ setContextMenuFeature(feature) {
399
+ self.contextMenuFeature = feature;
400
+ },
401
+ }))
402
+ .views(self => ({
403
+ /**
404
+ * #getter
405
+ * region is too large if:
406
+ * - stats are ready
407
+ * - region is greater than 20kb (don't warn when zoomed in less than that)
408
+ * - and bytes is greater than max allowed bytes or density greater than max density
409
+ */
410
+ get regionTooLarge() {
411
+ const view = getContainingView(self);
412
+ if (!self.estimatedStatsReady || view.dynamicBlocks.totalBp < 20000) {
413
+ return false;
414
+ }
415
+ const bpLimitOrDensity = self.userBpPerPxLimit
416
+ ? view.bpPerPx > self.userBpPerPxLimit
417
+ : self.currentFeatureScreenDensity > self.maxFeatureScreenDensity;
418
+ return (self.currentBytesRequested > self.maxAllowableBytes ||
419
+ bpLimitOrDensity);
420
+ },
421
+ /**
422
+ * #getter
423
+ * only shows a message of bytes requested is defined, the feature density
424
+ * based stats don't produce any helpful message besides to zoom in
425
+ */
426
+ get regionTooLargeReason() {
427
+ const req = self.currentBytesRequested;
428
+ const max = self.maxAllowableBytes;
429
+ return req && req > max
430
+ ? `Requested too much data (${getDisplayStr(req)})`
431
+ : '';
432
+ },
433
+ }))
434
+ .actions(self => {
435
+ const { reload: superReload } = self;
436
+ return {
437
+ /**
438
+ * #action
439
+ */
440
+ async reload() {
441
+ self.setError();
442
+ const aborter = new AbortController();
443
+ const view = getContainingView(self);
444
+ // extra check for contentBlocks.length
445
+ // https://github.com/GMOD/jbrowse-components/issues/2694
446
+ if (!view.initialized || !view.staticBlocks.contentBlocks.length) {
447
+ return;
448
+ }
356
449
  try {
357
- const aborter = new AbortController();
358
- const view = getContainingView(self);
359
- // extra check for contentBlocks.length
360
- // https://github.com/GMOD/jbrowse-components/issues/2694
361
- if (!view.initialized ||
362
- !view.staticBlocks.contentBlocks.length) {
363
- return;
364
- }
365
- // don't re-estimate featureDensity even if zoom level changes,
366
- // jbrowse1-style assume it's sort of representative
367
- if (((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.featureDensity) !== undefined) {
368
- self.setCurrBpPerPx(view.bpPerPx);
369
- return;
370
- }
371
- // we estimate stats once at a given zoom level
372
- if (view.bpPerPx === self.currBpPerPx) {
373
- return;
374
- }
375
- self.clearRegionStats();
376
- self.setCurrBpPerPx(view.bpPerPx);
377
- const statsP = self.estimateRegionsStats(view.staticBlocks.contentBlocks, { signal: aborter.signal });
378
- self.setRegionStatsP(statsP);
379
- const estimatedRegionStats = await statsP;
450
+ self.estimatedRegionStatsP = self.estimateRegionsStats(view.staticBlocks.contentBlocks, { signal: aborter.signal });
451
+ const estimatedRegionStats = await self.estimatedRegionStatsP;
380
452
  if (isAlive(self)) {
381
453
  self.setRegionStats(estimatedRegionStats);
454
+ superReload();
455
+ }
456
+ else {
457
+ return;
382
458
  }
383
459
  }
384
460
  catch (e) {
385
- if (!isAbortException(e) && isAlive(self)) {
386
- console.error(e);
387
- self.setError(e);
388
- }
461
+ console.error(e);
462
+ self.setError(e);
389
463
  }
390
- }, { delay: 500 }));
391
- },
392
- };
393
- })
394
- .views(self => ({
395
- regionCannotBeRenderedText(_region) {
396
- return self.regionTooLarge ? 'Force load to see features' : '';
397
- },
398
- /**
399
- * @param region -
400
- * @returns falsy if the region is fine to try rendering. Otherwise,
401
- * return a react node + string of text.
402
- * string of text describes why it cannot be rendered
403
- * react node allows user to force load at current setting
404
- */
405
- regionCannotBeRendered(_region) {
406
- const { regionTooLarge } = self;
407
- return regionTooLarge ? React.createElement(TooLargeMessage, { model: self }) : null;
408
- },
409
- trackMenuItems() {
410
- return [];
411
- },
412
- contextMenuItems() {
413
- return self.contextMenuFeature
414
- ? [
415
- {
416
- label: 'Open feature details',
417
- icon: MenuOpenIcon,
418
- onClick: () => {
419
- if (self.contextMenuFeature) {
420
- self.selectFeature(self.contextMenuFeature);
464
+ },
465
+ afterAttach() {
466
+ // this autorun performs stats estimation
467
+ //
468
+ // the chain of events calls estimateRegionsStats against the data
469
+ // adapter which by default uses featureDensity, but can also respond
470
+ // with a byte size estimate and fetch size limit (data adapter can
471
+ // define what is too much data)
472
+ addDisposer(self, autorun(async () => {
473
+ var _a;
474
+ try {
475
+ const aborter = new AbortController();
476
+ const view = getContainingView(self);
477
+ // extra check for contentBlocks.length
478
+ // https://github.com/GMOD/jbrowse-components/issues/2694
479
+ if (!view.initialized ||
480
+ !view.staticBlocks.contentBlocks.length) {
481
+ return;
482
+ }
483
+ // don't re-estimate featureDensity even if zoom level changes,
484
+ // jbrowse1-style assume it's sort of representative
485
+ if (((_a = self.estimatedRegionStats) === null || _a === void 0 ? void 0 : _a.featureDensity) !== undefined) {
486
+ self.setCurrBpPerPx(view.bpPerPx);
487
+ return;
488
+ }
489
+ // we estimate stats once at a given zoom level
490
+ if (view.bpPerPx === self.currBpPerPx) {
491
+ return;
421
492
  }
493
+ self.clearRegionStats();
494
+ self.setCurrBpPerPx(view.bpPerPx);
495
+ const statsP = self.estimateRegionsStats(view.staticBlocks.contentBlocks, { signal: aborter.signal });
496
+ self.setRegionStatsP(statsP);
497
+ const estimatedRegionStats = await statsP;
498
+ if (isAlive(self)) {
499
+ self.setRegionStats(estimatedRegionStats);
500
+ }
501
+ }
502
+ catch (e) {
503
+ if (!isAbortException(e) && isAlive(self)) {
504
+ console.error(e);
505
+ self.setError(e);
506
+ }
507
+ }
508
+ }, { delay: 500 }));
509
+ },
510
+ };
511
+ })
512
+ .views(self => ({
513
+ /**
514
+ * #method
515
+ */
516
+ regionCannotBeRenderedText(_region) {
517
+ return self.regionTooLarge ? 'Force load to see features' : '';
518
+ },
519
+ /**
520
+ * #method
521
+ * @param region -
522
+ * @returns falsy if the region is fine to try rendering. Otherwise,
523
+ * return a react node + string of text.
524
+ * string of text describes why it cannot be rendered
525
+ * react node allows user to force load at current setting
526
+ */
527
+ regionCannotBeRendered(_region) {
528
+ const { regionTooLarge } = self;
529
+ return regionTooLarge ? React.createElement(TooLargeMessage, { model: self }) : null;
530
+ },
531
+ /**
532
+ * #method
533
+ */
534
+ trackMenuItems() {
535
+ return [];
536
+ },
537
+ /**
538
+ * #method
539
+ */
540
+ contextMenuItems() {
541
+ return self.contextMenuFeature
542
+ ? [
543
+ {
544
+ label: 'Open feature details',
545
+ icon: MenuOpenIcon,
546
+ onClick: () => {
547
+ if (self.contextMenuFeature) {
548
+ self.selectFeature(self.contextMenuFeature);
549
+ }
550
+ },
422
551
  },
552
+ ]
553
+ : [];
554
+ },
555
+ /**
556
+ * #method
557
+ */
558
+ renderProps() {
559
+ const view = getContainingView(self);
560
+ return {
561
+ ...getParentRenderProps(self),
562
+ notReady: self.currBpPerPx !== view.bpPerPx || !self.estimatedRegionStats,
563
+ rpcDriverName: self.rpcDriverName,
564
+ displayModel: self,
565
+ onFeatureClick(_, featureId) {
566
+ const f = featureId || self.featureIdUnderMouse;
567
+ if (!f) {
568
+ self.clearFeatureSelection();
569
+ }
570
+ else {
571
+ const feature = self.features.get(f);
572
+ if (feature) {
573
+ self.selectFeature(feature);
574
+ }
575
+ }
423
576
  },
424
- ]
425
- : [];
426
- },
427
- renderProps() {
428
- const view = getContainingView(self);
429
- return {
430
- ...getParentRenderProps(self),
431
- notReady: self.currBpPerPx !== view.bpPerPx || !self.estimatedRegionStats,
432
- rpcDriverName: self.rpcDriverName,
433
- displayModel: self,
434
- onFeatureClick(_, featureId) {
435
- const f = featureId || self.featureIdUnderMouse;
436
- if (!f) {
577
+ onClick() {
437
578
  self.clearFeatureSelection();
438
- }
439
- else {
440
- const feature = self.features.get(f);
441
- if (feature) {
442
- self.selectFeature(feature);
579
+ },
580
+ // similar to click but opens a menu with further options
581
+ onFeatureContextMenu(_, featureId) {
582
+ const f = featureId || self.featureIdUnderMouse;
583
+ if (!f) {
584
+ self.clearFeatureSelection();
443
585
  }
444
- }
445
- },
446
- onClick() {
447
- self.clearFeatureSelection();
448
- },
449
- // similar to click but opens a menu with further options
450
- onFeatureContextMenu(_, featureId) {
451
- const f = featureId || self.featureIdUnderMouse;
452
- if (!f) {
586
+ else {
587
+ // feature id under mouse passed to context menu
588
+ self.setContextMenuFeature(self.features.get(f));
589
+ }
590
+ },
591
+ onMouseMove(_, featureId) {
592
+ self.setFeatureIdUnderMouse(featureId);
593
+ },
594
+ onMouseLeave(_) {
595
+ self.setFeatureIdUnderMouse(undefined);
596
+ },
597
+ onContextMenu() {
598
+ self.setContextMenuFeature(undefined);
453
599
  self.clearFeatureSelection();
600
+ },
601
+ };
602
+ },
603
+ }))
604
+ .actions(self => ({
605
+ /**
606
+ * #method
607
+ */
608
+ async renderSvg(opts) {
609
+ const { height, id } = self;
610
+ const { overrideHeight } = opts;
611
+ const view = getContainingView(self);
612
+ const { offsetPx: viewOffsetPx, roundedDynamicBlocks, width } = view;
613
+ const renderings = await Promise.all(roundedDynamicBlocks.map(block => {
614
+ const blockState = BlockState.create({
615
+ key: block.key,
616
+ region: block,
617
+ });
618
+ // regionCannotBeRendered can return jsx so look for plaintext
619
+ // version, or just get the default if none available
620
+ const cannotBeRenderedReason = self.regionCannotBeRenderedText(block) ||
621
+ self.regionCannotBeRendered(block);
622
+ if (cannotBeRenderedReason) {
623
+ return {
624
+ reactElement: (React.createElement(React.Fragment, null,
625
+ React.createElement("rect", { x: 0, y: 0, width: width, height: 20, fill: "#aaa" }),
626
+ React.createElement("text", { x: 0, y: 15 }, cannotBeRenderedReason))),
627
+ };
454
628
  }
455
- else {
456
- // feature id under mouse passed to context menu
457
- self.setContextMenuFeature(self.features.get(f));
458
- }
459
- },
460
- onMouseMove(_, featureId) {
461
- self.setFeatureIdUnderMouse(featureId);
462
- },
463
- onMouseLeave(_) {
464
- self.setFeatureIdUnderMouse(undefined);
465
- },
466
- onContextMenu() {
467
- self.setContextMenuFeature(undefined);
468
- self.clearFeatureSelection();
469
- },
470
- };
471
- },
472
- }))
473
- .actions(self => ({
474
- async renderSvg(opts) {
475
- const { height, id } = self;
476
- const { overrideHeight } = opts;
477
- const view = getContainingView(self);
478
- const { offsetPx: viewOffsetPx, roundedDynamicBlocks, width } = view;
479
- const renderings = await Promise.all(roundedDynamicBlocks.map(block => {
480
- const blockState = BlockState.create({
481
- key: block.key,
482
- region: block,
483
- });
484
- // regionCannotBeRendered can return jsx so look for plaintext
485
- // version, or just get the default if none available
486
- const cannotBeRenderedReason = self.regionCannotBeRenderedText(block) ||
487
- self.regionCannotBeRendered(block);
488
- if (cannotBeRenderedReason) {
489
- return {
490
- reactElement: (React.createElement(React.Fragment, null,
491
- React.createElement("rect", { x: 0, y: 0, width: width, height: 20, fill: "#aaa" }),
492
- React.createElement("text", { x: 0, y: 15 }, cannotBeRenderedReason))),
493
- };
494
- }
495
- const { rpcManager, renderArgs, renderProps, rendererType } = renderBlockData(blockState, self);
496
- return rendererType.renderInClient(rpcManager, {
497
- ...renderArgs,
498
- ...renderProps,
499
- viewParams: getViewParams(self, true),
500
- exportSVG: opts,
501
- });
502
- }));
503
- return (React.createElement(React.Fragment, null, renderings.map((rendering, index) => {
504
- const { offsetPx } = roundedDynamicBlocks[index];
505
- const offset = offsetPx - viewOffsetPx;
506
- const clipid = getId(id, index);
507
- return (React.createElement(React.Fragment, { key: `frag-${index}` },
508
- React.createElement("defs", null,
509
- React.createElement("clipPath", { id: clipid },
510
- React.createElement("rect", { x: 0, y: 0, width: width, height: overrideHeight || height }))),
511
- React.createElement("g", { transform: `translate(${offset} 0)` },
512
- React.createElement("g", { clipPath: `url(#${clipid})` }, React.isValidElement(rendering.reactElement) ? (rendering.reactElement) : (
513
- // eslint-disable-next-line react/no-danger
514
- React.createElement("g", { dangerouslySetInnerHTML: { __html: rendering.html } }))))));
515
- })));
516
- },
517
- }))
518
- .postProcessSnapshot(self => {
519
- // xref https://github.com/mobxjs/mobx-state-tree/issues/1524 for Omit
520
- const r = self;
521
- const { blockState, ...rest } = r;
522
- return rest;
523
- });
629
+ const { rpcManager, renderArgs, renderProps, rendererType } = renderBlockData(blockState, self);
630
+ return rendererType.renderInClient(rpcManager, {
631
+ ...renderArgs,
632
+ ...renderProps,
633
+ viewParams: getViewParams(self, true),
634
+ exportSVG: opts,
635
+ });
636
+ }));
637
+ return (React.createElement(React.Fragment, null, renderings.map((rendering, index) => {
638
+ const { offsetPx } = roundedDynamicBlocks[index];
639
+ const offset = offsetPx - viewOffsetPx;
640
+ const clipid = getId(id, index);
641
+ return (React.createElement(React.Fragment, { key: `frag-${index}` },
642
+ React.createElement("defs", null,
643
+ React.createElement("clipPath", { id: clipid },
644
+ React.createElement("rect", { x: 0, y: 0, width: width, height: overrideHeight || height }))),
645
+ React.createElement("g", { transform: `translate(${offset} 0)` },
646
+ React.createElement("g", { clipPath: `url(#${clipid})` }, React.isValidElement(rendering.reactElement) ? (rendering.reactElement) : (React.createElement("g", {
647
+ /* eslint-disable-next-line react/no-danger */
648
+ dangerouslySetInnerHTML: { __html: rendering.html } }))))));
649
+ })));
650
+ },
651
+ }))
652
+ .postProcessSnapshot(self => {
653
+ // xref https://github.com/mobxjs/mobx-state-tree/issues/1524 for Omit
654
+ const r = self;
655
+ const { blockState, ...rest } = r;
656
+ return rest;
657
+ });
658
+ }
659
+ export const BaseLinearDisplay = stateModelFactory();
524
660
  //# sourceMappingURL=BaseLinearDisplayModel.js.map