1/22/2009

AT89S5X easy demo

公司同事功能上的測試
需要另一個mcu做簡單的功能
剛好就用51來做

按一下key
傳送clk 和 data
功能簡單
所以我就直接按一下key
傳送key計數值
同時顯示在lcd上
/*
Progarm: key + send 8bit clk & data + lcm Demo
Arranged by: Brian @ Taiwan
Last modified date:
2009/01/22
*/
#include "AT89X52.H"

// for key scan
#define Key_port P3
#define Mark_Key 0x01 //p3_0
#define DebounceCnt 20
#define b_Debounce 0x01
#define b_Pressed 0x02
#define b_Release 0x04

// for lcm
#define LCM_En P1_0
#define LCM_Rs P1_1
#define LCM_Rw P1_2
#define LCM_Data_port P2

// for send clk data
#define Send_Port P3
#define SE_Clk 0x40 //p3_6
#define SE_Da 0x80 //p3_7

void sys_init(void); //system_init function

char GetKey(void); //get press key number
unsigned char Get_KeyStatus(void); //get press key or release key
void Key_Loop(void); //scan key user polling

void LCM_Init(void); //lcm initial
void LCM_Com_Writer(void); //lcm write command
void LCM_Show_Data(unsigned char addr,unsigned char *sd); //lcm show data

void msDelay(unsigned int MaxDelay);//delay function

void Spi_Tx_Loop(unsigned char tx_data);//send data & clk

char Key_flag; //0x01 = Debounce 0x02 =press 0x04= release
char R_DebounceCnt; //KEY DEBOUNCE COUNG
char R_KeyBuffer; //KEY BUFFER SAVE INPUT KEY
char First_key; //memory first pressed key
char Port_buffer; // memory port status

unsigned int DelayCNT;
unsigned int TimeCNT;

