找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 2198|回复: 5
打印 上一主题 下一主题
收起左侧

自己摸索写了一段单片机三通道轮询方式检测ADC的值,好像不正确,请大家指点

[复制链接]
跳转到指定楼层
楼主
本帖最后由 zhth1979 于 2022-1-7 11:31 编辑

前两天发了求助帖,但没有什么找到这方面的例程 ,自己摸索写了一段三通道轮询方式检测ADC的值,好像不正确,请大家指点!单片机型号:STC8H3K32S2


#include "AD.h"

unsigned char ad_flag=1;
unsigned char ad_result=0;
int ad_show1=0;
int ad_show2=0;

unsigned char ADC_Conv(unsigned char channel)
{
        
       // unsigned char ad_result=0;
  P1M1 = 0x07;   P1M0 = 0x00;   //设置 P1.0 P1.1 P1.2 为 ADC 输入口

        
        ADC_SetChannel(channel);   //1.选通道
        P_SW2|=0X80;
        ADCTIM=0X3F;    //设置ADC内部时序
        P_SW2&=0X7F;
        ADCCFG=0X0F;    //设置ADC时钟为系统时钟/2/16        
        ADC_CONTR = 0x80  | channel;            ADC_CONTR|=0X40; //启动AD转换
        _nop_();
        _nop_();
        while(!(ADC_CONTR&0x20));  //查询ADC完成标志
        ADC_CONTR &=~0X20;        //清完成标志
        ad_result=(ADC_RES<<8)|ADC_RESL;               //读取ADC结果
          _nop_();
          _nop_();
                return ad_result;        
}

void Timer0Init()
{
  TMOD &= 0XF0;    //设置定时器模式
        TMOD |=0X01;     //设置定时器16位不可重装载模式
        TH0=0XFC;        //设置定时初值
        TL0=0X18;        //设置定时初值
        TF0=0;           //清除TF0标志
        ET0=1;           //定时器0的中断开关
        TR0=1;           //定时器0开始计时
}


void timer0_ISR() interrupt 1
{
        static unsigned int timer0Cnt;
        timer0Cnt++;
        if(timer0Cnt>=1000)
        {
          timer0Cnt=0;
                ad_flag=1;
        }
  TR0=0;
        TH0=0XFC;
        TL0=0X18;
        TR0=1;
}


void adc()
{
        unsigned int ad_0,ad_1,ad_2;
        unsigned char channel=0;
  Timer0Init();
        EA=1;
        if(ad_flag==1)
        {
                ad_flag=0;                     
                ad_0=ADC_Conv(0);
                ad_1=ADC_Conv(1);
                ad_2=ADC_Conv(2);
               
                ad_show1 = ad_0- ad_1;         //压力传感器差分值
                ad_show2 = ad_2/4096*2.5;     //测量电池电压           
        }
}
主函数再调用   adc();    ad_show1和ad_show2两个值。





分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏 分享淘帖 顶 踩
回复

使用道具 举报

沙发
ID:161164 发表于 2022-1-5 17:52 | 只看该作者
main呢?
while(1)呢?
回复

使用道具 举报

板凳
ID:686513 发表于 2022-1-6 08:38 | 只看该作者
lkc8210 发表于 2022-1-5 17:52
main呢?
while(1)呢?

这个是子程序,main在主程序里呢。
回复

使用道具 举报

地板
ID:213173 发表于 2022-1-6 10:51 | 只看该作者
这是ADC.C ,形参CH范围0~14。供主函数调用GetADCResult(x);。
  1. #include <STC8G.H>
  2. #include "intrins.h"
  3. #define uchar unsigned char
  4. #define uint unsigned int
  5. #define ADCTIM  (*(unsigned char volatile xdata *)0xfea8)
  6. //宏定义ADC的操作命令
  7. #define ADC_POWER   0x80                        //ADC power control dit (宏定义ADC电源控制位)1000 0000
  8. #define ADC_START   0x40                        //ADC start control dit (宏定义ADC启动控制位)0100 0000
  9. #define ADC_FLAG    0x20                        //ADC complete flag (宏定义ADC完成标志位)    0010 0000
  10. #define ADC_EPWMT   0x10                        //使能 PWM  实时触发 ADC                     0001 0000

  11. //InitADC 初始化ADC
  12. void Init_ADC()
  13. {        //ADC 控制器  电源  启动  完成  --   15通道模拟选择位
  14.         //ADC_CONTR    B7    B6    B5   B4   B3   B2   B1   B0
  15.         P_SW2 |= 0x80;                        //打开
  16.         ADCTIM = 0x3f;                        //设置 ADC 内部时序
  17.         P_SW2 &= 0x7f;                        //关闭
  18.         ADCCFG = 0x27;                        //设置ADC结果右对齐,速度为512系统时钟
  19.         ADC_RES=0;                                //清除ADC_RES存储器以前的结果
  20.         ADC_RESL=0;
  21.         ADC_CONTR=ADC_POWER; //ADC 开启电源
  22.         delayms(1);                                //上电延时1ms                                                                                       
  23. }

  24. //        读取ADC结果
  25. uint GetADCResult(uchar CH)
  26. {
  27.         ADC_CONTR=ADC_POWER|ADC_START|CH;//启动转换1100 1000
  28.         _nop_();_nop_();                                //小延时
  29.         while (!(ADC_CONTR & ADC_FLAG));//等待ADC转换完成标志置位 1010 0000
  30.         ADC_CONTR &=~ADC_FLAG;                        //清完成标志
  31.         return ADC_RES<<8|ADC_RESL;                //返回十位ADC结果
  32. }
复制代码

回复

使用道具 举报

5#
ID:686513 发表于 2022-1-6 15:15 | 只看该作者
本帖最后由 zhth1979 于 2022-1-6 15:25 编辑
wulin 发表于 2022-1-6 10:51
这是ADC.C ,形参CH范围0~14。供主函数调用GetADCResult(x);。

这个不错,应该可以用!但这两句是什么意思?没看懂。#define ADCTIM  (*(unsigned char volatile xdata *)0xfea8)    #define ADC_EPWMT   0x10                        //使能 PWM  实时触发 ADC                     0001 0000    在我这个应用中应该没作用吧?
回复

使用道具 举报

6#
ID:301191 发表于 2022-1-6 18:34 | 只看该作者
顶一下
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表