注意: uint8_t正常左移8位是0,但如果赋值给uint16_t就占uint16_t中高8位,要保留数据就要把八位数据左移8位后赋给16数据,继续赋给8位数据,结果就是0

注意:通过ADC采集数据并输出电压的原理是  电压和对应ADC端口采集结果的比值是恒定的

ADC第15通道采集的内部参考电压值非常稳定,约为1.19V,不会随芯片的工作改变,可以拿来反推其他通道的电压。

   内部电压 / ADC15采集值 = 需要测量的电压 / 对应ADC通道采集值

内部电压 / ADC15采集值 = 实际电源电压 / 1023    推算出来实际电压值

1.普通的IO口只能识别0和1,以STC8的IO口为例,输入0.7V识别为0,输入3.3V识别为1,输入一个0.7 ~3.3 V的电压,IO口的输入结果就是随机的了。

2.STC8有10位的ADC模数转换口,10位指的是将0到最大电压进行分割的份数,即1024份,位数越多,测量结果越精确,因为分割的份数多。

 3.  因为要通过串口观察查询到的结果,所以串口初始化函数要保留。在主函数中执行,就可以和电脑建立串口。

4.串口自带的输出功能太麻烦,这里要用的printf函数。调用printf需要

  #include "stdio.h"头文件

在串口初始化函数中修改输出标志位 TI = 1;

5.ADC的函数初始化比较简单

 ADCCFG = 0X2F;   //设置采集到的数据右对齐,采集速度为16分频

6.采集电压的函数

unsigned int Fetch_Power(void)
{
    unsigned int res;
    ADC_CONTR = 0X87;      //打开ADC开关,选择P1.7  ADC7 端口
    ADC_CONTR |=0X40;    // 启动ADC
    _nop_();           
    _nop_();                                 //等待一会
    while(!(ADC_CONTR & 0X20));   //通过标志位,确保在ADC采集完成前不会执行其他语句

                                                          //前面也右好几个地方,是一样通过标志位确保执行完成
    ADC_CONTR &= ~ 0X20;            //标志位需要手动清0
    res = (ADC_RES << 8 )| ADC_RESL ;

//因为采集结果是右对齐,将ADC_RES采集到的2位左移8位,给ADC_RESL腾空间,按照下面的说明就会ADC_RES 和ADC_RESL 里面的10位数全部都放到16位变量res里面

   uint8_t正常左移8位是0,但如果赋值给uint16_t就占uint16_t中高8位 (原因:未知,实际转换成 32位?)          |的意义:就是把data[1]赋值给低8位,原因:0|1 = 1 0|0 = 1  。

          知识盲区。。。。。
    return res;                                      //返回采集到的结果,注意函数了类型要联动修改
}

#include "stc8g.h"
#include "intrins.h"
#include "stdio.h"

……

……

…….

/* 串口初始化函数 */
void UartInit(void)        //115200bps@35MHz
{
    SCON = 0x50;        //8位数据,可变波特率
    AUXR |= 0x01;        //串口1选择定时器2为波特率发生器
    AUXR |= 0x04;        //定时器2时钟为Fosc,即1T
    T2L = 0xB4;        //设定定时初值
    T2H = 0xFF;        //设定定时初值
    AUXR |= 0x10;        //启动定时器2
    
  TI = 1;
}

/* adc初始化函数 */
void ADC_Init(void)
{
 ADCCFG = 0X2F;
}

unsigned int Fetch_Power(void)
{
    unsigned int res;
    ADC_CONTR = 0X87;
    ADC_CONTR |=0X40;
    _nop_();
    _nop_();
    while(!(ADC_CONTR & 0X20));
    ADC_CONTR &= ~ 0X20;
    res = (ADC_RES << 8 )| ADC_RESL ;
    return res;
}

/* 主函数 */
void main()
{
    unsigned int Power;
    P0M0 = 0x00;   //设置P0.0~P0.7为双向口模式
    P0M1 = 0x00;
    
    UartInit(); // 串口初始化
    ADC_Init();   //最开始忘记调用ADC初始化函数,采集到的数据非常离谱,是个负数……..
    while(1)
    {
        delay_ms(1000);
        Power = Fetch_Power();
        printf("Power =  %d \r\n",    Power);    //采集的数据赋值后输出

    }
}

 

          

物联沃分享整理
物联沃-IOTWORD物联网 » STC8学习 ——ADC 1

发表评论