SlideShare uma empresa Scribd logo
1 de 131
Baixar para ler offline
A Quick & Dirty D3.js
Young-Ho Kim
Human-Computer Interaction Lab
Dept. of Computer Science & Engineering
Seoul National University
Course
Course | Young-Ho Kim – A Quick and Dirty D3.js
Overview
In this course, we will go through…
1. A quick & dirty introduction of D3.js
2. Play with D3 on HTML document
The material is based on my experience of learning by many people’s
blogs, slides, tutorials, and books. It may have grammatical issues
and technical issues about D3. If you find anything strange, please let
me know.
yhkim@hcil.snu.ac.kr
About This Course
2
Course | Young-Ho Kim – A Quick and Dirty D3.js
Overview
1. Brief History of D3
2. Data Preparation
3. Basic Drawing
4. Advanced Chart Drawing
5. Interaction
6. Transitions
7. Other Features
8. Tips
9. Q&A
Table of Contents
3
Course | Young-Ho Kim – A Quick and Dirty D3.js
Overview
D3.js is a JavaScript library for manipulating
documents based on data – d3js.org
What is D3.js?
4
Data-Driven Documents
Course | Young-Ho Kim – A Quick and Dirty D3.js
Overview
• D3 is a research project in Stanford Vis Group.
• D3 was written and maintained by Micheal Bostock.
• Proposed at InfoVis 2011.
Micheal Bostock, Vadim Ogievetsky, and Jeffrey Heer. D3: Data-Driven Documents.
• descendant of ProtoVis (2009) chart drawing library.
5
What is D3.js?
Course | Young-Ho Kim – A Quick and Dirty D3.js
Why D3.js?
People are getting more familiar with charts and visualization.
Data Journalism, Big Data, Infographics…
6
Today’s Visualization is Dynamic
Daily MaverickInteractive visualizations of NY Times
Course | Young-Ho Kim – A Quick and Dirty D3.js
Why D3.js?
Digital media enables high interactivity
Information visualization is no more a static chart printed on paper.
7
Today’s Visualization is Dynamic
Radik Sadana et al. TouchVis Tipco Spotfire
Course | Young-Ho Kim – A Quick and Dirty D3.js
Why D3.js?
Web is the most accessible, and actively-used
platform for interactive visualization.
Don’t need to install stand-alone applications,
One-sided modification(bug fix, upgrade, …) is available.
8
Today’s Visualization is Dynamic
Course | Young-Ho Kim – A Quick and Dirty D3.js
What is D3.js?
• D3 helps you draw visual elements based on the arrays of
the data.
• You can dynamically modify DOM element of an HTML do
cument without explicitly looping among the data points.
9
Simple description on D3
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tutorial
Using D3 demands basic knowledges of...
• JavaScript : D3 is a JavaScript library.
• HTML : D3 substitutes DOM elements for drawing.
• CSS : D3 visualizations can be stylized using CSS.
• jQuery : D3 resembles jQuery much. But a little different in terms of
its syntax. You will have to use jQuery together for more complicate
d interactive visualization.
10
Prerequisites
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tutorial
Lets use D3.js!
Tutorial 1. Prepare to use D3
11
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tutorial
• A Web browser and a text editor
• We will use FireFox or Safari in this tutorial for some reasons.
• You may use any text editor familiar with you.
• Developer tools on a browser are very helpful for JavaScript
programing.
12
Tutorial 1. Prepare to use D3 (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tutorial
http://hcil.snu.ac.kr/~muclipse/d3_course_tutorial_yhkim.zip
Download the tutorial files.
Start tutorial from starthere.html file.
The tutorial is incremental and sequential.
If you didn’t catch the tutorial, skip it by using the answer files
and use it as a start point from the next tutorial.
13
Tutorial 1. Prepare to use D3 (Cont.)
Data Preparation
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
• Building data table to be used in your visualization is almost
a half of the visualization process.
• A scheme of the data is crucial for the conciseness of your c
ode and the difficulty of your entire development.
• Deriving a table from a chart is much more difficult than dra
wing a chart from a table.
15
Using Data Table on Interactive Visualization
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
Imagine you want to draw a bar chart like this.
16
Using Data Table on Interactive Visualization
Sally Tom John
5
10
7.5
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
It’s not hard to derive this table from the chart.
17
Using Data Table on Interactive Visualization
Sally Tom John
5
10
7.5
Sally 5
Tom 10
John 7.5
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
D3 is a JavaScript so the table must be the form of JSON…
18
Using Data Table on Interactive Visualization
Sally 5
Tom 10
John 7.5
{
“Sally”:5,
“Tom”:10,
“John”:7.5
}
[{“Sally”:5},
{“Tom”:10},
{“John”:7.5}]
or
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
You will have a very hard time with these data structures.
19
Using Data Table on Interactive Visualization
Sally 5
Tom 10
John 7.5
{
“Sally”:5,
“Tom”:10,
“John”:7.5
}
[{“Sally”:5},
{“Tom”:10},
{“John”:7.5}]
or
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
Every data table needs ‘schema’ – column names.
In other words, make your data structure to be “loopable”.
20
Using Data Table on Interactive Visualization
Name Value
Sally 5
Tom 10
John 7.5
[{“Name”:“Sally”, “Value”:5},
{“Name”:“Tom”, “Value”:10},
{“Name”:“John”, “Value”:7.5}]
A key must be a schema(column), not a value.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
• D3 provide functions to load data from an URL.
d3.csv(URL, callback)
d3.json(URL, callback)
• Tsv, text, xml, html are also supported.
• I recommend using JSON because it is versatile.
• Data is loaded asynchronously. So we should wait until t
he loading is finished : Do everything in a callback.
21
Loading Data in D3
d3.json(URL, function(error, json){
if(json!=null){
//Do Something
}
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
Add this code inside your <script> block.
22
Tutorial 2. Loading Data Table
d3.json(“data.json”, function(error, json){
if(json!=null){
console.log(json);
}
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Data Preparation
Add this code inside your <script> block.
23
Tutorial 2. Loading Data Table (Cont.)
d3.json(“data.json”, function(error, json){
if(json!=null){
console.log(json);
}
});
This callback is invoked when
the loading finishes.
The second parameter contains loaded
JSON object if loaded without an error.
Basic Drawing
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
D3 is similar to jQuery.
Selectors, Styles, Attributes, Text… but its syntax is slightly different.
D3 visualizes by substituting DOM elements.
Appending new elements, removing elements, modifying styles and a
ttributes of elements…
25
Drawing Mechanism of D3
codefactor.com
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Both jQuery and D3 starts with selection
26
D3 vs jQuery Basics
d3.select(“body”) $(“body”)
Appending new DOM element
d3.select(“body”).append(“p”) $(“body”).append(“<p></p>”)
D3 function is cascaded to descendant.
d3.select(“body”).append(“p”).text(“test”)
Returns <p> child element selection.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• Let’s draw an HTML table dynamically.
• Write this code somewhere in your <script> block.
27
Tutorial 3. Drawing Table Dynamically
var table = d3.select(“body”).append(“table”);
var row1 = table.append(“tr”);
row1.append(“td”).text(“Sally”);
row1.append(“td”).text(“5”);
var row2 = table.append(“tr”);
row2.append(“td”).text(“Tom”);
row2.append(“td”).text(“10”);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
28
Tutorial 3. Drawing Table Dynamically
var table = d3.select(“body”).append(“table”);
var row1 = table.append(“tr”);
row1.append(“td”).text(“Sally”);
row1.append(“td”).text(“5”);
var row2 = table.append(“tr”);
row2.append(“td”).text(“Tom”);
row2.append(“td”).text(“10”);
Save selection to variable if more than one child will be appended.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
To draw elements in a data-driven way, you should understa
nd a concept of Selections, Binding and Joins in D3.
Data-driven Drawing
1. Select elements to be connected to data (Selection)
2. Bind data to the selection (Binding)
3. Add, Modify, or Remove elements based on data (Join)
29
Going Data-Driven Way
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Elements are first ‘selected’ even if they don’t exist yet.
• d3.selectAll(selector) : returns all elements with selector
• d3.select(selector) : returns the first element with selector
• D3 uses CSS3 selectors.
• If no one matches the selector, they return an empty selection.
30
Selecting Elements
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Now the data is connected to the selection.
selection.data(array, key=null)
This function pairs selected elements with an array of data
values. → What if the number of data values are different from the s
elected elements? → That’s what Join does.
31
Binding Data
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Join handles 3 cases of the overlaps of Data and Nodes(selection).
Enter: A set of newly added data. Not matched with current selection.
Update: A set of already matched pairs of a data point and an element.
Exit: A set of selected nodes the data of which do not exist anymore.
32
Joins
Forget about Update
and Exit for now.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
D3 join functions returns selections with corresponding joi
n set.
• selection.data().enter() : returns the empty selection of el
ements that should be newly added.
• selection.data() : default data function returns an update se
lection.
• selection.data().exit() : returns selection of the elements
that should be removed.
33
Joins (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Let’s draw a bar chart in a data-driven way.
Add this code inside your callback.
34
Tutorial 4. Div Bar Chart
d3.json(“URL”, function(error, json){
if(json!=null){
//Write code here
}
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
35
Tutorial 4. Div Bar Chart (Cont.)
d3.json(“URL”, function(error, json){
if(json!=null){
d3.select(“body”)
.selectAll(“div”)
.data(json)
.enter()
.append(“div”);
}
}
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
36
Tutorial 4. Div Bar Chart (Cont.)
d3.json(“URL”, function(error, json){
if(json!=null){
d3.select(“body”)
.selectAll(“div”)
.data(json)
.enter()
.append(“div”);
}
}
←Use <div> for a bar.
←Bind data.
←Get enter selection
← Functions are applied to each
selected element without using loops.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• You will see nothing because <div> is transparent in defa
ult.
• D3 provides functions to modify attributes and styles of
DOM elements.
• Attributes provide additional information about HTML elements i
nside the tag. <div class=“contents”>
• Styles provide style information about selections in CSS, or abo
ut an element in “style” attribute.
37
Styles and Attributes
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
selection.attr(“attribute”, “value”)
selection.attr(“attribute”, function(datum, index){return value})
Changes attribute of each selected element. If value is functio
n, you can dynamically assign attribute on each element.
38
Styles and Attributes (Cont.)
selection.style(“style”, “value”)
selection.style(“style”, function(datum, index){return value})
Changes style. The style is applied to “style” attribute of each
selected element, not globally in CSS.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Append some style functions to the selection to make our
chart visible.
39
Tutorial 5. Div Bar Chart Styling
d3.select(“body”)
.selectAll(“div”)
.data(json)
.enter()
.append(“div”)
.style(“width”, function(d){return d.value * 5 + “px”;})
.style(“background”, “red”)
.text(function(d){return d.value});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• Using div has many limitations on chart drawing.
• SVG is more suitable for visualization.
• SVG(Scalable Vector Graphics) is a vector image defined by X
ML-based markups inside webpage. http://www.w3schools.com/svg/
• SVG graphic element is considered the same as other DOM ele
ments in the HTML document.
• Every geometric attributes are designated on attributes in tag, s
ome attributes are also available in style.
40
Introduction to SVG
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• SVG shares many styling properties with CSS.
• Some distinction that may confusing:
41
SVG Styles vs CSS Styles
CSS Style SVG Style(Attribute)
size font-size
color font-color
background fill
border-style stroke
border-width stroke-width
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• SVG drawing is different from classic HTML document.
• SVG elements are not cascaded in layout.
• They are defined under Cartesian coordinates inside the
canvas of SVG image.
42
Preparing SVG Drawing
<html><body>
<svg width=“150” height=“150”>
<rect x=“10” y=“20” width=“60” height=“30” fill=red/>
</svg>
</body></html>
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• <svg> tag with “width” and “height” attributes must be
defined as the outmost markup.
• Topleft corner is (0,0).
43
Preparing SVG Drawing (Cont.)
<svg width=“150” height=“150”>
</svg>
(0,0)
(150,150)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
rect (x,y,width,height)
circle (cx, cy, r)
ellipse (cx, cy, rx, ry)
line (x1, y1, x2, y2)
path (d)
polygon (points)
44
Basic SVG Elements (geometric attributes)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• <text> draws text on the svg image. Similar to simple
HTML text but provides more powerful styling and can
be drawn anywhere.
• <g> (group) groups its child elements and the position of
group acts as an origin of its children. Group is really
important in complicated visualization. You can reduce
the amount of code by clever use of groups.
45
Other important SVG Elements
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• Change your HTML bar chart to SVG.
46
Tutorial 6. Migration to SVG
d3.select(“body”)
.append(“svg”)
.attr({width:500, height:500})
.selectAll(“rect”)
.data(json)
.enter()
.append(“rect”)
.attr(“width”, function(d){return d.value * 5})
.attr(“height”, 500/json.length - 2)
.attr(“y”, function(d,i){return i * 500/json.length});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
• Change your HTML bar chart to SVG.
47
Tutorial 6. Migration to SVG (Cont.)
d3.select(“body”)
.append(“svg”)
.attr({width:500, height:500})
.selectAll(“rect”)
.data(json)
.enter()
.append(“rect”)
.attr(“width”, function(d){return d.value * 5})
.attr(“height”, 500/json.length - 2)
.attr(“y”, function(d,i){return i * 500/json.length});
←You can assign multiple attributes or
styles at once.
↑ Unlike HTML, SVG elements are not cascaded so
you should explicitly assign y position.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Basic Drawing
Your code should look like this.
48
Tutorial 6. Migration to SVG (Cont.)
Advanced Chart Drawing
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
Now we can draw bars based on data. But we still need
more things to make a complete chart.
50
Still Not enough to be a Complete Chart…
←The bar with maximum value do not exceed the canvas.
↑ Ordinary charts contains axes.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Scale is a function that maps data value to the extent of
real image coordinate under specific formula:
• Quantitative scales including linear, log, power,…
• Ordinal scales provide discrete positions for ordinal values.
• Time scales provide linear mappings for time points on timeline.
• When you draw data elements on SVG plane, it is
convenient to set their positions with scales rather than
calculating them by yourself.
51
Scales
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• d3.scale provide most of scale functions.
d3.scale.linear(), d3.scale.ordinal(), d3.scale.log() …
• Properties are cascaded to the end of these functions.
• Linear Scale Properties:
• domain([start, end]) : define the extent of data values.
• range([start, end]) : define the extent of output coordinates.
• Ordinal Scale Properties:
• domain([values]) : specify all the values.
• rangeBands([start, end]) : define the extent of output
coordinates.
52
Scales (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
Usage example:
var x = d3.scale.linear().domain([2,5]).range([0,10]);
Now you can calculate mapped coordinate by simply calling
x(dataValue).
Ordinal/nominal scales are similar:
var x = d3.scale.ordinal().domain([“A”, “B”, “C”])
.rangeBands([0, 10]);
Now you can calculate mapped coordinate by simply calling
x(“A”), x(“B”), or x(“C”).
53
Scales (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Define scale function on the top of callback, and replace
the width calculation code.
54
Tutorial 7. Employing scales
d3.json(“URL”, function(error, json){
if(json!=null){
var x = d3.scale.linear().domain([0, 100]).range([0, 500]);
d3.select(“body”)
…
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, 500/json.length - 2)
.attr(“y”, function(d,i){return i * 500/json.length});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Define scale function on the top of callback, and replace
the width calculation code.
55
Tutorial 7. Employing scales
d3.json(“URL”, function(error, json){
if(json!=null){
var x = d3.scale.linear().domain([0, 100]).range([0, 500]);
d3.select(“body”)
…
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, 500/json.length - 2)
.attr(“y”, function(d,i){return i * 500/json.length});
Horizontal range of the SVG plane
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• D3 provide axis as a function that draws axis based on scale.
• Axis component is attached to chart area in 4 directions:
56
Adding Axis
0 20 40 60 80 100 120 140
0 20 40 60 80 100 120 140
0
20
40
60
80
100
120
140
0
20
40
60
80
100
120
140
Top
Bottom
Left RightRed dots are pivot position of the axis
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
d3.svg.axis()
Returns a function to add axis component to a selection.
• axis.scale(scale) : assigns a scale for the axis.
• axis.orient(orientation) : assigns an orientation for
the axis. ( “left”, “top”, “right”, “bottom”)
57
Axis Component API
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• To add axis component in SVG, we need to prepare space.
58
Grouping Chart Regions
SVG
Chart(coordinate space)
Left A
xis
Bottom Axis
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
In convention, chart elements are drawn in a group.
59
Grouping Chart Regions
var padding = {left:50, top:10, right:10, bottom:50};
var chart = d3.select(“body”)
.append(“svg”).attr({width:500, height:500})
.append(“g”)
.attr(“transform”, “translate(” + padding.left + “,”
+ padding.top + “)”);
Paddings are used to allocate space for axes.
“Transform” attribute is used to translate group.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• We will add a left and a bottom axes.
• First, add paddings on the top of callback..
60
Tutorial 8. Employing Axis
d3.json(“URL”, function(error, json){
if(json!=null){
var padding = {left:50, top:10, right:10, bottom:50};
var chartWidth = 500 – padding.left – padding.right;
var chartHeight = 500 – padding.top – padding.bottom;
• chartWidth and chartHeight will be used in scales.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
Define x-axis function.
61
Tutorial 8. Employing Axis (Cont.)
var x = d3.scale.linear().domain([0, 100]).range([0, chartWidth]);
var xAxis = d3.svg.axis().orient(“bottom”).scale(x);
//This time we will use scale in y values, too.
var names = json.map(function(d){return d.name});
var y = d3.scale.ordinal().domain(names)
.rangeBands([0, chartHeight]);
var yAxis = d3.svg.axis().orient(“left”).scale(y);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Define chart area.
62
Tutorial 8. Employing Axis (Cont.)
var chart = d3.select(“body”)
.append(“svg”).attr({width:500, height:500})
.append(“g”)
.attr(“transform”, “translate(” + padding.left + “,”
+ padding.top + “)”);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Draw axis.
63
Tutorial 8. Employing Axis (Cont.)
chart.append(“g”).attr(“class”, “x axis”)
.attr(“transform”, “translate(0,” + chartHeight + “)”)
.call(xAxis);
chart.append(“g”).attr(“class”, “y axis”)
.call(yAxis);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Draw bars.
64
Tutorial 8. Employing Axis (Cont.)
chart.selectAll(“rect”)
.data(json)
.enter()
.append(“rect”)
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, chartHeight/json.length - 2)
.attr(“y”, function(d){return y(d.name)});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Now you have axes.
65
Tutorial 8. Employing Axis (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Your axis would look ugly. Let’s do some CSS.
66
Styling Chart
0 20 40 60 80
<path class=“domain” … >
<g class=“tick” … >
A tick and a value text are grouped.
<line … >
<text … >
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• The lines of the axis are <line> and <path> tags. We can
style these in CSS or just in code.
67
Axis Stylesheets
.axis path, .axis line{
fill:none;
stroke-width:1px;
stroke:black;
}
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• The tick labels are <text> tags.
68
Axis Stylesheets
.axis text{
font-size:10px;
font-weight:bold;
}
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Add <style> block.
69
Tutorial 9. Styling Axis
<head>
<style>
.axis path, .axis line{
fill:none;
stroke-width:1px;
stroke: black;
}
.axis text{
font-size:10px;
font-weight:bold;
}
</style>
…
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• We may want our chart to look more elaborated.
• e.g. Redundant encoding
• We will use <group> for mappings.
70
Toward More Complicated Data Elements
50
75
120
100
80
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
For now, we paired each data value to one SVG element.
71
Grouping Elements per Data Point
A 50
B 75
C 120
D 100
E 80
SVG Rect
chart.selectAll(“rect”)
.data(json)
.enter()
.append(“rect”)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Now a data value is paired to a set of a rect and a text.
72
Grouping Elements per Data Point
A 50
B 75
C 120
D 100
E 80
50
75
120
100
80
SVG Rect SVG Text
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• We will add values to our bars.
• Modify our bar drawing code.
73
Tutorial 10. Redundant Encoding
var bars = chart.selectAll(“g.bar”)
.data(json)
.enter()
.append(“g”)
.attr(“class”, “bar”)
.attr(“transform”,
function(d){return “translate(0,” + y(d.name) + “)”);
• Topmost data mapping is replaced by “g”.
• We defined y-position of bars on groups in advance.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Each group has one rect and one text.
74
Tutorial 10. Redundant Encoding
var barHeight = chartHeight/json.length – 2;
bars.append(“rect”)
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, barHeight);
bars.append(“text”)
.attr(“fill”, “white”)
.attr(“x”, function(d){return x(d.value) – 5})
.attr(“y”, barHeight/2)
.attr(“dominant-baseline”, “middle”)
.attr(“text-anchor”, “end”)
.text(function(d){return d.value});
86
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
• Each group has one rect and one text.
75
Tutorial 10. Redundant Encoding
var barHeight = chartHeight/json.length – 2;
bars.append(“rect”)
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, barHeight);
bars.append(“text”)
.attr(“fill”, “white”)
.attr(“x”, function(d){return x(d.value) – 5})
.attr(“y”, barHeight/2)
.attr(“dominant-baseline”, “middle”)
.attr(“text-anchor”, “end”)
.text(function(d){return d.value});
Right alignment,
center in vertical position
←set content of the block.
86
Course | Young-Ho Kim – A Quick and Dirty D3.js
Advanced Chart Drawing
Now the values are encoded to the length and the text.
76
Tutorial 10. Redundant Encoding
Interaction
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• D3 handles JavaScript event model to make the
elements responsive.
• D3 event works by adding event listeners to d3 selection.
78
Leveraging Advantages of Web
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• type: type of event to response
(e.g. “mouseover”, “mouseleave”, “click”, “mousedown”, “mouseup”)
• function(d,i): event handler.
d: a single corresponding data point (datum)
i: the index of the data point
• on() function returns selection itself, enabling cascading.
79
D3 Event API
selection.on(type, function(d,i){})
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• The parameters of handler function gives information
about data. It is useful for printing interacted data.
• ‘this’ in the scope of handler function indicates the DOM
element itself. So you can get a selection of responded
element by d3.select(this)
80
Event Handling
selection.on(type, function(d,i){
//d, i : data-level handling
//d3.select(this) : visualization-level handling
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Let’s make our bar chart more interactive. We will
highlight the bar which the mouse is hovering on.
81
Tutorial 11. Details-On-Demand
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
Append event functions to rect selections.
82
Tutorial 11. Details-On-Demand (Cont.)
bars.append(“rect”)
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, barHeight)
.on(“mouseover”, function(d,i){
d3.select(this).attr(“fill”, “orange”);
})
.on(“mouseleave”, function(d,i){
d3.select(this).attr(“fill”, null);
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
Append event functions to <rect> selections.
83
Tutorial 11. Details-On-Demand (Cont.)
bars.append(“rect”)
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, barHeight)
.on(“mouseover”, function(d,i){
d3.select(this).attr(“fill”, “orange”);
})
.on(“mouseleave”, function(d,i){
d3.select(this).attr(“fill”, null);
});
We didn’t use data information here.
←Change color
when mouse entered
←Reset color when
mouse leaved
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Now your rects are reactive to your mouse cursor.
• Let’s do some more. What about showing the value
labels only when mouse is hover?
• The bar unit is a group of a <rect> and a <text>. To
control both children, it is natural to attach event listener
to each group, not the rect.
84
Tutorial 12. Details-On-Demand Advanced
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Change the text labels transparent. We will show the label
only while the mouse is hovering on corresponding bar.
85
Tutorial 12. Details-On-Demand Advanced (Cont.)
bars.append(“text”)
.attr(“fill”, “white”)
.attr(“x”, function(d){return x(d) – 5})
.attr(“y”, barHeight/2)
.attr(“dominant-baseline”, “middle”)
.attr(“text-anchor”, “end”)
.attr(“display”, “none”)
.text(function(d){return d.value});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Remove event listener code from rect selections.
86
Tutorial 12. Details-On-Demand Advanced (Cont.)
bars.append(“rect”)
.attr(“width”, function(d){return x(d.value)})
.attr(“height”, barHeight);
.on(“mouseover”, function(d,i){
d3.select(this).attr(“fill”, “orange”);
})
.on(“mouseleave”, function(d,i){
d3.select(this).attr(“fill”, null);
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Substitute the group selection code.
87
Tutorial 12. Details-On-Demand Advanced (Cont.)
var bars = chart.selectAll(“g”)
…
.on(“mouseover”, function(d,i){
d3.select(this).select(“rect”).attr(“fill”, “orange”);
d3.select(this).select(“text”).attr(“display”, null);
})
.on(“mouseleave”, function(d,i){
d3.select(this).select(“rect”).attr(“fill”, null);
d3.select(this).select(“text”).attr(“display”, “none”);
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Substitute the group selection code.
88
Tutorial 12. Details-On-Demand Advanced (Cont.)
var bars = chart.selectAll(“g”)
…
.on(“mouseover”, function(d,i){
d3.select(this).select(“rect”).attr(“fill”, “orange”);
d3.select(this).select(“text”).attr(“display”, null);
})
.on(“mouseleave”, function(d,i){
d3.select(this).select(“rect”).attr(“fill”, null);
d3.select(this).select(“text”).attr(“display”, “none”);
});
<group> Null assigns ‘default value’
Course | Young-Ho Kim – A Quick and Dirty D3.js
Interactions
• Now the ticks shows only when hovering.
89
Tutorial 12. Details-On-Demand Advanced (Cont.)
Transitions
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Technically, transitions are smoothly changing the visuals
by interpolating geometric properties.
91
Benefits of Incorporating Transitions
Jeffrey Heer, George Robertson. 2007. Animated Transitions in Statistical Data Graphics
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Interpolating the elements can orient user to keep
perception of change – Useful for refreshing chart.
• Aesthetically pleasing.
92
Benefits of Incorporating Transitions (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• In D3, a transition is a special type of selection.
• Attributes and style assignment applies over time.
93
Transitions in D3
selection.transition()
• Transition object has 3 main properties:
• transition.duration(millis) : specifies per-element duration
in milliseconds. The parameter can be a function(d,i).
• transition.delay(millis) : the transition starts after the delay.
The parameter can be a function(d,i).
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
94
Transitions in D3 (Cont.)
transition.ease(“method”)
Specifies the transition easing function. The parameter can
be a function(t), or a predefined string constant.
D3.js Easing Checker
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Let’s make your bars appear smoothly.
• Animate the bar width from 0 to target width.
• First, set the initial width of rect as Zero.
95
Tutorial 13. Smooth Emerging
bars.append(“rect”)
.attr(“width”, 0)
.attr(“height”, barHeight)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Then derive a transition from the selection.
• Assign duration and the target attributes.
• Easing is optional. Try other easing functions, too.
96
Tutorial 13. Smooth Emerging (Cont.)
bars.append(“rect”)
.attr(“width”, 0)
.attr(“height”, barHeight)
.transition()
.duration(750)
.ease(“cubic-out”)
.attr(“width”, function(d){return x(d.value)});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• We learned that the delay function allows a function as a
paremeter. Let’s make our bars emerge sequentially.
97
Tutorial 13. Smooth Emerging (Cont.)
bars.append(“rect”)
.attr(“width”, 0)
.attr(“height”, barHeight)
.transition()
.duration(750)
.delay(function(d,i){ return i * 100 })
.ease(“cubic-out”)
.attr(“width”, function(d){return x(d.value)});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Transitions can be used in event handlers.
98
Tutorial 13. Smooth Emerging (Cont.)
on("mouseover", function(d,i){
d3.select(this).select("rect")
.transition().duration(300).ease("cubic-out")
.attr("fill", "orange");
d3.select(this).select("text").attr("display", null);
})
.on("mouseleave", function(d,i){
d3.select(this).select("rect")
.transition().duration(200).attr("fill", null);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Transition is powerful for interpolating between the two
states of visualization.
• D3’s AJAX data loading enables refreshing chart by
applying different data to the same chart.
• By combination of transition and joins, we can easily
refresh our visualization.
99
Transition between Data
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Transition between data is one of the major power of D3.
• In this final tutorial, we will make our visualization switch
between different dataset, SMOOTHLY.
100
Tutorial 14. Transition between Data
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• We will change the dataset.
• data2.json
• Containing two tables in an
array.
• Names in the second table
is a subset of the first one,
but the values are different.
101
Tutorial 14. Transition between Data (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• First, we need a button to shuffle.
• Add <button> element inside the body.
• Assign onClick event handler.
• We will define shuffle() later.
102
Tutorial 14. Transition between Data (Cont.)
<body>
<button onClick="shuffle()">Shuffle</button>
…
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Pull out the declaration of variables that should be consistent
during runtime.
• Variables declared inside the d3.json() callback cannot be
accessed outside.
103
Tutorial 14. Transition between Data (Cont.)
<script>
var padding = {left:80, top:0, right:30, bottom:50};
var chartWidth = 500 - padding.left - padding.right;
var chartHeight = 500 - padding.top - padding.bottom;
…
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
• Scales and axis functions are also reused during runtime.
• Y axis ticks should be changed so we don’t assign domain()
here.
104
Tutorial 14. Transition between Data (Cont.)
…
var chartHeight = 500 - padding.top - padding.bottom;
var x = d3.scale.linear().domain([0, 100]).range([0,
chartWidth]);
var xAxis = d3.svg.axis().orient("bottom").scale(x);
var y = d3.scale.ordinal().rangeBands([0, chartHeight]);
var yAxis = d3.svg.axis().orient("left").scale(y);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Pull out the chart canvas too. The SVG must be appended only
once.
105
Tutorial 14. Transition between Data (Cont.)
…
var yAxis = d3.svg.axis().orient("left").scale(y);
var chart = d3.select("body")
.append("svg").attr({width:500, height:500})
.append("g")
.attr("transform", "translate(" + padding.left
+ ",“ + padding.top + ")");
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
We also need the axis groups be appended only once.
106
Tutorial 14. Transition between Data (Cont.)
var chart = …
chart.append("g").attr("class", "x axis")
.attr("transform", "translate(0," + chartHeight + ")")
.call(xAxis);
chart.append("g").attr("class", "y axis")
.call(yAxis);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
All we need to do when the data loading is finished is to send
the reference of loaded data to global scope.
Do not forget to change the file name to “data2.json”.
107
Tutorial 14. Transition between Data (Cont.)
var data;
d3.json("data2.json", function(error, json){
if(json!=null){
data = json;
}
});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Next, we need to make routines to build final chart based on
the data.
In the routine, focus on what elements would change according
to the data. First, the Y-axis should be refreshed.
108
Tutorial 14. Transition between Data (Cont.)
function refresh(data){
y.domain(data.map(function(d){return d.name}));
chart.select(".y.axis")
.transition().duration(500).call(yAxis);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
This is the point. Remember the three joins in selection?
Memorize the order ‘Enter-Update-Exit’.
Handling joins is one of the most challenging part in D3.
Let’s start from initializing update selection by data() function.
109
Tutorial 14. Transition between Data (Cont.)
var bars = chart.selectAll("g.bar")
.data(data);
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Handling Enter selection – You initialize the new things.
The code is almost the same as before.
110
Tutorial 14. Transition between Data (Cont.)
var new_bars = bars.enter()
.append("g")
.attr("class", "bar")
…
new_bars.append("rect")
…
new_bars.append("text")
…
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Handling Update selection – Think about what properties
should be modified(or updated).
First, the height of bars could be changed because it is derived
by the number of data rows.
The Y position of bars could be changed, too.
111
Tutorial 14. Transition between Data (Cont.)
var barHeight = chartHeight/data.length - 2;
bars.transition().duration(500)
.attr("transform", function(d){return "translate(0,"
+y(d.name)+")"});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
A <rect> and a <text> elements in each group need to be
updated.
112
Tutorial 14. Transition between Data (Cont.)
bars.select("rect")
.transition().duration(500)
.delay(function(d,i){return i*100})
.attr("width", function(d){return x(d.value)})
.attr("height", barHeight);
bars.select("text")
.transition().duration(500)
.delay(function(d,i){return i*100})
.attr("x", function(d){return x(d.value) - 5})
.attr("y", barHeight/2)
.text(function(d){return d.value});
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Handling Exit selection – Remove the elements properly.
You don’t need to care about rects and texts, because they will
be removed with their parent group.
The remove() function will remove the bars after the transition
finishes.
113
Tutorial 14. Transition between Data (Cont.)
bars.exit()
.transition().duration(250)
.style("opacity",0)
.remove();
}//end of refresh(data)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Finally, prepare shuffle() function on the outmost scope.
114
Tutorial 14. Transition between Data (Cont.)
…
}//end of refresh(data)
var currentIndex = 0;
function shuffle()
{
currentIndex = (++currentIndex)%2;
refresh(data[currentIndex]);
}
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
Good job. Your chart will be refreshed smoothly.
115
Tutorial 14. Transition between Data (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
One more important thing.
This is the true difference of the two tables.
116
Tutorial 14. Transition between Data (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
But your visualization pairs the rows like this.
117
Tutorial 14. Transition between Data (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Transitions
This mapping causes the transition not to be meaningful,
because the transition doesn’t show the implicit change of
the data.
But don’t worry. D3 solves this mapping problem easily.
Specify the second parameter of the data() function.
118
Tutorial 14. Transition between Data (Cont.)
var bars = chart.selectAll("g.bar")
.data(data, function(d){return d.name});
Course | Young-Ho Kim – A Quick and Dirty D3.js
When D3 matches the old data and the new data in the
element, it compares the keys derived from the parameter
function.
In this case, D3 will consider the two data points with the same
name field to be paired.
Transitions
119
Tutorial 14. Transition between Data (Cont.)
var bars = chart.selectAll("g.bar")
.data(data, function(d){return d.name});
Other Features of D3
Which we didn’t cover today
Course | Young-Ho Kim – A Quick and Dirty D3.js
Other Features of D3
D3 provide brushing components with predefined interaction.
https://github.com/mbostock/d3/wiki/SVG-Controls
http://bl.ocks.org/mbostock/1667367
http://bl.ocks.org/mbostock/4063663
121
Brushing
Course | Young-Ho Kim – A Quick and Dirty D3.js
Other Features of D3
Requires D3-tip library
https://github.com/caged/d3-tip
http://bl.ocks.org/Caged/6476579
122
Tooltips
Course | Young-Ho Kim – A Quick and Dirty D3.js
Other Features of D3
• Using tickFormat() function on scales, You can
specify the format of the tick labels.
• http://bl.ocks.org/mbostock/9764126
123
Formatting Axis Ticks
Tips
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tips
• JavaScript is a powerful language, but using D3, you will
see your code gets too long.
• CoffeeScript is a little language that compiles into pure
JavaScript in one-to-one mappings. http://coffeescript.org/
• Using it instead of pure JavaScript will significantly
reduce the amount of your code.
125
Learn Simplified JavaScript Descendants
.attr(“width”, function(d){return x(d.value)})
.attr “width”, (d)->x(d.value)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tips
• There are plenty of tutorials and questions by Bostock and other gurus on web.
• Most of the barriers you met are already dealt with before in stackoverflow.com.
126
Learn by Plenty of Tutorials and Questions
bl.ocks.org stackoverflow
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tips
• Although JavaScript and D3 make it look interactive, SVG is merely a static
vector image defined by markups.
• Svg code can be saved in a *.svg file and modified in Adobe Illustrator.
• Good for building figures of chart which is not supported by canonical tools such
as R or Excel.
127
D3 Chart Can Be Used Elsewhere.
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tips
• D3’s asynchronous data loading is good for visualizing dynamic data.
• If you are using D3 on your website with database, you can attach D3
visualization with data pulled from your database.
128
Learn ways to Dynamically Generating
Web Server Database
Client Server
URL from d3.json parameter
Generate JSON from Database
Visualize Server-side Data
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tips
• Server Frameworks based on interpreter languages are convenient for
data preparation. Most of them are designed to easily handle data
structure.
Ruby On Rails (Ruby), Django(Python), …
• Also, most of them are incorporating database.
129
Learn ways to Dynamically Generating (Cont.)
Course | Young-Ho Kim – A Quick and Dirty D3.js
Tips
• Building a complete visualization with pure D3 from scratch is a real
pain.
• If you are not designing your original visualization, try using other
projects wrapping D3 or substituting D3.
C3.js, Dimple, MetricsGraphics, ….
130
Do not Keep Your Eyes only on D3
Thank You!
Any Questions?
131

Mais conteúdo relacionado

Mais procurados

D3 Basic Tutorial
D3 Basic TutorialD3 Basic Tutorial
D3 Basic TutorialTao Jiang
 
SVG, CSS3, and D3 for Beginners
SVG, CSS3, and D3 for BeginnersSVG, CSS3, and D3 for Beginners
SVG, CSS3, and D3 for BeginnersOswald Campesato
 
D3.js 30-minute intro
D3.js   30-minute introD3.js   30-minute intro
D3.js 30-minute introFelipe
 
Introduction to d3js (and SVG)
Introduction to d3js (and SVG)Introduction to d3js (and SVG)
Introduction to d3js (and SVG)zahid-mian
 
D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)
D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)
D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)Oleksii Prohonnyi
 
Advanced D3 Charting
Advanced D3 ChartingAdvanced D3 Charting
Advanced D3 Chartingdcryan
 
Visual Exploration of Large Data sets with D3, crossfilter and dc.js
Visual Exploration of Large Data sets with D3, crossfilter and dc.jsVisual Exploration of Large Data sets with D3, crossfilter and dc.js
Visual Exploration of Large Data sets with D3, crossfilter and dc.jsFlorian Georg
 
Creating, Updating and Deleting Document in MongoDB
Creating, Updating and Deleting Document in MongoDBCreating, Updating and Deleting Document in MongoDB
Creating, Updating and Deleting Document in MongoDBWildan Maulana
 
CS101- Introduction to Computing- Lecture 41
CS101- Introduction to Computing- Lecture 41CS101- Introduction to Computing- Lecture 41
CS101- Introduction to Computing- Lecture 41Bilal Ahmed
 
SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...
SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...
SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...Sencha
 
Understanding Connected Data through Visualization
Understanding Connected Data through VisualizationUnderstanding Connected Data through Visualization
Understanding Connected Data through VisualizationSebastian Müller
 
Core Data Migrations and A Better Option
Core Data Migrations and A Better OptionCore Data Migrations and A Better Option
Core Data Migrations and A Better OptionPriya Rajagopal
 
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.GeeksLab Odessa
 
PCA11: Python for Product Managers
PCA11: Python for Product ManagersPCA11: Python for Product Managers
PCA11: Python for Product ManagersDavid Heller
 
Academy PRO: D3, part 1
Academy PRO: D3, part 1Academy PRO: D3, part 1
Academy PRO: D3, part 1Binary Studio
 

Mais procurados (20)

D3 Basic Tutorial
D3 Basic TutorialD3 Basic Tutorial
D3 Basic Tutorial
 
SVG, CSS3, and D3 for Beginners
SVG, CSS3, and D3 for BeginnersSVG, CSS3, and D3 for Beginners
SVG, CSS3, and D3 for Beginners
 
D3.js 30-minute intro
D3.js   30-minute introD3.js   30-minute intro
D3.js 30-minute intro
 
D3 js
D3 jsD3 js
D3 js
 
Introduction to d3js (and SVG)
Introduction to d3js (and SVG)Introduction to d3js (and SVG)
Introduction to d3js (and SVG)
 
D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)
D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)
D3.JS Tips & Tricks (export to svg, crossfilter, maps etc.)
 
Utahjs D3
Utahjs D3Utahjs D3
Utahjs D3
 
Advanced D3 Charting
Advanced D3 ChartingAdvanced D3 Charting
Advanced D3 Charting
 
Visual Exploration of Large Data sets with D3, crossfilter and dc.js
Visual Exploration of Large Data sets with D3, crossfilter and dc.jsVisual Exploration of Large Data sets with D3, crossfilter and dc.js
Visual Exploration of Large Data sets with D3, crossfilter and dc.js
 
Viewpic
ViewpicViewpic
Viewpic
 
Creating, Updating and Deleting Document in MongoDB
Creating, Updating and Deleting Document in MongoDBCreating, Updating and Deleting Document in MongoDB
Creating, Updating and Deleting Document in MongoDB
 
CS101- Introduction to Computing- Lecture 41
CS101- Introduction to Computing- Lecture 41CS101- Introduction to Computing- Lecture 41
CS101- Introduction to Computing- Lecture 41
 
SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...
SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...
SenchaCon 2016: Add Magic to Your Ext JS Apps with D3 Visualizations - Vitaly...
 
D3.js workshop
D3.js workshopD3.js workshop
D3.js workshop
 
Understanding Connected Data through Visualization
Understanding Connected Data through VisualizationUnderstanding Connected Data through Visualization
Understanding Connected Data through Visualization
 
SVGD3Angular2React
SVGD3Angular2ReactSVGD3Angular2React
SVGD3Angular2React
 
Core Data Migrations and A Better Option
Core Data Migrations and A Better OptionCore Data Migrations and A Better Option
Core Data Migrations and A Better Option
 
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
Java/Scala Lab: Борис Трофимов - Обжигающая Big Data.
 
PCA11: Python for Product Managers
PCA11: Python for Product ManagersPCA11: Python for Product Managers
PCA11: Python for Product Managers
 
Academy PRO: D3, part 1
Academy PRO: D3, part 1Academy PRO: D3, part 1
Academy PRO: D3, part 1
 

Destaque

Angular js, Yeomon & Grunt
Angular js, Yeomon & GruntAngular js, Yeomon & Grunt
Angular js, Yeomon & GruntRichard Powell
 
Grunt js and WordPress
Grunt js and WordPressGrunt js and WordPress
Grunt js and WordPressWP Australia
 
An Introduction to AngularJs Unittesting
An Introduction to AngularJs UnittestingAn Introduction to AngularJs Unittesting
An Introduction to AngularJs UnittestingInthra onsap
 
Wrangling the WordPress Template Hierarchy Like a Boss
Wrangling the WordPress Template Hierarchy Like a BossWrangling the WordPress Template Hierarchy Like a Boss
Wrangling the WordPress Template Hierarchy Like a BossIntrepidRealist
 
WordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and Grunt
WordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and GruntWordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and Grunt
WordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and GruntBrajeshwar Oinam
 
Come migliorare le performance di WordPress con il Visual Composer
Come migliorare le performance di WordPress con il Visual ComposerCome migliorare le performance di WordPress con il Visual Composer
Come migliorare le performance di WordPress con il Visual Composerliciapelliconi.it
 
Javascript testing: tools of the trade
Javascript testing: tools of the tradeJavascript testing: tools of the trade
Javascript testing: tools of the tradeJuanma Orta
 
Using Composer to create manageable WordPress websites
Using Composer to create manageable WordPress websitesUsing Composer to create manageable WordPress websites
Using Composer to create manageable WordPress websitesAnna Ladoshkina
 
WordPress Database: What's behind those 12 tables
WordPress Database: What's behind those 12 tablesWordPress Database: What's behind those 12 tables
WordPress Database: What's behind those 12 tablesMauricio Gelves
 
JavaScript Test-Driven Development with Jasmine 2.0 and Karma
JavaScript Test-Driven Development with Jasmine 2.0 and Karma JavaScript Test-Driven Development with Jasmine 2.0 and Karma
JavaScript Test-Driven Development with Jasmine 2.0 and Karma Christopher Bartling
 
WordPress Template Hierarchy
WordPress Template HierarchyWordPress Template Hierarchy
WordPress Template HierarchySarah Whinnem
 
Getting Started With Grunt for WordPress Development
Getting Started With Grunt for WordPress DevelopmentGetting Started With Grunt for WordPress Development
Getting Started With Grunt for WordPress DevelopmentDavid Bisset
 
Excel Document Recovery to the Rescue
Excel Document Recovery to the RescueExcel Document Recovery to the Rescue
Excel Document Recovery to the RescueWiley
 
Library Management System PPT
Library Management System PPTLibrary Management System PPT
Library Management System PPTTamaghna Banerjee
 

Destaque (18)

Data to d3
Data to d3Data to d3
Data to d3
 
Mastering Grunt
Mastering GruntMastering Grunt
Mastering Grunt
 
Angular js, Yeomon & Grunt
Angular js, Yeomon & GruntAngular js, Yeomon & Grunt
Angular js, Yeomon & Grunt
 
Grunt js and WordPress
Grunt js and WordPressGrunt js and WordPress
Grunt js and WordPress
 
GruntJS + Wordpress
GruntJS + WordpressGruntJS + Wordpress
GruntJS + Wordpress
 
An Introduction to AngularJs Unittesting
An Introduction to AngularJs UnittestingAn Introduction to AngularJs Unittesting
An Introduction to AngularJs Unittesting
 
Wrangling the WordPress Template Hierarchy Like a Boss
Wrangling the WordPress Template Hierarchy Like a BossWrangling the WordPress Template Hierarchy Like a Boss
Wrangling the WordPress Template Hierarchy Like a Boss
 
Metadata and me
Metadata and meMetadata and me
Metadata and me
 
WordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and Grunt
WordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and GruntWordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and Grunt
WordPress Theme Development Workflow with Node.js, Ruby, Sass, Bower and Grunt
 
Come migliorare le performance di WordPress con il Visual Composer
Come migliorare le performance di WordPress con il Visual ComposerCome migliorare le performance di WordPress con il Visual Composer
Come migliorare le performance di WordPress con il Visual Composer
 
Javascript testing: tools of the trade
Javascript testing: tools of the tradeJavascript testing: tools of the trade
Javascript testing: tools of the trade
 
Using Composer to create manageable WordPress websites
Using Composer to create manageable WordPress websitesUsing Composer to create manageable WordPress websites
Using Composer to create manageable WordPress websites
 
WordPress Database: What's behind those 12 tables
WordPress Database: What's behind those 12 tablesWordPress Database: What's behind those 12 tables
WordPress Database: What's behind those 12 tables
 
JavaScript Test-Driven Development with Jasmine 2.0 and Karma
JavaScript Test-Driven Development with Jasmine 2.0 and Karma JavaScript Test-Driven Development with Jasmine 2.0 and Karma
JavaScript Test-Driven Development with Jasmine 2.0 and Karma
 
WordPress Template Hierarchy
WordPress Template HierarchyWordPress Template Hierarchy
WordPress Template Hierarchy
 
Getting Started With Grunt for WordPress Development
Getting Started With Grunt for WordPress DevelopmentGetting Started With Grunt for WordPress Development
Getting Started With Grunt for WordPress Development
 
Excel Document Recovery to the Rescue
Excel Document Recovery to the RescueExcel Document Recovery to the Rescue
Excel Document Recovery to the Rescue
 
Library Management System PPT
Library Management System PPTLibrary Management System PPT
Library Management System PPT
 

Semelhante a A Quick and Dirty D3.js Tutorial

D3 in Jupyter : PyData NYC 2015
D3 in Jupyter : PyData NYC 2015D3 in Jupyter : PyData NYC 2015
D3 in Jupyter : PyData NYC 2015Brian Coffey
 
Data Visualization on the Web - Intro to D3
Data Visualization on the Web - Intro to D3Data Visualization on the Web - Intro to D3
Data Visualization on the Web - Intro to D3Angela Zoss
 
How my team is applying JS framework for PHP projects.
How my team is applying JS framework for PHP projects.How my team is applying JS framework for PHP projects.
How my team is applying JS framework for PHP projects.Damon Hung Tran
 
elm-d3 @ NYC D3.js Meetup (30 June, 2014)
elm-d3 @ NYC D3.js Meetup (30 June, 2014)elm-d3 @ NYC D3.js Meetup (30 June, 2014)
elm-d3 @ NYC D3.js Meetup (30 June, 2014)Spiros
 
Asp.net Lab manual
Asp.net Lab manualAsp.net Lab manual
Asp.net Lab manualTamil Dhasan
 
Yeoman AngularJS and D3 - A solid stack for web apps
Yeoman AngularJS and D3 - A solid stack for web appsYeoman AngularJS and D3 - A solid stack for web apps
Yeoman AngularJS and D3 - A solid stack for web appsclimboid
 
Interacting with Accumulo and Graphulo using Julia/Python D4M
Interacting with Accumulo and Graphulo using Julia/Python D4MInteracting with Accumulo and Graphulo using Julia/Python D4M
Interacting with Accumulo and Graphulo using Julia/Python D4MAccumulo Summit
 
Performance #5 cpu and battery
Performance #5  cpu and batteryPerformance #5  cpu and battery
Performance #5 cpu and batteryVitali Pekelis
 
React, D3 and the dataviz ecosystem
React, D3 and the dataviz ecosystemReact, D3 and the dataviz ecosystem
React, D3 and the dataviz ecosystemMarcos Iglesias
 
1Computer Graphics new-L1-Introduction to Computer Graphics.pdf
1Computer Graphics new-L1-Introduction to Computer Graphics.pdf1Computer Graphics new-L1-Introduction to Computer Graphics.pdf
1Computer Graphics new-L1-Introduction to Computer Graphics.pdfYomna Mahmoud Ibrahim Hassan
 
The State of Front-end At CrowdTwist
The State of Front-end At CrowdTwistThe State of Front-end At CrowdTwist
The State of Front-end At CrowdTwistMark Fayngersh
 
SQL to NoSQL: Top 6 Questions
SQL to NoSQL: Top 6 QuestionsSQL to NoSQL: Top 6 Questions
SQL to NoSQL: Top 6 QuestionsMike Broberg
 
Supervised embedding techniques in search ranking system
Supervised embedding techniques in search ranking systemSupervised embedding techniques in search ranking system
Supervised embedding techniques in search ranking systemMarsan Ma
 
Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"
Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"
Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"Fwdays
 
Basic Deep Learning.pptx
Basic Deep Learning.pptxBasic Deep Learning.pptx
Basic Deep Learning.pptxmabog44
 
Computer Project for class 12 CBSE on school management
Computer Project for class 12 CBSE on school managementComputer Project for class 12 CBSE on school management
Computer Project for class 12 CBSE on school managementRemaDeosiSundi
 

Semelhante a A Quick and Dirty D3.js Tutorial (20)

D3 & MeteorJS
D3 & MeteorJSD3 & MeteorJS
D3 & MeteorJS
 
D3 & MeteorJS
D3 & MeteorJSD3 & MeteorJS
D3 & MeteorJS
 
D3 in Jupyter : PyData NYC 2015
D3 in Jupyter : PyData NYC 2015D3 in Jupyter : PyData NYC 2015
D3 in Jupyter : PyData NYC 2015
 
Data Visualization on the Web - Intro to D3
Data Visualization on the Web - Intro to D3Data Visualization on the Web - Intro to D3
Data Visualization on the Web - Intro to D3
 
How my team is applying JS framework for PHP projects.
How my team is applying JS framework for PHP projects.How my team is applying JS framework for PHP projects.
How my team is applying JS framework for PHP projects.
 
Data herding
Data herdingData herding
Data herding
 
Data herding
Data herdingData herding
Data herding
 
elm-d3 @ NYC D3.js Meetup (30 June, 2014)
elm-d3 @ NYC D3.js Meetup (30 June, 2014)elm-d3 @ NYC D3.js Meetup (30 June, 2014)
elm-d3 @ NYC D3.js Meetup (30 June, 2014)
 
Asp.net Lab manual
Asp.net Lab manualAsp.net Lab manual
Asp.net Lab manual
 
Yeoman AngularJS and D3 - A solid stack for web apps
Yeoman AngularJS and D3 - A solid stack for web appsYeoman AngularJS and D3 - A solid stack for web apps
Yeoman AngularJS and D3 - A solid stack for web apps
 
Interacting with Accumulo and Graphulo using Julia/Python D4M
Interacting with Accumulo and Graphulo using Julia/Python D4MInteracting with Accumulo and Graphulo using Julia/Python D4M
Interacting with Accumulo and Graphulo using Julia/Python D4M
 
Performance #5 cpu and battery
Performance #5  cpu and batteryPerformance #5  cpu and battery
Performance #5 cpu and battery
 
React, D3 and the dataviz ecosystem
React, D3 and the dataviz ecosystemReact, D3 and the dataviz ecosystem
React, D3 and the dataviz ecosystem
 
1Computer Graphics new-L1-Introduction to Computer Graphics.pdf
1Computer Graphics new-L1-Introduction to Computer Graphics.pdf1Computer Graphics new-L1-Introduction to Computer Graphics.pdf
1Computer Graphics new-L1-Introduction to Computer Graphics.pdf
 
The State of Front-end At CrowdTwist
The State of Front-end At CrowdTwistThe State of Front-end At CrowdTwist
The State of Front-end At CrowdTwist
 
SQL to NoSQL: Top 6 Questions
SQL to NoSQL: Top 6 QuestionsSQL to NoSQL: Top 6 Questions
SQL to NoSQL: Top 6 Questions
 
Supervised embedding techniques in search ranking system
Supervised embedding techniques in search ranking systemSupervised embedding techniques in search ranking system
Supervised embedding techniques in search ranking system
 
Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"
Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"
Алексей Ященко и Ярослав Волощук "False simplicity of front-end applications"
 
Basic Deep Learning.pptx
Basic Deep Learning.pptxBasic Deep Learning.pptx
Basic Deep Learning.pptx
 
Computer Project for class 12 CBSE on school management
Computer Project for class 12 CBSE on school managementComputer Project for class 12 CBSE on school management
Computer Project for class 12 CBSE on school management
 

Último

Oracle Database 23c Security New Features.pptx
Oracle Database 23c Security New Features.pptxOracle Database 23c Security New Features.pptx
Oracle Database 23c Security New Features.pptxSatishbabu Gunukula
 
Flow Control | Block Size | ST Min | First Frame
Flow Control | Block Size | ST Min | First FrameFlow Control | Block Size | ST Min | First Frame
Flow Control | Block Size | ST Min | First FrameKapil Thakar
 
How to release an Open Source Dataweave Library
How to release an Open Source Dataweave LibraryHow to release an Open Source Dataweave Library
How to release an Open Source Dataweave Libraryshyamraj55
 
Outage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedIn
Outage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedInOutage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedIn
Outage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedInThousandEyes
 
Emil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptx
Emil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptxEmil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptx
Emil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptxNeo4j
 
SIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENT
SIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENTSIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENT
SIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENTxtailishbaloch
 
Keep Your Finger on the Pulse of Your Building's Performance with IES Live
Keep Your Finger on the Pulse of Your Building's Performance with IES LiveKeep Your Finger on the Pulse of Your Building's Performance with IES Live
Keep Your Finger on the Pulse of Your Building's Performance with IES LiveIES VE
 
Technical SEO for Improved Accessibility WTS FEST
Technical SEO for Improved Accessibility  WTS FESTTechnical SEO for Improved Accessibility  WTS FEST
Technical SEO for Improved Accessibility WTS FESTBillieHyde
 
Where developers are challenged, what developers want and where DevEx is going
Where developers are challenged, what developers want and where DevEx is goingWhere developers are challenged, what developers want and where DevEx is going
Where developers are challenged, what developers want and where DevEx is goingFrancesco Corti
 
UiPath Studio Web workshop Series - Day 3
UiPath Studio Web workshop Series - Day 3UiPath Studio Web workshop Series - Day 3
UiPath Studio Web workshop Series - Day 3DianaGray10
 
UiPath Studio Web workshop series - Day 4
UiPath Studio Web workshop series - Day 4UiPath Studio Web workshop series - Day 4
UiPath Studio Web workshop series - Day 4DianaGray10
 
Extra-120324-Visite-Entreprise-icare.pdf
Extra-120324-Visite-Entreprise-icare.pdfExtra-120324-Visite-Entreprise-icare.pdf
Extra-120324-Visite-Entreprise-icare.pdfInfopole1
 
Automation Ops Series: Session 2 - Governance for UiPath projects
Automation Ops Series: Session 2 - Governance for UiPath projectsAutomation Ops Series: Session 2 - Governance for UiPath projects
Automation Ops Series: Session 2 - Governance for UiPath projectsDianaGray10
 
The Importance of Indoor Air Quality (English)
The Importance of Indoor Air Quality (English)The Importance of Indoor Air Quality (English)
The Importance of Indoor Air Quality (English)IES VE
 
TrustArc Webinar - How to Live in a Post Third-Party Cookie World
TrustArc Webinar - How to Live in a Post Third-Party Cookie WorldTrustArc Webinar - How to Live in a Post Third-Party Cookie World
TrustArc Webinar - How to Live in a Post Third-Party Cookie WorldTrustArc
 
Key Trends Shaping the Future of Infrastructure.pdf
Key Trends Shaping the Future of Infrastructure.pdfKey Trends Shaping the Future of Infrastructure.pdf
Key Trends Shaping the Future of Infrastructure.pdfCheryl Hung
 
EMEA What is ThousandEyes? Webinar
EMEA What is ThousandEyes? WebinarEMEA What is ThousandEyes? Webinar
EMEA What is ThousandEyes? WebinarThousandEyes
 
Scenario Library et REX Discover industry- and role- based scenarios
Scenario Library et REX Discover industry- and role- based scenariosScenario Library et REX Discover industry- and role- based scenarios
Scenario Library et REX Discover industry- and role- based scenariosErol GIRAUDY
 
2024.03.12 Cost drivers of cultivated meat production.pdf
2024.03.12 Cost drivers of cultivated meat production.pdf2024.03.12 Cost drivers of cultivated meat production.pdf
2024.03.12 Cost drivers of cultivated meat production.pdfThe Good Food Institute
 
Graphene Quantum Dots-Based Composites for Biomedical Applications
Graphene Quantum Dots-Based Composites for  Biomedical ApplicationsGraphene Quantum Dots-Based Composites for  Biomedical Applications
Graphene Quantum Dots-Based Composites for Biomedical Applicationsnooralam814309
 

Último (20)

Oracle Database 23c Security New Features.pptx
Oracle Database 23c Security New Features.pptxOracle Database 23c Security New Features.pptx
Oracle Database 23c Security New Features.pptx
 
Flow Control | Block Size | ST Min | First Frame
Flow Control | Block Size | ST Min | First FrameFlow Control | Block Size | ST Min | First Frame
Flow Control | Block Size | ST Min | First Frame
 
How to release an Open Source Dataweave Library
How to release an Open Source Dataweave LibraryHow to release an Open Source Dataweave Library
How to release an Open Source Dataweave Library
 
Outage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedIn
Outage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedInOutage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedIn
Outage Analysis: March 5th/6th 2024 Meta, Comcast, and LinkedIn
 
Emil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptx
Emil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptxEmil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptx
Emil Eifrem at GraphSummit Copenhagen 2024 - The Art of the Possible.pptx
 
SIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENT
SIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENTSIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENT
SIM INFORMATION SYSTEM: REVOLUTIONIZING DATA MANAGEMENT
 
Keep Your Finger on the Pulse of Your Building's Performance with IES Live
Keep Your Finger on the Pulse of Your Building's Performance with IES LiveKeep Your Finger on the Pulse of Your Building's Performance with IES Live
Keep Your Finger on the Pulse of Your Building's Performance with IES Live
 
Technical SEO for Improved Accessibility WTS FEST
Technical SEO for Improved Accessibility  WTS FESTTechnical SEO for Improved Accessibility  WTS FEST
Technical SEO for Improved Accessibility WTS FEST
 
Where developers are challenged, what developers want and where DevEx is going
Where developers are challenged, what developers want and where DevEx is goingWhere developers are challenged, what developers want and where DevEx is going
Where developers are challenged, what developers want and where DevEx is going
 
UiPath Studio Web workshop Series - Day 3
UiPath Studio Web workshop Series - Day 3UiPath Studio Web workshop Series - Day 3
UiPath Studio Web workshop Series - Day 3
 
UiPath Studio Web workshop series - Day 4
UiPath Studio Web workshop series - Day 4UiPath Studio Web workshop series - Day 4
UiPath Studio Web workshop series - Day 4
 
Extra-120324-Visite-Entreprise-icare.pdf
Extra-120324-Visite-Entreprise-icare.pdfExtra-120324-Visite-Entreprise-icare.pdf
Extra-120324-Visite-Entreprise-icare.pdf
 
Automation Ops Series: Session 2 - Governance for UiPath projects
Automation Ops Series: Session 2 - Governance for UiPath projectsAutomation Ops Series: Session 2 - Governance for UiPath projects
Automation Ops Series: Session 2 - Governance for UiPath projects
 
The Importance of Indoor Air Quality (English)
The Importance of Indoor Air Quality (English)The Importance of Indoor Air Quality (English)
The Importance of Indoor Air Quality (English)
 
TrustArc Webinar - How to Live in a Post Third-Party Cookie World
TrustArc Webinar - How to Live in a Post Third-Party Cookie WorldTrustArc Webinar - How to Live in a Post Third-Party Cookie World
TrustArc Webinar - How to Live in a Post Third-Party Cookie World
 
Key Trends Shaping the Future of Infrastructure.pdf
Key Trends Shaping the Future of Infrastructure.pdfKey Trends Shaping the Future of Infrastructure.pdf
Key Trends Shaping the Future of Infrastructure.pdf
 
EMEA What is ThousandEyes? Webinar
EMEA What is ThousandEyes? WebinarEMEA What is ThousandEyes? Webinar
EMEA What is ThousandEyes? Webinar
 
Scenario Library et REX Discover industry- and role- based scenarios
Scenario Library et REX Discover industry- and role- based scenariosScenario Library et REX Discover industry- and role- based scenarios
Scenario Library et REX Discover industry- and role- based scenarios
 
2024.03.12 Cost drivers of cultivated meat production.pdf
2024.03.12 Cost drivers of cultivated meat production.pdf2024.03.12 Cost drivers of cultivated meat production.pdf
2024.03.12 Cost drivers of cultivated meat production.pdf
 
Graphene Quantum Dots-Based Composites for Biomedical Applications
Graphene Quantum Dots-Based Composites for  Biomedical ApplicationsGraphene Quantum Dots-Based Composites for  Biomedical Applications
Graphene Quantum Dots-Based Composites for Biomedical Applications
 

A Quick and Dirty D3.js Tutorial

  • 1. A Quick & Dirty D3.js Young-Ho Kim Human-Computer Interaction Lab Dept. of Computer Science & Engineering Seoul National University Course
  • 2. Course | Young-Ho Kim – A Quick and Dirty D3.js Overview In this course, we will go through… 1. A quick & dirty introduction of D3.js 2. Play with D3 on HTML document The material is based on my experience of learning by many people’s blogs, slides, tutorials, and books. It may have grammatical issues and technical issues about D3. If you find anything strange, please let me know. yhkim@hcil.snu.ac.kr About This Course 2
  • 3. Course | Young-Ho Kim – A Quick and Dirty D3.js Overview 1. Brief History of D3 2. Data Preparation 3. Basic Drawing 4. Advanced Chart Drawing 5. Interaction 6. Transitions 7. Other Features 8. Tips 9. Q&A Table of Contents 3
  • 4. Course | Young-Ho Kim – A Quick and Dirty D3.js Overview D3.js is a JavaScript library for manipulating documents based on data – d3js.org What is D3.js? 4 Data-Driven Documents
  • 5. Course | Young-Ho Kim – A Quick and Dirty D3.js Overview • D3 is a research project in Stanford Vis Group. • D3 was written and maintained by Micheal Bostock. • Proposed at InfoVis 2011. Micheal Bostock, Vadim Ogievetsky, and Jeffrey Heer. D3: Data-Driven Documents. • descendant of ProtoVis (2009) chart drawing library. 5 What is D3.js?
  • 6. Course | Young-Ho Kim – A Quick and Dirty D3.js Why D3.js? People are getting more familiar with charts and visualization. Data Journalism, Big Data, Infographics… 6 Today’s Visualization is Dynamic Daily MaverickInteractive visualizations of NY Times
  • 7. Course | Young-Ho Kim – A Quick and Dirty D3.js Why D3.js? Digital media enables high interactivity Information visualization is no more a static chart printed on paper. 7 Today’s Visualization is Dynamic Radik Sadana et al. TouchVis Tipco Spotfire
  • 8. Course | Young-Ho Kim – A Quick and Dirty D3.js Why D3.js? Web is the most accessible, and actively-used platform for interactive visualization. Don’t need to install stand-alone applications, One-sided modification(bug fix, upgrade, …) is available. 8 Today’s Visualization is Dynamic
  • 9. Course | Young-Ho Kim – A Quick and Dirty D3.js What is D3.js? • D3 helps you draw visual elements based on the arrays of the data. • You can dynamically modify DOM element of an HTML do cument without explicitly looping among the data points. 9 Simple description on D3
  • 10. Course | Young-Ho Kim – A Quick and Dirty D3.js Tutorial Using D3 demands basic knowledges of... • JavaScript : D3 is a JavaScript library. • HTML : D3 substitutes DOM elements for drawing. • CSS : D3 visualizations can be stylized using CSS. • jQuery : D3 resembles jQuery much. But a little different in terms of its syntax. You will have to use jQuery together for more complicate d interactive visualization. 10 Prerequisites
  • 11. Course | Young-Ho Kim – A Quick and Dirty D3.js Tutorial Lets use D3.js! Tutorial 1. Prepare to use D3 11
  • 12. Course | Young-Ho Kim – A Quick and Dirty D3.js Tutorial • A Web browser and a text editor • We will use FireFox or Safari in this tutorial for some reasons. • You may use any text editor familiar with you. • Developer tools on a browser are very helpful for JavaScript programing. 12 Tutorial 1. Prepare to use D3 (Cont.)
  • 13. Course | Young-Ho Kim – A Quick and Dirty D3.js Tutorial http://hcil.snu.ac.kr/~muclipse/d3_course_tutorial_yhkim.zip Download the tutorial files. Start tutorial from starthere.html file. The tutorial is incremental and sequential. If you didn’t catch the tutorial, skip it by using the answer files and use it as a start point from the next tutorial. 13 Tutorial 1. Prepare to use D3 (Cont.)
  • 15. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation • Building data table to be used in your visualization is almost a half of the visualization process. • A scheme of the data is crucial for the conciseness of your c ode and the difficulty of your entire development. • Deriving a table from a chart is much more difficult than dra wing a chart from a table. 15 Using Data Table on Interactive Visualization
  • 16. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation Imagine you want to draw a bar chart like this. 16 Using Data Table on Interactive Visualization Sally Tom John 5 10 7.5
  • 17. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation It’s not hard to derive this table from the chart. 17 Using Data Table on Interactive Visualization Sally Tom John 5 10 7.5 Sally 5 Tom 10 John 7.5
  • 18. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation D3 is a JavaScript so the table must be the form of JSON… 18 Using Data Table on Interactive Visualization Sally 5 Tom 10 John 7.5 { “Sally”:5, “Tom”:10, “John”:7.5 } [{“Sally”:5}, {“Tom”:10}, {“John”:7.5}] or
  • 19. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation You will have a very hard time with these data structures. 19 Using Data Table on Interactive Visualization Sally 5 Tom 10 John 7.5 { “Sally”:5, “Tom”:10, “John”:7.5 } [{“Sally”:5}, {“Tom”:10}, {“John”:7.5}] or
  • 20. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation Every data table needs ‘schema’ – column names. In other words, make your data structure to be “loopable”. 20 Using Data Table on Interactive Visualization Name Value Sally 5 Tom 10 John 7.5 [{“Name”:“Sally”, “Value”:5}, {“Name”:“Tom”, “Value”:10}, {“Name”:“John”, “Value”:7.5}] A key must be a schema(column), not a value.
  • 21. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation • D3 provide functions to load data from an URL. d3.csv(URL, callback) d3.json(URL, callback) • Tsv, text, xml, html are also supported. • I recommend using JSON because it is versatile. • Data is loaded asynchronously. So we should wait until t he loading is finished : Do everything in a callback. 21 Loading Data in D3 d3.json(URL, function(error, json){ if(json!=null){ //Do Something } });
  • 22. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation Add this code inside your <script> block. 22 Tutorial 2. Loading Data Table d3.json(“data.json”, function(error, json){ if(json!=null){ console.log(json); } });
  • 23. Course | Young-Ho Kim – A Quick and Dirty D3.js Data Preparation Add this code inside your <script> block. 23 Tutorial 2. Loading Data Table (Cont.) d3.json(“data.json”, function(error, json){ if(json!=null){ console.log(json); } }); This callback is invoked when the loading finishes. The second parameter contains loaded JSON object if loaded without an error.
  • 25. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing D3 is similar to jQuery. Selectors, Styles, Attributes, Text… but its syntax is slightly different. D3 visualizes by substituting DOM elements. Appending new elements, removing elements, modifying styles and a ttributes of elements… 25 Drawing Mechanism of D3 codefactor.com
  • 26. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Both jQuery and D3 starts with selection 26 D3 vs jQuery Basics d3.select(“body”) $(“body”) Appending new DOM element d3.select(“body”).append(“p”) $(“body”).append(“<p></p>”) D3 function is cascaded to descendant. d3.select(“body”).append(“p”).text(“test”) Returns <p> child element selection.
  • 27. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • Let’s draw an HTML table dynamically. • Write this code somewhere in your <script> block. 27 Tutorial 3. Drawing Table Dynamically var table = d3.select(“body”).append(“table”); var row1 = table.append(“tr”); row1.append(“td”).text(“Sally”); row1.append(“td”).text(“5”); var row2 = table.append(“tr”); row2.append(“td”).text(“Tom”); row2.append(“td”).text(“10”);
  • 28. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing 28 Tutorial 3. Drawing Table Dynamically var table = d3.select(“body”).append(“table”); var row1 = table.append(“tr”); row1.append(“td”).text(“Sally”); row1.append(“td”).text(“5”); var row2 = table.append(“tr”); row2.append(“td”).text(“Tom”); row2.append(“td”).text(“10”); Save selection to variable if more than one child will be appended.
  • 29. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing To draw elements in a data-driven way, you should understa nd a concept of Selections, Binding and Joins in D3. Data-driven Drawing 1. Select elements to be connected to data (Selection) 2. Bind data to the selection (Binding) 3. Add, Modify, or Remove elements based on data (Join) 29 Going Data-Driven Way
  • 30. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Elements are first ‘selected’ even if they don’t exist yet. • d3.selectAll(selector) : returns all elements with selector • d3.select(selector) : returns the first element with selector • D3 uses CSS3 selectors. • If no one matches the selector, they return an empty selection. 30 Selecting Elements
  • 31. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Now the data is connected to the selection. selection.data(array, key=null) This function pairs selected elements with an array of data values. → What if the number of data values are different from the s elected elements? → That’s what Join does. 31 Binding Data
  • 32. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Join handles 3 cases of the overlaps of Data and Nodes(selection). Enter: A set of newly added data. Not matched with current selection. Update: A set of already matched pairs of a data point and an element. Exit: A set of selected nodes the data of which do not exist anymore. 32 Joins Forget about Update and Exit for now.
  • 33. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing D3 join functions returns selections with corresponding joi n set. • selection.data().enter() : returns the empty selection of el ements that should be newly added. • selection.data() : default data function returns an update se lection. • selection.data().exit() : returns selection of the elements that should be removed. 33 Joins (Cont.)
  • 34. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Let’s draw a bar chart in a data-driven way. Add this code inside your callback. 34 Tutorial 4. Div Bar Chart d3.json(“URL”, function(error, json){ if(json!=null){ //Write code here } });
  • 35. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing 35 Tutorial 4. Div Bar Chart (Cont.) d3.json(“URL”, function(error, json){ if(json!=null){ d3.select(“body”) .selectAll(“div”) .data(json) .enter() .append(“div”); } }
  • 36. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing 36 Tutorial 4. Div Bar Chart (Cont.) d3.json(“URL”, function(error, json){ if(json!=null){ d3.select(“body”) .selectAll(“div”) .data(json) .enter() .append(“div”); } } ←Use <div> for a bar. ←Bind data. ←Get enter selection ← Functions are applied to each selected element without using loops.
  • 37. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • You will see nothing because <div> is transparent in defa ult. • D3 provides functions to modify attributes and styles of DOM elements. • Attributes provide additional information about HTML elements i nside the tag. <div class=“contents”> • Styles provide style information about selections in CSS, or abo ut an element in “style” attribute. 37 Styles and Attributes
  • 38. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing selection.attr(“attribute”, “value”) selection.attr(“attribute”, function(datum, index){return value}) Changes attribute of each selected element. If value is functio n, you can dynamically assign attribute on each element. 38 Styles and Attributes (Cont.) selection.style(“style”, “value”) selection.style(“style”, function(datum, index){return value}) Changes style. The style is applied to “style” attribute of each selected element, not globally in CSS.
  • 39. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Append some style functions to the selection to make our chart visible. 39 Tutorial 5. Div Bar Chart Styling d3.select(“body”) .selectAll(“div”) .data(json) .enter() .append(“div”) .style(“width”, function(d){return d.value * 5 + “px”;}) .style(“background”, “red”) .text(function(d){return d.value});
  • 40. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • Using div has many limitations on chart drawing. • SVG is more suitable for visualization. • SVG(Scalable Vector Graphics) is a vector image defined by X ML-based markups inside webpage. http://www.w3schools.com/svg/ • SVG graphic element is considered the same as other DOM ele ments in the HTML document. • Every geometric attributes are designated on attributes in tag, s ome attributes are also available in style. 40 Introduction to SVG
  • 41. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • SVG shares many styling properties with CSS. • Some distinction that may confusing: 41 SVG Styles vs CSS Styles CSS Style SVG Style(Attribute) size font-size color font-color background fill border-style stroke border-width stroke-width
  • 42. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • SVG drawing is different from classic HTML document. • SVG elements are not cascaded in layout. • They are defined under Cartesian coordinates inside the canvas of SVG image. 42 Preparing SVG Drawing <html><body> <svg width=“150” height=“150”> <rect x=“10” y=“20” width=“60” height=“30” fill=red/> </svg> </body></html>
  • 43. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • <svg> tag with “width” and “height” attributes must be defined as the outmost markup. • Topleft corner is (0,0). 43 Preparing SVG Drawing (Cont.) <svg width=“150” height=“150”> </svg> (0,0) (150,150)
  • 44. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing rect (x,y,width,height) circle (cx, cy, r) ellipse (cx, cy, rx, ry) line (x1, y1, x2, y2) path (d) polygon (points) 44 Basic SVG Elements (geometric attributes)
  • 45. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • <text> draws text on the svg image. Similar to simple HTML text but provides more powerful styling and can be drawn anywhere. • <g> (group) groups its child elements and the position of group acts as an origin of its children. Group is really important in complicated visualization. You can reduce the amount of code by clever use of groups. 45 Other important SVG Elements
  • 46. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • Change your HTML bar chart to SVG. 46 Tutorial 6. Migration to SVG d3.select(“body”) .append(“svg”) .attr({width:500, height:500}) .selectAll(“rect”) .data(json) .enter() .append(“rect”) .attr(“width”, function(d){return d.value * 5}) .attr(“height”, 500/json.length - 2) .attr(“y”, function(d,i){return i * 500/json.length});
  • 47. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing • Change your HTML bar chart to SVG. 47 Tutorial 6. Migration to SVG (Cont.) d3.select(“body”) .append(“svg”) .attr({width:500, height:500}) .selectAll(“rect”) .data(json) .enter() .append(“rect”) .attr(“width”, function(d){return d.value * 5}) .attr(“height”, 500/json.length - 2) .attr(“y”, function(d,i){return i * 500/json.length}); ←You can assign multiple attributes or styles at once. ↑ Unlike HTML, SVG elements are not cascaded so you should explicitly assign y position.
  • 48. Course | Young-Ho Kim – A Quick and Dirty D3.js Basic Drawing Your code should look like this. 48 Tutorial 6. Migration to SVG (Cont.)
  • 50. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing Now we can draw bars based on data. But we still need more things to make a complete chart. 50 Still Not enough to be a Complete Chart… ←The bar with maximum value do not exceed the canvas. ↑ Ordinary charts contains axes.
  • 51. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Scale is a function that maps data value to the extent of real image coordinate under specific formula: • Quantitative scales including linear, log, power,… • Ordinal scales provide discrete positions for ordinal values. • Time scales provide linear mappings for time points on timeline. • When you draw data elements on SVG plane, it is convenient to set their positions with scales rather than calculating them by yourself. 51 Scales
  • 52. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • d3.scale provide most of scale functions. d3.scale.linear(), d3.scale.ordinal(), d3.scale.log() … • Properties are cascaded to the end of these functions. • Linear Scale Properties: • domain([start, end]) : define the extent of data values. • range([start, end]) : define the extent of output coordinates. • Ordinal Scale Properties: • domain([values]) : specify all the values. • rangeBands([start, end]) : define the extent of output coordinates. 52 Scales (Cont.)
  • 53. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing Usage example: var x = d3.scale.linear().domain([2,5]).range([0,10]); Now you can calculate mapped coordinate by simply calling x(dataValue). Ordinal/nominal scales are similar: var x = d3.scale.ordinal().domain([“A”, “B”, “C”]) .rangeBands([0, 10]); Now you can calculate mapped coordinate by simply calling x(“A”), x(“B”), or x(“C”). 53 Scales (Cont.)
  • 54. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Define scale function on the top of callback, and replace the width calculation code. 54 Tutorial 7. Employing scales d3.json(“URL”, function(error, json){ if(json!=null){ var x = d3.scale.linear().domain([0, 100]).range([0, 500]); d3.select(“body”) … .attr(“width”, function(d){return x(d.value)}) .attr(“height”, 500/json.length - 2) .attr(“y”, function(d,i){return i * 500/json.length});
  • 55. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Define scale function on the top of callback, and replace the width calculation code. 55 Tutorial 7. Employing scales d3.json(“URL”, function(error, json){ if(json!=null){ var x = d3.scale.linear().domain([0, 100]).range([0, 500]); d3.select(“body”) … .attr(“width”, function(d){return x(d.value)}) .attr(“height”, 500/json.length - 2) .attr(“y”, function(d,i){return i * 500/json.length}); Horizontal range of the SVG plane
  • 56. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • D3 provide axis as a function that draws axis based on scale. • Axis component is attached to chart area in 4 directions: 56 Adding Axis 0 20 40 60 80 100 120 140 0 20 40 60 80 100 120 140 0 20 40 60 80 100 120 140 0 20 40 60 80 100 120 140 Top Bottom Left RightRed dots are pivot position of the axis
  • 57. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing d3.svg.axis() Returns a function to add axis component to a selection. • axis.scale(scale) : assigns a scale for the axis. • axis.orient(orientation) : assigns an orientation for the axis. ( “left”, “top”, “right”, “bottom”) 57 Axis Component API
  • 58. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • To add axis component in SVG, we need to prepare space. 58 Grouping Chart Regions SVG Chart(coordinate space) Left A xis Bottom Axis
  • 59. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing In convention, chart elements are drawn in a group. 59 Grouping Chart Regions var padding = {left:50, top:10, right:10, bottom:50}; var chart = d3.select(“body”) .append(“svg”).attr({width:500, height:500}) .append(“g”) .attr(“transform”, “translate(” + padding.left + “,” + padding.top + “)”); Paddings are used to allocate space for axes. “Transform” attribute is used to translate group.
  • 60. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • We will add a left and a bottom axes. • First, add paddings on the top of callback.. 60 Tutorial 8. Employing Axis d3.json(“URL”, function(error, json){ if(json!=null){ var padding = {left:50, top:10, right:10, bottom:50}; var chartWidth = 500 – padding.left – padding.right; var chartHeight = 500 – padding.top – padding.bottom; • chartWidth and chartHeight will be used in scales.
  • 61. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing Define x-axis function. 61 Tutorial 8. Employing Axis (Cont.) var x = d3.scale.linear().domain([0, 100]).range([0, chartWidth]); var xAxis = d3.svg.axis().orient(“bottom”).scale(x); //This time we will use scale in y values, too. var names = json.map(function(d){return d.name}); var y = d3.scale.ordinal().domain(names) .rangeBands([0, chartHeight]); var yAxis = d3.svg.axis().orient(“left”).scale(y);
  • 62. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Define chart area. 62 Tutorial 8. Employing Axis (Cont.) var chart = d3.select(“body”) .append(“svg”).attr({width:500, height:500}) .append(“g”) .attr(“transform”, “translate(” + padding.left + “,” + padding.top + “)”);
  • 63. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Draw axis. 63 Tutorial 8. Employing Axis (Cont.) chart.append(“g”).attr(“class”, “x axis”) .attr(“transform”, “translate(0,” + chartHeight + “)”) .call(xAxis); chart.append(“g”).attr(“class”, “y axis”) .call(yAxis);
  • 64. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Draw bars. 64 Tutorial 8. Employing Axis (Cont.) chart.selectAll(“rect”) .data(json) .enter() .append(“rect”) .attr(“width”, function(d){return x(d.value)}) .attr(“height”, chartHeight/json.length - 2) .attr(“y”, function(d){return y(d.name)});
  • 65. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Now you have axes. 65 Tutorial 8. Employing Axis (Cont.)
  • 66. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Your axis would look ugly. Let’s do some CSS. 66 Styling Chart 0 20 40 60 80 <path class=“domain” … > <g class=“tick” … > A tick and a value text are grouped. <line … > <text … >
  • 67. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • The lines of the axis are <line> and <path> tags. We can style these in CSS or just in code. 67 Axis Stylesheets .axis path, .axis line{ fill:none; stroke-width:1px; stroke:black; }
  • 68. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • The tick labels are <text> tags. 68 Axis Stylesheets .axis text{ font-size:10px; font-weight:bold; }
  • 69. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Add <style> block. 69 Tutorial 9. Styling Axis <head> <style> .axis path, .axis line{ fill:none; stroke-width:1px; stroke: black; } .axis text{ font-size:10px; font-weight:bold; } </style> …
  • 70. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • We may want our chart to look more elaborated. • e.g. Redundant encoding • We will use <group> for mappings. 70 Toward More Complicated Data Elements 50 75 120 100 80
  • 71. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing For now, we paired each data value to one SVG element. 71 Grouping Elements per Data Point A 50 B 75 C 120 D 100 E 80 SVG Rect chart.selectAll(“rect”) .data(json) .enter() .append(“rect”)
  • 72. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Now a data value is paired to a set of a rect and a text. 72 Grouping Elements per Data Point A 50 B 75 C 120 D 100 E 80 50 75 120 100 80 SVG Rect SVG Text
  • 73. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • We will add values to our bars. • Modify our bar drawing code. 73 Tutorial 10. Redundant Encoding var bars = chart.selectAll(“g.bar”) .data(json) .enter() .append(“g”) .attr(“class”, “bar”) .attr(“transform”, function(d){return “translate(0,” + y(d.name) + “)”); • Topmost data mapping is replaced by “g”. • We defined y-position of bars on groups in advance.
  • 74. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Each group has one rect and one text. 74 Tutorial 10. Redundant Encoding var barHeight = chartHeight/json.length – 2; bars.append(“rect”) .attr(“width”, function(d){return x(d.value)}) .attr(“height”, barHeight); bars.append(“text”) .attr(“fill”, “white”) .attr(“x”, function(d){return x(d.value) – 5}) .attr(“y”, barHeight/2) .attr(“dominant-baseline”, “middle”) .attr(“text-anchor”, “end”) .text(function(d){return d.value}); 86
  • 75. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing • Each group has one rect and one text. 75 Tutorial 10. Redundant Encoding var barHeight = chartHeight/json.length – 2; bars.append(“rect”) .attr(“width”, function(d){return x(d.value)}) .attr(“height”, barHeight); bars.append(“text”) .attr(“fill”, “white”) .attr(“x”, function(d){return x(d.value) – 5}) .attr(“y”, barHeight/2) .attr(“dominant-baseline”, “middle”) .attr(“text-anchor”, “end”) .text(function(d){return d.value}); Right alignment, center in vertical position ←set content of the block. 86
  • 76. Course | Young-Ho Kim – A Quick and Dirty D3.js Advanced Chart Drawing Now the values are encoded to the length and the text. 76 Tutorial 10. Redundant Encoding
  • 78. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • D3 handles JavaScript event model to make the elements responsive. • D3 event works by adding event listeners to d3 selection. 78 Leveraging Advantages of Web
  • 79. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • type: type of event to response (e.g. “mouseover”, “mouseleave”, “click”, “mousedown”, “mouseup”) • function(d,i): event handler. d: a single corresponding data point (datum) i: the index of the data point • on() function returns selection itself, enabling cascading. 79 D3 Event API selection.on(type, function(d,i){})
  • 80. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • The parameters of handler function gives information about data. It is useful for printing interacted data. • ‘this’ in the scope of handler function indicates the DOM element itself. So you can get a selection of responded element by d3.select(this) 80 Event Handling selection.on(type, function(d,i){ //d, i : data-level handling //d3.select(this) : visualization-level handling });
  • 81. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Let’s make our bar chart more interactive. We will highlight the bar which the mouse is hovering on. 81 Tutorial 11. Details-On-Demand
  • 82. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions Append event functions to rect selections. 82 Tutorial 11. Details-On-Demand (Cont.) bars.append(“rect”) .attr(“width”, function(d){return x(d.value)}) .attr(“height”, barHeight) .on(“mouseover”, function(d,i){ d3.select(this).attr(“fill”, “orange”); }) .on(“mouseleave”, function(d,i){ d3.select(this).attr(“fill”, null); });
  • 83. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions Append event functions to <rect> selections. 83 Tutorial 11. Details-On-Demand (Cont.) bars.append(“rect”) .attr(“width”, function(d){return x(d.value)}) .attr(“height”, barHeight) .on(“mouseover”, function(d,i){ d3.select(this).attr(“fill”, “orange”); }) .on(“mouseleave”, function(d,i){ d3.select(this).attr(“fill”, null); }); We didn’t use data information here. ←Change color when mouse entered ←Reset color when mouse leaved
  • 84. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Now your rects are reactive to your mouse cursor. • Let’s do some more. What about showing the value labels only when mouse is hover? • The bar unit is a group of a <rect> and a <text>. To control both children, it is natural to attach event listener to each group, not the rect. 84 Tutorial 12. Details-On-Demand Advanced
  • 85. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Change the text labels transparent. We will show the label only while the mouse is hovering on corresponding bar. 85 Tutorial 12. Details-On-Demand Advanced (Cont.) bars.append(“text”) .attr(“fill”, “white”) .attr(“x”, function(d){return x(d) – 5}) .attr(“y”, barHeight/2) .attr(“dominant-baseline”, “middle”) .attr(“text-anchor”, “end”) .attr(“display”, “none”) .text(function(d){return d.value});
  • 86. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Remove event listener code from rect selections. 86 Tutorial 12. Details-On-Demand Advanced (Cont.) bars.append(“rect”) .attr(“width”, function(d){return x(d.value)}) .attr(“height”, barHeight); .on(“mouseover”, function(d,i){ d3.select(this).attr(“fill”, “orange”); }) .on(“mouseleave”, function(d,i){ d3.select(this).attr(“fill”, null); });
  • 87. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Substitute the group selection code. 87 Tutorial 12. Details-On-Demand Advanced (Cont.) var bars = chart.selectAll(“g”) … .on(“mouseover”, function(d,i){ d3.select(this).select(“rect”).attr(“fill”, “orange”); d3.select(this).select(“text”).attr(“display”, null); }) .on(“mouseleave”, function(d,i){ d3.select(this).select(“rect”).attr(“fill”, null); d3.select(this).select(“text”).attr(“display”, “none”); });
  • 88. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Substitute the group selection code. 88 Tutorial 12. Details-On-Demand Advanced (Cont.) var bars = chart.selectAll(“g”) … .on(“mouseover”, function(d,i){ d3.select(this).select(“rect”).attr(“fill”, “orange”); d3.select(this).select(“text”).attr(“display”, null); }) .on(“mouseleave”, function(d,i){ d3.select(this).select(“rect”).attr(“fill”, null); d3.select(this).select(“text”).attr(“display”, “none”); }); <group> Null assigns ‘default value’
  • 89. Course | Young-Ho Kim – A Quick and Dirty D3.js Interactions • Now the ticks shows only when hovering. 89 Tutorial 12. Details-On-Demand Advanced (Cont.)
  • 91. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Technically, transitions are smoothly changing the visuals by interpolating geometric properties. 91 Benefits of Incorporating Transitions Jeffrey Heer, George Robertson. 2007. Animated Transitions in Statistical Data Graphics
  • 92. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Interpolating the elements can orient user to keep perception of change – Useful for refreshing chart. • Aesthetically pleasing. 92 Benefits of Incorporating Transitions (Cont.)
  • 93. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • In D3, a transition is a special type of selection. • Attributes and style assignment applies over time. 93 Transitions in D3 selection.transition() • Transition object has 3 main properties: • transition.duration(millis) : specifies per-element duration in milliseconds. The parameter can be a function(d,i). • transition.delay(millis) : the transition starts after the delay. The parameter can be a function(d,i).
  • 94. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions 94 Transitions in D3 (Cont.) transition.ease(“method”) Specifies the transition easing function. The parameter can be a function(t), or a predefined string constant. D3.js Easing Checker
  • 95. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Let’s make your bars appear smoothly. • Animate the bar width from 0 to target width. • First, set the initial width of rect as Zero. 95 Tutorial 13. Smooth Emerging bars.append(“rect”) .attr(“width”, 0) .attr(“height”, barHeight)
  • 96. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Then derive a transition from the selection. • Assign duration and the target attributes. • Easing is optional. Try other easing functions, too. 96 Tutorial 13. Smooth Emerging (Cont.) bars.append(“rect”) .attr(“width”, 0) .attr(“height”, barHeight) .transition() .duration(750) .ease(“cubic-out”) .attr(“width”, function(d){return x(d.value)});
  • 97. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • We learned that the delay function allows a function as a paremeter. Let’s make our bars emerge sequentially. 97 Tutorial 13. Smooth Emerging (Cont.) bars.append(“rect”) .attr(“width”, 0) .attr(“height”, barHeight) .transition() .duration(750) .delay(function(d,i){ return i * 100 }) .ease(“cubic-out”) .attr(“width”, function(d){return x(d.value)});
  • 98. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Transitions can be used in event handlers. 98 Tutorial 13. Smooth Emerging (Cont.) on("mouseover", function(d,i){ d3.select(this).select("rect") .transition().duration(300).ease("cubic-out") .attr("fill", "orange"); d3.select(this).select("text").attr("display", null); }) .on("mouseleave", function(d,i){ d3.select(this).select("rect") .transition().duration(200).attr("fill", null);
  • 99. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Transition is powerful for interpolating between the two states of visualization. • D3’s AJAX data loading enables refreshing chart by applying different data to the same chart. • By combination of transition and joins, we can easily refresh our visualization. 99 Transition between Data
  • 100. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Transition between data is one of the major power of D3. • In this final tutorial, we will make our visualization switch between different dataset, SMOOTHLY. 100 Tutorial 14. Transition between Data
  • 101. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • We will change the dataset. • data2.json • Containing two tables in an array. • Names in the second table is a subset of the first one, but the values are different. 101 Tutorial 14. Transition between Data (Cont.)
  • 102. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • First, we need a button to shuffle. • Add <button> element inside the body. • Assign onClick event handler. • We will define shuffle() later. 102 Tutorial 14. Transition between Data (Cont.) <body> <button onClick="shuffle()">Shuffle</button> …
  • 103. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Pull out the declaration of variables that should be consistent during runtime. • Variables declared inside the d3.json() callback cannot be accessed outside. 103 Tutorial 14. Transition between Data (Cont.) <script> var padding = {left:80, top:0, right:30, bottom:50}; var chartWidth = 500 - padding.left - padding.right; var chartHeight = 500 - padding.top - padding.bottom; …
  • 104. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions • Scales and axis functions are also reused during runtime. • Y axis ticks should be changed so we don’t assign domain() here. 104 Tutorial 14. Transition between Data (Cont.) … var chartHeight = 500 - padding.top - padding.bottom; var x = d3.scale.linear().domain([0, 100]).range([0, chartWidth]); var xAxis = d3.svg.axis().orient("bottom").scale(x); var y = d3.scale.ordinal().rangeBands([0, chartHeight]); var yAxis = d3.svg.axis().orient("left").scale(y);
  • 105. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Pull out the chart canvas too. The SVG must be appended only once. 105 Tutorial 14. Transition between Data (Cont.) … var yAxis = d3.svg.axis().orient("left").scale(y); var chart = d3.select("body") .append("svg").attr({width:500, height:500}) .append("g") .attr("transform", "translate(" + padding.left + ",“ + padding.top + ")");
  • 106. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions We also need the axis groups be appended only once. 106 Tutorial 14. Transition between Data (Cont.) var chart = … chart.append("g").attr("class", "x axis") .attr("transform", "translate(0," + chartHeight + ")") .call(xAxis); chart.append("g").attr("class", "y axis") .call(yAxis);
  • 107. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions All we need to do when the data loading is finished is to send the reference of loaded data to global scope. Do not forget to change the file name to “data2.json”. 107 Tutorial 14. Transition between Data (Cont.) var data; d3.json("data2.json", function(error, json){ if(json!=null){ data = json; } });
  • 108. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Next, we need to make routines to build final chart based on the data. In the routine, focus on what elements would change according to the data. First, the Y-axis should be refreshed. 108 Tutorial 14. Transition between Data (Cont.) function refresh(data){ y.domain(data.map(function(d){return d.name})); chart.select(".y.axis") .transition().duration(500).call(yAxis);
  • 109. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions This is the point. Remember the three joins in selection? Memorize the order ‘Enter-Update-Exit’. Handling joins is one of the most challenging part in D3. Let’s start from initializing update selection by data() function. 109 Tutorial 14. Transition between Data (Cont.) var bars = chart.selectAll("g.bar") .data(data);
  • 110. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Handling Enter selection – You initialize the new things. The code is almost the same as before. 110 Tutorial 14. Transition between Data (Cont.) var new_bars = bars.enter() .append("g") .attr("class", "bar") … new_bars.append("rect") … new_bars.append("text") …
  • 111. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Handling Update selection – Think about what properties should be modified(or updated). First, the height of bars could be changed because it is derived by the number of data rows. The Y position of bars could be changed, too. 111 Tutorial 14. Transition between Data (Cont.) var barHeight = chartHeight/data.length - 2; bars.transition().duration(500) .attr("transform", function(d){return "translate(0," +y(d.name)+")"});
  • 112. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions A <rect> and a <text> elements in each group need to be updated. 112 Tutorial 14. Transition between Data (Cont.) bars.select("rect") .transition().duration(500) .delay(function(d,i){return i*100}) .attr("width", function(d){return x(d.value)}) .attr("height", barHeight); bars.select("text") .transition().duration(500) .delay(function(d,i){return i*100}) .attr("x", function(d){return x(d.value) - 5}) .attr("y", barHeight/2) .text(function(d){return d.value});
  • 113. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Handling Exit selection – Remove the elements properly. You don’t need to care about rects and texts, because they will be removed with their parent group. The remove() function will remove the bars after the transition finishes. 113 Tutorial 14. Transition between Data (Cont.) bars.exit() .transition().duration(250) .style("opacity",0) .remove(); }//end of refresh(data)
  • 114. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Finally, prepare shuffle() function on the outmost scope. 114 Tutorial 14. Transition between Data (Cont.) … }//end of refresh(data) var currentIndex = 0; function shuffle() { currentIndex = (++currentIndex)%2; refresh(data[currentIndex]); }
  • 115. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions Good job. Your chart will be refreshed smoothly. 115 Tutorial 14. Transition between Data (Cont.)
  • 116. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions One more important thing. This is the true difference of the two tables. 116 Tutorial 14. Transition between Data (Cont.)
  • 117. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions But your visualization pairs the rows like this. 117 Tutorial 14. Transition between Data (Cont.)
  • 118. Course | Young-Ho Kim – A Quick and Dirty D3.js Transitions This mapping causes the transition not to be meaningful, because the transition doesn’t show the implicit change of the data. But don’t worry. D3 solves this mapping problem easily. Specify the second parameter of the data() function. 118 Tutorial 14. Transition between Data (Cont.) var bars = chart.selectAll("g.bar") .data(data, function(d){return d.name});
  • 119. Course | Young-Ho Kim – A Quick and Dirty D3.js When D3 matches the old data and the new data in the element, it compares the keys derived from the parameter function. In this case, D3 will consider the two data points with the same name field to be paired. Transitions 119 Tutorial 14. Transition between Data (Cont.) var bars = chart.selectAll("g.bar") .data(data, function(d){return d.name});
  • 120. Other Features of D3 Which we didn’t cover today
  • 121. Course | Young-Ho Kim – A Quick and Dirty D3.js Other Features of D3 D3 provide brushing components with predefined interaction. https://github.com/mbostock/d3/wiki/SVG-Controls http://bl.ocks.org/mbostock/1667367 http://bl.ocks.org/mbostock/4063663 121 Brushing
  • 122. Course | Young-Ho Kim – A Quick and Dirty D3.js Other Features of D3 Requires D3-tip library https://github.com/caged/d3-tip http://bl.ocks.org/Caged/6476579 122 Tooltips
  • 123. Course | Young-Ho Kim – A Quick and Dirty D3.js Other Features of D3 • Using tickFormat() function on scales, You can specify the format of the tick labels. • http://bl.ocks.org/mbostock/9764126 123 Formatting Axis Ticks
  • 124. Tips
  • 125. Course | Young-Ho Kim – A Quick and Dirty D3.js Tips • JavaScript is a powerful language, but using D3, you will see your code gets too long. • CoffeeScript is a little language that compiles into pure JavaScript in one-to-one mappings. http://coffeescript.org/ • Using it instead of pure JavaScript will significantly reduce the amount of your code. 125 Learn Simplified JavaScript Descendants .attr(“width”, function(d){return x(d.value)}) .attr “width”, (d)->x(d.value)
  • 126. Course | Young-Ho Kim – A Quick and Dirty D3.js Tips • There are plenty of tutorials and questions by Bostock and other gurus on web. • Most of the barriers you met are already dealt with before in stackoverflow.com. 126 Learn by Plenty of Tutorials and Questions bl.ocks.org stackoverflow
  • 127. Course | Young-Ho Kim – A Quick and Dirty D3.js Tips • Although JavaScript and D3 make it look interactive, SVG is merely a static vector image defined by markups. • Svg code can be saved in a *.svg file and modified in Adobe Illustrator. • Good for building figures of chart which is not supported by canonical tools such as R or Excel. 127 D3 Chart Can Be Used Elsewhere.
  • 128. Course | Young-Ho Kim – A Quick and Dirty D3.js Tips • D3’s asynchronous data loading is good for visualizing dynamic data. • If you are using D3 on your website with database, you can attach D3 visualization with data pulled from your database. 128 Learn ways to Dynamically Generating Web Server Database Client Server URL from d3.json parameter Generate JSON from Database Visualize Server-side Data
  • 129. Course | Young-Ho Kim – A Quick and Dirty D3.js Tips • Server Frameworks based on interpreter languages are convenient for data preparation. Most of them are designed to easily handle data structure. Ruby On Rails (Ruby), Django(Python), … • Also, most of them are incorporating database. 129 Learn ways to Dynamically Generating (Cont.)
  • 130. Course | Young-Ho Kim – A Quick and Dirty D3.js Tips • Building a complete visualization with pure D3 from scratch is a real pain. • If you are not designing your original visualization, try using other projects wrapping D3 or substituting D3. C3.js, Dimple, MetricsGraphics, …. 130 Do not Keep Your Eyes only on D3

Notas do Editor

  1. 본 강의에서, 여러분은 D3.js를 빠르게 훑게 될 겁니다. 그리고, HTML 도큐먼트 상에서 D3로 차트를 만들어보는 튜토리얼을 경험하게 될 겁니다. 본 강의는 D3에 대한 개념 설명과 튜토리얼이 번갈아 등장하도록 구성되어 있고, 모든 튜토리얼은 같은 코드를 계속해서 발전시켜 나가는 식으로 이루어져 있습니다. 이 강의 한 번으로 저는 여러분을 D3의 마스터로 만들어 드릴 수는 없습니다. 다만, 이 강의를 통해 여러분은 D3로 시각화를 만드는 아주 기초적인 프로세스를 경험하게 될 것이고, 차후에 계속해서 D3를 사용하시게 될 때, 추가적인 것들을 더 배우고자 할 때 어떤 정보들을 이용하면 될지 감을 잡게 될 것입니다.
  2. 본 강의는 다음과 같은 순서로 진행됩니다. 먼저, D3가 어떤 라이브러리인지 간단한 역사를 소개해 드릴 거구요. 그 다음엔 D3에서 사용하기 위한 데이터를 준비하는 과정에 대해 안내할 것입니다. 그 다음으로는 실제 D3 드로잉으로 들어가서, 기초적인 드로잉을 경험해볼 것이고, 차트로서의 구색을 갖춘 시각화를 만들기 위한 심화적인 드로잉에 들어갈 것입니다. 그리고 인터랙티브 시각화에서 빼놓을 수 없는 인터랙션 또한 간단히 다룰 것입니다. 마지막으로, 제가 D3를 사용하면서 체득한, D3와 관련된 팁을 몇 가지 안내해 드리고 질의응답 시간을 거쳐 강의를 마무리할 계획입니다. 이렇게 한 사이클을 돌고 나면, 앞으로 D3를 하실 때 왠만한 다른 기능들은 직접 찾아서 하실 수 있을 겁니다.
  3. D3란 무엇인가? D3는 Data-Driven Documents의 약자로, 데이터를 기반으로 다큐먼트를 조작하는 자바스크립트 라이브러리 입니다. D3js.org에 접속해보시면 아주 많은 예시들이 있을 겁니다. 이 예시들이 각각의 사람들이 D3를 이용해서 만든 시각화들이고요. 클릭하시면 해당 시각화 사이트로 이동하게 됩니다. Processing이나 HTML Canvas 등 다른 드로잉 라이브러리들과 D3를 구분짓는 부분이 바로 이 Data-driven이라는 말인데, 여기서의 Data-driven이란 게 어떤 의미인지는, 차차 이해하시게 될 겁니다.
  4. D3는 스탠퍼드 대학의 시각화 그룹에서 연구 목적으로 진행된 프로젝트고요. 마이크 보스톡에 의해 대부분 작성되었고, 지금도 계속 업데이트되고 있습니다. 제프 히어 교수가 당시 마이크 보스톡의 지도 교수였는데, 원래 유명한 사람이었지만 제자의 연구 덕분에 톡을 다니면서 할 이야기들이 더 많아졌죠. 제프 히어의 경우는 작년에 서울대에서 톡을 한 번 했었는데, 마이크 보스톡에 대해 어떻게 생각하냐는 질문에, “그는 내가 만났던 사람들 중 가장 뛰어난 API 디자이너”라고 답을 했습니다. D3는 인포비즈라는 정보 시각화 쪽의 가장 큰 학회에서 2011년 처음 논문의 형태로 발표되었고, 지금은 일반인들에게도 널리 사용되고 있습니다. 사실은 그 이전 2009년에 ProtoVis라는 비슷한 시각화 라이브러리를 같은 저자들이 냈었는데, 여기서 패러다임을 완전히 바꿔서 새로 만든 겁니다.
  5. 왜 D3가 주목받고 있는가? 몇 가지 이유가 있는데, 이를 한가지로 종합하면 오늘날의 비쥬얼라이제이션이 굉장히 역동적이라는 말로 표현할 수가 있습니다. 일단, 요즘 세상에는 시각화가 굉장히 일반화되어 있어요. 사람들이 시각화에 굉장히 친숙합니다. 여러분이 Facebook 담벼락 서핑하시다 보면 인포그래픽으로 나오는 보도자료같은 것들이 굉장히 많죠. 공중파 뉴스사에서도 SNS로 각종 인포그래픽 영상이나 이미지들을 이용해 뉴스들을 홍보하는 경우가 부쩍 많아졌습니다. 이렇게 데이터를 중심으로 뉴스기사들이 전개되는 움직임을 보통 데이터 저널리즘이라고 하는데, 요즘 빅데이터 같은 개념들이 트렌드화 되면서 엄청나게 퍼져있습니다. 보통 인포메이션 비쥬얼라이제이션 수업을 들으면 예시로 나오는 것들이 뉴욕 타임즈의 인터랙티브 시각화들입니다. 뉴욕 타임즈에서는 앞서 소개한 D3를 만든 마이크 보스톡을 아예 영입해서 계속하여 인터랙티브 시각화들을 내놓고 있습니다.
  6. D3가 주목받는 두번째 이유는 요즘 시각화들이 사용되는 주 미디어가 디지털이라는 데에 있습니다. 일단 이 시대에 이야기하는 정보 시각화는 더 이상 옛날처럼 종이에 인쇄된 차트같은 것들만을 가리키지 않습니다. 지금은 대부분의 시각화가 컴퓨터 상에서 이루어집니다. Spotfire같은 Visual Analytics 툴들도 많이 나오고 있죠.
  7. 게다가 시각화 미디어 중 요즘 가장 널리 쓰이고 있는 플랫폼은 바로 웹입니다. 웹 기반 인터랙티브 시각화는 앞에서 말씀드린 모든 시대 흐름에 장점을 지니고 있습니다. 웹 자체가 데이터 저널리즘의 소통 창구가 되고요, 사람들이 별도의 소프트웨어를 설치하지 않고도 들어가볼 수 있죠. 개발자의 입장에서는 따로 패치를 배포하지 않고도 서버단에서 문제를 수정하거나, 내용을 업그레이드할 수 있습니다. 이런 점들이 D3의 폭발적인 확산에 도움을 주었다고 봅니다.
  8. 자, 그럼 이제 D3에 대해서 본격적으로 살펴보도록 하겠습니다. 아까 D3가 Document를 Manipulate한다고 했는데, 여기서 Chart를 그려준다던지, 그런 식으로 표현하지 않은 이유가 있습니다. D3는 정확히 말하면 데이터를 넣어서 차트를 뱉어내는 라이브러리는 아닙니다. 그건 앞서 말씀드렸던 ProtoVis가 그런 라이브러리였죠. D3는 엄밀히 말하면, 데이터의 어레이를 기반으로 Visual Element들을 표현하는 데 특화된 라이브러리입니다. 즉, HTML 도큐먼트의 DOM 엘리먼트들을 데이터를 기반으로 수정해줍니다. 별도로 for loop을 돌거나 하지 않고요.
  9. D3를 사용하기 위해서는 몇 가지 선행지식이 필요합니다. 제가 보기엔 이 네 가지 정도만 간단히 아시면 D3를 충분히 다룰 수 있습니다. 자바스크립트는 d3가 자바스크립트로 씌어진 라이브러리이기 때문에 당연히 할 줄 아셔야 하고요. HTML도 D3가 HTML DOM element를 조작해서 시각화를 만들어내기 때문에 기초지식이 필요합니다. CSS는 D3의 시각화 요소들을 스타일링할 때 사용됩니다. jQuery는 반드시 필요한 지식은 아닙니다. 하지만 이것도 잘 하시면 나중에 아주 큰 도움이 됩니다. jQuery는 자바스크립트 라이브러리인데, CSS처럼 코드상에서 특정한 조건에 맞는 DOM element들을 선택하여 여러가지 가공을 할 수 있도록 해줍니다. 보통 웹사이트 브라우져상에서 이루어지는 많은 인터랙션들이 jQuery에 기반하고 있는 경우가 많습니다. D3같은 경우도 jQuery와 많이 닮았습니다. jQuery의 방식을 많이 답습했고요. 물론 문법같은 것들이 좀 다르기 때문에 나중에는 좀 헷갈리실 겁니다. 두 라이브러리가 하는 역할이 다르기 때문에, 복잡한 인터랙션이 들어가는 시각화에서는 d3와 jQuery를 섞어서 사용할 경우 굉장한 시너지 효과를 봅니다.
  10. 자 그럼 이제 D3를 실제로 사용할 준비를 해보겠습니다.
  11. 일단, 웹브라우져와 텍스트 에디터 하나씩을 띄우세요. 본 강의에서는 파이어폭스를 사용합니다. 맥을 사용하시는 분들은 사파리를 쓰셔도 괜찮습니다. Cross origin 텍스트 에디터는 아무거나 자신에게 맞는 것을 사용하시면 됩니다. 저는 Sublime Text를 사용할 겁니다. VIM이 수족같이 편하신 분들은 VIM을 쓰셔도 됩니다만, 만일 그렇지 않으면 저는 추천하지 않습니다. Tutorial을 진행할 때 이미 작성된 코드 사이사이를 수정할 거거든요.
  12. 비쥬얼라이제이션에서 사용하기 위한 데이터를 가공하고, 준비하는 과정에 대한 설명입니다. 모든 비쥬얼라이제이션의 첫걸음은 데이터를 디자인하는 단계라고 생각합니다. 이 단계가 중요한 이유는 먼저 시각화에 사용되는 데이터의 구조가 전반적인 코드 길이와 개발 난이도에 중요한 영향을 미칩니다. 또한, 보통 우리가 어떤 비쥬얼라이제이션을 제작할 때, 시각화를 먼저 결정해놓고 거기에 데이터 구조를 끼워맞추게 되는데, 이게 은근히 어렵습니다. 왜냐면 기존에 데이터셋이 데이터베이스라던지 거대한 액셀 테이블같은거로 이미 존재하는데, 그걸 새로 가공해서 알맞는 스키마를 가진 데이터를 뽑아내야 하거든요. 그래서 이 데이터 디자인 부터 간단히 짚고 넘어가려는 것입니다.
  13. 데이터를 직접 만드는 과정까진 오늘 다루지 않을겁니다.
  14. AJAX 콜 웹페이지가 다 로딩된 다음부터 데이터를 불러오기 시작. 데이터가 필요한 루틴은 모두 두번째 파라미터인 콜백 속에서 이루어져야 한다.
  15. 데이터가 파싱되어 들어옴
  16. D3의 데이터 기반 드로잉은, 먼저 데이터와 Binding할 엘리먼트를 선택한 뒤 데이터를 바인딩하고, 그에 맞춰서 엘리먼트를 추가, 수정, 삭제하는 방식으로 이루어진다.
  17. 아무것도 이루어지지 않은 빈 차트에서도 일단 존재하지 않는 엘리먼트가 선택되어야 한다.
  18. 우린 당분간은 완전히 빈 차트에서 새롭게 데이터를 넣어서 엘리먼트를 그리는 것만 할 것이기 때문에, 계속 Enter 셀렉션만 사용하게 될 것이다.
  19. Element와 Element간 레이아웃의 Dependency가 없다. 반대로 말하면 모든 지오메트릭 프로퍼티를 대부분 일일히 지정해줘야 한다는 뜻.
  20. 정렬도 자유롭다. Group transformation
  21. 차트의 구색맞추기부터 시작
  22. 데이터의 값을 실제 이미지 좌표에 맵핑해주는 역할. 직접 계산하면 매우 귀찮은 일이지만 D3에서 편하게 여러 가지를 제공한다.
  23. 그냥 g를 셀렉트하면 기존의 Axis 혹은 Chart 최상단에 만들어둔 다른 그룹들이 다 선택되어버리기 때문에, g에 클래스 부여
  24. Group에서 이미 y포지션을 지정해 놓았기 때문에 child 엘리먼트는 그룹 내 상대위치만 생각하면 된다.
  25. 차례대로 애니메이션이 시작되는 효과
  26. 이전까지의 예제에서는 웹페이지가 그려지고, 데이터가 로딩될 때 차트를 한 번 쭉 그려주고 끝냄. 이번에는 한 번 그려진 차트에 계속해서 액세스 해야함.
  27. Y 스케일의 도메인은 여기서 지정하지 않는다.
  28. 특히 Append에 대해서 주의를 기울여야 한다. 캔버스의 Append는 일반적으로 한 번만 호출되어야 한다.
  29. 글로벌 스코프로 데이터의 레퍼런스를 빼주는 역할을 한다.
  30. Join을 활용하는 것이 D3에서 가장 어려운 부분 중 하나다. 또한, 가장 중요한 부분 중 하나다.
  31. 변하지 않는 속성들은 이미 Enter Selection에서 정해졌을 것이므로, Update Selection에서는 건드리지 않아도 된다.
  32. Interactive Visualization의 중요한 테크닉 중 하나가 브러싱인데요. 차트의 비쥬얼 엘리먼트를 직접 선택해서 하이라이트하는 인터랙션을 말합니다. 직접 구현하려면 마우스 좌표 따고 박스 업데이트 해주고 엄청 고생을 해야 하는데, D3에서는 이걸 미리 구현해서 Axis처럼 함수형태로 붙일 수 있게 해놨습니다.
  33. Spotfire나 Tableau같은 시각화 라이브러리에서는 마우스를 차트 엘리먼트에 갖다대면 툴팁으로 자세한 정보들을 표시해줍니다. D3에서는 자체적으로 툴팁을 지원하지는 않고, 별도의 라이브러리가 있습니다. D3-tip : SVG로 툴팁 그려줌. SVG 캔버스 내에서만 그려진다는 단점. 이를 해결하고 싶다면 Qtip같은 jQuery 기반의 div를 이용한 툴팁 라이브러리를 붙여주면 됨.
  34. 본 튜토리얼에서는 Axis에 틱을 그대로 표시했으나, D3에서는 tick의 개수나 간격, 그 표시 포맷 등을 모두 커스터마이징 가능.
  35. (15분) 강의는 이것으로 마치고, 마지막으로 제가 그 동안 D3를 이용해 연구를 하면서 체득한 팁들을 몇가지 나누고 질의응답으로 넘어가도록 하겠습니다.
  36. 제가 오늘 강의에서는 자바스크립트를 사용했는데요. 사실 저는 자바스크립트보다는 커피스크립트를 더 많이 사용합니다. 자바스크립트가 웹에서 가장 널리 쓰이는 Client-side 언어이긴 하지만, 변수와 함수가 구분없이 쓰이다 보니 순수한 자바스크립트로는 코드가 지나치게 길어지는 문제도 있고 스펙이 워낙 방대하다 보니 여러모로 불편한 점들이 있습니다. 그래서 요즘에는 자바스크립트를 마치 어셈블리어처럼 접근하여, 별개의 언어로 코딩을 한 다음 그것을 컴파일해서 자바스크립트 코드로 만드는 특이한 방법들이 많이 사용되고 있는데요, 그 중 하나가 커피스크립트입니다. 커피스크립트는 자바스크립트와 1:1 대응으로 컴파일되는 언어로, 자바스크립트보다 간결한 문법을 사용하는 인덴트 기반의 언어입니다. 요즘 마이크로소프트에서 발표한 타입스크립트같은 것들도 있는데, 이것은 자바스크립트의 슈퍼셋이기 때문에 d3도 별도의 버전을 써야 하는 문제도 있고, 그래서 저는 커피스크립트를 사용하빈다. 보시는 바와 같이 functio이 파라미터로 들어가는 경우, 저 함수 정의 부분이 이렇게 짧아지죠. 또한, 자바스크립트 특성상 괄호를 열고 닫는 것이 계속 중첩되어서 쌓이는 경우가 많아, 이게 나중에는 엄청 복잡해집니다. 커피스크립트는 함수에서 괄호를 생략할 수 있고, 블록 정의 또한 인덴트로만 이루어지기 때문에 이런 부분이 엄청 수월하더군요. 웹 기반 프로그래밍을 전문으로 하실 분들이라면 한 번 사용을 고려해보셔도 좋을 듯 합니다.
  37. 두 번째는, 웹에 널려있는 D3의 튜토리얼과 질문들을 적극 활용하시라는 겁니다. D3는 Github에서 별을 42000개 넘게 받고, Fork도 11000번이 넘은 프로젝트이기 때문에, 사용자 층이 굉장히 두텁습니다. 특히 Mike bostock 이 사람이 연구자가 맞나 싶을 정도로, D3에 대한 도큐먼테이션도 굉장히 잘 해놓았고, 따로 blocks 라는 사이트를 만들어서 친절하게 수많은 튜토리얼 코드들을 올려놓았습니다. 실제로 Google에다가 d3 XX chart 이런식으로 검색을 하시면, 이 blocks 예제가 가장 많이 나올 겁니다. 그리고, d3로 작업을 하다가 막히는 부분이 있으면 stackoverflow를 적극적으로 활용하시기 바랍니다. 대부분 여러분이 겪는 문제점들은 다 먼저 삽질한 사람들이 있기 때문에, 대부분 이미 질문되고, 답변이 달려있는 경우가 많습니다. 이렇게 인터넷의 튜토리얼과 stackoverflow를 활용하시면 d3로 왠만한 건 다 하실 수 있게 될 겁니다.
  38. 또 하나의 팁은, D3의 시각화를 다른 용도로도 사용할 수 있다는 점입니다. 우리가 여기서 계속 D3로 다이나믹하고 인터랙티브한 차트를 만들었지만, 사실 각 순간에 그 시각화는 정지된 SVG 이미지에 불과합니다. 단지 마크업 언어로 정의되어 있다는 점이 보통의 비트맵 이미지와 다르죠. SVG 포맷은 어도비 일러스트레이터같은 이미지 저작도구에서 벡터 이미지 저장시 고를 수 있는 일반 이미지 포맷 중 하나이기 때문에, 브라우져의 개발자 도구에서 svg 코드를 꺼내 따로 저장하면, 일러스트레이터에서 그림처럼 열 수가 있어요. 논문에 피규어를 넣는다거나 할 때, 엑셀이나 R 같은데서 그려주지 못하는 특이한 시각화 같은 걸 넣고 싶으면, 그걸 D3로 그려서 svg로 저장해 사용하는 좋은 방법이 있습니다. 저도 이번에 논문을 쓸 대 Parallel Set이라는 시각화로 피규어를 넣고자 했는데, 엑셀이나 R에서 잘 지원하지 않아서, 이런 식으로 D3 패럴렐 셋 예제에다가 데이터를 넣어서 일러스트레이터로 수정해서 실제 논문에 삽입했습니다. 꼭 논문이 아니더라도 차트가 벡터로 나오기 때문에, 이런게 가능하다는 점을 알고 계시면 나중에 인포그래픽을 제작한다던지, 파워포인트에 집어넣는다던지 할 때 유용하게 써먹으실 수 있을 겁니다. 특히, 스타일시트로 적용된 속성같은 경우엔, 인터넷에 검색해보시면 스타일시트를 어트리뷰트로 바꿔서 svg로 저장해주는 라이브러리까지 있어서, 쉽게 가능하실 겁니다.
  39. 다음으로, 웹 기술에 대한 이야기를 좀 하겠습니다. 우리가 D3에서 데이터 로딩하는 메서드를 사용할 때, 파라메터에 URL을 집어넣었었죠. 이 URL은 특별히 json 이나 csv 파일같은 이미 만들어진 파일을 가리킬 필요 없이, 동적으로 json 이나 csv 스트링을 출력해주는 URL이기만 하면 됩니다. D3가 웹 기반이기 때문에, 웹서버에 데이터베이스까지 붙어있을 경우 그 데이터베이스의 자료를 시각화 할 때 굉장히 편리하게 쓸 수 있습니다. 가령 d3.json에 파라메터로 넣은 URL이 웹서버에 데이터를 요청하면, 서버는 데이터베이스로부터 적당히 json 스트링을 가공해서 다시 보내주는 식이죠. 이런 식으로 서버사이드 데이터를 클라이언트에서 시각화할 수 있게 되는 겁니다.
  40. 이런 총체적인 웹 시스템을 개발하기에 좋은 게 인터프리터 언어로 이루어진 프레임워크들인데, 대표적으로 Ruby on Rails나 Django같은게 있습니다. Ruby On Rails는 이름 그대로 Ruby로 서버단 프로그래밍을 하고, Django는 Python을 사용하는데, Ruby와 Python은 둘 다 데이터를 가공하는 데에 특화된 언어들이죠. 그래서 여러가지 종류의 시각화를 d3로 붙일 때, 각 시각화에 맞도록 다양한 구조의 데이터를 내보내는 코드를 간결하게 짤 수 있따는 강점이 있습니다. 게다가 Rails같은 경우는 아예 데이터베이스 기반의 웹사이트를 MVC 모델로 쉽게 만들려고 개발된 프레임웍이기 때문에, 데이터베이스도 하이레벨로 랩핑되어 있어서 다루기 아주 편하고, 자바스크립트도 시스템에서 함께 관리합니다. 저같은 경우에는 이런 이유들 때문에 Rails를 주로 사용하는데, 사실 뭐가 좋다 나쁘다는 없습니다. 자신이 쓰기 편한 언어로 쓰면 되는거죠.
  41. 제가 마지막으로 드릴 팁은, D3만 바라보지 마시라는 겁니다. 순수한 D3를 이용해 빈 코드에서부터 시각화 하나를 통째로 짜는 건 엄청난 노동을 요구합니다. 만약 자기만의 특수한 시각화를 디자인하거나 하는 것이 아니라 그냥 평범한 차트로 데이터를 표현하는 것이 목적이라면, 사실 D3를 쓰는 것보다는 D3를 랩핑해서 편리하게 만들어놓은 다른 라이브러리를 사용하는 것이 더 시간이 덜 걸릴겁니다. 이렇게 랩핑된 라이브러리들은 보통 하이레벨로 특정 차트 객체를 선언하고, 데이터나 스타일 등 여러 파라메터를 집어넣으면 완성된 인터랙티브 차트가 딱 그려지는 식으로 이루어져 있습니다. C3.js가 좀 널리 쓰이는 래퍼고요, 그 외에 다른 것들도 여러가지가 있으니 필요에 따라 찾아보고 이용하시면 되겠습니다.