Skocz do zawartości

Arduino Mega2560 + Ethernet + DS18B20 + 7-seg. moduł LED TM1637 - Pomiar temperatury i wysyłanie do bazy SQL


szczepulek

Pomocna odpowiedź

Witam, jak to często bywa, początkujący porywa się na gruby projekt 🙂 w tym przypadku też ale ambicje są, gorzej z praktyką i wiedzą 😉

Projekt jaki chcę stworzyć to mikro kontroler z zastosowaniem Mega 2560 do którego podłączone są dwa czujniki DS18B20 na osobnych pinach (by w przypadku uszkodzenia jednego z nich uniknąć ponownego programowania układu, a tutaj akurat znaczenie ma kolejność czujników) dwa wyświetlacze LED 7-segmentowe moduły komunikujące się na 1-wire( układ TM1637);

Wyświetlacze na bieżąco podają temperaturę z czujników, przy czym po przekroczeniu nastawnej granicy temperatury dla czujnik drugiego uruchamia się przekaźnik dla lampy sygnalizacyjnej, Od włączenia układu następuje odliczanie od 0 do około 5 minut (300000ms) pod WARUNKIEM że na jednym z pinów jest stan niski (zwarcie z masą poprzez przekaźnik dostający sygnał z zewnętrznego urządzenia) gdy odliczanie dobiegnie do końca poprzez Ethernet shield wysyłane są dane pomiarów do bazy danych gdzieś w sieci lokalnej. po wysłaniu wszystko zaczyna się od początku, czyli zliczanie i kolejne wysyłanie danych.

 

Tak na brudno w notatniku wypisałem sobie:
 

po uruchomieniu programu:

-wykrycie czujników ds18b20 na PIN 2 ("temp_in" -temp. wejścia powietrza do chłodzenia) i PIN 3 ("temp_out" -temp.powietrza po schłodzeniu obszaru/produktu);

-wyświetlenie wartości "temp_in" na TM1637 wyświetlacz pierwszy jako "DisplayTin" oraz "temp_out" na "DisplayTout" - wyświetlacz drugi.
Ze względu na brak znaku kropki wyświetlacza i 9-bit rozdzielczość pomiaru  zamiast kropki wyświetlany znak stopni, np dla wartości temperatury 17.0 i 24.5:

          ----      ----     ----
     |        |    |    |   |    |
     |        |    |    |   |    |
                    ----
     |        |             |    |
     |        |             |    |
                             ----
          

 ----               ----     ----
     |   |    |    |    |   |
     |   |    |    |    |   |
 ----     ----      ----     ----
|             |                  |
|             |                  |
 ----                        ----
          

-sprawdzenie warunku jeśli temp_out >= tempALARM (wartość ustawiana i zapamietywana po zaniku zasilania)  to na pinie alarmu stan wysoki wyzwalający przekaźnik;

-sprawdzenie wciśnięcia przycisku (PINy 30-33) zmiany wartości maksymalnej temperatury na wyjsciu "tempALARM", lub numeru linii produkcyjnej "liniaNr";

-sprawdzenie wartości na wejściu pinu NARAwAuto (aktywne schladzanie w trybie automatycznym) jesli prawda uaktywniene zliczania licznika do 4.5-5min (300000 ms);

--po osiąnięciu wartości max licznika 300000 ms uruchomienie funkcji dla EthShield wysyłającej dane pomiaru "temp_in" "temp_out" numer linii produkcyjnej "liniaNr" (ustawiany recznie i zapamietywany) oraz stan wyjscia pinu ALARMtemp;

-podczas zmian nastawy tempALARM na wyświetlaczu pojawia się na 5 sekund wartość w postaci:

 ----               ----     ----
|    |   |              |   |
|    |   |       O      |   |
 ----               ----     ----
|    |   |       O      |        |
|    |   |              |        |
          ----      ----     ----
 
 skok o 1 stopień celciusza, zakres 1 do 50
 
 
 Dla zmiany  numeru linii przykładowo wyświetla:
 
                    ----     ----
|                       |        |
|               O       |        |
                    ----     
|               O  |             |
|                  |             |
 ----               ----
 
 skok o 1, zakres od 1 do 63,
 
 obie wartości muszą być zapamiętane po zaniku zasilania;

a podłączenie pinów mniej więcej tak rozmieszczone:
 

/* informacje pinologii
pin 0
pin 1
pin 2 DS18B20data temp_in //wejsciowa temp powietrza nr.1
pin 3 DS18B20data temp_out //temp po wyjsciu nr.2
pin 4 SDCardShield SS //SlaveSelect
pin 5 CLK1 out //zegar dla wyswietlacza 1 na tm1637
pin 6 DIO1 out //dane dla wysw.1
pin 7 CLK2 out //zegar dla wyswietlacza 2 na tm1637
pin 8 DIO2 out //dane dla wysw.2
pin 9 ALARMtemp out relay //po przekroczeniu nastawionej temp alarm na buzzer/sygnalizator swietlny przez przekaznik
pin 10 ETH SS Mega2560 pin 53 //SlaveSelect wybrannie ukladu perferyjnego eth/sd
pin 11 ETH MOSI Mega2560 pin 50 //dane do ukladu
pin 12 ETH MISO Mega2560 pin 51 //dane z ukladu
pin 13 ETH SCK Mega2560 pin 52 //sygnal zegara

pin 25 NARAwAuto in zRelay //zwarcie do masy po zapodaniu 24V z Nary do przekaznika
pin 27 SendTemp_LED (Mega2560) //wyslanie danych do bazy danych info LED
pin 30 keyENT lub keyAL_down
pin 31 keyEXIT lub keyAL_up
pin 32 keyDN lub keyLN_down
pin 33 keyUP luk keyLN_up
*/

Dla pin 30-33 nie jestem pewien rozwiązania, czyli czy zrobić menu, i przeskakiwanie po wartościach nastawianych czyli temp. maxymalna i wyzwalanie alarmu plus numer linii/urządzenia pomiarowego. Czy na sztywno przyporządkować dany przycisk pod zwiększanie/zmniejszanie parametru pierwszego i drugiego. Co będzie lepszym rozwiązaniem?

Znalazłem na forum temat

myślę że nada się idealnie ta biblioteka dla mnie,

jeden wątek na rozpoznanie czujników i wyświetlenie ich na wyświetlaczach + sprawdzenie wartości temp alarmu,

drugi watek sprawdzający wciśnięcie jednego z przycisków i ewentualną zmianę wartości i jej zapisanie do pamięci,

trzeci wątek odliczający ten czas 5 min (+czas na wykonanie pozostałych wątków) i po zakończeniu wysłania danych zresetowanie licznika.

W obecnej chwili udało mi się ujarzmić wyświetlanie dwóch wyświetlaczy na bibliotece TM1637Display.h , kolejny krok którym się zajmuje to wyświetlanie wartości czujników na osobnych modułach. Następnie dodanie możliwości zmiany parametrów z przycisków. Jak się to uda to jestem w 1/3 drogi do sukcesu.

Czy jakieś porady na początek, na co uważać, lub do samego zamysłu działania?

Edytowano przez Sabre
Link do komentarza
Share on other sites

11 minut temu, szczepulek napisał:

moduły komunikujące się na 1-wire( układ TM1637);

TM1637 nie obsługuje protokołu 1-Wire.

13 minut temu, szczepulek napisał:

Czy jakieś porady na początek, na co uważać, lub do samego zamysłu działania?

Wielozadaniowość to dobre rozwiązanie. To co mi się nie podoba to "TM1637Display.h". Funkcja jest blokująca a komunikacja z TM1637 koszmarnie wolna (10kHz) realizowana przez delay. Komunikacja jest podobna do I2C można więc użyć TWI i przerwań. Ze względu na bardzo wolna komunikacje można nawet zrealizować komunikację na przerwaniach od timera.

Link do komentarza
Share on other sites

(edytowany)

A fakt przepraszam, TM1637 posiada "Two-wire serial interface (CLK, DIO)". Co do wyświetlania, więc lepiej przeskoczyć na LCD z i2c? tam deklarowana prędkość o ile pamiętam to 100kHz do 400 kHz w zależności jaki układ. Pytanie czy w moim przypadku ta wolna komunikacja będzie miała widoczny wpływ?

