Milis fonksiyonu ile zaman hesabı

Öncelikle Herkese merhaba.

Arduino ile hassas ölçümler yaparken hepimiz sorun yaşamışızdır. Program delay kısmına gelince program delay kısmına kaç milisaniye yazarsak okadar duruyor. Buda bizim delay kısmında ölçüm yapmamızı engelliyor .

Milis program çalıştığı an başlıyor ve programın nekadar çalıştığını tutuyor. Her çağrıldığında zamanı milisaniye olarak döndürüyor. Örneğin bir ledi 5 saniye yakmak istiyoruz aynı zamanda serial monitöre sürekli birşeyler yazmak istiyoruz, delay fonksiyonunu kullansaydık arduino 5 saniye boyunca bekleyecek ve başka işlemler yapmamıza izin vermeyecek. Bunu engellemek için milis fonksiyonunu kullanabiliriz. Aşağıda örneği bulabilirsiniz;

Kod kısmı

Kod şu şekilde;

void setup() {
  pinMode(13,OUTPUT);
  Serial.begin(9600);
}

/* zaman değerlerinin tutulması için değişkenler tanımlanmalı */
unsigned long eskiZaman=0;
unsigned long yeniZaman;

int LEDdurumu = 0;

void loop() {
  /* Arduinonun çalışma suresi milisaniye cinsinden alınıyor */
  yeniZaman = millis(); 
  /* bir önceki turdan itibaren 5000 milisaniye geçmiş mi
  yani yeniZaman ile eskiZaman farkı 5000den büyük mü */
  if(yeniZaman-eskiZaman > 5000){
     if(LEDdurumu == 1){
      digitalWrite(13,LOW);
      LEDdurumu = 0;
     }else{
      digitalWrite(13,HIGH);
      LEDdurumu = 1;
     } 
     /* Eski zaman değeri yeni zaman değeri ile güncelleniyor */
     eskiZaman = yeniZaman;
  }
  
  /*Ekrana sürekli olarak mesaj yazdırılıyor */
  Serial.println("Arduino burada baska islemler de yapabilir.");
  /* Bekleme fonksiyonunun kullanılmasına gerek yok
}

Milis fonksiyonun çalışma mantığını anladığımza göre şimdi olayı farklı bir boyuta taşıyıp Tarih ve Zaman hesabı yapıp bunu bir lcd ekrana yazdırmaya çalışalım.

LCD ekrana 2 saniye de bir tarih ve zaman bilgisini yazdırmaya çalışalım. Fakat tarih ve zamanı default olarak girmemiz gerekiyor.

Kod şu şekilde;

#include <LiquidCrystal.h>
LiquidCrystal lcd(8,7,6,5,4,3);
int kacinci_gun=1; 
int gun=2,ay=1,yil=2018;
int saat=0,dakika=0,saniye;
unsigned long eskiZaman=0; 
unsigned long yeniZaman; 
unsigned long bir_gun=0;
unsigned long uc_saat=0; 
unsigned long bir_saniye=1000;
int durumu=0;
float analogDeger=0;

void tarihgoster() 
{
    if(yeniZaman-bir_gun>86400000)
   {
    kacinci_gun++;
    gun++;
     if(gun>31)
    {
       gun=1;
       ay++;     
    }
    if(ay>12 )
    {
         ay=1;
         yil++;
    }
    bir_gun=yeniZaman;
   }  
}
void saatGoster()
{
	if(yeniZaman-bir_saniye>1000)
   {
    saniye++;
     if(saniye>59)
    {
		saniye=0;
		dakika++;
	}
    if(dakika>59 )
    {
		dakik=0;
		saat++;
    }
	if(saat>23)
		saat=0;
    bir_saniye=yeniZaman;
   }  
}
void setup(){
  Serial.begin(9600);
  // LCD’yi 16 sütün, 2 satır olarak başlat
 lcd.begin(16,2);
  lcd.print("   Mehmet Altunel");
  lcd.setCursor(2,1); 
  delay(2000);
  lcd.clear();
}
void loop(){
	yeniZaman = millis();
   tarihgoster(); 
   saatGoster();
   if(yeniZaman-eskiZaman > 2000)  
    {
       if(durumu == 1)
       {
          lcd.begin(16, 2);

          lcd.setCursor(3, 1); 
          lcd.print(gun);
          lcd.print(".");
          lcd.print(ay);
          lcd.print(".");
          lcd.print(yil);
          durumu = 0;
       }
       else
       {
          lcd.clear();   
		       lcd.setCursor(3, 1); 
          lcd.print(saat);
          lcd.print(":");
          lcd.print(dakika);
          lcd.print(":");
          lcd.print(saniye);
          durumu = 1;
        } 
       eskiZaman = yeniZaman;
    }
}

 

9 Comments

  1. Good post however , I was wondering if you could write a litte more on this subject?
    I’d be very thankful if you could elaborate a little bit
    more. Many thanks!

  2. Thanks designed for sharing such a fastidious opinion, piece of writing is pleasant,
    thats why i have read it completely

  3. bir hata gördüm 60 olanlar 59 olacak.
    yoksa karşımız aşu hata çıkıyor 12.60.60 böyle bir saat olurmu? 12.59.59 olur
    teşekürler

    1. Evet Muahrrem bey haklısınız, gözümden kaçmış, küçük ama çok önemli bir detay. Güncelliyorum hemen. Teşekkür ediyorum.

  4. merhaba arduino da delay yerine millis kullanmak istiyorum ama programım çalışmıyor sensor okuduktan 5 saniye sonra durmasını istiyorum kodumu yolluyorum i yardımcı olabilir misiniz ?
    #define in2 6 // in2 pinini 6. pine tanımladık.
    #define ledk 10
    #define ledy 11
    #define leds 8

    int sayac=0;
    int butonDegisim = 0; // butonDegisim degişkenini tanımladık
    int butonDegisimi2 = 0; // butonDegisimi2 degişkenini tanımladık
    int sensorDegeri = 1; // sensorDegeri degişkenini tanımladık

    void setup() { // ana kurulum
    pinMode (buton1, INPUT); // 3. pin giriş oldu
    pinMode(buton2, INPUT); // 4. pin giriş oldu
    pinMode(enA, OUTPUT); // enA pini çıkış oldu
    pinMode(in1, OUTPUT); // in1 pini çıkış oldu
    pinMode(in2, OUTPUT); // in2 pini çıkış oldu
    pinMode(ledk, OUTPUT);
    pinMode(ledy, OUTPUT);
    pinMode(leds, OUTPUT);

    Serial.begin(9600); // seri haberleşme aç
    }

    void loop() { // sonsuz döngü

    if (digitalRead(buton1) == HIGH) { // okunan deger 1 ise
    butonDegisim = 1; // butonDegisim degiskenini 1 yap
    delay(10); // 10 milisaniye bekle
    }
    while (butonDegisim == 1) { // butonDegisim degiskeni 1 oldugunda

    int pot = analogRead(A1); // potansiyometre degerini oku
    int pwmoutput = map(pot, 0 , 1023 , 0 , 255); // potansiyometre degerini 0 ile 255 arası ayarla
    analogWrite(enA, pwmoutput); //L298N’e PWM sinyal yolla
    digitalWrite(ledy, HIGH);
    digitalWrite(ledk, LOW);
    digitalWrite(leds, LOW);
    delay(10);
    digitalWrite(in1, LOW);// L298N sürücü devresinde ki in1 girişine 0V verilecek
    digitalWrite(in2, HIGH); // L298N sürücü devresinde ki in2 girişine +5V verilecek

    int sensor = analogRead(A0); // sensor degerini oku
    Serial.println(sensorDegeri); // sensorDegerini görüntüle

    if ((sensor) == 0) { //sensorde okunan deger 1 ise
    sensorDegeri <= 0; //sensorDegeri degiskenini '<=0' yap
    delay(10); // 50 milisaniye bekle
    digitalWrite(enA, pwmoutput); //L298N'e PWM sinyal yolla
    digitalWrite(leds, HIGH);
    digitalWrite(ledy, LOW);
    digitalWrite(in1, HIGH); //L298N sürücü devresinde ki in1 girişine +5V verilecek
    digitalWrite(in2, LOW); //L298N sürücü devresinde ki in2 girişine 0V verilecek
    butonDegisim = 0; // butonDegisim degiskenini 0 yap

    delay(5000);

    digitalWrite(leds, LOW);
    digitalWrite(ledy, LOW);
    digitalWrite(ledk, HIGH);
    digitalWrite(enA, LOW); //L298N sürücü devresinde ki enable girişine 0V verilecek

    }

    if (digitalRead(buton2) == HIGH) { // okunan buton 1 ise
    butonDegisim = 0; // butonDegisim degiskenini 0 yap
    digitalWrite(leds, LOW);
    digitalWrite(ledy, LOW);
    (digitalWrite(ledk, HIGH));
    digitalWrite(enA, LOW); //L298N sürücü devresinde ki enable girişine 0V verilecek

    }
    }
    }

    1. Tam olarak ne yapmak istediğinizi anlamadım ama Sensörün okuduğu yere yani if içine bu yapıyı eklerseniz işinizi görecektir.
      //loop dışında zaman’ı tanımalamayı unutmayın
      zaman = millis();

      if(zaman>5000)
      {
      // 5 saniye sonra yapılmak istenen
      }
      else
      {
      // ilk 5 saniye yapılamk istene
      }

  5. if(gun>31)
    {
    gun=1;
    ay++;
    }

    Hocam burada şubat 28 veya 29 çekerse yada 30 çeken aylarda ne gibi bir işlem yapmayı düşünürsünüz.

  6. Yapmış olduğum çalışmada oda temizlendikce butona 5 saniye boyunca basılı tutulacak ve lcd ekran da butona basılan en son tarihi yazdırmaya çalışıyorum. Herhangi bir kod yazamadım.Bu konu da yardımcı olur musunuz?

Bir yanıt yazın

E-posta adresiniz yayınlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir