Not 11: ADC (Analog – Dijital Çevirici)

Yayınlandı: 03 Ocak 2012 / Microchip PIC Programlama...

Analog büyüklük, herhangi iki noktası arasına sınırsız sayıda değer alabilen büyüklüktür. Mesela 5 derece ısı ile 6 derece ısı arasını sonsuz parçalara bölebiliriz. Örnek olarak 5.0000012 derece, veya  5.999999999…..9 derece gibi. Doğada bulunan bütün büyüklükler (Isı, Ses, Işık, Zaman…) analog büyüklüklerdir. Bizim bu büyüklükleri mikroişlemciler ile algılayabilmemiz için bu büyüklüklerin sayısal büyüklüklere dönüştürülmesi gerekir. Bu işlemi yapan birimlere ise ADC birimleri denilmektedir. Analog-Dijital Converter  birimi çoğu mikrodenetleyicide dahili olarak bulunmaktadır. ADC birimi bulunmayan mikrodenetleyiciler için ise seri veya paralel çıkış üretebilen harici ADC entegreleri kullanılabilir.

ADC birimlerinin en önemli özellikleri çözünürlükleri yani bit sayılarıdır. 10 bitlik bir ADC 0 ile 1023 arasında değerler üretebilirken, 8 bitlik bir mikrodenetleyici 0 ile 255 arasında değerler alabilmektedir. ADC biriminin bit sayısı arttıkça çözünürlüğü de artmaktadır. Diyelim ki elimizde çıkış genliği  0V  ile 5V arasında değişen bir basınç sensörümüz var ve mikrodenetleyicimiz içerisindeki ADC birimi 10 bitlik. O halde 5V/1023=0.0048875855327468 gibi bir değer elde ederiz. Bu değer bizim ADC birimimizin hassasiyetini temsil etmektedir. Yani ADC birimimiz 4.8mV deerindeki voltaj değişimlerini hissedebilmektedir.  Eğer ADC birimimizden okuduğumuz değer 15 ise ADC biriminin girişinde bulunan voltaj değeri  15*0.0048875855327468=~0.073V’dur. Eğer ADC biriminden okuduğumuz değer 512 ise girişimizdeki sinyalin genlik değeri 512*0.0048875855327468=~2,5 V olur.Bu bilgiler ışığında hemen örnek bir uygulama yapalım. Bu uygulamada 16F628A mikrodenetleyicisinin içerisinde ADC birimi bulunmadığından 16F88 mikrodenetleyicisini kullanacağız.

ADC’Den okunan değer sadece o anda okunan değerin dijital karşılığıdır ve bu değer 10 bitlik bir ADC biriminde 0 ile 1023 arasında değişir. 5V/1023’den= 0,0048875855327468 V gibi bir değer alırız ki bu değerde bizim en küçük algılanabilen voltajımızdır. Yani bu voltaj değerini mikrodenetleyici okuduğunda bunun çıktısı bize 1 olarak yansıyacaktır. Fakat ölçülen voltaj değeri tam bu değerin iki katına ulaştığında ADC’den okunan değer 2 olacaktır. Ölçülen değer 5V iken okuduğumuz değer ise 1023 olacaktır.

Bu mikrodenetleyicinin içerisinde frekansı seçilebilir bir RC osilatör birimi bulunmakta. Frekansımızı 8MHZ olarak ayarladık. 16F88 içerisinde 5 kanal ADC birimi bulunmakta. Bu da demek oluyorki 5 adet farklı sinyalin seviyesi ölçülebilir. Bu uygulamamızda girişteki voltaja karşılık ADC biriminden okunan değerler LCD’ye aktarılmakta. 5V giriş geldiğinde 1023 değeri, 0V giriş geldiğinde ise 0 değeri LCD’de görülecek.

Devre Şeması:

Büyütmek için Tıklayın

Kod:


<pre>char txt[7];
int okunan;
void kurulum()
{
OSCCON=0b01111100;//Dahili osilatör frekansı 8MHZ olarak belirlendi
OSCTUNE=0; //Osilatör frekansı merkez olarak belirlendi.
ANSEL=0b00000001; //AN0 analog giriş diğer pinler dijital I/O
ADCON0.f7=1;//ADC/RC clock seçildi
ADCON0.f6=1;//ADC/RC clock seçildi
ADCON1=0b11000000;//Sonuçlar sağa dayalı, Referans gerilimler VDD ve VSS

Lcd_Init(&PORTB);//LCD kuruldu;
Lcd_Cmd(LCD_CURSOR_OFF);//LCD imleci kapatıldı
Lcd_Cmd(LCD_CLEAR);//LCD Temizlendi
}

