mirror of
https://github.com/OpenMW/openmw.git
synced 2025-01-20 05:23:53 +00:00
Feature #50: Handle weapon controllers (i.e. bowstring animations, etc)
This commit is contained in:
parent
975f0e05b4
commit
7cf22391a5
5 changed files with 76 additions and 3 deletions
|
@ -547,6 +547,7 @@ bool CharacterController::updateWeaponState()
|
|||
{
|
||||
getWeaponGroup(weaptype, weapgroup);
|
||||
mAnimation->showWeapons(false);
|
||||
mAnimation->setWeaponGroup(weapgroup);
|
||||
|
||||
mAnimation->play(weapgroup, Priority_Weapon,
|
||||
MWRender::Animation::Group_UpperBody, true,
|
||||
|
|
|
@ -870,6 +870,27 @@ bool Animation::getInfo(const std::string &groupname, float *complete, float *sp
|
|||
return true;
|
||||
}
|
||||
|
||||
float Animation::getStartTime(const std::string &groupname) const
|
||||
{
|
||||
AnimSourceList::const_iterator iter(mAnimSources.begin());
|
||||
for(;iter != mAnimSources.end();iter++)
|
||||
{
|
||||
const NifOgre::TextKeyMap &keys = (*iter)->mTextKeys;
|
||||
NifOgre::TextKeyMap::const_iterator found = findGroupStart(keys, groupname);
|
||||
if(found != keys.end())
|
||||
return found->first;
|
||||
}
|
||||
return -1.f;
|
||||
}
|
||||
|
||||
float Animation::getCurrentTime(const std::string &groupname) const
|
||||
{
|
||||
AnimStateMap::const_iterator iter = mStates.find(groupname);
|
||||
if(iter == mStates.end())
|
||||
return -1.f;
|
||||
|
||||
return iter->second.mTime;
|
||||
}
|
||||
|
||||
void Animation::disable(const std::string &groupname)
|
||||
{
|
||||
|
|
|
@ -271,12 +271,20 @@ public:
|
|||
*/
|
||||
bool getInfo(const std::string &groupname, float *complete=NULL, float *speedmult=NULL) const;
|
||||
|
||||
/// Get the absolute position in the animation track of the first text key with the given group.
|
||||
float getStartTime(const std::string &groupname) const;
|
||||
|
||||
/// Get the current absolute position in the animation track for the animation that is currently playing from the given group.
|
||||
float getCurrentTime(const std::string& groupname) const;
|
||||
|
||||
/** Disables the specified animation group;
|
||||
* \param groupname Animation group to disable.
|
||||
*/
|
||||
void disable(const std::string &groupname);
|
||||
void changeGroups(const std::string &groupname, int group);
|
||||
|
||||
virtual void setWeaponGroup(const std::string& group) {}
|
||||
|
||||
/** Retrieves the velocity (in units per second) that the animation will move. */
|
||||
float getVelocity(const std::string &groupname) const;
|
||||
|
||||
|
|
|
@ -71,6 +71,27 @@ float HeadAnimationTime::getValue() const
|
|||
return 1;
|
||||
}
|
||||
|
||||
float WeaponAnimationTime::getValue() const
|
||||
{
|
||||
if (mWeaponGroup.empty())
|
||||
return 0;
|
||||
float current = mAnimation->getCurrentTime(mWeaponGroup);
|
||||
if (current == -1)
|
||||
return 0;
|
||||
return current - mStartTime;
|
||||
}
|
||||
|
||||
void WeaponAnimationTime::setGroup(const std::string &group)
|
||||
{
|
||||
mWeaponGroup = group;
|
||||
mStartTime = mAnimation->getStartTime(mWeaponGroup);
|
||||
}
|
||||
|
||||
void WeaponAnimationTime::updateStartTime()
|
||||
{
|
||||
setGroup(mWeaponGroup);
|
||||
}
|
||||
|
||||
static NpcAnimation::PartBoneMap createPartListMap()
|
||||
{
|
||||
NpcAnimation::PartBoneMap result;
|
||||
|
@ -126,6 +147,7 @@ NpcAnimation::NpcAnimation(const MWWorld::Ptr& ptr, Ogre::SceneNode* node, int v
|
|||
mNpc = mPtr.get<ESM::NPC>()->mBase;
|
||||
|
||||
mHeadAnimationTime = Ogre::SharedPtr<HeadAnimationTime>(new HeadAnimationTime(mPtr));
|
||||
mWeaponAnimationTime = Ogre::SharedPtr<WeaponAnimationTime>(new WeaponAnimationTime(this));
|
||||
|
||||
for(size_t i = 0;i < ESM::PRT_Count;i++)
|
||||
{
|
||||
|
@ -223,6 +245,8 @@ void NpcAnimation::updateNpcBase()
|
|||
for(size_t i = 0;i < ESM::PRT_Count;i++)
|
||||
removeIndividualPart((ESM::PartReferenceType)i);
|
||||
updateParts();
|
||||
|
||||
mWeaponAnimationTime->updateStartTime();
|
||||
}
|
||||
|
||||
void NpcAnimation::updateParts()
|
||||
|
@ -588,9 +612,6 @@ bool NpcAnimation::addOrReplaceIndividualPart(ESM::PartReferenceType type, int g
|
|||
updateSkeletonInstance(mSkelBase->getSkeleton(), skel);
|
||||
}
|
||||
|
||||
// TODO:
|
||||
// type == ESM::PRT_Weapon should get an animation source based on the current offset
|
||||
// of the weapon attack animation (from its beginning, or start marker?)
|
||||
std::vector<Ogre::Controller<Ogre::Real> >::iterator ctrl(mObjectParts[type]->mControllers.begin());
|
||||
for(;ctrl != mObjectParts[type]->mControllers.end();ctrl++)
|
||||
{
|
||||
|
@ -600,6 +621,8 @@ bool NpcAnimation::addOrReplaceIndividualPart(ESM::PartReferenceType type, int g
|
|||
|
||||
if (type == ESM::PRT_Head)
|
||||
ctrl->setSource(mHeadAnimationTime);
|
||||
else if (type == ESM::PRT_Weapon)
|
||||
ctrl->setSource(mWeaponAnimationTime);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -25,6 +25,23 @@ public:
|
|||
{ }
|
||||
};
|
||||
|
||||
class WeaponAnimationTime : public Ogre::ControllerValue<Ogre::Real>
|
||||
{
|
||||
private:
|
||||
Animation* mAnimation;
|
||||
std::string mWeaponGroup;
|
||||
float mStartTime;
|
||||
public:
|
||||
WeaponAnimationTime(Animation* animation) : mAnimation(animation), mStartTime(0) {}
|
||||
void setGroup(const std::string& group);
|
||||
void updateStartTime();
|
||||
|
||||
virtual Ogre::Real getValue() const;
|
||||
virtual void setValue(Ogre::Real value)
|
||||
{ }
|
||||
};
|
||||
|
||||
|
||||
class NpcAnimation : public Animation, public MWWorld::InventoryStoreListener
|
||||
{
|
||||
public:
|
||||
|
@ -71,6 +88,7 @@ private:
|
|||
Ogre::Vector3 mFirstPersonOffset;
|
||||
|
||||
Ogre::SharedPtr<HeadAnimationTime> mHeadAnimationTime;
|
||||
Ogre::SharedPtr<WeaponAnimationTime> mWeaponAnimationTime;
|
||||
|
||||
float mAlpha;
|
||||
|
||||
|
@ -105,6 +123,8 @@ public:
|
|||
ViewMode viewMode=VM_Normal);
|
||||
virtual ~NpcAnimation();
|
||||
|
||||
virtual void setWeaponGroup(const std::string& group) { mWeaponAnimationTime->setGroup(group); }
|
||||
|
||||
virtual Ogre::Vector3 runAnimation(float timepassed);
|
||||
|
||||
virtual void showWeapons(bool showWeapon);
|
||||
|
|
Loading…
Reference in a new issue