I want to chart (line) a swimmer competition times over several meets.
For the series data I use the php code :
$datetime1=date('Y, m, d', strtotime($performances['PERF_DATE']."-1 month"));
$datetime2='Date.UTC('.$datetime1.')';
$chrono=strtotime($performances['PERF_DATE']);
$data[] = "[$datetime2, $chrono]";
The xAxis timeline is for swim meet dates :
xAxis: {
type: 'datetime',
dateTimeLabelFormats: {
day: '%d/%m/%Y'}
The yAxis timeline is for the race times :
yAxis: {
title : { text :'chronos'},
type: 'datetime', //y-axis will be in milliseconds
dateTimeLabelFormats: { //force all formats to be minute:second
second: '%M:%S',
minute: '%M:%S'
},
min: 0
}
The xAxis timeline works perfectly.
But I have a format issue with the yAxis: I cannot display the times in mm:ss format.
I'm using mysql 5.6.4 and the race times (PERF_TIME) are stored in type time(2) column , i.e. including 2 fractions of a second.
Race dates (PERF_DATE) are stored in type datetime column.
For example, $performances['PERF_DATE'] in a php generated table will display : 00:01:33.91.
But in Highcharts, on the yAxis, the value will be 16.Jan, and on the plot label it will show the value 1371333600. I guess those are microseconds.
I assume I need to apply the correct time format function on $chrono=strtotime($performances['PERF_DATE']);
Can someone help me with this ?
Thanks a lot.
Could you show your data output? For me it works fine, see: http://jsfiddle.net/Fusher/pQ5EC/12/ Make sure, your y-values are timestamps in milliseconds too.
$('#container').highcharts({
chart: {
type: 'column'
},
xAxis: {
type: 'datetime'
},
yAxis: {
type: 'datetime'
},
series: [{
name: 'Temperatures',
pointStart: new Date().getTime(),
pointInterval: 24 * 3600 * 1000,
data: [1.5 * 60 * 1000,1.2 * 60 * 1000,2.5 * 60 * 1000,1.9 * 60 * 1000,],
}]
});
Apologies, I did respond earlier but my answer was not saved by the system --- apparently there's an 8 hour black-out period where the author cannot answer his own question.
I figured it out:
my times are formated hh:mm:ss.00 in mysql. I thgouht there was a function to easily convert mysql time format into milliseconds format, but apparently there's none.
So I manually "explode" the time into milliseconds, using the code:
extract($performances);
//converts date from 2012-01-10 (mysql date format) to the format Highcharts understands 2012, 1, 10
$datetime1=date('Y, m, d', strtotime($performances['PERF_DATE']."-1 month"));
//getting the date into the required format for pushing the Data into the Series
$datetime2='Date.UTC('.$datetime1.')';
// value is in format hh:mm:ss.00
$chrono1=$performances['PERF_TIME'];
// explodes value in mn, sec and microseconds
sscanf($chrono1,"%d:%d:%d.%d",$hours,$minutes,$seconds,$milliseconds);
// calculate total of milliseconds
$chrono=$seconds * 1000 + $minutes * 60 * 1000 + $milliseconds * 10;
$data[] = "[$datetime2, $chrono]";
Maybe there's a cleaner way? But I can now feed $data to Highcharts and it works perfectly.
Thanks.
Related
Good evening (CET),
I collect data, calculate a day sum, store the value in mySQL with a time stamp close to 24h of that day (like August 4, 23:59:30).
In a Highchart Column graph, the value will be shown on the August 5th. (You will see this be hovering over the bar, that the value doesn't fit to the xAxis.)
A working example is at http://jsfiddle.net/bg8yu3ft/
// data
var data = [ [1501624793000, 3389], [1501883993000, 4045], [1501970397000, 6572], [1502056798000, 5836], [1502143193000, 4736], [1502229588000, 6629], [1502315996000, 3981], [1502402391000, 4424] ]
// create the chart
Highcharts.stockChart('container', {
series: [{
type: 'column',
data: data,
}]
});
Looking forward to any advice to center the bar on the day it belongs to.
Assuming all your data is going to be in the same format (i.e. close to midnight) you can do it easily with pointplacement like this: fiddle. Depending on your timezone you might have to adjust the value a little.
Highcharts.stockChart('container', {
series: [{
type: 'column',
data: data,
pointPlacement: -1.2
}]
});
Another option would be to move the ticks, API.
You could change your x data to the closes full day then in the chart all will work fine and axis, point, tooltip will show x values as full days.
If you need to have precise day in the tooltip, then you could show it as an info. Demo: http://jsfiddle.net/BlackLabel/7uhdfcj4/
// data
var data = [
[1501624793000, 3389],
[1501883993000, 4045],
[1501970397000, 6572],
[1502056798000, 5836],
[1502143193000, 4736],
[1502229588000, 6629],
[1502315996000, 3981],
[1502402391000, 4424],
];
Highcharts.each(data, function(d, i) {
var realTime = d[0],
date = Highcharts.dateFormat('%Y:%m:%d:%H:%M:%S:%L', realTime).split(':'),
day = (+date[2]) + ((+date[3]) > 19 ? 1 : 0);
data[i].push(realTime);
data[i][0] = Date.UTC(+date[0], +date[1], day);
});
// create the chart
Highcharts.stockChart('container', {
series: [{
type: 'column',
data: data,
keys: ['x', 'y', 'realTime'],
tooltip: {
pointFormat: '{point.realTime: %Y.%m.%d %H:%M:%S}'
}
}]
});
<script src="https://code.jquery.com/jquery-3.1.1.min.js"></script>
<script src="https://code.highcharts.com/stock/highstock.js"></script>
<script src="https://code.highcharts.com/stock/modules/exporting.js"></script>
<div id="container" style="height: 400px"></div>
I would like to ask if somebody knows how to set X axis in Highcharts to time. My aplication is taking data from database and the frequency of the samples is 250ms. I want the X axis not to show counted values but something like time. I render 2500 values at once so that means 10 secs. The best would be to have on X axis and a mark there every 0.5 sec that means every 125 samples a mark. Like (0 samples = 0 sec);(125 samples = 0,5 sec);(500 samples = 1 sec);(725 samples = 1.5 sec)
Thank you for your opinions.....
chart () {
var options = {
chart: {
renderTo: 'services',
type: 'line',
animation: 'false'
},
plotOptions: {
series: {
animation: {
duration: 10000
}
}
},
series: [{marker: {
enabled: false
}}]
};
You can supply a custom label formatter. For example...
xAxis: {
labels: {
formatter: function () {
return (baseTime + (this.value / 500)) + " sec";
}
}
},
where baseTime is the time of the first data point.
Documentation for custom label formatter can be found at...
http://api.highcharts.com/highcharts#xAxis.labels.formatter
Is it possible not to connect points between years? See screenshot of graph below. I've been told it's misleading. My only solution so far is to create year end nulls for each sample year of each station. That's about 750 entries in SQL table. Seems crude. Can anyone come up with a more elegant and programmatic solution.
Data is retrieved via json from Postgresql.
Any suggestions or references would be greatly appreciated,
Gaps in series can be created through null value points.
Other option is to place data for each year in different series that will be linked together and have same color options and names.
Example: http://jsfiddle.net/kcccL6vw/1/
$(function () {
$('#container').highcharts({
xAxis: {
type: 'datetime'
},
series: [{
pointStart: Date.UTC(2013, 11, 30),
pointInterval: 3,
pointIntervalUnit: 'month',
data: [1,2,3,4,5],
name: 'Series',
id: 'S1',
color: '#fa0'
},{
pointStart: Date.UTC(2015, 0, 15),
pointInterval: 3,
pointIntervalUnit: 'month',
data: [1,2,3,4,5],
name: 'Series',
linkedTo: 'S1',
color: '#fa0'
}]
});
});
Use scatter plot instead of line chart if you dont want to connect points.
type:'scatter'
It's ugly but it works for now. I got the year range of existing data then appended records with all year end('12/31/20xx')null values to existing data. connectNulls: false prevented any points connecting to them.Then sorted the array by date which was unnecessarily difficult.
I know my JavaScript skills suck, so if anyone sees a way to tighten it up, please respond. I need all the help i can get. Here's my jsfiddle I was working from
Thanks to all for help and suggestions,
Michael
var cruiseDate = [];
for (var i = 0; i < data.length; i++) {
sampleDate = data[i][1];
thisDate = moment(sampleDate).format('MM/DD/YYYY');
cruiseDate.push([thisDate]);
}
var minDate = moment(cruiseDate[0], "MM/DD/YYYY").year();
var maxDate = moment(cruiseDate[cruiseDate.length - 1], "MM/DD/YYYY").year();
console.log('first year: ' + minDate + ' last year: ' + maxDate);
for (var i = minDate; i <= maxDate; i++) {
temp = null;
insertDate = moment('12/31/' + i).valueOf();
console.log('epoch: ' + insertDate + ' ' + moment(insertDate).format("MM/DD/YYYY"));
data.push(["year-end-null", insertDate, 0, temp, temp, temp, temp, temp, temp, temp, temp, temp, temp, temp, temp, temp])
}
function compare(a, b) { // from stackoverflow
var aDate = new Date(a[1]);
var bDate = new Date(b[1]);
if (aDate < bDate) return -1;
if (aDate > bDate) return 1;
return 0;
}
data.sort(compare);
I'm creating a multichart (line and column) and I need to format the tooltip value for only one of my series. The thing is: formatter doesn't seem to work inside series.
I have a point value like: 212575200
In tooltip it's being formatted into 2.125.752,00
But I need it to be formatted into: 2.1 M (for million)
(K for thousand, M for million, B for billion)
How can I format a tooltip value for only one of my series?
This is the code I'm using:
series : [{
name : ((tipoGrafico == 'line' || tipoGrafico == 'column')?'ult':' '),
data : dadosJson,
pointStart: dadosJson[0][0],
pointInterval: 24 * 3600 * 1000,
yAxis: 0, // Em qual grafico do eixo Y irĂ£o esses dados
tooltip: {
valueDecimals: CASAS_DECIMAIS,
}
},{
type: 'column',
name: nomeEstudo,
data: volume,
pointStart: dadosJson[0][0],
pointInterval: 24 * 3600 * 1000,
yAxis: 1,
tooltip: {
valueDecimals: ((nomeEstudo != "neg") ? CASAS_DECIMAIS : 0),
pointFormat: '<tspan style="color:{series.color}"> {series.name}: </tspan><tspan> ' + formatNumber(('{point.y}'/formataValores('{point.y}').divisor))+formataValores('{point.y}').letra + '</tspan>'
},
}],
Notice that I'm trying pointFormat, but It's returning a NaN from my other JS functions, because it can't figure out in time '{point.y}' is actually a Number, not a String.
In the formatter you can check which serie is displayed in the tooltip, then use condition (i.e based on the id of serie or name or index) and return content.
Following kind of function will help you:
tooltip:
{
formatter: function() {
for(var temp=0,tempLength = this.points.length;temp<tempLength; temp++)
{
//You will get the point value here by using following code
var Value = this.points[temp].y;
//Now you can apply any format to this value
}
}
}
I have an issue with x-axis values from the rangeselector in Highstock If I select 1d x-axis values should be hourly basis like 00.00 ,01.00,02.00....23.00. If I select 1w x-axis values should be jan-1,jan-2,jan-3 If I select 1m x-axis values are jan-1, jan-2 with interval of one week.Please find the below fiddle file of my code.
http://jsfiddle.net/t6uYV/
buttons[1].on('click', function (e) {
console.debug("hello onclick of the button ");
reset_all_buttons();
chart.rangeSelector.buttons[1].setState(2);
chart.xAxis[0].setTitle({
title: {
text: 'Date/time',
type: "datetime",
tickInterval : 24 * 3600 * 1000,
dateTimeLabelFormats: {
day: '%b %d'
},
labels: {
formatter: function() {
return Highcharts.dateFormat('%b %d', this.value);
}
}
}
});
chart.setSize(900,600,false);
chart.addSeries({
name : 'Energy Consumption',
id : 'EnergyConsumption_data',
yAxis: 1,
data : [[Date.UTC(2013,05,20),12],[Date.UTC(2013,05,21),14],[Date.UTC(2013,05,22),16],[Date.UTC(2013,05,23),22],[Date.UTC(2013,05,24),11],[Date.UTC(2013,05,25),10],[Date.UTC(2013,05,26),14]],
pointInterval: 24 * 3600 * 1000
});
chart.addSeries({
name : 'OutDoor Temperature',
id : 'OutDoorTemperature_data',
data : [[Date.UTC(2013,05,20),24],[Date.UTC(2013,05,21),14],[Date.UTC(2013,05,22),16],[Date.UTC(2013,05,23),22],[Date.UTC(2013,05,24),11],[Date.UTC(2013,05,25),10],[Date.UTC(2013,05,26),14]],
pointInterval: 24 * 3600 * 1000
});
});
width is not applying when click any of the rangeselector value.
Please provide me the solution for this . Struggling for this last one week.
Thanks in Advance,
Mahidhar
It is related with tickInterval, so you need to use setting tickInterval dynamically. To achieve this, you should use tickPositioner http://api.highcharts.com/highstock#xAxis.tickPositioner