Arduino Polska Forum
Problem z sekundnikiem. - Wersja do druku

+- Arduino Polska Forum (https://forum.arduinopolska.pl)
+-- Dział: Korzystanie z Arduino (https://forum.arduinopolska.pl/dzial-korzystanie-z-arduino)
+--- Dział: Piaskownica (https://forum.arduinopolska.pl/dzial-piaskownica)
+--- Wątek: Problem z sekundnikiem. (/watek-problem-z-sekundnikiem)

Strony: 1 2


Problem z sekundnikiem. - ferdricco - 10-03-2017

Witam. 
Postanowiłem zrobić sobie taki projekcik jak zegarek z termometrem.
 Użyłem do tego projektu Arduino Nano, DS1307, DS18B20 oraz wyświetlacz Oled.
Problemem jest wskazanie sekund. A mianowicie czasem pokazuje sekunda po sekundzie, ale zazwyczaj pokazuje co drugą sekundę a wskazania sekund są nie metryczne. Czas wyświetlenia między zmianami nieraz trwa więcej niż sekundę a czasem ułamek sekundy. 
  Proszę o sprawdzenie kodu i wskazanie błędu. 

Kod PHP:
#include <Wire.h>
#include <DS1307.h>
#include <SPI.h> 
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <OneWire.h>
#include <DallasTemperature.h>
#define OLED_RESET 4
Adafruit_SSD1306 display(OLED_RESET);
DS1307 clock;
RTCDateTime dt;
 
#define ONE_WIRE_BUS 11
OneWire oneWire(ONE_WIRE_BUS);
DallasTemperature sensors(&oneWire);
void setup()
{
 
 clock.begin();
 
 display.begin(SSD1306_SWITCHCAPVCC0x3C);
 
 display.clearDisplay();
 
 display.setTextSize(1);
 
 display.setTextColor(WHITE);
 
 display.setCursor(25,0);
 
 display.println("inicjalizacja");
 
 display.setTextSize(2);
 
 display.setTextColor(WHITE);
 
 display.setCursor(25,15);
 
 display.println("DS 1307"); 
 
 display.display();
 
 sensors.begin();
 
 
  if 
(!clock.isReady())
 
 {
 
   
    clock
.setDateTime(__DATE____TIME__);
 
   
  
}
 
 delay(2000);
}
 
void loop()
{
 
 dt clock.getDateTime();
 
 sensors.requestTemperatures();
 
 display.clearDisplay();
 
 display.setTextSize(1);
 
 display.setTextColor(WHITE);
 
 display.setCursor(0,0);
 
 display.print("TEMPERATURA =");
 
 display.setTextSize(1);
 
 display.setTextColor(WHITE);
 
 display.setCursor(84,0);
 
 display.print(sensors.getTempCByIndex(0));
 
 display.setTextSize(1);
 
 display.setTextColor(WHITE);
 
 display.setCursor(30,25);
 
 display.print(dt.day);
 
 display.print(" - ");
 
 display.print(dt.month);
 
 display.print(" - ");
 
 display.print(dt.year);
 
 display.setTextSize(2);
 
 display.setTextColor(WHITE);
 
 display.setCursor(20,9);
 
 display.print(dt.hour);
 
 display.print(":");
 
 display.print(dt.minute);
 
 display.print(":");
 
 display.print(dt.second);
 
 display.display();
 
 delay(1000);




RE: Problem z sekundnikiem. - namok - 10-03-2017

Sprawa jest bardzo prosta -> usuń delay(1000) .


RE: Problem z sekundnikiem. - ferdricco - 11-03-2017

Ok. Pomogło z tym że nie jest to płynne odliczanie. Sporadycznie się przycina. Zauważyłem że te przycięcia są w momencie kiedy zmienia się wyświetlenie temperatury.


RE: Problem z sekundnikiem. - namok - 11-03-2017

1. Wysyłanie wszystkich informacji na wyświetlacz w każdym cyklu jest nieefektywne. Wysyłaj wartości które się zmieniają i to w momencie gdy nastąpi zmiana wartości.
2. Konwersja temperatury w czujniku trochę trwa(w zależności od rozdzielczości nawet 750ms). Wyślij "requestTemperatures", odczekaj odpowiedni czas, a potem odczytaj wartość. Wszystko to z użyciem millis aby nie blokować.
3. Odczyt wartości też robisz nieefektywnie bo używasz metody getTempCByIndex zamiast getTempC. Przy małej ilości urządzeń tego tak nie widać ale przy większej tak.
4. Generalnie to cała biblioteka jest trochę bez sensu bo przelicza na float. Jest to wygodne ale zajmuje dużo miejsca w pamięci i czasu.


RE: Problem z sekundnikiem. - Smaczek - 11-03-2017

Witam,
A nie możesz sprawdzać czy konwersja temperatury jest kompletna i dopiero wtedy zmieniać temperaturę do wyświetlania? Jeśli nie jest kompletna to wyświetlać jedynie czas.
Pozdrawiam.


RE: Problem z sekundnikiem. - ferdricco - 11-03-2017

Dzięki panowie za podpowiedzi. Starałem się poradzić sobie z tym problemem ale więcej namieszałem niż polepszyłem.
Jestem początkującym ale mam duży apetyt na wiedzę i wszelakie podpowiedz. ma takie pytanie. Jak wy poradzilibyście sobie z tym projektem. Chodzi mi o to jak byście napisali taki programik. Jestem ciekaw jak wyglądały by program napisany przez takich doświadczonych programistów.


RE: Problem z sekundnikiem. - ferdricco - 19-03-2017

Witam ponownie. Po kilku dniach kombinacji wypociłem takowy kod
Kod:
#include <Wire.h>
#include <DS1307.h>
#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <OneWire.h>
#include <DS18B20.h>
#define OLED_RESET 4
byte address[8] = {0x28, 0x16, 0x5A, 0x1E, 0x7, 0x0, 0x0, 0x88};
Adafruit_SSD1306 display(OLED_RESET);
DS1307 clock;
RTCDateTime dt;
#define ONE_WIRE_BUS 11
OneWire oneWire(ONE_WIRE_BUS);
DS18B20 sensors(&oneWire);
void setup()
{
 clock.begin();
 display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
 display.clearDisplay();
 display.setTextSize(1);
 display.setTextColor(WHITE);
 display.setCursor(25,0);
 display.println("inicjalizacja");
 display.setTextSize(2);
 display.setTextColor(WHITE);
 display.setCursor(25,15);
 display.println("DS 1307");
 display.display();
 sensors.begin(11);
 sensors.request(address);
 // Jeśli nie ustawiono daty, ustawiamy
 if (!clock.isReady())
 {
   // Data i czas z momentu kompilacji
   clock.setDateTime(__DATE__, __TIME__);
   
 }
 delay(2000);
}

void loop()
{
   if (sensors.available())
 {
   float temperature = sensors.readTemperature(address);
 sensors.request(address);
 }
 dt = clock.getDateTime();
 display.clearDisplay();
 display.setTextSize(1);
 display.setTextColor(WHITE);
 display.setCursor(0,0);
 display.print("TEMPERATURA =");
 display.setTextSize(1);
 display.setTextColor(WHITE);
 display.setCursor(84,0);
 display.print(sensors.readTemperature(address));
 display.setTextSize(1);
 display.setTextColor(WHITE);
 display.setCursor(25,25);
 display.print(dt.day);
 display.print(" - ");
 display.print(dt.month);
 display.print(" - ");
 display.print(dt.year);
 display.setTextSize(2);
 display.setTextColor(WHITE);
 display.setCursor(20,9);
 display.print(dt.hour);
 display.print(":");
 display.print(dt.minute);
 display.print(":");
 display.print(dt.second);
 display.display();
}


Raczej działa ale wolałbym żeby ktoś go sprawdził czy oby na pewno jest ok.


RE: Problem z sekundnikiem. - Smaczek - 20-03-2017

Witam,
Trzy poprawki:
- zmienną temperature zadeklaruj jako globalną, tj. przed blokiem setup() float temperature; Nie zapomnij wyciąć float przed temperature wewnątrz loop()!

- zamiast: display.print(sensors.readTemperature(address));
ma być: display.print(temperature);

- usuń zbędne, powtarzające się: display.setTextSize(1);
display.setTextColor(WHITE);
bo po co powtarzasz te instrukcje skoro nie zmieniasz koloru i rozmiaru czcionki (oczywiście dla godzin, minut i sekund zostaw .....setTextSize(2); ).

Pozdrawiam.


RE: Problem z sekundnikiem. - ferdricco - 20-03-2017

(20-03-2017, 15:04)Smaczek napisał(a): Witam,
Trzy poprawki:
- zmienną temperature zadeklaruj jako globalną, tj. przed blokiem setup()   float temperature;  Nie zapomnij wyciąć float przed temperature wewnątrz loop()!

- zamiast: display.print(sensors.readTemperature(address));
ma być: display.print(temperature);

- usuń zbędne, powtarzające się:    display.setTextSize(1);
                                                                     display.setTextColor(WHITE);
bo po co powtarzasz te instrukcje skoro nie zmieniasz koloru i rozmiaru czcionki (oczywiście dla godzin, minut i sekund zostaw .....setTextSize(2);  ).

Pozdrawiam.

Czy o to chodziło???
Kod:
#include <Wire.h>
#include <DS1307.h>
#include <SPI.h>
#include <Adafruit_GFX.h>
#include <Adafruit_SSD1306.h>
#include <OneWire.h>
#include <DS18B20.h>
#define OLED_RESET 4
#define ONE_WIRE_BUS 11
byte address[8] = {0x28, 0x16, 0x5A, 0x1E, 0x7, 0x0, 0x0, 0x88};
float temperature;
Adafruit_SSD1306 display(OLED_RESET);
DS1307 clock;
RTCDateTime dt;
OneWire oneWire(ONE_WIRE_BUS);
DS18B20 sensors(&oneWire);
void setup()
{
 clock.begin();
 display.begin(SSD1306_SWITCHCAPVCC, 0x3C);
 display.clearDisplay();
 display.setTextSize(1);
 display.setTextColor(WHITE);
 display.setCursor(25,0);
 display.println("inicjalizacja");
 display.setTextSize(2);
 display.setTextColor(WHITE);
 display.setCursor(25,15);
 display.println("DS 1307");
 display.display();
 sensors.begin(12);
 sensors.request(address);
 if (!clock.isReady())
 {
   clock.setDateTime(__DATE__, __TIME__);
 }
 delay(3000);
}

void loop()
{
   if (sensors.available())
 {
 temperature = sensors.readTemperature(address);
 sensors.request(address);
 }
 dt = clock.getDateTime();
 display.clearDisplay();
 display.setTextSize(1);
 display.setTextColor(WHITE);
 display.setCursor(0,0);
 display.print("TEMPERATURA =");
 display.setCursor(84,0);
 display.print(temperature);
 display.setCursor(25,25);
 display.print(dt.day);
 display.print(" - ");
 display.print(dt.month);
 display.print(" - ");
 display.print(dt.year);
 display.setTextSize(2);
 display.setCursor(20,9);
 display.print(dt.hour);
 display.print(":");
 display.print(dt.minute);
 display.print(":");
 display.print(dt.second);
 display.display();
}



RE: Problem z sekundnikiem. - Smaczek - 21-03-2017

Witam,
Tak, ale jeszcze display.setTextColor(WHITE); dubluje się Tobie w setup().
Pozdrawiam.