用C语言写的多级菜单源程序(单片机),自己试验过,不要网上拷贝过来,谢谢。

用C语言写的多级菜单源程序(单片机),自己试验过,不要网上拷贝过来,谢谢。,第1张

先看第一层菜单

{ 0, 0, 0, 1, 0, MainJob1 }

菜单的索引号为0,这个是可以自己随便定义的,但不要超过255,因为你的索引已经声明uchar了,

第二个0,按下向上键的时候,跳到索引号为0的菜单,也就是,保持现在的界面,第三个0也是一样,第四个1,按下回车的时候,跟到索引号为1的菜单,MainJob1一般是一个当然按键的功能函数,或是界面显示函数

这样说,不知道你能明白不?

{1 ,7 ,2 ,8 ,0 , Dsp Point}

1------是当前的索引号

7------按下向上的时候,跳到7号索引的菜单

2------按下向下的时候,跳到2号索引的菜单

8------按下回车的时候,跳到8号索引的菜单

0------按下回车的时候,跳到0号索引菜单,也就是返回到主界面了

至于说,怎么赋值的,其实就是看你自己想怎么设计你的菜单了,

当前的索引号,你自己定义

按下什么按键时,想跳到哪一个索引的菜单,就是这样了

首先你要搞清楚LCD的显示程序,要能写出反白显示的程序。正常情况下,显示的文字是白背景黑字,还要能写出一个反白显示文字的程序,即是黑背景白字的,这样才能显示出选中的菜单条是黑色的。

这个能做出来,剩下的工作就好做了,按键让选中的菜单条上下移动。按了某个菜单项,就转去执行相应子程序。

我以前倒是做过,不过程序还有点问题,调时间的时候容易过界,但正常走时候就正常了。开发环境用的IAR,单片机用f149,显示用的1602的四线模式。

你自己看着改程序吧,其实我也是51上移植过去的。

悲剧了,帖不下了.我帖在我博客里了啊,自己去找吧.

主程序

__________________________分隔线____________________________________

#include <msp430x14x.h>

#include "ds1302.h"

#include "LCD1602x4_mps.h"

#define DS1302_SECOND 0x81 //时钟芯片的寄存器位置,存放时间

#define DS1302_MINUTE 0x83

#define DS1302_HOUR 0x85

#define DS1302_WEEK 0x8b

#define DS1302_DAY 0x87

#define DS1302_MONTH 0x89

#define DS1302_YEAR 0x8d

unsigned char DateString[11],TimeString[9],week_value[2],TempBuffer[7] //

char hide_sec,hide_min,hide_hour,hide_day,hide_week,hide_month,hide_year

char done,count,temp,flag,up_flag,down_flag

//unsigned int temp_value=0,temp_max=0temp_min=0 //温度值

void DateToStr(void)//将时间年,月,日,星期数据转换成液晶显示字符串,放到数组里DateString[]

{ unsigned char Year,Month,Day,Week

Year=rtc_getyear()

Month=rtc_getmon()

Day=rtc_getdate()

Week=rtc_getday()

if(hide_year<2) //这里的if,else语句都是判断位闪烁,<2显示数据,>2就不显示,输出字符串为 2007/07/22

{

DateString[0] = '2'

DateString[1] = '0'

DateString[2] = Year/10 + '0'

DateString[3] = Year%10 + '0'

}

else

{

DateString[0] = ' '

DateString[1] = ' '

DateString[2] = ' '

DateString[3] = ' '

}

DateString[4] = '/'

if(hide_month<2)

{

DateString[5] = Month/10 + '0'

DateString[6] = Month%10 + '0'

}

else

{

DateString[5] = ' '

DateString[6] = ' '

}

DateString[7] = '/'

if(hide_day<2)

{

DateString[8] = Day/10 + '0'

DateString[9] = Day%10 + '0'

}

else

{

DateString[8] = ' '

DateString[9] = ' '

}

if(hide_week<2)

{

week_value[0] = Week%10 + '0' //星期的数据另外放到 week_value[]数组里,跟年,月,日的分开存放,因为等一下要在最后显示

}

else

{

week_value[0] = ' '

}

week_value[1] = '\0'

DateString[10] = '\0'//字符串末尾加 '\0' ,判断结束字符

}

void TimeToStr(void) //将时,分,秒数据转换成液晶显示字符放到数组 TimeString[]

