Refactor of points handling : no more need to pre-sort data. TODO : onclick + onmouseover
This commit is contained in:
parent
97c057e568
commit
0308b8582a
@ -4,7 +4,7 @@ Timeline.js
|
|||||||
|
|
||||||
Timeline.js is a lightweight JS library to plot graphs using SVG. As it uses SVG, you can add event listeners on the plotted graph very easily.
|
Timeline.js is a lightweight JS library to plot graphs using SVG. As it uses SVG, you can add event listeners on the plotted graph very easily.
|
||||||
|
|
||||||
I coded it because I couldn't find any basic JS library to do this, without any external dependencies and extra features. Timeline.js is only 13k once minified, and can be reduced under 10k thanks to obfuscation. Better results may be obtained with a little refactor, but that's enough for me.
|
I coded it because I couldn't find any basic JS library to do this, without any external dependencies and extra features. Timeline.js is only 13k once minified, and can be reduced under 10k thanks to obfuscation. Better results may be obtained with a little refactor, but that's enough for me. Plus it can be very easily customised to fit your needs.
|
||||||
|
|
||||||
## Usage
|
## Usage
|
||||||
|
|
||||||
@ -32,7 +32,7 @@ Finally, you can draw the SVG thanks to `SVG.draw();`.
|
|||||||
|
|
||||||
## Other functions
|
## Other functions
|
||||||
|
|
||||||
* `SVG.clearGraph(GRAPH);` to delete the data for the graph GRAPH, or for all graphs if GRAPH is not specified.
|
* `SVG.clearGraph(GRAPH);` to delete the data for the graph GRAPH, or for all graphs + the graphs definition if GRAPH is not specified.
|
||||||
* `SVG.hasGraph(GRAPH);` to check if a graph with name GRAPH has already been defined or not.
|
* `SVG.hasGraph(GRAPH);` to check if a graph with name GRAPH has already been defined or not.
|
||||||
|
|
||||||
## License
|
## License
|
||||||
@ -56,7 +56,6 @@ Feel free to contribute !
|
|||||||
* Legend on X axis is not implemented
|
* Legend on X axis is not implemented
|
||||||
* Y axis is not implemented, but could be implemented easily
|
* Y axis is not implemented, but could be implemented easily
|
||||||
* Over effect is a bit overkill right now
|
* Over effect is a bit overkill right now
|
||||||
* You must add your points sorted, as the script won't sort them for you and it may result in very weird graphs
|
|
||||||
* Onclick events not working when there are multiple graphs.
|
* Onclick events not working when there are multiple graphs.
|
||||||
|
|
||||||
The last three points are easy to implement by refactoring the way the raw points are stored and using a single array for all the graphs.
|
The last two points are easy to implement by refactoring the way the raw points are stored and using a single array for all the graphs.
|
||||||
|
@ -12,7 +12,7 @@
|
|||||||
<div id="holder"></div>
|
<div id="holder"></div>
|
||||||
<script type="text/javascript" src="../timeline.js"></script>
|
<script type="text/javascript" src="../timeline.js"></script>
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
SVG.init({'id': 'holder', 'height': '100%', 'width': '100%', 'grid': 'both', 'x_axis': true, 'line': 'line', 'rounded': false, 'fill': true; 'x_callback': false});
|
SVG.init({'id': 'holder', 'height': '100%', 'width': '100%', 'grid': 'both', 'x_axis': true, 'line': 'line', 'rounded': false, 'fill': true, 'x_callback': false});
|
||||||
|
|
||||||
SVG.addGraph('test', 'red');
|
SVG.addGraph('test', 'red');
|
||||||
SVG.addPoints('test', [{'x':200, 'y':50, 'label':'%x : %y test'},{'x':75, 'y':100, 'label':'%x : %y test2'},{'x':150,'y':25, 'label':'%x : %y test3'},{'x':175, 'y':-200, 'label':'%x : %y test4'},{'x':125, 'y':75, 'label':'%x : %y µg/m<sup>3</sup>'},{'x':225, 'y':-220, 'label':'%x : %y test4'}]);
|
SVG.addPoints('test', [{'x':200, 'y':50, 'label':'%x : %y test'},{'x':75, 'y':100, 'label':'%x : %y test2'},{'x':150,'y':25, 'label':'%x : %y test3'},{'x':175, 'y':-200, 'label':'%x : %y test4'},{'x':125, 'y':75, 'label':'%x : %y µg/m<sup>3</sup>'},{'x':225, 'y':-220, 'label':'%x : %y test4'}]);
|
||||||
|
212
timeline.js
212
timeline.js
@ -31,9 +31,8 @@ SVG.parent_holder = false;
|
|||||||
SVG.holder = false;
|
SVG.holder = false;
|
||||||
SVG.g = false;
|
SVG.g = false;
|
||||||
SVG.axis = false;
|
SVG.axis = false;
|
||||||
|
SVG.graphs = [];
|
||||||
SVG.raw_points = [];
|
SVG.raw_points = [];
|
||||||
SVG.labels = [];
|
|
||||||
SVG.click = [];
|
|
||||||
SVG.x_callback = false;
|
SVG.x_callback = false;
|
||||||
|
|
||||||
|
|
||||||
@ -54,17 +53,12 @@ SVG.hasClass = function (element, cls) {
|
|||||||
|
|
||||||
// Add a new graph to the SVG
|
// Add a new graph to the SVG
|
||||||
SVG.addGraph = function (graph, color) {
|
SVG.addGraph = function (graph, color) {
|
||||||
SVG.raw_points[graph] = {};
|
SVG.graphs[graph] = color;
|
||||||
SVG.raw_points[graph].color = color;
|
|
||||||
SVG.raw_points[graph].data = new Array();
|
|
||||||
|
|
||||||
SVG.labels[graph] = new Array();
|
|
||||||
SVG.click[graph] = new Array();
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// Test wether a graph of name "graph" already exists
|
// Test wether a graph of name "graph" already exists
|
||||||
SVG.hasGraph = function (graph) {
|
SVG.hasGraph = function (graph) {
|
||||||
if(SVG.raw_points[graph] === undefined) {
|
if(typeof(SVG.graphs[graph]) === 'undefined') {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -73,22 +67,40 @@ SVG.hasGraph = function (graph) {
|
|||||||
};
|
};
|
||||||
|
|
||||||
// Clear the specified graph data, or completely clear all the graph data
|
// Clear the specified graph data, or completely clear all the graph data
|
||||||
SVG.clearGraphData = function (graph) {
|
SVG.clearGraph = function (graph) {
|
||||||
if(typeof(graph) === 'undefined') {
|
if(typeof(graph) === 'undefined') {
|
||||||
SVG.raw_points = [];
|
SVG.raw_points = [];
|
||||||
SVG.labels = [];
|
SVG.graphs = [];
|
||||||
SVG.click = [];
|
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
SVG.raw_points[graph].data = new Array();
|
for(var i = 0; i < SVG.raw_points.length; i++) {
|
||||||
SVG.labels[graph] = new Array();
|
if(SVG.raw_points[i].graph === graph) {
|
||||||
SVG.click[graph] = new Array();
|
SVG.raw_points[i] = undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
// Add points to the specified graph
|
// Add points to the specified graph
|
||||||
SVG.addPoints = function (graph, data) {
|
SVG.addPoints = function (graph, data) {
|
||||||
data.sort(function (a, b) {
|
for(var point = 0; point < data.length; point++) {
|
||||||
|
var insert = {'graph': graph, 'x': data[point].x, 'y': data[point].y};
|
||||||
|
if(typeof(data[point].label) !== 'undefined') {
|
||||||
|
insert.label = data[point].label;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
insert.label = '';
|
||||||
|
}
|
||||||
|
if(typeof(data[point].click) !== 'undefined') {
|
||||||
|
insert.click = data[point].click;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
insert.click = false;
|
||||||
|
}
|
||||||
|
SVG.raw_points.push(insert);
|
||||||
|
}
|
||||||
|
|
||||||
|
SVG.raw_points.sort(function (a, b) {
|
||||||
if(a.x < b.x) {
|
if(a.x < b.x) {
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
@ -99,22 +111,6 @@ SVG.addPoints = function (graph, data) {
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
for(var point = 0; point < data.length; point++) {
|
|
||||||
SVG.raw_points[graph].data.push([data[point].x, data[point].y]);
|
|
||||||
if(data[point].label !== undefined) {
|
|
||||||
SVG.labels[graph].push(data[point].label);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
SVG.labels[graph].push('');
|
|
||||||
}
|
|
||||||
if(data[point].click !== undefined) {
|
|
||||||
SVG.click[graph].push(data[point].click);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
SVG.click[graph].push(false);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
// Compute new coordinates, knowing the min and max value to fit the graph in the container
|
// Compute new coordinates, knowing the min and max value to fit the graph in the container
|
||||||
@ -270,6 +266,7 @@ SVG.init = function (arg) {
|
|||||||
|
|
||||||
SVG.x_callback = arg.x_callback;
|
SVG.x_callback = arg.x_callback;
|
||||||
|
|
||||||
|
/* TODO
|
||||||
SVG.parent_holder.addEventListener('mousemove', function(e) {
|
SVG.parent_holder.addEventListener('mousemove', function(e) {
|
||||||
var evt = e || window.event;
|
var evt = e || window.event;
|
||||||
var rect = false;
|
var rect = false;
|
||||||
@ -284,9 +281,10 @@ SVG.init = function (arg) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
SVG.overEffect(evt.clientX, evt.clientY);
|
SVG.overEffect(evt.clientX, evt.clientY);
|
||||||
});
|
});*/
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/* TODO
|
||||||
// Handle the over effect
|
// Handle the over effect
|
||||||
SVG.overEffect = function(x, y) {
|
SVG.overEffect = function(x, y) {
|
||||||
if(!document.elementFromPoint(x, y)) {
|
if(!document.elementFromPoint(x, y)) {
|
||||||
@ -314,7 +312,7 @@ SVG.overEffect = function(x, y) {
|
|||||||
|
|
||||||
// Display again the rect element
|
// Display again the rect element
|
||||||
rect.setAttribute('display', 'block');
|
rect.setAttribute('display', 'block');
|
||||||
};
|
};*/
|
||||||
|
|
||||||
// Get the scale so that graph fits with window
|
// Get the scale so that graph fits with window
|
||||||
SVG.scale = function(data) {
|
SVG.scale = function(data) {
|
||||||
@ -327,46 +325,25 @@ SVG.scale = function(data) {
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
var minX = new Array(), minY = new Array();
|
var minX = false, minY = 0;
|
||||||
var maxX = new Array(), maxY = new Array();
|
var maxX = false, maxY = false;
|
||||||
var circle = false, last_point = false, line = false;
|
var circle = false, last_point = false, line = false;
|
||||||
|
|
||||||
var tmp_minX, tmp_minY, tmp_maxX, tmp_maxY;
|
|
||||||
|
|
||||||
// Look for max and min values for both axis
|
// Look for max and min values for both axis
|
||||||
for(graph in data) {
|
for(var point = 0; point < data.length; point++) {
|
||||||
tmp_minX = false;
|
if(data[point].x < minX || minX === false) {
|
||||||
tmp_minY = 0;
|
minX = data[point].x;
|
||||||
tmp_maxX = false;
|
|
||||||
tmp_maxY = false;
|
|
||||||
|
|
||||||
for(var point = 0; point < data[graph].data.length; point++) {
|
|
||||||
x = data[graph].data[point][0];
|
|
||||||
y = data[graph].data[point][1];
|
|
||||||
|
|
||||||
if(x < tmp_minX || tmp_minX === false) {
|
|
||||||
tmp_minX = x;
|
|
||||||
}
|
}
|
||||||
if(x > tmp_maxX || tmp_maxX === false) {
|
if(data[point].x > maxX || maxX === false) {
|
||||||
tmp_maxX = x;
|
maxX = data[point].x;
|
||||||
}
|
}
|
||||||
if(y < tmp_minY) {
|
if(data[point].y < minY) {
|
||||||
tmp_minY = y;
|
minY = data[point].y;
|
||||||
}
|
}
|
||||||
if(y > tmp_maxY || tmp_maxY === false) {
|
if(data[point].y > maxY || maxY === false) {
|
||||||
tmp_maxY = y;
|
maxY = data[point].y;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
minX.push(tmp_minX);
|
|
||||||
minY.push(tmp_minY);
|
|
||||||
maxX.push(tmp_maxX);
|
|
||||||
maxY.push(tmp_maxY);
|
|
||||||
}
|
|
||||||
|
|
||||||
minX = Math.min.apply(null, minX);
|
|
||||||
minY = Math.min.apply(null, minY);
|
|
||||||
maxX = Math.max.apply(null, maxX);
|
|
||||||
maxY = Math.max.apply(null, maxY);
|
|
||||||
|
|
||||||
// Scale the grid, if needed
|
// Scale the grid, if needed
|
||||||
var scale = SVG.getNewXY(minX, maxX, minY, maxY);
|
var scale = SVG.getNewXY(minX, maxX, minY, maxY);
|
||||||
@ -414,63 +391,66 @@ SVG.scale = function(data) {
|
|||||||
// Draw graphs
|
// Draw graphs
|
||||||
SVG.draw = function() {
|
SVG.draw = function() {
|
||||||
var scale = SVG.scale(SVG.raw_points);
|
var scale = SVG.scale(SVG.raw_points);
|
||||||
var x, y, path;
|
var points = [], path;
|
||||||
var px, py;
|
var px, py;
|
||||||
var element;
|
var element;
|
||||||
|
|
||||||
for(var graph in SVG.raw_points) {
|
for(var point = 0; point < SVG.raw_points.length; point++) {
|
||||||
x = new Array();
|
var tmp = scale(SVG.raw_points[point].x, SVG.raw_points[point].y);
|
||||||
y = new Array();
|
points.push({'x': tmp.x, 'y': tmp.y, 'graph': SVG.raw_points[point].graph, 'click': SVG.raw_points[point].click, 'label': SVG.raw_points[point].label});
|
||||||
path = '';
|
|
||||||
|
|
||||||
/* Draw points */
|
|
||||||
for(var point = 0; point < SVG.raw_points[graph].data.length; point++) {
|
|
||||||
var tmp = scale(SVG.raw_points[graph].data[point][0], SVG.raw_points[graph].data[point][1]);
|
|
||||||
x.push(tmp.x);
|
|
||||||
y.push(tmp.y);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Draw each graph
|
||||||
|
for(var graph in SVG.graphs) {
|
||||||
|
var filtered_points = points.filter(function(el) { return el.graph == graph; });
|
||||||
|
path = '';
|
||||||
|
|
||||||
|
// Draw line
|
||||||
if(SVG.rounded === true) {
|
if(SVG.rounded === true) {
|
||||||
|
// TODO
|
||||||
px = SVG.getControlPoints(x);
|
px = SVG.getControlPoints(x);
|
||||||
py = SVG.getControlPoints(y);
|
py = SVG.getControlPoints(y);
|
||||||
for(var point = 0; point < SVG.raw_points[graph].data.length - 1; point++) {
|
for(var point = 0; point < points.length - 1; point++) {
|
||||||
path += 'C '+px.p1[point]+' '+py.p1[point]+' '+px.p2[point]+' '+py.p2[point]+' '+x[point+1]+' '+y[point+1]+' ';
|
path += 'C '+px.p1[point]+' '+py.p1[point]+' '+px.p2[point]+' '+py.p2[point]+' '+x[point+1]+' '+y[point+1]+' ';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
for(var point = 1; point < SVG.raw_points[graph].data.length; point++) {
|
for(var point = 1; point < filtered_points.length; point++) {
|
||||||
path += 'L '+x[point]+' '+y[point]+' ';
|
path += 'L '+filtered_points[point].x+' '+filtered_points[point].y+' ';
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if(SVG.fill) {
|
|
||||||
element = SVG.createElement('path', {'class': 'graph', 'fill': SVG.raw_points[graph].color, 'opacity': '0.25', 'stroke': 'none', 'd': 'M '+x[0]+' '+2*SVG.marginBottom+' L '+x[0]+' '+y[0]+' '+ path + ' L '+x[SVG.raw_points[graph].data.length - 1]+' '+2*SVG.marginBottom+' Z' });
|
|
||||||
SVG.g.insertBefore(element, SVG.g.querySelectorAll('.over')[0]);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(SVG.line !== 'none') {
|
if(SVG.line !== 'none') {
|
||||||
element = SVG.createElement('path', {'class': 'line', 'stroke': SVG.raw_points[graph].color, 'stroke-width': 2, 'fill': 'none', 'd': 'M '+x[0]+' '+y[0]+' '+path});
|
element = SVG.createElement('path', {'class': 'line', 'stroke': SVG.graphs[graph], 'stroke-width': 2, 'fill': 'none', 'd': 'M '+filtered_points[0].x+' '+filtered_points[0].y+' '+path});
|
||||||
if(SVG.line === 'dashed') {
|
if(SVG.line === 'dashed') {
|
||||||
element.setAttribute('style', 'stroke-dasharray: '+SVG.dashed_style);
|
element.setAttribute('style', 'stroke-dasharray: '+SVG.dashed_style);
|
||||||
}
|
}
|
||||||
SVG.g.appendChild(element);
|
SVG.g.appendChild(element);
|
||||||
}
|
}
|
||||||
|
|
||||||
for(var point = 0; point < SVG.raw_points[graph].data.length; point++) {
|
// Draw fill
|
||||||
element = SVG.createElement('circle', {'class': 'point', 'id': 'point_'+point+'_'+graph, 'cx': x[point], 'cy': y[point], 'r': 4, 'fill': '#333', 'stroke': SVG.raw_points[graph].color, 'stroke-width': 2});
|
if(SVG.fill) {
|
||||||
SVG.g.insertBefore(element, SVG.g.querySelectorAll('.label')[0]);
|
element = SVG.createElement('path', {'class': 'graph', 'fill': SVG.graphs[graph], 'opacity': '0.25', 'stroke': 'none', 'd': 'M '+filtered_points[0].x+' '+2*SVG.marginBottom+' L '+filtered_points[0].x+' '+filtered_points[0].y+' '+ path + ' L '+filtered_points[filtered_points.length - 1].x+' '+2*SVG.marginBottom+' Z' });
|
||||||
|
SVG.g.insertBefore(element, SVG.g.querySelectorAll('.over')[0]);
|
||||||
if(SVG.click[graph][point] !== false) {
|
|
||||||
element.onclick = SVG.click[graph][point];
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if(SVG.labels[graph][point] !== '') {
|
// Draw points and labels
|
||||||
|
for(var point = 0; point < filtered_points.length; point++) {
|
||||||
|
element = SVG.createElement('circle', {'class': 'point', 'id': 'point_'+point+'_'+graph, 'cx': filtered_points[point].x, 'cy': filtered_points[point].y, 'r': 4, 'fill': '#333', 'stroke': SVG.graphs[graph], 'stroke-width': 2});
|
||||||
|
SVG.g.insertBefore(element, SVG.g.querySelectorAll('.label')[0]);
|
||||||
|
|
||||||
|
if(filtered_points[point].click !== false) {
|
||||||
|
element.onclick = filtered_points[point].click;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(filtered_points[point].label !== '') {
|
||||||
var g = SVG.createElement('g', { 'class': 'label', 'id': 'label_'+point+'_'+graph, 'transform': 'translate(0, ' + SVG.parent_holder.offsetHeight + ') scale(1, -1)'});
|
var g = SVG.createElement('g', { 'class': 'label', 'id': 'label_'+point+'_'+graph, 'transform': 'translate(0, ' + SVG.parent_holder.offsetHeight + ') scale(1, -1)'});
|
||||||
SVG.g.appendChild(g);
|
SVG.g.appendChild(g);
|
||||||
|
|
||||||
element = SVG.createElement('text', {});
|
element = SVG.createElement('text', {});
|
||||||
var text = SVG.labels[graph][point].replace('</sup>', '<sup>').split('<sup>');
|
var text = filtered_points[point].label.replace('</sup>', '<sup>').split('<sup>');
|
||||||
for(var i = 0; i < text.length; i++) {
|
for(var i = 0; i < text.length; i++) {
|
||||||
text[i] = text[i].replace(/(<([^>]+)>)/ig,"").replace('%y', SVG.raw_points[graph].data[point][1]).replace('%x', SVG.raw_points[graph].data[point][0]);
|
text[i] = text[i].replace(/(<([^>]+)>)/ig,"").replace('%y', filtered_points[point].y).replace('%x', filtered_points[point].x);
|
||||||
if(i % 2 == 0) {
|
if(i % 2 == 0) {
|
||||||
element.appendChild(document.createTextNode(text[i]));
|
element.appendChild(document.createTextNode(text[i]));
|
||||||
|
|
||||||
@ -488,30 +468,30 @@ SVG.draw = function() {
|
|||||||
g.appendChild(path);
|
g.appendChild(path);
|
||||||
g.appendChild(element);
|
g.appendChild(element);
|
||||||
|
|
||||||
var x_text = x[point] - element.getBoundingClientRect().width / 2;
|
var x_text = filtered_points[point].x - element.getBoundingClientRect().width / 2;
|
||||||
var y_text = SVG.parent_holder.offsetHeight - y[point] - 20;
|
var y_text = SVG.parent_holder.offsetHeight - filtered_points[point].y - 20;
|
||||||
var element_width = element.getBoundingClientRect().width;
|
var element_width = element.getBoundingClientRect().width;
|
||||||
var element_height = element.getBoundingClientRect().height;
|
var element_height = element.getBoundingClientRect().height;
|
||||||
|
|
||||||
if(x[point] - element.getBoundingClientRect().width / 2 < 0) {
|
if(filtered_points[point].x - element.getBoundingClientRect().width / 2 < 0) {
|
||||||
x_text = x[point] + 20;
|
x_text = filtered_points[point].x + 20;
|
||||||
y_text = SVG.parent_holder.offsetHeight - y[point] + 5;
|
y_text = SVG.parent_holder.offsetHeight - filtered_points[point].y + 5;
|
||||||
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text - 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text - 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
||||||
}
|
}
|
||||||
else if(y[point] + element.getBoundingClientRect().height + 12 > SVG.parent_holder.offsetHeight) {
|
else if(filtered_points[point].y + element.getBoundingClientRect().height + 12 > SVG.parent_holder.offsetHeight) {
|
||||||
x_text = x[point] + 20;
|
x_text = filtered_points[point].x + 20;
|
||||||
y_text = SVG.parent_holder.offsetHeight - y[point] + 5;
|
y_text = SVG.parent_holder.offsetHeight - filtered_points[point].y + 5;
|
||||||
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text - 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text - 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text - 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
||||||
|
|
||||||
if(x_text + element_width > SVG.parent_holder.offsetWidth) {
|
if(x_text + element_width > SVG.parent_holder.offsetWidth) {
|
||||||
x_text = x[point] - element_width - 20;
|
x_text = filtered_points[point].y - element_width - 20;
|
||||||
y_text = SVG.parent_holder.offsetHeight - y[point] + 5;
|
y_text = SVG.parent_holder.offsetHeight - filtered_points[point].y + 5;
|
||||||
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text + element_width + 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text + element_width + 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if(x[point] + element_width / 2 + 12 > SVG.parent_holder.offsetWidth) {
|
else if(filtered_points[point].x + element_width / 2 + 12 > SVG.parent_holder.offsetWidth) {
|
||||||
x_text = x[point] - element_width - 20;
|
x_text = filtered_points[point].x - element_width - 20;
|
||||||
y_text = SVG.parent_holder.offsetHeight - y[point] + 5;
|
y_text = SVG.parent_holder.offsetHeight - filtered_points[point].y + 5;
|
||||||
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text + element_width + 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
path.setAttribute('d', 'M '+(x_text - 5)+' '+(y_text + 5)+' L '+(x_text - 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 2.5)+' L '+(x_text + element_width + 10)+' '+(y_text - element_height/2 + 5)+' L '+(x_text + element_width + 5)+' '+(y_text - element_height/2 + 7.5)+' L '+(x_text + element_width + 5)+' '+(y_text + 5)+' Z');
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
@ -524,27 +504,28 @@ SVG.draw = function() {
|
|||||||
g.setAttribute('display', 'none');
|
g.setAttribute('display', 'none');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
for(var point = 0; point < SVG.raw_points[graph].data.length; point++) {
|
/*for(var point = 0; point < points.x.length; point++) {
|
||||||
var rect = SVG.createElement('rect', {'class': 'over', 'id': 'over_'+point+'_'+graph, 'y': 0, 'fill': 'white', 'opacity': 0, 'height': '100%'});
|
var rect = SVG.createElement('rect', {'class': 'over', 'id': 'over_'+point+'_'+graph, 'y': 0, 'fill': 'white', 'opacity': 0, 'height': '100%'});
|
||||||
if(point == 0) {
|
if(point == 0) {
|
||||||
rect.setAttribute('x', 0);
|
rect.setAttribute('x', 0);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
rect.setAttribute('x', (x[point] + x[point - 1]) / 2);
|
rect.setAttribute('x', (points.x[point] + points.x[point - 1]) / 2);
|
||||||
}
|
}
|
||||||
|
|
||||||
if(point == SVG.raw_points[graph].data.length - 1) {
|
if(point == SVG.raw_points.length - 1) {
|
||||||
rect.setAttribute('width', SVG.parent_holder.offsetWidth - (x[point] + x[point - 1])/2);
|
rect.setAttribute('width', SVG.parent_holder.offsetWidth - (points.x[point] + points.x[point - 1])/2);
|
||||||
}
|
}
|
||||||
else if(point == 0) {
|
else if(point == 0) {
|
||||||
rect.setAttribute('width', (x[1] + x[0])/2 + SVG.marginLeft);
|
rect.setAttribute('width', (points.x[1] + points.x[0])/2 + SVG.marginLeft);
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
rect.setAttribute('width', (x[point + 1] - x[point - 1])/2);
|
rect.setAttribute('width', (points.x[point + 1] - points.x[point - 1])/2);
|
||||||
}
|
}
|
||||||
SVG.g.appendChild(rect);
|
SVG.g.appendChild(rect);
|
||||||
|
/*
|
||||||
rect.onclick = (function(x, y) {
|
rect.onclick = (function(x, y) {
|
||||||
return function(e) {
|
return function(e) {
|
||||||
var evt = e || window.event;
|
var evt = e || window.event;
|
||||||
@ -568,8 +549,7 @@ SVG.draw = function() {
|
|||||||
element = SVG.createElement('line', {'class': 'legend_x', 'stroke': 'gray', 'stroke-width': 2, 'x1': x[point], 'x2': x[point], 'y1': y_zero - 5, 'y2': y_zero + 5});
|
element = SVG.createElement('line', {'class': 'legend_x', 'stroke': 'gray', 'stroke-width': 2, 'x1': x[point], 'x2': x[point], 'y1': y_zero - 5, 'y2': y_zero + 5});
|
||||||
SVG.g.appendChild(element);
|
SVG.g.appendChild(element);
|
||||||
}
|
}
|
||||||
}
|
}*/
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
var old = window.onresize || function () {};
|
var old = window.onresize || function () {};
|
||||||
|
2
timeline.min.js
vendored
2
timeline.min.js
vendored
File diff suppressed because one or more lines are too long
Loading…
x
Reference in New Issue
Block a user