工训大赛 心得 回忆录

4 篇文章 0 订阅
3 篇文章 0 订阅

经过大半年 努力拼搏 认识了一群志同道合的兄弟 很开心 ,

比赛完 又忙着期末 考试 忙的要死 终于考完试 了 在这里总结一下 嘚瑟一下 战果 并记下学习笔记 记录人生的精彩
话不多说先上图在这里插入图片描述
有个各性小眼神 组委会要求使用大屏 所以为了醒目 我们使用了 北京 某某 串口屏幕 stm32

串口通信 总结经验

void Send_data(USART_TypeDef * USARTx,u8 *s)
{	
  while(*s!='\0')	
 { 		
	while(USART_GetFlagStatus(USARTx,USART_FLAG_TC )==RESET);		
  USART_SendData(USARTx,*s);	
  s++;	
 }
}

主函数变量发送
sprintf(buf,"DS64(64,100,' %d',1);\r\n",er);
轱辘是怎么转起来的呢  

#include "motor.h"
void Motor_Init(void)
{
      
	GPIO_InitTypeDef GPIO_InitStructureB;    	//后轮
	GPIO_InitTypeDef GPIO_InitStructureC;    	//后轮
	GPIO_InitTypeDef GPIO_InitStructureE;     //前轮
	
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOB, ENABLE); //使能PB端口时钟
  GPIO_InitStructureB.GPIO_Pin = GPIO_Pin_4|GPIO_Pin_5;	//端口配置
  GPIO_InitStructureB.GPIO_Mode = GPIO_Mode_Out_PP;      //推挽输出
	GPIO_InitStructureB.GPIO_Speed = GPIO_Speed_50MHz;     //50M
  GPIO_Init(GPIOB, &GPIO_InitStructureB);					      //根据设定参数初始化GPIOB 

	RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOC, ENABLE); //使能PB端口时钟
  GPIO_InitStructureC.GPIO_Pin = GPIO_Pin_8|GPIO_Pin_9;	//端口配置
  GPIO_InitStructureC.GPIO_Mode = GPIO_Mode_Out_PP;      //推挽输出
	GPIO_InitStructureC.GPIO_Speed = GPIO_Speed_50MHz;     //50M
  GPIO_Init(GPIOC, &GPIO_InitStructureC);					      //根据设定参数初始化GPIOB 
	
  RCC_APB2PeriphClockCmd(RCC_APB2Periph_GPIOE, ENABLE); //使能PE端口时钟
  GPIO_InitStructureE.GPIO_Pin = GPIO_Pin_2|GPIO_Pin_3|GPIO_Pin_4|GPIO_Pin_5;	//端口配置
  GPIO_InitStructureE.GPIO_Mode = GPIO_Mode_Out_PP;      //推挽输出
	GPIO_InitStructureE.GPIO_Speed = GPIO_Speed_50MHz;     //50M
  GPIO_Init(GPIOE, &GPIO_InitStructureE);					      //根据设定参数初始化GPIOB 
}
void PWM_Init(u16 arr,u16 psc)
{		 		
		RCC->APB1ENR|=1<<3;       //TIM5时钟使能    
	RCC->APB2ENR|=1<<2;       //PORTA时钟使能 
	
	GPIOA->CRL&=0XFFFF0000;   //PORTA0,1,2,3复用输出
	GPIOA->CRL|=0X0000BBBB;   //PORTA0,1,2,3复用输出
	
	TIM5->ARR=arr;//设定计数器自动重装值 
	TIM5->PSC=psc;//预分频器不分频
	
	TIM5->CCMR1|=6<<4; //CH1 PWM1模式	
	TIM5->CCMR1|=6<<12;//CH2 PWM1模式	
	
	TIM5->CCMR2|=6<<4; //CH3 PWM1模式
	TIM5->CCMR2|=6<<12;//CH4 PWM1模式	

	TIM5->CCMR1|=1<<3; //CH1预装载使能	
	TIM5->CCMR1|=1<<11;//CH2预装载使能	
	TIM5->CCMR2|=1<<3; //CH3预装载使能	
	TIM5->CCMR2|=1<<11;//CH4预装载使能	 
	
	TIM5->CCER|=1<<0;  //CH1输出使能	
	TIM5->CCER|=1<<4;  //CH2输出使能	   
	TIM5->CCER|=1<<8;  //CH3输出使能	
	TIM5->CCER|=1<<12; //CH4输出使能	   
	
	TIM5->CR1=0x8000;  //ARPE使能 
	TIM5->CR1|=0x01;   //使能定时器3 	

 
} 

