Getting Started with D3.js Topographic Maps using topojson

Getting Started with D3.js Topographic Maps using topojson

Topography is a detailed map of the surface features of land. It includes the mountains, hills, creeks, and other bumps and lumps on a particular hunk of earth. This handy word is a Greek-rooted combo of topos meaning “place” and graphein “to write."

Producing scalable vector maps can be challenging. Especially considering the bewlidering array of projections, geospatial data types and file formats.

D3’s topojson helper library takes away much of the heavy lifting, making maps much more accessible. The only challenge left to the developer is obtaining topographic feature data in a GeoJson format. Google offers up numerous tutorials on converting shape files and such to GeoJson.

The examples I’ve used here are somewhat trivial, represeting country and US county borders. These are available all over the internet as to files

  1. us.json
  2. world-110m.json

With these feature files, getting simple maps onto a page is very straight forward.


<!doctype html>
<html class="no-js" lang="">
    <meta charset="utf-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <title>Example D3.js & Topojson Topographic Maps</title>
    <meta name="description" content="D3.js | topojson | Topographic Maps">
    <meta name="viewport" content="width=device-width, initial-scale=1">
        path {
            fill: #ccc;
            stroke: #fff;
            stroke-width: .5px;
        path:hover {
            fill: red;

    <!-- HTML DIV Containers -->
    <div id="World"></div> <div id="US"></div>
    <!-- Load D3 & topojson libs -->>
    <script src="d3.v3.min.js"></script>
    <script src="topojson.v1.min.js"></script>

    <script> // Eample 1 : World Map
    var width = 960, height = 500;  // Set SVG canvas size
    // Bind SVG canvas to DIV container
    var svg1 ="#US").append("svg") 
        //Set SVG canvas dimension attributes
        .attr("width", width)
        .attr("height", height);
    // Define a topographic path object
    var us_path = d3.geo.path()
    // Load geo/topo data and exec callback function
    d3.json("us.json", function(error, topology) {
            // All the geospatial vector magic happens here
            .data(topojson.feature(topology, topology.objects.counties).features)
            // For each topographic feature appent a path object          
            // Assign the path object the features from the dataset
            .attr("d", us_path);

    <script> // Example 2 : US Map
    var width = 960, height = 500;
    var projection = d3.geo.mercator()
        .center([0, 50 ])

    var svg2 ="#World").append("svg")
        .attr("width", width)
        .attr("height", height);

    var world_path = d3.geo.path()

    d3.json("world-110m.json", function(error, topology) {
            .data(topojson.feature(topology, topology.objects.countries).features)
            .attr("d", world_path)

Adventures in Data...
Hey There!
What is This?