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

📄 main.c

📁 超声波的哦
💻 C
字号:

#define PI 3.1415926535
/******************陀螺仪相关*************************/
float   theta         = 0.0;        // 校正后的陀螺仪角度
float   theta1        = 0.0;        // 校正前的陀螺仪角度
float   Zero          = 0.0;        // 陀螺仪的相对零值
const float	Adjust_L = 360 / 358.4;	// 左转校正值
const float	Adjust_R = 360 / 360;	// 右转校正值

/******************PID控制相关*************************/
fp32   adjust             = 0;		// 调整量
fp32   erro_l_r_d         = 0;
fp32   erro_l_r_d_last    = 0;
fp32   erro_l_r           = 0;
fp32   erro_l_r_last      = 0;
fp32   erro_l_r_last_last = 0;
INT32S LeftMotorSpeed     = 0;		// 当前左轮应设速度
INT32S RightMotorSpeed    = 0;		// 当前右轮应设速度
INT32S MaxSpeed    = 7500;
INT32S MinSpeed    = 500;//500;

/******************各目标角度**************************/
float TargetAngle1 = -27;			// 起始目标角度	
float TargetAngle2 = -180;  		// 到位目标角度

float firstAngle  = -25.5;//-26.5;	// 方案 0,1,2 的第一个角度
float secondAngle = -58;	// 方案 0 的第二个角度
   
/***************************************************************************
***复位PID控制的全局变量***
****************************************************************************/
void ClearData(void)
{
   adjust             = 0;	
   erro_l_r_d         = 0;
   erro_l_r_d_last    = 0;
   erro_l_r           = 0;
   erro_l_r_last      = 0;
   erro_l_r_last_last = 0;
   RightMotorSpeed    = 0;		
   LeftMotorSpeed     = 0;
}
	
/*********************************************************************
***小车右转弯***
**********************************************************************/
void TurnToRight(int32 time, float angle)
{
	float  Angle = 0.0;
	int32 CurrentTime    = 0;
	int32 timedifference = 0;
	
	ClearData();
	
	Angle = theta - angle;
	if (Angle < -180)
	{
		Angle += 360; 
	}
	Angle = fabs(Angle) ;//* 0.5;
	
	CurrentTime = nowtime;
		
	while (1)	    
	{	
		timedifference = nowtime - CurrentTime;
		
		if(timedifference >= time) // 设置到位的时间
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		erro_l_r = theta - angle;
		
		if (erro_l_r < -180)
		{
			erro_l_r += 360;
		}
		
		if (erro_l_r > 25)//30
		{
			Epos_SetSpeed(&eposL, MaxSpeed*0.27);//0.4
			Epos_SetSpeed(&eposR, 0);
		}

		else if (erro_l_r <= 1.0)	// 1.0  到要转过的角度则停止转动
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		else						// 往右转不够
		{
			LeftMotorSpeed = MaxSpeed * 0.25 * erro_l_r / 25;//30;//MaxSpeed * 0.4 * erro_l_r / 30;
			
			if (LeftMotorSpeed > MaxSpeed * 0.25)//MaxSpeed*0.4)
			{
				LeftMotorSpeed = MaxSpeed * 0.25;//MaxSpeed*0.4;
			}
			else if (LeftMotorSpeed < MinSpeed*0.1)
			{
				LeftMotorSpeed = MinSpeed*0.1;
			}
	
			Epos_SetSpeed(&eposL, LeftMotorSpeed);
			Epos_SetSpeed(&eposR, 0);
		}
		
		erro_l_r_last = erro_l_r;
		OSTimeDly(1);	
	}
}

/*********************************************************************
***小车左转弯***
**********************************************************************/
void TurnToLeft(int32 time, float angle)
{
	float  Angle = 0.0;
	int32 CurrentTime    = 0;
	int32 timedifference = 0;
	
	ClearData();
	Angle = -(theta - angle);
	if (Angle < -180)
	{
		Angle += 360; 
	}
	Angle = fabs(Angle) ;
	
	CurrentTime = nowtime;
		
	while (1)	    
	{	
		timedifference = nowtime - CurrentTime;
		
		if(timedifference >= time) // 设置到位的时间
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		erro_l_r = -(theta - angle);
		
		if (erro_l_r <= -180)
		{
			erro_l_r += 360;
		}
		
		if (erro_l_r > 25)
		{
			Epos_SetSpeed(&eposL, -MaxSpeed*0.27);
			Epos_SetSpeed(&eposR, 0);
		}
		
		else if (erro_l_r <= 1.0)	// 到要转过的角度则停止转动
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		else						// 往右转不够
		{
			LeftMotorSpeed = MaxSpeed * 0.25 * erro_l_r / 25;
			
			if (LeftMotorSpeed > MaxSpeed*0.25)
			{
				LeftMotorSpeed = MaxSpeed*0.25;
			}
			else if (LeftMotorSpeed < MinSpeed*0.1)
			{
				LeftMotorSpeed = MinSpeed*0.1;
			}
			{
				Epos_SetSpeed(&eposL, -LeftMotorSpeed);
				Epos_SetSpeed(&eposR, 0);
			}
		}
		
		erro_l_r_last = erro_l_r;
		OSTimeDly(1);	
	}
}

/*********************************************************************
***小车去取对方白块时的左转弯:左轮不动,右轮正转***
**********************************************************************/
void TurnToLeft1(int32 time, float angle)
{
	float  Angle = 0.0;
	int32 CurrentTime    = 0;
	int32 timedifference = 0;
	ClearData();
	Angle = -(theta - angle);
	if (Angle < -180)
	{
		Angle += 360; 
	}
	Angle = fabs(Angle) ;//* 0.5;
	
	CurrentTime = nowtime;
		
	while (1)	    
	{	
		timedifference = nowtime - CurrentTime;
		
		if(timedifference >= time) // 设置到位的时间
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		erro_l_r = -(theta - angle);
		
		if (erro_l_r <= -180)
		{
			erro_l_r += 360;
		}
		
		if (erro_l_r > 25)
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, -MaxSpeed*0.27);
		}
		
		else if (erro_l_r <= 1.0)	// 到要转过的角度则停止转动
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		else						// 往右转不够
		{
			LeftMotorSpeed = MaxSpeed * 0.25 * erro_l_r / 25;
			
			if (LeftMotorSpeed > MaxSpeed*0.25)
			{
				LeftMotorSpeed = MaxSpeed*0.25;
			}
			else if (LeftMotorSpeed < MinSpeed*0.1)
			{
				LeftMotorSpeed = MinSpeed*0.1;
			}
			{
				Epos_SetSpeed(&eposL, 0);
				Epos_SetSpeed(&eposR, -LeftMotorSpeed);
			}
		}
		
		erro_l_r_last = erro_l_r;
		OSTimeDly(1);	
	}
}

/*********************************************************************
***小车差速原地转180度***
**********************************************************************/
void TurnToBack(int32 time)
{
	float  Angle = 0.0;
	int32 CurrentTime    = 0;
	int32 timedifference = 0;
	int8  turnflag		 = 0;
	ClearData();
	Angle =-180;
	if (theta >= -180 && theta <0)
	{
		turnflag = 1;
	}
	else
	{
		turnflag = -1;
	}
	CurrentTime = nowtime;
		
	while (1)	    
	{	
		timedifference = nowtime - CurrentTime;
		
		if(timedifference >= time) // 设置到位的时间
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		erro_l_r = fabs(theta - Angle);
		
		if (erro_l_r > 30)
		{
			Epos_SetSpeed(&eposL, turnflag*MaxSpeed*0.125);
			Epos_SetSpeed(&eposR, turnflag*MaxSpeed*0.125);
		}
		
		else if (erro_l_r <= 1.0)	// 到要转过的角度则停止转动
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
	
		else					
		{
			LeftMotorSpeed = MaxSpeed * 0.125 * erro_l_r / 30;
			
			if (LeftMotorSpeed > MaxSpeed*0.125)
			{
				LeftMotorSpeed = MaxSpeed*0.125;
			}
			else if (LeftMotorSpeed < MinSpeed*0.1)
			{
				LeftMotorSpeed = MinSpeed*0.1;
			}
			
			Epos_SetSpeed(&eposL, turnflag*LeftMotorSpeed);
			Epos_SetSpeed(&eposR, turnflag*LeftMotorSpeed);
			
		}
		
		erro_l_r_last = erro_l_r;
		OSTimeDly(1);	
	}	
	
}
/*********************************************************************
***小车后退***
**********************************************************************/	
void BackCar(int time)
{
	uint32 CurrentTime = 0;
	uint32 timedifference =0;
		
	CurrentTime = nowtime;
	while (1)		
	{
		timedifference = nowtime - CurrentTime;
		
		if(timedifference >= time) // 设置到位的时间
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		Epos_SetSpeed(&eposL,-MaxSpeed*0.36);
		Epos_SetSpeed(&eposR,MaxSpeed*0.36);
	}
	Epos_SetSpeed(&eposL, 0);
	Epos_SetSpeed(&eposR, 0);
}

