Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032 #ifndef CatmullRomInterpolator_INCLUDE_ONCE
00033 #define CatmullRomInterpolator_INCLUDE_ONCE
00034
00035 #include <vlCore/Interpolator.hpp>
00036
00037 namespace vl
00038 {
00045 template<typename T>
00046 class CatmullRomInterpolator: public Object
00047 {
00048 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolator<typename T>, Object)
00049
00050 public:
00051 CatmullRomInterpolator()
00052 {
00053 VL_DEBUG_SET_OBJECT_NAME()
00054 }
00055
00056 CatmullRomInterpolator(const std::vector<T>& path): mPath(path) {}
00057
00059 void setupEndPoints(bool is_loop)
00060 {
00061 VL_CHECK(mPath.size()>=2)
00062 if (mPath.size()<2)
00063 return;
00064
00065 mCatmullRomSpline = mPath;
00066
00067
00068
00069
00070
00071
00072
00073
00074
00075 if (is_loop)
00076 {
00077 T a = mCatmullRomSpline[0];
00078 T b = mCatmullRomSpline[1];
00079 T c = mCatmullRomSpline[mCatmullRomSpline.size()-2];
00080 T d = mCatmullRomSpline[mCatmullRomSpline.size()-1];
00081
00082 mCatmullRomSpline.insert(mCatmullRomSpline.begin(),d);
00083 mCatmullRomSpline.push_back(a);
00084 mCatmullRomSpline.push_back(b);
00085 }
00086 else
00087 {
00088 T a = mCatmullRomSpline[0] + (mCatmullRomSpline[0] - mCatmullRomSpline[1]);
00089 T b = mCatmullRomSpline[mCatmullRomSpline.size()-1] + (mCatmullRomSpline[mCatmullRomSpline.size()-1] - mCatmullRomSpline[mCatmullRomSpline.size()-2]);
00090 mCatmullRomSpline.insert(mCatmullRomSpline.begin(),a);
00091 mCatmullRomSpline.push_back(b);
00092 }
00093
00094 }
00095
00097 T computePoint(float t) const
00098 {
00099 VL_CHECK(mCatmullRomSpline.size() >= 4)
00100 size_t size = mCatmullRomSpline.size()-2;
00101 t = clamp(t, 0.0f, 1.0f);
00102 if (t == 0.0f)
00103 return mCatmullRomSpline[1];
00104 else
00105 if (t == 1.0f)
00106 return mCatmullRomSpline[ mCatmullRomSpline.size()-1-1 ];
00107 else
00108 {
00109 int i = 1 + (int)((size-1)*t);
00110 int i0 = i-1;
00111 int i1 = i;
00112 int i2 = i+1;
00113 int i3 = i+2;
00114 VL_CHECK(i3<(int)mCatmullRomSpline.size())
00115 float tt = (size-1)*t - int((size-1)*t);
00116 T p0 = mCatmullRomSpline[i0];
00117 T p1 = mCatmullRomSpline[i1];
00118 T p2 = mCatmullRomSpline[i2];
00119 T p3 = mCatmullRomSpline[i3];
00120 T p = ( (p1 * 2.0f) + (-p0 + p2) * tt +
00121 ( p0*2.0f - p1*5.0f + p2*4.0f - p3) * tt*tt +
00122 ( p0*-1 + p1*3.0f - p2*3.0f + p3) * tt*tt*tt ) * 0.5f;
00123 return p;
00124 }
00125 }
00126
00131 void setPath(const std::vector<T>& path) { mPath = path; }
00132
00134 const std::vector<T>& path() const { return mPath; }
00135
00137 std::vector<T>& path() { return mPath; }
00138
00139 protected:
00140 std::vector<T> mPath;
00141 std::vector<T> mCatmullRomSpline;
00142 };
00143
00144 typedef CatmullRomInterpolator<float> CatmullRomInterpolatorFloat_T;
00145 typedef CatmullRomInterpolator<fvec2> CatmullRomInterpolatorFVec2_T;
00146 typedef CatmullRomInterpolator<fvec3> CatmullRomInterpolatorFVec3_T;
00147 typedef CatmullRomInterpolator<fvec4> CatmullRomInterpolatorFVec4_T;
00148 typedef CatmullRomInterpolator<double> CatmullRomInterpolatorDouble_T;
00149 typedef CatmullRomInterpolator<dvec2> CatmullRomInterpolatorDVec2_T;
00150 typedef CatmullRomInterpolator<dvec3> CatmullRomInterpolatorDVec3_T;
00151 typedef CatmullRomInterpolator<dvec4> CatmullRomInterpolatorDVec4_T;
00152
00154 class CatmullRomInterpolatorFVec4: public InterpolatorFVec4
00155 {
00156 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorFVec4, InterpolatorFVec4)
00157 public:
00158 CatmullRomInterpolatorFVec4(): mInterpolator( new CatmullRomInterpolatorFVec4_T ) {}
00159 CatmullRomInterpolatorFVec4(const std::vector<fvec4>& path): mInterpolator( new CatmullRomInterpolatorFVec4_T(path) ) {}
00160 fvec4 computePoint(float t) const { return interpolator()->computePoint(t); }
00161 CatmullRomInterpolatorFVec4_T* interpolator() { return mInterpolator.get(); }
00162 const CatmullRomInterpolatorFVec4_T* interpolator() const { return mInterpolator.get(); }
00163 void setInterpolator(CatmullRomInterpolatorFVec4_T* interpolator) { mInterpolator = interpolator; }
00164 protected:
00165 ref<CatmullRomInterpolatorFVec4_T> mInterpolator;
00166 };
00168 class CatmullRomInterpolatorFVec3: public InterpolatorFVec3
00169 {
00170 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorFVec3, InterpolatorFVec3)
00171 public:
00172 CatmullRomInterpolatorFVec3(): mInterpolator( new CatmullRomInterpolatorFVec3_T ) {}
00173 CatmullRomInterpolatorFVec3(const std::vector<fvec3>& path): mInterpolator( new CatmullRomInterpolatorFVec3_T(path) ) {}
00174 fvec3 computePoint(float t) const { return interpolator()->computePoint(t); }
00175 CatmullRomInterpolatorFVec3_T* interpolator() { return mInterpolator.get(); }
00176 const CatmullRomInterpolatorFVec3_T* interpolator() const { return mInterpolator.get(); }
00177 void setInterpolator(CatmullRomInterpolatorFVec3_T* interpolator) { mInterpolator = interpolator; }
00178 protected:
00179 ref<CatmullRomInterpolatorFVec3_T> mInterpolator;
00180 };
00182 class CatmullRomInterpolatorFVec2: public InterpolatorFVec2
00183 {
00184 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorFVec2, InterpolatorFVec2)
00185 public:
00186 CatmullRomInterpolatorFVec2(): mInterpolator( new CatmullRomInterpolatorFVec2_T ) {}
00187 CatmullRomInterpolatorFVec2(const std::vector<fvec2>& path): mInterpolator( new CatmullRomInterpolatorFVec2_T(path) ) {}
00188 fvec2 computePoint(float t) const { return interpolator()->computePoint(t); }
00189 CatmullRomInterpolatorFVec2_T* interpolator() { return mInterpolator.get(); }
00190 const CatmullRomInterpolatorFVec2_T* interpolator() const { return mInterpolator.get(); }
00191 void setInterpolator(CatmullRomInterpolatorFVec2_T* interpolator) { mInterpolator = interpolator; }
00192 protected:
00193 ref<CatmullRomInterpolatorFVec2_T> mInterpolator;
00194 };
00196 class CatmullRomInterpolatorFloat: public InterpolatorFloat
00197 {
00198 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorFloat, InterpolatorFloat)
00199 public:
00200 CatmullRomInterpolatorFloat(): mInterpolator( new CatmullRomInterpolatorFloat_T ) {}
00201 CatmullRomInterpolatorFloat(const std::vector<float>& path): mInterpolator( new CatmullRomInterpolatorFloat_T(path) ) {}
00202 float computePoint(float t) const { return interpolator()->computePoint(t); }
00203 CatmullRomInterpolatorFloat_T* interpolator() { return mInterpolator.get(); }
00204 const CatmullRomInterpolatorFloat_T* interpolator() const { return mInterpolator.get(); }
00205 void setInterpolator(CatmullRomInterpolatorFloat_T* interpolator) { mInterpolator = interpolator; }
00206 protected:
00207 ref<CatmullRomInterpolatorFloat_T> mInterpolator;
00208 };
00210 class CatmullRomInterpolatorDVec4: public InterpolatorDVec4
00211 {
00212 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorDVec4, InterpolatorDVec4)
00213 public:
00214 CatmullRomInterpolatorDVec4(): mInterpolator( new CatmullRomInterpolatorDVec4_T ) {}
00215 CatmullRomInterpolatorDVec4(const std::vector<dvec4>& path): mInterpolator( new CatmullRomInterpolatorDVec4_T(path) ) {}
00216 dvec4 computePoint(float t) const { return interpolator()->computePoint(t); }
00217 CatmullRomInterpolatorDVec4_T* interpolator() { return mInterpolator.get(); }
00218 const CatmullRomInterpolatorDVec4_T* interpolator() const { return mInterpolator.get(); }
00219 void setInterpolator(CatmullRomInterpolatorDVec4_T* interpolator) { mInterpolator = interpolator; }
00220 protected:
00221 ref<CatmullRomInterpolatorDVec4_T> mInterpolator;
00222 };
00224 class CatmullRomInterpolatorDVec3: public InterpolatorDVec3
00225 {
00226 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorDVec3, InterpolatorDVec3)
00227 public:
00228 CatmullRomInterpolatorDVec3(): mInterpolator( new CatmullRomInterpolatorDVec3_T ) {}
00229 CatmullRomInterpolatorDVec3(const std::vector<dvec3>& path): mInterpolator( new CatmullRomInterpolatorDVec3_T(path) ) {}
00230 dvec3 computePoint(float t) const { return interpolator()->computePoint(t); }
00231 CatmullRomInterpolatorDVec3_T* interpolator() { return mInterpolator.get(); }
00232 const CatmullRomInterpolatorDVec3_T* interpolator() const { return mInterpolator.get(); }
00233 void setInterpolator(CatmullRomInterpolatorDVec3_T* interpolator) { mInterpolator = interpolator; }
00234 protected:
00235 ref<CatmullRomInterpolatorDVec3_T> mInterpolator;
00236 };
00238 class CatmullRomInterpolatorDVec2: public InterpolatorDVec2
00239 {
00240 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorDVec2, InterpolatorDVec2)
00241 public:
00242 CatmullRomInterpolatorDVec2(): mInterpolator( new CatmullRomInterpolatorDVec2_T ) {}
00243 CatmullRomInterpolatorDVec2(const std::vector<dvec2>& path): mInterpolator( new CatmullRomInterpolatorDVec2_T(path) ) {}
00244 dvec2 computePoint(float t) const { return interpolator()->computePoint(t); }
00245 CatmullRomInterpolatorDVec2_T* interpolator() { return mInterpolator.get(); }
00246 const CatmullRomInterpolatorDVec2_T* interpolator() const { return mInterpolator.get(); }
00247 void setInterpolator(CatmullRomInterpolatorDVec2_T* interpolator) { mInterpolator = interpolator; }
00248 protected:
00249 ref<CatmullRomInterpolatorDVec2_T> mInterpolator;
00250 };
00252 class CatmullRomInterpolatorDouble: public InterpolatorDouble
00253 {
00254 VL_INSTRUMENT_CLASS(vl::CatmullRomInterpolatorDouble, InterpolatorDouble)
00255 public:
00256 CatmullRomInterpolatorDouble(): mInterpolator( new CatmullRomInterpolatorDouble_T ) {}
00257 CatmullRomInterpolatorDouble(const std::vector<double>& path): mInterpolator( new CatmullRomInterpolatorDouble_T(path) ) {}
00258 double computePoint(float t) const { return interpolator()->computePoint(t); }
00259 CatmullRomInterpolatorDouble_T* interpolator() { return mInterpolator.get(); }
00260 const CatmullRomInterpolatorDouble_T* interpolator() const { return mInterpolator.get(); }
00261 void setInterpolator(CatmullRomInterpolatorDouble_T* interpolator) { mInterpolator = interpolator; }
00262 protected:
00263 ref<CatmullRomInterpolatorDouble_T> mInterpolator;
00264 };
00265 }
00266
00267 #endif