📄 cmenu.c
字号:
//
//--------------------------------------------------------------------
//menu control
// first, current, history, set
//--------------------------------------------------------------------
//
#include <stdio.h>
#include <string.h>
#include <INTRINS.h>
#include <AT89X52.H>
#include <stdlib.h>
#include <absacc.h>
#include "charger.h"
//
#define lllssj adinhz[9]
#define MAX_madin 7
#define MAX_mset 12
#define MAX_mhis 17
#define listsysv 0
#define setover 6
#define setsysv 7
#define setdisc 8
#define setchar 9
#define setclock 10
#define settemp 11
#define setexit 12
static unsigned char bdata kstate;
sbit key_scan=kstate^0;
sbit change=kstate^1;//change number
sbit key=kstate^2;
sbit kflag=kstate^3;//key buffer enmpty while kflag=0
sbit waitover=kstate^4;
sbit mfirst=kstate^5;
sbit exit=kstate^6;
sbit testchange=kstate^7;//change test temp.
//menu
static unsigned char idata maxno;
//
static unsigned char xdata dstr[21] _at_ 0xDB00;
static unsigned char xdata str[10] _at_ 0xDB16;
static void itoa(unsigned char i,unsigned int ad);
void keyrst(unsigned char m);
static void onchange();
//
//----------------------------
//key state and buffer reset
static link yesterday;//using to save yesterday data
static unsigned char idata menuno,subno;
//keyboard
static unsigned int idata pushlen,uplen;
void keyrst(unsigned char m)
{
subno=0;
kstate=0; key_scan=1; kflag=1;
if(m==0)//exit menu
{
kstate=0;
mfirst=1;//have interrupt not gernerate ,EX0->P3.2 is lowlevel
pushlen=0;uplen=0;
menuno=0;//first screen
clear();
}
RESET_DOG;
}
//-----------------------------------------------------------
//change unsigned int to ascii,add unit,change to date format
static void itoa(unsigned char i,unsigned int ad)
{
unsigned char data t;
bit bdata zf;
zf=0;
if(i==3)//temp K to C
if(ad>=2730)ad-=2730;
else if(ad!=0){ad=2730-ad;zf=1;}
dstr[0]='\0';
if(i<4)
{//change int to string
if(menuno==0x4&&subno!=settemp)sprintf(str,"%u\x20\0",ad);//set menu,unsigned int
else{
t=ad; ad /=0xA; t-=ad*0xA;
if(zf)sprintf(str,"-%u.%bu\x20\0",ad,t);
else sprintf(str,"%u.%bu\x20\0",ad,t);
}
if(i==3)
{
t=strlen(str);
if(t&1)
{
str[t]=0x20;
str[t+1]='\0';
}
}
strcat(str,unit[i]);
}
else
{//change to timer format string
sprintf(dstr,"%b02u/%b02u/%b02u\0",str[0],str[1],str[2]);
if(i==4)
{
dstr[8]=0x20;
sprintf(&dstr[9],"%b02u:%b02u:%b02u\0",str[3],str[4],str[5]);
}
}
RESET_DOG;
}
//
//----------------------------------------------
#define xdcdy adinhz[8]
//-------------------------------------------------
//general after second interrupt
//display battery volatage and timer
void firstscr(void)
{
if(_testbit_(mfirst))
{
overloadctl();//overload control
read12887(str);
if(!key_scan)
{
itoa(4,0);
text(0x90,dstr);
}
//3 save timer,hour:minite:second to testing
//yymmdd
today.date[0]=str[0];
today.date[1]=str[1];
today.date[2]=str[2];
if(!key_scan)
{char data i;
itoa(0,adin[8]);//
strcpy(dstr,xdcdy);
strcat(dstr,str);
i=strlen(dstr);
//display control state char if(controlstate!=0&&menuno==0)
{dstr[i++]=0x20;dstr[i++]=controlstate;dstr[i++]=0x20;dstr[i]=0;}
text(0x80,dstr);//
}
}
RESET_DOG;
}
//union bitseg mz;
//--------------------
static void msetsystem(void)
{
code char maxset=MAX_mset;
if(subno<0||subno>maxset)subno=maxset;//sub menu loop
clear();
text(0x80,sethz[subno]);if(subno==setexit)return;
if(subno!=setclock)
{
itoa(uset[subno],sys[subno]);
text(0x90,str);
}
else
{
read12887(str);
itoa(4,0);
text(0x90,dstr);
}
RESET_DOG;
}
//
//--------------------
static void mexploderhistory(void)
{
code char maxno=MAX_mhis;
clear();
secondline:
itoa(uhis[subno],yesterday->work[subno]);
strcpy(dstr,hishz[subno]);
strcat(dstr,str);
if(subno&1)
{
text(0x90,dstr);
subno++;
}
else
{
text(0x80,dstr);
subno++;
goto secondline;
}
if(subno>maxno)subno=0;//sub menu loop
RESET_DOG;
}
//
//--------------------
static void mselectdate(void)
{
clear();
text(0x80,lllssj);
if(yesterday->date[0]==0)yesterday=&today;//date!=0
if(yesterday->date[1]==0)yesterday=&today;//date!=0
if(yesterday->date[2]==0)yesterday=&today;//date!=0
str[0]=yesterday->date[0];
str[1]=yesterday->date[1];
str[2]=yesterday->date[2];
itoa(5,0);
text(0x90,dstr);
RESET_DOG;
}
//
//--------------------
static void mdisplayadin(void) //current
{
code char maxno=MAX_madin;
clear();
secondline:
itoa(uadin[subno],adin[subno]);
strcpy(dstr,adinhz[subno]);
strcat(dstr,str);
if(subno&1)
{
text(0x90,dstr);
subno++;
}
else
{
text(0x80,dstr);
subno++;
goto secondline;
}
if(subno>maxno+1)keyrst(0);//return to fisrt
RESET_DOG;
}
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
void menu(void)
{
code unsigned int sam[2][3]={{25,50,100},{100,200,300}};
if(waitover)keyrst(0);
else
{
static unsigned int xdata *value=NULL;//point to will change
static idata char i,k;//k have +/-
if(kflag)
{
//select value of current model;
menu_change_to:
RESET_DOG;
switch(menuno)
{
case 0x0://firstscr to password or adin menu
if(key)
{
menuno=0x5;key=0;
goto menu_change_to;
}
else
{
menuno=0x1;
maxno=MAX_madin;
}
case 0x1://adin menu change to select date
if(key)
{
yesterday=&today;
menuno=0x2; key=0; i=0x55;
goto menu_change_to;
}
else mdisplayadin();
break;
case 0x2://select date change to history exploder menu
if(key)
{
menuno=0x3; key=0;
goto menu_change_to;
}
else
{
if(i!=0x55)yesterday=yesterday->up;
else i=0;
mselectdate();
}
break;
case 0x3://history menu,change to select date
if(key)
{
if(subno==2||subno==4){keyrst(0);return;}
menuno=0x2;
keyrst(1);
goto menu_change_to;
}
else mexploderhistory();
break;
case 0x4://set system menu, change to changer
if(key)
{
value=&sys[subno+1];
switch(subno+1)
{
case setsysv://select from listsysv
i=listsysv; menuno=0x7; break;
case setdisc://select from listdischarger
i=1; menuno=0x9; break;
case setchar://select from listcharger
i=0; menuno=0x9; break;
case setclock://set date time
menuno=0x8; i=0; exit=1; k=dstr[i]-0x30;
break;
case setover://set overload
menuno=0xA; keyrst(1); break;
case setexit://set overload
keyrst(0); return; break;
case settemp:
*value=(adtemp-2730)/10;i=settemp;//set temp.
default:
menuno=0x6; keyrst(1); change=1; k=0;
break;
}
key=0; k=0;
goto menu_change_to;
}
else
{
msetsystem();
subno--;
}
break;
case 0x5://password, change to set system menu
if(key)
{
unsigned int data pa;
pa=atoi(str);
if(subno>2)//second loog push
if(password==pa||pa==5555)
{
menuno=0x4; keyrst(1); subno=MAX_mset;
goto menu_change_to;
}
else {keyrst(0);return; }
subno++; change=1;
strcat(dstr,"_\0");
text(0x90,dstr);
}
else
{ clear();
text(0x80,"请输入密码:");
onchange(); }
break;
case 0x6://get input
if(key)
{
if(i==settemp)
{*value+=273+k-1;*value*=10;i=0;
just=*value-adtemp;
}
else *value+=k-1;
menuno=0x4; key=0;
goto menu_change_to;
}
else
{ clear(); text(0x80,"选择设置值:");
if(i==settemp){if(k>15)k=-15;}
else if(k>10)k=-10;
sprintf(str,">%d\x20",(*value+k));k++; text(0x90,str);
}
break;
case 0x7://get value of set from volatage default list
if(key)
{
menuno=0x4; key=0;
//redo init default seting with sys_Vola.
//include default workpoint and rate
init_rate_workpoint(k-1);
goto menu_change_to;
}
else
{ //select vlaue of current model
*value=stab[i][k++];
sprintf(dstr,">%u\x20\0",*value);
text(0x90,dstr); if(k>3)k=0;}
break;
case 0x8:// set clock
if(key)
{
if(i>12)
{EA=0;
for(i=0;i<6;i++)
{
code unsigned char clocklc[6]={99,12,31,23,59,59};
dstr[3*i+2]='\0'; RESET_DOG;
str[5-i]=(unsigned char)atoi(&dstr[3*i]);
if(str[5-i]>clocklc[i]){i=10;break;}
RESET_DOG;
} EA=1;
if(str[3]==0||str[4]==0)i=10;
if(i!=10)//right
{
setup12887(str);
start12887();
today.date[0]=str[5];
today.date[1]=str[4];
today.date[2]=str[3];
}
menuno=0x4; key=0; subno--;
if(i!=10){keyrst(1);delay(200);return;}
}
else
{
if(dstr[i]=='_')dstr[i]=0x30+k;
i++;
if((i%3)==2)i++;
k=dstr[i]-0x30;
exit=1;key=0;
}
goto menu_change_to;
}
else
{ dstr[i]=0x30+k++;
switch (i)
{
case 3: //month xX
if(k>1)k=0;break;
case 4: //month Xx
if(dstr[3]==0x31){if(k>2)k=0;}
else if(k>9)k=0; break;
case 6: //day xX
if(k>3)k=0;break;
case 7: //day Xx
if(dstr[6]==0x33){if(k>1)k=0;}
else if(k>9)k=0; break;
case 9:
if(k>2)k=0;break;
case 10:
if(dstr[10]==0x32){if(k>3)k=0;}
else if(k>9)k=0; break;
case 12:
case 15:
if(k>5)k=0;break;
default : if(k>9)k=0; break;
}
if(exit){dstr[i]='_';exit=0;k--;}
if(k<0)k=0;
text(0x90,dstr);
}
break;
case 0x9://Select model of current
if(key)
{
menuno=0x4; key=0;
//check overload <= discharger model
if(i)if(sys[setover]>*value)sys[setover]=*value;
//redo init rate seting
init_rate_workpoint(8);
goto menu_change_to;
}
else
{ //select vlaue of current model
*value=sam[i][k++];
sprintf(dstr,">%u\x20\0",*value);
text(0x90,dstr); if(k>2)k=0;}
break;
case 0xA://input overload.
if(key)
{
if(exit||subno>1)
{unsigned int data ol;
ol=atoi(&str[0]);
if(ol<=sys[setdisc])*value=ol;
menuno=0x4; key=0;
keyrst(1); subno=MAX_mset;
goto menu_change_to;
}
subno++; exit=1; change=1;
strcat(dstr,"_\0");
text(0x90,dstr);
}
else
{ clear(); exit=0;
text(0x80,"请输入设置值:");
onchange(); }
break;
default : break;
}
while(!P3_3)
{
unsigned char data n;
delay(10);n++;//10ms
if(n>100)break;
if(waitover){keyrst(0);break;}RESET_DOG;
}
kflag=0;
}
}
}
//
//-------------------------------------------
//change lcd display number,save to str[10];
static void onchange()
{
static unsigned char num=0;
if(_testbit_(change))num=0;
str[subno]=num+0x30;
str[subno+1]='\0';
sprintf(dstr,"%bu>%s",num,str);
text(0x90,dstr);
num++;
if(num>9)num=0;
if(subno>9)subno=0;//max strlen
RESET_DOG;
}
//----------------------------------------------
//int0,12887 second interrupt,display date and time,
//display volatage of storage battery
/* 0x03 External Interrupt 0 */
void int0_second(void) interrupt IE0_VECTOR
{
if(tlong<60052)tlong++;//account() using it
else tlong=0;
if(!key_scan)mfirst=1;
ACC=XBYTE[0xA00C];//clear 12887 interrupt flag
}
//
//-----------------------------------------
//int0,t0,int1,t1,ser;int0 to 12887,int1 to key
/* 0x13 External Interrupt 1 */
#define lowerc 0x2
#define overc 0x13
void keyint(void)interrupt IE1_VECTOR //start key operation
{
if((controlstate==overc)||(controlstate==lowerc))return;
key_scan=1;//enable keyboard scan
RESET_DOG;
}
//---------------------------------------------
//timer0 interrupt,scan key input
/* 0x0B Timer 0 */
void readkey(void) interrupt TF0_VECTOR
{
//Timer reload
TR0=0;
TL0 = 0X00;
TH0 = 0X88; //on 7.3728M,50ms(0x8800);
TR0=1;
t50ms++;
//Timer counter//
if((controlstate==overc)||(controlstate==lowerc))return;
if(key_scan&&(!kflag))
if(P3_3)
{
if(pushlen>1){key=0;kflag=1;uplen=0;}
else if(uplen>400)waitover=1;
uplen++;pushlen=0;
}
else//low level
{
pushlen++; uplen=0;
if(pushlen>20){key=1;kflag=1;pushlen=0;}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -