Generating random data at 1 minute intervals: Highcharts - highcharts

I have created a spline real time chart where I want to show points at regular intervals.
Every point is an event taking place after one minute. However I am having a hard time trying to understand all the moving pieces:
the interval function on the highchart demo I referred updated every 1 second, I have made that 6000.
the dummy updating in the javascript just takes the latest time and appends it, is there supposed to be some delay introduced there?
the dummy initialization data in series has a for loop which again I could not understand. I understand that javascript produces a UNIX timestamp and its millisecond manipulation however the default code (again slightly modified from a highchart demo) runs from -9999 to 0 and multiples by a number.
I want to understand these parts and make sure that every time my x axis 'ticks' towards the right, I have a one minute gap and only one point on the graph.
PS: Please forgive any missing brackets, they might have been missed while posting the question, but I assure you that it isnt a problem.
Here is my code for series:
series: [{
type: 'spline',
name: 'Random data',
data: (function () {
// generate an array of random data
var data = [],
time = (new Date()).getTime(),
i;
for (i = -9999; i <= 0; i += 1) {
data.push([
time + i * 60000,
Math.round(Math.random() * 100) + 10
]);
}
return data;
}())
}]
Here is my code for the chart:
chart: {
events: {
load: function () {
// Set up the updating
var series = this.series[0];
setInterval(function () {
var x = (new Date()).getTime(), // current time
y = Math.round(Math.random() * 100) + 10
series.addPoint([x, y], true, true);
}, 6000);
}
}
}

As to your questions:
If you want to have 1 minute data interval, you need to use 60000 value (60 * 1000), 6000 milliseconds is 6 seconds.
Current date in the interval function is taking every 6000 milliseconds, which causes gaps in the data every 6000 milliseconds.
That data initialization depends on subtracting multiples of six seconds from the current timestamp:
data: (function() {
// generate an array of random data
var data = [],
time = (new Date()).getTime(),
i;
for (i = -9999; i <= 0; i += 1) {
if (i === -500) {
console.log(time, i, 60000); // 1560941909847 + (-500 * 60000)
console.log(time + i * 60000); // 1560911909847
} else if (i === -499) {
console.log(time, i, 60000); // 1560941909847 + (-499 * 60000)
console.log(time + i * 60000); // 1560911969847
} else if (i === 0) {
console.log(time, i, 60000); // 1560941909847 + (0 * 60000)
console.log(time + i * 60000); // 1560941909847 = actual time
}
data.push([
time + i * 60000,
Math.round(Math.random() * 100) + 10
]);
}
return data;
}())

Related

Hightcharts: Smooth zoom in/out distance

How to smoothly zoom in and out of the chart using buttons?
Below I gave the code approximation of the graph.
(If this is important: I have Data every second.)
var min = chart.xAxis[0].getExtremes().min,
max = chart.xAxis[0].getExtremes().max;
chart.xAxis[0].setExtremes((min + 12 * 2000),(max - 12 * 2000));
Zoom smoothness depends on the amount of rendered points on the chart. I have noticed that if dataGrouping is disabled and points amount is less than 250 animation works fine.
Demo: https://jsfiddle.net/BlackLabel/hj5Lyda7/
var chart = Highcharts.stockChart('container', {
chart: {
animation: true
},
title: {
text: 'AAPL Stock Price'
},
series: [{
name: 'AAPL',
data: data,
dataGrouping: {
enabled: false
}
}]
});
document.getElementById("btn").addEventListener('click', function() {
var min = chart.xAxis[0].getExtremes().min,
max = chart.xAxis[0].getExtremes().max;
chart.xAxis[0].setExtremes((min + 24 * 3600 * 1000), (max - 24 * 3600 * 1000), true, {
duration: 2000
}); //12 hrs on min and 12hrs on max, summarised it is one day.
})
I am afraid that for more points it is impossible to keep this smoothness and displayed range must be changed by using the rangeSelector feature.

Shifting Issue In Navigator Series in HighCharts

There is a peculiar issue i am facing when drawing live chart.
I am adding point to a series every 1 sec and shifting after 14 min.(Added shift condition (14 * 60 + 1)).
Navigator gets points from 1st series and shifts but becomes straight line beyond 14 min.
Navigator series data length also becomes 0.
But Navigator series option data displays right length.
Please find the image in below url
http://postimg.org/image/5xxxq65cn/
Could anyone provide any input on the same ?
function updateChart(data) {
var i, dateTime = new Date(data[0].TimeStamp), signalSeries, shift;
for (i = 0; i < data.length; i += 1) {
signalSeries = chart.get(data[i].Key);
if (signalSeries) {
shift = signalSeries.options.data.length > (14 * 60 + 1);
chart.get(data[i].Key).addPoint([dateTime.getTime(), data[i].Value], false, shift);
}
}
chart.redraw();
}
With Regards,
Tripati Patra

Creating highstock zoom-in/out button

I have the following problem - I'm trying to create highstock graphic with zoom-in/zoom-out buttons, but something is wrong with the zooming. When i press the button most of the times the chart zooms to the correct time interval, however, after I press the button a couple more times, the chart starts to behave weird - the animations aren't correct or it doesn't zoom or it zooms to the wrong interval.
This is the zooming function:
var xAxis = graphic.xAxis[0];
var minimum = xAxis.dataMin;
var maximum = xAxis.dataMax;
var newMin = 0;
var newMax = 0;
//when zooming out
newMin = xAxis.min - 360000;
newMax = xAxis.max + 360000;
//when zooming in
//newMin = xAxis.min - 360000;
//newMax = xAxis.max + 360000;
if (newMin < minimum)
newMin = minimum;
if (newMax > maximum)
newMax = maximum;
if (newMin > newMax) {
alert("min bigger than max");
}
console.log("newMin: " + newMin + " newMax: " + newMax);
xAxis.setExtremes(newMin, newMax);
Here's a fiddle: http://jsfiddle.net/E5kth/3/
jquery - 1.6.4
jquery mousewheel - 3.1.6
highstock - 1.3.7
Thanks in advance ;]
EDIT:
Here is a NEW video with better explanations of the problem: https://www.dropbox.com/s/5x1k5b0lbtqw81u/highstock_ordinal-false_bug_converted.avi
for better quality - download the video, dropbox streaming is with low quality.
I prepared simple example how it should be done, http://jsfiddle.net/3vB5B/. It get range from chart and then reduce range on 24 hours.
$('#btn').click(function(){
var min = chart.xAxis[0].getExtremes().min,
max = chart.xAxis[0].getExtremes().max;
chart.xAxis[0].setExtremes((min + 12 * 3600 * 1000),(max - 12 * 3600 * 1000)); //12 hrs on min and 12hrs on max, summarised it is one day.
});

How to create series and setup X and Y axis?

I have to make a series as shown in the image.
The Dates and the values are dynamically generating based on the user selection. The Time is in 24 hrs format. Please tell me how can i create the series for this. Also how to put the duration 1 hour for the time value.
Image for Reference:
In your series data you are using data: [Date.UTC(2012, 10, 01, 12,11,10)] you can simply change that to: data: [90 *60 * 1000] //For 90 Minute
Here is the LIVE DEMO
If you want to plot other series for other days then you should add categories in xAxies. for example for showing 3 days:
xAxis: {
categories: ['01/10/2012', '01/11/2012', '01/2/2012']
},
And in series-data use equal number of parameters as you have in your categories for 3 categories:
data: [ 50 *60 * 1000, 100 *60 * 1000, 50 *60 * 1000 ]
See the LIVE DEMO
Use formatter in tooltip to see a correct hour:minutes when you hover the series.
tooltip: {
formatter: function() {
var ms = this.y;
var x = ms / 1000;
var seconds = x % 60;
x = x / 60;
var minutes = x % 60;
x = x / 60;
var hours = parseInt(x % 24);
x = (x / 24);
var days = parseInt(x);
if(days == 0)
{
return '<b>' + this.series.name +'</b> ->' + this.x + '<br/>' + hours +':' + minutes;
} else {
return '<b>' + this.series.name +'</b><br/>' + days + ' Day ' + hours +':' + minutes;
}
}
},
See the LIVE DEMO

Parsing x-axis with D3 error for column chart

I'm new to D3 having problems parsing the x-axis for a positive and negative value bar chart, as seen here:http://bl.ocks.org/mbostock/2368837
Instead of showing the actual year, it is repeating '1970' which is when the time code starts counting. I think it might be an error where the year is not being converted to a string, but it doesn't seem to be a simple d3.timescale since bar charts require the ordinal axis.
var data = [
{"date":19990101,"change":123000},
{"date":19990102,"change":409000},
{"date":19990103,"change":108000},
{"date":19990104,"change":373000},
{"date":19990105,"change":213000},
{"date":19990106,"change":263000},
{"date":19990107,"change":293000},
{"date":19990108,"change":191000},
{"date":19990109,"change":203000},
{"date":19990110,"change":403000},
{"date":19990111,"change":291000},
{"date":19990112,"change":300000},
{"date":20000101,"change":233000},
{"date":20000102,"change":130000},
{"date":20000103,"change":471000},
{"date":20000104,"change":287000},
{"date":20000105,"change":225000},
{"date":20000106,"change":-46000},
{"date":20000107,"change":166000},
{"date":20000108,"change":2000},
{"date":20000109,"change":127000},
{"date":20000110,"change":-12000},
{"date":20000111,"change":223000},
{"date":20000112,"change":138000},
{"date":20010101,"change":-32000},
{"date":20010102,"change":69000},
{"date":20010103,"change":-29000},
{"date":20010104,"change":-281000},
{"date":20010105,"change":-41000},
{"date":20010106,"change":-126000},
{"date":20010107,"change":-122000},
{"date":20010108,"change":-156000},
{"date":20010109,"change":-244000},
{"date":20010110,"change":-327000},
{"date":20010111,"change":-296000},
{"date":20010112,"change":-172000},
{"date":20020101,"change":-143000},
{"date":20020102,"change":-135000},
{"date":20020103,"change":-22000},
{"date":20020104,"change":-83000},
{"date":20020105,"change":-6000},
{"date":20020106,"change":52000},
{"date":20020107,"change":-92000},
{"date":20020108,"change":-14000},
{"date":20020109,"change":-58000},
{"date":20020110,"change":124000},
{"date":20020111,"change":7000},
{"date":20020112,"change":-162000},
{"date":20030101,"change":89000},
{"date":20030102,"change":-158000},
{"date":20030103,"change":-215000},
{"date":20030104,"change":-51000},
{"date":20030105,"change":-10000},
{"date":20030106,"change":-3000},
{"date":20030107,"change":20000},
{"date":20030108,"change":-44000},
{"date":20030109,"change":105000},
{"date":20030110,"change":197000},
{"date":20030111,"change":13000},
{"date":20030112,"change":119000},
{"date":20040101,"change":159000},
{"date":20040102,"change":43000},
{"date":20040103,"change":333000},
{"date":20040104,"change":247000},
{"date":20040105,"change":306000},
{"date":20040106,"change":78000},
{"date":20040107,"change":37000},
{"date":20040108,"change":125000},
{"date":20040109,"change":155000},
{"date":20040110,"change":343000},
{"date":20040111,"change":65000},
{"date":20040112,"change":128000},
{"date":20050101,"change":130000},
{"date":20050102,"change":240000},
{"date":20050103,"change":135000},
{"date":20050104,"change":362000},
{"date":20050105,"change":168000},
{"date":20050106,"change":246000},
{"date":20050107,"change":372000},
{"date":20050108,"change":192000},
{"date":20050109,"change":65000},
{"date":20050110,"change":81000},
{"date":20050111,"change":335000},
{"date":20050112,"change":158000},
{"date":20060101,"change":274000},
{"date":20060102,"change":316000},
{"date":20060103,"change":280000},
{"date":20060104,"change":181000},
{"date":20060105,"change":21000},
{"date":20060106,"change":80000},
{"date":20060107,"change":210000},
{"date":20060108,"change":179000},
{"date":20060109,"change":159000},
{"date":20060110,"change":-3000},
{"date":20060111,"change":205000},
{"date":20060112,"change":169000},
{"date":20070101,"change":234000},
{"date":20070102,"change":90000},
{"date":20070103,"change":186000},
{"date":20070104,"change":76000},
{"date":20070105,"change":141000},
{"date":20070106,"change":80000},
{"date":20070107,"change":-35000},
{"date":20070108,"change":-24000},
{"date":20070109,"change":77000},
{"date":20070110,"change":86000},
{"date":20070111,"change":111000},
{"date":20070112,"change":93000},
{"date":20080101,"change":14000},
{"date":20080102,"change":-85000},
{"date":20080103,"change":-79000},
{"date":20080104,"change":-215000},
{"date":20080105,"change":-186000},
{"date":20080106,"change":-169000},
{"date":20080107,"change":-216000},
{"date":20080108,"change":-270000},
{"date":20080109,"change":-459000},
{"date":20080110,"change":-472000},
{"date":20080111,"change":-775000},
{"date":20080112,"change":-705000},
{"date":20090101,"change":-794000},
{"date":20090102,"change":-695000},
{"date":20090103,"change":-830000},
{"date":20090104,"change":-704000},
{"date":20090105,"change":-352000},
{"date":20090106,"change":-472000},
{"date":20090107,"change":-351000},
{"date":20090108,"change":-210000},
{"date":20090109,"change":-233000},
{"date":20090110,"change":-170000},
{"date":20090111,"change":-21000},
{"date":20090112,"change":-220000},
{"date":20100101,"change":-13000},
{"date":20100102,"change":-40000},
{"date":20100103,"change":154000},
{"date":20100104,"change":229000},
{"date":20100105,"change":521000},
{"date":20100106,"change":-130000},
{"date":20100107,"change":-86000},
{"date":20100108,"change":-37000},
{"date":20100109,"change":-43000},
{"date":20100110,"change":228000},
{"date":20100111,"change":144000},
{"date":20100112,"change":95000},
{"date":20110101,"change":69000},
{"date":20110102,"change":196000},
{"date":20110103,"change":205000},
{"date":20110104,"change":304000},
{"date":20110105,"change":115000},
{"date":20110106,"change":209000},
{"date":20110107,"change":78000},
{"date":20110108,"change":132000},
{"date":20110109,"change":225000},
{"date":20110110,"change":166000},
{"date":20110111,"change":174000},
{"date":20110112,"change":230000},
{"date":20120101,"change":311000},
{"date":20120102,"change":271000},
{"date":20120103,"change":205000},
{"date":20120104,"change":112000},
{"date":20120105,"change":125000},
{"date":20120106,"change":87000},
{"date":20120107,"change":153000},
{"date":20120108,"change":165000},
{"date":20120109,"change":138000},
{"date":20120110,"change":160000},
{"date":20120111,"change":247000},
{"date":20120112,"change":219000},
{"date":20130101,"change":148000},
{"date":20130102,"change":332000},
{"date":20130103,"change":142000},
{"date":20130104,"change":199000},
{"date":20130105,"change":195000},
{"date":20130106,"change":195000}
];
var margin = {top: 34, right: 0, bottom: 30, left: 60},
width = 900;
height = 420 - margin.top - margin.bottom;
var parseDate = d3.time.format("%Y%d%m").parse;
formatValue = d3.format(",");
formatTime = d3.time.format("%Y");
var x = d3.scale.ordinal()
.rangeRoundBands([0, width], 0.2);
var y = d3.scale.linear()
.range([height, 0]);
var xAxis = d3.svg.axis()
.scale(x)
.tickPadding(10)
.ticks(20)
.orient("top")
.tickFormat(function(d) { return d3.time.format('%Y')(new Date(d)); });
// .tickFormat(d3.time.format("%Y"));
var yAxis = d3.svg.axis()
.scale(y)
.orient("left");
var svg = d3.select("#chart").append("svg")
.attr("width", width + margin.right)
.attr("height", height + margin.top + margin.bottom)
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")");
// });
x.domain(data.map(function(d) {
return +d.date;
}));
y.domain(d3.extent(data, function(d) {
return d.change;
})).nice();
// add grid lines
function make_X_axis() {
return d3.svg.axis()
.scale(xScale)
.orient("bottom")
.ticks(6);
}
svg.selectAll(".bar")
.data(data)
.enter().append("rect")
.attr("class", function(d) { return d.change < 0 ? "bar negative" : "bar positive"; })
.attr("y", function(d) {
if (d.change < 0) {
return y(0);
} else {
return y(d.change);
}
})
.attr("x", function(d) {
return x(d.change);
})
.attr("height", function(d) {
return Math.abs(y(d.change) - y(0));
})
.attr("width", x.rangeBand())
.on("mouseover", function(d) {
//Get this bar's x/y values, then augment for the tooltip
var xPosition = parseFloat(d3.select(this).attr("x")) + x.rangeBand() / 2;
var yPosition = parseFloat(d3.select(this).attr("y")) / 2 + height / 2;
//Update the tooltip position and value
d3.select("#tooltip")
.style("left", xPosition + "px")
.style("top", yPosition + "px")
.style("right", xPosition + "px")
.select("#value")
// .text(formatValue(d.change)) + formatTime(d.date);
.text(formatValue(d.change));
//Show the tooltip
d3.select("#tooltip").classed("hidden", false);
})
.on("mouseout", function() {
//Hide the tooltip
d3.select("#tooltip").classed("hidden", true);
});
// Update the inner dimensions.
var g = svg.select("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")");
// Regular x-axis
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis.orient("bottom").tickValues([1999, 20000101, 20010101, 20020101, 20030101, 20040101, 20050101, 20060101, 20070101, 20080101, 20090101, 20100101, 20110101, 20120101, 20130101]))
.style("text-anchor", "start");
svg.append("g")
.attr("class", "y axis")
.call(yAxis)
.append("text")
.attr("x", -25)
.attr("y", -25)
.style("text-anchor", "end")
.text("Jobs");
svg.append("g")
.attr("class", "grid")
.call(make_Y_axis()
.tickSize(-width, 0, 0)
.tickFormat(""));
// //Zero axis
svg.append("g")
.attr("transform", "translate(0," + Y0() + ")")
.call(xAxis.tickFormat("").tickSize(1));
// add grid lines
function make_X_axis() {
return d3.svg.axis()
.scale(x)
.orient("bottom")
.ticks(6);
}
function make_Y_axis() {
return d3.svg.axis()
.scale(y)
.orient("left")
.ticks(10);
}
function Y0() {
return y(0);
}
You need to fix your representation of dates. There are several common ways to represent dates in JavaScript:
As a number (e.g., 1375284578036) representing the number of milliseconds since UNIX epoch.
As an arbitrary string (e.g., "2013-07-31"); this is typically parsed with d3.time.format.
As a bonafide Date object (e.g., new Date(2013, 6, 31)).
In general, your strategy should be to get things into Date objects as quickly as possible, because this is the canonical representation in JavaScript. You should only use a number or a string to represent (“serialize”) dates in a data file, such as CSV or JSON. In sum, always represent dates as Date objects in-code, and convert strings or numbers to Date objects on load as necessary.
In your code, you appear to be using a number of the form YYYYMMDD (with the exception of the first tick value of your x-axis, which is YYYY). Because there are no leading zeroes in the years you are using (i.e., they are all four digits), it’s technically possible to represent a date this way and then coerce it to a string before parsing it with d3.time.format—but this is a bad idea. You should use a string to serialize your dates, rather than a number; only use a number for milliseconds since UNIX epoch.
Notice in your x-axis tick format you are saying new Date(d). This is taking one of the domain values (a number of the form YYYYMMDD) and then converting it to a Date object using the Date constructor. But when the Date constructor is passed a single number, it assumes this is milliseconds since epoch, which is why all of your dates are in the 1970s.
If you convert all your dates to Date objects first when the data is loaded, then the domain of your x-scale will be Date objects, and you won’t need to coerce to dates as part of formatting ticks. You can simply use d3.time.format("%Y") as your tick format.

Resources