root/OpenSceneGraph/trunk/include/osgAnimation/Interpolator @ 11009

Revision 11009, 9.2 kB (checked in by robert, 5 years ago)

From Cedric Pinson, "Here a list of changes:
Bone now inherit from MatrixTransform?. It simplify a lot the update of
Bone matrix. It helps to have the bone system more generic. eg it's now
possible to have animation data with precomputed bind matrix. The other
benefit, is now the collada plugin will be able to use osgAnimation to
display skinned mesh. Michael Plating did a great work to improve this
aspect, he is working on the collada plugin and should be able to submit
a new version soon.
The RigGeometry? has been refactored so now it works when you save and
reload RigGeometry? because the source is not touched anymore. The
benefit with this update is that it should be now possible to use a
MorphGeometry? as source for a RigGeometry?.

The bad news is that the format has changed, so i have rebuild osg-data
related to osgAnimation data, updated the blender exporter to export to
the new format.
The fbx plugin could be touched about this commit, i dont compile it so
i can't give more information about it.
The bvh plugin has been updated by Wang rui so this one is fixed with
the new code of osgAnimation.
The examples has been updated to work with the new code too...

The example osg-data/example.osg should be remove, it's an old example
that does not work.

For people using blender the blender exporter up to date is here:
http://hg.plopbyte.net/osgexport2/
it will be merge to http://hg.plopbyte.net/osgexport/ as soon as the
modification will be push in the trunk.
"

RevLine 
[9093]1/*  -*-c++-*-
[10527]2 *  Copyright (C) 2008 Cedric Pinson <cedric.pinson@plopbyte.net>
[9093]3 *
4 * This library is open source and may be redistributed and/or modified under 
5 * the terms of the OpenSceneGraph Public License (OSGPL) version 0.0 or
6 * (at your option) any later version.  The full license is in LICENSE file
7 * included with this distribution, and on the openscenegraph.org website.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12 * OpenSceneGraph Public License for more details.
[10527]13 *
14 * Authors:
15 *         Cedric Pinson <cedric.pinson@plopbyte.net>
16 *         Michael Platings <mplatings@pixelpower.com>
17 */
[9093]18
[10877]19#ifndef OSGANIMATION_INTERPOLATOR
20#define OSGANIMATION_INTERPOLATOR 1
[9093]21
[9531]22#include <osg/Notify>
[9093]23#include <osgAnimation/Keyframe>
24
25namespace osgAnimation
26{
27
28    template <class TYPE, class KEY>
29    class TemplateInterpolatorBase
30    {
31    public:
32        typedef KEY KeyframeType;
33        typedef TYPE UsingType;
34
35    public:
36        mutable int _lastKeyAccess;
37
38        TemplateInterpolatorBase() : _lastKeyAccess(-1) {}
39
40        void reset() { _lastKeyAccess = -1; }
41        int getKeyIndexFromTime(const TemplateKeyframeContainer<KEY>& keys, float time) const
42        {
43            // todo use a cache
44            int key_size = keys.size();
[9531]45            if (!key_size) {
46                osg::notify(osg::WARN) << "TemplateInterpolatorBase::getKeyIndexFromTime the container is empty, impossible to get key index from time" << std::endl;;
47                return -1;
48            }
[9093]49            const TemplateKeyframe<KeyframeType>* keysVector = &keys.front();
[9531]50            for (int i = 0; i < key_size-1; i++)
[9093]51            {
52                float time0 = keysVector[i].getTime();
53                float time1 = keysVector[i+1].getTime();
[9456]54
[9093]55                if ( time >= time0 && time < time1 )
56                {
57                    _lastKeyAccess = i;
58                    return i;
59                }
60            }
[9531]61            osg::notify(osg::WARN) << time << " first key " << keysVector[0].getTime() << " last key " << keysVector[key_size-1].getTime() << std::endl;
[9093]62            return -1;
63        }
64    };
65
66
67    template <class TYPE, class KEY=TYPE>
[10527]68    class TemplateStepInterpolator : public TemplateInterpolatorBase<TYPE,KEY>
69    {
70    public:
71
72        TemplateStepInterpolator() {}
73        void getValue(const TemplateKeyframeContainer<KEY>& keyframes, float time, TYPE& result) const
74        {
75     
76            if (time >= keyframes.back().getTime())
77            {
78                result = keyframes.back().getValue();
79                return;
80            }
81            else if (time <= keyframes.front().getTime())
82            {
83                result = keyframes.front().getValue();
84                return;
85            }
86
87            int i = getKeyIndexFromTime(keyframes,time);
[10552]88            result = keyframes[i].getValue();
[10527]89        }
90    };
91
92
93    template <class TYPE, class KEY=TYPE>
[9093]94    class TemplateLinearInterpolator : public TemplateInterpolatorBase<TYPE,KEY>
95    {
96    public:
97
98        TemplateLinearInterpolator() {}
99        void getValue(const TemplateKeyframeContainer<KEY>& keyframes, float time, TYPE& result) const
100        {
101     
102            if (time >= keyframes.back().getTime())
103            {
104                result = keyframes.back().getValue();
105                return;
106            }
107            else if (time <= keyframes.front().getTime())
108            {
109                result = keyframes.front().getValue();
110                return;
111            }
112       
113            int i = getKeyIndexFromTime(keyframes,time);
114            float blend = (time - keyframes[i].getTime()) / ( keyframes[i+1].getTime() -  keyframes[i].getTime());
115            const TYPE& v1 =  keyframes[i].getValue();
116            const TYPE& v2 =  keyframes[i+1].getValue();
117            result = v1*(1-blend) + v2*blend;
118        }
119    };
120
121
122    template <class TYPE, class KEY=TYPE>
123    class TemplateSphericalLinearInterpolator : public TemplateInterpolatorBase<TYPE,KEY>
124    {
125    public:
126        TemplateSphericalLinearInterpolator() {}
127        void getValue(const TemplateKeyframeContainer<KEY>& keyframes, float time, TYPE& result) const
128        {
129            if (time >= keyframes.back().getTime())
130            {
131                result = keyframes.back().getValue();
132                return;
133            }
134            else if (time <= keyframes.front().getTime())
135            {
136                result = keyframes.front().getValue();
137                return;
138            }
139
140            int i = getKeyIndexFromTime(keyframes,time);
141            float blend = (time -  keyframes[i].getTime()) / ( keyframes[i+1].getTime() -  keyframes[i].getTime());
142            const TYPE& q1 =  keyframes[i].getValue();
143            const TYPE& q2 =  keyframes[i+1].getValue();
144            result.slerp(blend,q1,q2);
145        }
146    };
147
148
149    template <class TYPE, class KEY>
150    class TemplateLinearPackedInterpolator : public TemplateInterpolatorBase<TYPE,KEY>
151    {
152    public:
153
154        TemplateLinearPackedInterpolator() {}
155        void getValue(const TemplateKeyframeContainer<KEY>& keyframes, float time, TYPE& result) const
156        {
157            if (time >= keyframes.back().getTime())
158            {
159                keyframes.back().getValue().uncompress(keyframes.mScale, keyframes.mMin, result);
160                return;
161            }
162            else if (time <= keyframes.front().getTime())
163            {
164                keyframes.front().getValue().uncompress(keyframes.mScale, keyframes.mMin, result);
165                return;
166            }
167
168            int i = getKeyIndexFromTime(keyframes,time);
169            float blend = (time - keyframes[i].getTime()) / ( keyframes[i+1].getTime() -  keyframes[i].getTime());
170            TYPE v1,v2;
171            keyframes[i].getValue().uncompress(keyframes.mScale, keyframes.mMin, v1);
172            keyframes[i+1].getValue().uncompress(keyframes.mScale, keyframes.mMin, v2);
173            result = v1*(1-blend) + v2*blend;
174        }
175    };
176
177
178    // http://en.wikipedia.org/wiki/B%C3%A9zier_curve
179    template <class TYPE, class KEY=TYPE>
180    class TemplateCubicBezierInterpolator : public TemplateInterpolatorBase<TYPE,KEY>
181    {
182    public:
183
184        TemplateCubicBezierInterpolator() {}
185        void getValue(const TemplateKeyframeContainer<KEY>& keyframes, float time, TYPE& result) const
186        {
187     
188            if (time >= keyframes.back().getTime())
189            {
190                result = keyframes.back().getValue().getPosition();
191                return;
192            }
193            else if (time <= keyframes.front().getTime())
194            {
195                result = keyframes.front().getValue().getPosition();
196                return;
197            }
198
199            int i = getKeyIndexFromTime(keyframes,time);
200     
201            float t = (time - keyframes[i].getTime()) / ( keyframes[i+1].getTime() -  keyframes[i].getTime());
202            float one_minus_t = 1.0-t;
203            float one_minus_t2 = one_minus_t * one_minus_t;
204            float one_minus_t3 = one_minus_t2 * one_minus_t;
205            float t2 = t * t;
206
207            TYPE v0 = keyframes[i].getValue().getPosition() * one_minus_t3;
[11009]208            TYPE v1 = keyframes[i].getValue().getControlPointIn() * (3.0 * t * one_minus_t2);
209            TYPE v2 = keyframes[i].getValue().getControlPointOut() * (3.0 * t2 * one_minus_t);
[9093]210            TYPE v3 = keyframes[i+1].getValue().getPosition() * (t2 * t);
211
212            result = v0 + v1 + v2 + v3;
213        }
214    };
215
[10527]216    typedef TemplateStepInterpolator<double, double> DoubleStepInterpolator;
217    typedef TemplateStepInterpolator<float, float> FloatStepInterpolator;
218    typedef TemplateStepInterpolator<osg::Vec2, osg::Vec2> Vec2StepInterpolator;
219    typedef TemplateStepInterpolator<osg::Vec3, osg::Vec3> Vec3StepInterpolator;
220    typedef TemplateStepInterpolator<osg::Vec3, Vec3Packed> Vec3PackedStepInterpolator;
221    typedef TemplateStepInterpolator<osg::Vec4, osg::Vec4> Vec4StepInterpolator;
222    typedef TemplateStepInterpolator<osg::Quat, osg::Quat> QuatStepInterpolator;
223
[9093]224    typedef TemplateLinearInterpolator<double, double> DoubleLinearInterpolator;
225    typedef TemplateLinearInterpolator<float, float> FloatLinearInterpolator;
226    typedef TemplateLinearInterpolator<osg::Vec2, osg::Vec2> Vec2LinearInterpolator;
227    typedef TemplateLinearInterpolator<osg::Vec3, osg::Vec3> Vec3LinearInterpolator;
228    typedef TemplateLinearInterpolator<osg::Vec3, Vec3Packed> Vec3PackedLinearInterpolator;
229    typedef TemplateLinearInterpolator<osg::Vec4, osg::Vec4> Vec4LinearInterpolator;
230    typedef TemplateSphericalLinearInterpolator<osg::Quat, osg::Quat> QuatSphericalLinearInterpolator;
[11009]231    typedef TemplateLinearInterpolator<osg::Matrixf, osg::Matrixf> MatrixLinearInterpolator;
[9093]232
233    typedef TemplateCubicBezierInterpolator<float, FloatCubicBezier > FloatCubicBezierInterpolator;
234    typedef TemplateCubicBezierInterpolator<double, DoubleCubicBezier> DoubleCubicBezierInterpolator;
235    typedef TemplateCubicBezierInterpolator<osg::Vec2, Vec2CubicBezier> Vec2CubicBezierInterpolator;
236    typedef TemplateCubicBezierInterpolator<osg::Vec3, Vec3CubicBezier> Vec3CubicBezierInterpolator;
237    typedef TemplateCubicBezierInterpolator<osg::Vec4, Vec4CubicBezier> Vec4CubicBezierInterpolator;
238
239}
240#endif
Note: See TracBrowser for help on using the browser.