ESP8266 (Wemos D1 mini) Eltako Windmesser

Hallo zusammen
Habe ein Eltako ESP8266 (Wemos D1 mini) Windmesser im einsatz den muss ich von seinem Urspruenglichen Ort wegnehmen und an einen anderen Ort setzen. Habe den immer mit USB spannung versorgt und hat auch gut funktioniert aber nun muss der an einen ort wo ich kein Strom habe oder hinbauen kann also muss er ueber Batterie betrieben werden.

Mein Code:

#include <ESP8266WiFi.h>
#include "settings.h"
#include <ESP8266HTTPClient.h>
#include <ESP8266httpUpdate.h>
#include <PubSubClient.h>
#include <Wire.h>
#include <LiquidCrystal_I2C.h>

//LiquidCrystal_I2C lcd(0x26,20,4);
LiquidCrystal_I2C lcd(0x27,20,4);

unsigned long  next_timestamp = 0;
volatile unsigned long i = 0;
float wind = 0;
float last_wind = 0;
int count = 0;
volatile unsigned long last_micros;
long debouncing_time = 5; //in millis
int input_pin = 13;
char charBuffer[32];

WiFiClient espClient;
PubSubClient client(espClient);

void ICACHE_RAM_ATTR Interrupt()
{
  if((long)(micros() - last_micros) >= debouncing_time * 1000) {
    i++;
    last_micros = micros();
  }
}

void setup() {
  lcd.init();
  lcd.clear();
  lcd.backlight();
  Serial.begin(115200);
  delay(10);
  pinMode(input_pin, INPUT_PULLUP);//D7
  // We start by connecting to a WiFi network
  if(debugOutput){
    Serial.println();
    Serial.println();
    Serial.print("Verbinde mit ");
    lcd.setCursor(0, 0);
    lcd.print("Verbinde mit ");
    Serial.println(ssid);
    lcd.setCursor(0, 1);
    lcd.print(ssid);
  }
  WiFi.persistent(false);
  WiFi.mode(WIFI_STA);
  WiFi.begin(ssid, password);
  int maxWait = 500;
  while (WiFi.status() != WL_CONNECTED) {
    delay(500);
    if(debugOutput) Serial.print("."); 
    lcd.print(".");
    if(maxWait <= 0)
     ESP.restart();
    maxWait--;
  }
  if(debugOutput){
    delay(1000);
    lcd.clear();
    Serial.println("");
    Serial.println("WiFi Verbunden"); 
    lcd.print("WiFi connected");
    delay(10); 
    Serial.println("IP address: ");
    Serial.println(WiFi.localIP());
    lcd.setCursor(0, 0);
    lcd.print(ssid);
    lcd.setCursor(0, 1);
    lcd.print("IP address: ");
    lcd.setCursor(0, 2);
    lcd.print(WiFi.localIP());
    lcd.setCursor(0, 3);
    lcd.print("(c) 2022 by Th.Alex");
    delay(100);
//
//lcd.clear();
  }
  delay(500);
//  do_update();
  client.setServer(mqtt_host, mqtt_port);
  reconnect();
  attachInterrupt(input_pin,Interrupt,RISING);
}


void loop() 
{
  if (millis() > next_timestamp )    
  { 
    detachInterrupt(input_pin);
    count++; 
    float rps = i/number_reed; //computing rounds per second 
    if(i == 0)
      wind = 0.0;
    else
      wind = 1.761 / (1 + rps) + 3.013 * rps;// found here: https://www.amazon.de/gp/customer-reviews/R3C68WVOLJ7ZTO/ref=cm_cr_getr_d_rvw_ttl?ie=UTF8&ASIN=B0018LBFG8 (in German)
    if(last_wind - wind > 0.8 || last_wind - wind < -0.8 || count >= 10){
      if(debugOutput){
        lcd.clear();
        lcd.setCursor(0, 0);
        lcd.print("Eltako Anemometer");
        lcd.setCursor(0, 1);
        lcd.print("--------------------");
        Serial.print("Wind: ");
        lcd.setCursor(0, 2);
        lcd.print("Wind: ");
        Serial.print(wind);
        lcd.print(wind);
        Serial.println(" km/h");
        lcd.print(" km/h");
        lcd.setCursor(0, 3);
        lcd.print("(c) 2022 by Th.Alex");
      }
      String strBuffer;
      strBuffer =  String(wind);
      strBuffer.toCharArray(charBuffer,10);
      if (!client.publish(mqtt_topic_prefix, charBuffer, false))
      {
        ESP.restart();
        delay(100);
      }
      count = 0;
    }
    i = 0;
    last_wind = wind;
    if(WiFi.status() != WL_CONNECTED) {
      ESP.restart();
      delay(100);
    }
    next_timestamp  = millis()+1000; //intervall is 1s
    attachInterrupt(input_pin,Interrupt,RISING);
  }
  yield();
}

