?? keyboard.c
字號:
/********************Copyright******************************
煙臺佳園智能數碼科技有限公司
名稱:KEYBOARD.C
功能:掌上維護器驅動程序
說明:與HICJ5的結合不是很好,雖然能正常跑起來,但是由于相對HICJ5.C有較多功能重復性代碼
浪費了一定的內存及代碼資源
修改:2004/12/6 增加了取消報警狀態功能
2004/12/7 去掉了通信時鐘等功能,對于表的類型顯示采用了固定值法
************************************************************/
#include "P89C60X2.h"
#include "hicj6.h"
//#include "INTRINS.H"
/**************new define**********************************/
unsigned char idata Key_value;
unsigned char idata House_count;
unsigned char idata Idletime_count;
unsigned char idata Speaker_count;
//unsigned char idata Msb_led_val;
//unsigned char idata Msb_led; //表字顯示的最高位
unsigned char idata Blink_led;
unsigned long idata Blink_led_val;
unsigned long idata Modified_hdd; //修改后的讀數暫存
unsigned char idata Point_position;
unsigned char idata Press_interval;
unsigned char idata Short_rmb;
unsigned char idata Break_rmb;
bit Key_flag=0;
bit Key_modify_flag=0;
bit Led_blink_flag=0;
bit Speaker_flag=0;
bit Disp_flag=0;
bit Key_en=1;
bit Short_flag=0;
bit Break_flag=0;
unsigned char idata Led[16];
/****** HD7279A 指令 ******/
#define CMD_RESET 0xa4
#define CMD_TEST 0xbf
#define DECODE0 0x80
#define DECODE1 0xc8
#define CMD_READ 0x15
#define UNDECODE 0x90
#define RTL_CYCLE 0xa3
#define RTR_CYCLE 0xa2
#define RTL_UNCYL 0xa1
#define RTR_UNCYL 0xa0
#define ACTCTL 0x98
#define SEGON 0xe0
#define SEGOFF 0xc0
#define BLINKCTL 0x88
//******鍵值定義*******
#define ASK 58
#define RIGHT 59
#define LEFT 61
#define INCREASE 60
#define DECREASE 62
#define ENTER 57
#define Pulse_constant 1
extern void write7279(unsigned char, unsigned char,unsigned char);// 發送一個字節 // 寫入到HD7279
extern unsigned char read7279(unsigned char,unsigned char); // 從HD7279讀出
extern void send_byte(unsigned char,unsigned char);
extern unsigned char receive_byte();
extern void Write1B(unsigned char,unsigned char,bit);
extern unsigned char Read1B(unsigned char,bit);
extern unsigned char ReadSR();
extern unsigned long Read_hdd_new(unsigned char);
extern void Write_hdd_new(unsigned char);
extern void Key_Pro(void);
void waitNms(unsigned char);
void assign_dispdata(unsigned char);
void disp_reading(void);
void write_dispdata(void);
void disappear_contrl(void);
void alarm_chk(void);
extern unsigned char idata Type_temp;
extern union hdd_long {BYTE Hdd_B[4];unsigned long Hdd_L;} Hdd_Str;
/**********************************************************
*名 稱:init_timer2
*功 能:初使化定時計數器2
*說 明:工作方式為16位重裝,遞增計數,與hicj5.c結合時此函數可省略
*調 用:無
*入口參數:無
*返 回 值:無
***********************************************************/
/*void init_timer2(void)
{
TH2 = 0x00;
TL2 = 0x00;
RCAP2H = 0x00;
RCAP2L = 0x00;
T2CON = 0x04;
ET2 = 1;
EA = 1;
}*/
/**********************************************************
*名 稱:timer2_int
*功 能:利用中斷來實現各種延時
*說 明:中斷一次為62.5ms;結合時將此函數轉移到HICJ5.C的TIMER2_INT中
*調 用:無
*入口參數:無
*返 回 值:無
***********************************************************/
/*void timer2_int(void) interrupt 5 using 1
{
TF2=0;
if(Key_flag) //是否有按鍵
{
Idletime_count++;
if(Idletime_count==100) //是否已延時62.5*100次
{
Key_flag=0; // 清除所有標志位
Disp_flag=0;
Led_blink_flag=0;
Key_modify_flag=0;
House_count=0;
Idletime_count=0;
send_byte(CMD_RESET,0); //數碼管全部消隱
cs1=cs2=1;
write7279(DECODE0+0,0x0f,1);
write7279(DECODE0+1,0x0f,1);
write7279(DECODE0+2,0x0f,1);
write7279(DECODE0+3,0x0f,1);
}
}
if(Speaker_flag) //控制SPEAKER鳴200MS
{
Speaker_count++;
if(Speaker_count==3)
{
Speaker_count=0;
Speaker_flag=0;
Speaker=1;
}
}
if(!Key_en) //控制兩個按鍵之間的間隔為300ms
{
Press_interval++;
if(Press_interval==4)
{
Press_interval=0;
Key_en=1;
}
}
} */
void keyboard(void)
{
// send_byte(CMD_RESET,1);
// send_byte(CMD_RESET,0);
// cs1=cs2=1;
if((!Key)&Key_en)
{
Key_value=read7279(CMD_READ,1);
switch(Key_value)
{
/* case(ASK): //查詢鍵只實現循環查徇功能,而不能由此鍵引起修改
Key_flag=1;
Idletime_count=0; //兩次按鍵間的空閑時間計數(由定時器TIME2完成)
if(House_count>=40)
House_count=0; //房屋號計數,值為1-40對應1-40號房屋
House_count++;
assign_dispdata(House_count); //讀出并分配House_count戶的數據
disappear_contrl();
disp_reading(); //顯示讀數及房屋號
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
break;*/
case(ASK):
break;
case(RIGHT): //向右查詢,在些鍵基礎上按ENTER可進行修改
Disp_flag=1; //對于鍵盤,只有RIGHT,LEFT兩個鍵可以引起顯示
Key_flag=1; //
Idletime_count=0;
if(Led_blink_flag)
{
if(Blink_led==1)
Blink_led=128;
else
Blink_led=Blink_led>>1;
write7279(BLINKCTL,~Blink_led,0); // 閃爍位右移一位
}
else
{
if(House_count>=40)
House_count=0;
House_count++; //key press count
assign_dispdata(House_count); //House_count為0~39對應1-40回路
disappear_contrl();
disp_reading(); //顯示讀數
alarm_chk(); //顯示報警及表具類型
}
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
break;
case(LEFT):
Disp_flag=1;
Key_flag=1;
Idletime_count=0;
if(Led_blink_flag)
{
if(Blink_led==128)
Blink_led=1;
else
Blink_led=Blink_led<<1;
write7279(BLINKCTL,~Blink_led,0); // 閃爍位右移一位
}
else
{
if((House_count==1)|(House_count==0))
House_count=41;
House_count--;
assign_dispdata(House_count);
disappear_contrl();
disp_reading(); //顯示讀數
alarm_chk();
}
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
break;
case(ENTER):
if(Disp_flag&!Key_modify_flag&!Short_flag&!Break_flag) //如果此前只有RIGHT及LEFT按鍵
{
Key_flag=1;
Idletime_count=0;
Blink_led=128;
if(!Led_blink_flag)
{
assign_dispdata(House_count);
disp_reading();
write7279(BLINKCTL,~Blink_led,0); //最高們閃爍
Led_blink_flag=1;
}
else
{
write7279(BLINKCTL,0xff,0); //消除閃爍屬性
Led_blink_flag=0;
}
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
}
if(Key_modify_flag) //如果此前按的是UP,DOWN鍵
{
Key_flag=1;
Idletime_count=0;
write_dispdata();
write7279(BLINKCTL,0xff,0); //消除閃爍屬性
Led_blink_flag=0;
Key_modify_flag=0;
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
}
if(Short_flag)
{
Short_flag=0;
Short_rmb&=(~(1<<(House_count-1)%8));
Write1B(Short_rmb,170+(House_count-1)/8,0);
write7279(UNDECODE+6,0x00|0x01,1);
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
}
if(Break_flag)
{
Break_flag=0;
Break_rmb&=(~(1<<(House_count-1)%8));
Write1B(Break_rmb,175+(House_count-1)/8,0);
write7279(UNDECODE+6,0x00|0x01,1);
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
}
break;
case(INCREASE):
if(Led_blink_flag)
{
Key_flag=1;
Idletime_count=0;
Key_modify_flag=1;
switch(Blink_led)
{
case(1): Blink_led_val=0;break;
case(2): Blink_led_val=1;break;
case(4): Blink_led_val=2;break;
case(8): Blink_led_val=3;break;
case(16): Blink_led_val=4;break;
case(32): Blink_led_val=5;break;
case(64): Blink_led_val=6;break;
case(128): Blink_led_val=7;break;
default:break;
}
Led[Point_position]&=0x0f;
if(Led[Blink_led_val]>=9)
Led[Blink_led_val]=0;
else Led[Blink_led_val]++;
disp_reading();
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
}
break;
case(DECREASE):
if(Led_blink_flag)
{
Key_flag=1;
Idletime_count=0;
Key_modify_flag=1;
switch(Blink_led)
{
case(1): Blink_led_val=0;break;
case(2): Blink_led_val=1;break;
case(4): Blink_led_val=2;break;
case(8): Blink_led_val=3;break;
case(16): Blink_led_val=4;break;
case(32): Blink_led_val=5;break;
case(64): Blink_led_val=6;break;
case(128): Blink_led_val=7;break;
default:break;
}
Led[Point_position]&=0x0f;
if(Led[Blink_led_val]==0)
Led[Blink_led_val]=9;
else Led[Blink_led_val]--;
disp_reading();
Speaker=0;
Speaker_flag=1;
Speaker_count=0;
}
break;
default:
break;
}
Key_en=0;
//waitNms(100);
}
}
/**********************************************************
*名 稱:waitNms
*功 能:延時N毫秒
*說 明:i,j需定義為IDATA
*調 用:無
*入口參數:N
*返 回 值:無
***********************************************************/
/*void waitNms(unsigned char data n)
{
unsigned char idata i,j;
for(i=0;i<n;i++)
for (j=0;j<100;j++)
{
_nop_();
_nop_();
_nop_();
_nop_();
_nop_();
}
}*/
/**********************************************************
*名 稱:assign_dispdata
*功 能:讀出并分配要顯示的數據,將戶號及讀數存于LED[i]
*說 明:無
*調 用:Read_hdd_new,Read1B,
*入口參數:House(房屋號)
*返 回 值:無
***********************************************************/
void assign_dispdata(unsigned char data House2)
{
unsigned char idata a,i;
Read_hdd_new(House2); //讀HOUSE回路讀數
Hdd_Str.Hdd_L=Hdd_Str.Hdd_L/Pulse_constant; //除以脈沖常數32=3200
Led[7]= Hdd_Str.Hdd_L/10000000;
Led[6]=(Hdd_Str.Hdd_L%10000000)/1000000;
Led[5]=(Hdd_Str.Hdd_L%1000000 )/100000;
Led[4]=(Hdd_Str.Hdd_L%100000 )/10000;
Led[3]=(Hdd_Str.Hdd_L%10000 )/1000;
Led[2]=(Hdd_Str.Hdd_L%1000 )/100;
Led[1]=(Hdd_Str.Hdd_L%100 )/10;
Led[0]= Hdd_Str.Hdd_L%10;
Led[15]=Read1B(House2*3-1,1); //分配房屋號
a=Read1B(House2*3-2,1);
Led[9]=a/0x10;
Led[8]=a%0x10;
a=Read1B(House2*3-3,1);
Led[11]=a/0x10;
Led[10]=a%0x10;
for(i=8;i<12;i++)
{
if(Led[i]>9)
Led[i]=0x0f;
}
Point_position=Read1B(200+House2-1,0); //小數點位置確定
Point_position=(Point_position>>4)&7;
if(Point_position)
Led[Point_position]|=0x80;
}
/**********************************************************
*名 稱:disappear_contrl
*功 能:控制當最高位為0時將其消隱
*說 明:最低顯示0.00
*調 用:
*入口參數:無
*返 回 值:無
***********************************************************/
void disappear_contrl(void)
{
if (Led[7]==0)
{
Led[7]=0x0f;
if(Led[6]==0)
{
Led[6]=0x0f;
if(Led[5]==0)
{
Led[5]=0x0f;
if(Led[4]==0)
{
Led[4]=0x0f;
if(Led[3]==0)
{
Led[3]=0x0f;
}
}
}
}
}
}
/**********************************************************
*名 稱:disp_reading
*功 能:顯示計量表讀數及戶號
*說 明:最低顯示0.00
*調 用:
*入口參數:無
*返 回 值:無
***********************************************************/
void disp_reading(void)
{
unsigned char idata i;
Led[Point_position]|=0x80; //小數點位置
for(i=0;i<8;i++)
{
write7279(DECODE0+i,Led[i],0); //Hdd
}
for(i=0;i<4;i++)
{
write7279(DECODE0+i,Led[i+8],1); //House Codez
}
}
/**********************************************************
*名 稱:write_dispdata
*功 能:將修改后的讀數寫入存儲器
*說 明:十六進制第5位進位時總是進不上去!?。。。。。。。?!
長整數后加L解決問題
*調 用:
*入口參數:無
*返 回 值:無
***********************************************************/
void write_dispdata(void)
{
Led[Point_position]&=0x0f; //消除小數點位置造成的數值錯誤
Modified_hdd=Led[0]+Led[1]*10+Led[2]*100+Led[3]*1000
+Led[4]*10000L+Led[5]*100000L+Led[6]*1000000L
+Led[7]*10000000L;
Hdd_Str.Hdd_L=Modified_hdd*Pulse_constant; //兩位小數
Write_hdd_new(House_count);
}
/**********************************************************
*名 稱:alarm_chk
*功 能:檢查是否有報警狀態
*說 明:指曾發生過的報警,有報警則置位相應的標志位
*調 用:
*入口參數:無
*返 回 值:無
***********************************************************/
void alarm_chk(void)
{
Short_flag=Break_flag=0;
Short_rmb=Read1B(170+(House_count-1)/8,0);
Break_rmb=Read1B(175+(House_count-1)/8,0);
if(Short_rmb&(1<<(House_count-1)%8))
{
write7279(UNDECODE+6,0x10|0x01,1);
Short_flag=1;
if(Break_rmb&(1<<(House_count-1)%8))
{
write7279(UNDECODE+6,0x30|0x01,1);
Break_flag=1;
}
}
else
{
if(Break_rmb&(1<<(House_count-1)%8))
{
write7279(UNDECODE+6,0x20|0x01,1);
Break_flag=1;
}
else
write7279(UNDECODE+6,0x00|0x01,1);
}
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -