Czujnik temperatury - zasilanie bateryjne

Masz pomysł na funkcjonalność lub koncepcję na rozwój projektu. Opisz wszystko tutaj.
Komar000
Posts: 31
Joined: Mon Feb 12, 2018 9:28 am

Post

Mam pomysł na zrobienie czujnika d18b20 podłączonego (nie bezpośrednio) do supli, z zasilaniem akumulatorowym. Działałoby to w ten sposób:
Esp(client) łączy się do sieci wifi pobiera dane z czujnika np temperatura i wysyła je do drugiego esp(server), który jednocześnie może być przekaźnikiem, sterownikiem rgb itp. Po czym esp(client) przechodzi w deep sleep, a esp(server) umieszcza na cloud otrzymaną wartość biorąc ją ze zmiennej.
Przy częstotliwości pomiaru co około 6 min bateria 18650 powinna wytrzymać kilka miesięcy.
Programuję w Arduine IDE. Połączenie miedzy esp i przesył danych mam ogarnięte, nie wiem tylko jak umieścić na supli wartość temperatury. Próbowałem przypisać wartość do parametru "t" i inne różne wariacje, ale to nie przynosi efektu, w supli mam cały czas ---

Code: Select all

double get_temperature(int channelNumber, double last_val) {

    double t = tempespclient;
    
   // if ( sensors.getDeviceCount() > 0 )
   //   {
     //    sensors.requestTemperatures();
     //    t = sensors.getTempCByIndex(0);
     // };

    return t;  
}
Podrzucie info jak ktoś wie, w którym miejscu kodu mogę podać wartość temp tak, aby w supla cloud była widoczna poprawnie.
User avatar
Duch__
Posts: 1785
Joined: Wed Aug 24, 2016 7:26 pm
Location: Opole

Post

Dopóki na serwerze nie zostanie ogarniety temat znikającej temperatury po zerwaniu łączności z modułem to zapomnij. Pzygmunt powinien sie wypowiedzieć na ten temat. Obecnie u mnie pracują czujniki w oparciu o thingspeak. Chciałem nawet odczytywać wyniki z thingspeaka i wrzucać je na suple co mi się udało, ale przy każdym odczycie, na moment zrywa połączenie z suplą i zamiast ostatniej wartości pojawiał mi się symbol ---. Na obecną chwilę zmuszony jestem zostać przy własnym zewnetrznym rozwiazaniu. Co do kodu to zerknij tutaj: viewtopic.php?f=11&t=2989 Zamieściłem tam kod do czujnika pyłu który podszywa się pod czujnik temperatury. Swoją drogą jak łączysz się pomiędzy ESP? Możesz wrzucić fragment jakiegoś kodu?
You do not have the required permissions to view the files attached to this post.
Image
User avatar
shimano73
Posts: 1976
Joined: Sun Feb 28, 2016 12:27 pm
Location: Orzesze

Post

Temperatura w zmiennej t musi się zmieniać . Robiłem to tak , ze pierwszy odczyt był oryginalny przy drugim dodawałem 0.5 stopnia i tak w petli. Tak działają moje BME . Chyba Przemek pisał ze wystarczy jeden taki myk bez pętli.
W elektronice jak nie wiadomo o co chodzi to zwykle chodzi o zasilanie

Wezmę udział w Supla Offline Party 2024 :)
Komar000
Posts: 31
Joined: Mon Feb 12, 2018 9:28 am

Post

Ja komunikację między ESP rozwiązałem tak:

ESP Server:

Code: Select all

#include <ESP8266WiFi.h>

String  tempertura;
IPAddress staticIP46_10(192,168,1,10);
IPAddress gateway46_10(192,168,1,1);
IPAddress subnet46_10(255,255,255,0);

WiFiServer server(80);

void setup()
{
  tempertura = "";

  Serial.begin(9600);
    WiFi.disconnect();
  delay(3000);
  Serial.println("Uruchamiam...");
   WiFi.begin("my-net","mypass");
  while ((!(WiFi.status() == WL_CONNECTED))){
    delay(300);
    Serial.print("..");

  }
  Serial.println("Polaczony");
  WiFi.config(staticIP46_10, gateway46_10, subnet46_10);
  Serial.println("Twoj IP to:");
  Serial.println((WiFi.localIP()));
  server.begin();

}


