STM32F4驱动42步进电机(采用驱动器)

您所在的位置:网站首页 l298n驱动42步进电机程序 STM32F4驱动42步进电机(采用驱动器)

STM32F4驱动42步进电机(采用驱动器)

2024-07-06 21:08:34| 来源: 网络整理| 查看: 265

提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档

文章目录 器件实物接线TB6600拨码卡关代码说明main.c 代码如下(示例):main.c 代码(极简版)step_motor.c 代码如下(示例):step_motor.c 代码(极简版)step_motor.h 代码step_motor.h 代码(极简版)说明

器件

stm32f407zgt6芯片,tb6600驱动器

植树机代码,可以驱动四路42步进电机,以下是只驱动1路。

实物

在这里插入图片描述 在这里插入图片描述

接线

在这里插入图片描述 红线接B+(TB6600), 蓝线接B-, 绿线接A-, 黑线接A+ 1 该图片是转载的。根据本文代码:Signal的-统一接开发板的GND(解法看实物照片),而PUL+接PC6(开发板)——控制脉冲,即距离和转速、DIR+接PE5(开发板)——控制转向,ENA+空着。TB6600驱动板的GND和VCC外接电源(不要用单纯的杜邦线)。

TB6600拨码卡关

在这里插入图片描述 1区:一个脉冲,电机转动1.8度,而1区的NC可以控制单位转角,即1.8/NC,挡位越大则转动的角度越小,可以做到精度越高。 2区:控制电流。 3、4区:即拨码开关,通过拨动右侧的六个开关即可以调到相应挡位。向上拨,是OFF。

代码说明

:极简版的代码是只能驱动步进电机进行调试而已,而完整版(植树机)有比较多的函数可以用来参考。

