Czujnik temperatury - zasilanie bateryjne

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

Tue Mar 13, 2018 11:14 pm

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: 506
Joined: Wed Aug 24, 2016 7:26 pm
Location: Opole

Wed Mar 14, 2018 5:10 am

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?
Attachments
IMG_20180314_060453.png
IMG_20180314_060453.png (184.55 KiB) Viewed 3982 times
Aktualnie na budowie: 8x SRW-01, 1x ROW-02, SUPLA BUTTON V2.0, 16 x DS na ESP (GUI), Sonoff S20 jak kontroler CWU, Ping IP Socket.

Przydatne linki:
viewtopic.php?f=9&t=4160
search.php?keywords=
User avatar
shimano73
Posts: 909
Joined: Sun Feb 28, 2016 12:27 pm
Location: Orzesze

Wed Mar 14, 2018 7:32 am

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
Komar000
Posts: 30
Joined: Mon Feb 12, 2018 9:28 am

Wed Mar 14, 2018 8:26 am

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: 909
Joined: Sun Feb 28, 2016 12:27 pm
Location: Orzesze

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-)
W elektronice jak nie wiadomo o co chodzi to zwykle chodzi o zasilanie
Komar000
Posts: 30
Joined: Mon Feb 12, 2018 9:28 am

Wed Mar 21, 2018 12:35 am

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: 30
Joined: Mon Feb 12, 2018 9:28 am

Wed Mar 21, 2018 11:01 pm

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: 30
Joined: Mon Feb 12, 2018 9:28 am

Sat Mar 31, 2018 6:04 pm

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: 74
Joined: Wed May 22, 2019 2:40 pm
Location: Szczecin
Contact:

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.
Supla na pokładzie wemosa D1 mini z relay shield (gate Zibiego)+ sonoff basic z domyślnym softem + broadlink RM mini 3 + Philips hue z bridge v1
User avatar
shimano73
Posts: 909
Joined: Sun Feb 28, 2016 12:27 pm
Location: Orzesze

Fri Sep 20, 2019 12:11 pm

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
Post Reply