?? alarm.c
字號:
//處理鬧鐘中斷后的進程
//執行中斷里面鬧鐘的處理
//重新把下一個最近的鬧鐘值寫入鬧鐘寄存器
void Alarm_Process(void)
{
u16 cbcolor;
u16 cpcolor;
cbcolor=BACK_COLOR; //保存先前的畫筆狀態
cpcolor=POINT_COLOR;
//對于只要鬧鈴一次的鬧鐘,在執行之后關閉鬧鐘
if((Alarm[AlarmInLine].Status&0x03)==0)
{
Alarm[AlarmInLine].Status&=0xF7; //取消鬧鈴
Save_Alarm(AlarmInLine);//將數據保存,下次不再啟用
}
READ_GRAM(111,151);
BACK_COLOR=GRAY;
POINT_COLOR=BLACK;
TFT_ShowNum(112,152,Alarm[AlarmInLine].hour,16,0x00);
TFT_ShowChar(128,152,':',16,0x00);
TFT_ShowNum(136,152,Alarm[AlarmInLine].min,16,0x00);
POINT_COLOR=GRED;
TFT_DrawRectangle(111,151,152,168);
Play_Alarm_Ring();//響鬧鈴
RECOVER_GRAM(111,151);
Init_Alarm_Reg();//取得下一個鬧鐘的時間
POINT_COLOR=cpcolor;//恢復先前的畫筆狀態
BACK_COLOR=cbcolor;
}
//鬧鐘初始化
void Alarm_Init(void)
{
u8 t,i;
while(!(RTC->CRL&(1<<3)));//等待RTC寄存器同步
RTC->CRH|=0X02; //允許鬧鐘中斷
while(!(RTC->CRL&(1<<5)));//等待RTC寄存器操作完成
rtc_get();//得到時間
t=FM24C16_ReadOneByte(263);//讀取第一個鬧鐘的小時
if(t>23) //未被初始化
{
for(i=0;i<8;i++)//初始化
{
Alarm[i].Status=0;
Alarm[i].WeekMark=0;
Alarm[i].Ring=0;
Alarm[i].hour=0;
Alarm[i].min=0;
Alarm[i].Ring_Addr=0;
}
Save_Alarm(8);//全部保存
}else Read_Alarm(8);//全部讀取鬧鐘數據,包括鬧鐘鈴聲
Init_Alarm_Reg(); //更新鬧鐘寄存器
}
//加載星期自定義的設置
void Self_Define(u8 sfd)
{
u8 t;
BACK_COLOR=LGRAY;
//加載條目信息
for(t=0;t<7;t++)
{
if(sfd&0x80)POINT_COLOR=RED;
else POINT_COLOR=LGRAY;
TFT_DrawRectangle(20+29*t,146,46+29*t,162);//26*16方框
sfd<<=1;
}
}
//顯示鈴聲的名字
void Show_Ring_Name(void)
{
u8 str[8];
if(Alarm_Temp.Status&0x04)//收音機作為鈴聲
{
if(Alarm_Temp.Ring_Addr>=8750&&Alarm_Temp.Ring_Addr<=10800)//存在合法頻段
{
str[0]='F';
str[1]='M';
if(Alarm_Temp.Ring_Addr>=10000)str[2]='1';//
else str[2]=' ';//
str[3]=(Alarm_Temp.Ring_Addr/1000)%10+'0';//
str[4]=(Alarm_Temp.Ring_Addr/100)%10+'0';//
str[5]='.';//
str[6]=(Alarm_Temp.Ring_Addr/10)%10+'0';//小數點后一位
str[7]='\0';//加入結束符
Show_Str_Mid(0,210,str,0x00,240); //疊加模式,非自動換
}else Show_Str_Mid(0,210,"空白",0x00,240); //不存在FM,跳出
}
else //MP3作為鈴聲
{
if(Alarm_Temp.Ring_Addr>2)Show_Str_Mid(0,210,Alarm_Temp.Ring_Name,0x00,240); //疊加模式,非自動換
else Show_Str_Mid(0,210,"空白",0x00,240); //疊加模式,非自動換
}
}
u8 AlarmTPos=0;//鬧鈴時鐘所在位置 XX:XX 共四位
//選項選中/取消
//num:目錄項 0,1,2,4,5
//sel:1選中/0取消
void Item_Sel(u8 num,u8 sel)
{
u8 temp;
Self_Define(0);//默認去除星期框
if(num==1||num==4)BACK_COLOR=WHITE;//假定沒有選中,原背景
else BACK_COLOR=LGRAY;
if(sel)BACK_COLOR=BROWN;//棕色背景,選中了
POINT_COLOR=BLACK; //筆是黑色的
temp=Alarm_Temp.Status; //得到狀態值
switch(num)
{
case 0: //鬧鈴開關
if(temp&0x08)Show_Str(144,50,"打開",0x00); //非疊加模式,非自動換行
else Show_Str(144,50,"關閉",0x00); //非疊加模式,非自動換行
break;
case 1://鬧鈴時間
temp=Alarm_Temp.hour;//獲得小時
TFT_ShowChar(140,82,temp/10+'0',16,0x00);
TFT_ShowChar(148,82,temp%10+'0',16,0x00);
TFT_ShowChar(156,82,':',16,0x00);
temp=Alarm_Temp.min;//獲得分鐘
TFT_ShowChar(164,82,temp/10+'0',16,0x00);
TFT_ShowChar(172,82,temp%10+'0',16,0x00);
if(sel)
{
BACK_COLOR=BLUE;//
POINT_COLOR=WHITE;
switch(AlarmTPos)
{
case 0:
TFT_ShowChar(140,82,Alarm_Temp.hour/10+'0',16,0x00);
break;
case 1:
TFT_ShowChar(148,82,Alarm_Temp.hour%10+'0',16,0x00);
break;
case 2:
TFT_ShowChar(164,82,Alarm_Temp.min/10+'0',16,0x00);
break;
case 3:
TFT_ShowChar(172,82,Alarm_Temp.min%10+'0',16,0x00);
break;
}
Load_KeyBoard(1);//加載鍵盤
}else Load_KeyBoard(0);
break;
case 2://響鈴方式
temp=temp&0x03;
switch(temp)
{
case 0://一次
Show_Str(136,114," 一次 ",0x00); //疊加模式,非自動換行
break;
case 1://每天
Show_Str(136,114," 每天 ",0x00); //疊加模式,非自動換行
break;
case 2://自定義
Show_Str(136,114,"自定義",0x00); //疊加模式,非自動換行
Self_Define(Alarm_Temp.WeekMark);//加載星期框
break;
}
break;
case 4:
if(temp&0x04)//FM作為鈴聲
{
Read_Ring(1,Alarm_Temp.Ring,Alarm_Temp.Ring_Name,&Alarm_Temp.Ring_Addr);
Show_Str(136,178,"FM廣播",0x00); //疊加模式,非自動換行
}
else //MP3作為鈴聲
{
Read_Ring(0,Alarm_Temp.Ring,Alarm_Temp.Ring_Name,&Alarm_Temp.Ring_Addr);
Show_Str(136,178," 鈴聲 ",0x00); //疊加模式,非自動換行
}
TFT_Fill(0,202,239,234,LGRAY);//清空上次顯示
BACK_COLOR=LGRAY;
Show_Ring_Name();
break;
case 5:
TFT_Fill(0,202,239,234,LGRAY);//清空上次顯示
Show_Ring_Name(); break;
}
}
//處理鍵值
//selx:鍵值條目編號
void Pro_Key_Alarm(u8 selx)
{
u8 temp;
switch(selx)
{
case 0://開關按鍵
if(Is_In_Area(85,46,109,70)||Is_In_Area(210,46,234,70))
{
if(Alarm_Temp.Status&0x08)Alarm_Temp.Status&=0xF7;//取消操作
else Alarm_Temp.Status|=0x08;//選擇操作
Item_Sel(0,1);
}
break;
case 1://時間設置
if(Is_In_Area(140,82,148,98))AlarmTPos=0;//選中小時十位
else if(Is_In_Area(148,82,156,98))AlarmTPos=1;//選中小時個位
else if(Is_In_Area(164,82,172,98))AlarmTPos=2;//選中分鐘十位
else if(Is_In_Area(172,82,180,98))AlarmTPos=3;//選中分鐘個位
Item_Sel(1,1);
break;
case 2://響鈴方式
temp=Alarm_Temp.Status&0x03;
if(Is_In_Area(85,110,109,134))//左鍵
{
if(temp)temp--;
else temp=2;
}else if(Is_In_Area(210,110,234,134))//右鍵
{
temp++;
if(temp>2)temp=0;
}
Alarm_Temp.Status&=0XFC;
Alarm_Temp.Status|=temp;
Item_Sel(2,1);
break;
case 4: //鈴聲設置
if(Is_In_Area(85,174,109,198)||Is_In_Area(210,174,234,198))
{
if(Alarm_Temp.Status&0x04)Alarm_Temp.Status&=0xFB;//取消操作 0,MP3鈴聲
else Alarm_Temp.Status|=0x04;//選擇操作 1,FM鈴聲
Item_Sel(4,1);
}
break;
case 5:
Set_Alarm_Ring(); //鬧鐘鈴聲
Load_Gui_Set_Alarm(); //裝載ALARM編輯主界面
for(temp=0;temp<6;temp++)
{
if(temp==5)Item_Sel(temp,1);//選中鬧鈴開關
else if(temp!=3)Item_Sel(temp,0);
}
break;
}
}
//得到星期幾按鍵返回值
//返回:1~8
//返回8:按鍵無效
u8 Get_WeekBit_Val(void)
{
u8 t;
for(t=0;t<7;t++)if(Is_In_Area(20+29*t,146,46+29*t,162))return t+1;//返回星期幾的編號
return 8;
}
//設置鬧鐘
//index:鬧鐘編號
void Set_Alarm(u8 index)
{
u8 key,sel;
Alarm_Temp=Alarm[index];
Alarm_Temp.Ring=index;//保存鬧鐘編號
Read_Ring(Alarm_Temp.Status&0x04,Alarm_Temp.Ring,Alarm_Temp.Ring_Name,&Alarm_Temp.Ring_Addr);//讀取鬧鐘鈴聲信息
Load_Gui_Set_Alarm(); //裝載ALARM編輯主界面
for(sel=0;sel<6;sel++)
{
if(sel==0)Item_Sel(sel,1);//選中鬧鈴開關
else if(sel!=3)Item_Sel(sel,0);
}
key=0;
sel=0;//默認選擇0
Pen_Point.Key_Sta=Key_Up;//釋放顯示期間的觸發
while(1)//等待按鍵
{
if((Pen_Point.Key_Sta==Key_Down||NPEN)&&Pen_Point.Key_LSta)key=Touch_To_Num(4);//得到按鍵值
if(PEN)//按鍵松開了,狀態改變(狀態機)
{
Pen_Point.Key_LSta=1;
Pen_Point.Key_Sta=Key_Up;
}
if(key)//有按鍵按下
{
Pen_Point.Key_LSta=0;
switch(key)
{
case 1:
case 2:
case 3:
case 5:
case 6:
key-=1;
if(sel!=key&&key<8)//選中一個
{
AlarmTPos=0;//復位到第一位
Item_Sel(sel,0);
sel=key;//選擇這次選擇的
Item_Sel(sel,1);
}else if(sel==key)//選擇按鈕,或者雙擊
{
Pro_Key_Alarm(sel);//操作
}
break;
case 9://確認按鈕按下了
Alarm[index]=Alarm_Temp;
Save_Alarm(index);//保存特定編號的鬧鐘數據
Init_Alarm_Reg(); //更新鬧鐘寄存器
return; //保存并返回
case 10:return;//選擇了"返回"按鈕,返回一個不可能值
default:
if(sel==1)//時間輸入
{
key=Get_KeyBoard_Val();
if(key==10&&AlarmTPos)AlarmTPos--;//退格操作
if(key<10)
{
switch(AlarmTPos)
{
case 0://修改小時的十位
Alarm_Temp.hour%=10;
Alarm_Temp.hour+=key*10;
if(Alarm_Temp.hour>23)Alarm_Temp.hour=23;
break;
case 1:
Alarm_Temp.hour/=10;
Alarm_Temp.hour*=10;
Alarm_Temp.hour+=key;
if(Alarm_Temp.hour>23)Alarm_Temp.hour=23;
break;
case 2://修改分鐘的十位
if(key>5)key=5;
Alarm_Temp.min%=10;
Alarm_Temp.min+=key*10;
break;
case 3:
Alarm_Temp.min/=10;
Alarm_Temp.min*=10;
Alarm_Temp.min+=key;
break;
}
if(AlarmTPos<3)AlarmTPos++;//自動切換到下一個
}
Item_Sel(1,1);//更新顯示數據
}else if(sel==2&&(((Alarm_Temp.Status)&0x03)==2))//自定義星期
{
key=Get_WeekBit_Val();
if(key<8)
{
key=8-key;
if(Alarm_Temp.WeekMark&(1<<key))
{
Alarm_Temp.WeekMark&=~(1<<key);
}else
{
Alarm_Temp.WeekMark|=(1<<key);
}
}
Item_Sel(2,1);
}
break;
}
key=0;//取消按鍵值
}
delay_ms(1);
}
}
//鬧鐘瀏覽
//相關鬧鐘的設置全部在這個函數里面了
void Alarm_Viewer(void)
{
u8 selx=0;
u8 t;
u8 *p=(u8 *)iclip;
ARST:
Read_Alarm(8);//獲取鬧鐘數據
for(t=0;t<8;t++)Alarm_F1[t]=p+t*30;//地址映射到 Alarm_F1里面
for(t=0;t<8;t++)
{
Alarm_F1[t][0]=Alarm[t].hour/10+'0';
Alarm_F1[t][1]=Alarm[t].hour%10+'0';
Alarm_F1[t][2]=':';
Alarm_F1[t][3]=Alarm[t].min/10+'0';
Alarm_F1[t][4]=Alarm[t].min%10+'0';
Alarm_F1[t][5]='\0'; //添加結束符
}
while(1)
{
selx=Load_Fun_Sel((const u8 * *)Alarm_F1,"鬧鐘設置","編輯",8,selx);
if(selx==8)return;//返回
else
{
Set_Alarm(selx);//設置鬧鐘 goto ARST;
}
}
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -