NEWS
Test Adapter shuttercontrol v1.7.x
-
@simatec sagte in Test Adapter shuttercontrol v1.0.x:
@MichMein
Das steht auf der Todo und wird wenn es meine Zeit erlaubt kommenDas hört sich sehr gut an, vielen Dank im voraus.
-
@FredF sagte in Test Adapter shuttercontrol v1.0.x:
Wenn ich wieder Zeit habe, aktualisiere ich die Doku...
Hast du das schon???
oder war ich gestern blind? -
@Homoran Was meinst du?
Ich hatte die DE Doku anfang August auf den neuesten Stand gebracht. Die neuen Änderungen wollte ich demnächst einpflegen. -
@FredF sagte in Test Adapter shuttercontrol v1.0.x:
Was meinst du?
heute habe ich den Hinweis auf den manuellen Eingriff auf Ahieb gefunden, nach dem ich gestern lange gesucht hatte
Hinweis:
Wird ein Rollladen manuell verstellt und entspricht die Position nicht der automatisch angefahrenen, setzt die Automatik aus! Ausnahme:
Wenn der Rollladen das erste Mal am Tag manuell auf 100% geöffnet wird, wird ebenso der Sonnenschutz ermöglicht. Hierbei fährt der Rollladen bei Bedarf kurz nach dem manuellen Hochfahren in den Sonnenschutz. Wird der Rollladen automatisch hochgefahren und sind die Voraussetzungen für den Sonnenschutz erfüllt, so fährt er direkt die Höhe des Sonnenschutzes an. -
@Homoran
Geht mir auch manchmal so...
Und nein, das steht schon seit August so drin -
@FredF Danke für die deutsche Anleitung. Vielleicht könnte man die Doku.version (oder ein Datum) unter "Grundlegendes" vermerken, dort steht z.Zt. immer der Hinweis auf "0.7.0"
@simatec Stichwort To-Do-Liste: Meine Frau mag die "manuelle-Bewegung-schaltet-Automatik-aus" (s. 2368) nicht, anders formuliert: könnte man das auch "ausschalten" bzw. die Automatik aktiv lassen ?Neue Frage:
Dieses Blockly-Script kriege ich nicht in den Adapter ...
Das ist der letzte Versuch der nicht funktioniert ...
Ich befürchte, da steht etwas in der Anleitung, dass ich übersehe oder nicht (bzw. falsch) verstehe ...
Danke für die Reaktionen.
-
@RaspiUser sagte in Test Adapter shuttercontrol v1.0.x:
Meine Frau mag die "manuelle-Bewegung-schaltet-Automatik-aus" (s. 2368) nicht,
so unterschiedlich kann das sein.
Das ist bei meiner Frau Bedingung! Wenn sie etwas verändert muss das so bleiben!
-
@RaspiUser sagte in Test Adapter shuttercontrol v1.0.x:
Vielleicht könnte man die Doku.version (oder ein Datum) unter "Grundlegendes" vermerken, dort steht z.Zt. immer der Hinweis auf "0.7.0"
Guter Punkt
-
@RaspiUser und @Homoran ich sag nur „WomanAcceptanceFactor“, damit kämpfen wohl viele
-
@Homoran said in Test Adapter shuttercontrol v1.0.x:
Wenn sie etwas verändert muss das so bleiben!
Das ist der Kern ... SIE hat es nicht verändert ...
Aber diesmal muss ich ihr zustimmen. -
@Homoran tja, dann muss SIE am abend z.b. die automatik wieder aktivieren!
-
Hallo,
ich hätte noch einen Wunsch:
Könnte man einen Datenpunkt einbauen, der den Status der Beschattung angibt:
Beispiel:
- Beschalltung ausgeschaltet
- Himmelsrichtung nicht erreicht
- Helligkeit nicht erreicht
- innenTemp nicht erreicht
- AusenTemp nicht erreicht
- Aussperrschutz aktiv
- Beschattung aktiv
.
.
.
Ich frage mich des öfteren, warum jetzt die Beschattung nicht gefahren ist,... und muss dann immer alle Werte kontrollieren.... hier wäre es toll, wenn ich das auf einen Blick sehen könnte...
Grüße Daniel
-
@rde-master sagte in Test Adapter shuttercontrol v1.0.x:
...Ich frage mich des öfteren, warum jetzt die Beschattung nicht gefahren ist,... und muss dann immer alle Werte kontrollieren.... hier wäre es toll, wenn ich das auf einen Blick sehen könnte...
Grüße Daniel
geht mir genauso: immer wieder mal die Frage, warum ist die Markise denn jetzt rausgefahren?
-
@simatec zuerst, toller adapter von dir, danke!
...den Beginn der Beschattung bzw. das Ende der Beschattung!
aktuell fahren die Jalousien sofort runter wenn an einem bewölkten Tag nur kurz die Sonne raus schaut und ständig rauf/runter wenn an einem schönen Tag kurz Wolken kommen. Hysterese habe ich aktuell auf 50%, diese könnte man noch höher drehen, gilt aber nicht für das runter fahren.
bis jetzt habe ich über KNX die Beschattung erst aktiviert, wenn zb. für 15min die Sonne herausen ist, selbige für das hochfahren!lg.
-
@lackylacky sagte in Test Adapter shuttercontrol v1.0.x:
wenn zb. für 15min die Sonne herausen ist, selbige für das hochfahren!
dann musst du auf einen eigenen Datenpunkt triggern, den du über ein Skript/Blockly mit dem Wert befüllst, wenn die Sonne 15 Minuten am Stück scheint, oder einen fließenden Mittelwert über 15 Minuten überschreitet, oder....
Je nachdem worauf du da gerade reagierst geht das ggf. auch in der Hardware.
So bieten HomeMatic Bewegungsmelder an, die geringste Helligkeit der letzten x Messungen anzugeben -
@Homoran ja richtig, daß mache ich gerade aktuell, bekomme ja die Verzögerung der Beschattung von der KNX Wetterstation und schreibe diesen Wert in den Helligkeitswert vom Adapter, aber eben nur 0/1... funktionieren tut es so auch, aber ist halt nicht die elegante Art!
-
@lackylacky
ich halte immer eine Kombi aus Lichtsensor, Außentemperatur und Innentemperatur für sinnvoll -
@simatec das habe ich mit diesem Adapter jetzt auch realisiert, ändert aber nix bei wechselnder Bewölkung.
-
@lackylacky
ich nutze für Temperaturen und Sonne jeweils einen Mittelwert von 15 Min und zusätzlich beim Sonnenschutz eine Hysterese von 70%. Funktionierte den ganzen Sommer für mich einwandfrei. Kein unnötiges Hoch- oder Runterfahren.Anbei das Script falls das jemand benötigt. Hier aus dem Forum, etwas angepasst durch mich
// https://forum.iobroker.net/topic/1037/gleitender-durchschnitt-min-max-%C3%BCber-def-zeitraum/82 // ######################################################################################################## // Berechnung von gleitendem Durchschnitt, Minimum und Maximum über einen Zeitraum // Version 1.4.1 // ######################################################################################################## "use strict"; const idTable = '0_userdata.0.JavaScript.GleitMittelwert.Tabelle'; createState(idTable, '', {type: 'string'}); // // // // Berechnet Min/Max, Durchschnitt und Median über die letzten 24h. // Berechnet Min/Max, Durchschnitt über die letzte 1h. // // IDs aller benötigten Datenpunkte // // Als Array im Array mit folgendem Format: // 1\. original Datenpunktname // 2\. neuer Datenpunktname // Beispiel: javascript.0.Status.Temperatur.Außen // javascript.0.Status.Luftfeuchtigkeit.Außen // 3\. Beschreibung des Messwertes (zur Erzeugung neue Datenpunkte) // Beispliele: Temperatur // Luftfeuchtigkeit // 4\. Einheit (zur Erzeugung neue Datenpunkte) // Beispiele: °C, % // // 5\. Anzahl Nachkommastellen // Beispiele: 0 oder 1 oder 2 // // Ist beliebig erweiterbar und für beliebige Werte nutzbar. // Beispiel 1: // const idData = [['hm-rpc.3.CUX3200312.1.TEMPERATURE','javascript.0.Status.Temperatur.Außen','Temperatur','°C'], // ['hm-rpc.3.CUX9002580.1.HUMIDITY' ,'javascript.0.Status.Luftfeuchtigkeit.Außen','Luftfeuchtigkeit','%']]; // // Beispiel 2: // const idData = [['hm-rpc.3.CUX3200312.1.TEMPERATURE','javascript.0.Status.Außen.Temperatur','Temperatur','°C'], // ['hm-rpc.3.CUX9002580.1.HUMIDITY' ,'javascript.0.Status.Außen.Luftfeuchtigkeit','Luftfeuchtigkeit','%'], // ['hm-rpc.3.CUX4007637.1.Data' ,'javascript.0.Status.Außen.Lichtstärke','Lichtstärke','lux']]; // const idData = [['linkeddevices.0.Aussen.KNX_Temperatur','0_userdata.0.Außen.Temperatur','Temperatur','°C',1], ['alias.0.Außen.Helligkeit_links','0_userdata.0.Außen.Helligkeit_links','Helligkeit','L',0], ['alias.0.Außen.Helligkeit_mitte','0_userdata.0.Außen.Helligkeit_mitte','Helligkeit','L',0], ['alias.0.Außen.Helligkeit_rechts','0_userdata.0.Außen.Helligkeit_rechts','Helligkeit','L',0], ['linkeddevices.0.OG.Flur_Temperatur','0_userdata.0.OG.Flur_Temperatur','Temperatur','°C',1], ['linkeddevices.0.EG.Wohn_Temperatur','0_userdata.0.EG.Wohn_Temperatur','Temperatur','°C',1], ['linkeddevices.0.KG.Arbeit_Temperatur','0_userdata.0.KG.Arbeit_Temperatur','Temperatur','°C',1] ]; //Datenpunkt zur Speicherung aller internen Daten const dpData='0_userdata.0.JavaScript.GleitMittelwert.Statistic'; // ######################################################################################################## // Implementierung -- hier nichts mehr ändern // ######################################################################################################## // globale Konstanten const tc = 3; // Abtastrate in Minuten const statDataLength24 = Math.round((24 * 60) / tc); // Anzahl der Werte für 24h const statDataLength1 = Math.round(60 / tc); // Anzahl der Werte für stündlich const statDataLength15 = Math.round(15 / tc); // Anzahl der Werte für 15 Min // globale Variablen var listStatData; //interne Speicherung aller Werte //Funktion zum einmaligem initialisieren aller Datenpunkte function initializeStatData() { // Datenpunkt zur Speicherung der internen Werte erzeugen createState(dpData, 0, false, { name: "StatisticData", read: true, write: true, desc: 'Statistische Daten', type: 'string', def: '', role: 'json' }); //internes Array initialisieren var needInit = false; try { listStatData = JSON.parse(getState(dpData).val); } catch (ex) { needInit = true; } if (needInit || !listStatData || (listStatData.length < idData.length)) { listStatData = new Array(idData.length); } //logDebug('initializeStatData for', dpData, listStatData); for (var i = 0; i < idData.length; i++) { if (!listStatData[i]) { listStatData[i] = {}; } listStatData[i].value = idData[i][1]; listStatData[i].max24h = idData[i][1] + '.Max_24h'; listStatData[i].min24h = idData[i][1] + '.Min_24h'; listStatData[i].mean24h = idData[i][1] + '.Mean_24h'; listStatData[i].median24h = idData[i][1] + '.Median_24h'; listStatData[i].max1h = idData[i][1] + '.Max_1h'; listStatData[i].min1h = idData[i][1] + '.Min_1h'; listStatData[i].mean1h = idData[i][1] + '.Mean_1h'; listStatData[i].max15 = idData[i][1] + '.Max_15'; listStatData[i].min15 = idData[i][1] + '.Min_15'; listStatData[i].mean15 = idData[i][1] + '.Mean_15'; createState(listStatData[i].value, 0, false, { name: idData[i][2], read: true, write: true, desc: idData[i][2]+ ' Aktueller Wert', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].max24h, 0, false, { name: 'Maximum_24h', read: true, write: true, desc: idData[i][2] + ' Maximum', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].min24h, 0, false, { name: 'Minimum_24h', read: true, write: true, desc: idData[i][2] + ' Minimum', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].mean24h, 0, false, { name: 'Mittelwert_24h', read: true, write: true, desc: idData[i][2] + ' Mittelwert', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].median24h, 0, false, { name: 'Median_24h', read: true, write: true, desc: idData[i][2] + ' Median', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].max1h, 0, false, { name: 'Maximum_1h', read: true, write: true, desc: idData[i][2] + ' Maximum', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].min1h, 0, false, { name: 'Minimum_1h', read: true, write: true, desc: idData[i][2] + ' Minimum', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].mean1h, 0, false, { name: 'Mittelwert_1h', read: true, write: true, desc: idData[i][2] + ' Mittelwert', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].max15, 0, false, { name: 'Maximum_15', read: true, write: true, desc: idData[i][2] + ' Maximum', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].min15, 0, false, { name: 'Minimum_15', read: true, write: true, desc: idData[i][2] + ' Minimum', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); createState(listStatData[i].mean15, 0, false, { name: 'Mittelwert_15', read: true, write: true, desc: idData[i][2] + ' Mittelwert', type: 'number', def: 0, unit: idData[i][3], role: 'value' }); if (needInit || !listStatData[i].data || (listStatData[i].data.length != statDataLength24)) { listStatData[i].data = new Array(statDataLength24); // 1\. Script start: Liste und String-Datenpunkt füllen var x = getState(idData[i][0]).val; for (var j = 0; j < statDataLength24; j++) { listStatData[i].data[j] = x; } //logDebug(listStatData[i], i); setStateDelayed(listStatData[i].value, x, false, 1000); setStateDelayed(listStatData[i].min24h, x, false, 1000); setStateDelayed(listStatData[i].max24h, x, false, 1000); setStateDelayed(listStatData[i].mean24h, x, false, 1000); setStateDelayed(listStatData[i].median24h, x, false, 1000); setStateDelayed(listStatData[i].min1h, x, false, 1000); setStateDelayed(listStatData[i].max1h, x, false, 1000); setStateDelayed(listStatData[i].mean1h, x, false, 1000); setStateDelayed(listStatData[i].min15, x, false, 1000); setStateDelayed(listStatData[i].max15, x, false, 1000); setStateDelayed(listStatData[i].mean15, x, false, 1000); } } setState(dpData, JSON.stringify(listStatData)); } //Berechnung der Werte function calcStatData() { if (!listStatData || (idData.length != listStatData.length)) { initializeStatData(); } //logDebug('starting calcStatData'); var table = []; for (var i = 0; i < idData.length; i++) { var obj = {}; var sensor = listStatData[i].value.split('.'); obj.Sensor = sensor[4] + ' ' + sensor[3]; listStatData[i].data.pop(); //Remove the last element of an array var x = parseFloat(getState(idData[i][0]).val); obj.Wert = x; listStatData[i].data.unshift(x); //Add new items to the beginning of an array setState(listStatData[i].value, x); var min = x; var max = x; var sum = 0.0; for (var j = 0; j < statDataLength24; j++) { var s = parseFloat(listStatData[i].data[j]); if (s < min) min = s; if (s > max) max = s; sum += s; if (j == (statDataLength1-1)) { setState(listStatData[i].min1h, min); setState(listStatData[i].max1h, max); setState(listStatData[i].mean1h, round(sum / statDataLength1, idData[i][4])); } if (j == (statDataLength15-1)) { setState(listStatData[i].min15, min); setState(listStatData[i].max15, max); setState(listStatData[i].mean15, round(sum / statDataLength15, idData[i][4])); } } setState(listStatData[i].min24h, min); setState(listStatData[i].max24h, max); setState(listStatData[i].mean24h, round(sum / statDataLength24, idData[i][4])); setState(listStatData[i].median24h, round(getMedian(listStatData[i].data), idData[i][4])); obj.Min_24h = min; obj.Max_24h = max; obj.Mean_24h = round(sum / statDataLength24, idData[i][4]); obj.Median_24h = round(getMedian(listStatData[i].data), idData[i][4]); table[i] = obj; } setState(dpData, JSON.stringify(listStatData)); setState(idTable, JSON.stringify(table), true); } function getMedian(args) { if (!args.length) {return 0} var numbers = args.slice(0).sort((a,b) => a - b); var middle = Math.floor(numbers.length / 2); var isEven = numbers.length % 2 === 0; return isEven ? (numbers[middle] + numbers[middle - 1]) / 2 : numbers[middle]; } /** * round a number * @param value to round * @param exp exponent to round * @returns the round number */ function round(value, exp) { if (typeof exp === 'undefined' || +exp === 0) return Math.round(value); value = +value; exp = +exp; if (isNaN(value) || !(typeof exp === 'number' && exp % 1 === 0)) return NaN; // Shift var values = value.toString().split('e'); value = Math.round(+(values[0] + 'e' + (values[1] ? (+values[1] + exp) : exp))); // Shift back var values = value.toString().split('e'); return +(values[0] + 'e' + (values[1] ? (+values[1] - exp) : -exp)); } initializeStatData(); schedule('*/' + tc + ' * * * *', function () { calcStatData(); });
sieht dann so aus. Verwenden tue ich Mean15
-
welche meinst du genau?