AD转换器和51单片机和LED
发布网友
发布时间:2022-05-02 01:44
我来回答
共3个回答
热心网友
时间:2022-06-26 10:17
这个是一个用PCF8591结合51单片机的AD用数码管显示程序
可以看一看
#include<reg52.h>
#include <intrins.h>
sbit lockd=P1^0;
sbit lockw=P1^1; //地址:写0x90/读0x91
sbit scl=P1^2;
sbit sda=P1^3;
unsigned char ad_date,da_date;
#define port P0 //定义数据端口 程序中遇到DataPort 则用P0 替换
unsigned char code anma[]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x80,0x3e};// 显示段码值0~9
unsigned char code weima[]={0x7f,0xbf,0xdf,0xef,0xf7,0xfb,0xfd,0xfe};//分别对应相应的数码管点亮,即位码
unsigned long int k;
unsigned char ge,shi,;
unsigned int m=0;
/*-------------------------------------
数码管一位显示
--------------------------------------*/
void display1(unsigned char an,unsigned char wei)
{
port=0;
lockd=1;
lockd=0;
port=weima[wei];
lockw=1;
lockw=0;
port=anma[an];
lockd=1;
lockd=0;
}
/*-------------------------------------
数码管三位显示A/D转化数据
--------------------------------------*/
void display_ad()
{
display1(,3);
display1(10,3);
display1(shi,2);
display1(ge,1);
display1(11,0);
}
/*------------------------------
i2c启动
--------------------------------*/
void start_i2c()
{
sda=1;
scl=1;
_nop_();_nop_();_nop_();
sda=0;
_nop_();_nop_();_nop_();
scl=0;
}
/*------------------------------
i2c停止
--------------------------------*/
void stop_i2c()
{
sda=0;
_nop_();
scl=1;
_nop_();_nop_();
sda=1;
_nop_();
}
/*------------------------------
i2c发送一个字节
--------------------------------*/
void send_i2c(unsigned char date)
{
char i;
scl=0;
for(i=0;i<8;i++)
{
if(date&0x80)sda=1;
else sda=0;
_nop_();
scl=1;
date=date<<1;
_nop_();_nop_();_nop_();_nop_();
scl=0;
_nop_();
}
sda=1;
scl=0;
}
/*------------------------------
i2c接收一个字节
--------------------------------*/
unsigned char recive_i2c()
{
unsigned char recive=0;
char i;
scl=0;
_nop_();
sda=1; //置数据线为输入方式
for(i=0;i<8;i++)
{
scl=0; //置时钟线为低,准备接收数据位
_nop_(); //时钟低电平周期大于4.7us
_nop_();_nop_();_nop_();_nop_();
scl=1;
_nop_();
if(sda)recive |=0x01;
else recive &=0xfe;
_nop_();
recive=recive<<1;
scl=0;
}
return(recive);
scl=0;
}
/*------------------------------
i2c应答脉冲
--------------------------------*/
void i2c_ack_p()
{
scl=0;
_nop_();
scl=1;
_nop_();_nop_();
_nop_();
scl=0;
}
/*------------------------------
i2c应答
--------------------------------*/
void i2c_ack()
{
scl=0;
_nop_();
sda=0;
_nop_();
scl=1;
_nop_();_nop_();
scl=0;
_nop_();
}
/*------------------------------
i2c非应答
--------------------------------*/
void i2c_noack()
{
scl=0;
_nop_();
sda=1;
_nop_();
scl=1;
_nop_();_nop_();
scl=0;
}
/*------------------------------
D/A转换
--------------------------------*/
void da_zh(unsigned char date)
{
start_i2c();
send_i2c(0x90); //地址 写
i2c_ack_p();
send_i2c(0x40); //控制字,D/A转化
i2c_ack_p();
send_i2c(date);
i2c_ack_p();
stop_i2c();
}
/*------------------------------
A/D转换
--------------------------------*/
unsigned char ad_zh()
{
unsigned char date;
start_i2c();
send_i2c(0x90); //地址 写
i2c_ack_p();
send_i2c(0x40);
i2c_ack_p();
stop_i2c();
start_i2c();
send_i2c(0x91); //地址 读
i2c_ack_p();
date=recive_i2c();
i2c_ack();
date=recive_i2c();
i2c_noack();//当主器件作接收器时,必须发出数据传输结束信号给发送器
stop_i2c(); //即它在最后一个字节之后的应答脉冲期间不会产生应答(不拉低SDA)
//这种情况,发送器必须释放SDA为高以便主器件产生停止条件
return(date);
}
/*----------------------
主函数
-----------------------*/
void main(void)
{
while(1)
{
m++;
if(m==500)
{
m=0;
ad_date=ad_zh();// A/D转换
da_date=ad_date;
k=da_date;
k=(k*500)/0xff;
da_zh(da_date);// D/A转换
=k/100;
shi=(k%100)/10;
ge=(k%100)%10;
}
display_ad();
}
}
热心网友
时间:2022-06-26 10:17
需要写AD转换的接口,和显示程序,很简单的,到网上搜一搜,相似的程序不少。搜电压表吧,原理一样的,AD转换送显示。
热心网友
时间:2022-06-26 10:18
是三相电吗?追问嗯,请问你有程序不?