Changeset 18:5b1657e5f5c8 in rrlib_geometry


Ignore:
Timestamp:
14.11.2011 15:36:38 (8 years ago)
Author:
Tobias Föhst <foehst@…>
Branch:
default
Phase:
public
Message:

Fixed issues with static const values and added GetCurvature for 2- and 3-dimensional Bezier curves

Files:
6 edited

Legend:

Unmodified
Added
Removed
  • curves/tBezierCurve.h

    r17 r18  
    8383public: 
    8484 
    85   static const unsigned int cDEGREE; 
    86   static const unsigned int cNUMBER_OF_CONTROL_POINTS; 
     85  static inline const unsigned int Degree() 
     86  { 
     87    return Tdegree; 
     88  } 
     89 
     90  static inline const unsigned int NumberOfControlPoints() 
     91  { 
     92    return Tdegree + 1; 
     93  } 
    8794 
    8895  typedef typename tShape::tPoint::tElement tParameter; 
  • curves/tBezierCurve.hpp

    r17 r18  
    5757// Const values 
    5858//---------------------------------------------------------------------- 
    59 template <size_t Tdimension, typename TElement, unsigned int Tdegree> 
    60 const unsigned int tBezierCurve<Tdimension, TElement, Tdegree>::cDEGREE = Tdegree; 
    61  
    62 template <size_t Tdimension, typename TElement, unsigned int Tdegree> 
    63 const unsigned int tBezierCurve<Tdimension, TElement, Tdegree>::cNUMBER_OF_CONTROL_POINTS = Tdegree + 1; 
    6459 
    6560//---------------------------------------------------------------------- 
     
    7671{ 
    7772  static_assert(Tdegree > 0, "The degree of Bezier curves must be greater than zero"); 
    78   assert(static_cast<size_t>(std::distance(begin, end)) == this->cNUMBER_OF_CONTROL_POINTS); 
     73  assert(static_cast<size_t>(std::distance(begin, end)) == this->NumberOfControlPoints()); 
    7974  size_t index = 0; 
    8075  for (TIterator it = begin; it != end; ++it) 
     
    8883tBezierCurve<Tdimension, TElement, Tdegree>::tBezierCurve(const TSTLContainer &control_points) 
    8984{ 
     85  std::cout << "control_points: " << control_points.size() << std::endl; 
     86  std::cout << "degree: " << Tdegree << std::endl; 
     87  std::cout << "expected number of points: " << this->NumberOfControlPoints() << std::endl; 
    9088  static_assert(Tdegree > 0, "The degree of Bezier curves must be greater than zero"); 
    91   assert(control_points.size() == this->cNUMBER_OF_CONTROL_POINTS); 
     89  assert(control_points.size() == this->NumberOfControlPoints()); 
    9290  for (size_t i = 0; i < control_points.size(); ++i) 
    9391  { 
     
    102100void tBezierCurve<Tdimension, TElement, Tdegree>::SetControlPoint(size_t i, const typename tShape::tPoint &point) 
    103101{ 
    104   assert(i < this->cNUMBER_OF_CONTROL_POINTS); 
     102  assert(i < this->NumberOfControlPoints()); 
    105103  this->control_points[i] = point; 
    106104  this->SetChanged(); 
     
    127125const typename tBezierCurve<Tdimension, TElement, Tdegree>::tSubdivision tBezierCurve<Tdimension, TElement, Tdegree>::GetSubdivision() const 
    128126{ 
    129   typename tShape::tPoint left_half[this->cNUMBER_OF_CONTROL_POINTS]; 
    130   typename tShape::tPoint right_half[this->cNUMBER_OF_CONTROL_POINTS]; 
    131   typename tShape::tPoint temp_points[this->cNUMBER_OF_CONTROL_POINTS]; 
    132   std::memcpy(temp_points, this->control_points, this->cNUMBER_OF_CONTROL_POINTS * sizeof(typename tShape::tPoint)); 
     127  typename tShape::tPoint left_half[this->NumberOfControlPoints()]; 
     128  typename tShape::tPoint right_half[this->NumberOfControlPoints()]; 
     129  typename tShape::tPoint temp_points[this->NumberOfControlPoints()]; 
     130  std::memcpy(temp_points, this->control_points, this->NumberOfControlPoints() * sizeof(typename tShape::tPoint)); 
    133131 
    134132  left_half[0] = temp_points[0]; 
     
    147145  } 
    148146 
    149   return std::make_pair(tBezierCurve(left_half, left_half + this->cNUMBER_OF_CONTROL_POINTS), tBezierCurve(right_half, right_half + this->cNUMBER_OF_CONTROL_POINTS)); 
     147  return std::make_pair(tBezierCurve(left_half, left_half + this->NumberOfControlPoints()), tBezierCurve(right_half, right_half + this->NumberOfControlPoints())); 
    150148} 
    151149 
     
    158156  assert((0.0 <= t) && (t <= 1.0)); 
    159157 
    160   typename tShape::tPoint temp_points[this->cNUMBER_OF_CONTROL_POINTS]; 
    161   std::memcpy(temp_points, this->control_points, (this->cNUMBER_OF_CONTROL_POINTS) * sizeof(typename tShape::tPoint)); 
     158  typename tShape::tPoint temp_points[this->NumberOfControlPoints()]; 
     159  std::memcpy(temp_points, this->control_points, (this->NumberOfControlPoints()) * sizeof(typename tShape::tPoint)); 
    162160 
    163161  size_t k = 0; 
     
    332330tBezierCurve<Tdimension, TElement, Tdegree> &tBezierCurve<Tdimension, TElement, Tdegree>::Translate(const math::tVector<Tdimension, TElement> &translation) 
    333331{ 
    334   for (size_t i = 0; i < this->cNUMBER_OF_CONTROL_POINTS; ++i) 
     332  for (size_t i = 0; i < this->NumberOfControlPoints(); ++i) 
    335333  { 
    336334    this->control_points[i] += translation; 
     
    346344tBezierCurve<Tdimension, TElement, Tdegree> &tBezierCurve<Tdimension, TElement, Tdegree>::Rotate(const math::tMatrix<Tdimension, Tdimension, TElement> &rotation) 
    347345{ 
    348   for (size_t i = 0; i < this->cNUMBER_OF_CONTROL_POINTS; ++i) 
     346  for (size_t i = 0; i < this->NumberOfControlPoints(); ++i) 
    349347  { 
    350348    this->control_points[i] = rotation * this->control_points[i]; 
     
    377375#endif 
    378376 
    379   for (size_t i = 0; i < this->cNUMBER_OF_CONTROL_POINTS; ++i) 
     377  for (size_t i = 0; i < this->NumberOfControlPoints(); ++i) 
    380378  { 
    381379    this->control_points[i] = transformation.MultiplyHomogeneously(this->control_points[i]); 
     
    391389void tBezierCurve<Tdimension, TElement, Tdegree>::UpdateBoundingBox(typename tShape::tBoundingBox &bounding_box) const 
    392390{ 
    393   for (size_t i = 0; i < this->cNUMBER_OF_CONTROL_POINTS; ++i) 
     391  for (size_t i = 0; i < this->NumberOfControlPoints(); ++i) 
    394392  { 
    395393    bounding_box.Add(this->control_points[i]); 
     
    403401void tBezierCurve<Tdimension, TElement, Tdegree>::UpdateCenterOfGravity(typename tShape::tPoint &center_of_gravity) const 
    404402{ 
    405   for (size_t i = 0; i < this->cNUMBER_OF_CONTROL_POINTS; ++i) 
     403  for (size_t i = 0; i < this->NumberOfControlPoints(); ++i) 
    406404  { 
    407405    center_of_gravity += this->control_points[i]; 
    408406  } 
    409   center_of_gravity /= this->cNUMBER_OF_CONTROL_POINTS; 
     407  center_of_gravity /= this->NumberOfControlPoints(); 
    410408} 
    411409 
  • functions.h

    r14 r18  
    4242#include <cmath> 
    4343 
     44#include <boost/utility/enable_if.hpp> 
     45 
    4446//---------------------------------------------------------------------- 
    4547// Internal includes with "" 
     
    6365inline const math::tAngleRad GetSlope(const tLineSegment<2, TElement> &line_segment) 
    6466{ 
    65   return std::atan2(line.End().Y() - line.Begin().Y(), line.End().X() - line.Begin().X()); 
     67  return std::atan2(line_segment.End().Y() - line_segment.Begin().Y(), line_segment.End().X() - line_segment.Begin().X()); 
    6668} 
     69 
     70template <size_t Tdimension, typename TElement, unsigned int Tdegree> 
     71inline const typename boost::enable_if_c<(Tdimension <= 3), double>::type GetCurvature(const tBezierCurve<Tdimension, TElement, Tdegree> &curve, TElement parameter) 
     72{ 
     73  typename tBezierCurve<Tdimension, TElement, Tdegree>::tDerivative first_derivative(curve.GetDerivative()); 
     74  typename tBezierCurve<Tdimension, TElement, Tdegree>::tDerivative::tDerivative second_derivative(first_derivative.GetDerivative()); 
     75 
     76  math::tVector<3, TElement, math::vector::Cartesian> first(first_derivative(parameter)); 
     77  math::tVector<3, TElement, math::vector::Cartesian> second(second_derivative(parameter)); 
     78  double first_length = first.Length(); 
     79 
     80  return CrossProduct(first, second).Length() / (first_length * first_length * first_length); 
     81} 
     82 
     83 
    6784 
    6885//---------------------------------------------------------------------- 
  • tShape.h

    r14 r18  
    8181public: 
    8282 
    83   static const size_t cDIMENSION; 
     83  static inline const size_t Dimension() 
     84  { 
     85    return Tdimension; 
     86  } 
    8487 
    8588  typedef geometry::tPoint<Tdimension, TElement> tPoint; 
  • tShape.hpp

    r14 r18  
    5757// Const values 
    5858//---------------------------------------------------------------------- 
    59 template <size_t Tdimension, typename TElement> 
    60 const size_t tShape<Tdimension, TElement>::cDIMENSION = Tdimension; 
    6159 
    6260//---------------------------------------------------------------------- 
  • test/test_geometries.cpp

    r17 r18  
    4646#include "rrlib/geometry/curves/tUniformBSplineCurve.h" 
    4747#include "rrlib/geometry/curves/tCardinalSplineCurve.h" 
     48#include "rrlib/geometry/functions.h" 
    4849 
    4950//---------------------------------------------------------------------- 
     
    117118void DrawControlPolygon(tWindow &window, const tBezierCurve &bezier_curve) 
    118119{ 
    119   for (size_t i = 1; i < bezier_curve.cNUMBER_OF_CONTROL_POINTS; ++i) 
     120  for (size_t i = 1; i < bezier_curve.NumberOfControlPoints(); ++i) 
    120121  { 
    121122    const tPoint &start(bezier_curve.GetControlPoint(i - 1)); 
     
    188189  control_points.push_back(tPoint(0.3, 0.5)); 
    189190  control_points.push_back(tPoint(0.7, 0.6)); 
    190   control_points.push_back(tPoint(0.9, 0.4)); 
     191  control_points.push_back(tPoint(0.5, 0.2)); 
    191192 
    192193  window.Clear(); 
     
    211212  DrawBezierCurve(window, bezier_curve); 
    212213  window.Render(); 
     214 
     215 
     216  for (int i = 0; i <= 100; ++i) 
     217  { 
     218    double t = i / 100.0; 
     219    tPoint p = bezier_curve(t); 
     220    window.Clear(); 
     221    DrawBezierCurve(window, bezier_curve); 
     222    DrawPoint(window, p); 
     223 
     224    double curvature = rrlib::geometry::GetCurvature(bezier_curve, t); 
     225    if (curvature > 0.0) 
     226    { 
     227      double radius = 1.0 / curvature; 
     228 
     229      tBezierCurve::tDerivative first(bezier_curve.GetDerivative()); 
     230      tPoint m(p + (first(t).Normalized().Rotated(-M_PI_2) * radius)); 
     231 
     232      window.SetColor(1); 
     233      window.DrawCircleNormalized(m.X(), m.Y(), radius, false); 
     234    } 
     235 
     236    window.Render(); 
     237  } 
    213238 
    214239  std::cout << std::endl << "=== Bezier curve intersects line ===" << std::endl; 
Note: See TracChangeset for help on using the changeset viewer.