PIC16F886 ile 11Bit ADC Okuma Ve LCD Voltmetre

PIC16F886 ile yapılmış LCD ekranlı 11 Bit ADC dönüşümlü voltmetre.

Bu uygulamayı internetteki bir örnekten faydalanarak hazırladım. Bilindiği gibi 16F serisi piclerde 8 bit ve 10 Bit ADC (Analog Digital Converter) bulunuyor.  Daha yüksek çözünürlükte ADC gerektiğinde ya harici eleman, yada bu donanıma sahip daha gelişmiş PIC tercih etmek zorunda kalıyoruz. örnek aldığım uygulamada ADC referans voltajı dirençlerle kontrollü olarak değiştirilerek çözünürlük arttırılmıştı. bende sistemi biraz hafifleterek hiç direnç kullanmadan, sınırları aşmadan ve doğru gösteren 11 bit dönüşümlü örnek voltmetre projesi hazırladım.  Burada esasen voltmetre değil 11 bit ADC örneği göstermek istedim.

DEVRENİN ÇALIŞMASI.

Uygulamanın çalışma mantığı yukarıda bahsettiğim gibi ADC referans voltajını kontrollü değiştirmeye dayanıyor.  10 Bit dönüşümde referansı 2,5v uygularsak 2,5/1023=0,00244379~ v (yuvarlak 2,5 mv) hassasiyetli okuma yapabiliriz ancak bu durumda analog  girişten en fazla 2,5v okunabilinir. 5v gerilimi aynı hassasiyette dönüştürmek için 2 ayrı 10 bit okuma yapmalıyız. o nedenle 5/2=2,5v referans kullandık.  zaten datasheete göre bu gerilimin altına düşmek sağlıklı sonuçlar vermez.

2,5v referans elde etmek için direnç yada zener benzeri bir dönüştürücü kullanmadım.  PIC16F886 donanımında dahili, ayarlanabilir referans voltaj çıkışı bulunmaktadır.

Referans voltaj çıkışının ilgili ayarları VRCON registeri ile yapılıyor. dier piclerde bu isim farklı olabilir. örneğin 16F88 de CVRCON diye yazar. şimdilik bu açıklamaları 16F886 için yapıyorum.

VRCON registerini inceleyecek olursak önce datasheetdeki şu tabloya bakmalıyız:

Gördüğünüz gibi registerin 0,1,2,3 ve 5. bitleri referans çıkış değerini belirliyor. Burada önemli olan,  VROE  biti (6. bit) referans çıkışını RA2 portuna veriyor ve VREN (7.bit) ise 1 olarak ayarlandığında referansı aktif hale getiriyor.   VRCON registerinin tamamına binary “11101100”  değeri yüklendiğimizde RA2 den tam 2,5v referans voltajı almış oluruz.  Ayrıca ADC için gerekli olan vref- ile aynı pini kullanıyor.  referansı aktif ettğimizde vref- den bu voltajı direk okuyabiliriz.

2,5v referans gerilimimizi elde ettiğimize göre sıra geldi ADC okumaya.  ADC nin referans girişi olan vref- ve vref + için aynı 2.5v değeri kullanacağımızdan dolayı bu iki bacağı birbirine birleştirip 100n kondansatör ile flitreledim.

Not: Burada bahsettiğim referans gerilimini isterseniz harici olarak bu pinlere uygulayabilirsiniz. PIC referansı beslemeye göre kararsızlık gösterebilir. piyasada, ayarlanabilir daha kararlı referans entegreleri mevcuttur.

PIC16F886 da ADC referans girişlerimizi dışarıdan okuyabildiğimiz gibi ADCON1 registeri ile bağımsız olarak VDD ve VSS beslemeye dahil edebiliyoruz. 11 Bit dönüşümü için bu özelliği kullanacağız.

Uyarı: Bazı PIC ler, özellikle eski olanları bu referans girişlerini bağımsız kontrol donanımına sahip değildir.  böyle durumlarda daha farklı teknikler kullanmanız gerekir.

Öncelikle şunu belirteyim ki, Örnek hazırladığım projenin yazılımı için CCS nin PCWHD derleyicisini kullandım.  Bu normal C dili olmasına karşın PIC programlarken register atamaları yapmıyoruz. yerine uygun fonksiyon komutları kullanılıyor.  diğer dillerde yazmak isteyenler yukarıdaki bahsettiğim registerleri ayarlamak zorunda.

derleyiciye PIC16f886 kütübhanesini eklerken yanında RA2 referans çıkış ayarı için kullanacağımız VRCON registerinin 6. bitinide dahil etmemiz gerekiyor.

#include <16F886.h>
#define VREF_A2   0x40

sanırım derleyici buglarından biri bu olmalı 🙂 16F88 için bunu yapmaya gerek yok.

Daha sonra main bölümünde ilgili donanım ayarlarını yapıyoruz. burada referans voltajını 2,5v olarak ayarlamak ve RA2 den çıkarmak için şu fonksiyonu kullandım:

setup_vref(VREF_LOW|12|VREF_A2);

ve sıra geldik ana döngümüze.

ilk önce ADC nin 0. kanalını açıp vref- yi VSS beslemeye yani şaseye, vref+ yı ise 2,5v olarak ayarladığımız referans çıkışımıza dahil ediyoruz ve ilgili ADC kanalını okuyup “ADC0” isimli 16 Bitlik word değişkenimize kaydediyoruz.

setup_adc_ports(sAN0|VSS_VREF);
set_adc_channel(0);
delay_ms(10);
ADC0=read_adc(ADC_START_AND_READ);

daha sonra,  vref- yi 2,5v referansımıza dahil edip vref+ yı ise VDD yani +5v beslememize uyguluyoruz ve aynı kanaldan tekrar ADC dünüşümü yapıp dier “ADC1” isimli bir değişkene kaydediyoruz.

setup_adc_ports(sAN0|VREF_VDD);
set_adc_channel(0);
delay_ms(10);
ADC1=read_adc(ADC_START_AND_READ);

Bunları yaptıktan sonra her 2 değişkenin değerlerini toplayıp ayrıyetten voltaj değeri dönüşümüde yapıyoruz.

TOPLAM=ADC0+ADC1;
VOLT=TOPLAM;
VOLT=(VOLT * 5 )/2046;

“TOPLAM” değişkeni 16 bitlik word olup, “VOLT” ise 32 bitlik FLOAT yani ondalıklı sayı değişkenidir.  voltaj değerimiz ondalıklı olduğu için bunu kullandım. FLOAT değerleri hafızada çok yer kaplamasına karşın kullanımı pratiktir ancak  bazı derleyiciler bunu desteklemez. böyle durumlarda farklı işlemler yapılır. neyse, esas konumuz 11 Bit ADC olduğuna göre, yöntemini kısaca açıklamış oldum.  C kullanmayanlar için elimde proton basic verisiyonuda mevcut. isteyenler email göndersin.

KAYNAK DOSYALAR.

Projenin CCS PCWHD 4.134 ile derlenmiş C dosyası, özel LCD kütübhanesi, HEX dosyası ve proteus DSN dosyasını Buradan indirin:

https://github.com/profahmet/projedosyalar/raw/master/PIC16F886_LCD_11Bit_ADC.zip

DEVRE DENENMİŞTİR.

Kolay Gelsin.