标题:
单片机四路抢答器(倒计时)基于51单片机
[打印本页]
作者:
123456ld
时间:
2019-11-10 12:03
标题:
单片机四路抢答器(倒计时)基于51单片机
本帖最后由 123456ld 于 2019-11-11 15:09 编辑
基于c51的四路抢答器,本实验通过数码管结合矩阵按键及独立按键组成四路抢答器。对不同选手的判断从而在数码管上显示那位选手抢答成功暂停计时,或哪三位选手犯规触发蜂鸣器报警。其中倒计时的开始由独立按键K1实现,对抢答或倒计时的恢复由独立按键K3实现。程序源码为本人自创,如有不懂,请留言发问。篇幅有限仅提供部分代码。详情请下载后查阅。
该程序适用stc89c51单片机
单片机源程序如下:
/****************************************************
* 实验内容
* 四路抢答器
**************************************************/
#include <reg52.h>
typedef unsigned int u16;
typedef unsigned char u8;
/***********************************************
*
* 变量及引脚定义声明
*************************************************/
sbit AA = P2^2;
sbit BB = P2^3;
sbit CC = P2^4;
sbit k3 = P3^2;
sbit k4 = P3^3;
sbit beep = P1^5;
int i=0; //初始状态控制毫秒的两位数码管为0
int j=10; //初始状态控制秒的两位数码管为10
int jishu=0; //以10ms为一个剂量,精准控制毫秒的99-0
int cishu=0; //消除最后一秒带来的影响
int xuanshou=0; //选手编号
int biaozhi=1; //控制抢答开始后只有一个人可以被记录
int wei1=0 , wei2=0 , wei3=0;
enum position {zero, one, two, three, four, five, six, seven};
u16 code duanxuan[16] = { 0x3f,0x06,0x5b,0x4f,
0x66,0x6d,0x7d,0x07,
0x7f,0x6f,0x77,0x7c,
0x39,0x5e,0x79,0x71};
/*****************************************************
*
* 子函数申明
******************************************************/
void delay(u16 i); //延时函数
void jvzhen(); //矩阵键盘选手确定
void weixuan( u16 i ); //数码管位选
void timer0(); //定时器初始化
void xianshi(); //数码管倒计时显示
void int0(); //中断0倒计时开始
void int1(); //中断1问题结束恢复数码管
void panduan(); //答题选手的判断
void qiangda(); //选手抢答时的判断
/*****************************************************
* 主函数
*******************************************************/
void main()
{
int0();
int1();
timer0();
while(1)
{
xianshi();
jvzhen();
panduan();
qiangda();
}
}
void qiangda()
{
if( j==10&&xuanshou!=0 )
{
wei1 = xuanshou;
while(1)
{
xianshi();
weixuan(7);
P0 = duanxuan[wei1];
delay(1);
P0 = 0x00;
beep=~beep;
delay(1);
jvzhen();
if( xuanshou!=wei1 )
{
break;
}
if( k4==0 )
{
break;
}
}
wei2 = xuanshou;
while(1)
{
xianshi();
weixuan(7);
P0 = duanxuan[wei2];
delay(1);
P0 = 0x00;
weixuan(6);
P0 = duanxuan[wei1];
delay(1);
P0 = 0x00;
beep=~beep;
delay(1);
jvzhen();
if( xuanshou!=wei2 )
{
break;
}
if( k4==0 )
{
break;
}
}
wei3 = xuanshou;
while(1)
{
xianshi();
weixuan(7);
P0 = duanxuan[wei3];
delay(1);
P0 = 0x00;
weixuan(6);
P0 = duanxuan[wei2];
delay(1);
P0 = 0x00;
weixuan(5);
P0 = duanxuan[wei1];
delay(1);
P0 = 0x00;
beep=~beep;
delay(1);
jvzhen();
if( k4==0 )
{
break;
}
}
}
}
/* 延时 */
void delay(u16 i)
{
u16 a;
while(i--)
{
for(a = 0; a < 100; a++)
{
;
}
}
}
/* 显示哪位选手按键暂停 */
void panduan()
{
if( i!=0 && xuanshou!=0 )
{
switch( xuanshou )
{
case 1 : TR0=0; weixuan(7); P0=duanxuan[1]; delay(1); P0 = 0x00; break;
case 2 : TR0=0; weixuan(7); P0=duanxuan[2]; delay(1); P0 = 0x00; break;
case 3 : TR0=0; weixuan(7); P0=duanxuan[3]; delay(1); P0 = 0x00; break;
case 4 : TR0=0; weixuan(7); P0=duanxuan[4]; delay(1); P0 = 0x00; break;
}
biaozhi=0;
}
}
/* 矩阵键盘选手确定 */
void jvzhen()
{
P1 = 0x0f;
if( (P1!=0x0f&&biaozhi==1) )
{
delay(5);
if( (P1!=0x0f) )
{
switch( P1 )
{
case 0x07 : xuanshou = 1; break;
case 0x0b : xuanshou = 2; break;
case 0x0d : xuanshou = 3; break;
case 0x0e : xuanshou = 4; break;
}
P1=0xf0;
switch( P1 )
{
case (0x70) : xuanshou = xuanshou; break;
}
}
}
}
/* 数码管位选*/
void weixuan( u16 i )
{
switch(i)
{
case (zero): CC = 0; BB = 0; AA = 0; break; //第零位
case (one): CC = 0; BB = 0; AA = 1; break; //第一位
case (two): CC = 0; BB = 1; AA = 0; break; //第二位
case (three): CC = 0; BB = 1; AA = 1; break; //第三位
case (four): CC = 1; BB = 0; AA = 0; break; //第四位
case (five): CC = 1; BB = 0; AA = 1; break; //第五位
case (six): CC = 1; BB = 1; AA = 0; break; //第六位
case (seven): CC = 1; BB = 1; AA = 1; break; //第七位
}
}
/* 定时器初始化*/
void timer0()
{
TMOD =0x01;
TH0 = (65536-1000)/256;
TL0 = (65536-1000)%256; //1ms
ET0 = 1;
EA = 1;
}
/* 倒计时显示 */
void xianshi()
{
weixuan(0);
P0 = duanxuan[i%10];
delay(1);
P0 = 0x00;
weixuan(1);
P0 = duanxuan[i/10];
delay(1);
P0 = 0x00;
weixuan(2);
P0 = 0x40;
delay(1);
P0 = 0x00;
weixuan(3);
P0 = duanxuan[j%10];
delay(1);
P0 = 0x00;
weixuan(4);
P0 = duanxuan[j/10];
delay(1);
P0 = 0x00;
}
/* 倒计时开始 */
void int0()
{
EA=1;
IT0=1;
EX0=1;
}
/* 数码管复位 */
void int1()
{
EX1=1;
IT1=1;
EA=1;
}
复制代码
所有资料51hei提供下载:
四路抢答器(倒计时).zip
(35.3 KB, 下载次数: 39)
2019-11-10 12:02 上传
点击文件名下载附件
下载积分: 黑币 -5
作者:
admin
时间:
2019-11-10 21:14
本帖需要重新编辑补全电路原理图,源码,详细说明与图片即可获得100+黑币(帖子下方有编辑按钮)
欢迎光临 (http://www.51hei.com/bbs/)
Powered by Discuz! X3.1