#说明:采用的芯片是89C51,LED点阵屏的规格是16*16,同时使用了两个74HC595芯片,字模生成软件在文末有网盘连接。web
总体的电路链接如上图所示,单片机只须要使用三个IO接口,就能够实现对点阵屏的控制。固然对于不一样的单片机而言连线是不一样的,可是使用74HC595扩展的原理是相同的,在这里再也不对于其IO扩展原理进行探究。算法
在51单片机以及C语言的环境下,实现LED点阵屏幕上汉字的平滑滚动,就像是公交车上显示“前方到站第二医院,下车乘客请提早作好准备”同样。咱们最后显示的是“计算机测控技术”几个字,固然显示的汉字内容是自定义的。同时,设置一个按钮可以让平滑滚动的汉字能够随时停下来。
这里有两点细节须要注意一下:
一、汉字循环到最后一个时,要继续滚动出第一个汉字,而不是跳变到开头从新循环。
二、汉字滚动的时候按下按钮中止,滚动中止的时候按下按钮继续滚动,使用同一个按钮。数组
在这里咱们定义芯片P3.四、P3.五、P3.6 三个接口为输出IO接口,P2.7为接开关控制的IO接口。同时定义一个大数组储存全部汉字对应的取模16进制码,一个小数组用于表示如今屏幕上所需显示的汉字。数据结构
#include <reg51.h> #include <intrins.h> typedef unsigned int u16; //常规无符号字符串和整数定义 typedef unsigned char u8; //将595的三个内置接口赋给新的名字 sbit SRCLK = P3 ^ 6; // 数据输入口(串) sbit RCLK = P3 ^ 5; // 移位寄存器时钟 sbit SER = P3 ^ 4; // 存储寄存器时钟 sbit stopscreen = P2^7; //暂停与开始开关定义引脚 /*定义一个数组存储全部须要平滑滚动的文字的16进制码,由取模软件自动生成, 每一个字由32个16进制数字组合而成,如今数组中存储的是“计算机测控技术”*/ u8 code word[] = { /*-- 文字: 计 --*/ 0x00, 0x02, 0x04, 0x02, 0x08, 0x02, 0x08, 0x02, 0x00, 0x02, 0x00, 0x02, 0xEF, 0x7F, 0x08, 0x02, 0x08, 0x02, 0x08, 0x02, 0x08, 0x02, 0x08, 0x02, 0x28, 0x02, 0x18, 0x02, 0x08, 0x02, 0x00, 0x02, /*-- 文字: 算 --*/ 0x04, 0x02, 0x7C, 0x7E, 0x12, 0x09, 0x01, 0x00, 0xFC, 0x1F, 0x04, 0x10, 0xFC, 0x1F, 0x04, 0x10, 0xFC, 0x1F, 0x04, 0x10, 0xFC, 0x1F, 0x10, 0x04, 0xFF, 0x7F, 0x10, 0x04, 0x08, 0x04, 0x04, 0x04, /*-- 文字: 机 --*/ 0x08, 0x00, 0x88, 0x0F, 0x88, 0x08, 0x88, 0x08, 0xBF, 0x08, 0x88, 0x08, 0x8C, 0x08, 0x9C, 0x08, 0xAA, 0x08, 0xAA, 0x08, 0x89, 0x08, 0x88, 0x48, 0x88, 0x48, 0x48, 0x48, 0x48, 0x70, 0x28, 0x00, /*-- 文字: 测 --*/ 0x00, 0x20, 0xE4, 0x23, 0x28, 0x22, 0x28, 0x2A, 0xA1, 0x2A, 0xA2, 0x2A, 0xA2, 0x2A, 0xA8, 0x2A, 0xA8, 0x2A, 0xA4, 0x2A, 0xA7, 0x2A, 0x84, 0x20, 0x44, 0x21, 0x44, 0x22, 0x24, 0x28, 0x10, 0x10, /*-- 文字: 控 --*/ 0x08, 0x02, 0x08, 0x04, 0x08, 0x04, 0xC8, 0x7F, 0x5F, 0x40, 0x28, 0x29, 0x88, 0x10, 0x58, 0x20, 0x0C, 0x00, 0x8B, 0x3F, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0xEA, 0x7F, 0x04, 0x00, /*-- 文字: 技 --*/ 0x08, 0x04, 0x08, 0x04, 0x08, 0x04, 0xC8, 0x7F, 0x3F, 0x04, 0x08, 0x04, 0x08, 0x04, 0xA8, 0x3F, 0x18, 0x21, 0x0C, 0x11, 0x0B, 0x12, 0x08, 0x0A, 0x08, 0x04, 0x08, 0x0A, 0x8A, 0x11, 0x64, 0x60, /*-- 文字: 术 --*/ 0x80, 0x00, 0x80, 0x04, 0x80, 0x08, 0x80, 0x08, 0xFE, 0x3F, 0xC0, 0x01, 0xA0, 0x02, 0xA0, 0x02, 0x90, 0x04, 0x88, 0x08, 0x84, 0x10, 0x82, 0x20, 0x81, 0x40, 0x80, 0x00, 0x80, 0x00, 0x80, 0x00}; //下面一个用于存储每一时刻点阵屏显示内容的数字,随着时间会不断从新赋值与变化 u8 now[32] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 };
因为使用595进行了接口扩展,首先编写行显示函数LED_line,接着再编写汉字显示函数LED_array,>>和<<这两个符号是二进制移位符号。svg
void delay(u16 i) //延时函数,很普通 { while (i--); } //行显示函数: LED_line (字节1 1 ,字节2 2 ,行号) void LED_line(u8 ledata1, u8 ledata2, u8 line_num) { u8 b_num, i; u8 REG595[4]; // 发送到595的四个字节。 REG595[0] = ledata2; REG595[1] = ledata1; if (line_num<8) { REG595[2] = 0; REG595[3] = 0x01 << line_num; } else { REG595[2] = 0x01 << (line_num - 8); REG595[3] = 0; } SRCLK = 1; // 移位准备 RCLK = 1; //输出准备 for (b_num = 0; b_num<4; b_num++) { // 向595发送四个字节 for (i = 0; i<8; i++) { //发送8位数 SER = REG595[b_num] >> 7; //从最高位开始发送 REG595[b_num] <<= 1; SRCLK = 0; SRCLK = 1; //移位寄存器时序,低电平准备,高电平有效 } } RCLK = 0; // 存储寄存器时序,低电平准备,高电平有效,四个字节同时发出 RCLK = 1; } void LED_array(u8 word[], u16 t_delay) //汉字显示函数 { u8 i; while (t_delay--) { for (i = 0; i<16; i++) { // 逐行显示 LED_line(~word[i * 2], ~word[i * 2 + 1], i); } } }
经过上面的内容,咱们只要调用LED_array函数,正确传参后就能够在LED点阵屏上显示咱们想要显示的内容了。实现平滑滚动才是本文的关键,主函数的算法流程图以下所示:
总的来讲,就是使用小数组(now)在大数组(word)中一步步移动的方法,在算法与数据结构里,咱们每每把这种方法叫作滑动窗口法。在汉字取模软件中生成的16进制数,每两个一组表明LED点阵上的一行灯的亮灭。这也不难理解,由于一行是16个LED灯,一个两位16进制数恰好能够表示8个2进制数,因此两个两位16进制数控制一行。所以,咱们滑动窗口每次移动2个两位16进制数。函数
void main() //主函数 { u16 i, j; for(j=0;;j++){ //在这里不使用while循环是由于while循环显示输出不稳定 //每次赋给now的值都后移两位,显示出来就是点阵一行行地变化 for (i=0;i<32;i++){ //对now中32个位置,每一个位置都赋值 /*将须要实时显示的内容放到实时数组now中去,同时使用对数组最大数224取余实现循环平滑滚动*/ now[i] = word[(i+(2*j))%224]; } LED_array(now, 10); //调用汉字显示函数,依次显示now中内容 delay(300); //延迟后进行下一循环 if(stopscreen==0){ //按键防抖设计 delay(50); if(stopscreen==0){ while(1){ //按第一下开关中止平滑滚动 LED_array(now, 10); if(stopscreen==0){ //按键防抖设计 delay(50); if(stopscreen==0){ break; //按第二下开关继续平滑滚动 } } } } } } }
清楚了LED点阵屏显示的原理,咱们能够设计LED点阵屏的多种显示方式,甚至能够作出动画片、游戏等。
字模生成软件百度云:连接:https://pan.baidu.com/s/1OwK_L_aDjWas5LF_MuULmQ
提取码:idov动画