Czyli jeśli dobrze rozumiem pomiar temperatury rozdzielić z wyświetlaniem, by nie "mulić" całego procesu ?

Edytowano przez szczepulek
Link do komentarza
Share on other sites

1 godzinę temu, szczepulek napisał:

Co do wyświetlania, więc lepiej przeskoczyć na LCD z i2c? tam deklarowana prędkość o ile pamiętam to 100kHz do 400 kHz w zależności jaki układ.

O jakim wyświetlaczu/module piszesz?

1 godzinę temu, szczepulek napisał:

Pytanie czy w moim przypadku ta wolna komunikacja będzie miała widoczny wpływ?

To zależy co ma robis program i jak go napiszesz.

1 godzinę temu, szczepulek napisał:

Czyli jeśli dobrze rozumiem pomiar temperatury rozdzielić z wyświetlaniem, by nie "mulić" całego procesu ?

Prosta wielozadaniowość może nie rozwiązać problemu "mulenia" programu. W pewnych sytuacjach trzeba sięgnąc po RTOS ale zapomnij o RTOS na UNO. MEGA już się nada, nie tylko dlatego, że ma 4 razy więcej ram niż UNO ale także dlatego, że ma 6 timerów w tym 5 16-bit. Uno tylko 3 i tylko jeden 16-bit. RTOS wymaga timera, więc UNO dotkliwie odczuje brak jednego, MEGA już nie. Na UNO RTOS przełącza taski korzystając z watchdoga, więc min czas przełączania 15ms i na tyle może być "zablokowany" inny task. Jak rozwiązano problem priorytetów przerwań na AVR nie wiem bo ogólnie RTOS na AVR to nieporozumienie. Jeśli więc będziesz potrzebował RTOS to zacznij uczyć się na ARM.

Zadanie, które opisałeś jest proste, ale sprawdzanie ENC jest w pętli głównej, więc nie możesz zawieszać programu przez np na 100ms gdy wysyłasz dane do LCD graficznego. Policz na ile "zawiesisz" program gdy bez użycia przerwań będziesz wysyłał dane do TM1637. Może być nieciekawie. Podobnie, na ile "zawiesisz" program gdy będziesz wysyłał dane do ENC? Ile ramek przychodzących może przepaść (np ARP, ICMP). ENC ma tylko 8kB RAM. Typowo ustawia się 2kB dla TX i 6kB dla RX. Na szczęście ramki RX bedą krótkie (ARP, ICPM, GET) i o ile petla główna będzie trwała max 10ms będzie ok, jak 100 to obawiam się, że zaczną się problemy.

Link do komentarza
Share on other sites

Zarejestruj się lub zaloguj, aby ukryć tę reklamę.
Zarejestruj się lub zaloguj, aby ukryć tę reklamę.

jlcpcb.jpg

jlcpcb.jpg

Produkcja i montaż PCB - wybierz sprawdzone PCBWay!
   • Darmowe płytki dla studentów i projektów non-profit
   • Tylko 5$ za 10 prototypów PCB w 24 godziny
   • Usługa projektowania PCB na zlecenie
   • Montaż PCB od 30$ + bezpłatna dostawa i szablony
   • Darmowe narzędzie do podglądu plików Gerber
Zobacz również » Film z fabryki PCBWay

oto co na razie stworzyłem na próbę bez wątków,

obsługa 2 czujniki i wyświetlanie na 2 modułach LCD 8seg, pewnie są jakieś niedoróbki w kodzie.
 

#include <TM1637Display.h>
#include <OneWire.h>
#include <DallasTemperature.h>


#define ONE_WIRE_temp_in 2 //pin dla 1 czujnika ds18b20
#define ONE_WIRE_temp_out 3 //pin dla drugiego czujnika
#define CLK1 5 //wyswietlacz nr1 8segm.4-cz dla wejscia powietrza - temp
#define DIO1 6 //wyswietlacz nr1 8segm.4-cz
#define CLK2 7 //wyswietlacz nr2 8segm.4-cz dla wyjscia powietrza - temp
#define DIO2 8 //wyswietlacz nr2 8segm.4-cz

