00001
00002 #ifndef INCLUDED_IKThreeLink_h_
00003 #define INCLUDED_IKThreeLink_h_
00004
00005 #include "IKSolver.h"
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 class IKThreeLink : public IKSolver {
00021 public:
00022
00023 IKThreeLink() : IKSolver(), invertThird(false), hasInverseSolution(false), inverseKnee() {}
00024
00025 virtual bool solve(const Point& pEff, const Rotation& oriEff, KinematicJoint& j, const Position& pTgt, float posPri, const Orientation& oriTgt, float oriPri) const;
00026 using IKSolver::solve;
00027
00028 virtual IKSolver::StepResult_t step(const Point& pEff, const Rotation& oriEff, KinematicJoint& j, const Position& pTgt, float pDist, float posPri, const Orientation& oriTgt, float oriDist, float oriPri) const;
00029 using IKSolver::step;
00030
00031 protected:
00032
00033 static const float EPSILON;
00034
00035 static unsigned int setLinks(KinematicJoint& eff, KinematicJoint* links[], unsigned int remain);
00036
00037
00038 void computeFirstLink(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool& valid) const {
00039 if(curlink.jointType==KinematicJoint::PRISMATIC) {
00040 computeFirstLinkPrismatic(curlink,Pobj,endlink,Plink,valid);
00041 } else {
00042 computeFirstLinkRevolute(curlink,Pobj,endlink,Plink,valid);
00043 }
00044 }
00045
00046 void computeFirstLinkRevolute(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool& valid) const;
00047
00048 void computeFirstLinkPrismatic(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool& valid) const;
00049
00050
00051 void computeSecondLink(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool invert, bool& valid) const {
00052 if(curlink.jointType==KinematicJoint::PRISMATIC) {
00053 computeSecondLinkPrismatic(curlink,Pobj,endlink,Plink,invert,valid);
00054 } else {
00055 computeSecondLinkRevolute(curlink,Pobj,endlink,Plink,invert,valid);
00056 }
00057 }
00058
00059 void computeSecondLinkRevolute(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool invert, bool& valid) const;
00060
00061 void computeSecondLinkPrismatic(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool invert, bool& valid) const;
00062
00063
00064 void computeThirdLink(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool invert, bool& valid) const {
00065 if(curlink.jointType==KinematicJoint::PRISMATIC) {
00066 computeThirdLinkPrismatic(curlink,Pobj,endlink,Plink,invert,valid);
00067 } else {
00068 computeThirdLinkRevolute(curlink,Pobj,endlink,Plink,invert,valid);
00069 }
00070 }
00071
00072 void computeThirdLinkRevolute(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool invert, bool& valid) const;
00073
00074 void computeThirdLinkPrismatic(KinematicJoint& curlink, const fmat::Column<3>& Pobj, KinematicJoint& endlink, const fmat::Column<3>& Plink, bool invert, bool& valid) const;
00075
00076
00077 static fmat::fmatReal computePrismaticQ(fmat::fmatReal objD2, fmat::fmatReal neckD2, fmat::fmatReal inner);
00078
00079
00080 static float normalize_angle(float x) { return x - static_cast<float>( rint(x/(2*M_PI)) * (2*M_PI) ); }
00081
00082 bool invertThird;
00083
00084 mutable bool hasInverseSolution;
00085 mutable float inverseKnee;
00086
00087 private:
00088
00089 static const std::string autoRegisterIKThreeLink;
00090 };
00091
00092
00093
00094
00095
00096 #endif