Main Page | Class Hierarchy | Compound List | All functions | Search

KeyFrameInterpolator Class Reference

A key frame interpolator. More...

List of all members.

Key Frames

void setFrame (Frame *fr)
Frameframe () const
void addKeyFrame (const Frame &fr)
void addKeyFrame (const Frame &fr, const float time)
void addKeyFrame (const Frame *fr)
void addKeyFrame (const Frame *fr, const float time)
void deletePath ()
int numberOfKeyFrames () const
Frame keyFrame (const int i) const
Vec keyFramePosition (const int i) const
Quaternion keyFrameOrientation (const int i) const
float keyFrameTime (const int i) const

Interpolation parameters

float interpolationTime () const
void setInterpolationTime (const float time)
float interpolationSpeed () const
void setInterpolationSpeed (const float speed)
int interpolationPeriod () const
void setInterpolationPeriod (const int msecs)
bool loopInterpolation () const
void setLoopInterpolation (const bool loop=true)
bool closedPath () const
void setClosedPath (const bool closed=true)

Interpolation

virtual void interpolateAtTime (const float time)
void startInterpolation (const int msecs=-1)
void stopInterpolation ()
void resetInterpolation ()
bool interpolationIsStarted () const
void toggleInterpolation ()

Path drawing

virtual void drawPath (const int mask=1, int nbFrames=6, const float scale=1.0f)
virtual void drawPathModifyGLState (const int mask, int nbFrames, const float scale)

XML representation

virtual QDomElement domElement (const QString &name, QDomDocument &doc) const
virtual void initFromDOMElement (const QDomElement &de)

Public Slots

virtual void update ()

Signals

void interpolated ()
void finished ()

Public Member Functions

 KeyFrameInterpolator (Frame *fr=NULL)
virtual ~KeyFrameInterpolator ()


Detailed Description

A key frame interpolator.

KeyFrameInterpolator implements a classical interpolation of key Frames, using a smooth Catmull-Rom interpolation. See the keyFrames example for an illustration of the class.

Use addKeyFrame() to define the keyframes and then call startInterpolation(). The frame() associated with the interpolator (using the constructor or with setFrame()) will then be updated over time. frame() should be a pointer to one of the Frame of your application, the one that you want the KeyFrameInterpolator to drive:

  // The KeyFrameInterpolator must be given the Frame that it will drive over time. 
  KeyFrameInterpolator kfi( new Frame() );

  init()
  {
    kfi.addKeyFrame( Frame( Vec(1,0,2), Quaternion() ) );
    kfi.addKeyFrame( new Frame( Vec(2,1,0), Quaternion() ) );
    // ...and so on for all the Key Frames.

    // Ask for a display update after each update of the KeyFrameInterpolator
    connect(&kfi, SIGNAL(interpolated()), SLOT(updateGL()));
    
    kfi.startInterpolation();
  }

  draw()
  {
    kfi.drawPath();
    glPushMatrix();
    // Recover kfi associated frame with kfi.frame(), and use its matrix 
    glMultMatrixd( kfi.frame()->matrix() );
      // Draw your object here. Its position and orientation will be interpolated.
    glPopMatrix();
  }

The interpolation can loop (setLoopInterpolation()) and the keyFrame path can be closed (setClosedPath()) (not yet implemented). The current interpolation time (interpolationTime()) and speed (interpolationSpeed()) can also be tuned.

The keyFrames are defined by a Frame and a time, expressed in seconds. If the keyFrame is defined using a pointer to a Frame, the keyFrame path will automatically be updated if the Frame is modified (see the Frame::modified() signal).

The time has to be monotonously increasing over keyFrames. When interpolationSpeed() equals 1.0, these times correspond to actual user' seconds during the interpolation (provided that your QGLViewer::draw() function is fast enough).

Note that a Camera has 12 attached KeyFrameInterpolator binded to the F1-F12 keys. Press Alt+Fx to define a new keyFrame for path x. Pressing Fx plays/pause path interpolation. See the shortcuts page for details.