void main(void)
{
char PressKey,KeyStatus;
unsigned char SData1[]="Key Count =";
unsigned char SData2[]="Brian @Taiwan";
unsigned char SData3[3];
unsigned char Key_count=0;
unsigned char num_temp;

sys_init();
msDelay(10);

LCM_Init();
msDelay(10);

LCM_Show_Data(0x80,SData1);
LCM_Show_Data(0xC0,SData2);

while(1)
{
KeyStatus = Get_KeyStatus();

if(KeyStatus==0x04) //release key
{
PressKey=GetKey();
switch(PressKey)
{
case 1:
SData3[0]=Key_count/100+0x30;
num_temp = Key_count%100;
SData3[1]=num_temp/10+0x30;
num_temp = num_temp%10;
SData3[2]=num_temp%10+0x30;
Spi_Tx_Loop(Key_count);
LCM_Show_Data(0x8D,SData3);
Key_count++;
break;
}
}

Key_Loop();
}

}
//================================================================================
// Description: Power on system initial
// Function: sys_init()
// Syntax: void sys_init(void)
// Input Paramter: none
// Return: none
// Note:
//=================================================================================
void sys_init(void)
{
IE = 0x82; //USER INTERRUPT TIME0
TMOD = 0x02; //SET TIME 0 MODE
TH0 = 256-200; //SET RELOAD VALUE
TL0 = 256-200; // FAST VALUE
TimeCNT=0;
TR0=1; //time int enabled

Key_flag = 0;
R_DebounceCnt = 0;
R_KeyBuffer = 0;
First_key = 0;
Port_buffer=0;

Key_port=0x00;
P1=0x00;
P2=0x00;
P3=0xC0;

}
//================================================================================
// Description: Delay time
// Function: msDelay(unsigned int MaxDelay)
// Syntax: void msDelay(unsigned int MaxDelay)
// Input Paramter: unsigned int MaxDelay
// Return: none
// Note:
//=================================================================================
void msDelay(unsigned int MaxDelay)
{
DelayCNT = 0x0000;
while(DelayCNT < MaxDelay) {}
}
//================================================================================
// Description: interrept 1
// Function: note
// Syntax: note
// Input Paramter: note
// Return: none
// Note: 1000 = 0.1S, 100=0.01S ,10=0.001S
//=================================================================================
void Time0_int(void)interrupt 1
{
TimeCNT++;
if(TimeCNT>=10)
{
DelayCNT++;
TimeCNT=0;
}
}
//================================================================================
// Description: Key Scan Service loop
// Function: Key_Loop(void)
// Syntax: void Key_Loop(void)
// Input Paramter: note
// Return: none
// Note:
//=================================================================================
void Key_Loop(void)
{
char Key;
char Key_chang;

if(Key_flag & b_Debounce)
{
R_DebounceCnt--;
if(R_DebounceCnt != 0) //debounce
return;
}

Key_chang = Key_port & Mark_Key; //read input key port

if(Key_chang != Port_buffer)
{
Port_buffer = Key_port & Mark_Key;
First_key = Port_buffer & Mark_Key;
Key_flag = b_Debounce;
R_DebounceCnt = DebounceCnt;
return;
}

if(Key_flag & b_Debounce)
{
Key = Key_port & Mark_Key;

if(Key & First_key)
{
Key_flag = b_Pressed;
R_KeyBuffer = Key;
}
else
{
Key_flag = b_Release;
}
}
else
{
Key_flag=0;
}

}
//================================================================================
// Description: read key status
// Function: Get_KeyStatus(void)
// Syntax: unsigned char Get_KeyStatus(void)
// Input Paramter: note
// Return: unsigned char
// Note: 01 = debounce 02=press key 04 =release
//=================================================================================
unsigned char Get_KeyStatus(void)
{
return Key_flag;
}
//================================================================================
// Description: read press/release key code
// Function: GetKey(void)
// Syntax: char GetKey(void)
// Input Paramter: note
// Return: char
// Note:
//=================================================================================
char GetKey(void)
{
return R_KeyBuffer;
}
//================================================================================
// Description: LCM Initial
// Function: LCM_Init(void)
// Syntax: void LCM_Init(void)
// Input Paramter: note
// Return: none
// Note:
//=================================================================================
void LCM_Init(void)
{
LCM_Data_port = 0x38;
LCM_Com_Writer();
/*
function set 001(dl)(n)(f)xx
(dl=1 data=8bit dl=0 4bit)
(n=1 double line n=0 one line)
(f=0=5*7dot f=1 5*10 dot)
*/
LCM_Data_port = 0x38;
LCM_Com_Writer();

LCM_Data_port = 0x06;//enter mode 01(ld)(s) ld=0 addr++ ld=1 addr-- s=1 addr shift
LCM_Com_Writer();

LCM_Data_port = 0x01;//clear lcm show data
LCM_Com_Writer();

// lcd on/off 1(d)(c)(b) 1=lcd on 0=lcd off d=lcd c=cursor b=bline
LCM_Data_port = 0x0C;
LCM_Com_Writer();
}
//================================================================================
// Description: Lcm command write
// Function: LCM_Com_Writer(void)
// Syntax: void LCM_Com_Writer(void)
// Input Paramter: note
// Return: none
// Note:
//=================================================================================
void LCM_Com_Writer(void)
{
LCM_Rs=0;
LCM_Rw=0;
LCM_En=1;
msDelay(1);
LCM_En=0;
msDelay(1);
}
//================================================================================
// Description: LCM data write
// Function: LCM_Data_Writer(void)
// Syntax: void LCM_Data_Writer(void)
// Input Paramter: note
// Return: none
// Note:
//=================================================================================
void LCM_Data_Writer(void)
{
LCM_Rs=1;
LCM_Rw=0;
LCM_En=1;
msDelay(1);
LCM_En=0;
LCM_Rs=0;
msDelay(1);
}
//================================================================================
// Description: LCM Show Data
// Function: LCM_Show_Data(unsigned char addr,unsigned char *sd)
// Syntax: void LCM_Show_Data(unsigned char addr,unsigned char *sd)
// Input Paramter: unsigned char addr,unsigned char *sd
// Return: none
// Note:if addr ==0 define addr=0x80
//=================================================================================
void LCM_Show_Data(unsigned char addr,unsigned char *sd)
{
if(addr!=0)
{
LCM_Data_port = addr;
LCM_Com_Writer();
}

while(*sd!=0)
{
LCM_Data_port = *sd++;
LCM_Data_Writer();
}
}
//================================================================================
// Description: Create clk and send data
// Function: Spi_Tx_Loop(unsigned char tx_data)
// Syntax: void Spi_Tx_Loop(unsigned char tx_data)
// Input Paramter: unsigned char tx_data
// Return: none
// Note:
//clk ___ _ _ _ _ _ _ _ __________
// |__| |_| |_| |_| |_| |_| |_| |__|
//data ____ __________________________ ___________
// |_|__________________________|_|
//=================================================================================
void Spi_Tx_Loop(unsigned char tx_data)
{
unsigned char Port_status;
unsigned char temp;
int i;

Port_status = Send_Port;
Port_status &= ~SE_Clk;
Send_Port = Port_status;
msDelay(3);
Port_status = Send_Port;
Port_status &= ~SE_Da;
Send_Port = Port_status;
msDelay(3);

for(i=0;i<8;i++)
{
Port_status = Send_Port;
Port_status |= SE_Clk;
Send_Port = Port_status;

temp = tx_data & SE_Da;
Port_status = Send_Port;

if(temp)
Port_status |= SE_Da;
else
Port_status &= ~SE_Da;

Send_Port = Port_status;

tx_data<<=1;

msDelay(1);

Port_status = Send_Port;
Port_status &= ~SE_Clk;
Send_Port = Port_status;
msDelay(1);
}

Port_status = Send_Port;
Port_status &= ~SE_Da;
Send_Port = Port_status;
msDelay(3);
Port_status = Send_Port;
Port_status |= SE_Da;
Send_Port = Port_status;
msDelay(3);
Port_status = Send_Port;
Port_status |= SE_Clk;
Send_Port = Port_status;
}

沒有留言: