-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathbar.js
More file actions
133 lines (101 loc) · 2.74 KB
/
bar.js
File metadata and controls
133 lines (101 loc) · 2.74 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
// https://ejb.github.io/2016/05/23/a-better-way-to-structure-d3-code.html
var Bar = function(opts) {
// load in args from config obj
this.data = opts.data;
this.element = opts.element;
// create the chart
this.draw();
}
Bar.prototype.draw = function() {
// define width, height and margin
this.width = this.element.offsetWidth;
this.height = this.width / 2;
this.margin = {
top:20,
right:75,
bottom:45,
left:50
};
// set up parent element and SVG
this.element.innerHtml = '';
var svg = d3.select(this.element).append('svg');
svg.attr('width', this.width);
svg.attr('height', this.height);
// we'll actually be a ppending to a <g> element
this.plot = svg.append('g')
.attr('transform', 'translate('+this.margin.left+','+this.margin.top+')')
// create the other stuff
this.createScales();
this.addAxes();
this.addLine();
}
Bar.prototype.createScales = function(){
// short hand to save typing later
var m = this.margin;
// calculate max and min for data
var xExtent = d3.extent(this.data, function(d,i){
return d[0]
});
var yExtent = d3.extent(this.data, function(d,i){
return d[1];
});
// force zero baseline if all data points are positive
if (yExtent[0] > 0) { yExtent[0] = 0};
this.xScale = d3.time.scale()
.range([0, this.width - m.right])
.domain(xExtent);
this.yScale = d3.scale.linear()
.range([this.height - (m.top + m.bottom), 0])
.domain(yExtent);
}
Bar.prototype.addAxes = function(){
var m = this.margin;
// create and append axis elements
// this all pretty straighfforward D3 stuff
var xAxis = d3.svg.axis()
.scale(this.xScale)
.orient('bottom')
.ticks(d3.time.month, 1);
var yAxis = d3.svg.axis()
.scale(this.yScale)
.orient('left')
.tickFormat(d3.format('d'));
this.plot.append('g')
.attr('class', 'x-axis')
.attr("transform", "translate(0," + (this.height-(m.top+m.bottom)) + ")")
.call(xAxis);
this.plot.append('g')
.attr('class', 'y axis')
.call(yAxis);
}
Bar.prototype.addLine = function(){
// need to load `this` into that;
var _this = this;
var line = d3.svg.line()
.x(function(d){
// ... so we can access it here
return _this.xScale(d[0]);
})
.y(function(d){
return _this.yScale(d[0]);
});
this.plot.append('path')
// use data stored in `this`
.datum(this.data)
.classed('line', true)
.attr('d', line)
// set stroke to specified color, or default to red
.style('stroke', this.lineColor || 'red');
}
// the following are 'public methods'
// which can be used by code outside of this file
Bar.prototype.setColor = function(newColor){
this.plot.select('.line')
.style('stroke', newColor);
// store for use when redrawing
}
Bar.prototype.setData = function(newData){
this.data = newData;
// full redraw needed
this.draw();
}