├── .gitignore ├── .npmignore ├── .DS_Store ├── index.js ├── src ├── .DS_Store └── d3-electrophoresis.js ├── test ├── .DS_Store └── d3-electrophoresis_test.js ├── assets ├── result_scale_200-400_1.png ├── result_text_name1_small1.png ├── electrophoresis_trump-speech_cleanbench1_small1.jpg └── electrophoresis_trump-speech_cleanbench1_up1_smal1.jpg ├── package.json ├── LICENSE ├── examples ├── d3-electrophoresis_simple1.html ├── d3-electrophoresis_switch_DNA_sequence1.html └── d3-electrophoresis_switch_trump-inauguration1.html └── README.md /.gitignore: -------------------------------------------------------------------------------- 1 | node_modules -------------------------------------------------------------------------------- /.npmignore: -------------------------------------------------------------------------------- 1 | node_modules 2 | assets -------------------------------------------------------------------------------- /.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/.DS_Store -------------------------------------------------------------------------------- /index.js: -------------------------------------------------------------------------------- 1 | export {default as electrophoresis} from "./src/d3-electrophoresis"; 2 | -------------------------------------------------------------------------------- /src/.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/src/.DS_Store -------------------------------------------------------------------------------- /test/.DS_Store: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/test/.DS_Store -------------------------------------------------------------------------------- /assets/result_scale_200-400_1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/assets/result_scale_200-400_1.png -------------------------------------------------------------------------------- /assets/result_text_name1_small1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/assets/result_text_name1_small1.png -------------------------------------------------------------------------------- /assets/electrophoresis_trump-speech_cleanbench1_small1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/assets/electrophoresis_trump-speech_cleanbench1_small1.jpg -------------------------------------------------------------------------------- /assets/electrophoresis_trump-speech_cleanbench1_up1_smal1.jpg: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/squarednob/d3-electrophoresis/HEAD/assets/electrophoresis_trump-speech_cleanbench1_up1_smal1.jpg -------------------------------------------------------------------------------- /test/d3-electrophoresis_test.js: -------------------------------------------------------------------------------- 1 | // install tape with "npm instll tape". 2 | // From top folder, "node test/d3-electrophoresis_test.js". 3 | var test = require("../node_modules/tape"); 4 | var elect = require("../src/d3-electrophoresis.js"); 5 | 6 | test("test_test1", function(t){ 7 | t.equal(1+1, 2); 8 | t.end(); 9 | }) 10 | -------------------------------------------------------------------------------- /package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "d3-electrophoresis", 3 | "version": "1.0.3", 4 | "description": "D3.js plugin to simulate electrophoresis by cutting text.", 5 | "main": "index.js", 6 | "directories": { 7 | "test": "test" 8 | }, 9 | "dependencies": {}, 10 | "devDependencies": { 11 | "tape": "^4.6.3" 12 | }, 13 | "scripts": { 14 | "test": "node test/d3-electrophoresis_test.js" 15 | }, 16 | "repository": { 17 | "type": "git", 18 | "url": "git+https://github.com/squarednob/d3-electrophoresis.git" 19 | }, 20 | "keywords": [ 21 | "d3", 22 | "d3-module", 23 | "svg", 24 | "visualization", 25 | "data", 26 | "biology", 27 | "NLP" 28 | ], 29 | "author": "Nobuyuki Hirakata", 30 | "url": "http://gappyfacets.com/", 31 | "license": "MIT", 32 | "bugs": { 33 | "url": "https://github.com/squarednob/d3-electrophoresis/issues" 34 | }, 35 | "homepage": "https://github.com/squarednob/d3-electrophoresis#readme" 36 | } 37 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2017 squarednob 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /examples/d3-electrophoresis_simple1.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 |
11 | 12 |
13 | 14 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # d3-electrophoresis 2 | A D3.js plugin to simulate electrophoresis which is a basic biotechnological technique to visualize length of DNA segments cut by restriction enzyme. 3 | Using this plugin, you can cut not only DNA sequence, but also any text, by words. 4 | 5 | ### Examples 6 | #### Cutting text by words 7 | ![result_text_name1_small1.png](assets/result_text_name1_small1.png) 8 | 9 | You can change text and words in the showcases. 10 | * Simple example: [Showcase and code](https://bl.ocks.org/squarednob/bd2a39f09d177c99b982ca406ca9cf1d). 11 | * Changinge scale: [showcase and code](https://bl.ocks.org/squarednob/fc711a3e6a25800efbf03067b0231825). 12 | * Trump inauguration text: [Showcase](https://bl.ocks.org/squarednob/raw/846808f07995e537dc7af2e9bcffdf3b/), [Code](https://bl.ocks.org/squarednob/846808f07995e537dc7af2e9bcffdf3b). 13 | * DNA sequence: [Showcas](https://bl.ocks.org/squarednob/raw/959bac1f4eca03059e02dbd480982c60/), [Code](https://bl.ocks.org/squarednob/959bac1f4eca03059e02dbd480982c60). 14 | 15 | 16 | 17 | ##### Using SVG for CGI 18 | By [SVG Crowbar](http://nytimes.github.io/svg-crowbar/), you can download the resulted DNA bands as SVG. And the SVG can be used for, such as 3D object in Blender. The CGI image below was made with Blender, including SVG bands in the gel. 19 | 20 | The detail and other images are on the blog: [New D3.js plugin: D3-electrophoresis released](http://gappyfacets.com/2017/02/18/new-d3-js-plugin-d3-electrophoresis-released/). 21 | ![electrophoresis_trump-speech_cleanbench1_up1_smal1.jpg](assets/electrophoresis_trump-speech_cleanbench1_up1_smal1.jpg) 22 | 23 | ### Install 24 | 1. Download [d3-electrophoresis.js](https://raw.githubusercontent.com/squarednob/d3-electrophoresis/master/src/d3-electrophoresis.js) from right click, or use npm `npm install d3-electrophoresis` and get it in "src" folder. 25 | 2. In HTML, load D3.js (__v.4__) and d3-electrophoresis.js with ` 29 | 30 | ``` 31 | 32 | ### Basic Usage 33 | ```js 34 | var gel = electrophoresis(); 35 | 36 | var svg = d3.select("body").append("svg") 37 | .attr("width", 460) 38 | .attr("height", 500) 39 | .call(gel.makeGel); // Make black background first. 40 | 41 | var text = "AGCGCCCAATACGCAAACCGCCTCTCCCCGCGCGTTGGCCGATTCACGTTTACGAGTTGGAAACGA"; 42 | var words = [[1,5,10,15,20,30,40,50,70,100],"CAAA","GTTGG","GGATCC", "GA",["GT","CCT"],"ACC", "GAAA"]; 43 | var names = ["marker", "1", "2", "3", "4", "5", "6", "7"]; 44 | // You can set every parameter by dictionary or method-chain. Example: {DNA: text} or .DNA(text). 45 | gel = electrophoresis().DNA(text).enzymes(words).names(names); 46 | svg.call(gel); 47 | ``` 48 | 49 | ### Parameters 50 | You can set every parameter by dictionary input: 51 | ```js 52 | var gel = electrophoresis({DNA:"agtctatcacg", enzymes:["ac","gca"]}); 53 | ``` 54 | __and/or__ by method-chain: 55 | ```js 56 | var gel = electrophoresis().DNA("agtctatcacg").enzymes(["ac","gca"]); 57 | ``` 58 | 59 | ### Tips 60 | #### Changing scale 61 | ![result_scale_200-400_1.png](assets/result_scale_200-400_1.png) 62 | 63 | To change vertical scale of band, like changing gel concentration, use `.scale()` chain, and input d3's scale object. 64 | 65 | For example, to make band within y=200 to 400 in linear scale, add scale() chain after electrophoresis().~, and input d3-scale object: 66 | ```js 67 | var yScale = d3.scaleLinear().range([200,400]); 68 | gel = electrophoresis({DNA: text}).enzymes(words).names(names).scale(yScale); 69 | ``` 70 | [Demo](https://bl.ocks.org/squarednob/fc711a3e6a25800efbf03067b0231825). 71 | 72 | ### API Reference 73 | # electrophoresis.__DNA__([_text_]) 74 | 75 | Target text to be cut. 76 | 77 | Default: _"AGCGCCCAATACGCAAACCGCCTCTCCCCGCGCGTTGGCCGATTCACGTTTACGAGTTGGAAACGA"_. 78 | 79 | # electrophoresis.__enzymes__([_list_]) 80 | 81 | Word list to cut target text. 82 | 83 | When the word list includes a number list as a element, (e.g. _["AC",[10,15,20]]_), the numbers are directly used as resulted length of cut segmented text without cutting text. When the word list includes a word list as a element, (e.g. _["AC",["GT","CCT"]]_), target text is cut by both of the two words all together. 84 | 85 | Default: _[[1,5,10,15,20,30,40,50,70,100],"CAAA","GTTGG","GGATCC", "GA",["GT","CCT"],"ACC", "GAAA"]_. 86 | 87 | # electrophoresis.__names__([_list_]) 88 | 89 | Name list of enzymes. They appear as tooltips on each resulted lane. 90 | 91 | Default: _["marker", "1", "2", "3", "4", "5", "6", "7"]_. 92 | 93 | # electrophoresis.__scale__([_obj_]) 94 | 95 | A scale to map length values of segmented texts from top to the bottom. The input must be a scale object in D3-v.4 syntax, such as `d3.scaleSqrt()`, `d3.scaleLinear()`, `d3.scalePow()` .etc. See how to use [d3/d3-scale](https://github.com/d3/d3-scale). 96 | 97 | To make band within height of 200-500 in linear scale, for example, use `d3.scaleLinear().range([200, 500]))`. 98 | 99 | Default: _`d3.scaleLinear()`_. 100 | 101 | # electrophoresis.__lane_number__([_int_]) 102 | 103 | Max number of lanes. 104 | 105 | Default: _8_. 106 | 107 | # electrophoresis.__gel_margin__([_dict_]) 108 | 109 | Margin size from edges of background. 110 | 111 | Default: _{top: 40, right: 20, bottom: 30, left: 20}_. 112 | 113 | # electrophoresis.__duration__([_float_]) 114 | 115 | Time to finish animation. 116 | 117 | Default: _6000_. 118 | 119 | # electrophoresis.__band_width__([_float_]) 120 | 121 | Width of bands. 122 | 123 | Default: _38_. 124 | 125 | # electrophoresis.__band_blur__([_float_]) 126 | 127 | Blur of bands. 128 | 129 | Default: _2_. 130 | 131 | # electrophoresis.__band_thick_min__([_float_]) 132 | 133 | Minimum thickness of bands. 134 | 135 | Default: _1_. 136 | 137 | # electrophoresis.__band_thick_rate__([_float_]) 138 | 139 | How bands turns less thick as the bands go down. 140 | 141 | Default: _0.04_ 142 | 143 | # electrophoresis.__tooltip_name_on__([_str_]) 144 | 145 | "on" or "off" for tooltips of enzyme name on upper side. 146 | 147 | Default: _"on"_. 148 | 149 | # electrophoresis.__tooltip_name_size__([_float_]) 150 | 151 | Size of name tooltips. 152 | 153 | Default: _17_. 154 | 155 | # electrophoresis.__tooltip_name_offsetX__([_float_]) 156 | 157 | Horizontal offset of name tooltips. 158 | 159 | Default: _0_. 160 | 161 | # electrophoresis.__tooltip_name_offsetY__([_float_]) 162 | 163 | Vertical Offset of name tooltips. 164 | 165 | Default: _20_. 166 | 167 | # electrophoresis.__tooltip_band_on__([_str_]) 168 | 169 | "on" or "off" for tooltips of band length. 170 | 171 | Default: _"on"_; 172 | 173 | # electrophoresis.__tooltip_band_size__([_float_]) 174 | 175 | size of band tooltips. 176 | 177 | Default: _13_. 178 | 179 | # electrophoresis.__tooltip_band_offsetX__([_float_]) 180 | 181 | Horizontal offset of band tooltips. 182 | 183 | Default: _0_. 184 | 185 | # electrophoresis.__tooltip_band_offsetY__([_float_]) 186 | 187 | Vertical offset of band tooltips. 188 | 189 | Default: _0_. 190 | -------------------------------------------------------------------------------- /examples/d3-electrophoresis_switch_DNA_sequence1.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | D3 Electrophoresis Generator 6 | 7 | 8 | 9 | 10 | 11 | 12 |
13 |
14 | 15 |
16 |
17 |   18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 |
27 |
28 |   29 | 30 | 31 |
32 | 33 |
34 | DNA Text:
35 | 94 |
95 | Wells with restriction enzyme:
96 | 97 | 98 | 99 | 100 | 101 | 102 | 103 | 104 |
105 |
106 | 107 | 176 | 177 | 178 | -------------------------------------------------------------------------------- /examples/d3-electrophoresis_switch_trump-inauguration1.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | D3 Electrophoresis Generator 6 | 7 | 8 | 9 | 10 | 11 | 12 |
13 |
14 | 15 |
16 |
17 |   18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 |
27 |
28 |   29 | 30 | 31 |
32 | 33 |
34 | DNA Text:
35 | 101 |
102 | Wells with restriction enzyme:
103 | 104 | 105 | 106 | 107 | 108 | 109 | 110 | 111 |
112 |
113 | 114 | 182 | 183 | 184 | -------------------------------------------------------------------------------- /src/d3-electrophoresis.js: -------------------------------------------------------------------------------- 1 | 2 | function electrophoresis(config){ 3 | // ---------------Dict arguments ---------------- 4 | var config = (config === undefined) ? {} : config; 5 | config.DNA = (config.DNA === undefined) ? "AGCGCCCAATACGCAAACCGCCTCTCCCCGCGCGTTGGCCGATTCACGTTTACGAGTTGGAAACGA" : config.DNA; 6 | config.enzymes = (config.enzymes === undefined) ? [[1,5,10,15,20,30,40,50,70,100],"CAAA","GTTGG","GGATCC", "GA",["GT","CCT"],"ACC", "GAAA"] : config.enzymes; 7 | config.names = (config.names === undefined) ? ["marker", "1", "2", "3", "4", "5", "6", "7"]: config.names; 8 | config.scale = (config.scale === undefined) ? d3.scaleSqrt(): config.scale; 9 | config.lane_number = (config.lane_number === undefined) ? 8 : config.lane_number; 10 | config.gel_margin = (config.gel_margin === undefined) ? {top: 40, right: 20, bottom: 30, left: 20} : config.gel_margin; 11 | config.duration = (config.duration === undefined) ? 6000: config.duration; 12 | config.band_width = (config.band_width === undefined) ? 38 : config.band_width; 13 | config.band_blur = (config.band_blur === undefined) ? 2 : config.band_blur; 14 | config.band_thick_min = (config.band_thick_min === undefined) ? 1 : config.band_thick_min; 15 | config.band_thick_rate = (config.band_thick_rate === undefined) ? 0.04 : config.band_thick_rate; 16 | config.tooltip_name_on = (config.tooltip_name_on === undefined) ? "on" : config.tooltip_name_on; 17 | config.tooltip_name_size = (config.tooltip_name_size === undefined) ? 17 : config.tooltip_name_size; 18 | config.tooltip_name_offsetX = (config.tooltip_name_offsetX === undefined) ? 0 : config.tooltip_name_offsetX; 19 | config.tooltip_name_offsetY = (config.tooltip_name_offsetY === undefined) ? 20 : config.tooltip_name_offsetY; 20 | config.tooltip_band_on = (config.tooltip_band_on === undefined) ? "on" : config.tooltip_band_on; 21 | config.tooltip_band_size = (config.tooltip_band_size === undefined) ? 13 : config.tooltip_band_size; 22 | config.tooltip_band_offsetX = (config.tooltip_band_offsetX === undefined) ? 0 : config.tooltip_band_offsetX; 23 | config.tooltip_band_offsetY = (config.tooltip_band_offsetY === undefined) ? 0 : config.tooltip_band_offsetY; 24 | 25 | 26 | function elect(selection){ 27 | // ---------------- Define functiions--------------- 28 | function makeLenList(fragments, enzyme){ 29 | var len_list = []; 30 | var enzyme_half1 = Math.round(enzyme.length/2); 31 | var enzyme_half2 = enzyme.length - enzyme_half1; 32 | 33 | fragments.forEach(function(fragment){ 34 | var no_blank = fragment.replace(/\s*/g, ""); 35 | len_list.push(fragment.length); 36 | }); 37 | 38 | // Distribute Enzyme strings at each cut end to fill the deleted parts by split(). 39 | if (len_list.length > 1){ 40 | len_list.forEach(function(d,i){ 41 | if (i != 0){ 42 | len_list[i] = len_list[i] + enzyme_half1; 43 | } 44 | if (i != len_list.length-1){ 45 | len_list[i] += enzyme_half2; 46 | } 47 | }) 48 | } 49 | return len_list; 50 | } 51 | 52 | function cutDNA(DNA_seq, enzymes){ 53 | var len_list = []; 54 | var fragments = []; 55 | if(typeof DNA_seq === "string"){ 56 | DNA_seq = DNA_seq.toUpperCase(); 57 | } 58 | 59 | // If enzyme is a list. 60 | if (enzymes.constructor === Array){ 61 | var len_list_temp = []; 62 | fragments = [DNA_seq]; 63 | enzymes.forEach(function(enzyme){ 64 | if (typeof enzyme == "number"){ 65 | len_list = len_list.concat(enzyme); 66 | } 67 | // Cut string by multiple strings. 68 | if (typeof enzyme == "string"){ 69 | var fragments_temp = []; 70 | fragments = fragments.map(function(frag){ 71 | enzyme = enzyme.toUpperCase(); 72 | return frag.split(enzyme); 73 | }); 74 | // Flatten lists. 75 | fragments = [].concat.apply([], fragments); 76 | len_list_temp = len_list_temp.concat(makeLenList(fragments, enzyme)); 77 | } 78 | }); 79 | 80 | len_list = len_list.concat(len_list_temp); 81 | return len_list; 82 | } // If enzyme is not a list. 83 | else { 84 | if (typeof enzymes === "number"){ 85 | len_list.push(enzymes); 86 | return len_list; 87 | } 88 | if (typeof enzymes === "string"){ 89 | enzymes = enzymes.toUpperCase(); 90 | fragments = DNA_seq.split(enzymes); 91 | len_list = makeLenList(fragments, enzymes); 92 | return len_list; 93 | } 94 | } 95 | } 96 | 97 | // --------------- Make SVG ------------------ 98 | function electrify(len_list, name_list, lane_number, band_width, band_duration, 99 | yScale, gel_margin, blur, thick_min, thick_rate, 100 | tooltip_name_on, tooltip_name_size, tooltip_name_offsetX, tooltip_name_offsetY, 101 | tooltip_band_on, tooltip_band_size, tooltip_band_offsetX,tooltip_band_offsetY) { 102 | 103 | var gel_width = selection.attr("width") - gel_margin.left - gel_margin.right; 104 | var gel_height = selection.attr("height") - gel_margin.top - gel_margin.bottom; 105 | var max_value = d3.max(d3.merge(len_list)); 106 | 107 | // if range or domain is default, set min-max. 108 | if (yScale.domain().toString() == [0, 1].toString()){ 109 | yScale.domain([0, max_value]); 110 | } 111 | if (yScale.range().toString() == [0, 1].toString()){ 112 | yScale.range([gel_height,0]); 113 | } else { 114 | var yScale_range0 = yScale.range()[0]; 115 | var yScale_range1 = yScale.range()[1]; 116 | yScale.range([yScale_range1, yScale_range0]); 117 | } 118 | 119 | // Filter for blur. 120 | var lane_filter = selection.append("defs").attr("class", "gel") 121 | .append("filter").attr("id", "gel-filter").attr("height","500%").attr("widht","100%") 122 | .append("feGaussianBlur").attr("in", "SourceGraphic").attr("stdDeviation", blur).attr("result", "blur") 123 | .append("feOffset").attr("result","offsetBlur").attr("dx",0).attr("dy",-5) 124 | .append("feBrend").attr("in","blur").attr("in2","offsetBlur").attr("mode","normal"); 125 | 126 | gel= selection.append("g") 127 | .attr("class", "gel") 128 | .attr("transform", "translate(" + gel_margin.left + "," + gel_margin.top + ")"); 129 | 130 | var lanes = gel.selectAll("g .gel-lane") 131 | .data(len_list).enter() 132 | .append("g") 133 | .attr("class", "gel-lane") 134 | .attr("transform", function(d,i){return "translate(" + i*(gel_width/lane_number) + "," + 0 + ")";}); 135 | 136 | var rects = lanes.selectAll("g .gel-band") 137 | .data(function(d){return d;}) 138 | .enter() 139 | .append("g") 140 | .attr("class","gel-band"); 141 | 142 | var rectAttr = rects.append("rect") 143 | .attr("x", function(d){return 2;}) 144 | .attr("y", function(d){return 0;}) 145 | .attr("width", band_width) 146 | .attr("height", 12) 147 | .attr("fill", "white") 148 | .attr("filter", "url(#gel-filter)") // Apply blur filter. 149 | .transition() 150 | .attr("height", function(d){ return thick_min + ((gel_height-yScale(d)) * thick_rate); }) 151 | .attr("y", function(d){ return yScale(d);}) 152 | .duration(band_duration); 153 | 154 | if(tooltip_name_on == "on"){ 155 | var tooltips_name = lanes.append("text") 156 | .attr("class","gel-tooltip") 157 | .attr("fill","white") 158 | .attr("font-size",tooltip_name_size) 159 | .attr("text-anchor", "middle") 160 | .attr("x", (gel_width/lane_number/3) + tooltip_name_offsetX) 161 | .attr("y",-(gel_margin.top - tooltip_name_offsetY)) 162 | .text(function(d,i){ return name_list[i]; }) 163 | .attr("opacity", 0); 164 | 165 | tooltips_name.transition() 166 | .duration(1000) 167 | .delay(band_duration) 168 | .attr("opacity", 1); 169 | } 170 | if(tooltip_band_on == "on"){ 171 | var tooltips_band = rects.append("text") 172 | .attr("class","gel-tooltip") 173 | .attr("fill","white") 174 | .attr("font-size",tooltip_band_size) 175 | .attr("x",tooltip_band_offsetX) 176 | .attr("y",function(d){ return yScale(d) + tooltip_band_offsetY;}) 177 | .text(function(d){return d;}) 178 | .attr("opacity", 0); 179 | 180 | tooltips_band.transition() 181 | .duration(1500) 182 | .delay(band_duration+800) 183 | .attr("opacity", 1); 184 | } 185 | } 186 | 187 | // ----------------- Execute ------------------ 188 | var len_list = []; 189 | config.enzymes.forEach(function(enzyme){ 190 | len_list.push(cutDNA(config.DNA, enzyme)); 191 | }); 192 | electrify(len_list, config.names, 193 | lane_number=config.lane_number, 194 | band_width=config.band_width,band_duration=config.duration, 195 | yScale=config.scale, gel_margin=config.gel_margin, blur=config.band_blur, 196 | thick_min=config.band_thick_min, thick_rate=config.band_thick_rate, 197 | tooltip_name_on=config.tooltip_name_on, tooltip_name_size=config.tooltip_name_size, 198 | tooltip_name_offsetX=config.tooltip_name_offsetX, tooltip_name_offsetY=config.tooltip_name_offsetY, 199 | tooltip_band_on=config.tooltip_band_on, tooltip_band_size=config.tooltip_band_size, 200 | tooltip_band_offsetX=config.tooltip_band_offsetX, tooltip_band_offsetY=config.tooltip_band_offsetY); 201 | } 202 | 203 | // --------------- Method Chain -------------- 204 | // Make black background by .call() before make bands. 205 | elect.makeGel = function(selection) { 206 | selection.append("rect") 207 | .attr("width", "100%") 208 | .attr("height", "100%") 209 | .attr("fill", "#222222"); 210 | return elect; 211 | }; 212 | elect.DNA = function(value) { 213 | if (!arguments.length) return config.DNA; 214 | config.DNA = value; 215 | return elect; 216 | }; 217 | elect.enzymes = function(value) { 218 | if (!arguments.length) return config.enzymes; 219 | config.enzymes = value; 220 | return elect; 221 | }; 222 | elect.names = function(value) { 223 | if (!arguments.length) return config.names; 224 | config.names = value; 225 | return elect; 226 | }; 227 | elect.scale = function(value) { 228 | if (!arguments.length) return config.scale; 229 | config.scale = value; 230 | return elect; 231 | }; 232 | elect.lane_number = function(value) { 233 | if (!arguments.length) return config.lane_number; 234 | config.lane_number = value; 235 | return elect; 236 | }; 237 | elect.gel_margin = function(value) { 238 | if (!arguments.length) return config.gel_margin; 239 | config.gel_margin = value; 240 | return elect; 241 | }; 242 | elect.duration = function(value) { 243 | if (!arguments.length) return config.duration; 244 | config.duration = value; 245 | return elect; 246 | }; 247 | elect.band_width = function(value) { 248 | if (!arguments.length) return config.band_width; 249 | config.band_width = value; 250 | return elect; 251 | }; 252 | elect.band_blur = function(value) { 253 | if (!arguments.length) return config.band_blur; 254 | config.band_blur = value; 255 | return elect; 256 | }; 257 | elect.band_thick_min = function(value) { 258 | if (!arguments.length) return config.band_thick_min; 259 | config.band_thick_min = value; 260 | return elect; 261 | }; 262 | elect.band_thick_rate = function(value) { 263 | if (!arguments.length) return config.band_thick_rate; 264 | config.band_thick_rate = value; 265 | return elect; 266 | }; 267 | elect.tooltip_name_on = function(value) { 268 | if (!arguments.length) return config.tooltip_name_on; 269 | config.tooltip_name_on = value; 270 | return elect; 271 | }; 272 | elect.tooltip_name_size = function(value) { 273 | if (!arguments.length) return config.tooltip_name_size; 274 | config.tooltip_name_size = value; 275 | return elect; 276 | }; 277 | elect.tooltip_name_offsetX = function(value) { 278 | if (!arguments.length) return config.tooltip_name_offsetX; 279 | config.tooltip_name_offsetX = value; 280 | return elect; 281 | }; 282 | elect.tooltip_name_offsetY = function(value) { 283 | if (!arguments.length) return config.tooltip_name_offsetY; 284 | config.tooltip_name_offsetY = value; 285 | return elect; 286 | }; 287 | elect.tooltip_band_on = function(value) { 288 | if (!arguments.length) return config.tooltip_band_on; 289 | config.tooltip_band_on = value; 290 | return elect; 291 | }; 292 | elect.tooltip_band_size = function(value) { 293 | if (!arguments.length) return config.tooltip_band_size; 294 | config.tooltip_band_size = value; 295 | return elect; 296 | }; 297 | elect.tooltip_band_offsetX = function(value) { 298 | if (!arguments.length) return config.tooltip_band_offsetX; 299 | config.tooltip_band_offsetX = value; 300 | return elect; 301 | }; 302 | elect.tooltip_band_offsetY = function(value) { 303 | if (!arguments.length) return config.tooltip_band_offsetY; 304 | config.tooltip_band_offsetY = value; 305 | return elect; 306 | }; 307 | 308 | return elect; 309 | } 310 | --------------------------------------------------------------------------------