TM1637Display display_1(CLK1, DIO1);
TM1637Display display_2(CLK2, DIO2);
OneWire oneWire_in(ONE_WIRE_temp_in);
OneWire oneWire_out(ONE_WIRE_temp_out);

DallasTemperature sensor_airin(&oneWire_in);
DallasTemperature sensor_airout(&oneWire_out);


void setup(void)
{
    Serial.begin(9600);
    Serial.println("Dallas Temperature Control Library Demo - TwoPin_DS18B20");
    sensor_airin.begin();
    sensor_airout.begin();
   display_1.setBrightness(0x0a); //jasnosc wysw nr 1 nizej 2
   display_2.setBrightness(0x0a); // -||-

}

void loop(void)
{
    uint8_t wysw1LED[] = { 0x00, 0x00, 0x00, 0x00 };
    uint8_t wysw2LED[] = { 0x00, 0x00, 0x00, 0x00 };
    Serial.print("Requesting temperatures...");
    
    sensor_airin.requestTemperatures();
    sensor_airout.requestTemperatures();
    Serial.println(" done");

    Serial.print("airin: ");
    Serial.println(sensor_airin.getTempCByIndex(0));

    Serial.print("airout: ");
    Serial.println(sensor_airout.getTempCByIndex(0)); //wyswietla w serial monitor, ostatecznie bedzie usuniete
    
  int  airinCalkow = sensor_airin.getTempCByIndex(0)*100; //pozbycie sie kropki w wyniku pomiaru xx.xx
  int  airoutCalkow = sensor_airout.getTempCByIndex(0)*100; //podobnie dla drugiego pomiaru


  //obsluga wyswietlania pierwszego wyswietlacza dla czujnika 1 ,szczegolna uwage nalezy zwrocic na prawidlowe odwolanie sie do uint, i display
 
  wysw1LED[0] = display_1.encodeDigit(airinCalkow/1000%10); //wyswietla cyfre dziesiatek z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw1LED[1] = display_1.encodeDigit(airinCalkow/100%10); //wyswietla cyfre jednosci z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw1LED[2] = (SEG_A | SEG_B | SEG_F | SEG_G); // znak stopni zamiast kropki ktore brak w wyswietlaczu ktory posiadam
  wysw1LED[3] = display_1.encodeDigit(airinCalkow/10%10); //pierwsza cyfra czesci dziesietnych
  display_1.setSegments(wysw1LED); // wyswietlenie  temperatury na pierwszym wyswietlaczu


  //obsluga wyswietlania drugiego wyswietlacza dla czujnika 2
 
  wysw2LED[0] = display_2.encodeDigit(airoutCalkow/1000%10); //wyswietla cyfre dziesiatek z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw2LED[1] = display_2.encodeDigit(airoutCalkow/100%10); //wyswietla cyfre jednosci z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw2LED[2] = (SEG_A | SEG_B | SEG_F | SEG_G); // znak stopni zamiast kropki ktore brak w wyswietlaczu ktory posiadam
  wysw2LED[3] = display_2.encodeDigit(airoutCalkow/10%10); //pierwsza cyfra czesci dziesietnych
  display_2.setSegments(wysw2LED); // wyswietlenie  temperatury na drugim wyswietlaczu

  //pominieto ostatnia cyfre czyli czesci setne pomiaru z czujnikow, nie potrzebuje az tak doklanych danych a zaokraglanie tylko zajmowalo by zasoby procesora
}

i fotki jak to wygląda

img-20191016-wa0002.jpgimg-20191016-wa0003.jpgimg-20191016-wa0001.jpg

Link do komentarza
Share on other sites

Zmierz czas obiegu pętli głównej.

