StackedAndGroupedColumn series value for both stack - highcharts

Hello in a stacked grouped column chart how is it possible to have values of one series for both stacks?
What i would like to achieve is Group the Stacks by Customer which is simple.
But in my case i have values of different commodities for both stacks.
I have created the following jsfiddle example which explains a little bit better the problem.
link to code
$(function () {
$('#container').highcharts({
chart: {
type: 'column'
},
title: {
text: 'Stacked Grouped'
},
xAxis: {
categories: ['Customer1', 'Customer2']
},
yAxis: {
allowDecimals: false,
min: 0,
title: {
text: 'Count'
}
},
tooltip: {
formatter: function() {
return '<b>'+ this.x +'</b><br/>'+
this.series.name +': '+ this.y +'<br/>'+
'Total: '+ this.point.stackTotal;
}
},
plotOptions: {
column: {
stacking: 'normal'
},
bar: {
dataLabels: {
enabled: true
}
}
},
series: [{
name: 'Iron Ore',
data: [5, 3],
stack: 'today',
}, {
name: 'Manetite',
data: [3, 4],
stack: 'yesterday'
},
{
name: 'Iron Ore',
data: [5, 3],
stack: 'today'
}, {
name: 'Manetite',
data: [3, 4],
stack: 'yesterday'
}]
});
});
As you can see the commodities are doubled in this way but i want them on both stacks.
Any help is much appreciated.
Thank you!

You can use x/y parameters
{
x: 0, //number of group
y: 3
}
http://jsfiddle.net/9Y64w/2/

Related

How to make yAxis stackLabels under yAxis in Highcharts?

I am using Stacked and grouped column to display data, I want to show the yAxis stackLabels and let it below yAxis as the picture shown below:
below is my core code and I have created a jsfiddle to show the result:
$(function () {
$('#container').highcharts({
chart: {
type: 'column'
},
title: {
text: 'Total fruit consumtion, grouped by gender'
},
xAxis: {
categories: ['Apples', 'Oranges', 'Pears', 'Grapes', 'Bananas'],
offset:30
},
yAxis: {
allowDecimals: false,
//offset:10,
title: {
text: 'Number of fruits'
},
stackLabels: {
enabled: true,
verticalAlign: 'bottom',
//y:30, //it will won't display labels if y is greater than 0
style: {
fontWeight: 'bold',
color: 'gray'
},
formatter: function() {
return this.stack;
}
}
},
tooltip: {
formatter: function () {
return '<b>' + this.x + '</b><br/>' +
this.series.name + ': ' + this.y + '<br/>' +
'Stack: ' + this.series.options.stack;
}
},
plotOptions: {
column: {
stacking: 'normal'
}
},
series: [{
name: 'John',
data: [5, 3, 4, 7, 2],
stack: 'male'
}, {
name: 'Joe',
data: [3, 4, 4, 2, 5],
stack: 'male'
}, {
name: 'Jane',
data: [2, 5, 6, 2, 1],
stack: 'female'
}, {
name: 'Janet',
data: [3, 0, 4, 4, 3],
stack: 'female'
}]
});
});
I found that if I set the value of y greater than 0 it will not show the stacklabels.
Can anyone help me, thanks a lot!
stackLabels: {
enabled: true,
verticalAlign: 'bottom',
y:30, //it will won't display labels if y is greater than 0
style: {
fontWeight: 'bold',
color: 'gray'
},
formatter: function() {
return this.stack;
}
}
You can simply use CSS (see https://www.highcharts.com/docs/chart-design-and-style/style-by-css):
.highcharts-stack-labels text {
transform: translate(0, 20px);
}
Your fiddle updated: https://jsfiddle.net/beaver71/jraw54c2/
By default It is as you say
I found that if I set the value of y greater than 0,it will not show the stacklabels
To have desired behavior, you have to do following things:
1>Add extra series with negative values in each stack.
series: [{
name: 'test',
data: [-1, -1, -1, -1, -1],
stack: 'male',
color: 'transparent', //transparent color
showInLegend: false, //hide legend
}, {
name: 'tests',
data: [-1, -1, -1, -1, -1],
stack: 'female',
color: 'transparent',
showInLegend: false,
}, {
name: 'John',
data: [5, 3, 4, 7, 2],
stack: 'male'
}, {
name: 'Joe',
data: [3, 4, 4, 2, 5],
stack: 'male'
}, {
name: 'Jane',
data: [2, 5, 6, 2, 1],
stack: 'female'
}, {
name: 'Janet',
data: [3, 0, 4, 4, 3],
stack: 'female'
}]
2> In stackLabel property of yAxis you have to hide positive value stack labels
formatter: function() {
if (this.isNegative) {
return this.stack;
}
}
3>yAxis values should start from 0 show hide negative values,
labels: {
formatter: function() {
console.log(this.value)
if (this.value > -1) {
return this.value
}
}
},
4>Similarly tooltip should not activate on negative values
tooltip: {
formatter: function() {
if (this.y > -1) {
return '<b>' + this.x + '</b><br/>' +
this.series.name + ': ' + this.y + '<br/>' +
'Stack: ' + this.series.options.stack;
} else {
return false;
}
}
},
Applying this output
$(function() {
$('#container').highcharts({
chart: {
type: 'column'
},
title: {
text: 'Total fruit consumtion, grouped by gender'
},
xAxis: {
categories: ['Apples', 'Oranges', 'Pears', 'Grapes', 'Bananas'],
//offset:30
},
yAxis: {
allowDecimals: false,
//offset:10,
labels: {
formatter: function() {
if (this.value > -1) {
return this.value
}
}
},
title: {
text: 'Number of fruits'
},
stackLabels: {
enabled: true,
verticalAlign: 'bottom',
y: 0,
style: {
fontWeight: 'bold',
color: 'gray'
},
formatter: function() {
if (this.isNegative) {
return this.stack;
}
}
}
},
tooltip: {
formatter: function() {
if (this.y > -1) {
return '<b>' + this.x + '</b><br/>' +
this.series.name + ': ' + this.y + '<br/>' +
'Stack: ' + this.series.options.stack;
} else {
return false;
}
}
},
plotOptions: {
column: {
stacking: 'normal'
}
},
series: [{
name: 'test',
data: [-1, -1, -1, -1, -1],
stack: 'male',
color: 'transparent',
showInLegend: false,
tooltip: {
pointFormat: ''
}
}, {
name: 'tests',
data: [-1, -1, -1, -1, -1],
stack: 'female',
color: 'transparent',
showInLegend: false,
tooltip: {
pointFormat: ''
}
}, {
name: 'John',
data: [5, 3, 4, 7, 2],
stack: 'male'
}, {
name: 'Joe',
data: [3, 4, 4, 2, 5],
stack: 'male'
}, {
name: 'Jane',
data: [2, 5, 6, 2, 1],
stack: 'female'
}, {
name: 'Janet',
data: [3, 0, 4, 4, 3],
stack: 'female'
}]
});
});
<script src="https://code.jquery.com/jquery-3.2.1.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; margin: 0 auto"></div>

highcharts- stacked bar, how can I make the chart cover the width 100%?

I have created a chart in jsfiddle which represents two values. id like the stacked bar chart to be adjusted so that it takes the whole width of the div. it should cover the background, like so.
http://jsfiddle.net/ftaran/jBHDM/4/
$(function () {
$('#container').highcharts({
chart: {
type: 'bar',
background:'yellow'
},
credits: {
enabled: false
},
title: {
text: null
},
xAxis: {
labels: {
enabled: false
}
},
yAxis: {
title: null,
labels: {
enabled: false
},
labels: {
enabled: false
}
},
tooltip: {
formatter: function () {
return '<b>' + this.series.name + ':</b> ' + this.y + '<br/>' + this.percentage.toFixed(2) + '%';
}
},
legend: {
enabled: false
},
plotOptions: {
series: {
stacking: 'normal'
}
},
series: [{
name: 'Fail',
color: 'red',
data: [5]
}, {
name: 'Success',
color: 'green',
data: [2]
}]
});
});
Try using this yAxis parameter:
yAxis: {
...
endOnTick: false,
...
},
Just complementing #wergeld's answer. If you still haven't gotten the result expected after applying his suggestion:
yAxis: {
max: totalOfSeriesData
}
Per example:
series: [
{
name: 'John',
data: [5],
color: 'red',
},
{
name: 'Jane',
data: [2],
},
{
name: 'Joe',
data: [3],
},
],
yAxis: {
max: 10, // 5 + 2 + 3 = 10
endOnTick: false,
}

How to make stacked column graph to show total data value on top

I want to show total of all stacks of column to display on top of each column below is the link how i want to get the chart.
http://jsfiddle.net/gh/get/jquery/1.9.1/highslide-software/highcharts.com/tree/master/samples/highcharts/demo/column-stacked/
Below is the code i am using.
$(function () {
$('#container').highcharts({
chart: {
type: 'column'
},
title: {
text: 'Total fruit consumtion, grouped by gender'
},
xAxis: {
categories: ['Apples', 'Oranges', 'Pears', 'Grapes', 'Bananas']
},
yAxis: {
allowDecimals: false,
min: 0,
title: {
text: 'Number of fruits'
}
},
tooltip: {
formatter: function() {
return '<b>'+ this.x +'</b><br/>'+
this.series.name +': '+ this.y +'<br/>'+
'Total: '+ this.point.stackTotal;
}
},
plotOptions: {
column: {
stacking: 'normal',
dataLabels: {
enabled: true,
color: (Highcharts.theme && Highcharts.theme.dataLabelsColor) || 'white'
}
}
},
series: [{
name: 'John',
data: [5, 3, 4, 7, 2],
stack: 'male'
}, {
name: 'Joe',
data: [3, 4, 4, 2, 5],
stack: 'male'
}, {
name: 'Jane',
data: [2, 5, 6, 2, 1],
stack: 'female'
}, {
name: 'Janet',
data: [3, 0, 4, 4, 3],
stack: 'female'
}]
});
});
You have to use stackLabels. You missed it in your code. You can find it in yAxis -> stackLabels
stackLabels: {
enabled: true,
style: {
fontWeight: 'bold',
color:'gray'
}
}
Here is how:
yAxis: {
allowDecimals: false,
min: 0,
title: {
text: 'Number of fruits'
},
stackLabels: {
enabled: true,
style: {
fontWeight: 'bold',
color:'gray'
}
}
},

Highcharts: legend of stacked chart

This is the chart I have for example to explain the question.
$(function () {
$('#container').highcharts({
chart: {
type: 'column'
},
title: {
text: 'Total fruit consumtion, grouped by gender'
},
xAxis: {
categories: ['Apples', 'Oranges', 'Pears', 'Grapes', 'Bananas']
},
yAxis: {
allowDecimals: false,
min: 0,
title: {
text: 'Number of fruits'
}
},
tooltip: {
formatter: function() {
return '<b>'+ this.x +'</b><br/>'+
this.series.name +': '+ this.y +'<br/>'+
'Total: '+ this.point.stackTotal;
}
},
plotOptions: {
column: {
stacking: 'normal'
}
},
series: [{
name: 'John',
data: [5, 3, 4, 7, 2],
stack: 'male'
}, {
name: 'Joe',
data: [3, 4, 4, 2, 5],
stack: 'male'
}, {
name: 'Jane',
data: [2, 5, 6, 2, 1],
stack: 'female'
}, {
name: 'Janet',
data: [3, 0, 4, 4, 3],
stack: 'female'
}]
});
});
We have series names in the legend. And chart is stacked with grouped columns.
we have stacked them in male and female categories.
Is there any way to get Male and Female in the legends? so that we can see only male food consumption or female food consumption at a time.
You can refer fiddle as here - jsfiddle.net/bLZHd/
Thanks
You can use labelFormatter to replace item name with stack name. Two series shoud be hidden in legend (showInLegend) paramter. Then only what you need is catching legendItemClick and iterate for checking serie stack name.
legendItemClick: function () {
var chart = this.chart,
key = this.options.stack;
$.each(this.chart.series,function(i,serie){
if(serie.options.stack === key) {
if(serie.visible)
serie.hide();
else
serie.show();
}
});
return false;
}
http://api.highcharts.com/highcharts#legend.labelFormatter
Do you really need to switch by legends?
I would recommend you that kind of issue, that switch by spans: http://jsfiddle.net/bLZHd/1/
All you need is:
$.each(chart.series, function (k, v) {
if (v.options.stack == elemId) { //elemId is the string to compare
chart.series[k].show();
} else {
chart.series[k].hide();
}
});

Sort series per category

I have a chart that looks like this:
http://jsfiddle.net/rtGFm/37/
I would like to have a "sort" button that sorts high to low each category, putting the columns in a different order for each category. Is this possible with HighCharts?
var chart;
$(document).ready(function() {
chart = new Highcharts.Chart({
chart: {
renderTo: 'container',
type: 'column'
},
title: {
text: ''
},
subtitle: {
text: ''
},
xAxis: {
categories: [
'foreclosures',
'nuisances',
'distance from city center'
]
},
yAxis: {
min: 0,
title: {
text: ''
}
},
tooltip: {
formatter: function() {
return ''+
this.x +': '+ this.y +' mm';
}
},
plotOptions: {
column: {
pointPadding: 0.2,
borderWidth: 0
}
},
series: [{
name: 'Alger Heights',
data: [49.9, 71.5, 50]
}, {
name: 'Shawmut Hills',
data: [83.6, 78.8, 67]
}, {
name: 'Baxter',
data: [48.9, 38.8, 100]
}, {
name: 'Midtown',
data: [42.4, 33.2, 80]
}, {
type: 'scatter',
data: [55,60,70],
marker: {
symbol: 'square',
lineColor: '#FFFFFF',
lineWidth: 1,
radius: 8
},
name: 'Average'
}]
});
});
I had the same problem :) highcharts still does not provide any solution for this problem, but it is flexibel enough so that you can sort anyway - just by javascript.
Put your data in a separate value:
var dataMain = [{name:"test1",data:5}, {name:"test1",data:1},{name:"test1",data:2}]
In series you can just add a function which sorts your data:
series: (function(){
for(var i = 0;i<dataMain.length;i++){
dataMain[i].data = dataMain[i].data.sort(function(a,b){
return a[0] - b[0] ;
})
return dataMain;
}
Hope I got everything wright.
Got it to work, I believe. Trick is to add each column in correct order as a new serie with same type (column), reuse colors and hide legend...
Very hackish, the JS code to sort like 8 categories independently will be ugly but the result looks fine.
Edit: Updated fiddle, I see the spacing between the categories grows with series, doesn't look supernice.
My jsfiddle is here
$(function () {
$('#container').highcharts({
chart: {
inverted: true
},
title: {
text: 'Series sorted in within categories'
},
xAxis: {
categories: ['January']
},
series: [{
type: 'column',
name: 'Stockholm',
data: [{x:0, y:95, color: Highcharts.getOptions().colors[0]}]
}, {
type: 'column',
name: 'Göteborg',
data: [{x:0, y:80, color: Highcharts.getOptions().colors[1]}]
}, {
type: 'column',
name: 'Göteborg',
data: [{x: 1, name: 'February', y: 98, color: Highcharts.getOptions().colors[1] // VGR's color
}],
showInLegend: false,
dataLabels: {
enabled: false
}
}, {
type: 'column',
name: 'Stockholm',
data: [{x: 1, name: 'February', y: 80, color: Highcharts.getOptions().colors[0] // VGR's color
}],
showInLegend: false,
dataLabels: {
enabled: false
}
}]
});
});
br,
Jens
I think this can be done,
this may look like a little work around.
since we have a limited number of columns i mean 4 in the given example.
if we have arrays with sorting done with respect to each series then we can handle them.
on button click we can update the chart with new set of data as well as category array.
May be there is no solution from the APi.
According to me this is a possible approach.
Thanks,

Resources