00001
00002 #ifndef _SHAPE_SPACE_PLANNER_BASE_H_
00003 #define _SHAPE_SPACE_PLANNER_BASE_H_
00004
00005 #include "Motion/KinematicJoint.h"
00006 #include "Planners/PlannerObstacles.h"
00007 #include "DualCoding/DualCoding.h"
00008 #include "GenericRRT.h"
00009
00010
00011
00012
00013 template <size_t N>
00014 class ShapeSpaceCollisionCheckerBase {
00015 protected:
00016
00017 DualCoding::Shape<DualCoding::PolygonData> worldBounds;
00018
00019 float const inflation;
00020
00021
00022 std::vector<PlannerObstacle<N>*> obstacles;
00023
00024 public:
00025 ShapeSpaceCollisionCheckerBase(ShapeSpace &shs,
00026 const Shape<PolygonData> &_worldBounds,
00027 float _inflation);
00028
00029 virtual ~ShapeSpaceCollisionCheckerBase();
00030
00031 const Shape<PolygonData> getWorldBounds() const { return worldBounds; }
00032
00033 BoundingBox<N> getObstacleBoundingBox() const;
00034
00035
00036 void getRobotObstacle(const KinematicJoint &j, HierarchicalObstacle &hierObs) const;
00037 void addObstacleFromCollisionModel(const LinkComponent& j, const fmat::Transform& robotT, HierarchicalObstacle& hierObs) const;
00038
00039
00040 void addObstaclesToShapeSpace(DualCoding::ShapeSpace & shs) const;
00041 };
00042
00043 template <size_t N>
00044 BoundingBox<N> ShapeSpaceCollisionCheckerBase<N>::getObstacleBoundingBox() const {
00045 if (obstacles.empty()) return BoundingBox<N>();
00046
00047 BoundingBox<N> bounds = obstacles.front()->getBoundingBox();
00048
00049 for (unsigned int i = 0; i < obstacles.size(); i++) {
00050 bounds.expand(obstacles[i]->getBoundingBox());
00051 }
00052 return bounds;
00053 }
00054
00055 template <size_t N>
00056 ShapeSpaceCollisionCheckerBase<N>::ShapeSpaceCollisionCheckerBase(ShapeSpace &shs,
00057 const Shape<PolygonData> &_worldBounds,
00058 float _inflation) :
00059 worldBounds(_worldBounds), inflation(_inflation), obstacles() {
00060 SHAPEROOTVEC_ITERATE(shs, s) {
00061 if ( s->getId() != DualCoding::VRmixin::theAgent->getId() && s->isObstacle() )
00062 PlannerObstacle<N>::convertShapeToPlannerObstacle(s, inflation, obstacles);
00063 } END_ITERATE;
00064
00065 DualCoding::Point location = VRmixin::theAgent->getCentroid();
00066 }
00067
00068 template <size_t N>
00069 ShapeSpaceCollisionCheckerBase<N>::~ShapeSpaceCollisionCheckerBase() {
00070 for (unsigned int i = 0; i < obstacles.size(); i++)
00071 delete obstacles[i];
00072 }
00073
00074 template <size_t N>
00075 void ShapeSpaceCollisionCheckerBase<N>::addObstaclesToShapeSpace(ShapeSpace &shs) const {
00076 for (unsigned int i = 0; i < obstacles.size(); i++) {
00077 EllipticalObstacle *c = dynamic_cast<EllipticalObstacle*>(obstacles[i]);
00078 if (c) {
00079 fmat::Column<2> p = c->getCenter();
00080 NEW_SHAPE(obstacle, EllipseData, new EllipseData(shs, Point(p[0],p[1]), c->semimajor, c->semiminor));
00081 obstacle->setColor(rgb(0,255,0));
00082 }
00083
00084 RectangularObstacle *r = dynamic_cast<RectangularObstacle*>(obstacles[i]);
00085 if (r) {
00086 std::vector<Point> pts;
00087 for (int j = 0; j < 4; j++) {
00088 fmat::Column<2> p = r->getCorner(static_cast<RectangularObstacle::CornerOrder>(j));
00089 pts.push_back(Point(p[0],p[1]));
00090 }
00091
00092 NEW_SHAPE(obstacle, PolygonData, new PolygonData(shs, pts, true));
00093 obstacle->setColor(rgb(0,255,0));
00094 }
00095 }
00096 }
00097
00098 template <size_t N>
00099 void ShapeSpaceCollisionCheckerBase<N>::getRobotObstacle(const KinematicJoint& j, HierarchicalObstacle& hierObs) const {
00100
00101 for (KinematicJoint::branch_iterator it = j.getBranches().begin(); it != j.getBranches().end(); ++it) {
00102 getRobotObstacle(**it, hierObs);
00103 }
00104
00105
00106 RectangularObstacle* rect = new RectangularObstacle;
00107 j.getOwnBB2D(j.getFullT(), *rect);
00108 hierObs.add(rect);
00109 for (KinematicJoint::component_iterator it = j.components.begin(); it != j.components.end(); ++it) {
00110
00111
00112 RectangularObstacle* r = new RectangularObstacle;
00113 (*it)->getOwnBB2D(j.getFullT(), *r);
00114 hierObs.add(r);
00115 }
00116 }
00117
00118 template <size_t N>
00119 void ShapeSpaceCollisionCheckerBase<N>::addObstacleFromCollisionModel(const LinkComponent& j, const fmat::Transform& robotT, HierarchicalObstacle& hierObs) const {
00120
00121 fmat::Transform t;
00122 j.getCollisionModelTransform(t);
00123 t = t * robotT;
00124 fmat::Column<3> scale;
00125 j.collisionModelScale.exportTo(scale);
00126
00127
00128 if (j.collisionModel == "Cube") {
00129 RectangularObstacle* rect = new RectangularObstacle;
00130 j.getOwnBB2D(fmat::Transform(), *rect);
00131 hierObs.add(rect);
00132 }
00133 else if (j.collisionModel == "Cylinder") {
00134
00135
00136 }
00137 else if (j.collisionModel == "Sphere") {
00138
00139 fmat::Matrix<3,3> scaleM;
00140 scaleM(0,0) = 1/(scale[0]*scale[0]);
00141 scaleM(1,1) = 1/(scale[1]*scale[1]);
00142 scaleM(2,2) = 1/(scale[2]*scale[2]);
00143 fmat::Matrix<2,2> m(t.rotation() * scaleM * t.rotation().transpose());
00144
00145 fmat::fmatReal discriminant = std::sqrt(std::pow((m(0,0) - m(1,1)), 2) + 4*m(0,1)*m(0,1));
00146 fmat::fmatReal lambda1 = (m(0,0) + m(1,1) + discriminant) / 2;
00147 fmat::fmatReal lambda2 = (m(0,0) + m(1,1) - discriminant) / 2;
00148
00149 fmat::fmatReal semimajor, semiminor, ori;
00150 semimajor = 1 / std::sqrt(lambda1);
00151 semiminor = 1 / std::sqrt(lambda2);
00152
00153 if (m(0,1) == 0)
00154 ori = 0;
00155 else {
00156 fmat::Column<2> v;
00157 v[0] = m(0,1) / (lambda1 - m(0,0));
00158 v[1] = 1;
00159 ori = fmat::atan(v);
00160 }
00161
00162 EllipticalObstacle* ellipse = new EllipticalObstacle(fmat::Column<2>(t.translation()), semimajor, semiminor, ori);
00163 std::cout << ellipse->toString() << std::endl;
00164 hierObs.add(ellipse);
00165 }
00166 }
00167
00168
00169 #endif