/*********************************************************************
***小车走直线***
**********************************************************************/
void GoStraight(int32 time1, float angle1)
{
	fp32  Ud 	          = 0;
	fp32  Ud_last         = 0;
	uint8 coefficient     = 1;
	int32 CurrentTime1    = 0;
	int32 timedifference1 = 0;
	uint8 temp            = 0;
	uint8 flag_adjust	  = 0;
	ClearData();
	
	CurrentTime1 = nowtime;

	while (1)		
	{
		timedifference1 = nowtime - CurrentTime1;
			
		if (timedifference1 >= time1) // 设置到位的时间
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		temp = gpio_get(SWITCH_Arrive);
		
		if (temp == 0)				  // 检测到限位开关立即停
		{
			Epos_SetSpeed(&eposL, 0);
			Epos_SetSpeed(&eposR, 0);
			
			break;
		}
		
		erro_l_r_last_last = erro_l_r_last;
		erro_l_r_last      = erro_l_r;
		erro_l_r           = theta - angle1;
		
		// 修正erro_l_r
		if (erro_l_r < -180)
		{
			erro_l_r += 360;
		}
		
		erro_l_r_d_last    = erro_l_r_d;
		erro_l_r_d         = erro_l_r - erro_l_r_last;
			
		Ud = 0.5 * Ud_last + 10 * 0.5 * erro_l_r_d;
		if (RightMotorSpeed >= MaxSpeed || LeftMotorSpeed >= MaxSpeed)
		{
			if(erro_l_r >= 0)
				coefficient = 0;
			else
				coefficient = 1;
		}	
		else if (RightMotorSpeed <= MinSpeed || LeftMotorSpeed <= MinSpeed)
		{
			if(erro_l_r <= 0)
				coefficient = 0;
			else
				coefficient = 1;
		}	
		else
		{
			coefficient = 1;
		}
			
		if (erro_l_r * erro_l_r_d > 0 || erro_l_r_d == 0)
		{
			adjust += MaxSpeed * 0.018 * (erro_l_r - erro_l_r_last)+ (Ud - Ud_last); 
		}
		else
		{
			adjust = adjust;
		}
	
		Ud_last = Ud;
		
		//最后1.3秒到0.5秒减速
		if(timedifference1 < (time1 - 120) && timedifference1 >= (time1-130))
		{
			if (flag_adjust == 0)
			{
				flag_adjust = 1;
			}
			Epos_SetSpeed(&eposL,  (MaxSpeed + adjust)*0.922);//
			Epos_SetSpeed(&eposR, -(MaxSpeed - adjust)*0.937);//
			continue;
		}
		else if(timedifference1 < (time1 - 110) && timedifference1 >= (time1-120))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed + adjust)*0.844);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.859);//
			continue;
		}
		else if(timedifference1 < (time1 - 100) && timedifference1 >= (time1-110))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.766);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.781);//
			continue;
		}
		else if(timedifference1 < (time1 - 90) && timedifference1 >= (time1-100))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.688);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.703);//
			continue;
		}
		else if(timedifference1 < (time1 - 80) && timedifference1 >= (time1-90))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.61);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.625);//
			continue;
		}
		else if(timedifference1 < (time1 - 70) && timedifference1 >= (time1-80))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.532);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.547);//
			continue;
		}
		else if(timedifference1 < (time1 - 60) && timedifference1 >= (time1-70))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.454);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.469);//
			continue;
		}
		else if(timedifference1 < (time1 - 50) && timedifference1 >= (time1-60))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.376);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.391);//
			continue;
		}
		else if(timedifference1 < (time1 - 40) && timedifference1 >= (time1-50))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.298);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.313);//
			continue;
		}
		else if(timedifference1 < (time1 - 30) && timedifference1 >= (time1-40))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.22);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.235);//
			continue;
		}
		else if(timedifference1 < (time1 - 20) && timedifference1 >= (time1-30))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.142);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.157);//
			continue;
		}
		else if(timedifference1 < (time1 - 10) && timedifference1 >= (time1-20))
		{
			Epos_SetSpeed(&eposL, (MaxSpeed+ adjust)*0.064);//
			Epos_SetSpeed(&eposR, -(MaxSpeed-adjust)*0.079);//
			continue;
		}
		else if(timedifference1 < time1  && timedifference1 >= (time1-10))
		{
			Epos_SetSpeed(&eposL, 0);//+ adjust
			Epos_SetSpeed(&eposR, 0);//-adjust
			continue;
		}
		
		
		if ((fabs(adjust) > MaxSpeed) && (adjust < 0))
		{
			LeftMotorSpeed  = 0;
			RightMotorSpeed = -(MaxSpeed - adjust);
		}
		else if ((fabs(adjust) > MaxSpeed*0.99) && (adjust > 0))
		{
			LeftMotorSpeed  = (MaxSpeed   + adjust)*0.99;
			RightMotorSpeed = 0;
		}
		else
		{ 
			LeftMotorSpeed  = (MaxSpeed   + adjust)*0.99;
			RightMotorSpeed = -(MaxSpeed - adjust);
		}
		if (LeftMotorSpeed > MaxSpeed)
		{
			LeftMotorSpeed = MaxSpeed;
		}
		else if (LeftMotorSpeed < MinSpeed)
		{
			LeftMotorSpeed = MinSpeed;
		}
		
		if (RightMotorSpeed < -MaxSpeed)
		{
			RightMotorSpeed = -MaxSpeed;
		}
		else if (RightMotorSpeed > -MinSpeed)
		{
			RightMotorSpeed = -MinSpeed;
		}
		
		Epos_SetSpeed(&eposL, LeftMotorSpeed);
		Epos_SetSpeed(&eposR, RightMotorSpeed);
		
		OSTimeDly(1);
	}
}

⌨️ 快捷键说明

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