diff --git a/data/intro/flip_animating.png b/data/intro/flip_animating.png new file mode 100644 index 0000000..3953824 Binary files /dev/null and b/data/intro/flip_animating.png differ diff --git a/data/intro/flip_apollo.png b/data/intro/flip_apollo.png new file mode 100644 index 0000000..046e37d Binary files /dev/null and b/data/intro/flip_apollo.png differ diff --git a/data/intro/flip_circos.png b/data/intro/flip_circos.png new file mode 100644 index 0000000..24d7166 Binary files /dev/null and b/data/intro/flip_circos.png differ diff --git a/data/intro/flip_static.png b/data/intro/flip_static.png new file mode 100644 index 0000000..fb30ba1 Binary files /dev/null and b/data/intro/flip_static.png differ diff --git a/data/intro/genome_animated.png b/data/intro/genome_animated.png new file mode 100644 index 0000000..2c4679e Binary files /dev/null and b/data/intro/genome_animated.png differ diff --git a/data/intro/genome_apollo.png b/data/intro/genome_apollo.png new file mode 100644 index 0000000..f0ae590 Binary files /dev/null and b/data/intro/genome_apollo.png differ diff --git a/data/intro/genome_circos.png b/data/intro/genome_circos.png new file mode 100644 index 0000000..0032136 Binary files /dev/null and b/data/intro/genome_circos.png differ diff --git a/data/intro/genome_static2.png b/data/intro/genome_static2.png new file mode 100644 index 0000000..90308da Binary files /dev/null and b/data/intro/genome_static2.png differ diff --git a/data/intro/intro.png b/data/intro/intro.png new file mode 100644 index 0000000..971ae6f Binary files /dev/null and b/data/intro/intro.png differ diff --git a/data/intro/intro2.png b/data/intro/intro2.png new file mode 100644 index 0000000..42dee7e Binary files /dev/null and b/data/intro/intro2.png differ diff --git a/data/intro/phylo.png b/data/intro/phylo.png new file mode 100644 index 0000000..8f3eb91 Binary files /dev/null and b/data/intro/phylo.png differ diff --git a/genome.html b/genome.html index 0ab3351..1094d8b 100644 --- a/genome.html +++ b/genome.html @@ -13,8 +13,25 @@ +
+
-

Click Icons to Select Species.

+

Click on two different animals from the phylogenetic tree to select, + and then go to the chromosome view to see the genome evolution and + divergence of the two species, based on common ancestors!

+

Click Icons to Select Species.

- +
@@ -55,6 +75,7 @@ + diff --git a/index.html b/index.html index 6d08715..7e11d47 100644 --- a/index.html +++ b/index.html @@ -15,35 +15,49 @@
+
@@ -57,12 +71,14 @@
-

Click Icons to Select Species.

+

Click on two different animals from the phylogenetic tree to select, + and then go to the chromosome view to see the genome evolution and + divergence of the two species, based on common ancestors!

