Ok,I tested this but couldn't get it to work. Presumably I didn't follow the instructions properly. To try to understand it better, and to amuse myself, I wrote a script to do what I want, more or less. I use a javascript script to grab the data that I want:
// so you can optionally pass the bindings
// {'binHours': 12, 'nBins': 12}
// but if you don't doesn't matter.
var myImports = new JavaImporter(java.io, java.lang, java.util, java.text);
with(myImports) {
var sVar = mcApi.uidTag().getByUid("kwh_uid").getSensorVariable();
var powerUsed = [];
var endTimes = [];
// check for some possible bindings:
if( typeof binHours === 'undefined' || !binHours ) {
var binHours = 1
}
if( typeof nBins === 'undefined' || !nBins ) {
var nBins = 5;
}
var binDuration = 1000*60*60*binHours; // hours in milliseconds
var endTime = Date.now();
var startTime;
for(var i=0; i< nBins; i++ ) {
startTime = endTime - binDuration;
minMaxData = mcApi.metric().getSensorVariableMetricDouble(sVar, startTime, endTime);
powerUsed[i] = minMaxData.maximum - minMaxData.minimum;
endTimes[i] = endTime.toString();
endTime = startTime;
}
}
And a template using d3.js:
<link rel=stylesheet type="text/css" href="myd3.css">
<div id="wrapper" style="text-align: center">
<canvas id="simpled3" style="display: none;"></canvas>
<div style="font-size:11px" id="viz"></div>
</div>
<script>
var margin = {
top: 15,
right: 20,
bottom: 30,
left: 30
};
var width = 900- margin.left - margin.right;
var height = 360 - margin.top - margin.bottom;
// we get the data from the script
var x = d3.time.scale().range([0, width]);
var y = d3.scale.linear().range([height, 0]);
var xAxis = d3.svg.axis().scale(x)
.orient("bottom").ticks(5);
var yAxis = d3.svg.axis().scale(y)
.orient("left").ticks(5);
var valueline = d3.svg.line()
.interpolate("step-before")
.x(function (d) {
return x(d.date);
})
.y(function (d) {
return y(d.watts);
});
var svg = d3.select("#viz")
.append("svg")
.attr("width", width + margin.left + margin.right)
.attr("height", height + margin.top + margin.bottom)
.attr("style", "outline: thin solid black;")
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")");
// Get the data
// should look like an array
// with each element date: milliseconds, watts: double
//
var data = [];
// get the values from the hash
// being careful of the indices which
// turn out to be character strings
var hashIndex;
<#list endTimes?keys as k>
hashIndex = +${k};
data[hashIndex] = {date: new Date(+${endTimes[k]}),
watts: +${powerUsed[k]}}
</#list>
// Scale the range of the data
x.domain(d3.extent(data, function (d) {
return d.date;
}));
y.domain([0, d3.max(data, function (d) {
return d.watts;
})]);
svg.append("path") // Add the valueline path.
.attr("d", valueline(data));
svg.append("g") // Add the X Axis
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis);
svg.append("g") // Add the Y Axis
.attr("class", "y axis")
.call(yAxis);
</script>
Some settings are in the custom css file. You can then create a plot, specifying the size in hours of each bin (1 hour by default), and the number of bins to plot. It looks like:
So you can see when we get up in the mornings and when we cook tea in the evenings
With some work it could be better, so for example, I lose the hover information, and I had trouble getting two of these plots on one dashboard with different bins. But I'm not too worried, since at the moment my main concern is why the sensor keeps dropping out. When I work out my hardware issues I might try to do better with the software.
Thanks
Robert