#include "MDSFxx_SFR.h"
#include "XSFR_GLOBAL.h"
#include "Allhex.h"
//********************************************************************************
//								      MEMO
//********************************************************************************
/*-IR remote decode
Head: Low(9ms) + High(4.5ms) 
Stop   : Low(39.8ms)

640us,1.64ms
1 = Low(640us) + High(640us)
0 = Low(640us) + High(1.64ms)

First remote control:
				    Adress 16bits              Adress 16bits
	"1" 	=	0000 0000 1111 1111			1010 0010 0101 1101
	"2"		=	0000 0000 1111 1111         0110 0010 1001 1101
	"3"		=	0000 0000 1111 1111			1110 0010 0001 1101
	"4"		=	0000 0000 1111 1111			0010 0010 1101 1101
	"5"		=	0000 0000 1111 1111			0000 0010 1111 1101	
	"6"		=	0000 0000 1111 1111			1100 0010 0011 1101
	"7"		=	0000 0000 1111 1111	 		1110 0000 0001 1111
	"8"		=	0000 0000 1111 1111			1010 1000 0101 0111
	"9"		=	0000 0000 1111 1111			1001 0000 0110 1111
	"0"		=	0000 0000 1111 1111			1001 1000 0110 0111
	"*"		=	0000 0000 1111 1111			0110 1000 1001 0111
	"#"		=	0000 0000 1111 1111		 	1011 0000 0100 1111
	"ok"	=	0000 0000 1111 1111			0011 1000 1100 0111
	"up"	=	0000 0000 1111 1111			0001 1000 1110 0111
	"down"	=	0000 0000 1111 1111			0100 1010 1011 0101
	"left"	=	0000 0000 1111 1111			0001 0000 1110 1111
	"right"	=	0000 0000 1111 1111			0101 1010 1010 0101
	
*/
//********************************************************************************
//								       RAM
//********************************************************************************
//The variables defined by data are placed in the first 128 bytes (0x00~0x7F) address space
//The variables defined by idata are placed in the (0x00~0xFF) address space
//The variable defined by xdata are placed in the external extended RAM  (generally refers to the external 0xF000~0xF1FF space, the specific space size varies with the MCU , and some MCU do not have external RAM)

//The variable defined by data is the fastest, followed by idata, and xdata is slower than the first two
//Variables that are often used are declared with data/idata; variables that are not commonly used are declared with xdata.

#if (IR_Control == 1)
	xdata	uint16	Ir_data_temp;
	xdata	uint16	Ir_data_buffer;
	xdata 	uint8 	ir_data_bit_counter;
	xdata 	uint16 	key_time = 0;

	#if(IR_decoding_UR_Enable==1)
		xdata	uint16	Capture_High_Header;
		xdata	uint16	Capture_Counter_ur;
		xdata	uint16	Capture_Address_ur;
		xdata	uint8	Cpature_data_read_times;
	#endif
#endif

#define IrDA_PIN P3_3
data bit IrDA_PIN_pre = 0;
data bit IrDA_Trigger = 0;
data bit IrDA_CMD_end = 0;
data bit Power_On = 0;
uint16 IrDA_cnt = 0;
uint8 Power_SW_cnt = 0;
xdata uint16 IrDA_CMD_temp = 0XFFFF;
xdata uint16 IrDA_CMD = 0;

