choropleth.js 6.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258
  1. Shiny.addCustomMessageHandler("choropleth_values", function(message) {
  2. var choropleth_data = message[0][1];
  3. var heatmap_data = message[1];
  4. var mesos_data = message[2];
  5. // Create dropdown menu
  6. var years = [2012, 2013, 2014, 2015, 2016, 2017];
  7. var margin = { top: 0, right: 0, bottom: 0, left: 0 },
  8. width = window.innerWidth * 0.3,
  9. height = window.innerHeight * 0.7;
  10. // Sizes for small multiples
  11. var swidth = window.innerWidth * 0.6,
  12. sheight = window.innerHeight * 0.2;
  13. var select = d3.select("#choropleth_dropdown_area")
  14. .append('select')
  15. .attr('class', 'year_select')
  16. .on('change', onchange);
  17. var options = select.selectAll('options')
  18. .data(years)
  19. .enter()
  20. .append('option')
  21. .text(function(d) { return d;});
  22. draw(choropleth_data);
  23. function onchange() {
  24. var selectValue = d3.select('.year_select')
  25. .property('value');
  26. if (selectValue == "2012") {
  27. draw(message[0][0]);
  28. } else if (selectValue == "2013") {
  29. draw(message[0][1]);
  30. } else if (selectValue == "2014"){
  31. draw(message[0][2]);
  32. } else if (selectValue == "2015") {
  33. draw(message[0][3]);
  34. } else if (selectValue == "2016") {
  35. draw(message[0][4]);
  36. } else if (selectValue == "2017") {
  37. draw(message[0][5]);
  38. }
  39. }
  40. var tooltip = d3.select("body")
  41. .append("div")
  42. .style("position", "absolute")
  43. .style("z-index", "10")
  44. .style("visibility", "hidden")
  45. .style("color", "white")
  46. .style("padding", "8px")
  47. .style("background-color", "rgba(0, 0, 0, 0.75)")
  48. .style("border-radius", "6px")
  49. .style("font", "12px sans-serif")
  50. .text("tooltip");
  51. var projection = d3.geoEquirectangular();
  52. var path = d3.geoPath()
  53. .projection(projection);
  54. var x = d3.scaleLinear()
  55. .domain(choropleth_data.percentage)
  56. .rangeRound([600, 860]);
  57. var dataDomain = [];
  58. function getDomain (l) {
  59. var v = d3.max(l) / 9;
  60. return [v, v*2, v*3, v*4, v*5, v*6, v*7, v*8];
  61. }
  62. var color = d3.scaleThreshold()
  63. .domain(getDomain(choropleth_data.percentage)).range(d3.schemeBlues[9]);
  64. var choropleth = d3.select("#choropleth_area")
  65. .append("svg")
  66. .attr("width", width)
  67. .attr("height", height);
  68. var zooming = function(o) {
  69. var offset = [d3.event.transform.x, d3.event.transform.y];
  70. var newScale = d3.event.transform.k * 2000;
  71. projection.translate(offset)
  72. .scale(newScale);
  73. choropleth.selectAll("path")
  74. .style("stroke", "black")
  75. .style("stroke-width", 1)
  76. .attr("d", path);
  77. };
  78. var zoom = d3.zoom()
  79. .on("zoom", zooming);
  80. var center = projection([-12.1, -50.6]);
  81. var map = choropleth.append("g")
  82. .attr("id", "map")
  83. .call(zoom)
  84. .call(zoom.transform, d3.zoomIdentity
  85. .translate(width*1.5, height/3)
  86. .scale(0.25));
  87. //invisible rect covering all svg, so we can drag anywhere
  88. map.append("rect")
  89. .attr("x", 0)
  90. .attr("y", 0)
  91. .attr("width", width)
  92. .attr("height", height)
  93. .attr("opacity", 0);
  94. function draw(dataset) {
  95. d3.select("#choropleth_area").selectAll("#painted").remove();
  96. d3.json("uf.json").then(function(json) {
  97. for (var i = 0; i < dataset.uf.length; i++) {
  98. var dataState = dataset.uf[i];
  99. var dataValue = parseFloat(dataset.percentage[i]);
  100. for (var j = 0; j < json.features.length; j++) {
  101. var jsonState = json.features[j].properties.NOME_UF;
  102. if (dataState == jsonState) {
  103. json.features[j].properties.value = dataValue;
  104. break;
  105. }
  106. }
  107. }
  108. map.selectAll("path")
  109. .data(json.features)
  110. .enter()
  111. .append("path")
  112. .attr("d", path).attr("id", "painted")
  113. .style("stroke", "black")
  114. .style("stroke-width", 1)
  115. .style("fill",function(d) {
  116. var value = d.properties.value;
  117. if (value) {
  118. return color(value);
  119. } else {
  120. return "#ccc";
  121. }
  122. })
  123. .on("mouseover", function(d){
  124. d3.select(this).style("stroke", "orange")
  125. .style("stroke-width", 2);
  126. tooltip.html(d.properties.NOME_UF);
  127. return tooltip.style("visibility", "visible").style("opacity", 1);
  128. })
  129. .on("mouseout", function(d){
  130. d3.select(this).style("stroke", "black")
  131. .style("stroke-width", 1);
  132. tooltip.html(d.properties.NOME_UF);
  133. return tooltip.style("visibility", "hidden").style("opacity", 1);
  134. }).on("mousemove", function() {
  135. d3.select(this)
  136. .style("stroke", "orange")
  137. .style("stroke-width", "1px");
  138. return tooltip.style("top",(d3.event.pageY-10)+"px").style("left",(d3.event.pageX+10)+"px");
  139. })
  140. .on("click", function(d) {
  141. drawSmallMultiples(d, mesos_data);
  142. //From heatmap.js
  143. drawHeatMaps(heatmap_data, d.properties.NOME_UF);
  144. });
  145. });
  146. }
  147. //Draw isolated states
  148. function drawSmallMultiples (location, mesos_data) {
  149. d3.select("#smallmultiples_container").selectAll("svg").remove();
  150. d3.select("#heatmap_stripes_area").selectAll("svg").remove();
  151. var locationSet = [];
  152. d3.json("mesorregiao.json").then(function(json) {
  153. var ufLocation = location.properties.NOME_UF;
  154. for (var j = 0; j < json.features.length; j++) {
  155. var jsonState = json.features[j].properties.UF;
  156. if (ufLocation == jsonState) {
  157. locationSet.push(json.features[j]);
  158. }
  159. }
  160. var spath = d3.geoPath()
  161. .projection(projection
  162. .fitExtent([[0, 0], [swidth/6*0.8, sheight*0.8]], location));
  163. for(var i = 0; i < 6; i++) {
  164. var small = d3.select("#sm20"+(i+12)+"_area")
  165. .append("svg")
  166. .attr("width", swidth/6)
  167. .attr("height", sheight);
  168. var sm = small.append("g")
  169. .attr("id", "small"+(i+12));
  170. sm.selectAll("path")
  171. .data(locationSet)
  172. .enter()
  173. .append("path")
  174. .attr("d", spath)
  175. .style("stroke", "black")
  176. .style("stroke-width", 1)
  177. .style("fill", function(d) {
  178. var value;
  179. for (var j = 0; j < mesos_data[i].mesorregiao.length; j++) {
  180. if (d.properties.MESO.toLowerCase() == mesos_data[i].mesorregiao[j].toLowerCase()) {
  181. value = mesos_data[i].percentage[j];
  182. }
  183. }
  184. if (value) {
  185. return color(value);
  186. } else {
  187. return "#ccc";
  188. }
  189. }).on("mouseover", function(d){
  190. d3.select(this).style("stroke", "orange")
  191. .style("stroke-width", 2);
  192. tooltip.html(d.properties.MESO);
  193. return tooltip.style("visibility", "visible").style("opacity", 1);})
  194. .on("mouseout", function(d){
  195. d3.select(this).style("stroke", "black")
  196. .style("stroke-width", 1);
  197. tooltip.html(d.properties.MESO);
  198. return tooltip.style("visibility", "hidden").style("opacity", 1);
  199. })
  200. .on("mousemove", function() {
  201. d3.select(this)
  202. .style("stroke", "orange")
  203. .style("stroke-width", "1px");
  204. return tooltip.style("top",(d3.event.pageY-10)+"px").style("left",(d3.event.pageX+10)+"px");
  205. });
  206. }
  207. });
  208. }
  209. });