diff --git a/src/g_shared/a_specialspot.cpp b/src/g_shared/a_specialspot.cpp index 2797ab70f..f677adc13 100644 --- a/src/g_shared/a_specialspot.cpp +++ b/src/g_shared/a_specialspot.cpp @@ -42,7 +42,6 @@ static FRandom pr_spot ("SpecialSpot"); IMPLEMENT_CLASS(DSpotState, false, false) -IMPLEMENT_CLASS(ASpecialSpot, false, false) TObjPtr DSpotState::SpotState; //---------------------------------------------------------------------------- @@ -54,7 +53,7 @@ TObjPtr DSpotState::SpotState; struct FSpotList { PClassActor *Type; - TArray Spots; + TArray Spots; unsigned Index; int SkipCount; int numcalls; @@ -77,7 +76,7 @@ struct FSpotList // //---------------------------------------------------------------------------- - bool Add(ASpecialSpot *newspot) + bool Add(AActor *newspot) { for(unsigned i = 0; i < Spots.Size(); i++) { @@ -93,7 +92,7 @@ struct FSpotList // //---------------------------------------------------------------------------- - bool Remove(ASpecialSpot *spot) + bool Remove(AActor *spot) { for(unsigned i = 0; i < Spots.Size(); i++) { @@ -113,13 +112,13 @@ struct FSpotList // //---------------------------------------------------------------------------- - ASpecialSpot *GetNextInList(int skipcounter) + AActor *GetNextInList(int skipcounter) { if (Spots.Size() > 0 && ++SkipCount > skipcounter) { SkipCount = 0; - ASpecialSpot *spot = Spots[Index]; + AActor *spot = Spots[Index]; if (++Index >= Spots.Size()) Index = 0; numcalls++; return spot; @@ -133,7 +132,7 @@ struct FSpotList // //---------------------------------------------------------------------------- - ASpecialSpot *GetSpotWithMinMaxDistance(double x, double y, double mindist, double maxdist) + AActor *GetSpotWithMinMaxDistance(double x, double y, double mindist, double maxdist) { if (Spots.Size() == 0) return NULL; int i = pr_spot() % Spots.Size(); @@ -160,7 +159,7 @@ struct FSpotList // //---------------------------------------------------------------------------- - ASpecialSpot *GetRandomSpot(bool onlyfirst) + AActor *GetRandomSpot(bool onlyfirst) { if (Spots.Size() && !numcalls) { @@ -219,8 +218,7 @@ DSpotState::DSpotState () void DSpotState::OnDestroy () { - SpotLists.Clear(); - SpotLists.ShrinkToFit(); + SpotLists.Reset(); SpotState = NULL; Super::OnDestroy(); @@ -270,7 +268,7 @@ FSpotList *DSpotState::FindSpotList(PClassActor *type) // //---------------------------------------------------------------------------- -bool DSpotState::AddSpot(ASpecialSpot *spot) +bool DSpotState::AddSpot(AActor *spot) { FSpotList *list = FindSpotList(spot->GetClass()); if (list != NULL) return list->Add(spot); @@ -283,7 +281,7 @@ bool DSpotState::AddSpot(ASpecialSpot *spot) // //---------------------------------------------------------------------------- -bool DSpotState::RemoveSpot(ASpecialSpot *spot) +bool DSpotState::RemoveSpot(AActor *spot) { FSpotList *list = FindSpotList(spot->GetClass()); if (list != NULL) return list->Remove(spot); @@ -308,7 +306,7 @@ void DSpotState::Serialize(FSerializer &arc) // //---------------------------------------------------------------------------- -ASpecialSpot *DSpotState::GetNextInList(PClassActor *type, int skipcounter) +AActor *DSpotState::GetNextInList(PClassActor *type, int skipcounter) { FSpotList *list = FindSpotList(type); if (list != NULL) return list->GetNextInList(skipcounter); @@ -321,7 +319,7 @@ ASpecialSpot *DSpotState::GetNextInList(PClassActor *type, int skipcounter) // //---------------------------------------------------------------------------- -ASpecialSpot *DSpotState::GetSpotWithMinMaxDistance(PClassActor *type, double x, double y, double mindist, double maxdist) +AActor *DSpotState::GetSpotWithMinMaxDistance(PClassActor *type, double x, double y, double mindist, double maxdist) { FSpotList *list = FindSpotList(type); if (list != NULL) return list->GetSpotWithMinMaxDistance(x, y, mindist, maxdist); @@ -334,34 +332,10 @@ ASpecialSpot *DSpotState::GetSpotWithMinMaxDistance(PClassActor *type, double x, // //---------------------------------------------------------------------------- -ASpecialSpot *DSpotState::GetRandomSpot(PClassActor *type, bool onlyonce) +AActor *DSpotState::GetRandomSpot(PClassActor *type, bool onlyonce) { FSpotList *list = FindSpotList(type); if (list != NULL) return list->GetRandomSpot(onlyonce); return NULL; } -//---------------------------------------------------------------------------- -// -// -// -//---------------------------------------------------------------------------- - -void ASpecialSpot::BeginPlay() -{ - DSpotState *state = DSpotState::GetSpotState(); - if (state != NULL) state->AddSpot(this); -} - -//---------------------------------------------------------------------------- -// -// -// -//---------------------------------------------------------------------------- - -void ASpecialSpot::OnDestroy() -{ - DSpotState *state = DSpotState::GetSpotState(false); - if (state != NULL) state->RemoveSpot(this); - Super::OnDestroy(); -} diff --git a/src/g_shared/a_specialspot.h b/src/g_shared/a_specialspot.h index 4bfef3b63..fee1a804b 100644 --- a/src/g_shared/a_specialspot.h +++ b/src/g_shared/a_specialspot.h @@ -4,17 +4,6 @@ #include "actor.h" #include "tarray.h" -class ASpecialSpot : public AActor -{ - DECLARE_CLASS (ASpecialSpot, AActor) - -public: - - void BeginPlay(); - void OnDestroy() override; -}; - - struct FSpotList; @@ -32,12 +21,12 @@ public: void Tick (); static DSpotState *GetSpotState(bool create = true); FSpotList *FindSpotList(PClassActor *type); - bool AddSpot(ASpecialSpot *spot); - bool RemoveSpot(ASpecialSpot *spot); + bool AddSpot(AActor *spot); + bool RemoveSpot(AActor *spot); void Serialize(FSerializer &arc); - ASpecialSpot *GetNextInList(PClassActor *type, int skipcounter); - ASpecialSpot *GetSpotWithMinMaxDistance(PClassActor *type, double x, double y, double mindist, double maxdist); - ASpecialSpot *GetRandomSpot(PClassActor *type, bool onlyonce = false); + AActor *GetNextInList(PClassActor *type, int skipcounter); + AActor *GetSpotWithMinMaxDistance(PClassActor *type, double x, double y, double mindist, double maxdist); + AActor *GetRandomSpot(PClassActor *type, bool onlyonce = false); }; diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 88a95e3b7..944839130 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -3349,7 +3349,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Teleport) { PARAM_ACTION_PROLOGUE(AActor); PARAM_STATE_ACTION (teleport_state) - PARAM_CLASS (target_type, ASpecialSpot) + PARAM_CLASS (target_type, AActor) PARAM_CLASS (fog_type, AActor) PARAM_INT (flags) PARAM_FLOAT (mindist) diff --git a/src/scripting/vmthunks.cpp b/src/scripting/vmthunks.cpp index 685dc1289..4c8fe81ba 100644 --- a/src/scripting/vmthunks.cpp +++ b/src/scripting/vmthunks.cpp @@ -1883,15 +1883,38 @@ DEFINE_ACTION_FUNCTION_NATIVE(AKey, GetKeyType, P_GetKeyType) // //===================================================================================== -static DSpotState *GetSpotState() -{ - return DSpotState::GetSpotState(); -} -DEFINE_ACTION_FUNCTION_NATIVE(DSpotState, GetSpotState, GetSpotState) +DEFINE_ACTION_FUNCTION_NATIVE(DSpotState, GetSpotState, DSpotState::GetSpotState) { PARAM_PROLOGUE; - ACTION_RETURN_OBJECT(DSpotState::GetSpotState()); + PARAM_BOOL(create); + ACTION_RETURN_OBJECT(DSpotState::GetSpotState(create)); +} + +static void AddSpot(DSpotState *state, AActor *spot) +{ + state->AddSpot(spot); +} + +DEFINE_ACTION_FUNCTION_NATIVE(DSpotState, AddSpot, AddSpot) +{ + PARAM_SELF_PROLOGUE(DSpotState); + PARAM_OBJECT(spot, AActor); + self->AddSpot(spot); + return 0; +} + +static void RemoveSpot(DSpotState *state, AActor *spot) +{ + state->RemoveSpot(spot); +} + +DEFINE_ACTION_FUNCTION_NATIVE(DSpotState, RemoveSpot, RemoveSpot) +{ + PARAM_SELF_PROLOGUE(DSpotState); + PARAM_OBJECT(spot, AActor); + self->RemoveSpot(spot); + return 0; } static AActor *GetNextInList(DSpotState *self, PClassActor *type, int skipcounter) diff --git a/wadsrc/static/zscript/base.txt b/wadsrc/static/zscript/base.txt index 48461790c..449e8aa09 100644 --- a/wadsrc/static/zscript/base.txt +++ b/wadsrc/static/zscript/base.txt @@ -598,15 +598,6 @@ struct DropItem native native readonly int Amount; } -class SpotState : Object native -{ - native static SpotState GetSpotState(); - native SpecialSpot GetNextInList(class type, int skipcounter); - native SpecialSpot GetSpotWithMinMaxDistance(Class type, double x, double y, double mindist, double maxdist); - native SpecialSpot GetRandomSpot(class type, bool onlyonce); - -} - struct LevelLocals native { enum EUDMF diff --git a/wadsrc/static/zscript/shared/specialspot.txt b/wadsrc/static/zscript/shared/specialspot.txt index baacd286f..e62e27e7a 100644 --- a/wadsrc/static/zscript/shared/specialspot.txt +++ b/wadsrc/static/zscript/shared/specialspot.txt @@ -1,6 +1,36 @@ - -class SpecialSpot : Actor native +class SpotState : Object native { + native static SpotState GetSpotState(bool create = true); + native SpecialSpot GetNextInList(class type, int skipcounter); + native SpecialSpot GetSpotWithMinMaxDistance(Class type, double x, double y, double mindist, double maxdist); + native SpecialSpot GetRandomSpot(class type, bool onlyonce); + native void AddSpot(SpecialSpot spot); + native void RemoveSpot(SpecialSpot spot); + +} + +class SpecialSpot : Actor +{ + override void BeginPlay() + { + let sstate = SpotState.GetSpotState(); + if (sstate != NULL) sstate.AddSpot(self); + Super.BeginPlay(); + } + + //---------------------------------------------------------------------------- + // + // + // + //---------------------------------------------------------------------------- + + override void OnDestroy() + { + let sstate = SpotState.GetSpotState(false); + if (sstate != NULL) sstate.RemoveSpot(self); + Super.OnDestroy(); + } + // Mace spawn spot ---------------------------------------------------------- // Every mace spawn spot will execute this action. The first one