mirror of
https://github.com/ZDoom/gzdoom.git
synced 2024-11-22 20:21:26 +00:00
- dsdhacked: Allow dynamic creation of new actors
This commit is contained in:
parent
b44741b8aa
commit
24d57b58c5
1 changed files with 38 additions and 29 deletions
|
@ -97,6 +97,7 @@ static TArray<int> OrgHeights;
|
||||||
// disappear, but that doesn't explain why frame patches specify an exact
|
// disappear, but that doesn't explain why frame patches specify an exact
|
||||||
// state rather than a code pointer.)
|
// state rather than a code pointer.)
|
||||||
static TArray<int> CodePConv;
|
static TArray<int> CodePConv;
|
||||||
|
static bool dsdhacked = false;
|
||||||
|
|
||||||
// Sprite names in the order Doom originally had them.
|
// Sprite names in the order Doom originally had them.
|
||||||
struct DEHSprName
|
struct DEHSprName
|
||||||
|
@ -122,6 +123,28 @@ static TArray<FSoundID> SoundMap;
|
||||||
// Names of different actor types, in original Doom 2 order
|
// Names of different actor types, in original Doom 2 order
|
||||||
static TArray<PClassActor *> InfoNames;
|
static TArray<PClassActor *> InfoNames;
|
||||||
|
|
||||||
|
static PClassActor* FindInfoName(int index, bool mustexist = false)
|
||||||
|
{
|
||||||
|
if (index < 0) return nullptr;
|
||||||
|
if (index < (int)InfoNames.Size()) return InfoNames[index];
|
||||||
|
|
||||||
|
if (dsdhacked)
|
||||||
|
{
|
||||||
|
FStringf name("~Dsdhacked~%d", index);
|
||||||
|
auto cls = PClass::FindActor(name);
|
||||||
|
if (cls)
|
||||||
|
{
|
||||||
|
GetDefaultByType(cls)->flags8 |= MF8_RETARGETAFTERSLAM; // This flag is not a ZDoom default, but it must be a Dehacked default.
|
||||||
|
return cls;
|
||||||
|
}
|
||||||
|
if (!mustexist)
|
||||||
|
{
|
||||||
|
return static_cast<PClassActor*>(RUNTIME_CLASS(AActor)->CreateDerivedClass(name.GetChars(), (unsigned)sizeof(AActor)));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
// bit flags for PatchThing (a .bex extension):
|
// bit flags for PatchThing (a .bex extension):
|
||||||
struct BitName
|
struct BitName
|
||||||
{
|
{
|
||||||
|
@ -163,10 +186,8 @@ struct MBFParamState
|
||||||
|
|
||||||
PClassActor* GetTypeArg(int i)
|
PClassActor* GetTypeArg(int i)
|
||||||
{
|
{
|
||||||
PClassActor* type = nullptr;
|
|
||||||
int num = (int)args[i];
|
int num = (int)args[i];
|
||||||
if (num > 0 && num < int(InfoNames.Size())) type = InfoNames[num-1]; // Dehacked is 1-based.
|
return FindInfoName(num-1, true);
|
||||||
return type;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
FState* GetStateArg(int i)
|
FState* GetStateArg(int i)
|
||||||
|
@ -341,7 +362,7 @@ FString PatchName;
|
||||||
static int PatchSize;
|
static int PatchSize;
|
||||||
static char *Line1, *Line2;
|
static char *Line1, *Line2;
|
||||||
static int dversion, pversion;
|
static int dversion, pversion;
|
||||||
static bool including, includenotext, dsdhacked = false;
|
static bool including, includenotext;
|
||||||
static int LumpFileNum;
|
static int LumpFileNum;
|
||||||
|
|
||||||
static const char *unknown_str = "Unknown key %s encountered in %s %d.\n";
|
static const char *unknown_str = "Unknown key %s encountered in %s %d.\n";
|
||||||
|
@ -373,8 +394,8 @@ static int PatchPars (int);
|
||||||
static int PatchCodePtrs (int);
|
static int PatchCodePtrs (int);
|
||||||
static int PatchMusic (int);
|
static int PatchMusic (int);
|
||||||
static int DoInclude (int);
|
static int DoInclude (int);
|
||||||
static int PatchSpriteNames (int);
|
static int PatchSpriteNames(int) { return 0; } // todo
|
||||||
static int PatchSoundNames(int) {} // todo
|
static int PatchSoundNames(int) { return 0; } // todo
|
||||||
static bool DoDehPatch();
|
static bool DoDehPatch();
|
||||||
|
|
||||||
static const struct {
|
static const struct {
|
||||||
|
@ -710,11 +731,12 @@ static void CreateMushroomFunc(FunctionCallEmitter &emitters, int value1, int va
|
||||||
// misc1 = type (arg +0), misc2 = Z-pos (arg +2)
|
// misc1 = type (arg +0), misc2 = Z-pos (arg +2)
|
||||||
static void CreateSpawnFunc(FunctionCallEmitter &emitters, int value1, int value2, MBFParamState* state)
|
static void CreateSpawnFunc(FunctionCallEmitter &emitters, int value1, int value2, MBFParamState* state)
|
||||||
{ // A_SpawnItem
|
{ // A_SpawnItem
|
||||||
if (InfoNames[value1-1] == nullptr)
|
auto p = FindInfoName(value1 - 1, true);
|
||||||
|
if (p == nullptr)
|
||||||
{
|
{
|
||||||
I_Error("No class found for dehackednum %d!\n", value1+1);
|
I_Error("No class found for dehackednum %d!\n", value1+1);
|
||||||
}
|
}
|
||||||
emitters.AddParameterPointerConst(InfoNames[value1-1]); // itemtype
|
emitters.AddParameterPointerConst(p); // itemtype
|
||||||
emitters.AddParameterFloatConst(0); // distance
|
emitters.AddParameterFloatConst(0); // distance
|
||||||
emitters.AddParameterFloatConst(value2); // height
|
emitters.AddParameterFloatConst(value2); // height
|
||||||
emitters.AddParameterIntConst(0); // useammo
|
emitters.AddParameterIntConst(0); // useammo
|
||||||
|
@ -1124,29 +1146,16 @@ static int PatchThing (int thingy)
|
||||||
type = NULL;
|
type = NULL;
|
||||||
info = (AActor *)&dummy;
|
info = (AActor *)&dummy;
|
||||||
ednum = &dummyed;
|
ednum = &dummyed;
|
||||||
if (thingy > (int)InfoNames.Size() || thingy <= 0)
|
auto thingytype = FindInfoName(thingy-1);
|
||||||
|
if (thingytype == nullptr)
|
||||||
{
|
{
|
||||||
Printf ("Thing %d out of range.\n", thingy);
|
Printf ("Thing %d out of range or invalid.\n", thingy);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
DPrintf (DMSG_SPAMMY, "Thing %d\n", thingy);
|
DPrintf (DMSG_SPAMMY, "Thing %d\n", thingy);
|
||||||
if (thingy > 0)
|
info = GetDefaultByType (type);
|
||||||
{
|
ednum = &type->ActorInfo()->DoomEdNum;
|
||||||
type = InfoNames[thingy - 1];
|
|
||||||
if (type == NULL)
|
|
||||||
{
|
|
||||||
info = (AActor *)&dummy;
|
|
||||||
ednum = &dummyed;
|
|
||||||
// An error for the name has already been printed while loading DEHSUPP.
|
|
||||||
Printf ("Could not find thing %d\n", thingy);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
info = GetDefaultByType (type);
|
|
||||||
ednum = &type->ActorInfo()->DoomEdNum;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
oldflags = info->flags;
|
oldflags = info->flags;
|
||||||
|
@ -1280,13 +1289,13 @@ static int PatchThing (int thingy)
|
||||||
}
|
}
|
||||||
else if (linelen == 12 && stricmp(Line1, "dropped item") == 0)
|
else if (linelen == 12 && stricmp(Line1, "dropped item") == 0)
|
||||||
{
|
{
|
||||||
val--; // This is 1-based and 0 means 'no drop'.
|
auto drop = FindInfoName(val - 1);
|
||||||
if ((unsigned)val < InfoNames.Size())
|
if (drop)
|
||||||
{
|
{
|
||||||
FDropItem* di = (FDropItem*)ClassDataAllocator.Alloc(sizeof(FDropItem));
|
FDropItem* di = (FDropItem*)ClassDataAllocator.Alloc(sizeof(FDropItem));
|
||||||
|
|
||||||
di->Next = nullptr;
|
di->Next = nullptr;
|
||||||
di->Name = InfoNames[val]->TypeName.GetChars();
|
di->Name = drop->TypeName;
|
||||||
di->Probability = 255;
|
di->Probability = 255;
|
||||||
di->Amount = -1;
|
di->Amount = -1;
|
||||||
info->GetInfo()->DropItems = di;
|
info->GetInfo()->DropItems = di;
|
||||||
|
|
Loading…
Reference in a new issue