Merge remote-tracking branch 'zini/master' into animation2

Conflicts:
	apps/openmw/mwrender/actors.cpp
	apps/openmw/mwrender/actors.hpp
actorid
Chris Robinson 12 years ago
commit 1ce8eaf52c

@ -9,6 +9,7 @@
#include <components/bsa/bsa_archive.hpp>
#include <components/files/configurationmanager.hpp>
#include <components/translation/translation.hpp>
#include <components/nif/nif_file.hpp>
#include <components/nifoverrides/nifoverrides.hpp>
#include <components/nifbullet/bullet_nif_loader.hpp>

@ -84,7 +84,7 @@ namespace MWBase
///< Start playing music from the selected folder
/// \param name of the folder that contains the playlist
virtual void say(MWWorld::Ptr reference, const std::string& filename) = 0;
virtual void say(const MWWorld::Ptr &reference, const std::string& filename) = 0;
///< Make an actor say some text.
/// \param filename name of a sound file in "Sound/" in the data directory.
@ -92,10 +92,10 @@ namespace MWBase
///< Say some text, without an actor ref
/// \param filename name of a sound file in "Sound/" in the data directory.
virtual bool sayDone(MWWorld::Ptr reference=MWWorld::Ptr()) const = 0;
virtual bool sayDone(const MWWorld::Ptr &reference=MWWorld::Ptr()) const = 0;
///< Is actor not speaking?
virtual void stopSay(MWWorld::Ptr reference=MWWorld::Ptr()) = 0;
virtual void stopSay(const MWWorld::Ptr &reference=MWWorld::Ptr()) = 0;
///< Stop an actor speaking
virtual SoundPtr playTrack(const MWSound::DecoderPtr& decoder, PlayType type) = 0;
@ -105,14 +105,14 @@ namespace MWBase
PlayMode mode=Play_Normal) = 0;
///< Play a sound, independently of 3D-position
virtual SoundPtr playSound3D(MWWorld::Ptr reference, const std::string& soundId,
virtual SoundPtr playSound3D(const MWWorld::Ptr &reference, const std::string& soundId,
float volume, float pitch, PlayMode mode=Play_Normal) = 0;
///< Play a sound from an object
virtual void stopSound3D(MWWorld::Ptr reference, const std::string& soundId) = 0;
virtual void stopSound3D(const MWWorld::Ptr &reference, const std::string& soundId) = 0;
///< Stop the given object from playing the given sound,
virtual void stopSound3D(MWWorld::Ptr reference) = 0;
virtual void stopSound3D(const MWWorld::Ptr &reference) = 0;
///< Stop the given object from playing all sounds.
virtual void stopSound(const MWWorld::CellStore *cell) = 0;
@ -121,7 +121,7 @@ namespace MWBase
virtual void stopSound(const std::string& soundId) = 0;
///< Stop a non-3d looping sound
virtual bool getSoundPlaying(MWWorld::Ptr reference, const std::string& soundId) const = 0;
virtual bool getSoundPlaying(const MWWorld::Ptr &reference, const std::string& soundId) const = 0;
///< Is the given sound currently playing on the given object?
virtual void pauseSounds(int types=Play_TypeMask) = 0;

@ -16,31 +16,31 @@ namespace MWRender
{
using namespace Ogre;
Actors::~Actors(){
std::map<MWWorld::Ptr, Animation*>::iterator it = mAllActors.begin();
for (; it != mAllActors.end(); ++it) {
Actors::~Actors()
{
PtrAnimationMap::iterator it = mAllActors.begin();
for(;it != mAllActors.end();++it)
{
delete it->second;
it->second = NULL;
}
}
void Actors::setMwRoot(Ogre::SceneNode* root){
mMwRoot = root;
}
void Actors::setMwRoot(Ogre::SceneNode* root)
{ mMwRoot = root; }
void Actors::insertBegin (const MWWorld::Ptr& ptr)
void Actors::insertBegin(const MWWorld::Ptr &ptr)
{
Ogre::SceneNode* cellnode;
if(mCellSceneNodes.find(ptr.getCell()) == mCellSceneNodes.end())
CellSceneNodeMap::const_iterator celliter = mCellSceneNodes.find(ptr.getCell());
if(celliter != mCellSceneNodes.end())
cellnode = celliter->second;
else
{
//Create the scenenode and put it in the map
cellnode = mMwRoot->createChildSceneNode();
mCellSceneNodes[ptr.getCell()] = cellnode;
}
else
{
cellnode = mCellSceneNodes[ptr.getCell()];
}
Ogre::SceneNode* insert = cellnode->createChildSceneNode();
const float *f = ptr.getRefData().getPosition().pos;
@ -51,13 +51,13 @@ void Actors::insertBegin (const MWWorld::Ptr& ptr)
f = ptr.getCellRef().mPos.rot;
// Rotate around X axis
Quaternion xr(Radian(-f[0]), Vector3::UNIT_X);
Ogre::Quaternion xr(Ogre::Radian(-f[0]), Ogre::Vector3::UNIT_X);
// Rotate around Y axis
Quaternion yr(Radian(-f[1]), Vector3::UNIT_Y);
Ogre::Quaternion yr(Ogre::Radian(-f[1]), Ogre::Vector3::UNIT_Y);
// Rotate around Z axis
Quaternion zr(Radian(-f[2]), Vector3::UNIT_Z);
Ogre::Quaternion zr(Ogre::Radian(-f[2]), Ogre::Vector3::UNIT_Z);
// Rotates first around z, then y, then x
insert->setOrientation(xr*yr*zr);
@ -83,20 +83,21 @@ bool Actors::deleteObject (const MWWorld::Ptr& ptr)
{
delete mAllActors[ptr];
mAllActors.erase(ptr);
if (Ogre::SceneNode *base = ptr.getRefData().getBaseNode())
{
if(Ogre::SceneNode *base=ptr.getRefData().getBaseNode())
{
Ogre::SceneNode *parent = base->getParentSceneNode();
for (std::map<MWWorld::Ptr::CellStore *, Ogre::SceneNode *>::const_iterator iter (
mCellSceneNodes.begin()); iter!=mCellSceneNodes.end(); ++iter)
if (iter->second==parent)
CellSceneNodeMap::const_iterator iter(mCellSceneNodes.begin());
for(;iter != mCellSceneNodes.end();++iter)
{
if(iter->second == parent)
{
base->removeAndDestroyAllChildren();
mRend.getScene()->destroySceneNode (base);
ptr.getRefData().setBaseNode (0);
return true;
}
}
return false;
}
@ -104,57 +105,68 @@ bool Actors::deleteObject (const MWWorld::Ptr& ptr)
return true;
}
void Actors::removeCell(MWWorld::Ptr::CellStore* store){
if(mCellSceneNodes.find(store) != mCellSceneNodes.end())
{
Ogre::SceneNode* base = mCellSceneNodes[store];
base->removeAndDestroyAllChildren();
mCellSceneNodes.erase(store);
mRend.getScene()->destroySceneNode(base);
base = 0;
}
for(std::map<MWWorld::Ptr, Animation*>::iterator iter = mAllActors.begin(); iter != mAllActors.end(); )
void Actors::removeCell(MWWorld::Ptr::CellStore* store)
{
for(PtrAnimationMap::iterator iter = mAllActors.begin();iter != mAllActors.end();)
{
if(iter->first.getCell() == store){
if(iter->first.getCell() == store)
{
delete iter->second;
mAllActors.erase(iter++);
}
else
++iter;
}
CellSceneNodeMap::iterator celliter = mCellSceneNodes.find(store);
if(celliter != mCellSceneNodes.end())
{
Ogre::SceneNode *base = celliter->second;
base->removeAndDestroyAllChildren();
mRend.getScene()->destroySceneNode(base);
mCellSceneNodes.erase(celliter);
}
}
void Actors::playAnimationGroup (const MWWorld::Ptr& ptr, const std::string& groupName, int mode, int number){
if(mAllActors.find(ptr) != mAllActors.end())
mAllActors[ptr]->playGroup(groupName, mode, number);
void Actors::playAnimationGroup (const MWWorld::Ptr& ptr, const std::string& groupName, int mode, int number)
{
PtrAnimationMap::const_iterator iter = mAllActors.find(ptr);
if(iter != mAllActors.end())
iter->second->playGroup(groupName, mode, number);
}
void Actors::skipAnimation (const MWWorld::Ptr& ptr){
if(mAllActors.find(ptr) != mAllActors.end())
mAllActors[ptr]->skipAnim();
void Actors::skipAnimation (const MWWorld::Ptr& ptr)
{
PtrAnimationMap::const_iterator iter = mAllActors.find(ptr);
if(iter != mAllActors.end())
iter->second->skipAnim();
}
void Actors::update (float duration){
for(std::map<MWWorld::Ptr, Animation*>::iterator iter = mAllActors.begin(); iter != mAllActors.end(); iter++)
void Actors::update (float duration)
{
for(PtrAnimationMap::const_iterator iter = mAllActors.begin();iter != mAllActors.end();iter++)
iter->second->runAnimation(duration);
}
void
Actors::updateObjectCell(const MWWorld::Ptr &ptr)
void Actors::updateObjectCell(const MWWorld::Ptr &ptr)
{
Ogre::SceneNode *node;
MWWorld::CellStore *newCell = ptr.getCell();
if(mCellSceneNodes.find(newCell) == mCellSceneNodes.end()) {
CellSceneNodeMap::const_iterator celliter = mCellSceneNodes.find(newCell);
if(celliter != mCellSceneNodes.end())
node = celliter->second;
else
{
node = mMwRoot->createChildSceneNode();
mCellSceneNodes[newCell] = node;
} else {
node = mCellSceneNodes[newCell];
}
node->addChild(ptr.getRefData().getBaseNode());
if (mAllActors.find(ptr) != mAllActors.end()) {
PtrAnimationMap::iterator iter = mAllActors.find(ptr);
if(iter != mAllActors.end())
{
/// \note Update key (Ptr's are compared only with refdata so mCell
/// on key is outdated), maybe redundant
Animation *anim = mAllActors[ptr];
mAllActors.erase(ptr);
Animation *anim = iter->second;
mAllActors.erase(iter);
mAllActors[ptr] = anim;
}
}

@ -16,14 +16,19 @@ namespace MWRender
class Actors
{
typedef std::map<MWWorld::CellStore*,Ogre::SceneNode*> CellSceneNodeMap;
typedef std::map<MWWorld::Ptr,Animation*> PtrAnimationMap;
OEngine::Render::OgreRenderer &mRend;
std::map<MWWorld::CellStore *, Ogre::SceneNode *> mCellSceneNodes;
Ogre::SceneNode* mMwRoot;
std::map<MWWorld::Ptr, Animation*> mAllActors;
CellSceneNodeMap mCellSceneNodes;
PtrAnimationMap mAllActors;
public:
Actors(OEngine::Render::OgreRenderer& _rend): mRend(_rend) {}
~Actors();
void setMwRoot(Ogre::SceneNode* root);
void insertBegin (const MWWorld::Ptr& ptr);
void insertCreature (const MWWorld::Ptr& ptr);

@ -13,7 +13,7 @@ namespace Interpreter
namespace MWScript
{
/// \brief Temporaty script functionality limited to the console
/// \brief Temporary script functionality limited to the console
namespace User
{
void registerExtensions (Compiler::Extensions& extensions);

@ -160,7 +160,7 @@ namespace MWSound
return volume;
}
bool SoundManager::isPlaying(MWWorld::Ptr ptr, const std::string &id) const
bool SoundManager::isPlaying(const MWWorld::Ptr &ptr, const std::string &id) const
{
SoundMap::const_iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end())
@ -229,7 +229,7 @@ namespace MWSound
startRandomTitle();
}
void SoundManager::say(MWWorld::Ptr ptr, const std::string& filename)
void SoundManager::say(const MWWorld::Ptr &ptr, const std::string& filename)
{
if(!mOutput->isInitialized())
return;
@ -269,12 +269,12 @@ namespace MWSound
}
}
bool SoundManager::sayDone(MWWorld::Ptr ptr) const
bool SoundManager::sayDone(const MWWorld::Ptr &ptr) const
{
return !isPlaying(ptr, "_say_sound");
}
void SoundManager::stopSay(MWWorld::Ptr ptr)
void SoundManager::stopSay(const MWWorld::Ptr &ptr)
{
SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end())
@ -328,7 +328,7 @@ namespace MWSound
return sound;
}
MWBase::SoundPtr SoundManager::playSound3D(MWWorld::Ptr ptr, const std::string& soundId,
MWBase::SoundPtr SoundManager::playSound3D(const MWWorld::Ptr &ptr, const std::string& soundId,
float volume, float pitch, PlayMode mode)
{
MWBase::SoundPtr sound;
@ -356,7 +356,7 @@ namespace MWSound
return sound;
}
void SoundManager::stopSound3D(MWWorld::Ptr ptr, const std::string& soundId)
void SoundManager::stopSound3D(const MWWorld::Ptr &ptr, const std::string& soundId)
{
SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end())
@ -371,7 +371,7 @@ namespace MWSound
}
}
void SoundManager::stopSound3D(MWWorld::Ptr ptr)
void SoundManager::stopSound3D(const MWWorld::Ptr &ptr)
{
SoundMap::iterator snditer = mActiveSounds.begin();
while(snditer != mActiveSounds.end())
@ -418,7 +418,7 @@ namespace MWSound
}
}
bool SoundManager::getSoundPlaying(MWWorld::Ptr ptr, const std::string& soundId) const
bool SoundManager::getSoundPlaying(const MWWorld::Ptr &ptr, const std::string& soundId) const
{
return isPlaying(ptr, soundId);
}

@ -14,8 +14,6 @@
#include "../mwbase/soundmanager.hpp"
#include "../mwworld/ptr.hpp"
namespace MWSound
{
class Sound_Output;
@ -57,7 +55,7 @@ namespace MWSound
std::string lookup(const std::string &soundId,
float &volume, float &min, float &max);
void streamMusicFull(const std::string& filename);
bool isPlaying(MWWorld::Ptr ptr, const std::string &id) const;
bool isPlaying(const MWWorld::Ptr &ptr, const std::string &id) const;
void updateSounds(float duration);
void updateRegionSound(float duration);
@ -93,7 +91,7 @@ namespace MWSound
///< Start playing music from the selected folder
/// \param name of the folder that contains the playlist
virtual void say(MWWorld::Ptr reference, const std::string& filename);
virtual void say(const MWWorld::Ptr &reference, const std::string& filename);
///< Make an actor say some text.
/// \param filename name of a sound file in "Sound/" in the data directory.
@ -101,10 +99,10 @@ namespace MWSound
///< Say some text, without an actor ref
/// \param filename name of a sound file in "Sound/" in the data directory.
virtual bool sayDone(MWWorld::Ptr reference=MWWorld::Ptr()) const;
virtual bool sayDone(const MWWorld::Ptr &reference=MWWorld::Ptr()) const;
///< Is actor not speaking?
virtual void stopSay(MWWorld::Ptr reference=MWWorld::Ptr());
virtual void stopSay(const MWWorld::Ptr &reference=MWWorld::Ptr());
///< Stop an actor speaking
virtual MWBase::SoundPtr playTrack(const DecoderPtr& decoder, PlayType type);
@ -113,14 +111,14 @@ namespace MWSound
virtual MWBase::SoundPtr playSound(const std::string& soundId, float volume, float pitch, PlayMode mode=Play_Normal);
///< Play a sound, independently of 3D-position
virtual MWBase::SoundPtr playSound3D(MWWorld::Ptr reference, const std::string& soundId,
virtual MWBase::SoundPtr playSound3D(const MWWorld::Ptr &reference, const std::string& soundId,
float volume, float pitch, PlayMode mode=Play_Normal);
///< Play a sound from an object
virtual void stopSound3D(MWWorld::Ptr reference, const std::string& soundId);
virtual void stopSound3D(const MWWorld::Ptr &reference, const std::string& soundId);
///< Stop the given object from playing the given sound,
virtual void stopSound3D(MWWorld::Ptr reference);
virtual void stopSound3D(const MWWorld::Ptr &reference);
///< Stop the given object from playing all sounds.
virtual void stopSound(const MWWorld::CellStore *cell);
@ -129,7 +127,7 @@ namespace MWSound
virtual void stopSound(const std::string& soundId);
///< Stop a non-3d looping sound
virtual bool getSoundPlaying(MWWorld::Ptr reference, const std::string& soundId) const;
virtual bool getSoundPlaying(const MWWorld::Ptr &reference, const std::string& soundId) const;
///< Is the given sound currently playing on the given object?
virtual void pauseSounds(int types=Play_TypeMask);

@ -1,5 +1,6 @@
#include "scene.hpp"
#include <components/nif/nif_file.hpp>
#include "../mwbase/environment.hpp"
#include "../mwbase/world.hpp" /// FIXME

@ -31,150 +31,30 @@
#include "../files/constrainedfiledatastream.hpp"
namespace
{
using namespace Ogre;
using namespace Bsa;
struct PathPatternMatcher
{
PathPatternMatcher (char const * pattern) : pattern (pattern)
{
}
bool operator () (char const * input)
{
char const * p = pattern;
char const * i = input;
while (*p && *i)
{
if (*p == '*')
{
++p;
while (*i && *i != *p && *i != '/' && *i != '\\')
++i;
}
else
if (*p == '?')
{
if (*i == '/' || *i == '\\')
break;
++i, ++p;
}
if (*p == '/' || *p == '\\')
{
if (*i != '/' && *i != '\\')
break;
++i, ++p;
}
else
{
if (*i != *p)
break;
++i, ++p;
}
}
return *p == 0 && *i == 0;
}
private:
char const * pattern;
};
static bool fsstrict = false;
struct FileNameGatherer
static char strict_normalize_char(char ch)
{
StringVectorPtr ptr;
FileNameGatherer (StringVectorPtr ptr) : ptr (ptr)
{
}
void operator () (std::string const & filename) const
{
ptr->push_back (filename);
}
};
return ch == '\\' ? '/' : ch;
}
struct FileInfoGatherer
static char nonstrict_normalize_char(char ch)
{
Archive const * archive;
FileInfoListPtr ptr;
FileInfoGatherer (Archive const * archive, FileInfoListPtr ptr) :
archive (archive), ptr (ptr)
{
}
void operator () (std::string filename) const
{
FileInfo fi;
std::size_t pt = filename.rfind ('/');
if (pt == std::string::npos)
pt = 0;
fi.archive = const_cast <Archive *> (archive);
fi.path = filename.substr (0, pt);
fi.filename = filename.substr (pt);
fi.compressedSize = fi.uncompressedSize = 0;
ptr->push_back(fi);
}
};
return ch == '\\' ? '/' : std::tolower(ch);
}
template <typename file_iterator, typename filename_extractor, typename match_handler>
void matchFiles (bool recursive, std::string const & pattern, file_iterator begin, file_iterator end, filename_extractor filenameExtractor, match_handler matchHandler)
template<typename T1, typename T2>
static std::string normalize_path(T1 begin, T2 end)
{
if (recursive && pattern == "*")
{
for (file_iterator i = begin; i != end; ++i)
matchHandler (filenameExtractor (*i));
}
else
{
PathPatternMatcher matcher (pattern.c_str ());
if (recursive)
{
for (file_iterator i = begin; i != end; ++i)
{
char const * filename = filenameExtractor (*i);
char const * matchable_part = filename;
for (char const * j = matchable_part; *j; ++j)
{
if (*j == '/' || *j == '\\')
matchable_part = j + 1;
}
if (matcher (matchable_part))
matchHandler (filename);
}
}
else
{
for (file_iterator i = begin; i != end; ++i)
{
char const * filename = filenameExtractor (*i);
if (matcher (filename))
matchHandler (filename);
}
}
}
std::string normalized;
normalized.reserve(std::distance(begin, end));
char (*normalize_char)(char) = fsstrict ? &strict_normalize_char : &nonstrict_normalize_char;
std::transform(begin, end, std::back_inserter(normalized), normalize_char);
return normalized;
}
static bool fsstrict = false;
/// An OGRE Archive wrapping a BSAFile archive
class DirArchive: public Ogre::Archive
{
@ -182,37 +62,12 @@ class DirArchive: public Ogre::Archive
index mIndex;
static char strict_normalize_char(char ch)
{
return ch == '\\' ? '/' : ch;
}
static char nonstrict_normalize_char(char ch)
{
return ch == '\\' ? '/' : std::tolower (ch);
}
static std::string normalize_path (std::string::const_iterator begin, std::string::const_iterator end)
{
std::string normalized;
normalized.reserve (end-begin);
char (*normalize_char) (char) = fsstrict ? &strict_normalize_char : &nonstrict_normalize_char;
std::transform (begin, end, std::back_inserter (normalized), normalize_char);
return normalized;
}
index::const_iterator lookup_filename (std::string const & filename) const
{
std::string normalized = normalize_path (filename.begin (), filename.end ());
return mIndex.find (normalized);
}
static char const * extractFilename (index::value_type const & entry)
{
return entry.first.c_str ();
}
public:
DirArchive(const String& name)
@ -273,15 +128,20 @@ public:
StringVectorPtr find(const String& pattern, bool recursive = true,
bool dirs = false)
{
std::string normalizedPattern = normalize_path (pattern.begin (), pattern.end ());
std::string normalizedPattern = normalize_path(pattern.begin(), pattern.end());
StringVectorPtr ptr = StringVectorPtr(new StringVector());
matchFiles (recursive, normalizedPattern, mIndex.begin (), mIndex.end (), extractFilename, FileNameGatherer (ptr));
for(index::const_iterator iter = mIndex.begin();iter != mIndex.end();iter++)
{
if(Ogre::StringUtil::match(iter->first, normalizedPattern) ||
(recursive && Ogre::StringUtil::match(iter->first, "*/"+normalizedPattern)))
ptr->push_back(iter->first);
}
return ptr;
}
bool exists(const String& filename)
{
return lookup_filename (filename) != mIndex.end ();
return lookup_filename(filename) != mIndex.end ();
}
time_t getModifiedTime(const String&) { return 0; }
@ -289,21 +149,44 @@ public:
FileInfoListPtr findFileInfo(const String& pattern, bool recursive = true,
bool dirs = false) const
{
std::string normalizedPattern = normalize_path(pattern.begin(), pattern.end());
FileInfoListPtr ptr = FileInfoListPtr(new FileInfoList());
FileInfoGatherer gatherer (this, ptr);
std::string normalizedPattern = normalize_path (pattern.begin (), pattern.end ());
index::const_iterator i = mIndex.find(normalizedPattern);
if(i != mIndex.end())
{
std::string::size_type pt = i->first.rfind('/');
if(pt == std::string::npos)
pt = 0;
index::const_iterator i = mIndex.find (normalizedPattern);
FileInfo fi;
fi.archive = const_cast<DirArchive*>(this);
fi.path = i->first.substr(0, pt);
fi.filename = i->first.substr((i->first[pt]=='/') ? pt+1 : pt);
fi.compressedSize = fi.uncompressedSize = 0;
if (i != mIndex.end ())
{
gatherer (i->first);
ptr->push_back(fi);
}
else
{
for(index::const_iterator iter = mIndex.begin();iter != mIndex.end();iter++)
{
if(Ogre::StringUtil::match(iter->first, normalizedPattern) ||
(recursive && Ogre::StringUtil::match(iter->first, "*/"+normalizedPattern)))
{
std::string::size_type pt = iter->first.rfind('/');
if(pt == std::string::npos)
pt = 0;
FileInfo fi;
fi.archive = const_cast<DirArchive*>(this);
fi.path = iter->first.substr(0, pt);
fi.filename = iter->first.substr((iter->first[pt]=='/') ? pt+1 : pt);
fi.compressedSize = fi.uncompressedSize = 0;
matchFiles (recursive, normalizedPattern, mIndex.begin (), mIndex.end (), extractFilename, gatherer);
ptr->push_back(fi);
}
}
}
return ptr;
@ -312,9 +195,9 @@ public:
class BSAArchive : public Archive
{
BSAFile arc;
Bsa::BSAFile arc;
static char const * extractFilename (BSAFile::FileStruct const & entry)
static const char *extractFilename(const Bsa::BSAFile::FileStruct &entry)
{
return entry.name;
}
@ -330,13 +213,13 @@ public:
void load() {}
void unload() {}
DataStreamPtr open(const String& filename, bool recursive = true) const
DataStreamPtr open(const String& filename, bool readonly = true) const
{
// Get a non-const reference to arc. This is a hack and it's all
// OGRE's fault. You should NOT expect an open() command not to
// have any side effects on the archive, and hence this function
// should not have been declared const in the first place.
BSAFile *narc = const_cast<BSAFile*>(&arc);
Bsa::BSAFile *narc = const_cast<Bsa::BSAFile*>(&arc);
// Open the file
return narc->getFile(filename.c_str());
@ -360,32 +243,51 @@ public:
return findFileInfo ("*", recursive, dirs);
}
// After load() is called, find("*") is called once. It doesn't seem
// to matter that we return an empty list, exists() gets called on
// the correct files anyway.
StringVectorPtr find(const String& pattern, bool recursive = true,
bool dirs = false)
{
StringVectorPtr find(const String& pattern, bool recursive = true,
bool dirs = false)
{
std::string normalizedPattern = normalize_path(pattern.begin(), pattern.end());
const Bsa::BSAFile::FileList &filelist = arc.getList();
StringVectorPtr ptr = StringVectorPtr(new StringVector());
matchFiles (recursive, pattern, arc.getList ().begin (), arc.getList ().end (), extractFilename, FileNameGatherer (ptr));
for(Bsa::BSAFile::FileList::const_iterator iter = filelist.begin();iter != filelist.end();iter++)
{
std::string ent = normalize_path(iter->name, iter->name+std::strlen(iter->name));
if(Ogre::StringUtil::match(ent, normalizedPattern) ||
(recursive && Ogre::StringUtil::match(ent, "*/"+normalizedPattern)))
ptr->push_back(iter->name);
}
return ptr;
}
}
FileInfoListPtr findFileInfo(const String& pattern, bool recursive = true,
bool dirs = false) const
{
std::string normalizedPattern = normalize_path(pattern.begin(), pattern.end());
FileInfoListPtr ptr = FileInfoListPtr(new FileInfoList());
const Bsa::BSAFile::FileList &filelist = arc.getList();
/* Gets called once for each of the ogre formats, *.program,
*.material etc. We ignore all these.
for(Bsa::BSAFile::FileList::const_iterator iter = filelist.begin();iter != filelist.end();iter++)
{
std::string ent = normalize_path(iter->name, iter->name+std::strlen(iter->name));
if(Ogre::StringUtil::match(ent, normalizedPattern) ||
(recursive && Ogre::StringUtil::match(ent, "*/"+normalizedPattern)))
{
std::string::size_type pt = ent.rfind('/');
if(pt == std::string::npos)
pt = 0;
However, it's also called by MyGUI to find individual textures,
and we can't ignore these since many of the GUI textures are
located in BSAs. So instead we channel it through exists() and
set up a single-element result list if the file is found.
*/
FileInfoListPtr findFileInfo(const String& pattern, bool recursive = true,
bool dirs = false) const
{
FileInfoListPtr ptr = FileInfoListPtr(new FileInfoList());
matchFiles (recursive, pattern, arc.getList ().begin (), arc.getList ().end (), extractFilename, FileInfoGatherer (this, ptr));
return ptr;
}
FileInfo fi;
fi.archive = const_cast<BSAArchive*>(this);
fi.path = std::string(iter->name, pt);
fi.filename = std::string(iter->name + ((ent[pt]=='/') ? pt+1 : pt));
fi.compressedSize = fi.uncompressedSize = iter->fileSize;
ptr->push_back(fi);
}
}
return ptr;
}
};
// An archive factory for BSA archives
@ -445,7 +347,6 @@ static void insertDirFactory()
}
}
}
namespace Bsa
{

Loading…
Cancel
Save