Jump to content
OMRON Forums

Tuning Coupled Loads


WuBill
 Share

Recommended Posts

Hello, I have a Stewart Platform and the tuning of the servos seem to be off. I'm having trouble tuning the motors while they are coupled to the top platform of the Stewart Platform. Are there any documents on manual tuning of motors? Also this platform changes from being horizontal to vertical so should I tune for both of the different configurations and find some happy medium or can you change tuning settings on the fly. I should also mention that this Stewart Platform was my first motion project with more that one axis and also my first with a Delta Tau project so I'm probably behind the curve on tuning and other motion concepts. I can post more information about the Stewart Platform, motors, controller, and load if more specific information is needed.
Link to comment
Share on other sites

  • Replies 5
  • Created
  • Last Reply

Top Posters In This Topic

Attached is a brief tutorial on tuning the servo loop manually in PMAC from our Turbo PMAC training program. Basically, you execute a step move or a parabolic move in the PMAC Tuning Pro2 program (part of the Executive Pro2 Suite), and then alter your gains according to what the position profile or following error profiles look like. Please read it over and let us know if you need any more help. Yes, you can adjust the tuning parameters on the fly by changing the associated I-Variables in a PLC, motion program, etc. It is best to use a PLC for this. You could develop a set of gains for horizontal motion, a set of gains for vertical motion, and then have a PLC change the gains based on an I/O point, internal indicator, or whatever. However, be careful to test the effects of this, as you could suddenly cause the system to become unstable if you incorrectly modify any controller gains. Note that our tuning program only tunes 1 axis at a time. I'll write some examples of how to tune coupled loads using PLCs and post them for your reference. Edit (3/30/11): Servo Loop Tuning attachment has been updated.
Link to comment
Share on other sites

