找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 4924|回复: 6
打印 上一主题 下一主题
收起左侧

STC89C52单片机控制74HC595,74HC138双色16x16点阵屏循环显示汉字

  [复制链接]
跳转到指定楼层
楼主
对应德飞莱的16x16 LED点阵, 这个点阵有两种型号, 一种是单色, 一种是双色, 双色多一个IO口
背面元件图, 这个是单色的, 有几个焊盘是空的, 另外8x8LED的引脚也有部分是空的. 双色的焊盘和LED点阵引脚都是满焊的


用89C51去驱动, 主要是通过74HC595和74HC138这两个逻辑芯片
* 74HC138负责行扫描, 每次时钟中断会扫描其中一行, 这行的位置是由ABCD这4个脚控制的, 对应了两片74HC138, 每片控制8个行, 通过P0.0-P0.1, 可以让指定的行显示
* 74HC595负责准备当前行上的数据, 这个数据有16bit所以是两个字节, 对应每个汉字, 有16x16个点, 就是16个2字节, 每次时钟中断就将这2个字节的内容送到74HC595上去, 同样是两片74HC595, 每片负责8个bit, 走的是SPI类型的串行输入-锁存-并行输出的方式

接线方式
  1.         R1        => P2.4 红色数据信号
  2.         D         => P0.3
  3.         C         => P0.2
  4.         B         => P0.1
  5.         A         => P0.0 A-D用于控制16行,通过2路 HC138 控制
  6.         LATCH     => P2.6 锁存
  7.         SCK       => P2.5 时钟
  8.         G1        => P0.4 绿色数据信号, 如果使用单红色屏此信号无需连接
  9.         OE        => P2.1 可以用IO引脚PWM控制亮度, 或者使用此引脚控制拖尾现象
  10.         +5V       => 5V
  11.         GND       => GND
复制代码


