Joint vel-cmd for torque PID loop and linear encoder PID

More
02 Jul 2018 14:22 #113229 by Glite
Hi all,

I have encountered a problem when tried to setup the dual loop feedback system with servos in torque mode and linear scale, using Mesa 7i77.
When I disable net x-vel-cmd => pid.x.command-deriv signal, to get velocity command calculated from the corrected position of scales through the pid component, I'm getting constant following error (10 microns, 1-3 with signal connected) during acceleration/deceleration, error during cruise stays the same. Same behavior exists when I do the same without scales feedback fed into drives PID. I tried to tune it, but with no luck. So i just left the joint.x.vel-cmd connected to pid.x.command-deriv and getting pid.x.command from the scales, which does the trick, but makes the D term of drives PID not fully correct because the velocity command should change along with position command from the scales PID.
Is there a some way to correct the velocity command from trajectory planer along with position command? I thought to make another pid for the velocity command with the same Integral term as for the position command, but i don't think that velocity feedback from 1 um scales is a reliable source for the correction as well as if using the same I term will work at all.

hal and ini files are in attachments, I haven't saved any plots, because didn't thought that using raw velocity command can be a problem.

Thanks
Attachments:

Please Log in or Create an account to join the conversation.

More
02 Jul 2018 15:02 #113237 by PCW
1. I think you should just use the TPs commanded velocity, any scale corrections to this will just add noise and no useful information (plus if you rely on the PIDs DDT for commanded velocity calculation, it will be one cycle late)
2. For a true dual loop system I would think you should just use the scale for slow (integral only perhaps) feedback with a separate PID component feeding the bias input of the primary (rotary encoder) PID

Please Log in or Create an account to join the conversation.

More
02 Jul 2018 16:14 #113241 by Glite
1. Can this behavior of command derivative calculation be some kind of floating point operations error? Looking at the pid and simple_tp code I see that in simple_tp commanded position is calculated from velocity and in pid it is opposite.
2. Currently my system is looking like that:
position command -> (scale PID) -> corrected position -> (rotary PID) -> torque mode drive
Scale PID only has small amount of I term (20 and 25 to be exact), adding P term makes system completely unstable. Is this is what you mean?

Also i have a problem with homing to index (i saw few threads about that), which was partially solved by hardwiring scales index to the rotary index input. It has a small jerk of motors, when encoders are reset and sometimes a following error. When I tried to use only scale index in HAL or vice versa or both, i was getting constant following error, because position of one encoder was not reset (seen through the halscope).

Please Log in or Create an account to join the conversation.

More
02 Jul 2018 16:35 #113243 by PCW
1 No the commanded velocity is correct and you definitely do not want anything but the TPs commanded velocity to feed the primary PIDs commanded velocity input

2. I dont think you want cascaded PID controllers for the dual loop but rather the slow feedback from the scale should be added to the primary PID output (most easily via the bias pin)

3. You may want cascaded primary PIDs to get the best performance from a torque loop (a position loop controlling a velocity loop controlling the drive)
The following user(s) said Thank You: Glite

Please Log in or Create an account to join the conversation.

More
02 Jul 2018 20:25 - 02 Jul 2018 20:31 #113250 by Glite
2. Wouldn't that cause a commanded and actual position mismatch for the primary PID and axis due to some amount of backlash in a system (0.005-0.015 mm, scales are helping with that)? That's the main concern, because commanded position for both axes will be the same, but feedback is different. Primary PID will try to negate the error, but the scale PID wouldn't agree with that.
How the scale PID output should be scaled to be added as a bias to the primary PID? Because for now 10 V output is 250% of torque, and scale PID adds no more than 20-30 um to the position command.

3. I should definitely try that, but I need some inputs on how to tune it, I've got used to tune that torque loop, but cascaded loops are more complex. As I understand I have to tune the velocity loop first using some kind of square wave signal to get the fastest response for the velocity command without oscillation using all three terms as well as FF0 and FF1, but i don't know the order and correct usage for them. Then I should tune the position loop using P, I and maybe FF1 if I'm correct, and tune the scale loop using I term.
Another question is do I need to use both position and velocity commands. I see that for the position loop I can only use motor-pos-cmd which will output the velocity command for the velocity loop, and I don't see a place where I can use the joint-vel-cmd. I fear that I will encounter same problem with derived velocity command.
Last edit: 02 Jul 2018 20:31 by Glite.

Please Log in or Create an account to join the conversation.

More
02 Jul 2018 20:46 #113251 by PCW
Backlash will always be an issue no matter what you do with the control loops since it introduces a non -linearity in unexpected and unknowable places (unless you can guess when the backlash take-up movement will occur, it wont necessarily occur at reversals when there is external load)

I agree is difficult to do this with you current setup, this is why a cascaded primary control is probably better, That way the velocity loop
(velocity command velocity feedback torque output) is a P+I control and the position loop (P and FF1 only)

In any case you always want to use the TPs commanded velocity as the source for FF1 in the position loop

Please Log in or Create an account to join the conversation.

More
02 Jul 2018 21:52 #113257 by Glite
Thanks a lot. It's much clearer to me now.
I will try to make 3 cascaded PID loops when I get to the machine, because I'm not sure that bias input will work in my case.

Also command-deriv of pid component is not used for FF1 term, commandD which is actually used for FF1 is calculated from commanded position. I'm not sure if this needs to be changed in component's code.

Thanks again.

Please Log in or Create an account to join the conversation.

More
16 Jul 2018 06:18 - 16 Jul 2018 06:32 #114280 by Glite
Hi again,
I want to share with you my results.
Using only P and I terms for the velocity loop it's possible to get very neat response to the square and sine velocity signal:


But when it comes to tuning the position PID, I'm getting strong oscillations. I found that I need to add a very small amount of D term to the velocity PID, and after that response to the velocity command becomes very noisy, like in DaBit's thread, but i don't get oscillations in position PID tuning.
Funny thing that I couldn't get better results than using only position-to-torque PID loop.
Cascaded PID (I term wasn't used here, this could be a mistake):

Single PID:


Also here is what happening when I disconnect joint-vel-cmd from pid.command-deriv of position-torque loop:

When it's connected:

Gains have the same value, but it becomes almost impossible to tune it.
Last edit: 16 Jul 2018 06:32 by Glite.

Please Log in or Create an account to join the conversation.

More
16 Jul 2018 06:52 #114281 by Glite
Main question here: what is happening with derivative calculation?

Please Log in or Create an account to join the conversation.

More
16 Jul 2018 09:19 #114283 by Glite
Also I think that the part of FF1 source in pid.c has to be changed to use actual command-deriv value. Now it looks like this:
/* calculate derivative of command */
/* save old value for 2nd derivative calc later */
tmp2 = *(pid->cmd_d);
if(!(pid->prev_ie && !*(pid->index_enable))) {
    // not falling edge of index_enable: the normal case
    *(pid->cmd_d) = (command - pid->prev_cmd) * periodrecip;
}
and has to be changed to this:
/* calculate derivative of command */
/* save old value for 2nd derivative calc later */
tmp2 = *(pid->cmd_d);
*(pid->cmd_d) = *(pid->commandv);
I don't have possibility to test it any time soon, so if someone can, please, share the impact of that change.

Please Log in or Create an account to join the conversation.

Time to create page: 0.084 seconds
Powered by Kunena Forum