void Set_Motor(int MotorA,int MotorB,int MotorC,int MotorD)
{
	if(MotorA>0)
	{
		AIN1=0,			AIN2=1;
		PWMA=MotorA;
	}
	else
	{
		AIN1=1,			AIN2=0;
		PWMA=-MotorA;
	}
	
/	
	if(MotorB>0)
	{
		BIN1=0,			BIN2=1;
		PWMB=MotorB;
	}
	else
	{
		BIN1=1,			BIN2=0;
		PWMB=-MotorB;
	}
///	
	
	if(MotorC>0)
	{
		CIN1=1,			CIN2=0;
		PWMC=MotorC;
	}
	else
	{
		CIN1=0;			CIN2=1;
		PWMC=-MotorC;
	}
/	
	if(MotorD>0)
	{
		DIN1=1;			DIN2=0;
		PWMD=MotorD;
	}
	else
	{
		DIN1=0,			DIN2=1;
		PWMD=-MotorD;
	}
}


、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、
#include "encoder.h"

int Encoder[4];


void Encoder_Init(void)
{
	Encoder_Init_TIM8();
	Encoder_Init_TIM2();
	Encoder_Init_TIM3();
	Encoder_Init_TIM4();
}
/**************************************************************************
函数功能:把TIM1初始化为编码器接口模式
入口参数:无
返回  值:无
**************************************************************************/
void Encoder_Init_TIM8(void)
{
	RCC->APB1ENR|=1<<0;     //TIM2时钟使能
	RCC->APB2ENR|=1<<13;     //TIM8时钟使能
	RCC->APB2ENR|=1<<4;    //使能PORTC时钟
	GPIOC->CRL&=0X00FFFFFF;//PC6,7
	GPIOC->CRL|=0X44000000;//浮空输入

	/* 把定时器初始化为编码器模式 */ 
	TIM8->PSC = 0;//预分频器
	TIM8->ARR = 0xFFFF-1;//设定计数器自动重装值 
  TIM8->CCMR1 |= 1<<0;          //输入模式,IC1FP1映射到TI1上
	TIM8->CCMR1 |= 0xC<<4;        //输入滤波器
  TIM8->CCMR1 |= 1<<8;          //输入模式,IC2FP2映射到TI2上
	TIM8->CCMR1 |= 0xC<<12;       //输入滤波器
  TIM8->CCER |= 0<<1;           //IC1不反向
  TIM8->CCER |= 0<<5;           //IC2不反向
	TIM8->SMCR |= 3<<0;	          //SMS='011' 所有的输入均在上升沿和下降沿有效
	TIM8->CR1 |= 0x01;    				//CEN=1,使能定时器
}

/**************************************************************************
函数功能:把TIM2初始化为编码器接口模式
入口参数:无
返回  值:无
**************************************************************************/
void Encoder_Init_TIM2(void)
{
//TIM2的输入端口已经重新映射
//部分重映射,CH1---PA15,CH2---PB3
	RCC->APB1ENR|=1<<0;     //TIM2时钟使能
	RCC->APB2ENR|=1<<2;    //使能PORTA时钟
	RCC->APB2ENR|=1<<3;    //使能PORTB时钟
	GPIOA->CRH&=0X0FFFFFFF;//PA15
	GPIOA->CRH|=0X40000000;//浮空输入
	GPIOB->CRL&=0XFFFF0FFF;//PB3
	GPIOB->CRL|=0X00004000;//浮空输入
	/* 把定时器初始化为编码器模式 */ 
	TIM2->PSC = 0;//预分频器
	TIM2->ARR = 0xFFFF-1;//设定计数器自动重装值 
  TIM2->CCMR1 |= 1<<0;          //输入模式,IC1FP1映射到TI1上
	TIM2->CCMR1 |= 0xC<<4;        //输入滤波器
  TIM2->CCMR1 |= 1<<8;          //输入模式,IC2FP2映射到TI2上
	TIM2->CCMR1 |= 0xC<<12;       //输入滤波器
  TIM2->CCER |= 0<<1;           //IC1不反向
  TIM2->CCER |= 0<<5;           //IC2不反向
	TIM2->SMCR |= 3<<0;	          //SMS='011' 所有的输入均在上升沿和下降沿有效
	TIM2->CR1 |= 0x01;    				//CEN=1,使能定时器
}