void loop()
{

    WiFiClient client = server.available();
    if (!client) { return; }
    while(!client.available()){  delay(1); }
    tempertura = (client.readStringUntil('\r'));

}
ESP Client:

Code: Select all

#include <ESP8266WiFi.h>

#include <ESP8266HTTPClient.h>

String  i;
IPAddress staticIP26_11(192,168,1,11);
IPAddress gateway26_11(192,168,1,1);
IPAddress subnet26_11(255,255,255,0);

String  httpurl;
HTTPClient http;

void setup()
{
  i = "-300";

  Serial.begin(9600);
    WiFi.disconnect();
  delay(3000);
  Serial.println("Uruchamiam");
   WiFi.begin("my-net","mypass");
  while ((!(WiFi.status() == WL_CONNECTED))){
    delay(300);
    Serial.print("..");

  }
  Serial.println("Polaczony");
  WiFi.config(staticIP26_11, gateway26_11, subnet26_11);
  Serial.println("Twoj IP to:");
  Serial.println((WiFi.localIP()));

}


void loop()
{

    httpurl = "http://";
    httpurl+="192.168.1.10";
    httpurl+="/";
    httpurl+=i;
    http.begin(httpurl);
    http.GET();
    http.end();
    ESP.deepSleep(355e6); // deep sleep na 355 sekund

}
Jak na serwerze odbierzesz pakiet to musisz go jeszcze odpowiednio przyciąć i przekonwertować ze string do double.

A wracając do umieszczania temperatury na cloud, rozumiem, że wystarczy mniej więcej taka modyfikacja w kodzie?

Code: Select all

double get_temperature(int channelNumber, double last_val) {

    double t = tempespclient;
    delay(100);
    t += 0,05;
    delay(100);
    t -= 0,06;
 

    return t;  
}
Czy konieczne jest jeszcze przyspisanie zmiennej do last_val?

Code: Select all

last_val = t;
Edit:
Siedząc w pracy mnie chyba trochę olśniło. Pewnie nie chodzi o dodawanie i odejmowanie od t a raczej żeby client wysyłał dwa (różne) pomiary w krótkim odstępie czasu np 100 ms.
Tak czy inaczej wieczorem sprawdzę, jak będzie działać wrzucę wemosa w zew zasilanie i zrobie praktyczny test ile czasu wytrzyma :)
User avatar
shimano73
Posts: 1976
Joined: Sun Feb 28, 2016 12:27 pm
Location: Orzesze

Post

Tak , właśnie o to chodziło , tylko ja wtedy jeszcze o tym nie wiedziałem :?
Przyznam że rozwiązałeś mój problem w jednym projekcie , a mianowicie zegar na lampach nixie z termometrem.
Nie chciałem aby zegar dokonywał pomiaru temp tylko brać go z innego czujnika + czujnika zewnętrznego.
Teraz już wiem jak 8-)
W elektronice jak nie wiadomo o co chodzi to zwykle chodzi o zasilanie

Wezmę udział w Supla Offline Party 2024 :)
Komar000
Posts: 31
Joined: Mon Feb 12, 2018 9:28 am

Post

Męczę się z tematem, kod jak dopracuję umieszczę ponownie. Mam pytanie co się dzieje że jest problem z obsługą ponad dwóch termometrów. Zrobiłem to za pomocą caseow i dopóki są tylko dwa nie ma problemu jak pojawia się trzeci mam 3 kreski. Na dole kodu jest pętla która dodaje minimalną wartość temp, na początku definiuję -100 i ta temperatura pojawia się od razu w cloud na dwóch pierwszych kanałach. To co chcę osiągnąć to przesłanie do esp 3 pomiarów z innego esp, które będzie zasilane bateryjnie. Teraz żeby 3 termometr pokazał temperaturę muszę przesłać kilka pomiarów (np złapać termometr w ręce), co też jest dla mnie dziwne. Co istotne, parametry w zmiennych termometrx lądują prawidłowo. Jest ktoś w stanie mi wytłumaczyć na jakiej zasadzie to działa?

