Smiley face
Wetterstation WS2000  OpenMQTT Gateway

17.06.2024 19:59:15 Uhr
 22.3& °C   7.8 mm
 999 hPa    7140 Lux
 13.6 km/h  125° +/-45 °

Smiley face
ELV Wetterstation 

17.Juni 20:00 Uhr
 20,2 °C& °C   9,4  mm
 13,1 km/h km/h W-SW ±45° 

Smiley face
DIY Wetterstation!

  June 17 2024 19:56:19 Uhr
125 °C
100 %
0 lux

Smiley face
3D Drucker

Wenn du nicht mehr weißt was du machen sollst fange damit an....

Smiley face
Smart Home

Das ist ein Bild meiner Zentrale, dies ist seit 2020 mit einem Raspberry am Start. 

Smiley face
Node RED

Damit erstelle ich meine Visualisierung meines SmartHomes ein Spielzeug für alle Schiebekinder.

Klima Stein

Der Klima Stein ist die schöne Version der Klimakiste. Vorlage war der Stein Wasser aus dem fünften Element. Das Ding macht nichts anderes als wie Feuchtigkeit und Temperatur messen Anzeigen und die LED (RGB) in verschiedenen Farben leuchten lassen.
Der Prozessor ist ein Arduino Nano der einen SD1306 OLED Anzeige bekommt mit 128x64 Pixel.

Für die Temperaturmessung und Feuchtigkeitsmessung verwende ich einen AHT10.
Mit der RGB LED wird der Stand der Feuchtigkeitsmessung ausgegeben. Grün Fader alles gut, Blau Blinken Luftfeuchtigkeit im Raum zu hoch. Weiter Möglichkeiten kommen eventuell noch hinzu.
Die Bedienung geht über die drei Taster oben auf dem Gerät.
Auf der Linken Taste ist im Normalbetrieb die Durchschnittstemperatur der Letzten Minuten. Gleiches für die Feuchtigkeit auf der Rechten Taste. Mit der Vorderentaste kommt man in das Setupmenü. 
Im Setup des Gerätes kann man die Schwelle für die Feuchtigkeitswarnung sowie die LED Helligkeit einstellen
Ein Problem wo ich am Anfang, völlig naive drüber gestolpert bin,  dass ich es mir leicht machen wollte und einfach die Adafruit Library genommen habe für das Display...  ja schade ruck zuck waren die 32K Byte Speicher voll. Deshalb habe ich die Library nochmal gewechselt mit dem Nachteil das die SD1306ASCII nur Zeichen kann und keinen Zeichnung ( Linien usw.) möglich sind. 


// Stefan Zilt Klimastein
// Version 1.0 20.10.23
#include <Wire.h>
#include <SSD1306Ascii.h>
#include <SSD1306AsciiWire.h>
#include <Adafruit_AHTX0.h>
#include <EEPROM.h>

// AHT10/20
Adafruit_AHTX0 aht;
// Display
#define I2C_ADDRESS 0x3C
#define RST_PIN -1

const char* fontName[] = {
  "Arial14",
  "Arial_bold_14",
  "Callibri11",
  "Callibri11_bold",
  "Callibri11_italic",
  "Callibri15",
  "Corsiva_12",
  "fixed_bold10x15",
  "font5x7",
  "font8x8",
  "Iain5x7",
  "lcd5x7",
  "Stang5x7",
  "System5x7",
  "TimesNewRoman16",
  "TimesNewRoman16_bold",
  "TimesNewRoman16_italic",
  "utf8font10x16",
  "Verdana12",
  "Verdana12_bold",
  "Verdana12_italic",
  "X11fixed7x14",
  "X11fixed7x14B",
  "ZevvPeep8x16"
};
const uint8_t* fontList[] = {
  Arial14,
  Arial_bold_14,
  Callibri11,
  Callibri11_bold,
  Callibri11_italic,
  Callibri15,
  Corsiva_12,
  fixed_bold10x15,
  font5x7,
  font8x8,
  Iain5x7,
  lcd5x7,
  Stang5x7,
  System5x7,
  TimesNewRoman16,
  TimesNewRoman16_bold,
  TimesNewRoman16_italic,
  utf8font10x16,
  Verdana12,
  Verdana12_bold,
  Verdana12_italic,
  X11fixed7x14,
  X11fixed7x14B,
  ZevvPeep8x16
};
uint8_t nFont = sizeof(fontList)/sizeof(uint8_t*);

SSD1306AsciiWire display;

// Trendvariablen
int trent_x = 0;
int trent_n = 300; // Durchschnittswerte ins sek
float temp_trent;
float hydr_trent;
float temp_t;
float hydr_t;
float temp_t2;
float hydr_t2;
char temp_txt[8];
char hydr_txt[8];
int balken = 0;
bool balken_x = true;
float test;
float temperatur_ist;
float feuchtigkeit_ist;
char text;
// INput
int Taster = 2;
int Taster_status = 0;

// Loopvar
long Timer_1 = millis();
// RGB LED
int LEDblau = 5; // Farbe blau an Pin 3
int LEDrot = 3; // Farbe rot an Pin 5
int LEDgruen=6; // Farbe gruen an Pin 6
int brightness1a = 100; 
int brightness1b = 100; 
int brightness1c = 100; 
int dunkel = 255; // Zahlenwert 0 bedeutet Spannung 0V – also LED aus.
int dimmer_ok = 0;
int led_helligkeit;
int led_I = 1;
// Menue Var
bool menue_on = false;
int menue_pos= 0;
char* menue_txt;
int menue_wert;
long menue_ontime = millis();   
long untermenue_klick = millis();
int grw_feuchte=1;
long Auswahl_entprellen = 0;
long Auswahl_entprellen_UP = 0;
long Auswahl_entprellen_DOWN = 0;
bool tippup= false;
bool tippdown= false;
bool auswahl= false;
char* texter;
char* number;
float zwergli;
long LED_BLINKER = millis();
bool BLINKER = false;
int TMP[5];
int DB_Feuchte[20];
int DB_F = 0;
int aa;
bool line_f = false;
long line_f_time;
bool line_f2 = false;
long line_f_time2;
bool led_fade = true;
bool led_feuchte_hysterese = false;
int display_hintergrund = false;
// Setup
void setup() {
  Wire.begin();       
  Wire.setClock(400000L);
  Serial.begin(9600);
  display.begin(&Adafruit128x64, I2C_ADDRESS, RST_PIN);
    
// starten AHT10
  if (!aht.begin()) {
      Serial.println("Kein Geber AHT? Check");
      delay(100);
      } 
 // EE-Promm lesen
   grw_feuchte = read_int(0);
    if (grw_feuchte < 1 ||  grw_feuchte > 512 ){
        grw_feuchte = 60;
       }
        TMP[0] = grw_feuchte;  

  led_helligkeit = read_int(2);
  if (led_helligkeit < 1 ||  led_helligkeit > 200 ){
        led_helligkeit = 100;
        }  
      TMP[1] = led_helligkeit;
  display.setFont(Verdana12);
  display.clear();
// IOs Konfig
pinMode(LEDblau, OUTPUT);
pinMode(LEDgruen, OUTPUT);
pinMode(LEDrot, OUTPUT);
pinMode(10, INPUT_PULLUP);
pinMode(11, INPUT_PULLUP);
pinMode(12, INPUT_PULLUP);
}
// Normalprogram
void loop() {
// Tasten abrufen
int taste1 = digitalRead(11);
int Taster_up = digitalRead(10);
int Taster_down = digitalRead(12);

if(taste1 == LOW && Auswahl_entprellen < millis()){
   menue_ontime = millis();
   menue_on = true;
   auswahl = true;
   Auswahl_entprellen = 300 + millis();
   menue_ontime = millis();
   menue_pos++;
   if (menue_pos > 3){menue_pos = 1;}
   }

if(Taster_up == LOW && Auswahl_entprellen_UP < millis()){
   menue_ontime = millis();
   Auswahl_entprellen_UP = 80 + millis();
   tippup = true;
   }

if(Taster_down == LOW && Auswahl_entprellen_DOWN < millis()){
   menue_ontime = millis();
   Auswahl_entprellen_DOWN = 80 + millis();
   tippdown = true;
   }
// Taste Rechts Anzeige ausgeben
if(tippup == true && menue_on == false ){
  line_f = true;
  tippup = false;
  line_f_time = millis();
    display.clear();
    display.setFont(fixed_bold10x15);
    display.set1X();
    display.setCursor(0, 0); 
    display.println("Feuchte");
    display.set2X();
    display.setCursor(0, 30);
    display.println(hydr_t,1);
    display.setCursor(90, 30);
    display.print("%");
    display.set1X();
    display.setCursor(0,40);
    display.println("Schnitt");
    display.setCursor(84,40);
    display.println(trent_n/60);
    display.setCursor(98,40);
    display.print("min");

}
if(line_f == true && line_f_time+3000 < millis()){
   line_f = false; 
   display.clear();
}

// Taste Links Anzeige ausgeben
if(tippdown == true && menue_on == false ){
  line_f2 = true;
  tippdown = false;
  line_f_time2 = millis();
    display.clear();
    display.setFont(fixed_bold10x15);
    display.set1X();
    display.setCursor(0, 0); 
    display.println("Temperatur");
    display.set2X();
    display.setCursor(0, 30);
    display.println(temp_t,1);
    display.setCursor(90, 30);
    display.print("C");
    display.set1X();
    display.setCursor(0,40);
    display.println("Schnitt");
    display.setCursor(84,40);
    display.println(trent_n/60);
    display.setCursor(98,40);
    display.print("min");

}
if(line_f2 == true && line_f_time2+3000 < millis()){
   line_f2 = false;
   display.clear();
}

// Taste Vorne Setupmenüe aufrufen
if(auswahl == true && menue_on == true && line_f == false && line_f2 == false){
   menue_wert=0;
    display.clear();
    TMP[0]=grw_feuchte;
     
    switch (menue_pos)
                  {
                      case 0:
                        break;   
                      case 1:
                        menue_txt = "Setup\n Klimastein\n Ver. 1.0";
                        break;                     
                      case 2:
                        menue_txt = "Feuchte";
                        menue_wert = grw_feuchte;
                        break;                      
                      case 3:               
                        menue_txt = "LEDlight";
                        menue_wert=led_helligkeit;                
                        break;                                             
                      default:
                        break;
                 }  
auswahl = false;
}

if(tippup == true && menue_on == true || tippdown == true && menue_on == true){      
 Serial.println("drin");
      switch (menue_pos)
                  {
                      case 1:
                            
                        break;
                      case 2:                           
                            if(tippup == true ){ grw_feuchte++  ;}
                            if(tippdown == true ){ grw_feuchte--  ;}  
                              if(grw_feuchte < 1){grw_feuchte = 1;} 
                              if(grw_feuchte > 95){grw_feuchte = 95;}   
                              menue_wert=grw_feuchte;                                      
                      break; 
                      case 3:                    
                            if(tippup == true ){ led_helligkeit++  ;}
                            if(tippdown == true ){ led_helligkeit--  ;}  
                              if(led_helligkeit < 1){led_helligkeit = 1;} 
                              if(led_helligkeit > 200){led_helligkeit = 200;}   
                              menue_wert=led_helligkeit;     
                        break;                        
                      default:
                        break; 
                  }
    tippup = false;
    tippdown = false;
}
 
 if(menue_on==true){
  
   display.set1X();
   display.setCursor(0, 0);
   texter = menue_txt;
   display.println(texter);
   if(menue_wert>0){
   display.setCursor(0, 40);
   display.set2X();
   display.println(menue_wert);
   }
} 

if(menue_on == true && (menue_ontime+3000) < millis()){
    menue_pos = 0;
    menue_on = false;
     menue_txt = "";
    menue_wert = ".";
    // Autosave bei Änderung
    if(grw_feuchte != TMP[0]){
       write_int(0, grw_feuchte );
      }
    if(led_helligkeit != TMP[1]){
       write_int(2, led_helligkeit );
      }
      display.clear();
}

  if (Timer_1+1000 < millis()){
      // Sensor AHT 10/20
          sensors_event_t humidity, temp;
          aht.getEvent(&humidity, &temp);
          temperatur_ist =  temp.temperature;
          feuchtigkeit_ist = humidity.relative_humidity;
          temp_trent = temp_trent + temperatur_ist;
          hydr_trent = hydr_trent + feuchtigkeit_ist;
          trent_x++;
 
  if (trent_x == trent_n ) {
    if(display_hintergrund == 0){display_hintergrund = 1;}
      else{display_hintergrund = 0;}
        display.invertDisplay(display_hintergrund);
    // Durchschnitt
    temp_t2 = round(temp_trent*10.0 / trent_n)/10.0;
    hydr_t2 = round(hydr_trent*10.0 / trent_n)/10.0;
    trent_x = 1;
    temp_trent = temp_t = temp_t2;
    hydr_trent = hydr_t = hydr_t2;
  }
 
  if (menue_on == false && line_f == false && line_f2 == false) {  
       balken = round(128 / trent_n * trent_x);
          if(balken_x==false){
             dimmer_ok = 255-(balken/2);
             }
           else{
            dimmer_ok = (balken/2)+150;
            }
  }
 
 if (Timer_1+1000 < millis() && menue_on == false && line_f == false && line_f2 == false){ 
    display.setFont(fixed_bold10x15); 
    display.set2X();
    display.setCursor(0, 0);
    display.println(temperatur_ist,1);
    display.setCursor(90, 0);
    display.println("C");
    display.setCursor(5, 52);
    display.println(feuchtigkeit_ist,1);
    display.setCursor(92, 52);
    display.println("%");
  }

// RGB LED Ansteuerung
if((LED_BLINKER+1000)<millis()){
    //Fader
    if(led_I<led_helligkeit && led_fade == true){ led_I++;}
     if(led_fade == false){ led_I--;}
      if(led_I==led_helligkeit){led_fade = false;}
        if(led_I == 1){led_fade=true;}
     // Blinktakt 
      if(BLINKER==false){
          BLINKER=true;
         }
        else{ BLINKER=false;}
  LED_BLINKER = millis();
 }
 analogWrite(LEDgruen, dunkel);
 analogWrite(LEDblau, dunkel);
 analogWrite(LEDrot, dunkel);
//LED Blau wenn zu feucht
if(float(grw_feuchte)<feuchtigkeit_ist||led_feuchte_hysterese==true){
    led_feuchte_hysterese=true;
    if(BLINKER==true){
        analogWrite(LEDblau, 255-led_helligkeit);
    }
    else{
        analogWrite(LEDblau, dunkel);
    } 
  }
if(feuchtigkeit_ist<float(grw_feuchte)-3.0){ led_feuchte_hysterese = false;}
if(led_feuchte_hysterese==false){   
      analogWrite(LEDgruen, 255-led_I);
  }
    Timer_1 = millis();
 }
}
// Lesen aus EEPROM
int read_int(int address)
{
  long byte_2 = EEPROM.read(address);
  long byte_1 = EEPROM.read(address + 1);
  int val = ((byte_2 << 0) & 0xFFFFFF) + ((byte_1 << 8) & 0xFFFFFFFF);
  return val;
}
// Schreibe in EEPROM
void write_int(int address, int value)
{
  byte byte_2 = (value & 0xFF);
  byte byte_1 = ((value >> 8) & 0xFF);
  EEPROM.update(address, byte_2);
  EEPROM.update(address + 1, byte_1);
}


 
Klima Stein
AHT10 I2C SensorDeckel Unterseite
Klimastein Grundkörper