打印
[PIC®/AVR®/dsPIC®产品]

【CuriosityNano测评报告】利用Timer1驱动步进电机

[复制链接]
455|6
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
本帖最后由 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设备,按照固定的间隔周期发送相序数据,驱动步进电机正反转。改变这个周期,就能改变步进电机的转速。关键代码如下:
uint8_t F_Rotation[4]={0x10,0x20,0x40,0x80};//正转表格
uint8_t B_Rotation[4]={0x80,0x40,0x20,0x10};//反转表格
#define STEP_MAX 4
//// 方式B,根据电机参数说明
//uint8_t F_Rotation[8]={0x80,0xC0,0x40,0x60,0x20,0x30,0x10,0x90};//正转表格
//uint8_t B_Rotation[8]={0x80,0xC0,0x40,0x60,0x20,0x30,0x10,0x90};//反转表格
//#define STEP_MAX 8

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

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

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

    //GSS T1G_pin;
    T1GATE = 0x00;

    //CS FOSC/4;
    T1CLK = 0x01;

    //TMR1H 255;
    TMR1H = 0xFF;

    //TMR1L 6;
    TMR1L = 0x06;

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

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

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

    // Set Default Interrupt Handler
    TMR1_SetInterruptHandler(TMR1_DefaultInterruptHandler);

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

// 定时器1中断,设计为1ms周期
void TMR1_DefaultInterruptHandler(void){
    uint8_t next_step=0;
    // add your TMR1 interrupt custom code
    // or set custom function using TMR1_SetInterruptHandler()
    LATFbits.LATF3 = ~LATFbits.LATF3;
    if (fb_flag>0) {
        // 每间隔固定时间让步进马达走一步
       timer1_int_cnt++;
       if (timer1_int_cnt==step_period_ms) {
           timer1_int_cnt=0;
           if (fb_flag==1) {
               // 正转场合
               stepmotor_pos=(stepmotor_pos+1)%STEP_MAX;
           } else if (fb_flag==2) {
               // 反转场合
               stepmotor_pos=(stepmotor_pos+STEP_MAX-1)%STEP_MAX;
           }
           next_step=F_Rotation[stepmotor_pos];
           LATF = (LATF & 0x0F) | next_step;
       }      
    } else {
        timer1_int_cnt=0;
        LATF = LATF & 0x0F;
    }
}
定时器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;
在主程序中,使用开发板仅有的一个按钮,来实现电机正转、反转、停转三种方式的交替转换。
if (!SW0_GetValue()) {
            __delay_ms(50); // 消除抖动的处理
            if (!SW0_GetValue()) {
                // 指示灯显示变化
                LED0_Toggle();
                // 正反转标志0-stop.1-正转,2-反转
                fb_flag=(fb_flag+1)%3;
                // 串口输出信息
                printf("BUTTON PRESSED\r\n");
                // 等待按钮松开
                while (!SW0_GetValue());
            }
        }
实际测试时,通过示波器的测量可以看到,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。   

使用特权

评论回复
5
chenci2013| | 2022-10-13 17:19 | 只看该作者
定时器的告诉输出能否用于步进电机驱动脉冲

使用特权

评论回复
6
soodesyt| | 2022-10-13 18:00 | 只看该作者
定时器如何通过改变定时器装载值来控制步进电机的转速

使用特权

评论回复
7
suncat0504|  楼主 | 2022-10-14 09:20 | 只看该作者
本帖最后由 suncat0504 于 2022-10-14 09:22 编辑

控制电机转速,可以使用pmw。控制输出pmw正是定时器的强项。但是控制步进电机,个人感觉,用pmw好像不太合适。

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

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

87

主题

2421

帖子

5

粉丝