O tyle mnie to ciekawi, że tego typu program, nawet na AVR, powinien wyrabiać się w czasie poniżej 1ms. W kodzie, który pokazałeś jest to niemożliwe, bo arduinowe biblioteki TM1637 i 1-Wire blokują program na czas komunikacji, a 1-Wire dodatkowo zawiesza przerwania dlatego jestem ciekaw czasów. Tego typu kod, na ARM (STM32) wykonuje się w czasie poniżej 1us oczywiście nie gdy korzystasz z arduinowych bibliotek , wtedy" para idzie w gwizdek" i czy to AVR 16MHz czy ARM 480MHz czas wykonania pętli jest praktycznie taki sam. Robiłem kiedyś takie porównanie dotyczące wyświetlaczy graficznych, wyniki udostępniłem na Elektrodzie. Później praktycznie taki sam test przeprowadził ktoś inny, potwierdzając moje wyniki. Źle napisany program (biblioteka) nie zadziała szybciej (albo zadziała niezauważalnie szybciej) na szybszym (nawet kilka tysięcy razy) CPU. Doświadczyłem tego dziś na RPi. Źle napisane biblioteki (słynny Adafruit) powodują, że RPi (ponad 1GHz) wykonuje zadanie kilkadziesiąt razy wolniej niż AVR 8Mhz!

Jak natrafisz na biblioteki Adafruit, to traktuj je jako demo. Użytek z nich żaden, czy to na AVR czy RPi. Napisane są wyjątkowo beznadziejnie. Nawet nie ma co poprawiać, trzeba je napisać od nowa.

Jak chcesz dam Ci kody obsługi 1-Wire, które nie zawieszają przerwań a co ciekawsze,  mogą obsługiwać komunikacje na przerwaniach, co prawda nie dla overdrive, ale termometry nie obsługują tego trybu..

Link do komentarza
Share on other sites

Jasne jak możesz to podeślij kod. W jaki sposób sprawnie obliczyc ile zajmuje czasu mój program?? Oczywiście czas bez wysylania na serial monitor bo takowego nie potrzebuje. 

Na pewno przerobić będe musiał czujnik w wersji wodoodpornej. Ponieważ jak temp nie zmienia się gwałtownie to pomiar jest dobry dla takich potrzem. Biorąc czujnik w dłoń widać szybki przyrost temperatury.. szybki pojęcie względne. No powiedzmy ten 1-2 st na sek. Dla mnie ok. Ale gdy puszczę to jednak schładzanie to temp pokojowej trwa kilka minut. Obudowa metalowa i zapewne wnętrze-powietrze wokół scalaka trzyma temperaturę. Pomysły to:

A. Skrócić tę metalową rurkę.

B. Wypełnić wnętrze jakąś pastą termoprzewodzącą nie przewodzącą prądu.

C. Połączyć te dwa pomysły. 

Kiedyś robiłem próby na samym układzie na płytce stykowej.. bezpośrednio dotykając i czasy reakcji wzrostu i spadku temperatur były satysfakcjonujące

Link do komentarza
Share on other sites

53 minuty temu, szczepulek napisał:

W jaki sposób sprawnie obliczyc ile zajmuje czasu mój program??

W loop zmieniaj stan GPIO i zmierz oscyloskopem albo analizatorem logicznym.

53 minuty temu, szczepulek napisał:

Oczywiście czas bez wysylania na serial monitor bo takowego nie potrzebuje. 

Potrzebujesz. Arduino nie ma debugera. Serialmonitor to jedyny sposób na pseudo debugowanie.

54 minuty temu, szczepulek napisał:

Jasne jak możesz to podeślij kod.

Daj e-mail.

 

Link do komentarza
Share on other sites

5 minut temu, szczepulek napisał:

Szału nie ma :'D

Ponad sekunda? Szok. Będziesz gubił ramki przychodzące po ETH.

Pokaz kod. Pomierz też czas wykonania poszczególnych funkcji jak obsługa 1-Wire (pewnie zrobiłeś to źle i 700ms "w plecy"), DTH i co tam jeszcze masz. Bedziesz wiedział co należy poprawić a co nie ma dużego znaczenia.

Link do komentarza
Share on other sites

Wróce z pracy to pomierzę. Czyli z osobna odczyt ds i wyśw. Najlepiej myślę wyprowadzić sygnał na dwóch pinach do dwóch kanałów oscyloskopu przy czym jeden sygnał będzie Przed wykonaniem funkcji a drugi po zakończeniu jeśli miałyby obydwie biblioteki jednocześnie pracować

Jeśli chodzi o kod źródłowy w pętli loop ustawiłem PIN 40 jako wyjście poniżej ustawienie stanu wysokiego następnie Delay jedna milisekunda i ustawienie poziom niski na pinie reszta kodu taka jak wcześniej wkleiłem

