مبدل آنالوگ به دیجیتال

هدف پروژه: راه اندازی واحد adc (مبدل آنالوگ به دیجیتال) و استفاده از سیگنال های آنالوگ بیرون میکرو و قابل فهم کردن آن ها برای میکروی دیجیتال. روند کار به این صورت است که یک ورودی آنالوگ به یکی از پایه های میکرو وصل است. آن را خوانده و مقدار ولتاژ آن لحظه سیگنال را در ال سی دی کاراکتری نمایش می دهیم.

سخت افزار مورد استفاده: در این مثال از برد آموزشی avr شرکت نامینیک مبتنی بر تراشه ATMEGA32 استفاده می کنیم. به جای سیگنال آنالوگ از یک تقسیم ولتاژ پتانسیومتری استفاده می کنیم. که در برد موجود است. خروجی پتانسیومتر به پایه 5 پورت a متصل است. می دانیم که واحد adc فقط 8 کانال روی پورت a این میکرو دارد. سخت افزار مورد استفاده برای نصب و راه اندازی ال سی دی کاراکتری هم روی بورد هست که در مثال های قبلی بررسی شده است.

کتابخانه های استفاده شده: به جز تعریف خود میکرو در خط 9، کتابخانه تاخیر ها و ال سی دی نیز در خطوط 10 و 11 تعریف شده و در دو خط بعدی هم توابع کاراکتری و ورودی خروجی مورد نیاز برای خطوط 84 و 85 تعریف شده اند.

تشریح کد: واحد adc در خطوط 34 و 35 مقدار دهی اولیه شده است. فرکانس واحد adc 125 کیلو هرتز تعیین شده، ولتاژ مرجع aref در بورد میزان ثابت 3.3 ولت است و سیگنال آنالوگ به 8 بیت دیجیتال تبدیل می شود. اگر حالت های دیگری را مد نظر دارید، به دیتاشیت یا کدویزارد مراجعه کنید. شرکت اتمل در دیتاشیت میکرو توصیه می کند فرکانس کلاک واحد adc را بین 50 تا 200 کیلوهرتز تعیین کنید. اگر به سرعت نمونه برداری بیشتری نیاز داشتید باید حتما از حالت تبدیل به 8 بیت استفاده کنید نه 10 بیت. ضمن اینکه هرچه فرکانس از 200 کیلوهرتز دورتر شود عدم قطعیت و خطا در اندازه گیری بیشتر می شود.

کدویزارد در حالتی که وقفه واحد adc فعال نباشد، یک تابع به نام read_adc تعریف می کند. که در خطوط 17 الی 27 برنامه، این تابع را مشاهده می کنید. این تابع یک آرگومان می گیرد که شماره پینی از 8 پین پورت a است که باید تبدیل روی آن کانال انجام شود. عدد بیشتر از 7 ممکن است جواب های ناخواسته دهد یا برنامه را قفل کند. خروجی پتانسیومتر ما به پین 5 وصل می شود. وظیفه این تابع خواندن کانال انتخاب شده و برگرداندن 8 بیت (البته در این جا) معادل سیگنال آنالوگ پین مربوطه (نسبت به ولتاژ مرجع vref) است. این تابع بعد از شرط شروع تبدیل (خط 22) آنقدر منتظر می ماند (حلقه while خط 23) تا تبدیل کامل شود و نتیجه معتبر گردد.  توجه کنید که باتوجه به فرکانس انتخاب شده  برای واحد adc، تابع read_adc حدود 0.32 میلی ثانیه طول می کشد. یعنی عملا نمونه بردای از یک سیگنال آنالوگ خارجی با فرکانس بیشتر از1600 هرتز بی فایده بوده و اطلاعات کامل بازیابی نمی شود. در دیتاشیت میکرو هم بدون هیچ تابع و دستور اضافه، حداکثر سرعت تبدیل واحد adc را در حداکثر فرکانس، 15 کیلو نمونه بر ثانیه آورده است.  پس به این نکته هم دقت کنید.

در خط 41 تابع read_adc برای کانال 5 فراخوانی می شود. در خط 42 مقدار تبدیل شده به مقدار ولتاژی بین صفر تا 3.3 ولت تبدیل می شود. در خط 48 اندازه ولتاژ به در یک متغییر با دو رقم اعشار ریخته می شود و در نهایت در خط 49 این رشته به مقداری که بتوان آن را در ال سی دی نمایش داد در می آید.

/*****************************************************
Chip type               : ATmega32
AVR Core Clock frequency: 8.000000 MHz
Memory model            : Small
External RAM size       : 0
Data Stack size         : 512
*****************************************************/
 
#include <mega32.h>
#include <delay.h>
#include <alcd.h>
#include <stdio.h>      //use for call sprinf function in line 85.
#include <stdlib.h>     //use for call ftoa function in line 84.
 
#define ADC_VREF_TYPE 0x20
 
unsigned char read_adc(unsigned char adc_input) //this function read signal from spaceficed pin in adc_input.
{
ADMUX=adc_input | (ADC_VREF_TYPE & 0xff);      //change channel.
delay_us(10);          //wait for change channel.
 
ADCSRA|=0x40;          //start the AD conversion.
while ((ADCSRA & 0x10)==0);    //wait for the AD conversion to complete.
 
ADCSRA|=0x10;          //clear interrupt flag.
return ADCH;
}
 
void main(void)
{
unsigned char init_result[3],lcd_result[9];
float bss;
 
ADMUX=ADC_VREF_TYPE & 0xff;   
ADCSRA=0x86;          //initiate AD for 125kHz clock, 8 bit result and AREF pin as voltage reference.
 
lcd_init(8);   //lcd connect to port D and 8 line mode.
 
while (1)
      {
        bss=read_adc(5);
        bss=bss*(3.3/256);
        
        lcd_clear();
        lcd_gotoxy(0,0);
        lcd_putsf("voltage is:");
        
        ftoa(bss,2,init_result);
        sprintf(lcd_result,"%d volt.", init_result);
        
        lcd_gotoxy(1,0);
        lcd_puts(lcd_result);
        
        delay_ms(350);
      }
}

دانلود سورس کد

در  اینجا شما میتوانید سورس برنامه را دریافت ،کامپایل و پروگرم نمایید و شاهد عملکرد برنامه باشید.

Tags: , , ,