//********************************************************************************
//								  IR_Decode
//********************************************************************************
#if (IR_Control == 1)
	void IRDecode(void){
		idata	uint16  CaptureLow_Level;
		idata	uint16  CaptureHigh_Level;
		idata	uint16  CaptureTotal_Level;
		xdata	uint16	Ir_address;
		
		if(key_time==0){
			SFR_PAGE = 0; 
			GET_HI_BYTE(CaptureHigh_Level) = CAPH_H;
			GET_LO_BYTE(CaptureHigh_Level) = CAPH_L;
			SFR_PAGE = 0; 
			GET_HI_BYTE(CaptureTotal_Level) = CAPT_H;
			GET_LO_BYTE(CaptureTotal_Level) = CAPT_L;
			
			CaptureLow_Level = CaptureTotal_Level-CaptureHigh_Level;
			
		// Decode head
			if(FLAG.IR_Decode_Header==0){
				if(CaptureHigh_Level>Ir_high_head_counter_min-Ir_high_head_counter_error
				&&CaptureHigh_Level<Ir_high_head_counter_max+Ir_high_head_counter_error){
					FLAG.IR_Decode_Header = 1;
					#if(IR_decoding_UR_Enable==1)
						Capture_High_Header = CaptureHigh_Level;
					Cpature_data_read_times = 0;
					#endif
					
					#if(IR_data_format==0)
						bit_check(CaptureLow_Level);
					#endif
					
				}
				else
					IR_Decode_error();
			}
			else{
				if(ir_data_bit_counter<Ir_adress_number+Ir_data_number)//12
					ir_data_bit_counter++;
					
				#if(IR_data_format==0)
					bit_check(CaptureLow_Level);
					if(ir_data_bit_counter==(Ir_adress_number-1)){
				#else
					bit_check(CaptureHigh_Level);
					if(ir_data_bit_counter==(Ir_adress_number)){
				#endif
					Ir_address = Ir_data_temp;
					Ir_data_temp = 0;
					if(Ir_address!=IR_address_value)
						IR_Decode_error();
				}
				#if(IR_data_format==0)
					else if(ir_data_bit_counter==(Ir_adress_number+Ir_data_number-1)){
				#else
					else if(ir_data_bit_counter==(Ir_adress_number+Ir_data_number)){
				#endif
					Ir_data_buffer = Ir_data_temp;
					Ir_data_temp = 0;
					ir_data_bit_counter = 0;
					FLAG.IR_Data_Decode_Finish = 1;
				}
			}
		}
	}
#endif

#if (IR_Control == 1)
	void bit_check(unsigned int Capture_Level_buf){
		#if(IR_decoding_UR_Enable==1)
			Cpature_data_read_times++;
			if(Cpature_data_read_times==Ir_data_number_ur){
				Capture_Counter_ur = Capture_Level_buf;
				P2_7=!P2_7;
			}
		#endif
		
		if((Capture_Level_buf>Ir_0_data_counter-Ir_data_counter_error)&&		//0	
		(Capture_Level_buf<Ir_0_data_counter+Ir_data_counter_error))			
			Ir_data_temp <<= 1;
		
		else if((Capture_Level_buf>Ir_1_data_counter-Ir_data_counter_error)&&	//1
		(Capture_Level_buf<Ir_1_data_counter+Ir_data_counter_error)){ 	
			Ir_data_temp <<= 1;
			Ir_data_temp++;
		}
		else
			IR_Decode_error();
			
		#if(IR_decoding_UR_Enable==1)
			if(Cpature_data_read_times==Ir_adress_number)
				Capture_Address_ur = Ir_data_temp;
		#endif
	}
#endif
//********************************************************************************
//								IR_Decode_Read
//********************************************************************************	
#if (IR_Control==1)
	void IRDecode_Read(void){
		if(FLAG.IR_Data_Decode_Finish==1){
			switch(Ir_data_buffer){
				case IR_DATA_OFF:		RF_Channel = R_OFF;			break;
				case IR_DATA_SPEED1:	RF_Channel = R_1_SPEED;		break;
				case IR_DATA_SPEED2:	RF_Channel = R_2_SPEED;		break;
				case IR_DATA_SPEED3:	RF_Channel = R_3_SPEED;		break;
				case IR_DATA_SPEED4:	RF_Channel = R_4_SPEED;		break;
				case IR_DATA_SPEED5:	RF_Channel = R_5_SPEED;		break;
				case IR_DATA_SMART:		RF_Channel = R_SMART;		break;
				case IR_DATA_1H:		RF_Channel = R_1H;			break;
				case IR_DATA_2H:		RF_Channel = R_2H;			break;
				case IR_DATA_4H:		RF_Channel = R_4H;			break;
				case IR_DATA_6H:		RF_Channel = R_6H;			break;
				case IR_DATA_8H:		RF_Channel = R_8H;			break;
			}
			if(RF_Channel!=R_INIT){					// Execute remote control key
				#if (dIPWM_MODE == 1)
					if(FLAG.Buzzer_SW==0){
						FLAG.Buzzer_SW = 1;
						ipwm_counter = 0;
					}
				#endif
				
				RF_IR_Fun();
				FLAG.IR_Decode_Header = 0;
				key_time = 300;					//delay time
			}
			FLAG.IR_Data_Decode_Finish = 0;
		}
	}
#endif
//********************************************************************************
//								IR_Decode_Error
//********************************************************************************
#if (IR_Control == 1)
	void IR_Decode_error(void){
		FLAG.IR_Decode_Header = 0;
		Ir_data_temp = 0;
		ir_data_bit_counter = 0;
		#if(IR_decoding_UR_Enable==1)
			Cpature_data_read_times = 0;
		#endif
	}
#endif

void IrDA_Check(void)    // count value base on 100us timer
{
	if(IrDA_PIN_pre == 0)
	{
		if(IrDA_PIN == 1)
		{
			IrDA_Trigger = 1;
			IrDA_CMD_end = 0;
		}
	}

	if(IrDA_Trigger == 1) 
	{
		if((IrDA_PIN == 1) && (IrDA_CMD_end == 0))
		{
			IrDA_cnt++;
		}

		if(IrDA_cnt > 50)
		{
			IrDA_CMD_end = 1;
			IrDA_cnt = 0;
			IrDA_Trigger = 0;
//UART_Send_char(0x55);
//UART_Send_int(IrDA_CMD_temp);
			if((IrDA_CMD_temp == POWER_SW) || (IrDA_CMD_temp == SPEED_LV1) || (IrDA_CMD_temp == SPEED_LV2) || (IrDA_CMD_temp == SPEED_LV3) || (IrDA_CMD_temp == SPEED_LV4) || (IrDA_CMD_temp == SPEED_LV5) || (IrDA_CMD_temp == BOOST))
			{
				IrDA_CMD = IrDA_CMD_temp;
			}
			IrDA_CMD_temp = 0xFFFF;
		}

		if(IrDA_PIN == 0)
		{
			if(IrDA_cnt <= 10)
			{
				IrDA_CMD_temp = IrDA_CMD_temp<<1;	
				IrDA_CMD_temp |= 0x0;
			}
			else
			{
				IrDA_CMD_temp = IrDA_CMD_temp<<1;	
				IrDA_CMD_temp |= 0x1;
			}
			IrDA_cnt = 0;
			IrDA_Trigger = 0;
		} 
	}
	IrDA_PIN_pre = IrDA_PIN ;
}

void RemoteSpeedSet(uint16 RemoteSet)
{
	if((RemoteSet == POWER_SW) && (Power_On == 0))
	{
		if(SpeedNum == 0)
		{
			SpeedNum = SpeedNum_pre;
			FLAG.MOTOR_PWM_ENABLE = 1;
			FLAG.MOTOR_OFF_FLAG = 0;
			IrDA_CMD = 0;
			FLAG.Buzzer_SW = 1;
			Buzzer_TIMES = IPWM_TIMES_Init;
			IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
			IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
		}
		else
		{
			FLAG.MOTOR_PWM_ENABLE = 0;
			FLAG.MOTOR_OFF_FLAG = 1;
			#if (SPEED_CONTROL == 1)
				SpeedCmd = 0;
				SpeedNum_temp = 0;    // If it is not clear to 0 and starts immediately after it is turned off, the motor will run at "SpeedCmd = 0;"
			#endif

			#if (CURRENT_CONTROL == 1)
				CurrentCmd = 0;
				CurrentCmdTemp = 0;
			#endif

			SPEED_UI_MACRO(Spd_MinLimit);
			SpeedNum = 0;
			IrDA_CMD = 0;
			FLAG.Buzzer_SW = 1;
			Buzzer_TIMES = IPWM_TIMES_Init;
			IPWM_RUN_TIME = 600;
			IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
		}
		Power_On = 1;
	}      
	else if(RemoteSet == SPEED_LV1)
	{
		#if (CURRENT_CONTROL == 1)
			CurrentCmd = IR_Current_1_VALUE;
		#endif

		SpeedNum = 1;
		SpeedNum_pre = SpeedNum;
		FLAG.MOTOR_PWM_ENABLE = 1;
		FLAG.MOTOR_OFF_FLAG = 0;
		IrDA_CMD = 0;
		FLAG.Buzzer_SW = 1;
		Buzzer_TIMES = IPWM_TIMES_Init;
		IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
		IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
	}
	else if(RemoteSet == SPEED_LV2)
	{
		#if (CURRENT_CONTROL == 1)
			CurrentCmd = IR_Current_2_VALUE;
		#endif

		SpeedNum = 2;
		SpeedNum_pre = SpeedNum;
		FLAG.MOTOR_PWM_ENABLE = 1;
		FLAG.MOTOR_OFF_FLAG = 0;
		IrDA_CMD = 0;
		FLAG.Buzzer_SW = 1;
		Buzzer_TIMES = IPWM_TIMES_Init;
		IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
		IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
	}
	else if(RemoteSet == SPEED_LV3)
	{
		#if (CURRENT_CONTROL == 1)
			CurrentCmd = IR_Current_3_VALUE;
		#endif

		SpeedNum = 3;
		SpeedNum_pre = SpeedNum;
		FLAG.MOTOR_PWM_ENABLE = 1;
		FLAG.MOTOR_OFF_FLAG = 0;
		IrDA_CMD = 0;
		FLAG.Buzzer_SW = 1;
		Buzzer_TIMES = IPWM_TIMES_Init;
		IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
		IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
	}
	else if(RemoteSet == SPEED_LV4)
	{
		#if (CURRENT_CONTROL == 1)
			CurrentCmd = IR_Current_4_VALUE;
		#endif

		SpeedNum = 4;
		SpeedNum_pre = SpeedNum;
		FLAG.MOTOR_PWM_ENABLE = 1;
		FLAG.MOTOR_OFF_FLAG = 0;
		IrDA_CMD = 0;
		FLAG.Buzzer_SW = 1;
		Buzzer_TIMES = IPWM_TIMES_Init;
		IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
		IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
	}
	else if(RemoteSet == SPEED_LV5)
	{
		#if (CURRENT_CONTROL == 1)
			CurrentCmd = IR_Current_5_VALUE;
		#endif

		SpeedNum = 5;
		SpeedNum_pre = SpeedNum;
		FLAG.MOTOR_PWM_ENABLE = 1;
		FLAG.MOTOR_OFF_FLAG = 0;
		IrDA_CMD = 0;
		FLAG.Buzzer_SW = 1;
		Buzzer_TIMES = IPWM_TIMES_Init;
		IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
		IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
	}
	else if(RemoteSet==BOOST)
	{
		#if (CURRENT_CONTROL == 1)
			CurrentCmd = IR_Current_5_VALUE;
		#endif

		SpeedNum = 6;
		SpeedNum_pre = SpeedNum;
		FLAG.MOTOR_PWM_ENABLE = 1;
		FLAG.MOTOR_OFF_FLAG = 0;
		IrDA_CMD = 0;
		FLAG.Buzzer_SW = 1;
		Buzzer_TIMES = IPWM_TIMES_Init;
		IPWM_RUN_TIME = IPWM_RUN_TIME_Init;
		IPWM_STOP_TIME = IPWM_STOP_TIME_Init;
	}
}

