mirror of
https://gitlab.com/OpenMW/openmw.git
synced 2025-03-14 01:19:59 +00:00
Animation creatures
This commit is contained in:
parent
88c427543b
commit
653d999ac4
@ -135,6 +135,7 @@ bool OMW::Engine::frameRenderingQueued (const Ogre::FrameEvent& evt)
|
||||
mEnvironment.mWorld->advanceTime (
|
||||
mEnvironment.mFrameDuration*mEnvironment.mWorld->getTimeScaleFactor()/3600);
|
||||
|
||||
|
||||
if (changed) // keep change flag for another frame, if cell changed happend in local script
|
||||
mEnvironment.mWorld->markCellAsUnchanged();
|
||||
|
||||
|
@ -111,4 +111,18 @@ void Actors::removeCell(MWWorld::Ptr::CellStore* store){
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
void Actors::playAnimationGroup (const MWWorld::Ptr& ptr, const std::string& groupName, int mode, int number){
|
||||
mAllActors.find(ptr)->second->startScript(groupName, mode, number);
|
||||
}
|
||||
void Actors::skipAnimation (const MWWorld::Ptr& ptr){
|
||||
|
||||
}
|
||||
void Actors::addTime(){
|
||||
//std::cout << "Adding time in actors\n";
|
||||
for(std::map<MWWorld::Ptr, Animation*>::iterator iter = mAllActors.begin(); iter != mAllActors.end(); iter++)
|
||||
{
|
||||
(iter->second)->runAnimation(mEnvironment.mFrameDuration);
|
||||
}
|
||||
}
|
||||
|
@ -38,6 +38,20 @@ namespace MWRender{
|
||||
///< \return found?
|
||||
|
||||
void removeCell(MWWorld::Ptr::CellStore* store);
|
||||
|
||||
void playAnimationGroup (const MWWorld::Ptr& ptr, const std::string& groupName, int mode,
|
||||
int number = 1);
|
||||
///< Run animation for a MW-reference. Calls to this function for references that are currently not
|
||||
/// in the rendered scene should be ignored.
|
||||
///
|
||||
/// \param mode: 0 normal, 1 immediate start, 2 immediate loop
|
||||
/// \param number How offen the animation should be run
|
||||
|
||||
void skipAnimation (const MWWorld::Ptr& ptr);
|
||||
///< Skip the animation for the given MW-reference for one frame. Calls to this function for
|
||||
/// references that are currently not in the rendered scene should be ignored.
|
||||
|
||||
void addTime();
|
||||
|
||||
};
|
||||
}
|
||||
|
@ -3,8 +3,10 @@
|
||||
|
||||
namespace MWRender{
|
||||
std::map<std::string, int> Animation::mUniqueIDs;
|
||||
|
||||
Animation::~Animation(){
|
||||
}
|
||||
|
||||
std::string Animation::getUniqueID(std::string mesh){
|
||||
int counter;
|
||||
if(mUniqueIDs.find(mesh) == mUniqueIDs.end()){
|
||||
@ -27,6 +29,11 @@ namespace MWRender{
|
||||
//If groupname is recognized set animate to true
|
||||
//Set the start time and stop time
|
||||
//How many times to loop
|
||||
if(groupname == "all"){
|
||||
animate = true;
|
||||
time = startTime;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void Animation::handleShapes(std::vector<Nif::NiTriShapeCopy>* allshapes, Ogre::Entity* creaturemodel, Ogre::SkeletonInstance *skel){
|
||||
@ -35,7 +42,7 @@ namespace MWRender{
|
||||
for(allshapesiter = allshapes->begin(); allshapesiter != allshapes->end(); allshapesiter++)
|
||||
{
|
||||
|
||||
Nif::NiTriShapeCopy copy = *allshapesiter;
|
||||
Nif::NiTriShapeCopy& copy = *allshapesiter;
|
||||
std::vector<Ogre::Vector3> allvertices = copy.vertices;
|
||||
std::vector<Ogre::Vector3> allnormals = copy.normals;
|
||||
|
||||
@ -133,6 +140,7 @@ namespace MWRender{
|
||||
*addr = absVertPos.x;
|
||||
*(addr+1) = absVertPos.y;
|
||||
*(addr+2) = absVertPos.z;
|
||||
|
||||
|
||||
//std::cout << "Vertex" << vertices[verIndex] << "\n";
|
||||
}
|
||||
@ -147,6 +155,7 @@ namespace MWRender{
|
||||
*addr = absVertPos.x;
|
||||
*(addr+1) = absVertPos.y;
|
||||
*(addr+2) = absVertPos.z;
|
||||
std::cout << "We are actually 2\n";
|
||||
//std::cout << "Vertex" << verIndex << "Weight: " << boneinfo.weights[i].weight << "was seen twice\n";
|
||||
|
||||
}
|
||||
@ -194,8 +203,8 @@ namespace MWRender{
|
||||
Ogre::Vector3 transmult;
|
||||
Ogre::Quaternion rotmult;
|
||||
float scale;
|
||||
if(creaturemodel->getSkeleton()->hasBone(*boneSequenceIter)){
|
||||
Ogre::Bone *bonePtr = creaturemodel->getSkeleton()->getBone(*boneSequenceIter);
|
||||
if(skel->hasBone(*boneSequenceIter)){
|
||||
Ogre::Bone *bonePtr = skel->getBone(*boneSequenceIter);
|
||||
|
||||
|
||||
|
||||
@ -327,11 +336,7 @@ namespace MWRender{
|
||||
}
|
||||
|
||||
void Animation::handleAnimationTransforms(){
|
||||
Ogre::Bone* b = skel->getRootBone();
|
||||
b->setOrientation(.3,.3,.3,.3); //This is a trick
|
||||
skel->getManualBonesDirty();
|
||||
skel->_updateTransforms();
|
||||
skel->_notifyManualBonesDirty();
|
||||
|
||||
|
||||
std::vector<Nif::NiKeyframeData>::iterator iter;
|
||||
int slot = 0;
|
||||
|
@ -49,6 +49,19 @@ void CreatureAnimation::runAnimation(float timepassed){
|
||||
//Handle the animation transforms dependent on time
|
||||
|
||||
//Handle the shapes dependent on animation transforms
|
||||
time += timepassed;
|
||||
Ogre::Bone* b = skel->getRootBone();
|
||||
b->setOrientation(.3,.3,.3,.3); //This is a trick
|
||||
skel->getManualBonesDirty();
|
||||
skel->_updateTransforms();
|
||||
skel->_notifyManualBonesDirty();
|
||||
|
||||
base->getAllAnimationStates()->_notifyDirty();
|
||||
base->_updateAnimation();
|
||||
base->_notifyMoved();
|
||||
|
||||
handleAnimationTransforms();
|
||||
handleShapes(shapes, base, skel);
|
||||
|
||||
}
|
||||
}
|
||||
|
@ -173,7 +173,7 @@ NpcAnimation::NpcAnimation(const MWWorld::Ptr& ptr, MWWorld::Environment& _env,O
|
||||
if(hair)
|
||||
insertBoundedPart("meshes\\" + hair->model, "Head");
|
||||
|
||||
if (chest){
|
||||
/*if (chest){
|
||||
insertFreePart("meshes\\" + chest->model, ">\"", insert);
|
||||
|
||||
|
||||
@ -181,7 +181,7 @@ NpcAnimation::NpcAnimation(const MWWorld::Ptr& ptr, MWWorld::Environment& _env,O
|
||||
if (handr){
|
||||
insertFreePart("meshes\\" + handr->model , ">?", insert);
|
||||
|
||||
}
|
||||
}*/
|
||||
if (handl){
|
||||
insertFreePart("meshes\\" + handl->model, ">>", insert);
|
||||
|
||||
@ -207,25 +207,50 @@ void NpcAnimation::insertFreePart(const std::string &mesh, const std::string suf
|
||||
std::string meshNumbered = mesh + getUniqueID(mesh + suffix) + suffix;
|
||||
NIFLoader::load(meshNumbered);
|
||||
|
||||
Entity* ent = mRend.getScene()->createEntity(meshNumbered);
|
||||
insert->attachObject(ent);
|
||||
entityparts.push_back(ent);
|
||||
hand = mRend.getScene()->createEntity(meshNumbered);
|
||||
insert->attachObject(hand);
|
||||
//entityparts.push_back(ent);
|
||||
std::vector<Nif::NiTriShapeCopy>* shapes = ((NIFLoader::getSingletonPtr())->getShapes(mesh + "0000" + suffix));
|
||||
if(shapes){
|
||||
shapeparts.push_back(shapes);
|
||||
handleShapes(shapes, ent, skel);
|
||||
handleShapes(shapes, hand, skel);
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
|
||||
|
||||
void NpcAnimation::runAnimation(float timepassed){
|
||||
//Add the amount of time passed to time
|
||||
|
||||
//Handle the animation transforms dependent on time
|
||||
|
||||
//Handle the shapes dependent on animation transforms
|
||||
if(animate){
|
||||
//Add the amount of time passed to time
|
||||
time += timepassed;
|
||||
Ogre::Bone* b = skel->getRootBone();
|
||||
b->setOrientation(.3,.3,.3,.3); //This is a trick
|
||||
skel->getManualBonesDirty();
|
||||
skel->_updateTransforms();
|
||||
skel->_notifyManualBonesDirty();
|
||||
|
||||
//Handle the animation transforms dependent on time
|
||||
base->getAllAnimationStates()->_notifyDirty();
|
||||
base->_updateAnimation();
|
||||
base->_notifyMoved();
|
||||
|
||||
//Handle the shapes dependent on animation transforms
|
||||
}
|
||||
|
||||
handleAnimationTransforms();
|
||||
std::vector<std::vector<Nif::NiTriShapeCopy>*>::iterator shapepartsiter = shapeparts.begin();
|
||||
std::vector<Ogre::Entity*>::iterator entitypartsiter = entityparts.begin();
|
||||
int i = 0;
|
||||
while(shapepartsiter != shapeparts.end() && entitypartsiter != entityparts.end())
|
||||
{
|
||||
std::vector<Nif::NiTriShapeCopy>* shapes = *shapepartsiter;
|
||||
handleShapes(shapes, *entitypartsiter, skel);
|
||||
//std::cout << "Shape part size" << shapes->size() << "\n";
|
||||
shapepartsiter++;
|
||||
entitypartsiter++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
@ -16,7 +16,7 @@ namespace MWRender{
|
||||
|
||||
class NpcAnimation: public Animation{
|
||||
std::vector<Ogre::Entity*> entityparts;
|
||||
|
||||
Ogre::Entity* hand;
|
||||
std::vector<std::vector<Nif::NiTriShapeCopy>*> shapeparts; //All the NiTriShape data that we need for animating this particular npc
|
||||
public:
|
||||
NpcAnimation(const MWWorld::Ptr& ptr, MWWorld::Environment& _env, OEngine::Render::OgreRenderer& _rend);
|
||||
|
@ -234,13 +234,15 @@ void RenderingManager::playAnimationGroup (const MWWorld::Ptr& ptr, const std::s
|
||||
int mode, int number)
|
||||
{
|
||||
std::cout<<"play animation " << groupName << ", " << mode << ", " << number << std::endl;
|
||||
mActors.playAnimationGroup(ptr, groupName, mode, number);
|
||||
}
|
||||
|
||||
void RenderingManager::skipAnimation (const MWWorld::Ptr& ptr)
|
||||
{
|
||||
std::cout<<"skip animation"<<std::endl;
|
||||
}
|
||||
void RenderingManager::addTime(float timepassed){
|
||||
void RenderingManager::addTime(){
|
||||
mActors.addTime();
|
||||
//Notify each animation that time has passed
|
||||
}
|
||||
|
||||
|
@ -105,7 +105,7 @@ class RenderingManager: private RenderingInterface {
|
||||
///< Skip the animation for the given MW-reference for one frame. Calls to this function for
|
||||
/// references that are currently not in the rendered scene should be ignored.
|
||||
|
||||
void addTime(float timepassed);
|
||||
void addTime();
|
||||
|
||||
private:
|
||||
|
||||
|
@ -52,7 +52,9 @@ void insertCellRefList(MWRender::RenderingManager& rendering, MWWorld::Environme
|
||||
|
||||
namespace MWWorld
|
||||
{
|
||||
|
||||
void Scene::advanceTime(){
|
||||
mRendering.addTime();
|
||||
}
|
||||
void Scene::unloadCell (CellStoreCollection::iterator iter)
|
||||
{
|
||||
std::cout << "Unloading cell\n";
|
||||
|
@ -101,6 +101,7 @@ namespace MWWorld
|
||||
void markCellAsUnchanged();
|
||||
|
||||
void insertCell(ESMS::CellStore<MWWorld::RefData> &cell, MWWorld::Environment& environment);
|
||||
void advanceTime();
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -348,13 +348,14 @@ namespace MWWorld
|
||||
void World::advanceTime (double hours)
|
||||
{
|
||||
hours += mGlobalVariables->getFloat ("gamehour");
|
||||
|
||||
|
||||
setHour (hours);
|
||||
|
||||
int days = hours / 24;
|
||||
|
||||
if (days>0)
|
||||
mGlobalVariables->setInt ("dayspassed", days + mGlobalVariables->getInt ("dayspassed"));
|
||||
mWorldScene->advanceTime();
|
||||
}
|
||||
|
||||
void World::setHour (double hour)
|
||||
|
Loading…
x
Reference in New Issue
Block a user