本文包含原理图、PCB、源代码、封装库、中英文PDF等资源
您需要 登录 才可以下载或查看,没有账号?注册会员
×
各位高手,小弟最近看到ADC0832转换 1602显示电压的程序,有几个地方不是很理解(程序中红色部分),程序如下,可不可以帮我解释一下,谢谢了!
#include"reg51.h"
#include"led.h"
#include<intrins.h>
//******************adc0832****************************//
sbit CS=P1^0; //使能。
sbit CLK=P1^1;//时钟
sbit Do=P1^2; // 数据输出
sbit Di=P1^2;//数据输入
unsigned char CH=0x02;
//通道的选择:0x02就是单通道0;0x03就是单通道1;
//0x00就是双通道ch0=“+”; ch0=“-”
//0x01就是双通道ch0=“-”; ch0=“+”
//*****************************************************//
unsigned char ADconv(void)
{unsigned char i;
unsigned int data_f=0,data_c=0;
Di=1;
CS=1;
_nop_();
CS=0;
Di=1; ;//芯片使能之前的初始化。第一个下降沿
CLK=1;
_nop_();
_nop_();
/****************************************/
CLK=0; // 确定通道模式、第2个下降沿
_nop_();
_nop_();
CLK=1;
Di=(bit)(0x02&CH); //设定通道初始化
_nop_();
CLK=0;
_nop_();
_nop_();
CLK=1;
Di=(bit)(0x01&CH); //设定通道初始化 .第3个下降沿
_nop_();
_nop_();
CLK=0; //AD转化的初始化完成。
Di=1;
CLK=1;
_nop_();
_nop_();
CLK=0;
_nop_();
CLK=1;
for(i=8;i>0;i--)//得到一个正常排序的8位数据
{
data_f|=Do;
data_f<<=1;
CLK=1;
_nop_();
_nop_();
CLK=0;
_nop_();
}
for(i=8;i>0;i--)//得到一个反序排列的8位数据
{
data_c<<=1;
data_c|=Do;
_nop_();
CLK=1;
_nop_();
_nop_();
CLK=0;
_nop_();
}
CLK=0;
_nop_();
_nop_();
CLK=1;
_nop_();
_nop_();
CLK=0;
_nop_();
_nop_();
CLK=1;
_nop_();
CS=1;
_nop_();
_nop_();
return data_f;
}
void main(void)
{ unsigned int data_temp=0;
while(1)
{ data_temp=ADconv();
init();
xs_int(196*data_temp,1);
//这里为什么要乘以196?data-temp是字符型的,而xs-int中的参数是整型的,这是怎么转换的?
}
}
//***********************led.h*******************************************//
//******************led1602**********/
#include<intrins.h>
#include<math.h>
#define DD P2
sbit Rs=P3^0;
sbit Rw=P3^1;
sbit E=P3^2;
sbit busy_p=ACC^7;
//********************************//
void delay_1ms(unsigned char i) //最小延时1ms
{ unsigned char j;
while(i--)
for(j=0;j<125; j++);
}
void delay_10ns(unsigned char i) //最小延时10ns
{ unsigned char j;
while(i--)
for(j=0;j<10; j++);
}
/*
void rd_busy(void) //读忙。
{
do{
Rs=0;
Rw=1;
E=0;
delay_10ns(4); //>30ns
E=1; delay_10ns(1); //<25ns
DD=0xfe; delay_10ns(4); //<100ns
ACC=DD;
}while(busy_p==1);
}*/
void write_com(unsigned char com,bit p) //写指令
{if(p)
//rd_busy();
//delay_1ms(1);
delay_10ns(5);
E=0;
Rs=0;
Rw=0;
DD=com;
delay_10ns(50); //>40ns
E=1;
delay_1ms(2); //>150ns
E=0;
delay_10ns(4); //>25+10ns
}
void write_date(unsigned char DATA) //写数据
{
// rd_busy(); delay_1ms(1);
delay_10ns(50);
E=0;
Rs=1;
Rw=0;
DD=DATA;
delay_10ns(50);
E=1;
//delay_1ms(1);
delay_10ns(50);
E=0;
delay_10ns(4);
}
void addr_x_y(unsigned char x,bit y) //写坐标,定位置。
{ unsigned char temp=0x80;
if(y)
{temp|=0x40;}
temp|=x;
write_com(temp,0);
}
void desplay_char(unsigned char x,bit y,unsigned char p) //在指定位置显示一个字符。
{ addr_x_y(x,y);
write_date(p);
}
void init(void)
{delay_1ms(15);
write_com(0x38,0);
delay_1ms(5);
write_com(0x38,0);
delay_1ms(5);
write_com(0x38,0);
delay_1ms(5);
write_com(0x38,1);
write_com(0x08,1);
write_com(0x01,1);
write_com(0x06,1);
write_com(0x0c,1);
}
void xs_int(unsigned int shuju,bit t) //显示一个数字
{unsigned char huancun[6]={0};
unsigned char biaozhi=0,i;
if (shuju < 10) biaozhi = 1;
else if(shuju < 100) biaozhi = 2;
else if(shuju < 1000) biaozhi = 3;
else if(shuju < 10000) biaozhi = 4;
else if(shuju < 65535) biaozhi = 5;
switch(biaozhi)
{case 5:huancun[5] = shuju/10000;
case 4:huancun[3] = shuju%10000/1000;
case 3:huancun[2] = shuju%1000/100;
case 2:huancun[1] = shuju%100/10;
case 1:huancun[0] = shuju%10; //这几段是为什么要这么算?我是菜鸟一个,麻烦了!
break;
default:break;
}
for(i=6;i>1;i--)
{if(i==5)desplay_char(10,1,'.');
else desplay_char(15-i,t,0x30+huancun[i-1]); }
desplay_char(15,t,'V');
} |