Formatting Tooltip Value on Series - highcharts

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
}
}
}

Related

Highcharts - Stack Graph Display Average of all values

I am using highcharts for statistical data displaying. I want to display , on the stack label , the average of all the values .
Below is what i am doing but i cant seem to get it right :
yAxis: {
min: 0,
title: {
text: 'Task'
},
stackLabels: {
style: {
color: 'black'
},
enabled: true,
formatter: function() {
return (this.axis.series[1].yData[this.x]).toPrecision(2) + '%';
}
}
},
The above only takes the last value on the stack and shows the percentage. For instance , if the last value is 50 , the above displays 50% as the stack value . I want to take an average of all the values. Any help would be appreciated.
If you want to show any stack's percentage mean if your stacked column has two stack A-5 and B-10 , then the % of B in column is 66% and % of A is 33%. If you want to show that use following in formatter function ( refer This Fiddle Link)
formatter: function() {
return (this.axis.series[1].yData[this.x] / this.total * 100).toPrecision(2) + '%';
}
Updating as per OP 's comment Refer Working fiddle here
Use following code : Make your data in a variable and calculate the sum
var seriesData = [{
name: 'Incomplete',
data: [1, 3, 4, 7, 20]
}, {
name: 'Complete',
data: [3, 4, 4, 2, 5]
}];
var total = 0;
$.each(seriesData,function(item){
$.each(seriesData[item].data,function() {
total += this;
});
});
And then use following in stacklabel formatter :
formatter: function() {
return ( this.total/ total * 100).toPrecision(2) + '%';
}
series:seriesData
hope it helps :)
This doesn't seem to be as easy as it should be.
I would accomplish this by pre-processing the data to generate an array of averages, and then referencing that array from the stackLabels formatter function.
Example, build the averages (assumes array 'data' with sub array for each series data values):
var sum = 0;
var averages = [];
var dataLen = data.length;
$.each(data[0], function(x, point) {
sum = 0;
for(var i = 0; i < dataLen; i++) {
sum += data[i][x];
}
averages.push(sum/dataLen);
})
And then in the formatter:
yAxis : {
stackLabels: {
enabled: true,
formatter: function() {
return Highcharts.numberFormat(averages[this.x],2);
}
}
}
Example:
http://jsfiddle.net/jlbriggs/vatdrecb/
If I could find a way to get a reliable count of the points in each stack, you could just use
return this.total/countOfPoints;
in the formatter without needing to build an array, but I can't seem to reliably get that count.

timeline yAxis format with minutes:seconds only

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.

onclick events for highstock rangeselecor and width is not applying

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

Highcharts, how can I start xAxis on an arbitrary time

I have a line chart with a datetime xAxis. I need to show ticks every 10 minutes, for that I have set tickInterval to 10*60*1000, my problem is that I need to show ticks every 10 minutes since the first date, for example, if my first point is displayed at 10:33, I need to show ticks at 10:33, 10:43, 10:53, etc, but what I have are ticks at 10:30, 10:40, 10:50 and so on, is there any way to do this?
Thanks!
It's not that straightforward because Highcharts automatically determines the labels to use when the x-axis is of the type 'datetime':
"In a datetime axis, the numbers are given in milliseconds, and tick marks are placed on appropriate values like full hours or days"
To set labels like '10:33' you need to create your own categories. Luckily these can simply be derived from your data and the desired time interval.
Here's a working example: http://jsfiddle.net/Rt7ZV/
We just take the given start date, interval and number of points and build an array of the categories to be used as the x-axis labels.
function getTimes(numTimes, interval) {
var ms = (new Date(2012, 02, 30, 10, 33)).getTime();
var times = [];
var startDate = new Date(ms);
times.push(startDate.getHours() + ":" + startDate.getMinutes());
for (var i = 1; i< numTimes; i++)
{
ms += interval;
var nextTime = (new Date()).setTime(ms);
var nextDate = new Date(nextTime);
times.push(nextDate.getHours() + ":" + pad(nextDate.getMinutes(), 2));
}
return times;
}
function pad(num, size) {
var s = num+"";
while (s.length < size) s = "0" + s;
return s;
}
var data = [1, 2, 3, 4, 5, 3, 2, 5, 7, 6, 4];
var interval = 10*60*1000
var timeCategories = getTimes(data.length, interval);
$(function () {
var chart;
$(document).ready(function() {
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
zoomType: 'x',
spacingRight: 20
},
title: {
text: 'Time series'
},
xAxis: {
categories: timeCategories,
title: {
text: null
},
startOnTick: false
},
yAxis: {
title: {
text: 'Exchange rate'
},
startOnTick: false,
showFirstLabel: true
},
tooltip: {
shared: true
},
legend: {
enabled: false
},
series: [{
type: 'line',
name: 'time series',
data: [
1, 2, 3, 4, 5, 3, 2, 5, 7, 6, 4
]
}]
});
});
});
I found the tickPositions property on xAxis, which isn't documented on highcharts, only on highstock, but seems to work fine on both. With this property you can specify which values you want to hace a tick for, and work perfectly for my problem.

Highstock step graph with min-max value

I have a series of json data in a highstock chart and I want to trim this data in values that are only 0 or 1: 0 if the data is 0, else 1. What I have to write in my option? My code now is this:
window.chart = new Highcharts.StockChart({
chart: {
renderTo: 'chart_div'
},
rangeSelector: {
selected: 1
},
title: {
text: 'prova'
},
{% if net.ntype == "ztc" and sens.type == 2 %}
// HERE I WANT TO DO AN OPTION TO TRIM VALUES
// TO 0 OR 1
{% end %}
series: [{
name: 'prova',
data: data,
step: true,
tooltip: {
valueDecimals: 2
}
}]
})
}
First loop in your Jason using $each()
Creat an array for example x
Then add if condition and push to x your date time and value either 0 or 1
Then your data :x;
This is just an idea if you can give us your code we can help you more

Resources