更多单片机学习笔记:
单片机学习笔记 1. 点亮一个LED灯
单片机学习笔记 2. LED灯闪烁
单片机学习笔记 3. LED灯流水灯
单片机学习笔记 4. 蜂鸣器滴~滴~滴~
单片机学习笔记 5. 数码管静态显示
目录
0、实现的功能
1、Keil工程
1-1 数码管动态显示
1-2 数组的定义与引用
2、代码实现
0、实现的功能
数码管的动态显示,能直接显示三位数字
1、Keil工程
1-1 数码管动态显示
动态显示就是在静态显示的基础上,循环的显示数字,显示完1后再显示2,但是显示的很快让人眼分辨不出来,以为是同时显示的。其实是一步一步显示的,动态扫描。
1-2 数组的定义与引用
通常放到最前面,定义一个数组本,用的时候直接调用
2、代码实现
在上一节最后出现的问题已经解决,是因为循环的时候P0的值变换的太慢,导致段选锁存器打开的时候P0仍为上一位选时的值,就导致乱码了。所以我们加上延时试试
#include <reg52.h>
#include <intrins.h>#define uchar unsigned char
#define uint unsigned intsbit WE = P2^7; //锁存器位选,U8的LE,选择哪个数码管
sbit DU = P2^6; //锁存器段选,U9的LE,控制亮什么数字//延时模块
void delay(uint z)
{uint x;uint y;for(x = z; x > 0; x--)for(y = 114; y > 0; y--);
}void main()
{while(1){//第一个数码管P0 = 0xff; //清除断码,让位锁存器哪个都不选WE = 1;//位选锁存打开P0 = 0xfe;//选第一个管WE = 0; //进入锁存DU = 1;//段选锁存打开P0 = 0x06;//亮1DU = 0;//进入锁存delay(5); //延时5ms//第二个数码管P0 = 0xff; //清除断码,让位锁存器哪个都不选WE = 1;//位选锁存打开P0 = 0xfd;//选第二个管WE = 0; //关上位选锁存器,进入锁存DU = 1;//段选锁存打开P0 = 0x5B;//亮2DU = 0;//进入锁存delay(5); //延时5ms}
}
效果还可以,已经不会出现其他数码管有亮灯的情况,且只亮12。
但为了更方便一些,最好还是写个函数,直接输入数字就能直接显示
1、直接定义一个函数display(uchar i),在main函数中直接display(xxx)就能显示
2、对于某个数i,要分解为单个的数----定义bai、shi、ge(只对显示三位数的)
3、段选的时候不能直接 P0 = bai,要转成对应的数码管段选值----要在最开始定义一个数组,存放共阴数码管的段选表
【注】不加code关键字,默认存放在data区(RAM);加上code关键字,就存放在ROM
所以把这个段选表直接放到ROM中,不会受到影响
代码实现:
#include <reg52.h>
#include <intrins.h>#define uchar unsigned char
#define uint unsigned intsbit WE = P2^7; //锁存器位选,U8的LE,选择哪个数码管
sbit DU = P2^6; //锁存器段选,U9的LE,控制亮什么数字//共阴极数码管段选表0-9
uchar code table[] = {0x3f, 0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7d, 0x07, 0x7f, 0x6f,} ;//延时模块
void delay(uint z)
{uint x;uint y;for(x = z; x > 0; x--)for(y = 114; y > 0; y--);
}void display(uint i)
{uchar bai, shi, ge;//对于只显示三位数的定义bai = i / 100;shi = i % 100 /10;ge = i % 10;//第一个数码管P0 = 0xff; //清除断码,让位锁存器哪个都不选WE = 1;//位选锁存打开P0 = 0xfe;//选第一个管WE = 0; //进入锁存DU = 1;//段选锁存打开P0 = table[bai]; //亮baiDU = 0;//进入锁存delay(5); //延时5ms//第二个数码管P0 = 0xff; //清除断码,让位锁存器哪个都不选WE = 1;//位选锁存打开P0 = 0xfd;//选第二个管WE = 0; //关上位选锁存器,进入锁存DU = 1;//段选锁存打开P0 = table[shi]; //亮shiDU = 0;//进入锁存delay(5); //延时5ms//第三个数码管P0 = 0xff; //清除断码,让位锁存器哪个都不选WE = 1;//位选锁存打开P0 = 0xfb;//选第三个管WE = 0; //关上位选锁存器,进入锁存DU = 1;//段选锁存打开P0 = table[ge]; //亮geDU = 0;//进入锁存delay(5); //延时5ms
}void main()
{while(1){display(927);}
}
实物展示: