要求8个数码管分别单独依次显示0~9的值,然后所有数码管一起同时显示0 ~F的值,如此往复。
训练重点:1、弄清楚数码管的段码与显示数值之间的关系
2、共阳数码管的基本控制方法,特别是弄清楚com端与显示码的关系。
come端口控制数码管的位置。而come端口是通过一个锁存器的P0端口输入来控制的,但前提是138译码器的输出值要选中这个锁存器,才能使P0口输入的值给了输出。
同样的数码管的段码也是由一个锁存器控制的,而锁存器只要当38译码器输出值选中这个锁存器才能使P0端口的输入给输出。
先考虑如何使一个数码管显示,假设要让come1的数码管显示6
#include "reg52.h"
void Delay(unsigned int t)
{
while(t--);
while(t--);
}
void InitHC138(unsigned char channel)
{
switch(channel)
{
case 4: P2 = (P2 & 0x1f) | 0x80; break;
case 5: P2 = (P2 & 0x1f) | 0xa0; break;
case 6: P2 = (P2 & 0x1f) | 0xc0; break;
case 7: P2 = (P2 & 0x1f) | 0xe0; break;
}
}
void showSMG()
{
InitHC138(6); //数码管亮的位置
P0=0x01;
InitHC138(7); //数码管显示的内容
P0=0x82;
}
void
void main()
{
while (1)
{
showSMG();
}
}
接着考虑如何使8个数码管独立依次显示6;
#include "reg52.h"
unsigned char code SMG_duanma[16]= //code 是表格形式
{0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,
0x80,0x90,0x88,0x80,0xc6,0xc0,0x86,0x8e,
0xbf,0x7f};
void Delay(unsigned int t)
{
while(t--);
while(t--);
}
void InitHC138(unsigned char channel)
{
switch(channel)
{
case 4: P2 = (P2 & 0x1f) | 0x80; break;
case 5: P2 = (P2 & 0x1f) | 0xa0; break;
case 6: P2 = (P2 & 0x1f) | 0xc0; break;
case 7: P2 = (P2 & 0x1f) | 0xe0; break;
}
}
void showSMG_Bit(unsigned char dat, unsigned pos)
{
InitHC138(6); //数码管亮的位置
P0=0x01 << pos;
InitHC138(7); //数码管显示的内容
P0=dat;
}
void SUM_Static()
{
unsigned int i;
for(i=0;i<8;i++)
{
showSMG_Bit(SMG_duanma[6],i);
Delay(60000);
Delay(60000);
}
}
void
void main()
{
while (1)
{
SMG_Static();
}
}
然后是每个数码管单独依次显示0 ~ 9;
#include "reg52.h"
unsigned char code SMG_duanma[16]= //code 是表格形式
{0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,
0x80,0x90,0x88,0x80,0xc6,0xc0,0x86,0x8e,
0xbf,0x7f};
void Delay(unsigned int t)
{
while(t--);
while(t--);
}
void InitHC138(unsigned char channel)
{
switch(channel)
{
case 4: P2 = (P2 & 0x1f) | 0x80; break;
case 5: P2 = (P2 & 0x1f) | 0xa0; break;
case 6: P2 = (P2 & 0x1f) | 0xc0; break;
case 7: P2 = (P2 & 0x1f) | 0xe0; break;
}
}
void showSMG_Bit(unsigned char dat, unsigned pos)
{
InitHC138(6); //数码管亮的位置
P0=0x01 << pos;
InitHC138(7); //数码管显示的内容
P0=dat;
}
void SUM_Static()
{
unsigned int i,j;
for(i=0;i<8;i++)
{
for(j=0;j<10;j++)
showSMG_Bit(SMG_duanma[j],i);
Delay(60000);
Delay(60000);
}
}
void
void main()
{
while (1)
{
SMG_Static();
}
}
最后在8个数码管分别单独依次显示0~9的基础上,然后所有数码管一起同时显示0 ~F的值
#include "reg52.h"
unsigned char code SMG_duanma[16]= //code 是表格形式
{0xc0,0xf9,0xa4,0xb0,0x99,0x92,0x82,0xf8,
0x80,0x90,0x88,0x80,0xc6,0xc0,0x86,0x8e,
0xbf,0x7f};
void Delay(unsigned int t)
{
while(t--);
while(t--);
}
void InitHC138(unsigned char channel)
{
switch(channel)
{
case 4: P2 = (P2 & 0x1f) | 0x80; break;
case 5: P2 = (P2 & 0x1f) | 0xa0; break;
case 6: P2 = (P2 & 0x1f) | 0xc0; break;
case 7: P2 = (P2 & 0x1f) | 0xe0; break;
}
}
void showSMG_Bit(unsigned char dat, unsigned pos)
{
InitHC138(6); //数码管亮的位置
P0=0x01 << pos;
InitHC138(7); //数码管显示的内容
P0=dat;
}
void SUM_Static()
{
unsigned int i,j;
for(i=0;i<8;i++)
{
for(j=0;j<10;j++)
showSMG_Bit(SMG_duanma[j],i);
Delay(60000);
Delay(60000);
}
for(j=0;j<16;j++)
{
InitHC138(6); //数码管亮的位置
P0=0xff; //8个数码管一起亮
InitHC138(7); //数码管显示的内容
P0= SMG_duanma[j];
Delay(60000);
}
}
void
void main()
{
while (1)
{
SMG_Static();
}
}
在这一节中新学习的知识还有code关键字
有这样一种数据,我们在程序中要使用,但是却不会改变它的值,定义这种数据时可以加一个code关键字修饰一下,这样可以大大节省单片机的RAM的使用量。
那么现在要使用的数码管真值表,我们只用它们的值,不需要改变他们,就可以用code把他们都放入Flash中。
keilc51 中的关键字 代表了RAM不同区域的划分
data:片内RAM 从 0x00 ~ 0x7F
idata:片内RAM从 0x00 ~ 0xFF
pdata:片外RAM从0x00 ~ 0xFF
xdata:片外RAM从0x0000 ~ 0xFFFF
来源:CSDN
作者:......Oops
链接:https://blog.csdn.net/qq_44892126/article/details/103126503