亲自原创,采用PROTEUS仿真AT89C51单片机结合ADC0801,对外接设备进行电压、电阻、电流三项指标的同时监测,使用的芯片相对比较简单和低级,主要是希望能够对于想DIY充电监测USB的同鞋起到抛砖引玉的作用,大家一起交流学习。下面是原理图和代码:
单片机源码:
- #include <reg52.h>
- #define uchar unsigned char
- #define uint unsigned int
- #define ulong unsigned long
- uchar code num[10]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};//数码管10个数字
- sbit wei1=P2^0; //数码管位选1
- sbit wei2=P2^1; //数码管位选2
- sbit CS=P2^2; //ADC模块通讯信号CS
- sbit read=P2^3; //ADC模块通讯信号RD
- sbit daduan=P2^4; //ADC模块通讯信号INT
- sbit LE=P2^5; //ADC模块输入锁存器控制
- sbit point=P1^7; //数码管的。点
- sbit write=P2^6; //ADC模块通讯信号WR
- sbit udis=P0^0; //电压数码管锁存器使能引脚
- sbit rdis=P0^1; //电阻数码管锁存器使能引脚
- sbit idis=P0^2; //电流数码管锁存器使能引脚
- uint adc;
- void delay1ms();
- void main()
- {
- uint a,qian,bai,shi,ge,u,r,i1,i;
- float rf;
- /*****************************初始化***********************************/
- P1=0X00; //数码管驱动脚
- P3=0XFF; //ADC数据接收脚
- CS=1; //ADC控制引脚为产生起始时序,初始化给高电平
- read=1; //ADC控制引脚为产生起始时序,初始化给高电平
- daduan=1; //ADC控制引脚为产生起始时序,初始化给高电平
- /*****************************主要部分***********************************/
- while(1)
- {
- /*****************************给ADC应答时序开始转换**********************************/
- LE=1;
- CS=0;
- delay1ms();
- write=0;
- delay1ms();
- while(daduan==0); //等待ADC转换结束
- CS=0;
- delay1ms();
- read=0;
- delay1ms();
- LE=0;
- /************************************************************************************/
- adc=P3; //对ADC转换结果进行取值
- read=1; //将ADC通讯引脚重新初始化到高电平状态
- CS=1; //将ADC通讯引脚重新初始化到高电平状态
- daduan=1; //将ADC通讯引脚重新初始化到高电平状态
- write=1; //将ADC通讯引脚重新初始化到高电平状态
- delay1ms();
- /*******************************电压显示部分*****************************************/
- a=(uint)adc*19.53125*2; //将ADC结果进行十进制的电压转换19.53125mV=5V/256,乘2结果符合实际,不知道为啥
- u=a; //先将a值取出,以免后续被肢解
- qian=a/1000;
- a=a%1000;
- bai=a/100;
- a=a%100;
- shi=a/10;
- a=a%10;
- ge=a;
- udis=1; //打开电压显示数码管对应的锁存器
- rdis=0; //关闭电阻显示数码管对应的锁存器
- wei2=0;wei1=0;
- P1=num[qian];point=1;
- delay1ms();
- wei2=0;wei1=1;
- P1=num[bai];
- delay1ms();
- wei2=1;wei1=0;
- P1=num[shi];
- delay1ms();
- wei2=1;wei1=1;
- P1=num[ge];
- delay1ms();
- P1=0X00; //给数码管低电平消影
- udis=0; //关闭电压显示数码管对应的锁存器
- /*******************************电流显示部分*****************************************/
- i=(5000-u)*10;
- i1=i;
- qian=i/1000;
- i=i%1000;
- bai=i/100;
- i=i%100;
- shi=i/10;
- i=i%10;
- ge=i;
- idis=1; //打开电流显示数码管对应的锁存器
- wei2=0;wei1=0;
- P1=num[qian]; point=1;
- delay1ms();
- wei2=0;wei1=1;
- P1=num[bai];
- delay1ms();
- wei2=1;wei1=0;
- P1=num[shi];
- delay1ms();
- wei2=1;wei1=1;
- P1=num[ge];
- delay1ms();
- P1=0X00; //给数码管低电平消影
- idis=0; //关闭电流显示数码管对应的锁存器
- /*******************************电阻显示部分*****************************************/
- rf=(u*1.000/i1)*1000; //中间进行一步浮点运算,主要考虑u/i1除法运算只有浮点型时才能够保留小数点以后数值
- r=(uint)rf; //将得出的浮点值强制转换为整型变量
- qian=r/1000;
- r=r%1000;
- bai=r/100;
- r=r%100;
- shi=r/10;
- r=r%10;
- ge=r;
- rdis=1; //打开电阻显示数码管对应的锁存器
- wei2=0;wei1=0;
- P1=num[qian];point=1;
- delay1ms();
- wei2=0;wei1=1;
- P1=num[bai];
- delay1ms();
- wei2=1;wei1=0;
- P1=num[shi];
- delay1ms();
- wei2=1;wei1=1;
- P1=num[ge];
- delay1ms();
- P1=0X00; //给数码管低电平消影
- rdis=0; //关闭电阻显示数码管对应的锁存器
- }
- }
- void delay1ms()
- {
- unsigned char a,b;
- for(b=102;b>0;b--)
- for(a=3;a>0;a--);
- }
复制代码
附件是包括仿真电路和程序代码的所有文件
电压电阻电流同时监测.zip
(357.23 KB, 下载次数: 130)
|