00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063
00064
00065
00066
00072
00073 static const char rcsid[] = "$Id: dynamics.cpp,v 1.34 2006/05/19 18:32:30 gourdeau Exp $";
00074
00075 #include "robot.h"
00076
00077 #ifdef use_namespace
00078 namespace ROBOOP {
00079 using namespace NEWMAT;
00080 #endif
00081
00082
00083 ReturnMatrix Robot_basic::inertia(const ColumnVector & q)
00085 {
00086 Matrix M(dof,dof);
00087 ColumnVector torque(dof);
00088 set_q(q);
00089 for(int i = 1; i <= dof; i++) {
00090 for(int j = 1; j <= dof; j++) {
00091 torque(j) = (i == j ? 1.0 : 0.0);
00092 }
00093 torque = torque_novelocity(torque);
00094 M.Column(i) = torque;
00095 }
00096 M.Release(); return M;
00097 }
00098
00099
00100 ReturnMatrix Robot_basic::acceleration(const ColumnVector & q,
00101 const ColumnVector & qp,
00102 const ColumnVector & tau_cmd)
00104 {
00105 ColumnVector qpp(dof);
00106 qpp = 0.0;
00107 qpp = inertia(q).i()*(tau_cmd-torque(q,qp,qpp));
00108 qpp.Release();
00109 return qpp;
00110 }
00111
00112 ReturnMatrix Robot_basic::acceleration(const ColumnVector & q, const ColumnVector & qp,
00113 const ColumnVector & tau_cmd, const ColumnVector & Fext,
00114 const ColumnVector & Next)
00127 {
00128 ColumnVector qpp(dof);
00129 qpp = 0.0;
00130 qpp = inertia(q).i()*(tau_cmd-torque(q, qp, qpp, Fext, Next));
00131 qpp.Release();
00132 return qpp;
00133 }
00134
00135 ReturnMatrix Robot::torque(const ColumnVector & q, const ColumnVector & qp,
00136 const ColumnVector & qpp)
00141 {
00142 ColumnVector Fext(3), Next(3);
00143 Fext = 0;
00144 Next = 0;
00145 return torque(q, qp, qpp, Fext, Next);
00146 }
00147
00148 ReturnMatrix Robot::torque(const ColumnVector & q, const ColumnVector & qp,
00149 const ColumnVector & qpp, const ColumnVector & Fext,
00150 const ColumnVector & Next)
00215 {
00216 int i;
00217 ColumnVector ltorque(dof);
00218 Matrix Rt, temp;
00219 if(q.Nrows() != dof) error("q has wrong dimension");
00220 if(qp.Nrows() != dof) error("qp has wrong dimension");
00221 if(qpp.Nrows() != dof) error("qpp has wrong dimension");
00222 set_q(q);
00223 set_qp(qp);
00224
00225 vp[0] = gravity;
00226 for(i = 1; i <= dof; i++) {
00227 Rt = links[i].R.t();
00228 if(links[i].get_joint_type() == 0) {
00229 w[i] = Rt*(w[i-1] + z0*qp(i));
00230 wp[i] = Rt*(wp[i-1] + z0*qpp(i)
00231 + CrossProduct(w[i-1],z0*qp(i)));
00232 vp[i] = CrossProduct(wp[i],p[i])
00233 + CrossProduct(w[i],CrossProduct(w[i],p[i]))
00234 + Rt*(vp[i-1]);
00235 } else {
00236 w[i] = Rt*w[i-1];
00237 wp[i] = Rt*wp[i-1];
00238 vp[i] = Rt*(vp[i-1] + z0*qpp(i))
00239 + 2.0*CrossProduct(w[i],Rt*z0*qp(i))
00240 + CrossProduct(wp[i],p[i])
00241 + CrossProduct(w[i],CrossProduct(w[i],p[i]));
00242 }
00243 a[i] = CrossProduct(wp[i],links[i].r)
00244 + CrossProduct(w[i],CrossProduct(w[i],links[i].r))
00245 + vp[i];
00246 }
00247
00248 for(i = dof; i >= 1; i--) {
00249 F[i] = a[i] * links[i].m;
00250 N[i] = links[i].I*wp[i] + CrossProduct(w[i],links[i].I*w[i]);
00251 if(i == dof) {
00252 f[i] = F[i] + Fext;
00253 n[i] = CrossProduct(p[i],f[i])
00254 + CrossProduct(links[i].r,F[i]) + N[i] + Next;
00255 } else {
00256 f[i] = links[i+1].R*f[i+1] + F[i];
00257 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i],f[i])
00258 + CrossProduct(links[i].r,F[i]) + N[i];
00259 }
00260 if(links[i].get_joint_type() == 0)
00261 temp = ((z0.t()*links[i].R)*n[i]);
00262 else
00263 temp = ((z0.t()*links[i].R)*f[i]);
00264 ltorque(i) = temp(1,1)
00265 + links[i].Im*links[i].Gr*links[i].Gr*qpp(i)
00266 + links[i].Gr*(links[i].Gr*links[i].B*qp(i) + links[i].Cf*sign(qp(i)));
00267 }
00268
00269 ltorque.Release(); return ltorque;
00270 }
00271
00272 ReturnMatrix Robot::torque_novelocity(const ColumnVector & qpp)
00277 {
00278 int i;
00279 ColumnVector ltorque(dof);
00280 Matrix Rt, temp;
00281 if(qpp.Nrows() != dof) error("qpp has wrong dimension");
00282
00283 vp[0] = 0.0;
00284 for(i = 1; i <= dof; i++) {
00285 Rt = links[i].R.t();
00286 if(links[i].get_joint_type() == 0) {
00287 wp[i] = Rt*(wp[i-1] + z0*qpp(i));
00288 vp[i] = CrossProduct(wp[i],p[i])
00289 + Rt*(vp[i-1]);
00290 } else {
00291 wp[i] = Rt*wp[i-1];
00292 vp[i] = Rt*(vp[i-1] + z0*qpp(i))
00293 + CrossProduct(wp[i],p[i]);
00294 }
00295 a[i] = CrossProduct(wp[i],links[i].r) + vp[i];
00296 }
00297
00298 for(i = dof; i >= 1; i--) {
00299 F[i] = a[i] * links[i].m;
00300 N[i] = links[i].I*wp[i];
00301 if(i == dof) {
00302 f_nv[i] = F[i];
00303 n_nv[i] = CrossProduct(p[i],f_nv[i])
00304 + CrossProduct(links[i].r,F[i]) + N[i];
00305 } else {
00306 f_nv[i] = links[i+1].R*f_nv[i+1] + F[i];
00307 n_nv[i] = links[i+1].R*n_nv[i+1] + CrossProduct(p[i],f_nv[i])
00308 + CrossProduct(links[i].r,F[i]) + N[i];
00309 }
00310 if(links[i].get_joint_type() == 0)
00311 temp = ((z0.t()*links[i].R)*n_nv[i]);
00312 else
00313 temp = ((z0.t()*links[i].R)*f_nv[i]);
00314 ltorque(i) = temp(1,1) + links[i].Im*links[i].Gr*links[i].Gr*qpp(i);
00315
00316 }
00317
00318 ltorque.Release(); return ltorque;
00319 }
00320
00321 ReturnMatrix Robot::G()
00323 {
00324 int i;
00325 ColumnVector ltorque(dof);
00326 Matrix Rt, temp;
00327
00328 vp[0] = gravity;
00329 for(i = 1; i <= dof; i++) {
00330 Rt = links[i].R.t();
00331 if(links[i].get_joint_type() == 0)
00332 vp[i] = Rt*(vp[i-1]);
00333 else
00334 vp[i] = Rt*vp[i-1];
00335
00336 a[i] = vp[i];
00337 }
00338
00339 for(i = dof; i >= 1; i--) {
00340 F[i] = a[i] * links[i].m;
00341 if(i == dof) {
00342 f[i] = F[i];
00343 n[i] = CrossProduct(p[i],f[i])
00344 + CrossProduct(links[i].r,F[i]);
00345 } else {
00346 f[i] = links[i+1].R*f[i+1] + F[i];
00347 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i],f[i])
00348 + CrossProduct(links[i].r,F[i]);
00349 }
00350 if(links[i].get_joint_type() == 0)
00351 temp = ((z0.t()*links[i].R)*n[i]);
00352 else
00353 temp = ((z0.t()*links[i].R)*f[i]);
00354 ltorque(i) = temp(1,1);
00355 }
00356
00357 ltorque.Release(); return ltorque;
00358 }
00359
00360 ReturnMatrix Robot::C(const ColumnVector & qp)
00362 {
00363 int i;
00364 ColumnVector ltorque(dof);
00365 Matrix Rt, temp;
00366 if(qp.Nrows() != dof) error("qp has wrong dimension");
00367
00368 vp[0]=0;
00369 for(i = 1; i <= dof; i++) {
00370 Rt = links[i].R.t();
00371 if(links[i].get_joint_type() == 0) {
00372 w[i] = Rt*(w[i-1] + z0*qp(i));
00373 wp[i] = Rt*(wp[i-1] + CrossProduct(w[i-1],z0*qp(i)));
00374 vp[i] = CrossProduct(wp[i],p[i])
00375 + CrossProduct(w[i],CrossProduct(w[i],p[i]))
00376 + Rt*(vp[i-1]);
00377 } else {
00378 w[i] = Rt*w[i-1];
00379 wp[i] = Rt*wp[i-1];
00380 vp[i] = Rt*vp[i-1] + 2.0*CrossProduct(w[i],Rt*z0*qp(i))
00381 + CrossProduct(wp[i],p[i])
00382 + CrossProduct(w[i],CrossProduct(w[i],p[i]));
00383 }
00384 a[i] = CrossProduct(wp[i],links[i].r)
00385 + CrossProduct(w[i],CrossProduct(w[i],links[i].r))
00386 + vp[i];
00387 }
00388
00389 for(i = dof; i >= 1; i--) {
00390 F[i] = a[i] * links[i].m;
00391 N[i] = links[i].I*wp[i] + CrossProduct(w[i],links[i].I*w[i]);
00392 if(i == dof) {
00393 f[i] = F[i];
00394 n[i] = CrossProduct(p[i],f[i])
00395 + CrossProduct(links[i].r,F[i]) + N[i];
00396 } else {
00397 f[i] = links[i+1].R*f[i+1] + F[i];
00398 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i],f[i])
00399 + CrossProduct(links[i].r,F[i]) + N[i];
00400 }
00401 if(links[i].get_joint_type() == 0)
00402 temp = ((z0.t()*links[i].R)*n[i]);
00403 else
00404 temp = ((z0.t()*links[i].R)*f[i]);
00405 ltorque(i) = temp(1,1)
00406 + links[i].Gr*(links[i].Gr*links[i].B*qp(i) + links[i].Cf*sign(qp(i)));
00407 }
00408
00409 ltorque.Release(); return ltorque;
00410 }
00411
00412 ReturnMatrix mRobot::torque(const ColumnVector & q, const ColumnVector & qp,
00413 const ColumnVector & qpp)
00415 {
00416 ColumnVector Fext(3), Next(3);
00417 Fext = 0;
00418 Next = 0;
00419 return torque(q, qp, qpp, Fext, Next);
00420 }
00421
00422 ReturnMatrix mRobot::torque(const ColumnVector & q, const ColumnVector & qp,
00423 const ColumnVector & qpp, const ColumnVector & Fext_,
00424 const ColumnVector & Next_)
00487 {
00488 int i;
00489 ColumnVector ltorque(dof);
00490 Matrix Rt, temp;
00491 if(q.Nrows() != dof) error("q has wrong dimension");
00492 if(qp.Nrows() != dof) error("qp has wrong dimension");
00493 if(qpp.Nrows() != dof) error("qpp has wrong dimension");
00494 set_q(q);
00495 set_qp(qp);
00496
00497 vp[0] = gravity;
00498 for(i = 1; i <= dof; i++) {
00499 Rt = links[i].R.t();
00500 if(links[i].get_joint_type() == 0) {
00501 w[i] = Rt*w[i-1] + z0*qp(i);
00502 wp[i] = Rt*wp[i-1] + CrossProduct(Rt*w[i-1],z0*qp(i))
00503 + z0*qpp(i);
00504 vp[i] = Rt*(CrossProduct(wp[i-1],p[i])
00505 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i]))
00506 + vp[i-1]);
00507 } else {
00508 w[i] = Rt*w[i-1];
00509 wp[i] = Rt*wp[i-1];
00510 vp[i] = Rt*(vp[i-1] + CrossProduct(wp[i-1],p[i])
00511 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i])))
00512 + z0*qpp(i)+ 2.0*CrossProduct(w[i],z0*qp(i));
00513 }
00514 a[i] = CrossProduct(wp[i],links[i].r)
00515 + CrossProduct(w[i],CrossProduct(w[i],links[i].r))
00516 + vp[i];
00517 }
00518
00519
00520 ColumnVector Fext(3), Next(3);
00521 if(fix)
00522 {
00523 Fext = links[dof+fix].R*Fext_;
00524 Next = links[dof+fix].R*Next_;
00525 }
00526 else
00527 {
00528 Fext = Fext_;
00529 Next = Next_;
00530 }
00531
00532 for(i = dof; i >= 1; i--) {
00533 F[i] = a[i] * links[i].m;
00534 N[i] = links[i].I*wp[i] + CrossProduct(w[i],links[i].I*w[i]);
00535 if(i == dof) {
00536 f[i] = F[i] + Fext;
00537 n[i] = CrossProduct(links[i].r,F[i]) + N[i] + Next;
00538 } else {
00539 f[i] = links[i+1].R*f[i+1] + F[i];
00540 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i+1],links[i+1].R*f[i+1])
00541 + CrossProduct(links[i].r,F[i]) + N[i];
00542 }
00543 if(links[i].get_joint_type() == 0)
00544 temp = (z0.t()*n[i]);
00545 else
00546 temp = (z0.t()*f[i]);
00547 ltorque(i) = temp(1,1)
00548 + links[i].Im*links[i].Gr*links[i].Gr*qpp(i)
00549 + links[i].Gr*(links[i].Gr*links[i].B*qp(i) + links[i].Cf*sign(qp(i)));
00550 }
00551
00552 ltorque.Release(); return ltorque;
00553 }
00554
00555 ReturnMatrix mRobot::torque_novelocity(const ColumnVector & qpp)
00557 {
00558 int i;
00559 ColumnVector ltorque(dof);
00560 Matrix Rt, temp;
00561 if(qpp.Ncols() != 1 || qpp.Nrows() != dof) error("qpp has wrong dimension");
00562
00563 vp[0] = 0.0;
00564 for(i = 1; i <= dof; i++) {
00565 Rt = links[i].R.t();
00566 if(links[i].get_joint_type() == 0) {
00567 wp[i] = Rt*wp[i-1] + z0*qpp(i);
00568 vp[i] = Rt*(CrossProduct(wp[i-1],p[i]) + vp[i-1]);
00569 } else {
00570 wp[i] = Rt*wp[i-1];
00571 vp[i] = Rt*(vp[i-1] + CrossProduct(wp[i-1],p[i]))
00572 + z0*qpp(i);
00573 }
00574 a[i] = CrossProduct(wp[i],links[i].r) + vp[i];
00575 }
00576
00577 for(i = dof; i >= 1; i--) {
00578 F[i] = a[i] * links[i].m;
00579 N[i] = links[i].I*wp[i];
00580 if(i == dof) {
00581 f_nv[i] = F[i];
00582 n_nv[i] = CrossProduct(links[i].r,F[i]) + N[i];
00583 } else {
00584 f_nv[i] = links[i+1].R*f_nv[i+1] + F[i];
00585 n_nv[i] = links[i+1].R*n_nv[i+1] + CrossProduct(p[i+1],links[i+1].R*f_nv[i+1])
00586 + CrossProduct(links[i].r,F[i]) + N[i];
00587 }
00588
00589 if(links[i].get_joint_type() == 0)
00590 temp = (z0.t()*n_nv[i]);
00591 else
00592 temp = (z0.t()*f_nv[i]);
00593 ltorque(i) = temp(1,1) + links[i].Im*links[i].Gr*links[i].Gr*qpp(i);
00594 }
00595
00596 ltorque.Release(); return ltorque;
00597 }
00598
00599 ReturnMatrix mRobot::G()
00601 {
00602 int i;
00603 ColumnVector ltorque(dof);
00604 Matrix Rt, temp;
00605
00606 vp[0] = gravity;
00607 for(i = 1; i <= dof; i++) {
00608 Rt = links[i].R.t();
00609 if(links[i].get_joint_type() == 0)
00610 vp[i] = Rt*vp[i-1];
00611 else
00612 vp[i] = Rt*vp[i-1];
00613 a[i] = vp[i];
00614 }
00615
00616 for(i = dof; i >= 1; i--) {
00617 F[i] = a[i] * links[i].m;
00618 if(i == dof) {
00619 f[i] = F[i];
00620 n[i] = CrossProduct(links[i].r,F[i]);
00621 } else {
00622 f[i] = links[i+1].R*f[i+1] + F[i];
00623 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i+1],links[i+1].R*f[i+1])
00624 + CrossProduct(links[i].r,F[i]);
00625 }
00626 if(links[i].get_joint_type() == 0)
00627 temp = (z0.t()*n[i]);
00628 else
00629 temp = (z0.t()*f[i]);
00630 ltorque(i) = temp(1,1);
00631 }
00632
00633 ltorque.Release(); return ltorque;
00634 }
00635
00636 ReturnMatrix mRobot::C(const ColumnVector & qp)
00638 {
00639 int i;
00640 ColumnVector ltorque(dof);
00641 Matrix Rt, temp;
00642 if(qp.Nrows() != dof) error("qp has wrong dimension");
00643
00644 vp[0] = 0;
00645 for(i = 1; i <= dof; i++) {
00646 Rt = links[i].R.t();
00647 if(links[i].get_joint_type() == 0) {
00648 w[i] = Rt*w[i-1] + z0*qp(i);
00649 wp[i] = Rt*wp[i-1] + CrossProduct(Rt*w[i-1],z0*qp(i));
00650 vp[i] = Rt*(CrossProduct(wp[i-1],p[i])
00651 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i]))
00652 + vp[i-1]);
00653 } else {
00654 w[i] = Rt*w[i-1];
00655 wp[i] = Rt*wp[i-1];
00656 vp[i] = Rt*(vp[i-1] + CrossProduct(wp[i-1],p[i])
00657 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i])))
00658 + 2.0*CrossProduct(w[i],z0*qp(i));
00659 }
00660 a[i] = CrossProduct(wp[i],links[i].r)
00661 + CrossProduct(w[i],CrossProduct(w[i],links[i].r))
00662 + vp[i];
00663 }
00664
00665 for(i = dof; i >= 1; i--) {
00666 F[i] = a[i] * links[i].m;
00667 N[i] = links[i].I*wp[i] + CrossProduct(w[i],links[i].I*w[i]);
00668 if(i == dof) {
00669 f[i] = F[i];
00670 n[i] = CrossProduct(links[i].r,F[i]) + N[i];
00671 } else {
00672 f[i] = links[i+1].R*f[i+1] + F[i];
00673 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i+1],links[i+1].R*f[i+1])
00674 + CrossProduct(links[i].r,F[i]) + N[i];
00675 }
00676 if(links[i].get_joint_type() == 0)
00677 temp = (z0.t()*n[i]);
00678 else
00679 temp = (z0.t()*f[i]);
00680 ltorque(i) = temp(1,1)
00681 + links[i].Gr*(links[i].Gr*links[i].B*qp(i) + links[i].Cf*sign(qp(i)));
00682 }
00683
00684 ltorque.Release(); return ltorque;
00685 }
00686
00687 ReturnMatrix mRobot_min_para::torque(const ColumnVector & q, const ColumnVector & qp,
00688 const ColumnVector & qpp)
00690 {
00691 ColumnVector Fext(3), Next(3);
00692 Fext = 0;
00693 Next = 0;
00694 return torque(q, qp, qpp, Fext, Next);
00695 }
00696
00697 ReturnMatrix mRobot_min_para::torque(const ColumnVector & q, const ColumnVector & qp,
00698 const ColumnVector & qpp, const ColumnVector & Fext_,
00699 const ColumnVector & Next_)
00708 {
00709 int i;
00710 ColumnVector ltorque(dof);
00711 Matrix Rt, temp;
00712 if(q.Nrows() != dof) error("q has wrong dimension");
00713 if(qp.Nrows() != dof) error("qp has wrong dimension");
00714 if(qpp.Nrows() != dof) error("qpp has wrong dimension");
00715 set_q(q);
00716 set_qp(qp);
00717
00718 vp[0] = gravity;
00719 for(i = 1; i <= dof; i++) {
00720 Rt = links[i].R.t();
00721 if(links[i].get_joint_type() == 0)
00722 {
00723 w[i] = Rt*w[i-1] + z0*qp(i);
00724 wp[i] = Rt*(wp[i-1] + CrossProduct(w[i-1],z0*qp(i)))
00725 + z0*qpp(i);
00726 vp[i] = Rt*(CrossProduct(wp[i-1],p[i])
00727 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i]))
00728 + vp[i-1]);
00729 }
00730 else
00731 {
00732 w[i] = Rt*w[i-1];
00733 wp[i] = Rt*wp[i-1];
00734 vp[i] = Rt*(vp[i-1] + CrossProduct(wp[i-1],p[i])
00735 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i])))
00736 + z0*qpp(i)+ 2.0*CrossProduct(w[i],z0*qp(i));
00737 }
00738 }
00739
00740 ColumnVector Fext(3), Next(3);
00741 if(fix)
00742 {
00743 Fext = links[dof+fix].R*Fext_;
00744 Next = links[dof+fix].R*Next_;
00745 }
00746 else
00747 {
00748 Fext = Fext_;
00749 Next = Next_;
00750 }
00751
00752 for(i = dof; i >= 1; i--)
00753 {
00754 F[i] = vp[i]*links[i].m + CrossProduct(wp[i], links[i].mc) +
00755 CrossProduct(w[i], CrossProduct(w[i], links[i].mc));
00756 N[i] = links[i].I*wp[i] + CrossProduct(w[i],links[i].I*w[i]) +
00757 CrossProduct(-vp[i], links[i].mc);
00758 if(i == dof)
00759 {
00760 f[i] = F[i] + Fext;
00761 n[i] = N[i] + Next;
00762 }
00763 else
00764 {
00765 f[i] = links[i+1].R*f[i+1] + F[i];
00766 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i+1],links[i+1].R*f[i+1]) + N[i];
00767 }
00768
00769 if(links[i].get_joint_type() == 0)
00770 temp = (z0.t()*n[i]);
00771 else
00772 temp = (z0.t()*f[i]);
00773 ltorque(i) = temp(1,1)
00774 + links[i].Im*links[i].Gr*links[i].Gr*qpp(i)
00775 + links[i].Gr*(links[i].Gr*links[i].B*qp(i) + links[i].Cf*sign(qp(i)));
00776 }
00777
00778 ltorque.Release(); return ltorque;
00779 }
00780
00781
00782 ReturnMatrix mRobot_min_para::torque_novelocity(const ColumnVector & qpp)
00784 {
00785 int i;
00786 ColumnVector ltorque(dof);
00787 Matrix Rt, temp;
00788 if(qpp.Ncols() != 1 || qpp.Nrows() != dof) error("qpp has wrong dimension");
00789
00790 vp[0] = 0.0;
00791 for(i = 1; i <= dof; i++)
00792 {
00793 Rt = links[i].R.t();
00794 if(links[i].get_joint_type() == 0)
00795 {
00796 wp[i] = Rt*wp[i-1] + z0*qpp(i);
00797 vp[i] = Rt*(CrossProduct(wp[i-1],p[i]) + vp[i-1]);
00798 }
00799 else
00800 {
00801 wp[i] = Rt*wp[i-1];
00802 vp[i] = Rt*(vp[i-1] + CrossProduct(wp[i-1],p[i]))
00803 + z0*qpp(i);
00804 }
00805 }
00806
00807 for(i = dof; i >= 1; i--)
00808 {
00809 F[i] = vp[i]*links[i].m + CrossProduct(wp[i], links[i].mc);
00810 N[i] = links[i].I*wp[i] + CrossProduct(-vp[i], links[i].mc);
00811 if(i == dof)
00812 {
00813 f_nv[i] = F[i];
00814 n_nv[i] = N[i];
00815 }
00816 else
00817 {
00818 f_nv[i] = links[i+1].R*f_nv[i+1] + F[i];
00819 n_nv[i] = links[i+1].R*n_nv[i+1] + CrossProduct(p[i+1],links[i+1].R*f_nv[i+1]) + N[i];
00820 }
00821
00822 if(links[i].get_joint_type() == 0)
00823 temp = (z0.t()*n_nv[i]);
00824 else
00825 temp = (z0.t()*f_nv[i]);
00826 ltorque(i) = temp(1,1) + links[i].Im*links[i].Gr*links[i].Gr*qpp(i);
00827 }
00828
00829 ltorque.Release(); return ltorque;
00830 }
00831
00832 ReturnMatrix mRobot_min_para::G()
00834 {
00835 int i;
00836 ColumnVector ltorque(dof);
00837 Matrix Rt, temp;
00838
00839 vp[0] = gravity;
00840 for(i = 1; i <= dof; i++) {
00841 Rt = links[i].R.t();
00842 if(links[i].get_joint_type() == 0)
00843 vp[i] = Rt*vp[i-1];
00844 else
00845 vp[i] = Rt*vp[i-1];
00846 }
00847
00848 for(i = dof; i >= 1; i--)
00849 {
00850 F[i] = vp[i]*links[i].m;
00851 N[i] = CrossProduct(-vp[i], links[i].mc);
00852 if(i == dof)
00853 {
00854 f[i] = F[i];
00855 n[i] = N[i];
00856 }
00857 else
00858 {
00859 f[i] = links[i+1].R*f[i+1] + F[i];
00860 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i+1],links[i+1].R*f[i+1]) + N[i];
00861 }
00862
00863 if(links[i].get_joint_type() == 0)
00864 temp = (z0.t()*n[i]);
00865 else
00866 temp = (z0.t()*f[i]);
00867 ltorque(i) = temp(1,1);
00868 }
00869
00870 ltorque.Release(); return ltorque;
00871 }
00872
00873 ReturnMatrix mRobot_min_para::C(const ColumnVector & qp)
00875 {
00876 int i;
00877 ColumnVector ltorque(dof);
00878 Matrix Rt, temp;
00879 if(qp.Nrows() != dof) error("qp has wrong dimension");
00880 set_qp(qp);
00881
00882 vp[0] = 0;
00883 for(i = 1; i <= dof; i++) {
00884 Rt = links[i].R.t();
00885 if(links[i].get_joint_type() == 0)
00886 {
00887 w[i] = Rt*w[i-1] + z0*qp(i);
00888 wp[i] = Rt*(wp[i-1] + CrossProduct(w[i-1],z0*qp(i)));
00889 vp[i] = Rt*(CrossProduct(wp[i-1],p[i])
00890 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i]))
00891 + vp[i-1]);
00892 }
00893 else
00894 {
00895 w[i] = Rt*w[i-1];
00896 wp[i] = Rt*wp[i-1];
00897 vp[i] = Rt*(vp[i-1] + CrossProduct(wp[i-1],p[i])
00898 + CrossProduct(w[i-1],CrossProduct(w[i-1],p[i])))
00899 + 2.0*CrossProduct(w[i],z0*qp(i));
00900 }
00901 }
00902
00903 for(i = dof; i >= 1; i--)
00904 {
00905 F[i] = vp[i]*links[i].m + CrossProduct(wp[i], links[i].mc) +
00906 CrossProduct(w[i], CrossProduct(w[i], links[i].mc));
00907 N[i] = links[i].I*wp[i] + CrossProduct(w[i],links[i].I*w[i]) +
00908 CrossProduct(-vp[i], links[i].mc);
00909 if(i == dof)
00910 {
00911 f[i] = F[i];
00912 n[i] = N[i];
00913 }
00914 else
00915 {
00916 f[i] = links[i+1].R*f[i+1] + F[i];
00917 n[i] = links[i+1].R*n[i+1] + CrossProduct(p[i+1],links[i+1].R*f[i+1]) + N[i];
00918 }
00919
00920 if(links[i].get_joint_type() == 0)
00921 temp = (z0.t()*n[i]);
00922 else
00923 temp = (z0.t()*f[i]);
00924 ltorque(i) = temp(1,1)
00925 + links[i].Gr*(links[i].Gr*links[i].B*qp(i) + links[i].Cf*sign(qp(i)));
00926 }
00927
00928 ltorque.Release(); return ltorque;
00929 }
00930
00931 #ifdef use_namespace
00932 }
00933 #endif
00934