Test alignment 'Center' to the highchart legend content - javascript

I have been working on the highchart for a while, I have the chart like this
and i have placed the legend at the botton of the page and what i need to do is make the legend text align center like in the following image
I found few question of text alignment in highchart but does not suite my request. So I am unable to move further.
Fiddle http://jsfiddle.net/AbNpB/12/
Thanks in Advance!

It's possible to align each line using a custom code that will translate each legend item.
It's easier to resize output window in JSFiddle: http://jsfiddle.net/BlackLabel/a02czac2/
$(function() {
(function(H) {
H.wrap(H.Legend.prototype, 'render', function(proceed) {
// proceed
proceed.apply(this, [].slice.call(arguments, 1));
// custom
var legend = this,
centerRow = function(tab, w, x) {
var offset = (legend.legendWidth - (x + w)) / 2;
H.each(tab, function(elem) {
elem.legendGroup.attr({
translateX: elem.legendGroup.translateX + offset
});
});
}
if (legend.options.centerItemLines) {
var items = legend.allItems || [],
lastY = items[0] && items[0]._legendItemPos[1],
rowItems = [],
pos, prevX, prevW;
H.each(items, function(item) {
pos = item._legendItemPos;
if (pos[1] > lastY) {
lastY = pos[1];
centerRow(rowItems, prevW, prevX);
rowItems = [];
}
rowItems.push(item);
prevX = pos[0];
prevW = item.legendGroup.getBBox(true).width;
});
centerRow(rowItems, prevW, prevX); // last line
}
});
}(Highcharts))
var chart = new Highcharts.Chart({
chart: {
renderTo: 'container'
},
legend: {
itemStyle: {
width: 350
},
centerItemLines: true
},
series: [{
data: [6, 4, 2],
name: 'First'
}, {
data: [7, 3, 2],
name: 'Second a longer legend text and longer and longer and longer'
}, {
data: [9, 4, 8],
name: 'Third'
}, {
data: [1, 2, 6],
name: 'Fourth'
}, {
data: [4, 6, 4],
name: 'Fifth'
}]
});
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>
<script src="https://code.highcharts.com/highcharts.js"></script>
<div id="container" style="height: 400px;"></div>

Try to add this one:
legend: {
align: 'center',
verticalAlign: 'bottom',
x: 0,
y: 0
},
Hope this helps.

Related

Echart: How to set mark area to fill sections in xAxis

I have a problem with marking area: i need to be able to select a bar area based on xAxis, for example from 0 to 1, from 1 to 2, etc. But when i try to provide options for bar like
[{xAxis: 0, itemStyle: {color: red}},{xAxis: 1}]
it marks an area from a middle of xAxis area with an index of 0 to a middle of xAxis area with an index of 1. Is there a way to make it mark from start of an area to an end. Currently i managed to do so only with x option in pixels:
https://codesandbox.io/s/react-echart-markarea-ksj31?file=/src/index.js:714-726
Is there a better way to do it?
I can't imagine a method that would cover your requirements. It seems there is no such but nothing prevents to do it ourselves, see below.
When call function with join = true markedArea will calc as range from first to last.
calcMarkAreaByBarIndex(myChart, join = true, [4, 9])
When call function with join = false markedArea will calc for each bar.
calcMarkAreaByBarIndex(myChart, join = true, [4, 5, 6, 9])
var myChart = echarts.init(document.getElementById('main'));
var option = {
tooltip: {},
xAxis: {
data: [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11]
},
yAxis: {},
series: [
{
id: 'myBar',
name: 'Series',
type: 'bar',
data: [11, 11, 11, 11, 12, 13, 110, 123, 113, 134, 93, 109],
markArea: {
data: [
[{x: 184},{x: 216}],
[{x: 224},{x: 256}],
]
},
},
]
};
myChart.setOption(option);
function calcMarkAreaByBarIndex(chartInstance, join = false, barIdx){
var series = chartInstance.getModel().getSeriesByType('bar');
var seriesData = series.map((s, idx) => s.getData())[0];
var barNum = seriesData.count();
var barCoors = [];
var layout = idx => seriesData.getItemLayout(idx);
for(var i = 0; i < barNum; i++){
if(!barIdx.includes(i)) continue;
barCoors.push([
{ x: layout(i).x },
{ x: layout(i).x + layout(i).width },
])
}
if(join){
return [
[
{ x: barCoors[0][0].x },
{ x: barCoors[barCoors.length - 1][1].x }
]
]
} else {
return barCoors
}
}
var markedAreas = {
series: {
id: 'myBar',
markArea: {
data: calcMarkAreaByBarIndex(myChart, join = true, [4,9])
}
}
};
myChart.setOption(markedAreas);
<script src="https://cdn.jsdelivr.net/npm/echarts#4.7.0/dist/echarts.min.js"></script>
<div id="main" style="width: 600px;height:400px;"></div>
I found a solution, that worked for me:
Basically, you need to manually set yAxis's max props, add another xAxis, make it invisible, create a custom series with type 'bar' and set xAxisIndex to 1:
data: [maxYaxisValue,maxYaxisValue...], //length === xAxis.data.length
type: 'bar',
barWidth: '100%',
color: transparent,
xAxisIndex: 1,
And style a bar by index with background color and borderWidth
You can check the working example here
https://codesandbox.io/s/react-echart-markarea-m0mgq?file=/src/index.js

Synchronized tooltips positioning with line and horizontal bar charts

I'm having trouble aligning tooltip position on bar chart. Tooltip positioning works fine if all charts are line chart but not with bar/column charts. Could the Highcharts experts please help me with this issue?
http://jsfiddle.net/yhenwtsb/1/
var charts = [],
options1, options2;
function syncTooltip(container, p) {
var i = 0;
for (; i < charts.length; i++) {
if (container.id != charts[i].container.id) {
if (charts[i].tooltip.shared) {
charts[i].tooltip.refresh([charts[i].series[0].data[p]]);
} else {
charts[i].tooltip.refresh(charts[i].series[0].data[p]);
}
}
}
}
options1 = {
chart: {
type: "column",
inverted: true
},
plotOptions: {
series: {
point: {
events: {
mouseOver: function() {
syncTooltip(this.series.chart.container, this.x - 1);
}
}
}
}
},
xAxis: {
type: 'datetime'
}
};
options2 = {
plotOptions: {
series: {
point: {
events: {
mouseOver: function() {
syncTooltip(this.series.chart.container, this.x - 1);
}
}
}
}
},
xAxis: {
type: 'datetime'
}
};
charts[0] = new Highcharts.Chart($.extend(true, {}, options1, {
chart: {
renderTo: 'container1',
marginLeft: 40, // Keep all charts left aligned
},
tooltip: {
shared: true,
crosshairs: true,
valueDecimals: 2
},
series: [{
data: [
[1, 29.9],
[2, 71.5],
[3, 106.4]
]
}, {
data: [
[1, 59.9],
[2, 91.5],
[3, 136.4]
]
}]
}));
charts[1] = new Highcharts.Chart($.extend(true, {}, options2, {
chart: {
renderTo: 'container2',
marginLeft: 40, // Keep all charts left aligned
},
tooltip: {
shared: false
},
series: [{
data: [
[1, 29.9],
[2, 71.5],
[3, 106.4]
]
}]
}));
You can set tooltip.followPointer to true and add a small plugin to synchronize the second chart:
(function(H) {
H.wrap(H.Pointer.prototype, 'runPointActions', function(proceed, e, p) {
proceed.apply(this, Array.prototype.slice.call(arguments, 1));
var tooltipPos = this.chart.tooltip.now;
Highcharts.charts.forEach(function(chart) {
if (chart !== this.chart) {
chart.tooltip.updatePosition({
plotX: tooltipPos.x - chart.plotLeft,
plotY: tooltipPos.y - chart.plotTop
});
}
}, this);
});
}(Highcharts));
Live demo: http://jsfiddle.net/BlackLabel/2w9683gb/
API Reference: https://api.highcharts.com/highcharts/tooltip.followPointer
Docs: https://www.highcharts.com/docs/extending-highcharts

How to show more than one "dataMax" in Highcharts?

Currently, I'm showing a max point in the line chart. But I want to change dataMax to top 5 max value points in chart.How can I achieve this in Highcharts?
var defaultData = 'urlto.csv';
var urlInput = document.getElementById('fetchURL');
var pollingCheckbox = document.getElementById('enablePolling');
var pollingInput = document.getElementById('pollingTime');
function createChart() {
Highcharts.chart('closed5', {
chart: {
type: 'area',
zoomType: 'x'
},
plotOptions: {
series: {
dataLabels: {
enabled: true,
style: {},
formatter: function() {
if (this.y === this.series.dataMax) {
return this.y;
}
}
}
}
},
title: {
text: 'Chart for charting'
},
data: {
csvURL: urlInput.value,
enablePolling: pollingCheckbox.checked === true,
dataRefreshRate: parseInt(pollingInput.value, 10)
}
});
if (pollingInput.value < 1 || !pollingInput.value) {
pollingInput.value = 1;
}
}
urlInput.value = defaultData;
// We recreate instead of using chart update to make sure the loaded CSV
// and such is completely gone.
pollingCheckbox.onchange = urlInput.onchange = pollingInput.onchange = createChart;
// Create the chart
createChart();
As #ewolden rightly noticed, you can sort your data and show only the five highest values:
var data = [11, 22, 33, 44, 55, 66, 15, 25, 35, 45, 55, 65],
sortedData = data.slice().sort(function(a, b){
return b - a
});
Highcharts.chart('container', {
series: [{
data: data,
dataLabels: {
enabled: true,
formatter: function() {
if (sortedData.indexOf(this.y) < 5) {
return this.y;
}
}
}
}]
});
Live demo: http://jsfiddle.net/BlackLabel/xkf2w5tb/
API: https://api.highcharts.com/highmaps/series.mapbubble.dataLabels.formatter
As far as I know formatter callback is the way to format the data labels. If you want to show the top N points you should sort the data in a new array and pull the top 5 values. This is an example of how to clone and sort the array and extract the top 5 elements in the formatter call.
let data = [32, 10, 20, 99, 30, 54, 85, 56, 11, 26, 15, 45, 55, 65];
//Copy the array
let temp = data.slice();
// Sort the temp array in descending order
temp.sort((a, b) => b - a);
Highcharts.chart('closed5', {
chart: {
type: 'area',
zoomType: 'x'
},
title: {
text: 'Chart for charting'
},
series: [{
data: data,
dataLabels: {
enabled: true,
formatter: function() {
if (temp.indexOf(this.y) < 5) {
return this.y;
}
},
},
}]
});
<script src="https://code.highcharts.com/highcharts.js"></script>
<div id="closed5"></div>

Tooltip position is not working properly in D3 Funnel Chart

I am trying to do a d3 horizontal funnel chart.
Everything is working properly but tooltip position is not working properly it appears at a different location.
Here is my code:
const data = [
["L0", 10],
["L1", 0],
["L2", 5],
["L3", 10],
["L4", 3],
["L5", 10]
];
newdata = data.map(function (d,i){
var new_d = d
if (new_d[1] == 0){
new_d[1] = 0.50
}
return new_d
})
const options = {
chart: {
width: 200,
height: 450,
bottomWidth: 1 / 2,
bottomPinch: 1,
},
block: {
dynamicSlope: true,
dynamicHeight: true,
minHeight:50
},
label: {
enabled: true,
fontSize: '18px',
fill: '#fff',
/* format: '{l}: {f}' */
format: function(label, value) {
console.log('value', value);
if(value ==0.50){
var a=0;
return label+ ":" + a;
}else{
return label+ ":" + value;
}
}
},
tooltip: {
enabled: true,
format: '{l}: {f}'
}
};
const chart = new D3Funnel('#funnel');
chart.draw(newdata, options);
<script src="https://d3js.org/d3.v4.js"></script>
<script src="https://rawgit.com/jakezatecky/d3-funnel/master/dist/d3-funnel.min.js"></script>
<div id="funnel" style="transform: rotate(270deg);height: 539px;width:1px;margin-left:267px;"></div>
(from http://jsfiddle.net/3x265bLj/79/)

"Play with this data!" not showing up for my plotly.js plot

I was under the assumption the "Play with this data!" link was supposed the show up by default. Any ideas on why it may not appear? I am just working with a basic scatter plot.
Note that this code below is not standalone as is, it is just the excerpt that does the plotly work.
var xData = [];
var yData = [];
var h = results;
for(var k in h) {
var localdate = k;
var plotdate = moment(localdate).format('YYYY-MM-DD HH:mm:ss');
xData.push(plotdate);
if (currentPort === "t") {
yData.push(CtoF(h[k]));
} else {
yData.push(h[k]);
};
}
var plotdata = [
{
x: xData,
y: yData,
type: 'scatter',
mode: 'markers+lines',
line: {
'color': HELIUM_BLUE
},
marker: {
'symbol': 'circle',
'color': HELIUM_PINK,
'maxdisplayed': 50
}
}
];
var layout = {
title: currentData,
xaxis: {
'title': 'Date / Time'
},
yaxis: {
'title': title
}
};
Plotly.newPlot(plotHolder, plotdata, layout);
You would need to add {showLink: true} as the fourth argument (after layout). I guess the default value changed from true to false.
If you want to change the caption of the button, use {showLink: true, "linkText": "Play with this data"}
var xData = [1, 2, 3, 4, 5];
var yData = [10, 1, 25, 12, 9];
var plotdata = [
{
x: xData,
y: yData,
type: 'scatter',
mode: 'markers+lines',
}
];
var layout = {
title: 'Edit me',
xaxis: {
'title': 'x'
},
yaxis: {
'title': 'y'
}
};
Plotly.newPlot(plotHolder, plotdata, layout, {showLink: true, "linkText": "Play with this data"});
<script src="https://cdn.plot.ly/plotly-latest.min.js"></script>
<div id='plotHolder'>
</div>

Categories

Resources