GAMS  1.2.2
Coordinate.h
Go to the documentation of this file.
1 
54 #include "ReferenceFrame.h"
55 
56 #ifndef _GAMS_POSE_COORDINATE_H_
57 #define _GAMS_POSE_COORDINATE_H_
58 
59 #include "gams/GamsExport.h"
60 #include <string>
61 #include <cfloat>
62 #include <utility>
63 #include "gams/CPP11_compat.h"
64 #include "madara/knowledge/containers/DoubleVector.h"
65 #include "madara/knowledge/containers/NativeDoubleVector.h"
66 #include "ReferenceFrameFwd.h"
67 
68 
69 #ifdef __GNUC__
70 #pragma GCC diagnostic push
71 #pragma GCC diagnostic ignored "-Wunused-parameter"
72 #include "Eigen/Geometry"
73 #pragma GCC diagnostic pop
74 #endif
75 
76 #define INVAL_COORD DBL_MAX
77 
78 namespace gams { namespace pose {
79 
81 namespace units {
83  template<typename T>
84  struct absolute {};
85 
86  struct length {};
87  struct velocity {};
88  struct acceleration {};
89  struct plane_angle {};
90  struct angular_velocity {};
92 
94  template<typename T>
95  struct base_of
96  {
97  using type = T;
98  };
99 
100  template<typename T>
101  struct base_of<absolute<T>>
102  {
103  using type = T;
104  };
105 
107  template<typename L, typename R>
108  struct same_base :
109  std::is_same<typename base_of<L>::type,
110  typename base_of<R>::type> {};
111 }
112 
114 template<typename Units>
116 {
117  static_assert(sizeof(Units) < 0, "Unit type not supported by BasicVector");
118 };
119 
122 {
124  {
125  private:
126  Eigen::Vector3d vec_;
127 
128  public:
130  : vec_(0, 0, 0) {}
131 
132  storage_mixin(double x, double y)
133  : vec_(x, y, 0) {}
134 
135  storage_mixin(double x, double y, double z)
136  : vec_(x, y, z) {}
137 
138  template<typename T, size_t N,
139  typename std::enable_if<std::is_floating_point<T>::value, int>::type = 0>
140  storage_mixin(T (&a)[N])
141  : vec_(N>0 ? a[0] : 0, N>1 ? a[1] : 0, N>2 ? a[2] : 0) {}
142 
143  explicit storage_mixin(const Eigen::Vector3d &vec) : vec_(vec) {}
144 
145  explicit storage_mixin(const madara::knowledge::containers::DoubleVector &v)
146  : vec_(v.size() > 0 ? v[0] : 0,
147  v.size() > 1 ? v[1] : 0,
148  v.size() > 2 ? v[2] : 0) {}
149 
150  explicit storage_mixin(const madara::knowledge::containers::NativeDoubleVector &v)
151  : vec_(v.size() > 0 ? v[0] : 0,
152  v.size() > 1 ? v[1] : 0,
153  v.size() > 2 ? v[2] : 0) {}
154 
155  Eigen::Vector3d &vec() { return vec_; }
156  const Eigen::Vector3d &vec() const { return vec_; }
157  };
158 };
159 
162 {
163  static const bool positional = true;
164 };
165 
166 class Quaternion;
167 
168 inline Eigen::Vector3d quat_to_axis_angle(const Eigen::Quaterniond &quat)
169 {
170  double norm = sqrt(quat.x() * quat.x() +
171  quat.y() * quat.y() +
172  quat.z() * quat.z());
173  double angle = 2 * atan2(norm, quat.w());
174  double sin_half_angle = sin(angle / 2);
175  if(sin_half_angle < 1e-10)
176  {
177  return {0, 0, 0};
178  }
179  return {(quat.x() / sin_half_angle) * angle,
180  (quat.y() / sin_half_angle) * angle,
181  (quat.z() / sin_half_angle) * angle};
182 }
183 
186 {
187  static const bool positional = false;
188 
190  {
191  public:
193  using Base::Base;
194 
195  storage_mixin() = default;
196 
197  storage_mixin(const Quaternion &quat);
198 
199  template<typename Units>
200  storage_mixin(double rx, double ry, double rz, Units units)
201  : Base(units.to_radians(rx),
202  units.to_radians(ry),
203  units.to_radians(rz)) {}
204 
205  template<typename T, typename Units, size_t N,
206  typename std::enable_if<std::is_floating_point<T>::value, int>::type = 0>
207  storage_mixin(T (&a)[N], Units units)
208  : Base(
209  N>0 ? units.to_radians(a[0]) : 0,
210  N>1 ? units.to_radians(a[1]) : 0,
211  N>2 ? units.to_radians(a[2]) : 0) {}
212 
213  public:
218  storage_mixin(const Eigen::Quaterniond &quat)
219  : Base(quat_to_axis_angle(quat)) {}
220  };
221 };
222 
224 template<typename Derived>
226 {
227  Derived &self() { return static_cast<Derived&>(*this); }
228  const Derived &self() const { return static_cast<const Derived&>(*this); }
229 
230  double x() const { return self().vec()[0]; }
231  double y() const { return self().vec()[1]; }
232  double z() const { return self().vec()[2]; }
233 
234  double x(double v) { return (self().vec()[0] = v); }
235  double y(double v) { return (self().vec()[1] = v); }
236  double z(double v) { return (self().vec()[2] = v); }
237 };
238 
239 template<>
240 struct unit_traits<units::absolute<units::length>>
242 {
243  static const bool free = false;
244 
245  template<typename Derived>
246  struct mixin : basic_positional_mixin<Derived> {
248  using Base::x;
249  using Base::y;
250  using Base::z;
251  using Base::self;
252 
253  double lng () const { return x(); }
254  double lon () const { return x(); }
255  double longitude () const { return x(); }
256 
257  double lat () const { return y(); }
258  double latitude () const { return y(); }
259 
260  double alt () const { return -z(); }
261  double altitude () const { return -z(); }
262 
263  double lng (double v) { return x(v); }
264  double lon (double v) { return x(v); }
265  double longitude (double v) { return x(v); }
266 
267  double lat (double v) { return y(v); }
268  double latitude (double v) { return y(v); }
269 
270  double alt (double v) { return z(-v); }
271  double altitude (double v) { return z(-v); }
272 
273  Eigen::Vector3d &pos_vec() { return self().vec(); }
274  const Eigen::Vector3d &pos_vec() const { return self().vec(); }
275  };
276 };
277 
278 template<>
279 struct unit_traits<units::length>
281 {
282  static const bool free = true;
283 
284  template<typename Derived>
285  struct mixin : basic_positional_mixin<Derived> {
287  using Base::self;
288 
289  Eigen::Vector3d &dis_vec() { return self().vec(); }
290  const Eigen::Vector3d &dis_vec() const { return self().vec(); }
291  };
292 };
293 
294 template<>
295 struct unit_traits<units::velocity>
297 {
298  static const bool free = true;
299 
300  template<typename Derived>
301  struct mixin {
302  Derived &self() { return static_cast<Derived&>(*this); }
303  const Derived &self() const { return static_cast<const Derived&>(*this); }
304 
305  double dx() const { return self().vec()[0]; }
306  double dy() const { return self().vec()[1]; }
307  double dz() const { return self().vec()[2]; }
308 
309  double dx(double v) { return (self().vec()[0] = v); }
310  double dy(double v) { return (self().vec()[1] = v); }
311  double dz(double v) { return (self().vec()[2] = v); }
312 
313  Eigen::Vector3d &vel_vec() { return self().vec(); }
314  const Eigen::Vector3d &vel_vec() const { return self().vec(); }
315  };
316 };
317 
318 template<>
319 struct unit_traits<units::acceleration>
321 {
322  static const bool positional = true;
323  static const bool free = true;
324 
325  template<typename Derived>
326  struct mixin {
327  Derived &self() { return static_cast<Derived&>(*this); }
328  const Derived &self() const { return static_cast<const Derived&>(*this); }
329 
330  double ddx() const { return self().vec()[0]; }
331  double ddy() const { return self().vec()[1]; }
332  double ddz() const { return self().vec()[2]; }
333 
334  double ddx(double v) { return (self().vec()[0] = v); }
335  double ddy(double v) { return (self().vec()[1] = v); }
336  double ddz(double v) { return (self().vec()[2] = v); }
337 
338  Eigen::Vector3d &acc_vec() { return self().vec(); }
339  const Eigen::Vector3d &acc_vec() const { return self().vec(); }
340  };
341 };
342 
344 template<typename Derived>
346 {
347  Derived &self() { return static_cast<Derived&>(*this); }
348  const Derived &self() const { return static_cast<const Derived&>(*this); }
349 
350  double angle_to(const Derived &target) const
351  {
352  return self().distance_to(target);
353  }
354 
355  template<typename U>
356  double angle_to (const Derived &target, U u) const
357  {
358  return u.from_radians (self().angle_to (target));
359  }
360 };
361 
363 template<typename Derived>
365 {
367  using Base::self;
368 
369  double rx() const { return self().vec()[0]; }
370  double ry() const { return self().vec()[1]; }
371  double rz() const { return self().vec()[2]; }
372 
373  double rx(double v) { return (self().vec()[0] = v); }
374  double ry(double v) { return (self().vec()[1] = v); }
375  double rz(double v) { return (self().vec()[2] = v); }
376 
381  Eigen::Quaterniond into_quat() const
382  {
383  double magnitude = sqrt(rx() * rx() + ry() * ry() + rz() * rz());
384  if(magnitude == 0)
385  {
386  return {1, 0, 0, 0};
387  }
388  double half_mag = magnitude / 2;
389  double cos_half_mag = cos(half_mag);
390  double sin_half_mag = sin(half_mag);
391  return {cos_half_mag,
392  (rx() / magnitude) * sin_half_mag,
393  (ry() / magnitude) * sin_half_mag,
394  (rz() / magnitude) * sin_half_mag};
395  }
396 
397  void from_quat(const Eigen::Quaterniond &quat)
398  {
399  this->vec() = quat_to_axis_angle(quat);
400  }
401 
402  template<typename Other>
403  auto slerp(double scale, const Other &other) ->
404  typename std::decay<decltype(other.into_quat(),
405  std::declval<Derived>())>::type
406  {
407  return Derived(into_quat().slerp(scale, other.into_quat()));
408  }
409 
410  template<typename Other>
411  auto slerp(const Other &other, double scale) ->
412  typename std::decay<decltype(other.into_quat(),
413  std::declval<Derived>())>::type
414  {
415  return slerp(scale, other);
416  }
417 
418  template<typename Other>
419  auto slerp_this(double scale, const Other &other) ->
420  decltype(other.into_quat(), void())
421  {
422  self() = Derived(into_quat().slerp(scale, other.into_quat()));
423  }
424 
425  template<typename Other>
426  auto slerp_this(const Other &other, double scale) ->
427  decltype(other.into_quat(), void())
428  {
429  return slerp_this(scale, other);
430  }
431 };
432 
433 template<>
434 struct unit_traits<units::absolute<units::plane_angle>>
436 {
437  static const bool free = false;
438 
439  template<typename Derived>
440  struct mixin : basic_rotational_mixin<Derived> {
442  using Base::self;
443 
444  Eigen::Vector3d &ori_vec() { return self().vec(); }
445  const Eigen::Vector3d &ori_vec() const { return self().vec(); }
446  };
447 };
448 
449 template<>
450 struct unit_traits<units::plane_angle>
452 {
453  static const bool free = true;
454 
455  template<typename Derived>
456  struct mixin : basic_rotational_mixin<Derived> {
458  using Base::self;
459 
460  Eigen::Vector3d &rot_vec() { return self().vec(); }
461  const Eigen::Vector3d &rot_vec() const { return self().vec(); }
462  };
463 };
464 
465 template<>
466 struct unit_traits<units::angular_velocity>
468 {
469  static const bool free = true;
470 
471  template<typename Derived>
472  struct mixin {
473  Derived &self() { return static_cast<Derived&>(*this); }
474  const Derived &self() const { return static_cast<const Derived&>(*this); }
475 
476  double drx() const { return self().vec()[0]; }
477  double dry() const { return self().vec()[1]; }
478  double drz() const { return self().vec()[2]; }
479 
480  double drx(double v) { return (self().vec()[0] = v); }
481  double dry(double v) { return (self().vec()[1] = v); }
482  double drz(double v) { return (self().vec()[2] = v); }
483 
484  Eigen::Vector3d &ang_vel_vec() { return self().vec(); }
485  const Eigen::Vector3d &ang_vel_vec() const { return self().vec(); }
486  };
487 };
488 
489 template<>
490 struct unit_traits<units::angular_acceleration>
492 {
493  static const bool positional = true;
494  static const bool free = true;
495 
496  template<typename Derived>
497  struct mixin {
498  Derived &self() { return static_cast<Derived&>(*this); }
499  const Derived &self() const { return static_cast<const Derived&>(*this); }
500 
501  double ddrx() const { return self().vec()[0]; }
502  double ddry() const { return self().vec()[1]; }
503  double ddrz() const { return self().vec()[2]; }
504 
505  double ddrx(double v) { return (self().vec()[0] = v); }
506  double ddry(double v) { return (self().vec()[1] = v); }
507  double ddrz(double v) { return (self().vec()[2] = v); }
508 
509  Eigen::Vector3d &ang_acc_vec() { return self().vec(); }
510  const Eigen::Vector3d &ang_acc_vec() const { return self().vec(); }
511  };
512 };
513 
515 template<typename Derived, typename Units>
517  : public unit_traits<Units>::storage_mixin,
518  public unit_traits<Units>::template mixin<Derived>
519 {
520 private:
521  Eigen::Vector3d vec_;
522 
526 
527 public:
528  using storage_mixin::storage_mixin;
529  using storage_mixin::vec;
530 
531  using mixin::self;
532 
533  using derived_type = Derived;
534  using units_type = Units;
535 
536  BasicVector() = default;
537 
539  template<typename Derived2>
541 
543  static constexpr bool positional() { return traits::positional; }
544 
546  static constexpr bool rotational() { return !positional(); }
547 
549  static constexpr bool free() { return traits::free; }
550 
552  static constexpr bool fixed() { return !free(); }
553 
555  size_t size() const { return (size_t)vec().size(); }
556 
560  double get(size_t i) const { return vec()[i]; }
561 
568  double set(size_t i, double v) { return (vec()[i] = v); }
569 
571  bool is_set() const
572  {
573  for (int i = 0; i < vec().size(); ++i) {
574  if (vec()[i] != INVAL_COORD) {
575  return true;
576  }
577  }
578  return false;
579  }
580 
582  bool is_zero() const
583  {
584  for (int i = 0; i < vec().size(); ++i) {
585  if (vec()[i] != 0) {
586  return false;
587  }
588  }
589  return true;
590  }
591 
605  template<typename ContainType>
606  void to_array(ContainType &out) const
607  {
608  for(size_t i = 0; i < size(); i++)
609  {
610  out[i] = get(i);
611  }
612  }
613 
626  template<typename ContainType>
627  void from_array(const ContainType &in)
628  {
629  for(size_t i = 0; i < size(); i++)
630  {
631  set(i, in[i]);
632  }
633  }
634 
641  std::string to_string (
642  const std::string & delimiter = ",",
643  const std::string & unset_identifier = "<unset>") const
644  {
645  std::stringstream buffer;
646  bool first = true;
647 
648  for (int i = 0; i < vec().size(); ++i)
649  {
650  auto x = vec()[i];
651 
652  if (!first) {
653  buffer << delimiter;
654  } else {
655  first = false;
656  }
657 
658  if (x != INVAL_COORD)
659  buffer << x;
660  else
661  buffer << unset_identifier;
662  }
663 
664  return buffer.str ();
665  }
666 
672  madara::knowledge::containers::NativeDoubleVector &container) const
673  {
674  container.set (0, this->get (0));
675  container.set (1, this->get (1));
676  container.set (2, this->get (2));
677  }
678 
684  const madara::knowledge::containers::NativeDoubleVector &container)
685  {
686  this->set (0, container[0]);
687  this->set (1, container[1]);
688  this->set (2, container[2]);
689  }
690 
694  template<typename Other>
695  double dot(const BasicVector<Other, Units> &other) const
696  {
697  return this->vec().dot(other.vec());
698  }
699 
703  template<typename Other>
704  Derived cross(const BasicVector<Other, Units> &other) const
705  {
706  Derived ret = this->self();
707  ret.vec() = this->vec().cross(other.vec());
708  return ret;
709  }
710 
714  double norm() const
715  {
716  return this->vec().norm();
717  }
718 
722  double squaredNorm() const
723  {
724  return this->vec().squaredNorm();
725  }
726 
730  Derived normalized() const
731  {
732  Derived ret = this->self();
733  ret.vec().normalize();
734  return ret;
735  }
736 
747  /*template<typename Derived2>
748  bool approximately_equal(const BasicVector<Derived2, Units> &other,
749  double epsilon) const
750  {
751  return std::fabs(self().distance_to(other.self())) < epsilon;
752  }*/
753 
770  /*template<typename Derived2>
771  double distance_to(const BasicVector<Derived2, Units> &target) const {
772  return (target.vec() - vec()).norm();
773  }*/
774 };
775 
776 } }
777 
778 #include "Coordinate.inl"
779 
780 #include "Framed.h"
781 #include "Stamped.h"
782 
783 namespace gams { namespace pose {
784 
786 #define GAMS_POSE_MAKE_COMPOSITE_VEC_SCALAR_OP(op) \
787 template<typename Derived, typename Units, typename Scalar> \
788 inline auto operator op##=(BasicVector<Derived, Units> &vec, Scalar scalar) -> \
789  typename std::enable_if<std::is_arithmetic<Scalar>::value && \
790  BasicVector<Derived, Units>::free(), \
791  typename BasicVector<Derived, Units>::derived_type&>::type \
792 { \
793  vec.vec() op##= scalar; \
794  return vec.self(); \
795 }
796 
798 #define GAMS_POSE_MAKE_BINARY_VEC_SCALAR_OP(op) \
799 template<typename Derived, typename Units, typename Scalar> \
800 inline auto operator op(const BasicVector<Derived, Units> &vec, Scalar scalar) -> \
801  typename std::enable_if<std::is_arithmetic<Scalar>::value && \
802  BasicVector<Derived, Units>::free(), \
803  typename BasicVector<Derived, Units>::derived_type>::type \
804 { \
805  typename BasicVector<Derived, Units>::derived_type ret = vec.self(); \
806  ret op##= scalar; \
807  return ret; \
808 } \
809 \
810 template<typename Derived, typename Units, typename Scalar> \
811 inline auto operator op(Scalar scalar, const BasicVector<Derived, Units> &vec) -> \
812  decltype(vec op scalar) \
813 { \
814  return vec op scalar; \
815 }
816 
817 #define GAMS_POSE_MAKE_VEC_SCALAR_OPS(op) \
818 GAMS_POSE_MAKE_COMPOSITE_VEC_SCALAR_OP(op) \
819 GAMS_POSE_MAKE_BINARY_VEC_SCALAR_OP(op)
820 
823 
825 #define GAMS_POSE_MAKE_COMPOSITE_VECS_OP(op) \
826 template<typename LDerived, \
827  typename RDerived, typename Units> \
828 inline auto operator op##=(BasicVector<LDerived, Units> &lhs, \
829  const Eigen::MatrixBase<RDerived> &rhs) -> \
830  typename std::enable_if<unit_traits<Units>::positional, \
831  LDerived &>::type \
832 { \
833  lhs.vec() op##= rhs; \
834  return lhs.self(); \
835 } \
836 \
837 template<typename LDerived, \
838  typename RDerived, typename Units> \
839 inline auto operator op##=(BasicVector<LDerived, Units> &lhs, \
840  const BasicVector<RDerived, Units> &rhs) -> \
841  typename std::enable_if<unit_traits<Units>::positional && \
842  unit_traits<Units>::free, LDerived &>::type \
843 { \
844  lhs.vec() op##= rhs.vec(); \
845  return lhs.self(); \
846 } \
847 \
848 template<typename LDerived, \
849  typename RDerived, typename Units> \
850 inline auto operator op##=(BasicVector<LDerived, units::absolute<Units>> &lhs, \
851  const BasicVector<RDerived, Units> &rhs) -> \
852  typename std::enable_if<unit_traits<Units>::positional && \
853  unit_traits<Units>::free, LDerived &>::type \
854 { \
855  lhs.vec() op##= rhs.vec(); \
856  return lhs.self(); \
857 } \
858 
861 
864 template<typename LDerived, typename LUnits,
865  typename RDerived, typename RUnits>
866 inline auto operator+(const BasicVector<LDerived, LUnits> &lhs,
867  const BasicVector<RDerived, RUnits> &rhs) ->
868  typename std::enable_if<RDerived::free(), LDerived>::type
869 {
870  LDerived ret = lhs.self();
871  ret += rhs;
872  return ret;
873 }
874 
877 template<typename LDerived, typename LUnits,
878  typename RDerived, typename RUnits>
879 inline auto operator+(const BasicVector<LDerived, LUnits> &lhs,
880  const BasicVector<RDerived, RUnits> &rhs) ->
881  typename std::enable_if<LDerived::free() && RDerived::fixed(), RDerived>::type
882 {
883  RDerived ret = rhs.self();
884  ret += lhs;
885  return ret;
886 }
887 
890 template<typename LDerived, typename LUnits,
891  typename RDerived, typename RUnits>
893  const BasicVector<RDerived, RUnits> &rhs) ->
894  typename std::enable_if<LDerived::free() && RDerived::free(), LDerived>::type
895 {
896  LDerived ret = lhs.self();
897  ret -= rhs;
898  return ret;
899 }
900 
903 template<typename T>
904 struct fixed_into_free {};
905 
908 template<typename LDerived, typename LUnits,
909  typename RDerived, typename RUnits>
910 inline auto operator-(const BasicVector<LDerived, LUnits> &lhs,
911  const BasicVector<RDerived, RUnits> &rhs) ->
912  typename std::enable_if<LDerived::fixed() && RDerived::fixed(),
913  typename fixed_into_free<LDerived>::type>::type
914 {
915  typename fixed_into_free<LDerived>::type ret(lhs);
916  ret.vec() -= rhs.vec();
917  return ret;
918 }
919 
921 #define GAMS_POSE_MAKE_COORDINATE_COMPARE_OPS(op) \
922  template<typename LDerived, typename RDerived, typename Units> \
923  inline bool operator op ( \
924  const BasicVector<LDerived, Units> &lhs, \
925  const BasicVector<RDerived, Units> &rhs) \
926  { \
927  for (int i = 0; i < lhs.vec().size(); ++i) { \
928  if (!(lhs.vec()[i] op rhs.vec()[i])) { \
929  return false; \
930  } \
931  } \
932  return true; \
933  } \
934  \
935  template<typename LDerived, typename RDerived, typename Units> \
936  inline bool operator op ( \
937  const Framed<BasicVector<LDerived, Units>> &lhs, \
938  const Framed<BasicVector<RDerived, Units>> &rhs) \
939  { \
940  return lhs.frame() op rhs.frame() && \
941  static_cast<const BasicVector<LDerived, Units> &>(lhs) op \
942  static_cast<const BasicVector<RDerived, Units> &>(rhs); \
943  } \
944  \
945  template<typename LDerived, typename RDerived, typename Units> \
946  inline bool operator op ( \
947  const Stamped<Framed<BasicVector<LDerived, Units>>> &lhs, \
948  const Stamped<Framed<BasicVector<RDerived, Units>>> &rhs) \
949  { \
950  return lhs.time() op rhs.time() && \
951  static_cast<const Framed<BasicVector<LDerived, Units> &>>(lhs) op \
952  static_cast<const Framed<BasicVector<RDerived, Units> &>>(rhs); \
953  }
954 
961 
966 #define GAMS_POSE_MAKE_COORDINATE_TYPE(name, units) \
967 class name##Vector : \
968  public BasicVector<name##Vector, units> \
969 { \
970 public: \
971  using Base = BasicVector<name##Vector, units>; \
972  using Base::Base; \
973  static constexpr const char * type_name = #name "Vector"; \
974 }; \
975 \
976 class name : \
977  public Framed<BasicVector<name, units>> \
978 { \
979 public: \
980  using Base = Framed<BasicVector<name, units>>; \
981  using Base::Base; \
982  static constexpr const char * type_name = #name; \
983  operator name##Vector () const { return name##Vector(this->vec()); } \
984  name(name##Vector o) : Base(o.vec()) {} \
985  name() = default; \
986 }; \
987 \
988 class Stamped##name : \
989  public Stamped<Framed<BasicVector<Stamped##name, units>>> \
990 { \
991 public: \
992  using Base = Stamped<Framed<BasicVector<Stamped##name, units>>>; \
993  using Base::Base; \
994  static constexpr const char * type_name = "Stamped" #name; \
995  operator name##Vector () const { return name##Vector(this->vec()); } \
996  operator name () const { return name(this->frame(), this->vec()); } \
997  Stamped##name(name##Vector o) : Base(o.vec()) {} \
998  Stamped##name(name o) : Base(o.frame(), o.vec()) {} \
999  Stamped##name() = default; \
1000 }
1001 
1005 class Position;
1006 
1011 class Position;
1012 
1016 class Velocity;
1017 
1021 class Accelerations;
1022 
1029 class Orientation;
1030 
1037 class Rotation;
1038 
1044 class AngularVelocity;
1045 
1051 class AngularAccelerations;
1052 
1057 
1062 
1063 template<>
1065 {
1067 };
1068 
1069 template<>
1071 {
1073 };
1074 
1075 template<>
1077 {
1079 };
1080 
1081 template<>
1083 {
1085 };
1086 
1087 template<>
1089 {
1090  using type = Rotation;
1091 };
1092 
1093 template<>
1095 {
1097 };
1098 
1099 inline std::ostream &operator<<(std::ostream &o, const Eigen::Vector3d &v)
1100 {
1101  bool first = true;
1102  for (int i = 0; i < v.size(); ++i)
1103  {
1104  auto x = v[i];
1105 
1106  if (!first) {
1107  o << ",";
1108  } else {
1109  first = false;
1110  }
1111 
1112  if (x != INVAL_COORD) {
1113  o << x;
1114  } else {
1115  o << "<unset>";
1116  }
1117  }
1118  return o;
1119 }
1120 
1121 template<typename Derived, typename Units>
1122 inline std::ostream &operator<<(std::ostream &o, const BasicVector<Derived, Units> &v)
1123 {
1124  o << Derived::type_name << "(";
1125  o << v.vec();
1126  o << ")";
1127  return o;
1128 }
1129 
1130 } }
1131 
1132 #endif
void from_container(const madara::knowledge::containers::NativeDoubleVector &container)
Assign values from a NativeDoubleVector container.
Definition: Coordinate.h:683
void to_array(ContainType &out) const
Outputs this Coordinates values to the referenced container.
Definition: Coordinate.h:606
auto slerp(const Other &other, double scale) -> typename std::decay< decltype(other.into_quat(), std::declval< Derived >())>::type
Definition: Coordinate.h:411
void from_quat(const Eigen::Quaterniond &quat)
Definition: Coordinate.h:397
double norm() const
Passthrough to Eigen vector norm method.
Definition: Coordinate.h:714
storage_mixin(const madara::knowledge::containers::DoubleVector &v)
Definition: Coordinate.h:145
double squaredNorm() const
Passthrough to Eigen vector squaredNorm method.
Definition: Coordinate.h:722
Derived cross(const BasicVector< Other, Units > &other) const
Passthrough to Eigen vector cross method.
Definition: Coordinate.h:704
Copyright (c) 2015 Carnegie Mellon University.
#define GAMS_POSE_MAKE_COMPOSITE_VECS_OP(op)
Generates Eigen passthroughs on vectors.
Definition: Coordinate.h:825
const Eigen::Vector3d & vec() const
Definition: Coordinate.h:156
static constexpr bool positional()
Is this coordinate a positional one?
Definition: Coordinate.h:543
bool is_zero() const
Does this coordinate have values all zeroes?
Definition: Coordinate.h:582
Trait to compare types, ignoring absolute.
Definition: Coordinate.h:108
auto slerp_this(double scale, const Other &other) -> decltype(other.into_quat(), void())
Definition: Coordinate.h:419
static constexpr bool fixed()
Is this coordinate a fixed vector?
Definition: Coordinate.h:552
Helper trait to customize BasicVector based on unit.
Definition: Coordinate.h:115
auto slerp_this(const Other &other, double scale) -> decltype(other.into_quat(), void())
Definition: Coordinate.h:426
STL namespace.
#define GAMS_POSE_MAKE_VEC_SCALAR_OPS(op)
Definition: Coordinate.h:817
static constexpr bool rotational()
Is this coordinate a rotational one?
Definition: Coordinate.h:546
const Eigen::Vector3d & rot_vec() const
Definition: Coordinate.h:461
Helper struct for defining which fixed coordinate types map to which free vector coordinate types...
Definition: Coordinate.h:904
const Eigen::Vector3d & vel_vec() const
Definition: Coordinate.h:314
Eigen::Quaterniond into_quat() const
Represent this rotation as a quaternion.
Definition: Coordinate.h:381
storage_mixin(double rx, double ry, double rz, Units units)
Definition: Coordinate.h:200
storage_mixin(const Eigen::Quaterniond &quat)
Construct from a Quaternion.
Definition: Coordinate.h:218
typename unit_traits< Units >::storage_mixin storage_mixin
Definition: Coordinate.h:524
Eigen::Vector3d vec_
Definition: Coordinate.h:521
std::string to_string(const std::string &delimiter=",", const std::string &unset_identifier="<unset>") const
Returns a string of the values x, y, z.
Definition: Coordinate.h:641
bool is_set() const
Does this coordinate have any values not INVAL_COORD?
Definition: Coordinate.h:571
BasicVector(const BasicVector< Derived2, Units > &v)
Construct from a vector of same units, but different derived type.
Definition: Coordinate.h:540
#define GAMS_POSE_MAKE_COORDINATE_COMPARE_OPS(op)
Generates comparison operators for coordinate types.
Definition: Coordinate.h:921
const Eigen::Vector3d & dis_vec() const
Definition: Coordinate.h:290
Tag that coordinate is a fixed vector, not free.
Definition: Coordinate.h:84
double angle_to(const Derived &target, U u) const
Definition: Coordinate.h:356
Contains all GAMS-related tools, classes and code.
void to_container(madara::knowledge::containers::NativeDoubleVector &container) const
Assign values into a NativeDoubleVector container.
Definition: Coordinate.h:671
double dot(const BasicVector< Other, Units > &other) const
Passthrough to Eigen vector dot method.
Definition: Coordinate.h:695
const Eigen::Vector3d & acc_vec() const
Definition: Coordinate.h:339
Trait to strip absolute off a unit tag.
Definition: Coordinate.h:95
gams::pose::Orientation Orientation
Represents a orientation or orientation within a reference frame.
Definition: Orientation.h:94
Copyright (c) 2015 Carnegie Mellon University.
#define INVAL_COORD
Definition: Coordinate.h:76
BaseAlgorithm Base
Used internally to implement angle operations.
Definition: Quaternion.h:74
For internal use. The underlying template for all coordinate types.
Definition: Coordinate.h:516
storage_mixin(double x, double y, double z)
Definition: Coordinate.h:135
void normalize()
Reduces this Coordinate to it&#39;s normalized form, should one exist.
typename unit_traits< Units >::template mixin< Derived > mixin
Definition: Coordinate.h:525
Eigen::Vector3d quat_to_axis_angle(const Eigen::Quaterniond &quat)
Definition: Coordinate.h:168
auto operator-(const BasicVector< LDerived, LUnits > &lhs, const BasicVector< RDerived, RUnits > &rhs) -> typename std::enable_if< LDerived::free()&&RDerived::free(), LDerived >::type
Pass through to Eigen operator- on vectors, for free types.
Definition: Coordinate.h:892
storage_mixin(const Eigen::Vector3d &vec)
Definition: Coordinate.h:143
auto slerp(double scale, const Other &other) -> typename std::decay< decltype(other.into_quat(), std::declval< Derived >())>::type
Definition: Coordinate.h:403
size_t size() const
Get number of values in this coordinate.
Definition: Coordinate.h:555
void from_array(const ContainType &in)
Overwrites this Coordinate&#39;s values with those pulled from the referenced array.
Definition: Coordinate.h:627
storage_mixin(const madara::knowledge::containers::NativeDoubleVector &v)
Definition: Coordinate.h:150
auto operator+(const BasicVector< LDerived, LUnits > &lhs, const BasicVector< RDerived, RUnits > &rhs) -> typename std::enable_if< RDerived::free(), LDerived >::type
Pass through to Eigen operator- on vectors, if RHS is free.
Definition: Coordinate.h:866
static constexpr bool free()
Is this coordinate a free vector?
Definition: Coordinate.h:549
#define GAMS_POSE_MAKE_COORDINATE_TYPE(name, units)
Creates the three variants for each coordinate type: {Coordinate}Vector: just the coordinate values a...
Definition: Coordinate.h:966
Derived normalized() const
Passthrough to Eigen vector normalized method.
Definition: Coordinate.h:730
double angle_to(const Derived &target) const
Definition: Coordinate.h:350
std::ostream & operator<<(std::ostream &o, const Eigen::Vector3d &v)
Definition: Coordinate.h:1099