main.c 代码如下(示例): #include "sys.h" #include "delay.h" //#include "usart.h" //#include "led.h" //#include "pwm.h" #include "step_motor.h" //#include "uart3.h" //#include "hongwai.h" #include "stdlib.h" //#include "oled.h" //int num=81; int shengyu_num=98; int last_num=1; //int s_flag=1; //extern u16 step_speed; //extern u16 step_angle; //extern u32 Toggle_Pulse[4]; //extern unsigned char BMP2[]; //extern unsigned char BMP3[]; //extern unsigned char BMP4[]; //extern unsigned char BMP5[]; u8 h_num=0; //void show_qiang() //{ // OLED_ShowCHinese(0,4,0); // OLED_ShowCHinese(18,4,1); // OLED_ShowCHinese(36,4,2); // OLED_ShowCHinese(54,4,3); // // delay_ms(3000); // num++; // OLED_ShowString(72,4,". "); // OLED_ShowNum(54,0,num,2,16); // // delay_ms(3000); // num++; // OLED_ShowString(90,4,". "); // OLED_ShowNum(54,0,num,2,16); // // delay_ms(3000); // num++; // OLED_ShowString(108,4,". "); // OLED_ShowNum(54,0,num,2,16); // delay_ms(3000); //} //void show_zhong() //{ // OLED_ShowCHinese(0,4,0); // OLED_ShowCHinese(18,4,1); // OLED_ShowCHinese(36,4,2); // OLED_ShowCHinese(54,4,3); // // delay_ms(3000); // OLED_ShowString(72,4,". "); // // delay_ms(3000); // num++; // OLED_ShowString(90,4,". "); // OLED_ShowNum(54,0,num,2,16); // // delay_ms(3000); // num++; // OLED_ShowString(108,4,". "); // OLED_ShowNum(54,0,num,2,16); // delay_ms(3000); //} //void show_ruo() //{ // OLED_ShowCHinese(0,4,0); // OLED_ShowCHinese(18,4,1); // OLED_ShowCHinese(36,4,2); // OLED_ShowCHinese(54,4,3); // // delay_ms(3000); // OLED_ShowString(72,4,". "); // // delay_ms(3000); // OLED_ShowString(90,4,". "); // // delay_ms(3000); // num++; // OLED_ShowString(108,4,". "); // OLED_ShowNum(54,0,num,2,16); // delay_ms(3000); //} //void show_wu() //{ // OLED_Clear(); // OLED_Refresh_Gram(); // OLED_ShowCHinese(0,0,14); // OLED_ShowCHinese(18,0,15); // OLED_ShowCHinese(36,0,16); // if(num>=100){ // num=100; // OLED_ShowNum(54,0,num,3,16); // } // else OLED_ShowNum(54,0,num,2,16); // OLED_ShowString(81,0,"%"); OLED_ShowCHinese(54,0,17); OLED_ShowCHinese(72,0,18); delay_ms(200); // // OLED_ShowCHinese(0,2,25);//已 // OLED_ShowCHinese(18,2,26); // OLED_ShowCHinese(36,2,27); // OLED_ShowCHinese(54,2,30); // OLED_ShowCHinese(72,2,31); // OLED_ShowCHinese(90,2,32); // OLED_ShowNum(108,2,last_num,1,16); // // OLED_ShowCHinese(0,4,33); // OLED_ShowCHinese(18,4,34); // OLED_ShowCHinese(36,4,35); // OLED_ShowCHinese(54,4,36); // OLED_ShowCHinese(72,4,37); // OLED_ShowCHinese(90,4,38); // OLED_ShowNum(108,4,shengyu_num,2,16); // // OLED_ShowCHinese(0,6,39); // OLED_ShowCHinese(18,6,40); // OLED_ShowCHinese(36,6,41); // OLED_ShowCHinese(54,6,42); // // OLED_ShowString(72,6,". "); // OLED_ShowString(90,6,". "); // OLED_ShowString(108,6,". "); //} //void show_ele() //{ // int i; // OLED_Clear(); // OLED_Refresh_Gram(); // OLED_Fill(1,5,110,10,1); // OLED_Fill(1,50,110,55,1); // OLED_Fill(0,5,5,55,1); // OLED_Fill(110,5,115,55,1); // OLED_Fill(115,20,120,40,1); // for(i=0;i // num=100; // OLED_ShowNum(54,0,num,3,16); // OLED_ShowCHinese(0,2,18);//停 // OLED_ShowCHinese(18,2,19); // OLED_ShowCHinese(36,2,20); // OLED_ShowCHinese(54,2,21); // OLED_ShowCHinese(0,4,20); // OLED_ShowCHinese(18,4,21); // OLED_ShowCHinese(36,4,22); // OLED_ShowCHinese(54,4,23); // OLED_ShowCHinese(72,4,16); // OLED_ShowCHinese(90,4,24); // while(1); // } // else OLED_ShowNum(54,0,num,2,16); // OLED_ShowString(81,0,"%"); OLED_ShowCHinese(54,0,17); OLED_ShowCHinese(72,0,18); delay_ms(200); // // OLED_ShowCHinese(0,2,8); // OLED_ShowCHinese(18,2,9); // OLED_ShowCHinese(36,2,10); // OLED_ShowCHinese(54,2,11); // OLED_ShowCHinese(72,2,12); // // switch(s_flag%3) // { // case 1: OLED_ShowCHinese(90,2,13); // show_qiang(); // break; // case 2: OLED_ShowCHinese(90,2,4); // show_zhong(); // break; // case 0: OLED_ShowCHinese(90,2,17); // show_ruo(); // break; // default: break; // } // s_flag++; //} //void show_ele2() //{ // int i; // OLED_Clear(); // OLED_Refresh_Gram(); // OLED_Fill(1,5,110,10,1); // OLED_Fill(1,50,110,55,1); // OLED_Fill(0,5,5,55,1); // OLED_Fill(110,5,115,55,1); // OLED_Fill(115,20,120,40,1); // for(i=0;i // num=100; // OLED_ShowNum(54,0,num,3,16); // OLED_ShowCHinese(0,2,18);//停 // OLED_ShowCHinese(18,2,19); // OLED_ShowCHinese(36,2,20); // OLED_ShowCHinese(54,2,21); // OLED_ShowCHinese(0,4,20); // OLED_ShowCHinese(18,4,21); // OLED_ShowCHinese(36,4,22); // OLED_ShowCHinese(54,4,23); // OLED_ShowCHinese(72,4,16); // OLED_ShowCHinese(90,4,24); // while(1); // } // else OLED_ShowNum(54,0,num,2,16); // OLED_ShowString(81,0,"%"); OLED_ShowCHinese(54,0,17); OLED_ShowCHinese(72,0,18); delay_ms(200); // // OLED_ShowCHinese(0,2,8); // OLED_ShowCHinese(18,2,9); // OLED_ShowCHinese(36,2,10); // OLED_ShowCHinese(54,2,11); // OLED_ShowCHinese(72,2,12); // OLED_ShowCHinese(90,2,17); // show_ruo(); // //} int main(void) { // int i; NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//设置系统中断优先级分组2 delay_init(168); //初始化延时函数 step_motor_1_Init(); //电机1初始化 step_motor_2_Init(); //电机2初始化 step_motor_3_Init(); //电机3初始化 step_motor_4_Init(); //电机4初始化 TIM8_OPM_RCR_Init(1000-1,168-1); // TIM4_PWM_Init(1000-1,84-1); // TIM13_PWM_Init(1999,84-1); // TIM14_PWM_Init(1999,84-1); // USART3_Init(9600); // HONGWAI_Init(); // OLED_Show_main(); // show_wu(); // while(1) // { // OLED_Clear(); // OLED_Refresh_Gram(); // OLED_Fill(1,5,110,10,1); // OLED_Fill(1,50,110,55,1); // OLED_Fill(0,5,5,55,1); // OLED_Fill(110,5,115,55,1); // OLED_Fill(115,20,120,40,1); // for(i=0;i // case 1: OLED_ShowCHinese(90,2,13); // show_qiang(); // break; // case 2: OLED_ShowCHinese(90,2,4); // show_zhong(); // break; // case 0: OLED_ShowCHinese(90,2,17); // show_ruo(); // break; // default: break; // } //OLED_ShowCHinese(90,2,13);//显示强字,13:强 4:中 17:弱 // OLED_ShowCHinese(0,4,0); // OLED_ShowCHinese(18,4,1); // OLED_ShowCHinese(36,4,2); // OLED_ShowCHinese(54,4,3); // // delay_ms(3000); // num++; OLED_ShowCHinese(72,4,5); // OLED_ShowString(72,4,". "); // OLED_ShowNum(54,0,num,2,16); // // delay_ms(3000); // num++; // OLED_ShowString(90,4,". "); OLED_ShowCHinese(90,4,6); // OLED_ShowNum(54,0,num,2,16); // // delay_ms(3000); // num++; // OLED_ShowString(108,4,". "); // OLED_ShowNum(54,0,num,2,16); // delay_ms(3000); // s_flag++; // OLED_ShowCHinese(108,4,7); // } // OLED_ShowCHinese(0,6,0); // OLED_ShowCHinese(18,6,1); // OLED_ShowCHinese(36,6,2); // OLED_ShowCHinese(54,6,3); // OLED_ShowCHinese(72,6,5); // OLED_ShowCHinese(90,6,6); // OLED_ShowCHinese(108,6,7); // delay_ms(500); // OLED_ShowLogo(0,0,64,64,BMP4); // OLED_DrawBMP1(0,0,64,64,BMP4); // OLED_Refresh_Gram(); // SUM_1=0; // SUM_2=0; // SUM_3=0; // SUM_4=0; // delay_ms(1000); // TIM_SetCompare1(TIM14,800);//解锁 // TIM_SetCompare1(TIM13,800); // delay_ms(1000); // motor_left(); // motor_right(); // Locate_Rle_3(11500,1);//三电机一个行程11000个 // delay_ms(12000);//M3一个行程的时间 // Locate_Rle_3(11500,0);//三电机一个行程11000个 // delay_ms(12000);//M3一个行程的时间 while(1) { Locate_Rle_1(10000,1);//下降,电机1 delay_ms(16000); Locate_Rle_1(10000,0);//上升,电机1 delay_ms(16000); // switch(step_flag) // { // case 0:move(1,1);break; // case 1:move(2,0);break; // case 2:move(2,0);move(1,1);break; // case 3:move(3,1);break; // case 4:move(3,0);break; // case 5:move(4,1);break; // case 6:move(4,0);break; // case 7:show_ele2(); break; // case 8:motion();break; // case 9: show_wu(); // delay_ms(10000); // break; // default:break; // } } } main.c 代码(极简版) #include "sys.h" #include "delay.h" #include "step_motor.h" #include "stdlib.h" int main(void) { NVIC_PriorityGroupConfig(NVIC_PriorityGroup_2);//设置系统中断优先级分组2 delay_init(168); //初始化延时函数 step_motor_1_Init(); //电机1初始化 step_motor_2_Init(); //电机2初始化 step_motor_3_Init(); //电机3初始化 step_motor_4_Init(); //电机4初始化 TIM8_OPM_RCR_Init(1000-1,168-1); while(1) { Locate_Rle_1(10000,1);//下降,电机1 delay_ms(16000); Locate_Rle_1(10000,0);//上升,电机1 delay_ms(16000); } } step_motor.c 代码如下(示例): #include "step_motor.h" #include "delay.h" #include "usart.h" long SUM_1; long SUM_2; long SUM_3; long SUM_4; u32 Toggle_Pulse[4]={900,500,500,100}; u32 pulse=0; u8 step_flag=9; //电机两个引脚 extern last_num,shengyu_num; void step_motor_1_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5|GPIO_Pin_6; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOE, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR1_ENA=0; STEPMOTOR1_DIR=1; } void step_motor_2_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3|GPIO_Pin_4; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOE, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR2_ENA=0; STEPMOTOR2_DIR=1; } void step_motor_3_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOE, &GPIO_InitStructure);//初始化GPIOE5,6 RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOG, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR3_ENA=0; STEPMOTOR3_DIR=1; } void step_motor_4_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_14; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOG, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR4_ENA=0; STEPMOTOR4_DIR=1; } //电机PWM信号生成口 void TIM8_OPM_RCR_Init(u16 arr,u16 psc) { GPIO_InitTypeDef GPIO_InitStructure; TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; TIM_OCInitTypeDef TIM_OCInitStructure; NVIC_InitTypeDef NVIC_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM8,ENABLE); //TIM8时钟使能 RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE); //使能PORTC时钟 GPIO_PinAFConfig(GPIOC,GPIO_PinSource6,GPIO_AF_TIM8); //复用为定时器8 GPIO_PinAFConfig(GPIOC,GPIO_PinSource7,GPIO_AF_TIM8); //复用为定时器8 GPIO_PinAFConfig(GPIOC,GPIO_PinSource8,GPIO_AF_TIM8); //复用为定时器8 GPIO_PinAFConfig(GPIOC,GPIO_PinSource9,GPIO_AF_TIM8); //复用为定时器8 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 |GPIO_Pin_7|GPIO_Pin_8|GPIO_Pin_9; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; //复用功能 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; //速度100MHz GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; //推挽复用输出 GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_DOWN; //下拉 GPIO_Init(GPIOC,&GPIO_InitStructure); //初始化 TIM_TimeBaseStructInit(&TIM_TimeBaseStructure); TIM_TimeBaseStructure.TIM_Period = arr; //设置在下一个更新事件装入活动的自动重装载寄存器周期的值 TIM_TimeBaseStructure.TIM_Prescaler =psc; //设置用来作为TIMx时钟频率除数的预分频值 TIM_TimeBaseStructure.TIM_ClockDivision = 0; //设置时钟分割:TDTS = Tck_tim TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上计数模式 TIM_TimeBaseInit(TIM8, &TIM_TimeBaseStructure); //根据TIM_TimeBaseInitStruct中指定的参数初始化TIMx的时间基数单位 TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; //选择定时器模式:TIM脉冲宽度调制模式2 TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; //比较输出2使能 TIM_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Disable; /****** 比较输出2N失能 *******/ TIM_OCInitStructure.TIM_Pulse = arr>>1; //设置待装入捕获比较寄存器的脉冲值 TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; //输出极性:TIM输出比较极性高 //CH1 TIM_OC1Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC1PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 //CH2 TIM_OC2Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC2PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 //CH3 TIM_OC3Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC3PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 //CH4 TIM_OC4Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC4PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 TIM_ARRPreloadConfig(TIM8, ENABLE); //使能TIMx在ARR上的预装载寄存器 TIM_CtrlPWMOutputs(TIM8,ENABLE); //MOE 主输出使能 TIM_ITConfig(TIM8, TIM_IT_Update ,ENABLE); //TIM8 使能或者失能指定的TIM中断 NVIC_InitStructure.NVIC_IRQChannel = TIM8_UP_TIM13_IRQn; //TIM8中断 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; //先占优先级1级 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //从优先级1级 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道被使能 NVIC_Init(&NVIC_InitStructure); //根据NVIC_InitStruct中指定的参数初始化外设NVIC寄存器 TIM_ClearITPendingBit(TIM8, TIM_IT_Update); //清除TIMx的中断待处理位:TIM 中断源 TIM_Cmd(TIM8, ENABLE); //使能TIM8 } /******* TIM8更新中断服务程序 *********/ void TIM8_UP_TIM13_IRQHandler(void) { if(TIM_GetITStatus(TIM8,TIM_FLAG_Update)!=RESET)//更新中断 { TIM_ClearITPendingBit(TIM8,TIM_FLAG_Update);//清除更新中断标志位 if(SUM_1==0)//重复计数器未设置完成 { TIM_SetCompare1(TIM8,0); } else { TIM_SetCompare1(TIM8,800); SUM_1--; } if(SUM_2==0)//重复计数器未设置完成 { TIM_SetCompare2(TIM8,0); } else { TIM_SetCompare2(TIM8,800); SUM_2--; } if(SUM_3==0)//重复计数器未设置完成 { TIM_SetCompare3(TIM8,0); } else { TIM_SetCompare3(TIM8,800); SUM_3--; } if(SUM_4==0)//重复计数器未设置完成 { TIM_SetCompare4(TIM8,0); } else { TIM_SetCompare4(TIM8,800); SUM_4--; } } } /***************** 启动TIM8 *****************/ void Locate_Rle_1(long num,int dir) //相对定位函数 { STEPMOTOR1_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR1_DIR=0; } else//逆时针 { STEPMOTOR1_DIR=1; } SUM_1=num; TIM_SetCompare1(TIM8,800); } void Locate_Rle_2(long num,int dir) //相对定位函数 { STEPMOTOR2_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR2_DIR=0; } else//逆时针 { STEPMOTOR2_DIR=1; } SUM_2=num; TIM_SetCompare2(TIM8,800); } void Locate_Rle_3(long num,int dir) //相对定位函数 { STEPMOTOR3_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR3_DIR=0; } else//逆时针 { STEPMOTOR3_DIR=1; } SUM_3=num; TIM_SetCompare3(TIM8,800); } void Locate_Rle_4(long num,int dir) //相对定位函数 { STEPMOTOR4_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR4_DIR=0; } else//逆时针 { STEPMOTOR4_DIR=1; } SUM_4=num; TIM_SetCompare4(TIM8,800); } void motion() { Locate_Rle_4(30000,1); jidianqi_open(); delay_ms(31000);//M4一个行程的时间 Locate_Rle_4(30000,0); delay_ms(30000); jidianqi_close(); Locate_Rle_3(11300,1); delay_ms(12000);//M3一个行程的时间 while(Hongwai_flag()) { Locate_Rle_1(900,1); Locate_Rle_2(900,0); delay_ms(100); } Locate_Rle_1(3000,1); Locate_Rle_2(900,0); delay_ms(4000); Locate_Rle_3(11300,0); last_num++; shengyu_num--; step_flag=9; } void move(int n,int t) { switch(n) { case 1: Locate_Rle_1(90,t);break; case 2: Locate_Rle_2(90,t);break; case 3: Locate_Rle_3(90,t);break; case 4: Locate_Rle_4(90,t);break; } } step_motor.c 代码(极简版) #include "step_motor.h" #include "delay.h" #include "usart.h" long SUM_1; long SUM_2; long SUM_3; long SUM_4; void step_motor_1_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_5|GPIO_Pin_6; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOE, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR1_ENA=0; STEPMOTOR1_DIR=1; } void step_motor_2_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3|GPIO_Pin_4; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOE, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR2_ENA=0; STEPMOTOR2_DIR=1; } void step_motor_3_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOE, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_2; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOE, &GPIO_InitStructure);//初始化GPIOE5,6 RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOG, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR3_ENA=0; STEPMOTOR3_DIR=1; } void step_motor_4_Init(void) { GPIO_InitTypeDef GPIO_InitStructure; RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOG, ENABLE);//使能GPIOE时钟 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_13|GPIO_Pin_14; //DRIVER_DIR DRIVER_OE对应引脚 GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;//普通输出模式 GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;//推挽输出 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz;//100M GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;//上拉 GPIO_Init(GPIOG, &GPIO_InitStructure);//初始化GPIOE5,6 STEPMOTOR4_ENA=0; STEPMOTOR4_DIR=1; } //电机PWM信号生成口 void TIM8_OPM_RCR_Init(u16 arr,u16 psc) { GPIO_InitTypeDef GPIO_InitStructure; TIM_TimeBaseInitTypeDef TIM_TimeBaseStructure; TIM_OCInitTypeDef TIM_OCInitStructure; NVIC_InitTypeDef NVIC_InitStructure; RCC_APB2PeriphClockCmd(RCC_APB2Periph_TIM8,ENABLE); //TIM8时钟使能 RCC_AHB1PeriphClockCmd(RCC_AHB1Periph_GPIOC, ENABLE); //使能PORTC时钟 GPIO_PinAFConfig(GPIOC,GPIO_PinSource6,GPIO_AF_TIM8); //复用为定时器8 GPIO_PinAFConfig(GPIOC,GPIO_PinSource7,GPIO_AF_TIM8); //复用为定时器8 GPIO_PinAFConfig(GPIOC,GPIO_PinSource8,GPIO_AF_TIM8); //复用为定时器8 GPIO_PinAFConfig(GPIOC,GPIO_PinSource9,GPIO_AF_TIM8); //复用为定时器8 GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6 |GPIO_Pin_7|GPIO_Pin_8|GPIO_Pin_9; GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF; //复用功能 GPIO_InitStructure.GPIO_Speed = GPIO_Speed_100MHz; //速度100MHz GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; //推挽复用输出 GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_DOWN; //下拉 GPIO_Init(GPIOC,&GPIO_InitStructure); //初始化 TIM_TimeBaseStructInit(&TIM_TimeBaseStructure); TIM_TimeBaseStructure.TIM_Period = arr; //设置在下一个更新事件装入活动的自动重装载寄存器周期的值 TIM_TimeBaseStructure.TIM_Prescaler =psc; //设置用来作为TIMx时钟频率除数的预分频值 TIM_TimeBaseStructure.TIM_ClockDivision = 0; //设置时钟分割:TDTS = Tck_tim TIM_TimeBaseStructure.TIM_CounterMode = TIM_CounterMode_Up; //TIM向上计数模式 TIM_TimeBaseInit(TIM8, &TIM_TimeBaseStructure); //根据TIM_TimeBaseInitStruct中指定的参数初始化TIMx的时间基数单位 TIM_OCInitStructure.TIM_OCMode = TIM_OCMode_PWM2; //选择定时器模式:TIM脉冲宽度调制模式2 TIM_OCInitStructure.TIM_OutputState = TIM_OutputState_Enable; //比较输出2使能 TIM_OCInitStructure.TIM_OutputNState = TIM_OutputNState_Disable; /****** 比较输出2N失能 *******/ TIM_OCInitStructure.TIM_Pulse = arr>>1; //设置待装入捕获比较寄存器的脉冲值 TIM_OCInitStructure.TIM_OCPolarity = TIM_OCPolarity_High; //输出极性:TIM输出比较极性高 //CH1 TIM_OC1Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC1PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 //CH2 TIM_OC2Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC2PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 //CH3 TIM_OC3Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC3PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 //CH4 TIM_OC4Init(TIM8, &TIM_OCInitStructure); //根据TIM_OCInitStruct中指定的参数初始化外设TIMx TIM_OC4PreloadConfig(TIM8, TIM_OCPreload_Enable); //CH2预装载使能 TIM_ARRPreloadConfig(TIM8, ENABLE); //使能TIMx在ARR上的预装载寄存器 TIM_CtrlPWMOutputs(TIM8,ENABLE); //MOE 主输出使能 TIM_ITConfig(TIM8, TIM_IT_Update ,ENABLE); //TIM8 使能或者失能指定的TIM中断 NVIC_InitStructure.NVIC_IRQChannel = TIM8_UP_TIM13_IRQn; //TIM8中断 NVIC_InitStructure.NVIC_IRQChannelPreemptionPriority = 1; //先占优先级1级 NVIC_InitStructure.NVIC_IRQChannelSubPriority = 1; //从优先级1级 NVIC_InitStructure.NVIC_IRQChannelCmd = ENABLE; //IRQ通道被使能 NVIC_Init(&NVIC_InitStructure); //根据NVIC_InitStruct中指定的参数初始化外设NVIC寄存器 TIM_ClearITPendingBit(TIM8, TIM_IT_Update); //清除TIMx的中断待处理位:TIM 中断源 TIM_Cmd(TIM8, ENABLE); //使能TIM8 } /******* TIM8更新中断服务程序 *********/ void TIM8_UP_TIM13_IRQHandler(void) { if(TIM_GetITStatus(TIM8,TIM_FLAG_Update)!=RESET)//更新中断 { TIM_ClearITPendingBit(TIM8,TIM_FLAG_Update);//清除更新中断标志位 if(SUM_1==0)//重复计数器未设置完成 { TIM_SetCompare1(TIM8,0); } else { TIM_SetCompare1(TIM8,800); SUM_1--; } if(SUM_2==0)//重复计数器未设置完成 { TIM_SetCompare2(TIM8,0); } else { TIM_SetCompare2(TIM8,800); SUM_2--; } if(SUM_3==0)//重复计数器未设置完成 { TIM_SetCompare3(TIM8,0); } else { TIM_SetCompare3(TIM8,800); SUM_3--; } if(SUM_4==0)//重复计数器未设置完成 { TIM_SetCompare4(TIM8,0); } else { TIM_SetCompare4(TIM8,800); SUM_4--; } } } /***************** 启动TIM8 *****************/ void Locate_Rle_1(long num,int dir) //相对定位函数 { STEPMOTOR1_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR1_DIR=0; } else//逆时针 { STEPMOTOR1_DIR=1; } SUM_1=num; TIM_SetCompare1(TIM8,800); } void Locate_Rle_2(long num,int dir) //相对定位函数 { STEPMOTOR2_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR2_DIR=0; } else//逆时针 { STEPMOTOR2_DIR=1; } SUM_2=num; TIM_SetCompare2(TIM8,800); } void Locate_Rle_3(long num,int dir) //相对定位函数 { STEPMOTOR3_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR3_DIR=0; } else//逆时针 { STEPMOTOR3_DIR=1; } SUM_3=num; TIM_SetCompare3(TIM8,800); } void Locate_Rle_4(long num,int dir) //相对定位函数 { STEPMOTOR4_ENA = 0; if(TIM8->CR2&0x01)//上一次脉冲还未发送完成 直接返回 { return; } if(dir==1)//顺时针 { STEPMOTOR4_DIR=0; } else//逆时针 { STEPMOTOR4_DIR=1; } SUM_4=num; TIM_SetCompare4(TIM8,800); } step_motor.h 代码 #ifndef _STEP_MOTOR_H #define _STEP_MOTOR_H #include "sys.h" #include "stm32f4xx_tim.h" #define STEPMOTOR8_DIR PCout(6) //motor1 #define STEPMOTOR1_DIR PEout(5) #define STEPMOTOR1_ENA PEout(6) //motor2 #define STEPMOTOR2_DIR PEout(3) #define STEPMOTOR2_ENA PEout(4) //motor3 #define STEPMOTOR3_DIR PEout(2) #define STEPMOTOR3_ENA PGout(12) //motor4 #define STEPMOTOR4_DIR PGout(13) #define STEPMOTOR4_ENA PGout(14) extern u32 Toggle_Pulse[4]; extern long SUM_1; extern long SUM_2; extern long SUM_3; extern long SUM_4; extern u8 step_flag; void step_motor_1_Init(void); void step_motor_2_Init(void); void step_motor_3_Init(void); void step_motor_4_Init(void); void TIM8_OPM_RCR_Init(u16 arr,u16 psc); void Locate_Rle_1(long num,int dir); void Locate_Rle_2(long num,int dir); void Locate_Rle_3(long num,int dir); void Locate_Rle_4(long num,int dir); void motion(void); void move(int n,int t); #endif step_motor.h 代码(极简版) #ifndef _STEP_MOTOR_H #define _STEP_MOTOR_H #include "sys.h" #include "stm32f4xx_tim.h" #define STEPMOTOR8_DIR PCout(6) //motor1 #define STEPMOTOR1_DIR PEout(5) #define STEPMOTOR1_ENA PEout(6) //motor2 #define STEPMOTOR2_DIR PEout(3) #define STEPMOTOR2_ENA PEout(4) //motor3 #define STEPMOTOR3_DIR PEout(2) #define STEPMOTOR3_ENA PGout(12) //motor4 #define STEPMOTOR4_DIR PGout(13) #define STEPMOTOR4_ENA PGout(14) extern long SUM_1; extern long SUM_2; extern long SUM_3; extern long SUM_4; void step_motor_1_Init(void); void step_motor_2_Init(void); void step_motor_3_Init(void); void step_motor_4_Init(void); void TIM8_OPM_RCR_Init(u16 arr,u16 psc); void Locate_Rle_1(long num,int dir); void Locate_Rle_2(long num,int dir); void Locate_Rle_3(long num,int dir); void Locate_Rle_4(long num,int dir); #endif 说明

本文只是用来学习42步进电机,后期的功能还需要设计,结合植树机代码和极简版代码进行设计。



【本文地址】

公司简介

联系我们

今日新闻


点击排行

实验室常用的仪器、试剂和
说到实验室常用到的东西,主要就分为仪器、试剂和耗
不用再找了,全球10大实验
01、赛默飞世尔科技(热电)Thermo Fisher Scientif
三代水柜的量产巅峰T-72坦
作者:寞寒最近,西边闹腾挺大,本来小寞以为忙完这
通风柜跟实验室通风系统有
说到通风柜跟实验室通风,不少人都纠结二者到底是不
集消毒杀菌、烘干收纳为一
厨房是家里细菌较多的地方,潮湿的环境、没有完全密
实验室设备之全钢实验台如
全钢实验台是实验室家具中较为重要的家具之一,很多

推荐新闻


图片新闻

实验室药品柜的特性有哪些
实验室药品柜是实验室家具的重要组成部分之一,主要
小学科学实验中有哪些教学
计算机 计算器 一般 打孔器 打气筒 仪器车 显微镜
实验室各种仪器原理动图讲
1.紫外分光光谱UV分析原理:吸收紫外光能量,引起分
高中化学常见仪器及实验装
1、可加热仪器:2、计量仪器:(1)仪器A的名称:量
微生物操作主要设备和器具
今天盘点一下微生物操作主要设备和器具,别嫌我啰嗦
浅谈通风柜使用基本常识
 众所周知,通风柜功能中最主要的就是排气功能。在

专题文章

    CopyRight 2018-2019 实验室设备网 版权所有 win10的实时保护怎么永久关闭