⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 jianpan._c

📁 实现3*3 键盘的控制。从而实现用键盘来对单片机进行控制。
💻 _C
字号:
//ICC-AVR application builder : 2004-4-28 13:15:44
// Target : M16
// Crystal: 8.0000Mhz
//串口通讯及控制命令格式(协议)如下:
// 命令的传输长度采用变长数据,第一个字节为指令,其余为可选参数
//----------------------------------------------------------------------------
//键盘特殊功能键定义如下:
//
//键码		功能
//-----------------------------------
//  F		ENTER(transmit the data to the master)
//  C		BACKSPACE
//  A		speedup
//  B		slowdown
//  E		go into the edit mode
//
#include <iom16v.h>
#include <macros.h>

#define uchar unsigned char
#define uint unsigned int
#define ulong unsigned long

#define ROUTE_TASK_NUM_LIMIT 30 
#define SET_ROUTE ( PIND & BIT(PD3) )	//键盘设定路径的选通引脚(来自Mega16)

//功能键定义
#define CANCEL	12	//C
#define ENTER		15	//F
#define EDIT		14      //e
#define speedup		10	//A
#define slowdown	11	//B
#define DEBUG	13	//D

//模式1参数个数Model1_flag
#define Model1_flag  8
//模式2参数个数Model2_flag
#define Model2_flag  4

//状态标志
#define START_COMMAND	0xF0
#define TRANSMIT 0x02
#define SAVE	 0x00
#define SETTING  0x01
#define FREE	 0X71	
#define STATE	 0X0f

#define PAR1    0x01
#define PAR2	0x02
#define PAR3	0x03
#define PAR4	0x04
#define PAR5	0x05
#define PAR6	0x06
#define PAR7	0x07
#define PAR8	0x08
#define PAR9	0x09
#define PAR10	0x0a
const uchar KeySet[] =
{
 1, 2, 3, 4,
 5, 6, 7, 8,
 9, 0, 10,11,
 12,13,14,15
};

uchar flag = 0;			 /* 状态标志变量 */
const uchar num_table[] = { 0x3f,0x06, 0x5b, 0x4f, 0x66, 0x6d, 0x7d, 0x07, 0x7f, 0x6f, 0x40 };
//自定义定时器
uint DelayCounter = 0;
uint SysCounter = 0;
//
uchar trans_buf[20];
uchar receive_buf[20];

//键盘控制行为变量
uint numL= 0;		//6位十进制
uchar numH=0;		//显示高2位

uchar mode = 0x71;	//显示'F'
uchar NumBitL=0;	//显示高2位
uchar NumBitH=0;         //6位十进制  显示低6位
uchar Cursor = 0;
uchar CursorDir = 0;
 
void delay( uint time );
//void master( uchar command, uchar* buf, uchar startP, uchar dataLen );
uchar scan_key( void );
void display( void );


void delay( uint time )
{
	for( DelayCounter = 0; DelayCounter < time; ) { WDR(); }
}

void send( uchar index, uchar num )
{
	PORTB = ~BIT( index ); 
	if( index < 7 ) { PORTA = num_table[num]; }
	else { PORTA = num; }
	delay( 1 );
}

void send_char( uchar index, uchar ch )
{
	PORTB = ~BIT( index );
	PORTA = ch;
	delay(1);
}

//键盘扫描
uchar scan_key( void )
{
 	uchar index;
	 if(!(PINC & 0x80))
 	 index = 0;
 	else if(!(PINC & 0x40))
 	 index = 1;
 	else if(!(PINC & 0x20))
 	 index = 2;
 	else if(!(PINC & 0x10))
 	 index = 3;
 	PORTC = 0x0F;	   //切换
 	DDRC = 0xF0;
 	if( !(PINC & 0x08) )
 	 index += 0;
 	else if( !(PINC & 0x04) )
 	 index += 4;
 	else if( !(PINC & 0x02) )
 	 index += 8;
 	else if( !(PINC & 0x01) )
 	 index += 12;
	 PORTC = 0xF0;	   //切换
 	DDRC = 0x0F;
 	return index;
}
//串口传送数据
void transmit(void)
{ 
	uchar i;
	uchar tmp;
 	for(i=0;i<10;i++)
 	{
 	send(7,7);
 	delay(2);
	}
 	for(i=0;i<20;i++)
 	{
 		while(!(UCSRA&BIT(UDRE)));     
 		UDR=trans_buf[i];
 		delay(1);
 	}	 
}
 void port_init(void)
{
 PORTA = 0x00;
 DDRA  = 0xFF;
 PORTB = 0xFF;
 DDRB  = 0xFF;
 PORTC = 0xf0; //m103 output only
 DDRC  = 0x0f;
 PORTD = 0xFF;
 DDRD  = 0xF0;
}

