refactored NIFFile parse to get better code/data seperation

actorid
Nathan Jeffords 12 years ago
parent 6de6d9ff6e
commit 0ed2015319

@ -185,6 +185,101 @@ NIFFile::~NIFFile()
delete records[i];
}
template <typename NodeType> static Record* construct() { return new NodeType; }
struct RecordFactoryEntry {
typedef Record* (*create_t) ();
char const * mName;
create_t mCreate;
RecordType mType;
};
/* These are all the record types we know how to read.
This can be heavily optimized later if needed. For example, a
hash table or a FSM-based parser could be used to look up
node names.
*/
static const RecordFactoryEntry recordFactories [] = {
{ "NiNode", &construct <NiNode >, RC_NiNode },
{ "AvoidNode", &construct <NiNode >, RC_NiNode },
{ "NiBSParticleNode", &construct <NiNode >, RC_NiNode },
{ "NiBSAnimationNode", &construct <NiNode >, RC_NiNode },
{ "NiBillboardNode", &construct <NiNode >, RC_NiNode },
{ "NiTriShape", &construct <NiTriShape >, RC_NiTriShape },
{ "NiRotatingParticles", &construct <NiRotatingParticles >, RC_NiRotatingParticles },
{ "NiAutoNormalParticles", &construct <NiAutoNormalParticles >, RC_NiAutoNormalParticles },
{ "NiCamera", &construct <NiCamera >, RC_NiCamera },
{ "RootCollisionNode", &construct <NiNode >, RC_RootCollisionNode },
{ "NiTexturingProperty", &construct <NiTexturingProperty >, RC_NiTexturingProperty },
{ "NiMaterialProperty", &construct <NiMaterialProperty >, RC_NiMaterialProperty },
{ "NiZBufferProperty", &construct <NiZBufferProperty >, RC_NiZBufferProperty },
{ "NiAlphaProperty", &construct <NiAlphaProperty >, RC_NiAlphaProperty },
{ "NiVertexColorProperty", &construct <NiVertexColorProperty >, RC_NiVertexColorProperty },
{ "NiShadeProperty", &construct <NiShadeProperty >, RC_NiShadeProperty },
{ "NiDitherProperty", &construct <NiDitherProperty >, RC_NiDitherProperty },
{ "NiWireframeProperty", &construct <NiWireframeProperty >, RC_NiWireframeProperty },
{ "NiSpecularProperty", &construct <NiSpecularProperty >, RC_NiSpecularProperty },
{ "NiStencilProperty", &construct <NiStencilProperty >, RC_NiStencilProperty },
{ "NiVisController", &construct <NiVisController >, RC_NiVisController },
{ "NiGeomMorpherController", &construct <NiGeomMorpherController >, RC_NiGeomMorpherController },
{ "NiKeyframeController", &construct <NiKeyframeController >, RC_NiKeyframeController },
{ "NiAlphaController", &construct <NiAlphaController >, RC_NiAlphaController },
{ "NiUVController", &construct <NiUVController >, RC_NiUVController },
{ "NiPathController", &construct <NiPathController >, RC_NiPathController },
{ "NiMaterialColorController", &construct <NiMaterialColorController >, RC_NiMaterialColorController },
{ "NiBSPArrayController", &construct <NiBSPArrayController >, RC_NiBSPArrayController },
{ "NiParticleSystemController", &construct <NiParticleSystemController >, RC_NiParticleSystemController },
{ "NiAmbientLight", &construct <NiLight >, RC_NiLight },
{ "NiDirectionalLight", &construct <NiLight >, RC_NiLight },
{ "NiTextureEffect", &construct <NiTextureEffect >, RC_NiTextureEffect },
{ "NiVertWeightsExtraData", &construct <NiVertWeightsExtraData >, RC_NiVertWeightsExtraData },
{ "NiTextKeyExtraData", &construct <NiTextKeyExtraData >, RC_NiTextKeyExtraData },
{ "NiStringExtraData", &construct <NiStringExtraData >, RC_NiStringExtraData },
{ "NiGravity", &construct <NiGravity >, RC_NiGravity },
{ "NiPlanarCollider", &construct <NiPlanarCollider >, RC_NiPlanarCollider },
{ "NiParticleGrowFade", &construct <NiParticleGrowFade >, RC_NiParticleGrowFade },
{ "NiParticleColorModifier", &construct <NiParticleColorModifier >, RC_NiParticleColorModifier },
{ "NiParticleRotation", &construct <NiParticleRotation >, RC_NiParticleRotation },
{ "NiFloatData", &construct <NiFloatData >, RC_NiFloatData },
{ "NiTriShapeData", &construct <NiTriShapeData >, RC_NiTriShapeData },
{ "NiVisData", &construct <NiVisData >, RC_NiVisData },
{ "NiColorData", &construct <NiColorData >, RC_NiColorData },
{ "NiPixelData", &construct <NiPixelData >, RC_NiPixelData },
{ "NiMorphData", &construct <NiMorphData >, RC_NiMorphData },
{ "NiKeyframeData", &construct <NiKeyframeData >, RC_NiKeyframeData },
{ "NiSkinData", &construct <NiSkinData >, RC_NiSkinData },
{ "NiUVData", &construct <NiUVData >, RC_NiUVData },
{ "NiPosData", &construct <NiPosData >, RC_NiPosData },
{ "NiRotatingParticlesData", &construct <NiRotatingParticlesData >, RC_NiRotatingParticlesData },
{ "NiAutoNormalParticlesData", &construct <NiAutoNormalParticlesData >, RC_NiAutoNormalParticlesData },
{ "NiSequenceStreamHelper", &construct <NiSequenceStreamHelper >, RC_NiSequenceStreamHelper },
{ "NiSourceTexture", &construct <NiSourceTexture >, RC_NiSourceTexture },
{ "NiSkinInstance", &construct <NiSkinInstance >, RC_NiSkinInstance },
};
static RecordFactoryEntry const * recordFactories_begin = &recordFactories [0];
static RecordFactoryEntry const * recordFactories_end = &recordFactories [sizeof (recordFactories) / sizeof (recordFactories[0])];
RecordFactoryEntry const * lookupRecordFactory (char const * name)
{
RecordFactoryEntry const * i;
for (i = recordFactories_begin; i != recordFactories_end; ++i)
if (strcmp (name, i->mName) == 0)
break;
if (i == recordFactories_end)
return NULL;
return i;
}
/* This file implements functions from the NIFFile class. It is also
where we stash all the functions we couldn't add as inline
definitions in the record types.
@ -223,88 +318,15 @@ void NIFFile::parse()
std::string rec = nif.getString();
/* These are all the record types we know how to read.
This can be heavily optimized later if needed. For example, a
hash table or a FSM-based parser could be used to look up
node names.
*/
// NiNodes
if(rec == "NiNode" || rec == "AvoidNode" ||
rec == "NiBSParticleNode" ||
rec == "NiBSAnimationNode" ||
rec == "NiBillboardNode") { r = new NiNode; r->recType = RC_NiNode; }
// Other nodes
else if(rec == "NiTriShape") { r = new NiTriShape; r->recType = RC_NiTriShape; }
else if(rec == "NiRotatingParticles") { r = new NiRotatingParticles; r->recType = RC_NiRotatingParticles; }
else if(rec == "NiAutoNormalParticles") { r = new NiAutoNormalParticles; r->recType = RC_NiAutoNormalParticles; }
else if(rec == "NiCamera") { r = new NiCamera; r->recType = RC_NiCamera; }
else if(rec == "RootCollisionNode"){ r = new NiNode; r->recType = RC_RootCollisionNode; }// a root collision node is exactly like a node
//that's why there is no need to create a new type
// Properties
else if(rec == "NiTexturingProperty") { r = new NiTexturingProperty; r->recType = RC_NiTexturingProperty; }
else if(rec == "NiMaterialProperty") { r = new NiMaterialProperty; r->recType = RC_NiMaterialProperty; }
else if(rec == "NiZBufferProperty") { r = new NiZBufferProperty; r->recType = RC_NiZBufferProperty; }
else if(rec == "NiAlphaProperty") { r = new NiAlphaProperty; r->recType = RC_NiAlphaProperty; }
else if(rec == "NiVertexColorProperty") { r = new NiVertexColorProperty; r->recType = RC_NiVertexColorProperty; }
else if(rec == "NiShadeProperty") { r = new NiShadeProperty; r->recType = RC_NiShadeProperty; }
else if(rec == "NiDitherProperty") { r = new NiDitherProperty; r->recType = RC_NiDitherProperty; }
else if(rec == "NiWireframeProperty") { r = new NiWireframeProperty; r->recType = RC_NiWireframeProperty; }
else if(rec == "NiSpecularProperty") { r = new NiSpecularProperty; r->recType = RC_NiSpecularProperty; }
else if(rec == "NiStencilProperty") { r = new NiStencilProperty; r->recType = RC_NiStencilProperty; }
// Controllers
else if(rec == "NiVisController") { r = new NiVisController; r->recType = RC_NiVisController; }
else if(rec == "NiGeomMorpherController") { r = new NiGeomMorpherController; r->recType = RC_NiGeomMorpherController; }
else if(rec == "NiKeyframeController") { r = new NiKeyframeController; r->recType = RC_NiKeyframeController; }
else if(rec == "NiAlphaController") { r = new NiAlphaController; r->recType = RC_NiAlphaController; }
else if(rec == "NiUVController") { r = new NiUVController; r->recType = RC_NiUVController; }
else if(rec == "NiPathController") { r = new NiPathController; r->recType = RC_NiPathController; }
else if(rec == "NiMaterialColorController") { r = new NiMaterialColorController; r->recType = RC_NiMaterialColorController; }
else if(rec == "NiBSPArrayController") { r = new NiBSPArrayController; r->recType = RC_NiBSPArrayController; }
else if(rec == "NiParticleSystemController") { r = new NiParticleSystemController; r->recType = RC_NiParticleSystemController; }
// Effects
else if(rec == "NiAmbientLight" ||
rec == "NiDirectionalLight") { r = new NiLight; r->recType = RC_NiLight; }
else if(rec == "NiTextureEffect") { r = new NiTextureEffect; r->recType = RC_NiTextureEffect; }
// Extra Data
else if(rec == "NiVertWeightsExtraData") { r = new NiVertWeightsExtraData; r->recType = RC_NiVertWeightsExtraData; }
else if(rec == "NiTextKeyExtraData") { r = new NiTextKeyExtraData; r->recType = RC_NiTextKeyExtraData; }
else if(rec == "NiStringExtraData") { r = new NiStringExtraData; r->recType = RC_NiStringExtraData; }
else if(rec == "NiGravity") { r = new NiGravity; r->recType = RC_NiGravity; }
else if(rec == "NiPlanarCollider") { r = new NiPlanarCollider; r->recType = RC_NiPlanarCollider; }
else if(rec == "NiParticleGrowFade") { r = new NiParticleGrowFade; r->recType = RC_NiParticleGrowFade; }
else if(rec == "NiParticleColorModifier") { r = new NiParticleColorModifier; r->recType = RC_NiParticleColorModifier; }
else if(rec == "NiParticleRotation") { r = new NiParticleRotation; r->recType = RC_NiParticleRotation; }
// Data
else if(rec == "NiFloatData") { r = new NiFloatData; r->recType = RC_NiFloatData; }
else if(rec == "NiTriShapeData") { r = new NiTriShapeData; r->recType = RC_NiTriShapeData; }
else if(rec == "NiVisData") { r = new NiVisData; r->recType = RC_NiVisData; }
else if(rec == "NiColorData") { r = new NiColorData; r->recType = RC_NiColorData; }
else if(rec == "NiPixelData") { r = new NiPixelData; r->recType = RC_NiPixelData; }
else if(rec == "NiMorphData") { r = new NiMorphData; r->recType = RC_NiMorphData; }
else if(rec == "NiKeyframeData") { r = new NiKeyframeData; r->recType = RC_NiKeyframeData; }
else if(rec == "NiSkinData") { r = new NiSkinData; r->recType = RC_NiSkinData; }
else if(rec == "NiUVData") { r = new NiUVData; r->recType = RC_NiUVData; }
else if(rec == "NiPosData") { r = new NiPosData; r->recType = RC_NiPosData; }
else if(rec == "NiRotatingParticlesData") { r = new NiRotatingParticlesData; r->recType = RC_NiRotatingParticlesData; }
else if(rec == "NiAutoNormalParticlesData") { r = new NiAutoNormalParticlesData; r->recType = RC_NiAutoNormalParticlesData; }
// Other
else if(rec == "NiSequenceStreamHelper") { r = new NiSequenceStreamHelper; r->recType = RC_NiSequenceStreamHelper; }
else if(rec == "NiSourceTexture") { r = new NiSourceTexture; r->recType = RC_NiSourceTexture; }
else if(rec == "NiSkinInstance") { r = new NiSkinInstance; r->recType = RC_NiSkinInstance; }
// Failure
RecordFactoryEntry const * entry = lookupRecordFactory (rec.c_str ());
if (entry != NULL)
{
r = entry->mCreate ();
r->recType = entry->mType;
}
else
fail("Unknown record type " + rec);
fail("Unknown record type " + rec);
assert(r != NULL);
assert(r->recType != RC_MISSING);

Loading…
Cancel
Save