Use the step move for tuning Kp, Kd, and Ki. For the synchronized step move, the procedure should be performed in a PLC like this: [list=1] [*]Configure gathering settings for motors 1-6 using Quick Plot. Need to gather actual and commanded positions. [*]Home the motors to give yourself room to move if needed. [*]Save the current settings in Ixx05 and Ixx06 for motors 1-6 (assuming your hexapod is using motors 1-6). [*]Set Ixx05 (master position register) to open memory locations starting with X:$10F0 and enable following with Ixx06=1. [*]Start gathering. [*]Command the step move for motors 1-6 by writing to their master position registers. [*]Wait a prescribed duration and then command a step move back to starting position. Hold prescribed amount. [*]End Gathering. [*]Set Ixx05 and Ixx06 back to original settings. [/list] Then you can examine the plots of actual and commanded position vs. time of sets of 4 motors at a time using the Quick Plot program (in PMAC Plot32Pro2), then adjust your tuning parameters, and issue the step move again. The example I wrote is lengthy because I wrote out completely how to move all 6 motors, but there are many comments, so read them and please let me know if you do not understand it: [code] #define Ixx08_Index P33 ; Dynamic index for Ixx08 #define MtrNoTimes100 P34 ; Storage variable for computational efficiency #define ctr P133 ; Loop counter #define MotorNumber P134 ; Selects motor number to address for various commands #define Ixx07_Index P135 ; Dynamic index for Ixx07 #define Ixx05_Index P136 ; Dynamic index for Ixx08 #define Ixx06_Index P137 ; Dynamic Index for Ixx06 #define StepSize P138 ; - User Input [cts]: size of step move in one direction #define StepTime P139 ; - User Input [msec]: time step is held #define FirstPrevIxx05Index 142 ; First P-Variable index to use for storing Ixx05 values - User Input #define FirstPrevIxx06Index 148 ; First P-Variable index to use for storing Ixx06 values - User Input #define NumberOfMotors 6 ; Total number of motors through which to cycle - User Input #define MtrxxMasterPos M1000 ; Dynamic pointer to point to motor master positions #define pMtrxxMasterPos M1001 ; Pointer to change M1000's address definition word #define MasterPosCmd M1002 ; Dynamic pointer to point to motor commanded master position #define pMasterPosCmd M1003 ; Pointer to change M1002's address definition word MtrxxMasterPos->D:$00008D ; #1 Present master pos (1/[Ixx07*32] cts) pMtrxxMasterPos->Y:$43E8,0,16 ; Point to M1000's address definition MasterPosCmd->X:$10F0,0,24 ; Point to open register; will write master pos command here pMasterPosCmd->Y:$43EA,0,16 ; Point to M1002's address definition StepSize = 500 ; cts - Default size of step move StepTime = 1000 ; ms - Default hold time for step move End Gat Del Gat Close // Step Move PLC Open PLC 25 Clear CMD"#1HM#2HM#3HM#4HM#5HM#6HM" ; Home motors 1 - 6 I5112=1*8388608/I10 While(I5112>0) EndW ; Wait 1 ms to force CMD execution While(M133=0 or M140=0 or M145=0 or M233=0 or M240=0 or M245=0 or M333=0 or M340=0 or M345=0 or M433=0 or M440=0 or M445=0 or M533=0 or M540=0 or M545=0 or M633=0 or M640=0 or M645=0) EndWhile // Wait for all 6 motors to home ctr = 0 // Initialize counter variable MotorNumber=0 While(ctr < NumberOfMotors) // Activate and close the loop for all 6 motors MotorNumber=ctr+1 // Calculate which motor to use right now MtrNoTimes100 = MotorNumber*100 ; Compute and store for computational efficiency Ixx05_Index = MtrNoTimes100 + 5 ; Compute Ixx05 index for this motor Ixx06_Index = MtrNoTimes100 + 6 ; Compute Ixx06 index for this motor P(FirstPrevIxx05Index + ctr) = I(Ixx05_Index) ; Store old Ixx05 value so we can reset to this value after the move P(FirstPrevIxx06Index + ctr) = I(Ixx06_Index) ; Store old Ixx06 value so we can reset to this value after the move I(Ixx05_Index) = $10F0 + ctr ; Assign Ixx05 to open memory temporarily I(Ixx06_Index) = 1 ; Activate master position following temporarily ctr = ctr + 1 ; Increment loop counter EndWhile CMD"End Gat" ; End gathering CMD"Del Gat" ; Delete gather buffer CMD"Def Gat" ; Define gather buffer CMD"Gat" ; Start gathering ctr = 0 ; Initialize counter variable pMtrxxMasterPos = $43E8 ; Initialize pointer to point to motor #1 Master pos pMasterPosCmd = $10F0 ; Initialize pointer to open memory, master pos cmd for motor #1 While(ctr < NumberOfMotors) ; Command step to all 6 motors (motors 1-6) MotorNumber=ctr+1 ; Calculate which motor to use right now MtrNoTimes100 = MotorNumber*100 ; Compute and store for computational efficiency Ixx07_Index = MtrNoTimes100 + 7 ; Compute Ixx07 index for this motor Ixx08_Index = MtrNoTimes100 + 8 ; Compute Ixx08 index for this motor MasterPosCmd = MasterPosCmd + StepSize*(32/I(Ixx07_Index)*I(Ixx08_Index)) ; Command the position ctr = ctr + 1 ; Increment loop counter pMtrxxMasterPos = pMtrxxMasterPos + 1 ; Point to next motor's commanded position pMasterPosCmd = pMasterPosCmd + 1 ; Point to next open memory register EndWhile I5112=StepTime*8388608/I10 While(I5112>0) EndW ; Wait specified amount of time ctr = 0 ; Initialize loop counter pMtrxxMasterPos = $43E8 ; Initialize pointer to point to motor #1 Master pos pMasterPosCmd = $10F0 ; Initialize pointer to open memory, master pos cmd for motor #1 While(ctr < NumberOfMotors) ; Cycle through all 6 motors MotorNumber=ctr+1 ; Calculate which motor to use right now MtrNoTimes100 = MotorNumber*100 ; Compute and store for computational efficiency Ixx07_Index = MtrNoTimes100 + 7 ; Compute Ixx07 index for this motor Ixx08_Index = MtrNoTimes100 + 8 ; Compute Ixx08 index for this motor MasterPosCmd = MasterPosCmd - StepSize*(32/I(Ixx07_Index)*I(Ixx08_Index)) ctr = ctr + 1 ; Increment loop counter pMtrxxMasterPos = pMtrxxMasterPos + 1 ; Increment pointer to next motor's commanded position pMasterPosCmd = pMasterPosCmd + 1 ; Point to next open memory register EndWhile I5112=StepTime*8388608/I10 While(I5112>0) EndW ; Wait specified amount of time CMD"End Gat" ; End gathering ctr=0 ; Initialize counter variable MotorNumber=0 While(ctr < NumberOfMotors) MotorNumber=ctr+1 ; Calculate which motor to use right now Ixx05_Index = MotorNumber*100 + 5 ; Compute index for this motor's Ixx05 Ixx06_Index = MotorNumber*100 + 6 ; Compute index for this motor's Ixx06 I(Ixx05_Index) = P(FirstPrevIxx05Index + ctr) ; Restore previous Ixx05 setting I(Ixx06_Index) = P(FirstPrevIxx06Index + ctr) ; Restore previous Ixx06 setting Address#MotorNumber ; Address next motor CMD"K" ; Kill motor ctr = ctr + 1 ; Increment loop counter EndWhile Disable PLC 25 Close [/code] You will just need to adjust your Step Size [cts] by adjusting P138 and the Step Time [msec] in P139, and then run Enable PLC 25. Use the parabolic move to tune Kvff, Kaff, and Ixx68. For the parabolic move, the procedure is much simpler: [list=1] [*]Configure gathering settings for motors 1-6 using Quick Plot. Need to gather actual and commanded velocity, acceleration, and the following error. [*]Temporarily assign all motors to the same axis in the same coordinate system. [*]Home the motors if needed. [*]Begin gathering. [*]Execute a PVT move in the positive direction with a prescribed magnitude, time, and with a zero ending velocity. [*]Execute a PVT move in the negative direction with the same prescribed magnitude, time, and with a zero ending velocity. [*]End Gathering. [/list] Example motion program for this procedure: [code] #define ParabolicSize P140 ; - User Input [cts]: size of parabolic move #define ParabolicTime P141 ; - User Input [msec]: time for parabolic move ParabolicSize = 1000 ; cts - Default size of parabolic move ParabolicTime = 500 ; ms - Default move time for parabolic move &2 ; Address coordinate system 2 #1->X ; Assign motor 1 to X axis with 1 user unit per count #2->X ; Assign motor 2 to X axis with 1 user unit per count #3->X ; Assign motor 3 to X axis with 1 user unit per count #4->X ; Assign motor 4 to X axis with 1 user unit per count #5->X ; Assign motor 5 to X axis with 1 user unit per count #6->X ; Assign motor 6 to X axis with 1 user unit per count End Gat Del Gat Close Open Prog 900 Clear Dwell 0 PVT(ParabolicTime/2) Inc CMD"End Gat" CMD"Del Gat" CMD"Def Gat" CMD"Gat" Dwell 0 X(ParabolicSize):0 X(-ParabolicSize):0 Dwell 0 CMD"End Gat" Dwell 0 Close [/code] Now just make sure all your motors are in closed loop and then issue "&2 B900 R" to run the program. I arbitrarily chose coordinate system 2 and program number 900 for this example but you can adjust the numbering to whatever you need. Then you can examine the results of the gathered data and adjust your tuning parameters accordingly. PMAC may complain when you try to reassign your motors to this coordinate system but you can just issue "Undefine All", download these definitions and the program, and then once you finish your analysis you can issue "Undefine All" again and then reassign your original coordinate system settings. The way I have written these examples, you will need P33-P35, P133-148, and M1000-M1003 to be free for use, as well as open memory registers $10F0 through $10F5 (both the X and the Y registers of these addresses need to be available). However, you can adjust the #define definitions to use whatever P-Variables you want, and you an also adjust the open memory registers as needed. Note that I use a technique with M-Variables called "Indirect Addressing" to cycle through the open memory registers by changing the pointer definition - please see the Turbo PMAC User Manual under "Indirect Addressing" for more details on this technique. To avoid using that technique you could just hard-code a bunch of M-Variables to the necessary locations if you want, but the code would be longer and less general. If you have any problems with this please post your questions or email me directly. Thanks.
Link to comment
Share on other sites

Guest
This topic is now closed to further replies.
 Share


×
×
  • Create New...