Xrange chart height - javascript

How can I set the height of each bar in xrange charts? I don't want to specify the height of the whole chart, instead the height of each single bar.
This type of chart (as in the link):
http://jsfiddle.net/vqpjL3ns/1/
height of bar

You should create separate series for each data point, than you will be able to set different width for each bar:
series: [{
name: 'Project 1',
pointWidth: 20,
data: [{
x: Date.UTC(2014, 10, 21),
x2: Date.UTC(2014, 11, 2),
y: 0,
partialFill: 0.25
}],
dataLabels: {
enabled: true
}
}, {
pointWidth: 15,
data: [{
x: Date.UTC(2014, 11, 2),
x2: Date.UTC(2014, 11, 5),
y: 1
}]
}, {
pointWidth: 30,
data: [{
x: Date.UTC(2014, 11, 8),
x2: Date.UTC(2014, 11, 9),
y: 2
}]
}, {
pointWidth: 40,
data: [{
x: Date.UTC(2014, 11, 9),
x2: Date.UTC(2014, 11, 19),
y: 1
}]
}, {
pointWidth: 10,
data: [{
x: Date.UTC(2014, 11, 10),
x2: Date.UTC(2014, 11, 23),
y: 2
}]
}]
Live demo: http://jsfiddle.net/BlackLabel/4uydm6tr/
API: https://api.highcharts.com/highcharts/series.xrange.pointWidth

Related

How to make a plot band on a single row in Highcharts Gantt?

I have a Gantt chart and I wanna plot a band only on a specific row. On my example below it displays on every row.
It can be a band plot or something similar (eg: SVG, bar, ...). As long as can control easily the position with start and end in time since I'll have a few for over 30 rows in different positions.
Here's a fiddle
And my code:
// THE CHART
Highcharts.ganttChart('container', {
title: {
text: 'Gantt Chart with Progress Indicators'
},
yAxis: {
categories: ['1', '2']
},
plotOptions: {
series: {
dataLabels: {
enabled: true,
verticalAlign: "top",
format: "{point.custom.label}"
}
}
},
xAxis: {
plotBands: [{
color: '#B3D1AE', // Color value
from: Date.UTC(2014, 10, 21), // Start of the plot band
to: Date.UTC(2014, 10, 22) // End of the plot band
}],
},
series: [{
type: 'line',
zoneAxis: 'x',
zones: [{
value: Date.UTC(2014, 10, 20)
}, {
dashStyle: 'dot',
value: Date.UTC(2014, 10, 25)
}],
data: [{
y: 0,
x: Date.UTC(2014, 10, 18),
custom: {
label: 1
}
}, {
y: 0,
x: Date.UTC(2014, 10, 25, 12),
custom: {
label: 2
}
}]
}, {
name: 'Project 1',
type: 'line',
zoneAxis: 'x',
zones: [{
value: Date.UTC(2014, 10, 28)
}, {
dashStyle: 'dot',
value: Date.UTC(2014, 10, 29)
}],
data: [{
x: Date.UTC(2014, 10, 25, 16),
y: 0,
custom: {
label: 3
}
}, {
x: Date.UTC(2014, 10, 29),
y: 0,
custom: {
label: 4
}
}]
}, {
type: 'line',
zoneAxis: 'x',
data: [{
x: Date.UTC(2014, 10, 25, 16),
y: 1,
custom: {
label: 3
}
}, {
x: Date.UTC(2014, 10, 29),
y: 1,
custom: {
label: 4
}
}]
}]
});
You can use SVG.Renderer to draw the "plotBands" and axis.toPixels() method to control the position.
Example:
chart: {
events: {
load() {
let from = this.xAxis[0].toPixels(Date.UTC(2014, 10, 21)),
to = this.xAxis[0].toPixels(Date.UTC(2014, 10, 22)),
width = to - from,
rowStart = this.yAxis[0].toPixels(0.5),
rowHeight = this.yAxis[0].toPixels(1) - this.yAxis[0].toPixels(0);
this.renderer.rect(from, rowStart, width, rowHeight)
.attr({
fill: '#ff0000',
zIndex: 0
}).add()
}
}
}
Demo:
https://jsfiddle.net/BlackLabel/qbo8Lmy6/
API References:
https://api.highcharts.com/class-reference/Highcharts.SVGRenderer
https://api.highcharts.com/class-reference/Highcharts.Axis#toPixels