Link do komentarza
Share on other sites

5 minut temu, szczepulek napisał:

Najlepiej myślę wyprowadzić sygnał na dwóch pinach do dwóch kanałów oscyloskopu

Wystarczy jeden. Przed wejściem do funkcji ustawiasz np poziom wysoki, po wyjściu niski. Jak masz kilka kanałów w oscyloskopie/analizatorze to możesz sprawdzić czas wykonania kilku funkcji używając kilku GPIO.

Co do kodu, to nie używaj "requestTemperatures()" tylko wydaj komendę pomiaru temperatury i po wymaganym czasie (przy 12-bit 700ms) odczytaj ją i kolejna komenda pomiaru. W pseudokodzie wygląda to tak:

uint_32 tPomiary;

setup(){
  
 CMD_POMIAR_TEMPERATURY; 
 tPomiary = millis() + 700;
}


loop(){
  
 if( millis() >= tPomiary ) {
  tPomiary = millis() + 700; 
   
   CMD_ODCZYT_TEMPERATURY;
 }
}

Zamiast ponad 1400ms (2*700ms) pętla główna, co 700ms będzie trwała ok 64us*8*(2+10) + 2*(460us + 240us + 70us) czyli ok  1,6ms razy 2 bo dwa termometry (liczby bajtów brałem z pamięci dla opcji bez adresowania, z z adresowaniem + 8 bajtów). Nawet jak się pomyliłem to przypuśćmy, że to łącznie 4ms. Prostym zabiegiem przyspieszyłeś kod 350 razy! Piałem już (może niekoniecznie w tym wątku) ale powtórzę, źle napisany kod "ubije" najszybszy CPU. Kod, który pokazałeś, uruchomiony na STM32H7 z zegarem 480MHz wykona się tak samo długo jak i na AVR 8MHz!

Pętla główna obsługi 1-Wire (dobrze napisana obsługa), na ARM zajmie nanosekundy! Na AVR mikrosekundy. Używając "z głową" arduinowych bibliotek, czy to AVR, czy ARM poniżej 4ms, "bez głowy" 1400ms.

Na razie nie widzę sensu abyś walczył z kodem 1-Wire aby angażować petle główna na mikrosekundy zamiast 4ms ale musisz mieć świadomość, ze na AVR, arduinowe 1-Wire blokuje przerwania na czas transmisji bitu czyli 64us. Czy to dużo czy mało? Gdy odbierasz dane z UART z prędkością 9600 to nie (czas transmisji bajtu ok 1ms) ale gdy 921600, (bajt ok 11us) to możesz tracić co jakiś czas nawet  4 bajty (nie 5 bo AVR ma 2 bajtowe FIFO).

 

Interesuje mnie czas wykonania "display_1.setSegments(wysw1LED);". Czy warto z tym walczyć czy nie?

 

Link do komentarza
Share on other sites

Zapomniałem o jednym temacie "wysyłanie do bazy SQL".  Arduino to arduino, niedopracowana zabawka. Nie wiem na jaki serwer i jak będziesz wysyłał  informacje ale gdy będzie to TCP to na czas wysyłki CPU będzie "zablokowany" a owa blokada, w przypadku np ThingSpeak trwa ok 5 sekund! 5 sekund aby przesłać 6 zmiennych! W tym czasie działają tylko przerwania. W swoim urządzeniu masz wyświetlacz, przez te przykładowe 5 sekund jego zawartość będzie "zamrożona". Gdy będziesz miał klawiaturę, to przez te 5 sekund nie będzie działać lub program zareaguje nawet za 5 sekund (zależy jak obsłużysz klawiaturę). Rozwiązań problemu jest wiele, pierwsza rzecz, rezygnacja z szyfrowania, bo AVR jest na to za słaby. Działać to działa ale to jak z LCD, wyświetlanie obrazka w "tylko" 12 sekund. Kolejne usprawnienie, UDP a nie TCP (mam nadzieję, ze wiesz czym to się różni). Ideałem bedzie RTOS albo napisanie własnej obsługi komunikacji z serwerem. Pisałeś, że jesteś początkujący (słusznie zauważyłeś, że porwałeś się z motyka na księżyc) więc pozostaje Ci RTOS.

