Is there an API for custom (multiple) temperature graphs?

Moderator: leecollings

Post Reply
MikeF
Posts: 350
Joined: Sunday 19 April 2015 0:36
Target OS: Raspberry Pi / ODroid
Domoticz version: V2022.2
Location: UK
Contact:

Is there an API for custom (multiple) temperature graphs?

Post by MikeF »

I'm currently producing graphs in Google Charts for multiple temperatures from Domoticz, like this:
Image
by creating a CSV file in Python.

I know that I can create a custom graph and download the CSV file from that, but can I do it programmatically, i.e., by a JSON / API call (like this for a single device: /json.htm?type=graph&sensor=temp&idx=IDX&range=day)?
User avatar
Egregius
Posts: 2592
Joined: Thursday 09 April 2015 12:19
Target OS: Linux
Domoticz version: v2024.7
Location: Beitem, BE
Contact:

Re: Is there an API for custom (multiple) temperature graphs?

Post by Egregius »

With php pretty easy. There's a file on my github in floorplan/scripts/chart.php that creates Google charts from a php array.
See temp.php for a example.
MikeF
Posts: 350
Joined: Sunday 19 April 2015 0:36
Target OS: Raspberry Pi / ODroid
Domoticz version: V2022.2
Location: UK
Contact:

Re: Is there an API for custom (multiple) temperature graphs?

Post by MikeF »

Thanks, I'll take a look
- how do you pass data to it? - I'm not familiar with creating php arrays.

