Highcharts: Adding extra text to legend - javascript

Hi all I have a pie chart with the legend format like this:
{
enabled: true,
labelFormatter: function() {
return this.name + ' (Gesamt: ' + this.y + ' - ' + this.percentage.toFixed(1) + '%)' ;
},
borderWidth: 1
};
In some specific cases, I need to add an extra text which I defined as text = 'Extra' to this legend box. The rest legends I still keep them in the box. How can I do that ?
My jsfiddle code: http://jsfiddle.net/wjnnt28p/

You can add some if condition and display text like you want.
e.g.
labelFormatter: function() {
var p = this.name + ' (Gesamt: ' + this.y + ' - ' + this.percentage.toFixed(1) + '%)';
if (this.name == 'Chrome') { // Test the name
return p + ' Other Text for Chrome';
} else {
return p;
}
}
Full example :
$(function () {
$(document).ready(function () {
var text = 'Extra';
// Build the chart
$('#container').highcharts({
chart: {
plotBackgroundColor: null,
plotBorderWidth: null,
plotShadow: false,
type: 'pie'
},
title: {
text: 'Browser market shares January, 2015 to May, 2015'
},
tooltip: {
pointFormat: '{series.name}: <b>{point.percentage:.1f}%</b>'
},
plotOptions: {
pie: {
allowPointSelect: true,
cursor: 'pointer',
dataLabels: {
enabled: false
},
showInLegend: true
}
},
legend: {
enabled: true,
labelFormatter: function () {
var p = this.name + ' (Gesamt: ' + this.y + ' - ' + this.percentage.toFixed(1) + '%)';
if (this.name == 'Chrome') { // Test the name
return p + ' Other Text for Chrome';
} else {
return p;
}
},
borderWidth: 1
},
series: [{
name: 'Brands',
colorByPoint: true,
data: [{
name: 'Microsoft Internet Explorer',
y: 56.33
}, {
name: 'Chrome',
y: 24.03,
sliced: true,
selected: true
}, {
name: 'Firefox',
y: 10.38
}, {
name: 'Safari',
y: 4.77
}, {
name: 'Opera',
y: 0.91
}, {
name: 'Proprietary or Undetectable',
y: 0.2
}]
}]
});
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script src="https://code.highcharts.com/highcharts.js"></script>
<script src="https://code.highcharts.com/modules/exporting.js"></script>
<div id="container" style="min-width: 310px; height: 400px; max-width: 600px; margin: 0 auto"></div>

Update 2 fiddle with empty series,extra legend (Latest with datalabel enabled)
you are almost there, use this >> put a field like "extra" in your series data .
Updated
labelFormatter: function() {
if(this.extra !=null){
return this.name + ' ('+this.extra+': ' + this.y + ' - ' + this.percentage.toFixed(1) + '%)' ;
}else{
return this.name + '(' + this.y + ' - ' + this.percentage.toFixed(1) + '%)' ;
}}
See the fiddle here
put a if condition to get rid of undefined .
As per comment below
create a empty series with the name "Extra" OR do like following
labelFormatter: function() { if(this.y ==null) return "Extra Legend"; jsfiddle.net/wjnnt28p/4
the catch is , as you are formatting legend,if y don't have any value it will show undefined text. (Empty series case) for that write conditional logic there.
Second solution is to return "Extra label" but click of this legend won't have data,so legendclick could be override .

Related

Shows a single chart on Highcharts

Hello I'm having a problem with my code in Highcharts I already declared my series but it only shows 1 set of chart. All data were set on var dataStr, on how the data that being put, I use push on every data that is being passed. So I think the problem is the with my push?
var dataStr = [
{name: 'JOB-182', problemReportCount: 0, totalCost: 50000, lostHour: 0, lostValue: 0},
{name: 'JOB-185', problemReportCount: 0, totalCost: 3432.65, lostHour: 0, lostValue: 0},
{name: 'JOB-188', problemReportCount: 4, totalCost: 5000, lostHour: 0, lostValue: 0},
{name: 'JOB-189', problemReportCount: 0, totalCost: 1000, lostHour: 0, lostValue: 0}
];
var jRefs = [];
var prJRefs = [];
var prLostVals = [];
var prLostHours = [];
var totCosts = [];
for (var i = 0; i < dataStr.length; i++) {
var jName = '' + dataStr[i].name;
if (jName != '') {
jRefs.push(jName);
var prCount = dataStr[i].problemReportCount;
if (prCount > 0) {
prJRefs.push(jName);
prLostVals.push(dataStr[i].lostValue);
prLostHours.push(dataStr[i].lostHour);
totCosts.push(dataStr[i].totalCost);
}
}
}
var genGraph = function() {
$("#backButton").hide();
$('#prGraph4').highcharts({
chart: {
type: 'column',
plotBackgroundColor: '#F7F7F7'
},
title: {
text: 'Problem Report'
},
subtitle: {
text: 'Estimated Lost Values'
},
xAxis: {
alternateGridColor: '#fff',
categories: prJRefs
},
yAxis: {
min: 0,
title: {
text: 'Amount'
},
stackLabels: {
enabled: true,
style: {
fontWeight: 'bold'
}
}
},
plotOptions: {
column: {
stacking: 'normal',
}
},
tooltip: {
shared: true,
formatter: function() {
var s = '<b>' + this.x + '</b>';
$.each(this.points, function() {
var lostValue = this.y;
s += '<br/><span style=" + dbl + "color:' + this.series.color + ';" + dbl + ">\u25CF</span> ' + this.series.name + ': <b>£</b> ' + lostValue.toFixed(2);
});
return s;
}
},
series:[{
name: 'Total Costs',
data: totCosts,
color: '#2ecc71',
stack: 'total'
}, {
name: 'Estimated Lost Materials Value',
data: prLostVals,
color: '#e74c3c',
stack: 'lost'
}, {
name: 'Estimated Lost Hours Price',
data: prLostHours,
color: '#e67e22',
stack: 'lost'
}]
});
};
Any help would be so much appreciated. Thanks!
You have only one visible column because only one set of data fulfills this condition:
if (prCount > 0) {
prJRefs.push(jName);
prLostVals.push(dataStr[i].lostValue);
prLostHours.push(dataStr[i].lostHour);
totCosts.push(dataStr[i].totalCost);
}
In addition, all values from series: Estimated Lost Materials Value and Estimated Lost Hours Price are 0.
Live demo: http://jsfiddle.net/BlackLabel/vu9ahfk5/

Highcharts: Duplicate X-Axis Labels when dataGrouping is enabled (by Month)

I'm experiencing an issue when grouping data by month. I believe it to be a bug with the size of the dataset (January 1, 2018 - April 30, 2018) that I'm using but perhaps there is a better way of utilizing dataGrouping. The issue that I'm experiencing is that the X-Axis labels are not correct.
For a date range of January 1, 2018 to April 30, 2018:
Expected X-Axis to Be:
"Jan, '18" "Feb, '18" "Mar, '18" "Apr, '18"
Actual X-Axis:
"Jan, '18" "Feb, '18" "Mar, '18" "Mar, '18" "Apr, '18"
In my example (jsfiddle), I'm conditionally enabling dataGrouping on line 76: data.dataGrouping.enabled = (e.target.value === 'month');
Any insight would be greatly appreciated.
I think I found the solution: Use HighStocks and not HighCharts
I have an updated fiddle with the result. Summary:
Use HighScocks and just turn off some features to make it appear like a Highstock chart:
var chart = Highcharts.stockChart('myChart', {
chart: {
type: 'column',
width: null
},
xAxis: {
labels: {
enabled: true,
formatter: function() {
if (grouping === 'date') {
return Highcharts.dateFormat('%b %e, \'%y', this.value);
} else {
return Highcharts.dateFormat('%b, \'%y', this.value);
}
}
}
},
navigator: {
enabled: false
},
scrollbar: {
enabled: false
},
rangeSelector: {
enabled: false
},
yAxis: {
title: {
text: null
}
},
title: {
text: null
},
legend: {
enabled: false
},
plotOptions: {
series: {
color: 'white'
}
},
tooltip: {
backgroundColor: '#0E7BBA',
style: {
color: 'white'
},
formatter: function() {
var s = ''
if (grouping === 'date') {
s = '<b>' + Highcharts.dateFormat('%A, %b %e, %Y', this.x) + '</b>';
} else {
s = '<b>' + 'Date: ' + Highcharts.dateFormat('%A, %b %e, %Y', this.x) + '<br />' +
'<b>Month: ' + Highcharts.dateFormat('%B %Y', this.x) + '</b>';
}
s += '<br />' + this.points[0].series.name + ': ' + this.y;
return s;
}
},
credits: {
enabled: false
},
series: []
}
);

Highcharts bar with negative stack: how to show different tooltip for left and right

i am using highcharts bar with negative stack, problem is when i hover over the left side of the chart that is in red color it shows the correct disease name that is "TB Suspect" but when i hover over the blue bar it shows the same "TB Suspect" disease which is wrong, it should show "Otitis Media"
same problem for all other diseases
Here is the code
<script>
$(function () {
if($('#disease-bar').length > 0){
// Age categories
var categories_c = [<?=$comm_disease_title?$comm_disease_title:0;?>];
var categories_nc = [<?=$non_comm_disease_title?$non_comm_disease_title:0;?>];
$(document).ready(function () {
$('#disease-bar').highcharts({
colors: ['#dd4c39', '#00a9e9', '#c61a7e', '#bd8030', '#949293', '#075290', '#7db6ed', '#009451', '#c84433'],
chart: {
type: 'bar',
backgroundColor: null
},
title: {
text: 'Top Five Communicable & Non-communicable Diseases'
},
xAxis: [{
categories: categories_c,
reversed: false,
crosshair: true,
labels: {
step: 1
}
}, { // mirror axis on right side
opposite: true,
reversed: false,
categories: categories_nc,
linkedTo: 0,
labels: {
step: 1
}
}],
yAxis: {
title: {
text: null
},
labels: {
formatter: function() {
var s = Math.abs(this.value);
if (s.toFixed(0) >= 1000000) {
return s.toFixed(0) / 1000000 + 'M';
} else {
return s.toFixed(0) / 1000 + 'K';
}
}
}
},
plotOptions: {
series: {
cursor: 'pointer',
stacking: 'normal',
//point: {
events: {
click: function () {
//alert(this.name);return;
if(this.name=="Communicable"){
var url = 'disease.php<?=$next_url;?>&module=1';
}
else {
var url = 'disease.php<?=$next_url;?>&module=2';
}
//alert(url);
location.href = url;
}
,legendItemClick: function (event) {
//console.log(event.target.visible);
if(event.target.name=='Communicable'){
if(event.target.visible){this.chart.xAxis[0].update({
labels: {
enabled: false
}
});}
else {this.chart.xAxis[0].update({
labels: {
enabled: true
}
});}
}
else {
if(event.target.visible){this.chart.xAxis[1].update({
labels: {
enabled: false
}
});}
else {this.chart.xAxis[1].update({
labels: {
enabled: true
}
});}
}
//console.log(event.target.name);
//console.log(this.chart.xAxis[0]);
}
}
// }
}
},
tooltip: {{
formatter: function () {
return '<b>' + this.point.category + '</b><br/>' +
'Diseases: <b>' + Math.abs(this.point.y) +'</b>';
}
},
exporting: {
//enabled: false
},
credits: {
enabled: false
},
series: [{
name: 'Communicable',
data: [<?=$comm_disease_value?$comm_disease_value:0;?>]
}, {
name: 'Non-communicable',
data: [<?=$non_comm_disease_value?$non_comm_disease_value:0;?>]
}]
});
});
}
});
</script>
Here is the tooltip code which i am using
tooltip: {{
formatter: function () {
return '<b>' + this.point.category + '</b><br/>' +
'Diseases: <b>' + Math.abs(this.point.y) +'</b>';
}
},
JS Fiddle : https://jsfiddle.net/hamza9/h1nrn9nu/
I was able to get the correct category from the formatter:
formatter: function() {
var subCategoryLabel = this.series.chart.xAxis[this.series._i]
.categories[this.point.index];
return '<b>' + subCategoryLabel + '</b><br/>' +
'Diseases: <b>' + Math.abs(this.point.y) + '</b>';
}
You have to modify series data as array of object, wheredd is respective categories name and y is the value
series: [{
name: 'Communicable',
data: [{y:-1489599,dd:'Acute (Upper) Respiratory Infections'}, {y:-256548,dd:'Scabies'}, {y:-157531,dd:'Diarrhoea / Dysentery < 5 yrs'}, {y:-148696,dd:'Diarrhoea / Dysentery > 5 yrs'}, {y:-86283,dd:'Worm Infestations'}]
//url: 'disease.php?frequency=m&year=2017&month=1&quarter=&fatype=&disease_cat=comm'
}, {
name: 'Non-communicable',
data: [{y:399786,dd:'Fever due to other causes'}, {y:247500,dd:'Peptic Ulcer Diseases'}, {y:196653,dd:'Hypertension'}, {y:176866,dd:'Dental Caries'}, {y:169514,dd:'Diabetes Mellitus'}]
//url: 'disease.php?frequency=m&year=2017&month=1&quarter=&fatype=&disease_cat=noncomm'
}]
In your tooltip you can access it via the "point" attribute of the object passed in:
tooltip: {
formatter: function() {
return '<b>' + this.point.dd + '</b><br/>' +
'Diseases: <b>' + Math.abs(this.point.y) + '</b>';
}
},
Fiddle demo
Simply get rid of the linkedTo property from the second xAxis and link 'Non-Communicable' series to 1 xAxis.
API Reference:
http://api.highcharts.com/highcharts/series%3Cbar%3E.xAxis
Example:
https://jsfiddle.net/yqe0kunn/

Javascript Heavy Scripting Load(Lags the website)

I have the website that runs on javascript 1.7.1 and everytime i click a button that runs the Javascript method, the web load becomes far more heavier and continuously run the javascript up to the point that the site starts to lag.Here is an example of my JS method:
function makeGraph() {
var cityValue = [];
var cityValue2 = [];
var cityName = [];
var numIndex = [];
var tDelivery = [];
var tIdle = [];
var tRepair = [];
var tReady = [];
var barColor = "";
var cityString = "";
var chrt = document.getElementById("myCanvas");
var cityList = [];
cityList = arguments;
$.ajax({
url: '../api/values',
type: 'GET',
datatype: 'json',
success: function (data) {
for (var j = 1; j < cityList.length; j++)
{
cityString = cityString + "||" + " data[i].Names==\"" + cityList[j] + "\"";
}
cityString = "data[i].Names==\"" + cityList[0] + "\""+cityString;
for (var i = 0; i < data.length; i++) {
if (eval(cityString)) {
numIndex.push(i);
}
}
for (var k = 0; k < numIndex.length; k++) {
cityValue.push(data[numIndex[k]].ValuesDouble);
cityValue2.push(data[numIndex[k]].ValuesDouble2);
cityName.push(data[numIndex[k]].Names);
tDelivery.push(data[numIndex[k]].truckDelivery);
tIdle.push(data[numIndex[k]].truckIdle);
tRepair.push(data[numIndex[k]].truckRepair);
tReady.push(data[numIndex[k]].truckReady);
}
if (numIndex.length > 0) {
for (var h = 0; h < numIndex.length - 1; h++) {
barColor = barColor + "{y:" + cityValue2[h] + ",color:'" + setGraphColor(cityValue2[h], cityValue[h]) + "'}" + ",";
}
barColor = "[" + barColor + "{y:" + cityValue2[numIndex.length-1] + ",color:'" + setGraphColor(cityValue2[numIndex.length-1],cityValue[numIndex.length-1]) + "'}" + "]";
}
else {
barColor = "[" + barColor + "{y:" + data[numIndex[0]].ValuesDouble2 + ",color:'" + setGraphColor(data[numIndex[0]].ValuesDouble2, data[numIndex[0]].ValuesDouble) + "'}" + "]";
}
$(function () {
Highcharts.chart('container', {
chart: {
type: 'column',
backgroundColor: 'black'
},
tooltip: {
formatter: function () {
var s = '<b>' + this.x + '</b><br/><div>__________________________</div><hr>';
$.each(this.points, function () {
s += '<br/><span style="color:' + this.series.color + '">\u25CF</span><b>' + this.series.name + '</b>: ' + this.y;
});
return s;
},
shared: true
},
title: {
text: ''
},
xAxis: {
categories: cityName,
},
yAxis: {
min: 0,
tickInterval: 500,
title: {
text: ''
}
},
legend: {
verticalAlign: 'top',
reversed: false,
backgroundColor: 'lightgrey'
},
plotOptions: {
series: {
stacking: 'normal'
}
},
series: [{
name: 'Daily Schedule',
data: eval(barColor)
},
{
name: 'Actual Delivery',
data: cityValue,
color: '#33FF66'
},
{
name: '0%-69%',
//data: cityValue,
color: '#FF3366'
},
{
name: '70%-89%',
// data: cityValue,
color: '#FFCC33'
},
{
name: '90%-100%',
// data: cityValue,
color: '#003DF5'
}]
});
});
//////////////GRAPH 2 INFLUENCE///////////
$(function () {
Highcharts.chart('container2', {
chart: {
type: 'column',
backgroundColor: 'black'
},
tooltip: {
formatter: function () {
var s = '<b>' + this.x + '</b><br/><div>__________________________</div><hr>';
$.each(this.points, function () {
s += '<br/><span style="color:' + this.series.color + '">\u25CF</span><b>' + this.series.name + '</b>: ' + this.y;
});
return s;
},
shared: true
},
title: {
text: ''
},
xAxis: {
categories: cityName,
},
yAxis: {
min: 0,
max:80,
tickInterval: 20,
title: {
text: ''
}
},
legend: {
verticalAlign: 'top',
reversed: false,
backgroundColor: 'lightgrey'
},
plotOptions: {
series: {
stacking: 'normal'
}
},
series: [
{
name: 'Truck Delivery',
data: tDelivery,
color: '#33FF66'
},
{
name: 'Truck Idle',
data: tIdle,
color: '#FFCC33'
},
{
name: 'Truck Repair',
data: tRepair,
color: '#FF3366'
},
{
name: 'Truck Ready',
data: tReady,
color: '#003DF5'
}]
});
});
//////////////GRAPH 3 INFLUENCE///////////
$(function () {
Highcharts.chart('container3', {
chart: {
type: 'column',
backgroundColor: 'black'
},
tooltip: {
formatter: function () {
var s = '<b>' + this.x + '</b><br/><div>__________________________</div><hr>';
$.each(this.points, function () {
s += '<br/><span style="color:' + this.series.color + '">\u25CF</span><b>' + this.series.name + '</b>: ' + this.y;
});
return s;
},
shared: true
},
title: {
text: ''
},
xAxis: {
categories: cityName,
},
yAxis: {
min: 0,
tickInterval: 500,
title: {
text: ''
}
},
legend: {
verticalAlign: 'top',
reversed: false,
backgroundColor: 'lightgrey'
},
plotOptions: {
series: {
stacking: 'normal'
}
},
series: [
{
name: 'Staff On Duty',
data: cityValue,
color: '#33FF66'
},
{
name: 'Staff Present',
data: cityValue,
color: '#003DF5'
},
{
name: 'Staff Absent',
data: cityValue,
color: '#FF3366'
}]
});
});
}
})
}
I also have run a developer tool in IE 11 which shows me that it is indeed from the nonstop javascript loop. I was wondering if anyone could help me stop the JS loop so that it is not continuous.(I am also using SignalR and i dont know if this is one of the factors).Thanks in advance.
These are the header tags:
<meta name="viewport" content="width=device-width" />
<script src="Scripts/jquery-1.7.1.min.js"></script>
<script src="Scripts/jquery.signalR-2.2.1.min.js"></script>
<script src="Scripts/highcharts/4.2.0/highcharts.js"></script>
<script src="Scripts/Chart.min.js"></script>
<script src="Scripts/Chart.js"></script>
<script src="/signalr/hubs" type="text/javascript"></script>
<script type="text/javascript">
and yes, I am using highchart.js in this function and the button is that so i can refresh and sort the graph according to the buttons i clicked which in these cases are categories of cities.

Updating Y-Axis of Highcharts line graph causes vertical line

I am implementing a Highcharts line graph where I need to be able to drag points as well as update the y-axis of my chart. When I drag a point, and then update the y axis, a line is drawn from the original point to where I dragged: Here is a picture of what is happening.
I'd really prefer to not have all these vertical lines, for some reason it seems to be duplicating the points because I also get some triangles when testing. Does it just leave the line but not actually update the point? To update the graph I am simply doing:
planChart.yAxis[0].max = newValueY;
$('.actualPlansPlot').highcharts(planChart);
Any guidance would be much appreciated!
Here is the rest of the code:
var values = [...my values];
planChart = {
chart: {
renderTo: 'container',
animation: false
},
title: {
text: ''
},
xAxis: {
categories: startDates,
crosshair: true,
},
yAxis: [{ // Primary yAxis
labels: {
format: '{value}',
style: {
color: '#20709e'
}
},
title: {
text: 'title',
style: {
color: '#20709e'
}
},
}],
plotOptions: {
series: {
point: {
events: {
drag: function (e) {
// Returning false stops the drag and drops. Example:
/*
if (e.newY > 300) {
this.y = 300;
return false;
}
*/
$('#drag').html(
'Dragging <b>' + this.series.name + '</b>, <b>' + this.category + '</b> to <b>' + Highcharts.numberFormat(e.y, 2) + '</b>');
},
drop: function () {
$('#drop').html(
'In <b>' + this.series.options.id + '</b>, <b>' + this.category + '</b> was set to <b>' + Highcharts.numberFormat(this.y, 2) + '</b>');
}
}
},
stickyTracking: false
},
column: {
stacking: 'normal'
},
line: {
cursor: 'ns-resize'
}
},
tooltip: {
shared: true
},
credits: {
enabled: false
},
series: [{
name: 'title',
tooltip: {
pointFormat: '<span style="color:{point.color}">\u25CF</span> <b> {point.y} ' + trainingPlan.unit + '</b><br/>'
},
data: values,
//draggableX: true,
draggableY: true,
dragMinY: 0,
style: {
color: '#20709e'
}
}]
}
$('.actualPlansPlot').highcharts(planChart);
It is pretty close to the example of draggable points online
Updated
use following code :
$(document).on('click', '#updateYScale', function(e) {
var yValue = $('#newYValue')[0].value;
var chart = $('.actualPlansPlot').highcharts();
chart.yAxis[0].update({
max: yValue
});
chart.redraw();
});
See demo fiddle with your issue's fix

Categories

Resources