This tutorial assumes you know a little about web development: how to edit a web page and view it in your browser, how to include d3.js on the page, and the like. You might find it convenient to fork this CodePen template to get started.

In vanilla JavaScript, you typically deal with elements one at a time. For example, to create a div element, set its contents, and then append it to the body:
This code snippet is JavaScript and should be placed in a script tag somewhere in the body, after loading D3.

With D3 (as with jQuery and other libraries), you instead handle groups of related elements called selections. Working with elements en masse gives selections their power; you can manipulate a single element or many of them without substantially restructuring your code. Although this may seem like a small change, eliminating loops and other control flow can make your code much cleaner.

A selection can be created in myriad ways. Most often you create one by querying a selector, which is a special string that identifies desired elements by property, say by name or class ("div" or ".foo", respectively). While you can create a selection for a single element:

Another convenience of selections is method chaining: selection methods, such as selection.attr, return the current selection. This lets you easily apply multiple operations to the same elements. To set the text color and background color of the body without method chaining, you’d say:

Note we didn’t even need a var for the selected body element. After applying any operations, the selection can be discarded. Method chaining lets you write shorter code (and waste less time fretting over variable names).

There is a gotcha with method chaining, however: while most operations return the same selection, some methods return a new one! For example, selection.append returns a new selection containing the new elements. This conveniently allows you to chain operations into the new elements.
The recommended indentation pattern for method chaining is four spaces for methods that preserve the current selection and two spaces for methods that change the selection.

Now consider how you might create a bar chart without JavaScript. After all, there are only six numbers in this trivial data set, so it’s not hard to write a few div elements by hand, set their width as a multiple of the data, and be done with it.
Careful observers will note that the three-pixel padding here distorts the accuracy of the chart by making the bars longer! This can be fixed via box-sizing: border-box, or by switching to SVG, as we will in part 2.

This chart has one div for a container, and one child div for each bar. The child divs have a blue background color and a white foreground color, giving the appearance of bars with right-aligned value labels. You could simplify this implementation even further by removing the containing chart div. But more commonly your page will contain content in addition to the chart, so having a chart container lets you position and style the chart without affecting the rest of the page.

Of course hard-coding is impractical for most datasets, and the point of this tutorial is to teach you how to create charts from data automatically. So now let’s create the identical structure using D3, starting with an empty page that contains only a div of class "chart". The following script selects the chart container and then appends a child div for each bar with the desired width:

Although partly familiar, this code introduces an important new concept — the data join. Let’s break it down, rewriting the above concise code in long form, to see how it works.

First, we select the chart container using a class selector.

var chart = d3.select(".chart");

Next we initiate the data join by defining the selection to which we will join data.

var bar = chart.selectAll("div");

The data join is a general pattern that can be used to create, update or destroy elements whenever data changes. It might feel odd, but the benefit of this approach is that you only have to learn and use a single pattern to manipulate the page. So whether you’re building a static chart or a dynamic one with fluid transitions and object constancy, your code remains roughly the same. Think of the initial selection as declaring the elements you want to exist (see “Thinking with Joins”).

Next we join the data (defined previously) to the selection using selection.data.
The data operator returns the update selection. The enter and exit selections hang off the update selection, so you can ignore them if you don’t need to add or remove elements.

var barUpdate = bar.data(data);

Since we know the selection is empty, the returned update and exit selections are also empty, and we need only handle the enter selection which represents new data for which there was no existing element. We instantiate these missing elements by appending to the enter selection.

var barEnter = barUpdate.enter().append("div");

Now we set the width of each new bar as a multiple of the associated data value, d.

barEnter.style("width", function(d) { return d * 10 + "px"; });

Because these elements were created with the data join, each bar is already bound to data. We set the dimensions of each bar based on its data by passing a function to compute the width style property.

Lastly, we use a function to set the text content of each bar, and produce a label.
When formatting numbers for text labels, you may want to use d3.format for rounding and grouping to improve readability.

barEnter.text(function(d) { return d; });

D3’s selection operators such as attr, style and property, allow you to specify the value either as a constant (the same for all selected elements) or a function (computed separately for each element). If the value of a particular attribute should be based on the element’s associated data, then use a function to compute it; otherwise, if it’s the same for all elements, then a string or number suffices.

One weakness of the code above is the magic number 10, which is used to scale the data value to the appropriate pixel width. This number depends on the domain of the data (the minimum and maximum value, 0 and 42 respectively), and the desired width of the chart (420), but of course these dependencies are only implicit in the value 10.

We can make these dependencies explicit and eliminate the magic number by using a linear scale. D3’s scales specify a mapping from data space (domain) to display space (range):
D3’s scales can also be used to interpolate many other types of display-space values, such as paths, color spaces and geometric transforms.

Although x here looks like an object, it is also a function that returns the scaled display value in the range for a given data value in the domain. For example, an input value of 4 returns 40, and an input value of 16 returns 160. To use the new scale, simply replace the hard-coded multiplication by calling the scale function:

The bare-bones bar chart presented here is simple to implement, yet obviously limited. A bar chart should have grid lines to assist in comparing values, and you may prefer vertical columns to horizontal bars. Or you might want a different chart type, such as a pie or streamgraph. For greater visual expression, you’ll need Scalable Vector Graphics. SVG is covered in the next section.
November 5, 2013Mike Bostock