最近在做一个F1控制步进电机的T型加减速的实验。
遇到现象:加速→匀速→急停。没有减速的效果。找了很多遍程序,跟硬石的程序一样。但是只能加速,没有减速效果。请教是哪里的问题啊。附上代码。
按理说,能加速,也就能减速呀
void MSD_PULSE_TIM_IRQHandler(void)
{
// 保存下一个延时周期
unsigned int new_step_delay;
// 加速过程中最后一次延时.
static int last_accel_delay;
// 移动步数计数器
static unsigned int step_count = 0;
// 记录new_step_delay中的余数,提高下一步计算的精度
static signed int rest = 0;
if (TIM_GetITStatus(MSD_PULSE_TIM, TIM_IT_Update) != RESET)
{
/* Clear MSD_PULSE_TIM Capture Compare1 interrupt pending bit*/
TIM_ClearITPendingBit(MSD_PULSE_TIM, TIM_IT_Update);
MSD_PULSE_TIM->CCR4=srd.step_delay >> 1;//周期的一半
MSD_PULSE_TIM->ARR=srd.step_delay;
//如果禁止输出,电机则停止运动
if(status.out_ena != TRUE)
{
srd.run_state = STOP;
}
switch(srd.run_state) {
case STOP:
step_count = 0;
rest = 0;
MSD_PULSE_TIM->CCER &= ~(1<<12); //禁止输出
TIM_Cmd(MSD_PULSE_TIM, DISABLE);
status.running = FALSE;
break;
case ACCEL:
MSD_PULSE_TIM->CCER |= 1<<12; //使能输出
MSD_StepCounter(srd.dir);
step_count++;
srd.accel_count++;
new_step_delay = srd.step_delay - (((2 * (long)srd.step_delay)
+ rest)/(4 * srd.accel_count + 1));
rest = ((2 * (long)srd.step_delay)+rest)%(4 * srd.accel_count + 1); //%为求
//检查是够应该开始减速
if(step_count >= srd.decel_start) {
srd.accel_count = srd.decel_val;
srd.run_state = DECEL;
}
//检查是否到达期望的最大速度
else if(new_step_delay <= srd.min_delay) {
last_accel_delay = new_step_delay;
new_step_delay = srd.min_delay;
rest = 0;
srd.run_state = RUN;
}
break;
case RUN:
MSD_PULSE_TIM->CCER |= 1<<12; //使能输出
MSD_StepCounter(srd.dir);
step_count++;
new_step_delay = srd.min_delay;
//检查是否需要开始减速
if(step_count >= srd.decel_start) {
srd.accel_count = srd.decel_val;
//以最后一次加速的延时作为开始减速的延时
new_step_delay = last_accel_delay;
srd.run_state = DECEL;
}
break;
case DECEL:
MSD_PULSE_TIM->CCER |= 1<<12; //使能输出
MSD_StepCounter(srd.dir);
step_count++;
srd.accel_count++;
new_step_delay = srd.step_delay - (((2 * (long)srd.step_delay)
+ rest)/(1+4 * srd.accel_count ));
rest = ((2 * (long)srd.step_delay)+rest)%(4 * srd.accel_count + 1);
//检查是否为最后一步
if(srd.accel_count >= 0){
srd.run_state = STOP;
}
break;
}
srd.step_delay = new_step_delay;
}
}