@gmod/bbi 8.1.2 → 9.0.3
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.
- package/README.md +0 -24
- package/dist/array-feature-view.d.ts +1 -1
- package/dist/array-feature-view.js.map +1 -1
- package/dist/bbi.d.ts +5 -25
- package/dist/bbi.js +31 -133
- package/dist/bbi.js.map +1 -1
- package/dist/bigbed.d.ts +0 -1
- package/dist/bigbed.js +20 -51
- package/dist/bigbed.js.map +1 -1
- package/dist/bigwig.d.ts +1 -2
- package/dist/bigwig.js +1 -2
- package/dist/bigwig.js.map +1 -1
- package/dist/block-view.d.ts +7 -16
- package/dist/block-view.js +369 -443
- package/dist/block-view.js.map +1 -1
- package/dist/parse-bigwig.d.ts +2 -2
- package/dist/parse-bigwig.js +5 -5
- package/dist/parse-bigwig.js.map +1 -1
- package/dist/range.d.ts +1 -15
- package/dist/range.js +16 -49
- package/dist/range.js.map +1 -1
- package/dist/util.d.ts +0 -22
- package/dist/util.js +0 -46
- package/dist/util.js.map +1 -1
- package/dist/wasm/inflate-wasm-inlined.js +3 -3
- package/dist/wasm/inflate-wasm-inlined.js.map +1 -1
- package/dist/wasm/inflate_wasm_bg.d.ts +1 -1
- package/dist/wasm/inflate_wasm_bg.js +2 -2
- package/esm/array-feature-view.d.ts +1 -1
- package/esm/array-feature-view.js.map +1 -1
- package/esm/bbi.d.ts +5 -25
- package/esm/bbi.js +31 -133
- package/esm/bbi.js.map +1 -1
- package/esm/bigbed.d.ts +0 -1
- package/esm/bigbed.js +20 -50
- package/esm/bigbed.js.map +1 -1
- package/esm/bigwig.d.ts +1 -2
- package/esm/bigwig.js +1 -2
- package/esm/bigwig.js.map +1 -1
- package/esm/block-view.d.ts +7 -16
- package/esm/block-view.js +369 -443
- package/esm/block-view.js.map +1 -1
- package/esm/parse-bigwig.d.ts +2 -2
- package/esm/parse-bigwig.js +5 -5
- package/esm/parse-bigwig.js.map +1 -1
- package/esm/range.d.ts +1 -15
- package/esm/range.js +15 -48
- package/esm/range.js.map +1 -1
- package/esm/util.d.ts +0 -22
- package/esm/util.js +0 -42
- package/esm/util.js.map +1 -1
- package/esm/wasm/inflate-wasm-inlined.js +3 -3
- package/esm/wasm/inflate-wasm-inlined.js.map +1 -1
- package/esm/wasm/inflate_wasm_bg.d.ts +1 -1
- package/esm/wasm/inflate_wasm_bg.js +1 -1
- package/package.json +21 -24
- package/src/array-feature-view.ts +5 -2
- package/src/bbi.ts +50 -153
- package/src/bigbed.ts +23 -55
- package/src/bigwig.ts +1 -3
- package/src/block-view.ts +525 -639
- package/src/parse-bigwig.ts +7 -9
- package/src/range.ts +19 -58
- package/src/util.ts +0 -46
- package/src/wasm/inflate-wasm-inlined.js +3 -3
- package/src/wasm/inflate_wasm_bg.js +1 -1
- package/src/wasm/inflate_wasm_bg.wasm +0 -0
- package/CHANGELOG.md +0 -350
package/src/bbi.ts
CHANGED
|
@@ -1,6 +1,4 @@
|
|
|
1
1
|
import { LocalFile, RemoteFile } from 'generic-filehandle2'
|
|
2
|
-
import { Observable, firstValueFrom } from 'rxjs'
|
|
3
|
-
import { toArray } from 'rxjs/operators'
|
|
4
2
|
|
|
5
3
|
import { BlockView } from './block-view.ts'
|
|
6
4
|
|
|
@@ -8,7 +6,6 @@ import type {
|
|
|
8
6
|
BigWigFeatureArrays,
|
|
9
7
|
BigWigHeader,
|
|
10
8
|
BigWigHeaderWithRefNames,
|
|
11
|
-
Feature,
|
|
12
9
|
RefInfo,
|
|
13
10
|
RequestOptions2,
|
|
14
11
|
RequestOptions,
|
|
@@ -89,13 +86,12 @@ export abstract class BBI {
|
|
|
89
86
|
const b = await this.bbi.read(requestSize, 0, opts)
|
|
90
87
|
const dataView = getDataView(b)
|
|
91
88
|
|
|
92
|
-
const r1 = dataView.getInt32(0, true)
|
|
93
|
-
if (r1 !== BIG_WIG_MAGIC && r1 !== BIG_BED_MAGIC) {
|
|
94
|
-
throw new Error('not a BigWig/BigBed file')
|
|
95
|
-
}
|
|
96
89
|
let offset = 0
|
|
97
90
|
const magic = dataView.getInt32(offset, true)
|
|
98
91
|
offset += 4
|
|
92
|
+
if (magic !== BIG_WIG_MAGIC && magic !== BIG_BED_MAGIC) {
|
|
93
|
+
throw new Error('not a BigWig/BigBed file')
|
|
94
|
+
}
|
|
99
95
|
const version = dataView.getUint16(offset, true)
|
|
100
96
|
offset += 2
|
|
101
97
|
const numZoomLevels = dataView.getUint16(offset, true)
|
|
@@ -159,7 +155,6 @@ export abstract class BBI {
|
|
|
159
155
|
const scoreSum = dataView.getFloat64(offset, true)
|
|
160
156
|
offset += 8
|
|
161
157
|
const scoreSumSquares = dataView.getFloat64(offset, true)
|
|
162
|
-
offset += 8
|
|
163
158
|
|
|
164
159
|
totalSummary = {
|
|
165
160
|
scoreMin,
|
|
@@ -209,39 +204,23 @@ export abstract class BBI {
|
|
|
209
204
|
const dataView = getDataView(
|
|
210
205
|
await this.bbi.read(32, chromosomeTreeOffset, opts),
|
|
211
206
|
)
|
|
212
|
-
|
|
213
|
-
|
|
214
|
-
offset += 4
|
|
215
|
-
// const blockSize = dataView.getUint32(offset, true) // unused
|
|
216
|
-
offset += 4
|
|
217
|
-
const keySize = dataView.getUint32(offset, true)
|
|
218
|
-
offset += 4
|
|
219
|
-
const valSize = dataView.getUint32(offset, true)
|
|
220
|
-
offset += 4
|
|
221
|
-
// const itemCount = dataView.getBigUint64(offset, true) // unused
|
|
222
|
-
offset += 8
|
|
207
|
+
const keySize = dataView.getUint32(8, true)
|
|
208
|
+
const valSize = dataView.getUint32(12, true)
|
|
223
209
|
|
|
224
210
|
// Recursively traverses the B+ tree to populate chromosome name-to-ID mappings
|
|
225
211
|
const readBPlusTreeNode = async (currentOffset: number) => {
|
|
226
|
-
const
|
|
227
|
-
const
|
|
228
|
-
|
|
229
|
-
const isLeafNode = dataView.getUint8(offset)
|
|
230
|
-
offset += 1
|
|
231
|
-
// const reserved = dataView.getUint8(offset) // unused
|
|
232
|
-
offset += 1
|
|
233
|
-
const count = dataView.getUint16(offset, true)
|
|
234
|
-
offset += 2
|
|
212
|
+
const header = getDataView(await this.bbi.read(4, currentOffset))
|
|
213
|
+
const isLeafNode = header.getUint8(0)
|
|
214
|
+
const count = header.getUint16(2, true)
|
|
235
215
|
|
|
236
216
|
// Leaf nodes contain the actual chromosome name-to-ID mappings
|
|
237
217
|
if (isLeafNode) {
|
|
238
218
|
const b = await this.bbi.read(
|
|
239
219
|
count * (keySize + valSize),
|
|
240
|
-
currentOffset +
|
|
220
|
+
currentOffset + 4,
|
|
241
221
|
)
|
|
242
222
|
const dataView = getDataView(b)
|
|
243
|
-
offset = 0
|
|
244
|
-
|
|
223
|
+
let offset = 0
|
|
245
224
|
for (let n = 0; n < count; n++) {
|
|
246
225
|
const keyEnd = b.indexOf(0, offset)
|
|
247
226
|
const effectiveKeyEnd =
|
|
@@ -254,22 +233,16 @@ export abstract class BBI {
|
|
|
254
233
|
offset += 4
|
|
255
234
|
const refSize = dataView.getUint32(offset, true)
|
|
256
235
|
offset += 4
|
|
257
|
-
|
|
258
236
|
refsByName[this.renameRefSeqs(key)] = refId
|
|
259
|
-
refsByNumber[refId] = {
|
|
260
|
-
name: key,
|
|
261
|
-
id: refId,
|
|
262
|
-
length: refSize,
|
|
263
|
-
}
|
|
237
|
+
refsByNumber[refId] = { name: key, id: refId, length: refSize }
|
|
264
238
|
}
|
|
265
239
|
} else {
|
|
266
240
|
// Non-leaf nodes contain pointers to child nodes
|
|
267
|
-
const nextNodes = []
|
|
268
241
|
const dataView = getDataView(
|
|
269
|
-
await this.bbi.read(count * (keySize + 8), currentOffset +
|
|
242
|
+
await this.bbi.read(count * (keySize + 8), currentOffset + 4),
|
|
270
243
|
)
|
|
271
|
-
|
|
272
|
-
|
|
244
|
+
const nextNodes = []
|
|
245
|
+
let offset = 0
|
|
273
246
|
for (let n = 0; n < count; n++) {
|
|
274
247
|
offset += keySize
|
|
275
248
|
const childOffset = Number(dataView.getBigUint64(offset, true))
|
|
@@ -286,6 +259,29 @@ export abstract class BBI {
|
|
|
286
259
|
}
|
|
287
260
|
}
|
|
288
261
|
|
|
262
|
+
private viewCache = new Map<string, BlockView>()
|
|
263
|
+
|
|
264
|
+
protected getOrCreateBlockView(
|
|
265
|
+
refsByName: Record<string, number>,
|
|
266
|
+
rTreeOffset: number,
|
|
267
|
+
uncompressBufSize: number,
|
|
268
|
+
blockType: string,
|
|
269
|
+
) {
|
|
270
|
+
const key = `${rTreeOffset}_${blockType}`
|
|
271
|
+
let view = this.viewCache.get(key)
|
|
272
|
+
if (!view) {
|
|
273
|
+
view = new BlockView(
|
|
274
|
+
this.bbi,
|
|
275
|
+
refsByName,
|
|
276
|
+
rTreeOffset,
|
|
277
|
+
uncompressBufSize,
|
|
278
|
+
blockType,
|
|
279
|
+
)
|
|
280
|
+
this.viewCache.set(key, view)
|
|
281
|
+
}
|
|
282
|
+
return view
|
|
283
|
+
}
|
|
284
|
+
|
|
289
285
|
/*
|
|
290
286
|
* fetches the "unzoomed" view of the bigwig data. this is the default for bigbed
|
|
291
287
|
* @param abortSignal - a signal to optionally abort this operation
|
|
@@ -293,8 +289,7 @@ export abstract class BBI {
|
|
|
293
289
|
protected async getUnzoomedView(opts?: RequestOptions) {
|
|
294
290
|
const { unzoomedIndexOffset, refsByName, uncompressBufSize, fileType } =
|
|
295
291
|
await this.getHeader(opts)
|
|
296
|
-
return
|
|
297
|
-
this.bbi,
|
|
292
|
+
return this.getOrCreateBlockView(
|
|
298
293
|
refsByName,
|
|
299
294
|
unzoomedIndexOffset,
|
|
300
295
|
uncompressBufSize,
|
|
@@ -310,44 +305,10 @@ export abstract class BBI {
|
|
|
310
305
|
opts?: RequestOptions,
|
|
311
306
|
): Promise<BlockView>
|
|
312
307
|
|
|
313
|
-
|
|
314
|
-
* Gets features from a BigWig file
|
|
315
|
-
*
|
|
316
|
-
* @param refName - The chromosome name
|
|
317
|
-
*
|
|
318
|
-
* @param start - The start of a region
|
|
319
|
-
*
|
|
320
|
-
* @param end - The end of a region
|
|
321
|
-
*
|
|
322
|
-
* @param opts - An object containing basesPerSpan (e.g. pixels per basepair)
|
|
323
|
-
* or scale used to infer the zoomLevel to use
|
|
324
|
-
*/
|
|
325
|
-
public async getFeatureStream(
|
|
326
|
-
refName: string,
|
|
327
|
-
start: number,
|
|
328
|
-
end: number,
|
|
329
|
-
opts?: RequestOptions2,
|
|
330
|
-
) {
|
|
331
|
-
await this.getHeader(opts)
|
|
332
|
-
const chrName = this.renameRefSeqs(refName)
|
|
333
|
-
let view: BlockView
|
|
308
|
+
private async _getView(opts?: RequestOptions2) {
|
|
334
309
|
const { basesPerSpan, scale } = opts || {}
|
|
335
|
-
|
|
336
|
-
|
|
337
|
-
view = await this.getView(1 / basesPerSpan, opts)
|
|
338
|
-
} else if (scale) {
|
|
339
|
-
view = await this.getView(scale, opts)
|
|
340
|
-
} else {
|
|
341
|
-
view = await this.getView(1, opts)
|
|
342
|
-
}
|
|
343
|
-
|
|
344
|
-
return new Observable<Feature[]>(observer => {
|
|
345
|
-
view
|
|
346
|
-
.readWigData(chrName, start, end, observer, opts)
|
|
347
|
-
.catch((e: unknown) => {
|
|
348
|
-
observer.error(e)
|
|
349
|
-
})
|
|
350
|
-
})
|
|
310
|
+
const viewScale = basesPerSpan ? 1 / basesPerSpan : (scale ?? 1)
|
|
311
|
+
return this.getView(viewScale, opts)
|
|
351
312
|
}
|
|
352
313
|
|
|
353
314
|
public async getFeatures(
|
|
@@ -356,86 +317,22 @@ export abstract class BBI {
|
|
|
356
317
|
end: number,
|
|
357
318
|
opts?: RequestOptions2,
|
|
358
319
|
) {
|
|
359
|
-
const
|
|
360
|
-
|
|
361
|
-
const arrays = await firstValueFrom(ob.pipe(toArray()))
|
|
362
|
-
const totalLength = arrays.reduce((sum, arr) => sum + arr.length, 0)
|
|
363
|
-
const result = new Array(totalLength)
|
|
364
|
-
let index = 0
|
|
365
|
-
for (const arr of arrays) {
|
|
366
|
-
for (const item of arr) {
|
|
367
|
-
result[index++] = item
|
|
368
|
-
}
|
|
369
|
-
}
|
|
370
|
-
return result
|
|
320
|
+
const view = await this._getView(opts)
|
|
321
|
+
return view.readWigData(this.renameRefSeqs(refName), start, end, opts)
|
|
371
322
|
}
|
|
372
323
|
|
|
373
|
-
/**
|
|
374
|
-
* Gets features from a BigWig file as typed arrays (more efficient than getFeatures)
|
|
375
|
-
*
|
|
376
|
-
* @param refName - The chromosome name
|
|
377
|
-
* @param start - The start of a region
|
|
378
|
-
* @param end - The end of a region
|
|
379
|
-
* @param opts - Options including basesPerSpan or scale
|
|
380
|
-
* @returns Promise with typed arrays: starts, ends, scores (and minScores/maxScores for summary data)
|
|
381
|
-
*/
|
|
382
324
|
public async getFeaturesAsArrays(
|
|
383
325
|
refName: string,
|
|
384
326
|
start: number,
|
|
385
327
|
end: number,
|
|
386
328
|
opts?: RequestOptions2,
|
|
387
329
|
): Promise<BigWigFeatureArrays | SummaryFeatureArrays> {
|
|
388
|
-
const
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
|
|
392
|
-
|
|
393
|
-
|
|
394
|
-
|
|
395
|
-
scores: new Float32Array(0),
|
|
396
|
-
isSummary: false as const,
|
|
397
|
-
}
|
|
398
|
-
}
|
|
399
|
-
|
|
400
|
-
const hasSummary = features[0]?.summary === true
|
|
401
|
-
|
|
402
|
-
if (hasSummary) {
|
|
403
|
-
const starts = new Int32Array(count)
|
|
404
|
-
const ends = new Int32Array(count)
|
|
405
|
-
const scores = new Float32Array(count)
|
|
406
|
-
const minScores = new Float32Array(count)
|
|
407
|
-
const maxScores = new Float32Array(count)
|
|
408
|
-
|
|
409
|
-
for (let i = 0; i < count; i++) {
|
|
410
|
-
const f = features[i]!
|
|
411
|
-
starts[i] = f.start
|
|
412
|
-
ends[i] = f.end
|
|
413
|
-
scores[i] = f.score ?? 0
|
|
414
|
-
minScores[i] = f.minScore ?? 0
|
|
415
|
-
maxScores[i] = f.maxScore ?? 0
|
|
416
|
-
}
|
|
417
|
-
|
|
418
|
-
return {
|
|
419
|
-
starts,
|
|
420
|
-
ends,
|
|
421
|
-
scores,
|
|
422
|
-
minScores,
|
|
423
|
-
maxScores,
|
|
424
|
-
isSummary: true as const,
|
|
425
|
-
}
|
|
426
|
-
}
|
|
427
|
-
|
|
428
|
-
const starts = new Int32Array(count)
|
|
429
|
-
const ends = new Int32Array(count)
|
|
430
|
-
const scores = new Float32Array(count)
|
|
431
|
-
|
|
432
|
-
for (let i = 0; i < count; i++) {
|
|
433
|
-
const f = features[i]!
|
|
434
|
-
starts[i] = f.start
|
|
435
|
-
ends[i] = f.end
|
|
436
|
-
scores[i] = f.score ?? 0
|
|
437
|
-
}
|
|
438
|
-
|
|
439
|
-
return { starts, ends, scores, isSummary: false as const }
|
|
330
|
+
const view = await this._getView(opts)
|
|
331
|
+
return view.readWigDataAsArrays(
|
|
332
|
+
this.renameRefSeqs(refName),
|
|
333
|
+
start,
|
|
334
|
+
end,
|
|
335
|
+
opts,
|
|
336
|
+
)
|
|
440
337
|
}
|
|
441
338
|
}
|
package/src/bigbed.ts
CHANGED
|
@@ -1,11 +1,9 @@
|
|
|
1
1
|
import AbortablePromiseCache from '@gmod/abortable-promise-cache'
|
|
2
2
|
import QuickLRU from '@jbrowse/quick-lru'
|
|
3
|
-
import { Observable, firstValueFrom, merge } from 'rxjs'
|
|
4
|
-
import { map, reduce } from 'rxjs/operators'
|
|
5
3
|
|
|
6
4
|
import { BBI } from './bbi.ts'
|
|
7
5
|
|
|
8
|
-
import type {
|
|
6
|
+
import type { RequestOptions } from './types.ts'
|
|
9
7
|
import type { GenericFilehandle } from 'generic-filehandle2'
|
|
10
8
|
|
|
11
9
|
const decoder = new TextDecoder('utf8')
|
|
@@ -24,10 +22,6 @@ interface Index {
|
|
|
24
22
|
field: number
|
|
25
23
|
}
|
|
26
24
|
|
|
27
|
-
export function filterUndef<T>(ts: (T | undefined)[]): T[] {
|
|
28
|
-
return ts.filter((t: T | undefined): t is T => !!t)
|
|
29
|
-
}
|
|
30
|
-
|
|
31
25
|
function getTabField(str: string, fieldIndex: number) {
|
|
32
26
|
if (fieldIndex < 0) {
|
|
33
27
|
return undefined
|
|
@@ -67,11 +61,9 @@ async function readBPlusTreeNode(
|
|
|
67
61
|
const len = 4 + blockSize * (keySize + valSize)
|
|
68
62
|
const buffer = await bbi.read(len, nodeOffset, opts)
|
|
69
63
|
const dataView = new DataView(buffer.buffer, buffer.byteOffset, buffer.length)
|
|
70
|
-
|
|
71
|
-
const
|
|
72
|
-
offset
|
|
73
|
-
const cnt = dataView.getInt16(offset, true)
|
|
74
|
-
offset += 2
|
|
64
|
+
const nodeType = dataView.getInt8(0)
|
|
65
|
+
const cnt = dataView.getInt16(2, true)
|
|
66
|
+
let offset = 4
|
|
75
67
|
|
|
76
68
|
// Non-leaf node (nodeType === 0): contains keys and child node pointers for navigation
|
|
77
69
|
if (nodeType === 0) {
|
|
@@ -153,6 +145,7 @@ async function readBPlusTreeNode(
|
|
|
153
145
|
|
|
154
146
|
return undefined
|
|
155
147
|
}
|
|
148
|
+
return undefined
|
|
156
149
|
}
|
|
157
150
|
|
|
158
151
|
export class BigBed extends BBI {
|
|
@@ -186,13 +179,8 @@ export class BigBed extends BBI {
|
|
|
186
179
|
const b = await this.bbi.read(64, extHeaderOffset)
|
|
187
180
|
|
|
188
181
|
const dataView = new DataView(b.buffer, b.byteOffset, b.length)
|
|
189
|
-
|
|
190
|
-
|
|
191
|
-
offset += 2
|
|
192
|
-
const count = dataView.getUint16(offset, true)
|
|
193
|
-
offset += 2
|
|
194
|
-
const dataOffset = Number(dataView.getBigUint64(offset, true))
|
|
195
|
-
offset += 8
|
|
182
|
+
const count = dataView.getUint16(2, true)
|
|
183
|
+
const dataOffset = Number(dataView.getBigUint64(4, true))
|
|
196
184
|
|
|
197
185
|
// no extra index is defined if count==0
|
|
198
186
|
if (count === 0) {
|
|
@@ -208,14 +196,10 @@ export class BigBed extends BBI {
|
|
|
208
196
|
for (let i = 0; i < count; i += 1) {
|
|
209
197
|
const b = buffer.subarray(i * blocklen)
|
|
210
198
|
const dataView = new DataView(b.buffer, b.byteOffset, b.length)
|
|
211
|
-
|
|
212
|
-
const
|
|
213
|
-
|
|
214
|
-
const
|
|
215
|
-
offset += 2
|
|
216
|
-
const dataOffset = Number(dataView.getBigUint64(offset, true))
|
|
217
|
-
offset += 8 + 4 // skip 8-byte offset + 4 reserved bytes
|
|
218
|
-
const field = dataView.getInt16(offset, true)
|
|
199
|
+
const type = dataView.getInt16(0, true)
|
|
200
|
+
const fieldcount = dataView.getInt16(2, true)
|
|
201
|
+
const dataOffset = Number(dataView.getBigUint64(4, true))
|
|
202
|
+
const field = dataView.getInt16(16, true)
|
|
219
203
|
indices.push({
|
|
220
204
|
type,
|
|
221
205
|
fieldcount,
|
|
@@ -249,17 +233,9 @@ export class BigBed extends BBI {
|
|
|
249
233
|
const b = await this.bbi.read(32, offset2, opts)
|
|
250
234
|
|
|
251
235
|
const dataView = new DataView(b.buffer, b.byteOffset, b.length)
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
const blockSize = dataView.getInt32(offset, true)
|
|
256
|
-
offset += 4
|
|
257
|
-
const keySize = dataView.getInt32(offset, true)
|
|
258
|
-
offset += 4
|
|
259
|
-
const valSize = dataView.getInt32(offset, true)
|
|
260
|
-
offset += 4
|
|
261
|
-
// const _itemCount = Number(dataView.getBigUint64(offset, true))
|
|
262
|
-
offset += 8
|
|
236
|
+
const blockSize = dataView.getInt32(4, true)
|
|
237
|
+
const keySize = dataView.getInt32(8, true)
|
|
238
|
+
const valSize = dataView.getInt32(12, true)
|
|
263
239
|
|
|
264
240
|
return readBPlusTreeNode(
|
|
265
241
|
this.bbi,
|
|
@@ -272,7 +248,8 @@ export class BigBed extends BBI {
|
|
|
272
248
|
opts,
|
|
273
249
|
)
|
|
274
250
|
})
|
|
275
|
-
|
|
251
|
+
const results = await Promise.all(locs)
|
|
252
|
+
return results.filter((l): l is Loc => l !== undefined)
|
|
276
253
|
}
|
|
277
254
|
|
|
278
255
|
/*
|
|
@@ -292,23 +269,14 @@ export class BigBed extends BBI {
|
|
|
292
269
|
return []
|
|
293
270
|
}
|
|
294
271
|
const view = await this.getUnzoomedView(opts)
|
|
295
|
-
const
|
|
296
|
-
|
|
297
|
-
view.readFeatures(
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
reduce((acc, curr) => {
|
|
302
|
-
acc.push(...curr)
|
|
303
|
-
return acc
|
|
304
|
-
}, [] as Feature[]),
|
|
305
|
-
map(features => features.map(f => ({ ...f, field: block.field }))),
|
|
306
|
-
)
|
|
307
|
-
})
|
|
308
|
-
const ret = await firstValueFrom(merge(...res))
|
|
309
|
-
// Filter to features where the indexed field matches the search name
|
|
272
|
+
const results = await Promise.all(
|
|
273
|
+
blocks.map(async block => {
|
|
274
|
+
const features = await view.readFeatures([block], opts)
|
|
275
|
+
return features.map(f => ({ ...f, field: block.field }))
|
|
276
|
+
}),
|
|
277
|
+
)
|
|
310
278
|
// field offset is adjusted by -3 to account for chrom, chromStart, chromEnd columns
|
|
311
|
-
return
|
|
279
|
+
return results.flat().filter(f => {
|
|
312
280
|
if (!f.rest) {
|
|
313
281
|
return false
|
|
314
282
|
}
|
package/src/bigwig.ts
CHANGED
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
import { BBI } from './bbi.ts'
|
|
2
|
-
import { BlockView } from './block-view.ts'
|
|
3
2
|
|
|
4
3
|
import type { RequestOptions } from './types.ts'
|
|
5
4
|
|
|
@@ -21,8 +20,7 @@ export class BigWig extends BBI {
|
|
|
21
20
|
for (let i = maxLevel; i >= 0; i -= 1) {
|
|
22
21
|
const zh = zoomLevels[i]
|
|
23
22
|
if (zh && zh.reductionLevel <= 2 * basesPerPx) {
|
|
24
|
-
return
|
|
25
|
-
this.bbi,
|
|
23
|
+
return this.getOrCreateBlockView(
|
|
26
24
|
refsByName,
|
|
27
25
|
zh.indexOffset,
|
|
28
26
|
uncompressBufSize,
|