【51单片机】数码管快速上手

一、数码管分类与定义

分类‌:数码管分为静态数码管(单个,一位)和动态数码管(联排,如2位、4位、8位)。‌

定义‌:数码管是由多个发光二极管封装在一起形成"8"字形的器件,用于显示数字和符号。‌

二、数码管构造与原理

构造‌:数码管内部由八个发光二极管组成,分别对应a、b、c、d、e、f、g和dp段,用于显示不同的数字和图形。‌

原理‌:通过控制对应的发光二极管亮灭来显示数字和符号。共阳极和共阴极数码管分别通过给予低电平和高电平来点亮LED。‌

三、数码管显示方式

静态显示‌:每个数码管的段选接一个8位的数据线来保持显示的字形码,显示稳定但硬件电路复杂,成本较高。‌

动态显示‌:通过扫描方式控制各个数码管轮流显示,节省I/O口资源,适用于多位数码管显示。‌

四、数码管在51单片机中的应用

在51单片机系统中,数码管常用于显示数字、字符等信息,如温度、时间等。‌

通过编程控制数码管的段选和位选信号,实现动态或静态显示。‌

可以利用译码器等外设进一步减少需要操作的引脚数,提高显示控制的灵活性。‌

五、硬件设计

我们可以通过阴极控制显示的位置,通过阳极控制显示的内容。两个数码管共有8个阴极引脚和16和阳极引脚,如果所有引脚都直接接入MCU,会造成MCU引脚的极大浪费。为了节省MCU的引脚,我们可以将两个数码管的阳极接在一起。

74HC138

由于8位数码管同一时刻只需显示1位,因此数码管的阴极可使用74HC138芯片进一步节省MCU的引脚

74HC245

由于51单片高电平的驱动能力很微弱,不足以点亮数码管,因此可以使用74HC245N作为驱动芯片

有了74HC245之后,51单片引脚的输出就只用作信号,而驱动数码管的电流则由74HC245的电源提供

硬件原理图

静态实现

确定显示位置称为数码管的位选 ,确定显示内容称为数码管的段选

数码管的位选通过74HC138芯片控制,更具体的说,是通过单片机的P13、P14、P15引脚控制

数码的段选通过单片机的P00~P07这7个引脚控制,具体的对应关系如下。

cpp 复制代码
#include <STC89C5xRC.H>
typedef unsigned char u8;

// 数字0-9的编码
static u8 codes[10] = {
    0x3F, // 0
    0x06, // 1
    0x5B, // 2
    0x4F, // 3
    0x66, // 4
    0x6D, // 5
    0x7D, // 6
    0x07, // 7
    0x7F, // 8
    0x6F  // 9
};


void DigitalTube_DisplaySingle(u8 position, u8 num_code)
{
    // 位选:P15 P14 P13
    position <<= 3;  //先左移3位
    P1 &= 0xC7;  //11000111 先把13 14 15位置0
    P1 |= position;  //赋值

    // 段选:P0
    P0 = num_code;
}

void main()
{
    //第一个数码管显示数字1
    DigitalTube_DisplaySingle(0, codes[1]);
    while (1) {
    }
}

动态实现

cpp 复制代码
#include <STC89C5xRC.H>
#include <INTRINS.H>
typedef unsigned char u8;
typedef unsigned int u16;
typedef unsigned long u32;

// 数字0-9的编码
static u8 codes[10] = {
    0x3F, // 0
    0x06, // 1
    0x5B, // 2
    0x4F, // 3
    0x66, // 4
    0x6D, // 5
    0x7D, // 6
    0x07, // 7
    0x7F, // 8
    0x6F  // 9
};

//数码管要显示每一位的数字
u8 buffer[8];

void Delay1ms(u16 count)
{
    u8 i, j;

    while (count > 0) {
        count--;
        _nop_();
        i = 2;
        j = 199;
        do {
            while (--j);
        } while (--i);
    }
}

//显示一位
void DigitalTube_DisplaySingle(u8 position, u8 num_code)
{
    P0 = 0x00;
    // 位选:P15 P14 P13
    position <<= 3;
    P1 &= 0xC7;
    P1 |= position;

    // 段选:P0
    P0 = num_code;
}

//显示多位
void DigitalTube_DisplayNum(u32 num)
{
    //先将数组所有值设置零
    u8 i;
    for (i = 0; i < 8; i++) {
        buffer[i] = 0x00;
    }
    //如果显示数字为0直接赋值最后一位为0,函数停止
    if (num == 0) {
        buffer[7] = codes[0];
        return;
    }

    //提取数字每一位到数组对应位置上
    i = 7;
    while (num > 0) {
        buffer[i] = codes[num % 10];
        num /= 10;
        i--;
    }
}

//显示每个数字
void DigitalTube_Refresh()
{
    u8 i;
    for (i = 0; i < 8; i++) {
        DigitalTube_DisplaySingle(i, buffer[i]);
        Delay1ms(1);
    }
}

void main()
{
    //显示多位数字
    DigitalTube_DisplayNum(1234567);
    while (1) {
        //不断刷新
        DigitalTube_Refresh();
    }
}
相关推荐
iiiiii114 分钟前
【论文阅读笔记】Reparameterization Proximal Policy Optimization (RPO):将PPO的稳定性引入可微分强化学习
论文阅读·人工智能·笔记·深度学习·机器学习·机器人·具身智能
国科安芯42 分钟前
ASC0101S自动双向电平转换原理深剖
单片机·嵌入式硬件·fpga开发·云计算·信息与通信
李永奉1 小时前
中科蓝讯SDK开发-开启串口Debug打印调试教程
单片机·嵌入式硬件·mcu·物联网·电脑
LCG元1 小时前
STM32硬件SPI驱动OLED SSD1306显示屏全流程实战:从CubeMX配置到中英文显示
stm32·单片机·嵌入式硬件
鱼子星_1 小时前
【C++】深入剖析list:list及其双向迭代器实现
开发语言·数据结构·c++·笔记·stl·list
caishenzhibiao1 小时前
市场同步系统 同花顺期货通指标
java·c语言·c#
飞凌嵌入式1 小时前
性能翻倍·功耗减半!RK3572八核核心板,重构嵌入式计算新标杆
人工智能·嵌入式硬件·飞凌嵌入式
say_fall2 小时前
【Linux系统编程】文件操作基础:C标准库、系统调用、fd是什么和fd与FILE*的关系
android·linux·c语言
zcmodeltech2 小时前
智慧农业沙盘模型物联网控制系统设计:基于STM32与Modbus RTU的传感器-执行器闭环方案
服务器·分布式·stm32·嵌入式硬件·物联网·能源
砚凝霜2 小时前
软考网络工程师|第 4 章 WLAN MAC 机制、Ad Hoc、无线安全、WPAN 蓝牙 ZigBee 完整备考笔记
网络·笔记·安全