Highcharts x-range series: difficulty removing numerical labels on y-axis

This is a question for anyone with HighchartsJS experience
I’m currently having an issue displaying state data using the Highcharts X-range series charts. Specifically, My problem is that our data that we are using to represent each individual state are both fairly high and non consecutive (768, 769 and 773). To label these individual states I’m using a sparse array and placing my labels at the corresponding indices.
The problem I am trying to solve which is depicted by this jsfiddle: https://jsfiddle.net/sn4d2hvq/10/
let categoryArray = [];
categoryArray[768] = 'one';
categoryArray[769] = 'two';
categoryArray[773] = 'three';
Highcharts.chart('container', {
chart: {
type: 'xrange'
},
title: {
text: 'Example'
},
xAxis: {
type: 'datetime'
},
yAxis: {
title: {
text: ''
},
categories: categoryArray,
},
series: [{
name: 'dataset 1',
borderColor: 'gray',
pointWidth: 20,
data: [{
x: Date.UTC(2014, 10, 21),
x2: Date.UTC(2014, 11, 2),
y: 768,
}, {
x: Date.UTC(2014, 11, 2),
x2: Date.UTC(2014, 11, 5),
y: 769
}, {
x: Date.UTC(2014, 11, 8),
x2: Date.UTC(2014, 11, 9),
y: 773
}, {
x: Date.UTC(2014, 11, 9),
x2: Date.UTC(2014, 11, 19),
y: 769
}, {
x: Date.UTC(2014, 11, 10),
x2: Date.UTC(2014, 11, 23),
y: 773
}],
dataLabels: {
enabled: true
}
}]
});
is that I want to exclude all values (which in this case means all numerical values) on the y-axis such that there are no numbers from zero up until the first index as well as no numbers in between any of the labels (ie. 770, 771,772). Here’s an example of the desired view:
https://jsfiddle.net/estgbr6j/2/
let categoryArray = ['one', 'two', 'three'];
Highcharts.chart('container', {
chart: {
type: 'xrange'
},
title: {
text: 'Example'
},
xAxis: {
type: 'datetime'
},
yAxis: {
title: {
text: ''
},
categories: categoryArray,
},
plotOptions: {
xrange: {
colorByPoint: false,
}
},
series: [{
name: 'dataset 1',
borderColor: 'gray',
pointWidth: 20,
data: [{
x: Date.UTC(2014, 10, 21),
x2: Date.UTC(2014, 11, 2),
y: 0,
}, {
x: Date.UTC(2014, 11, 2),
x2: Date.UTC(2014, 11, 5),
y: 1
}, {
x: Date.UTC(2014, 11, 8),
x2: Date.UTC(2014, 11, 9),
y: 2
}, {
x: Date.UTC(2014, 11, 9),
x2: Date.UTC(2014, 11, 19),
y: 1
}, {
x: Date.UTC(2014, 11, 10),
x2: Date.UTC(2014, 11, 23),
y: 2
}],
dataLabels: {
enabled: true
}
}]
});
The only way I’ve been able to consistently achieve the desired result (as depicted by the second example) has been to map the values from [768, 769, 773] => [0, 1, 2] and use a dense array to label the newly mapped values. It seems that this workaround shouldn’t be necessary but I have yet to find an option in the highcharts API to easily allow for our desired result without mapping the values. It should also be noted that in our actual data set, we are usually displaying multiple series with each series depicted by its own color rather than each category (which I have been able to achieve). I would like to know which API option or options are available to display our desired result. Thank you so much.
highcharts: 9.0.1
highcharts-angular: 2.10.0
angular: 12.0.5
node: 14.18.0
The solution with mapping your data is really good. The intervals must be regular if you want to have equally distributed points.
data: [{
x: Date.UTC(2014, 10, 21),
x2: Date.UTC(2014, 11, 2),
y: 0,
}, {
x: Date.UTC(2014, 11, 2),
x2: Date.UTC(2014, 11, 5),
y: 1
}, {
x: Date.UTC(2014, 11, 8),
x2: Date.UTC(2014, 11, 9),
y: 2
}, {
x: Date.UTC(2014, 11, 9),
x2: Date.UTC(2014, 11, 19),
y: 1
}, {
x: Date.UTC(2014, 11, 10),
x2: Date.UTC(2014, 11, 23),
y: 2
}]
You can use tickPositions property, but labels will not be equally distributed. Example: https://jsfiddle.net/BlackLabel/gbwhk5nx/
API Reference: https://api.highcharts.com/highcharts/yAxis.tickPositions
mateusz.b on the official Highcharts forum had a great answer to this. He suggested using a columnrange series instead of an xrange series to present the data.
Check out the post here:
https://www.highcharts.com/forum/viewtopic.php?f=9&t=47822

