mirror of
https://github.com/HifiExperiments/overte.git
synced 2025-08-09 15:20:08 +02:00
Created ScriptableAvatar class
This commit is contained in:
parent
d4199e6092
commit
4b867de864
2 changed files with 129 additions and 0 deletions
87
assignment-client/src/avatars/ScriptableAvatar.cpp
Normal file
87
assignment-client/src/avatars/ScriptableAvatar.cpp
Normal file
|
@ -0,0 +1,87 @@
|
||||||
|
//
|
||||||
|
// ScriptableAvatar.cpp
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Created by Clement on 7/22/14.
|
||||||
|
// Copyright 2014 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#include <QThread>
|
||||||
|
|
||||||
|
#include "ScriptableAvatar.h"
|
||||||
|
|
||||||
|
ScriptableAvatar::ScriptableAvatar(ScriptEngine* scriptEngine) : _scriptEngine(scriptEngine), _animation(NULL) {
|
||||||
|
connect(_scriptEngine, SIGNAL(update(float)), this, SLOT(update(float)));
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptableAvatar::startAnimation(const QString& url, float fps, float priority,
|
||||||
|
bool loop, bool hold, float firstFrame, float lastFrame, const QStringList& maskedJoints) {
|
||||||
|
if (QThread::currentThread() != thread()) {
|
||||||
|
QMetaObject::invokeMethod(this, "startAnimation", Q_ARG(const QString&, url), Q_ARG(float, fps),
|
||||||
|
Q_ARG(float, priority), Q_ARG(bool, loop), Q_ARG(bool, hold), Q_ARG(float, firstFrame),
|
||||||
|
Q_ARG(float, lastFrame), Q_ARG(const QStringList&, maskedJoints));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
_animation = _scriptEngine->getAnimationCache()->getAnimation(url);
|
||||||
|
_animationDetails = AnimationDetails("", QUrl(url), fps, 0, loop, hold, false, firstFrame, lastFrame, true, firstFrame);
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptableAvatar::stopAnimation(const QString& url) {
|
||||||
|
if (QThread::currentThread() != thread()) {
|
||||||
|
QMetaObject::invokeMethod(this, "stopAnimation", Q_ARG(const QString&, url));
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
_animation.clear();
|
||||||
|
}
|
||||||
|
|
||||||
|
AnimationDetails ScriptableAvatar::getAnimationDetails(const QString& url) {
|
||||||
|
if (QThread::currentThread() != thread()) {
|
||||||
|
AnimationDetails result;
|
||||||
|
QMetaObject::invokeMethod(this, "getAnimationDetails", Qt::BlockingQueuedConnection,
|
||||||
|
Q_RETURN_ARG(AnimationDetails, result),
|
||||||
|
Q_ARG(const QString&, url));
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
return _animationDetails;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ScriptableAvatar::update(float deltatime) {
|
||||||
|
// Run animation
|
||||||
|
if (_animation != NULL && _animation->isValid() && _animation->getFrames().size() > 0) {
|
||||||
|
QStringList modelJoints = getJointNames();
|
||||||
|
QStringList animationJoints = _animation->getJointNames();
|
||||||
|
|
||||||
|
if (_jointData.size() != modelJoints.size()) {
|
||||||
|
_jointData.resize(modelJoints.size());
|
||||||
|
}
|
||||||
|
|
||||||
|
float frameIndex = _animationDetails.frameIndex + deltatime * _animationDetails.fps;
|
||||||
|
if (_animationDetails.loop || frameIndex < _animationDetails.lastFrame) {
|
||||||
|
while (frameIndex >= _animationDetails.lastFrame) {
|
||||||
|
frameIndex -= (_animationDetails.lastFrame - _animationDetails.firstFrame);
|
||||||
|
}
|
||||||
|
_animationDetails.frameIndex = frameIndex;
|
||||||
|
|
||||||
|
const int frameCount = _animation->getFrames().size();
|
||||||
|
const FBXAnimationFrame& floorFrame = _animation->getFrames().at((int)glm::floor(frameIndex) % frameCount);
|
||||||
|
const FBXAnimationFrame& ceilFrame = _animation->getFrames().at((int)glm::ceil(frameIndex) % frameCount);
|
||||||
|
const float frameFraction = glm::fract(frameIndex);
|
||||||
|
|
||||||
|
for (int i = 0; i < modelJoints.size(); i++) {
|
||||||
|
int mapping = animationJoints.indexOf(modelJoints[i]);
|
||||||
|
if (mapping != -1) {
|
||||||
|
JointData& data = _jointData[i];
|
||||||
|
data.valid = true;
|
||||||
|
data.rotation = safeMix(floorFrame.rotations.at(i), ceilFrame.rotations.at(i), frameFraction);
|
||||||
|
} else if (i < _jointData.size()) {
|
||||||
|
_jointData[i].valid = false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
_animation.clear();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
42
assignment-client/src/avatars/ScriptableAvatar.h
Normal file
42
assignment-client/src/avatars/ScriptableAvatar.h
Normal file
|
@ -0,0 +1,42 @@
|
||||||
|
//
|
||||||
|
// ScriptableAvatar.h
|
||||||
|
//
|
||||||
|
//
|
||||||
|
// Created by Clement on 7/22/14.
|
||||||
|
// Copyright 2014 High Fidelity, Inc.
|
||||||
|
//
|
||||||
|
// Distributed under the Apache License, Version 2.0.
|
||||||
|
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifndef hifi_ScriptableAvatar_h
|
||||||
|
#define hifi_ScriptableAvatar_h
|
||||||
|
|
||||||
|
#include <AnimationCache.h>
|
||||||
|
#include <AvatarData.h>
|
||||||
|
#include <ScriptEngine.h>
|
||||||
|
|
||||||
|
class ScriptableAvatar : public AvatarData {
|
||||||
|
Q_OBJECT
|
||||||
|
public:
|
||||||
|
ScriptableAvatar(ScriptEngine* scriptEngine);
|
||||||
|
|
||||||
|
/// Allows scripts to run animations.
|
||||||
|
Q_INVOKABLE void startAnimation(const QString& url, float fps = 30.0f, float priority = 1.0f, bool loop = false,
|
||||||
|
bool hold = false, float firstFrame = 0.0f, float lastFrame = FLT_MAX, const QStringList& maskedJoints = QStringList());
|
||||||
|
|
||||||
|
/// Stops an animation as identified by a URL.
|
||||||
|
Q_INVOKABLE void stopAnimation(const QString& url);
|
||||||
|
|
||||||
|
Q_INVOKABLE AnimationDetails getAnimationDetails(const QString& url);
|
||||||
|
|
||||||
|
private slots:
|
||||||
|
void update(float deltatime);
|
||||||
|
|
||||||
|
private:
|
||||||
|
ScriptEngine* _scriptEngine;
|
||||||
|
AnimationPointer _animation;
|
||||||
|
AnimationDetails _animationDetails;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // hifi_ScriptableAvatar_h
|
Loading…
Reference in a new issue