Link do komentarza
Share on other sites

dokładnie jak przewidziałeś RFM, czas na wykonanie wyświetlenia LED8seg x2 to około 42-43ms, Pozostała część to pobranie z czujnika wartości. Sprawa się ma tak, że nie zależy mi na 10 bit rozdzielczości pomiaru tym bardziej 12, wystarczy mi 9 bit i wyświetlanie temperatury ze skokiem 0.5 st. C.

Przy dwóch czujnikach nie mogłem dojść do kompilującego się programu z ustawieniem 9 bit, zostało domyślnie.

Dodam jeszcze że żółty wykres to funkcja dla DS18b20, a niebieski to wyświetlacze LEDowe.

Postaram się teraz wprowadzić proponowane zmiany do obsługi czujników. Nadal nie daje mi spokoju ta rozdzielczość pomiaru 😕

oto i kod wykorzystany do pomiarów w tym momencie:

#include <TM1637Display.h>
#include <OneWire.h>
#include <DallasTemperature.h>


#define ONE_WIRE_temp_in 2 //pin dla 1 czujnika ds18b20
#define ONE_WIRE_temp_out 3 //pin dla drugiego czujnika
#define CLK1 5 //wyswietlacz nr1 8segm.4-cz dla wejscia powietrza - temp
#define DIO1 6 //wyswietlacz nr1 8segm.4-cz
#define CLK2 7 //wyswietlacz nr2 8segm.4-cz dla wyjscia powietrza - temp
#define DIO2 8 //wyswietlacz nr2 8segm.4-cz

TM1637Display display_1(CLK1, DIO1);
TM1637Display display_2(CLK2, DIO2);
OneWire oneWire_in(ONE_WIRE_temp_in);
OneWire oneWire_out(ONE_WIRE_temp_out);

DallasTemperature sensor_airin(&oneWire_in);
DallasTemperature sensor_airout(&oneWire_out);



void setup(void)
{
    Serial.begin(9600);
    Serial.println("Dallas Temperature Control Library Demo - TwoPin_DS18B20");
    sensor_airin.begin();
    sensor_airout.begin();
   display_1.setBrightness(0x0a); //jasnosc wysw nr 1 nizej 2
   display_2.setBrightness(0x0a); // -||-

pinMode(40, OUTPUT); // czas trwania dla DS18b20
pinMode(44, OUTPUT); //czas trwania dla LED-wysw
}

void loop(void)
{
    uint8_t wysw1LED[] = { 0x00, 0x00, 0x00, 0x00 };
    uint8_t wysw2LED[] = { 0x00, 0x00, 0x00, 0x00 };
    Serial.print("Requesting temperatures...");

       digitalWrite(40, HIGH); //start pomiaru odczytu DS18B20
    sensor_airin.requestTemperatures();
    sensor_airout.requestTemperatures();
    Serial.println(" done");

    Serial.print("airin: ");
    Serial.println(sensor_airin.getTempCByIndex(0));

    Serial.print("airout: ");
    Serial.println(sensor_airout.getTempCByIndex(0)); //wyswietla w serial monitor, ostatecznie bedzie usuniete
    
  int  airinCalkow = sensor_airin.getTempCByIndex(0)*100; //pozbycie sie kropki w wyniku pomiaru xx.xx
  int  airoutCalkow = sensor_airout.getTempCByIndex(0)*100; //podobnie dla drugiego pomiaru

       digitalWrite(40, LOW); //koniec pomiaru odczytu i przeliczenia na calkowita liczbe

  //obsluga wyswietlania pierwszego wyswietlacza dla czujnika 1 ,szczegulna uwage nalezy zwrocic na prawidlowe odwolanie sie do uint, i display
  
       digitalWrite(44, HIGH); //start wyswietlanie wartosci na led_tm1637
       
  wysw1LED[0] = display_1.encodeDigit(airinCalkow/1000%10); //wyswietla cyfre dziesiatek z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw1LED[1] = display_1.encodeDigit(airinCalkow/100%10); //wyswietla cyfre jednosci z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw1LED[2] = (SEG_A | SEG_B | SEG_F | SEG_G); // znak stopni zamiast kropki ktore brak w wyswietlaczu ktory posiadam
  wysw1LED[3] = display_1.encodeDigit(airinCalkow/10%10); //pierwsza cyfra czesci dziesietnych
  display_1.setSegments(wysw1LED); // wyswietlenie  temperatury na pierwszym wyswietlaczu


  //obsluga wyswietlania drugiego wyswietlacza dla czujnika 2
  
  wysw2LED[0] = display_2.encodeDigit(airoutCalkow/1000%10); //wyswietla cyfre dziesiatek z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw2LED[1] = display_2.encodeDigit(airoutCalkow/100%10); //wyswietla cyfre jednosci z pomiaru cz.1 na wyswietlaczu pierwszym
  wysw2LED[2] = (SEG_A | SEG_B | SEG_F | SEG_G); // znak stopni zamiast kropki ktore brak w wyswietlaczu ktory posiadam
  wysw2LED[3] = display_2.encodeDigit(airoutCalkow/10%10); //pierwsza cyfra czesci dziesietnych
  display_2.setSegments(wysw2LED); // wyswietlenie  temperatury na pierwszym wyswietlaczu

         digitalWrite(44, LOW); //koniec pomiaru wyswietlania na 2 szt modulu LED wyswietlacz tm1637
}

 

