Read this D3.js Data Visualization tutorial to learn the most essential API methods like Scales, Shape, Colors, Graph, Animation, and more:
This tutorial explains how a data-driven open-source javascript library d3.js can be utilized in data visualization using HTML, Document Object Model (DOM), Cascading Style Sheets (CSS), Scalable Vector Graphics (SVG), Canvas, and javascript through a web browser.
In the previous tutorial, we began with features, benefits, prerequisites for learning d3.js with the installation of d3.js files or alternatively include a path to these library files. Various API methods like selections, array, transition, collection, paths have been explained with codes, programs, and examples.
We will learn a few very essential API methods that can assist to quickly render data visualization using the dataset in CSV, XML, JSON file formats.
Let’s Start!!
Table of Contents:
D3 Scales API
Scales methods of d3.js are used for transforming data by mapping input data to an output range, thereby scaling methods for different types of charts, are explained below.
- d3.scaleLinear(): Continuous linear scale can be created where input data maps to the specified output range using this method,
- d3.scaleIdentity (): Using this method, Linear scale can be created, where both input data and output are the same.
- d3.scaleTime (): Linear scale where input data is in dates whereas the output in numbers is created with this method.
- d3.scaleLog (): This method helps to create a logarithmic scale.
- d3.scaleSqrt (): This method helps to create a square root scale.
- d3.scalePow (): Exponential scale gets created with this method.
- d3.scaleSequential (): Using this method, a sequential scale gets created; with the output range fixed by interpolator function.
- Domain: Minimum and maximum values of your input data referred by domain.
- Range: Range is an output range, to which the input values are mapped to plot scale.
In the example below, where Scales are plotted using d3 scales methods, we have continent wise population density taken as our array of records assigned to:
- variable infoset as var infoset = [59.5, 17.2, 9.6, 7.6, 5.5, 0.5]
- The width and height for plotting a scale are assigned to a variable span and ceil.
- Variable scalespan has methods like d3.scaleLinear() , .domain() and .range().
- The domain will map input data range and range for plotting the actual scale for the above input data from domain.
- The variable screen is plotting area on which scale is plotted with help of variable rule.
- SVG rectangle shapes are grouped into variable g, and transformed with translate function which moves the scale to the appropriate location on the canvas.
- Text is appended to screen variable, to display the values of scale over x-axis.
Example for D3 Scales API is given below
<html><head> <script src="https://d3js.org/d3.v5.min.js"></script></head> <body> <h3>Displaying Values using Scales API method</h3> <script> var infoset = [59.5, 17.2, 9.6, 7.6, 5.5, 0.5] var span = 500, ceil = 500; var scalespan = d3.scaleLinear() .domain([0, d3.max(infoset)]) .range([0, 400]); var screen = d3.select("body").append("svg") .attr("width", span) .attr("height", ceil) .append("g").attr("transform", "translate(5,20)"); var rule = screen.selectAll("rect") .data(infoset).enter() .append("rect") .attr("width", function(d){ return scalespan(d);}) .attr("height", 20) .attr("y", function(d, i){ return i*25; }) .attr("fill", "#b3ccff"); screen.selectAll("text") .data(infoset).enter().append("text") .attr("y", function(d, i){ return i*25; }) .attr("x", function(d){ return scalespan(d);}) .text(function(d) {return d;}) .attr("fill", "blue").attr("dy",".85em"); </script> </body> </html>
In D3 Scales example above, in order to display the dataset in the array, the continent-wise population density of 6 continents taken as values are displayed as below.
- Asia (59.5)
- Africa (17.2)
- Europe (9.6)
- North America (7.6)
- South America (5.5)
- Australia (0.5)
The above dataset of population density is assigned to variable infoset.
Scales API methods applied are scaleLinear(), domain ( actual input range), range (range to plot scale), the variable screen is formed by appending SVG to the body, which is further appended with rect (rectangle) shape, data is attached to this with .data(Infoset).enter(), width is mapped with scalespan (which was mapped with data values to plot these values as a scale).
Finally, the text is appended in order to display Infoset values along the lengths of the rectangles in the scale seen in the image.
D3 Axis API – d3 Axis API methods are used to draw axes,
- d3.axisTop () – Creates top horizontal axis
- d3.axisRight () – Creates right oriented vertical axis
- d3.axisBottom () – Creates bottom horizontal axis
- d3.axisLeft () – Creates left vertical axis
In order to display X coordinate or x-Axis that is divided into equal parts to accommodate input values from the infoset, which is an array of numbers that plots these values with different size of rectangles, the variable axis is assigned as below.
var axis = d3.axisTop().scale(scalespan);
d3.axisTop() defines the x-axis divided into values from the input values from infoset, with scale(scalespan), that internally takes d3.scaleLinear().domain().range()
In order to display x-axis, we need to call (axis) by attaching it as below.
screen.append("g").attr("transform","translate(0,160)") .call(axis);
The screen is the canvas on which the scale is displaying.
In order to design a coordinate system with x-axis and y-axis along horizontally starting from left to right direction, a combination of the following API methods is used.
Scale API method for scale along x-axis and y-axis that uses d3.scaleLinear ().domain ().range () will be applied. Axis API method, d3.axisBottom () will be set for width along the x-axis, where as d3.axisLeft () will be set for height along the y-axis.
Example of D3 Axis API methods is explained below
<html><head> <script src="https://d3js.org/d3.v5.min.js"></script> </head> <body> <script> var infoset = [59.5, 17.2, 9.6, 7.6, 5.5, 0.5] var span = 500, ceil = 500; var scalespan = d3.scaleLinear() .domain([0, d3.max(infoset)]) .range([0, 400]); var axis = d3.axisBottom().scale(scalespan); var screen = d3.select("body").append("svg") .attr("width", span).attr("height", ceil) .append("g").attr("transform", "translate(5,20)"); var rule = screen.selectAll("rect") .data(infoset).enter() .append("rect") .attr("width", function(d){ return scalespan(d);}) .attr("height", 20) .attr("y", function(d, i){ return i*25; }) .attr("fill", "#b3ccff"); screen.selectAll("text") .data(infoset).enter().append("text") .attr("y", function(d, i){ return i*25; }) .attr("x", function(d){ return scalespan(d);}) .text(function(d) {return d;}) .attr("fill", "blue").attr("dy",".85em"); screen.append("g").attr("transform", "translate(0, 150)").call(axis); </script> </body> </html>
Variable infoset is assigned the same set of values as that of Scales API example, as to add Axis to the coordinates here.
Variable scalespan is assigned to scaleLinear() function along with domain and range.
A variable screen acts as a canvas to draw SVG shape, like a rectangle.
Further, the variable rule is assigned with .data(Infoset).enter(), appended with rect (rectangle shape), here width is assigned with scalespan mapped with the corresponding values and index value along with y-axis.
Variable axis is assigned to d3.axisBottom() and scale(scalespan), which is called by screen using call(axis) function. This enables the display of the X-axis divided into an equal interval of 5 along with x coordinates in addition to rectangles with different lengths and their corresponding values of population density.
D3 Shapes API
D3.js Shapes API supports various shapes like arc, pie, and line. The corresponding API methods are explained in brief.
Arcs API
Arcs methods can produce circle or ring shape, various Arcs API methods are explained below
- d3.arc(): New arc gets generated with d3.arc() method.
- arc (args): This method will create a new arc with an argument as an input.
The syntax for arc(args) is explained below
<script> var arc = d3.arc(); arc({ innerRadius: 0,outerRadius: 100,startAngle: 0,endAngle: Math.PI / 2}); </script>
- arc.innerRadius ([radius]), arc.outerRadius ([radius]), and arc.cornerRadius ([radius]) – These methods help the value of the radius from inner, outer, corner sides of arc shape.
- arc.startAngle ([angle]), arc.endAngle ([angle]), arc.padAngle ([angle]) – These methods help to set angles at different areas.
Example for D3 Arcs API is given below
<html> <head> <style> path {fill: #99ccff;} </style> </head> <body> <svg width = "250" height = "400"> <g transform ="translate(30,100) rotate(30)"></g> </svg> <script src="https://d3js.org/d3.v5.min.js"></script> <script> var arcGen = d3.arc(); var arcData = arcGen({ startAngle: 0, endAngle: 0.5*Math.PI, innerRadius: 0, outerRadius: 100 }); d3.select("g").append('path').attr('d', arcData); </script> </body> </html>
Arcs API method from Shapes API methods of D3, applied to SVG element is shown below.
<svg width = "250" height ="400"> <g transform ="translate (30, 100) rotate (30)" ></g> </svg>
d3.arc() method creates arc shape, with its parameters like startAngle, innerRadius, and outerRadius, and finally appending path and arc attributes as below.
d3.select("g").append ('path').attr ('d', arcData);
Pie API
Pie API methods help create Pie (Two Radius lines of an arc, in other words, it is a portion of a circle.) Pie methods are as described below.
- d3.pie (): This method creates Pie shape
- pie (data[, arguments]): This method returns an array of objects and generates a pie for input value from an array, Objects are arc angles of information, with the following properties.
- Data: Values from an input data array
- Value: The numeric value of the arc
- Index: Index of the arc
- startAngle, endAngle, padAngle – start, end, and pad angle of an arc
- pie.value([value]): The method can be used to set the value to the function and generate pie shape.
- pie.set([compare]): The method used to sort the data to the function and generate pie.
- pie.startAngle ([angle]), pie.endAngle ([angle]), pie.padAngle ([angle]) are respective methods to set, start angle, end angle and pad angle in order to generate pie shape.
Lines API
Lines API methods help to generate lines.
- d3.line(): Helps to create new line using this method.
- line(data): Generates a line for a given array of data.
- line.x ([x]) , line.y([y]) Creates corresponding ‘x’ accessor and ‘y’ accessor respectively to functions and generate a line.
- line.defined ([defined]): This method sets the defined accessor to the function specified.
- line.curve([curve]) : This method sets the curve and generates line.
D3 Colors API
In Cascading Style Sheets (CSS) Color attribute of any element can be specified in different ways:
- By color names: In CSS style, color attributes can be recognized by browser with color names such as blue, red, green, black, white etc.
- RGB values: Colors are primarily combining Red, Green and Blue lights, with equal values of these three colors, we can create different shades of gray,
- Example rgb( 0,0,0): for Black color, rgb( 128,128,128) – for Gray color and rgb( 255, 255, 255) – for White color,
- Hexadecimal values: Colors can also be described in hexadecimal integers between 00 to ff which specifies the intensity of color.
- HSL values: For Cascading Style Sheet version 3 (CSS 3) HSL values represent color standards, where H stands for Hue, degree on the color wheel from 0 to 360, E.g. 0 is red, 120 is green and 240 is blue, S stands for Saturation, a percentage value, E.g. 0% means the shade of gray and 100% is the full intensity of color, L stands for Lightness, also measured in percentage, E.g. 0% is black, 100% is white.
- HWB values: For Cascading Style Sheet version 4 (CSS 4) HWB values represent standard to describe a color attribute, where H stands for Hue, W for whiteness, and B for blackness.
The following chart will map colors and its name, with corresponding Hex and RGB code.
[image source]
All browsers identify all the colors, in order to know specification, manipulation, and conversion operations for these colors D3.colors API methods are used, for changing color values to HSL, rotate the Hue by 45 degrees, and change the saturation level of the color.
A list of the major methods from D3 colors API are explained below.
- d3.color (specifier): This method is used in order to parse specific CSS color and return RGB or HSL color.
- color.opacity: This method is specific to change the opacity value of color, in order to fade the color to the required degree, one can change the opacity ranging from 0 to 1.
- color.rgb(): This method returns RGB value for the name of the color specified as input.
- color.toString(): This method return a string that represent color based on CSS Object Model specification.
- color.displayable(): This method will return a boolean value, true – when the color is displayable, and returns false, if RGB color value is less than 0 or greater than 255. (For the color to be visible the RGB value should be either rgb(0, 0, 0) , rgb (255, 255, 255) or any values in between 0 and 255.
- d3.rgb(color): This method is used in order to construct a new RGB color.
- d3.hsl(color): A new HSL color can be created with this method, where h, s, and l properties of the color are displayed.
Example of D3 Colors functions
<html> <head> <script src="https://d3js.org/d3.v5.min.js"></script> </head> <body> <script> var mycolr = d3.color("Aquamarine"); document.write(mycolr + "<p>"); document.write(mycolr.opacity + "<p>"); document.write(mycolr.displayable() + "<p>"); var c = d3.hsl("steelblue"); document.write(c +"<p>"); document.write(c.h+= 90 +"<p>"); document.write(c.s+= 0.8 +"<p>"); c.opacity = 0.2; document.write(c.rgb() +"<p>"); </script> </body> </html>
D3 Drag API
One of the most favorite and user-friendly features in web application used with a mouse as selecting and guiding user input, drag and drop feature is a very important pointing gesture, d3 drag API consists of various functions that help to accomplish mouse action of selecting an element and moving (dragging) it to a different location or placing it on to another element.
- d3.drag(): This method adds or creates a new drag behavior, which is a function as well as an object.
- drag(selection): This method is used to apply drag behavior via selection.call.
- drag.container([container]): This method is used to set the container to a function for dragging.
- drag.filter([filter]): This method is used to set the filter to a function.
- drag.subject([subject]): This method is used to set the subject to the function for dragging
- drag.clickDistance([distance]): This method is used for clicking a mouse down and mouse up the event and to set the maximum distance .
- drag.on(typenames, [listener]): This method is used to set the event listener for type names for dragging. Typename is a type which has either start (mouse down), drag (mouse move) or end (mouse up) values.
- d3.dragDisable(window): Used to disable the drag and drop selection. By preventing mouse down event, thereby does not allow dragging.
- d3.dragEnable (window[, noclick]): Used to enable the drag and drop selection, By allowing call to mouse up event action.
- D3.event method: Used to set drag event, it contains Target for drag behavior, Type that can contain anyone from start, drag or end, subject that is defined by drag subject.
D3 Zoom API
Zooming helps to scale (increase the area) the particular content, from a particular region with click and drag of the mouse.
D3 zooming API methods are explained below.
- d3.zoom(): With this method, a new zoom behavior is created.
- zoom(selection): Transformation of zoom behavior on a selected element is applied with this method.
- zoom.transform(selection, transform): This method is used to set current zoom transform for the selected elements, to the desired transform.
- zoom.translateBy(selection, x, y): This method helps to translate transform current zoom of the selected elements integer values.
- zoom.translateTo(selection, x, y): This method is used to translate the current zoom transform of the selected elements.
- zoom.scaleTo(selection, k): With this method, the current zoom transform of elements can be scaled to k, i.e. scale factor identified as numbers or functions.
- zoom.scaleBy(selection, k): With this method, the current zoom transform of elements can be scaled to k, i.e. scale factor identified as numbers or functions that returns numbers.
- zoom.filter([filter]): This method is used to set the filter to the function selected for zoom behavior.
- zoom.wheelDelta([delta]): This method returns current wheel delta function.
- zoom.extent([extent]): This method helps to set the extent to the array points specified by the user.
- zoom.scaleExtent([extent]): In order to set the extent to the array of numbers with the minimum allowed scale factor k0 to the maximum allowed K1. Users can scroll or move the mouse wheel in order to zoom in or zoom out.
- zoom.translateExtent([extent]): This method comes in handy when the value of extent is declared already, the translate extent can be set to the array of points specified.
- zoom.clickDistance([distance]): The method, zoom.clickDistance is used to set the maximum of the distance or a frame of height, that zoomable area can move between up and down.
- zoom.duration([duration]): The method, zoom.duration, help to set the duration for zoom transitions that should be set, on double-click and double-tap, its unit of measurement is the number of milliseconds.
- zoom.interpolate([interpolate]): This method helps to insert zoom transitions to the function selected.
- zoom.on(typenames[, listener]): This method is applied when the listener is already declared, then in order to set the event listener for the type name which allow multiple listeners to be registered to the same type should have mouse down i.e. after zooming begins i.e. Start, after a change to the zoom transform i.e. mouse move, or Zoom, and End i.e. after zooming ends which is mouse up.
D3 Requests API
D3 Requests API methods help to perform XMLHttpRequest, which supports both async and synchronous requests and perform GET, POST, PUT, and DELETE requests. We can load data set files that can be loaded by parsing JSON, CSV, and TSV, as well as text files.
D3 Requests API methods are explained below.
- d3.request(url[, callback]): New request returns for the given URL with the help of this method, if callback is assigned, then calling request is considered, else request is still pending i.e. not yet called.
- request.header(name[, value]): This function of request API is applied to set the value for the request header with a specified name.
- request.mimeType([type]): This function is used to assign the mime type to the value.
- request.user([value]): This method helps to assign a username for authentication. It will be null if the username is not specified.
- request.password([value]): This method helps in setting the password for authentication, for a specified value.
- request.timeout([timeout]): This method sets the timeout to the number of milliseconds for a specified timeout.
- request.get([data]): This method helps to send the GET request method.
- request.post([data]): This method helps to send the POST request method.
- request.send(method[, data]): This method can be used to send either GET or POST request type.
- request.abort(): This method helps to abort or cancel the request.
- d3.csv(url[[, row], callback]): This method returns new request for the CSV file at the URL specified. with default MIME type of text/csv data files.
D3 Delimiter Separated Values API
The delimiter is a special character that can be anything like comma, tab, or space or any character that separates two independent areas of values. Examples are comma-separated values (CSV) or tab-separated values (TSV).
D3 have methods that handle delimiter separated values as listed below
- d3.csvParse(string[, row]): With this method, data or records in CSV format can be parsed.
- d3.csvParseRows(string[, row]): With this method, data or records in CSV format can be parsed which is similar to rows.
- d3.csvFormat(rows[, columns]): With this method, CSV rows and columns can be formatted.
- d3.csvFormatRows(rows): Using this method, CSV rows can be formated
- d3.tsvParse(string[, row]): With this method data in tsv format can be parsed.
- d3.tsvParseRows(string[, row]): With this method data equivalent to rows in tsv format can be parsed.
- d3.tsvFormat(rows[, columns]): Using this method, tsv rows and columns can be formatted.
- d3.tsvFormatRows(rows): With the help of this method tsv rows can be formatted.
D3 Timer API
In order to perform concurrent animation synced with delay in timing, the timer API is used. The method used for animation in Timer API is to requestAnimationFrame, which intimates the browser that the animation operation is expected, thereby allowing the browser to call the function that updates an animation process.
Timer API methods are explained below
- d3.now(): This timer API member method returns the current time.
- d3.timer(callback[, delay[, time]]): This method helps to schedules a new timer and invokes the newly scheduled timer, one can set optionally numeric delay in an interval of milliseconds.
- timer.restart(callback[, delay[, time]]): With optional delay and time, we can restart a timer along with specifying a callback.
- timer.stop(): This method helps to stop the timer, by avoiding subsequent callbacks.
- d3.timeout(callback[, delay[, time]]): In order to stop the timer, on its first callback, which is passed as the elapsed time, we can use this method.
- d3.interval(callback[, delay[, time]]): This method invokes a time delay interval.
Animation In D3.js
Animation can be understood as a gradual progression or transition of the starting point to the ending point, the effect of animation becomes essential in data visualization, where a user can analyze real-time changes based on the data values.
The animation can be applied through transition API, by setting the starting point which is the current DOM position of an element, and endpoint by setting attributes, style, and other properties like color and size.
The following are a few methods that help to achieve the effect of animation in transition in D3.js.
- The duration (): Duration () method helps to change an attribute or properties smoothly that gives gradual transition in a given interval which is in milliseconds. D3.js also uses the interpolate method that has types such as interpolateNumber – supporting numerical values, interpolateRgb – that supports colors and interpolateString – supporting string.
- The delay () method: appending delay() method to the transition function attached to a particular svg or element, will allow transition take place after a certain time period.
Transition Lifecycle has the following phases
- Scheduling Transition: Transition is scheduled as soon as it is created along with attr(), style(), and other methods of gradual change to the element from its current DOM location.
- Starting Transition: Based on the delay () specified, when the transition is scheduled, in the absence of delay, the transition starts immediately.
- Running Transition: While transition starts running, the transition values that range from 0 to 1 get invoked repeatedly.
- End of Transition: The transition ends after the time spent i.e. the sum of time in delay and duration, thereby resulting in the element to complete the attribute values acquired.
Example of Animation Effect in d3
<html> <head> <script src="https://d3js.org/d3.v5.min.js"></script></head> <body> <script> var round = d3.select("body").append("svg") .attr("width", 300).attr("height", 400) .append("circle") .attr("cx", 75).attr("cy", 75).attr("r", 15) .attr("fill", "rgb(185, 133, 152)"); animate(); function animate(){ round.transition() .duration(3200).delay(1000) .attr("r", 75).attr("fill", "rgb(152, 68, 189)")} </script></body></html>
D3 Graphs API
Graphs is an important and essential feature in D3.js, in order to compare the two commodities, we use graphs, which are 2-dimensional areas that run horizontally as X-axis and vertically as Y-axis. Both the axis starts from the left down corner of a plane.
In real life, we usually compare the Duration in Years with the Count of the population in any geographic area, Rate or price fluctuations over the years for some commodity, say Gasoline (Petrol) from the Duration of Years as X-axis and Price per barrel as Y-axis.
D3.js helps in designing virtualization of data set that are used primarily as two columns with values that are compared in a graphical visualization that help in statistical analysis.
We need records in CSV format where values are given for 2 measurable attributes like Year and population in our case.
Records in data.csv file as given below are required to be uploaded onto the server, and the data is then processed like Year as inputs for values for X-axis and population as inputs for values for Y-axis.
After arranging dimensions for graph i.e. margin, height, and width, Scales methods like scaleLinear() is applied along with domain and range, in most of the cases, scaleLinear() method are used, which creates linear continuous scale will be designed.
- scaleLinear, input data will map with the output range.
- scaleIdentity() method can be applied when both the input and output data are same.
- scaleTime() method when one of the input data is in date format, either x or y-axis, and another data is numbers.
- scaleLog() will form logarithmic scale.
- scaleSqrt() will create square root scale.
- scalePow() for designing exponential scale, scaleSequential for sequential scale.
- axisTop(), axisRight(), axisBottom(), axisLeft() are methods that are used to align data values across Y axis as well as X axis.
Conclusion
In this tutorial, we have covered the most essential API methods of d3.js like scales API for transforming data into charting visualization, axis API that helps in plotting axes, x-axis, and y-axis.
Shapes API for plotting arcs, pie and line API methods, colors API for identifying specification and manipulating colors, drag API for drag n drop functionality of HTML elements, zoom API for scale-up (increase) the contents of a particular region, requests API for handling asynchronous and synchronous requests using various XML HTTP requests.
Delimiter separated values API for handling CSV data files and timer API to perform concurrent animations with time delay, animation in D3.js, and graphs using the available data to compare two commodities on the Cartesian axes, with relevant code examples to introduce you to the power of D3.js JavaScript library that is driven by data.