Exemple #1
0
float AnimClip::accumulateTime(float frame, float dt, Triggers& triggersOut) const {
    const float startFrame = std::min(_startFrame, _endFrame);
    if (startFrame == _endFrame) {
        // when startFrame >= endFrame
        frame = _endFrame;
    } else if (_timeScale > 0.0f) {
        // accumulate time, keeping track of loops and end of animation events.
        const float FRAMES_PER_SECOND = 30.0f;
        float framesRemaining = (dt * _timeScale) * FRAMES_PER_SECOND;
        while (framesRemaining > 0.0f) {
            float framesTillEnd = _endFrame - _frame;
            if (framesRemaining >= framesTillEnd) {
                if (_loopFlag) {
                    // anim loop
                    triggersOut.push_back(_id + "OnLoop");
                    framesRemaining -= framesTillEnd;
                    frame = startFrame;
                } else {
                    // anim end
                    triggersOut.push_back(_id + "OnDone");
                    frame = _endFrame;
                    framesRemaining = 0.0f;
                }
            } else {
                frame += framesRemaining;
                framesRemaining = 0.0f;
            }
        }
    }
    return frame;
}
void AnimBlendLinearMove::setFrameAndPhase(float dt, float alpha, int prevPoseIndex, int nextPoseIndex,
        float* prevDeltaTimeOut, float* nextDeltaTimeOut, Triggers& triggersOut) {

    const float FRAMES_PER_SECOND = 30.0f;
    auto prevClipNode = std::dynamic_pointer_cast<AnimClip>(_children[prevPoseIndex]);
    assert(prevClipNode);
    auto nextClipNode = std::dynamic_pointer_cast<AnimClip>(_children[nextPoseIndex]);
    assert(nextClipNode);

    float v0 = _characteristicSpeeds[prevPoseIndex];
    float n0 = (prevClipNode->getEndFrame() - prevClipNode->getStartFrame()) + 1.0f;
    float v1 = _characteristicSpeeds[nextPoseIndex];
    float n1 = (nextClipNode->getEndFrame() - nextClipNode->getStartFrame()) + 1.0f;

    // rate of change in phase space, necessary to achive desired speed.
    float omega = (_desiredSpeed * FRAMES_PER_SECOND) / ((1.0f - alpha) * v0 * n0 + alpha * v1 * n1);

    float f0 = prevClipNode->getStartFrame() + _phase * n0;
    prevClipNode->setCurrentFrame(f0);

    float f1 = nextClipNode->getStartFrame() + _phase * n1;
    nextClipNode->setCurrentFrame(f1);

    // integrate phase forward in time.
    _phase += omega * dt;

    // detect loop trigger events
    if (_phase >= 1.0f) {
        triggersOut.push_back(_id + "Loop");
        _phase = glm::fract(_phase);
    }

    *prevDeltaTimeOut = omega * dt * (n0 / FRAMES_PER_SECOND);
    *nextDeltaTimeOut = omega * dt * (n1 / FRAMES_PER_SECOND);
}