{ unsigned char Hour,Minute,Second

Hour=rtc_gethour()

Minute=rtc_getmin()

Second=rtc_getsec()

if(hide_hour<2)

{

TimeString[0] = Hour/10 + '0'

TimeString[1] = Hour%10 + '0'

}

else

{

TimeString[0] = ' '

TimeString[1] = ' '

}

TimeString[2] = ':'

if(hide_min<2)

{

TimeString[3] = Minute/10 + '0'

TimeString[4] = Minute%10 + '0'

}

else

{

TimeString[3] = ' '

TimeString[4] = ' '

}

TimeString[5] = ':'

if(hide_sec<2)

{

TimeString[6] = Second/10 + '0'

TimeString[7] = Second%10 + '0'

}

else

{

TimeString[6] = ' '

TimeString[7] = ' '

}

DateString[8] = '\0'

}

void show_time() //液晶显示程序

{

TimeToStr() //时间数据转换液晶字符

DateToStr() //日期数据转换液晶字符

// ReadTemp() //开启温度采集程序

// temp_to_str()//温度数据转换成液晶字符

LCD_PutStr(TempBuffer,25)//显示温度

LCD_PutStr(DateString,0)//显示日期

LCD_PutStr(week_value,15)//显示星期

LCD_PutStr(" Week",10)//在液晶上显示 字母 week

LCD_PutStr(TimeString,16)//显示时间

}

////////////////////////////////////////////////////////////////////////////

void outkey()//跳出调整模式,返回默认显示

{ unsigned char Second

if (!(P1IN&BIT0))

{

count=0

hide_sec=0,hide_min=0,hide_hour=0,hide_day=0,hide_week=0,hide_month=0,hide_year=0

Second=dataread(DS1302_SECOND)

datawrite(0x8e,0x00)//写入允许

datawrite(0x80,Second&0x7f)

datawrite(0x8E,0x80) //禁止写入

done=0//temp_max=0sund=1

while(!(P1IN&BIT0))

delay_nms(2)

}

}

////////////////////////////////////////////////////////////////////////////////////////////////////////////

void Upkey()//升序按键

{

if(!(P1IN&BIT1))

{

switch(count)

{case 1:

temp=dataread(DS1302_SECOND) //读取秒数

temp=temp+1 //秒数加1

up_flag=1 //数据调整后更新标志

if((temp&0x7f)>0x59) //超过59秒,清零

temp=0

break

case 2:

temp=dataread(DS1302_MINUTE) //读取分数

temp=temp+1 //分数加1

up_flag=1

if(temp>0x59) //超过59分,清零

temp=0

break

case 3:

temp=dataread(DS1302_HOUR) //读取小时数

temp=temp+1 //小时数加1

up_flag=1

if(temp>0x23) //超过23小时,清零

temp=0

break

case 4:

temp=dataread(DS1302_WEEK) //读取星期数

temp=temp+1 //星期数加1

up_flag=1

if(temp>0x7)

temp=1

break

case 5:

temp=dataread(DS1302_DAY) //读取日数

temp=temp+1 //日数加1

up_flag=1

if(temp>0x31)

temp=1

break

case 6:

temp=dataread(DS1302_MONTH) //读取月数

temp=temp+1 //月数加1

up_flag=1

if(temp>0x12)

temp=1

break

case 7:

temp=dataread(DS1302_YEAR) //读取年数

temp=temp+1 //年数加1

up_flag=1

if(temp>0x99)

temp=0

break

default:break

}

while(!(P1IN&BIT1))

delay_nms(2)

}

}

////////////////////////////////////////////////////////////////////////////////////////////////////////////

void Downkey()//降序按键

{

if(!(P1IN&BIT2))

{

switch(count)

{case 1:

temp=dataread(DS1302_SECOND) //读取秒数

temp=temp-1 //秒数减1

down_flag=1 //数据调整后更新标志

if((temp&0x7f)>0x59) //小于0秒,返回59秒

temp=0x59

break

case 2:

temp=dataread(DS1302_MINUTE) //读取分数

temp=temp-1 //分数减1

down_flag=1

if(temp>0x59)

temp=0x59 //小于0秒,返回59秒

break

case 3:

temp=dataread(DS1302_HOUR) //读取小时数

temp=temp-1 //小时数减1

down_flag=1

if(temp==0x00)

temp=0x23

break

case 4:

temp=dataread(DS1302_WEEK) //读取星期数

temp=temp-1 //星期数减1

down_flag=1

if(temp==0x00)

temp=0x07

break

case 5:

temp=dataread(DS1302_DAY) //读取日数

temp=temp-1 //日数减1

down_flag=1

if(temp==0x00)

temp=0x31

break

case 6:

temp=dataread(DS1302_MONTH) //读取月数

temp=temp-1 //月数减1

down_flag=1

if(temp==0x00)

temp=0x12

break

case 7:

temp=dataread(DS1302_YEAR) //读取年数

temp=temp-1 //年数减1

down_flag=1

if(temp>0x99)

temp=0x99

break

default:break

}

while(!(P1IN&BIT2))

delay_nms(2)

}

}

