Universal Robots Forum

Linear move while one joint rotating

I am using an UR10 for some deburring, and for that I need to make a linear move across the disk on the grinder, but at the same time I also need to rotate the wrist joint to rotate the part around.

Using just a linear move makes it do the linear move as expected, without the wrist rotating.
Using a joint move makes it rotate the wrist, but does not maintain an even force on the disk.

What would be the way to do this?

Without spending a little time playing with a robot one thought is have you tried breaking your move up into little segments? Then you could stitch those little segments back together with a movej to achieve an approximated linear move. A couple of ways to do this come to mind, you could set up a relative waypoint that moved the arm say 1 mm in the linear direction while rotating the wrist some small amount of radians. Then just loop through this move until you have reached your final destination.

Another would be to teach the start and end points and then use pose_interpolation (I believe that is the correct function name). This returns a pose based on the start and end point and a percentage of distance to go. I have not tried this but would be interested to see if that works. You could just loop through the percentage and make the move for each fraction of the distance.

You could also use pose_trans to calculate the next waypoint based on the current tool position. Let’s say you want to move 1mm in X and rotate .1 radians st each step around the Z axis. You would define a variable such as

var myNextPoint = pose_trans(Tool, p[0.001,0,0,0,0,.1])

Then you’d do a variable movej using that variable and loop through until you reach the final destination. I like doing this in my program over relative waypoints as it’s much easier to adjust the step or rotation when I am developing than trying to reteach a relative waypoint but they work the same way.

The interpolate_pose(A, B, alpha) script approach would be interesting.
There is some examples here.

But I agree with @mbush that the pose_trans() approach gives some good benefits.

Also note that PolyScope generated Relative Waypoints rely on the pose_add() and are hence using the same (first) coordinate system as reference. Where as the pose_trans() command puts the second argument/pose at the end of the coordinate system generated by the first argument/pose.
So there is a slight discrepancy between Relative Waypoints and pose_trans()

1 Like

I did try to split it up into multiple joint moves, and that is how it is currently doing it, but so far i only programmed it directly on the TP, so there are only a few points because I was too lazy to add more :wink:

The task is almost done, but for the next time the order comes back, I want to be ready to do it smarter.

I was thinking about teaching it just a start and end point, and then have a variable where I could define how many smaller pieces it should cut it into.

I just deployed a robot last week where we did something similar, we have a series of moves that need to happen to place a part in the assembly, then step over and do the exact same moves 4 more times. I started off using relative moves but that was too tedious to teach over and over as we dialed in the exact motion we needed so I did something different.

I set up two lists of points, a list of Y moves and Z moves, relative to the preceding move. I then looped through the list and used pose_add() and get_actual_tcp_pose() to make the robot move through this list. The great thing was if I wanted to add additional points it was just a matter of adding them to the list. Since they were relative to each other though I might have to adjust the next point to account for it, that was still pretty easy. I also placed a “codes” in the array for turning on or off an output, for instance when points in the Y and Z array are both 0 turn on the gripper output to open the gripper. This method worked really well. You could use the same looping system and a variable to slice up any two points into as many slices as you’d like and then go to that point

Hi!
If the topic is still hot, please find attached a script that I use on a UR3 to move linear with the robot paralell to the x-y plane of the base while rotating with wrist3. May that helps.

def rotate2target(target,rot_speed,linear_speed,linear_acc):
act_pos=get_actual_tcp_pose()

dist=point_dist(act_pos,target)
dt_a=linear_speed/linear_acc
ds_a=(linear_acc/2)pow(dt_a,2)
dt_v=(dist-(2
ds_a))/linear_speed
rot_acc=d2r(rot_speed)/dt_a
time=dt_a+dt_v

direction=pose_sub(target,act_pos)
xyz_movement=sqrt(pow(direction[0],2)+pow(direction[1],2)+pow(direction[2],2))

sp=linear_speed/xyz_movement
speed_vec=[spdirection[0],spdirection[1],sp*direction[2],0,0,d2r(rot_speed)]

speedl(speed_vec,linear_acc,time,rot_acc)
stopl(linear_acc,rot_acc)
end

Best regards
Andreas

2 Likes

Thank you, I will try to do some experiments with that

Andreas,

Why do you use ‘xyz_movement’ instead of ‘dist’? Aren’t the results the same (move vector magnitude)?

How would this move differ from a standard movel() between the same two waypoints? Is the benefit the ability to separate linear_speed from rot_speed?

I am trying to use this on an UR5 and an UR10, are they any different from an UR3 regarding this script?

It doesnt seem to do what I expected, it just moves in a straight line, without rotating.

The most optimal thing, would be to just set two points, where it splits the movement up and does multiple joint moves, to get closer to a linear move.

Yes for sure. The UR5 and UR10 have no possibility of infinite rotation in the last axis. So it wouldn’t work on this robots.

I also tried playing around with this https://www.universal-robots.com/how-tos-and-faqs/how-to/ur-how-tos/interpolate-a-position-using-script-15345/ and it kinda does the job, but the problem is that it still can rotate the wrong way around.

With the hoses and tool attached, it is very important it will rotate the correct way around, otherwise they will get stuck under the wrist.

On the matter of protection of hoses, you might consider using appropriate joint position safety limits.
The robot is not allowed to cross these limits - it may still bump into a limit, if you tell it to do so, but it will in this case not break your cables.

Nothing will break, reach the point I need it to get to. I need to rotate Wrist 3 around 370 degrees, and that result in Wrist 3 rotating only 10 degrees.

The interpolate_pose does the job fine of making it move, in a close enough straight line for what i need, but it does not make the Wrist turn like I need it to.

Is there a way to only use interpolate_pose from Base to Wrist 2, and then have Wrist 3 just getting the degrees it needs to move to?

I think I am onto something… So far it isn’t pretty, but it can get polished later.

I got the robot moving from one position to another, in a straight’ish line, as good as a bunch of movej’s can do, and I have now moved onto trying to figure out how to calculate radiuses between the moves.

There are some functions to return the distance between two poses, but to get it to do as I wanted, I am moving the joints to degree positions, which are in a list. Are there a way to convert the list back into a pose, and calculate the distance with that?