PS. Kod był przygotowany na wysłanie dwóch różnych pomiarów z esp, ale stwierdziłem, że jednak rozwiąże to dodając niewielką wartość na poziomie kodu.

Code: Select all

/**
 * Supla.org NodeMCU WiFi minimal example
 * Author: Programistyk - Kamil Kaminski <kamil@programistyk.pl>
 * Edited by: Komar000 
 * This example shows how to configure SuplaDevice for building for NodeMCU within Arduino IDE
 */


#include <srpc.h>
#include <log.h>
#include <eh.h>
#include <proto.h>
#include <IEEE754tools.h>
// We define our own ethernet layer
#define SUPLADEVICE_CPP
#include <SuplaDevice.h>
#include <lck.h>

#include <WiFiClient.h>
#include <ESP8266WiFiType.h>
#include <ESP8266WiFi.h>
#include <ESP8266WiFiScan.h>
#include <ESP8266WiFiMulti.h>
#include <WiFiServer.h>
#include <ESP8266WiFiGeneric.h>
#include <WiFiClientSecure.h>
#include <ESP8266WiFiAP.h>
#include <ESP8266WiFiSTA.h>
#include <WiFiUdp.h>

#include <SPI.h>
#include <Ethernet.h>
#include <OneWire.h>
#include <DallasTemperature.h>


String  wiadomosc;
float temp;
float termometr0;       // każdy termometr musi miec zdefiniowany swoja zmienna i zmienne do dwoch parametrow
float termometr00 = -100.00;      // pierwsza cyfra to numer termometru, druga to numer pomiaru
float termometr01;
float termometr1;
float termometr10 = -100.00;
float termometr11;
float termometr2;
float termometr20 = -100.00;
float termometr21;
uint8_t ktorypomiar; // get_temperature wymaga podawania conajmniej dwoch pomiarow
int indeks;

float przycinanie (String);

// Setup a oneWire instance
OneWire oneWire(4); // 24 - Pin number

// Pass oneWire reference to Dallas Temperature
DallasTemperature sensors(&oneWire);

// DS18B20 Sensor read implementation
double get_temperature(int channelNumber, double last_val) {

    double t = -275;
    
         switch(channelNumber)
          {
            case 0:
                   
                    t = termometr0;
                    break;
            case 1:                 // w zależnosci od ilosci termometrow nalezy dodac tyle case'ow
                    t = termometr1;
                    break;

            case 2:
                    t = termometr2;
                    break;        
           }       
         
        
         return t;  
}


IPAddress staticIP118_20(192,168,0,20);
IPAddress gateway118_20(192,168,0,1);
IPAddress subnet118_20(255,255,255,0);

WiFiServer server(80);



WiFiClient client;

// Setup Supla connection
const char* ssid     = "xxx";
const char* password = "xxx";

void setup() {
  Serial.begin(115200);
  delay(10);
  Serial.println("START");
   WiFi.begin("xxx","xxx");
  while ((!(WiFi.status() == WL_CONNECTED))){
    delay(300);
    Serial.print("..");

  }
  Serial.println("Connected");
  WiFi.config(staticIP118_20, gateway118_20, subnet118_20);
  Serial.println("Your IP is");
  Serial.println((WiFi.localIP()));
  server.begin();


  

   // Init DS18B20 library 
  sensors.begin();
  
  // Set temperature callback
  SuplaDevice.setTemperatureCallback(&get_temperature);

  // Replace the falowing GUID
  char GUID[SUPLA_GUID_SIZE] = {xxx};
  // with GUID that you can retrieve from https://www.supla.org/arduino/get-guid

  // Ethernet MAC address
  uint8_t mac[6] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00};

  /*
   * Having your device already registered at cloud.supla.org,
   * you want to change CHANNEL sequence or remove any of them,
   * then you must also remove the device itself from cloud.supla.org.
   * Otherwise you will get "Channel conflict!" error.
   */
   // CHANNEL0 - Temp
  SuplaDevice.addDS18B20Thermometer();
  SuplaDevice.addDS18B20Thermometer();
  SuplaDevice.addDS18B20Thermometer();
    
  // CHANNEL1 - RELAY
  //SuplaDevice.addRelay(15);           // 44 - Pin number where the relay is connected      
                                      // Call SuplaDevice.addRelay(44, true) with an extra "true" parameter 
                                      // to enable "port value inversion"
                                      // where HIGH == LOW, and LOW == HIGH   

  // CHANNEL2 - RELAY
 // SuplaDevice.addRelay(45, true);           // 45 - Pin number where the relay is connected   

  // CHANNEL3 - TWO RELAYS (Roller shutter operation)
  //SuplaDevice.addRollerShutterRelays(46,     // 46 - Pin number where the 1st relay is connected   
//                                     47, true);    // 47 - Pin number where the 2nd relay is connected  

  // CHANNEL4 - Opening sensor (Normal Open)
 // SuplaDevice.addSensorNC(5); // A0 - Pin number where the sensor is connected
                               // Call SuplaDevice.addSensorNO(A0, true) with an extra "true" parameter
                               // to enable the internal pull-up resistor


  // CHANNEL5 - Opening sensor (Normal Open)
  //SuplaDevice.addSensorNO(14); // A1 - Pin number where the sensor is connected


  // CHANNEL6 - DHT22 Sensor
  // SuplaDevice.addDHT11();
  // SuplaDevice.addAM2302();
  // SuplaDevice.addDHT22();
  
  

  SuplaDevice.begin(GUID,              // Global Unique Identifier 
                    mac,               // Ethernet MAC address
                    "supla.org",  // SUPLA server address
                    2,                 // Location ID 
                    "");               // Location Password
  ktorypomiar = 0;

}

void loop() {
  SuplaDevice.iterate();
  Serial.println(ktorypomiar);
  WiFiClient client = server.available();
    //if (!client) {return; }
    if (client == 1)
   {
    while(!client.available()){  delay(1); }
    wiadomosc = (client.readStringUntil('\r'));
    //Serial.println(wiadomosc);
    //Serial.println(wiadomosc[5]);

    if (wiadomosc.charAt(5) == '0')                  // Odczyt z termometra 0
    {
       if (wiadomosc.charAt(6) == '0')              // odczyt i zapis pierwszego pomiaru
        {
          przycinanie(wiadomosc);                   // wyciecie z wiadomosci (typu string) tylko pomiaru i zapisanie go do float
          termometr00 = temp;
          //Serial.println("termometr00: ");
          //Serial.println(termometr00);
        }
       /*if (wiadomosc.charAt(6) == '1')
        {
         przycinanie(wiadomosc);
         termometr01 = temp;
        }*/
     }
   if (wiadomosc.charAt(5) == '1')                // Odczyt z termometra 1
    {
       if (wiadomosc.charAt(6) == '0')             // pierwszy pomiar
        {
          przycinanie(wiadomosc);
          termometr10 = temp;
        }
       /*if (wiadomosc.charAt(6) == '1')           // drugi pomiar
        {
          przycinanie(wiadomosc);
          termometr11 = temp;
        }*/
    }
   if (wiadomosc.charAt(5) == '2')                // Odczyt z termometra 2
    {
       if (wiadomosc.charAt(6) == '0')             // pierwszy pomiar
        {
          przycinanie(wiadomosc);
          termometr20 = temp;
          //Serial.println("termometr20: ");
          //Serial.println(termometr20);
        }
      /* if (wiadomosc.charAt(6) == '1')           // drugi pomiar
        {
          przycinanie(wiadomosc);
          termometr21 = temp;
        }*/
    }
   }  
  
  if (ktorypomiar == 50) // pierwszy pomiar
  {
    termometr0 = termometr00; // przypisanie pierwszego pomiaru do termometru 1
   Serial.println(termometr0);
   delay(5);
    termometr1 = termometr10; // przypisanie pierwszego pomiaru do termometru 2
   Serial.println(termometr1);
   delay(5);
    termometr2 = termometr20;
   Serial.println(termometr2);
    delay(5);
    
  }
  ktorypomiar ++;
   if(ktorypomiar == 99) // drugi pomiar
  {
    termometr0 += 0.11; // przypisanie drugiego pomiaru do termometru 1
    termometr1 += 0.11; // przypisanie drugiego pomiaru do termometru 2
    termometr2 += 0.11;
    ktorypomiar = 0;
  }
    
} 

