PIC单片机-AD转换

2019-04-15 11:38发布

编写程序,使用数码管显示ADC测量得到的电压值。电压值由1位整数和1位小数构成。例如若当前AN0通道上的电压为6V,则数码管应显示3.6。 #include #include #define uint8 unsigned char #define uint16 unsigned int __CONFIG(FOSC_HS &WDTE_OFF &BOREN_OFF &PWRTE_OFF &LVP_OFF); //设置配置位 //WDTE_OFF:disable watchdog timer 看门狗禁止 //LVP_OFF:low voltage programming disabled 低电压编程禁止 //FOSC_HS:high speed crystal/resonator 4M以上晶振选择HS高速 //PWRTDIS:disable power up timer //BOREN_OFF:disable brown out reset /***************************定义全局变量***************************************/ uint8 disp[] = {0xC0, 0xF9, 0xA4, 0xB0, 0x99, 0x92, 0x82, 0xF8, 0x80, 0x90}; //共阳数码管段码表 uint16 AD_Result; //ADC转换结果变量 uint16 count; long AD_Result_temp; /***************************声明函数*******************************************/ void ADC_Init(void); void Time2_Init(void); void DelayUS(uint8 delay); void LED_Display(uint8 chosebit, uint8 wdata); /******************************************************************************* * 函 数 名: DelayUS(uint8 delay) * 函数功能: 微秒延时 for 20MHZ * 入口参数: delay * 返 回: 无 *******************************************************************************/ void DelayUS(uint8 delay) { while(--delay); } /****************************************************************************** * 函 数 名: ADC_Init(void) * 函数功能: ADC初始化 * 入口参数: 无 * 返 回: 无 *******************************************************************************/ void ADC_Init(void) { TRISA0 = 1; //模拟通道0设置为输入 ADCON1 = 0x8E; //10001110 Vref+ = VDD Vref- = VSS ADCON0 = 0x01; //选择通道0,使能AD ADIF = 0; //中断标志清零 ADIE = 1; //ADC中断使能 } /******************************************************************************* * 函 数 名: Time2_Init(void) * 函数功能: 定时器2初始化 * 入口参数: 无 * 返 回: 无 *******************************************************************************/ void Time2_Init(void) { T2CON = 0x01; //postscale 1:1 prescale 1:4 PR2 = 250; //匹配寄存器 1*4*250*200ns = 200us TMR2IF = 0; //定时器2中断标志位清零 GIE = 1; //开总中断 PEIE = 1; //开外设中断 TMR2IE = 1; //开定时器中断 } /******************************************************************************* * 函 数 名: LED_Display(uint8 chosebit,uint8 wdata) * 函数功能: 单个数码管显示 * 入口参数: chosebit选择字位,wdata字型 * 返 回: 无 *******************************************************************************/ void LED_Display(uint8 chosebit, uint8 wdata) { if((chosebit < 0) || (chosebit > 4)) return; ADCON1 = 0x8E; //10001110 RA0位模拟输入 TRISA &= 0x01; TRISE &= 0xEF; //配置PORTD为普通IO口,对PORTD的操作务必加上这句 TRISD = 0x00; //数据线配置为输出 PORTA = (PORTA & 0xE3) | ((chosebit + 3) << 2); //RA2:RA3:RA4:011 选通第一位 100选通第二位 101选通第三位 110选通第四位 PORTD = wdata; //送显示数字的断码 DelayUS(100); //延时 PORTD = 0xFF; //关闭显示 } /****************************************************************************** * 函 数 名: mian(void) * 函数功能: 对模拟通道0进行采样,并显示,再采样,再显示 * 入口参数: 无 * 返 回: 无 *******************************************************************************/ void main(void) { long temp; ADC_Init(); //ADC初始化 Time2_Init(); //定时器2初始化 GIE = 1; //总中断使能 PEIE = 1; //外设中断设能 GO = 1; //启动ADC转换 TMR2ON = 1; //启动定时器2计时 while(1) { temp = AD_Result_temp; temp /= 10; LED_Display(2, disp[temp % 10]); //显示十分位 temp /= 10; LED_Display(1, disp[temp % 10] & 0x7F); //显示个位 } } /****************************************************************************** * 函 数 名: interrupt PIC_Init(void) * 函数功能: 中断函数 * 入口参数: 无 * 返 回: 无 *******************************************************************************/ void interrupt PIC_Init(void) { if(ADIF == 1) { ADIE = 0; //关AD中断 ADIF = 0; //AD中断标志清零 AD_Result = ADRESL & 0x00FF; //读取ADC采样结果 AD_Result |= ADRESH << 8 ; AD_Result_temp = AD_Result * 50; //5V为VDD电压,根据不同的电压作修改 AD_Result_temp = AD_Result_temp * 10 / 1023; //再放大10倍,方便计算显示 ADIE = 1; //开启AD中断 } if(TMR2IF == 1) { TMR2IE = 0; //关定时器0中断 TMR2IF = 0; //清标志位 count++; //计数值加1 if(count >= 500) //200us*500 = 100ms,即0.1s启动采样一次 { count = 0; GO = 1; //启动ADC转换 } TMR2 = 0x00; TMR2IE = 1; //开中断 } }