//TIMER0 initialisation - prescale:64
// WGM: Normal
// desired value: 1mSec
// actual value:  1.000mSec (0.0%)
void timer0_init(void)
{
 TCCR0 = 0x00; //stop
 TCNT0 = 0x83; //set count
 OCR0  = 0x7D;  //set compare
 TCCR0 = 0x03; //start timer
}

#pragma interrupt_handler timer0_ovf_isr:10
void timer0_ovf_isr(void)
{
	TCNT0 = 0x83; //reload counter value
	DelayCounter ++;
	SysCounter ++;
}
//


//UART0 initialisation
// desired baud rate: 9600
// actual: baud rate:9615 (0.2%)
// char size: 8 bit
// parity: Disabled
void uart0_init(void)
{
 UCSRB = 0x00; //disable while setting baud rate
 UCSRA = 0x00;
 UCSRC = 0x86;
 UBRRL = 51; //set baud rate lo
 UBRRH = 0x00; //set baud rate hi
 UCSRB = 0x18;
}

//Watchdog initialisation
// prescale: 32K cycles
void watchdog_init(void)
{
 WDR(); //this prevents a timout on enabling
 WDTCR = 0x0A; //WATCHDOG ENABLED - dont forget to issue WDRs
}

//call this routine to initialise all peripherals
void init_devices(void)
{
 //stop errant interrupts until set up
 CLI(); //disable all interrupts
 port_init();
 timer0_init(); 
 uart0_init();
 //watchdog_init();
 
 MCUCR = 0x00;
 GICR  = 0x00;
 TIMSK = 0x01; //timer interrupt sources
 SEI(); //re-enable interrupts
 //all peripherals are now initialised
}
//显示
void display( void )
{
	uint tmp;
	send( 7, mode );
	tmp=numL;
	switch( NumBitL )
	{
		case 5: send( 0, tmp % 10 );
			tmp=tmp/10;
			send( 1, tmp% 10 );
			tmp=tmp/10;
    			send( 2, tmp % 10 );
    			tmp=tmp/10;
    			send( 3, tmp % 10 );
    			tmp=tmp/10;
    			send( 4, tmp % 10 );
    			delay(1);
    			break;
		case 4:send( 0, tmp % 10 );
			tmp=tmp/10;
			send( 1, tmp% 10 );
			tmp/=10;
    			send( 2, tmp % 10 );
    			tmp/=10;
    			send( 3, tmp % 10 );
    			delay(1);
    			break;
		case 3: send( 0, numL % 10 );
			tmp=numL/10;
			send( 1, tmp% 10 );
			tmp/=10;
    			send( 2, tmp % 10 );
    			delay(1);
    			break;		
		case 2: send( 0, numL% 10 );
    			send( 1, numL / 10 % 10 );
    			delay(2);
    			break;
    case 1: send( 0, numL % 10 );
    			delay(3);
    			break;
    default: delay(3); 
    			break;
	}
	
	switch(NumBitH)
	{
			case 2: send( 5, numH% 10 );
    			send( 6, numH / 10 % 10 );
    			delay(2);
    			break;
    	case 1: send(5,numH%10);
    			delay(2);
    			break;
    	default: delay(3); 
    			break;
   }
}

uchar num_bit( uint Val )
{
	uchar bit;
	if(Val>=10000) 		{ bit = 5; }
	else if(Val>=1000) 	{ bit = 4; }
	else if(Val>=100 )	{ bit = 3; }
	else if(Val>=10 )	{ bit = 2; }
	else if( Val )		{ bit = 1; }
	else { bit = 1; }
	return ( bit );
}
//
void init_transbuf(void)
{
	uchar tmp;
	for(tmp=0;tmp<20;tmp++)
	 trans_buf[tmp]=0xff;
	}
