当前位置:文档之家› C++菜单程序(实现秒表、倒计时、电子琴等功能)

C++菜单程序(实现秒表、倒计时、电子琴等功能)

#include<reg52.h>
#define uchar unsigned char
#define uint unsigned int

//音乐按键定义
#define M_1 0
#define M_2 1
#define M_3 2
#define M_4 4
#define M_5 5
#define M_6 6
#define M_7 8
#define M_8 9

//以下是C调中音的音频宏定义
#define dao 523 //将“dao”宏定义为中音“1”的频率523Hz
#define re 587 //将“re”宏定义为中音“2”的频率587Hz
#define mi 659 //将“mi”宏定义为中音“3”的频率659Hz
#define fa 698 //将“fa”宏定义为中音“4”的频率698Hz
#define sao 784 //将“sao”宏定义为中音“5”的频率784Hz
#define la 880 //将“la”宏定义为中音“6”的频率880Hz
#define xi 987 //将“xi”宏定义为中音“7”的频率987
#define i 1046 //将“i”宏定义为中音“8”的频率1046

unsigned char keyval; //定义变量储存按键值

sbit sound=P1^2; //将sound位定义为P1.2
unsigned int C; //全局变量,储存定时器的定时常数
unsigned int f; //全局变量,储存音阶的频率



/****1602接口定义****/
sbit rs=P2^4;
sbit rw=P2^5;//1602的读写选择口
sbit en=P2^6;//1602使能信号
/****按钮接口定义****/
sbit s1=P3^0;//确认
sbit s2=P3^1;//下翻页
sbit s3=P3^2;//上翻页
sbit s4=P3^3;//返回
sbit sgnd=P3^7;//按键地线
/****变量定义****/
uchar num,kennum;
uchar num1;//显示for循环变量
uint num2=0;//秒表变量
uchar num3=99;
uchar hm,miao,smiao,fen,sfen,xshi,sxshi;
uchar flog; //程序执行标志
/****数组定义****/
/*主页面显示*/
uchar code table_0[]=" 1602 ";//**num=0**主菜单显示 1排
uchar code table_01[]=" MENU ";//**num=0**主菜单显示 2排
/*功能1显示*/
uchar code table_1[]="1.Stopwatches @ ";//
/*功能2显示*/
uchar code table_2[]="2.Being @ ";//
/*功能3显示*/
uchar code table_3[]="3.Music @ ";//
/*功能4显示*/
uchar code table_4[]="4.volume ";//
/*功能5显示*/
uchar code table_5[]="5.Copyright @ ";//
/*显示 功能*/
uchar code table_6[]=" MENU ";//
/*显示 清屏*/
uchar code table_7[]=" ";//
/*显示我的学号*/
uchar code table_8[]="ID:080522019 ";
uchar code table_9[]="6.Luminosity ";//
uchar code table_10[]="7.EEPROM ";//
uchar code table_11[]="8.Calculator ";//
uchar code table_12[]="9.External interrupt";//
uchar code table_13[]="10.Timer ";//

/****函数声明****/
void delay(uchar z)//延时子函数
{
uint x,y;
for(x=z;x>0;x--)
for(y=110;y>0;y--);
}

void wilte_com(uchar);//1602写命令
void wilte_data(uchar);//1602写数据
void init();//程序主初始
uchar k

en();//按键(翻页)
bit Music();
void Output_Sound(void);
uchar KeyScan();
/**********************************************************************************

程序主函数


*********************************************************************/
void main()
{
init();

EA=1; //开总中断
ET0=1; //定时器T0中断允许
// ET1=1; //定时器T1中断允许
// TR1=1; //定时器T1启动,开始键盘扫描
TMOD=0x10; //分别使用定时器T1的模式1,T0的模式0
// TH1=(65536-500)/256; //定时器T1的高8位赋初值
// TL1=(65536-500)%256; //定时器T1的高8位赋初值

while(1)
{
num=ken(); //读按键值,
/********************************************
主页面
*******************************/
if(num==0)
{
/****显示主页面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_0[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_01[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
}

/********************************************
功能:1
*******************************/
if(num==1)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能1界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_1[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
if(s1==0)//确认键按下后执行内部语句
{
delay(3);
if(s1==0)
{
while(!s1); //松手检测 放开后执行相关程序
flog=1;
/******更新显示*******/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_1[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_7[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}

while(flog)
{
flog=1;
delay(1); //延时
num2++;
sxshi=num2/10000;
xshi=num2/100000/1000;
sfen=num2/10000;
fen=num2/1000;
smiao=num2%1000/100;
miao=num2%100/10;
hm=num2%10;
if(num2==600)
{
num2 = 0;

fen++;
if(smiao==6)

{
smiao = 0;
fen++;
}
if(sfen==6)
{
sfen = 0;
xshi++;
}
}


wilte_com(0x80+0x40+0);
wilte_data(0x30+sxshi);

wilte_com(0x80+0x40+1);
wilte_data(0x30+xshi);
wilte_com(0x80+0x40+2);
wilte_data(0x3a);
wilte_com(0x80+0x40+3);
wilte_data(0x30+sfen);


wilte_com(0x80+0x40+4);
wilte_data(0x30+fen);
wilte_com(0x80+0x40+5);
wilte_data(0x3a);
wilte_com(0x80+0x40+6);
wilte_data(0x30+smiao);
wilte_com(0x80+0x40+7);
wilte_data(0x30+miao); //显示十位
wilte_com(0x80+0x40+9);
wilte_data(0x30+hm); //显示个位
if(num2==600)
{
num2=0;
fen++;
}

if(s4==0)
{
delay(2);
if(s4==0)
{
flog=0;
num2=0;
}
}
if(s2==0)
{
delay(2);
if(s2==0)
while(!s2);
}
if(s3==0)
{
delay(2);
if(s3==0)
num2=0;
}
}
}
}
}
/********************************************
功能:2
*******************************/

if(num==2)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能2界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_2[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
if(s1==0)//确认键按下后执行内部语句
{
delay(2);
if(s1==0)
{
while(!s1); //松手检测,放开后执行相关程序
flog=1;
/******更新显示*******/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_2[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_7[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
while(flog)
{
num3--;
if(num3==0)
num3=99;
delay(50); //延时
smiao=num3/100;
miao=num3%100/10;
hm=num3%10;
wilte_com(0x80+0x40+0);
wilte_data(0x30+sxshi);

wilte_com(0x80+0x40+1);

wilte_data(0x30+xshi);
wilte_com(0x80+0x40+2);
wilte_data(0x3a);
wilte_com(0x80+0x40+3);
wilte_data(0x30+sfen);


wilte_com(0x80+0x40+4);
wilte_data(0x30+fen);
wilte_com(0x80+0x40+5);
wilte_data(0x3a);
wilte_com(0x80+0x40+6);
wilte_data(0x30+smiao);
wilte_com(0x80+0x40+7);
wilte_data(0x30+miao); //显示十位
wilte_com(0x80+0x40+9);
wilte_data(0x30+hm); //显示个位
if(s4==0)
{
delay(2);
if(s4==0)
{
flog=0;
num3=0;
}
}
if(s2==0)
{
delay(2);
if(s2==0)
while(!s2);
}
if(s3==0)
{
delay(2);
if(s3==0)
num3=100;
}
}
}
}
}
/********************************************
功能

:3
*******************************/
if(num==3)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能3界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_3[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}

if(s1 == 0)
{
Music();
TR0 = 0;
P3 = 0X0F;
sgnd = 0;
}
/************************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(5);
} */
}
/********************************************
功能:4
*******************************/
if(num==4)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能4界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_4[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(3);
} */
}


/********************************************
功能:5
*******************************/
if(num==5)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示
字符表table1的内容
delay(5);
}
/****显示功能5界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_5[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
if(s1==0)//确认键按下后执行内部语句
{
if(s1==0)//确认键按下后执行内部语句
{
delay(2);
if(s1==0)
{
while(!s1); //松手检测 放开后执行相关程序
flog=1;
/******更新显示*******/
while(flog)
{
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_5[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_8[num1]);//160

2写数据 显示字符表table2的内容
delay(5);
}
if(s4==0)
{
delay(2);
if(s4==0)
flog=0;
}
}
}
}
}
}

/********************************************
功能:6
*******************************/
if(num==6)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能9界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_9[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(3);
} */
}
/********************************************
功能:7
*******************************/
if(num==7)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能9界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_10[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/**
**********************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(3);
} */
}
/********************************************
功能:8
*******************************/
if(num==8)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能9界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_11[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(3);
} */
}
/********************************************
功能:9
*******************************/
if(num==9)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能9界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(

num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_12[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(3);
} */
}
/********************************************
功能:10
*******************************/
if(num==10)
{
/****显示功能界面***/
wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_6[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能9界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(table_13[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}
/************************
确认是否执行相关程序
***/
/* if(s1==0)//确认键按下后执行内部语句
{
delay(3);
} */
}
}
}

/**********************************************************************************
按 键 (翻页)
********************************************************************
*/
uchar ken() // 按 键 (翻页)
{
if(s2==0)
{
delay(2);
if(s2==0)
{
while(!s2);
kennum++;
if(kennum==11)
kennum=1;
}
}
if(s3==0)
{
delay(2);
if(s3==0)
{
while(!s2);
kennum--;
if(kennum==0)
kennum=11;
}
}
if(s4==0)
{
delay(2);
if(s4==0)
{
while(!s4);
kennum=0;
}
}
return kennum; //返回值,确定当前所在页
}
/**********************************************************************************
1602写命令
*********************************************************************/
void wilte_com(uchar com)//1602写命令
{
rs=0;
en=0;
P0=com;
delay(5);
en=1;
delay(5);
en=0;
}
/**********************************************************************************
1602写数据
*********************************************************************/
void wilte_data(uchar data1)//1602写数据
{
rs=1;
en=0;
P0=data1;
delay(5);
en=1;
delay(5);
en=0;
}
void init()
{
flog=0;
/**按键相关初始**/
kennum=0; //s2_s3_s4 按键值
num=0; //读按键值变量
sgnd=0;//给按键端底电平
/**1602相关初始**/
rw=0;//我只对1602写数据,不读,所以一直给底,
en=0;//使能信号初始为底
wilte_com(0x38);//1602写命令 设置1602显示模式
wilte_com(0x0c);//1602写命令 开显示,不显示光标
wilte_com(0x06);//1602写命令 写一个字符,光标和地址加1
wilte_com(0x01);//完了防错的
}


void Display_Music(uchar dis)
{
uchar num1 = 0;
uchar code *music_tb[] = {"Pressed dao! ","Pressed re ! ","Pressed mi ! ", "Pressed fa ! ",
"Press

ed sao! ","Pressed la ! ", "Pressed xi ! ","Pressed i! ","Have no music! "};
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(*(music_tb[dis] + num1));//1602写数据 显示字符表table2的内容
delay(5);
}
}
//电子琴
bit Music(void)
{
uchar num = 0;
uchar key_num = 0xff;
uchar code music_no[] = "Have no music! ";

wilte_com(0x80);
for(num1=0;num1<16;num1++)//让字符表lable1的字符一个一个的累加显示在1602第一行上
{
wilte_data(table_3[num1]);//1602写数据 显示字符表table1的内容
delay(5);
}
/****显示功能3界面--功能名***/
wilte_com(0x80+0x40); //显示指针到第二排
for(num1=0;num1<16;num1++)//让字符表lable2的字符一个一个的累加显示在1602第二行上
{
wilte_data(music_no[num1]);//1602写数据 显示字符表table2的内容
delay(5);
}


while(1)
{
key_num = KeyScan();

switch(key_num)
{
case M_1: Display_Music(0);f = dao; Output_Sound(); break;
case M_2: Display_Music(1);f = re; Output_Sound(); break;
case M_3: Display_Music(2);f = mi; Output_Sound(); brea
k;
case M_4: Display_Music(3);f = fa; Output_Sound(); break;

case M_5: Display_Music(4);f = sao; Output_Sound(); break;
case M_6: Display_Music(5);f = la; Output_Sound(); break;
case M_7: Display_Music(6);f = xi; Output_Sound(); break;
case M_8: Display_Music(7);f = i; Output_Sound(); break;

case 15: key_num = 0xff;return 0;
default: key_num = 0xff;break;
}
key_num = 0xff;
}
}


//键盘扫描
uchar KeyScan(void)//键盘扫描函数,使用行列反转扫描法
{
uchar cord_h,cord_l;//行列值
uchar key_num = 0xff;
P3=0x0f; //行线输出全为0
cord_h=P3&0x0f; //读入列线值
if(cord_h!=0x0f) //先检测有无按键按下
{
delay(100); //去抖
if(cord_h!=0x0f)
{
cord_h=P3&0x0f; //读入列线值
P3=cord_h|0xf0; //输出当前列线值
cord_l=P3&0xf0; //读入行线值
key_num = cord_h + cord_l;
goto KEYNUM11;
//return(cord_h+cord_l);//键盘最后组合码值并返回
}
}//return(0xff); //否则返回固定值0xff

key_num = 0xff;
KEYNUM11:
switch(key_num)
{

case 0xee:return 0;//0 按下相应的键显示相对应的码值
case 0xde:return 1;//1
case 0xbe:return 2;//2
case 0x7e:return 3;//3
case 0xed:return 4;//4
case 0xdd:return 5;//5
case 0xbd:return 6;//6
case 0x7d:return 7;//7
case 0xeb:return 8;//8
case 0xdb:return 9;//9
case 0xbb:return 10;//a
case 0x7b:return 11;//b
case 0xe7:return 12;//c
case 0xd7:return 13;//d
case 0xb7:return 14;//e
case 0x77:return 15;//f
default: return 0xff;
}
}


void Output_Sound(void)
{
C=(46083/f)*10; //计算定时常数
TH0=(8192-C)/32; //可证明这是13位计数器TH0高8

位的赋初值方法
TL0=(8192-C)%32; //可证明这是13位计数器TL0低5位的赋初值方法
TR0=1; //开定时T0
// delay(); //延时200ms,播放音频
P3 = 0XF0;
while(0XF0 != P3)
{
P3 = 0XF0;
}
TR0=0; //关闭定时器
sound=1; //关闭蜂鸣器
Display_Music(8);
// keyval=0xff; //播放按键音频后,将按键值更改,停止播放
}
void Time0_serve(void ) interrupt 1 using 1
{

TH0=(8192-C)/32; //可证明这是13位计数器TH0高8位的赋初值方法
TL0=(8192-C)%32; //可证明这是13位计数器TL0低5位的赋初值方法
sound=!sound; //将P3.7引脚取反,输出音频方波
}

相关主题
文本预览
相关文档 最新文档