My idea is to display CPU and memory load with highcharts solid gauge which would update every few seconds, but what ever I do, it just wont run it as I wanted, so it's like this:
I have this php code which is giving me an integer for cpu and memory usage
$cpu = exec("mpstat 1 1 | grep 'all' | awk '{print 100 - $12}' | head -n 1");
$mem = exec("free -m | grep Mem | awk '{print $3 / $2 * 100}'");
This is my highcharts js script:
$(function () {
var gaugeOptions = {
chart: {
type: 'solidgauge'
},
title: null,
pane: {
center: ['50%', '85%'],
size: '105%',
startAngle: -90,
endAngle: 90,
background: {
backgroundColor: (Highcharts.theme && Highcharts.theme.background3) || '#EEE',
innerRadius: '60%',
outerRadius: '100%',
shape: 'arc'
}
},
tooltip: {
enabled: false
},
// the value axis
yAxis: {
stops: [
[0.1, '#55BF3B'], // green
[0.5, '#DDDF0D'], // yellow
[0.9, '#DF5353'] // red
],
lineWidth: 0,
minorTickInterval: null,
tickPixelInterval: 400,
tickWidth: 0,
title: {
y: -70
},
labels: {
y: 16
}
},
plotOptions: {
solidgauge: {
dataLabels: {
// y: 5,
borderWidth: 0,
useHTML: true
}
}
}
};setTimeout(function () {
$('#container-speed').highcharts(Highcharts.merge(gaugeOptions, {
yAxis: {
min: 0,
max: 100,
title: {
text: 'CPU'
}
},
credits: {
enabled: false
},
series: [{
name: 'CPU',
data: [0],
dataLabels: {
format: '<div style="text-align:center"><span style="font-size:18px;color:' +
((Highcharts.theme && Highcharts.theme.contrastTextColor) || '#CECECE') + '">{y:.1f} %</span><br/>' +
'<span style="font-size:12px;color:silver"></span></div>'
},
}]
}));
$('#container-rpm').highcharts(Highcharts.merge(gaugeOptions, {
yAxis: {
min: 0,
max: 100,
title: {
text: 'RAM'
}
},
series: [{
name: 'RAM',
data: [0],
dataLabels: {
format: '<div style="text-align:center"><span style="font-size:20px;font-family:Arial;color:' +
((Highcharts.theme && Highcharts.theme.contrastTextColor) || '#CECECE') + '">{y:.1f}%</span><br/>' +
'<span style="font-size:12px;color:silver"></span></div>'
},
}]
}));
var chart = $('#container-speed').highcharts(),
point,
newVal,
inc;
if (chart) {
point = chart.series[0].points[0];
inc = <?php echo $cpu; ?>;
newVal = inc;
if (newVal < 0 || newVal > 200) {
newVal = point.y - inc;
}
point.update(newVal);
}
chart = $('#container-rpm').highcharts();
if (chart) {
point = chart.series[0].points[0];
inc = <?php echo $mem; ?>;
newVal = inc;
if (newVal < 0 || newVal > 5) {
newVal = point.y - inc;
}
point.update(newVal);
} }, 5000);});
...and this is my container for calling the gauge:
<div style="width: 600px; height: 400px; margin: 0 auto" >
<div id="container-speed" style="width: 300px; height: 200px; float: left"></div>
<div id="container-rpm" style="width: 300px; height: 200px; float: left"></div></div>
Now, the problem is when it refreshes, it keeps giving me the same values on every refresh.
Thanks to everyone in advance.
I the meanwhile I managed to solve my problem with the help of #Grzegorz Blachliński's comment, so here goes:
first, my php code which is nothing more than two variables checking for cpu load and memory usage.
<?php
$cpu = exec("mpstat 1 1 | grep 'all' | awk '{print 100 - $12}' | head -n 1");
$mem = exec("free -m | grep Mem | awk '{print $3 / $2 * 100}'");
echo "[$cpu,$mem]";?>
Now, for some reason json_encode($cpu,$mem); was returning values which were inside quotes and I was able to read them as integer with for example alert(mem);, but the chart didn't accept those values and didn't draw chart, so I did a workaround for it by echoing the proper format of variable values.
Here's my javascript file:
function setDivHeight() {
var div = $('#cpu-meter');
div.height(div.width() * 0.75);
div = $('#memory-meter');
div.height(div.width() * 0.75); } $(function () {
if( $(window).width() < 1000){
setDivHeight();
$(window).on('load resize', function(){
setDivHeight();
});
}
var gaugeOptions = {
chart: {
type: 'solidgauge',
events: {
load: requestData
}
},
title: null,
pane: {
center: ['50%', '85%'],
size: '140%',
startAngle: -90,
endAngle: 90,
background: {
backgroundColor: (Highcharts.theme && Highcharts.theme.background2) || '#EEE',
innerRadius: '60%',
outerRadius: '100%',
shape: 'arc'
}
},
tooltip: {
enabled: false
},
// the value axis
yAxis: {
stops: [
[0.1, '#55BF3B'], // green
[0.5, '#DDDF0D'], // yellow
[0.9, '#DF5353'] // red
],
lineWidth: 0,
minorTickInterval: null,
tickPixelInterval: 400,
tickWidth: 0,
title: {
y: -70
},
labels: {
y: 16
}
},
plotOptions: {
solidgauge: {
dataLabels: {
y: 5,
borderWidth: 0,
useHTML: true
}
}
}
};
$('#cpu-meter').highcharts(Highcharts.merge(gaugeOptions, {
yAxis: {
min: 0,
max: 100,
title: {
text: 'CPU Usage'
}
},
credits: {
enabled: false
},
series: [{
data: [0],
dataLabels: {
format: '<div style="text-align:center"><span style="font-size:20px;font-family:Arial;color:#777;">{y:.2f} %</span><br/>'
},
}]
}));
$('#memory-meter').highcharts(Highcharts.merge(gaugeOptions, {
yAxis: {
min: 0,
max: 100,
title: {
text: 'Memory Usage'
}
},
credits: {
enabled: false
},
series: [{
data: [0],
dataLabels: {
format: '<div style="text-align:center"><span style="font-size:20px;font-family:Arial;color:#777;">{y:.2f} %</span><br/>'
},
}]
}));
function requestData() {
$.ajax({
url: 'core/cpu-data.php',
type: "GET",
dataType:"json",
success: function(load) {
var chart = $('#cpu-meter').highcharts(),
point = 0,
newVal = 0,
inc = 0;
point = chart.series[0].points[0];
inc = load[0];
diff = newVal - inc;
if (diff > 0) {
newVal = newVal + diff;
} else {
newVal = newVal - diff;
}
point.update(newVal);
chart = $('#memory-meter').highcharts(),
point = 0,
newVal = 0,
inc = 0;
point = chart.series[0].points[0];
inc = load[1];
diff = newVal - inc;
if (diff > 0) {
newVal = newVal + diff;
} else {
newVal = newVal - diff;
}
point.update(newVal);
setTimeout(requestData, 3000);
},
cache: false
});
}});
As you can see, ajax is getting data from my php file and making gauge increase and decrease it's value for setTimeout value (don't use setInterval).
Once again, thanks to all for help.
The chart may be reloading, but it looks like you never reload the $cpu and $mem variables themselves. They would also need to be refreshed, as once they're assigned, they will continue to hold their initial value until you specifically re-execute their exec(...) commands and update them.
Related
i have the next problem with Highcharts. This is a new Highchart for an other site.
See here: https://imgur.com/a/VQQLU
The arrow show to -3 Megawatts but the value at the bottom shows another value. At the first pageload the values are identical, but there comes all 5 seconds new values. And they are not updated at the bottom.
Edit: The tolltip will be updated correctly.
My code:
$(function () {
$.getJSON('jsonlive.php', function(chartData) {
var ADatum; var Eheit; var AktL; var MinL; var MaxL; var chartValue; var i;
ADatum = chartData[0].AktDatum;
Eheit = chartData[0].Einheit;
AktL = chartData[0].AktuelleLeistung;
MinL = chartData[0].MinLeistung;
MaxL = chartData[0].MaxLeistung;
var tMin = (MinL*-1); var tMax = MaxL;
var ttt = new Array();
if (tMin < tMax) { chartValue = tMax; } else if (tMin > tMax) { chartValue = tMin; } // Ermitteln ob neg/pos Zahl die größere ist.
ttt[0] = (chartValue*-1); // Skala mit Zahlen beschriften
for (i = 1; i < chartValue; i++) { ttt[i] = (i*-1); }
var tz = ttt.length ;
for (i = 0; i < chartValue; i++) { ttt[(tz+i)] = i; }
ttt[ttt.length] = chartValue;
var gaugeOptions = {
chart:{ events: {
load: function () { setInterval(function () {
$.getJSON('jsonlive.php', function(chartData) {
ADatum = chartData[0].AktDatum;
AktL = chartData[0].AktuelleLeistung;
var point = $('#inhalt').highcharts().series[0].setData([AktL], true);
});}, 5000);}
}, type: 'gauge' },
title: null,
pane: {
center: ['50%', '85%'], size: '140%', startAngle: -90, endAngle: 90,
background: [{
backgroundColor: {
linearGradient: { x1: 0, y1: 0, x2: 0, y2: 1 },
stops: [[0, '#00fb00'],[1, '#003f00']]},
borderWidth: 2,
outerRadius: '109%',
innerRadius: '102%', shape: 'arc' }]
},
series: [{
data: [AktL],
dataLabels: { borderWidth: 0,align: 'center',x: 0,y: 110,
format: '<div style="text-align:center;font-size:24px;color:black">'+AktL+' ' +Eheit+'</span></div>'
}
}],
tooltip: {
formatter: function () { return 'Datum: <b>' + (new Date(ADatum).toLocaleString("de-DE", { timeZone: 'UTC' })) +
'</b> <br>Leistung <b>' + AktL + ' ' + Eheit + '</b>';}, enabled: true },
yAxis: {lineWidth: 10, minorTickInterval: null, tickPixelInterval: 100, tickWidth: 5, title: { y: -250 }, labels: { y: 2 }}
};
// Anzeige
$('#inhalt').highcharts(Highcharts.merge(gaugeOptions, {
yAxis: {
min: (chartValue*-1),max: chartValue,tickPositions: ttt,tickColor: '#666',minorTickColor: '#666',
plotBands: [{ // optionaler Bereich, zeigt von 0-1 grün, 1 bis hälfte maximum gelb, und hälfte max bis max rot
from: 0, to: -1, color: '#55BF3B' }, { // green
from: -1, to: ((chartValue*-1)/2), color: '#DDDF0D' }, { // yellow
from: ((chartValue*-1)/2),to: (chartValue*-1),color: '#DF5353' }, { // red
from: 0,to: 1,color: '#55BF3B' }, { // green
from: 1,to: (chartValue/2),color: '#DDDF0D' }, { // yellow
from: (chartValue/2),to: chartValue,color: '#DF5353' }],// red
title: { style: { color: 'black', fontWeight: 'bold', fontSize: '24px' }, text: 'Leistung in '+Eheit },
labels: { formatter: function () { return this.value; }}},
credits: { enabled: false } // Link auf highcharts rechts unten an/aus
}));
});
});
</script>
The problem here is that you use a hard-coded value (AktL) in your dataLabels.format. In your example format is just a string that's used all the time.
Use {point.y} to have the label updated on every setData():
series: [{
data: [val],
dataLabels: {
// format: val // WONT WORK
format: '{point.y}'
}
}],
Live demo: http://jsfiddle.net/BlackLabel/v28q5n09/
I need to create a div container for a highcharts graphic. This should be done by means of code, but I can not make it work.
The reason to create divs by code is because I have to show many graphics.
Currently I first create the div, then the id and finally the properties.
Error on graphic:
Example :
http://jsfiddle.net/povyq7em/1/
My code is:
var nombre="container-speed";
var div = document.createElement('div');
div.setAttribute("style", "width: 580px; height: 400px; float: left");
div.setAttribute("id", nombre);
var gaugeOptions = {
chart: {
type: 'solidgauge'
},
title: null,
pane: {
center: ['50%', '85%'],
size: '140%',
startAngle: -90,
endAngle: 90,
background: {
backgroundColor: (Highcharts.theme &&
Highcharts.theme.background2) || '#EEE',
innerRadius: '60%',
outerRadius: '100%',
shape: 'arc'
}
},
tooltip: {
enabled: false
},
yAxis: {
stops: [
[0.1, '#55BF3B'], // green
[0.5, '#DDDF0D'], // yellow
[0.9, '#DF5353'] // red
],
lineWidth: 0,
minorTickInterval: null,
tickAmount: 2,
title: {
y: -70
},
labels: {
y: 16
}
},
plotOptions: {
solidgauge: {
dataLabels: {
y: 5,
borderWidth: 0,
useHTML: true
}
}
}
};
var chartSpeed = Highcharts.chart(nombre, Highcharts.merge(gaugeOptions, {
yAxis: {
min: 0,
max: 200,
title: {
text: 'Speed'
}
},
credits: {
enabled: false
},
series: [{
name: 'Speed',
data: [80],
dataLabels: {
format: '<div style="text-align:center"><span style="font-size:25px;color:' +
((Highcharts.theme && Highcharts.theme.contrastTextColor) || 'black') + '">{y}</span><br/>' +
'<span style="font-size:12px;color:silver">km/h</span></div>'
},
tooltip: {
valueSuffix: ' km/h'
}
}]
}));
.highcharts-yaxis-grid .highcharts-grid-line {
display: none;
}
<script src="https://code.highcharts.com/highcharts.js"></script>
<script src="https://code.highcharts.com/highcharts-more.js"></script>
<script src="https://code.highcharts.com/modules/solid-gauge.js"></script>
<!--<div id="container-speed" style="width: 300px; height: 200px; float: left"></div>-->
Thank you very much for your help.
You're just missing one step. You need to append the element after you create it. Here's the beginning of your code:
var nombre="container-speed";
var div = document.createElement('div');
div.setAttribute("style", "width: 580px; height: 400px; float: left");
div.setAttribute("id", nombre);
// APPEND ELEMENT TO document.body
document.body.appendChild(div);
Also, I updated your fiddle
Per your request, I updated the fiddle once more. I made 3 changes. Only one of which were really important.
declare and value name to be used as element id and as argument for grafica()
var name = "chart-" + i;
alter setAttribute to div.setAttribute("id", name);
***MOST IMPORTANTLY, you changed the variable nombre to name in every place but here var chartSpeed = Highcharts.chart(name, Highcharts.merge(gaugeOptions, {... which you can tell, I've updated.
I've seen tutorials and posts about getting data from the x axis into the tooltip but I am overriding it with categories and cannot figure out how to get the x axis to show up in the tooltip.
This is what im working with:
function showTooltip(x, y, contents) {
$('<div id="tooltip" class="flot-tooltip tooltip"><div class="tooltip-arrow"></div>' + contents + '</div>').css({
top: y - 43,
left: x - 15,
}).appendTo("body").fadeIn(200);
}
var data = [[1492854610, -1240],[1492939020, -1273],[1493025073, -1279],[1493117066, -1186],[1493198484, -1269],[1493289175, -1198],[1493370646, -1280],[1493458518, -1255],[1493543731, -1275],[1493630250, -1273],[1493716306, -1279],[1493803609, -1264],[1493889258, -1276],[1493975557, -1278],[1494064529, -1235],[1494155440, -1160],[1494237980, -1224],[1494321047, -1280],[1494407990, -1271],[1494494125, -1275],[1494581609, -1257],[1494668321, -1252],[1494753220, -1277],[1494847855, -1140],[1494925963, -1278],[1495012537, -1275],[1495099289, -1269],[1495188205, -1227],[1495273568, -1244],[1495358329, -1272]];
$.plot($("#placeholder"), [{
label: "Delay: ",
data: data,
color: "#3a8ce5"
}], {
xaxis: {
mode: "categories",
tickLength: 0,
ticks: [[0, "1:50 AM"],[1, "1:17 AM"],[2, "1:11 AM"],[3, "2:44 AM"],[4, "1:21 AM"],[5, "2:32 AM"],[6, "1:10 AM"],[7, "1:35 AM"],[8, "1:15 AM"],[9, "1:17 AM"],[10, "1:11 AM"],[11, "1:26 AM"],[12, "1:14 AM"],[13, "1:12 AM"],[14, "1:55 AM"],[15, "3:10 AM"],[16, "2:06 AM"],[17, "1:10 AM"],[18, "1:19 AM"],[19, "1:15 AM"],[20, "1:33 AM"],[21, "1:38 AM"],[22, "1:13 AM"],[23, "3:30 AM"],[24, "1:12 AM"],[25, "1:15 AM"],[26, "1:21 AM"],[27, "2:03 AM"],[28, "1:46 AM"],[29, "1:18 AM"]]
},
yaxis: {
min: -2000,
max: 1000,
},
series: {
lines: {
show: true,
fill: true
},
points: {
show: true,
}
},
grid: {
hoverable: true,
clickable: true,
markings: [
{ color: '#000', lineWidth: 1, yaxis: { from: 0, to: 0 } },
]
},
legend: {
show: false
}
});
$("#placeholder").bind("plothover", function(event, pos, item) {
if (item) {
if (previousPoint != item.dataIndex) {
previousPoint = item.dataIndex;
$("#tooltip").remove();
var y = item.datapoint[1].toFixed();
showTooltip(item.pageX, item.pageY,
item.series.label + " = " + y);
}
} else {
$("#tooltip").remove();
previousPoint = null;
}
});
I am trying to get the times part of the categories. The item array has 3 pieces of data, none of which are the times
jFiddle:
http://jsfiddle.net/zw14y8c3/2/
The item.datapoint[0] data has the index of the x-axis tick. With that you can get the actual tick label from the ticks array:
var x = $("#placeholder").data('plot').getAxes().xaxis.ticks[item.datapoint[0]].label;
See the updated fiddle for the full example.
I am using a polar chart with chart type line and rendering colors into it once chart gets created.
On exporting chart as a png, svg etc the colors which are rendered doesn't appear in exported chart.
Is there a way to retain rendered colors on exported chart?
$(function () {
var chart = new Highcharts.Chart({
chart: {
polar: true,
renderTo: 'container'
},
title: {
text: 'Highcharts Polar Chart'
},
pane: {
startAngle: 0,
endAngle: 360
},
xAxis: {
tickInterval: 45,
min: 0,
max: 360,
labels: {
formatter: function () {
return this.value + '°';
}
}
},
yAxis: {
min: 0,
tickInterval: 2,
showLastLabel: true
},
plotOptions: {
series: {
pointStart: 0,
pointInterval: 45
},
column: {
pointPadding: 0,
groupPadding: 0
},
line: {
pointPlacement: "between",
dataLabels: {
allowOverlap: true,
enabled: true
}
}
},
series: [{
type: 'line',
name: 'Line',
data: [1, 2, 3, 4, 5, 6, 7, 8]
}]
});
var colors = ["#058DC7", "#50B432", "#ED561B", "#DDDF00", "#24CBE5", "#7cb5ec", "#434348", "#90ed7d", "#f7a35c", "#8085e9", "#f15c80", "#e4d354", "#2b908f", "#f45b5b", "#91e8e1", "#696969", "#64E572", "#FF9655", "#FFF263", "#6AF9C4"];
var parts = 8;
for(var i = 0; i < parts; i++) {
chart.renderer.arc(chart.plotLeft + chart.yAxis[0].center[0],
chart.plotTop + chart.yAxis[0].center[1],
chart.yAxis[0].height,
0,
-Math.PI + (Math.PI/(parts/2) * i),
-Math.PI + (Math.PI/(parts/2) * (i+1))).attr({
fill: colors[i % colors.length],
'stroke-width': 1,
'opacity': 1
}).add();
}
});
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.9.1/jquery.min.js"></script>
<script src="http://code.highcharts.com/highcharts.js"></script>
<script src="http://code.highcharts.com/highcharts-more.js"></script>
<script src="http://code.highcharts.com/modules/exporting.js"></script>
<div id="container" style="width: 500px; height: 500px; margin: 0 auto"></div>
Defaulty when you export chart, then new copy of options are exported, ignoring elementes which are renderered after chart init. Like your arcs. You should add shapes in load event to keep that objects "in chart options".
chart: {
polar: true,
renderTo: 'container',
events: {
load: function() {
var chart = this,
parts = 8,
colors = ["#058DC7", "#50B432", "#ED561B", "#DDDF00", "#24CBE5", "#7cb5ec", "#434348", "#90ed7d", "#f7a35c", "#8085e9", "#f15c80", "#e4d354", "#2b908f", "#f45b5b", "#91e8e1", "#696969", "#64E572", "#FF9655", "#FFF263", "#6AF9C4"];
for (var i = 0; i < parts; i++) {
chart.renderer.arc(chart.plotLeft + chart.yAxis[0].center[0],
chart.plotTop + chart.yAxis[0].center[1],
chart.yAxis[0].height,
0, -Math.PI + (Math.PI / (parts / 2) * i), -Math.PI + (Math.PI / (parts / 2) * (i + 1))).attr({
fill: colors[i % colors.length],
'stroke-width': 1,
'opacity': 1
}).add();
}
}
}
},
Example:
- http://jsfiddle.net/71yrh58e/1/
I am trying to make the HighStock chart's scroll bar default to the left hand side location. Essentially, I am looking at forecast data that starts from today's date. The chart defaults to a 3 month window, and I need this window's starting location to be from today. Here is an example plot:
I need the highlighted scroll bar to default to the left. I am working with a team in India on this issue, and they told me "it's not possible, and is a HighChart's limitation". I'm not saying they are wrong, but I really feel like it can be done without too much issue. Bellow is the js that generates my specific plot (not the same as the one pictured above).
$(function () {
var now = new Date();
var utc_timestamp = Date.UTC(now.getFullYear(), now.getMonth(), now.getDate(), 0, 0, 0, 0);
$.ajax({
type: 'GET',
url: '/Conductivity/ForecastPlot',
data: { USGSID: Source1Id },
success: function (jsonData) {
var BestCase = new Array();
var WorstCase = new Array();
for (var i = 0 ; i < jsonData.AverageForecastData.length ; i++) {
var BestData = new Object();
var WorstData = new Object();
BestData = jsonData.AverageForecastData[i];
WorstData = jsonData.MaximumForecastData[i];
BestCase.push(BestData.cond);
WorstCase.push(WorstData.cond)
}
$('#Forecast_Source_1').empty();
$('#Forecast_Source_1').highcharts('StockChart', {
rangeSelector: {
selected: 1,
},
chart: {
type: 'spline',
zoomType: 'x',
width: 630,
height: 300
},
xAxis: {
type: 'datetime',
tickInterval: 24 * 3600 * 1000 * 21,
title: {
text: 'Date'
}
},
yAxis: {
title: {
text: 'Conductivity'
}
},
credits: {
enabled: false
},
tooltip: {
shared: true,
crosshairs: true
},
plotOptions: {
series: {
cursor: 'pointer',
point: {
events: {
click: function (e) {
}
}
},
marker: {
enabled:false,
lineWidth: 1
}
}
},
legend: {
enabled: true,
layout: 'horizontal',
borderWidth: 1
},
series: [{
name: 'WorstCase',
pointInterval: 24 * 3600 * 1000,
pointStart: utc_timestamp,
data: WorstCase,
color: '#FF0000'
},{
name: 'Expected',
pointInterval: 24 * 3600 * 1000,
pointStart: utc_timestamp,
data: BestCase
}]
});
}
});
});
I've taken a quick look at the API and I don't specifically see an option for this in the "scrollbar" option, but I am thinking of creating a custom zoom function that loads the appropriate window with the From: xx/xx/xx To: xx/xx/xx boxes when a user clicks on the 1m,3m,or 6m buttons.
Edit: Partial Solution
I have a partial solution that seems to be working great. Here is what I changed:
First of all, I know that all the data in my MySQL database is always rounded to the nearest day, so I made sure that the code was rounding also:
var now = new Date();
now.setHours(now.getHours()) + Math.round(now.getMinutes());
now.setMinutes(0);
var utc_timestamp_today = Date.UTC(now.getFullYear(), now.getMonth(), now.getDate(), 0, 0, 0, 0);
var utc_timestamp_3moFromNow = Date.UTC(now.getFullYear(), (now.getMonth() + 3), now.getDate(), 0, 0, 0, 0);
After adding this in, I simply added a "min" and "max" to my "xAxis" parameter.
xAxis: {
type: 'datetime',
tickInterval: 24 * 3600 * 1000 * 21,
min: utc_timestamp_today,
max: utc_timestamp_3moFromNow,
title: {
text: 'Date'
}
You can see the new plot below. This is the actual plots I am dealing with, and you can see how when the page first loads the scroll bar is now in the proper location:
Now my only remaining issue is that when the user goes and clicks on the 1m, 3m, 6m option the graph's window scroll bar will revert to being back at the right hand side. Does anyone know how I might solve this?
Final Working Solution:
$(function () {
var now = new Date();
now.setHours(0, 0, 0, 0);;
now.setMinutes(0);
var plus1mo = new Date();
plus1mo.setMonth((now.getMonth() + 1));
plus1mo.setHours(0, 0, 0, 0);
plus1mo.setMinutes(0);
var plus3mo = new Date();
plus3mo.setMonth((now.getMonth() + 3));
plus3mo.setHours(0, 0, 0, 0);
plus3mo.setMinutes(0);
var plus6mo = new Date();
plus6mo.setMonth((now.getMonth() + 6));
plus6mo.setHours(0, 0, 0, 0);
plus6mo.setMinutes(0);
var utc_timestamp_today = Date.UTC(now.getFullYear(), now.getMonth(), now.getDate(), 0, 0, 0, 0);
var utc_timestamp_1moFromNow = Date.UTC(plus1mo.getFullYear(), plus1mo.getMonth(), plus1mo.getDate(), 0, 0, 0, 0);
var utc_timestamp_3moFromNow = Date.UTC(plus3mo.getFullYear(), plus3mo.getMonth(), plus3mo.getDate(), 0, 0, 0, 0);
var utc_timestamp_6moFromNow = Date.UTC(plus6mo.getFullYear(), plus6mo.getMonth(), plus6mo.getDate(), 0, 0, 0, 0);
$.ajax({
type: 'GET',
url: '/Conductivity/ForecastPlot',
data: { USGSID: Source1Id },
success: function (jsonData) {
var BestCase = new Array();
var WorstCase = new Array();
for (var i = 0 ; i < jsonData.AverageForecastData.length ; i++) {
var BestData = new Object();
var WorstData = new Object();
BestData = jsonData.AverageForecastData[i];
WorstData = jsonData.MaximumForecastData[i];
BestCase.push(BestData.cond);
WorstCase.push(WorstData.cond)
}
$('#Forecast_Source_1').empty();
$('#Forecast_Source_1').highcharts('StockChart', {
rangeSelector: {
buttons: [{
type: 'month',
count: 1,
text: '1m'
}, {
type: 'month',
count: 3,
text: '3m'
}, {
type: 'month',
count: 6,
text: '6m'
}, {
type: 'all',
text: 'All'
}],
selected: 1
},
chart: {
type: 'spline',
zoomType: 'x',
width: 630,
height: 300
},
xAxis: {
type: 'datetime',
tickInterval: 24 * 3600 * 1000 * 21,
min: utc_timestamp_today,
max: utc_timestamp_3moFromNow,
title: {
text: 'Date'
},
events: {
afterSetExtremes: function (e)
{
if(e.trigger == "rangeSelectorButton" && e.rangeSelectorButton.text == "1m") {
setTimeout(function () {
Highcharts.charts[1].xAxis[0].setExtremes(utc_timestamp_today, utc_timestamp_1moFromNow)
}, 1);
}
else if(e.trigger == "rangeSelectorButton" && e.rangeSelectorButton.text == "3m") {
setTimeout(function () {
Highcharts.charts[1].xAxis[0].setExtremes(utc_timestamp_today, utc_timestamp_3moFromNow)
}, 1);
}
else if(e.trigger == "rangeSelectorButton" && e.rangeSelectorButton.text == "6m") {
setTimeout(function () {
Highcharts.charts[1].xAxis[0].setExtremes(utc_timestamp_today, utc_timestamp_6moFromNow)
}, 1);
}
}
}
},
yAxis: {
title: {
text: 'Conductivity'
}
},
credits: {
enabled: false
},
tooltip: {
shared: true,
crosshairs: true
},
plotOptions: {
series: {
cursor: 'pointer',
point: {
events: {
click: function (e) {
}
}
},
marker: {
enabled:false,
lineWidth: 1
}
}
},
legend: {
enabled: true,
layout: 'horizontal',
borderWidth: 1
},
series: [{
name: 'WorstCase',
pointInterval: 24 * 3600 * 1000,
pointStart: utc_timestamp_today,
data: WorstCase,
color: '#FF0000'
},{
name: 'Expected',
pointInterval: 24 * 3600 * 1000,
pointStart: utc_timestamp_today,
data: BestCase
}]
});
}
});
});
The trick was setting a "timeout" function to be called after HighCharts is doing all it's stuff. Only then do I set the min/max so that I can get the appropriate range. (By the way: It's Highcharts.charts[1] because I have 2 charts)
Set this in your xAxis
xAxis : {
events: {
setExtremes: function(e) {
if(typeof(e.rangeSelectorButton)!== 'undefined')
{ this.min= utc_timestamp_today;
this.max= utc_timestamp_3moFromNow;
}
}
}