[AVR单片机] ATmega128控制74595实现跑马灯

[复制链接]
4520|11
 楼主| hvcb_hlj 发表于 2009-7-16 15:13 | 显示全部楼层 |阅读模式
//=============================================

#include <avr/io.h>
#include <avr/delay.h>
#include <avr/signal.h>
#include <avr/interrupt.h>
#include <avr/pgmspace.h>
#define sbi(sfr,bit) (_SFR_BYTE(sfr)|=_BV(bit)) 
#define cbi(sfr,bit) (_SFR_BYTE(sfr)&=~_BV(bit))
#include <avr/signal.h>
#include <stdlib.h>
#include <inttypes.h>
//=============================================
#define set_rclk_in() sbi(DDRB,PB0);//rclk为锁存脉冲输入
#define set_rclk_in1() sbi(PORTB,PB0);//rclk输入高
#define set_rclk_in0() cbi(PORTB,PB0);//rclk输入低

#define set_srclk_in() sbi(DDRB,PB1);//srclk为移位脉冲输入
#define set_srclk_in1() sbi(PORTB,PB1);//srclk输入高
#define set_srclk_in0() cbi(PORTB,PB1);//srclk输入低

#define set_ser_in() sbi(DDRB,PB2);//ser输入
#define set_ser_in1() sbi(PORTB,PB2);//ser输入高
#define set_ser_in0() cbi(PORTB,PB2);//ser输入低

void delay_us(uint16_t x)  //x=1对应3.03us

    while(x) 
    { 
        x--; 
    } 

void delay_ms(uint8_t xtal)
{
    uint8_t i;
    for(i=1;i<(uint8_t)(xtal*143-2);i++)
    {;}
}


//--------向前面板指示灯595写一个字节数据
void ser_out(uint8_t dat)
{


    set_rclk_in();//设置PE3为输出
    set_srclk_in();//设置PE2为输出
    set_ser_in();//设置PE4输出

    int i;
    for(i=0;i<8;i++)
    {
        if(dat&0x80)
        {
            set_ser_in0();//ser输入低
        }
        else
        {
            set_ser_in1();//ser输入高
        }
        set_srclk_in1();//srclk输入高
        set_srclk_in0();//srclk输入低
        dat<<=1;
    } 
    
        set_rclk_in1();//PE3输出高,rclk输入高,锁存内容到锁存器,指示灯显示
    set_rclk_in0();//PE2输出低,srclk输入低
}



//===============主程序===============
void main (void)
{
    uint8_t i,j,m,data;
    for(;;)
    {
        data=1;
        for(i=0;i<=7;i++)
        {
            for(j=0;j<=250;j++)
            {
                delay_ms(255);
            }
            ser_out(data);
            data=data<<1;
            
        }
        
        data=0x80;
        for(i=0;i<=7;i++)
        {
            for(j=0;j<=250;j++)
            {
                delay_ms(255);
            }
            ser_out(data);
            data=data>>1;
            
        }
    }
}
bear15888 发表于 2009-8-2 10:46 | 显示全部楼层
本帖最后由 bear15888 于 2009-8-2 10:49 编辑

程序借用了。
admin 发表于 2009-8-2 10:59 | 显示全部楼层
  1. //=============================================

  2. #include <avr/io.h>
  3. #include <avr/delay.h>
  4. #include <avr/signal.h>
  5. #include <avr/interrupt.h>
  6. #include <avr/pgmspace.h>
  7. #define sbi(sfr,bit) (_SFR_BYTE(sfr)|=_BV(bit))
  8. #define cbi(sfr,bit) (_SFR_BYTE(sfr)&=~_BV(bit))
  9. #include <avr/signal.h>
  10. #include <stdlib.h>
  11. #include <inttypes.h>
  12. //=============================================
  13. #define set_rclk_in() sbi(DDRB,PB0);//rclk为锁存脉冲输入
  14. #define set_rclk_in1() sbi(PORTB,PB0);//rclk输入高
  15. #define set_rclk_in0() cbi(PORTB,PB0);//rclk输入低

  16. #define set_srclk_in() sbi(DDRB,PB1);//srclk为移位脉冲输入
  17. #define set_srclk_in1() sbi(PORTB,PB1);//srclk输入高
  18. #define set_srclk_in0() cbi(PORTB,PB1);//srclk输入低

  19. #define set_ser_in() sbi(DDRB,PB2);//ser输入
  20. #define set_ser_in1() sbi(PORTB,PB2);//ser输入高
  21. #define set_ser_in0() cbi(PORTB,PB2);//ser输入低

  22. void delay_us(uint16_t x)  //x=1对应3.03us
  23. {
  24.     while(x)
  25.     {
  26.         x--;
  27.     }
  28. }
  29. void delay_ms(uint8_t xtal)
  30. {
  31.     uint8_t i;
  32.     for(i=1;i<(uint8_t)(xtal*143-2);i++)
  33.     {;}
  34. }


  35. //--------向前面板指示灯595写一个字节数据
  36. void ser_out(uint8_t dat)
  37. {


  38.     set_rclk_in();//设置PE3为输出
  39.     set_srclk_in();//设置PE2为输出
  40.     set_ser_in();//设置PE4输出

  41.     int i;
  42.     for(i=0;i<8;i++)
  43.     {
  44.         if(dat&0x80)
  45.         {
  46.             set_ser_in0();//ser输入低
  47.         }
  48.         else
  49.         {
  50.             set_ser_in1();//ser输入高
  51.         }
  52.         set_srclk_in1();//srclk输入高
  53.         set_srclk_in0();//srclk输入低
  54.         dat<<=1;
  55.     }
  56.    
  57.         set_rclk_in1();//PE3输出高,rclk输入高,锁存内容到锁存器,指示灯显示
  58.     set_rclk_in0();//PE2输出低,srclk输入低
  59. }



  60. //===============主程序===============
  61. void main (void)
  62. {
  63.     uint8_t i,j,m,data;
  64.     for(;;)
  65.     {
  66.         data=1;
  67.         for(i=0;i<=7;i++)
  68.         {
  69.             for(j=0;j<=250;j++)
  70.             {
  71.                 delay_ms(255);
  72.             }
  73.             ser_out(data);
  74.             data=data<<1;
  75.             
  76.         }
  77.         
  78.         data=0x80;
  79.         for(i=0;i<=7;i++)
  80.         {
  81.             for(j=0;j<=250;j++)
  82.             {
  83.                 delay_ms(255);
  84.             }
  85.             ser_out(data);
  86.             data=data>>1;
  87.             
  88.         }
  89.     }
  90. }
bear15888 发表于 2009-8-2 11:13 | 显示全部楼层
void main(void)
{
  unsigned char i;
  unsigned int DS;
  unsigned char Data=0111111;
   DDRB=0X0F;
   PORTB=0X0F;                              //将B口0,1,2脚做输出用

while(1)
{
   
  for(i=0;i<8;i++)
  {
    PORTB=(0<<PB2);             //先置为低
    DS=Data&0x80;               //取数据的最高位
    PORTB=(DS<<PB1);            //将某位的值赋给PB1
      Data<<= 1;                  //将数据的次高位移到最高位,为下一次取数据做准备
    PORTB=(1<<PB2);             //再置为高,产生移位时钟上升沿,上升沿时数据寄存器的数据移位
    delay(10);
  }
  PORTB=(0<<PB0);          //先置为低
  PORTB=(1<<PB0);         //再置为高,产生移位时钟上升沿,上升沿时移位寄存器的数据进入数据存储寄存器,更新显示数据。  
  }  
}

楼主,不知可否帮忙看看,哪有错误?在一位数码管上只循环点亮一次就不亮了,不知道是哪里的时序出了错!
bear15888 发表于 2009-8-2 19:43 | 显示全部楼层
哎,还是热心人少哦。上面的问题,自己已经解决!
gaohq 发表于 2009-8-2 19:48 | 显示全部楼层
没有while(1)吧,

我这时才看到。
我也是初学。
auzxj 发表于 2009-8-2 20:20 | 显示全部楼层
6# gaohq
for(;;)是什么?
bear15888 发表于 2009-8-3 09:06 | 显示全部楼层
7# auzxj

和while(1)的功能一样,换个面具活着而已
auzxj 发表于 2009-8-3 09:33 | 显示全部楼层
8# bear15888
呵呵,我那是在对 我楼上的gaohq进行启发式。。。。
bear15888 发表于 2009-8-5 09:30 | 显示全部楼层
9# auzxj

不好意思,小的误会了@!
naotaoya 发表于 2009-8-10 08:55 | 显示全部楼层
程序接过来瞄一下!:lol
欧阳青云 发表于 2009-8-10 23:15 | 显示全部楼层
您需要登录后才可以回帖 登录 | 注册

本版积分规则

3

主题

4

帖子

0

粉丝
快速回复 在线客服 返回列表 返回顶部