/**************************************************************************
函数功能:把TIM2初始化为编码器接口模式
入口参数:无
返回  值:无
**************************************************************************/
void Encoder_Init_TIM3(void)
{
	RCC->APB1ENR|=1<<0;     //TIM2时钟使能
	RCC->APB1ENR|=1<<1;     //TIM3时钟使能
	RCC->APB2ENR|=1<<2;    //使能PORTA时钟
	GPIOA->CRL&=0X00FFFFFF;//PA6 PA7
	GPIOA->CRL|=0X44000000;//浮空输入
	/* 把定时器初始化为编码器模式 */ 
	TIM3->PSC = 0;//预分频器
	TIM3->ARR = 0xFFFF-1;//设定计数器自动重装值 
  TIM3->CCMR1 |= 1<<0;          //输入模式,IC1FP1映射到TI1上
	TIM3->CCMR1 |= 0xC<<4;        //输入滤波器
  TIM3->CCMR1 |= 1<<8;          //输入模式,IC2FP2映射到TI2上
	TIM3->CCMR1 |= 0xC<<12;       //输入滤波器
  TIM3->CCER |= 0<<1;           //IC1不反向
  TIM3->CCER |= 0<<5;           //IC2不反向
	TIM3->SMCR |= 3<<0;	          //SMS='011' 所有的输入均在上升沿和下降沿有效
	TIM3->CR1 |= 0x01;    				//CEN=1,使能定时器
}
/**************************************************************************
函数功能:把TIM4初始化为编码器接口模式
入口参数:无
返回  值:无
**************************************************************************/
void Encoder_Init_TIM4(void)
{
	RCC->APB1ENR|=1<<0;     //TIM2时钟使能
	RCC->APB1ENR|=1<<2;     //TIM4时钟使能
	RCC->APB2ENR|=1<<3;    //使能PORTb时钟
	GPIOB->CRL&=0X00FFFFFF;//PB6 PB7
	GPIOB->CRL|=0X44000000;//浮空输入
	/* 把定时器初始化为编码器模式 */ 
	TIM4->PSC = 0;//预分频器
	TIM4->ARR = 0xFFFF-1;//设定计数器自动重装值 
  TIM4->CCMR1 |= 1<<0;          //输入模式,IC1FP1映射到TI1上
	TIM4->CCMR1 |= 0xC<<4;        //输入滤波器
  TIM4->CCMR1 |= 1<<8;          //输入模式,IC2FP2映射到TI2上
	TIM4->CCMR1 |= 0xC<<12;        //输入滤波器
  TIM4->CCER |= 0<<1;           //IC1不反向
  TIM4->CCER |= 0<<5;           //IC2不反向
	TIM4->SMCR |= 3<<0;	          //SMS='011' 所有的输入均在上升沿和下降沿有效
	TIM4->CR1 |= 0x01;    				//CEN=1,使能定时器
}
/**************************************************************************
函数功能:单位时间读取编码器计数
入口参数:定时器
返回  值:速度值
**************************************************************************/
void Read_Encoder(void)
{
	Encoder[0]= (short)TIM2 -> CNT;  TIM2 -> CNT=0;//前左轮
	Encoder[1]= (short)TIM8 -> CNT;  TIM8 -> CNT=0;//前右轮
	Encoder[2]= (short)TIM3 -> CNT;  TIM3 -> CNT=0;//后左轮
	Encoder[3]= (short)TIM4 -> CNT;  TIM4 -> CNT=0;//后右轮
}
、、、
这一堆代码 看着难受  海底找手册 、、、、、】】】】】辛苦些吧、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、、

就这样就 编码器 我men 用的是140转的 那么pid呢


就是这啦//定时器6中断服务程序	 
void TIM6_IRQHandler(void)
{ 
   delay5ms++;
	if(TIM6->SR&0X0001)//溢出中断
	{			
			USART_SendData(USART1,FF);
		Contorl_stick++;
		if(Contorl_stick==4)
		{
			Contorl_stick=0;
			Read_Encoder();//读编码器	
      encoder_1+=Encoder[1];
//			OLED_ShowNum(30,4,encoder_1,6,16);
		
			for(nmr=0;nmr<4;nmr++)
			{
				PID_Motor[nmr].error=Encoder[nmr]-Motor_Speed[nmr];
				//输出的P值
				PID_Motor[nmr].pout = PID_Motor[nmr].Pdat * PID_Motor[nmr].error;
				//输出的I值
				PID_Motor[nmr].iout += (PID_Motor[nmr].Idat*0.05) * PID_Motor[nmr].error;
				PID_Motor[nmr].iout = Get_MxMi(PID_Motor[nmr].iout,200,-200);//判读I是否超出范围
				//输出的D值
				PID_Motor[nmr].dout = PID_Motor[nmr].Ddat*0.05*(PID_Motor[nmr].error-PID_Motor[nmr].Last_error);	
				PID_Motor[nmr].Last_error=PID_Motor[nmr].error;	
				//PID三个值融合
				PID_Motor[nmr].OUT += PID_Motor[nmr].pout + PID_Motor[nmr].iout +PID_Motor[nmr].dout;P,I,D值相加
				PID_Motor[nmr].OUT=Get_MxMi(PID_Motor[nmr].OUT,7199,-7199);
			}
			Set_Motor(PID_Motor[0].OUT, PID_Motor[1].OUT, PID_Motor[2].OUT, PID_Motor[3].OUT);
		}
	}
	TIM6->SR&=~(1<<0);//清除中断标志位 	    
}

