igv 2.12.0 → 2.12.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.
- package/README.md +10 -10
- package/dist/igv.esm.js +124 -75
- package/dist/igv.esm.min.js +9 -9
- package/dist/igv.esm.min.js.map +1 -1
- package/dist/igv.js +129 -70
- package/dist/igv.min.js +7 -7
- package/dist/igv.min.js.map +1 -1
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -12,19 +12,19 @@ Below are examples and a quickstart guide. See the [Wiki](https://github.com/ig
|
|
|
12
12
|
|
|
13
13
|
# Examples
|
|
14
14
|
|
|
15
|
-
***[Alignments](https://igv.org/web/release/2.12.
|
|
15
|
+
***[Alignments](https://igv.org/web/release/2.12.1/examples/cram-vcf.html)***
|
|
16
16
|
|
|
17
|
-
***[Interactions](https://igv.org/web/release/2.12.
|
|
17
|
+
***[Interactions](https://igv.org/web/release/2.12.1/examples/interact.html)***
|
|
18
18
|
|
|
19
|
-
***[Copy number](https://igv.org/web/release/2.12.
|
|
19
|
+
***[Copy number](https://igv.org/web/release/2.12.1/examples/copyNumber.html)***
|
|
20
20
|
|
|
21
|
-
***[Multiple regions](https://igv.org/web/release/2.12.
|
|
21
|
+
***[Multiple regions](https://igv.org/web/release/2.12.1/examples/multi-locus.html)***
|
|
22
22
|
|
|
23
|
-
***[Mutation Annotation Format (MAF)](https://igv.org/web/release/2.12.
|
|
23
|
+
***[Mutation Annotation Format (MAF)](https://igv.org/web/release/2.12.1/examples/maf-tcga.html)***
|
|
24
24
|
|
|
25
|
-
***[Variant color options](https://igv.org/web/release/2.12.
|
|
25
|
+
***[Variant color options](https://igv.org/web/release/2.12.1/examples/variant-colors.html)***
|
|
26
26
|
|
|
27
|
-
***[More](https://igv.org/web/release/2.12.
|
|
27
|
+
***[More](https://igv.org/web/release/2.12.1/examples/)***
|
|
28
28
|
|
|
29
29
|
|
|
30
30
|
# Quickstart
|
|
@@ -33,18 +33,18 @@ Below are examples and a quickstart guide. See the [Wiki](https://github.com/ig
|
|
|
33
33
|
igv.js consists of a single javascript file with no external dependencies.
|
|
34
34
|
|
|
35
35
|
Pre-built files for ES5 (igv.min.js) and ES6 (igv.esm.min.js)
|
|
36
|
-
can be downloaded from [https://cdn.jsdelivr.net/npm/igv@2.12.
|
|
36
|
+
can be downloaded from [https://cdn.jsdelivr.net/npm/igv@2.12.1/dist/](https://cdn.jsdelivr.net/npm/igv@2.12.1/dist/).
|
|
37
37
|
|
|
38
38
|
To import igv as an ES6 module
|
|
39
39
|
|
|
40
40
|
```javascript
|
|
41
|
-
import igv from "https://cdn.jsdelivr.net/npm/igv@2.12.
|
|
41
|
+
import igv from "https://cdn.jsdelivr.net/npm/igv@2.12.1/dist/igv.esm.min.js"
|
|
42
42
|
```
|
|
43
43
|
|
|
44
44
|
Or as a script include (defines the "igv" global)
|
|
45
45
|
|
|
46
46
|
```html
|
|
47
|
-
<script src="https://cdn.jsdelivr.net/npm/igv@2.12.
|
|
47
|
+
<script src="https://cdn.jsdelivr.net/npm/igv@2.12.1/dist/igv.min.js"></script>
|
|
48
48
|
```
|
|
49
49
|
|
|
50
50
|
Alternatively you can install with npm
|
package/dist/igv.esm.js
CHANGED
|
@@ -19712,6 +19712,8 @@ const knownFileExtensions = new Set([
|
|
|
19712
19712
|
"bb",
|
|
19713
19713
|
"bigbed",
|
|
19714
19714
|
"biginteract",
|
|
19715
|
+
"biggenepred",
|
|
19716
|
+
"bignarrowpeak",
|
|
19715
19717
|
"bw",
|
|
19716
19718
|
"bigwig",
|
|
19717
19719
|
"bam",
|
|
@@ -19863,6 +19865,8 @@ function inferTrackType(config) {
|
|
|
19863
19865
|
case "bed":
|
|
19864
19866
|
case "bigbed":
|
|
19865
19867
|
case "bb":
|
|
19868
|
+
case "biggenepred":
|
|
19869
|
+
case "bignarrowpeak":
|
|
19866
19870
|
return "bedtype"
|
|
19867
19871
|
default:
|
|
19868
19872
|
return "annotation"
|
|
@@ -22792,7 +22796,7 @@ const Cytoband = function (start, end, name, typestain) {
|
|
|
22792
22796
|
}
|
|
22793
22797
|
};
|
|
22794
22798
|
|
|
22795
|
-
const _version = "2.12.
|
|
22799
|
+
const _version = "2.12.1";
|
|
22796
22800
|
function version() {
|
|
22797
22801
|
return _version
|
|
22798
22802
|
}
|
|
@@ -22940,7 +22944,7 @@ class Genome {
|
|
|
22940
22944
|
constructor(config, sequence, ideograms, aliases) {
|
|
22941
22945
|
|
|
22942
22946
|
this.config = config;
|
|
22943
|
-
this.id = config.id;
|
|
22947
|
+
this.id = config.id || generateGenomeID(config);
|
|
22944
22948
|
this.sequence = sequence;
|
|
22945
22949
|
this.chromosomeNames = sequence.chromosomeNames;
|
|
22946
22950
|
this.chromosomes = sequence.chromosomes; // An object (functions as a dictionary)
|
|
@@ -23262,6 +23266,18 @@ function constructWG(genome, config) {
|
|
|
23262
23266
|
|
|
23263
23267
|
}
|
|
23264
23268
|
|
|
23269
|
+
function generateGenomeID(config) {
|
|
23270
|
+
if (config.id !== undefined) {
|
|
23271
|
+
return config.id
|
|
23272
|
+
} else if (config.fastaURL && isString$3(config.fastaURL)) {
|
|
23273
|
+
return config.fastaURL
|
|
23274
|
+
} else if (config.fastaURL && config.fastaURL.name) {
|
|
23275
|
+
return config.fastaURL.name
|
|
23276
|
+
} else {
|
|
23277
|
+
return ("0000" + (Math.random() * Math.pow(36, 4) << 0).toString(36)).slice(-4)
|
|
23278
|
+
}
|
|
23279
|
+
}
|
|
23280
|
+
|
|
23265
23281
|
/**
|
|
23266
23282
|
* Created by dat on 9/16/16.
|
|
23267
23283
|
*/
|
|
@@ -23847,7 +23863,7 @@ class TrackViewport extends Viewport {
|
|
|
23847
23863
|
|
|
23848
23864
|
viewport.addEventListener('click', (event) => {
|
|
23849
23865
|
|
|
23850
|
-
if (this.enableClick) {
|
|
23866
|
+
if (this.enableClick && this.canvas) {
|
|
23851
23867
|
if (3 === event.which || event.ctrlKey) {
|
|
23852
23868
|
return
|
|
23853
23869
|
}
|
|
@@ -29004,6 +29020,10 @@ class BamSource {
|
|
|
29004
29020
|
* THE SOFTWARE.
|
|
29005
29021
|
*/
|
|
29006
29022
|
|
|
29023
|
+
const fixColor = (colorString) => {
|
|
29024
|
+
return (colorString.indexOf(",") > 0 && !colorString.startsWith("rgb")) ?
|
|
29025
|
+
`rgb(${colorString})` : colorString
|
|
29026
|
+
};
|
|
29007
29027
|
|
|
29008
29028
|
/**
|
|
29009
29029
|
* A collection of properties and methods shared by all (or most) track types.
|
|
@@ -29048,8 +29068,8 @@ class TrackBase {
|
|
|
29048
29068
|
|
|
29049
29069
|
this.order = config.order;
|
|
29050
29070
|
|
|
29051
|
-
this.color = config.color;
|
|
29052
|
-
this.altColor = config.altColor;
|
|
29071
|
+
if(config.color) this.color = fixColor(config.color);
|
|
29072
|
+
if(config.altColor) this.altColor = fixColor(config.altColor);
|
|
29053
29073
|
if ("civic-ws" === config.sourceType) { // Ugly proxy for specialized track type
|
|
29054
29074
|
this.defaultColor = "rgb(155,20,20)";
|
|
29055
29075
|
} else {
|
|
@@ -30944,7 +30964,7 @@ class ChordSetManager {
|
|
|
30944
30964
|
return this.tracks.find(t => name === t.name)
|
|
30945
30965
|
}
|
|
30946
30966
|
|
|
30947
|
-
|
|
30967
|
+
getChordSet(name) {
|
|
30948
30968
|
return this.chordSets.find(cs => name === cs.name)
|
|
30949
30969
|
}
|
|
30950
30970
|
|
|
@@ -31062,9 +31082,8 @@ class CircularView {
|
|
|
31062
31082
|
buttonContainer.appendChild(this.showControlsButton);
|
|
31063
31083
|
this.showControlsButton.innerText = 'none' === this.controlPanel.style.display ? 'Show Controls' : 'Hide Controls';
|
|
31064
31084
|
this.showControlsButton.addEventListener('click', (event) => {
|
|
31065
|
-
const
|
|
31066
|
-
if (
|
|
31067
|
-
|
|
31085
|
+
const panelRows = this.controlPanel.querySelectorAll('div');
|
|
31086
|
+
if (panelRows.length > 0) {
|
|
31068
31087
|
if ('none' === this.controlPanel.style.display) {
|
|
31069
31088
|
this.controlPanel.style.display = 'flex';
|
|
31070
31089
|
event.target.innerText = 'Hide Controls';
|
|
@@ -31148,10 +31167,10 @@ class CircularView {
|
|
|
31148
31167
|
hideShowButton.innerText = true === chordSet.visible ? 'Hide' : 'Show';
|
|
31149
31168
|
hideShowButton.addEventListener('click', event => {
|
|
31150
31169
|
if (true === chordSet.visible) {
|
|
31151
|
-
this.
|
|
31170
|
+
this.hideChordSet(chordSet.name);
|
|
31152
31171
|
event.target.innerText = "Show";
|
|
31153
31172
|
} else {
|
|
31154
|
-
this.
|
|
31173
|
+
this.showChordSet(chordSet.name);
|
|
31155
31174
|
event.target.innerText = "Hide";
|
|
31156
31175
|
}
|
|
31157
31176
|
});
|
|
@@ -31175,7 +31194,7 @@ class CircularView {
|
|
|
31175
31194
|
color: chordSet.color,
|
|
31176
31195
|
onChange: ({rgbaString}) => {
|
|
31177
31196
|
colorPickerButton.style.backgroundColor = setAlpha(rgbaString, 1);
|
|
31178
|
-
this.
|
|
31197
|
+
this.setColor(chordSet.name, rgbaString);
|
|
31179
31198
|
alphaSlider.value = alphaToValue(getAlpha(chordSet.color));
|
|
31180
31199
|
}
|
|
31181
31200
|
};
|
|
@@ -31193,7 +31212,7 @@ class CircularView {
|
|
|
31193
31212
|
alphaSlider.value = alphaToValue(getAlpha(chordSet.color));
|
|
31194
31213
|
alphaSlider.oninput = () => {
|
|
31195
31214
|
const v = valueToAlpha(alphaSlider.value);
|
|
31196
|
-
this.
|
|
31215
|
+
this.setColor(chordSet.name, setAlpha(chordSet.color, v));
|
|
31197
31216
|
picker.setColor(chordSet.color);
|
|
31198
31217
|
};
|
|
31199
31218
|
row.appendChild(alphaSlider);
|
|
@@ -31213,11 +31232,13 @@ class CircularView {
|
|
|
31213
31232
|
*/
|
|
31214
31233
|
setAssembly(igvGenome) {
|
|
31215
31234
|
|
|
31216
|
-
|
|
31235
|
+
const id = this.genomeId || guid();
|
|
31236
|
+
|
|
31237
|
+
if (this.genomeId === id) {
|
|
31217
31238
|
return
|
|
31218
31239
|
}
|
|
31219
31240
|
this.chordManager.clearChords();
|
|
31220
|
-
this.genomeId =
|
|
31241
|
+
this.genomeId = id;
|
|
31221
31242
|
this.chrNames = new Set(igvGenome.chromosomes.map(chr => shortChrName$1(chr.name)));
|
|
31222
31243
|
|
|
31223
31244
|
const regions = [];
|
|
@@ -31238,7 +31259,7 @@ class CircularView {
|
|
|
31238
31259
|
this.assembly = {
|
|
31239
31260
|
name: igvGenome.name,
|
|
31240
31261
|
sequence: {
|
|
31241
|
-
trackId:
|
|
31262
|
+
trackId: id,
|
|
31242
31263
|
type: 'ReferenceSequenceTrack',
|
|
31243
31264
|
adapter: {
|
|
31244
31265
|
type: 'FromConfigSequenceAdapter',
|
|
@@ -31279,7 +31300,7 @@ class CircularView {
|
|
|
31279
31300
|
|
|
31280
31301
|
addChords(newChords, options = {}) {
|
|
31281
31302
|
|
|
31282
|
-
const tmp = options.
|
|
31303
|
+
const tmp = options.name || options.track || "*";
|
|
31283
31304
|
const trackName = tmp.split(' ')[0].replaceAll("%20", " ");
|
|
31284
31305
|
const chordSetName = tmp.replaceAll("%20", " ");
|
|
31285
31306
|
|
|
@@ -31332,21 +31353,6 @@ class CircularView {
|
|
|
31332
31353
|
this.viewState.pluginManager.rootModel.session.clearSelection();
|
|
31333
31354
|
}
|
|
31334
31355
|
|
|
31335
|
-
getFeature(featureId) {
|
|
31336
|
-
|
|
31337
|
-
// TODO -- broken
|
|
31338
|
-
// const display = this.viewState.pluginManager.rootModel.session.view.tracks[0].displays[0]
|
|
31339
|
-
// const feature = display.data.features.get(featureId)
|
|
31340
|
-
// return feature;
|
|
31341
|
-
|
|
31342
|
-
const features = [...this.viewState.config.tracks[0].adapter.features.value];
|
|
31343
|
-
for (let f of features) {
|
|
31344
|
-
if (featureId === f.uniqueId) {
|
|
31345
|
-
return f
|
|
31346
|
-
}
|
|
31347
|
-
}
|
|
31348
|
-
}
|
|
31349
|
-
|
|
31350
31356
|
/**
|
|
31351
31357
|
* Deprecated, use "visible" property
|
|
31352
31358
|
*/
|
|
@@ -31369,23 +31375,23 @@ class CircularView {
|
|
|
31369
31375
|
this.parent.style.display = isVisible ? 'block' : 'none';
|
|
31370
31376
|
}
|
|
31371
31377
|
|
|
31372
|
-
|
|
31373
|
-
let
|
|
31374
|
-
if (
|
|
31375
|
-
|
|
31378
|
+
hideChordSet(trackName) {
|
|
31379
|
+
let cs = this.getChordSet(trackName);
|
|
31380
|
+
if (cs) {
|
|
31381
|
+
cs.visible = false;
|
|
31376
31382
|
this.render();
|
|
31377
31383
|
} else {
|
|
31378
31384
|
console.warn(`No track with name: ${name}`);
|
|
31379
31385
|
}
|
|
31380
31386
|
}
|
|
31381
31387
|
|
|
31382
|
-
|
|
31383
|
-
let
|
|
31384
|
-
if (
|
|
31385
|
-
|
|
31388
|
+
showChordSet(name) {
|
|
31389
|
+
let cs = this.getChordSet(name);
|
|
31390
|
+
if (cs) {
|
|
31391
|
+
cs.visible = true;
|
|
31386
31392
|
this.render();
|
|
31387
31393
|
} else {
|
|
31388
|
-
console.warn(`No track with name: ${
|
|
31394
|
+
console.warn(`No track with name: ${name}`);
|
|
31389
31395
|
}
|
|
31390
31396
|
}
|
|
31391
31397
|
|
|
@@ -31411,12 +31417,12 @@ class CircularView {
|
|
|
31411
31417
|
this.render();
|
|
31412
31418
|
}
|
|
31413
31419
|
|
|
31414
|
-
|
|
31415
|
-
return this.groupByTrack ? this.chordManager.getTrack(name) : this.chordManager.
|
|
31420
|
+
getChordSet(name) {
|
|
31421
|
+
return this.groupByTrack ? this.chordManager.getTrack(name) : this.chordManager.getChordSet(name)
|
|
31416
31422
|
}
|
|
31417
31423
|
|
|
31418
|
-
|
|
31419
|
-
const t = this.
|
|
31424
|
+
setColor(name, color) {
|
|
31425
|
+
const t = this.getChordSet(name);
|
|
31420
31426
|
if (t) {
|
|
31421
31427
|
t.color = color;
|
|
31422
31428
|
const trackID = t.id;
|
|
@@ -31443,8 +31449,6 @@ class CircularView {
|
|
|
31443
31449
|
// Remove all children from possible previous renders. React might do this for us when we render, but just in case.
|
|
31444
31450
|
ReactDOM.unmountComponentAtNode(this.container);
|
|
31445
31451
|
|
|
31446
|
-
|
|
31447
|
-
|
|
31448
31452
|
const visibleChordSets =
|
|
31449
31453
|
(this.groupByTrack ? this.chordManager.tracks : this.chordManager.chordSets).filter(t => t.visible);
|
|
31450
31454
|
|
|
@@ -31523,7 +31527,7 @@ function guid() {
|
|
|
31523
31527
|
|
|
31524
31528
|
function embedCSS$1() {
|
|
31525
31529
|
|
|
31526
|
-
const css = '.igv-circview-container {\n z-index: 2048;\n
|
|
31530
|
+
const css = '.igv-circview-container {\n z-index: 2048;\n width: fit-content;\n height: fit-content;\n box-sizing: content-box;\n color: dimgray;\n font-family: \"Open Sans\", sans-serif;\n font-size: 12px;\n background-color: white;\n border-color: dimgray;\n border-style: solid;\n border-width: thin;\n display: flex;\n flex-direction: column;\n flex-wrap: nowrap;\n justify-content: flex-start;\n align-items: flex-start;\n}\n\n.igv-circview-toolbar {\n position: relative;\n width: 100%;\n height: 32px;\n background-color: lightgrey;\n border-bottom-style: solid;\n border-bottom-color: dimgray;\n border-bottom-width: thin;\n display: flex;\n flex-flow: row;\n flex-wrap: nowrap;\n justify-content: space-between;\n align-items: center;\n}\n\n.igv-circview-toolbar-button-container {\n height: 100%;\n width: fit-content;\n display: flex;\n flex-flow: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n align-items: center;\n}\n.igv-circview-toolbar-button-container > div {\n margin: 4px;\n}\n\n.igv-circview-track-panel {\n z-index: 1024;\n position: absolute;\n top: 33px;\n left: 0;\n width: 100%;\n height: fit-content;\n border-bottom-style: solid;\n border-bottom-color: dimgray;\n border-bottom-width: thin;\n background-color: white;\n display: flex;\n flex-flow: column;\n flex-wrap: nowrap;\n justify-content: flex-start;\n align-items: flex-start;\n}\n.igv-circview-track-panel > div {\n display: flex;\n flex-flow: row;\n flex-wrap: nowrap;\n justify-content: flex-start;\n align-items: center;\n}\n.igv-circview-track-panel > div > div {\n margin: 4px;\n}\n\n.igv-circview-swatch-button {\n cursor: pointer;\n padding: 5px;\n width: 8px;\n height: 8px;\n border: 1px solid #8d8b8b;\n border-radius: 16px;\n}\n\n.igv-circview-button {\n cursor: pointer;\n padding: 5px;\n color: #444;\n vertical-align: middle;\n text-align: center;\n font-family: \"Open Sans\", sans-serif;\n font-size: 12px;\n border: 1px solid #8d8b8b;\n border-radius: 4px;\n background: #efefef;\n box-shadow: 0 0 5px -1px rgba(0, 0, 0, 0.2);\n}\n\n.igv-circview-button:hover {\n background: #efefef;\n box-shadow: 0 0 5px -1px rgba(0, 0, 0, 0.6);\n}\n\n.igv-circview-button:active {\n color: #007bff;\n box-shadow: 0 0 5px -1px rgba(0, 0, 0, 0.6);\n}\n\n/*# sourceMappingURL=circular-view.css.map */\n';
|
|
31527
31531
|
|
|
31528
31532
|
const style = document.createElement('style');
|
|
31529
31533
|
style.setAttribute('type', 'text/css');
|
|
@@ -33181,10 +33185,13 @@ class AlignmentTrack {
|
|
|
33181
33185
|
case "pairOrientation":
|
|
33182
33186
|
|
|
33183
33187
|
if (this.pairOrientation && alignment.pairOrientation) {
|
|
33184
|
-
|
|
33188
|
+
const oTypes = orientationTypes[this.pairOrientation];
|
|
33185
33189
|
if (oTypes) {
|
|
33186
|
-
|
|
33187
|
-
if (pairColor)
|
|
33190
|
+
const pairColor = this.pairColors[oTypes[alignment.pairOrientation]];
|
|
33191
|
+
if (pairColor) {
|
|
33192
|
+
color = pairColor;
|
|
33193
|
+
break
|
|
33194
|
+
}
|
|
33188
33195
|
}
|
|
33189
33196
|
}
|
|
33190
33197
|
if ("pairOrientation" === option) {
|
|
@@ -35793,7 +35800,7 @@ function decodeBed(tokens, header) {
|
|
|
35793
35800
|
const eEnd = eStart + parseInt(exonSizes[i]);
|
|
35794
35801
|
exons.push({start: eStart, end: eEnd});
|
|
35795
35802
|
}
|
|
35796
|
-
findUTRs(exons, feature.cdStart, feature.cdEnd);
|
|
35803
|
+
findUTRs$1(exons, feature.cdStart, feature.cdEnd);
|
|
35797
35804
|
feature.exons = exons;
|
|
35798
35805
|
}
|
|
35799
35806
|
|
|
@@ -35901,7 +35908,7 @@ function decodeGenePred(tokens, header) {
|
|
|
35901
35908
|
const end = parseInt(exonEnds[i]);
|
|
35902
35909
|
exons.push({start: start, end: end});
|
|
35903
35910
|
}
|
|
35904
|
-
findUTRs(exons, cdStart, cdEnd);
|
|
35911
|
+
findUTRs$1(exons, cdStart, cdEnd);
|
|
35905
35912
|
|
|
35906
35913
|
feature.exons = exons;
|
|
35907
35914
|
|
|
@@ -35944,7 +35951,7 @@ function decodeGenePredExt(tokens, header) {
|
|
|
35944
35951
|
const end = parseInt(exonEnds[i]);
|
|
35945
35952
|
exons.push({start: start, end: end});
|
|
35946
35953
|
}
|
|
35947
|
-
findUTRs(exons, cdStart, cdEnd);
|
|
35954
|
+
findUTRs$1(exons, cdStart, cdEnd);
|
|
35948
35955
|
|
|
35949
35956
|
feature.exons = exons;
|
|
35950
35957
|
|
|
@@ -35985,14 +35992,14 @@ function decodeReflat(tokens, header) {
|
|
|
35985
35992
|
const end = parseInt(exonEnds[i]);
|
|
35986
35993
|
exons.push({start: start, end: end});
|
|
35987
35994
|
}
|
|
35988
|
-
findUTRs(exons, cdStart, cdEnd);
|
|
35995
|
+
findUTRs$1(exons, cdStart, cdEnd);
|
|
35989
35996
|
|
|
35990
35997
|
feature.exons = exons;
|
|
35991
35998
|
|
|
35992
35999
|
return feature
|
|
35993
36000
|
}
|
|
35994
36001
|
|
|
35995
|
-
function findUTRs(exons, cdStart, cdEnd) {
|
|
36002
|
+
function findUTRs$1(exons, cdStart, cdEnd) {
|
|
35996
36003
|
|
|
35997
36004
|
for (let exon of exons) {
|
|
35998
36005
|
const end = exon.end;
|
|
@@ -39508,7 +39515,7 @@ class TextFeatureSource {
|
|
|
39508
39515
|
this.sourceType = (config.sourceType === undefined ? "file" : config.sourceType);
|
|
39509
39516
|
this.maxWGCount = config.maxWGCount || DEFAULT_MAX_WG_COUNT;
|
|
39510
39517
|
|
|
39511
|
-
const queryableFormats = new Set(["bigwig", "bw", "bigbed", "bb", "biginteract", "tdf"]);
|
|
39518
|
+
const queryableFormats = new Set(["bigwig", "bw", "bigbed", "bb", "biginteract", "biggenepred", "bignarrowpeak", "tdf"]);
|
|
39512
39519
|
|
|
39513
39520
|
if (config.features && Array.isArray(config.features)) {
|
|
39514
39521
|
// Explicit array of features
|
|
@@ -39928,11 +39935,9 @@ class BufferedReader {
|
|
|
39928
39935
|
}
|
|
39929
39936
|
}
|
|
39930
39937
|
|
|
39931
|
-
//table chromatinInteract
|
|
39932
|
-
|
|
39933
39938
|
function getDecoder(definedFieldCount, fieldCount, autoSql, format) {
|
|
39934
39939
|
|
|
39935
|
-
if (autoSql && 'chromatinInteract' === autoSql.table ||
|
|
39940
|
+
if ("biginteract" === format || (autoSql && ('chromatinInteract' === autoSql.table) || 'interact' === autoSql.table)) {
|
|
39936
39941
|
return decodeInteract
|
|
39937
39942
|
} else {
|
|
39938
39943
|
const standardFieldCount = definedFieldCount - 3;
|
|
@@ -39969,6 +39974,7 @@ function getDecoder(definedFieldCount, fieldCount, autoSql, format) {
|
|
|
39969
39974
|
const eEnd = eStart + parseInt(exonSizes[i]);
|
|
39970
39975
|
exons.push({start: eStart, end: eEnd});
|
|
39971
39976
|
}
|
|
39977
|
+
findUTRs(exons, feature.cdStart, feature.cdEnd);
|
|
39972
39978
|
feature.exons = exons;
|
|
39973
39979
|
}
|
|
39974
39980
|
|
|
@@ -39986,6 +39992,28 @@ function getDecoder(definedFieldCount, fieldCount, autoSql, format) {
|
|
|
39986
39992
|
}
|
|
39987
39993
|
}
|
|
39988
39994
|
|
|
39995
|
+
//table chromatinInteract
|
|
39996
|
+
// "Chromatin interaction between two regions"
|
|
39997
|
+
// (
|
|
39998
|
+
// string chrom; "Chromosome (or contig, scaffold, etc.). For interchromosomal, use 2 records"
|
|
39999
|
+
// uint chromStart; "Start position of lower region. For interchromosomal, set to chromStart of this region"
|
|
40000
|
+
// uint chromEnd; "End position of upper region. For interchromosomal, set to chromEnd of this region"
|
|
40001
|
+
// string name; "Name of item, for display"
|
|
40002
|
+
// uint score; "Score from 0-1000"
|
|
40003
|
+
// double value; "Strength of interaction or other data value. Typically basis for score"
|
|
40004
|
+
// string exp; "Experiment name (metadata for filtering). Use . if not applicable"
|
|
40005
|
+
// string color; "Item color. Specified as r,g,b or hexadecimal #RRGGBB or html color name, as in //www.w3.org/TR/css3-color/#html4."
|
|
40006
|
+
// string region1Chrom; "Chromosome of lower region. For non-directional interchromosomal, chrom of this region."
|
|
40007
|
+
// uint region1Start; "Start position of lower/this region"
|
|
40008
|
+
// uint region1End; "End position in chromosome of lower/this region"
|
|
40009
|
+
// string region1Name; "Identifier of lower/this region"
|
|
40010
|
+
// string region1Strand; "Orientation of lower/this region: + or -. Use . if not applicable"
|
|
40011
|
+
// string region2Chrom; "Chromosome of upper region. For non-directional interchromosomal, chrom of other region"
|
|
40012
|
+
// uint region2Start; "Start position in chromosome of upper/this region"
|
|
40013
|
+
// uint region2End; "End position in chromosome of upper/this region"
|
|
40014
|
+
// string region2Name; "Identifier of upper/this region"
|
|
40015
|
+
// string region2Strand; "Orientation of upper/this region: + or -. Use . if not applicable"
|
|
40016
|
+
// )
|
|
39989
40017
|
function decodeInteract(feature, tokens) {
|
|
39990
40018
|
|
|
39991
40019
|
feature.chr1 = tokens[5];
|
|
@@ -40005,6 +40033,24 @@ function getDecoder(definedFieldCount, fieldCount, autoSql, format) {
|
|
|
40005
40033
|
}
|
|
40006
40034
|
}
|
|
40007
40035
|
|
|
40036
|
+
function findUTRs(exons, cdStart, cdEnd) {
|
|
40037
|
+
|
|
40038
|
+
for (let exon of exons) {
|
|
40039
|
+
const end = exon.end;
|
|
40040
|
+
const start = exon.start;
|
|
40041
|
+
if (end < cdStart || start > cdEnd) {
|
|
40042
|
+
exon.utr = true;
|
|
40043
|
+
} else {
|
|
40044
|
+
if (cdStart >= start && cdStart <= end) {
|
|
40045
|
+
exon.cdStart = cdStart;
|
|
40046
|
+
}
|
|
40047
|
+
if (cdEnd >= start && cdEnd <= end) {
|
|
40048
|
+
exon.cdEnd = cdEnd;
|
|
40049
|
+
}
|
|
40050
|
+
}
|
|
40051
|
+
}
|
|
40052
|
+
}
|
|
40053
|
+
|
|
40008
40054
|
function scoreShade(score, color) {
|
|
40009
40055
|
const alpha = Math.min(1, 0.11 + 0.89 * (score / 779));
|
|
40010
40056
|
return alpha.toString()
|
|
@@ -41544,11 +41590,12 @@ function zoomLevelForScale(chr, bpPerPixel, genome) {
|
|
|
41544
41590
|
* THE SOFTWARE.
|
|
41545
41591
|
*/
|
|
41546
41592
|
|
|
41593
|
+
const bbFormats = new Set(['bigwig', 'bw', 'bigbed', 'bb', 'biginteract', 'biggenepred', 'bignarrowpeak']);
|
|
41547
41594
|
|
|
41548
41595
|
function FeatureSource(config, genome) {
|
|
41549
41596
|
|
|
41550
41597
|
const format = config.format ? config.format.toLowerCase() : undefined;
|
|
41551
|
-
if (
|
|
41598
|
+
if (bbFormats.has(format)) {
|
|
41552
41599
|
return new BWSource(config, genome)
|
|
41553
41600
|
} else if ("tdf" === format) {
|
|
41554
41601
|
return new TDFSource(config, genome)
|
|
@@ -41796,10 +41843,9 @@ function renderFeatureLabel(ctx, feature, featureX, featureX1, featureY, referen
|
|
|
41796
41843
|
const textBox = ctx.measureText(name);
|
|
41797
41844
|
const xleft = centerX - textBox.width / 2;
|
|
41798
41845
|
const xright = centerX + textBox.width / 2;
|
|
41799
|
-
if (options.labelAllFeatures || xleft > options.
|
|
41800
|
-
options.
|
|
41846
|
+
if (options.labelAllFeatures || xleft > options.rowLastLabelX[feature.row] || gtexSelection) {
|
|
41847
|
+
options.rowLastLabelX[feature.row] = xright;
|
|
41801
41848
|
IGVGraphics.fillText(ctx, name, centerX, labelY, geneFontStyle, transform);
|
|
41802
|
-
|
|
41803
41849
|
}
|
|
41804
41850
|
} finally {
|
|
41805
41851
|
ctx.restore();
|
|
@@ -42156,24 +42202,27 @@ class FeatureTrack extends TrackBase {
|
|
|
42156
42202
|
|
|
42157
42203
|
const rowFeatureCount = [];
|
|
42158
42204
|
options.rowLastX = [];
|
|
42205
|
+
options.rowLastLabelX = [];
|
|
42159
42206
|
for (let feature of featureList) {
|
|
42160
|
-
|
|
42161
|
-
|
|
42162
|
-
rowFeatureCount[row]
|
|
42163
|
-
|
|
42164
|
-
|
|
42207
|
+
if(feature.start > bpStart && feature.end < bpEnd) {
|
|
42208
|
+
const row = this.displayMode === "COLLAPSED" ? 0 : feature.row || 0;
|
|
42209
|
+
if (rowFeatureCount[row] === undefined) {
|
|
42210
|
+
rowFeatureCount[row] = 1;
|
|
42211
|
+
} else {
|
|
42212
|
+
rowFeatureCount[row]++;
|
|
42213
|
+
}
|
|
42214
|
+
options.rowLastX[row] = -Number.MAX_SAFE_INTEGER;
|
|
42215
|
+
options.rowLastLabelX[row] = -Number.MAX_SAFE_INTEGER;
|
|
42165
42216
|
}
|
|
42166
|
-
options.rowLastX[row] = -Number.MAX_SAFE_INTEGER;
|
|
42167
42217
|
}
|
|
42218
|
+
const pixelsPerFeature = pixelWidth / Math.max(...rowFeatureCount);
|
|
42168
42219
|
|
|
42169
42220
|
let lastPxEnd = [];
|
|
42170
42221
|
for (let feature of featureList) {
|
|
42171
42222
|
if (feature.end < bpStart) continue
|
|
42172
42223
|
if (feature.start > bpEnd) break
|
|
42173
|
-
|
|
42174
42224
|
const row = this.displayMode === 'COLLAPSED' ? 0 : feature.row;
|
|
42175
|
-
|
|
42176
|
-
options.drawLabel = options.labelAllFeatures || featureDensity > 10;
|
|
42225
|
+
options.drawLabel = options.labelAllFeatures || pixelsPerFeature > 10;
|
|
42177
42226
|
const pxEnd = Math.ceil((feature.end - bpStart) / bpPerPixel);
|
|
42178
42227
|
const last = lastPxEnd[row];
|
|
42179
42228
|
if (!last || pxEnd > last) {
|
|
@@ -42187,7 +42236,6 @@ class FeatureTrack extends TrackBase {
|
|
|
42187
42236
|
ctx.globalAlpha = 1.0;
|
|
42188
42237
|
}
|
|
42189
42238
|
lastPxEnd[row] = pxEnd;
|
|
42190
|
-
|
|
42191
42239
|
}
|
|
42192
42240
|
}
|
|
42193
42241
|
|
|
@@ -51005,6 +51053,7 @@ class Browser {
|
|
|
51005
51053
|
}
|
|
51006
51054
|
|
|
51007
51055
|
createCircularView(container, show) {
|
|
51056
|
+
show = show === true; // convert undefined to boolean
|
|
51008
51057
|
this.circularView = createCircularView(container, this);
|
|
51009
51058
|
this.circularViewControl = new CircularViewControl(this.$toggle_button_container.get(0), this);
|
|
51010
51059
|
this.circularView.setAssembly({
|
|
@@ -51013,7 +51062,7 @@ class Browser {
|
|
|
51013
51062
|
chromosomes: makeCircViewChromosomes(this.genome)
|
|
51014
51063
|
});
|
|
51015
51064
|
this.circularViewVisible = show;
|
|
51016
|
-
|
|
51065
|
+
return this.circularView
|
|
51017
51066
|
}
|
|
51018
51067
|
|
|
51019
51068
|
get circularViewVisible() {
|