From dd96961088d5ba54e6cce99c2f99ccdbec94099b Mon Sep 17 00:00:00 2001 From: corywang Date: Sat, 7 Mar 2015 02:13:16 -0500 Subject: [PATCH] Merge with Pujan's code --- VQI_GenomeBrowser.js | 447 +++++++++++++++++++++++++------------------ 1 file changed, 258 insertions(+), 189 deletions(-) mode change 100644 => 100755 VQI_GenomeBrowser.js diff --git a/VQI_GenomeBrowser.js b/VQI_GenomeBrowser.js old mode 100644 new mode 100755 index b44b4ac..b11f823 --- a/VQI_GenomeBrowser.js +++ b/VQI_GenomeBrowser.js @@ -7,6 +7,7 @@ function VQI_GenomeBrowser(id) { var margin = 50; var trackList = []; + var trackSelections = []; var genomeData = []; @@ -18,40 +19,95 @@ function VQI_GenomeBrowser(id) { // $("#" + id).append("
CPG:Shore:Shelve:
"); - d3.select("#" + id).append("div").text("Chromosome: ") - var chromosomeSelect = d3.select("#" + id) - .append("div") - .append("select") - .on("change", function (d) { - graph(chromosomeSelect.property("value")); - }); +// d3.select("#" + id).append("div").text("Chromosome: ") +// var select = d3.select("#" + id) +// .append("div") +// .append("select") +// .on("change", function (d) { +// graph(select.property("value")); +// }); +// +// d3.select("#" + id).append("div").text("Start: ") +// var minNumber = d3.select("#" + id) +// .append("input") +// .attr("type", "number") +// .property("value", 0); +// +// d3.select("#" + id).append("div").text("End: ") +// var maxNumber = d3.select("#" + id) +// .append("input") +// .attr("type", "number") +// .property("value", 0); +// var graphButton = d3.select("#" + id) +// .append("input") +// .attr("type", "button") +// .attr("value", "Graph") +// .on("click", function () { +// graph(select.property("value"), minNumber.property("value"), maxNumber.property("value")) +// }); + + var navigateToRegion = function () { + var chrom = $("#" + divId + " #chrom").val(); + var chrom_start = $("#" + divId + " #chrom_start").val(); + var chrom_end = $("#" + divId + " #chrom_end").val(); + graph(chrom, chrom_start, chrom_end); + }; + this.makeNavigationForm = function () { + var chromSelectBox = ""; + var chromStartBox = ""; + var chromEndBox = ""; + var navigateButton = ""; + var form = ""; + $("#" + divId).append(form); + $("#" + divId + " #navigatebutton").on("click", navigateToRegion.bind(this)); + }; + this.makeNavigationForm(); - d3.select("#" + id).append("div").text("Start: ") - var minNumber = d3.select("#" + id) - .append("input") - .attr("type", "number") - .property("value", 0) - .on("change", function () { - setBounds(minNumber.property("value"), maxNumber.property("value")) - }); + var browseToGene = function () { + var geneName = $("#" + divId + " #geneName").val(); - d3.select("#" + id).append("div").text("End: ") - var maxNumber = d3.select("#" + id) - .append("input") - .attr("type", "number") - .property("value", 0) - .on("change", function () { - setBounds(minNumber.property("value"), maxNumber.property("value")) - }); + var genes = [geneName]; + dataToPost = JSON.stringify(genes); + + $.ajax({ + url: vqi_url + 'serverside/web/VQService.php?service=gene-info-for-gene-symbol', + type: 'POST', + dataType: "json", + data: { + "genes": dataToPost + }, + async: false + }).success(function (data) { + var thisGene = data.slice(1)[0]; + var gene_chrom = thisGene[2]; + var gene_start = thisGene[3]; + var gene_end = thisGene[4]; + thisObj.navigate(gene_chrom, gene_start, gene_end); +// objVQIResult.parseSNPAndSNP(data, true); + }).error(function (req, status, error) { + $("body").append(status + ": " + error); + }); + }; + + this.makeFormForGeneSearch = function () { + var geneText = "Gene: "; + var geneSearchButton = ""; + var form = "
" + geneText + geneSearchButton + "
"; + $("#" + divId).append(form); + $("#" + divId + " #genesearchbutton").on("click", browseToGene.bind(this)); + }; + this.makeFormForGeneSearch(); var colocalize = function () { var track1Name = $("#" + divId + " #track1").val(); var track2Name = $("#" + divId + " #track2").val(); + var coloc_dist = $("#" + divId + " #coloc_dist").val(); var data1 = this.getTrackByName(track1Name); var data2 = this.getTrackByName(track2Name); + var dataToPost1 = [], dataToPost2 = []; dataToPost1 = JSON.stringify(data1); dataToPost2 = JSON.stringify(data2); @@ -62,7 +118,8 @@ function VQI_GenomeBrowser(id) { dataType: "json", data: { "bed1": dataToPost1, - "bed2": dataToPost2 + "bed2": dataToPost2, + "coloc_dist": coloc_dist }, async: false }).success(function (data) { @@ -70,8 +127,8 @@ function VQI_GenomeBrowser(id) { var data2 = [] data = data.slice(1); for (var i in data) { - data1.push(data[i].slice(0, 3)); - data2.push(data[i].slice(3)); + data1.push(data[i].slice(0, 6)); + data2.push(data[i].slice(6)); } thisObj.addTrack(data1); thisObj.addTrack(data2); @@ -82,8 +139,10 @@ function VQI_GenomeBrowser(id) { }); }; + + this.makeFormForColocalization = function () { - var track1Select = "
track1 "; for (var i in trackList) { var thisTrack = trackList[i]; var text = thisTrack['name']; @@ -92,7 +151,7 @@ function VQI_GenomeBrowser(id) { } track1Select += ""; - var track2Select = "
track2 "; for (var i in trackList) { var thisTrack = trackList[i]; var text = thisTrack['name']; @@ -101,9 +160,10 @@ function VQI_GenomeBrowser(id) { } track2Select += ""; + var distanceTextBox = ""; - var colocalizeButton = "
"; - var form = "
" + track1Select + track2Select + colocalizeButton + "
"; + var colocalizeButton = ""; + var form = "
" + track1Select + track2Select + distanceTextBox + colocalizeButton + "
"; $("#" + divId).append(form); $("#" + divId + " #colocalize").on("click", colocalize.bind(this)); }; @@ -111,13 +171,7 @@ function VQI_GenomeBrowser(id) { var self = this; - /*var graphButton = d3.select("#" + id) - .append("input") - .attr("type", "button") - .attr("value", "Graph") - .on("click", function () { - graph(select.property("value"), minNumber.property("value"), maxNumber.property("value")) - });*/ + this.svg = d3.select("#" + id) .append("svg") @@ -143,8 +197,6 @@ function VQI_GenomeBrowser(id) { .attr("transform", "translate(0," + (0 + margin) + ")"); // .attr("transform", "translate(0," + (height + margin) + ")"); - var zoom = d3.behavior.zoom(); - //Just a line svg.append("line") .attr("x1", margin) @@ -153,9 +205,11 @@ function VQI_GenomeBrowser(id) { .attr("y2", height / 2 + margin + 20) .style("stroke", "blue"); + var zoom = d3.behavior.zoom(); + //set up tool tips - /* var tip = d3.tip() + /*var tip = d3.tip() .attr('class', 'd3-tip') .offset([-20, 0]) .html(function (d) { @@ -169,7 +223,7 @@ function VQI_GenomeBrowser(id) { + "(" + d[indexArray.chr] + " : " + d[indexArray.start] + " - " + d[indexArray.end] + ")" + ""; }); - svg.call(tip);*/ + svg.call(tip); d3.selectAll(".d3-tip").style({ "line-height": "1", @@ -178,7 +232,7 @@ function VQI_GenomeBrowser(id) { "background": "rgba(0, 0, 0, 0.8)", "color": "#fff", "border-radius": "2px" - }); + });*/ var zoomed = function () { xAxisSelection.call(xAxis); @@ -191,8 +245,18 @@ function VQI_GenomeBrowser(id) { return xScale(d[indexArray.start]) }) - minNumber.property("value", xScale.domain()[0]); - maxNumber.property("value", xScale.domain()[1]); + for (var i in trackSelections) { + trackSelections[i] + .attr("x1", function (d) { + return xScale(d[indexArray.start]); + }) + .attr("x2", function (d) { + return xScale(d[indexArray.end]); + }) + } + + // minNumber.property("value", xScale.domain()[0]); + //maxNumber.property("value", xScale.domain()[1]); d3.selectAll(".axis path, .axis line").style({ "fill": "none", @@ -202,7 +266,11 @@ function VQI_GenomeBrowser(id) { d3.selectAll(".axis text").style({ "font-family": "sans-serif", "font-size": "11px"}); - } + }; + + this.navigate = function (chrom, chrom_start, chrom_end) { + graph(chrom, chrom_start, chrom_end); + }; var setBounds = function(min, max){ var xMax = Number(max); @@ -211,42 +279,39 @@ function VQI_GenomeBrowser(id) { xScale.domain([xMin - (xMax - xMin) * 1 / 10, xMax + (xMax - xMin) * 1 / 10]) .range([margin, width + margin]); - xAxisSelection.call(xAxis); - - svg.selectAll("rect") - .attr("width", function (d) { - return xScale(d[indexArray.end]) - xScale(d[indexArray.start]) - }) - .attr("x", function (d) { - return xScale(d[indexArray.start]) - }) + zoomed(); zoom.x(xScale).on("zoom", zoomed); svg.call(zoom); - minNumber.property("value", xMin); - maxNumber.property("value", xMax); - - d3.selectAll(".axis path, .axis line").style({ - "fill": "none", - "stroke": "black", - "shape-rendering": "crispEdges"}); - - d3.selectAll(".axis text").style({ - "font-family": "sans-serif", - "font-size": "11px"}); + // minNumber.property("value", xMin); + // maxNumber.property("value", xMax); } - var graph = function (chromosome) { + var graph = function (chromosome, min, max) { var indexList = indexArray; - + //Graphs the current chromosome. If min and max are specified, graph only in that range. + //Otherwise, graphs the whole chromosome var self = this; var currentData; + var xMax = 0; + var xMin = 0; //Populates drop down list with different chromosomes - chromosomeSelect.selectAll("option") +// select.selectAll("option") +// .data(chromosomes) +// .enter() +// .append("option") +// .attr("value", function (d) { +// return d; +// }) +// .text(function (d) { +// return d; +// }); + + d3.select("#chrom").selectAll("option") .data(chromosomes) .enter() .append("option") @@ -255,35 +320,47 @@ function VQI_GenomeBrowser(id) { }) .text(function (d) { return d; - }) + }); chrom_curr = chromosome; - //Gets relevant data and calculates min/max if needed currentData = genomeData.filter(function (d) { return d[indexList.chr] == chromosome }); - - var xMax = d3.max(currentData, function (d) { - return d[indexList.end] - }); - var xMin = d3.min(currentData, function (d) { - return d[indexList.start] - }); + //Gets relevant data and calculates min/max if needed + if (min == null || max == null) { + xMax = d3.max(currentData, function (d) { + return d[indexList.end] + }); + xMin = d3.min(currentData, function (d) { + return d[indexList.start] + }); +// minNumber.property("value", xMin); +// maxNumber.property("value", xMax); + + d3.select("#chrom_start").property("value", xMin); + d3.select("#chrom_end").property("value", xMax); + } + else { + /* currentData = genomeData.filter(function (d) { + return d[indexList.chr] == chromosome;// && d[indexList.start] >= min && d[indexList.end] <= max + });*/ + xMax = Number(max); + xMin = Number(min); + } setBounds(xMin,xMax); svg.selectAll("rect") - .data(currentData, function(d){return d;}) + .data(currentData) .exit() .remove(); svg.selectAll("rect") - .data(currentData, function(d){return d;}) + .data(currentData) .enter() .append("rect"); svg.selectAll("rect") - .data(currentData, function(d){return d;}) .style("fill-opacity", ".4") .style("stroke", function (d) { var type = d[indexList.type]; @@ -343,18 +420,14 @@ function VQI_GenomeBrowser(id) { svg.attr("height", height + 2 * margin + ySpace); var thisY = height / 2 + margin + 20 + ySpace; - if (!i) { - svg.selectAll("line") - .data([name], function (d) {return d;}) - .enter() - .append("line") + /*svg.append("line") .attr("x1", margin) .attr("y1", height / 2 + margin + 20 + ySpace) .attr("x2", width + margin) .attr("y2", height / 2 + margin + 20 + ySpace) .style("stroke-width", 1) - .style("stroke", "black"); + .style("stroke", "black");*/ svg.selectAll("text") .data([name], function (d) {return d;}) .enter() @@ -367,28 +440,28 @@ function VQI_GenomeBrowser(id) { .text(name); } // test.addTrack({start:20000000, end:20000100}) - var tracks = svg.selectAll("tracks") - .data(thisData, function (d) {return d;}) + var tracks = svg.selectAll("line") + .data(thisData) .enter() - .append("rect"); - var rectAttributes = tracks - .attr("x", function (d) { + .append("line"); + var lineAttributes = tracks + .attr("x1", function (d) { return xScale(d[index.start]); }) - .attr("y", function (d) { + .attr("y1", function (d) { - return thisY - fHeight / 2; + return height / 2 + margin + 20 + ySpace; }) - .attr("height", function (d) { - return fHeight; + .attr("x2", function (d) { + return xScale(d[index.end]); }) - .attr("width", function (d) { + .attr("y2", function (d) { // return 50; - return xScale(d[index.end]) - xScale(d[index.start]); + return height / 2 + margin + 20 + ySpace; }) - .style("fill-opacity", ".4") - .style("stroke", "blue") - .style("fill", "green"); + .style("stroke", "black") + + trackSelections.push(tracks); var exons = []; @@ -401,6 +474,7 @@ function VQI_GenomeBrowser(id) { { var exon = value.slice(0); + exon[indexArray.name] = exon[indexArray.name] + " Exon " + (i+1) + "/" + value[indexArray.exonStarts].length; exon[indexArray.start] = parseInt(exon[indexArray.exonStarts][i]); exon[indexArray.end] = parseInt(exon[indexArray.exonEnds][i]); exons.push(exon); @@ -418,46 +492,41 @@ function VQI_GenomeBrowser(id) { }) .attr("y", function (d) { - return thisY - fHeight; + return thisY - fHeight / 2; }) .attr("height", function (d) { - return fHeight*2; + return fHeight; }) .attr("width", function (d) { // return 50; return xScale(d[index.end]) - xScale(d[index.start]); }) - .style("fill-opacity", ".4") - .style("stroke", "blue") - .style("fill", "blue"); + .style("fill-opacity", ".8") + .style("stroke", "gray") + .style("fill", "gray"); + //.style("fill", "green") //.on('mouseover', tip.show) //.on('mouseout', tip.hide); -// .tipsy({ -// gravity: 'w', -// html: true, -// title: function (d) { -// return d[indexArray.name] + " (" + d[indexArray.chr] + " : " + d[indexArray.start] + " - " + d[indexArray.end] + ")"; -// } -// }); -// + $('svg rect').tipsy({ gravity: 'n', html: true, title: function () { var d = this.__data__; - var strand = ""; - if (d.length > indexArray.strand) { - strand = " (" + d[indexArray.strand] + ")"; - } -// , c = colors(d.i); - return d[indexArray.name] + strand + " (" + d[indexArray.chr] + " : " + d[indexArray.start] + " - " + d[indexArray.end] + ")"; + var name = (d.length > indexArray.name) ? d[indexArray.name] : ''; + return name + " (" + d[indexArray.chr] + " : " + d[indexArray.start] + " - " + d[indexArray.end] + ")"; + } + }); + $('svg line').tipsy({ + gravity: 'n', + html: true, + title: function () { + var d = this.__data__; + var name = (d.length > indexArray.name) ? d[indexArray.name] : ''; + return name + " (" + d[indexArray.chr] + " : " + d[indexArray.start] + " - " + d[indexArray.end] + ")"; } }); -// .text(function (d) { -// return d[indexArray.name] + " (" + d[indexArray.chr] + " : " + d[indexArray.start] + " - " + d[indexArray.end] + ")"; -// }); -// data['name'] = name; @@ -489,7 +558,7 @@ function VQI_GenomeBrowser(id) { return genomeData; } - /* var submitFile = function () { + var submitFile = function () { genomeData = []; chromosomes = []; var file_dir = "./saved-data/"; @@ -565,7 +634,7 @@ function VQI_GenomeBrowser(id) { } d3.select("#" + id + " #submit").on("click", submitFile.bind(this)); -// submitFile();*/ +// submitFile(); this.loadCPGFiles = function (cpg, shoer, shelf) { genomeData = []; @@ -656,69 +725,69 @@ function VQI_GenomeBrowser(id) { }; - this.makeFormForColocalization = function () { - var track1Select = "
track1 "; - - var track2Select = "
track2 "; - - - var colocalizeButton = "
"; - var form = "
" + track1Select + track2Select + colocalizeButton + "
"; - $("#" + divId).append(form); - $("#" + divId + " #colocalize").on("click", colocalize.bind(this)); - }; - - var colocalize = function () { - var track1Name = $("#" + divId + " #track1").val(); - var track2Name = $("#" + divId + " #track2").val(); - - var data1 = this.getTrackByName(track1Name); - var data2 = this.getTrackByName(track2Name); - - var dataToPost1 = [], dataToPost2 = []; - dataToPost1 = JSON.stringify(data1); - dataToPost2 = JSON.stringify(data2); - - $.ajax({ - url: vqi_url + 'serverside/web/VQService.php?service=coloc-bed-and-bed', - type: 'POST', - dataType: "json", - data: { - "bed1": dataToPost1, - "bed2": dataToPost2 - }, - async: false - }).success(function (data) { - var data1 = []; - var data2 = [] - data = data.slice(1); - for (var i in data) { - data1.push(data[i].slice(0, 3)); - data2.push(data[i].slice(3)); - } - thisObj.addTrack(data1); - thisObj.addTrack(data2); - -// objVQIResult.parseSNPAndSNP(data, true); - }).error(function (req, status, error) { - $("body").append(status + ": " + error); - }); - - }; +// this.makeFormForColocalization = function () { +// var track1Select = "
track1 "; +// +// var track2Select = "
track2 "; +// +// +// var colocalizeButton = "
"; +// var form = "
" + track1Select + track2Select + colocalizeButton + "
"; +// $("#" + divId).append(form); +// $("#" + divId + " #colocalize").on("click", colocalize.bind(this)); +// }; +// +// var colocalize = function () { +// var track1Name = $("#" + divId + " #track1").val(); +// var track2Name = $("#" + divId + " #track2").val(); +// +// var data1 = this.getTrackByName(track1Name); +// var data2 = this.getTrackByName(track2Name); +// +// var dataToPost1 = [], dataToPost2 = []; +// dataToPost1 = JSON.stringify(data1); +// dataToPost2 = JSON.stringify(data2); +// +// $.ajax({ +// url: vqi_url + 'serverside/web/VQService.php?service=coloc-bed-and-bed', +// type: 'POST', +// dataType: "json", +// data: { +// "bed1": dataToPost1, +// "bed2": dataToPost2 +// }, +// async: false +// }).success(function (data) { +// var data1 = []; +// var data2 = [] +// data = data.slice(1); +// for (var i in data) { +// data1.push(data[i].slice(0, 3)); +// data2.push(data[i].slice(3)); +// } +// thisObj.addTrack(data1); +// thisObj.addTrack(data2); +// +//// objVQIResult.parseSNPAndSNP(data, true); +// }).error(function (req, status, error) { +// $("body").append(status + ": " + error); +// }); +// +// }; this.getTrackByName = function (name) { for (var i in trackList) { @@ -747,7 +816,7 @@ function VQI_GenomeBrowser(id) { }; - this.makeFormForColocalization(); +// this.makeFormForColocalization(); }