void Setkey()//模式选择按键

{

if(!(P1IN&BIT3))

{

count=count+1 //Setkey按一次,count就加1

done=1 //进入调整模式

while(!(P1IN&BIT3))

delay_nms(2)

}

}

void keydone()//按键功能执行

{unsigned char Second

if(flag==0)//关闭时钟,停止计时

{ datawrite(0x8e,0x00)//写入允许

temp=dataread(DS1302_SECOND)

datawrite(0x80,temp|0x80)

datawrite(0x8e,0x80)//禁止写入

flag=1

}

Setkey() //扫描模式切换按键

switch(count)

{

case 1:do //count=2,调整秒

{

outkey() //扫描跳出按钮

Upkey() //扫描加按钮

Downkey() //扫描减按钮

if(up_flag==1||down_flag==1) //数据更新,重新写入新的数据

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x80,temp|0x80)//写入新的秒数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_sec++ //位闪计数

if(hide_sec>3)

hide_sec=0

show_time()//液晶显示数据

}while(count==2)break

case 2:do //count=3,调整分

{

hide_sec=0

outkey()

Upkey()

Downkey()

if(temp>0x60)

temp=0

if(up_flag==1||down_flag==1)

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x82,temp)//写入新的分数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_min++

if(hide_min>3)

hide_min=0

show_time()

}while(count==3)break

case 3:do //count=4,调整小时

{

hide_min=0

outkey()

Upkey()

Downkey()

if(up_flag==1||down_flag==1)

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x84,temp)//写入新的小时数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_hour++

if(hide_hour>3)

hide_hour=0

show_time()

}while(count==4)break

case 4:do //count=5,调整星期

{

hide_hour=0

outkey()

Upkey()

Downkey()

if(up_flag==1||down_flag==1)

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x8a,temp)//写入新的星期数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_week++

if(hide_week>3)

hide_week=0

show_time()

}while(count==5)break

case 5:do //count=6,调整日

{

hide_week=0

outkey()

Upkey()

Downkey()

if(up_flag==1||down_flag==1)

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x86,temp)//写入新的日数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_day++

if(hide_day>3)

hide_day=0

show_time()

}while(count==6)break

case 6:do //count=7,调整月

{

hide_day=0

outkey()

Upkey()

Downkey()

if(up_flag==1||down_flag==1)

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x88,temp)//写入新的月数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_month++

if(hide_month>3)

hide_month=0

show_time()

}while(count==7)break

case 7:do //count=8,调整年

{

hide_month=0

outkey()

Upkey()

Downkey()

if(up_flag==1||down_flag==1)

{

datawrite(0x8e,0x00)//写入允许

datawrite(0x8c,temp)//写入新的年数

datawrite(0x8e,0x80)//禁止写入

up_flag=0

down_flag=0

}

hide_year++

if(hide_year>3)

hide_year=0

show_time()

}while(count==8)break

case 8: count=0hide_year=0 //count8, 跳出调整模式,返回默认显示状态

Second=dataread(0x80)

datawrite(0x8e,0x00)//写入允许

datawrite(0x80,Second&0x7f)

datawrite(0x8E,0x80) //禁止写入

done=0//temp_max=0sund=1

break//count=7,开启中断,标志位置0并退出

default:break

}

}

////////////////////////////////////////////////////////////////////////////

void rtcinit ()

{

rtc_wp(0)

rtc_stop(0)

rtc_charger(1,1)

}

void sysinit ()

{ WDTCTL = WDTPW + WDTHOLD //关闭看门狗

P4OUT = 0xff

P4DIR = 0xff

P5OUT = 0x0f

P5DIR = 0xf0

P6OUT = 0xfc

P6DIR = 0xfc

}

void main ()

{unsigned char temp

sysinit ()

rtcinit ()

LCD_init() //液晶初始化

_EINT()

while (1)

{

while(done==1)

keydone() //进入调整模式

while(done==0)

{

temp=rtc_getsec()

delay_nms(10)

if(temp!=rtc_getsec())

show_time() //液晶显示数据

flag=0

Setkey()//扫描各功能键

}

}

}


欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/yw/11124506.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2023-05-13
下一篇 2023-05-13

发表评论

登录后才能评论

评论列表(0条)

保存