// Supla.org ethernet layer
    int supla_arduino_tcp_read(void *buf, int count) {
        _supla_int_t size = client.available();
       
        if ( size > 0 ) {
            if ( size > count ) size = count;
            return client.read((uint8_t *)buf, size);
        };
    
        return -1;
    };
    
    int supla_arduino_tcp_write(void *buf, int count) {
        return client.write((const uint8_t *)buf, count);
    };
    
    bool supla_arduino_svr_connect(const char *server, int port) {
          return client.connect(server, 2015);
    }
    
    bool supla_arduino_svr_connected(void) {
          return client.connected();
    }
    
    void supla_arduino_svr_disconnect(void) {
         client.stop();
    }
    
    void supla_arduino_eth_setup(uint8_t mac[6], IPAddress *ip) {

       // Serial.println("WiFi init");
        WiFi.begin(ssid, password);

        while (WiFi.status() != WL_CONNECTED) {
            delay(500);
        //    Serial.print(".");
        }

        //Serial.print("\nlocalIP: ");
        //Serial.println(WiFi.localIP());
        //Serial.print("subnetMask: ");
        //Serial.println(WiFi.subnetMask());
        //Serial.print("gatewayIP: ");
        //Serial.println(WiFi.gatewayIP());
    }

SuplaDeviceCallbacks supla_arduino_get_callbacks(void) {
          SuplaDeviceCallbacks cb;
          
          cb.tcp_read = &supla_arduino_tcp_read;
          cb.tcp_write = &supla_arduino_tcp_write;
          cb.eth_setup = &supla_arduino_eth_setup;
          cb.svr_connected = &supla_arduino_svr_connected;
          cb.svr_connect = &supla_arduino_svr_connect;
          cb.svr_disconnect = &supla_arduino_svr_disconnect;
          cb.get_temperature = NULL;
          cb.get_temperature_and_humidity = NULL;
          cb.get_rgbw_value = NULL;
          cb.set_rgbw_value = NULL;
          
          return cb;
}
//***********************************************************************
float przycinanie (String wiadomosc)
{
  wiadomosc = wiadomosc.substring(7);  // na pozycji 7 powinien byc poczatek pomiaru przesylanego pomiaru
      for(int x = 0; x < wiadomosc.length(); x++) // znalezienie spacji, która oddziela temperature od reszty wiadomosci
      {
          if(wiadomosc.charAt(x) == ' ') 
          {
          indeks = x;
          continue;
          }
      }   
       wiadomosc.remove(indeks); 
          
         temp = wiadomosc.toFloat();  // przekonwertowanie wiadomosci do float 
         //Serial.println(temp);   
         return temp;
}
Komar000
Posts: 31
Joined: Mon Feb 12, 2018 9:28 am

Post

Poprzedni kod był trochę niezrozumiały, dziś skupiłem się tylko na zmuszeniu esp do wrzucenia 3 pomiarów na cloud.
Fragment kodu wygląda tak:

Code: Select all