上位机代码(STC89C52RC), 只要是12T的STC单片机都可以

  1. #include<reg52.h>

  2. sbit G1    = P0^4;       //数据引脚,屏上标识G1
  3. sbit OE    = P2^1;       //使能引脚,屏上标识EN/OE
  4. sbit R1    = P2^4;       //数据引脚,屏上标识R1
  5. sbit T_CLK = P2^5;       //时钟引脚,屏上标识CLK
  6. sbit T_STR = P2^6;       //锁存引脚,屏上标识LATCH

  7. unsigned char pos=0;

  8. unsigned char tab[8];
  9. unsigned char DIS[]={0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15};//行数据

  10. /*-----------------------------------------------
  11.              16x16汉字取模数据
  12. ------------------------------------------------*/
  13. unsigned char code hztest[][32]=    //二维数组, 每个汉字32个字节
  14. {
  15. /*--  文字:  电  --*/
  16. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  17. 0x00,0x01,0x00,0x01,0x00,0x01,0xF8,0x3F,0x08,0x21,0x08,0x21,0x08,0x21,0xF8,0x3F,
  18. 0x08,0x21,0x08,0x21,0x08,0x21,0xF8,0x3F,0x0A,0x21,0x02,0x01,0x02,0x01,0xFE,0x00,

  19. /*--  文字:  子  --*/
  20. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  21. 0x00,0x00,0xF8,0x7F,0x10,0x00,0x20,0x00,0x40,0x00,0x80,0x01,0x00,0x01,0xFE,0xFF,
  22. 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x05,0x00,0x02,

  23. /*--  文字:  工  --*/
  24. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  25. 0x00,0x00,0x00,0x00,0xFC,0x7F,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,
  26. 0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x01,0xFE,0xFF,0x00,0x00,0x00,0x00,

  27. /*--  文字:  程  --*/
  28. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  29. 0x00,0x08,0xFC,0x1D,0x04,0xF1,0x04,0x11,0x04,0x11,0xFC,0xFD,0x00,0x10,0x00,0x30,
  30. 0xFE,0x39,0x20,0x54,0x20,0x54,0xFC,0x91,0x20,0x10,0x20,0x10,0xFE,0x13,0x00,0x10,

  31. /*--  文字:  信  --*/
  32. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  33. 0x40,0x08,0x20,0x08,0xFE,0x0B,0x00,0x10,0x00,0x10,0xFC,0x31,0x00,0x30,0x00,0x50,
  34. 0xFC,0x91,0x00,0x10,0x00,0x10,0xFC,0x11,0x04,0x11,0x04,0x11,0xFC,0x11,0x04,0x11,

  35. /*--  文字:  息  --*/
  36. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  37. 0x00,0x01,0x00,0x02,0xF0,0x1F,0x10,0x10,0xF0,0x1F,0x10,0x10,0xF0,0x1F,0x10,0x10,
  38. 0xF0,0x1F,0x10,0x10,0x00,0x01,0x84,0x08,0x92,0x48,0x12,0x48,0xF0,0x87,0x00,0x00,

  39. /*--  文字:  科  --*/
  40. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  41. 0x10,0x08,0x10,0x1D,0x90,0xF0,0x90,0x10,0x10,0x10,0x10,0xFD,0x90,0x10,0x90,0x38,
  42. 0x10,0x34,0x1E,0x50,0xF0,0x53,0x10,0x90,0x10,0x10,0x10,0x10,0x10,0x10,0x10,0x10,

  43. /*--  文字:  学  --*/
  44. /*--  宋体12;  此字体下对应的点阵为:宽x高=16x16   --*/
  45. 0x08,0x22,0x08,0x11,0x10,0x11,0x20,0x00,0xFE,0x7F,0x02,0x40,0x04,0x80,0xE0,0x1F,
  46. 0x40,0x00,0x80,0x01,0xFE,0xFF,0x00,0x01,0x00,0x01,0x00,0x01,0x00,0x05,0x00,0x02,


  47. };

  48. /*-----------------------------------------------
  49.              向595写入一个字节, 红色
  50. ------------------------------------------------*/
  51. void InputByte(unsigned  char dat)
  52. {
  53.   unsigned char i;
  54.   for(i = 8; i > 0; i--)
  55.   {
  56.     R1 = !(dat & 0x01);
  57.     T_CLK = 0;
  58.     T_CLK = 1;
  59.     dat = dat >> 1;
  60.   }
  61. }

  62. /*-----------------------------------------------
  63.              向595写入一个字节, 绿色
  64. ------------------------------------------------*/
  65. void InputByteG(unsigned  char dat)
  66. {
  67.   unsigned  char i;
  68.   for(i = 8; i > 0; i--)
  69.   {
  70.     G1 = !(dat & 0x01);
  71.     T_CLK = 0;
  72.     T_CLK = 1;
  73.     dat = dat >> 1;
  74.   }
  75. }

  76. /*-----------------------------------------------
  77.              向595写入两个字节 双色
  78. ------------------------------------------------*/
  79. void Input2Byte(unsigned  char DataR1, unsigned  char DataG1) //写一个字节
  80. {
  81.   unsigned  char i;
  82.   for(i=8; i>0; i--)
  83.   {
  84.     R1 = !(DataR1&0x01);
  85.     G1 = !(DataG1&0x01);
  86.     T_CLK = 0;
  87.     T_CLK = 1;
  88.     DataR1 = DataR1 >> 1;
  89.     DataG1 = DataG1 >> 1;
  90.   }
  91. }

  92. /*-----------------------------------------------
  93.             初始化定时器,做为动态扫描
  94. ------------------------------------------------*/
  95. void Init_Timer1(void)
  96. {
  97.   TMOD |= 0x10;                             
  98.   EA=1;                      //总中断使能
  99.   ET1=1;                     //定时中断使能
  100.   TR1=1;                     //打开定时器开关
  101. }

  102. /*-----------------------------------------------
  103.                       主程序
  104. ------------------------------------------------*/
  105. main()
  106. {
  107.   unsigned int i;
  108.   unsigned char a;
  109.   Init_Timer1(); //初始化定时器

  110.   while(1)
  111.   {
  112.     for(i = 0; i < 1000; i++); // 延时
  113.     a++;
  114.     if(a == 8) a = 0; // 汉字循环
  115.     pos = a;
  116.   }
  117. }

  118. /*-----------------------------------------------
  119.              定时器执行动态扫描
  120. ------------------------------------------------*/
  121. void Timer1_isr(void) interrupt 3
  122. {
  123.   static unsigned char count, j;
  124.   unsigned char i;
  125.   TH1=0xff;                // 重装初值
  126.   TL1=0;

  127.   T_STR=0;    // 锁存释放
  128.   for(j = 0; j < 1; j++) //取当前汉字在i位置的2个字节,数据传输完成后锁存输出
  129.         {
  130.     InputByte(hztest[j+pos][i]);
  131.     InputByte(hztest[j+pos][i+1]);
  132.         }
  133.   OE = 1;    // 关闭屏幕, 如果没有使用该引脚控制则会出现拖影现象
  134.   T_STR=1;   // 锁存有效, 此时一行的数据显示到屏上

  135.   P0 = DIS[count] | 0xF0; //低4位对应P0.0-P0.3, 通过HC138 4-16译码器, 循环扫描其他15行
  136.   OE = 0;    // 打开屏幕
  137.   count++;

  138.   i += 2;    // 当前汉字下一位置
  139.   if(count == 16) count = 0;
  140.   if(i == 32) i = 0;
  141. }
复制代码



评分

参与人数 1黑币 +50 收起 理由
admin + 50 共享资料的黑币奖励!

查看全部评分

分享到:  QQ好友和群QQ好友和群 QQ空间QQ空间 腾讯微博腾讯微博 腾讯朋友腾讯朋友
收藏收藏8 分享淘帖 顶1 踩
回复

使用道具 举报

沙发
ID:605498 发表于 2021-12-25 10:00 | 只看该作者
程序注释,讲解比较细致,编程逻辑性好。学习了有提高。谢了。
回复

使用道具 举报

板凳
ID:1002257 发表于 2022-1-26 22:59 | 只看该作者
这个先留个脚印方便再找
回复

使用道具 举报

地板
ID:297903 发表于 2022-1-27 20:50 | 只看该作者
i学习下,准备自己有时间也整一套试试!!
回复

使用道具 举报

5#
ID:1068268 发表于 2023-4-4 22:19 | 只看该作者
楼主写的非常好,对我很有启发
回复

使用道具 举报

6#
ID:863362 发表于 2023-4-6 08:56 | 只看该作者
我看着照片上显示的字是错误的吧?
回复

使用道具 举报

7#
ID:983193 发表于 2023-6-26 12:22 | 只看该作者
学习到了,感谢大佬的程序
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表