Arkadaşlar 7 segment displayde ds18b20 ile derece yaptım.Ancak şöyle bir sorunla karşılaştım.7 segment display 1 saniye sıcaklığı gösterip kayboluyor.Sonra 3 veya 5 saniye gibi düzensiz peryotlarla sıcaklığı 1 saniye göseri gösterip kayboluyor.Sorunu çözemedim.Yardımlarınızı bekliyorum.
#include <16f877.h>
#device *=16
#device adc=10
#fuses XT,NOWDT,NOPROTECT
#use delay (clock=20000000)
#include <ds18b20.c>
char display1_onlar,display1_birler,display2_onlar,display2_birler,display3_onlar,display3_birler,temp;
const int display_digit[10]={0x40,0x79,0x24,0x30,0x19,0x12,0x02,0x78,0x00,0x10}; // ortak anotlu için
unsigned long int sicaklik_bilgisi;
float sicaklik;
void sicaklik_tara()
{
output_d(0b00000001);
output_b(display_digit[display1_onlar]);
delay_ms(2);
output_d(0b00000010);
output_b(display_digit[display1_birler]);
delay_ms(2);
output_d(0b00000100);
output_b(0x9c); // derece simgesi
delay_ms(2);
output_d(0b00001000);
output_b(0xc6); // C harfi
delay_ms(2);
output_d(0b00000000);
}
//------- ana program ----------------------------------------------------------
void main ()
{
output_a(0x00);
output_b(0x00);
output_d(0x00);
delay_ms(2);
setup_adc(adc_clock_internal);
setup_adc_ports(AN0);
for(;;)
{
sicaklik_tara();
sicaklik = ds1820_read(); //Sıcaklık bilgisi okunuyor ve çevriliyor
temp = sicaklik;
display1_birler=temp%10;
display1_onlar=(temp/10);
sicaklik_tara();
delay_ms(5);
}
}
Hocam buda İSİS dosyası:
http://s3.dosya.tc/server13/fRlCcc/ds18b207segment.rar.html (http://s3.dosya.tc/server13/fRlCcc/ds18b207segment.rar.html)
Arkadaşlar haftalardır uğraşılarıma rağmen bu sıkıntıyı gideremedim. Yardımlarınızı bekliyorum.Çok acil bir şekide gerekli.Lütfen işi bilen birisi varsa yukarıdaki kodlar üzerinde bir değişilik yaparsa çok memnun olurum.
"for" döngüsü içinde neden iki defa display taradınız?
Picden anlamam ama ds18b20 deneyimlerine göre: ds18b20 12 bit en yüksek çözünürlükte ~750 ms okuma gecikmesi yaratır. Sıcaklığı okuduğunuz fonksiyon kendi içinde, da18b20den sonucun gelmesini bekliyor. Bütün işlemleri bloke ediyor. Seven segment yazdirma işini bir interrupt la yapmanız yada seven segmente latch gibi son sonucu sürekli gösteren bir ek yapmanız gerekir.
Ds18b20 fonksiyonuna hakimseniz 750 ms lik beklemeyi delay şeklinde değil de seven segmente veri göndermek için faydalı bir şekile sokabilirsiniz.
@Oxefe dediği gibi.Kendi fonksiyonunuzu yazıp dener iseniz belki sorun çözülür gibi.
şemadeki dirençleri isis'de dijital olarak tanımladınız mı? Eğer analog olarak tanımlı ise bilgisayarda düşük konfigürasyonda ise bu tür hataları yapabilir.
ana fonksiyon içindeki for döngüsünden "delay_ms(5);" satırını kaldır.
bir tane sayac koy. sayac 125 (4*2=8 * 125=1000ms) olduğunda DS18B20'yi oku. ve sayacı sıfırla.
ds18b20.c içindeki ds1820_read fonksiyonunda 200ms bir gecikme verilmiş.
bunun gibi kayıpları değerlendirebiliriz.
ds18b20.c dosyasından bu kısımı bul:
float ds1820_read()
{
int8 busy=0, temp1, temp2;
signed int16 temp3;
float result;
onewire_reset();
onewire_write(0xCC);
onewire_write(0x44);
while (busy == 0)
busy = onewire_read();
onewire_reset();
onewire_write(0xCC);
onewire_write(0xBE);
temp1 = onewire_read();
temp2 = onewire_read();
temp3 = make16(temp2, temp1);
result = (float) temp3 / 16.0;
delay_ms(200);
return(result);
}
ve böyle değiştir:
float ds1820_read()
{
int8 busy=0, temp1, temp2;
signed int16 temp3;
float result;
onewire_reset();
onewire_write(0xCC);
onewire_write(0x44);
while (busy == 0)
{busy = onewire_read();sicaklik_tara();}
onewire_reset();
onewire_write(0xCC);
onewire_write(0xBE);
temp1 = onewire_read();
temp2 = onewire_read();
temp3 = make16(temp2, temp1);
result = (float) temp3 / 16.0;
for(int i=0;i<25;i++)
{sicaklik_tara();}
return(result);
}
#include <ds18b20.c> komutunu ise main üstüne taşı.
sanki salakca bişey yaptım gibime geliyor ama istersen bir dene. proteusta bu şekilde çalıştırdım.
birde interup ile yapılabilinir ama ds18b20 için gerekli zamanlamaları etkileyebilir diye düşündüm.
Alıntı yapılan: pwm.c - 09 Aralık 2013, 20:36:22
ds18b20.c içindeki ds1820_read fonksiyonunda 200ms bir gecikme verilmiş.
bunun gibi kayıpları değerlendirebiliriz.
ds18b20.c dosyasından bu kısımı bul:
float ds1820_read()
{
int8 busy=0, temp1, temp2;
signed int16 temp3;
float result;
onewire_reset();
onewire_write(0xCC);
onewire_write(0x44);
while (busy == 0)
busy = onewire_read();
onewire_reset();
onewire_write(0xCC);
onewire_write(0xBE);
temp1 = onewire_read();
temp2 = onewire_read();
temp3 = make16(temp2, temp1);
result = (float) temp3 / 16.0;
delay_ms(200);
return(result);
}
ve böyle değiştir:
float ds1820_read()
{
int8 busy=0, temp1, temp2;
signed int16 temp3;
float result;
onewire_reset();
onewire_write(0xCC);
onewire_write(0x44);
while (busy == 0)
{busy = onewire_read();sicaklik_tara();}
onewire_reset();
onewire_write(0xCC);
onewire_write(0xBE);
temp1 = onewire_read();
temp2 = onewire_read();
temp3 = make16(temp2, temp1);
result = (float) temp3 / 16.0;
for(int i=0;i<25;i++)
{sicaklik_tara();}
return(result);
}
#include <ds18b20.c> komutunu ise main üstüne taşı.
sanki salakca bişey yaptım gibime geliyor ama istersen bir dene. proteusta bu şekilde çalıştırdım.
birde interup ile yapılabilinir ama ds18b20 için gerekli zamanlamaları etkileyebilir diye düşündüm.
Hocam Allah ne muradın varsa versin.Senin dediğin yolla bu iş çözüldü.Allah yolunu açık etsin.Saygılarımla.
Merhaba tam kodu paylasirmisiniz. Yazilanlari yaaptim ama olmadi calismadi
Onewire, if, for, next,
Ömrümü yedin ömrümü...
https://www.sifirzero.com/2024/01/ds18b20-seven-segment-termometre.html?m=0 (https://www.sifirzero.com/2024/01/ds18b20-seven-segment-termometre.html?m=0)
Ds18b20 16f628a 3 digit sevensegment sorunu çözdüm. Arkadaşın verdiği örnek gibi yaptım. Eksi degerleride gosteriyor. Derin dondurucada test ettim 🤭 web sitemizde kodlari paylaştim