double get_temperature(int channelNumber, double last_val) {

    double t = -275;
    
      
         switch(channelNumber)
          {
            case 0:
                    if (fakepomiar == 0)t = termometr0;          // fakepomiar jest zdefiniowany na poczatku jako	 int fakepomiar = 0;
                      else t = termometr0 + 0.01;
                    break;
            case 1: 
                    if (fakepomiar == 0)t = termometr1;
                      else t = termometr1 + 0.01;                   
                    break;

            case 2:
                    if (fakepomiar == 0)t = termometr2;
                     else t = termometr2 + 0.01;                    
                                           
                      Serial.print("Pomiar Termometr 2: ");
                      Serial.println(t);
                    break;        
           }       
         
         //Serial.println(t);
         //Serial.print("Fakepomiar: ");
         //Serial.println(fakepomiar); 
         if (channelNumber == 2)
         {
          if (fakepomiar == 0) fakepomiar = 1;
          else fakepomiar = 0;       
         }
         return t;  
} 
Problem w tym, że dwa pierwsze termometry pojawiają się zaraz po zmianie pomiaru, ten trzeci (termometr2) niestety nie. Jeżeli z case 1 wyrzuce wszystko oprócz break, tak żeby nie zwracał wartości (a raczej zwracał stałą -275) to. Pomiar z termometr2 się od razu pokazuje, a przy termometr1 mam: ---
Skoro raz na jakiś czas udawało mi się zmusić do pokazywania 3 pomiarów jednocześnie to jakie warunki poza zmianą pomiaru muszę spełnić :( ?
Komar000
Posts: 31
Joined: Mon Feb 12, 2018 9:28 am

Post

Podałem się jeżeli chodzi o funkcjonalność 3 termometrow. Aktualnie działają dwa i funkcjonuje to bardzo fajnie. Kod wrzucę na dniach jak uporam się z jednym problemem. Mianowicie jako serwer który przyjmuje dane z zew czujnika działa sonoff basic (wemos d1 leży na zewnątrz na bateriach) i po około 36 godzinach sonoff rozłącza się z supli i pomaga tylko odłączenie go od prądu i podłączenie ponownie. Spotkał się ktoś już z tym? Może potrzebna jakaś prosta linijka kodu?
User avatar
akszyn
Posts: 180
Joined: Wed May 22, 2019 2:40 pm
Location: Szczecin

Post

shimano73 wrote: Wed Mar 14, 2018 2:34 pm Tak , właśnie o to chodziło , tylko ja wtedy jeszcze o tym nie wiedziałem :?
Przyznam że rozwiązałeś mój problem w jednym projekcie , a mianowicie zegar na lampach nixie z termometrem.
Nie chciałem aby zegar dokonywał pomiaru temp tylko brać go z innego czujnika + czujnika zewnętrznego.
Teraz już wiem jak 8-)
Też się zastanawiam nad zrobieniem czegoś podobnego tylko że lampy nixie są drogie a tańsza alternatywa zrobienia takiego zegara będzie na lampach vfd a jeszcze tańsze na cronixie (lixie) na diodach LED chyba że tańszy będzie widmowy.
Supla na pokładzie wemosa D1 mini z relay shield (gate Zybiego)z DS18B20 + sonoff basic (domyślny soft) + broadlink RM mini 3 + Philips hue white z bridge v1 + LoraTap (RF 433) z kinetycznym przełącznikiem + ai-speaker Dev1 i Dev3
User avatar
shimano73
Posts: 1976
Joined: Sun Feb 28, 2016 12:27 pm
Location: Orzesze

Post

akszyn wrote: Fri Sep 20, 2019 11:42 am
shimano73 wrote: Wed Mar 14, 2018 2:34 pm Tak , właśnie o to chodziło , tylko ja wtedy jeszcze o tym nie wiedziałem :?
Przyznam że rozwiązałeś mój problem w jednym projekcie , a mianowicie zegar na lampach nixie z termometrem.
Nie chciałem aby zegar dokonywał pomiaru temp tylko brać go z innego czujnika + czujnika zewnętrznego.
Teraz już wiem jak 8-)
Też się zastanawiam nad zrobieniem czegoś podobnego tylko że lampy nixie są drogie a tańsza alternatywa zrobienia takiego zegara będzie na lampach vfd a jeszcze tańsze na cronixie (lixie) na diodach LED chyba że tańszy będzie widmowy.
Nie koniecznie drogie, jak kupiłem używany, sprawny miernik częstotliwości polskiej produkcji, 8 nixie z 100zl :D , ale na razie projekt leży w szufladzie
W elektronice jak nie wiadomo o co chodzi to zwykle chodzi o zasilanie

Wezmę udział w Supla Offline Party 2024 :)

Return to “Pomysły i koncepcje”