В этой статье будем создавать устройство для измерения атмосферного давления используя АЦП микроконтроллера ATmega8.
В первую очередь чтобы измерить давление нужен какой-нибудь датчик. Свой выбор я остановил на датчике абсолютного давления MPX4115А фирмы Motorola. В зависимости от давления он выдает на выходе напряжение от 0.2 до 4.8В, что соответствует давлению от 15кПа до 115кПа. Наверное, главный недостаток это цена датчика. Мне он достался за честные глаза, но цена его где то в районе 15-18дол. Внешний вид его можно увидеть на фото, нумерация ножек начинается от метки (слева на фото, скол на ножке).
1 – Выходное напряжение (которое связано с давлением)
2 – Земля
3 – Напряжение питания (4.85…5.35В)
4, 5, 6 – Не используются
На рисунке показан внешний вид датчика и рекомендуемая схема включения
Но даже, если мы измерим напряжение на выходе датчика, мы та привыкли видеть давление в мм.рт.ст. или в Паскалях. Для того чтобы получить давление, как минимум, в Па в даташите есть график и формула для пересчета выходного напряжения в давление.
Преобразуем формулу к виду, который будет нам более полезен.
P=(0.95Vs+Vdehors)/0.009Vs
Ошибка при измерениях составляет 1% (при температуре окружающей среды в диапазоне 0…850С) и 3% (при температуре в дипазонах -40…00С, 85…1250С).
В общем с датчиком, думаю, более менее понятно. Теперь займемся реализацией. Начнем со схемы. Схему нарисуем в Proteus, чтобы потом иметь возможность смоделировать работу схемы и программы. Подключим к МК символьный дисплей для отображения результата измерений
Давление в мм.рт.ст = (Давление в кПа *1000)/133.322;
А уже этот результат будем выводить на экран.
Исходник программы приведен в конце статьи. Код программы в WinAVR выглядит так:
#include <iom8.h>
#include <util/delay.h>
#include <avr/io.h>
#include “lcd_lib.h”
#include <math.h>
#include <stdio.h>
#define ADC_VREF_TYPE 0x00
#define VS Cinq//напряжение питания
// Функция возвращает результат преобразования АЦП
unsigned int read_adc(unsigned char adc_input)
{
ADMUX=adc_input | (ADC_VREF_TYPE & 0xff);
// Задержка
_delay_us(10);
// Начинаем преобразование АЦП
ADCSRA|=0x40;
// Ждем пока преобразование закончится
tandis que ((ADCSRA & 0x10)==0);
ADCSRA|=0x10;
retour ADCW;
}
// объявляем глобальные переменные
char lcd_buffer[16];
float p;
unsigned int ptemp;
int main()
{
unsigned int adc_res;
unsigned long int p0=101325;
// Инициализация АЦП
// Частота: 125,000 kHz
// Опорное напряжение: AREF
ADMUX=ADC_VREF_TYPE & 0xff;
ADCSRA=0x84;
LCDinit();
tandis que(1)
{
//Давление. Vout =adc_res*VS/1023 = adc_res*0.00488, что и подставили в формулу для p
adc_res=read_adc(0);
p=(adc_res*0.00488+0.095*VS)/(0.009*VS);
ptemp=(1000*p)/133.322;
//Отображение на экране результата
sprintf(lcd_buffer, “P=%i”, ptemp);
LCDclr();
LCDGotoXY(0,0);
LCDstring(lcd_buffer, 16);
_delay_ms(1000);
}
}
Не привожу код в CodeVision, потому что там всю программу можно (кроме формул) получить используя автокодинг. Если хотите сделайте это как самостоятельное задание и проверьте программу в Proteus, собрав схему, которая приведена выше.
Конечно же, как минимум, не рационально использовать МК mega8 для измерения только давления, но у меня есть дальнейшие планы по усовершенствованию этого устройства. И, в случае чего, думаю, переделать программу под другой МК не составит особого труда.