打印

数码管不能动态扫描~~~~求大侠帮忙~~~

[复制链接]
2762|13
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
#include <AT89X51.H>
#define unchar unsigned char
#define unint unsigned int
unchar code dispcode[]={         
    0x3F,  //"0"
                0x06,  //"1"
                0x5B,  //"2"
                0x4F,  //"3"
                0x66,  //"4"
                0x6D,  //"5"
                0x7D,  //"6"
                0x07,  //"7"
                0x7F,  //"8"
                0x6F,  //"9"
                0x77,  //"A"
                0x7C,  //"B"
                0x39,  //"C"
                0x5E,  //"D"
                0x79,  //"E"
                0x71,  //"F"
    0x00,  //熄灭
                0x40,  //"-"
};//数码管段码 (共阴)
unchar data disdata[5];
unint tvalue; //温度值
unchar tflag; //温度正负标志
sbit DQ=P3^5; //ds18b20与单片机连接口
unchar i,j;
//******************************************************************/
void Delay(unchar a)
{
  unchar i;
while (--a!=0)
{
         for (i=0;i<100;i++);
}
}
//******************************************************************/
void delay_18B20(unint i) //延时1微秒
{
    while(i--);
}
//******************************************************************/
void ds1820rst()   //ds1820复位
{
unchar x=0;
DQ = 1;            //DQ复位
delay_18B20(4);   //延时
DQ = 0;            //DQ拉低
delay_18B20(100);   //精确延时大于480us
DQ = 1;            //拉高
delay_18B20(40);
}
//******************************************************************/
unchar ds1820rd()   //读数据*/
{
unchar i=0;
unchar dat = 0;
for (i=8;i>0;i--)
{   
  DQ = 0;    //给脉冲信号
     dat>>=1;
     DQ = 1;    //给脉冲信号
     if(DQ)
     dat|=0x80;
     delay_18B20(10);
}
    return(dat);
}
//******************************************************************/
void ds1820wr(unchar wdata) //写数据
{
unsigned char i=0;
    for (i=8; i>0; i--)
    {
     DQ = 0;
      DQ = wdata&0x01;
      delay_18B20(10);
      DQ = 1;
     wdata>>=1;
    }
}
//******************************************************************/
read_temp()     //读取温度值并转换
{
unchar a,b;
ds1820rst();   
ds1820wr(0xcc);   //跳过读序列号
ds1820wr(0x44);   //启动温度转换
ds1820rst();   
ds1820wr(0xcc);   //跳过读序列号
ds1820wr(0xbe);   //读取温度
a=ds1820rd();
b=ds1820rd();
tvalue=b;
tvalue<<=8;
tvalue=tvalue|a;
    if(tvalue<0x0fff)
    tflag=0;
    else
    {
     tvalue=~tvalue+1;
  tflag=1;
    }
tvalue=tvalue*(0.625); //温度值扩大10倍,精确到1位小数
return(tvalue);
}
//******************************************************************/
void ds1820disp()//温度值显示
{
read_temp();
    disdata[0]=tvalue/1000; //百位数
    disdata[1]=tvalue%1000/100;//十位数
    disdata[2]=tvalue%100/10; //个位数
    disdata[3]=tvalue%10;  //小数位
    if(disdata[0]==0)
    {
  disdata[0]=16;   //如果百位为0,不显示
     if(disdata[1]==0)
     {
   disdata[1]=16;  //如果百位为0,十位为0也不显示
     }
    }
  P0=0x01; //选通一位
  P2=dispcode[disdata[3]];//
  Delay(5);
  P0=0x02; //选通一位
  P2=dispcode[disdata[2]]-0x80;//
  Delay(5);
  P0=0x04; //选通一位
  P2=dispcode[disdata[1]];//
      Delay(5);
  P0=0x08; //选通一位
  P2=dispcode[disdata[0]];//
}
//............................................................................................
void main(void)
{
    EA=1;
    while(1)
    {
       ds1820disp();   
    }
}

PNT_MWMX6@67]T7RC{2PV6O.jpg (260.73 KB )

PNT_MWMX6@67]T7RC{2PV6O.jpg

相关帖子

沙发
NE5532| | 2009-11-25 20:37 | 只看该作者
又见仿真族。你把这么大个程序写完了,发现显示不正确,是不是很想哭?应该在动手写的时候就边写边测。见《脱离仿真器玩单片机》,另外建议——珍爱生命,远离仿真!

使用特权

评论回复
板凳
zhenxing2000| | 2009-11-25 21:56 | 只看该作者
位选三极管接错了吧?
这种接法三极管的PN节无**向偏置,也就无法选通数码管。

使用特权

评论回复
地板
程序匠人| | 2009-11-25 23:05 | 只看该作者
珍爱生命,远离仿真——这句话很新颖。

使用特权

评论回复
5
123987| | 2009-11-26 14:37 | 只看该作者
同意三楼的说法。建议回去抱着《模拟电路》刻苦攻读三个晚上自己再试试。单片机的入门很简单,但要想深入的研究就要拓宽自己的知识面。模拟电路,数字电路是两门最基础的功课。据我所知有些计算机专业的是不学模拟电路的。还有就是奉劝楼主把基础打牢,在学校的时候别就光想着英语过4级,计算机过三级的。毕竟英语和计算机只是工具而已。当然造成这种现象的原因不能全怪楼主,市场要承担很大一部分责任。呵呵!真正体现电工价值的还是专业知识。“珍爱生命,远离仿真”,这句话似乎有恐吓之嫌哦!哈哈!!!

使用特权

评论回复
6
sjn201| | 2009-11-26 14:46 | 只看该作者
:D

使用特权

评论回复
7
jackxn| | 2009-11-26 15:32 | 只看该作者
disdata[0]=tvalue/1000; //百位数
    disdata[1]=tvalue%1000/100;//十位数
    disdata[2]=tvalue%100/10; //个位数
    disdata[3]=tvalue%10;  //小数位
怎么感觉有点怪?这个写法对么?

使用特权

评论回复
8
myl0913| | 2009-11-26 17:03 | 只看该作者
貌似不对吧

使用特权

评论回复
9
青石向晚|  楼主 | 2009-11-26 22:43 | 只看该作者
5楼的回答让我很崩溃~~~都牵扯上社会~~~我不想说我数电模电有多强,说了你也不信,至于上面那个问题也很快解决了,所以在没有得到是什么实质性答案后就赶快结贴了~~~回7.8楼,那个写法是对的~~~

使用特权

评论回复
10
123987| | 2009-11-27 10:05 | 只看该作者
我不想要求你谦虚,因为谦虚不是你的义务。可能我的说法有点让你不快了。但是作为一个电工要加强自身的技术能力还是非常有必要的,毕竟咱们都是靠技术吃饭的。贴出这种图贻笑大方(我不是指我只大方)不是你的错,但不谦虚,还想让别人帮助你。你的要求是不是也多了点。

使用特权

评论回复
11
青石向晚|  楼主 | 2009-11-27 22:08 | 只看该作者
我不是电工,我的专业方向是dsp,这个是帮我同学做的,单片机我也只是顺手学的,并不精通~~~

使用特权

评论回复
12
tcc8073| | 2009-11-28 11:57 | 只看该作者
DSP不是单片机啊,我现在才知道,我一直以为51,DSP,ARM都是单片机,惭愧,我也一直当单片机用

使用特权

评论回复
13
青石向晚|  楼主 | 2009-11-28 12:42 | 只看该作者
我有说不是单片机吗,我就纳闷了,这么大人了,怎么还这么好斗,跟小孩子一样,你觉得在这边唧唧歪歪的有意思吗,无聊至极,有时间做点有意义的事不好吗,这是最后一次回你的帖,如果你觉得无聊可以继续找别人~~~

使用特权

评论回复
14
ecomputer| | 2009-11-29 18:58 | 只看该作者
前些天女朋友实训时我给他做的,上班时间背着老板半小时搞定,我叫她对着我给她的电路图焊接,程序发给她第3次就OK吧,你可以参考一下,动态少苗最好用定时器定时,我这没用
#include <reg52.h>
#define uint unsigned int
#define uchar unsigned char

sbit DQ = P1^4; //18b20接口

//uchar data i = 0; // 位码(选通各位数码管),初值为11111110
unsigned int temp; //读取的温度值

//uchar seg_tab[] = {0x7f,0xbf,0xdf,0xef};
sbit high = P2^6;
sbit low = P2^7;

sbit buzzer = P3^5; //蜂鸣器

//unsigned int time_count; //中断时间计数

uchar tab[]={
                0xC0,/*0*/
        0xF9,/*1*/
        0xA4,/*2*/
        0xB0,/*3*/
        0x99,/*4*/
        0x92,/*5*/
        0x82,/*6*/
        0xF8,/*7*/
        0x80,/*8*/
        0x90,/*9*/
                }; //共阳数码管 0~9
/*
***********************************************************
** Name: void delay(unsigned int i)
** description: 延时函数
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/
void delay(uint i)
{
         while(i--);
}

/*
***********************************************************
** Name: void init_18b20(void)
** description: 18b20初始化函数
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/
void init_18b20(void)
{
         uchar x=0;
         DQ = 1;    //DQ复位
         delay(8);  //稍做延时
         DQ = 0;    //单片机将DQ拉低
         delay(80); //精确延时 大于 480us
         DQ = 1;    //拉高总线
         delay(14);
         x=DQ;      //稍做延时后 如果x=0则初始化成功 x=1则初始化失败
         delay(20);
}

/*
***********************************************************
** Name: uchar ReadOneChar(void)
** description: 从18b20读取一个字节
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/
uchar ReadOneChar(void)
{
        uchar i=0;
        uchar dat = 0;
        for (i=8;i>0;i--)
         {
                  DQ = 0;
                  dat>>=1;//先得到高位
                 DQ = 1;
                  if(DQ)
                   dat|=0x80;
                  delay(4);
         }
         return(dat);
}


/*
***********************************************************
** Name: void WriteOneChar(uchar dat)
** description: 向18b20写一个字节
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/
void WriteOneChar(uchar dat)
{
         uchar i=0;
         for (i=8; i>0; i--)
         {
                  DQ = 0;
                  DQ = dat&0x01;
                  delay(5);
                  DQ = 1;
                  dat>>=1;//先写低位,后写高位
         }
}



/*
***********************************************************
** Name: uint ReadTemperature(void)
** description: 读取温度
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/

uint ReadTemperature(void)//采用上电默认的12位分辨率
{
        uchar a=0;
        uchar b=0;
        uint t=0;
        uchar Temperature;
        init_18b20();
        WriteOneChar(0xCC); // 跳过读序号列号的操作
        WriteOneChar(0x44); // 启动温度转换
        init_18b20();
        WriteOneChar(0xCC); //跳过读序列号的操作
        WriteOneChar(0xBE); //读取温度寄存器等(共可读9个寄存器) 前两个就是温度
        a=ReadOneChar();//温度数字量低字节
        b=ReadOneChar();//温度数字量高字节
        t=b;
        t<<=8;
        t=t|a;
        Temperature=(t&0x07f0)>>4;
        return Temperature;
}


/*
***********************************************************
** Name:void timer0_init(void)
** description: 定时器0初始化 //计时50ms
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/
/*void timer0_init(void)
{
        TMOD = 0x01;     // 定时/计数器0工作于方式1   2ms   
    TH0=0xf8;
    TL0=0x30;
    ET0 = 1;         // 定时/计数器0允许中断   
    TR0 = 1;         // 启动定时/计数器0
}*/


/*
***********************************************************
** Name:void timer0(void) interrupt 1 using 0
** description: 定时器0中断函数
** parameters: None
** Returns: None      
** Author: lhl
** Date: 2009.11.01
** Version:       
***********************************************************
*/
/*void timer0(void) interrupt 1 using 0
{
        P2 = seg_tab[~i];

        if(i == 0)
        P0 = tab[temp/10]; // 显示十位
        else       
        P0 = tab[temp%10]; // 显示个位        
    TH0=0xf8;
    TL0=0x30;
}*/

void main(void)
{
       
        //timer0_init();
        //EA = 1;
        P2 = 0xff;
        P3 = 0xff;
    while(1)
        {
                temp = ReadTemperature();
                //temp = 15;
                P0 = tab[temp/10]; // 显示十位
                high = 0;
                low = 1;
               
                P0 = tab[temp%10]; //显示个位
                low = 0;
                high = 1;

                if(temp > 25)
                buzzer = 0;
                else
                buzzer = 1;
        }
}

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

13

主题

41

帖子

0

粉丝