void reconnect() {
  int maxWait = 0;
  while (!client.connected()) {
    if(debugOutput) Serial.print("Attempting MQTT connection...");
    if (client.connect(mqtt_id)) {
      if(debugOutput) Serial.println("connected");
    } else {
      if(debugOutput){ 
        Serial.print("failed, rc=");
        Serial.print(client.state());
        Serial.println(" try again in 5 seconds");
      }
      delay(5000);
      if(maxWait > 10)
        ESP.restart();
      maxWait++;
      delay(5000);
      ESP.deepSleep(9e8); //9e8 = 15 min
    }
  }
}


Das Programm arbeitet seit 2 Jahren einwandfrei nur jetzt muss deep sleep rein was ich auch getan habe aber es funktioniert nicht der Sensor geht nicht Schlafen was in der Serial console festzustellen ist.
Die pins RST und D0 sind durch einen Jumper gebrueckt.

Brauche mal eure Hilfe denn irgendwas mach ich sicher falsch

Danke im vorraus
Hitman43

Warum?

Na der Wemos muss auch wieder wach werden nach 15 min
Sorry hab mich verschrieben meine RST und D0

Beschreibe mal besser das Fehlerbild.
Dein loop() erreichst du nicht, da du im setup() -> reconnect() schon schlafen gehst.

Baue dir Serielle Ausgaben ein, um herauszufinden wo er falsch abbiegt.

Ein verlassen des DeepSleeps kommt einem Reset/Neustart des Programms gleich.

Ich habe einen Windsensor (sihe Bild) der ueben eine USB Stromversorgung aus dem Haus hatte und das hat auch funktioniert. Jetzt soll der sensor aber ueber Batterie laufen und dazu muss er in den Deep.Sleep modus sonst ist die Batterie schnell leer.

Der Sensor sendet seine Daten wie mit der USB stromversorgung und geht nicht schlafen siehe Bild2

Und das soll er beben nicht tun. Der Wemos Geht nicht schlafen obwohl deep.sleep im Programm steht

Hallo,
mich stören die vielen esp.restart() in Deinem code. Aber das nur nebenbei.
Bau doch mal von den deepsleep noch eine Serielle Ausgabe ein .
Serial.println("gehe jetzt schlafen")
um zu sehen ob du da hinkommst .Zudem sollte nach dem deepsleep noch ein delay() kommen.

bei mir sieht das so aus.

WiFi.disconnect(true);
  delay(1);
  WiFi.mode(WIFI_OFF);
  WiFi.forceSleepBegin ();
  delay(1);
 Serial.println("gehe jetzt pennen");
  ESP.deepSleep(sl * 1000000, WAKE_NO_RFCAL);
  delay(1);

Die serielle ausgabe hab ich schion drinne

     delay(200);
      Serial.print("Ich gehe nu fuer 15 min schlafen");
      ESP.deepSleep(9e+8);
      delay(100);

Aber das wird auch nicht in der serial konsole angeigt

OK dann ist dein Problem ja nicht der deep Sleep sondern ehr Dein Code, Du kommst da nicht hin.

Ich kenne mich mit Mqt nicht aus , aber irgendwann muss das Telegram ja beendet sein und das ist dann das Ende. Zudem würde ich vor dem deepsleep noch die ISR für das Windrad abschalten also Interrupt sperren damit nicht ständig die ISR dazwischen funken kann.

Du könntest auch die ganz harte Tour nehmen und im loop millis() abfragen. wenn der Wert > z.B 20s ist verzweigst Du zum deep sleep und Schluss is...

Das werde ich heute abend mal austesten gebe dann bescheid

Hallo,
ich hab mir mal Deinen Code etwas näher angesehen. Ich finde gar nicht nicht die Stelle wo die Fuction aufgerufen wird.
Bin ich blind :joy:

doch ist ziemlich weit unten drinne

void reconnect() {
  int maxWait = 0;
  while (!client.connected()) {
    if(debugOutput) Serial.print("Attempting MQTT connection...");
    if (client.connect(mqtt_id)) {
      if(debugOutput) Serial.println("connected");
    } else {
      if(debugOutput){ 
        Serial.print("failed, rc=");
        Serial.print(client.state());
        Serial.println(" try again in 5 seconds");
      }
      delay(5000);
      if(maxWait > 10)
        ESP.restart();
      maxWait++;
      delay(5000);
      ESP.deepSleep(9e8); //9e8 = 15 min
    }
  }
}