- +
@@ -85,6 +101,7 @@ + @@ -94,6 +111,7 @@ +
diff --git a/js/genome/genome.js b/js/genome/genome.js index 642ebe4..68398c0 100644 --- a/js/genome/genome.js +++ b/js/genome/genome.js @@ -1,10 +1,16 @@ -$("#reset").click(function(){ - // reload whole page to reset visualizations (not efficient) - window.location.reload(); +$("#recenter").click(function(){ + // recenter the zoomed svg + svg + .call(zoom_function.transform, d3.zoomIdentity) + .attr("transform", "translate(" + margin.left + "," + (0) + ")");; }); +$("#phylo").click(function(){ + // window will load in the same tag + window.location.replace("phylo.html"); +}); //get filename from previous page. @@ -65,23 +71,26 @@ var margin = { width = 550 - margin.left - margin.right, height = 1050 - margin.top - margin.bottom; +var zoom_function = d3.zoom().scaleExtent([1, 2.5]).on("zoom", function () { svg.attr("transform", d3.event.transform); }) + var svg = d3.select("#chromosomes") .append("svg") .style("cursor","move") - .attr("width", 1800 + margin.left + margin.right) + //.attr("width", 1800 + margin.left + margin.right) + .attr("width", '84%') .attr("id", "chrSvg") - .attr("height", 1400 + margin.top + margin.bottom) + //.attr("height", 1400 + margin.top + margin.bottom) + .attr("height", '100%') .attr("preserveAspectRatio", "xMinYMin meet") .attr("viewBox", "0 0 1800 1550") - .call(d3.zoom().scaleExtent([1, 2.5]).on("zoom", function () { - svg.attr("transform", d3.event.transform); - }))// enable zoom and pan with d3 - .append("g") - .attr("id", "tree") - .attr("transform", "translate(" + margin.left + "," + (-130) + ")"); + .call(zoom_function)// enable zoom and pan with d3 + .append("g") + .attr("id", 'tree') + .attr("class", "panSelect") + .attr("transform", "translate(" + margin.left + "," + (0) + ")"); -//make svg responsive ???? +//make svg responsive var chart = $("#chrSvg"), originalWidth = chart.width(), aspect = originalWidth / $(window).width(); @@ -399,7 +408,6 @@ queue.awaitAll(function(error, csvDataSets) { }); function changeCursorStyle() { - console.log("here418"); d3.select(this).style("cursor","zoom-in"); } @@ -455,7 +463,7 @@ queue.awaitAll(function(error, csvDataSets) { if (mode == "forward" || mode == "backward") { $("#morphthenslide").css("color", "#d23600"); d3.select("#tree") - .attr("transform", "translate(" + margin.left + "," + (-130) + ")"); + .attr("transform", "translate(" + margin.left + "," + (0) + ")"); d3.selectAll(".circos").remove(); d3.selectAll(".chrChart path").remove(); for (b = data.length - 1; b >= 0; b--) { @@ -474,7 +482,7 @@ queue.awaitAll(function(error, csvDataSets) { forward_pointer_event(); $("#morphthenslide").css("color", "#555555"); d3.select("#tree") - .attr("transform", "translate(" + margin.left + "," + (-130) + ")"); + .attr("transform", "translate(" + margin.left + "," + (0) + ")"); selectedLink = []; for (b = data.length - 1; b >= 0; b--) { d3.select("#" + childrens[b] + " text").style("opacity", 1); @@ -886,8 +894,11 @@ function appendRow(num, temparray, data, layer, spe) { } function circos(data, data2, childSpe, parentSpe) { - d3.select("#tree") - .attr("transform", "translate(" + (margin.left) + "," + (-50) + ")scale(1.2)"); + //d3.select("#tree") + //.attr("transform", "translate(" + (margin.left) + "," + (-50) + ")scale(1.2)"); + //d3.select(".link_big .node").attr("transform", "translate(" + (margin.left) + "," + (-50) + ")scale(1.2)"); + + //console.log("2") var groupCounts = {}; var translocations = []; @@ -920,7 +931,9 @@ function circos(data, data2, childSpe, parentSpe) { else{ y = y2 + (y1 - y2)/2.5; } - var x = x1 + (x2 - x1)/1.8; + var x = x1 + (x2 - x1)/5; // 1,8 + + console.log(x) data2.forEach(function(d, i) { if(uniqueCounts[d.chr + d.name] === undefined){ @@ -969,10 +982,12 @@ function circos(data, data2, childSpe, parentSpe) { .groups(groups) .edges(translocations); - var g = d3.select("#chrSvg").append("g") + var g = d3.select("#tree").append("g") .attr("transform", "translate(" + x + "," + y + ")") - .attr("class", parentSpe + "_" + childSpe + "_circos circos") - .attr('pointer-events', 'all'); + .attr('class', `${parentSpe}_${childSpe}_circos circos panSelect`) + //.attr("class", parentSpe + "_" + childSpe + "_circos circos") + .attr('pointer-events', 'all') + var line = g.append("line") .style("stroke", "white") @@ -1019,7 +1034,8 @@ function circos(data, data2, childSpe, parentSpe) { }) .attr("class",function(d){return chr[d.index];}) .attr("d", d3.arc().innerRadius(innerRadius).outerRadius(outerRadius)) - .on("click",fade(0.5)); + .on("click",fade(0.5)) + .attr("cursor", "pointer"); group.append("text") .filter(function(d) { return unique.indexOf(d.index) != -1; }) @@ -1042,7 +1058,7 @@ function circos(data, data2, childSpe, parentSpe) { } }) .style("text-anchor", function(d) { return d.angle > Math.PI ? "end" : ""; }) - .text(function(d) { return chr[d.index].split("_")[1]; }); + .text(function(d) { return chr[d.index].split("_")[1]; }) g.append("g").attr("class", "ribbons") .selectAll("path") diff --git a/js/phylo/createIntroSlides.js b/js/phylo/createIntroSlides.js new file mode 100644 index 0000000..e183d8c --- /dev/null +++ b/js/phylo/createIntroSlides.js @@ -0,0 +1,229 @@ +var page = 0; +var title_text; +var body_text; +var body_image; +var original_width = 2560 +var original_height = 1257 +var width = $(window).width(); +var height = $(window).height(); +var text_ratio = Math.min(width/original_width, height/original_height) +var title_font_size = text_ratio * 3; +var body_font_size = text_ratio * 1.5; + + + +$("#show_intro").click(function() { + page = 0; + $(".modal").css("display", "flex"); + assignPageText(0); + +}); + +$(".skip-button-box").click(function() { + page = 0; + $(".modal").css("display", "none"); +}) + +$(".next-button-box").click(function() { + console.log("here") + page = page+1; + assignPageText(page); +}) + +$('.previous-button-box').click(function() { + console.log("p") + page = page-1; + assignPageText(page); +}) + +function assignPageText(pageNum) { + if(pageNum == 0) { + // load html text content, and previous button + console.log("page 0") + title_text = "Did you Know Animals Share Large Chunks of DNA?"; + addTitleText(title_text); + body_text = "Animals such as humans, whales, and dogs are made up of cells. Inside these cells are chromosomes.

" + + "Chromosomes are composed of DNA, and the set of chromosomes for a species is called its genome.

" + + "Animal genomes mutate and evolve into new species over time." + + " These new species share preserved DNA segments with their ancestor, called synteny blocks. " + + "It's like a puzzle where the DNA blocks are the pieces, and they've been put together in a new way! ..."; + addBodyText(body_text, "../data/intro/intro.png", 7, 5); + addButtons(1,0); + + } else if (pageNum == 1) { + console.log("page 1") + title_text = "Synteny Blocks Come From Common Ancestors"; + addTitleText(title_text); + body_text = "Today's species such as dolphins and cats also share synteny blocks between each other." + + "

" + + "By studying the genomes of two existing species, scientists can figure out when they diverged from each other! " + + "This diverging animal, which existed many millions of years ago, is called a Common Ancestor, " + + "and contains DNA that is shared by both current, diverged species." + + "

" + + "Use this application to learn how synteny blocks evolve from Common Ancestors to current species..."; + addBodyText(body_text, "../data/intro/intro2.png", 5, 7); + addButtons(1,1); + + } else if (pageNum == 2) { + title_text = "The Phylogenetic Tree Classifies Species"; + addTitleText(title_text); + body_text = "



Use the mini tree in the left sidebar to get an overview. " + + "Drag the white frame to take a closer look at different part of the tree. " + + "Zoom in and out by scrolling the mouse. " + + "

Click on the animal icons in the tree to " + + " learn more about them. When two species are in the right sidebar, " + + "the path to their most recent common ancestor is highlighted. " + + "Then click on \"go to genome view\" to explore their chromosome evolution."; + addBodyText(body_text, "../data/intro/phylo.png", 7, 5); + addButtons(1,1); + + } else if (pageNum == 3) { + title_text = "Use The Genome View To Evolve Chromosomes"; + addTitleText(title_text); + body_text = "The genome view is for showing indivdiual genome evolution." + + "

" + + "The chromosomes for each species are shown as a set of colored bars. " + + "Clicking on a chromosome will show how the chromosome evolved from the Common Ancestor to today's species. " + + "Chromosomes split, flip, or move to other chromosomes! " + + "

Click the arrow connecting two species to evolve the entire genome at once!

" + + "To go back to the full tree, hover on \"Synteny Explorer\" at the top left and click."; + addBodyText(body_text, "../data/intro/genome_animated.png", 6, 6); + addButtons(1,1); + + } else if (pageNum == 4) { + title_text = "Synteny Blocks Sometimes Flip Out!"; + addTitleText(title_text); + body_text = "Synteny blocks sometimes invert. This type of rearrangement is a disrupting event, " + + "and is an important mechanism for scientists in studying genome evolution. " + + "

To denote a flip, a synteny block will do a half spin." + + "

Use \"Mode\" in the navigation bar to select different representations of the genome evolution."; + addBodyText(body_text, "../data/intro/flip_animating.png", 6, 6); + addButtons(1,1); + + } else if (pageNum == 5) { + title_text = "Explore and Learn!"; + addTitleText(title_text); + body_text = "Have fun playing!

" + + "Use the Help icon if you're not sure what to do. " + + "

" + // + "Quiz yourself by clicking the Test You Knowledge icon." + // + "\n\n" + // + "When you're done playing, please click the I'm Finished button to end your "+ + // "session, grab the paper slip for the user study note.\n\n" + + + "Thanks from the team!
" + + "Chris, Greg, Kathy, Dr Kwan-Liu Ma, and Dr Harris Lewin"; + addBodyText(body_text, 0, 9, 3); + addButtons(1,1); + + } else if (pageNum == 6) { + title_text = "Thanks for playing!"; + addTitleText(title_text); + + body_text = "If you're interested in learning more about genomic evolution, " + + "consider looking at some of the following resources:

" + + "\u2022 Wikipedia pages for 'genome evolution', 'comparative genomics', or 'synteny'
" + + "\u2022 Online genome databases like Genome Browser (https://genome.ucsc.edu)
" + + "\u2022 Check out a book on genomics at local library
" + + "\u2022 Explore a natural history museum
" + + "\u2022 Talk to your biology teacher at school" + "

" + + "Don't forget to let us know what you think of the app. It really helps out our student research and this project's development!"; + addBodyText(body_text, 0, 9, 3); + addButtons(0,1); + + } + + function addTitleText(text) { + + $(window).resize(function() { + width = $(window).width(); + height = $(window).height(); + text_ratio = Math.min(width/original_width, height/original_height) + //console.log("new text ratio: ", text_ratio) + title_font_size = text_ratio * 3; + body_font_size = text_ratio * 1.5; + + var textSize = title_font_size+"rem" + console.log(textSize) + $('.title-text-box').css("font-size", title_font_size + "rem"); + $('.title-text-box').html("
" + text +"
"); + $('.skip-button-box').html("
×
"); + }) + + + var textSize = title_font_size+"rem" + console.log(textSize) + $('.title-text-box').css("font-size", title_font_size + "rem"); + $('.title-text-box').html("
" + text +"
"); + $('.skip-button-box').html("
×
"); + } + + function addBodyText(text, image_url, col1, col2) { + $(window).resize(function() { + width = $(window).width(); + height = $(window).height(); + text_ratio = Math.min(width/original_width, height/original_height); + //console.log("new text ratio: ", text_ratio) + title_font_size = text_ratio * 3; + body_font_size = text_ratio * 1.5; + + if (image_url == 0) { + $('#modal-content-body').html( + "
" + + text +"
" + + "
"); + } else { + $('#modal-content-body').html( + "
" + + text +"
" + + "\"\""); + } + }) + + if (image_url == 0) { + $('#modal-content-body').html( + "
" + + text +"
" + + "
"); + } else { + $('#modal-content-body').html( + "
" + + text +"
" + + "\"\""); + } + } + + function addButtons(next, previous) { + if (next == 1) { + $('.next-button-box').html("
Next »
"); + } else { + $('.next-button').remove(); + } + //Next » + if (previous == 1) { + $('.previous-button-box').html("
« Previous
"); + } else { + $('.previous-button').remove(); + } + + } +} + +var loadfirst = (function() { + var executed = false; + return function() { + if (!executed) { + executed = true; + // do something + console.log("true?") + assignPageText(0); + } + }; +})(); + +loadfirst(); + +/*var queue = d3.queue(); +queue.awaitAll(function() { + //show instruction slides when first load + assignPageText(0); +});*/ diff --git a/js/phylo/createLinearTree.js b/js/phylo/createLinearTree.js index 481fab5..be10690 100644 --- a/js/phylo/createLinearTree.js +++ b/js/phylo/createLinearTree.js @@ -1,8 +1,35 @@ var disable_Parents; + +var original_width = 2560 +var original_height = 1257 +var width = $(window).width(); +var height = $(window).height(); +var text_ratio = Math.min(width/original_width, height/original_height) +var side_bar_font_size = text_ratio * 0.9; + +$("#selectSpe1").css("font-size", side_bar_font_size+"rem") +$("#selectSpe2").css("font-size", side_bar_font_size+"rem") + + +$(window).resize(function() { + width = $(window).width(); + height = $(window).height(); + text_ratio = Math.min(width/original_width, height/original_height) + side_bar_font_size = text_ratio * 0.9; + $("#selectSpe1").css("font-size", side_bar_font_size+"rem") + $("#selectSpe2").css("font-size", side_bar_font_size+"rem") + + +}) + + function creatLinearTree(life, info, baseSvg) { - var showTime = 0; + var showTime = 1; var showName = 1; + $("#show_timeLine").css("color", "#d23600"); $("#show_name").css("color", "#d23600"); + $("#linear").css("color", "#d23600"); + $("#radial").css("color", "#555555"); $("#zoomValue").val('100'); @@ -26,6 +53,10 @@ function creatLinearTree(life, info, baseSvg) { .scale(zoomValue / 100)); }); + if (showTime == 1) { + showTimeLine(); + } + $("#show_timeLine").click(function(){ if(showTime == 0){ $("#show_timeLine").css("color", "#d23600"); @@ -56,7 +87,7 @@ function creatLinearTree(life, info, baseSvg) { showTime = 0; }); - var chart = baseSvg.append("g").attr("transform", "translate(50, 20)"); + var chart = baseSvg.append("g").attr("transform", "translate(50, 20)") tree(root); function scaleBranchLengths(nodes, w) { @@ -148,7 +179,10 @@ function creatLinearTree(life, info, baseSvg) { } }) .on("click", function(d) { - console.log(selected); + console.log(firstNodeName); + console.log(secondNodeName); + //var side_bar_font_size = 0.9; + if (selected == 0) { // both empty: 00 secondNode = ""; secondNodeName = ""; @@ -173,18 +207,20 @@ function creatLinearTree(life, info, baseSvg) { firstNode = d; selected = 1; firstNodeName = "" + d.data.name; - $("#speOne").html("

" + + $("#speOne").html("

" + sName[d.data.name] + "

" + wiki[d.data.name] + "

"); - $("#speTwo").html("

Click Icons to Select Species.

"); + $("#speTwo").html("

Click Icons to Select Species.

"); d3.selectAll('#miniTree svg').remove(); // become 10 after selection, close button: go to 00 d3.select("#speOne") .select(".closeButton") .on("click", function(){ - $("#speOne").html("

Click Icons to Select Species.

"); + $("#speOne").html("

Click on two different animals from the phylogenetic tree" + + " to select, and then go to the chromosome view to see the genome evolution and " + + "divergence of the two species, based on common ancestors!

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -220,7 +256,9 @@ function creatLinearTree(life, info, baseSvg) { selected = 0; firstNode = ""; firstNodeName = "";*/ - $("#speOne").html("

Click Icons to Select Species.

"); + $("#speOne").html("

Click on two different animals from the phylogenetic tree" + + " to select, and then go to the chromosome view to see the genome evolution and " + + "divergence of the two species, based on common ancestors!

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -235,9 +273,9 @@ function creatLinearTree(life, info, baseSvg) { selected = 3; // go to state 11 secondNodeName = "" + d.data.name; $("#speTwo").html("

" + + d.data.name + "_sm.png style=\"width:60px;height:60px;\">

" + sName[d.data.name] + "

" + - [d.data.name] + "

"); + wiki[d.data.name] + "

"); var miniLife = buildMiniTree(firstNode, secondNode); localStorage.setItem("miniLife", miniLife); createMiniTree(miniLife, info); @@ -247,7 +285,9 @@ function creatLinearTree(life, info, baseSvg) { d3.select("#speOne") .select(".closeButton") .on("click", function(){ - $("#speOne").html("

Click Icons to Select Species.

"); + $("#speOne").html("

Click on two different animals from the phylogenetic tree" + + " to select, and then go to the chromosome view to see the genome evolution and " + + "divergence of the two species, based on common ancestors!

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -266,7 +306,7 @@ function creatLinearTree(life, info, baseSvg) { d3.select("#speTwo") .select(".closeButton") .on("click", function(){ - $("#speTwo").html("

Click Icons to Select Species.

"); + $("#speTwo").html("

Click Icons to Select Species.

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -314,7 +354,7 @@ function creatLinearTree(life, info, baseSvg) { selected = 0; firstNode = ""; firstNodeName = "";*/ - $("#speTwo").html("

Click Icons to Select Species.

"); + $("#speTwo").html("

Click Icons to Select Species.

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -329,9 +369,9 @@ function creatLinearTree(life, info, baseSvg) { selected = 3; // go to state 11 firstNodeName = "" + d.data.name; $("#speOne").html("

" + + d.data.name + "_sm.png style=\"width:60px;height:60px;\">

" + sName[d.data.name] + "

" + - [d.data.name] + "

"); + wiki[d.data.name] + "

"); var miniLife = buildMiniTree(firstNode, secondNode); localStorage.setItem("miniLife", miniLife); createMiniTree(miniLife, info); @@ -340,7 +380,7 @@ function creatLinearTree(life, info, baseSvg) { d3.select("#speOne") .select(".closeButton") .on("click", function(){ - $("#speOne").html("

Click Icons to Select Species.

"); + $("#speOne").html("

Click Icons to Select Species.

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -358,7 +398,7 @@ function creatLinearTree(life, info, baseSvg) { d3.select("#speTwo") .select(".closeButton") .on("click", function(){ - $("#speTwo").html("

Click Icons to Select Species.

"); + $("#speTwo").html("

Click Icons to Select Species.

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -403,17 +443,17 @@ function creatLinearTree(life, info, baseSvg) { selected = 1; firstNodeName = "" + d.data.name; $("#speOne").html("

" + + "_sm.png style=\"width:60px;height:60px;\">

" + sName[d.data.name] + "

" + wiki[d.data.name] + "

"); - $("#speTwo").html("

Click Icons to Select Species.

"); + $("#speTwo").html("

Click Icons to Select Species.

"); d3.selectAll('#miniTree svg').remove(); // become 10 after selection, close button: go to 00 d3.select("#speOne") .select(".closeButton") .on("click", function(){ - $("#speOne").html("

Click Icons to Select Species.

"); + $("#speOne").html("

Click Icons to Select Species.

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -430,7 +470,7 @@ function creatLinearTree(life, info, baseSvg) { } }) } else if (thirdNodeName == firstNodeName) { // when deselect the first node - $("#speOne").html("

Click Icons to Select Species.

"); + $("#speOne").html("

Click Icons to Select Species

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -450,7 +490,7 @@ function creatLinearTree(life, info, baseSvg) { } } } else if (thirdNodeName == secondNodeName) { // when deselect the second node - $("#speTwo").html("

Click Icons to Select Species.

"); + $("#speTwo").html("

Click Icons to Select Species.

"); $(".button").hide() d3.selectAll('#miniTree svg').remove(); d3.selectAll(".boarder").attr("opacity",0); @@ -478,7 +518,9 @@ function creatLinearTree(life, info, baseSvg) { .attr("opacity",0.5); } } + } + }) .attr("pointer-events", function(d) { if (sName[d.data.name] != "") { @@ -577,15 +619,27 @@ function creatLinearTree(life, info, baseSvg) { var rootDist = root.descendants().map(function(n) { return n.data.length; }); + rootDist = rootDist.filter(element => { + return element !== undefined; + }); rootDists = d3.max(rootDist); + d3.select('.xaxis').remove(); + + console.log(rootDist) + console.log(rootDists) + console.log(w) + console.log("0") timeLineScale = d3.scaleLinear() .domain([rootDists, 0]) - .rangeRound([0, w * scale2]).nice(); + .rangeRound([0, w * scale2]); xAxis = d3.axisBottom(timeLineScale); + let tickLabels = ['300 million years ago', '250 million years ago', '200 million years ago', '150 million years ago','100 million years ago', '50 million years ago','Present']; + + d3.select(".timeLine").append("g") .attr("class", "xaxis") .attr("transform", function() { @@ -595,7 +649,7 @@ function creatLinearTree(life, info, baseSvg) { return "translate(35," + 20 + ")"; } }) - .call(xAxis.ticks(5)) + .call(xAxis.ticks(8).tickFormat((d,i) => tickLabels[i])) .selectAll("text") .style("font-size", "15px"); } diff --git a/js/phylo/createRadialTree.js b/js/phylo/createRadialTree.js index d953a42..ca4095d 100644 --- a/js/phylo/createRadialTree.js +++ b/js/phylo/createRadialTree.js @@ -2,6 +2,8 @@ function creatRadialTree(life, info, baseSvg) { var showTime = 0; var showName = 1; $("#show_name").css("color", "#d23600"); + $("#radial").css("color", "#d23600"); + $("#linear").css("color", "#555555"); $("#zoomValue").val('100'); outerRadius = w / 2.8, innerRadius = outerRadius - 170; diff --git a/js/phylo/panAndZoom.js b/js/phylo/panAndZoom.js index 412dc85..4bace05 100644 --- a/js/phylo/panAndZoom.js +++ b/js/phylo/panAndZoom.js @@ -25,7 +25,60 @@ d3.demo.canvas = function(life, info) { var yScale = d3.scaleLinear() .domain([-height / 2, height / 2]) .range([height, 0]); + var svg = selection.append("svg") + .attr("class", "svg canvas") + .attr("id","canvas") + .attr("preserveAspectRatio", "xMinYMid meet") + .attr("height", height) + .attr("height", width + 700) + .attr("viewBox", "0 0 " + (width + 700) + " " + height); + + creatDefs(svg, info, 80, "big"); + creatDefs(svg, info, 60, "mini"); + creatDefs(svg, info, 50, "xmini"); + + var svgDefs = svg.append("defs"); + + var filter = svgDefs.append("svg:filter") + .attr("id", "minimapDropShadow_gmult") + .attr("x", "-20%") + .attr("y", "-20%") + .attr("width", "150%") + .attr("height", "150%"); + + filter.append("svg:feOffset") + .attr("result", "offOut") + .attr("in", "SourceGraphic") + .attr("dx", "1") + .attr("dy", "1"); + + var innerWrapper = svg.append("g") + .attr("class", "wrapper inner") + .attr("transform", "translate(" + (wrapperBorder) + "," + (wrapperBorder) + ")") + + innerWrapper.append("g") + .attr("class", "timeLine"); + + innerWrapper.append("rect") + .attr("class", "background") + .attr("width", width) + .attr("height", height) + .style("cursor","default"); + + var panCanvas = innerWrapper.append("g") + .attr("class", "panCanvas") + .attr("width", width) + .attr("height", height) + .attr("transform", "translate(0,0)"); + + + panCanvas.append("rect") + .attr("class", "background") + .attr("width", width) + .attr("height", height) + + var zoomHandler = function(newScale) { if (d3.event) { scale = d3.event.transform.k; @@ -44,9 +97,19 @@ d3.demo.canvas = function(life, info) { Math.max(Math.min(translation[0], rbound), lbound), Math.max(Math.min(translation[1], bbound), tbound) ]; + console.log("translation") + console.log(translation) + + + } + //.attr("transform", d3.event.transform); - d3.select(".panCanvas, .panCanvas .bg") + /*if (d3.event.sourceEvent instanceof MouseEvent || d3.event.sourceEvent instanceof WheelEvent) { + minimap.update(d3.event.transform); + }*/ + + panCanvas .attr("transform", "translate(" + translation + ")" + " scale(" + scale + ")"); minimap.scale(scale).render(); @@ -56,57 +119,9 @@ d3.demo.canvas = function(life, info) { .scaleExtent([0.7, 1.7]) .on("zoom.canvas", zoomHandler); - var svg = selection.append("svg") - .attr("class", "svg canvas") - .attr("id","canvas") - .attr("preserveAspectRatio", "xMinYMid meet") - .attr("height", height) - .attr("height", width + 700) - .attr("viewBox", "0 0 " + (width + 700) + " " + height); - - creatDefs(svg, info, 80, "big"); - creatDefs(svg, info, 60, "mini"); - creatDefs(svg, info, 50, "xmini"); - - - var svgDefs = svg.append("defs"); - - var filter = svgDefs.append("svg:filter") - .attr("id", "minimapDropShadow_gmult") - .attr("x", "-20%") - .attr("y", "-20%") - .attr("width", "150%") - .attr("height", "150%"); - - filter.append("svg:feOffset") - .attr("result", "offOut") - .attr("in", "SourceGraphic") - .attr("dx", "1") - .attr("dy", "1"); - - var innerWrapper = svg.append("g") - .attr("class", "wrapper inner") - .attr("transform", "translate(" + (wrapperBorder) + "," + (wrapperBorder) + ")").call(zoom).on("dblclick.zoom", null); - - innerWrapper.append("g") - .attr("class", "timeLine"); - - innerWrapper.append("rect") - .attr("class", "background") - .attr("width", width) - .attr("height", height) - .style("cursor","default"); - - var panCanvas = innerWrapper.append("g") - .attr("class", "panCanvas") - .attr("width", width) - .attr("height", height) - .attr("transform", "translate(0,0)"); - - panCanvas.append("rect") - .attr("class", "background") - .attr("width", width) - .attr("height", height); + innerWrapper + .call(zoom) + .on("dblclick.zoom", null); miniBaseSvg = d3.select("#contextTree").append("svg") .attr("id", "miniBaseSvg"); @@ -116,7 +131,6 @@ d3.demo.canvas = function(life, info) { .target(panCanvas) .minimapScale(minimapScale); - miniBaseSvg.call(minimap); /** ADD SHAPE **/ @@ -259,10 +273,14 @@ d3.demo.minimap = function(life, info, baseSvg) { timeLineScale.rangeRound([0, w * scale2]); xAxis = d3.axisBottom(timeLineScale); + let tickLabels = ['300 million years ago', '250 million years ago', '200 million years ago', '150 million years ago','100 million years ago', '50 million years ago','Present']; + if(display == "linear"){ d3.select(".timeLine") - .attr("transform", "translate(" + frameTranslate[0] + "," + 0 + ")") - .call(xAxis.ticks(5)); + .attr("transform", "translate(" + (frameTranslate[0]+35) + "," + 0 + ")") + .call(xAxis.ticks(8).tickFormat((d,i) => tickLabels[i])) + .selectAll("text") + .style("font-size", "15px");; } } } @@ -288,7 +306,7 @@ d3.demo.minimap = function(life, info, baseSvg) { if(timeLineScale !== undefined){ d3.select(".timeLine") - .attr("transform", "translate(" + translate[0] + "," + 0 + ")"); + .attr("transform", "translate(" + (translate[0]+35) + "," + 0 + ")"); } } @@ -364,6 +382,17 @@ d3.demo.minimap = function(life, info, baseSvg) { height = parseInt(target.attr("height"), 10); return this; }; + + + /*minimap.update = function(hostTransform) { + // invert the incoming zoomTransform; ordering matters here! you have to scale() before you translate() + var modifiedTransform = d3.zoomIdentity.scale((1/hostTransform.k)).translate(-hostTransform.x, -hostTransform.y); + // call this.zoom.transform which will reuse the handleZoom method below + zoom.transform(frame, modifiedTransform); + // update the new transform onto the minimapCanvas which is where the zoomBehavior stores it since it was the call target during initialization + //container.property("__zoom", modifiedTransform); + return this; + };*/ return minimap; }; diff --git a/js/phylo/phylo.js b/js/phylo/phylo.js index 9f29c53..7389ec7 100644 --- a/js/phylo/phylo.js +++ b/js/phylo/phylo.js @@ -4,20 +4,22 @@ var outerRadius = null, innerRadius = null var w = 1770, h = 1361; var zoomValue, zoom; var selected = 0; +var page = 0; var wiki= {}, sName = {}; var display = "linear"; var miniCanvas, rootDists, timeLineScale, xAxis, frameTranslate, dragTransform = null, scale2 = 1; var overview = "open"; + + $(".button").hide(); $(".button").click(function(){ // window will load in the same tag window.location.replace("genome.html?" + str, 'genome view'); }); -$(".closeButton").on("click",function(){ - console.log("here2"); -}) + + @@ -58,7 +60,6 @@ d3.queue() $("#radial").click(function() { d3.selectAll('.panCanvas g').remove(); d3.selectAll('.miniCanvas g').remove(); - canvas.addRadialTree(); display = "radial"; addMiniMap(life, info) diff --git a/main.css b/main.css index 8643537..e6820a7 100644 --- a/main.css +++ b/main.css @@ -10,6 +10,266 @@ background-position: center; overflow: hidden; } + #brand-title { + font-size: x-large; + } + + .web-name { + cursor: default; + text-decoration:none !important; + color:#555555 !important; + } + .web-name:hover { + text-decoration:none !important; + color: #555555 !important; + } + + .modal { + display: flex; /* Hidden by default */ + position: fixed; /* Stay in place */ + z-index: 1; /* Sit on top */ + left: 0; + top: 0; + width: 100%; /* Full width */ + height: 100%; /* Full height */ + overflow: auto; /* Enable scroll if needed */ + background-color: rgb(0,0,0); /* Fallback color */ + background-color: rgba(0,0,0,0.4); /* Black w/ opacity */ + } + + .modal-content { + background-color: #fefefe; + margin: auto; + padding: 0px; + border: 0; + border-radius: 25px; + width: 60%; + height:70%; + } + +@media only screen and (max-width: 1100px) { + #modal-content-title { + position: relative; + margin: 0; + padding: 0 2%; + border-radius: 25px 25px 0 0; + display:flex; + border: 2px solid black; + width: 100%; /* Full width */ + height: 15%; /* Full height */ + background-color: #a29c9c; /* Fallback color */ + } + + #modal-content-body { + position: relative; + padding: 1% 2%; + margin:0; + display:flex; + border-left: 2px solid black; + border-right: 2px solid black; + width: 100%; /* Full width */ + height: 70%; /* Full height */ + background-color: #e5d6c4; /* Fallback color */ + } + + #modal-content-buttons { + position: relative; + margin:0; + padding:1%; + border-radius: 0 0 25px 25px; + border: 2px solid black; + display:flex; + width: 100%; /* Full width */ + height: 15%; /* Full height */ + background-color: #a29c9c; /* Fallback color */ + } + + .skip-button { + color: #af5147; + font-size: 2rem; + font-weight: bold; + } + + .skip-button:hover, + .skip-button:focus { + color: #000; + text-decoration: none; + cursor: pointer; + } + + .next-button { + font-size:0.7rem; + margin: 0 3%; + background-color: #111c3cbb; + color: white; + cursor: pointer; + padding: 0 8%; + border-radius: 10px; + } + + .previous-button { + font-size:0.7rem; + margin: 0; + background-color: #111c3cbb; + color: white; + cursor: pointer; + padding: 0 7%; + border-radius: 10px; + } +} + +@media only screen and (min-width: 1101px) { + #modal-content-title { + position: relative; + margin: 0; + padding: 0 3%; + border-radius: 25px 25px 0 0; + display:flex; + border: 2px solid black; + width: 100%; /* Full width */ + height: 15%; /* Full height */ + background-color: #a29c9c; /* Fallback color */ + } + + #modal-content-body { + position: relative; + padding: 1% 3%; + margin:0; + display:flex; + border-left: 2px solid black; + border-right: 2px solid black; + width: 100%; /* Full width */ + height: 70%; /* Full height */ + background-color: #e5d6c4; /* Fallback color */ + } + + #modal-content-buttons { + position: relative; + margin:0; + padding:1%; + border-radius: 0 0 25px 25px; + border: 2px solid black; + display:flex; + width: 100%; /* Full width */ + height: 15%; /* Full height */ + background-color: #a29c9c; /* Fallback color */ + } + + .skip-button { + color: #af5147; + font-size: 3rem; + font-weight: bold; + } + + .skip-button:hover, + .skip-button:focus { + color: #000; + text-decoration: none; + cursor: pointer; + } + + .next-button { + font-size:1.3rem; + margin: 0 3%; + background-color: #111c3cbb; + color: white; + cursor: pointer; + padding: 0 8%; + border-radius: 10px; + } + + .previous-button { + font-size:1.3rem; + margin: 0; + background-color: #111c3cbb; + color: white; + cursor: pointer; + padding: 0 8%; + border-radius: 10px; + } +} + +@media only screen and (min-width: 2000px) { + #modal-content-title { + position: relative; + margin: 0; + padding: 0 5%; + border-radius: 25px 25px 0 0; + display:flex; + border: 2px solid black; + width: 100%; /* Full width */ + height: 15%; /* Full height */ + background-color: #a29c9c; /* Fallback color */ + } + + #modal-content-body { + position: relative; + padding: 2% 5%; + margin:0; + display:flex; + border-left: 2px solid black; + border-right: 2px solid black; + width: 100%; /* Full width */ + height: 70%; /* Full height */ + background-color: #e5d6c4; /* Fallback color */ + } + + #modal-content-buttons { + position: relative; + margin:0; + padding:2%; + border-radius: 0 0 25px 25px; + border: 2px solid black; + display:flex; + width: 100%; /* Full width */ + height: 15%; /* Full height */ + background-color: #a29c9c; /* Fallback color */ + } + + .skip-button { + color: #af5147; + font-size: 5rem; + font-weight: bold; + } + + .skip-button:hover, + .skip-button:focus { + color: #000; + text-decoration: none; + cursor: pointer; + } + + .next-button { + font-size:1.8rem; + margin: 0 3%; + background-color: #111c3cbb; + color: white; + cursor: pointer; + padding: 0 8%; + border-radius: 10px; + } + + .previous-button { + font-size:1.8rem; + margin: 0; + background-color: #111c3cbb; + color: white; + cursor: pointer; + padding: 0 7%; + border-radius: 10px; + } +} + + + #genome_intro_slides { + display: none; + } + + #phylo_intro_slides { + display: none; +} + + p{ font-family: 'Raleway', sans-serif; } @@ -150,6 +410,7 @@ border-style: solid; border-width: 3px; border-color: rgba(115, 115, 115,.5); + text-align: center; } .boxOne { position: fixed; @@ -166,6 +427,7 @@ overflow: hidden; } .textArea{ + margin-top: 16px; height: 60%; font-size:0.75vw; line-height: 20px; diff --git a/phylo.html b/phylo.html new file mode 100644 index 0000000..83c689d --- /dev/null +++ b/phylo.html @@ -0,0 +1,118 @@ + + + + + + + + + + + + + + + + +
+ + +
+
+
+

overview

+
+
+
+
+
+
+
+

Click on two different animals from the phylogenetic tree to select, + and then go to the chromosome view to see the genome evolution and + divergence of the two species, based on common ancestors!

+
+ +
+
+ +
+
+
+

Click Icons to Select Species.

+
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + +
+ + + \ No newline at end of file