Highchart x-range chart extending the data point without ending

I have an x-range highchart which is used to display an event timeline. I was able to make it work for events which has start and end date. But I have events that are not yet ended and for those I need to extend the data point of the chart without stopping like below. Green event hasn't finished yet.
Following is my existing code:
Highcharts.chart('container', {
chart: {
type: 'xrange',
height: 100
},
title: {
text: ''
},
xAxis: {
visible: true,
tickLength: 0,
lineWidth: 6,
lineColor: '#000',
labels: {
enabled: false
}
},
yAxis: {
visible: false
},
legend: {
enabled: false
},
series: [{
name: '',
borderRadius: 0,
pointPadding: 0,
borderWidth: 6,
groupPadding: 0,
data: [{
x: Date.UTC(2014, 10, 21),
x2: Date.UTC(2014, 11, 2),
y: 0,
color: 'transparent',
borderColor: 'rgba(230, 141, 11, 0.5)'
}, {
x: Date.UTC(2014, 10, 26),
x2: Date.UTC(2014, 11, 5),
y: 0,
color: 'transparent',
borderColor: 'rgba(228, 53, 70, 0.5)'
}, {
x: Date.UTC(2014, 11, 8),
x2: Date.UTC(2014, 11, 10),
y: 0,
color: 'transparent',
borderColor: 'rgba(40, 167, 69, 0.5)'
}, {
x: Date.UTC(2014, 11, 9),
x2: Date.UTC(2014, 11, 12),
y: 0,
color: 'transparent',
borderColor: 'rgba(40, 147, 164, 0.5)'
}],
dataLabels: {
enabled: false
}
}]
});
<script src="https://code.highcharts.com/highcharts.js"></script>
<script src="https://code.highcharts.com/modules/xrange.js"></script>
<div id="container"></div>
I tried putting Date.UTC(0, 0, 0) for the x2 but it didn't work as expected. Is this possible with xrange charts in highcharts. Thanks in advance!
You can set the x2 value to a later date than xAxis.max:
xAxis: {
...,
max: Date.UTC(2014, 11, 5)
},
...,
series: [{
data: [{
x: Date.UTC(2014, 10, 26),
x2: Date.UTC(2014, 11, 15),
...
}],
...
}]
Live demo: http://jsfiddle.net/BlackLabel/9f6Lejbs/
API Reference: https://api.highcharts.com/highcharts/xAxis.max

Chart.js Dynamically Updating Chart with X Axis Time

