Lektion 5: Nun mit Konnekting

Erweitern des Temperatursensors

Wir haben nun einen Temperatursensor mit einer Taste und einer LED, verbunden mit einer BCU. Bislang kamen wir ohne ein EEPROM aus. Konnekting benötigt es aber zum Speichern der Konfigurationsdaten. Näheres dazu findest du im nächsten Kapitel.

Nun müssen wir die Konnekting-Bibliothek und unsere Header-Datei in unseren Sketch einbauen.

//includes für KNX
#include <KonnektingDevice.h>
#include "kdevice_SimpleSensor.h"

Als nächstes definieren wir Schnittstelle, ProgLED und ProgButton. Die Definitionen passen für den XIAO und müssen an das jeweilige Board angepasst werden.

#define KNX_SERIAL Serial1			// D7=RX/D6=TX / Seeeduino XIAO
#define PROG_LED_PIN LED_BUILTIN
#define PROG_BUTTON_PIN 10			// pin with interrupt

In der Setup-Funktion muss nun KNX initialisiert werden.

Konnekting.init(KNX_SERIAL,
                  PROG_BUTTON_PIN,
                  PROG_LED_PIN,
                  MANUFACTURER_ID,
                  DEVICE_ID,
                  REVISION);

An dieser Stelle wird die BCU initialisiert. Wenn du den Sketch ausprobierst muss die BCU mit dem KNX-Bus verbunden sein. Da die BCU ihre Betriebsspannung aus dem Bus bezieht, schlägt die Initialisierung sonst fehl und das Gerät verharrt in einer Dauer-Resetschleife. Prüfe in dem Fall bitte auch die serielle Verbindung von Arduino zur BCU.

Anschließend werden die Parameter eingelesen, sofern vorhanden. Ansonsten wird direkt der Programmiermodus gestartet.

if (!Konnekting.isFactorySetting()) {
    sendDelay = 1000 * (uint32_t)Konnekting.getUINT32Param(PARAM_tempPollingTime);
  }
  else{
    Konnekting.toggleProgState();
  }

Beim XIAO ist die LED genau anders herum gepolt wie üblich. Deshalb leuchtet sie, wenn der Programmiermodus deaktiviert ist. Im Programmiermodus ist sie aus.

In der Hauptschleife muss der KNX.task regelmäßig und möglichst oft aufgerufen werden. Dort darf also nicht z.B. auf einen Tastendruck gewartet werden.

Knx.task();

Nun müssen wir abfragen, ob das Gerät bereit ist, die Applikation auszuführen oder ob das Gerät gerade programmiert wird.

 if (Konnekting.isReadyForApplication()) {

Und natürlich muss die aktuelle Temperatur noch auf den Bus gelegt werden.

aktTemp = temperature.readTemperatureC(); //aktuelle Temperatur einlesen
    Knx.write(COMOBJ_tempValue, aktTemp);     //und auf den Bus
    DEBUGSERIAL.print("Aktuelle Temperatur ");
    DEBUGSERIAL.print(aktTemp);               //und zum Monitor
    DEBUGSERIAL.println(" ºC");
    lastmillis = currentmillis;

Nun noch die Callback-Funktion für kommende Daten (bleibt in unserem Fall leer).

void knxEvents(byte index) {
  
}

Der komplette Sketch sollte nun so aussehen.

/**********************************************************************
 * Einfacher Temperatursensor als Beispiel für Konnekting
 * 
 * schickt alle 5 Sekunden die aktuelle Temperatur
 * 
 * Temperatursensor: LM 75
 * Benutzt die LM75-Library von Jeremy Cole aus der Bibliothekverwaltung
 * 
 * Prozessor ist ein SAMD21G18 (Seeeduino XIAO, Arduino Zero)
 * 
 **********************************************************************/
 
#define DEBUGSERIAL Serial   // USB port

//includes für KNX
#include <KonnektingDevice.h>
#include "kdevice_SimpleSensor.h"
#include "EEPROM_24AA256.h"

#include <Adafruit_SleepyDog.h>


#define KNX_SERIAL Serial1			// D7=RX/D6=TX / Seeeduino XIAO
#define PROG_LED_PIN LED_BUILTIN
#define PROG_BUTTON_PIN 10			// pin with interrupt

#include <Temperature_LM75_Derived.h>

// The Generic_LM75 class will provide 9-bit (±0.5°C) temperature for any
// LM75-derived sensor. More specific classes may provide better resolution.
Generic_LM75 temperature;
 
unsigned long lastmillis = millis();
uint32_t sendDelay = 5000;
 
void setup()
{
  DEBUGSERIAL.begin(9600);
  Wire.begin();

  Konnekting.setMemoryReadFunc(&readMemory);
  Konnekting.setMemoryWriteFunc(&writeMemory);
  Konnekting.setMemoryUpdateFunc(&updateMemory);
  Konnekting.setMemoryCommitFunc(&commitMemory);

  // Initialize KNX enabled Arduino Board
  Konnekting.init(KNX_SERIAL,
                  PROG_BUTTON_PIN,
                  PROG_LED_PIN,
                  MANUFACTURER_ID,
                  DEVICE_ID,
                  REVISION);

 

  // If device has been parametrized with KONNEKTING Suite, read params from EEPROM
  // Otherwise start programming mode
  if (!Konnekting.isFactorySetting()) {
    sendDelay = 1000 * (uint32_t)Konnekting.getUINT32Param(PARAM_tempPollingTime);
  }
  else{
    Konnekting.toggleProgState();
  }

  lastmillis = millis();
  Watchdog.enable(4000);
}
 
void loop()
{
  float aktTemp;
  unsigned long currentmillis = millis();

  Knx.task();
  Watchdog.reset();
  
  if (Konnekting.isReadyForApplication()) {
    if (currentmillis - lastmillis >= sendDelay)
    {
      aktTemp = temperature.readTemperatureC(); //aktuelle Temperatur einlesen
      Knx.write(COMOBJ_tempValue, aktTemp);     //und auf den Bus
      DEBUGSERIAL.print("Aktuelle Temperatur ");
      DEBUGSERIAL.print(aktTemp);               //und zum Monitor
      DEBUGSERIAL.println(" ºC");
      lastmillis = currentmillis;
    }
  }
}

// ################################################
// ### KNX EVENT CALLBACK
// ################################################

void knxEvents(byte index) {
  
}

Beim Programmieren werden die übertragenen Daten (Parameter und Gruppenadressen) im EEPROM gespeichert. Nach dem Programmieren wird das Gerät neu gestartet und die Daten eingelesen.

<– Lektion 4: Es geht in die PraxisLektion 6: EEPROM & Co. –>