欢迎您访问365答案网,请分享给你的朋友!
生活常识 学习资料

51单片机入入入入入入门小练习之——动态数码管

时间:2023-06-04

       数码管本质上就是八个led,在程序中通过”段选“来控制led的显示组合,从而显示数字或符号。

       动态数码管利用人眼的视觉暂留原理,通过不停的“段选、位选”,循环显示几个不同数字,使几个数字可供人眼同时观察。

本次实验内容:

1.第 5 位显示一个 8;

2.按下 K1 显示 1,按下 K2 显示 2,按下 K3 显示 3,按下 K4 显示 4;

3.按下 K1 显示的数加 1,按下 K2 显示的数减 1,初始数值为 0;

4.数码管依次显示“198605”(无线电小组成立时间);

5.更多有趣设计!!!

参考代码:

(参考代码格式相对标准易读,适合大家学习、理解。但并非最简单的代码)

1.第 5 位显示一个 8;

#include "reg52.h" //此文件中定义了单片机的一些特殊功能寄存器sbit LSA=P2^2;sbit LSB=P2^3;sbit LSC=P2^4;void main(){LSA=1;LSB=0;LSC=1; //位选第5位(第五位是从右往左数第六个数码管)P0=0x7f;//段选显示8}

2.按下 K1 显示 1,按下 K2 显示 2,按下 K3 显示 3,按下 K4 显示 4;

#include "reg52.h" //此文件中定义了单片机的一些特殊功能寄存器typedef unsigned int u16; //对数据类型进行声明定义typedef unsigned char u8;sbit LSA=P2^2;sbit LSB=P2^3;sbit LSC=P2^4;sbit k1=P3^1; //定义P31口是k1sbit k2=P3^0; //定义P30口是k2sbit k3=P3^2; //定义P31口是k1sbit k4=P3^3; //定义P30口是k2u8 code smgduan[4]={0x06,0x5b,0x4f,0x66};//显示1~4的值int i;void delay(u16 i){while(i--);}void key(){if(k1==0) //检测按键K1是否按下{delay(1000); //消除抖动 一般大约10msif(k1==0) //再次判断按键是否按下{P0=smgduan[0]; //发送段码}while(!k1); //检测按键是否松开}if(k2==0) //检测按键K2是否按下{delay(1000); //消除抖动 一般大约10msif(k2==0) //再次判断按键是否按下{P0=smgduan[1]; //发送段码}while(!k2); //检测按键是否松开}if(k3==0) //检测按键K2是否按下{delay(1000); //消除抖动 一般大约10msif(k3==0) //再次判断按键是否按下{P0=smgduan[2]; //发送段码}while(!k2); //检测按键是否松开}if(k4==0) //检测按键K2是否按下{delay(1000); //消除抖动 一般大约10msif(k4==0) //再次判断按键是否按下{P0=smgduan[3]; //发送段码}while(!k2); //检测按键是否松开}}void main(){LSA=0;LSB=0;LSC=0; //位选初始化P0=0x00;//段选初始化while(1){key(); //按键处理函数}}

3.按下 K1 显示的数加 1,按下 K2 显示的数减 1,初始数值为 0;

示例1:一位数字、可显示负数

      负数的显示,需要对数字正负进行判断,若为负数,将负号显示在数字前,再将负数取正,按照正数显示方法显示数字的值。

      (如果不对数字进行处理,那单个数码管仅能显示一位数字,所显示数字无法超过9)

#include "reg52.h" //此文件中定义了单片机的一些特殊功能寄存器typedef unsigned int u16; //对数据类型进行声明定义typedef unsigned char u8;sbit LSA=P2^2;sbit LSB=P2^3;sbit LSC=P2^4;sbit k1=P3^1; //定义P31口是k1sbit k2=P3^0; //定义P30口是k2u8 code smgduan[10]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};//显示0~9的值char i;void delay(u16 i){while(i--);}void DigDisplay(){if(i>=0){LSA=0;LSB=0;LSC=0;P0=smgduan[i]; //发送段码delay(100); //间隔一段时间扫描P0=0x00; //消隐}if(i<0){LSA=1;LSB=0;LSC=0;P0=0x40; //发送负号的十六进制段码到P0delay(100); //间隔一段时间扫描P0=0x00; //消隐LSA=0;LSB=0;LSC=0;P0=smgduan[-i];//发送段码(“-i”将i变为正数)delay(100); //间隔一段时间扫描P0=0x00; //消隐}}void key(){if(k1==0) //检测按键K1是否按下{delay(1000); //消除抖动 一般大约10msif(k1==0) //再次判断按键是否按下{i++;}while(!k1); //检测按键是否松开}if(k2==0) //检测按键K2是否按下{delay(1000); //消除抖动 一般大约10msif(k2==0) //再次判断按键是否按下{i--;}while(!k2); //检测按键是否松开}}void main(){LSA=0;LSB=0;LSC=0; //位选初始化P0=0x00;//段选初始化 while(1){DigDisplay(); //数码管显示函数key(); //按键处理函数}}

示例2:多位数字、可显示负数。

      要想显示多位数字,需要对数字进行分位处理(即将数字每一位分开显示)。本示例所用的方法是对数字进行末位取余,再利用for循环进行动态显示。for循环在数字除尽(等于零0)时结束(整型变量的除法中,除数如果大于被除数,商为0)。

(由于变量定义为int数字值不能超出int型整数的取值范围,若想显示更大数,将变量改为双精度型即可)

【说的可能很难理解,但我是故意的( ̄︶ ̄)。大家仔细读代码就能懂了。】

【随手写的代码,期待大家有更好的方法】

#include "reg52.h" //此文件中定义了单片机的一些特殊功能寄存器typedef unsigned int u16; //对数据类型进行声明定义typedef unsigned char u8;sbit LSA=P2^2;sbit LSB=P2^3;sbit LSC=P2^4;sbit k1=P3^1; //定义P31口是k1sbit k2=P3^0; //定义P30口是k2u8 code smgduan[10]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};//显示0~9的值u8 LS_A[8]={0,1,0,1,0,1,0,1};u8 LS_B[8]={0,0,1,1,0,0,1,1};u8 LS_C[8]={0,0,0,0,1,1,1,1};int i;void delay(u16 i){while(i--);}void DigDisplay(){u8 k=0;u16 q=0;if(i>=0){k=0;for(q=i;q!=0;){LSA=LS_A[k];LSB=LS_B[k];LSC=LS_C[k];P0=smgduan[(q%10)]; //发送段码delay(100); //间隔一段时间扫描P0=0x00; //消隐q=q/10;k=k+1;}}if(i<0){for(q=-i;q!=0;){LSA=LS_A[k];LSB=LS_B[k];LSC=LS_C[k];P0=smgduan[q%10]; //发送段码delay(100); //间隔一段时间扫描P0=0x00; //消隐q=q/10;k++;}LSA=LS_A[k];LSB=LS_B[k];LSC=LS_C[k];P0=0x40; //发送负号的十六进制段码到P0delay(100); //间隔一段时间扫描P0=0x00; //消隐}}void key(){if(k1==0) //检测按键K1是否按下{delay(1000); //消除抖动 一般大约10msif(k1==0) //再次判断按键是否按下{i++;}while(!k1); //检测按键是否松开}if(k2==0) //检测按键K2是否按下{delay(1000); //消除抖动 一般大约10msif(k2==0) //再次判断按键是否按下{i--;}while(!k2); //检测按键是否松开}}void main(){LSA=0;LSB=0;LSC=0; //位选初始化P0=0x00;//段选初始化 while(1){DigDisplay(); //数码管显示函数key(); //按键处理函数}}

4.数码管依次显示“198605”(无线电小组成立时间);

#include "reg52.h" //此文件中定义了单片机的一些特殊功能寄存器typedef unsigned int u16; //对数据类型进行声明定义typedef unsigned char u8;sbit LSA=P2^2;sbit LSB=P2^3;sbit LSC=P2^4;u8 code smgduan[17]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f,0x77,0x7c,0x39,0x5e,0x79,0x71};//显示0~F的值void delay(u16 i){while(i--);}void DigDisplay(){LSA=0;LSB=0;LSC=0;//显示第0位 P0=smgduan[5];//发送段码delay(100); //间隔一段时间扫描P0=0x00;//消隐LSA=1;LSB=0;LSC=0;//显示第1位P0=smgduan[0];delay(100); P0=0x00;LSA=0;LSB=1;LSC=0;//显示第2位P0=smgduan[6];delay(100); P0=0x00;LSA=1;LSB=1;LSC=0;//显示第3位P0=smgduan[8];delay(100);P0=0x00;LSA=0;LSB=0;LSC=1;//显示第4位P0=smgduan[9];delay(100); P0=0x00;LSA=1;LSB=0;LSC=1;//显示第5位P0=smgduan[1];delay(100); P0=0x00;}void main(){while(1){DigDisplay(); //数码管显示函数}}

无线电小组———TZ

Copyright © 2016-2020 www.365daan.com All Rights Reserved. 365答案网 版权所有 备案号:

部分内容来自互联网,版权归原作者所有,如有冒犯请联系我们,我们将在三个工作时内妥善处理。