00001 /*
00002 File: Hermite.cc
00003
00004 Function:
00005
00006 Author: Andrew Willmott
00007
00008 Notes:
00009 */
00010
00011 #include "gcl/Hermite.h"
00012
00013
00014 /* This basis takes [x(0),x(1),x'(0),x'(1)] as knot points
00015 Each column holds the coefficients of one of the Hermite
00016 polynomials. */
00017
00018 static Transform gHermiteMatrix(
00019 1.0, 0.0, 0.0, 0.0,
00020 0.0, 0.0, 1.0, 0.0,
00021 -3.0, 3.0, -2.0, -1.0,
00022 2.0, -2.0, 1.0, 1.0
00023 );
00024
00025
00026 /*
00027 Calculate hermite coefficients.
00028
00029 t0, y0, ySlope0 are start time, value, and slope.
00030 t1, y1, ySlope1 are end time, value, and slope.
00031 t1 had better not equal t0.
00032
00033 For automatic slope control, set
00034 ySlope1 = (y2 - y0) / (t2 - t0);
00035 ySlope0 = (y1 - y-1) / (t1 - t-1);
00036 */
00037
00038 Void CalcHermiteCoeffs(
00039 GCLReal t0,
00040 GCLReal t1,
00041 GCLReal y0,
00042 GCLReal y1,
00043 GCLReal ySlope0,
00044 GCLReal ySlope1,
00045 Cubic &result
00046 )
00047 {
00048 result = gHermiteMatrix *
00049 Cubic(y0, y1, ySlope0 * (t1 - t0), ySlope1 * (t1 - t0));
00050 }
00051
00052 GCLReal EvalCubic(Cubic &cubicCoeffs, GCLReal t, GCLReal t0, GCLReal t1)
00053 // evaluate y(t), using coeffs computed by CalcHermiteCoeffs().
00054 // t0, t1 have to be same as you supplied to CalcHermiteCoeffs().
00055 // t should be between t0 and t1, inclusive.
00056 {
00057 GCLReal u = (t - t0) / (t1 - t0);
00058 Cubic uCubic(1, u, sqr(u), sqr(u) * u);
00059
00060 return(dot(uCubic, cubicCoeffs));
00061 }
00062
00063
00064 /*
00065 Here's a dumb sample program that interpolates values of y between
00066 frame 0 and frame 30:
00067 */
00068
00069 #ifdef HM_DEBUG
00070 #include <stdio.h>
00071
00072 main()
00073 {
00074 Cubic coeffs;
00075 GCLReal t0 = 0, t1 = 30;
00076 GCLReal y0 = 1, y1 = 3;
00077 GCLReal dy0 = .2, dy1 = 0;
00078 Int t;
00079
00080 CalcHermiteCoeffs(t0, t1, y0, y1, dy0, dy1, coeffs);
00081
00082 for(t = 0; t < 31; t++)
00083 printf("\ny(%d) = %f", t, EvalCubic(coeffs, t, t0, t1) );
00084 }
00085
00086 #endif