Hallo
das habe ich schon gefunden , das ist ja die Function selbst, aber wo wird sie aufgerufen ?

Oh ja dann hab ich das wohl vergessen ist ja auch schon nen weile her das ich das gemacht hab. Aber wo muesste die dann reinkommen und wie schaut die aus

Na ja
ich schließe daraus das der code letztlich nicht von Dir ist. Wenn man die Function nicht benötigt dann lass sie halt raus. Es geht doch darum.

aufwecken
Einrichten
einmal messen
versenden
schlafen gehen

Jetzt musst Du halt rausbekommen wann die Arbeit erledigt ist , oder du machst die brutale Art und fragst millis() ab und verzweigst.

Was für eine Batterie hast Du denn vor zu nutzen. Du hast ja anscheinend auch noch eine Anzeige dran. Die kann ja sicher komplett weg. Wenn der D1 läuft und WIFI ein ist musst Du im Mittel mindestens mit 100mA rechnen. Hast Du schon mal eine Energie-Bilanz berechnet. Nicht das Du anschließend enttäuscht bist wenn die Batterie nach 1Woche leer ist.

Am Ende vom setup()

Generell gehört der Code neu aufgebaut. Ein Loop braut es eigentlich nicht beim DeepSleep. Der ESP wacht auf, erledigt alles im Setup, geht am Ende vom Setup schlafen.

da hast du auch recht den hat kumpel geschrieben und bei ihm funktioniert der genauso wie bei mir nur er hat seinen sensor am gartenhaus wo auch festern strom ist

Bin da nicht so gut in sowas zu schreiben da brauche ich dann hilfe

Es kommen 3,7V 1000mA lipro Akkus zum Einsatz

Stimmt , da macht das deepSleep aber so keinen Sinn. Ja da hast Du recht der code ist so ungeeignet. Darum würde ich die Murx Methode vorschlagen. :wink:

deepsleep kann schon im loop Sinn machen denke ich. Es kommt darauf an was zu machen ist. Und wann dann der Job erledigt ist. Für die Messung des Windrades hier in dem Beispiel wird ja eine endliche Zeit benötigt, also mehrere Umläufe. Wenn man das nur im Setup machen wollte müsste man also eine künstliche Schleife programieren. Gleiches Gilt sicher für das versenden der Daten. Man kann das schon im loop machen es braucht zwei Statusszstände
1 Messung beendet Messwert liegt vor
2 Daten sind gesendet ( eventuell Antwort vom Server auswerten)

dann in eine Function verzweigen die die Verbindung zum WIFI abbaut und den deepsleep ausführt.
Das könnte man noch in einer Schrittkette Statemaschine machen.

Gruß Heinz

werde mich damit in ruhe besassen denn bei mir dauert sowas bin ja kein fachmann da drinne

ich hatte mir mal eine excell Tabelle gemacht das mal für Deinen Fall gerechnet . Annahme die Laufzeit beträgt 20s und es gibt keine wesentlichen Stromverbraucher außer dem D1

System Daten
Zykluszeit gesamt 900 s
davon aktiv Zeit 20 s
sleep Zeit 880 s
Mittlerer aktiv Strom 100 mA
sleep Modus 0,4 mA
mittler Strom eins Zyklus 2,613 mA
System Spannung 3,7 V
System Leistung 9,67 mW
Energieverbrauch/Tag (Arbeit) 232,06 mWh
Batterie-Daten
Batterie Kapazität 1000 mAh
Batterie Spannung 3,7 V
Energie Aku 3700 mWh
Wirkungsgrad Stromversorgung 80 %
nutzbare Energie (Arbeit) 2960,00 mWh
Batterie Laufzeit ohne Ladung 12,76 Tage

das sind jetzt theoretische Werte , real wird das ehr weniger sein. Im Winter wenn es kalt ist haben die Akus auch ehr 50% Kapazität.
so in Etwa sieht´s aus

Das Problem ist auch, das wenn man ein ESP im Akkubetrieb betreibt, der Code so schnell wie möglich abgearbeitet werden soll.

Ich vermute, der TO wird kaum über 1 Monat Laufzeit kommen, wenn er es so Aufbaut und belässt.

Der effektivere Weg wäre, etwas Stromsparendes wie ATTiny, der die Messwerte ausarbeitet, dieses dann zum Bsp. über nRF24 oder ähnliches zu einem stationären ESP der das dann ins Homegedöns einbindet.