void Car_Control(int Y_Move,int X_Move,int Yaw0)
{
	Motor_Speed[0] =  (-Y_Move + X_Move + Yaw0);	Motor_Speed[3] = (Y_Move - X_Move + Yaw0);
	Motor_Speed[2] = 	(-Y_Move - X_Move + Yaw0);	Motor_Speed[1] = (Y_Move + X_Move + Yaw0);	
}

void PID_Init(void)
{	
	PID_Motor[0].Pdat=-16;	PID_Motor[0].Idat=0;	PID_Motor[0].Ddat=-4;	
	PID_Motor[1].Pdat=16;	PID_Motor[1].Idat=0;	PID_Motor[1].Ddat=4;
	PID_Motor[2].Pdat=16;	  PID_Motor[2].Idat=0;	PID_Motor[2].Ddat=4;
	PID_Motor[3].Pdat=-16;	PID_Motor[3].Idat=0;	PID_Motor[3].Ddat=-4;
	
	PID_Motor[0].iout=0;
	PID_Motor[1].iout=0;
	PID_Motor[2].iout=0;
	PID_Motor[3].iout=0;
	
	PID_Motor[0].OUT=0;
	PID_Motor[1].OUT=0;
	PID_Motor[2].OUT=0;
	PID_Motor[3].OUT=0;
	
	PID_Motor[0].error=0;
	PID_Motor[1].error=0;
	PID_Motor[2].error=0;
	PID_Motor[3].error=0;
	
	PID_Motor[0].Last_error=0;
	PID_Motor[1].Last_error=0;
	PID_Motor[2].Last_error=0;
	PID_Motor[3].Last_error=0;

}

float Get_MxMi(float num,float max,float min)
{
	if(num>max)
		return max;
	else if(num<min)
		return min;
	else
		return num;
}
int encoder(int ax)
{
	motor1_d=encoder_1-ax*3500;
//	if(-motor1_d<2000)
//	{ 
//	 motor1_b=(3000+motor1_d)/50;
//	 motor1_b=Get_MxMi(motor1_b,65,45);
//	}
  
//	OLED_ShowNum(30,4,-motor1_d,6,16);
		 if(motor1_d<0)
		 {	
			flag_mm=0;
		  if(motor1_d>=-800)
      flag_mm= 2;
		 
		 }
		 if(motor1_d>0)
			flag_mm= 1;
		 
		return flag_mm;
}

int encoder1(int ax)
{
	motor1_d=-encoder_1-ax*3100;

	

		 if(motor1_d<0)
		 {	
			flag_mm=0;
		  if(motor1_d>=-2600)
      flag_mm= 2;
		 
		 }
		 if(motor1_d>0)
			flag_mm= 1;
		 
		return flag_mm;
}
int encoder2(int ax)
{
	motor1_d=-encoder_1-ax*2800;

  
	
		 if(motor1_d<0)
		 {	
			flag_mm=0;
		  if(motor1_d>=-1500)
      flag_mm= 2;
		 
		 }
		 if(motor1_d>0)
			flag_mm= 1;
		 
		return flag_mm;
}
int encoder3(int ax)
{
	motor1_d=encoder_1-ax*2958;
	
  
	
		 if(motor1_d<0)
		 {	
			flag_mm=0;
		  if(motor1_d>=-1500)
      flag_mm= 2;
		 
		 }
		 if(motor1_d>0)
			flag_mm= 1;
		 
		return flag_mm;
}

