• Witaj na Forum Arduino Polska! Zapraszamy do rejestracji!
  • Znajdziesz tutaj wiele informacji na temat hardware / software.
Witaj! Logowanie Rejestracja


Ocena wątku:
  • 0 głosów - średnia: 0
  • 1
  • 2
  • 3
  • 4
  • 5
Hydrostat na DHT22 z opóźnieniem wyłączenia
#1
Witam,
na początek chciałbym się przywitać, ponieważ jestem nowy na tym forum.
Zatem witam serdecznie wszystkich na forum Smile

Mam następujący problem, którego nie potrafię rozwiązać.
Jestem w trakcie budowania higrostatu, który jest zbudowany na czujniku DHT-22.
Wyniki są wyświetlane na TFT 5".
W założeniach, urządzenie mierzy wilgotność w łazience i jeśli przekroczy ona 65% ma załączyć przekaźnik. Nie byłoby w tym nic dziwnego gdyby nie fakt, że potrzebuję wyłączyć przekaźnik dopiero przy 60% lub (niby prościej) - po osiągnięciu 65% wilgotności jeszcze działać przez zadany czas. Potrzebna mi ta funkcja ponieważ urządzenie działa w tej chwili następująco: po włączeniu przekaźnika włącza się wentylator, który pracując przez kilka sekund obniża wilgotność i osiągając <65% się wyłącza. Po kilku sekundach znowu narasta wilgotność na czujniku i znowu się włącza przekaźnik... Jest tak 3-5 razy zanim się ustabilizuje. Jeśli udałoby mi się tak zmodernizować kod aby wentylator się włączał po osiągnięciu 65% a wyłączał po 60% wydaje mi się, że problem byłby rozwiązany. Drugą opcją byłoby po osiągnięciu wilgotności <=65% aby wentylator pracował jeszcze przez ustalony czas (np. 20 sek.)

A oto mój kod:
Kod:
// Arduino Higrostat - DHT-22 na bazie
// Example testing sketch for various DHT humidity/temperature sensors
// Written by ladyada, public domain

#include <UTFT.h>
#include "DHT.h"

#define DHTPIN A0       // what digital pin we're connected to
#define DHTTYPE DHT22   // DHT 22  (AM2302), AM2321
#define fan A2          // Wentylator

extern uint8_t UbuntuBold[];

int maxHum = 65;
int maxTemp = 35;

// Initialize DHT sensor.
DHT dht(DHTPIN, DHTTYPE);

// Initialize UTFT
UTFT myGLCD(ITDB50,38,39,40,41);    // Standard Arduino Mega/Due shield

void setup() {
 pinMode(fan, OUTPUT);
 myGLCD.InitLCD();
 myGLCD.InitLCD(LANDSCAPE);
 myGLCD.setFont(UbuntuBold);
 myGLCD.clrScr();
 
 //Serial.begin(9600);
 //Serial.println("DHTxx test!");
 myGLCD.print("DHTxx test!", CENTER, 10);
 dht.begin();
}

void loop() {
 // Wait a few seconds between measurements.
 delay(2000);
 
 myGLCD.clrScr();
 
 // Reading temperature or humidity takes about 250 milliseconds!
 // Sensor readings may also be up to 2 seconds 'old' (its a very slow sensor)
 float h = dht.readHumidity();
 // Read temperature as Celsius (the default)
 float t = dht.readTemperature();

 // Check if any reads failed and exit early (to try again).
 if (isnan(h) || isnan(t)) {
   // Serial.println("Failed to read from DHT sensor!");
   myGLCD.print("Failed to read from DHT sensor!", CENTER, 30);
   return;
 }
 if(h > maxHum || t > maxTemp) {
    digitalWrite(fan, HIGH);
    myGLCD.print("Wentylator: ON ", 20, 400);
 }
 else {
    digitalWrite(fan, LOW);
    myGLCD.print("Wentylator: OFF", 20, 400);
 }

 // Compute heat index in Celsius (isFahreheit = false)
 float hic = dht.computeHeatIndex(t, h, false);
 // Serial.print("Humidity: ");
 // Serial.print(h);
 // Serial.print(" %\t");
 myGLCD.print("Wilgotnosc: ", 20, 100);
 myGLCD.printNumF(h, 1, 320, 100);
 myGLCD.print("%", 450, 100);
 
 // Serial.print("Temperature: ");
 // Serial.print(t);
 myGLCD.print("Temperatura: ", 20, 200);
 myGLCD.printNumF(t, 1, 320, 200);
 myGLCD.print("`C", 450, 200);
 // Serial.print(" *C ");
 // Serial.print("Heat index: ");
 // Serial.print(hic);
 myGLCD.print("Humidex: ", 20, 300);
 myGLCD.printNumF(hic, 1, 320, 300);
 myGLCD.print("`C", 450, 300);
 myGLCD.setColor(255, 255, 255);
 // Serial.print(" *C ");
}
 
Odpowiedź
#2
Witam
Masz tu klasyczny przykład histerezy. Przy przekaźnikach może to nawet doprowadzić do migotania i sklejenia zestyków - czyli bardzo niebezpieczne zjawisko. 
Jak sobie z tym poradzić? 
Przez wprowadzenia do klasycznej teorii sterowania histerezy właśnie :-)
Czyli dodaj do swojego programu zmienną globalną:
volatile int histereza=0;
a potem w kodzie:
Kod:
if(h > (maxHum+histereza) || t > maxTemp) {
   histereza=-5;
   digitalWrite(fan, HIGH);
    myGLCD.print("Wentylator: ON ", 20, 400);
 }
 else {
   histereza=0;
   digitalWrite(fan, LOW);
    myGLCD.print("Wentylator: OFF", 20, 400);
 }
  To volatile jest po to aby procesor nie upraszczał sobie zadania, i zmieniał wartość histerezy na bieżąco, bez uproszczeń (tzn. dopiero po wyjściu z if-a na przykład). Można tego nie robić, ale lepiej warto :-)
Pozdrawiam
 
Odpowiedź
#3
Thumbs Up 
Bardzo dziękuję za pomoc "wojtekizk". O taki efekt mi chodziło. Pozdrawiam serdecznie.
 
Odpowiedź
  


Skocz do:


Przeglądający: 1 gości