//
void edit(void)
{
	uchar flag=STATE;
	uchar i;
	init_transbuf();
	numL=0;
	while(flag!=0xff)
	{
	if( !(PIND&BIT(PD2)) )	// 检测按键状态
	{ 
		display();					//延时
		display();					//延时
		if( !(PIND & BIT(PD2)) )	//再次检测按键状态
	  	{
			uchar KeyIndex = scan_key();	// 读取扫描序号
			while( !(PIND & BIT(PD2)) ) { WDR(); display(); };	//等待按键松开
			for( i = 0; i < 5; i ++ ) { display(); }		//延时
			//backspace
			if((KeySet[KeyIndex]==1|(KeySet[KeyIndex]==2))&&(flag==STATE))
			{
			 trans_buf[0]=KeySet[KeyIndex];
			 flag=1;
			 numH=10*KeySet[KeyIndex]+flag;
			 NumBitH=num_bit(numH);
			}
			else if(KeySet[KeyIndex]==3&&(flag==STATE))
			{
			 trans_buf[0]=KeySet[KeyIndex];
			 transmit();
			 flag=0xff;
			}
			else if((flag>=PAR1)&&(flag<=PAR7)&&( KeySet[KeyIndex]!=ENTER)&&( KeySet[KeyIndex]!=CANCEL))
			{
			 numL=10*numL+KeySet[KeyIndex];
			 NumBitL=num_bit(numL);
			}
			else if(KeySet[KeyIndex]==CANCEL)
			{
			 numL = numL/10;
			 NumBitL = num_bit(numL);
			}
			else if(KeySet[KeyIndex]==ENTER)
			{
			 trans_buf[flag]=numL;
			 flag++;
			 numH++;
			 numL=0;
			 NumBitL=0;
			 if ((flag==Model1_flag)&&(numH/10==1))//模式1参数个数Model1_flag
			 {
			  flag=0xff;
			  transmit();
			  numH=0;
			  NumBitH=0;
			 }
			 else if ((flag==Model2_flag)&&(numH/10==2))//模式2参数个数Model2_flag
			 {
			  flag=0xff;
			  transmit();
			  numH=0;
			  NumBitH=0;
			 }
			}
			else if(((KeySet[KeyIndex]!=1)|(KeySet[KeyIndex]!=2)|(KeySet[KeyIndex]!=3))&&(flag==STATE)) {edit();}
			
		}
	}
	display();
	}
       mode=FREE;
}

void reset( void )
{
	for(DelayCounter = 0; DelayCounter < 500;)
	{
		PORTA = 0xFF;
		PORTB <<= BIT(0);
		WDR();
	}
	SysCounter = 0;
	DelayCounter=0;
	Cursor = 0;
	CursorDir = 0;
	//p_speed=speed_table[0];
}
//
void main(void)
{
	uchar i;
	init_devices();
	reset();
	send(7,0x79);
	while( 1 )
	{
		mode=FREE;	
		WDR();
		if( !(PIND & BIT(PD2)) )	// 检测按键状态
		{ 
			display();					//延时
			display();					//延时
			if( !(PIND & BIT(PD2)) )	//再次检测按键状态
		  	{
				uchar KeyIndex = scan_key();	// 读取扫描序号
				while( !(PIND & BIT(PD2)) ) { WDR(); display(); };	//等待按键松开
				for( i = 0; i < 5; i ++ ) { display(); }		//延时
				//按下编辑键
				if(KeySet[KeyIndex]==EDIT)
				{
					mode=0x79;    //''E'
					edit();
				}
				else if(KeySet[KeyIndex]==ENTER)	    
				{
					transmit();
				}
			}
		}
		else
		{
			if( SysCounter > 500 )
			{
				SysCounter = 0;	
				if( CursorDir == 0 )
				{
					if( ++Cursor == 7 ) { CursorDir = 1; }
				}
				else if( CursorDir == 1 )
				{
					if( --Cursor == 0 )	{ CursorDir = 0; }
				}
			}
			PORTA = 0x40;	//显示'_'
			PORTB = 0xFF;
			PORTB &= ~BIT( Cursor );
			delay(1);
		}
	}
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -