打印
[Cortex-M0技术交流]

[2012助学第一期]hzy41y学习笔记之二(用HC595和LS164驱动7位LED)

[复制链接]
2140|9
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
hzy41y|  楼主 | 2012-6-8 14:56 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
沙发
hzy41y|  楼主 | 2012-6-8 14:58 | 只看该作者
本帖最后由 hzy41y 于 2012-6-8 15:22 编辑

备用

使用特权

评论回复
板凳
ningling_21| | 2012-6-9 22:12 | 只看该作者
不错,继续...

使用特权

评论回复
地板
hotpower| | 2012-6-10 16:03 | 只看该作者
继续努力,最好加压缩包

使用特权

评论回复
5
hzy41y|  楼主 | 2012-6-13 14:38 | 只看该作者

程序终于完成了

使用特权

评论回复
6
hzy41y|  楼主 | 2012-6-13 14:41 | 只看该作者
display[8]  为 LED显示缓存

//基于NUC120学习套件用HC595和LS164驱动7位数码管
//作者:hzy41y
//最后更新日期2012年06月13日11:06
#include <stdio.h>
#include <string.h>
#include "NUC1xx.h"
#include "Driver\DrvSYS.h"
#include "Driver\DrvGPIO.h"
#include "DrvTimer.h"
#include "hzy.h"
#define SCL595_set DrvGPIO_SetBit(E_GPC,14)
#define SCL164_set DrvGPIO_SetBit(E_GPC,15)
#define SDA_set DrvGPIO_SetBit(E_GPC,6)
#define SCL595_clr DrvGPIO_ClrBit(E_GPC,14)
#define SCL164_clr DrvGPIO_ClrBit(E_GPC,15)
#define SDA_clr DrvGPIO_ClrBit(E_GPC,6)

uint16_t timer; //全局时间延时变量

uint8_t tabl[] = {0xfa,0x60,0xdc,0xec,0x66,0xae,0xbe,0xe0,0xfe,0xee,0x08,0x10,0x04};
/* 0 1 2 3 4 5 6 7 8 9
display[0]对应LED左边第一位,display[6]对应LED最后第七位;
display[7]为闪烁使能,最高位对应LED左边第一位,那位为0则闪烁 */
uint8_t display[8]; //LED显示缓存

//***定时器回调函数*************//
void Timer0_Callback(void) // Timer0 interrupt subroutine
{ static uint16_t S_counter; //各位闪烁计数器
static uint8_t S_Enable; //各位闪烁使能
static uint8_t ch; //1-7显示通道变量
static hzy_b bit;
uint8_t j;
uint8_t display1;

if(bit.bg)
bit.bn=S_Enable>>7;
else bit.bn=1; //判Led相对位要闪烁
S_Enable<<=1; //判Led相对位不闪烁
display1=display[ch];
for(j=8;j>0;j--)
{ if(bit.bn)
{ if(display1>>7)SDA_set;
else SDA_clr;
display1<<=1;
}else SDA_clr; //判Led相对位要闪烁595各段输出为低电平

SCL595_set;
SCL595_clr; // 595--11pin
}
if(ch==0)SDA_clr;
else SDA_set; // 595--14pin和164--1pin/2pin
SCL164_set;
SCL164_clr; // 595--12pin/13pin 和164--8pin
ch++; //显示通道加1
if(ch==8)
{ SCL164_set;SCL164_clr;ch=0;
S_Enable=display[7];
}
S_counter++;
if(S_counter==500)
{ bit.bg=!bit.bg;
S_counter=0;
}
timer++; //全局时间延时变量
TIMER0->TISR.TIF =1;
}


//---------TIMER0初始化-----------------------------//
void InitTIMER0(void)
{
//第1步。启用和选择时钟源 /
SYSCLK->CLKSEL1.TMR0_S = 0; // Timer0的时钟源选择12MHZ
SYSCLK->APBCLK.TMR0_EN =1; //使能定时器时钟源

//第2步。选择操作模式//
TIMER0->TCSR.MODE=1; //选择定期模式,运作模

/*第3步。选择了时间周期=(周期定时器时钟输入)*(8位预分频+1)*(24位TCMP)
Step 3. Select Time out period = (Period of timer clock input) * (8-bit Prescale + 1) * (24-bit TCMP)*/
TIMER0->TCSR.PRESCALE=255; // Set Prescale [0~255]
TIMER0->TCMPR = 100; // Set TCMPR [0~16777215]
// (1/12000000)*(255+1)*(2765)=

/* Step 4. Enable interrupt */
TIMER0->TCSR.IE = 1;
TIMER0->TISR.TIF = 1; //Write 1 to clear for safty
NVIC_EnableIRQ(TMR0_IRQn); //Enable Timer0 Interrupt

/* Step 5. Enable Timer module */

DrvTIMER_SetTimerEvent(E_TMR0,1,(TIMER_CALLBACK) Timer0_Callback,0);
TIMER0->TCSR.CRST = 1; //Reset up counter
TIMER0->TCSR.CEN = 1; //Enable Timer0

// TIMER0->TCSR.TDR_EN=1; // Enable TDR function
}


//***************IO和显示初始化*****************************//
void init()
{ uint8_t i;

DrvGPIO_Open( E_GPA, 2, E_IO_OUTPUT );
DrvGPIO_Open( E_GPC, 6, E_IO_QUASI ); //标准数字双向口
DrvGPIO_Open( E_GPC, 14, E_IO_QUASI );
DrvGPIO_Open( E_GPC, 15, E_IO_QUASI );

for(i=0;i<7;i++)
{ display[i]=tabl[8];}
display[7]=0x00; //设置闪烁位
InitTIMER0();
timer=0;
while (timer<5000);
for(i=0;i<7;i++)
{ display[i]=tabl[i];}
display[7]=0xFF; //设置闪烁位
timer=0;
while (timer<5000);
}

/*----------------------------------------------------------------------------
MAIN function
----------------------------------------------------------------------------*/
int32_t main (void)
{
UNLOCKREG();
SYSCLK->PWRCON.XTL12M_EN = 1;
LOCKREG();
init();
while(1);

}



display[0]对应LED左边第一位,display[6]对应LED最后第七位;
display[7]为闪烁使能,最高位对应LED左边第一位,那位为0则闪烁

使用特权

评论回复
7
hzy41y|  楼主 | 2012-6-13 14:42 | 只看该作者
UNC_7LED.rar (208.02 KB)

使用特权

评论回复
8
john_lee| | 2012-6-13 17:51 | 只看该作者
楼主可以继续改进,使用SPI接口来驱动595。

使用特权

评论回复
9
mcs8098| | 2012-6-26 22:38 | 只看该作者
不错

使用特权

评论回复
10
hzy41y|  楼主 | 2012-7-3 11:13 | 只看该作者
自顶一吓

使用特权

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

本版积分规则

7

主题

75

帖子

2

粉丝