(1) Overview
Introduction
Background
Statistical graphics have been in use since at least the 1600s [, ], but work to understand the links between visualization and human perception, and to create visualization “best practices”, is a much more recent development [, , , ]. This research, combined with insights into human-computer interaction [] and the exponential growth of computing power, has laid the foundation for the release of open-source software packages for data visualization in the late 2000s [, , ]. Released in 2011, the Data-Driven Documents JavaScript library, or D3.js, provides a process for manipulating web documents based on data, which allows users to create interactive data visualizations on the web []. D3.js has since been documented [] and has attained widespread use []. At its core, D3.js facilitates the manipulation of the Document Object Model based on data. No full-fledged charting functions are provided in the core D3, but a suite of functions for creating scales, manipulating data and creating axes are included for easy chart creation; this functionality has led to the creation of hundreds of examples and over a dozen charting libraries built using D3.js [].
Many charting libraries have been written based on D3.js. Most of these focus on providing custom wrapper functions for generating charts with just a few lines of code. These libraries range from functions used to create specified chart types to extremely broad, declarative visualization grammars which provide a standard process for creating a wide variety of custom visualizations [, , ]. Many existing libraries have prescribed options for basic interactivity (filtering, zooming, etc.) and customizations (changing colors, adding annotations, etc.). Libraries may allow users to write custom JavaScript around a given chart, but adding interactivity outside of the intended use of a library is often impossible without editing the source code or reverse engineering the visualization using the base D3.js library.
Approach
Webcharts combines a fairly broad charting framework with a functional, event-driven approach to interactivity. Three central objects are combined with the concept of a 5-step chart lifecycle to create an environment where data visualizations can be created using initial, declarative configurations and then extended with custom functions. This enables a wide range of customization within the Webcharts framework, which allows for complex, interactive charts. Further, care has been taken to reduce dependencies and ensure that the Webcharts library is compatible with both modern web browsers and the Node.js environment.
The three objects in Webcharts are:
-
Chart – A chart with conventional x- and y-axes, rendered with SVG. Each chart is created by calling a function using the following parameters:
- A CSS selector that identifies the DOM element in which to create the chart (required)
- A configuration object whose properties describe the chart’s behavior and appearance (required)
- A controls object, described below (optional)
- Table – A simple table, rendered as an HTML <table> element with a <thead> and <tbody>. A table is created by a function using the same parameters as above.
- Controls – A set of inputs, rendered with <input> and <select> elements. Controls manipulate charts and/or tables by changing its configuration (thus changing its appearance or behavior) or by filtering the underlying data.
The Webcharts objects are rendered via a standard 5-step process that includes steps for the Creation, Initialization, Layout, Drawing and Resizing of the objects. Each step in this life cycle can be refined using insertion points for custom code, implemented as callback functions. A set of Chart, Table, and/or Controls objects can be packaged together with a collection of such callbacks to create powerful templating functions. This approach allows for easy reproduction of highly-complex visualizations, as demonstrated by the examples shown below.
Implementation and architecture
Loading Webcharts
Webcharts can be used in modern browsers (Chrome, Firefox, IE9+, etc.) and also exports itself as a CommonJS module for compatibility with Node. Install the package via npm:
npm install --save webcharts
Then, use it in your modules:
var webCharts = require(‘webcharts’);
// or, in ES6:
import webCharts from ‘webcharts’;
To use Webcharts in the browser, just make sure to include a reference to D3 first:
<script type=‘text/javascript’ src=‘http://d3js.org/d3.v3.min.js’></script>
<script type=‘text/javascript’ src=‘webcharts.js’>
</script>
Webcharts can also be used with an AMD module loader like Require.js:
require.config({
paths: {
webCharts: ‘webcharts’
}
});
require([‘webCharts’], function(webCharts) {
console.log(webCharts.version);
// make some charts!
});
Making a Chart
Once Webcharts and D3.js are loaded, a chart is created with a call to webCharts.createChart(). The function returns an object that represents a chart. The code to initialize a simple scatter plot is given below. See http://bl.ocks.org/nbryant/aeaf8d734d7600ca3afa for a live example:
var settings = {
“max_width”:“500”,
“x”:{
“label”:“Protein (g)”,
“type”:“linear”,
“column”:“Protein (g)”
},
“y”:{
“label”:“Carbs (g)”,
“type”:“linear”,
“column”:“Carbo(g)”
},
“marks”:[
{
“type”:“circle”,
“per”:[“Food”],
“tooltip”:“[Food]”
}
],
“aspect”:“1”,
“gridlines”:“xy”
};
d3.csv(‘calories.csv’,function(error,csv){
webCharts.createChart(‘body’, settings).init(csv);
})
The first argument, “body”, tells the function where to draw the chart. This is a simple CSS selector, so it may reference a DOM element name (like in this example) or class attribute, like “.chart-wrapper”.
The second argument is a JavaScript object that sets a number of options for the chart. The config object in this example sets some basic options like: what dataset fields should be mapped to the x and y axes, what type of marks should be drawn, how wide the chart can get (max_width), its aspect ratio, and where gridlines should be drawn. All of the possible configuration options are described at https://github.com/RhoInc/Webcharts/wiki/Chart-Configuration.
The chart object returned by webCharts.createChart() can then be initialized by passing data to the chart via its init() method. The init method triggers the remainder of the chart’s life-cycle (Table 1), including the Layout, Draw, and Resize phases.
Order | Phase | Description |
---|---|---|
1 | Chart Creation | Chart Object is created and returned via the createChart() method. |
2 | Initialization | The init() methods establishes default settings, binds data to the chart, and triggers the remaining steps in the life-cycle. |
3 | Layout | An svg is added to the DOM along with placeholder chart components (e.g. axes). |
4 | Draw | Raw data is processed as needed for charting. Pre-processing steps are completed (e.g. Scales are calculated.) |
5 | Resize | All chart marks are rendered/updated. |
The initial settings for a chart are established via a settings object during the Chart Creation step, and data is linked to the chart when the chart is initialized. However, both the settings and the underlying data can be modified throughout the remainder of a chart’s lifecycle, either via a linked control object or custom callback functions. Changing a control object linked to a chart immediately updates the object by triggering steps 4 and 5 in the chart’s lifecycle. More detail about the lifecycle of Webcharts objects can be found at: https://github.com/RhoInc/Webcharts/wiki/Webcharts-Life-Cycle.
Webcharts does not restrict the file size of the data loaded, but browser performance may be poor when rendering large numbers of elements (issues typically start at around 10,000 elements). Standard techniques such as data aggregation and server-side rendering can be used in conjunction with Webcharts to improve performance with very large data sets.
Examples
While it can be used in any domain, Webcharts was principally designed to be used in clinical trial research, which is reflected in the examples below Figures 1, 2 and 3. Additional examples are available at https://github.com/RhoInc/Webcharts/wiki/Examples.
Quality control
Webcharts has been tested in modern web browsers, including: Chrome, Firefox, Safari and Internet Explorer (version 9 and later). Full documentation and working examples are available at: https://github.com/RhoInc/Webcharts/wiki/. Additionally, outstanding issues, planned features, and support requests are tracked at: https://github.com/RhoInc/Webcharts/issues.
(2) Availability
Operating system
Webcharts does not target specific operating systems; it is compatible with modern web browsers (IE 9+, Google Chrome, Firefox, Safari, etc.)
Programming language
JavaScript
Additional system requirements
None
Dependencies
Data Driven Documents (D3.js) version 3
List of contributors
Nathan Bryant, Lead Programmer and Designer
Jeremy Wildfire, Group Lead and Programmer
Ryan Bailey, Project Manager
Spencer Childress, Testing
Rich Budrevich, Testing
Britt Sikora, Coordination and Editing
All contributors are at Rho, Inc.
Software location
Archive
Name: Zenodo
Persistent identifier:10.5281/zenodo.49396
Licence: MIT
Publisher: Nathan Bryant
Version published: 1.6.1
Date published: 5/6/2016
Code repository
Name: Github
Identifier:https://github.com/RhoInc/Webcharts
Licence: MIT
Date published: 8/31/2015
Language
English
(3) Reuse potential
Webcharts is open source and has a permissive MIT License that allows users to share and adapt the library. Although Webcharts was designed with a focus on clinical trial application, it can be used in any data domain.
Technically, the Webcharts library was designed to balance reusability and customizations. The code used to create a chart for a given dataset can often be applied to many other, similar datasets. If the structure of the input dataset is consistent, a chart can be rendered again and again with new data. The library has a single well-supported dependency (D3.js) and is compatible both with modern web browsers and the Node.js environment.