reimplement the state pointer serializer.

This commit is contained in:
Christoph Oelckers 2023-10-18 19:05:59 +02:00
parent 0aaefceb04
commit 19f52dc1c2

View file

@ -35,10 +35,6 @@ BEGIN_BLD_NS
void validateLinks(); void validateLinks();
#if 0 // state serialization will be reactivated later when the rest is working.
// name, type, duration, trigger, enter, move, think, next
// AISTATE "genIdle", "+0", 1, 0, null, null, null, null, "none";
#ifdef NOONE_EXTENSIONS #ifdef NOONE_EXTENSIONS
// Serializing states is a lot more tricky for custom dudes. // Serializing states is a lot more tricky for custom dudes.
// Note that this makes no assumptions about the relationship between actor and dude because at restoration this isn't known. // Note that this makes no assumptions about the relationship between actor and dude because at restoration this isn't known.
@ -49,19 +45,6 @@ struct AIStateRep
}; };
static AIStateRep makeStateRep(AISTATE* state) static AIStateRep makeStateRep(AISTATE* state)
{ {
int i = 0;
if (state == nullptr) return { nullptr, -1 };
for (auto cstate : allAIStates)
{
if (state == cstate)
{
return { nullptr, i };
}
i++;
}
if (gModernMap)
{
// now it gets ugly: the custom dudes each have a copied set of states. Find out which one. // now it gets ugly: the custom dudes each have a copied set of states. Find out which one.
BloodSpriteIterator it; BloodSpriteIterator it;
while (auto actor = it.Next()) while (auto actor = it.Next())
@ -80,102 +63,55 @@ static AIStateRep makeStateRep(AISTATE* state)
} }
} }
} }
} // this should never happen.
Printf(PRINT_HIGH, "Attempt to save invalid state!\n"); // we got no further info here, sorry! Printf(PRINT_HIGH, "Attempt to save invalid state!\n"); // we got no further info here, sorry!
return { nullptr, -1 }; return { nullptr, -1 };
} }
static AISTATE* getStateFromRep(AIStateRep* rep) #endif
{
if (rep->owner == nullptr)
{
int i = rep->index;
if (i >= 0 && i < countof(allAIStates))
{
return allAIStates[i];
}
else
{
return nullptr;
}
}
else if (gModernMap)
{
// at this point the object may not have been deserialized but it definitely has been allocated so we can just take the address.
AISTATE* state = (AISTATE*)rep->owner->states;
return state + rep->index;
}
else return nullptr;
}
FSerializer& Serialize(FSerializer& arc, const char* keyname, AIStateRep& w, AIStateRep* def) FSerializer& Serialize(FSerializer& arc, const char* keyname, AISTATE*& w, AISTATE** def)
{ {
unsigned i = 0;
if (arc.BeginObject(keyname)) if (arc.BeginObject(keyname))
{ {
arc("object", w.owner)
("index", w.index)
.EndObject();
}
return arc;
}
FSerializer& Serialize(FSerializer& arc, const char* keyname, AISTATE*& w, AISTATE** def)
{
unsigned i = 0;
if (arc.isWriting()) if (arc.isWriting())
{ {
#ifdef NOONE_EXTENSIONS
if (w && w->name != NAME_None && gModernMap)
{
auto rep = makeStateRep(w); auto rep = makeStateRep(w);
arc(keyname, rep); arc("object", rep.owner)
} ("index", rep.index);
else
{
AIStateRep rep;
arc(keyname, rep);
w = getStateFromRep(&rep);
}
return arc;
}
#else
FSerializer& Serialize(FSerializer& arc, const char* keyname, AISTATE*& w, AISTATE** def)
{
unsigned i = 0;
if (arc.isWriting())
{
if (def && w == *def) return arc;
for (auto cstate : allAIStates)
{
if (w == cstate)
{
arc(keyname, i);
return arc;
}
i++;
}
} }
else else
#endif
{ {
arc(keyname, i); FName name = w ? w->name : NAME_None;
if (i < countof(allAIStates)) arc("name", name);
{ }
w = allAIStates[i];
} }
else else
{ {
w = nullptr; w = nullptr;
FName name = NAME_None;
arc("name", name);
#ifdef NOONE_EXTENSIONS
if (name == NAME_None && gModernMap)
{
AIStateRep rep{};
arc("object", rep.owner)
("index", rep.index);
w = rep.owner->states[0] + rep.index;
} }
#endif
}
arc.EndObject();
} }
return arc; return arc;
} }
#endif
#else
FSerializer& Serialize(FSerializer& arc, const char* keyname, AISTATE*& w, AISTATE** def)
{
return arc;
}
#endif
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
// //