Kabellose Komunikation für Smarthome System

Hallo zusammen,
kurz zusammengefasst, ich benötige eine Möglichkeit mehrere Microcontroller an einen Master zu verbinden, der Anweisungen gibt und auch Daten empfängt.
Ich möchte auch jedes Modul über OTA updaten können und suche dafür die richtige Methode (BLE, NRF,…)

Ich arbeite gerade an einem etwas umfangreicheren Projekt.
Ich möchte mein Zimmer mit einigen Smarthome Funktionen ausstatten.
Habe gerade eine Wandbeleuchtung gebaut (Nanoleaf Replika) und plane noch eine kleine Wetterstation für außen und innen zu basteln. Außerdem möchte ich diese dann mit Fernsteröffner verbinden.
Jetzt habe ich mir gedacht ich nehme einen Microcontroller als “Master”, der mit einem Display sowie Wlan und Bluetooth ausgestattet ist.
Wlan um eine kleine Webseite zu hosten in der man mit dem Handy die aktuellen Werte auslesen kann und Bluetooth um mit den anderen Arduinos zu kommunizieren.
Ich möchte nicht an jedes Element eine Wlan verbindung Packen, da Wlan doch noch mal einiges mehr Strahlung als Bluetooth abgibt.
Jetzt ist meine Frage nur, ob ich Bluetooth verwenden kann um sozusagen einen Master und mehrere Slaves zu verbinden.
Was ich bis jetzt gelesen habe ist dass nicht so einfach, könnte aber auch die Verbindung immer wieder abbrechen und neu aufbauen, da ich zum Beispiel die Messwerte e immer nur alle paar minuten auslese.
Oder wäre da vielleicht ein NRF24 Modul besser geeignet?
Zu erwähnen wäre noch, dass ich für jedes Gerät die möglichkeit haben möchte, Updates über OTA hochzuladen. Geht das mit NRF Module auch?

Ich hoffe ich bekomme da ne kurze Einschätzung oder einen Erfahrungsbericht.

OTA ist mir jetzt nur bei WLan ohne großen Aufwand bekannt. Da du dann aber den Controller aktualisierst, kannst du auch Anpassungen für BT aktualisieren.

Für ESP8266 oder ESP32

ElegantOTA

in Verbindung mit
ESP-DASH

Hier ein Democode mit dem man über Webinterface die OnBoard-LED von ESP8266 oder EPS32node-MCUs das Blinken per Button ein/ausschalten kann und die Blinkfrequenz per Schieberegler einstellen. Dazu muss null HTML-programmiert werden. Das macht die DASH-library im Hintergrund.

#include <Arduino.h>
#if defined(ESP8266)
  /* ESP8266 Dependencies */
  #include <ESP8266WiFi.h>
  #include <ESPAsyncTCP.h>
  #include <ESPAsyncWebServer.h>
  /* on ESP8266 LED is connected to Vdd => HIGH = LED off */
  #define  LEDStateOff HIGH 
#elif defined(ESP32)
  /* ESP32 Dependencies */
  #include <WiFi.h>
  #include <AsyncTCP.h>
  #include <ESPAsyncWebServer.h>
  #define  LEDStateOff LOW
#endif
#include <AsyncElegantOTA.h> // manual https://randomnerdtutorials.com/esp32-ota-over-the-air-arduino/
#include <ESPDash.h>

const char *ssid     = "FRITZ!Box 7490";
const char *password = "";

unsigned long MyTestTimer = 0; // variables used with millis() MUST be of type unsigned long
const byte    OnBoard_LED = 2;

bool DoBlink = true;

unsigned long BlinkFreq = 500;
int Slider2Pos = 5;

AsyncWebServer MyServer(80);

ESPDash MyDashboard(&MyServer); 

//  Button Card Format - (Dashboard Instance, Card Type, descriptive Text)
Card MyButton(&MyDashboard, BUTTON_CARD, "Blink On / Off");

//  Slider Card Format - (Dashboard Instance, Card Type, descriptive Text, Card Symbol(optional), int min, int max)
Card MySlider1(&MyDashboard, SLIDER_CARD, "Blink-Period in Milliseconds", "", 50, 1000);
Card MySlider2(&MyDashboard, SLIDER_CARD, "2ndSlider", "Testtext", 0, 10);

void PrintFileNameDateTime() {
  Serial.println("Code running comes from file ");
  Serial.println(__FILE__);
  Serial.print("  compiled ");
  Serial.print(__DATE__);
  Serial.print(" ");
  Serial.println(__TIME__);  
}

boolean TimePeriodIsOver (unsigned long &expireTime, unsigned long TimePeriod) {
  unsigned long currentMillis  = millis();  
  if ( currentMillis - expireTime >= TimePeriod )
  {
    expireTime = currentMillis; // set new expireTime
    return true;                // more time than TimePeriod) has elapsed since last time if-condition was true
  } 
  else return false;            // not expired
}


void BlinkHeartBeatLED(int IO_Pin, int BlinkPeriod) {
  static unsigned long MyBlinkTimer;
  pinMode(IO_Pin, OUTPUT);
  
  if ( TimePeriodIsOver(MyBlinkTimer,BlinkPeriod) ) {
    digitalWrite(IO_Pin,!digitalRead(IO_Pin) ); 
  }
}


void setup(){
  Serial.begin(115200);
  delay(200);
  Serial.println("Setup-Start");
  PrintFileNameDateTime();

  pinMode(OnBoard_LED, OUTPUT);
  digitalWrite(OnBoard_LED, LOW);
  
  Serial.print("Trying to connect to WiFi..");
  Serial.print(ssid);
  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    Serial.print(".");
  }
  Serial.print("connected \r\n type this IP-Adress into your browser ");
  Serial.println(WiFi.localIP() );
  Serial.println("to see the ESP-Dash-Board");

  // Attach Button Callback this function gets executed every time the Button is clicked 
  MyButton.attachCallback([&](bool MyButtonState){
    DoBlink = MyButtonState;
    Serial.println("Button Triggered: " + String((MyButtonState)?"true":"false"));
    MyButton.update(MyButtonState); //Make sure we update our button's value and send update to dashboard */
    MyDashboard.sendUpdates();
  });

  // Attach Slider Callback this function gets executed every time the slider is adjusted to a new value
  MySlider1.attachCallback([&](int MySliderValue){
    BlinkFreq = MySliderValue;
    Serial.println("MySlider1 Triggered: " + String(MySliderValue));
    MySlider1.update(MySliderValue); // Make sure we update our slider's value and send update to dashboard */
    MyDashboard.sendUpdates();
  });

  MySlider2.attachCallback([&](int MySliderValue){
    Serial.println("slider2 Triggered: " + String(MySliderValue));
    Slider2Pos = MySliderValue;
    MySlider2.update(MySliderValue);
    MyDashboard.sendUpdates();
  });

  AsyncElegantOTA.begin(&MyServer);   // Start ElegantOTA
  MyServer.begin();                   // Start server
  MyButton.update(DoBlink); 
  
  MySlider1.update( int(500) );
  MyDashboard.sendUpdates();
}

void loop() {
  AsyncElegantOTA.loop(); // this line enables the OTA-updating
  if (DoBlink) {
    BlinkHeartBeatLED(OnBoard_LED,BlinkFreq / 2); // half and half On/Off
  }
  else {
    digitalWrite(OnBoard_LED,LEDStateOff); 
  }

  if ( TimePeriodIsOver(MyTestTimer,1000) ) {
    Slider2Pos++;
    if (Slider2Pos > 10) {
      Slider2Pos = 0;
    }
    MySlider2.update( int(Slider2Pos) ); // your code can change the sliders value too
    MyDashboard.sendUpdates();
  }  
}

Mit den paar Zeilen hat man dann ein Webinterface
das so aussieht

Und OTA-updaten geht dann über
http://IPadresse/update

und hat einen Standard Datei wählen Dialog