I'm using Chart.js version 2.7.1 and I am dynamically updating my Line chart when temperature data comes in.
The problem is that the lines never pass the halfway mark of the x axis in time. Every time I update, the chart auto scales the right side ( max time ) of the x axis to be further out, so my data never approaches the right side of the chart. What I want is for the line to approach the right side, and only a small margin of time is extended into the future for the x-axis each time I update. How can I accomplish this?
Here is how I configure the chart:
var ctx = document.getElementById('tempChart').getContext('2d');
ctx.canvas.width = 320;
ctx.canvas.height = 240;
var chart = new Chart(ctx, {
type: 'line',
data: {
labels: [],
legend: {
display: true
},
datasets: [{
fill: false,
data: [],
label: 'Hot Temperature',
backgroundColor: "#FF2D00",
borderColor: "#FF2D00",
type: 'line',
pointRadius: 1,
lineTension: 2,
borderWidth: 2
},
{
fill: false,
data: [],
label: 'Cold Temperature',
backgroundColor: "#0027FF",
borderColor: "#0027FF",
type: 'line',
pointRadius: 1,
lineTension: 2,
borderWidth: 2
}]
},
options: {
animation: false,
responsive: true,
scales: {
xAxes: [{
scaleLabel: {
display: true,
labelString: 'Time ( UTC )'
},
type: 'time',
time: {
tooltipFormat: "hh:mm:ss",
displayFormats: {
hour: 'MMM D, hh:mm:ss'
}
},
ticks: {
maxRotation: 90,
minRotation: 90
}
}],
yAxes: [{
scaleLabel: {
display: true,
labelString: 'Temperature ( Celcius )'
},
}]
}
}
});
Here is the chart:
as you can see in the following snippet and thanks also to Daniel W Strimpel for creating the initial snippet, you problem is in the hot and cold temperature data.
{ x: new Date(2019, 0, 1, 14, 1, 19, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 20, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 21, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 22, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 23, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 24, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 25, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 26, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 27, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 28, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 29, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 30, 0) }
both of those arrays have n number of entries in the end missing the y coordinate including the temperature value. I recreated your scenario by deleting the y for the 5 last entries of the cold and hot temperatures data.
The chart will add the date to the x axis, but it will not add a temperature value and the line will not show up.
{x: new Data(2019, 0, 14, 1, 26, 0) }
The code snippet recreates your scenario, you can run it to understand the problem and fix it by adding the y value to the last 5 entries in the getHotTempData and getColdTempData
var ctx = document.getElementById('tempChart').getContext('2d');
ctx.canvas.width = 320;
ctx.canvas.height = 240;
var chart = new Chart(ctx, {
type: 'line',
data: {
labels: [],
legend: {
display: true
},
datasets: [{
fill: false,
data: getHotTempData(),
label: 'Hot Temperature',
backgroundColor: "#FF2D00",
borderColor: "#FF2D00",
type: 'line',
pointRadius: 1,
lineTension: 2,
borderWidth: 2
},
{
fill: false,
data: getColdTempData(),
label: 'Cold Temperature',
backgroundColor: "#0027FF",
borderColor: "#0027FF",
type: 'line',
pointRadius: 1,
lineTension: 2,
borderWidth: 2
}]
},
options: {
animation: false,
responsive: true,
scales: {
xAxes: [{
scaleLabel: {
display: true,
labelString: 'Time ( UTC )'
},
type: 'time',
time: {
tooltipFormat: "hh:mm:ss",
displayFormats: {
hour: 'MMM D, hh:mm:ss'
}
},
ticks: {
maxRotation: 90,
minRotation: 90
}
}],
yAxes: [{
scaleLabel: {
display: true,
labelString: 'Temperature ( Celcius )'
},
}]
}
}
});
function getHotTempData() {
return [
{ x: new Date(2019, 0, 1, 14, 1, 19, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 20, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 21, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 22, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 23, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 24, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 25, 0), y: Math.random() * 0.5 + 35 },
{ x: new Date(2019, 0, 1, 14, 1, 26, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 27, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 28, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 29, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 30, 0) }
];
}
function getColdTempData() {
return [
{ x: new Date(2019, 0, 1, 14, 1, 19, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 20, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 21, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 22, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 23, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 24, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 25, 0), y: Math.random() * 0.5 + 23.5 },
{ x: new Date(2019, 0, 1, 14, 1, 26, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 27, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 28, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 29, 0) },
{ x: new Date(2019, 0, 1, 14, 1, 30, 0) }
];
}
<script src="https://cdnjs.cloudflare.com/ajax/libs/moment.js/2.24.0/moment-with-locales.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/Chart.js/2.7.3/Chart.min.js"></script>
<canvas id="tempChart"></canvas>

Highcharts xrange timeline overlapping

I am using Highcharts with the xrange plugin, as seen in this fiddle here.
As seen in the dataobject, I have two areas that overlap:
data: [{
x: Date.UTC(2015, 0, 1),
x2: Date.UTC(2020, 11, 2),
y: 0
}
,{
x: Date.UTC(2015, 0, 1),
x2: Date.UTC(2020, 5, 2),
y: 0
}
, {
x: Date.UTC(2015, 0, 2),
x2: Date.UTC(2020, 11, 5),
y: 1
}]
Is there a Highcharts way to group a 'y row' according to the rowLabel, as is done in google charts, as seen below?
var options = {
**timeline: { groupByRowLabel: true},**
backgroundColor: 'white',
avoidOverlappingGridLines: true,
tooltip: { isHtml: false }
};
I would like to create this without creating a new row (e.g. y:3), as this causes spacing, alternating colours and visual confusion in the dataset.
EDIT: Here is what I am looking for:

Categories

Resources