Robowflex  v0.1
Making MoveIt Easy
tsr.cpp
Go to the documentation of this file.
1 /* Author: Zachary Kingston */
2 
3 #include <boost/format.hpp>
4 
5 #include <dart/dynamics/InverseKinematics.hpp>
6 #include <dart/dynamics/SimpleFrame.hpp>
7 
10 #include <robowflex_library/tf.h>
11 
12 #include <robowflex_dart/robot.h>
13 #include <robowflex_dart/space.h>
15 #include <robowflex_dart/tsr.h>
16 #include <robowflex_dart/world.h>
17 
19 using namespace robowflex::darts;
20 
21 ///
22 /// TSR::Specification
23 ///
24 
25 TSR::Specification::Specification(const std::string &structure, const std::string &target_frame,
26  const Eigen::Ref<const Eigen::Vector3d> &position,
27  const Eigen::Quaterniond &rotation)
28 {
29  setTarget(structure, target_frame);
30  setPose(position, rotation);
31 }
32 
34 {
35  target.structure = structure;
36  target.frame = frame;
37 
38  if (base.structure.empty())
39  base.structure = structure;
40 }
41 
43 {
44  base.structure = structure;
45  base.frame = frame;
46 }
47 
48 void TSR::Specification::setFrame(const std::string &structure, const std::string &target_frame,
49  const std::string &base_frame)
50 {
51  target.structure = structure;
52  base.structure = structure;
53 
54  target.frame = target_frame;
55  base.frame = base_frame;
56 }
57 
59 {
60  target.structure = target.structure + suffix;
61  base.structure = base.structure + suffix;
62 }
63 
64 void TSR::Specification::setPosition(const Eigen::Ref<const Eigen::Vector3d> &position)
65 {
66  pose.translation() = position;
67 }
68 
69 void TSR::Specification::setPosition(double x, double y, double z)
70 {
71  setPosition(Eigen::Vector3d(x, y, z));
72 }
73 
74 void TSR::Specification::setRotation(const Eigen::Quaterniond &orientation)
75 {
76  pose.linear() = orientation.toRotationMatrix();
77 }
78 
79 void TSR::Specification::setRotation(double w, double x, double y, double z)
80 {
81  setRotation(Eigen::Quaterniond(w, x, y, z));
82 }
83 
84 void TSR::Specification::setRotation(double x, double y, double z)
85 {
86  auto n = Eigen::AngleAxisd(x, Eigen::Vector3d::UnitX()) * //
87  Eigen::AngleAxisd(y, Eigen::Vector3d::UnitY()) * //
88  Eigen::AngleAxisd(z, Eigen::Vector3d::UnitZ());
89 
90  setRotation(n);
91 }
92 
94 {
95  pose = other;
96 }
97 
98 void TSR::Specification::setPose(const Eigen::Ref<const Eigen::Vector3d> &position,
99  const Eigen::Quaterniond &rotation)
100 {
101  pose = TF::createPoseQ(position, rotation);
102 }
103 
104 void TSR::Specification::setPose(double xp, double yp, double zp, double wr, double xr, double yr, double zr)
105 {
106  setPosition(xp, yp, zp);
107  setRotation(wr, xr, yr, zr);
108 }
109 
111 {
112  const auto &sim = world->getSim();
113 
114  const auto &tskl = sim->getSkeleton(target.structure);
115  const auto &tbn = tskl->getBodyNode(target.frame);
116 
117  if (base.frame != magic::ROOT_FRAME)
118  {
119  const auto &bskl = sim->getSkeleton(base.structure);
120  const auto &bbn = bskl->getBodyNode(base.frame);
121 
122  pose = tbn->getTransform(bbn);
123  }
124  else
125  pose = tbn->getTransform();
126 }
127 
129 {
130  setXPosTolerance(-bound, bound);
131 }
132 
134 {
135  setYPosTolerance(-bound, bound);
136 }
137 
139 {
140  setZPosTolerance(-bound, bound);
141 }
142 
143 void TSR::Specification::setXPosTolerance(double lower, double upper)
144 {
145  position.lower[0] = lower;
146  position.upper[0] = upper;
147  fixBounds();
148 
149  indices[3] = isPosConstrained(lower, upper);
150  dimension = getDimension();
151 }
152 
153 void TSR::Specification::setYPosTolerance(double lower, double upper)
154 {
155  position.lower[1] = lower;
156  position.upper[1] = upper;
157  fixBounds();
158 
159  indices[4] = isPosConstrained(lower, upper);
160  dimension = getDimension();
161 }
162 
163 void TSR::Specification::setZPosTolerance(double lower, double upper)
164 {
165  position.lower[2] = lower;
166  position.upper[2] = upper;
167  fixBounds();
168 
169  indices[5] = isPosConstrained(lower, upper);
170  dimension = getDimension();
171 }
172 
174 {
175  setXRotTolerance(-bound, bound);
176 }
177 
179 {
180  setYRotTolerance(-bound, bound);
181 }
182 
184 {
185  setZRotTolerance(-bound, bound);
186 }
187 
188 void TSR::Specification::setXRotTolerance(double lower, double upper)
189 {
190  orientation.lower[0] = lower;
191  orientation.upper[0] = upper;
192  fixBounds();
193 
194  indices[0] = isRotConstrained(lower, upper);
195  dimension = getDimension();
196 }
197 
198 void TSR::Specification::setYRotTolerance(double lower, double upper)
199 {
200  orientation.lower[1] = lower;
201  orientation.upper[1] = upper;
202  fixBounds();
203 
204  indices[1] = isRotConstrained(lower, upper);
205  dimension = getDimension();
206 }
207 
208 void TSR::Specification::setZRotTolerance(double lower, double upper)
209 {
210  orientation.lower[2] = lower;
211  orientation.upper[2] = upper;
212  fixBounds();
213 
214  indices[2] = isRotConstrained(lower, upper);
215  dimension = getDimension();
216 }
217 
219 {
220  setXPosTolerance(std::numeric_limits<double>::infinity());
221 }
222 
224 {
225  setYPosTolerance(std::numeric_limits<double>::infinity());
226 }
227 
229 {
230  setZPosTolerance(std::numeric_limits<double>::infinity());
231 }
232 
234 {
235  setNoXPosTolerance();
236  setNoYPosTolerance();
237  setNoZPosTolerance();
238 }
239 
241 {
242  setXRotTolerance(constants::pi);
243 }
244 
246 {
247  setYRotTolerance(constants::pi);
248 }
249 
251 {
252  setZRotTolerance(constants::pi);
253 }
254 
256 {
257  setNoXRotTolerance();
258  setNoYRotTolerance();
259  setNoZRotTolerance();
260 }
261 
263 {
264  {
265  Eigen::Vector3d u, l;
266  for (std::size_t i = 0; i < 3; ++i)
267  {
268  u[i] = std::max(position.lower[i], position.upper[i]);
269  l[i] = std::min(position.lower[i], position.upper[i]);
270  }
271 
272  position.lower = l;
273  position.upper = u;
274  }
275 
276  {
277  Eigen::Vector3d u, l;
278  for (std::size_t i = 0; i < 3; ++i)
279  {
280  u[i] = std::max({orientation.lower[i], orientation.upper[i], -constants::pi});
281  l[i] = std::min({orientation.lower[i], orientation.upper[i], constants::pi});
282  }
283 
284  orientation.lower = l;
285  orientation.upper = u;
286  }
287 }
288 
290 {
291  std::size_t k = 0;
292  for (const auto &idx : indices)
293  {
294  if (idx)
295  k++;
296  }
297 
298  return k;
299 }
300 
301 bool TSR::Specification::isPosConstrained(double lower, double upper) const
302 {
303  return std::isfinite(lower) or std::isfinite(upper);
304 }
305 
306 bool TSR::Specification::isRotConstrained(double lower, double upper) const
307 {
308  return std::abs(upper - lower) < constants::two_pi;
309 }
310 
311 Eigen::Vector3d TSR::Specification::getPosition() const
312 {
313  return pose.translation();
314 }
315 
316 Eigen::Quaterniond TSR::Specification::getRotation() const
317 {
318  return TF::getPoseRotation(pose);
319 }
320 
322 {
323  return getRotation().toRotationMatrix().eulerAngles(0, 1, 2);
324 }
325 
327 {
328  // must be same reference frame
329  if (target.structure != other.target.structure or target.frame != other.target.frame)
330  return false;
331 
332  if (base.structure != other.base.structure or base.frame != other.base.frame)
333  return false;
334 
335  // TODO: Check if rotations overlap
336  // if (getRotation().angularDistance(other.getRotation()) > magic::DEFAULT_IK_TOLERANCE)
337  // return false;
338 
339  Eigen::Vector3d p = getPosition();
340  Eigen::Vector3d op = other.getPosition();
341 
342  // check if positions overlap
343  for (std::size_t i = 0; i < 3; ++i)
344  {
345  double pi = p[i], piu = position.upper[i], pil = position.lower[i];
346  double opi = op[i], opiu = other.position.upper[i], opil = other.position.lower[i];
347 
348  // pi---------> piu
349  // --|------|------|------|-- axis
350  // opil <---------opi
351  // Check if overlap
352 
353  if (pi < opi)
354  if ((pi + piu) < (opi + opil))
355  return false;
356 
357  // opi--------> opiu
358  // --|------|------|------|-- axis
359  // pil <----------pi
360  // Check if overlap
361 
362  if (pi > opi)
363  if ((pi + pil) > (opi + opiu))
364  return false;
365  }
366 
367  Eigen::Vector3d np;
368 
369  if (not isRotationConstrained())
370  setRotation(other.getRotation());
371 
372  // enforce new bounds
373  for (std::size_t i = 0; i < 3; ++i)
374  {
375  if (other.orientation.lower[i] > orientation.lower[i])
376  orientation.lower[i] = other.orientation.lower[i];
377  if (other.orientation.upper[i] < orientation.upper[i])
378  orientation.upper[i] = other.orientation.upper[i];
379 
380  double pi = p[i], piu = position.upper[i], pil = position.lower[i];
381  double opi = op[i], opiu = other.position.upper[i], opil = other.position.lower[i];
382 
383  double low = std::max(pi + pil, opi + opil);
384  double high = std::min(pi + piu, opi + opiu);
385 
386  np[i] = (high + low) / 2.;
387  double v = std::fabs(high - np[i]);
388 
389  position.upper[i] = v;
390  position.lower[i] = -v;
391 
392  indices[i] = isRotConstrained(orientation.lower[i], orientation.upper[i]);
393  indices[3 + i] = isPosConstrained(-v, v);
394  }
395 
396  dimension = getDimension();
397  setPosition(np);
398 
399  return true;
400 }
401 
403 {
404  return base.frame != magic::ROOT_FRAME;
405 }
406 
408 {
409  bool value = false;
410  for (std::size_t i = 0; i < 3; ++i)
411  value |= isPosConstrained(position.lower[i], position.upper[i]);
412 
413  return value;
414 }
415 
417 {
418  bool value = false;
419  for (std::size_t i = 0; i < 3; ++i)
420  value |= isRotConstrained(orientation.lower[i], orientation.upper[i]);
421 
422  return value;
423 }
424 
426 {
427  if (isRelative())
428  out << boost::format("B:%1%:%2% => T:%3%:%4%") //
429  % base.frame % base.structure % target.frame % target.structure;
430  else
431  out << boost::format("T:%1%:%2%") //
432  % target.frame % target.structure;
433 
434  out << std::endl;
435  out << "Position Orientation" << std::endl;
436 
437  auto p = getPosition();
438  auto o = getRotation();
439  out << boost::format( //
440  " x:%1$+07.4f (%2$+07.4f, %3$+07.4f) [%7%] x:%4$+07.4f (%5$+07.4f, %6$+07.4f) [%8%]") //
441  % p[0] % position.lower[0] % position.upper[0] //
442  % o.x() % orientation.lower[0] % orientation.upper[0] //
443  % indices[3] % indices[0];
444  out << std::endl;
445  out << boost::format( //
446  " y:%1$+07.4f (%2$+07.4f, %3$+07.4f) [%7%] y:%4$+07.4f (%5$+07.4f, %6$+07.4f) [%8%]") //
447  % p[1] % position.lower[1] % position.upper[1] //
448  % o.y() % orientation.lower[1] % orientation.upper[1] //
449  % indices[4] % indices[1];
450  out << std::endl;
451  out << boost::format( //
452  " z:%1$+07.4f (%2$+07.4f, %3$+07.4f) [%7%] z:%4$+07.4f (%5$+07.4f, %6$+07.4f) [%8%]") //
453  % p[2] % position.lower[2] % position.upper[2] //
454  % o.z() % orientation.lower[2] % orientation.upper[2] //
455  % indices[5] % indices[2];
456  out << std::endl;
457  out << boost::format(" w:%1$+07.4f") % o.w();
458  out << std::endl;
459 }
460 
461 ///
462 /// TSR
463 ///
464 
465 TSR::TSR(const WorldPtr &world, const Specification &spec) : world_(world), spec_(spec)
466 {
467 }
468 
470 {
471  clear();
472 }
473 
475 {
476  if (tnd_ and ik_)
477  tnd_->clearIK();
478 
479  frame_ = nullptr;
480  ik_ = nullptr;
481  tnd_ = nullptr;
482  tsr_ = nullptr;
483 }
484 
485 void TSR::setWorld(const WorldPtr &world)
486 {
487  clear();
488  world_ = world;
489  initialize();
490 }
491 
492 void TSR::useGroup(const std::string &name)
493 {
494  auto robot = world_->getRobot(spec_.target.structure);
495  if (not robot)
496  throw std::runtime_error("Target robot does exist in world!");
497 
498  useIndices(robot->getGroupIndices(name));
499 }
500 
502 {
503  indices_ = indices;
504  if (ik_)
505  {
506  ik_->setDofs(indices_);
507  indices_ = ik_->getDofs();
508  }
509 
511 }
512 
514 {
516  for (const auto &index : indices)
517  {
518  if (index.first == getSkeletonIndex())
519  use.emplace_back(index.second);
520  }
521 
522  useIndices(use);
523 }
524 
526 {
527  world_indices_ = indices;
529 }
530 
532 {
533  if (not tnd_)
534  initialize();
535 
536  return skel_index_;
537 }
538 
540 {
541  return indices_;
542 }
543 
545 {
547  for (const auto &index : indices_)
548  wi.emplace_back(skel_index_, index);
549 
550  return wi;
551 }
552 
554 {
555  return world_indices_;
556 }
557 
559 {
560  return spec_.dimension;
561 }
562 
564 {
565  return indices_.size();
566 }
567 
569 {
570  return world_indices_.size();
571 }
572 
574 {
575  const auto &sim = world_->getSim();
576  const auto &bskl = sim->getSkeleton(spec_.base.structure);
577  auto *bnd = bskl->getBodyNode(spec_.base.frame);
578 
579  if (not tnd_)
580  throw std::runtime_error("Target body node is not initialized");
581 
582  return tnd_->getTransform(bnd);
583 }
584 
585 void TSR::getErrorWorldRaw(Eigen::Ref<Eigen::VectorXd> error) const
586 {
587  world_->lock();
588  error = tsr_->computeError();
589  world_->unlock();
590 }
591 
592 void TSR::getErrorWorld(Eigen::Ref<Eigen::VectorXd> error) const
593 {
594  world_->lock();
595 
596  auto tsr_error = tsr_->computeError();
597 
598  std::size_t j = 0;
599  for (std::size_t i = 0; i < 6; ++i)
600  {
601  if (spec_.indices[i])
602  error[j++] = tsr_error[i];
603  }
604 
605  world_->unlock();
606 }
607 
608 void TSR::getErrorWorldState(const Eigen::Ref<const Eigen::VectorXd> &world,
609  Eigen::Ref<Eigen::VectorXd> error) const
610 {
611  if (bijection_.empty())
612  getError(world, error);
613  else
614  {
615  Eigen::VectorXd state(getNumDofs());
616  fromBijection(state, world);
617  getError(state, error);
618  }
619 }
620 
621 void TSR::getError(const Eigen::Ref<const Eigen::VectorXd> &state, Eigen::Ref<Eigen::VectorXd> error) const
622 {
623  setPositions(state);
624  getErrorWorld(error);
625 }
626 
627 void TSR::getJacobianWorld(Eigen::Ref<Eigen::MatrixXd> jacobian) const
628 {
629  world_->lock();
630 
631  auto tjac = ik_->computeJacobian();
632 
633  std::size_t j = 0;
634  for (std::size_t i = 0; i < 6; ++i)
635  {
636  if (spec_.indices[i])
637  jacobian.row(j++) = tjac.row(i);
638  }
639 
640  world_->unlock();
641 }
642 
643 void TSR::getJacobianWorldState(const Eigen::Ref<const Eigen::VectorXd> &world,
644  Eigen::Ref<Eigen::MatrixXd> jacobian) const
645 {
646  if (bijection_.empty())
647  getJacobian(world, jacobian);
648  else
649  {
650  Eigen::VectorXd state(getNumDofs());
651  fromBijection(state, world);
652 
653  Eigen::VectorXd tjac(getDimension(), getNumDofs());
654  getJacobian(state, tjac);
655 
656  for (std::size_t i = 0; i < bijection_.size(); ++i)
657  if (bijection_[i] < world_indices_.size())
658  jacobian.col(bijection_[i]) = tjac.col(i);
659  }
660 }
661 
662 void TSR::getJacobian(const Eigen::Ref<const Eigen::VectorXd> &state,
663  Eigen::Ref<Eigen::MatrixXd> jacobian) const
664 {
665  world_->lock();
666  setPositions(state);
667  getJacobianWorld(jacobian);
668  world_->unlock();
669 }
670 
671 double TSR::distanceWorld() const
672 {
673  Eigen::VectorXd x(getDimension());
674  getErrorWorld(x);
675  return x.norm();
676 }
677 
678 double TSR::distanceWorldState(const Eigen::Ref<const Eigen::VectorXd> &world) const
679 {
680  Eigen::VectorXd x(getDimension());
681  getErrorWorldState(world, x);
682  return x.norm();
683 }
684 
685 double TSR::distance(const Eigen::Ref<const Eigen::VectorXd> &state) const
686 {
687  Eigen::VectorXd x(getDimension());
688  getError(state, x);
689  return x.norm();
690 }
691 
693 {
694  if (not ik_)
695  {
696  RBX_ERROR("TSR: Solve called before initialize!");
697  return false;
698  }
699 
700  world_->lock();
701  bool r = ik_->solveAndApply();
702  world_->unlock();
703  return r;
704 }
705 
706 bool TSR::solveWorldState(Eigen::Ref<Eigen::VectorXd> world)
707 {
708  if (bijection_.empty())
709  return solve(world);
710 
711  Eigen::VectorXd state(getNumDofs());
712  fromBijection(state, world);
713  bool r = solve(state);
714  toBijection(world, state);
715  return r;
716 }
717 
718 bool TSR::solve(Eigen::Ref<Eigen::VectorXd> state)
719 {
720  world_->lock();
721 
722  setPositions(state);
723  bool r = solveWorld();
724  getPositions(state);
725 
726  world_->unlock();
727  return r;
728 }
729 
731 {
732  world_->lock();
733 
734  Eigen::VectorXd state = ik_->getPositions();
735  bool r = solveGradient(state);
736  setPositions(state);
737 
738  world_->unlock();
739  return r;
740 }
741 
742 bool TSR::solveGradientWorldState(Eigen::Ref<Eigen::VectorXd> world)
743 {
744  if (bijection_.empty())
745  return solveGradient(world);
746 
747  Eigen::VectorXd state(getNumDofs());
748  fromBijection(state, world);
749  bool r = solveGradient(state);
750  toBijection(world, state);
751  return r;
752 }
753 
754 bool TSR::solveGradient(Eigen::Ref<Eigen::VectorXd> state)
755 {
756  world_->lock();
757 
758  unsigned int iter = 0;
759  double norm = 0;
760  Eigen::VectorXd f(getDimension());
761  Eigen::MatrixXd j(getDimension(), getNumDofs());
762 
763  const double squared_tolerance = spec_.tolerance * spec_.tolerance;
764 
765  setPositions(state);
766  getErrorWorld(f);
767 
768  while ((norm = f.norm()) > squared_tolerance && iter++ < spec_.maxIter)
769  {
770  getJacobianWorld(j);
771  state -= j.jacobiSvd(Eigen::ComputeThinU | Eigen::ComputeThinV).solve(f);
772 
773  setPositions(state);
774  getErrorWorld(f);
775  }
776 
777  world_->unlock();
778 
779  return norm < squared_tolerance;
780 }
781 
782 void TSR::setPositionsWorldState(const Eigen::Ref<const Eigen::VectorXd> &world) const
783 {
784  Eigen::VectorXd state(getNumDofs());
785  fromBijection(state, world);
786  setPositions(state);
787 }
788 
789 void TSR::setPositions(const Eigen::Ref<const Eigen::VectorXd> &state) const
790 {
791  world_->lock();
792  ik_->setPositions(state);
793  world_->unlock();
794 }
795 
796 void TSR::getPositionsWorldState(Eigen::Ref<Eigen::VectorXd> world) const
797 {
798  Eigen::VectorXd state(getNumDofs());
799  getPositions(state);
800  toBijection(world, state);
801 }
802 
803 void TSR::getPositions(Eigen::Ref<Eigen::VectorXd> state) const
804 {
805  world_->lock();
806  state = ik_->getPositions();
807  world_->unlock();
808 }
809 
811 {
812  return spec_;
813 }
814 
816 {
817  if (frame_)
818  frame_->setRelativeTransform(spec_.pose);
819 }
820 
822 {
823  if (tsr_)
824  {
825  tsr_->setLinearBounds(spec_.position.lower, spec_.position.upper);
826  tsr_->setAngularBounds(spec_.orientation.lower, spec_.orientation.upper);
827  }
828 }
829 
831 {
832  if (ik_)
833  {
834  ik_->getSolver()->setTolerance(spec_.tolerance);
835  ik_->getSolver()->setNumMaxIterations(spec_.maxIter);
836  }
837 }
838 
840 {
841  const auto &sim = world_->getSim();
842  const auto &tskl = sim->getSkeleton(spec_.target.structure);
843  if (not tskl)
844  throw std::runtime_error("Target skeleton " + spec_.target.structure + " in TSR does not exist!");
845  skel_index_ = world_->getSkeletonIndex(tskl);
846 
847  const auto &bskl = sim->getSkeleton(spec_.base.structure);
848  if (not bskl)
849  throw std::runtime_error("Base skeleton " + spec_.base.structure + " in TSR does not exist!");
850 
851  tnd_ = tskl->getBodyNode(spec_.target.frame);
852  ik_ = tnd_->getIK(true);
853  frame_ = ik_->getTarget();
854 
856  {
857  auto *bnd = bskl->getBodyNode(spec_.base.frame);
858  frame_ = frame_->clone(bnd);
859  }
860 
861  ik_->setTarget(frame_);
862 
863  tsr_ = &ik_->setErrorMethod<dart::dynamics::InverseKinematics::TaskSpaceRegion>();
864  tsr_->setComputeFromCenter(false);
865 
866  updatePose();
867  updateBounds();
868  updateSolver();
869 
870  if (indices_.empty())
871  indices_ = ik_->getDofs();
872  else
873  ik_->setDofs(indices_);
874 }
875 
876 void TSR::toBijection(Eigen::Ref<Eigen::VectorXd> world, const Eigen::Ref<const Eigen::VectorXd> &state) const
877 {
878  if (bijection_.empty())
879  world = state;
880  else
881  for (std::size_t i = 0; i < bijection_.size(); ++i)
882  if (bijection_[i] < world_indices_.size())
883  world[bijection_[i]] = state[i];
884 }
885 
886 void TSR::fromBijection(Eigen::Ref<Eigen::VectorXd> state,
887  const Eigen::Ref<const Eigen::VectorXd> &world) const
888 {
889  if (bijection_.empty())
890  state = world;
891  else
892  for (std::size_t i = 0; i < bijection_.size(); ++i)
893  if (bijection_[i] < world_indices_.size())
894  state[i] = world[bijection_[i]];
895 }
896 
898 {
899  if (world_indices_.empty())
900  return;
901 
903 
904  bool same = world_indices_.size() == indices_.size();
905  for (std::size_t i = 0; i < indices_.size(); ++i)
906  {
908  for (std::size_t j = 0; j < world_indices_.size(); ++j)
909  {
910  auto entry = world_indices_[j];
911  if (entry.first == getSkeletonIndex() and entry.second == indices_[i])
912  {
913  bijection_[i] = j;
914  same &= i == j;
915  break;
916  }
917  }
918  }
919 
920  if (same)
921  bijection_.clear();
922 }
923 
924 ///
925 /// TSRSet
926 ///
927 
928 TSRSet::TSRSet(const WorldPtr &world, const TSRPtr &tsr) : world_(world)
929 {
930  addTSR(tsr);
931 }
932 
933 TSRSet::TSRSet(const WorldPtr &world, const std::vector<TSRPtr> &tsrs, bool intersect) : world_(world)
934 {
935  for (const auto &tsr : tsrs)
936  addTSR(tsr, intersect);
937 }
938 
939 void TSRSet::addTSR(const TSRPtr &tsr, bool intersect, double weight)
940 {
941  TSRPtr ntsr = tsr;
942  TSR::Specification spec = tsr->getSpecification();
943  if (intersect)
944  {
945  for (auto &etsr : tsrs_)
946  // Don't need this entire TSR if we can intersect
947  if (etsr->getSpecification().intersect(spec))
948  {
949  dimension_ = 0;
950  for (auto &tsr : tsrs_)
951  dimension_ += tsr->getDimension();
952  return;
953  }
954 
955  // copy for intersections later
956  ntsr = std::make_shared<TSR>(world_, spec);
957  ntsr->useIndices(tsr->getIndices());
958  ntsr->setWorldIndices(tsr->getWorldIndices());
959 
960  // weight relative frames less
961  if ((weight - 1.) < constants::eps)
962  if (spec.isRelative())
963  weight = 0.1;
964  }
965 
966  tsrs_.emplace_back(ntsr);
967  weights_.emplace_back(weight);
968 
969  dimension_ += ntsr->getDimension();
971 }
972 
974 {
975  return tsrs_.size();
976 }
977 
979 {
980  return tsrs_;
981 }
982 
983 void TSRSet::setWorld(const WorldPtr &world)
984 {
985  for (auto &tsr : tsrs_)
986  tsr->setWorld(world);
987 
988  world_ = world;
989  initialize();
990 }
991 
992 void TSRSet::addSuffix(const std::string &suffix)
993 {
994  for (auto &tsr : tsrs_)
995  tsr->getSpecification().addSuffix(suffix);
996 }
997 
998 void TSRSet::useGroup(const std::string &name)
999 {
1000  for (auto &tsr : tsrs_)
1001  tsr->useGroup(name);
1002 }
1003 
1005 {
1006  for (auto &tsr : tsrs_)
1007  tsr->useIndices(indices);
1008 }
1009 
1011 {
1012  for (auto &tsr : tsrs_)
1013  tsr->useWorldIndices(indices);
1014 }
1015 
1017 {
1018  for (auto &tsr : tsrs_)
1019  tsr->setWorldIndices(indices);
1020 }
1021 
1023 {
1024  return dimension_;
1025 }
1026 
1027 void TSRSet::getErrorWorld(Eigen::Ref<Eigen::VectorXd> error) const
1028 {
1029  world_->lock();
1030 
1031  std::size_t i = 0;
1032  for (std::size_t j = 0; j < tsrs_.size(); ++j)
1033  {
1034  const auto &tsr = tsrs_[j];
1035  tsr->getErrorWorld(error.segment(i, tsr->getDimension()));
1036  error.segment(i, tsr->getDimension()) *= weights_[j];
1037 
1038  i += tsr->getDimension();
1039  }
1040 
1041  world_->unlock();
1042 }
1043 
1044 void TSRSet::getErrorWorldState(const Eigen::Ref<const Eigen::VectorXd> &world,
1045  Eigen::Ref<Eigen::VectorXd> error) const
1046 {
1047  world_->lock();
1048 
1049  std::size_t i = 0;
1050  for (std::size_t j = 0; j < tsrs_.size(); ++j)
1051  {
1052  const auto &tsr = tsrs_[j];
1053  tsr->getErrorWorldState(world, error.segment(i, tsr->getDimension()));
1054  error.segment(i, tsr->getDimension()) *= weights_[j];
1055 
1056  i += tsr->getDimension();
1057  }
1058 
1059  world_->unlock();
1060 }
1061 
1062 void TSRSet::getJacobianWorldState(const Eigen::Ref<const Eigen::VectorXd> &world,
1063  Eigen::Ref<Eigen::MatrixXd> jacobian) const
1064 {
1065  world_->lock();
1066 
1067  unsigned int i = 0;
1068  std::size_t n = world.size();
1069  for (std::size_t j = 0; j < tsrs_.size(); ++j)
1070  {
1071  const auto &tsr = tsrs_[j];
1072  tsr->getJacobianWorldState(world, jacobian.block(i, 0, tsr->getDimension(), n));
1073  jacobian.block(i, 0, tsr->getDimension(), n) *= weights_[j];
1074 
1075  i += tsr->getDimension();
1076  }
1077 
1078  world_->unlock();
1079 }
1080 
1082 {
1083  Eigen::VectorXd x(getDimension());
1084  getErrorWorld(x);
1085  return x.norm();
1086 }
1087 
1088 double TSRSet::distanceWorldState(const Eigen::Ref<const Eigen::VectorXd> &world) const
1089 {
1090  Eigen::VectorXd x(getDimension());
1091  getErrorWorldState(world, x);
1092  return x.norm();
1093 }
1094 
1096 {
1097  world_->lock();
1098 
1099  if (tsrs_.size() == 1)
1100  {
1101  bool r = tsrs_[0]->solveWorld();
1102  world_->unlock();
1103  return r;
1104  }
1105 
1106  auto sim = world_->getSim();
1107 
1108  bool r = true;
1109  for (const auto &skidx : skel_indices_)
1110  {
1111  auto skel = sim->getSkeleton(skidx);
1112  auto ik = skel->getIK(true);
1113  r &= ik->solveAndApply(true);
1114  }
1115 
1116  world_->unlock();
1117  return r;
1118 }
1119 
1120 bool TSRSet::solveWorldState(Eigen::Ref<Eigen::VectorXd> world)
1121 {
1122  world_->lock();
1123  for (auto &tsr : tsrs_)
1124  tsr->setPositionsWorldState(world);
1125 
1126  bool r = solveWorld();
1127 
1128  for (auto &tsr : tsrs_)
1129  tsr->getPositionsWorldState(world);
1130 
1131  world_->unlock();
1132  return r;
1133 }
1134 
1135 bool TSRSet::solveGradientWorldState(Eigen::Ref<Eigen::VectorXd> world)
1136 {
1137  unsigned int iter = 0;
1138  double norm = 0;
1139  Eigen::VectorXd f(getDimension());
1140  Eigen::MatrixXd j(getDimension(), world.size());
1141 
1142  const double squared_tolerance = tolerance_ * tolerance_;
1143  const Eigen::VectorXd limit = Eigen::VectorXd::Constant(world.size(), limit_);
1144 
1145  world_->lock();
1146  getErrorWorldState(world, f);
1147 
1148  while ((norm = f.norm()) > squared_tolerance and iter++ < maxIter_)
1149  {
1150  getJacobianWorldState(world, j);
1151  if (qr_)
1152  world -= (step_ * j.colPivHouseholderQr().solve(f)).cwiseMin(limit).cwiseMax(-limit);
1153  else
1154  {
1155  if (damped_)
1156  {
1157  auto svd = j.jacobiSvd(Eigen::ComputeFullU | Eigen::ComputeFullV);
1158  auto lr = svd.rank();
1159  const auto &u = svd.matrixU().leftCols(lr);
1160  const auto &v = svd.matrixV().leftCols(lr);
1161  const auto &s = svd.singularValues().head(lr);
1162  const auto &d = Eigen::VectorXd::Constant(lr, damping_);
1163 
1164  const auto &damped = s.cwiseQuotient(s.cwiseProduct(s) + d.cwiseProduct(d));
1165 
1166  Eigen::MatrixXd tmp;
1167  tmp.noalias() = u.adjoint() * f;
1168  tmp = damped.asDiagonal().inverse() * tmp;
1169  auto step = v * tmp;
1170 
1171  world -= (step_ * step).cwiseMin(limit).cwiseMax(-limit);
1172  }
1173  else
1174  world -= (step_ * j.jacobiSvd(Eigen::ComputeThinU | Eigen::ComputeThinV).solve(f))
1175  .cwiseMin(limit)
1176  .cwiseMax(-limit);
1177  }
1178 
1179  enforceBoundsWorld(world);
1180 
1181  getErrorWorldState(world, f);
1182  }
1183 
1184  world_->forceUpdate();
1185  world_->unlock();
1186 
1187  return norm < squared_tolerance;
1188 }
1189 
1191 {
1192  auto sim = world_->getSim();
1193  for (const auto &skidx : skel_indices_)
1194  {
1195  auto skel = sim->getSkeleton(skidx);
1196  auto ik = skel->getIK(true);
1197 
1198  auto sv = ik->getSolver();
1199  sv->setNumMaxIterations(maxIter_);
1200  sv->setTolerance(tolerance_);
1201  }
1202 }
1203 
1205 {
1206  return maxIter_;
1207 }
1208 
1209 double TSRSet::getTolerance() const
1210 {
1211  return tolerance_;
1212 }
1213 
1215 {
1216  skel_indices_.clear();
1217  for (auto &tsr : tsrs_)
1218  {
1219  tsr->initialize();
1220  skel_indices_.emplace(tsr->getSkeletonIndex());
1221  }
1222 
1223  updateSolver();
1224  RBX_INFO("TSRSet: Initialized %d TSRs!", tsrs_.size());
1225 }
1226 
1228 {
1229  return tsrs_[0]->getWorldIndices();
1230 }
1231 
1232 void TSRSet::getPositionsWorldState(Eigen::Ref<Eigen::VectorXd> world) const
1233 {
1234  const auto &wi = getWorldIndices();
1235  for (std::size_t i = 0; i < wi.size(); ++i)
1236  {
1237  const auto &wii = wi[i];
1238  world[i] = world_->getSim()->getSkeleton(wii.first)->getDof(wii.second)->getPosition();
1239  }
1240 }
1241 
1243 {
1244  const auto &wi = getWorldIndices();
1245  std::size_t n = wi.size();
1246 
1247  upper_ = Eigen::VectorXd::Zero(n);
1248  lower_ = Eigen::VectorXd::Zero(n);
1249  for (std::size_t i = 0; i < n; ++i)
1250  {
1251  const auto &wii = wi[i];
1252  const auto &dof = world_->getSim()->getSkeleton(wii.first)->getDof(wii.second);
1253  // if (dof->isCyclic())
1254  // {
1255  // lower_[i] = -constants::pi;
1256  // upper_[i] = constants::pi;
1257  // }
1258  // else
1259  // {
1260  auto limits = dof->getPositionLimits();
1261  lower_[i] = limits.first;
1262  upper_[i] = limits.second;
1263  // }
1264  }
1265 }
1266 
1268 {
1269  maxIter_ = iterations;
1270 }
1271 
1272 void TSRSet::setTolerance(double tolerance)
1273 {
1274  tolerance_ = tolerance;
1275 }
1276 
1277 void TSRSet::setWorldUpperLimits(const Eigen::Ref<const Eigen::VectorXd> &upper)
1278 {
1279  upper_ = upper;
1280 }
1281 
1282 void TSRSet::setWorldLowerLimits(const Eigen::Ref<const Eigen::VectorXd> &lower)
1283 {
1284  lower_ = lower;
1285 }
1286 
1287 void TSRSet::enforceBoundsWorld(Eigen::Ref<Eigen::VectorXd> world) const
1288 {
1289  if (upper_.size())
1290  world = world.cwiseMin(upper_);
1291  if (lower_.size())
1292  world = world.cwiseMax(lower_);
1293 }
1294 
1295 void TSRSet::print(std::ostream &out) const
1296 {
1297  out << "TSRSet --------------------" << std::endl;
1298  for (const auto &tsr : tsrs_)
1299  tsr->getSpecification().print(out);
1300  out << "---------------------------" << std::endl;
1301 }
1302 
1303 void TSRSet::setStep(double step)
1304 {
1305  step_ = step;
1306 }
1307 
1308 double TSRSet::getStep() const
1309 {
1310  return step_;
1311 }
1312 
1314 {
1315  qr_ = false;
1316 }
1317 
1319 {
1320  qr_ = true;
1321 }
1322 
1323 void TSRSet::setLimit(double limit)
1324 {
1325  limit_ = limit;
1326 }
1327 
1328 double TSRSet::getLimit() const
1329 {
1330  return limit_;
1331 }
1332 
1333 void TSRSet::setDamping(double damping)
1334 {
1335  damping_ = damping;
1336 }
1337 
1338 double TSRSet::getDamping() const
1339 {
1340  return damping_;
1341 }
1342 
1343 void TSRSet::useDamping(bool damping)
1344 {
1345  damped_ = damping;
1346 }
1347 
1348 ///
1349 /// TSRConstraint
1350 ///
1351 
1353  : TSRConstraint(space, std::make_shared<TSRSet>(space->getWorld(), tsr))
1354 {
1355 }
1356 
1358  : TSRConstraint(space, std::make_shared<TSRSet>(space->getWorld(), tsrs))
1359 {
1360 }
1361 
1363  : ompl::base::Constraint(space->getDimension(), tsr->getDimension(), tsr->getTolerance())
1364  , space_(space)
1365  , tsr_(tsr)
1366 {
1367  tsr_->useWorldIndices(space->getIndices());
1368  tsr_->setWorldIndices(space->getIndices());
1369  tsr_->setWorld(space->getWorld());
1370 
1371  tsr_->setWorldLowerLimits(space->getLowerBound());
1372  tsr_->setWorldUpperLimits(space->getUpperBound());
1373  tsr_->initialize();
1374 }
1375 
1376 void TSRConstraint::function(const Eigen::Ref<const Eigen::VectorXd> &x,
1377  Eigen::Ref<Eigen::VectorXd> out) const
1378 {
1379  tsr_->getErrorWorldState(x, out);
1380 }
1381 
1382 void TSRConstraint::jacobian(const Eigen::Ref<const Eigen::VectorXd> &x,
1383  Eigen::Ref<Eigen::MatrixXd> out) const
1384 {
1385  tsr_->getJacobianWorldState(x, out);
1386 }
1387 
1388 bool TSRConstraint::project(Eigen::Ref<Eigen::VectorXd> x) const
1389 {
1390  space_->setWorldState(space_->getWorld(), x);
1391 
1392  bool r = false;
1393  if (tsr_->numTSRs() == 1 or not options.use_gradient)
1394  r = tsr_->solveWorldState(x);
1395 
1396  else if (options.use_gradient)
1397  r = tsr_->solveGradientWorldState(x);
1398 
1399  return r;
1400 }
1401 
1403 {
1404  return tsr_;
1405 }
A shared pointer wrapper for robowflex::darts::StateSpace.
An OMPL constraint for TSRs. Under the hood, creates a TSRSet that is used for all computation....
Definition: tsr.h:1017
bool project(Eigen::Ref< Eigen::VectorXd > x) const override
Definition: tsr.cpp:1388
TSRSetPtr tsr_
Set of TSR constraints.
Definition: tsr.h:1059
TSRSetPtr getSet()
Get TSR set for this constraint.
Definition: tsr.cpp:1402
void jacobian(const Eigen::Ref< const Eigen::VectorXd > &x, Eigen::Ref< Eigen::MatrixXd > out) const override
Definition: tsr.cpp:1382
struct robowflex::darts::TSRConstraint::@7 options
Public options.
StateSpacePtr space_
Robot state space.
Definition: tsr.h:1058
TSRConstraint(const StateSpacePtr &space, const TSRPtr &tsr)
Constructor for a single TSR.
Definition: tsr.cpp:1352
void function(const Eigen::Ref< const Eigen::VectorXd > &x, Eigen::Ref< Eigen::VectorXd > out) const override
Definition: tsr.cpp:1376
A shared pointer wrapper for robowflex::darts::TSR.
A shared pointer wrapper for robowflex::darts::TSRSet.
Manager for a set of TSR constraints. Attempts to reduce redundancy and combines errors and Jacobians...
Definition: tsr.h:726
std::size_t getDimension() const
Get the error dimension of this set of TSRs.
Definition: tsr.cpp:1022
void setStep(double step)
Set the step parameter in the solver.
Definition: tsr.cpp:1303
double tolerance_
Tolerance for solving.
Definition: tsr.h:991
std::size_t getMaxIterations() const
Get the maximum iterations allowed.
Definition: tsr.cpp:1204
void getJacobianWorldState(const Eigen::Ref< const Eigen::VectorXd > &world, Eigen::Ref< Eigen::MatrixXd > jacobian) const
Get the Jacobian given a provided world configuration.
Definition: tsr.cpp:1062
void useWorldIndices(const std::vector< std::pair< std::size_t, std::size_t >> &indices)
Use World DoF indices for all TSRs computation. World indices are pairs of skeleton index and DoF ind...
Definition: tsr.cpp:1010
void setWorldLowerLimits(const Eigen::Ref< const Eigen::VectorXd > &lower)
Set the lower limit on joints given their index in the world configuration.
Definition: tsr.cpp:1282
void addSuffix(const std::string &suffix)
Add a suffix to the end of all structures in the TSRs in the set.
Definition: tsr.cpp:992
Eigen::VectorXd upper_
Upper bounds on world configuration.
Definition: tsr.h:998
void useIndices(const std::vector< std::size_t > &indices)
Use DoF indices for all TSRs computation.
Definition: tsr.cpp:1004
double distanceWorldState(const Eigen::Ref< const Eigen::VectorXd > &world) const
Get the distance to satisfaction given a provided world configuration.
Definition: tsr.cpp:1088
Eigen::VectorXd lower_
Lower bounds on world configuration.
Definition: tsr.h:999
bool damped_
If true, use damped SVD.
Definition: tsr.h:987
void useDamping(bool damping)
Set if damping is used in SVD solving.
Definition: tsr.cpp:1343
void enforceBoundsWorld(Eigen::Ref< Eigen::VectorXd > world) const
Enforce upper and lower bounds on a world configuration.
Definition: tsr.cpp:1287
void getErrorWorld(Eigen::Ref< Eigen::VectorXd > error) const
Get the current error given the world state.
Definition: tsr.cpp:1027
WorldPtr world_
World to use.
Definition: tsr.h:983
std::size_t maxIter_
Maximum iterations to use for solving.
Definition: tsr.h:992
double getLimit() const
Get the solver limit parameter.
Definition: tsr.cpp:1328
void setWorld(const WorldPtr &world)
Set the world used by this TSR set.
Definition: tsr.cpp:983
void setWorldUpperLimits(const Eigen::Ref< const Eigen::VectorXd > &upper)
Set the upper limit on joints given their index in the world configuration.
Definition: tsr.cpp:1277
std::vector< double > weights_
Weights on TSRs.
Definition: tsr.h:995
void addTSR(const TSRPtr &tsr, bool intersect=true, double weight=1.0)
Add a TSR to the set.
Definition: tsr.cpp:939
void useQR()
Use QR for solving.
Definition: tsr.cpp:1318
std::size_t dimension_
Total error dimension of set.
Definition: tsr.h:996
void initialize()
Initialize this set of TSRs.
Definition: tsr.cpp:1214
bool solveWorldState(Eigen::Ref< Eigen::VectorXd > world)
Solve for a satisfying configuration given an initial world configuration.
Definition: tsr.cpp:1120
void getPositionsWorldState(Eigen::Ref< Eigen::VectorXd > world) const
Get the current world state.
Definition: tsr.cpp:1232
void print(std::ostream &out) const
Print out the TSRs in this set.
Definition: tsr.cpp:1295
double limit_
Step size limit.
Definition: tsr.h:989
std::set< std::size_t > skel_indices_
All skeleton indices used by members of the set.
Definition: tsr.h:984
std::vector< TSRPtr > tsrs_
Set of TSRs.
Definition: tsr.h:994
std::size_t numTSRs() const
Get the number of TSRs in the set.
Definition: tsr.cpp:973
double getDamping() const
Get the solver damping parameter.
Definition: tsr.cpp:1338
void setTolerance(double tolerance)
Set the maximum tolerance used for solving.
Definition: tsr.cpp:1272
double distanceWorld() const
Get the current distance to satisfaction given the world state.
Definition: tsr.cpp:1081
double getTolerance() const
Get the numerical tolerance for solving.
Definition: tsr.cpp:1209
bool qr_
If true, use QR in gradient solve. Else, SVD.
Definition: tsr.h:986
TSRSet(const WorldPtr &world, const TSRPtr &tsr)
Constructor.
Definition: tsr.cpp:928
double step_
Step scaling in gradient.
Definition: tsr.h:988
const std::vector< TSRPtr > & getTSRs() const
Get the TSRs that form the set.
Definition: tsr.cpp:978
bool solveGradientWorldState(Eigen::Ref< Eigen::VectorXd > world)
Solve using gradient descent for a satisfying configuration given an initial world configuration.
Definition: tsr.cpp:1135
const std::vector< std::pair< std::size_t, std::size_t > > & getWorldIndices() const
Get the world indices used.
Definition: tsr.cpp:1227
void useSVD()
Use SVD for solving.
Definition: tsr.cpp:1313
bool solveWorld()
Solve for a satisfying configuration given the current state of the world.
Definition: tsr.cpp:1095
void useGroup(const std::string &name)
Use the joints in a robot's group. Robot used is the target frame's structure.
Definition: tsr.cpp:998
void setLimit(double limit)
Set the limit parameter in the solver.
Definition: tsr.cpp:1323
void setDamping(double damping)
Set the damping parameter in the solver.
Definition: tsr.cpp:1333
void computeLimits()
Compute the upper and lower limits from the skeleton.
Definition: tsr.cpp:1242
double getStep() const
Get the solver step parameter.
Definition: tsr.cpp:1308
void getErrorWorldState(const Eigen::Ref< const Eigen::VectorXd > &world, Eigen::Ref< Eigen::VectorXd > error) const
Get the error given a provided world configuration.
Definition: tsr.cpp:1044
double damping_
Damping factor.
Definition: tsr.h:990
void setMaxIterations(std::size_t iterations)
Set the maximum iterations used for solving.
Definition: tsr.cpp:1267
void updateSolver()
Update the solver information (iterations, tolerance, etc.)
Definition: tsr.cpp:1190
void setWorldIndices(const std::vector< std::pair< std::size_t, std::size_t >> &indices)
Output world indices. TSR information for *WorldState methods uses this set of world indices....
Definition: tsr.cpp:1016
The specification of a TSR.
Definition: tsr.h:70
void setNoZPosTolerance()
Set no position tolerance on the Z-axis.
Definition: tsr.cpp:228
Eigen::Vector3d lower
Lower position tolerance.
Definition: tsr.h:92
bool isPosConstrained(double lower, double upper) const
Checks if two values correspond to a position constraint.
Definition: tsr.cpp:301
std::string structure
Structure target frame is in.
Definition: tsr.h:76
bool isRotConstrained(double lower, double upper) const
Checks if two values correspond to a orientation constraint.
Definition: tsr.cpp:306
void setTarget(const std::string &structure, const std::string &frame)
Setting TSR Frame.
Definition: tsr.cpp:33
void addSuffix(const std::string &suffix)
Add a suffix to the structures for the target and base frame.
Definition: tsr.cpp:58
void setBase(const std::string &structure, const std::string &frame)
Set the base frame.
Definition: tsr.cpp:42
void setZRotTolerance(double bound)
Set the Z orientation tolerance to (-bound, bound).
Definition: tsr.cpp:183
void setRotation(const Eigen::Quaterniond &orientation)
Set the rotation of the TSR.
Definition: tsr.cpp:74
void setPose(const RobotPose &other)
Set the pose of the TSR.
Definition: tsr.cpp:93
void setFrame(const std::string &structure, const std::string &target, const std::string &base=magic::ROOT_FRAME)
Set the base and target frame.
Definition: tsr.cpp:48
std::string frame
Name of target frame.
Definition: tsr.h:77
void setYPosTolerance(double bound)
Set the Y position tolerance to (-bound, bound).
Definition: tsr.cpp:133
Eigen::Quaterniond getRotation() const
Get the current desired orientation.
Definition: tsr.cpp:316
void setNoPosTolerance()
Set no position tolerance at all.
Definition: tsr.cpp:233
std::size_t maxIter
Maximum iterations for solver.
Definition: tsr.h:109
bool isRotationConstrained() const
Returns true if TSR is orientation constrained.
Definition: tsr.cpp:416
void setNoXPosTolerance()
Set no position tolerance on the X-axis.
Definition: tsr.cpp:218
std::size_t getDimension() const
Compute and return constraint dimension of the TSR.
Definition: tsr.cpp:289
RobotPose pose
Pose of TSR.
Definition: tsr.h:86
void print(std::ostream &out) const
Print out this TSR information.
Definition: tsr.cpp:425
std::size_t dimension
Number of constrained dimensions.
Definition: tsr.h:102
void setNoXRotTolerance()
Set no orientation tolerance on the X-axis.
Definition: tsr.cpp:240
void setNoYPosTolerance()
Set no position tolerance on the Y-axis.
Definition: tsr.cpp:223
void setYRotTolerance(double bound)
Set the Y orientation tolerance to (-bound, bound).
Definition: tsr.cpp:178
Eigen::Vector3d getEulerRotation() const
Get the current desired orientation.
Definition: tsr.cpp:321
void setNoZRotTolerance()
Set no orientation tolerance on the Z-axis.
Definition: tsr.cpp:250
double tolerance
Tolerance on solution for solver.
Definition: tsr.h:110
struct robowflex::darts::TSR::Specification::@5 position
Position tolerances.
bool isPositionConstrained() const
Returns true if TSR is position constrained.
Definition: tsr.cpp:407
struct robowflex::darts::TSR::Specification::@6 orientation
Orientation tolerances.
ROBOWFLEX_EIGEN Eigen::Vector3d upper
Upper position tolerance.
Definition: tsr.h:91
void setXPosTolerance(double bound)
Setting Position Tolerances.
Definition: tsr.cpp:128
ROBOWFLEX_EIGEN struct robowflex::darts::TSR::Specification::@3 target
Target frame.
void setZPosTolerance(double bound)
Set the Z position tolerance to (-bound, bound).
Definition: tsr.cpp:138
void setXRotTolerance(double bound)
Setting Orientation Tolerances.
Definition: tsr.cpp:173
void setPoseFromWorld(const WorldPtr &world)
Set the pose of the TSR for the desired frame in a provided world. Uses world's current configuration...
Definition: tsr.cpp:110
void setNoYRotTolerance()
Set no orientation tolerance on the Y-axis.
Definition: tsr.cpp:245
Eigen::Vector3d getPosition() const
Getters and Informative Methods.
Definition: tsr.cpp:311
void setPosition(const Eigen::Ref< const Eigen::Vector3d > &position)
Setting TSR Pose.
Definition: tsr.cpp:64
struct robowflex::darts::TSR::Specification::@4 base
Base frame.
bool isRelative() const
Returns true if TSR is a relative reference frame (not the world).
Definition: tsr.cpp:402
bool intersect(const Specification &other)
Operations.
Definition: tsr.cpp:326
void setNoRotTolerance()
Set no orientation tolerance at all.
Definition: tsr.cpp:255
void fixBounds()
Fixes bounds so they are correct.
Definition: tsr.cpp:262
std::vector< bool > indices
Vector of active constraints. If an index is true, that constraint is active. Ordered by X-,...
Definition: tsr.h:107
Specification()=default
Default constructor.
dart::dynamics::InverseKinematics::TaskSpaceRegion * tsr_
TSR.
Definition: tsr.h:705
std::size_t getNumDofs() const
Get the number of controlled DoF for this TSR.
Definition: tsr.cpp:563
std::vector< std::size_t > indices_
Controlled indices.
Definition: tsr.h:696
void getErrorWorldRaw(Eigen::Ref< Eigen::VectorXd > error) const
Get the current error given the world state, with all values.
Definition: tsr.cpp:585
bool solveGradientWorld()
Solve using gradient descent for a satisfying configuration given the current state of the world.
Definition: tsr.cpp:730
std::vector< std::pair< std::size_t, std::size_t > > world_indices_
World indices.
Definition: tsr.h:697
const std::vector< std::pair< std::size_t, std::size_t > > & getWorldIndices() const
Get the set of output world indices used.
Definition: tsr.cpp:553
void fromBijection(Eigen::Ref< Eigen::VectorXd > state, const Eigen::Ref< const Eigen::VectorXd > &world) const
From a world configuration, map that configuration into a controlled DoF configuration....
Definition: tsr.cpp:886
std::vector< std::size_t > bijection_
Definition: tsr.h:698
void useWorldIndices(const std::vector< std::pair< std::size_t, std::size_t >> &indices)
Use World DoF indices for TSR computation. World indices are pairs of skeleton index and DoF index.
Definition: tsr.cpp:513
WorldPtr world_
Underlying world.
Definition: tsr.h:692
void updateBounds()
If the bounds of the specification are updated, call this to update underlying IK solver.
Definition: tsr.cpp:821
void getJacobianWorldState(const Eigen::Ref< const Eigen::VectorXd > &world, Eigen::Ref< Eigen::MatrixXd > jacobian) const
Get the Jacobian given a provided world configuration.
Definition: tsr.cpp:643
double distanceWorldState(const Eigen::Ref< const Eigen::VectorXd > &world) const
Get the distance to satisfaction given a provided world configuration.
Definition: tsr.cpp:678
std::shared_ptr< dart::dynamics::SimpleFrame > frame_
Target frame of TSR.
Definition: tsr.h:702
std::vector< std::pair< std::size_t, std::size_t > > computeWorldIndices() const
Compute the set of world indices used based on the underlying active indices.
Definition: tsr.cpp:544
void updateSolver()
If the solver parameters of the specification are updated, call this to update underlying IK solver.
Definition: tsr.cpp:830
void getPositionsWorldState(Eigen::Ref< Eigen::VectorXd > world) const
Get the positions of the world into a world configuration.
Definition: tsr.cpp:796
dart::dynamics::BodyNode * tnd_
Target body node.
Definition: tsr.h:703
void toBijection(Eigen::Ref< Eigen::VectorXd > world, const Eigen::Ref< const Eigen::VectorXd > &state) const
From a configuration of controlled indices, map that configuration into a world configuration....
Definition: tsr.cpp:876
void getErrorWorld(Eigen::Ref< Eigen::VectorXd > error) const
Get the current error given the world state.
Definition: tsr.cpp:592
void initialize()
Initialize this TSR. Creates IK node attached to body node in world.
Definition: tsr.cpp:839
double distanceWorld() const
Get the current distance to satisfaction given the world state.
Definition: tsr.cpp:671
void setWorldIndices(const std::vector< std::pair< std::size_t, std::size_t >> &indices)
Output world indices. TSR information for *WorldState methods uses this set of world indices....
Definition: tsr.cpp:525
void clear()
Clears the initialization of this TSR.
Definition: tsr.cpp:474
robowflex::RobotPose getTransformToFrame() const
Gets the transformation from the specification's base to the TSR's frame.
Definition: tsr.cpp:573
std::shared_ptr< dart::dynamics::InverseKinematics > ik_
Inverse kinematics module.
Definition: tsr.h:704
Specification & getSpecification()
Get the specification for this TSR.
Definition: tsr.cpp:810
void getJacobianWorld(Eigen::Ref< Eigen::MatrixXd > jacobian) const
Get the current Jacobian given the world state.
Definition: tsr.cpp:627
bool solve(Eigen::Ref< Eigen::VectorXd > state)
Solve for a satisfying configuration given an initial configuration of the controlled DoF.
Definition: tsr.cpp:718
void computeBijection()
Compute the mapping from world indices to controlled DoF indices.
Definition: tsr.cpp:897
std::size_t getDimension() const
Get the error dimension of this TSR.
Definition: tsr.cpp:558
~TSR()
Destructor. Disables IK on node if created.
Definition: tsr.cpp:469
void setPositions(const Eigen::Ref< const Eigen::VectorXd > &state) const
Set the positions of the world given a configuration.
Definition: tsr.cpp:789
void useIndices(const std::vector< std::size_t > &indices)
Use DoF indices for TSR computation.
Definition: tsr.cpp:501
bool solveWorldState(Eigen::Ref< Eigen::VectorXd > world)
Solve for a satisfying configuration given an initial world configuration.
Definition: tsr.cpp:706
void updatePose()
If the pose of the specification is updated, call this to update underlying IK solver.
Definition: tsr.cpp:815
TSR(const WorldPtr &world, const Specification &spec)
Constructor.
Definition: tsr.cpp:465
void getJacobian(const Eigen::Ref< const Eigen::VectorXd > &state, Eigen::Ref< Eigen::MatrixXd > jacobian) const
Get the Jacobian given a configuration of the controlled DoF.
Definition: tsr.cpp:662
double distance(const Eigen::Ref< const Eigen::VectorXd > &state) const
Get the distance to satisfaction given a configuration of the controlled DoF.
Definition: tsr.cpp:685
void getError(const Eigen::Ref< const Eigen::VectorXd > &state, Eigen::Ref< Eigen::VectorXd > error) const
Get the error given a configuration of the controlled DoF.
Definition: tsr.cpp:621
std::size_t skel_index_
Index of controlled skeleton.
Definition: tsr.h:695
void setPositionsWorldState(const Eigen::Ref< const Eigen::VectorXd > &world) const
Set the positions of the world given a world configuration.
Definition: tsr.cpp:782
void getPositions(Eigen::Ref< Eigen::VectorXd > state) const
Get the positions of the world given into a configuration.
Definition: tsr.cpp:803
void setWorld(const WorldPtr &world)
Set the world used by this TSR.
Definition: tsr.cpp:485
bool solveWorld()
Solve for a satisfying configuration given the current state of the world.
Definition: tsr.cpp:692
bool solveGradientWorldState(Eigen::Ref< Eigen::VectorXd > world)
Solve using gradient descent for a satisfying configuration given an initial world configuration.
Definition: tsr.cpp:742
void useGroup(const std::string &name)
Use the joints in a robot's group. Robot used is the target frame's structure.
Definition: tsr.cpp:492
Specification spec_
TSR specification.
Definition: tsr.h:693
bool solveGradient(Eigen::Ref< Eigen::VectorXd > state)
Solve using gradient descent for a satisfying configuration given an initial configuration of the con...
Definition: tsr.cpp:754
void getErrorWorldState(const Eigen::Ref< const Eigen::VectorXd > &world, Eigen::Ref< Eigen::VectorXd > error) const
Get the error given a provided world configuration.
Definition: tsr.cpp:608
std::size_t getSkeletonIndex()
Get the skeleton index for the target frame's structure.
Definition: tsr.cpp:531
const std::vector< std::size_t > & getIndices() const
Get the set of indices used for TSR computation.
Definition: tsr.cpp:539
std::size_t getNumWorldDofs() const
Get the number of world DoF for this TSR.
Definition: tsr.cpp:568
A shared pointer wrapper for robowflex::darts::World.
T clear(T... args)
T emplace_back(T... args)
T emplace(T... args)
T empty(T... args)
T endl(T... args)
T fabs(T... args)
T isfinite(T... args)
#define RBX_ERROR(fmt,...)
Output a error logging message.
Definition: log.h:102
#define RBX_INFO(fmt,...)
Output a info logging message.
Definition: log.h:118
T max(T... args)
T min(T... args)
Functions for loading and animating robots in Blender.
RobotPose createPoseQ(double x, double y, double z, double W, double X, double Y, double Z)
Creates a robot pose from a linear component and a Quaternion.
Definition: tf.cpp:47
Eigen::Quaterniond getPoseRotation(const RobotPose &pose)
Get the rotational component of a robot pose.
Definition: tf.cpp:69
static const double two_pi
Definition: constants.h:24
static const double pi
Definition: constants.h:21
static const double eps
Definition: constants.h:16
static const std::string ROOT_FRAME
Definition: tsr.h:31
DART-based robot modeling and planning.
Definition: acm.h:16
std::string format(const std::string &fmt, Args &&... args)
Recursion base case, return string form of formatted arguments.
Definition: log.h:60
std::decay< decltype(std::declval< moveit::core::Transforms >().getTransform("")) >::type RobotPose
A pose (point in SE(3)) used in various functions. Defined from what MoveIt! uses.
Definition: adapter.h:24
T resize(T... args)
T size(T... args)