Related
I'm using Highcharts to generate dynamic charts.
I have a monthly data comparison, however, I would like to know if it is possible to keep only one subtitle name.
To understand better I'm putting down my code.
You may notice that the legend has two names "Fumularios", this is due to the comparison I am doing, however, visually I would like it to display only one name, the second is not necessary to show, because the colors already indicate the information of the data.
chart = new Highcharts.Chart({
"chart": {
"renderTo": "container_5c6d32c33fee6",
"type": "column"
},
"title": {
"text": "Total por Capta\u00e7\u00f5es - Convers\u00f5es (Formul\u00e1rio|Chatbot|Whatsapp)"
},
"colors": ["#65c07f", "#1d6c3f", "#f79969", "#e46a2b", "#fdc076", "#e4452b", "#004b76", "#003f23", "#b6740c", "#005a64", "#1b964e", "#83ccb0", "#24a1ae", "#ec9631", "#147bb6", "#ff7754", "#007b5a", "#6ecbd6", "#ba0d00", "#68a9dc"],
"xAxis": {
"categories": ["Fev", "Mar", "Abr", "Mai", "Jun", "Jul", "Ago", "Set", "Out", "Nov", "Dez", "Jan \u21e9-64.78%"]
},
"yAxis": {
"title": {
"text": "Quantidade"
},
"maxPadding": 0.01,
"stackLabels": {
"enabled": 1,
"style": {
"fontWeight": "bold",
"fontSize": "14px",
"color": "#000"
}
}
},
"legend": {
"align": "center",
"verticalAlign": "bottom",
"backgroundColor": (Highcharts.theme && Highcharts.theme.legendBackgroundColorSolid) || 'white',
"borderColor": "#CCC",
"borderWidth": 1,
"shadow": false
},
"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": 1,
"crop": 0,
"style": {
"fontSize": "14px"
},
"overflow": "justify",
"color": (Highcharts.theme && Highcharts.theme.dataLabelsColor) || 'white'
}
}
},
"series": [{
"name": "Formul\u00e1rio",
"data": [1391, 1573, 1943, 1816, 1393, 2213, 2311, 1722, 1822, 1691, 1505, 1878],
"color": "#1d6c3f",
"stack": "A"
}, {
"name": "Formul\u00e1rio",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 579],
"color": "#1d6c3f",
"stack": "B"
}, {
"name": "Chatbot",
"data": [628, 498, 689, 512, 511, 505, 501, 510, 623, 699, 665, 669],
"color": "#68a9dc",
"stack": "A"
}, {
"name": "Chatbot",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 285],
"color": "#68a9dc",
"stack": "B"
}, {
"name": "Whatsapp",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 9, 90, 96, 0],
"color": "#65c07f",
"stack": "A"
}, {
"name": "Whatsapp",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 33],
"color": "#65c07f",
"stack": "B"
}]
});
You can achieve it by setting series.column.showInLegend = false on duplicated series. Check demo and code posted below.
Code:
chart = new Highcharts.Chart({
"chart": {
"renderTo": "container",
"type": "column"
},
"title": {
"text": "Total por Capta\u00e7\u00f5es - Convers\u00f5es (Formul\u00e1rio|Chatbot|Whatsapp)"
},
"colors": ["#65c07f", "#1d6c3f", "#f79969", "#e46a2b", "#fdc076", "#e4452b", "#004b76", "#003f23", "#b6740c", "#005a64", "#1b964e", "#83ccb0", "#24a1ae", "#ec9631", "#147bb6", "#ff7754", "#007b5a", "#6ecbd6", "#ba0d00", "#68a9dc"],
"xAxis": {
"categories": ["Fev", "Mar", "Abr", "Mai", "Jun", "Jul", "Ago", "Set", "Out", "Nov", "Dez", "Jan \u21e9-64.78%"]
},
"yAxis": {
"title": {
"text": "Quantidade"
},
"maxPadding": 0.01,
"stackLabels": {
"enabled": 1,
"style": {
"fontWeight": "bold",
"fontSize": "14px",
"color": "#000"
}
}
},
"legend": {
"align": "center",
"verticalAlign": "bottom",
"backgroundColor": (Highcharts.theme && Highcharts.theme.legendBackgroundColorSolid) || 'white',
"borderColor": "#CCC",
"borderWidth": 1,
"shadow": false
},
"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": 1,
"crop": 0,
"style": {
"fontSize": "14px"
},
"overflow": "justify",
"color": (Highcharts.theme && Highcharts.theme.dataLabelsColor) || 'white'
}
}
},
"series": [{
"name": "Formul\u00e1rio",
"data": [1391, 1573, 1943, 1816, 1393, 2213, 2311, 1722, 1822, 1691, 1505, 1878],
"color": "#1d6c3f",
"stack": "A"
}, {
"name": "Formul\u00e1rio",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 579],
"color": "#1d6c3f",
showInLegend: false,
"stack": "B"
}, {
"name": "Chatbot",
"data": [628, 498, 689, 512, 511, 505, 501, 510, 623, 699, 665, 669],
"color": "#68a9dc",
"stack": "A"
}, {
"name": "Chatbot",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 285],
"color": "#68a9dc",
showInLegend: false,
"stack": "B"
}, {
"name": "Whatsapp",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 9, 90, 96, 0],
"color": "#65c07f",
"stack": "A"
}, {
"name": "Whatsapp",
"data": [0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 33],
"color": "#65c07f",
showInLegend: false,
"stack": "B"
}]
});
<script src="https://code.highcharts.com/highcharts.js"></script>
<div id="container"></div>
Demo:
https://jsfiddle.net/BlackLabel/xfadnovy/1/
API reference:
https://api.highcharts.com/highcharts/series.column.showInLegend
I am trying to calculate % values for each series, what I managed to find is function like
formatter:function() {
var pcnt = (this.y / dataSum) * 100;
return Highcharts.numberFormat(pcnt) + '%';
}
But what confuses me is how can I make dynamically this function so it can be applied on every serie object that is provided
Emphasize on dataSum from function above.
I tried googling just in case highcharts provide already some solution that they have in their documentation but sadly I did not find anything, only thing I found is to concatenate already provided value with + '%', and that is far beyond real value of percentage of that specific serie
$(function() {
var chart = new Highcharts.Chart(
{
"meta": {
"drilldownEnabled": false
},
"chart": {
renderTo:"container",
"additionalData": {
"dateTime": false,
"datetype": "string",
"cliccable": true,
"drillable": false,
"drillableChart": false,
"isCockpit": true,
"categoryColumn": "city",
"categoryGroupBy": "",
"categoryGroupByNamens": "",
"categoryName": "city",
"categoryOrderColumn": "",
"categoryOrderType": "",
"categoryStacked": "",
"categoryStackedType": ""
},
"zoomType": "xy",
"panning": true,
"type": "column",
"options3d": {
"enabled": false,
"alpha": 25,
"beta": 15,
"depth": 50,
"viewDistance": 25
},
"backgroundColor": "#FFFFFF",
"heightDimType": "pixels",
"widthDimType": "pixels",
"plotBackgroundColor": null,
"plotBorderWidth": null,
"plotShadow": false,
"borderColor": "#FFFFFF",
"style": {
"backgroundColor": "#FFFFFF",
"fontFamily": "",
"fontWeight": "",
"fontSize": ""
},
"events": {}
},
"colors": [
"#7cb5ec",
"#434348",
"#90ed7d",
"#f7a35c",
"#8085e9",
"#f15c80",
"#e4d354",
"#2b908f",
"#f45b5b",
"#91e8e1"
],
"title": {
"text": "",
"style": {
"align": "",
"color": "",
"fontFamily": "",
"fontSize": "",
"fontWeight": ""
}
},
"legend": {
"itemDistance": 0,
"symbolPadding": 25,
"enabled": false
},
"xAxis": [
{
"plotBands": [
{
"label": {
"text": "",
"align": "center"
},
"color": "",
"from": 0,
"to": 0
}
],
"plotLines": [
{
"label": {
"text": "",
"align": "center"
},
"color": "",
"dashStyle": "",
"value": 0,
"width": 0
}
],
"type": "category",
"id": 0,
"title": {
"customTitle": false,
"text": "city",
"style": {}
},
"labels": {
"style": {
"color": "",
"fontFamily": "",
"fontSize": "",
"fontWeight": ""
},
"align": ""
}
}
],
"yAxis": [
{
"plotBands": [
{
"label": {
"text": "",
"align": "center"
},
"color": "",
"from": 0,
"to": 0
}
],
"plotLines": [
{
"label": {
"text": "",
"align": "center"
},
"color": "",
"dashStyle": "",
"value": 0,
"width": 0,
"zIndex": 1
}
],
"title": {
"text": "",
"customTitle": false,
"style": {
"color": "",
"fontFamily": "",
"fontWeight": "",
"fontSize": ""
}
},
"labels": {
"style": {
"color": "",
"fontFamily": "",
"fontSize": "",
"fontWeight": ""
},
"align": ""
},
"gridLineDashStyle": "$convertedTypeline",
"minorGridLineDashStyle": "$convertedMinorTpeline"
}
],
"series": [
{
"name": "total_children",
"dataLabels": {
"style": {
"color": "",
"fontFamily": "",
"fontWeight": "",
"fontSize": "",
"fontStyle": ""
},
"enabled": true,
"labelFormat": "{y:,.2f}"
},
"data": [
{
"drilldown": false,
"y": 271,
"name": "Pomona",
"datetype": "string"
},
{
"drilldown": false,
"y": 237,
"name": "Port Hammond",
"datetype": "string"
},
{
"drilldown": false,
"y": 205,
"name": "Port Orchard",
"datetype": "string"
},
{
"drilldown": false,
"y": 239,
"name": "Portland",
"datetype": "string"
},
{
"drilldown": false,
"y": 265,
"name": "Puyallup",
"datetype": "string"
},
],
"selected": true,
"tooltip": {
"valueDecimals": 2,
"scaleFactor": "empty",
"ttBackColor": "#FCFFC5"
},
"yAxis": 0
},
{
"name": "num_cars_owned",
"dataLabels": {
"style": {
"color": "",
"fontFamily": "",
"fontWeight": "",
"fontSize": "",
"fontStyle": ""
},
"enabled": true,
"labelFormat": "{y:,.2f}"
},
"data": [
{
"drilldown": false,
"y": 228,
"name": "Acapulco",
"datetype": "string"
},
{
"drilldown": false,
"y": 189,
"name": "Albany",
"datetype": "string"
},
{
"drilldown": false,
"y": 212,
"name": "Altadena",
"datetype": "string"
},
{
"drilldown": false,
"y": 219,
"name": "Anacortes",
"datetype": "string"
},
{
"drilldown": false,
"y": 231,
"name": "Arcadia",
"datetype": "string"
},
],
"selected": true,
"tooltip": {
"valueDecimals": 2,
"scaleFactor": "empty",
"ttBackColor": "#FCFFC5"
},
"yAxis": 0
}
],
"tooltip": {
"borderWidth": 0,
"borderRadius": 0,
"followTouchMove": false,
"followPointer": true,
"useHTML": true,
"backgroundColor": null,
"style": {
"padding": 0
}
},
"lang": {
"noData": ""
},
"noData": {
"style": {
"fontFamily": "",
"fontSize": "",
"color": ""
},
"position": {
"align": "center",
"verticalAlign": "middle"
}
},
"credits": {
"enabled": false
},
"plotOptions": {
"line": {
"marker": {
"symbol": "circle",
"lineWidth": 2
}
},
"series": {
"events": {},
"showCheckbox": true,
"cursor": "pointer",
"point": {
"events": {}
},
"dataLabels": {
"allowOverlap": true
},
"turboThreshold": 2000
}
}
}
);
});
Has anyone ever step onto solution that provides % values of series by any case ?
I am trying to calculate % of total_children, and % of num_cars_owned serie as they are separated objects of serie array.
You can find code example on link HERE http://jsfiddle.net/JeLrb/538/
You need to calculate dataSum value:
tooltip: {
...,
formatter: function() {
var dataSum = 0,
pcnt;
this.series.points.forEach(function(point) {
dataSum += point.y;
});
pcnt = (this.y / dataSum) * 100;
return Highcharts.numberFormat(pcnt) + '%';
}
}
Live demo: http://jsfiddle.net/BlackLabel/9tbynahj/
API Reference: https://api.highcharts.com/highcharts/tooltip
I am trying to return a highchart using AJAX from python bottle web service.
The code for the web service:
app.get('/getmyname/<jsonstring>')
def getmyname(db, jsonstring):
ret = """{
"chart": {
"type": "column"
},
"colors": [
"#00B7DE"
"#00539E"
],
"title": {
"text": "SALES - VOLUME"
},
"xAxis": {
"categories": [w,w,w,w,w,w,w,w,w,w,w,w,w,w],
"tickLength": "0"
},
"yAxis": {
"gridLineWidth": 0,
"minorGridLineWidth": 0,
"min": 0,
"title": {
"text": "K UNITS"
},
"labels": {
"enabled": false
},
"stackLabels": {
"enabled": true,
"style": {
"fontWeight": "bold",
"color": "(Highcharts.theme && Highcharts.theme.textColor) || 'gray'"
}
}
},
"credits": {
"enabled": false
},
"legend": {
"align": "right",
"x": "-30",
"verticalAlign": "top",
"y": "25",
"floating": true,
"backgroundColor": "(Highcharts.theme && Highcharts.theme.background2) || 'white'",
"borderColor": "#CCC",
"borderWidth": "1",
"shadow": true,
},
"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'",
"style": {
"textShadow": "0 0 3px black"
}
}
}
},
"series": [{
"name": "EST",
"data": [1, 4, 2, 6, 5, 8, 3, 6, 1, 2, 8, 3, 4],
}, {
"name": "VOD",
"data": [1, 4, 2, 6, 5, 8, 3, 6, 1, 2, 8, 3, 4]
}]
}""";
return json.dumps(ret)
Ajax Call:
$.ajax({
type: "GET",
url: "http://localhost:8080/getmyname/Query",
data: JSON.stringify(output),
contentType: "application/json; charset=utf-8",
dataType: "json",
success: function(data){
alert(data) ;
$('#container').highcharts(data);
},
error: function() {
alert("Something is not OK")
},
});
Though I can see the returned success alert(due to which I assume the Ajax call has returned required the data), the chart doesnot get populated. Not sure where I am going wrong. It would be great if somebody could point out the error.
Not sure how but changing the return method helped and also the some changes with the JSON format. Every (, ' "") matters. The corrected code is bleow:
#app.get('/getmyname/<jsonstring>')
def getmyname(db, jsonstring):
ret = """{
"chart": {
"type": "column"
},
"colors": [
"#00B7DE",
"#00539E"
],
"title": {
"text": "SALES - VOLUME"
},
"xAxis": {
"categories": ["Avg", "W", "W", "W", "W", "W", "W", "W", "W", "W", "W", "W", "W"],
"tickLength": 0
},
"yAxis": {
"gridLineWidth": 0,
"minorGridLineWidth": 0,
"min": 0,
"title": {
"text": "K EURO"
},
"labels": {
"enabled": false
},
"stackLabels": {
"enabled": true,
"style": {
"fontWeight": "bold",
"color": "gray"
}
}
},
"credits": {
"enabled": false
},
"legend": {
"align": "right",
"x": -30,
"verticalAlign": "top",
"y": 25,
"floating": true,
"backgroundColor": "white",
"borderColor": "#CCC",
"borderWidth": 1,
"shadow": true
},
"plotOptions": {
"column": {
"stacking": "normal",
"dataLabels": {
"enabled": true,
"color": "white",
"style": {
"textShadow": "0 0 3px black"
}
}
}
},
"series": [{
"name": "EST",
"data": [5, 3, 4, 7, 2, 4, 7, 3, 4, 1, 6, 2, 2]
}, {
"name": "VOD",
"data": [2, 2, 3, 2, 1, 3, 5, 3, 4, 7, 2, 4, 5]
}]
}"""
return json.loads(ret)
EDIT: I found this tool very helpful to debug JSON Format JSONFormtter
In highcharts, if there is no data found in the json value, I want to display an error message.
I used this code:
if(options.series[0].data.length == 0) {
alert('nodatafound');
} else {
var chart = new Highcharts.Chart(options);
}
This error appears:
TypeError: options.series[0].data is undefined
Data from JSON:
{
"chart": {
"renderTo": "container2",
"type": "column",
"marginRight": 10,
"marginBottom": 125
},
"title": {
"text": "",
"x": -20
},
"exporting": {
"enabled": false
},
"credits": {
"enabled": false
},
"subtitle": {
"text": "",
"x": -20
},
"xAxis": {
"labels": {
"rotation": -90,
"style": {
"fontSize": "10px"
}
}
},
"yAxis": {
"title": {
"text": ""
},
"plotLines": [{
"width": 1,
"color": "#808080"
}]
},
"tooltip": {
"shared": true
},
"legend": {
"align": "right",
"verticalAlign": "top",
"x": 0,
"y": 20,
"borderWidth": 0
},
"plotOptions": {
"column": {
"stacking": "normal",
"dataLabels": {
"enabled": false,
"color": "white"
}
}
},
"series": [{
"name": "2015-16-Q1"
}, {
"name": "2015-16-Q2"
}, {
"name": "2015-16-Q3"
}, {
"name": "2015-16-Q4"
}]
}
You can use no-data module which allows do that.
Ref: http://code.highcharts.com/modules/no-data-to-display.js
Example: http://jsfiddle.net/6o8o03fe/1/
I have this graph :
http://jsfiddle.net/ZKGZb/
$(document).ready(function() {
chart16 = new Highcharts.Chart({
"chart": {
"renderTo": "right-22",
"type": "column",
"width": 550,
"height": 400,
},
"xAxis": {
"categories": ["a very long long text ", "2another long text", "dda", "bbb", "aaa"],
"allowDecimals": "0",
"title": {
"text": "Hello world",
"offset": -350,
"align": "left",
"style": {
"color": "red"
}
},
"labels":{"useHtml": true }
},
"yAxis": {
"allowDecimals": false,
"labels": {
"overflow": "justify"
},
"title": {
"text": " "
},
"max": 20
},
"tooltip": {
"formatter": function() {
return this.series.name + this.y + "";
}
},
"title": {
"text": "a very long long text",
"margin": 50
},
"plotOptions": {
"column": {
"groupPadding": null,
"borderWidth": null,
"dataLabels": {
"enabled": null,
"color": null,
"style": {
"fontSize": null,
"font-weight": "bold"
},
"formatter": function() {
return this.series.name + this.y + "";
}
}
}
},
"exporting": {
"enabled": false
},
"credits": {
"enabled": false
},
"labels": {
"enabled": null
},
"legend": {
"enabled": 0,
"layout": "vertical",
"align": "top",
"verticalAlign": "top",
"y": 0,
"x": 0,
"floating": false,
"borderWidth": 1,
"backgroundColor": "#FFFFFF",
"shadow": true
},
"series": [{
"data": [{
"y": 19,
},
{
"y": 0,
"name": ""},
{
"y": 0,
"name": ""},
{
"y": 1,
"name": ""},
{
"y": 0,
"name": ""}],
"name": "Total: "}]
}, function(chartObj) {});
});
How do I make the categories labels look good? I need to be able to show the whole text of each category but I cannot find a way to do it .
I tried adding and using "useHtml" option but it didn't work
Thanks in advance
"xAxis": {
"categories": ["a very long long text ", "2another long text", "dda", "bbb", "aaa"],
"allowDecimals": "0",
"title": {
"text": "Hello world",
"offset": -350,
"align": "left",
"style": {
"color": "red"
}
},
Removing the "title=>offset" fixes it..