img_20191017_141017.jpg

img_20191017_141235.jpg

Link do komentarza
Share on other sites

(edytowany)

Wrzut na serwer w sieci lokalnej, na wzór poradnika

Cytat

utworzenie bazy danych mysql i tam dorzucanie poprzez php danych.

Jeśli chodzi o zamarzanie pomiarów, ich wyświetlania nie stanowi to problemu, może być ta sama temp nawet i pół minuty.

Wręcz nawet może być wyświetlane na jednym z display'i ot takie coś:

LED1 

 ----     ----               
|        |                       |
|        |                       |
 ----     ----      ----     ----
     |   |         |    |   |    |
     |   |         |    |   |    |
 ----     ----               ----
            
            
 Gdy Succes! LED2 (opcjonalnie)  
  
                             ----               
     |                      |    
     |                      |    
 ----     ----      ----     ----
|    |   |    |    |    |   |    
|    |   |    |    |    |   |    
 ----     ----               ----   Np.

 

Wytyczne dla projektu:

- wyświetlana temp. może byc z dokładnością do 0.5 st.C

- odświeżanie wskazań na wyświetlaczach wystarczy i co 10 sek na upartego.

- przyciski, jeśli mają być nie aktywne prze 5-10 sek, nie ma problemu, zamiast diody na jednym z pinów sygnalizującej że trwa łączenie + wysyłanie przez ETH, użyję jak  wyżej napisałem komunikatów SEND. A dioda spełni zadanie ostrzeżenia "zajęty" migając kilka razy przed wykonaniem samej funkcji dla Ethernetu.

Będzie to sygnał że zaraz nic nie będzie można zmienić klawiszami.

Edytowano przez szczepulek
uaktualnienie informacji
Link do komentarza
Share on other sites

Dołącz do dyskusji, napisz odpowiedź!

Jeśli masz już konto to zaloguj się teraz, aby opublikować wiadomość jako Ty. Możesz też napisać teraz i zarejestrować się później.
Uwaga: wgrywanie zdjęć i załączników dostępne jest po zalogowaniu!

Anonim
Dołącz do dyskusji! Kliknij i zacznij pisać...

×   Wklejony jako tekst z formatowaniem.   Przywróć formatowanie

  Dozwolonych jest tylko 75 emoji.

×   Twój link będzie automatycznie osadzony.   Wyświetlać jako link

×   Twoja poprzednia zawartość została przywrócona.   Wyczyść edytor

×   Nie możesz wkleić zdjęć bezpośrednio. Prześlij lub wstaw obrazy z adresu URL.

×
×
  • Utwórz nowe...

Ważne informacje

Ta strona używa ciasteczek (cookies), dzięki którym może działać lepiej. Więcej na ten temat znajdziesz w Polityce Prywatności.