If category axis label text is long or multiple words in a c3js chart, they are overlapping and makes it unreadable, is there any config or hack to fix this issue?
c3js category axis example
Copy and paste following code to reproduce this bug.
var chart = c3.generate({
data: {
columns: [
['data1',40, 30, 200, 100, 400, 150, 250, 50, 100, 250,67,190,48,123,76,54,254]
]
},
axis: {
rotated: true,
x: {
type: 'category',
categories: ['Travel and Hospitality','Life Science and Pharma', 'Saas and Cloud', 'Hi-tech Manufacturing', 'Software', 'Business Services', 'Govt/Public Sector', 'Energy', 'Manufacturing', 'Healthcare','Media','Internet','Retail','Biotech','Automobile','Consumer Goods','Financial Services']
}
}
});
I found the solution in the 'multiline' config under axis_x_tick as shown below:-
axis: {
rotated: true,
x: {
tick: {
multiline: false,
},
type: 'category',
}
}
Working example- multiline axis label disabled
Related
I am using the Javascript ECharts library for displaying some data in my Angular 2+ app. I see that all the examples have some configuration like the following:
{
xAxis: [
data: ['00:00', '01:15', '02:30', '03:45']
],
series: [
{ name: 'A', type: 'line', data: [300, 280, 250, 260] },
{ name: 'B', type: 'line', data: [200, 120, 700, 290] },
]
}
But my data does not always provide values for all the labels in the x axis. For example, I would need to fit these arrays of custom objects into the chart:
const series1 = [{ label: '00:00', value: 300 }, { label: '02:30', value: 120 }];
const series2 = [{ label: '03:45', value: 890} ];
Of course, I could manually insert null or empty values in all the series so that all of them provide a value for each label in the axis. But I believe there should be a more straightforward way to achieve this in ECharts, as it is quite simple in other chart libraries like Kendo Charts.
Assuming you are working with line chart, below is the solution, anyway it is not that different for other charts, just make sure your xAxis type is category
Your xAxis type should be set to category, and data should be something like this
xAxis: [
type: 'category'
data: [ {name: '00:00'}, ....]
]
your series data should look like this
//dimx , value
const series2 = [['03:45', 890]];
You can use the 'time' format to fit series with different lengths.
Even the series, in this way, can have different lengths.
const colors = ['#5470C6', '#EE6666'];
let option = {
color: colors,
xAxis: {
type: 'time',
splitNumber: 11,
axisLabel: {
rotate: 45,
formatter: { hour: '{hh} : {mm}' },
},
},
yAxis: {
type: 'value',
},
series: [
{
name: 'Precipitation(2015)',
type: 'line',
data: [
['2012-03-01T12:22:33.123', 2.2],
['2012-03-01T12:23:33.123', 5.6],
['2012-03-01T12:24:33.123', 7.9],
['2012-03-01T12:25:33.123', 9.0],
['2012-03-01T12:28:33.123', 7.9],
['2012-03-01T12:30:33.123', 9.0],
['2012-03-01T12:32:33.123', 26.4],
['2012-03-01T12:40:33.123', 28.7],
],
},
{
name: 'Precipitation(2016)',
type: 'line',
data: [
['2012-03-01T12:22:33.123', 2.2],
['2012-03-01T12:23:33.123', 5.6],
['2012-03-01T12:38:33.123', 26.4],
['2012-03-01T12:40:33.123', 28.7],
],
},
],
};
result
I'm putting the code to color the graphic in array, but it takes one color for the 3 columns, even having declared 3 colors for each column
options: {
chart: {
type: 'bar',
id: 'chart',
},
colors: ['#3366ff','#66ff66','#ff0000'],
dataLabels: {
enabled: false
},
series: [],
title: {
text: 'PRAZOS OS',
},
bar: {
columnWidth: '50%',
endingShape: 'rounded'
},
Data
this.$axios.get("/Operacional/GetRelatorio").then(res => {
this.prazos = res.data
this.$refs.chart1.updateSeries([{
name: 'PRAZOS OS',
data: [this.prazos.noPrazo, this.prazos.emDia, this.prazos.atrasadas ],
}])
})
how it looks
enter image description here
I declared in the code 3 colors for array, but only one color remains for the 3 columns
To achieve the effect you want, you need to set distributed: true in bar in plotOptions in your options.
Like this:
plotOptions: {
bar: {
distributed: true
}
}
Taken from Custom DataLabels Bar in the examples.
You can also find the description for distributed in the documentation.
distributed: Boolean
Turn this option to make the bars discrete. Each value indicates one bar per series.
Example:
var options = {
chart: {
type: 'bar',
id: 'chart',
},
colors: ['#3366ff', '#66ff66', '#ff0000'],
dataLabels: {
enabled: false
},
series: [{
data: [400, 430, 448, 470, 540, 580, 690, 1100, 1200, 1380]
}],
title: {
text: 'PRAZOS OS',
},
bar: {
columnWidth: '50%',
endingShape: 'rounded'
},
plotOptions: {
bar: {
distributed: true
}
}
};
var chart = new ApexCharts(document.querySelector("#chart"), options);
chart.render();
<script src="https://cdn.jsdelivr.net/npm/apexcharts"></script>
<div id="chart"></div>
I have a bar chart with a legend in ExtJS 6.0.2.
I need to update the colors of the bars and of the legend when the user does an action (clicking on a pie slice in my case).
Updating the color of the bars works as intended, but the legend doesn't. Here is an example of what I do right now :
chart.getLegendStore().data.items.forEach(function(x){
x.data.mark = 'rgb(255,255,255)';
});
The colors are correctly set, but they only update when I click on the legend item. I guess it's because ExtJS has no way to know that the underlying store has been modified. I tried going up the callstack with the debugger but I didn't find anything useful.
Is there a better way to do what I want, or/and how to make the legend update instanly ?
EDIT: If it helps, here is how I update the bars :
serie.setConfig("colors", newColors);
EDIT2 : And here is the full chart code :
Ext.define('QuoteBarChart', {
extend: 'Ext.chart.CartesianChart',
alias: 'widget.quotebarchart',
xtype: 'quotebarchart',
requires: [
'Ext.chart.axis.Category',
'Ext.chart.axis.Numeric',
'Ext.chart.series.Bar',
'Ext.chart.series.Line',
'Ext.chart.theme.Muted',
'Ext.chart.interactions.ItemHighlight'
],
flex: 2,
height: 600,
theme: 'Muted',
itemId: 'chartId',
store: {
type: 'quote'
},
insetPadding: {
top: 40,
bottom: 40,
left: 20,
right: 40
},
axes: [{
type: 'numeric',
position: 'left',
fields: ['won', 'lost', 'open'],
minimum: 0,
grid: true,
titleMargin: 20,
title: 'Offres'
}, {
type: 'category',
position: 'bottom',
label: {
rotate: {
degrees: 45
}
},
fields: ['month']
}
],
series: [{
type: 'bar',
axis: 'left',
xField: 'month',
itemId: 'barId',
yField: ['open','lost','won'],
title: ['Ouvertes', 'Perdues','Gagnées'],
stacked: true,
fullStack: true,
colors: [
'rgb(64, 145, 186)', 'rgb(151, 65, 68)','rgb(140, 166, 64)'
],
highlight: {
strokeStyle: 'red',
fillStyle: 'black'
},
tooltip: {
trackMouse: true,
scope: this,
renderer: function (toolTip, storeItem, item) {
var name = "";
switch(item.field) {
case 'won': name = "Gagnées"; break;
case 'lost': name = "Perdues"; break;
case 'open': name = "Ouvertes"; break;
}
toolTip.setHtml("");
}
}
}],
legend: {
docked: 'bottom',
listeners: {
itemclick: 'onLegendItemClick',
itemmouseenter: 'onLegendItemHover'
}
}
)};
Ok, instead of modify colors of the series and colors of the legend, you can modify all of them in the same time doing this
chart.setColors(['red','blue','green']);
chart.redraw();
So you need to set colors on chart and not on series, and modify the array on button click.
I have a simple c3js line chart w/3 different lines. When I "unselect" all 3 data sources, the x-axis tick values disappear. I was wondering if there was anyway to reverse this behavior? I'd like to show the x-axis tick values even when there is no data present.
The xaxis tick values are of a 'timeseries' type. Thanks!
Here is my c3 config for the line chart:
bindto: '#test',
data: {
x: 'date',
xFormat: '%m%d',
columns: [],
},
legend: {
position: 'bottom',
},
axis: {
y: {
tick: {
format: function (d) { return d + '%'; },
count: 5,
},
max: 100,
padding: {
top: 0,
bottom: 0,
},
},
x: {
type: 'timeseries',
tick: {
culling: false,
},
},
},
color: {
pattern: [testRateColor, firstRateColor, secRateColor],
},
Unfortunately this functionality is baked into c3.js and the only way to change this (aside from working purely from d3) is monkey patching. You will find the offender on line 6814 of c3.js:
tickExit = tick.exit().remove(),
If you change this to:
tickExit = function() {},
The ticks are no longer removed.
Trying to Style up the Bullet Graph to be exactly as Marketing desires. The desired Graph looks like:
How do you add the labels at the top of the bars?
I've tried to set the labels property from the Kendo Documentation:
labels:
{
visible: true,
format: "{0}",
font: "14px Arial",
},
Here is my script that isn't working:
$barChart = $("#bar-chart").empty();
$barChart.kendoChart({
theme: global.app.chartsTheme,
renderAs: "svg",
legend: {
position: "bottom"
},
seriesDefaults: {
type: "column"
},
series: [
{
type: "verticalBullet",
currentField: "score",
targetField: "average",
target: {
color: "#444",
dashType: "dot",
line: {
width: 1,
}
},
labels:
{
visible: true,
format: "{0}",
font: "14px Arial",
},
data: [
{
score: 93.7,
average: 65.2,
}, {
score: 80.2,
average: 22.2,
}, {
score: 60.8,
average: 35.2,
}, {
score: 82.1,
average: 45.2,
}, {
score: 74.2,
average: 55.2,
}
]
}
],
categoryAxis: {
labels: { rotation: -45 },
categories: ["Sales & Contracting", "Implementation & Training", "Functionality & Upgrades", "Service & Support", "General"],
line: {
visible: false
},
color: "#444",
axisCrossingValue: [0, 0, 100, 100]
},
tooltip: {
visible: false
}
}).data("kendoChart");
Any help would be greatly appreciated.
Because this is not a supported feature, any attempt to do this is by it's nature a hack. I had a look at kendo demo and noticed that there is a tooltip element with class k-tooltip that contains the total for a bar on mouseover. You should take a look into that mouseover to display the totals.
What you're attempting to do is possible. I've created an example on our Try Kendo UI site here: http://trykendoui.telerik.com/#jbristowe/aDIf/7
To recap, bullet charts don't support that type of label you need, and bar charts don't support the visual you need (the special line on the chart).
You could switch back to bar charts and write a custom visual. However, an easier way is to use a plotband on the value axis: https://docs.telerik.com/kendo-ui/api/javascript/dataviz/ui/chart/configuration/valueaxis.plotbands
<div id="chart"></div>
<script>
$("#chart").kendoChart({
valueAxis: {
plotBands: [
{ from: 1, to: 2, color: "red" }
]
},
series: [
{ data: [1, 2, 3] }
]
});
</script>
If you make a very narrow band, it will work pretty. It won't be dotted as in your reference image, and it will be behind the bar, which might be a problem... To go deeper, you would need a custom visual, and it's going to be involved: https://docs.telerik.com/kendo-ui/api/javascript/dataviz/ui/chart/configuration/series.visual