When interpolated, the KeyFrameInterpolator emits an interpolated() signal, which should be connected to the viewer's updateGL() slot. See the interpolated() documentation for details.


Constructor & Destructor Documentation

KeyFrameInterpolator Frame fr = NULL  ) 
 

Creates a KeyFrameInterpolator, which will drive the fr frame. See setFrame() for details on the associated frame fr.

Use addKeyFrame() to define the key frames. Default interpolationTime() is 0.0, and interpolationSpeed() is 1.0.

See the keyFrames example for an illustration.

~KeyFrameInterpolator  )  [virtual]
 

Virtual destructor. Releases allocated memory.


Member Function Documentation

void addKeyFrame const Frame fr,
const float  time
 

Same as the reference version of addKeyFrame(), but with a pointer to a frame. NULL pointers are silently ignored.

void addKeyFrame const Frame fr  ) 
 

Same as the reference version of addKeyFrame(), but with a pointer to a frame. NULL pointers are silently ignored.

See the keyFrames example for an illustration.

void addKeyFrame const Frame fr,
const float  time
 

Defines a new keyFrame, and the associated time (in seconds) that will be used to rhythm the interpolation. The keyFrameTime() have to be monotonously increasing over keyFrames.

void addKeyFrame const Frame fr  ) 
 

Defines a new keyFrame. Same as addKeyFrame() with a keyFrameTime() specification, except that the time is automatically set as previous keyFrameTime() + 1 second.

See the keyFrames example for an illustration.

bool closedPath  )  const [inline]
 

Whether or not (default) the path defined by the keyFrames is a closed loop. When true, the last and the first KeyFrame are linked by a new spline segment.

:
Use setLoopInterpolation() to create a continuous animation over the entire path.
Attention:
The closed path feature is not yet implemented.

void deletePath  ) 
 

Remove all keyFrames from the path. The numberOfKeyFrames() is set to 0.

QDomElement domElement const QString &  name,
QDomDocument &  doc
const [virtual]
 

Creates an XML QDomElement that represents the KeyFrameInterpolator. name is the name of the QDomElement tag. You need to provide the QDomDocument doc that will hold the resulting element.

Use initFromDOMElement() to restore the KeyFrameInterpolator state from the resulting domElement.

See also Camera::domElement(), Frame::domElement()...

If you want to save the KeyFrameInterpolator kfi in a file, use

 QDomDocument doc( "myKFI" );
 doc.appendChild( kfi.domElement("KFI", doc) );
 ofstream file( "myKFI.xml" );
 file << doc.toString();
Note that the Camera::keyFrameInterpolator() are automatically saved by QGLViewer::saveToFile() when a QGLViewer is closed (default shortcut key is Escape).

Use the following code to retrieve the KeyFrameInterpolator kfi from the saved file:

 // Load DOM from file
 QDomDocument doc;
 QFile f("myKFI.xml");
 f.open(IO_ReadOnly);
 doc.setContent(&f);
 f.close();
 // Parse the DOM tree
 QDomElement main=doc.documentElement();
 kfi.initFromDOMElement(main);

Attention:
For KeyFrames defined by pointers, only the values of the pointed Frame are saved. See Frame::domElement().

Only the KeyFrames are saved, you still need to define the attached frame() with setFrame().

void drawPath const int  mask = 1,
int  nbFrames = 6,
const float  scale = 1.0f
[virtual]
 

Draws the path that will be used to interpolate the frame().

mask controls what is drawn on the path : if (mask & 1) (default), the position path is drawn. If (mask & 2), a camera representation is regularly drawn and if (mask & 4), an oriented axis is regularly drawn.

  drawPath();  // Simply draws the interpolation path
  drawPath(3); // Draws path and cameras
  drawPath(7); // Draws path, cameras and axis
  drawPath(5); // Draws path and axis

