mirror of
https://gitlab.com/OpenMW/openmw.git
synced 2025-01-25 06:35:30 +00:00
Use Ogre data streams for loading NIFs
This commit is contained in:
parent
0143cacd2b
commit
b3aa453f9a
@ -24,9 +24,8 @@
|
||||
#ifndef _NIF_FILE_H_
|
||||
#define _NIF_FILE_H_
|
||||
|
||||
#include <libs/mangle/stream/stream.hpp>
|
||||
#include <libs/mangle/stream/filters/buffer_stream.hpp>
|
||||
#include <components/misc/slice_array.hpp>
|
||||
#include <OgreResourceGroupManager.h>
|
||||
#include <OgreDataStream.h>
|
||||
|
||||
#include <stdexcept>
|
||||
#include <vector>
|
||||
@ -36,8 +35,6 @@
|
||||
#include "record.hpp"
|
||||
#include "nif_types.hpp"
|
||||
|
||||
using namespace Mangle::Stream;
|
||||
|
||||
namespace Nif
|
||||
{
|
||||
|
||||
@ -51,7 +48,7 @@ class NIFFile
|
||||
int ver;
|
||||
|
||||
/// Input stream
|
||||
StreamPtr inp;
|
||||
Ogre::DataStreamPtr inp;
|
||||
|
||||
/// File name, used for error messages
|
||||
std::string filename;
|
||||
@ -72,22 +69,10 @@ public:
|
||||
}
|
||||
|
||||
/// Open a NIF stream. The name is used for error messages.
|
||||
NIFFile(StreamPtr nif, const std::string &name)
|
||||
NIFFile(const std::string &name)
|
||||
: filename(name)
|
||||
{
|
||||
/* Load the entire file into memory. This allows us to use
|
||||
direct pointers to the data arrays in the NIF, instead of
|
||||
individually allocating and copying each one.
|
||||
|
||||
The NIF data is only stored temporarily in memory, since once
|
||||
the mesh data is loaded it is siphoned into OGRE and
|
||||
deleted. For that reason, we might improve this further and
|
||||
use a shared region/pool based allocation scheme in the
|
||||
future, especially since only one NIFFile will ever be loaded
|
||||
at any given time.
|
||||
*/
|
||||
inp = StreamPtr(new BufferStream(nif));
|
||||
|
||||
inp = Ogre::ResourceGroupManager::getSingleton().openResource(name);
|
||||
parse();
|
||||
}
|
||||
|
||||
@ -112,11 +97,14 @@ public:
|
||||
Parser functions
|
||||
****************************************************/
|
||||
|
||||
void skip(size_t size) { inp->getPtr(size); }
|
||||
void skip(size_t size) { inp->skip(size); }
|
||||
|
||||
template<class X> X getType()
|
||||
{
|
||||
return *(const X*)inp->getPtr(sizeof(X));
|
||||
X obj;
|
||||
if(inp->read(&obj, sizeof(X)) != sizeof(X))
|
||||
fail("Failed to read from NIF");
|
||||
return obj;
|
||||
}
|
||||
unsigned short getShort() { return getType<unsigned short>(); }
|
||||
int getInt() { return getType<int>(); }
|
||||
@ -127,7 +115,8 @@ public:
|
||||
std::vector<X> getArrayLen(int num)
|
||||
{
|
||||
std::vector<X> v(num);
|
||||
memcpy(&v[0], inp->getPtr(num*sizeof(X)), num*sizeof(X));
|
||||
if(inp->read(&v[0], num*sizeof(X)) != num*sizeof(X))
|
||||
fail("Failed to read from NIF");
|
||||
return v;
|
||||
}
|
||||
|
||||
@ -151,7 +140,8 @@ public:
|
||||
{
|
||||
std::string str;
|
||||
str.resize(size);
|
||||
memcpy(&str[0], inp->getPtr(size), size);
|
||||
if(inp->read(&str[0], size) != size)
|
||||
fail("Failed to read from NIF");
|
||||
return str.substr(0, str.find('\0'));
|
||||
}
|
||||
std::string getString()
|
||||
|
@ -25,7 +25,6 @@ http://www.gnu.org/licenses/ .
|
||||
#include <Ogre.h>
|
||||
#include <stdio.h>
|
||||
|
||||
#include <libs/mangle/vfs/servers/ogre_vfs.hpp>
|
||||
#include "../nif/nif_file.hpp"
|
||||
#include "../nif/node.hpp"
|
||||
#include "../nif/data.hpp"
|
||||
@ -47,13 +46,11 @@ typedef unsigned char ubyte;
|
||||
using namespace std;
|
||||
using namespace Ogre;
|
||||
using namespace Nif;
|
||||
using namespace Mangle::VFS;
|
||||
|
||||
using namespace NifBullet;
|
||||
|
||||
ManualBulletShapeLoader::~ManualBulletShapeLoader()
|
||||
{
|
||||
delete vfs;
|
||||
}
|
||||
|
||||
Ogre::Matrix3 ManualBulletShapeLoader::getMatrix(Nif::Transformation* tr)
|
||||
@ -94,20 +91,11 @@ void ManualBulletShapeLoader::loadResource(Ogre::Resource *resource)
|
||||
|
||||
mTriMesh = new btTriangleMesh();
|
||||
|
||||
if (!vfs) vfs = new OgreVFS(resourceGroup);
|
||||
|
||||
if (!vfs->isFile(resourceName))
|
||||
{
|
||||
warn("File not found.");
|
||||
return;
|
||||
}
|
||||
|
||||
// Load the NIF. TODO: Wrap this in a try-catch block once we're out
|
||||
// of the early stages of development. Right now we WANT to catch
|
||||
// every error as early and intrusively as possible, as it's most
|
||||
// likely a sign of incomplete code rather than faulty input.
|
||||
Nif::NIFFile nif(vfs->open(resourceName), resourceName);
|
||||
|
||||
Nif::NIFFile nif(resourceName);
|
||||
if (nif.numRecords() < 1)
|
||||
{
|
||||
warn("Found no records in NIF.");
|
||||
|
@ -50,14 +50,6 @@ namespace Nif
|
||||
class Matrix;
|
||||
}
|
||||
|
||||
namespace Mangle
|
||||
{
|
||||
namespace VFS
|
||||
{
|
||||
class OgreVFS;
|
||||
}
|
||||
}
|
||||
|
||||
namespace NifBullet
|
||||
{
|
||||
|
||||
@ -68,7 +60,7 @@ class ManualBulletShapeLoader : public BulletShapeLoader
|
||||
{
|
||||
public:
|
||||
|
||||
ManualBulletShapeLoader():resourceGroup("General"){vfs = 0;}
|
||||
ManualBulletShapeLoader():resourceGroup("General"){}
|
||||
virtual ~ManualBulletShapeLoader();
|
||||
|
||||
void warn(std::string msg)
|
||||
@ -119,8 +111,6 @@ private:
|
||||
*/
|
||||
void handleNiTriShape(Nif::NiTriShape *shape, int flags,Ogre::Matrix3 parentRot,Ogre::Vector3 parentPos,float parentScales,bool raycastingOnly);
|
||||
|
||||
Mangle::VFS::OgreVFS *vfs;
|
||||
|
||||
std::string resourceName;
|
||||
std::string resourceGroup;
|
||||
|
||||
|
@ -379,16 +379,12 @@ String NIFLoader::getUniqueName(const String &input)
|
||||
// is lost in that case.
|
||||
void NIFLoader::findRealTexture(String &texName)
|
||||
{
|
||||
assert(vfs);
|
||||
if (vfs->isFile(texName)) return;
|
||||
|
||||
int len = texName.size();
|
||||
if (len < 4) return;
|
||||
if(Ogre::ResourceGroupManager::getSingleton().resourceExistsInAnyGroup(texName))
|
||||
return;
|
||||
|
||||
// Change texture extension to .dds
|
||||
texName[len-3] = 'd';
|
||||
texName[len-2] = 'd';
|
||||
texName[len-1] = 's';
|
||||
String::size_type pos = texName.rfind('.');
|
||||
texName.replace(pos, texName.length(), ".dds");
|
||||
}
|
||||
|
||||
//Handle node at top
|
||||
@ -1290,9 +1286,6 @@ void NIFLoader::loadResource(Resource *resource)
|
||||
{
|
||||
calculateTransform();
|
||||
}
|
||||
// Set up the VFS if it hasn't been done already
|
||||
if (!vfs) vfs = new OgreVFS(resourceGroup);
|
||||
|
||||
// Get the mesh
|
||||
mesh = dynamic_cast<Mesh*>(resource);
|
||||
assert(mesh);
|
||||
@ -1301,12 +1294,6 @@ void NIFLoader::loadResource(Resource *resource)
|
||||
resourceName = mesh->getName();
|
||||
//std::cout << resourceName << "\n";
|
||||
|
||||
if (!vfs->isFile(resourceName))
|
||||
{
|
||||
warn("File "+resourceName+" not found.");
|
||||
return;
|
||||
}
|
||||
|
||||
// Helper that computes bounding boxes for us.
|
||||
BoundsFinder bounds;
|
||||
|
||||
@ -1314,8 +1301,7 @@ void NIFLoader::loadResource(Resource *resource)
|
||||
// of the early stages of development. Right now we WANT to catch
|
||||
// every error as early and intrusively as possible, as it's most
|
||||
// likely a sign of incomplete code rather than faulty input.
|
||||
NIFFile nif(vfs->open(resourceName), resourceName);
|
||||
|
||||
NIFFile nif(resourceName);
|
||||
if (nif.numRecords() < 1)
|
||||
{
|
||||
warn("Found no records in NIF.");
|
||||
|
@ -154,13 +154,6 @@ class NIFLoader : Ogre::ManualResourceLoader
|
||||
return resourceName + ".skel";
|
||||
}
|
||||
|
||||
// This is the interface to the Ogre resource system. It allows us to
|
||||
// load NIFs from BSAs, in the file system and in any other place we
|
||||
// tell Ogre to look (eg. in zip or rar files.) It's also used to
|
||||
// check for the existence of texture files, so we can exchange the
|
||||
// extension from .tga to .dds if the texture is missing.
|
||||
Mangle::VFS::OgreVFS *vfs;
|
||||
|
||||
std::string verbosePath;
|
||||
std::string resourceName;
|
||||
std::string resourceGroup;
|
||||
|
Loading…
x
Reference in New Issue
Block a user