这些核心的 东西 搞好 搞稳  路径就好写  但是 我们的目的不是参与奖  而是特等奖 我们需要更加稳定的巡线算法 于是 某个大神高出了 pid 横向 巡线 
**************************************/
void Lxunji_pid(int v)
{


			a0=ARED1;
      a1=ARED3;
			 
     error=a1-a0-flagREDL;
			if(error<0)
				error=-error;

			pout = Pdat * error;//输出的P值
			iout += (Idat*0.05) * error;//输出的I值
			iout = Get_MxMi(iout,10,-10);//判读I是否超出范围
			dout = Ddat*0.05*(error-Last_error);					//输出的D值
			Last_error=error;	
			OUT += pout  +dout;P,I,D值相加	//PID三个值融合
			 if(OUT<100)
			LEFT(v,v,v,v);
			else
			{
//				OLED_ShowNum(30,6,OUT/10,6,16);
			  OUT=Get_MxMi(OUT,v+10,v);
			  if(a1<a0)
			  LEFT(OUT,v,v,v); 
			  else if(a1>a0)
			  LEFT(v,v,OUT,v); 
		  }
			if(DRED3==0&&DRED1==1)            //数字量保险回线
			{
			  LEFT(v-10,v+10,v+10,v-10);
			}
			if(DRED3==1&&DRED1==0)             //数字量保险回线
			{
				LEFT(v+10,v-10,v-10,v+10);
			}
}保证 车正 线直 于是效果很完美





这些 过后路径只要是思路清晰的话就很好写的  我就不上 了 上了也没啥大用

然后 我们就顺利的 进入了决赛  经过 一晚上努力付出 终于把临场的任务写完
无非就是 改改路径 罢了

但是加了wifi 模组 udp 连接模式  比赛当晚 出了些问题好在最后解决了 
对于8266我用了三种 首先放弃了at 命令 之后 用了arduino  for 8266
#include <ESP8266WiFi.h>
#include <WiFiUdp.h>
const char* ssid = "GXDS2019";
const char* password = "xnsq2019";
unsigned long previousMillis = 0; //毫秒时间记录
const long interval = 100;       //时间间隔
WiFiUDP Udp;
unsigned int localUdpPort = 9050;  // local port to listen on
char incomingPacket[255];  // buffer for incoming packets
char  replyPacket[] = " Got the message)";  // a reply string to send back


void setup()
{
  pinMode(2, OUTPUT);
  Serial.begin(115200);
  Serial.println();
  Serial.printf("Connecting %s ");
  WiFi.mode(WIFI_STA);
  WiFi.setAutoConnect(false);
  WiFi.begin(ssid, password);
  while (WiFi.status() != WL_CONNECTED)
  { 
    digitalWrite(2, HIGH);
    delay(500);
    //Serial.print(".");
    digitalWrite(2, LOW);
  }
  Serial.println(" connected");

  Udp.begin(localUdpPort);
  //Serial.printf("Now listening at IP %s, UDP port %d\n", WiFi.localIP().toString().c_str(), localUdpPort);
}


void loop()
{
//  unsigned long currentMillis = millis();         //读取当前时间
//  if (currentMillis - previousMillis >= interval) //如果和前次时间大于等于时间间隔
//  {
//    
//    previousMillis = currentMillis; //更新时间记录
//          
//  }
 digitalWrite(2, LOW);
  int packetSize = Udp.parsePacket();
  if (packetSize)
  {
    // receive incoming UDP packets
   // Serial.printf("Received %d bytes from %s, port %d\n", packetSize, Udp.remoteIP().toString().c_str(), Udp.remotePort());
    int len = Udp.read(incomingPacket, 255);
    if (len > 0)
    {
       
      incomingPacket[len] = 0;
    }
    Serial.printf(incomingPacket);

    // send back a reply, to the IP address and port we got the packet from"UDP packet contents: %s\n", 
   Udp.beginPacket(Udp.remoteIP(), Udp.remotePort());
   // Udp.beginPacket("192.168.137.255",Udp.remotePort());
    Udp.write(replyPacket);
    Udp.endPacket();
  }
}
但是 我怕比赛时候出事啊 于是又有了第三种方案
AIthink 的sdk
// 头文件引用
//==================================================================================
#include "user_config.h"		// 用户配置
#include "driver/uart.h"  		// 串口
#include "driver/oled.h"  		// OLED

//#include "at_custom.h"
#include "c_types.h"			// 变量类型
#include "eagle_soc.h"			// GPIO函数、宏定义
#include "ip_addr.h"			// 被"espconn.h"使用。在"espconn.h"开头#include"ip_addr.h"或#include"ip_addr.h"放在"espconn.h"之前
#include "espconn.h"			// TCP/UDP接口
//#include "espnow.h"
#include "ets_sys.h"			// 回调函数
//#include "gpio.h"
#include "mem.h"				// 内存申请等函数
#include "os_type.h"			// os_XXX
#include "osapi.h"  			// os_XXX、软件定时器
//#include "ping.h"
//#include "pwm.h"
//#include "queue.h"
//#include "smartconfig.h"
//#include "sntp.h"
//#include "spi_flash.h"
//#include "upgrade.h"
#include "user_interface.h" 	// 系统接口、system_param_xxx接口、WIFI、RateContro
//==================================================================================


// 宏定义
//==================================================================================
#define		ProjectName			"STA_UDP_Client"		// 工程名宏定义

#define		ESP8266_STA_SSID	"GXDS2019"			// 接入的WIFI名
#define		ESP8266_STA_PASS	"xnsq2019"		// 接入的WIFI密码

#define		LED_ON				GPIO_OUTPUT_SET(GPIO_ID_PIN(4),0)		// LED亮
#define		LED_OFF				GPIO_OUTPUT_SET(GPIO_ID_PIN(4),1)		// LED灭
//==================================================================================


// 全局变量
//==================================================================================
os_timer_t OS_Timer_1;			// 定义软件定时器

struct espconn ST_NetCon;		// 网络连接结构体
//==================================================================================


// 毫秒延时函数
//===========================================
void ICACHE_FLASH_ATTR delay_ms(u32 C_time)
{	for(;C_time>0;C_time--)
		os_delay_us(1000);
}
//===========================================


// ESP8266_STA初始化
//==============================================================================
void ICACHE_FLASH_ATTR ESP8266_STA_Init_JX()
{
	struct station_config STA_Config;	// STA参数结构体

	struct ip_info ST_ESP8266_IP;		// STA信息结构体

	// 设置ESP8266的工作模式
	//------------------------------------------------------------------------
	wifi_set_opmode(0x01);				// 设置为STA模式,并保存到Flash

	/*
	// 设置STA模式下的IP地址【ESP8266默认开启DHCP Client,接入WIFI时会自动分配IP地址】
	//--------------------------------------------------------------------------------
	wifi_station_dhcpc_stop();						// 关闭 DHCP Client
	IP4_ADDR(&ST_ESP8266_IP.ip,192,168,8,88);		// 配置IP地址
	IP4_ADDR(&ST_ESP8266_IP.gw,192,168,8,1);		// 配置网关地址
	IP4_ADDR(&ST_ESP8266_IP.netmask,255,255,255,0);	// 配置子网掩码
	wifi_set_ip_info(STATION_IF,&ST_ESP8266_IP);	// 设置STA模式下的IP地址
	*/

	// 结构体赋值,配置STA模式参数
	//-------------------------------------------------------------------------------
	os_memset(&STA_Config, 0, sizeof(struct station_config));	// STA参数结构体 = 0
	os_strcpy(STA_Config.ssid,ESP8266_STA_SSID);				// 设置WIFI名
	os_strcpy(STA_Config.password,ESP8266_STA_PASS);			// 设置WIFI密码

	wifi_station_set_config(&STA_Config);	// 设置STA参数,并保存到Flash

	// wifi_station_connect();		// ESP8266连接WIFI
}
//=========================================================================================


// 成功发送网络数据的回调函数
//==========================================================
void ICACHE_FLASH_ATTR ESP8266_WIFI_Send_Cb_JX(void *arg)
{
	//os_printf("\nESP8266_WIFI_Send_OK\n");
}
//==========================================================


// 成功接收网络数据的回调函数【参数1:网络传输结构体espconn指针、参数2:网络传输数据指针、参数3:数据长度】
//=========================================================================================================
void ICACHE_FLASH_ATTR ESP8266_WIFI_Recv_Cb_JX(void * arg, char * pdata, unsigned short len)
{
	struct espconn * T_arg = arg;		// 缓存网络连接结构体指针

	remot_info * P_port_info = NULL;	// 定义远端连接信息指针


	// 根据数据设置LED的亮/灭
	//-------------------------------------------------------------------------------
	os_printf("#%s\r\n",pdata);		// 串口打印接收到的数据
	OLED_ShowString(32,6,pdata);
	// 获取远端信息【UDP通信是无连接的,向远端主机回应时需获取对方的IP/端口信息】
	//------------------------------------------------------------------------------------
	if(espconn_get_connection_info(T_arg, &P_port_info, 0)==ESPCONN_OK)	// 获取远端信息
	{
		T_arg->proto.udp->remote_port  = P_port_info->remote_port;		// 获取对方端口号
		T_arg->proto.udp->remote_ip[0] = P_port_info->remote_ip[0];		// 获取对方IP地址
		T_arg->proto.udp->remote_ip[1] = P_port_info->remote_ip[1];
		T_arg->proto.udp->remote_ip[2] = P_port_info->remote_ip[2];
		T_arg->proto.udp->remote_ip[3] = P_port_info->remote_ip[3];
		//os_memcpy(T_arg->proto.udp->remote_ip,P_port_info->remote_ip,4);	// 内存拷贝
	}

	//--------------------------------------------------------------------
	OLED_ShowIP(16,4,T_arg->proto.udp->remote_ip);	// 显示远端主机IP地址
	//--------------------------------------------------------------------

	//espconn_send(T_arg,"ESP8266_WIFI_Recv_OK",os_strlen("ESP8266_WIFI_Recv_OK"));	// 向对方发送应答
}
//=========================================================================================================


