[PIC®/AVR®/dsPIC®产品] 【CuriosityNano测评报告】利用Timer1驱动步进电机

[复制链接]
 楼主| suncat0504 发表于 2022-7-18 10:10 | 显示全部楼层 |阅读模式
<
本帖最后由 suncat0504 于 2022-7-20 08:53 编辑

PIC18F57Q43 Curiosity Nano开发板的管脚构成图如下:
准备使用RF4~RF7控制一个24线的步进电机。电机参数如下:
控制时序:

实际测试时,发现这个相序控制效果不是太好,于是改用以下方式处理:
uint8_t F_Rotation[4]={0x10,0x20,0x40,0x80};//正转表格
按照从0-3的顺序发送数据给步进电机的接口,可以让步进电机正转;按照从3-0的顺序发送数据给步进电机的接口,可以让步进电机反转。
在程序中使用Timer1设备,按照固定的间隔周期发送相序数据,驱动步进电机正反转。改变这个周期,就能改变步进电机的转速。关键代码如下:
  1. uint8_t F_Rotation[4]={0x10,0x20,0x40,0x80};//正转表格
  2. uint8_t B_Rotation[4]={0x80,0x40,0x20,0x10};//反转表格
  3. #define STEP_MAX 4
  4. //// 方式B,根据电机参数说明
  5. //uint8_t F_Rotation[8]={0x80,0xC0,0x40,0x60,0x20,0x30,0x10,0x90};//正转表格
  6. //uint8_t B_Rotation[8]={0x80,0xC0,0x40,0x60,0x20,0x30,0x10,0x90};//反转表格
  7. //#define STEP_MAX 8

  8. // 步进电机正反转标志
  9. uint8_t fb_flag=0;
  10. // 步进电机当前驱动相序
  11. uint8_t stepmotor_pos=0;
  12. // 步进间隔计数周期
  13. uint32_t step_period_ms=2;

  14. // 定时器1的初始化配置
  15. void TMR1_Initialize(void) {
  16.     //Set the Timer to the options selected in the GUI

  17.     //T1GE disabled; T1GTM disabled; T1GPOL low; T1GGO done; T1GSPM disabled;
  18.     T1GCON = 0x00;

  19.     //GSS T1G_pin;
  20.     T1GATE = 0x00;

  21.     //CS FOSC/4;
  22.     T1CLK = 0x01;

  23.     //TMR1H 255;
  24.     TMR1H = 0xFF;

  25.     //TMR1L 6;
  26.     TMR1L = 0x06;

  27.     // Clearing IF flag before enabling the interrupt.
  28.     PIR3bits.TMR1IF = 0;

  29.     // Load the TMR value to reload variable
  30.     timer1ReloadVal=(uint16_t)((TMR1H << 8) | TMR1L);

  31.     // Enabling TMR1 interrupt.
  32.     PIE3bits.TMR1IE = 1;

  33.     // Set Default Interrupt Handler
  34.     TMR1_SetInterruptHandler(TMR1_DefaultInterruptHandler);

  35.     // CKPS 1:1; NOT_SYNC synchronize; TMR1ON enabled; T1RD16 disabled;
  36.     T1CON = 0x01;
  37. }

  38. // 定时器1中断,设计为1ms周期
  39. void TMR1_DefaultInterruptHandler(void){
  40.     uint8_t next_step=0;
  41.     // add your TMR1 interrupt custom code
  42.     // or set custom function using TMR1_SetInterruptHandler()
  43.     LATFbits.LATF3 = ~LATFbits.LATF3;
  44.     if (fb_flag>0) {
  45.         // 每间隔固定时间让步进马达走一步
  46.        timer1_int_cnt++;
  47.        if (timer1_int_cnt==step_period_ms) {
  48.            timer1_int_cnt=0;
  49.            if (fb_flag==1) {
  50.                // 正转场合
  51.                stepmotor_pos=(stepmotor_pos+1)%STEP_MAX;
  52.            } else if (fb_flag==2) {
  53.                // 反转场合
  54.                stepmotor_pos=(stepmotor_pos+STEP_MAX-1)%STEP_MAX;
  55.            }
  56.            next_step=F_Rotation[stepmotor_pos];
  57.            LATF = (LATF & 0x0F) | next_step;
  58.        }      
  59.     } else {
  60.         timer1_int_cnt=0;
  61.         LATF = LATF & 0x0F;
  62.     }
  63. }
