设计要求:#
写出矩阵键盘的驱动
分别按下对应的键。数码管会将键盘对应的值累加并显示
设计概述:#
按照设计要求,所需要的单片机芯片为STC89C52,所用的硬件工具是由华清远见开发的基于STC89C52的智能小车。该小车配备所需要的矩阵按键模块和数码管模块,矩阵按键模块由P3口控制,数码管模块位选P2.7口控制,段选由P2.6口控制,数字显示由P0口控制。STC89C52是一种低功耗,高性能的8位微控制器,是加强版的80C51单片机。
矩阵键盘:4x4矩阵键盘共有16个按键,每个按键的左端都连接在一根线上形成行线,每个按键的右端也都连接在一根线上形成列线。P3口的低4位分别于行线连接,高4位分别与列线连接。通过扫描矩阵键盘中按键两端的电平变化来准确识别其中的按键。
源代码:#
#include #define uint unsigned int #define uchar unsigned char sbit WELA = P2^7; //定义位选IO口 sbit DULA = P2^6;//定义段选IO口 void matrix_key_scan(); void delay_ms(uint ms); void sum_key(); void display_num(unsigned int num); void display_digit(unsigned char wela,unsigned char dula); uint key_value = 0; //定义全局变量保存键值 uint keynum1 = 0; uint keynum2 = 0; //数码管0-9段选编码 uchar code Du[] = {0x3f,0x06,0x5b,0x4f, 0x66,0x6d,0x7d,0x07, 0x7f,0x6f}; /*-----矩阵键盘扫描函数-----*/ void matrix_key_scan() { uchar temp; uchar a = 0; P3 = 0x0f;//将所有行电平拉高,列电平拉低,进行行扫描 temp = P3; if(temp != 0x0f)//检测是否有键按下 { delay_ms(5);//延时去抖 if(temp != 0x0f)//再次确认按键按下 { P3 = 0x0f;//将所有行电平拉高,列电平拉低,进行行扫描 temp = P3; switch(temp) { case 0x0e:key_value = 0; //第1行 break; case 0x0d:key_value = 4; //第2行 break; case 0x0b:key_value = 8; //第3行 break; case 0x07:key_value = 12; //第4行 break; } P3 = 0xf0;//将所有列电平拉高,行电平拉低,进行列扫描 temp = P3; switch(temp) { case 0xe0:key_value = key_value + 0;//第1列 break; case 0xd0:key_value = key_value + 1;//第2列 break; case 0xb0:key_value = key_value + 2;//第3列 break; case 0x70:key_value = key_value + 3;//第4列 break; //这里需要延时200ms,因为矩阵键盘扫描函数在while循环中是不断执行 //如果按下键后不松开或者松开键慢了,keynum2变量就会不断累加, delay_ms(200); keynum1 = key_value;![image](https://img2020.cnblogs.com/blog/2427665/202109/2427665-20210902095257265-732916178.jpg) keynum2 = keynum2 + keynum1; } } while((a < 50)&&(temp != 0xf0))//等待按键释放 { a++; } } /*-----毫秒级延时函数-----*/ void delay_ms(uint ms) { volatile uint i,j; for(i = ms;i > 0;i--) { for(j=0;j<110;j++); } } /*--------数码管显示数字函数---------*/ void display_num(unsigned int num) { unsigned int div = 0; unsigned char rema = 0; unsigned char index = 0; while((div = num / 10) > 0) { rema = num % 10; display_digit(index,rema); num = div; index++; delay_ms(2); } rema = num % 10; display_digit(index,rema); } /*-------数码管位选函数-------*/ void display_digit(unsigned char wela,unsigned char dula) { WELA = 1;// 位选端锁存器置高,送数据 P0 = 0xFF;//消影 P0 &= ~(1 << (7 - wela));//1000 0000 0111 1111 WELA = 0;// 位选端锁存器置低,保存数据 DULA = 1;// 段选端锁存器置高,送数据 P0 = Du[dula];//送数据 DULA = 0;// 段选端锁存器置低,保存数据 } void main() { while(1) { matrix_key_scan(); display_num(keynum2); } }小车部分原理图:#
上一篇:软件模拟实现iic协议(51为例)
下一篇:基于STC51单片机的风扇
推荐阅读最新更新时间:2024-11-12 16:32
设计资源 培训 开发板 精华推荐
- LTC3803MPS6-5、4:1 输入范围 3.3V 输出隔离反激式 DC/DC 转换器的典型应用电路
- 使用 MaxLinear, Inc 的 SPX1202 的参考设计
- SP7662 典型应用,4.5-5.5V 至 3.3V/12A 同步降压稳压器
- USB Type-C™和电力输送双端口接口板,带汽车级STUSB1702Y USB Type-C控制器
- 4.2V、1 节、便携式锂离子电池充电器
- 超声波测距系统
- VD6283 Nucleo 包,带 X-NUCLEO-6283A1 扩展板和 STM32-F401RE Nucleo 板
- TX16S萝丽ppm高频头
- 具有 6uA 反向泄漏电流的 LT1767EMS8E-5 双源电源的典型应用电路
- 【训练营】物联网时钟_592780A