// 定义espconn型结构体
//-----------------------------------------------
//struct espconn ST_NetCon;	// 网络连接结构体

// 初始化网络连接(UDP通信)
//==================================================================================================
void ICACHE_FLASH_ATTR ESP8266_NetCon_Init_JX()
{
	// 结构体赋值
	//--------------------------------------------------------------------------
	ST_NetCon.type = ESPCONN_UDP;		// 设置通信协议为UDP

	ST_NetCon.proto.udp = (esp_udp *)os_zalloc(sizeof(esp_udp));	// 开辟内存

	// 此处需要设置目标IP/端口(ESP8266作为Client,需要预先知道Server的IP/端口)
	//--------------------------------------------------------------------------
	ST_NetCon.proto.udp->local_port  = 9050 ;	// 设置本地端口
	ST_NetCon.proto.udp->remote_port = 9050;	// 设置目标端口
	ST_NetCon.proto.udp->remote_ip[0] = 192;	// 设置目标IP地址
	ST_NetCon.proto.udp->remote_ip[1] = 168;
	ST_NetCon.proto.udp->remote_ip[2] = 3;
	ST_NetCon.proto.udp->remote_ip[3] = 50;
	//u8 remote_ip[4] = {192,168,8,47};		// 目标ip地址
	//os_memcpy(ST_NetCon.proto.udp->remote_ip,remote_ip,4);	// 拷贝内存

	// 注册回调函数192.168.3.50
	//-------------------------------------------------------------------------------------------
	espconn_regist_sentcb(&ST_NetCon,ESP8266_WIFI_Send_Cb_JX);	// 注册网络数据发送成功的回调函数
	espconn_regist_recvcb(&ST_NetCon,ESP8266_WIFI_Recv_Cb_JX);	// 注册网络数据接收成功的回调函数

	// 调用UDP初始化API
	//-----------------------------------------------
	espconn_create(&ST_NetCon);		// 初始化DUP通信


	// 主动向Server发起通信
	//----------------------------------------------------------------------------
	//espconn_send(&ST_NetCon,"Hello,I am ESP8266",os_strlen("Hello,I am ESP8266"));
}
//==================================================================================================


// 软件定时的回调函数
//=========================================================================================================
void ICACHE_FLASH_ATTR OS_Timer_1_cb(void)
{
	u8 C_LED_Flash = 0;				// LED闪烁计次

	struct ip_info ST_ESP8266_IP;	// ESP8266的IP信息
	u8 ESP8266_IP[4];				// ESP8266的IP地址


	// 成功接入WIFI【STA模式下,如果开启DHCP(默认),则ESO8266的IP地址由WIFI路由器自动分配】
	//-------------------------------------------------------------------------------------
	if( wifi_station_get_connect_status() == STATION_GOT_IP )	// 判断是否获取IP
	{
		wifi_get_ip_info(STATION_IF,&ST_ESP8266_IP);	// 获取STA的IP信息
		ESP8266_IP[0] = ST_ESP8266_IP.ip.addr;			// IP地址高八位 == addr低八位
		ESP8266_IP[1] = ST_ESP8266_IP.ip.addr>>8;		// IP地址次高八位 == addr次低八位
		ESP8266_IP[2] = ST_ESP8266_IP.ip.addr>>16;		// IP地址次低八位 == addr次高八位
		ESP8266_IP[3] = ST_ESP8266_IP.ip.addr>>24;		// IP地址低八位 == addr高八位

		// 显示ESP8266的IP地址
		//-----------------------------------------------------------------------------------------------
		//os_printf("ESP8266_IP = %d.%d.%d.%d\n",ESP8266_IP[0],ESP8266_IP[1],ESP8266_IP[2],ESP8266_IP[3]);
		OLED_ShowIP(16,2,ESP8266_IP);	// OLED显示ESP8266的IP地址
		//-----------------------------------------------------------------------------------------------

		// 接入WIFI成功后,LED快闪3次
		//----------------------------------------------------
		for(; C_LED_Flash<=5; C_LED_Flash++)
		{
			GPIO_OUTPUT_SET(GPIO_ID_PIN(4),(C_LED_Flash%2));
			delay_ms(100);
		}


		os_timer_disarm(&OS_Timer_1);	// 关闭定时器

		ESP8266_NetCon_Init_JX();		// 初始化网络连接(UDP通信)
	}
}
//=========================================================================================================



