Here's a simple datetime chart made with this unpretending React.js SVG library.
Last active
August 29, 2015 14:04
-
-
Save fiatjaf/d4353158a6783edc6861 to your computer and use it in GitHub Desktop.
a bl.ocks example of ReactLineChart
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Generated by CoffeeScript 1.7.1 | |
(function() { | |
var AxesHelper; | |
AxesHelper = function() { | |
var format, getTicks, interval, registry, scales, self; | |
self = this; | |
registry = {}; | |
this.register = function(id, scaleType, opts) { | |
var domain; | |
domain = scaleType === 'time' ? [opts.domain[0].getTime ? opts.domain[0].getTime() : opts.domain[0], opts.domain[1].getTime ? opts.domain[1].getTime() : opts.domain[1]] : opts.domain; | |
return registry[id] = { | |
domain: domain, | |
range: opts.range, | |
scale: scales[scaleType](domain, opts.range), | |
interval: opts.interval || interval(domain), | |
tickFormat: opts.tickFormat || function(d) { | |
return format[scaleType](id, d); | |
} | |
}; | |
}; | |
this.format = function(id) { | |
return function(v) { | |
return registry[id].tickFormat(v); | |
}; | |
}; | |
this.getTicks = function(id) { | |
return getTicks(id); | |
}; | |
this.scale = function(id) { | |
return registry[id].scale; | |
}; | |
scales = { | |
linear: function(domain, range) { | |
return function(value) { | |
var d, m; | |
m = domain[1] - domain[0]; | |
d = range[1] - range[0]; | |
return ((value - domain[0]) / m) * d + range[0]; | |
}; | |
}, | |
time: function(domain, range) { | |
var lin; | |
lin = this.linear(domain, range); | |
return function(value) { | |
return lin((value.getTime ? value.getTime() : value)); | |
}; | |
} | |
}; | |
interval = function(domain) { | |
return (domain[1] - domain[0]) / 12; | |
}; | |
format = { | |
daysOfWeek: ['Sun', 'Mon', 'Tue', 'Wed', 'Thu', 'Fri', 'Sat'], | |
linear: function(id, v) { | |
var commaize, nDecimals, parts; | |
parts = v.toString().split('.'); | |
commaize = function(s) { | |
if (s.length > 3) { | |
return commaize(s.slice(0, -3)) + ',' + s.slice(-3); | |
} else { | |
return s; | |
} | |
}; | |
nDecimals = 5 - parts[0].length; | |
return commaize(parts[0]) + (parts[1] && nDecimals > 1 ? "." + parts[1] : '').slice(0, nDecimals); | |
}, | |
time: function(id, v) { | |
var d, itv; | |
d = new Date(v); | |
itv = registry[id].interval; | |
switch (false) { | |
case !(itv < 6e4): | |
return d.getMinutes() + 'm' + d.getSeconds() + 's'; | |
case !(itv < 36e5): | |
return d.getHours() + 'h' + d.getMinutes() + 'm'; | |
case !(itv < 864e5): | |
return this.daysOfWeek[d.getDay()] + ', ' + d.getHours() + 'h'; | |
case !(itv < 2592e6): | |
return d.getDate() + '/' + (d.getMonth() + 1); | |
case !(itv < 126144e6): | |
return (d.getMonth() + 1) + '/' + d.getYear(); | |
default: | |
return d.getFullYear(); | |
} | |
} | |
}; | |
getTicks = function(id) { | |
var domain, itv, scale, t, tickFormat, ticks, _i, _ref, _ref1; | |
tickFormat = registry[id].tickFormat; | |
scale = registry[id].scale; | |
domain = registry[id].domain; | |
itv = registry[id].interval; | |
ticks = []; | |
for (t = _i = _ref = domain[0], _ref1 = domain[1]; itv > 0 ? _i <= _ref1 : _i >= _ref1; t = _i += itv) { | |
ticks.push({ | |
offset: scale(t), | |
text: tickFormat(t) | |
}); | |
} | |
return ticks; | |
}; | |
return this; | |
}; | |
window.Axes = AxesHelper(); | |
}).call(this); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<script src="http://cdnjs.cloudflare.com/ajax/libs/react/0.11.0/react.js"></script> | |
<script src="axes-helper.js"></script><!--bundled dependency--> | |
<script src="react-line-chart.js"></script> | |
<div id="example"></div> | |
<script src="main.js"></script> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
React.renderComponent(ReactLineChart({ | |
width: 800, | |
height: 300, | |
data: [{ | |
x: new Date(1406841907474), y: 3223 | |
}, { | |
x: new Date(1406868310708), y: 7250 | |
}, { | |
x: new Date(1406869310708), y: 6330 | |
}, { | |
x: new Date(1406870310708), y: 7000 | |
}, { | |
x: new Date(1406871812096), y: 4600 | |
}, { | |
x: new Date(1406880007565), y: 2321 | |
}, { | |
x: new Date(1406882110290), y: 2000 | |
}, { | |
x: new Date(1406882120290), y: 2700 | |
}], | |
series: { | |
x: { | |
'scale': 'time', | |
'legend': 'TIME' | |
}, | |
y: { | |
'scale': 'linear', | |
'legend': 'VALUE' | |
} | |
} | |
}), document.getElementById('example')) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// Generated by CoffeeScript 1.7.1 | |
(function() { | |
var ReactLineChart, circle, div, g, line, path, span, strong, style, svg, text, _ref; | |
_ref = React.DOM, div = _ref.div, span = _ref.span, strong = _ref.strong, svg = _ref.svg, g = _ref.g, circle = _ref.circle, line = _ref.line, text = _ref.text, path = _ref.path, style = _ref.style; | |
ReactLineChart = React.createClass({ | |
getDefaultProps: function() { | |
return { | |
width: 600, | |
height: 400, | |
margin: { | |
top: 20, | |
right: 20, | |
bottom: 30, | |
left: 50 | |
}, | |
axis: { | |
x: { | |
scale: 'linear' | |
}, | |
y: { | |
scale: 'linear' | |
} | |
} | |
}; | |
}, | |
shouldComponentUpdate: function(nextProps) { | |
return JSON.stringify(nextProps) !== JSON.stringify(this.props); | |
}, | |
render: function() { | |
var d, height, margin, pathCommands, r, tick, width, x, xs, y, ys, _i, _len, _ref1; | |
if (!this.props.data || !this.props.data.length) { | |
return null; | |
} | |
margin = this.props.margin; | |
width = this.props.width - this.props.margin.left - this.props.margin.right; | |
height = this.props.height - this.props.margin.top - this.props.margin.bottom; | |
xs = (function() { | |
var _i, _len, _ref1, _results; | |
_ref1 = this.props.data; | |
_results = []; | |
for (_i = 0, _len = _ref1.length; _i < _len; _i++) { | |
d = _ref1[_i]; | |
_results.push(d.x); | |
} | |
return _results; | |
}).call(this); | |
Axes.register('x', this.props.series.x.scale, { | |
range: [0, width], | |
domain: [Math.min.apply(this, xs), Math.max.apply(this, xs)] | |
}); | |
x = Axes.scale('x'); | |
ys = (function() { | |
var _i, _len, _ref1, _results; | |
_ref1 = this.props.data; | |
_results = []; | |
for (_i = 0, _len = _ref1.length; _i < _len; _i++) { | |
d = _ref1[_i]; | |
_results.push(d.y); | |
} | |
return _results; | |
}).call(this); | |
Axes.register('y', this.props.series.y.scale, { | |
range: [height, 0], | |
domain: [Math.min.apply(this, ys), Math.max.apply(this, ys)] | |
}); | |
y = Axes.scale('y'); | |
pathCommands = "M" + (x(this.props.data[0].x)) + "," + (y(this.props.data[0].y)); | |
_ref1 = this.props.data.slice(1); | |
for (_i = 0, _len = _ref1.length; _i < _len; _i++) { | |
r = _ref1[_i]; | |
pathCommands += "L" + (x(r.x)) + "," + (y(r.y)); | |
} | |
return div({ | |
className: 'react-chart-line' | |
}, style({ | |
scoped: true | |
}, '.react-chart-line { font: 10px sans-serif; } .axis path, .axis line { fill: none; stroke: #000; shape-rendering: crispEdges; } .x.axis path { display: none; } .line { fill: transparent; stroke: rgb(141, 24, 33); stroke-width: 1.5px; }'), svg({ | |
style: { | |
"height": "" + (height + margin.top + margin.bottom) + "px" | |
}, | |
width: width + margin.left + margin.right, | |
height: height + margin.top + margin.bottom | |
}, g({ | |
transform: "translate(" + margin.left + ", " + margin.top + ")" | |
}, g({ | |
className: "x axis", | |
transform: "translate(0," + height + ")" | |
}, (function() { | |
var _j, _len1, _ref2, _results; | |
_ref2 = Axes.getTicks('x'); | |
_results = []; | |
for (_j = 0, _len1 = _ref2.length; _j < _len1; _j++) { | |
tick = _ref2[_j]; | |
_results.push(g({ | |
className: "tick", | |
key: tick.text, | |
transform: "translate(" + tick.offset + ",0)", | |
style: { | |
"opacity": "1" | |
} | |
}, line({ | |
y2: "6", | |
x2: "0" | |
}), text({ | |
y: "9", | |
x: "0", | |
dy: ".71em", | |
style: { | |
"text-anchor": "middle" | |
} | |
}, tick.text))); | |
} | |
return _results; | |
})(), path({ | |
className: 'domain', | |
d: "M-6,6 V0 H" + width + " V6" | |
}), this.props.series.x.legend ? text({ | |
x: width - 10, | |
y: "-16", | |
style: { | |
'text-anchor': 'start' | |
} | |
}, this.props.series.x.legend) : void 0), g({ | |
className: "y axis" | |
}, (function() { | |
var _j, _len1, _ref2, _results; | |
_ref2 = Axes.getTicks('y'); | |
_results = []; | |
for (_j = 0, _len1 = _ref2.length; _j < _len1; _j++) { | |
tick = _ref2[_j]; | |
_results.push(g({ | |
className: "tick", | |
key: tick.text, | |
transform: "translate(0," + tick.offset + ")", | |
style: { | |
"opacity": "1" | |
} | |
}, line({ | |
x2: "-6", | |
y2: "0" | |
}), text({ | |
x: "-9", | |
y: "0", | |
dy: ".32em", | |
style: { | |
"text-anchor": "end" | |
} | |
}, tick.text))); | |
} | |
return _results; | |
})(), path({ | |
className: 'domain', | |
d: "M-6,0 H0 V" + height + " H-6" | |
}), this.props.series.y.legend ? text({ | |
transform: 'rotate(-90)', | |
y: '6', | |
dy: '.71em', | |
style: { | |
'text-anchor': 'end' | |
} | |
}, this.props.series.y.legend) : void 0), path({ | |
className: "line", | |
d: pathCommands | |
})))); | |
} | |
}); | |
window. ReactLineChart = ReactLineChart; | |
}).call(this); |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment