I have a highcharts graph which has both column and spline graph in it. The data sets are passed using handlebars variables. The code is like this
$(function () {
$('#container').highcharts({
title: {
text: '',
style: {
color: '#cc0000',
fontWeight: 'bold'
}
},
xAxis: {
categories: [{{{xaxisLabel}}}]
},
yAxis: [{ /* Primary yAxis */
labels: {
format: '{value}%',
style: {
color: '#cc0000'
}
},
title: {
text: 'Failure Percentage',
style: {
color: '#cc0000'
}
}
}, { /* Secondary yAxis */
title: {
text: 'Success Percentage',
style: {
color: '#009900'
}
},
max: 100,
labels: {
format: '{value} %',
style: {
color: '#009900'
}
},
opposite: true
}],
labels: {
items: [{
html: '',
style: {
left: '2px',
top: '18px',
color: (Highcharts.theme && Highcharts.theme.textColor) || 'black'
}
}]
},
credits: {
enabled: false
},
series: [{
type: 'column',
name: 'Success',
color: Highcharts.getOptions().colors[2],
yAxis: 1,
tooltip: {
valueSuffix: ' %'
},
data: [{{barSuccess}}]
}, {
type: 'spline',
name: 'Failure',
tooltip: {
valueSuffix: ' %'
},
data: [{{barFailure}}],
marker: {
lineWidth: 3,
lineColor: Highcharts.getOptions().colors[8],
fillColor: 'red'
}
}]
});
});
Now i have two more data sets called as {{toolTipSuccess}} and {{toolTipFailure}}.
{{toolTipSuccess}} goes in the column chart and {{toolTipFailure}} goes in the spline chart.
I want the data in these two datasets to come as a tooltip in the respective graphs. I know this can be done if i pass the data in the (x,y,z) format in the graph, but i'll have to do a lot of code change to accommodate that which i am avoiding.
Does anyone know any roundabout to this problem?
The data in the variables is of this type:-
{{barSuccess}} = [100, 99, 99, 99 .........]
{{barFailure}} = [ 0, 0, 1, 0.3........]
{{toolTipSuccess}} = [363, 763, 762, 987, ........]
{toolTipFailure}} = [12, 3, 13, 8, .........]
Thanks in advance
You could define your own tooltip formatter and then use the position of the column data point in the input 'bar' data to retrieve and display the appropriate data from toolTipSuccess / toolTipFailure. Consider this snippet of a series.tooltip definition:
//... more series definition
tooltip: {
pointFormatter: function(){
return "Rainfall: " + this.y + ", success: " + successPoints[this.series.data.indexOf( this )] + "<br />";
}
}
//... more code
var successPoints = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
JSfiddle here:
http://jsfiddle.net/L2ncbenx/1/
(Apologies, this is a rough edit of an existing highcharts example)
As you can see, this uses the position of the highlighted point to find the position of the required data in the other dataset.
Related
I have included a Highcharts chart embed on my website. Now I would like to create many additional charts using other series data. However, I would like all of these additional charts have exactly the same styling and be the same type as my chart1. The only things I will have to change in each chart is the subtitle and series name. I can easily just copy my chart1 code and rename it chart2, chart3 etc. and this works fine. However, I would very much like to just replicate my chart1 for the other data series while only changing subtitles and series name for each data series (CHART1 SUBTITLE and CHART1 SERIESNAME).
I have tried different solutions but none worked so far. Below is the code I have made for my chart1.
chartOptions.chart1 = {
chart: {
type: 'column'
},
title: {
text: 'CHARTNAME',
style: {
fontFamily: 'Montserrat,serif',
spacingTop: 30,
fontSize: '22px'
}
},
subtitle: {
text: 'CHART1 SUBTITLE',
align: 'left',
x: 55,
style: {
fontFamily: 'Montserrat,serif',
spacingTop: 25,
color: "#000",
fontSize: '14px'
}
},
xAxis: {
categories: [],
labels: {
rotation: -20,
}
},
yAxis: {
title: {
text: 'TITLETEXT',
rotation: 270,
y: -30
},
},
series: [{
name: 'CHART1 SERIESNAME',
color: '#006699',
data: []
}],
tooltip: {
}
},
};
Below is the code I use to initialize the series data in chart1. Here I have added a 'chart2' and I essentially hoped it would somehow be able to initialize that in 'chart1' and somehow also changing the chart subtitle and series name.
$('chart').ready(function() {
var tableName = '<?php echo $tableName; ?>'
$.getJSON("../companychart/chartdataNew.php", {id: escape(tableName)}, function(json) {
chartOptions.chart1.xAxis.categories = json['XAXIS NAME']['data'];
chartOptions.chart1.series[0].data = json['SERIES 1']['data'];
chartOptions.chart2.xAxis.categories = json['XAXIS NAME']['data'];
chartOptions.chart2.series[0].data = json['SERIES 2']['data'];
});
You can use Highcharts.merge method to extend default options (used in each chart) by particular chart options (series, subtitle). Check the demo posted below.
HTML:
<script src="https://code.highcharts.com/highcharts.js"></script>
<div id="container1"></div>
<div id="container2"></div>
<div id="container3"></div>
JS:
var chart1 = {
subtitle: {
text: 'CHART1 SUBTITLE',
},
series: [{
name: 'CHART1 SERIESNAME',
color: '#006699',
data: [1, 2, 3, 4, 5]
}]
},
chart2 = {
subtitle: {
text: 'CHART2 SUBTITLE',
},
series: [{
name: 'CHART2 SERIESNAME',
color: '#0034ef',
data: [5, 1, 2, 6, 2]
}]
},
chart3 = {
subtitle: {
text: 'CHART3 SUBTITLE',
},
series: [{
name: 'CHART3 SERIESNAME',
color: '#23ee45',
data: [3, 5, 2, 3, 1]
}]
},
chartDefaultOptions;
chartDefaultOptions = {
chart: {
type: 'column'
},
title: {
text: 'CHARTNAME',
style: {
fontFamily: 'Montserrat,serif',
spacingTop: 30,
fontSize: '22px'
}
},
subtitle: {
align: 'left',
x: 55,
style: {
fontFamily: 'Montserrat,serif',
spacingTop: 25,
color: "#000",
fontSize: '14px'
}
},
xAxis: {
categories: [],
labels: {
rotation: -20,
}
},
yAxis: {
title: {
text: 'TITLETEXT',
rotation: 270,
y: -30
},
}
};
Highcharts.chart('container1', Highcharts.merge(chartDefaultOptions, chart1));
Highcharts.chart('container2', Highcharts.merge(chartDefaultOptions, chart2));
Highcharts.chart('container3', Highcharts.merge(chartDefaultOptions, chart3));
Demo:
https://jsfiddle.net/BlackLabel/7utogs95/
I have a weird question:
The series1 variable is an array of date-times, which are too long. Because of this, the chart cannot display correctly. However, if I change series1 to make it contain the values of series2. It will work correctly. Can you let me know what I should do?
Also, how can I get each value in series1 shown as a date? suppose it is a variable from flask {{series1}}. thank you.
$(function () {
var series1 = [1489298400000L, 1492923600000L, 1492318800000L, 1480226400000L, 1494133200000L, 1490504400000L, 1488088800000L, 1475384400000L, 1493528400000L, 1491109200000L, 1480831200000L, 1471755600000L]
var series2 = [1, 7, 2, 1, 4, 1, 1, 1, 4, 6, 1, 1]
var series3 = [102, 95, 110, 111, 81, 104, 99, 92, 90, 100, 103, 98]
var myChart =
Highcharts.chart('container', {
chart: {
zoomType: 'xy'
},
title: {
text: 'Average Monthly Temperature and Rainfall in Tokyo'
},
credits: {
text: 'Songhuiming',
href: 'http://www.songhuiming.com'
},
subtitle: {
text: 'Source: WorldClimate.com'
},
xAxis: [{
categories: series1,
crosshair: true
}],
yAxis: [{ // Primary yAxis
labels: {
format: '{value}°C',
style: {
color: Highcharts.getOptions().colors[1]
}
},
title: {
text: 'Temperature',
style: {
color: Highcharts.getOptions().colors[1]
}
}
}, { // Secondary yAxis
title: {
text: 'Rainfall',
style: {
color: Highcharts.getOptions().colors[0]
}
},
labels: {
format: '{value} mm',
style: {
color: Highcharts.getOptions().colors[0]
}
},
opposite: true
}],
tooltip: {
shared: true
},
legend: {
layout: 'vertical',
align: 'left',
x: 120,
verticalAlign: 'top',
y: 100,
floating: true,
backgroundColor: (Highcharts.theme && Highcharts.theme.legendBackgroundColor) || '#FFFFFF'
},
series: [{
name: 'Rainfall',
type: 'column',
yAxis: 1,
data: series2,
tooltip: {
valueSuffix: ' mm'
}
}, {
name: 'Temperature',
type: 'spline',
data: series3,
tooltip: {
valueSuffix: '°C'
}
}]
});
});
About suffix "L" on the end you can read here.
What you need at first to make all items in series1 array be a string, because as it now, you will have an error. Then remove "L" and convert to dates
let series = ['1489298400000L', '1492923600000L', '1492318800000L', '1480226400000L', '1494133200000L', '1490504400000L', '1488088800000L', '1475384400000L', '1493528400000L', '1491109200000L', '1480831200000L', '1471755600000L'];
let series1 = series.map((item) => {
let date = new Date(parseInt(item.replace("L", ""))));
return `${date.getMonth()} ${date.getFullYear()}`;
});
I am creating column chart using Highcharts library. I am trying to custom Column chart according my requirement but two things I am unable to do.
First, bottom border of the column chart and second is column background for all the series. Look at the image below, what I need to achieve.
What I have done so far is here: jsfiddle
jQuery(document).ready(function(jQuery) {
jQuery('#portlet-content').highcharts({
credits: {
enabled: false
},
exporting: {
enabled: false
},
chart: {
type: 'column'
},
title: {
text: 'Number of Applications'
},
subtitle: {
text: 'BY COUNTRY'
},
xAxis: {
visible: false
},
yAxis: {
visible: false
},
legend: {
enabled: true,
align: 'right',
verticalAlign: 'middle',
layout: 'vertical',
padding: 3,
itemMarginTop: 5,
itemMarginBottom: 5,
itemStyle: {
lineHeight: '14px'
},
symbolHeight: 12,
symbolWidth: 12,
symbolRadius: 6
},
tooltip: {
formatter: function() {
return '<b style="color:'+this.point.color+'">'+ this.y +'</b>';
},
useHTML: true,
borderWidth: 0,
style: {
padding: 0,
fontSize: '16px'
},
shadow: false
},
series: [
{
name: "United Kingdom",
color: '#32323A',
data: [
[294]
]
}, {
name: "USA",
color: '#EB4825',
data: [
[65]
]
}
, {
name: "United Arab Emirates",
color: '#F7CC1E',
data: [
[35]
]
}
, {
name: "India",
color: '#24C746',
data: [
[23]
]
}
, {
name: "Canada",
color: '#2587EC',
data: [
[18]
]
}
]
});
});
Note: I have modified my answer to better address the specific requests in the original poster's question.
Here's what I would suggest:
Create a stacked column chart, where one of the series is a "dummy" series with which the user can't interact. This will serve as your background.
Here's a quick fiddle I worked up based on the Highcharts stacked column demo: http://jsfiddle.net/brightmatrix/v97p3eam/
plotOptions: {
column: { stacking: 'percent' }
},
series: [
/* this is the "dummy" series
set the "showInLegend" and "enableMouseTracking" attributes
to "false" to prevent user interaction */
{ name: 'dummy data', data: [5, 3, 4, 7, 2], color:'gray',
showInLegend: false, enableMouseTracking: false },
/* here's the real data; set a unique color for each
set nulls for the columns where that color/data is not needed */
{ name: 'Series 1', color: 'red', data: [2,null,null,null,null] },
{ name: 'Series 2', color: 'orange', data: [null,2,null,null,null] },
{ name: 'Series 3', color: 'yellow', data: [null,null,2,null,null] },
{ name: 'Series 4', color: 'green', data: [null,null,null,2,null] },
{ name: 'Series 5', color: 'blue', data: [null,null,null,null,1] }
]
Please let me know if this is helpful for you!
I am working on this demo. Why is the plot options color not getting the bar colors from the Color options (two colors)? As you can see it is taking color from only one for both colors.
$(function () {
chart1 = new Highcharts.Chart({
chart: {
renderTo: 'container',
type: 'bar'
},
plotOptions: {
column: {
colorByPoint: true
},
series: {
pointWidth: 50
}
},
colors: [
'#D9844B',
'#3F4539'],
credits: {
enabled: false
},
title: {
text: 'Test',
style: {
color: '#2d2d2d',
fontWeight: 'normal',
fontSize: '11',
marginBottom: '30'
}
},
xAxis: {
categories: ['Ecology & Economics', 'Economics Only'],
},
yAxis: {
tickInterval: 50,
max: 300,
title: {
text: 'Number of ROR Facilities'
}
},
legend: {
enabled: false
},
tooltip: {
formatter: function () {
return this.x + ' <b> : ' + this.y + '</b>';
}
},
series: [{
data: [29.9, 71.5],
dataLabels: {
enabled: true,
color: '#2d2d2d',
align: 'right',
x: -40,
y: 0,
style: {
fontSize: '12px',
fontFamily: 'Verdana, sans-serif'
}
}
}]
});
});
I think the documentation is wrong. It says that colorByPoint is a bar/column option but you are correct it isn't working. Moving it to a series option and it does work:
plotOptions: {
series: {
pointWidth: 50,
colorByPoint: true
}
},
Updated fiddle.
Referring to #Mark answer, the Highcharts documentation is correct.
There is a difference between defining options in every series in Highcharts, especially bar and column series are different series.
You are using bar series (chart.type: 'bar'), but in plotOptions you are defining colorByPoint only for a column series which, obviously, does not even exist in your chart.
You have many solutions:
1) You can define colorByPoint inside a specific series options:
chart: {
type: 'bar'
},
series: [{
colorByPoint: true,
data: [4, 3, 5]
}]
2) you can define colorByPoint for all series:
chart: {
type: 'bar'
},
plotOptions: {
series: {
colorByPoint: true
}
},
series: [{
data: [4, 3, 5]
}]
3) You can define colorByPoint for all bar type series:
chart: {
type: 'bar'
},
plotOptions: {
bar: {
colorByPoint: true
}
},
series: [{
data: [4, 3, 5]
}]
4) You can use inverted column type series (which is actually a bar series):
chart: {
type: 'column',
inverted: true
},
plotOptions: {
column: {
colorByPoint: true
}
},
series: [{
data: [4, 3, 5]
}]
5) You can also define the color for each bar separately:
series: [{
type: 'bar',
data: [{
y: 4,
color: 'red'
}, {
y: 3,
color: 'blue'
}, {
y: 5,
color: 'green'
}]
}]
And even more. Above solution should be enough for you.
Remember, plotOptions.column will not work for chart.type: 'bar'.
I'm struggling to do something that I think ought to be simple in Highcharts. I want the background dark grey and all the axis labels, title, etc texts light gray.
I can almost accomplish this by adding a lot of "color" declarations, but ... that seems repetitive and I'm sure there's a better way.
$(function () {
$('#container').highcharts({
chart: {
type: 'line',
// WHY CAN't I SET A GLOBAL "COLOR" HERE?
backgroundColor: '#272b30'
},
title: {
text: "Title Title",
align: 'left',
style: {
// DEFINE IT ONCE FOR THE TITLE
color: '#99aabb'
}
},
legend: {
// DEFINE AGAIN FOR LEGEND BORDER
borderColor: '#99aabb',
// AND FOR LEGEND ITEMS
itemStyle: {
color: '#99aabb'
}
},
xAxis: {
categories: ["2016", "2017", "2018", "2019", "2020"]
},
yAxis: {
title: {
text: 'axis label',
style: {
// DEFINE ONE MORE FOR THE AXIS LABEL
color: '#99aabb'
}
}
},
series: [{
name: 'Series',
data: [61, 55, 67, 88, 59]
}, {
name: 'Other Series',
data: [20, 15, 17, 22, 28]
}, ]
});
});
I am confident that I'm missing something super obvious here!
You can color legend using itemStyle, for example:
legend: {
itemStyle: {
color: '#000000',
fontWeight: 'bold'
}
},
See docs Highchart Options Reference
You can define global variable, which will keep color, and then set theme with defined variable.
http://www.highcharts.com/demo/line-basic/grid
But you'll still have to explicitly theme each component to get the color from that variable.
You can actually do it programmatically... just a little function which will lighten base color for you:
function shadeColor(color, percent) {
var num = parseInt(color,16),
amt = Math.round(2.55 * percent),
R = (num >> 16) + amt,
G = (num >> 8 & 0x00FF) + amt,
B = (num & 0x0000FF) + amt;
return (0x1000000 + (R<255?R<1?0:R:255)*0x10000 + (G<255?G<1?0:G:255)*0x100 + (B<255?B<1?0:B:255)).toString(16).slice(1);
}
then set and use the base color as variable
var baseColor = '272b30'
now you can dynamically can generate your skin.
$(function () {
$('#container').highcharts({
chart: {
type: 'line',
// WHY CAN't I SET A GLOBAL "COLOR" HERE?
backgroundColor: '#' + baseColor
},
title: {
text: "Title Title",
align: 'left',
style: {
// DEFINE IT ONCE FOR THE TITLE
color: '#' + shadeColor(baseColor,70)
}
},
legend: {
// DEFINE AGAIN FOR LEGEND BORDER
borderColor: '#' + shadeColor(baseColor,70),
// AND FOR LEGEND ITEMS
itemStyle: {
color: '#' + shadeColor(baseColor,70)
}
},
xAxis: {
categories: ["2016", "2017", "2018", "2019", "2020"]
},
yAxis: {
title: {
text: 'axis label',
style: {
// DEFINE ONE MORE FOR THE AXIS LABEL
color: '#' + shadeColor(baseColor,70)
}
}
},
series: [{
name: 'Series',
data: [61, 55, 67, 88, 59]
}, {
name: 'Other Series',
data: [20, 15, 17, 22, 28]
}, ]
});
});