mirror of
https://github.com/JulianGro/overte.git
synced 2025-08-07 08:54:58 +02:00
move AnimationHandle from render-utils to animation. give Rig some jointstates and animation lists
This commit is contained in:
parent
75a35f9fcf
commit
bcd6b30ec3
14 changed files with 220 additions and 99 deletions
|
@ -28,7 +28,7 @@ enum CameraMode
|
|||
};
|
||||
|
||||
Q_DECLARE_METATYPE(CameraMode);
|
||||
static int cameraModeId = qRegisterMetaType<CameraMode>();
|
||||
// static int cameraModeId = qRegisterMetaType<CameraMode>();
|
||||
|
||||
class Camera : public QObject {
|
||||
Q_OBJECT
|
||||
|
|
|
@ -49,7 +49,6 @@ void FaceModel::simulate(float deltaTime, bool fullUpdate) {
|
|||
}
|
||||
|
||||
void FaceModel::maybeUpdateNeckRotation(const JointState& parentState, const FBXJoint& joint, JointState& state) {
|
||||
Avatar* owningAvatar = static_cast<Avatar*>(_owningHead->_owningAvatar);
|
||||
// get the rotation axes in joint space and use them to adjust the rotation
|
||||
glm::mat3 axes = glm::mat3_cast(glm::quat());
|
||||
glm::mat3 inverse = glm::mat3(glm::inverse(parentState.getTransform() *
|
||||
|
|
|
@ -488,7 +488,7 @@ void MyAvatar::loadLastRecording() {
|
|||
}
|
||||
|
||||
AnimationHandlePointer MyAvatar::addAnimationHandle() {
|
||||
AnimationHandlePointer handle = _skeletonModel.createAnimationHandle();
|
||||
AnimationHandlePointer handle = _rig.createAnimationHandle();
|
||||
_animationHandles.append(handle);
|
||||
return handle;
|
||||
}
|
||||
|
@ -506,7 +506,7 @@ void MyAvatar::startAnimation(const QString& url, float fps, float priority,
|
|||
Q_ARG(float, lastFrame), Q_ARG(const QStringList&, maskedJoints));
|
||||
return;
|
||||
}
|
||||
AnimationHandlePointer handle = _skeletonModel.createAnimationHandle();
|
||||
AnimationHandlePointer handle = _rig.createAnimationHandle();
|
||||
handle->setURL(url);
|
||||
handle->setFPS(fps);
|
||||
handle->setPriority(priority);
|
||||
|
@ -534,7 +534,7 @@ void MyAvatar::startAnimationByRole(const QString& role, const QString& url, flo
|
|||
}
|
||||
}
|
||||
// no joy; use the parameters provided
|
||||
AnimationHandlePointer handle = _skeletonModel.createAnimationHandle();
|
||||
AnimationHandlePointer handle = _rig.createAnimationHandle();
|
||||
handle->setRole(role);
|
||||
handle->setURL(url);
|
||||
handle->setFPS(fps);
|
||||
|
|
|
@ -156,7 +156,7 @@ AnimationPanel::AnimationPanel(AnimationsDialog* dialog, const AnimationHandlePo
|
|||
buttons->addWidget(remove);
|
||||
connect(remove, SIGNAL(clicked(bool)), SLOT(removeHandle()));
|
||||
|
||||
_stop->connect(_handle.data(), SIGNAL(runningChanged(bool)), SLOT(setEnabled(bool)));
|
||||
_stop->connect(_handle.get(), SIGNAL(runningChanged(bool)), SLOT(setEnabled(bool)));
|
||||
_stop->setEnabled(_handle->isRunning());
|
||||
}
|
||||
|
||||
|
|
|
@ -35,7 +35,6 @@ void Cube3DOverlay::render(RenderArgs* args) {
|
|||
|
||||
// TODO: handle registration point??
|
||||
glm::vec3 position = getPosition();
|
||||
glm::vec3 center = getCenter();
|
||||
glm::vec3 dimensions = getDimensions();
|
||||
glm::quat rotation = getRotation();
|
||||
|
||||
|
|
|
@ -30,7 +30,7 @@ void LocalModelsOverlay::update(float deltatime) {
|
|||
|
||||
void LocalModelsOverlay::render(RenderArgs* args) {
|
||||
if (_visible) {
|
||||
float glowLevel = getGlowLevel(); // FIXME, glowing removed for now
|
||||
// float glowLevel = getGlowLevel(); // FIXME, glowing removed for now
|
||||
|
||||
auto batch = args ->_batch;
|
||||
Application* app = Application::getInstance();
|
||||
|
|
|
@ -10,7 +10,7 @@
|
|||
//
|
||||
|
||||
#include "AnimationHandle.h"
|
||||
#include "Model.h"
|
||||
|
||||
|
||||
void AnimationHandle::setURL(const QUrl& url) {
|
||||
if (_url != url) {
|
||||
|
@ -20,28 +20,17 @@ void AnimationHandle::setURL(const QUrl& url) {
|
|||
}
|
||||
}
|
||||
|
||||
static void insertSorted(QList<AnimationHandlePointer>& handles, const AnimationHandlePointer& handle) {
|
||||
for (QList<AnimationHandlePointer>::iterator it = handles.begin(); it != handles.end(); it++) {
|
||||
if (handle->getPriority() > (*it)->getPriority()) {
|
||||
handles.insert(it, handle);
|
||||
return;
|
||||
}
|
||||
}
|
||||
handles.append(handle);
|
||||
}
|
||||
|
||||
void AnimationHandle::setPriority(float priority) {
|
||||
if (_priority == priority) {
|
||||
return;
|
||||
}
|
||||
if (isRunning()) {
|
||||
_model->_runningAnimations.removeOne(_self);
|
||||
_rig->removeRunningAnimation(getAnimationHandlePointer());
|
||||
if (priority < _priority) {
|
||||
replaceMatchingPriorities(priority);
|
||||
}
|
||||
_priority = priority;
|
||||
insertSorted(_model->_runningAnimations, _self);
|
||||
|
||||
_rig->addRunningAnimation(getAnimationHandlePointer());
|
||||
} else {
|
||||
_priority = priority;
|
||||
}
|
||||
|
@ -68,21 +57,21 @@ void AnimationHandle::setRunning(bool running) {
|
|||
}
|
||||
_animationLoop.setRunning(running);
|
||||
if (isRunning()) {
|
||||
if (!_model->_runningAnimations.contains(_self)) {
|
||||
insertSorted(_model->_runningAnimations, _self);
|
||||
if (!_rig->isRunningAnimation(getAnimationHandlePointer())) {
|
||||
_rig->addRunningAnimation(getAnimationHandlePointer());
|
||||
}
|
||||
} else {
|
||||
_model->_runningAnimations.removeOne(_self);
|
||||
_rig->removeRunningAnimation(getAnimationHandlePointer());
|
||||
restoreJoints();
|
||||
replaceMatchingPriorities(0.0f);
|
||||
}
|
||||
emit runningChanged(isRunning());
|
||||
}
|
||||
|
||||
AnimationHandle::AnimationHandle(Model* model) :
|
||||
QObject(model),
|
||||
_model(model),
|
||||
_priority(1.0f)
|
||||
AnimationHandle::AnimationHandle(RigPointer rig) :
|
||||
QObject(rig.get()),
|
||||
_rig(rig),
|
||||
_priority(1.0f)
|
||||
{
|
||||
}
|
||||
|
||||
|
@ -110,42 +99,52 @@ void AnimationHandle::setAnimationDetails(const AnimationDetails& details) {
|
|||
}
|
||||
|
||||
|
||||
void AnimationHandle::setJointMappings(QVector<int> jointMappings) {
|
||||
_jointMappings = jointMappings;
|
||||
}
|
||||
|
||||
|
||||
void AnimationHandle::simulate(float deltaTime) {
|
||||
if (!_animation || !_animation->isLoaded()) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
_animationLoop.simulate(deltaTime);
|
||||
|
||||
// update the joint mappings if necessary/possible
|
||||
|
||||
if (_jointMappings.isEmpty()) {
|
||||
if (_model && _model->isActive()) {
|
||||
_jointMappings = _model->getGeometry()->getJointMappings(_animation);
|
||||
}
|
||||
if (_jointMappings.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
if (!_maskedJoints.isEmpty()) {
|
||||
const FBXGeometry& geometry = _model->getGeometry()->getFBXGeometry();
|
||||
for (int i = 0; i < _jointMappings.size(); i++) {
|
||||
int& mapping = _jointMappings[i];
|
||||
if (mapping != -1 && _maskedJoints.contains(geometry.joints.at(mapping).name)) {
|
||||
mapping = -1;
|
||||
}
|
||||
}
|
||||
}
|
||||
qDebug() << "AnimationHandle::simulate -- _jointMappings.isEmpty()";
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
// // update the joint mappings if necessary/possible
|
||||
// if (_jointMappings.isEmpty()) {
|
||||
// if (_model && _model->isActive()) {
|
||||
// _jointMappings = _model->getGeometry()->getJointMappings(_animation);
|
||||
// }
|
||||
// if (_jointMappings.isEmpty()) {
|
||||
// return;
|
||||
// }
|
||||
// if (!_maskedJoints.isEmpty()) {
|
||||
// const FBXGeometry& geometry = _model->getGeometry()->getFBXGeometry();
|
||||
// for (int i = 0; i < _jointMappings.size(); i++) {
|
||||
// int& mapping = _jointMappings[i];
|
||||
// if (mapping != -1 && _maskedJoints.contains(geometry.joints.at(mapping).name)) {
|
||||
// mapping = -1;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
const FBXGeometry& animationGeometry = _animation->getGeometry();
|
||||
if (animationGeometry.animationFrames.isEmpty()) {
|
||||
stop();
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
if (_animationLoop.getMaxFrameIndexHint() != animationGeometry.animationFrames.size()) {
|
||||
_animationLoop.setMaxFrameIndexHint(animationGeometry.animationFrames.size());
|
||||
}
|
||||
|
||||
|
||||
// blend between the closest two frames
|
||||
applyFrame(getFrameIndex());
|
||||
}
|
||||
|
@ -154,17 +153,21 @@ void AnimationHandle::applyFrame(float frameIndex) {
|
|||
if (!_animation || !_animation->isLoaded()) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
const FBXGeometry& animationGeometry = _animation->getGeometry();
|
||||
int frameCount = animationGeometry.animationFrames.size();
|
||||
const FBXAnimationFrame& floorFrame = animationGeometry.animationFrames.at((int)glm::floor(frameIndex) % frameCount);
|
||||
const FBXAnimationFrame& ceilFrame = animationGeometry.animationFrames.at((int)glm::ceil(frameIndex) % frameCount);
|
||||
float frameFraction = glm::fract(frameIndex);
|
||||
QVector<JointState> jointStates = _rig->getJointStates();
|
||||
for (int i = 0; i < _jointMappings.size(); i++) {
|
||||
int mapping = _jointMappings.at(i);
|
||||
if (mapping != -1) {
|
||||
JointState& state = _model->_jointStates[mapping];
|
||||
state.setRotationInConstrainedFrame(safeMix(floorFrame.rotations.at(i), ceilFrame.rotations.at(i), frameFraction), _priority);
|
||||
JointState& state = jointStates[mapping];
|
||||
state.setRotationInConstrainedFrame(safeMix(floorFrame.rotations.at(i),
|
||||
ceilFrame.rotations.at(i),
|
||||
frameFraction),
|
||||
_priority);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -173,7 +176,8 @@ void AnimationHandle::replaceMatchingPriorities(float newPriority) {
|
|||
for (int i = 0; i < _jointMappings.size(); i++) {
|
||||
int mapping = _jointMappings.at(i);
|
||||
if (mapping != -1) {
|
||||
JointState& state = _model->_jointStates[mapping];
|
||||
QVector<JointState> jointStates = _rig->getJointStates();
|
||||
JointState& state = jointStates[mapping];
|
||||
if (_priority == state._animationPriority) {
|
||||
state._animationPriority = newPriority;
|
||||
}
|
||||
|
@ -185,9 +189,9 @@ void AnimationHandle::restoreJoints() {
|
|||
for (int i = 0; i < _jointMappings.size(); i++) {
|
||||
int mapping = _jointMappings.at(i);
|
||||
if (mapping != -1) {
|
||||
JointState& state = _model->_jointStates[mapping];
|
||||
QVector<JointState> jointStates = _rig->getJointStates();
|
||||
JointState& state = jointStates[mapping];
|
||||
state.restoreRotation(1.0f, state._animationPriority);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -18,22 +18,43 @@
|
|||
#include <QUrl>
|
||||
#include <QVector>
|
||||
|
||||
#include <AnimationCache.h>
|
||||
#include <AnimationLoop.h>
|
||||
#include "AnimationCache.h"
|
||||
#include "AnimationLoop.h"
|
||||
#include "Rig.h"
|
||||
|
||||
class AnimationHandle;
|
||||
class Model;
|
||||
|
||||
typedef QSharedPointer<AnimationHandle> AnimationHandlePointer;
|
||||
typedef QWeakPointer<AnimationHandle> WeakAnimationHandlePointer;
|
||||
typedef std::shared_ptr<AnimationHandle> AnimationHandlePointer;
|
||||
typedef std::weak_ptr<AnimationHandle> WeakAnimationHandlePointer;
|
||||
inline uint qHash(const std::shared_ptr<AnimationHandle>& a, uint seed) {
|
||||
// return qHash(a.get(), seed);
|
||||
AnimationHandle* strongRef = a ? a.get() : nullptr;
|
||||
return qHash(strongRef, seed);
|
||||
}
|
||||
inline uint qHash(const std::weak_ptr<AnimationHandle>& a, uint seed) {
|
||||
AnimationHandlePointer strongPointer = a.lock();
|
||||
AnimationHandle* strongRef = strongPointer ? strongPointer.get() : nullptr;
|
||||
return qHash(strongRef, seed);
|
||||
}
|
||||
|
||||
|
||||
// inline uint qHash(const WeakAnimationHandlePointer& handle, uint seed) {
|
||||
// return qHash(handle.data(), seed);
|
||||
// }
|
||||
|
||||
|
||||
|
||||
/// Represents a handle to a model animation.
|
||||
class AnimationHandle : public QObject {
|
||||
class AnimationHandle : public QObject, public std::enable_shared_from_this<AnimationHandle> {
|
||||
Q_OBJECT
|
||||
|
||||
|
||||
public:
|
||||
|
||||
AnimationHandle(RigPointer rig);
|
||||
|
||||
AnimationHandlePointer getAnimationHandlePointer() { return shared_from_this(); }
|
||||
|
||||
void setRole(const QString& role) { _role = role; }
|
||||
const QString& getRole() const { return _role; }
|
||||
|
||||
|
@ -45,26 +66,26 @@ public:
|
|||
|
||||
void setMaskedJoints(const QStringList& maskedJoints);
|
||||
const QStringList& getMaskedJoints() const { return _maskedJoints; }
|
||||
|
||||
|
||||
|
||||
void setFPS(float fps) { _animationLoop.setFPS(fps); }
|
||||
float getFPS() const { return _animationLoop.getFPS(); }
|
||||
|
||||
void setLoop(bool loop) { _animationLoop.setLoop(loop); }
|
||||
bool getLoop() const { return _animationLoop.getLoop(); }
|
||||
|
||||
|
||||
void setHold(bool hold) { _animationLoop.setHold(hold); }
|
||||
bool getHold() const { return _animationLoop.getHold(); }
|
||||
|
||||
|
||||
void setStartAutomatically(bool startAutomatically);
|
||||
bool getStartAutomatically() const { return _animationLoop.getStartAutomatically(); }
|
||||
|
||||
|
||||
void setFirstFrame(float firstFrame) { _animationLoop.setFirstFrame(firstFrame); }
|
||||
float getFirstFrame() const { return _animationLoop.getFirstFrame(); }
|
||||
|
||||
|
||||
void setLastFrame(float lastFrame) { _animationLoop.setLastFrame(lastFrame); }
|
||||
float getLastFrame() const { return _animationLoop.getLastFrame(); }
|
||||
|
||||
|
||||
void setRunning(bool running);
|
||||
bool isRunning() const { return _animationLoop.isRunning(); }
|
||||
|
||||
|
@ -74,30 +95,25 @@ public:
|
|||
AnimationDetails getAnimationDetails() const;
|
||||
void setAnimationDetails(const AnimationDetails& details);
|
||||
|
||||
void setJointMappings(QVector<int> jointMappings);
|
||||
void simulate(float deltaTime);
|
||||
void applyFrame(float frameIndex);
|
||||
void replaceMatchingPriorities(float newPriority);
|
||||
void restoreJoints();
|
||||
void clearJoints() { _jointMappings.clear(); }
|
||||
|
||||
signals:
|
||||
|
||||
|
||||
void runningChanged(bool running);
|
||||
|
||||
public slots:
|
||||
|
||||
void start() { setRunning(true); }
|
||||
void stop() { setRunning(false); }
|
||||
|
||||
|
||||
private:
|
||||
|
||||
friend class Model;
|
||||
|
||||
AnimationHandle(Model* model);
|
||||
|
||||
void simulate(float deltaTime);
|
||||
void applyFrame(float frameIndex);
|
||||
void replaceMatchingPriorities(float newPriority);
|
||||
void restoreJoints();
|
||||
|
||||
void clearJoints() { _jointMappings.clear(); }
|
||||
|
||||
Model* _model;
|
||||
WeakAnimationHandlePointer _self;
|
||||
RigPointer _rig;
|
||||
AnimationPointer _animation;
|
||||
QString _role;
|
||||
QUrl _url;
|
||||
|
@ -105,8 +121,11 @@ private:
|
|||
|
||||
QStringList _maskedJoints;
|
||||
QVector<int> _jointMappings;
|
||||
|
||||
|
||||
AnimationLoop _animationLoop;
|
||||
|
||||
static QHash<QWeakPointer<Animation>, QVector<int>> _jointMappingsCache;
|
||||
static QVector<int> getJointMappings(const AnimationPointer& animation);
|
||||
};
|
||||
|
||||
|
|
@ -9,4 +9,85 @@
|
|||
// See the accompanying file LICENSE or http://www.apache.org/licenses/LICENSE-2.0.html
|
||||
//
|
||||
|
||||
#include "AnimationHandle.h"
|
||||
|
||||
#include "Rig.h"
|
||||
|
||||
bool Rig::removeRunningAnimation(AnimationHandlePointer animationHandle) {
|
||||
return _runningAnimations.removeOne(animationHandle);
|
||||
}
|
||||
|
||||
static void insertSorted(QList<AnimationHandlePointer>& handles, const AnimationHandlePointer& handle) {
|
||||
for (QList<AnimationHandlePointer>::iterator it = handles.begin(); it != handles.end(); it++) {
|
||||
if (handle->getPriority() > (*it)->getPriority()) {
|
||||
handles.insert(it, handle);
|
||||
return;
|
||||
}
|
||||
}
|
||||
handles.append(handle);
|
||||
}
|
||||
|
||||
void Rig::addRunningAnimation(AnimationHandlePointer animationHandle) {
|
||||
insertSorted(_runningAnimations, animationHandle);
|
||||
}
|
||||
|
||||
bool Rig::isRunningAnimation(AnimationHandlePointer animationHandle) {
|
||||
return _runningAnimations.contains(animationHandle);
|
||||
}
|
||||
|
||||
void Rig::initJointStates(glm::vec3 scale, glm::vec3 offset, QVector<JointState> states) {
|
||||
_jointStates = states;
|
||||
initJointTransforms(scale, offset);
|
||||
|
||||
int numStates = _jointStates.size();
|
||||
float radius = 0.0f;
|
||||
for (int i = 0; i < numStates; ++i) {
|
||||
float distance = glm::length(_jointStates[i].getPosition());
|
||||
if (distance > radius) {
|
||||
radius = distance;
|
||||
}
|
||||
_jointStates[i].buildConstraint();
|
||||
}
|
||||
for (int i = 0; i < _jointStates.size(); i++) {
|
||||
_jointStates[i].slaveVisibleTransform();
|
||||
}
|
||||
|
||||
// XXX update AnimationHandles from here?
|
||||
}
|
||||
|
||||
void Rig::initJointTransforms(glm::vec3 scale, glm::vec3 offset) {
|
||||
// compute model transforms
|
||||
int numStates = _jointStates.size();
|
||||
for (int i = 0; i < numStates; ++i) {
|
||||
JointState& state = _jointStates[i];
|
||||
const FBXJoint& joint = state.getFBXJoint();
|
||||
int parentIndex = joint.parentIndex;
|
||||
if (parentIndex == -1) {
|
||||
// const FBXGeometry& geometry = _geometry->getFBXGeometry();
|
||||
// NOTE: in practice geometry.offset has a non-unity scale (rather than a translation)
|
||||
glm::mat4 parentTransform = glm::scale(scale) * glm::translate(offset); // * geometry.offset; XXX
|
||||
state.initTransform(parentTransform);
|
||||
} else {
|
||||
const JointState& parentState = _jointStates.at(parentIndex);
|
||||
state.initTransform(parentState.getTransform());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void Rig::resetJoints() {
|
||||
if (_jointStates.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// const FBXGeometry& geometry = _geometry->getFBXGeometry();
|
||||
for (int i = 0; i < _jointStates.size(); i++) {
|
||||
const FBXJoint& fbxJoint = _jointStates[i].getFBXJoint();
|
||||
_jointStates[i].setRotationInConstrainedFrame(fbxJoint.rotation, 0.0f);
|
||||
}
|
||||
}
|
||||
|
||||
AnimationHandlePointer Rig::createAnimationHandle() {
|
||||
AnimationHandlePointer handle(new AnimationHandle(getRigPointer()));
|
||||
_animationHandles.insert(handle);
|
||||
return handle;
|
||||
}
|
||||
|
|
|
@ -16,8 +16,39 @@
|
|||
|
||||
#include <QObject>
|
||||
|
||||
class Rig : public QObject {
|
||||
#include "JointState.h"
|
||||
|
||||
class AnimationHandle;
|
||||
typedef std::shared_ptr<AnimationHandle> AnimationHandlePointer;
|
||||
// typedef QWeakPointer<AnimationHandle> WeakAnimationHandlePointer;
|
||||
|
||||
class Rig;
|
||||
typedef std::shared_ptr<Rig> RigPointer;
|
||||
|
||||
|
||||
class Rig : public QObject, public std::enable_shared_from_this<Rig> {
|
||||
|
||||
public:
|
||||
RigPointer getRigPointer() { return shared_from_this(); }
|
||||
|
||||
bool removeRunningAnimation(AnimationHandlePointer animationHandle);
|
||||
void addRunningAnimation(AnimationHandlePointer animationHandle);
|
||||
bool isRunningAnimation(AnimationHandlePointer animationHandle);
|
||||
const QList<AnimationHandlePointer>& getRunningAnimations() const { return _runningAnimations; }
|
||||
|
||||
void initJointStates(glm::vec3 scale, glm::vec3 offset, QVector<JointState> states);
|
||||
void initJointTransforms(glm::vec3 scale, glm::vec3 offset);
|
||||
void resetJoints();
|
||||
|
||||
QVector<JointState> getJointStates() { return _jointStates; }
|
||||
|
||||
AnimationHandlePointer createAnimationHandle();
|
||||
|
||||
protected:
|
||||
QVector<JointState> _jointStates;
|
||||
|
||||
QSet<AnimationHandlePointer> _animationHandles;
|
||||
QList<AnimationHandlePointer> _runningAnimations;
|
||||
};
|
||||
|
||||
#endif /* defined(__hifi__Rig__) */
|
||||
|
|
|
@ -1255,17 +1255,6 @@ QStringList Model::getJointNames() const {
|
|||
return isActive() ? _geometry->getFBXGeometry().getJointNames() : QStringList();
|
||||
}
|
||||
|
||||
uint qHash(const WeakAnimationHandlePointer& handle, uint seed) {
|
||||
return qHash(handle.data(), seed);
|
||||
}
|
||||
|
||||
AnimationHandlePointer Model::createAnimationHandle() {
|
||||
AnimationHandlePointer handle(new AnimationHandle(this));
|
||||
handle->_self = handle;
|
||||
_animationHandles.insert(handle);
|
||||
return handle;
|
||||
}
|
||||
|
||||
// virtual override from PhysicsEntity
|
||||
void Model::buildShapes() {
|
||||
// TODO: figure out how to load/build collision shapes for general models
|
||||
|
@ -1830,9 +1819,9 @@ void Model::deleteGeometry() {
|
|||
clearShapes();
|
||||
|
||||
for (QSet<WeakAnimationHandlePointer>::iterator it = _animationHandles.begin(); it != _animationHandles.end(); ) {
|
||||
AnimationHandlePointer handle = it->toStrongRef();
|
||||
AnimationHandlePointer handle = it->lock();
|
||||
if (handle) {
|
||||
handle->_jointMappings.clear();
|
||||
handle->clearJoints();
|
||||
it++;
|
||||
} else {
|
||||
it = _animationHandles.erase(it);
|
||||
|
|
|
@ -209,7 +209,6 @@ public:
|
|||
|
||||
QStringList getJointNames() const;
|
||||
|
||||
AnimationHandlePointer createAnimationHandle();
|
||||
|
||||
const QList<AnimationHandlePointer>& getRunningAnimations() const { return _runningAnimations; }
|
||||
|
||||
|
|
Loading…
Reference in a new issue