void main()
{
kurulum();//Kurulum alt programı çağrıldı;
while(1) //sonsuz döngü
{
okunan=Adc_Read(0);// AN0 kanalından değer okundu ve sonuç integer tipindeki "okunan" değişkenine atıldı
IntToStr(okunan,txt); okunan değişkeninin içeriğini LCD'de yazdırabilmek için stringe çeviriyoruz ve txt isimli 7 karakterlik diziye aktarıyoruz.
lcd_out(1,1,txt);
delay_ms(10);
}
}

MikroC analog dijital çeviricinin okunmasını kütüphanesi ile çok basit hale getirmiş. “ADC_read(kanal)” komutu ile istediğimiz kanaldan analog-dijital çevrimi gerçekleştirebiliyoruz. Tabiki ilk olarak ADC birimini ayarlamak gerekiyor. Bunun için ise PIC mikrodenetleyicilerin kataloglarındaki A/D Modül kısmını iyi okumamız gerekiyor. Çünkü her mikrodenetleyicide benzer fakat ufak farklar içeren ADC birimleri bulunmakta.

Konu ile ilgili tüm kaynaklara buradan ulaşabilirsiniz.

Sorularınızı ve görüşlerinizi aşağıdan iletebilirsiniz. İyi çalışmalar.

yorum
  1. Alp dedi ki:

    char txt[7];

    bu kodun tam manası ne oluyor hocam.

    • mikrodunya dedi ki:

      “IntToStr(okunan,txt);” kodunda kullanılan “txt” dizisini tanımlar.
      MikroC’nin help dosyasını inceleyebilirsiniz kütüphane fonksiyonlarını görebilmek için.

  2. Alp dedi ki:

    OSCCON=0b01111100;//Dahili osilatör frekansı 8MHZ olarak belirlendi
    OSCTUNE=0; //Osilatör frekansı merkez olarak belirlendi.
    ANSEL=0b00000001; //AN0 analog giriş diğer pinler dijital I/O

    16f877a kullanıyorum ve bu satırlarda hata alıyorum.

    • mikrodunya dedi ki:

      Çünkü bu satırlar 16F88 işlemcisine özel registerlara kod yükleyen satırlardır. 16f877’de bu registerlar yok.
      Datasheetleri iyi inceleyin.

  3. özkan dedi ki:

    Hocam ADC ile voltmetre yapmak istiyorum; fakat aynı mantıkla nasıl yapabilirim? Pot’ a en fazla 5V okutabilirim bu durumda. Yardımcı olabilirseniz sevinirim.

    • mikrodunya dedi ki:

      Maksimum voltajınız diyelim ki 30V. Bu durumda işlemciye maksimum 5V girebileceğine göre gerilim bölücü dirençler vasıtası ile 30V değerini 5V’a dönüştürmemiz gerekir. Bunun için null resimdeki gibi 10K/2K dirençleri kullanarak bir gerilim bölücü yapıp dirençlerin birbirlerine bağlandıkları yerden PIC’e giriş sağlayabiliriz. Daha sonra ölçtüğümüz değeri 6 ile çarparak gerçek değeri buluruz.

  4. özkan dedi ki:

    Çok teşekkür ededrim üstadım. Sorumun cevabını aldım.

  5. Alp dedi ki:

    Hocam ben bu devreyi 16f877a ile yapmaya çalışıyorum.Pot yerine Lm35 Sıcaklık sensörü kullanıyorum.
    sicaklik=ADC_Read(0);
    Lcd_Out(1,1,”Sicaklik=”);
    inttostr(sicaklik,txt);
    Lcd_Out(2,1,rtrim(txt));

    bu kodlarla ekrana almaya çalışıyorum. sürekli değişken int sayılar alıyorum. bu devreyi düzgün hale getirmek için neler yapabilirm.

    • mikrodunya dedi ki:

      Hocam lm35’i ısıttıkça değerlerde bir artış ve azalma görüyor musun? Eğer görüyorsan adc ölçümün gerçekleşiyor demektir. Akşam bununla ilgili bir kod yazayım ve sitede paylaşayım.

      • Alp dedi ki:

        çok net olmamakla bir artış gözleniyor. ya ben çok hassas yaptım. ya da çevrim çok hızlı olduğu için ekran da dereceyi net göremiyorum.

        hocam bi de 16f877 kullanarak yaparsanız çok makbule geçer.

        saygılar.

  6. Ali ÇETİNKAYA dedi ki:

    Merhabalar kolay gelsin. Benim sorum= ADCON1=0b11000000; ile neyi tanımlıyoruz sistem içerisinde. başka yerlerde ADCON1=0x80; denmiş ben analoğ dijital portlarını mikro c’ye ADCON1 ile tanıtırken ne yapmalıyım. veya 0x80 ne anlama geliyor. hexadecimal sayı olarak neyi kastediyorsunuz. Aynı örnek gibi ADCON1=0x09; deniyor başka biryerdede bu 00001001 anlamına geliyor. yani entegrenin 0. ile 3. pin mi aktif oluyor?? çalışmalarınızda başarılar. iyi geceler.

  7. özkan dedi ki:

    Hocam sizden özür dileyerek bu konu başlığının altına yazmak zorunda kalıyorum. 16f628a ile bunu yapmaya çalıştım; fakat yapamadım. Aşağıda ki kodların çalışmama sebebi nedir hocam? 10 cm den mesafe büyükse led yansın, küçükse sönsün şeklinde çalışması lazım. ADC mi lazım. Hocam yardımcı olabilirseniz çok mutlu olurum. Sizden tekrar özür diliyorum buraya yazdığım için; ama gerçekten mikroc 16f628 de paylaşım bulamadım. Pic bilgim çok iyi değil, sizlerin sayesinde öğreniyoruz.

    unsigned int distance,time;
    sbit trig at RA0_bit;
    sbit ECHO at RA1_bit;

    void main() {
    TRISB = 0;
    TRISA =0xff;
    porta=0;
    portb=0;

    T1CON = 0b10000001;

    while(1){
    trig=1;
    delay_us(15);
    trig=0;
    while(!(ECHO) ){
    TMR1L = 0;
    TMR1H = 0;
    }
    while(ECHO){
    time = TMR1H;
    time = time <=10){
    portb.b0=1;
    }
    else if(distance<=9){
    portb.b0=0;
    }

    delay_ms(100);

    }
    }

  8. evliya dedi ki:

    IntToStr(adet,AdetS);
    LCD_Out(1,1,AdetS), Şeklinde lcd de görüntü alamıyorm sorunun ne oldugunu bılen varmı

  9. Omer dedi ki:

    0-5 volta olarak verdiğiniz deger mikrodenetleyicinin input voltajımı?

    • mikrodunya dedi ki:

      Evet. Mikrodenetleyiciye 5v uzerinde gerilim giremeyiz.

      • Omer dedi ki:

        Benim mikroişlemcim arm lm4f120h5qr cortex m4 lerden. 3. 3 volt alabiliyorum. Öncelikle amacım bir ohm metre yapmak. bunun için şu linkteki http://p1305.hizliresim.com/19/c/mz52l.jpg devreyi kullanacam. Fakat adc yi yapamadım daha doğrusu datasheetteki 20 sayfalık kısımda yer alan adc kısmında ölçeceğim voltaj değerine program içerisinde nereden ulaşacağımı anlayamadım. Kullanmak zorunda oldugum dil Assembly baska bir dil kullnamıyorum.Datasheette 13. bolumde 20 sayfalık kısımda adc konusu var. Okuyacağım voltaj değerini program içerisinde nereden alıp kullanabileceğim husunda beni bilgilendirebilirseniz çok iyi olur. datasheet bu adreste:http://www.keil.com/dd/docs/datashts/ti/stellaris/lm4f120h5qr_ds.pdf.
        Şimdiden çok teşekkür ederim.İyi akşamlar

  10. Omer dedi ki:

    bu arada sadece adc den voltaj değeri mi okunabilir?

  11. Omer dedi ki:

    pardon şöyle demek istemiştim. Adc den sadece voltaj değerimi okunabilir? diğer devre için gerekli daha farklı değerlerde okunabilirmi?

    • mikrodunya dedi ki:

      Adcden sadece voltaj degeri okunabilir. Ohm bilgisi ölçmek için bir direnç uzerinden sabit bir akim gecirerek direnc uzerinde olusan voltaji olcmek gerekir. Bahsettiginiz islemcinin datasheetine bakip size bilgi verecegim.

      • Omer dedi ki:

        teşekkürler. Fakat ben lm 317 ile sabit akım geçirerek devreyi kurmak yerine linkte gönderdiğim resimdeki gibi bir devre kurmak istiyorum bilginizE?

      • Omer dedi ki:

        Teşekkürler. Ben LM317 ile sabit akım geçirerek ohmmetre yapmak istemiyorum. Çünkü o devredede mikroişlemcimin yanma ihtimali çok büyük. ;3.3 volttan fazla voltaj değeri geldiğinde.
        O nedenle gönderdiğim linkteki gibi bir devre kurmak istiyorum bilginizE?

      • mikrodunya dedi ki:

        Neden 3.3 Volttan fazla gerilim gelsin ki? LM317’nin girişine bir de voltaj regülatörü koyarsınız olur biter.

      • mikrodunya dedi ki:

        Ayrıca bahsettiğiniz işlemcinin manuelinin 785. sayfasında ADCSSFIFO isimli registerdan ADC örnekleme sonucunu alabileceğiniz belirtilmiş.
        Saygılar.

  12. Omer dedi ki:

    Çok teşekkür ederim. Yeni naşladığım için kafama ayrı bir soru takıldı.Lm 317 kullanınca baska sıkıntılar ortaya çıkıyor. Peki Lm317 olmadan diğer linkte attığım gibi bir devre olustursam bana dez avantajları ne olabilir yani aynı derecede çalişmaz mı?

    • mikrodunya dedi ki:

      Akımı sabitlemeden direnci ölçemezsiniz. 10uA gibi bir akım geçirin ölçeceğiniz dirençten. Verdiğiniz devre çalışmaz.

      • Omer dedi ki:

        Öncelikle tekrar teşekkürler. Ben bu devrenin çalişacağını düşünüyorum ancak analog to digital ile voltaj değerini nasıl alacağımı bilmiyorum. Yani datasheet kısmındaki 20 sayfalık bölümde bir çok adc registerları mevcut fakat hangilerini nasıl ne içi kullanacağımı bilmiyorum. Bu konuda hangi registerları falan kullanmam gerektiği hususunda bana bilgi verirseniz çok sevinirim.(Zamanım çok fazla kalmadıgı için ayrıntılı incelesemde datasheeti anlayamadım)

      • Omer dedi ki:

        Adc hususunda yardımcı olma şansınız yok mu=?

      • mikrodunya dedi ki:

        Hocam su anda vaktim yok. Picproje.org adresini oneririm size.

      • Omer dedi ki:

        Selamlar.Hocam şu anda müsait vaktiniz var mı? Sadece gönderdiğim datasheet teki ADC bölümü hususunda sorularım olacaktı.Birde birkaç kısa sorularım var.Yardımcı olabilirseniz çok sevinirim.İyi günler

  13. Omer dedi ki:

    ???

  14. omer dedi ki:

    Arkadaşlar yardımcı olabilecek arkadaş var mı?

  15. sertan dedi ki:

    hocam merhaba. benim bir ödevim var. pic 16f887 ile2 kademeli dijital voltmetre yapımı.bana bu devrenin mikroc kodları gerekmekte.yardımcı olabilirmisiniz

  16. Mehmet YALVAÇ dedi ki:

    Merhaba. Bende mikrodenetleyici ye uygulanan direnç değerine göre farklı işlemler yaptırmak istiyorum. Yukarıda bahsettiğiniz gibi 10uA akımı ölçmek istediğim dirençten (sistemden) nasıl geçirebilirim acaba?

  17. kazım dedi ki:

    Bilgi paylaşımlariniz icin teşekkür ederim.
    Nesne algilayan ve bu nesneyi android veya Windows isletim sistemlerine aktaracagimiz cihaza ihtiyacimiz var.
    Bunun icin fotoelektrik, lazer sensörler piyasada mevcut ancak belirttigim isletim sistemlerine sadece 0 1 gibi veriler veya herhangi bir veriyle aktarim gerceklestirebilecegimiz bunun icinse sanırım donusturucunun olmasi gerekiyor. Piyasada farkli algilama ile bu çözümü veren cihazlar var ancak yuksek maliyetli.
    Belirledigimiz nesneyi (renk vb.) algilayan ve bu sinyali dijtal ortama tasiyan cihaza ihtiyacimiz.
    Bu cihazin uretimi ekonomik maliyette olusturdugumuzda endüstrisi alaninda kullanacagiz. Bunu nasil veya siz olustarabilirmisiniz
    Teşekkürler

    • mikrodunya dedi ki:

      Hocam mesajınızdan anladığım kadarı ile bir cismi algılayarak bunu bir işletim sistemine aktarmak istiyorsunuz. Cihazın hangi özelliklerini algılamak istiyorsunuz detay verirseniz ona göre yardımcı olmaya çalışayım.

      • kazım dedi ki:

        Sabit bir zemin uzerinden gecen nesneyi algılama. Nesnenin sabit zemin uzerinden gecme suresi saniye araliginda.

      • mikrodunya dedi ki:

        Hocam bu yapılabilir fakat nesnenin hangi özelliklerini algılayacağız? Uzaklık, boyut, renk gibi özelliklerini mi yoksa sadece nesne var ya da yok gibi mi?

      • kazım dedi ki:

        Renk algilama daha ayirt edici bir cozum ancak ana renklerin disinda ara renklerde olacak bu da hata payini arttirabilecegini dusunuyorum veya cozum mutlak ise ve maliyette dusuk ise bu olabilir.
        Nesne var yok cozumu ise sabit zeminden ayirt ederek algilama yaptirabilirsek ve mutlak cozum sunarsa bu secenekte olabilir.
        Ayrica maliyetin dusuk olmasi gerekiyor seri uretimde maliyet duscektir ama minimal sartlarda olmali. Ayrica piyasadakiler gibi kalem boyutta olmali sensör kismi donustucu boyutu onemli degil. Bu sistem usb çıkışlı olmasi daha ideal.
        Örnek olarak optik mauslari inceliyorum optik kismi belli mesafede algiliyor ve bunu usb ile isletim sistemlerine aktabiliyor. Bunun malzemelerini donustucu olarakta kullanabilirmiyiz.

      • mikrodunya dedi ki:

        Algılanacak cismin zeminden yüksekliği ne kadar? Cisimleri saymak için mi kullanacaksınız bu sistemi?

      • kazım dedi ki:

        Nesnenin zeminden yüksekliği ayarlanabilir, max 15 cm ilk etapta yeterli olcaktir. Sonraki asamalarda max 1m olarak ayarlanibilir.
        Nesne sayimi icin kullanilacak, neseneler sensor de min 12 max 60 sn kalacak.
        Bu nesneler 2-3 gunde bir renk degistirecek.

      • mikrodunya dedi ki:

        hocam zahmet olmazsa yapmak istediğiniz sistemin bir kaba taslak şemasını mikrodunya@gmail.com adresine mail olarak atar mısınız? Mail üzerinden devam edelim isterseniz.

  18. Süha dedi ki:

    Merhabalar

    ADC kullanımının hakkında fikir sahibiyim.HI-TECH C derleyicisi kullanıyorum. Fakat araştırmalarıma rağmen ADRESH ile ADRESL register içerisindeki bit değerlerinin nasıl elde edildiğini bulamadım? ADCON1 registerindaki ADFM bitini 1 yaparak sağa yaslı şekilde yaptığımız zaman; örneğin; volt diye int değişkenimiz olsun,
    volt=(int)((ADRESH*256+ADRESL) şeklinde bir komut karşıma çıkıyo bu volt değeri nedir ifade olarak ? nasıl bir değerdir? ve ADRESH ‘ın iki bitini kulanıyoruz 00 01 10 11 ihtimalleri var bunu 256 ile nasıl çarpıyo ne elde ediliyo anlayamadım.

    micro c kullanımı daha farklı ancak bilginiz vardır diye sormak istedim yardımcı olursanız teşekkürler..
    Kolay gelsin..

Bir Cevap Yazın

Aşağıya bilgilerinizi girin veya oturum açmak için bir simgeye tıklayın:

WordPress.com Logosu

WordPress.com hesabınızı kullanarak yorum yapıyorsunuz. Çıkış  Yap / Değiştir )

Twitter resmi

Twitter hesabınızı kullanarak yorum yapıyorsunuz. Çıkış  Yap / Değiştir )

Facebook fotoğrafı

Facebook hesabınızı kullanarak yorum yapıyorsunuz. Çıkış  Yap / Değiştir )

Google+ fotoğrafı

Google+ hesabınızı kullanarak yorum yapıyorsunuz. Çıkış  Yap / Değiştir )

Connecting to %s