block by rveciana 5181105

D3 tutorial V: Adding tooltips

Full Screen

This example belongs to the presentation made to the OSGeo local group in Barcelona Geoinquiets The example is an adaptation from Mike Bostock‘s Symbol Map example

index.html

<!DOCTYPE html>
<meta charset="utf-8">
<style>

.states {
  fill: #ccc;
  stroke: #fff;
}

.symbol {
  fill: steelblue;
  fill-opacity: .8;
  stroke: #fff;
}

.tooltip{ background-color:rgba(68,136,187,0.5);;
          margin: 10px;
          height: 50px;
          width: 150px;
          padding-left: 10px; 
          padding-top: 10px;
    -webkit-border-radius:10px;
    -moz-border-radius:10px;
    border-radius:10px;
        }
</style>
<body>
<button type="button" id="change">Change</button>

<script src="//d3js.org/d3.v3.min.js"></script>
<script src="//d3js.org/topojson.v0.min.js"></script>
<script src="//d3js.org/queue.v1.min.js"></script>
<script type="text/javascript" src="./tooltip.js"></script>


<script>
var width = 960,
    height = 500;
var states, points;


var radius = d3.scale.sqrt()
    .domain([0, 1e6])
    .range([0, 10]);

var projection = d3.geo.mercator()
    .center([-97, 37])
    .scale(4000 / 2 / Math.PI)
    .translate([width / 2, height / 2]);


var path = d3.geo.path()
.projection(projection);

var svg = d3.select("body").append("svg")
    .attr("width", width)
    .attr("height", height);

queue()
    .defer(d3.json, "/mbostock/raw/4090846/us.json")
    .defer(d3.json, "/mbostock/raw/3750900/us-state-centroids.json")
    .await(ready);


function ready(error, us, centroid) {
states = svg.append("path")
      .attr("class", "states")
      .datum(topojson.object(us, us.objects.states))
      .attr("d", path);

    points =  svg.selectAll(".symbol")
      .data(centroid.features.sort(function(a, b) { return b.properties.population - a.properties.population; }))
    .enter().append("path")
      .attr("class", "symbol")
      .attr("d", path.pointRadius(function(d) { if(d.properties) { return radius(d.properties.population);} else {return;} }))
      .call(d3.helper.tooltip(
        function(d, i){
          return "<b>"+d.properties.name + "</b><br/>pop: "+d.properties.population;
        }
        ));
};

d3.select("#change").on("click", function() {
  projection = d3.geo.albers();
  path.projection(projection);
  states.transition()
      .duration(10000)
      .attr("d", path);
  points.transition()
      .duration(3000)
      .attr("d", path);
});


</script>

tooltip.js

d3.helper = {};

d3.helper.tooltip = function(accessor){
    return function(selection){
        var tooltipDiv;
        var bodyNode = d3.select('body').node();
        selection.on("mouseover", function(d, i){
            // Clean up lost tooltips
            d3.select('body').selectAll('div.tooltip').remove();
            // Append tooltip
            tooltipDiv = d3.select('body').append('div').attr('class', 'tooltip');
            var absoluteMousePos = d3.mouse(bodyNode);
            tooltipDiv.style('left', (absoluteMousePos[0] + 10)+'px')
                .style('top', (absoluteMousePos[1] - 15)+'px')
                .style('position', 'absolute') 
                .style('z-index', 1001);
            // Add text using the accessor function
            var tooltipText = accessor(d, i) || '';
            // Crop text arbitrarily
            //tooltipDiv.style('width', function(d, i){return (tooltipText.length > 80) ? '300px' : null;})
            //    .html(tooltipText);
        })
        .on('mousemove', function(d, i) {
            // Move tooltip
            var absoluteMousePos = d3.mouse(bodyNode);
            tooltipDiv.style('left', (absoluteMousePos[0] + 10)+'px')
                .style('top', (absoluteMousePos[1] - 15)+'px');
            var tooltipText = accessor(d, i) || '';
            tooltipDiv.html(tooltipText);
        })
        .on("mouseout", function(d, i){
            // Remove tooltip
            tooltipDiv.remove();
        });

    };
};