Wenn man das Design OK findet unglaublich effektiv
um ein Webinterface mit Interaktion zu programmieren.
Wenn mehrere Browser Das Webinterface anzeigen lassen wird die Anzeige auf allen Fenstern/Browsern sofort automatisch aktualisiert.

viele Grüße Stefan

Hallo,
das sieht ja einfach aus , müsste man sich mal intensiver mit beschäftigen.

Heinz

Danke, das ist wirklich nicht viel Code für die funktionalität und dass werde ich mir deffinitv etwas genau anschauen.
Leider könnte ich das ja dann nur auf dem einen Microcontroller wo ich auch WiFi habe, oder?
Alle anderen möchte ich ja über Bluetooth oder Ähnlichem die Daten austauschen lassen.

Hallo,

dann schau Dit mal die ESP32 Module an die haben beides.
Heinz

Komputer.de ESP32 nodeMCU 5,80 Euro Bluetooth und WiFi

Gibt es denn schon Module die Bluetooth benutzen und da eingebunden werden sollen? oder machst du alles neu?
vgs

Ja einen ESP32 möchte ich auch verwenden, aber nur für die Schnittstelle zwischen den verschiedenen Modulen.
Also ein ESP32 mit BL, damit werden die verschiedenen Module angesprochen (Beleuchtung, Fernsteröffner, Wetterstation, …)
Und mit dem WiFi vom ESP32 möchte ich eine Website hosten, auf der dann die Daten angezeigt werden.

Nein es gibt eigentlich noch nichts, darum wollte ich auch zuerst noch fragen, ob es sinnvoll ist hier Bluetooth zu verwenden oder doch eher eine Alternative.

Das käme jetzt auf das Gesamtsystem an.
Möchtest du per Smartphone Bluetooth einzelne Aktoren direkt ansprechen oder soll das immer über die zentrale laufen.

Bluetooth funkt auf 2,4 GHz mit gaaanz wenig Leistung damit kommt man nicht besonders weit.
Wenn es eine Zentrale sein soll und die funkt dann Aktoren im ganzen Haus an dann sollte es etwas mit 433MHz sein. Mit der niedrigeren Frequenz kommt man besser durch Wände durch.

WLAN haste wahrscheinlich eh im ganzen Haus verteilt. Das braucht aber ein bisschen mehr Strom. Da musste mit 0,5W pro ESP32 rechnen.
Es sei denn man verwendet deep-sleep-mode. Das würde heißen der Aktor legt sich 50 Sekunden schlafen wacht dann für 10 Sekunden auf und baut eine WiFi-Verbindung auf uns legt sich dann wieder schlafen.
Für Messwerte übermitteln würde das reichen. Für Jalousie hochfahren möchte man wahrscheinlich nicht 1 Minute warten ob was passiert oder nicht.

Ich vermute mal das die nRF24-Module eine größere Reichweite haben als Bluetooth. Das habe ich aber nicht gestestet. Sind aber auch 2,4 GHz. Die nRF24-module können von jedem noch so kleinen Microcontroller angesteuert werden.
vgs

Also strom Probleme habe ich nur bei der Wetterstation, denn die sollte auf die Maueraußenseite und muss daher mit Batterie laufen.
Und die Reichweite ist auch kein wirkliches problem, da sich e alles im Umkreis von 10 Metern befindet und max durch eine Außenmauer muss.
Oder stellt das schon ein Problem dar?
Ich möchte nur kein WLan verwenden, da ich nicht in meinem Zimmer in dem ich mich die meiste Zeit aufhalte und auch schlafe, 10 Geräte mit WLan verbunden haben möchte. (Bluetooth ist da meines Wissens nach etwas “Strahlungs extensiver”)

Ich habe jetzt daran gedacht einfach lauter ESP32 zu verwenden, denn die sind auch nicht teurer als ein Arduino und ein externes BLE modul dazu und dann kann ich ja die Datenübertragung über BLE machen und bei einem Uptdate einfach das WiFi des jeweiligen ESP einschalten und dann kurz hochladen und wieder ausschalten.