00001 #include <robodyn_controllers/KdlTreeFk.h>
00002
00003 KdlTreeFk::KdlTreeFk()
00004 {
00005 }
00006
00007 KdlTreeFk::~KdlTreeFk()
00008 {
00009 }
00010
00011 void KdlTreeFk::getPose(const KDL::JntArray& joints, const std::string& name, KDL::Frame& frame)
00012 {
00013 if (fkSolver->JntToCart(joints, frame, name) < 0)
00014 {
00015 std::stringstream err;
00016 err << "KdlTreeFk::getPose() failed to get pose";
00017 NasaCommonLogging::Logger::log("gov.nasa.controllers.KdlTreeFk", log4cpp::Priority::ERROR, err.str());
00018 throw std::runtime_error(err.str());
00019 return;
00020 }
00021 }
00022
00023 void KdlTreeFk::getPoses(const KDL::JntArray& joints, std::map<std::string, KDL::Frame>& frames)
00024 {
00025 if (joints.rows() != tree.getNrOfJoints())
00026 {
00027 std::stringstream err;
00028 err << "getPoses() joints not properly sized";
00029 NasaCommonLogging::Logger::log("gov.nasa.controllers.KdlTreeFk", log4cpp::Priority::ERROR, err.str());
00030 throw std::runtime_error(err.str());
00031 return;
00032 }
00033
00034 KDL::Frame baseFrame;
00035
00036 if (frames.empty())
00037 {
00038 recursiveGetPoses(true, baseFrame, tree.getRootSegment(), joints, frames);
00039 }
00040 else
00041 {
00043
00044 for (std::map<std::string, KDL::Frame>::const_iterator it = frames.begin(); it != frames.end(); ++it)
00045 {
00046 if (tree.getSegment(it->first) == tree.getSegments().end())
00047 {
00048 std::stringstream err;
00049 err << "KdlTreeFk::getPoses() requested an unavailable pose";
00050 NasaCommonLogging::Logger::log("gov.nasa.controllers.KdlTreeFk", log4cpp::Priority::ERROR, err.str());
00051 throw std::runtime_error(err.str());
00052 return;
00053 }
00054 }
00055
00056 recursiveGetPoses(false, baseFrame, tree.getRootSegment(), joints, frames);
00057 }
00058 }
00059
00060 void KdlTreeFk::getVelocities(const KDL::JntArrayVel& joints, std::map<std::string, KDL::FrameVel>& frames)
00061 {
00062 if (joints.q.rows() != tree.getNrOfJoints() || joints.qdot.rows() != tree.getNrOfJoints())
00063 {
00064 std::stringstream err;
00065 err << "getVelocities() joints not properly sized";
00066 NasaCommonLogging::Logger::log("gov.nasa.controllers.KdlTreeFk", log4cpp::Priority::ERROR, err.str());
00067 throw std::runtime_error(err.str());
00068 return;
00069 }
00070
00071 KDL::FrameVel baseFrame;
00072
00073 if (frames.empty())
00074 {
00075 recursiveGetVels(true, baseFrame, tree.getRootSegment(), joints, frames);
00076 }
00077 else
00078 {
00080
00081 for (std::map<std::string, KDL::FrameVel>::const_iterator it = frames.begin(); it != frames.end(); ++it)
00082 {
00083 if (tree.getSegment(it->first) == tree.getSegments().end())
00084 {
00085 std::stringstream err;
00086 err << "KdlTreeFk::getVelocities() requested an unavailable pose";
00087 NasaCommonLogging::Logger::log("gov.nasa.controllers.KdlTreeFk", log4cpp::Priority::ERROR, err.str());
00088 throw std::runtime_error(err.str());
00089 return;
00090 }
00091 }
00092
00093 recursiveGetVels(false, baseFrame, tree.getRootSegment(), joints, frames);
00094 }
00095 }
00096
00097 void KdlTreeFk::initialize()
00098 {
00099 fkSolver.reset(new KDL::TreeFkSolverPos_recursive(tree));
00100 }
00101
00102 void KdlTreeFk::recursiveGetPoses(bool getAll, const KDL::Frame& baseFrame,
00103 const KDL::SegmentMap::const_iterator& it, const KDL::JntArray& joints, std::map<std::string, KDL::Frame>& frames)
00104 {
00106 const std::string& segmentName = it->first;
00107 const KDL::TreeElement& element = it->second;
00108 const KDL::Segment& segment = element.segment;
00109 KDL::Frame currentFrame = baseFrame * (segment.pose(joints(element.q_nr)));
00110
00111 if (getAll)
00112 {
00113 frames[segmentName] = currentFrame;
00114 }
00115 else
00116 {
00117 std::map<std::string, KDL::Frame>::iterator frameIt = frames.find(segmentName);
00118
00119 if (frameIt != frames.end())
00120 {
00121 frameIt->second = currentFrame;
00122 }
00123 }
00124
00126 const std::vector<KDL::SegmentMap::const_iterator>& children = element.children;
00127
00128 for (std::vector<KDL::SegmentMap::const_iterator>::const_iterator childIt = children.begin();
00129 childIt != children.end(); ++childIt)
00130 {
00131 recursiveGetPoses(getAll, currentFrame, *childIt, joints, frames);
00132 }
00133 }
00134
00135 void KdlTreeFk::recursiveGetVels(bool getAll, const KDL::FrameVel& baseFrame,
00136 const KDL::SegmentMap::const_iterator& it, const KDL::JntArrayVel& joints, std::map<std::string, KDL::FrameVel>& frames)
00137 {
00139 const std::string& segmentName = it->first;
00140 const KDL::TreeElement& element = it->second;
00141 const KDL::Segment& segment = element.segment;
00142 unsigned int q_nr = element.q_nr;
00143 KDL::FrameVel currentFrame = baseFrame * KDL::FrameVel(segment.pose(joints.q(q_nr)),
00144 segment.twist(joints.q(q_nr), joints.qdot(q_nr)));
00145
00146 if (getAll)
00147 {
00148 frames[segmentName] = currentFrame;
00149 }
00150 else
00151 {
00152 std::map<std::string, KDL::FrameVel>::iterator frameIt = frames.find(segmentName);
00153
00154 if (frameIt != frames.end())
00155 {
00156 frameIt->second = currentFrame;
00157 }
00158 }
00159
00161 const std::vector<KDL::SegmentMap::const_iterator>& children = element.children;
00162
00163 for (std::vector<KDL::SegmentMap::const_iterator>::const_iterator childIt = children.begin();
00164 childIt != children.end(); ++childIt)
00165 {
00166 recursiveGetVels(getAll, currentFrame, *childIt, joints, frames);
00167 }
00168 }
00169