(I'm currently using the html file below (mostly Javascript), following online Google Charts documentation, reading in csv files for temperature and power. I would like to make use of the Domoticz graph API: /json.htm?type=graph&sensor=temp&idx=IDX&range=day)
Spoiler: show

Code: Select all

<html>

<head>
<meta charset="utf-8">

<title>Temperatures and power from Domoticz</title>

<script src="http://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js"></script>
<script src="jquery.csv.min.js"></script>
<script type="text/javascript" src="https://www.gstatic.com/charts/loader.js"></script>

<script type="text/javascript"> // load the visualisation API

google.charts.load('current', { packages: ['corechart','gauge'] });
google.charts.setOnLoadCallback(drawTemps);
google.charts.setOnLoadCallback(drawPower);

function drawTemps() {
   $.get("temps_daily.csv", function(csvString) {
      // transform the CSV string into a 2-dimensional array
      var arrayData = $.csv.toArrays(csvString, {onParseValue: $.csv.hooks.castToScalar});
	  
      // this new DataTable object holds all the data
      var data = new google.visualization.arrayToDataTable(arrayData);
      
      // get min, max outside temp
      var range = data.getColumnRange(3);
      
      var options = {
        explorer: {},
        title: 'Temperatures for last 24 hours',
        titleTextStyle: {color: 'grey', fontSize: 16},
        hAxis: {title: 'Time', titleTextStyle: {bold: false, italic: false, color: 'grey'}, slantedTextAngle: 90, textStyle: {fontSize: 12}},
        vAxis: {title: 'Degrees (C)', titleTextStyle: {bold: false, italic: false, color: 'grey'}},
        seriesType: 'line',
        series: {5: {type: 'area'}},
        interpolateNulls: true,
      	};
      
      var chart = new google.visualization.LineChart(document.getElementById('temps_div'));
      chart.draw(data, options);
      
      var columns = [];
      var series = {};
      for (var i = 0; i < data.getNumberOfColumns(); i++) {
        columns.push(i);
        if (i > 0) {
            series[i - 1] = {};
        }
      };
      
      google.visualization.events.addListener(chart, 'select', function () {
        var sel = chart.getSelection();
        // if selection length is 0, we deselected an element
        if (sel.length > 0) {
            // if row is undefined, we clicked on the legend
            if (sel[0].row === null) {
                var col = sel[0].column;
                if (columns[col] == col) {
                    // hide the data series
                    columns[col] = {
                        label: data.getColumnLabel(col),
                        type: data.getColumnType(col),
                        calc: function () {
                            return null;
                        }
                    };
                    
                    // grey out the legend entry
                    series[col - 1].color = '#CCCCCC';
                }
                else {
                    // show the data series
                    columns[col] = col;
                    series[col - 1].color = null;
                }
                var view = new google.visualization.DataView(data);
                view.setColumns(columns);
                chart.draw(view, options);
            }
        }
      });

      var gauge_min_data = google.visualization.arrayToDataTable([
        ['Label', 'Value'],
        ['min', range.min]
      ]);
      
      var formatter = new google.visualization.NumberFormat(
    	{suffix: 'C', pattern: '##.#'}
	  );
	  formatter.format(gauge_min_data,1);
      
      var gauge_min_options = {
        width: 120, height: 120,
        min: -5, max: 35,
        redFrom: -5, redTo: 5,
        greenFrom: 15, greenTo: 25,
        yellowFrom: 25, yellowTo: 35,
        minorTicks: 5
      };
      
      var chart1 = new google.visualization.Gauge(document.getElementById('gauge_min_div'));
      chart1.draw(gauge_min_data, gauge_min_options);
      
      var gauge_max_data = google.visualization.arrayToDataTable([
        ['Label', 'Value'],
        ['max', range.max]
      ]);
      
	  formatter.format(gauge_max_data,1);
	  
      var gauge_max_options = {
        width: 120, height: 120,
        min: -5, max: 35,
        redFrom: -5, redTo: 5,
        greenFrom: 15, greenTo: 25,
        yellowFrom: 25, yellowTo: 35,
        minorTicks: 5
      };
      
      var chart2 = new google.visualization.Gauge(document.getElementById('gauge_max_div'));
      chart2.draw(gauge_max_data, gauge_max_options);
      
    },'text');
      
}

function drawPower() {
   $.get("power_daily.csv", function(csvString) {
      // transform the CSV string into a 2-dimensional array
      var arrayData = $.csv.toArrays(csvString, {onParseValue: $.csv.hooks.castToScalar});
      
      // this new DataTable object holds all the data
      var data = new google.visualization.arrayToDataTable(arrayData);
      
      // get last values
      var n = data.getNumberOfRows() - 1;
      var kWh = data.getValue(n, 2);
      var cost = kWh * 13.9;
      
      var options = {
        title: 'Power for last 24 hours',
        titleTextStyle: {color: 'grey', fontSize: 16},
        hAxis: {title: 'Time', titleTextStyle: {bold: false, italic: false, color: 'grey'}, slantedTextAngle: 90, textStyle: {fontSize: 12}},
        legend: {position: 'top'},
        series:	{
        	0:	{targetAxisIndex: 0},
        	1:	{targetAxisIndex: 1}
        },
        vAxes:	{
        		0: {title: 'Power (W)', titleTextStyle: {bold: false, italic: false, color: 'grey'}},
        		1: {title: 'Cum. power (kWh)', titleTextStyle: {bold: false, italic: false, color: 'grey'}}
        },
        seriesType: 'line',
        interpolateNulls: true,
        
      };
      
      var chart = new google.visualization.LineChart(document.getElementById('power_div'));
    
      chart.draw(data, options);

      var gauge_kWh_data = google.visualization.arrayToDataTable([
        ['Label', 'Value'],
        ['kWh', kWh]
      ]);

      var gauge_kWh_options = {
        width: 120, height: 120,
        max: 20,
        yellowFrom:12, yellowTo: 15,
        redFrom: 15, redTo: 20,
        minorTicks: 5
      };

      var chart = new google.visualization.Gauge(document.getElementById('gauge_kWh_div'));
      chart.draw(gauge_kWh_data, gauge_kWh_options);
      
      var gauge_cost_data = google.visualization.arrayToDataTable([
        ['Label', 'Value'],
        ['cost', cost]
      ]);

      var formatter = new google.visualization.NumberFormat(
    	{suffix: 'p', pattern: '####.#'}
	  );
	  formatter.format(gauge_cost_data,1);
      
      var gauge_cost_options = {
        width: 120, height: 120,
        max: 300,
        yellowFrom: 150, yellowTo: 200,
        redFrom: 200, redTo: 300,
        minorTicks: 5
      };

      var chart = new google.visualization.Gauge(document.getElementById('gauge_cost_div'));
      chart.draw(gauge_cost_data, gauge_cost_options);
      
   },'text');
      
}

function GetClock(){
	var d=new Date();
	var nmonth=d.getMonth(),ndate=d.getDate(),nyear=d.getFullYear();
	var nhour=d.getHours(),nmin=d.getMinutes(),ap;
	
	if(nhour==0){ap=" AM";nhour=12;}
	else if(nhour<12){ap=" AM";}
	else if(nhour==12){ap=" PM";}
	else if(nhour>12){ap=" PM";nhour-=12;}

	if(nmin<=9) nmin="0"+nmin;

	document.getElementById('clockbox').innerHTML=""+ndate+"/"+(nmonth+1)+"/"+nyear+" "+nhour+":"+nmin+ap+"";
}

window.onload=function(){
	GetClock();
	setInterval(GetClock,1000);
	setInterval(drawTemps, 60000);
	setInterval(drawPower, 60000);
}

</script>

<style>
	table, th, td {
    	border: 2px solid #ccc;
    	border-collapse: collapse;
    	font-family: verdana;
    	font-size: 16px
	}
	th, td {
    	padding: 5px;
    	text-align: center;    
	}
	td {
		font-size: 12px
	}
	.graph {
  		width: 1000;
  		height: 400;
	}
	.meter {
  		padding: 15px;
  		width: 130;
  		height: 150;
  		font-size: 14px;
	}
</style>

</head>

<body>

<table>
  	<tr>
		<th>Temperatures and power from Domoticz</td>
		<td><div id="clockbox" style="font-size: 100%"></div></td>
  	</tr>
  	<tr>
		<td rowspan = "2"><div id="temps_div" class="graph"></div></td>
		<td>Outside<div id="gauge_min_div" class="meter"></div></td>
  	</tr>
  	<tr>
  		<td><div id="gauge_max_div" class="meter"></div></td>
  	</tr>
  	<tr>
		<td rowspan = "2"><div id="power_div" class="graph"></div></td>
		<td>Cum. power<div id="gauge_kWh_div" class="meter"></div></td>
  	</tr>
  	<tr>
  		<td>Cost<div id="gauge_cost_div" class="meter"></div></td>
  	</tr>
</table>

</body>

</html>
User avatar
Egregius
Posts: 2592
Joined: Thursday 09 April 2015 12:19
Target OS: Linux
Domoticz version: v2024.7
Location: Beitem, BE
Contact:

Re: Is there an API for custom (multiple) temperature graphs?

Post by Egregius »

Post Reply

Who is online

Users browsing this forum: No registered users and 1 guest