// 软件定时器初始化(ms毫秒)
//=====================================================================================
void ICACHE_FLASH_ATTR OS_Timer_1_Init_JX(u32 time_ms, u8 time_repetitive)
{
	os_timer_disarm(&OS_Timer_1);	// 关闭定时器
	os_timer_setfn(&OS_Timer_1,(os_timer_func_t *)OS_Timer_1_cb, NULL);	// 设置定时器
	os_timer_arm(&OS_Timer_1, time_ms, time_repetitive);  // 使能定时器
}
//=====================================================================================

// LED初始化
//=============================================================================
void ICACHE_FLASH_ATTR LED_Init_JX(void)
{
	PIN_FUNC_SELECT(PERIPHS_IO_MUX_GPIO4_U,	FUNC_GPIO4);	// GPIO4设为IO口

	GPIO_OUTPUT_SET(GPIO_ID_PIN(4),1);						// IO4 = 1
}
//=============================================================================


// user_init:entry of user application, init user function here
//==============================================================================
void ICACHE_FLASH_ATTR user_init(void)
{
	uart_init(115200,115200);	// 初始化串口波特率
	os_delay_us(10000);			// 等待串口稳定
	//os_printf("\r\n=================================================\r\n");
	//os_printf("\t Project:\t%s\r\n", ProjectName);
	//os_printf("\t SDK version:\t%s", system_get_sdk_version());
	//os_printf("\r\n=================================================\r\n");

	// OLED显示初始化
	//--------------------------------------------------------
	OLED_Init();							// OLED初始化
	//OLED_ShowString(0,0,"ESP8266");	// ESP8266模式
	OLED_ShowString(0,2,"I:");				// ESP8266_IP地址
	OLED_ShowString(0,4,"P:");	// 远端主机模式
	OLED_ShowString(0,6,"Rec:");				// 远端主机IP地址
	//--------------------------------------------------------

	LED_Init_JX();		// LED初始化


	ESP8266_STA_Init_JX();			// ESP8266_STA初始化

	OS_Timer_1_Init_JX(1000,1);		// 1秒定时
}
//==============================================================================



/******************************************************************************
 * FunctionName : user_rf_cal_sector_set
 * Description  : SDK just reversed 4 sectors, used for rf init data and paramters.
 *                We add this function to force users to set rf cal sector, since
 *                we don't know which sector is free in user's application.
 *                sector map for last several sectors : ABCCC
 *                A : rf cal
 *                B : rf init data
 *                C : sdk parameters
 * Parameters   : none
 * Returns      : rf cal sector
*******************************************************************************/
uint32 ICACHE_FLASH_ATTR user_rf_cal_sector_set(void)
{
    enum flash_size_map size_map = system_get_flash_size_map();
    uint32 rf_cal_sec = 0;

    switch (size_map) {
        case FLASH_SIZE_4M_MAP_256_256:
            rf_cal_sec = 128 - 5;
            break;

        case FLASH_SIZE_8M_MAP_512_512:
            rf_cal_sec = 256 - 5;
            break;

        case FLASH_SIZE_16M_MAP_512_512:
        case FLASH_SIZE_16M_MAP_1024_1024:
            rf_cal_sec = 512 - 5;
            break;

        case FLASH_SIZE_32M_MAP_512_512:
        case FLASH_SIZE_32M_MAP_1024_1024:
            rf_cal_sec = 1024 - 5;
            break;

        case FLASH_SIZE_64M_MAP_1024_1024:
            rf_cal_sec = 2048 - 5;
            break;
        case FLASH_SIZE_128M_MAP_1024_1024:
            rf_cal_sec = 4096 - 5;
            break;
        default:
            rf_cal_sec = 0;
            break;
    }

    return rf_cal_sec;
}

void ICACHE_FLASH_ATTR user_rf_pre_init(void){}

好复杂 好多代码 去球 反正成功了 再给看个效果图在这里插入图片描述
再后来 我们就比赛 了 期间 出了小意外 但是 不好意思了 我们特等奖 嘚瑟一下嘿嘿i在这里插入图片描述
然后给你men 看看我们的奖牌,妥妥的在这里插入图片描述
嘻嘻
马上就大四 准备找工作了 加油吧 少年

评论 6
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值