请问Arduino如何同时驱动两个步进电机,分别走不同步数?(使用TB6560驱动)
本帖最后由 JasmineL 于 2013-4-23 21:42 编辑http://www.geek-workshop.com/forum.php?mod=viewthread&tid=3266
我使用了了大连好人写的库函数,链接在上面
现在的主要问题是两个步进电机可以以不同速度运行,但是是同时开始同时停。
时间以运行时间长的步进电机为主,另一个步进电机走的比输入进去的步数多。
目前我能想到的解决办法是:在相同时间内,两个步进电机以一定比例的速度运行,以期盼能得到成比例的步数。
但又发现一个问题,如果比例较大,例如步数比为8:1时,一个电机转8圈的时候,另一个电机会转的比1圈多大概30度。
也就是说,速度成比例的时候,步数不完全成这个比例,转的数量少的时候,不明显,多了就不行了.....
求问大家,怎样才能同时驱动两个步进电机,且让他们走不同的步数...
我的代码如下:
//1,2电机以不同速度转动相同步数
#include <EasyStepper.h>
#define STEP1_PIN 2
#define STEP2_PIN 4
#define DIR1_PIN 6
#define DIR2_PIN 8
#define EN1_PIN 12
#define EN2_PIN 13//两个EN端悬空
#define DIR1_PIN_INVERTED true
#define DIR2_PIN_INVERTED true
#define EN1_PIN_INVERTED true
#define EN2_PIN_INVERTED true
EasyStepper stepper1(STEP1_PIN, DIR1_PIN, EN1_PIN, DIR1_PIN_INVERTED, EN1_PIN_INVERTED);
EasyStepper stepper2(STEP2_PIN, DIR2_PIN, EN2_PIN, DIR2_PIN_INVERTED, EN2_PIN_INVERTED);
int times=0;
int stepps=0;
void setup()
{
Serial.begin(9600);
stepper1.debugMode(false);
stepper1.startup();
stepper2.debugMode(false);
stepper2.startup();
}
void loop(){
if (Serial.available() > 0)
{
stepps=Serial.parseInt();
Serial.println(stepps);
stepper1.rotate(400.0,stepps/2);
stepper2.rotate(50.0,-stepps/2);
}
while(stepps!=0)
{
if (times < 2)
{
stepper1.run();
if (stepper1.isDone())
{
// go back
stepper1.rotate(400.0,stepps/2);
Serial.println("Iner1"+times);
}
stepper2.run();
if (stepper2.isDone())
{
// go back
stepper2.rotate(50.0,-stepps/2);
times++;
Serial.println("Iner2"+times);
}
if(times==2)
{
stepps=0;
times=0;
}
}
Serial.println("Outer"+times);
}}
找出问题了
if (times < 2)
{
stepper1.run();
if (stepper1.isDone())
{
// go back
stepper1.rotate(400.0,stepps/2);
Serial.println("Iner1"+times);
}
stepper2.run();
if (stepper2.isDone())
{
// go back
stepper2.rotate(50.0,-stepps/2);
times++;
Serial.println("Iner2"+times);
}
if(times==2)
{
stepps=0;
times=0;
}
看黑体代码部分,函数 .run是走一小步的意思, 每次step1走一小步,然后判断走完没有,然后step2再走一小步,然后再判断step2走完没有.
如果step1走完, 就继续走stepps/2步(对time和step2都没有影响), 只有等step2走完,time才加1.
只有time加到2, 才跳出函数,大家同时不走了.
所以导致的结果是,无论step1速度是多少,要走多少步,可是两个马达运行的时间都是以step2的设置为主
现在你知道应该怎么改你的程序了吧
gjfhahaha 发表于 2013-4-23 23:27 static/image/common/back.gif
找出问题了
if (times < 2)
谢谢高手~明白错在哪了,可还是不知道能怎么改....
因为run需要一个循环才能一直执行,两个步进电机如果想同时动,应该是要写在同一个循环里面的吧?
那循环的跳出方式用什么呢? gjfhahaha 发表于 2013-4-23 23:27 static/image/common/back.gif
找出问题了
if (times < 2)
我是这么改的,还没经过测试,不知道对不对?
//1,2电机以不同速度转动相同步数
#include <EasyStepper.h>
#define STEP1_PIN 2
#define STEP2_PIN 4
#define DIR1_PIN 6
#define DIR2_PIN 8
#define EN1_PIN 12
#define EN2_PIN 13//两个EN端悬空
#define DIR1_PIN_INVERTED true
#define DIR2_PIN_INVERTED true
#define EN1_PIN_INVERTED true
#define EN2_PIN_INVERTED true
EasyStepper stepper1(STEP1_PIN, DIR1_PIN, EN1_PIN, DIR1_PIN_INVERTED, EN1_PIN_INVERTED);
EasyStepper stepper2(STEP2_PIN, DIR2_PIN, EN2_PIN, DIR2_PIN_INVERTED, EN2_PIN_INVERTED);
int times=0;
int stepps=0;
void setup()
{
Serial.begin(9600);
stepper1.debugMode(false);
stepper1.startup();
stepper2.debugMode(false);
stepper2.startup();
}
void loop(){
if (Serial.available() > 0)
{
stepps=Serial.parseInt();
Serial.println(stepps);
stepper1.rotate(400.0,stepps);
stepper2.rotate(400.0,-stepps);
}
while(stepps!=0)
{
if (times < 1)
{
if (stepper1.isDone()==false)
{
stepper1.run();
}
if (stepper2.isDone()==false)
{
stepper2.run();
}
if(stepper1.isDone()&&stepper2.isDone())
{
times=1
stepps=0;
times=0;
}
}
}
} 直线插补,我发过个帖CNC用的GCode_Interpreter,参考里面的插补方式 JasmineL 发表于 2013-4-24 01:42 static/image/common/back.gif
我是这么改的,还没经过测试,不知道对不对?
times 这个变量貌似没用了吧 gjfhahaha 发表于 2013-4-24 16:12 static/image/common/back.gif
times 这个变量貌似没用了吧
是这样的,我实际用的时候,是没有while(stepp!=0)这一个循环的,因为两个电机走的步数是经过计算后得出的,不是这个测试程序这么简单,写的时候疏忽了~~现在程序已改正了 贴上个主程序里试验成功的函数吧,竖直平面内从现有位置移动到另一位置void xyMove(float dest_x,float dest_y)
{
init_a=float(sqrt(pow(init_x,2)+pow(init_y,2)));
init_b=float(sqrt(pow(D-init_x,2)+pow(init_y,2)));
dest_a=float(sqrt(pow(dest_x,2)+pow(dest_y,2)));
dest_b=float(sqrt(pow(D-dest_x,2)+pow(dest_y,2)));
da=dest_a-init_a;
db=dest_b-init_b;
//a,b电极旋转的正方向不同,去了再看,某个的da需要*-1
//记得试一试两电机同转,但符号不同的时候,是否方向相反
step_a=fabs(da*step_per_cm+0.5);
step_b=fabs(db*step_per_cm+0.5);//四舍五入
times=0;//电极需要初始化,以保证连续运动
if(step_a>=step_b)
{
speed_a=spd;
speed_b=(step_b*1.0/step_a)*spd;
}
else
{
speed_b=spd;
speed_a=(step_a*1.0/step_b)*spd;
}
if(da<0)
step_a=step_a*(-1);
if(db<0)
step_b=step_b*(-1);
stepper1.rotate(speed_a,-step_a);
stepper2.rotate(speed_b,step_b);
times=0;
while (times < 1)
{
if (stepper1.isDone()==false)
{
stepper1.run();
}
if (stepper2.isDone()==false)
{
stepper2.run();
}
if(stepper1.isDone()&&stepper2.isDone())
{
times=1;
}
}
init_x=dest_x;
init_y=dest_y;
} xmdesign 发表于 2013-4-24 07:26 static/image/common/back.gif
直线插补,我发过个帖CNC用的GCode_Interpreter,参考里面的插补方式
您发的那个Gcode的程序我想知道怎么用,很感兴趣。 串口(Serial.begin(19200);)键入G代码
1:G90 绝对坐标方式(G91为增量坐标方式)
2:G1 F3000 运行速度(F1~X)
3:X10 Y20 Z50移动目标坐标
4: M代码你发现其实可以你自己定义,比如打开或者关闭某个端口等
等等 G代码 xmdesign 发表于 2013-4-25 07:18 static/image/common/back.gif
串口(Serial.begin(19200);)键入G代码
1:G90 绝对坐标方式(G91为增量坐标方式)
2:G1 F3000 运行速度 ...
嗯,我正在改造我的小铣床,现在是做了个手动/自动走刀,控制xy两轴,z轴改动量比较大我就没改,我想实现雕刻或者铣平面的的工作,一直在找gcode的解释程序,您给的那个程序我下来看了下,觉得不错。就是不太清楚怎么写程序。 回复做个笔记,有空研究下,谢谢楼主 英文不好,打开相应链接就糊涂了。库文件下载,安装以及历程理解一直困扰。请不吝赐教;详尽些更好。 楼主可以发份源码吗!对我来说很有参考价值!([email protected])
:lol顺便问一下arduino最多可以实现同时控制多少个步进马达??
页:
[1]