When camera or axis is drawn, nbFrames controls the number of objects (axis or camera) drawn between two successive keyFrames. When nbFrames=1, only the path Key Frames are drawn. nbFrames=2 also draws the intermediate orientation, etc. The maximum value is 30. nbFrames should divide 30 so that an object is drawn for each Key Frame. Default value is 6.

scale (default=1.0) controls the scaling of the camera and axis drawing. A value of QGLViewer::sceneRadius() should give good results.

The color of the path is the one of the current glColor().

See the keyFrames example for an illustration.

This function actually call drawPathModifyGLState(), but saves and restores the GL state before and after.

void drawPathModifyGLState const int  mask,
int  nbFrames,
const float  scale
[virtual]
 

Same as drawPath(), but the GL state is modified : GL_LIGHTING is disabled and line width set to 2. This function should only be used for efficiency reasons (as is done by QGLViewer::postDraw()). Prefer calling drawPath(), which preserves the GL state, for debugging purpose.

void finished  )  [signal]
 

This signal is emitted when the interpolation reaches the last keyFrameTime(). Use startInterpolation() to start the interpolation and you will be warned with this signal when the interpolation is finished.

Note:
A call to stopInterpolation() will not emit this signal. If loopInterpolation() is activated, the signal is emitted each time the interpolation loops back to first keyFrame.

If the interpolationSpeed() is negative, finished() is emitted when interpolationTime() reaches the first keyFrameTime().

Frame* frame  )  const [inline]
 

The frame that is associated and modified by the KeyFrameInterpolator. Set using setFrame() or with the KeyFrameInterpolator() constructor.

void initFromDOMElement const QDomElement &  de  )  [virtual]
 

Restore the KeyFrameInterpolator state from a QDomElement created by domElement(). See also Camera::initFromDOMElement(), Frame::initFromDOMElement().

Attention:
For KeyFrames defined by pointers, only the values of the pointed Frame are saved.

Only the KeyFrames are saved, you still need to define the attached frame() with setFrame().

void interpolateAtTime const float  time  )  [virtual]
 

Interpolate frame() for time time. interpolationTime() is set to time and frame() is set accordingly.

If you simply want to change interpolationTime() but not the frame(), use setInterpolationTime() instead.

Emits the interpolated() signal.

void interpolated  )  [signal]
 

This signal is emitted whenever the frame() state is interpolated. Connect this signal to any object that should be notified.

This signal should especially be connected to your viewer updateGL() slot, so that the display is updated after every update of the KeyFrameInterpolator frame(). Use code like this :

    connect(myKeyFrameInterpolator, SIGNAL(interpolated()), SLOT(updateGL()));

Note that every QGLViewer::camera() holds several KeyFrameInterpolator and that their interpolated() signals are automatically connected to the viewer's updateGL() slot.

When several viewers display the same scene, it may be interesting to update all the viewers when a KeyFrameInterpolator (and probably hence an object) is interpolated. Simply use this code to achieve this behavior:

    QGLViewer::connectSignalToAllViewers(myKeyFrameInterpolator, SIGNAL(interpolated()));

See also the ManipulatedFrame::manipulated() and spinningFrame::spinned() signals documentations.

bool interpolationIsStarted  )  const [inline]
 

Returns true when the interpolation is being processed (after a call to startInterpolation()). Set to false by stopInterpolation(). See also toggleInterpolation().

int interpolationPeriod  )  const [inline]
 

Returns the current interpolation period, expressed in milliseconds. This period will be added to the interpolationTime() at each update(), when interpolationIsStarted() is true.

float interpolationSpeed  )  const [inline]
 

Returns the current interpolation speed. Default value is 1.0, which means that the times associated with the keyFrames (see keyFrameTime() and addKeyFrame()), expressed in seconds, will be respected during the interpolation (see startInterpolation()), provided that your display is fast enough.

A negative value will result in a reverse interpolation of the keyFrames.

float interpolationTime  )  const [inline]
 

Current interpolation time, updated when interpolationIsStarted() is true. Can be set directly with setInterpolationTime() or interpolateAtTime().

Frame keyFrame const int  i  )  const
 

Quaternion keyFrameOrientation const int  i  )  const
 

Returns the keyFrame orientation of keyFrame number i. No index verification is performed. See also keyFramePosition(), keyFrameTime() and numberOfKeyFrames().

Vec keyFramePosition const int  i  )  const
 

Returns the keyFrame position of keyFrame number i. No index verification is performed. See also keyFrameOrientation(), keyFrameTime() and numberOfKeyFrames().

float keyFrameTime const int  i  )  const
 

Returns the time associated with the keyframe number i. See also keyFramePosition(), keyFrameOrientation() and addKeyFrame().

bool loopInterpolation  )  const [inline]
 

Whether or not (default) the interpolation will be played in (infinite) loop when startInterpolation() is called (until stopInterpolation() is called). When false, the interpolation will stop when interpolationTime() reaches the last keyFrames associated time (see keyFrameTime()).

Use setClosedPath() to create a closed path with the keyFrames.

int numberOfKeyFrames  )  const [inline]
 

Number of keyFrames used in the interpolation. Use addKeyFrame() to add new keyFrames.

void resetInterpolation  ) 
 

interpolationTime() is reset to the keyFrameTime() associated with the first keyFrame and interpolation is stopped (not much more than stopInterpolation() and setInterpolationTime()).

void setClosedPath const bool  closed = true  )  [inline]
 

Set the closedPath() value.

Attention:
The closed path feature is not yet implemented.

void setFrame Frame fr  )  [inline]
 

Set the frame that will be associated with the KeyFrameInterpolator. Current frame is in frame().

The Frame you associate with a KeyFrameInterpolator is usually one of your application Frame, that you would like to interpolate. You will then setFrame() to a pointer to your Frame.

void setInterpolationPeriod const int  msecs  )  [inline]
 

Set the interpolationPeriod().

void setInterpolationSpeed const float  speed  )  [inline]
 

Set the interpolation speed. Negative values are possible. See interpolationSpeed().

void setInterpolationTime const float  time  )  [inline]
 

Set the current interpolation time. See also interpolationTime().

Attention:
The frame() is not affected by this method. Use this function to define the starting time of a future interpolation (see startInterpolation()). Use interpolateAtTime() to actually interpolate at a given time.

void setLoopInterpolation const bool  loop = true  )  [inline]
 

Set the loopInterpolation() value.

void startInterpolation const int  msecs = -1  ) 
 

Starts the interpolation process. A timer will be started with a period defined by msecs. The timer calls update() to update the frame() position and orientation. Use stopInterpolation() to stop interpolation, and setInterpolationTime() to change the interpolationTime(). interpolationIsStarted() will be true until stopInterpolation() is called.

If interpolationTime() is greater than the last keyFrameTime(), it is reset to the first keyFrameTime() and interpolation starts from there (natural behavior).

If msecs is negative (default with no parameter), the current interpolationPeriod() will be used (default is 25Hz, see setInterpolationPeriod()), otherwise interpolationPeriod() will be set to msecs.

You may also be interested in QGLViewer::animate() and QGLViewer::startAnimation().

See the keyFrames example for an illustration.

Attention:
The keyFrames must be defined before you startInterpolation(), or else the interpolation will naturally immediately stop.

void stopInterpolation  ) 
 

Stops an interpolation started with startInterpolation().

void toggleInterpolation  )  [inline]
 

Calls startInterpolation() or stopInterpolation(), depending on interpolationIsStarted().

void update  )  [virtual, slot]
 

Interpolates frame() for the next interpolationTime() (defined by interpolationPeriod()). This internal function is called by a timer when startInterpolation() is called. It is publicly provided for your debugging purpose only. stopInterpolation() is called when interpolationTime() reaches the first or last keyFrameTime(), unless loopInterpolation() is true.


Generated on Wed Feb 11 17:22:07 2004 for libQGLViewer by doxygen 1.3.3