D3.js is a wonderful JavaScript library which is used for creating interactive and visually appealing graphics. D3.js
stands for Data Driven Documents and uses HTML
, SVG
and CSS
to run its magic. From the official docs,
D3.js is a JavaScript library for manipulating documents based on data. D3 helps you bring data to life using HTML, SVG and CSS. D3’s emphasis on web standards gives you the full capabilities of modern browsers without tying yourself to a proprietary framework, combining powerful visualization components and a data-driven approach to DOM manipulation.
This tutorial will be an introductory tutorial on D3.js where we'll focus on some basic things to create a dynamic graph. Along the course of this tutorial, we'll see how to create a multi-line chart using the D3.js library.
Looking for a Quick Solution?
If you're looking for a quick solution, there's a selection of JavaScript chart items over on Envato Market.
Starting from just a few dollars, it's a great way to implement something in a few minutes that would take a lot longer to build from scratch!
You can find scripts to create everything from simple line charts to complex infographics.
Getting Started
To get started working with D3.js, download and include D3.js, or you can directly link to the latest version of D3.js.
<script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script>
We'll start by creating the X and Y axes for our chart. We'll use some sample data to plot the chart.
Creating the Axes
Here is the basic bare-bones HMTL code of index.html
:
<html lang="en"> <head> <link href="http://getbootstrap.com/dist/css/bootstrap.min.css" rel="stylesheet"> <link href="http://getbootstrap.com/examples/justified-nav/justified-nav.css" rel="stylesheet"> <script src="http://d3js.org/d3.v3.min.js" charset="utf-8"></script> </head> <body> <div class="container"> <div class="jumbotron"> </div> </div> </body> </html>
To get started, we'll require some sample data. Here is our sample data :
var data = [{ "sale": "202", "year": "2000" }, { "sale": "215", "year": "2001" }, { "sale": "179", "year": "2002" }, { "sale": "199", "year": "2003" }, { "sale": "134", "year": "2003" }, { "sale": "176", "year": "2010" }];
Scalable Vector Graphics (SVG) is an XML-based image format for drawing 2D graphics which has support for interactivity and animation. We'll use an svg
element to draw our graph. Add the svg
element in index.html
:
<svg id="visualisation" width="1000" height="500"></svg>
Next, let's define some constants like width
, height
, left margin
, etc., which we'll use while creating the graph. D3 provides a method called d3.select
to select an element. We'll use d3.select to select the svg
element from index.html
.
var vis = d3.select("#visualisation"), WIDTH = 1000, HEIGHT = 500, MARGINS = { top: 20, right: 20, bottom: 20, left: 50 },
Based on the data, we need to create scales for the X and Y axes. We'll require the maximum and minimum value of the available data to create the scales on the axes. D3 provides an API method called d3.scale.linear which we'll use to create scales for the axes.
d3.scale.linear
uses two properties called range
and domain
to create the scale. Range
defines the area available to render the graph, and Domain
defines the maximum and minimum values we have to plot in the available space.
xScale = d3.scale.linear().range([MARGINS.left, WIDTH - MARGINS.right]).domain([2000,2010]),
Range
has been specified in the above code so that it doesn't get crowded around the edges. Maximum and minimum values for the domain have been set based on the sample data used.
Similarly, define the yScale
as shown:
yScale = d3.scale.linear().range([HEIGHT - MARGINS.top, MARGINS.bottom]).domain([134,215]),
Next, let's create the axes using the scales defined in the above code. D3
provides an API method called d3.svg.axis to create axes.
xAxis = d3.svg.axis() .scale(xScale), yAxis = d3.svg.axis() .scale(yScale);
Next, append the created X axis to the svg
container as shown:
vis.append("svg:g") .call(xAxis);
Save the changes and try to browse index.html
. You should have something like:
As you can see, the X axis is drawn but it has some issues. First, we need to position it vertically downwards. While appending the X axis to the SVG container, we can use the transform property to move the axis downwards. We'll use translate transform
to move the axis based on coordinates. Since we need to move the X axis only downwards, we'll provide the transform coordinates for the X axis as 0 and the Y axis just above the margin.
vis.append("svg:g") .attr("transform", "translate(0," + (HEIGHT - MARGINS.bottom) + ")") .call(xAxis);
Now, let's add the Y Axis. Add the following code to append the Y Axis to the SVG container:
vis.append("svg:g") .call(yAxis);
Save the changes and browse index.html
and you should have both the axes as shown.
As you can see in the above screen shot, the Y axis
is not in the correct position. So, we need to change the orientation
of the above shown Y axis to the left. Once the axis is aligned to the left side, we'll apply D3 transform to place it correctly alongside the X axis. Add the orient
property to the yAxis
to change its orientation.
yAxis = d3.svg.axis() .scale(yScale) .orient("left");
Apply D3 transform
while trying to append the Y axis
to the SVG container:
vis.append("svg:g") .attr("transform", "translate(" + (MARGINS.left) + ",0)") .call(yAxis);
We have kept the y coordinate of translate as 0, since we only wanted to move it horizontally. Save the changes and browse index.html
. You should see something like:
Creating the Line
To plot the sample data in our chart, we need to apply the xScale
and the yScale
to the coordinates to transform them and to draw a line across the plotting space. D3 provides a API method called d3.svg.line()
to draw a line. So add the following code:
var lineGen = d3.svg.line() .x(function(d) { return xScale(d.year); }) .y(function(d) { return yScale(d.sale); });
As you can see in the above code, we have specified x and y coordinates for the line as per the xScale
and yScale
defined earlier.
Next, we'll append a line path to svg
and map the sample data to the plotting space using the lineGen
function. We'll also specify a few attributes for the line such as stroke
color, stroke-width
, etc., as shown below:
vis.append('svg:path') .attr('d', lineGen(data)) .attr('stroke', 'green') .attr('stroke-width', 2) .attr('fill', 'none');
Save the changes and browse index.html
. You should have the line graph as shown:
By default the line will have linear interpolation
. We can specify the interpolation as well as add some CSS to the axes to make it look better.
var lineGen = d3.svg.line() .x(function(d) { return xScale(d.year); }) .y(function(d) { return yScale(d.sale); }) .interpolate("basis");
Add the following CSS to index.html
:
.axis path { fill: none; stroke: #777; shape-rendering: crispEdges; } .axis text { font-family: Lato; font-size: 13px; }
Include the class to both xAxis
and yAxis
:
vis.append("svg:g") .attr("class","axis") .attr("transform", "translate(0," + (HEIGHT - MARGINS.bottom) + ")") .call(xAxis); vis.append("svg:g") .attr("class","axis") .attr("transform", "translate(" + (MARGINS.left) + ",0)") .call(yAxis);
With basis
interpolation and some CSS, here is how it should look:
Creating a Multi-Line Chart
Consider another sample data set as shown:
var data2 = [{ "sale": "152", "year": "2000" }, { "sale": "189", "year": "2002" }, { "sale": "179", "year": "2004" }, { "sale": "199", "year": "2006" }, { "sale": "134", "year": "2008" }, { "sale": "176", "year": "2010" }];
For the sake of simplicity, we have considered two different sample data sets with the same X axis
values. In order to plot the above shown data2
alongside data
, we simply need to append another svg path to the svg
element. The only difference is that the data passed to scale to the lineGen
function is data2
. Here is how it should look:
vis.append('svg:path') .attr('d', lineGen(data2)) .attr('stroke', 'blue') .attr('stroke-width', 2) .attr('fill', 'none');
Save the changes and browse index.html
. You should be able to see the multi-line chart as shown:
Conclusion
In this tutorial, we saw how to get started with creating a simple multi-line chart using D3.js. In the next part of this series, we'll take this tutorial to the next level by making the multi-line chart dynamic, and we'll also add some features to make the graph more interactive.
Source code from this tutorial is available on GitHub.
Do let us know your thoughts in the comments below!
Comments