定时器1 的固定周期中断处理中,累加timer1_int_cnt,当满足计数周期时,取得下一个要发送的相序数据。
正转场合,是按照正向获取相序数据的:stepmotor_pos=(stepmotor_pos+1)%STEP_MAX;
反转场合,是按照向获取相序数据的:stepmotor_pos=(stepmotor_pos+STEP_MAX-1)%STEP_MAX;
这样处理,可以保证正反转换时,保证相序的连续性。因为使用RF4-RF7作为2相四线步进电机的控制接口,使用RF3控制开发板上的LED0,所以发送控制数据时,使用以下代码,以保证RF的低四位接口数据不变。
LATF = (LATF & 0x0F) | next_step;
在主程序中,使用开发板仅有的一个按钮,来实现电机正转、反转、停转三种方式的交替转换。
  1. if (!SW0_GetValue()) {
  2.             __delay_ms(50); // 消除抖动的处理
  3.             if (!SW0_GetValue()) {
  4.                 // 指示灯显示变化
  5.                 LED0_Toggle();
  6.                 // 正反转标志0-stop.1-正转,2-反转
  7.                 fb_flag=(fb_flag+1)%3;
  8.                 // 串口输出信息
  9.                 printf("BUTTON PRESSED\r\n");
  10.                 // 等待按钮松开
  11.                 while (!SW0_GetValue());
  12.             }
  13.         }
实际测试时,通过示波器的测量可以看到,LED0的闪烁周期是2.5ms左右,那么Timer1的中断周期就是1.25ms左右(根据MCC是设置为1ms的),同时意味着步进马达每两个相序数据之间的间隔周期为2.5ms(step_period_ms=2)

  通过视频可以看出,这个电机转速用于控制光强检测板,应该是可以的,可能还有点快。但这里仅仅是为了演示同定时器驱动步进电机的转动。实际应用的时候,可能是在主程序中,每次转动一点角度,并检测光强的。速度不必很快,也不需要是连续的。下一步准备测试ADC处理,通过光电器件或者太阳能板取得和光强相关的电压并进行AD转换,配合步进电机的转动,找到光强最大的角度。
简单的测试是完成了,但我还是想吐槽下:这个AVR开发板是我用过的第二块使用MPLAB X IDE开发的开发板。因为PIC18F57Q43的中文资料不多,只能一点一点啃英文资料,对于学俄语的我,很难啊。同时,MPLAB X IDEMCC配置环境中全部是英文,并且好多短语。不同MCU的配置内容往往有不一样,学习起来,难度不是一般的高,我只能一点点摸索。

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有账号?注册

×
qiangtech 发表于 2022-7-19 14:06 | 显示全部楼层
很可以哦。
232321122 发表于 2022-10-13 16:38 | 显示全部楼层

步进电机驱动器的脉冲信号和方向控制信号怎么产生的   
sanfuzi 发表于 2022-10-13 16:51 | 显示全部楼层
做步进电机控制建议用PWM。   
chenci2013 发表于 2022-10-13 17:19 | 显示全部楼层
定时器的告诉输出能否用于步进电机驱动脉冲
soodesyt 发表于 2022-10-13 18:00 | 显示全部楼层
定时器如何通过改变定时器装载值来控制步进电机的转速
 楼主| suncat0504 发表于 2022-10-14 09:20 | 显示全部楼层
本帖最后由 suncat0504 于 2022-10-14 09:22 编辑

控制电机转速,可以使用pmw。控制输出pmw正是定时器的强项。但是控制步进电机,个人感觉,用pmw好像不太合适。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

认证:大连伊飞特信息技术有限公司软件工程师
简介:本人于1993年毕业于大连理工大学。毕业后从事单片机开发工作5年,之后转入软件开发工作至今。

158

主题

4504

帖子

6

粉丝
快速回复 在线客服 返回列表 返回顶部