From 6487681736ab205a6c99df5e91b2f59456914692 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 7 Oct 2016 17:49:00 +0200 Subject: [PATCH 001/255] - started porting constants.txt --- wadsrc/static/decorate.txt | 1 - wadsrc/static/{actors => zscript}/constants.txt | 0 2 files changed, 1 deletion(-) rename wadsrc/static/{actors => zscript}/constants.txt (100%) diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index c6a205d42..a77a4d583 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,4 +1,3 @@ -#include "actors/constants.txt" #include "actors/actor.txt" #include "actors/shared/inventory.txt" diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/zscript/constants.txt similarity index 100% rename from wadsrc/static/actors/constants.txt rename to wadsrc/static/zscript/constants.txt From 04d4bda2621eda7562f70df7906681b9f67f1421 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 7 Oct 2016 18:09:28 +0200 Subject: [PATCH 002/255] - converted all constants to enums and gave the enums names. --- wadsrc/static/zscript/constants.txt | 612 ++++++++++++++++------------ 1 file changed, 355 insertions(+), 257 deletions(-) diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index dce2488c2..da22b4180 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -1,92 +1,119 @@ // Flags for A_PainAttack -const int PAF_NOSKULLATTACK = 1; -const int PAF_AIMFACING = 2; -const int PAF_NOTARGET = 4; +enum EPainAttackFlags +{ + PAF_NOSKULLATTACK = 1, + PAF_AIMFACING = 2, + PAF_NOTARGET = 4, +}; // Flags for A_VileAttack -const int VAF_DMGTYPEAPPLYTODIRECT = 1; +enum EVileAttackFlags +{ + VAF_DMGTYPEAPPLYTODIRECT = 1, +}; // Flags for A_Saw -const int SF_NORANDOM = 1; -const int SF_RANDOMLIGHTMISS = 2; -const int SF_RANDOMLIGHTHIT = 4; -const int SF_RANDOMLIGHTBOTH = 6; -const int SF_NOUSEAMMOMISS = 8; -const int SF_NOUSEAMMO = 16; -const int SF_NOPULLIN = 32; -const int SF_NOTURN = 64; -const int SF_STEALARMOR = 128; +enum ESawFlags +{ + SF_NORANDOM = 1, + SF_RANDOMLIGHTMISS = 2, + SF_RANDOMLIGHTHIT = 4, + SF_RANDOMLIGHTBOTH = 6, + SF_NOUSEAMMOMISS = 8, + SF_NOUSEAMMO = 16, + SF_NOPULLIN = 32, + SF_NOTURN = 64, + SF_STEALARMOR = 128, +}; // Flags for A_BFGSpray -const int BFGF_HURTSOURCE = 1; -const int BFGF_MISSILEORIGIN = 2; +enum EBFGSprayFlags +{ + BFGF_HURTSOURCE = 1, + BFGF_MISSILEORIGIN = 2, +}; // Flags for A_CustomMissile -const int CMF_AIMOFFSET = 1; -const int CMF_AIMDIRECTION = 2; -const int CMF_TRACKOWNER = 4; -const int CMF_CHECKTARGETDEAD = 8; -const int CMF_ABSOLUTEPITCH = 16; -const int CMF_OFFSETPITCH = 32; -const int CMF_SAVEPITCH = 64; -const int CMF_ABSOLUTEANGLE = 128; +enum ECustomMissileFlags +{ + CMF_AIMOFFSET = 1, + CMF_AIMDIRECTION = 2, + CMF_TRACKOWNER = 4, + CMF_CHECKTARGETDEAD = 8, + CMF_ABSOLUTEPITCH = 16, + CMF_OFFSETPITCH = 32, + CMF_SAVEPITCH = 64, + CMF_ABSOLUTEANGLE = 128, +}; // Flags for A_CustomBulletAttack -const int CBAF_AIMFACING = 1; -const int CBAF_NORANDOM = 2; -const int CBAF_EXPLICITANGLE = 4; -const int CBAF_NOPITCH = 8; -const int CBAF_NORANDOMPUFFZ = 16; -const int CBAF_PUFFTARGET = 32; -const int CBAF_PUFFMASTER = 64; -const int CBAF_PUFFTRACER = 128; +enum ECustomBulletAttackFlags +{ + CBAF_AIMFACING = 1, + CBAF_NORANDOM = 2, + CBAF_EXPLICITANGLE = 4, + CBAF_NOPITCH = 8, + CBAF_NORANDOMPUFFZ = 16, + CBAF_PUFFTARGET = 32, + CBAF_PUFFMASTER = 64, + CBAF_PUFFTRACER = 128, +}; // Flags for A_GunFlash -const int GFF_NOEXTCHANGE = 1; +enum EGunFlashFlags +{ + GFF_NOEXTCHANGE = 1, +}; // Flags for A_FireBullets -const int FBF_USEAMMO = 1; -const int FBF_NORANDOM = 2; -const int FBF_EXPLICITANGLE = 4; -const int FBF_NOPITCH = 8; -const int FBF_NOFLASH = 16; -const int FBF_NORANDOMPUFFZ = 32; +enum EFireBulletsFlags +{ + FBF_USEAMMO = 1, + FBF_NORANDOM = 2, + FBF_EXPLICITANGLE = 4, + FBF_NOPITCH = 8, + FBF_NOFLASH = 16, + FBF_NORANDOMPUFFZ = 32, +}; // Flags for A_SpawnItemEx -const int SXF_TRANSFERTRANSLATION = 1 << 0; -const int SXF_ABSOLUTEPOSITION = 1 << 1; -const int SXF_ABSOLUTEANGLE = 1 << 2; -const int SXF_ABSOLUTEMOMENTUM = 1 << 3; //Since "momentum" is declared to be deprecated in the expressions, for compatibility -const int SXF_ABSOLUTEVELOCITY = 1 << 3; //purposes, this was made. It does the same thing though. Do not change the value. -const int SXF_SETMASTER = 1 << 4; -const int SXF_NOCHECKPOSITION = 1 << 5; -const int SXF_TELEFRAG = 1 << 6; -const int SXF_CLIENTSIDE = 1 << 7; // only used by Skulltag -const int SXF_TRANSFERAMBUSHFLAG = 1 << 8; -const int SXF_TRANSFERPITCH = 1 << 9; -const int SXF_TRANSFERPOINTERS = 1 << 10; -const int SXF_USEBLOODCOLOR = 1 << 11; -const int SXF_CLEARCALLERTID = 1 << 12; -const int SXF_MULTIPLYSPEED = 1 << 13; -const int SXF_TRANSFERSCALE = 1 << 14; -const int SXF_TRANSFERSPECIAL = 1 << 15; -const int SXF_CLEARCALLERSPECIAL = 1 << 16; -const int SXF_TRANSFERSTENCILCOL = 1 << 17; -const int SXF_TRANSFERALPHA = 1 << 18; -const int SXF_TRANSFERRENDERSTYLE = 1 << 19; -const int SXF_SETTARGET = 1 << 20; -const int SXF_SETTRACER = 1 << 21; -const int SXF_NOPOINTERS = 1 << 22; -const int SXF_ORIGINATOR = 1 << 23; -const int SXF_TRANSFERSPRITEFRAME = 1 << 24; -const int SXF_TRANSFERROLL = 1 << 25; -const int SXF_ISTARGET = 1 << 26; -const int SXF_ISMASTER = 1 << 27; -const int SXF_ISTRACER = 1 << 28; +enum ESpawnItemFlags +{ + SXF_TRANSFERTRANSLATION = 1 << 0, + SXF_ABSOLUTEPOSITION = 1 << 1, + SXF_ABSOLUTEANGLE = 1 << 2, + SXF_ABSOLUTEMOMENTUM = 1 << 3, //Since "momentum" is declared to be deprecated in the expressions, for compatibility + SXF_ABSOLUTEVELOCITY = 1 << 3, //purposes, this was made. It does the same thing though. Do not change the value. + SXF_SETMASTER = 1 << 4, + SXF_NOCHECKPOSITION = 1 << 5, + SXF_TELEFRAG = 1 << 6, + SXF_CLIENTSIDE = 1 << 7, // only used by Skulltag + SXF_TRANSFERAMBUSHFLAG = 1 << 8, + SXF_TRANSFERPITCH = 1 << 9, + SXF_TRANSFERPOINTERS = 1 << 10, + SXF_USEBLOODCOLOR = 1 << 11, + SXF_CLEARCALLERTID = 1 << 12, + SXF_MULTIPLYSPEED = 1 << 13, + SXF_TRANSFERSCALE = 1 << 14, + SXF_TRANSFERSPECIAL = 1 << 15, + SXF_CLEARCALLERSPECIAL = 1 << 16, + SXF_TRANSFERSTENCILCOL = 1 << 17, + SXF_TRANSFERALPHA = 1 << 18, + SXF_TRANSFERRENDERSTYLE = 1 << 19, + SXF_SETTARGET = 1 << 20, + SXF_SETTRACER = 1 << 21, + SXF_NOPOINTERS = 1 << 22, + SXF_ORIGINATOR = 1 << 23, + SXF_TRANSFERSPRITEFRAME = 1 << 24, + SXF_TRANSFERROLL = 1 << 25, + SXF_ISTARGET = 1 << 26, + SXF_ISMASTER = 1 << 27, + SXF_ISTRACER = 1 << 28, +}; // Flags for A_Chase -enum +enum EChaseFlags { CHF_FASTCHASE = 1, CHF_NOPLAYACTIVE = 2, @@ -102,20 +129,26 @@ enum }; // Flags for A_LookEx -const int LOF_NOSIGHTCHECK = 1; -const int LOF_NOSOUNDCHECK = 2; -const int LOF_DONTCHASEGOAL = 4; -const int LOF_NOSEESOUND = 8; -const int LOF_FULLVOLSEESOUND = 16; -const int LOF_NOJUMP = 32; +enum ELookFlags +{ + LOF_NOSIGHTCHECK = 1, + LOF_NOSOUNDCHECK = 2, + LOF_DONTCHASEGOAL = 4, + LOF_NOSEESOUND = 8, + LOF_FULLVOLSEESOUND = 16, + LOF_NOJUMP = 32, +}; // Flags for A_Respawn -const int RSF_FOG = 1; -const int RSF_KEEPTARGET = 2; -const int RSF_TELEFRAG = 4; +enum ERespawnFlags +{ + RSF_FOG = 1, + RSF_KEEPTARGET = 2, + RSF_TELEFRAG = 4, +}; // Flags for A_JumpIfTargetInLOS and A_JumpIfInTargetLOS -enum +enum EJumpFlags { JLOSF_PROJECTILE = 1, JLOSF_NOSIGHT = 1 << 1, @@ -133,98 +166,137 @@ enum }; // Flags for A_ChangeVelocity -const int CVF_RELATIVE = 1; -const int CVF_REPLACE = 2; +enum EChangeVelocityFlags +{ + CVF_RELATIVE = 1, + CVF_REPLACE = 2, +}; // Flags for A_WeaponReady -const int WRF_NOBOB = 1; -const int WRF_NOSWITCH = 2; -const int WRF_NOPRIMARY = 4; -const int WRF_NOSECONDARY = 8; -const int WRF_NOFIRE = WRF_NOPRIMARY | WRF_NOSECONDARY; -const int WRF_ALLOWRELOAD = 16; -const int WRF_ALLOWZOOM = 32; -const int WRF_DISABLESWITCH = 64; -const int WRF_ALLOWUSER1 = 128; -const int WRF_ALLOWUSER2 = 256; -const int WRF_ALLOWUSER3 = 512; -const int WRF_ALLOWUSER4 = 1024; +enum EWeaponReadyFlags +{ + WRF_NOBOB = 1, + WRF_NOSWITCH = 2, + WRF_NOPRIMARY = 4, + WRF_NOSECONDARY = 8, + WRF_NOFIRE = WRF_NOPRIMARY | WRF_NOSECONDARY, + WRF_ALLOWRELOAD = 16, + WRF_ALLOWZOOM = 32, + WRF_DISABLESWITCH = 64, + WRF_ALLOWUSER1 = 128, + WRF_ALLOWUSER2 = 256, + WRF_ALLOWUSER3 = 512, + WRF_ALLOWUSER4 = 1024, +}; // Flags for A_SelectWeapon -const int SWF_SELECTPRIORITY = 1; +enum ESelectWeaponFlags +{ + SWF_SELECTPRIORITY = 1, +}; // Morph constants -const int MRF_ADDSTAMINA = 1; -const int MRF_FULLHEALTH = 2; -const int MRF_UNDOBYTOMEOFPOWER = 4; -const int MRF_UNDOBYCHAOSDEVICE = 8; -const int MRF_FAILNOTELEFRAG = 16; -const int MRF_FAILNOLAUGH = 32; -const int MRF_WHENINVULNERABLE = 64; -const int MRF_LOSEACTUALWEAPON = 128; -const int MRF_NEWTIDBEHAVIOUR = 256; -const int MRF_UNDOBYDEATH = 512; -const int MRF_UNDOBYDEATHFORCED = 1024; -const int MRF_UNDOBYDEATHSAVES = 2048; -const int MRF_UNDOALWAYS = 4096; -const int MRF_TRANSFERTRANSLATION = 8192; +enum EMorphFlags +{ + MRF_ADDSTAMINA = 1, + MRF_FULLHEALTH = 2, + MRF_UNDOBYTOMEOFPOWER = 4, + MRF_UNDOBYCHAOSDEVICE = 8, + MRF_FAILNOTELEFRAG = 16, + MRF_FAILNOLAUGH = 32, + MRF_WHENINVULNERABLE = 64, + MRF_LOSEACTUALWEAPON = 128, + MRF_NEWTIDBEHAVIOUR = 256, + MRF_UNDOBYDEATH = 512, + MRF_UNDOBYDEATHFORCED = 1024, + MRF_UNDOBYDEATHSAVES = 2048, + MRF_UNDOALWAYS = 4096, + MRF_TRANSFERTRANSLATION = 8192, +}; // Flags for A_RailAttack and A_CustomRailgun -const int RGF_SILENT = 1; -const int RGF_NOPIERCING = 2; -const int RGF_EXPLICITANGLE = 4; -const int RGF_FULLBRIGHT = 8; -const int RGF_CENTERZ = 16; -const int RGF_NORANDOMPUFFZ = 32; +enum ERailFlags +{ + RGF_SILENT = 1, + RGF_NOPIERCING = 2, + RGF_EXPLICITANGLE = 4, + RGF_FULLBRIGHT = 8, + RGF_CENTERZ = 16, + RGF_NORANDOMPUFFZ = 32, +}; // Flags for A_Mushroom -const int MSF_Standard = 0; -const int MSF_Classic = 1; -const int MSF_DontHurt = 2; +enum EMushroomFlags +{ + MSF_Standard = 0, + MSF_Classic = 1, + MSF_DontHurt = 2, +}; // Flags for A_Explode -const int XF_HURTSOURCE = 1; -const int XF_NOTMISSILE = 4; -const int XF_EXPLICITDAMAGETYPE = 1 << 3; +enum EExplodeFlags +{ + XF_HURTSOURCE = 1, + XF_NOTMISSILE = 4, + XF_EXPLICITDAMAGETYPE = 1 << 3, +}; // Flags for A_RadiusThrust -const int RTF_AFFECTSOURCE = 1; -const int RTF_NOIMPACTDAMAGE = 2; -const int RTF_NOTMISSILE = 4; -const int RTF_THRUSTZ = 16; +enum ERadiusThrustFlags +{ + RTF_AFFECTSOURCE = 1, + RTF_NOIMPACTDAMAGE = 2, + RTF_NOTMISSILE = 4, + RTF_THRUSTZ = 16, +}; // Flags for A_RadiusDamageSelf -const int RDSF_BFGDAMAGE = 1; +enum ERadiusDamageSelfFlags +{ + RDSF_BFGDAMAGE = 1, +}; // Flags for A_Blast -const int BF_USEAMMO = 1; -const int BF_DONTWARN = 2; -const int BF_AFFECTBOSSES = 4; -const int BF_NOIMPACTDAMAGE = 8; +enum EBlastFlags +{ + BF_USEAMMO = 1, + BF_DONTWARN = 2, + BF_AFFECTBOSSES = 4, + BF_NOIMPACTDAMAGE = 8, +}; // Flags for A_SeekerMissile -const int SMF_LOOK = 1; -const int SMF_PRECISE = 2; -const int SMF_CURSPEED = 4; +enum ESeekerMissileFlags +{ + SMF_LOOK = 1, + SMF_PRECISE = 2, + SMF_CURSPEED = 4, +}; // Flags for A_CustomPunch -const int CPF_USEAMMO = 1; -const int CPF_DAGGER = 2; -const int CPF_PULLIN = 4; -const int CPF_NORANDOMPUFFZ = 8; -const int CPF_NOTURN = 16; -const int CPF_STEALARMOR = 32; +enum ECustomPunchFlags +{ + CPF_USEAMMO = 1, + CPF_DAGGER = 2, + CPF_PULLIN = 4, + CPF_NORANDOMPUFFZ = 8, + CPF_NOTURN = 16, + CPF_STEALARMOR = 32, +}; // Flags for A_CustomMissile -const int FPF_AIMATANGLE = 1; -const int FPF_TRANSFERTRANSLATION = 2; -const int FPF_NOAUTOAIM = 4; -const int FBF_PUFFTARGET = 64; -const int FBF_PUFFMASTER = 128; -const int FBF_PUFFTRACER = 256; +enum ECustomMissileFlags +{ + FPF_AIMATANGLE = 1, + FPF_TRANSFERTRANSLATION = 2, + FPF_NOAUTOAIM = 4, + FBF_PUFFTARGET = 64, + FBF_PUFFMASTER = 128, + FBF_PUFFTRACER = 256, +}; // Flags for A_Teleport -enum +enum ETeleportFlags { TF_TELEFRAG = 0x00000001, // Allow telefrag in order to teleport. TF_RANDOMDECIDE = 0x00000002, // Randomly fail based on health. (A_Srcr2Decide) @@ -244,11 +316,14 @@ enum }; // Flags for A_WolfAttack -const int WAF_NORANDOM = 1; -const int WAF_USEPUFF = 2; +enum EWolfAttackFlags +{ + WAF_NORANDOM = 1, + WAF_USEPUFF = 2 +}; // Flags for A_RadiusGive -enum +enum ERadiusGiveFlags { RGF_GIVESELF = 1, RGF_PLAYERS = 1 << 1, @@ -271,7 +346,7 @@ enum }; // Activation flags -enum +enum EActivationFlags { THINGSPEC_Default = 0, THINGSPEC_ThingActs = 1, @@ -282,23 +357,28 @@ enum THINGSPEC_ClearSpecial = 32, THINGSPEC_NoDeathSpecial = 64, THINGSPEC_TriggerActs = 128, + + // Shorter aliases for same + AF_Default = 0, + AF_ThingActs = 1, + AF_ThingTargets = 2, + AF_TriggerTargets = 4, + AF_MonsterTrigger = 8, + AF_MissileTrigger = 16, + AF_ClearSpecial = 32, + AF_NoDeathSpecial = 64, + AF_TriggerActs = 128, + }; -// Shorter aliases for same -const int AF_Default = 0; -const int AF_ThingActs = 1; -const int AF_ThingTargets = 2; -const int AF_TriggerTargets = 4; -const int AF_MonsterTrigger = 8; -const int AF_MissileTrigger = 16; -const int AF_ClearSpecial = 32; -const int AF_NoDeathSpecial = 64; -const int AF_TriggerActs = 128; // Flags for A_TakeInventory and A_TakeFromTarget -const int TIF_NOTAKEINFINITE = 1; +enum ETakeFlags +{ + TIF_NOTAKEINFINITE = 1 +}; // constants for A_PlaySound -enum +enum ESoundFlags { CHAN_AUTO = 0, CHAN_WEAPON = 1, @@ -317,96 +397,110 @@ enum }; // sound attenuation values -const float ATTN_NONE = 0; -const float ATTN_NORM = 1; -const float ATTN_IDLE = 1.001; -const float ATTN_STATIC = 3; +const ATTN_NONE = 0; +const ATTN_NORM = 1; +const ATTN_IDLE = 1.001; +const ATTN_STATIC = 3; // For SetPlayerProprty action special -Const Int PROP_FROZEN = 0; -Const Int PROP_NOTARGET = 1; -Const Int PROP_INSTANTWEAPONSWITCH = 2; -Const Int PROP_FLY = 3; -Const Int PROP_TOTALLYFROZEN = 4; -Const Int PROP_INVULNERABILITY = 5; // (Deprecated) -Const Int PROP_STRENGTH = 6; // (Deprecated) -Const Int PROP_INVISIBILITY = 7; // (Deprecated) -Const Int PROP_RADIATIONSUIT = 8; // (Deprecated) -Const Int PROP_ALLMAP = 9; // (Deprecated) -Const Int PROP_INFRARED = 10; // (Deprecated) -Const Int PROP_WEAPONLEVEL2 = 11; // (Deprecated) -Const Int PROP_FLIGHT = 12; // (Deprecated) -Const Int PROP_SPEED = 15; // (Deprecated) -Const Int PROP_BUDDHA = 16; +enum EPlayerProperties +{ + PROP_FROZEN = 0, + PROP_NOTARGET = 1, + PROP_INSTANTWEAPONSWITCH = 2, + PROP_FLY = 3, + PROP_TOTALLYFROZEN = 4, + PROP_INVULNERABILITY = 5, // (Deprecated) + PROP_STRENGTH = 6, // (Deprecated) + PROP_INVISIBILITY = 7, // (Deprecated) + PROP_RADIATIONSUIT = 8, // (Deprecated) + PROP_ALLMAP = 9, // (Deprecated) + PROP_INFRARED = 10, // (Deprecated) + PROP_WEAPONLEVEL2 = 11, // (Deprecated) + PROP_FLIGHT = 12, // (Deprecated) + PROP_SPEED = 15, // (Deprecated) + PROP_BUDDHA = 16, +} // Line_SetBlocking -Const Int BLOCKF_CREATURES = 1; -Const Int BLOCKF_MONSTERS = 2; -Const Int BLOCKF_PLAYERS = 4; -Const Int BLOCKF_FLOATERS = 8; -Const Int BLOCKF_PROJECTILES = 16; -Const Int BLOCKF_EVERYTHING = 32; -Const Int BLOCKF_RAILING = 64; -Const Int BLOCKF_USE = 128; +enum EBlockFlags +{ + BLOCKF_CREATURES = 1, + BLOCKF_MONSTERS = 2, + BLOCKF_PLAYERS = 4, + BLOCKF_FLOATERS = 8, + BLOCKF_PROJECTILES = 16, + BLOCKF_EVERYTHING = 32, + BLOCKF_RAILING = 64, + BLOCKF_USE = 128, +}; // Pointer constants, bitfield-enabled - -Const Int AAPTR_DEFAULT = 0; -Const Int AAPTR_NULL = 0x1; -Const Int AAPTR_TARGET = 0x2; -Const Int AAPTR_MASTER = 0x4; -Const Int AAPTR_TRACER = 0x8; - -Const Int AAPTR_PLAYER_GETTARGET = 0x10; -Const Int AAPTR_PLAYER_GETCONVERSATION = 0x20; - -Const Int AAPTR_PLAYER1 = 0x40; -Const Int AAPTR_PLAYER2 = 0x80; -Const Int AAPTR_PLAYER3 = 0x100; -Const Int AAPTR_PLAYER4 = 0x200; -Const Int AAPTR_PLAYER5 = 0x400; -Const Int AAPTR_PLAYER6 = 0x800; -Const Int AAPTR_PLAYER7 = 0x1000; -Const Int AAPTR_PLAYER8 = 0x2000; - -Const Int AAPTR_FRIENDPLAYER = 0x4000; -Const Int AAPTR_LINETARGET = 0x8000; +enum EPointerFlags +{ + AAPTR_DEFAULT = 0, + AAPTR_NULL = 0x1, + AAPTR_TARGET = 0x2, + AAPTR_MASTER = 0x4, + AAPTR_TRACER = 0x8, + + AAPTR_PLAYER_GETTARGET = 0x10, + AAPTR_PLAYER_GETCONVERSATION = 0x20, + + AAPTR_PLAYER1 = 0x40, + AAPTR_PLAYER2 = 0x80, + AAPTR_PLAYER3 = 0x100, + AAPTR_PLAYER4 = 0x200, + AAPTR_PLAYER5 = 0x400, + AAPTR_PLAYER6 = 0x800, + AAPTR_PLAYER7 = 0x1000, + AAPTR_PLAYER8 = 0x2000, + AAPTR_FRIENDPLAYER = 0x4000, + AAPTR_LINETARGET = 0x8000, +}; // Pointer operation flags -Const Int PTROP_UNSAFETARGET = 1; -Const Int PTROP_UNSAFEMASTER = 2; -Const Int PTROP_NOSAFEGUARDS = PTROP_UNSAFETARGET|PTROP_UNSAFEMASTER; - +enum EPointerOperations +{ + PTROP_UNSAFETARGET = 1, + PTROP_UNSAFEMASTER = 2, + PTROP_NOSAFEGUARDS = PTROP_UNSAFETARGET|PTROP_UNSAFEMASTER, +}; // Flags for A_Warp -Const Int WARPF_ABSOLUTEOFFSET = 0x1; -Const Int WARPF_ABSOLUTEANGLE = 0x2; -Const Int WARPF_USECALLERANGLE = 0x4; -Const Int WARPF_NOCHECKPOSITION = 0x8; -Const Int WARPF_INTERPOLATE = 0x10; -Const Int WARPF_WARPINTERPOLATION = 0x20; -Const Int WARPF_COPYINTERPOLATION = 0x40; -Const Int WARPF_STOP = 0x80; -Const Int WARPF_TOFLOOR = 0x100; -Const Int WARPF_TESTONLY = 0x200; -Const Int WAPRF_ABSOLUTEPOSITION = 0x400; -Const Int WARPF_ABSOLUTEPOSITION = 0x400; -Const Int WARPF_BOB = 0x800; -Const Int WARPF_MOVEPTR = 0x1000; -Const Int WARPF_USETID = 0x2000; -Const Int WARPF_COPYVELOCITY = 0x4000; -Const Int WARPF_COPYPITCH = 0x8000; +enum EWarpFlags +{ + WARPF_ABSOLUTEOFFSET = 0x1, + WARPF_ABSOLUTEANGLE = 0x2, + WARPF_USECALLERANGLE = 0x4, + WARPF_NOCHECKPOSITION = 0x8, + WARPF_INTERPOLATE = 0x10, + WARPF_WARPINTERPOLATION = 0x20, + WARPF_COPYINTERPOLATION = 0x40, + WARPF_STOP = 0x80, + WARPF_TOFLOOR = 0x100, + WARPF_TESTONLY = 0x200, + WAPRF_ABSOLUTEPOSITION = 0x400, + WARPF_ABSOLUTEPOSITION = 0x400, + WARPF_BOB = 0x800, + WARPF_MOVEPTR = 0x1000, + WARPF_USETID = 0x2000, + WARPF_COPYVELOCITY = 0x4000, + WARPF_COPYPITCH = 0x8000, +}; // flags for A_SetPitch/SetAngle/SetRoll -const int SPF_FORCECLAMP = 1; -const int SPF_INTERPOLATE = 2; - +enum EAngleFlags +{ + SPF_FORCECLAMP = 1, + SPF_INTERPOLATE = 2, +}; // flags for A_CheckLOF -enum +enum ELOFFlags { CLOFF_NOAIM_VERT = 0x1, CLOFF_NOAIM_HORZ = 0x2, @@ -449,7 +543,7 @@ enum }; // Flags for A_Kill (Master/Target/Tracer/Children/Siblings) series -enum +enum EKillFlags { KILS_FOILINVUL = 0x00000001, KILS_KILLMISSILES = 0x00000002, @@ -461,7 +555,7 @@ enum }; // Flags for A_Damage (Master/Target/Tracer/Children/Siblings/Self) series -enum +enum EDamageFlags { DMSS_FOILINVUL = 0x00000001, DMSS_AFFECTARMOR = 0x00000002, @@ -476,12 +570,15 @@ enum }; // Flags for A_AlertMonsters -const int AMF_TARGETEMITTER = 1; -const int AMF_TARGETNONPLAYER = 2; -const int AMF_EMITFROMTARGET = 4; +enum EAlertFlags +{ + AMF_TARGETEMITTER = 1, + AMF_TARGETNONPLAYER = 2, + AMF_EMITFROMTARGET = 4, +} // Flags for A_Remove* -enum +enum ERemoveFlags { RMVF_MISSILES = 0x00000001, RMVF_NOMONSTERS = 0x00000002, @@ -493,14 +590,14 @@ enum }; // Flags for A_Fade* -enum +enum EFadeFlags { FTF_REMOVE = 1 << 0, FTF_CLAMP = 1 << 1, }; // Flags for A_Face* -enum +enum EFaceFlags { FAF_BOTTOM = 1, FAF_MIDDLE = 2, @@ -509,7 +606,7 @@ enum }; // Flags for A_QuakeEx -enum +enum EQuakeFlags { QF_RELATIVE = 1, QF_SCALEDOWN = 1 << 1, @@ -520,7 +617,7 @@ enum }; // A_CheckProximity flags -enum +enum EProximityFlags { CPXF_ANCESTOR = 1, CPXF_LESSOREQUAL = 1 << 1, @@ -539,7 +636,7 @@ enum // Flags for A_CheckBlock // These flags only affect the calling actor('s pointer), not the ones being searched. -enum +enum ECheckBlockFlags { CBF_NOLINES = 1 << 0, //Don't check actors. CBF_SETTARGET = 1 << 1, //Sets the caller/pointer's target to the actor blocking it. Actors only. @@ -552,7 +649,7 @@ enum CBF_ABSOLUTEANGLE = 1 << 8, //Absolute angle for offsets. }; -enum +enum EParticleFlags { SPF_FULLBRIGHT = 1, SPF_RELPOS = 1 << 1, @@ -565,7 +662,7 @@ enum }; //Flags for A_FaceMovementDirection -enum +enum EMovementFlags { FMDF_NOPITCH = 1 << 0, FMDF_INTERPOLATE = 1 << 1, @@ -573,7 +670,7 @@ enum }; // Flags for GetZAt -enum +enum EZFlags { GZF_ABSOLUTEPOS = 1, // Use the absolute position instead of an offsetted one. GZF_ABSOLUTEANG = 1 << 1, // Don't add the actor's angle to the parameter. @@ -584,7 +681,7 @@ enum }; // Flags for A_WeaponOffset -enum +enum EWeaponOffsetFlags { WOF_KEEPX = 1, WOF_KEEPY = 1 << 1, @@ -592,7 +689,7 @@ enum }; // Flags for psprite layers -enum +enum EPSpriteFlags { PSPF_ADDWEAPON = 1 << 0, PSPF_ADDBOB = 1 << 1, @@ -601,13 +698,13 @@ enum }; // Default psprite layers -enum +enum EPSPLayers { PSP_WEAPON = 1, PSP_FLASH = 1000, }; -enum +enum EInputFlags { // These are the original inputs sent by the player. INPUT_OLDBUTTONS, @@ -633,7 +730,7 @@ enum MODINPUT_UPMOVE }; -enum +enum EButtons { BT_ATTACK = 1<<0, // Press "Fire". BT_USE = 1<<1, // Use button, to open doors, activate switches. @@ -665,22 +762,23 @@ enum BT_USER3 = 1<<23, BT_USER4 = 1<<24, }; + // Flags for GetAngle -enum +enum EGetAngleFlags { GAF_RELATIVE = 1, GAF_SWITCH = 1 << 1, }; //Flags for A_CopySpriteFrame -enum +enum ECopySpriteFrameFlags { CPSF_NOSPRITE = 1, CPSF_NOFRAME = 1 << 1, }; //Flags for A_SetMaskRotation -enum +enum EMaskRotationFlags { VRF_NOANGLESTART = 1, VRF_NOANGLEEND = 1 << 1, @@ -691,7 +789,7 @@ enum VRF_NOPITCH = VRF_NOPITCHSTART|VRF_NOPITCHEND, }; -enum +enum ERenderStyles { STYLE_None, STYLE_Normal, From 994bb4fc7ab6f6c4f5b5567c63125bb711105f98 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 01:05:27 +0200 Subject: [PATCH 003/255] - started to make ZScript parser work on real-life data. It will now read a lump named ZSCRIPT which is a list of filenames to be compiled. - place generated symbols into GlobalSymbols instead of a scratch table that will be discarded right away. - allow the state object to change source file scanners (I hope this works, but the old implementation was unable to do more than one with with a parse state so I had to change it.) - It can now parse constants.txt and insert everything in it into the global symbol table and make subsequent DECORATE compile properly. --- src/thingdef/thingdef.cpp | 12 +---- src/zscript/zcc-parse.lemon | 20 ++++---- src/zscript/zcc_parser.cpp | 92 ++++++++++++++++++++++++------------- src/zscript/zcc_parser.h | 4 +- 4 files changed, 75 insertions(+), 53 deletions(-) diff --git a/src/thingdef/thingdef.cpp b/src/thingdef/thingdef.cpp index 41e1e9542..abc136291 100644 --- a/src/thingdef/thingdef.cpp +++ b/src/thingdef/thingdef.cpp @@ -445,6 +445,7 @@ static void FinishThingdef() // Called from FActor::StaticInit() // //========================================================================== +void ParseScripts(); void LoadActors () { @@ -456,19 +457,10 @@ void LoadActors () FScriptPosition::ResetErrorCounter(); InitThingdef(); lastlump = 0; + ParseScripts(); while ((lump = Wads.FindLump ("DECORATE", &lastlump)) != -1) { FScanner sc(lump); - - if (Wads.GetLumpFile(lump) == 0) - { - // define namespace 'zdoom' - } - else - { - // use namespace 'zdoom' - } - ParseDecorate (sc); } FinishThingdef(); diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index ee8296ff6..cd2ed8efe 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -96,9 +96,9 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) } } } - stat->sc.ScriptMessage("%s\n%s\n", unexpected.GetChars(), expecting.GetChars()); + stat->sc->ScriptMessage("%s\n%s\n", unexpected.GetChars(), expecting.GetChars()); } -%parse_accept { stat->sc.ScriptMessage("input accepted\n"); } +%parse_accept { DPrintf(DMSG_SPAMMY, "Input accepted\n"); } %parse_failure { /**failed = true;*/ } %nonassoc EQ MULEQ DIVEQ MODEQ ADDEQ SUBEQ LSHEQ RSHEQ ANDEQ OREQ XOREQ. @@ -124,7 +124,7 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) %type opt_func_body {ZCC_CompoundStmt *} %type function_body {ZCC_CompoundStmt *} -main ::= translation_unit(A). { stat->TopNode = A; stat->sc.ScriptMessage("Parse complete\n"); } +main ::= translation_unit(A). { stat->TopNode = A; DPrintf(DMSG_SPAMMY, "Parse complete\n"); } %type translation_unit {ZCC_TreeNode *} translation_unit(X) ::= . { X = NULL; } @@ -339,7 +339,7 @@ enum_def(X) ::= ENUM(T) IDENTIFIER(A) enum_type(B) LBRACE opt_enum_list(C) RBRAC X = def; } -enum_type(X) ::= . { X.Int = ZCC_IntAuto; X.SourceLoc = stat->sc.GetMessageLine(); } +enum_type(X) ::= . { X.Int = ZCC_IntAuto; X.SourceLoc = stat->sc->GetMessageLine(); } enum_type(X) ::= COLON int_type(A). { X = A; /*X-overwrites-A*/ } enum_list(X) ::= error. { X = NULL; } @@ -398,7 +398,7 @@ states_def(X) ::= STATES(T) scanner_mode LBRACE states_body(A) RBRACE. * set immediately after LBRACE is consumed, rather than immediately after * STATES is consumed. */ -scanner_mode ::= . { stat->sc.SetStateMode(true); } +scanner_mode ::= . { stat->sc->SetStateMode(true); } states_body(X) ::= . { X = NULL; } states_body(X) ::= error. { X = NULL; } @@ -538,7 +538,7 @@ type_name(X) ::= DOT dottable_id(A). * straight away.) */ %token_class intconst INTCONST|UINTCONST. -vector_size(X) ::= . { X.Int = ZCC_Vector3; X.SourceLoc = stat->sc.GetMessageLine(); } +vector_size(X) ::= . { X.Int = ZCC_Vector3; X.SourceLoc = stat->sc->GetMessageLine(); } vector_size(X) ::= LT intconst(A) GT. { if (A.Int >= 2 && A.Int <= 4) @@ -548,7 +548,7 @@ vector_size(X) ::= LT intconst(A) GT. else { X.Int = ZCC_Vector3; - stat->sc.ScriptMessage("Invalid vector size %d\n", A.Int); + stat->sc->ScriptMessage("Invalid vector size %d\n", A.Int); } X.SourceLoc = A.SourceLoc; } @@ -656,11 +656,11 @@ declarator(X) ::= decl_flags(A) type_list_or_void(B) variables_or_function(C). { // An invalid if (B == NULL) { - stat->sc.ScriptMessage("Variables may not be of type void.\n"); + stat->sc->ScriptMessage("Variables may not be of type void.\n"); } else { - stat->sc.ScriptMessage("Variables may be of only one type.\n"); + stat->sc->ScriptMessage("Variables may be of only one type.\n"); } X = NULL; } @@ -750,7 +750,7 @@ decl_flags(X) ::= decl_flags(A) ACTION(T). { X.Int = A.Int | ZCC_Action; X.Sour decl_flags(X) ::= decl_flags(A) READONLY(T). { X.Int = A.Int | ZCC_ReadOnly; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } decl_flags(X) ::= decl_flags(A) DEPRECATED(T). { X.Int = A.Int | ZCC_Deprecated; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } -func_const(X) ::= . { X.Int = 0; X.SourceLoc = stat->sc.GetMessageLine(); } +func_const(X) ::= . { X.Int = 0; X.SourceLoc = stat->sc->GetMessageLine(); } func_const(X) ::= CONST(T). { X.Int = ZCC_FuncConst; X.SourceLoc = T.SourceLoc; } opt_func_body(X) ::= SEMICOLON. { X = NULL; } diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index 1f1fa4541..054954b54 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -5,6 +5,7 @@ #include "w_wad.h" #include "cmdlib.h" #include "m_alloc.h" +#include "i_system.h" #include "zcc_parser.h" #include "zcc_compile.h" @@ -161,44 +162,26 @@ static void InitTokenMap() #undef TOKENDEF #undef TOKENDEF2 -static void DoParse(const char *filename) +static void ParseSingleFile(const char *filename, void *parser, ZCCParseState &state) { - if (TokenMap.CountUsed() == 0) - { - InitTokenMap(); - } - - FScanner sc; - void *parser; int tokentype; int lump; - bool failed; + //bool failed; ZCCToken value; + FScanner sc; lump = Wads.CheckNumForFullName(filename, true); if (lump >= 0) { sc.OpenLumpNum(lump); } - else if (FileExists(filename)) - { - sc.OpenFile(filename); - } else { Printf("Could not find script lump '%s'\n", filename); return; } - - parser = ZCCParseAlloc(malloc); - failed = false; -#ifdef _DEBUG - FILE *f = fopen("trace.txt", "w"); - char prompt = '\0'; - ZCCParseTrace(f, &prompt); -#endif - ZCCParseState state(sc); + state.sc = ≻ while (sc.GetToken()) { value.SourceLoc = sc.GetMessageLine(); @@ -241,7 +224,7 @@ static void DoParse(const char *filename) default: TokenMapEntry *zcctoken = TokenMap.CheckKey(sc.TokenType); - if (zcctoken != NULL) + if (zcctoken != nullptr) { tokentype = zcctoken->TokenType; value.Int = zcctoken->TokenName; @@ -254,20 +237,55 @@ static void DoParse(const char *filename) break; } ZCCParse(parser, tokentype, value, &state); - if (failed) - { - sc.ScriptMessage("Parse failed\n"); - goto parse_end; - } } parse_end: value.Int = -1; ZCCParse(parser, ZCC_EOF, value, &state); + state.sc = nullptr; +} + +static void DoParse(int lumpnum) +{ + if (TokenMap.CountUsed() == 0) + { + InitTokenMap(); + } + + FScanner sc; + void *parser; + ZCCToken value; + + parser = ZCCParseAlloc(malloc); + ZCCParseState state; +#ifdef _DEBUG + FILE *f = fopen("trace.txt", "w"); + char prompt = '\0'; + ZCCParseTrace(f, &prompt); +#endif + + sc.OpenLumpNum(lumpnum); + // parse all files from this list in one go. + while (sc.GetString()) + { + if (Wads.GetLumpFile(sc.LumpNum) == 0) + { + int includefile = Wads.GetLumpFile(Wads.CheckNumForFullName(sc.String, true)); + if (includefile != 0) + { + I_FatalError("File %s is overriding core lump %s.", + Wads.GetWadFullName(includefile), sc.String); + } + } + + ParseSingleFile(sc.String, parser, state); + } + + value.Int = -1; + value.SourceLoc = sc.GetMessageLine(); ZCCParse(parser, 0, value, &state); ZCCParseFree(parser, free); - PSymbolTable symbols(&GlobalSymbols); - ZCCCompiler cc(state, NULL, symbols); + ZCCCompiler cc(state, NULL, GlobalSymbols); cc.Compile(); #ifdef _DEBUG if (f != NULL) @@ -275,6 +293,7 @@ parse_end: fclose(f); } FString ast = ZCC_PrintAST(state.TopNode); + FString filename = Wads.GetLumpFullName(lumpnum); FString astfile = ExtractFileBase(filename, false); astfile << ".ast"; f = fopen(astfile, "w"); @@ -286,6 +305,16 @@ parse_end: #endif } +void ParseScripts() +{ + int lump, lastlump = 0; + while ((lump = Wads.FindLump("ZSCRIPT", &lastlump)) != -1) + { + DoParse(lump); + } +} + +/* CCMD(parse) { if (argv.argc() == 2) @@ -293,6 +322,7 @@ CCMD(parse) DoParse(argv[1]); } } +*/ static FString ZCCTokenName(int terminal) { @@ -333,6 +363,6 @@ ZCC_TreeNode *ZCC_AST::InitNode(size_t size, EZCCTreeNodeType type, ZCC_TreeNode ZCC_TreeNode *ZCCParseState::InitNode(size_t size, EZCCTreeNodeType type) { ZCC_TreeNode *node = ZCC_AST::InitNode(size, type, NULL); - node->SourceName = Strings.Alloc(sc.ScriptName); + node->SourceName = Strings.Alloc(sc->ScriptName); return node; } diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index e74b5263e..507f80b9e 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -514,10 +514,10 @@ struct ZCC_AST struct ZCCParseState : public ZCC_AST { - ZCCParseState(FScanner &scanner) : sc(scanner) {} + ZCCParseState(FScanner *scanner = nullptr) : sc(scanner) {} ZCC_TreeNode *InitNode(size_t size, EZCCTreeNodeType type); - FScanner ≻ + FScanner *sc; }; #endif From fff428c71d5941a02d1032ff26a06f28979d54a3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 08:35:16 +0200 Subject: [PATCH 004/255] - added copyright headers to scripting files. --- src/zscript/ast.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/vmbuilder.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/vmdisasm.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/vmexec.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/vmframe.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/zcc_compile.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/zcc_expr.cpp | 33 +++++++++++++++++++++++++++++++++ src/zscript/zcc_parser.cpp | 33 +++++++++++++++++++++++++++++++++ 8 files changed, 264 insertions(+) diff --git a/src/zscript/ast.cpp b/src/zscript/ast.cpp index a68b1c69f..efb4a020b 100644 --- a/src/zscript/ast.cpp +++ b/src/zscript/ast.cpp @@ -1,3 +1,36 @@ +/* +** ast.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include "dobject.h" #include "sc_man.h" #include "memarena.h" diff --git a/src/zscript/vmbuilder.cpp b/src/zscript/vmbuilder.cpp index 8d7b5a8c1..fd9a0063e 100644 --- a/src/zscript/vmbuilder.cpp +++ b/src/zscript/vmbuilder.cpp @@ -1,3 +1,36 @@ +/* +** vmbuilder.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include "vmbuilder.h" //========================================================================== diff --git a/src/zscript/vmdisasm.cpp b/src/zscript/vmdisasm.cpp index 4e6f33ec7..68b92f9f3 100644 --- a/src/zscript/vmdisasm.cpp +++ b/src/zscript/vmdisasm.cpp @@ -1,3 +1,36 @@ +/* +** vmdisasm.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include "vm.h" #include "c_console.h" diff --git a/src/zscript/vmexec.cpp b/src/zscript/vmexec.cpp index 454f02d03..651090c6b 100644 --- a/src/zscript/vmexec.cpp +++ b/src/zscript/vmexec.cpp @@ -1,3 +1,36 @@ +/* +** vmexec.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include #include "vm.h" #include "xs_Float.h" diff --git a/src/zscript/vmframe.cpp b/src/zscript/vmframe.cpp index 50c7d78d9..e5e58aa47 100644 --- a/src/zscript/vmframe.cpp +++ b/src/zscript/vmframe.cpp @@ -1,3 +1,36 @@ +/* +** vmframe.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include #include "vm.h" diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index b7bfe81ba..e6d2e6d96 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -1,3 +1,36 @@ +/* +** zcc_compile.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include "dobject.h" #include "sc_man.h" #include "c_console.h" diff --git a/src/zscript/zcc_expr.cpp b/src/zscript/zcc_expr.cpp index e1a091b18..6f640d8f1 100644 --- a/src/zscript/zcc_expr.cpp +++ b/src/zscript/zcc_expr.cpp @@ -1,3 +1,36 @@ +/* +** zcc_expr.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include #include "dobject.h" #include "sc_man.h" diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index 054954b54..ed41253e1 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -1,3 +1,36 @@ +/* +** zcc_expr.cpp +** +**--------------------------------------------------------------------------- +** Copyright -2016 Randy Heit +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + #include "dobject.h" #include "sc_man.h" #include "c_console.h" From b71e8d09edd031f8b8a42c985f1610ae539abef2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 11:54:33 +0200 Subject: [PATCH 005/255] - create class types from the AST. This is the first thing the compiler has to do to get access to the class's symbol table. Of course at this point the final size of a class is not known yet so these are currently all treated as tentative. --- src/zscript/zcc-parse.lemon | 5 +- src/zscript/zcc_compile.cpp | 118 ++++++++++++++++++++++++++++++++++++ src/zscript/zcc_compile.h | 1 + src/zscript/zcc_parser.cpp | 27 ++++++++- src/zscript/zcc_parser.h | 4 +- 5 files changed, 149 insertions(+), 6 deletions(-) diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index cd2ed8efe..6d22f9ea4 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -175,6 +175,7 @@ class_head(X) ::= CLASS(T) IDENTIFIER(A) class_ancestry(B) class_flags(C). head->ParentName = B; head->Flags = C.Flags; head->Replaces = C.Replaces; + head->Type = nullptr; X = head; } @@ -184,8 +185,8 @@ class_ancestry(X) ::= COLON dottable_id(A). { X = A; /*X-overwrites-A*/ } %type class_flags{ClassFlagsBlock} class_flags(X) ::= . { X.Flags = 0; X.Replaces = NULL; } -class_flags(X) ::= class_flags(A) ABSTRACT. { X.Flags = A.Flags | 0/*FIXME*/; X.Replaces = A.Replaces; } -class_flags(X) ::= class_flags(A) NATIVE. { X.Flags = A.Flags | 0/*FIXME*/; X.Replaces = A.Replaces; } +class_flags(X) ::= class_flags(A) ABSTRACT. { X.Flags = A.Flags | ZCC_Abstract; X.Replaces = A.Replaces; } +class_flags(X) ::= class_flags(A) NATIVE. { X.Flags = A.Flags | ZCC_Native; X.Replaces = A.Replaces; } class_flags(X) ::= class_flags(A) REPLACES dottable_id(B). { X.Flags = A.Flags; X.Replaces = B; } /*----- Dottable Identifier -----*/ diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index e6d2e6d96..68261635f 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -181,10 +181,128 @@ void ZCCCompiler::MessageV(ZCC_TreeNode *node, const char *txtcolor, const char int ZCCCompiler::Compile() { + CreateClasses(); CompileConstants(Constants); return ErrorCount; } +//========================================================================== +// +// ZCCCompiler :: CreateClassTypes +// +// Creates a PClass for every class so that we get access to the symbol table +// These will be created with unknown size because for that we need to +// process all fields first, but to do that we need the PClass and some +// other info depending on the PClass. +// +//========================================================================== + +void ZCCCompiler::CreateClasses() +{ + auto OrigClasses = std::move(Classes); + Classes.Clear(); + bool donesomething = true; + while (donesomething) + { + for (unsigned i=0;iParentName != nullptr && c->ParentName->SiblingNext == c->ParentName) parent = PClass::FindClass(c->ParentName->Id); + else if (c->ParentName == nullptr) parent = RUNTIME_CLASS(DObject); + else + { + // The parent is a dotted name which the type system currently does not handle. + // Once it does this needs to be implemented here. + auto p = c->ParentName; + FString build; + + do + { + if (build.IsNotEmpty()) build += '.'; + build += FName(p->Id); + p = static_cast(p->SiblingNext); + } while (p != c->ParentName); + Error(c, "Qualified name '%s' for base class not supported in '%s'", build.GetChars(), FName(c->NodeName).GetChars()); + parent = RUNTIME_CLASS(DObject); + } + + if (parent != nullptr) + { + // The parent exists, we may create a type for this class + if (c->Flags & ZCC_Native) + { + // If this is a native class, its own type must also already exist. + auto me = PClass::FindClass(c->NodeName); + if (me == nullptr) + { + Error(c, "Unknown native class %s", FName(c->NodeName).GetChars()); + me = parent->FindClassTentative(c->NodeName); + } + else + { + DPrintf(DMSG_SPAMMY, "Registered %s as native with parent %s\n", me->TypeName.GetChars(), parent->TypeName.GetChars()); + } + c->Type = me; + } + else + { + auto me = PClass::FindClass(c->NodeName); + if (me != nullptr) + { + Error(c, "Redefining class %s", FName(c->NodeName).GetChars()); + } + else + { + me = parent->FindClassTentative(c->NodeName); + DPrintf(DMSG_SPAMMY, "Created %s with parent %s\n", me->TypeName.GetChars(), parent->TypeName.GetChars()); + } + c->Type = me; + } + Classes.Push(c); + OrigClasses.Delete(i); + i--; + donesomething = true; + } + else + { + // No base class found. Now check if something in the unprocessed classes matches. + // If not, print an error. If something is found let's retry again in the next iteration. + bool found = false; + for (auto d : OrigClasses) + { + if (d->NodeName == c->ParentName->Id) + { + found = true; + break; + } + } + if (!found) + { + Error(c, "Class %s has unknown base class %s", FName(c->NodeName).GetChars(), FName(c->ParentName->Id).GetChars()); + // create a placeholder so that the compiler can continue looking for errors. + c->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName); + Classes.Push(c); + OrigClasses.Delete(i); + donesomething = true; + } + } + } + } + + // What's left refers to some other class in the list but could not be resolved. + // This normally means a circular reference. + for (auto c : OrigClasses) + { + Error(c, "Class %s has circular inheritance", FName(c->NodeName).GetChars()); + c->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName); + Classes.Push(c); + } +} + //========================================================================== // // ZCCCompiler :: CompileConstants diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index d034464b7..24497acd9 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -8,6 +8,7 @@ public: int Compile(); private: + void CreateClasses(); void CompileConstants(const TArray &defs); PSymbolConst *CompileConstant(ZCC_ConstantDef *def); diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index ed41253e1..3a34abe07 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -318,8 +318,8 @@ static void DoParse(int lumpnum) ZCCParse(parser, 0, value, &state); ZCCParseFree(parser, free); - ZCCCompiler cc(state, NULL, GlobalSymbols); - cc.Compile(); + { + // Make a dump of the AST before running the compiler for diagnostic purposes. #ifdef _DEBUG if (f != NULL) { @@ -328,7 +328,28 @@ static void DoParse(int lumpnum) FString ast = ZCC_PrintAST(state.TopNode); FString filename = Wads.GetLumpFullName(lumpnum); FString astfile = ExtractFileBase(filename, false); - astfile << ".ast"; + astfile << "-before.ast"; + f = fopen(astfile, "w"); + if (f != NULL) + { + fputs(ast.GetChars(), f); + fclose(f); + } +#endif + } + + ZCCCompiler cc(state, NULL, GlobalSymbols); + cc.Compile(); + // ... and another one afterward so we can see what the compiler does with the data. +#ifdef _DEBUG + if (f != NULL) + { + fclose(f); + } + FString ast = ZCC_PrintAST(state.TopNode); + FString filename = Wads.GetLumpFullName(lumpnum); + FString astfile = ExtractFileBase(filename, false); + astfile << "-after.ast"; f = fopen(astfile, "w"); if (f != NULL) { diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 507f80b9e..8b82b7eae 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -16,7 +16,7 @@ struct ZCCToken ENamedName Name() { return ENamedName(Int); } }; -// Variable / Function modifiers +// Variable / Function / Class modifiers enum { ZCC_Native = 1 << 0, @@ -30,6 +30,7 @@ enum ZCC_Deprecated = 1 << 8, ZCC_ReadOnly = 1 << 9, ZCC_FuncConst = 1 << 10, + ZCC_Abstract = 1 << 11, }; // Function parameter modifiers @@ -185,6 +186,7 @@ struct ZCC_Class : ZCC_NamedNode ZCC_Identifier *Replaces; VM_UWORD Flags; ZCC_TreeNode *Body; + PClass *Type; }; struct ZCC_Struct : ZCC_NamedNode From 82ac2081b68b7efc2af584b8ff65fd43dfecf0e0 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 13:34:37 +0200 Subject: [PATCH 006/255] - create struct types. - fixed class creation. There was an infinite loop and some missing checks for native classes. - do not write the compiler's symbols to the same symbol table as the output. The output must go to GlobalSymbols but the internal symbols must go to a namespace specific table that can be discarded after compilation. --- src/dobjtype.cpp | 2 +- src/zscript/zcc-parse.lemon | 1 + src/zscript/zcc_compile.cpp | 52 +++++++++++++++++++++++-------------- src/zscript/zcc_compile.h | 6 +++-- src/zscript/zcc_parser.cpp | 3 ++- src/zscript/zcc_parser.h | 1 + 6 files changed, 41 insertions(+), 24 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 37ff26fe3..38c9f6fa2 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -3197,7 +3197,7 @@ void PClass::BuildFlatPointers () // // PClass :: NativeClass // -// Finds the underlying native type underlying this class. +// Finds the native type underlying this class. // //========================================================================== diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 6d22f9ea4..9fdc4603c 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -248,6 +248,7 @@ struct_def(X) ::= STRUCT(T) IDENTIFIER(A) LBRACE opt_struct_body(B) RBRACE opt_s NEW_AST_NODE(Struct,def,T); def->NodeName = A.Name(); def->Body = B; + def->Type = nullptr; X = def; } diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 68261635f..9dfbab847 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -51,8 +51,8 @@ // //========================================================================== -ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols) -: Outer(_outer), Symbols(&_symbols), AST(ast), ErrorCount(0), WarnCount(0) +ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, PSymbolTable &_outsymbols) +: Outer(_outer), Symbols(&_symbols), OutputSymbols(&_outsymbols), AST(ast), ErrorCount(0), WarnCount(0) { // Group top-level nodes by type if (ast.TopNode != NULL) @@ -181,11 +181,28 @@ void ZCCCompiler::MessageV(ZCC_TreeNode *node, const char *txtcolor, const char int ZCCCompiler::Compile() { - CreateClasses(); + CreateClassTypes(); + CreateStructTypes(); CompileConstants(Constants); return ErrorCount; } +//========================================================================== +// +// ZCCCompiler :: CreateStructTypes +// +// Creates a PStruct for every struct. +// +//========================================================================== + +void ZCCCompiler::CreateStructTypes() +{ + for(auto s : Structs) + { + s->Type = NewStruct(s->NodeName, nullptr); + } +} + //========================================================================== // // ZCCCompiler :: CreateClassTypes @@ -197,20 +214,20 @@ int ZCCCompiler::Compile() // //========================================================================== -void ZCCCompiler::CreateClasses() +void ZCCCompiler::CreateClassTypes() { auto OrigClasses = std::move(Classes); Classes.Clear(); bool donesomething = true; while (donesomething) { - for (unsigned i=0;iParentName != nullptr && c->ParentName->SiblingNext == c->ParentName) parent = PClass::FindClass(c->ParentName->Id); else if (c->ParentName == nullptr) parent = RUNTIME_CLASS(DObject); else @@ -235,13 +252,17 @@ void ZCCCompiler::CreateClasses() // The parent exists, we may create a type for this class if (c->Flags & ZCC_Native) { - // If this is a native class, its own type must also already exist. + // If this is a native class, its own type must also already exist and not be a runtime class. auto me = PClass::FindClass(c->NodeName); if (me == nullptr) { Error(c, "Unknown native class %s", FName(c->NodeName).GetChars()); me = parent->FindClassTentative(c->NodeName); } + else if (me->bRuntimeClass) + { + Error(c, "%s is not a native class", FName(c->NodeName).GetChars()); + } else { DPrintf(DMSG_SPAMMY, "Registered %s as native with parent %s\n", me->TypeName.GetChars(), parent->TypeName.GetChars()); @@ -250,17 +271,8 @@ void ZCCCompiler::CreateClasses() } else { - auto me = PClass::FindClass(c->NodeName); - if (me != nullptr) - { - Error(c, "Redefining class %s", FName(c->NodeName).GetChars()); - } - else - { - me = parent->FindClassTentative(c->NodeName); - DPrintf(DMSG_SPAMMY, "Created %s with parent %s\n", me->TypeName.GetChars(), parent->TypeName.GetChars()); - } - c->Type = me; + // We will never get here if the name is a duplicate, so we can just do the assignment. + c->Type = parent->FindClassTentative(c->NodeName); } Classes.Push(c); OrigClasses.Delete(i); @@ -371,7 +383,7 @@ PSymbolConst *ZCCCompiler::CompileConstant(ZCC_ConstantDef *def) sym = new PSymbolConstNumeric(def->NodeName, TypeError, 0); } def->Symbol = sym; - Symbols->ReplaceSymbol(sym); + OutputSymbols->ReplaceSymbol(sym); return sym; } diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index 24497acd9..6ef4a34f2 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -4,11 +4,12 @@ class ZCCCompiler { public: - ZCCCompiler(ZCC_AST &tree, DObject *outer, PSymbolTable &symbols); + ZCCCompiler(ZCC_AST &tree, DObject *outer, PSymbolTable &symbols, PSymbolTable &outsymbols); int Compile(); private: - void CreateClasses(); + void CreateStructTypes(); + void CreateClassTypes(); void CompileConstants(const TArray &defs); PSymbolConst *CompileConstant(ZCC_ConstantDef *def); @@ -47,6 +48,7 @@ private: DObject *Outer; PSymbolTable *Symbols; + PSymbolTable *OutputSymbols; ZCC_AST &AST; int ErrorCount; int WarnCount; diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index 3a34abe07..4f226f3f9 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -338,7 +338,8 @@ static void DoParse(int lumpnum) #endif } - ZCCCompiler cc(state, NULL, GlobalSymbols); + PSymbolTable symtable(&GlobalSymbols); + ZCCCompiler cc(state, NULL, symtable, GlobalSymbols); cc.Compile(); // ... and another one afterward so we can see what the compiler does with the data. #ifdef _DEBUG diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 8b82b7eae..31ad22c5e 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -192,6 +192,7 @@ struct ZCC_Class : ZCC_NamedNode struct ZCC_Struct : ZCC_NamedNode { ZCC_TreeNode *Body; + PStruct *Type; }; struct ZCC_Enum : ZCC_NamedNode From d139ee9f682b76b7b134360f1c94fcaba9433cc3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 15:27:20 +0200 Subject: [PATCH 007/255] - give the 'default' block its own node type in the AST. - group a class's body the same way as the global AST. Only partially implemented so far so that constants can be processed. --- src/dobjtype.h | 25 +++++++-------- src/zscript/ast.cpp | 12 +++++++- src/zscript/zcc-parse.lemon | 2 +- src/zscript/zcc_compile.cpp | 61 ++++++++++++++++++++++++++++++++----- src/zscript/zcc_compile.h | 57 ++++++++++++++++++++++++++++++++-- src/zscript/zcc_parser.h | 5 +++ 6 files changed, 138 insertions(+), 24 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index 338c51f98..d2a8aabf5 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -86,18 +86,6 @@ public: PSymbolType() : PSymbol(NAME_None) {} }; -// A symbol for a compiler tree node ---------------------------------------- - -class PSymbolTreeNode : public PSymbol -{ - DECLARE_CLASS(PSymbolTreeNode, PSymbol); -public: - struct ZCC_NamedNode *Node; - - PSymbolTreeNode(FName name, struct ZCC_NamedNode *node) : PSymbol(name), Node(node) {} - PSymbolTreeNode() : PSymbol(NAME_None) {} -}; - // A symbol table ----------------------------------------------------------- struct PSymbolTable @@ -141,6 +129,19 @@ private: friend class DObject; }; +// A symbol for a compiler tree node ---------------------------------------- + +class PSymbolTreeNode : public PSymbol +{ + DECLARE_CLASS(PSymbolTreeNode, PSymbol); +public: + struct ZCC_NamedNode *Node; + PSymbolTable Symbols; + + PSymbolTreeNode(FName name, struct ZCC_NamedNode *node) : PSymbol(name), Node(node) {} + PSymbolTreeNode() : PSymbol(NAME_None) {} +}; + extern PSymbolTable GlobalSymbols; // Basic information shared by all types ------------------------------------ diff --git a/src/zscript/ast.cpp b/src/zscript/ast.cpp index efb4a020b..a0a823b13 100644 --- a/src/zscript/ast.cpp +++ b/src/zscript/ast.cpp @@ -629,6 +629,15 @@ static void PrintCompoundStmt(FLispString &out, ZCC_TreeNode *node) out.Close(); } +static void PrintDefault(FLispString &out, ZCC_TreeNode *node) +{ + ZCC_Default *snode = (ZCC_Default *)node; + out.Break(); + out.Open("default"); + PrintNodes(out, snode->Content, false, true); + out.Close(); +} + static void PrintContinueStmt(FLispString &out, ZCC_TreeNode *node) { out.Break(); @@ -853,7 +862,8 @@ void (* const TreeNodePrinter[NUM_AST_NODE_TYPES])(FLispString &, ZCC_TreeNode * PrintConstantDef, PrintDeclarator, PrintVarDeclarator, - PrintFuncDeclarator + PrintFuncDeclarator, + PrintDefault }; FString ZCC_PrintAST(ZCC_TreeNode *root) diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 9fdc4603c..09faf9272 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -491,7 +491,7 @@ state_call_params(X) ::= LPAREN func_expr_list(A) RPAREN. { X = A; /*X-overwrite /* Definition of a default class instance. */ %type default_def {ZCC_CompoundStmt *} -default_def(X) ::= DEFAULT compound_statement(A). { X = A; /*X-overwrites-A*/ } +default_def(X) ::= DEFAULT compound_statement(A). { X = A; /*X-overwrites-A*/ X->NodeType = AST_Default; } /* Type names */ %type type_name {ZCC_BasicType *} diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 9dfbab847..d8af55394 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -45,6 +45,50 @@ #define DEFINING_CONST ((PSymbolConst *)(void *)1) +//========================================================================== +// +// ZCCCompiler :: ProcessClass +// +//========================================================================== + +void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *tnode) +{ + Classes.Push(ZCC_ClassWork(static_cast(cnode), tnode)); + ZCC_ClassWork &cls = Classes.Last(); + + auto node = cnode->Body; + + do + { + switch (node->NodeType) + { + case AST_Struct: + case AST_ConstantDef: + if ((tnode = AddNamedNode(static_cast(node)))) + { + switch (node->NodeType) + { + case AST_Struct: cls.Structs.Push(ZCC_StructWork(static_cast(node), tnode)); break; + case AST_ConstantDef: cls.Constants.Push(static_cast(node)); break; + default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); + } + } + break; + + case AST_Enum: break; + case AST_EnumTerminator:break; + + // todo + case AST_States: + case AST_VarDeclarator: + case AST_FuncDeclarator: + break; + } + node = node->SiblingNext; + } + while (node != cnode->Body); +} + //========================================================================== // // ZCCCompiler Constructor @@ -58,6 +102,7 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, if (ast.TopNode != NULL) { ZCC_TreeNode *node = ast.TopNode; + PSymbolTreeNode *tnode; do { switch (node->NodeType) @@ -65,12 +110,12 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, case AST_Class: case AST_Struct: case AST_ConstantDef: - if (AddNamedNode(static_cast(node))) + if ((tnode = AddNamedNode(static_cast(node)))) { switch (node->NodeType) { - case AST_Class: Classes.Push(static_cast(node)); break; - case AST_Struct: Structs.Push(static_cast(node)); break; + case AST_Class: ProcessClass(static_cast(node), tnode); break; + case AST_Struct: Structs.Push(ZCC_StructWork(static_cast(node), tnode)); break; case AST_ConstantDef: Constants.Push(static_cast(node)); break; default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); } @@ -99,7 +144,7 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, // //========================================================================== -bool ZCCCompiler::AddNamedNode(ZCC_NamedNode *node) +PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *parentsym) { FName name = node->NodeName; PSymbol *check = Symbols->FindSymbol(name, false); @@ -108,12 +153,14 @@ bool ZCCCompiler::AddNamedNode(ZCC_NamedNode *node) assert(check->IsA(RUNTIME_CLASS(PSymbolTreeNode))); Error(node, "Attempt to redefine '%s'", name.GetChars()); Error(static_cast(check)->Node, " Original definition is here"); - return false; + return nullptr; } else { - Symbols->AddSymbol(new PSymbolTreeNode(name, node)); - return true; + auto sy = new PSymbolTreeNode(name, node); + sy->Symbols.SetParentTable(parentsym); + Symbols->AddSymbol(sy); + return sy; } } diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index 6ef4a34f2..8b21f2617 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -1,6 +1,56 @@ #ifndef ZCC_COMPILE_H #define ZCC_COMPILE_H +struct ZCC_StructWork +{ + ZCC_Struct *strct; + PSymbolTreeNode *node; + TArray Constants; + + ZCC_StructWork(ZCC_Struct * s, PSymbolTreeNode *n) + { + strct = s; + node = n; + }; + + ZCC_Struct *operator->() + { + return strct; + } + + operator ZCC_Struct *() + { + return strct; + } + + +}; + +struct ZCC_ClassWork +{ + ZCC_Class *cls; + PSymbolTreeNode *node; + TArray Constants; + TArray Structs; + + ZCC_ClassWork(ZCC_Class * s, PSymbolTreeNode *n) + { + cls = s; + node = n; + }; + + ZCC_Class *operator->() + { + return cls; + } + + operator ZCC_Class *() + { + return cls; + } + +}; + class ZCCCompiler { public: @@ -8,16 +58,17 @@ public: int Compile(); private: + void ProcessClass(ZCC_Class *node, PSymbolTreeNode *tnode); void CreateStructTypes(); void CreateClassTypes(); void CompileConstants(const TArray &defs); PSymbolConst *CompileConstant(ZCC_ConstantDef *def); TArray Constants; - TArray Structs; - TArray Classes; + TArray Structs; + TArray Classes; - bool AddNamedNode(ZCC_NamedNode *node); + PSymbolTreeNode *AddNamedNode(ZCC_NamedNode *node, PSymbolTable *parentsym = nullptr); ZCC_Expression *Simplify(ZCC_Expression *root); ZCC_Expression *SimplifyUnary(ZCC_ExprUnary *unary); diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 31ad22c5e..8de0c3952 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -93,6 +93,7 @@ enum EZCCTreeNodeType AST_Declarator, AST_VarDeclarator, AST_FuncDeclarator, + AST_Default, NUM_AST_NODE_TYPES }; @@ -463,6 +464,10 @@ struct ZCC_FuncDeclarator : ZCC_Declarator ZCC_Statement *Body; }; +struct ZCC_Default : ZCC_CompoundStmt +{ +}; + typedef ZCC_ExprConstant *(*EvalConst1op)(ZCC_ExprConstant *); typedef ZCC_ExprConstant *(*EvalConst2op)(ZCC_ExprConstant *, ZCC_ExprConstant *, FSharedStringArena &); From 5bb6bb31cacc2406c9fb701eb82f8c7ebae03a2e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 15:39:54 +0200 Subject: [PATCH 008/255] - added ProcessStruct, analogous to ProcessClass. Now everything should be in place to resolve all constants - inside and outside classes or structs. --- src/zscript/zcc_compile.cpp | 49 +++++++++++++++++++++++++++++++++++-- src/zscript/zcc_compile.h | 1 + 2 files changed, 48 insertions(+), 2 deletions(-) diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index d8af55394..b282c29f3 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -82,13 +82,58 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *tnode) case AST_States: case AST_VarDeclarator: case AST_FuncDeclarator: + case AST_Default: break; + + default: + assert(0 && "Unhandled AST node type"); + break; } node = node->SiblingNext; } while (node != cnode->Body); } +//========================================================================== +// +// ZCCCompiler :: ProcessClass +// +//========================================================================== + +void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *tnode) +{ + Structs.Push(ZCC_StructWork(static_cast(cnode), tnode)); + ZCC_StructWork &cls = Structs.Last(); + + auto node = cnode->Body; + + do + { + switch (node->NodeType) + { + case AST_ConstantDef: + if ((tnode = AddNamedNode(static_cast(node)))) + { + cls.Constants.Push(static_cast(node)); break; + } + break; + + case AST_Enum: break; + case AST_EnumTerminator:break; + + // todo + case AST_VarDeclarator: + break; + + default: + assert(0 && "Unhandled AST node type"); + break; + } + node = node->SiblingNext; + } + while (node != cnode->Body); +} + //========================================================================== // // ZCCCompiler Constructor @@ -114,8 +159,8 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, { switch (node->NodeType) { - case AST_Class: ProcessClass(static_cast(node), tnode); break; - case AST_Struct: Structs.Push(ZCC_StructWork(static_cast(node), tnode)); break; + case AST_Class: ProcessClass(static_cast(node), tnode); break; + case AST_Struct: ProcessStruct(static_cast(node), tnode); break; case AST_ConstantDef: Constants.Push(static_cast(node)); break; default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); } diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index 8b21f2617..f92d8ad2d 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -59,6 +59,7 @@ public: private: void ProcessClass(ZCC_Class *node, PSymbolTreeNode *tnode); + void ProcessStruct(ZCC_Struct *node, PSymbolTreeNode *tnode); void CreateStructTypes(); void CreateClassTypes(); void CompileConstants(const TArray &defs); From 08f313d0118151f9641d37867020187c9bb33d65 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 22:16:10 +0200 Subject: [PATCH 009/255] - implemented complete resolving of constants - both global and class-local. This uses a different algorithm as the old implementation - instead of recursively resolving unknown symbols it will first collect all constants from all scopes and then process them in one operation, doing multiple passes over the list until no more constants can be resolved anymore. --- src/dobjtype.cpp | 11 + src/dobjtype.h | 15 ++ src/info.cpp | 1 - src/zscript/zcc-parse.lemon | 2 + src/zscript/zcc_compile.cpp | 324 +++++++++++++++++----------- src/zscript/zcc_compile.h | 27 ++- src/zscript/zcc_parser.cpp | 3 +- src/zscript/zcc_parser.h | 2 + wadsrc/static/zscript/constants.txt | 3 +- 9 files changed, 252 insertions(+), 136 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 38c9f6fa2..800416612 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2647,6 +2647,16 @@ void PClass::StaticInit () // Keep built-in classes in consistant order. I did this before, though // I'm not sure if this is really necessary to maintain any sort of sync. qsort(&AllClasses[0], AllClasses.Size(), sizeof(AllClasses[0]), cregcmp); + + // Set all symbol table relations here so that they are valid right from the start. + for (auto c : AllClasses) + { + if (c->ParentClass != nullptr) + { + c->Symbols.SetParentTable(&c->ParentClass->Symbols); + } + } + } //========================================================================== @@ -3131,6 +3141,7 @@ PClass *PClass::FindClassTentative(FName name, bool fatal) type->ParentClass = this; type->Size = TentativeClass; type->bRuntimeClass = true; + type->Symbols.SetParentTable(&Symbols); TypeTable.AddType(type, RUNTIME_CLASS(PClass), (intptr_t)type->Outer, name, bucket); return type; } diff --git a/src/dobjtype.h b/src/dobjtype.h index d2a8aabf5..1b230452b 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -99,6 +99,10 @@ struct PSymbolTable // Sets the table to use for searches if this one doesn't contain the // requested symbol. void SetParentTable (PSymbolTable *parent); + PSymbolTable *GetParentTable() const + { + return ParentSymbolTable; + } // Finds a symbol in the table, optionally searching parent tables // as well. @@ -108,6 +112,7 @@ struct PSymbolTable // specific symbol table the symbol was found in. PSymbol *FindSymbolInTable(FName symname, PSymbolTable *&symtable); + // Places the symbol in the table and returns a pointer to it or NULL if // a symbol with the same name is already in the table. This symbol is // not copied and will be freed when the symbol table is destroyed. @@ -120,6 +125,15 @@ struct PSymbolTable // Frees all symbols from this table. void ReleaseSymbols(); + // add a name to help debugging. +#ifdef _DEBUG + FString name; + void SetName(const char *nm) { name = nm; } +#else + void SetName(const char *) {} +#endif + + private: typedef TMap MapType; @@ -702,6 +716,7 @@ protected: TArray SpecialInits; virtual void Derive(PClass *newclass); void InitializeSpecials(void *addr) const; + void SetSuper(); public: typedef PClassClass MetaClass; MetaClass *GetClass() const; diff --git a/src/info.cpp b/src/info.cpp index 79c8e4268..ea6701fac 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -361,7 +361,6 @@ size_t PClassActor::PropagateMark() void PClassActor::InitializeNativeDefaults() { - Symbols.SetParentTable(&ParentClass->Symbols); assert(Defaults == NULL); Defaults = (BYTE *)M_Malloc(Size); if (ParentClass->Defaults != NULL) diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 09faf9272..7acc39212 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -176,6 +176,7 @@ class_head(X) ::= CLASS(T) IDENTIFIER(A) class_ancestry(B) class_flags(C). head->Flags = C.Flags; head->Replaces = C.Replaces; head->Type = nullptr; + head->Symbol = nullptr; X = head; } @@ -249,6 +250,7 @@ struct_def(X) ::= STRUCT(T) IDENTIFIER(A) LBRACE opt_struct_body(B) RBRACE opt_s def->NodeName = A.Name(); def->Body = B; def->Type = nullptr; + def->Symbol = nullptr; X = def; } diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index b282c29f3..59fcdf914 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -3,6 +3,7 @@ ** **--------------------------------------------------------------------------- ** Copyright -2016 Randy Heit +** Copyright 2016 Christoph Oelckers ** All rights reserved. ** ** Redistribution and use in source and binary forms, with or without @@ -41,6 +42,7 @@ #include "zcc_parser.h" #include "zcc_compile.h" #include "v_text.h" +#include "p_lnspec.h" #include "gdtoa.h" #define DEFINING_CONST ((PSymbolConst *)(void *)1) @@ -155,7 +157,7 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, case AST_Class: case AST_Struct: case AST_ConstantDef: - if ((tnode = AddNamedNode(static_cast(node)))) + if ((tnode = AddNamedNode(static_cast(node), Symbols))) { switch (node->NodeType) { @@ -204,6 +206,9 @@ PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *pa { auto sy = new PSymbolTreeNode(name, node); sy->Symbols.SetParentTable(parentsym); + FString name; + name << "nodes - " << FName(node->NodeName); + sy->Symbols.SetName(name); Symbols->AddSymbol(sy); return sy; } @@ -275,7 +280,7 @@ int ZCCCompiler::Compile() { CreateClassTypes(); CreateStructTypes(); - CompileConstants(Constants); + CompileAllConstants(); return ErrorCount; } @@ -292,6 +297,9 @@ void ZCCCompiler::CreateStructTypes() for(auto s : Structs) { s->Type = NewStruct(s->NodeName, nullptr); + s->Symbol = new PSymbolType(s->NodeName, s->Type); + s->Type->Symbols.SetName(FName(s->NodeName)); + GlobalSymbols.AddSymbol(s->Symbol); } } @@ -366,6 +374,9 @@ void ZCCCompiler::CreateClassTypes() // We will never get here if the name is a duplicate, so we can just do the assignment. c->Type = parent->FindClassTentative(c->NodeName); } + c->Symbol = new PSymbolType(c->NodeName, c->Type); + GlobalSymbols.AddSymbol(c->Symbol); + c->Type->Symbols.SetName(FName(c->NodeName).GetChars()); Classes.Push(c); OrigClasses.Delete(i); i--; @@ -389,6 +400,9 @@ void ZCCCompiler::CreateClassTypes() Error(c, "Class %s has unknown base class %s", FName(c->NodeName).GetChars(), FName(c->ParentName->Id).GetChars()); // create a placeholder so that the compiler can continue looking for errors. c->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName); + c->Symbol = new PSymbolType(c->NodeName, c->Type); + GlobalSymbols.AddSymbol(c->Symbol); + c->Type->Symbols.SetName(FName(c->NodeName).GetChars()); Classes.Push(c); OrigClasses.Delete(i); donesomething = true; @@ -403,28 +417,132 @@ void ZCCCompiler::CreateClassTypes() { Error(c, "Class %s has circular inheritance", FName(c->NodeName).GetChars()); c->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName); + c->Symbol = new PSymbolType(c->NodeName, c->Type); + c->Type->Symbols.SetName(FName(c->NodeName).GetChars()); + GlobalSymbols.AddSymbol(c->Symbol); Classes.Push(c); } } //========================================================================== // -// ZCCCompiler :: CompileConstants +// ZCCCompiler :: AddConstants // -// Make symbols from every constant defined at this level. +// Helper for CompileAllConstants // //========================================================================== -void ZCCCompiler::CompileConstants(const TArray &defs) +void ZCCCompiler::AddConstants(TArray &dest, TArray &Constants, PSymbolTable *nt, PSymbolTable *ot) { - for (unsigned i = 0; i < defs.Size(); ++i) + for (auto c : Constants) { - ZCC_ConstantDef *def = defs[i]; - if (def->Symbol == NULL) + dest.Push({ c, nt, ot }); + } +} + +//========================================================================== +// +// ZCCCompiler :: CompileAllConstants +// +// Make symbols from every constant defined at all levels. +// Since constants may only depend on other constants this can be done +// without any more involved processing of the AST as a first step. +// +//========================================================================== + +void ZCCCompiler::CompileAllConstants() +{ + // put all constants in one list to make resolving this easier. + TArray constantwork; + + AddConstants(constantwork, Constants, Symbols, OutputSymbols); + for (auto &c : Classes) + { + AddConstants(constantwork, c.Constants, &c.node->Symbols, &c->Type->Symbols); + for (auto &s : c.Structs) { - PSymbolConst *sym = CompileConstant(def); + AddConstants(constantwork, s.Constants, &s.node->Symbols, &s->Type->Symbols); } } + for (auto &s : Structs) + { + AddConstants(constantwork, s.Constants, &s.node->Symbols, &s->Type->Symbols); + } + + // Before starting to resolve the list, let's create symbols for all already resolved ones first (i.e. all literal constants), to reduce work. + for (unsigned i = 0; iValue->NodeType == AST_ExprConstant) + { + AddConstant(constantwork[i]); + // Remove the constant from the list + constantwork.Delete(i); + i--; + } + } + bool donesomething = true; + // Now go through this list until no more constants can be resolved. The remaining ones will be non-constant values. + while (donesomething && constantwork.Size() > 0) + { + donesomething = false; + for (unsigned i = 0; i < constantwork.Size(); i++) + { + if (CompileConstant(constantwork[i].node, constantwork[i].outputtable)) + { + AddConstant(constantwork[i]); + // Remove the constant from the list + constantwork.Delete(i); + i--; + donesomething = true; + } + } + } + for (unsigned i = 0; i < constantwork.Size(); i++) + { + Error(constantwork[i].node, "%s is not a constant", FName(constantwork[i].node->NodeName).GetChars()); + } +} + +//========================================================================== +// +// ZCCCompiler :: AddConstant +// +// Adds a constant to its assigned symbol table +// +//========================================================================== + +void ZCCCompiler::AddConstant(ZCC_ConstantWork &constant) +{ + auto def = constant.node; + auto val = def->Value; + if (val->NodeType == AST_ExprConstant) + { + ZCC_ExprConstant *cval = static_cast(val); + if (cval->Type == TypeString) + { + def->Symbol = new PSymbolConstString(def->NodeName, *(cval->StringVal)); + } + else if (cval->Type->IsA(RUNTIME_CLASS(PInt))) + { + def->Symbol = new PSymbolConstNumeric(def->NodeName, cval->Type, cval->IntVal); + } + else if (cval->Type->IsA(RUNTIME_CLASS(PFloat))) + { + def->Symbol = new PSymbolConstNumeric(def->NodeName, cval->Type, cval->DoubleVal); + } + else + { + Error(def->Value, "Bad type for constant definiton"); + def->Symbol = nullptr; + } + + if (def->Symbol == nullptr) + { + // Create a dummy constant so we don't make any undefined value warnings. + def->Symbol = new PSymbolConstNumeric(def->NodeName, TypeError, 0); + } + constant.outputtable->ReplaceSymbol(def->Symbol); + } } //========================================================================== @@ -432,51 +550,19 @@ void ZCCCompiler::CompileConstants(const TArray &defs) // ZCCCompiler :: CompileConstant // // For every constant definition, evaluate its value (which should result -// in a constant), and create a symbol for it. Simplify() uses recursion -// to resolve constants used before their declarations. +// in a constant), and create a symbol for it. // //========================================================================== -PSymbolConst *ZCCCompiler::CompileConstant(ZCC_ConstantDef *def) +bool ZCCCompiler::CompileConstant(ZCC_ConstantDef *def, PSymbolTable *sym) { - assert(def->Symbol == NULL); + assert(def->Symbol == nullptr); def->Symbol = DEFINING_CONST; // avoid recursion - ZCC_Expression *val = Simplify(def->Value); + ZCC_Expression *val = Simplify(def->Value, sym); def->Value = val; - PSymbolConst *sym = NULL; - if (val->NodeType == AST_ExprConstant) - { - ZCC_ExprConstant *cval = static_cast(val); - if (cval->Type == TypeString) - { - sym = new PSymbolConstString(def->NodeName, *(cval->StringVal)); - } - else if (cval->Type->IsA(RUNTIME_CLASS(PInt))) - { - sym = new PSymbolConstNumeric(def->NodeName, cval->Type, cval->IntVal); - } - else if (cval->Type->IsA(RUNTIME_CLASS(PFloat))) - { - sym = new PSymbolConstNumeric(def->NodeName, cval->Type, cval->DoubleVal); - } - else - { - Error(def->Value, "Bad type for constant definiton"); - } - } - else - { - Error(def->Value, "Constant definition requires a constant value"); - } - if (sym == NULL) - { - // Create a dummy constant so we don't make any undefined value warnings. - sym = new PSymbolConstNumeric(def->NodeName, TypeError, 0); - } - def->Symbol = sym; - OutputSymbols->ReplaceSymbol(sym); - return sym; + if (def->Symbol == DEFINING_CONST) def->Symbol = nullptr; + return (val->NodeType == AST_ExprConstant); } @@ -493,27 +579,27 @@ PSymbolConst *ZCCCompiler::CompileConstant(ZCC_ConstantDef *def) // //========================================================================== -ZCC_Expression *ZCCCompiler::Simplify(ZCC_Expression *root) +ZCC_Expression *ZCCCompiler::Simplify(ZCC_Expression *root, PSymbolTable *sym) { if (root->NodeType == AST_ExprUnary) { - return SimplifyUnary(static_cast(root)); + return SimplifyUnary(static_cast(root), sym); } else if (root->NodeType == AST_ExprBinary) { - return SimplifyBinary(static_cast(root)); + return SimplifyBinary(static_cast(root), sym); } else if (root->Operation == PEX_ID) { - return IdentifyIdentifier(static_cast(root)); + return IdentifyIdentifier(static_cast(root), sym); } else if (root->Operation == PEX_MemberAccess) { - return SimplifyMemberAccess(static_cast(root)); + return SimplifyMemberAccess(static_cast(root), sym); } else if (root->Operation == PEX_FuncCall) { - return SimplifyFunctionCall(static_cast(root)); + return SimplifyFunctionCall(static_cast(root), sym); } return root; } @@ -524,9 +610,13 @@ ZCC_Expression *ZCCCompiler::Simplify(ZCC_Expression *root) // //========================================================================== -ZCC_Expression *ZCCCompiler::SimplifyUnary(ZCC_ExprUnary *unary) +ZCC_Expression *ZCCCompiler::SimplifyUnary(ZCC_ExprUnary *unary, PSymbolTable *sym) { - unary->Operand = Simplify(unary->Operand); + unary->Operand = Simplify(unary->Operand, sym); + if (unary->Operand->Type == nullptr) + { + return unary; + } ZCC_OpProto *op = PromoteUnary(unary->Operation, unary->Operand); if (op == NULL) { // Oh, poo! @@ -545,10 +635,15 @@ ZCC_Expression *ZCCCompiler::SimplifyUnary(ZCC_ExprUnary *unary) // //========================================================================== -ZCC_Expression *ZCCCompiler::SimplifyBinary(ZCC_ExprBinary *binary) +ZCC_Expression *ZCCCompiler::SimplifyBinary(ZCC_ExprBinary *binary, PSymbolTable *sym) { - binary->Left = Simplify(binary->Left); - binary->Right = Simplify(binary->Right); + binary->Left = Simplify(binary->Left, sym); + binary->Right = Simplify(binary->Right, sym); + if (binary->Left->Type == nullptr || binary->Right->Type == nullptr) + { + // We do not know yet what this is so we cannot promote it (yet.) + return binary; + } ZCC_OpProto *op = PromoteBinary(binary->Operation, binary->Left, binary->Right); if (op == NULL) { @@ -569,32 +664,41 @@ ZCC_Expression *ZCCCompiler::SimplifyBinary(ZCC_ExprBinary *binary) // //========================================================================== -ZCC_Expression *ZCCCompiler::SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop) +ZCC_Expression *ZCCCompiler::SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop, PSymbolTable *symt) { - dotop->Left = Simplify(dotop->Left); + PSymbolTable *symtable; + + dotop->Left = Simplify(dotop->Left, symt); if (dotop->Left->Operation == PEX_TypeRef) { // Type refs can be evaluated now. PType *ref = static_cast(dotop->Left)->RefType; - PSymbolTable *symtable; PSymbol *sym = ref->Symbols.FindSymbolInTable(dotop->Right, symtable); - if (sym == NULL) - { - Error(dotop, "'%s' is not a valid member", FName(dotop->Right).GetChars()); - } - else + if (sym != nullptr) { ZCC_Expression *expr = NodeFromSymbol(sym, dotop, symtable); - if (expr == NULL) - { - Error(dotop, "Unhandled symbol type encountered"); - } - else + if (expr != nullptr) { return expr; } } } + else if (dotop->Left->Operation == PEX_Super) + { + symt = symt->GetParentTable(); + if (symt != nullptr) + { + PSymbol *sym = symt->FindSymbolInTable(dotop->Right, symtable); + if (sym != nullptr) + { + ZCC_Expression *expr = NodeFromSymbol(sym, dotop, symtable); + if (expr != nullptr) + { + return expr; + } + } + } + } return dotop; } @@ -607,12 +711,12 @@ ZCC_Expression *ZCCCompiler::SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop) // //========================================================================== -ZCC_Expression *ZCCCompiler::SimplifyFunctionCall(ZCC_ExprFuncCall *callop) +ZCC_Expression *ZCCCompiler::SimplifyFunctionCall(ZCC_ExprFuncCall *callop, PSymbolTable *sym) { ZCC_FuncParm *parm; int parmcount = 0; - callop->Function = Simplify(callop->Function); + callop->Function = Simplify(callop->Function, sym); parm = callop->Parameters; if (parm != NULL) { @@ -620,7 +724,7 @@ ZCC_Expression *ZCCCompiler::SimplifyFunctionCall(ZCC_ExprFuncCall *callop) { parmcount++; assert(parm->NodeType == AST_FuncParm); - parm->Value = Simplify(parm->Value); + parm->Value = Simplify(parm->Value, sym); parm = static_cast(parm->SiblingNext); } while (parm != callop->Parameters); @@ -751,12 +855,14 @@ ZCC_Expression *ZCCCompiler::AddCastNode(PType *type, ZCC_Expression *expr) // //========================================================================== -ZCC_Expression *ZCCCompiler::IdentifyIdentifier(ZCC_ExprID *idnode) +ZCC_Expression *ZCCCompiler::IdentifyIdentifier(ZCC_ExprID *idnode, PSymbolTable *symt) { // Check the symbol table for the identifier. PSymbolTable *table; - PSymbol *sym = Symbols->FindSymbolInTable(idnode->Identifier, table); - if (sym != NULL) + PSymbol *sym = symt->FindSymbolInTable(idnode->Identifier, table); + // GlobalSymbols cannot be the parent of a class's symbol table so we have to look for global symbols explicitly. + if (sym == nullptr && symt != &GlobalSymbols) sym = GlobalSymbols.FindSymbolInTable(idnode->Identifier, table); + if (sym != nullptr) { ZCC_Expression *node = NodeFromSymbol(sym, idnode, table); if (node != NULL) @@ -766,46 +872,26 @@ ZCC_Expression *ZCCCompiler::IdentifyIdentifier(ZCC_ExprID *idnode) } else { + // Also handle line specials. + // To call this like a function this needs to be done differently, but for resolving constants this is ok. + int spec = P_FindLineSpecial(FName(idnode->Identifier).GetChars()); + if (spec != 0) + { + ZCC_ExprConstant *val = static_cast(AST.InitNode(sizeof(*val), AST_ExprConstant, idnode)); + val->Operation = PEX_ConstValue; + val->Type = TypeSInt32; + val->IntVal = spec; + return val; + } + symt->DumpSymbolTable(); + GlobalSymbols.DumpSymbolTable(); + Error(idnode, "Unknown identifier '%s'", FName(idnode->Identifier).GetChars()); + idnode->ToErrorNode(); } - // Identifier didn't refer to anything good, so type error it. - idnode->ToErrorNode(); return idnode; } -//========================================================================== -// -// ZCCCompiler :: CompileNode -// -//========================================================================== - -PSymbol *ZCCCompiler::CompileNode(ZCC_NamedNode *node) -{ - assert(node != NULL); - if (node->NodeType == AST_ConstantDef) - { - ZCC_ConstantDef *def = static_cast(node); - PSymbolConst *sym = def->Symbol; - - if (sym == DEFINING_CONST) - { - Error(node, "Definition of '%s' is infinitely recursive", FName(node->NodeName).GetChars()); - sym = NULL; - } - else - { - assert(sym == NULL); - sym = CompileConstant(def); - } - return sym; - } - else if (node->NodeType == AST_Struct) - { - - } - return NULL; -} - //========================================================================== // // ZCCCompiler :: NodeFromSymbol @@ -814,18 +900,8 @@ PSymbol *ZCCCompiler::CompileNode(ZCC_NamedNode *node) ZCC_Expression *ZCCCompiler::NodeFromSymbol(PSymbol *sym, ZCC_Expression *source, PSymbolTable *table) { - assert(sym != NULL); - if (sym->IsA(RUNTIME_CLASS(PSymbolTreeNode))) - { - PSymbolTable *prevtable = Symbols; - Symbols = table; - sym = CompileNode(static_cast(sym)->Node); - Symbols = prevtable; - if (sym == NULL) - { - return NULL; - } - } + assert(sym != nullptr); + if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) { return NodeFromSymbolConst(static_cast(sym), source); diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index f92d8ad2d..fd6cdaee4 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -51,6 +51,13 @@ struct ZCC_ClassWork }; +struct ZCC_ConstantWork +{ + ZCC_ConstantDef *node; + PSymbolTable *nodetable; + PSymbolTable *outputtable; +}; + class ZCCCompiler { public: @@ -62,8 +69,11 @@ private: void ProcessStruct(ZCC_Struct *node, PSymbolTreeNode *tnode); void CreateStructTypes(); void CreateClassTypes(); - void CompileConstants(const TArray &defs); - PSymbolConst *CompileConstant(ZCC_ConstantDef *def); + void AddConstants(TArray &dest, TArray &Constants, PSymbolTable *nt, PSymbolTable *ot); + void CompileAllConstants(); + void AddConstant(ZCC_ConstantWork &constant); + int CompileConstants(const TArray &defs, PSymbolTable *Nodes, PSymbolTable *Output); + bool CompileConstant(ZCC_ConstantDef *def, PSymbolTable *Symbols); TArray Constants; TArray Structs; @@ -71,11 +81,11 @@ private: PSymbolTreeNode *AddNamedNode(ZCC_NamedNode *node, PSymbolTable *parentsym = nullptr); - ZCC_Expression *Simplify(ZCC_Expression *root); - ZCC_Expression *SimplifyUnary(ZCC_ExprUnary *unary); - ZCC_Expression *SimplifyBinary(ZCC_ExprBinary *binary); - ZCC_Expression *SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop); - ZCC_Expression *SimplifyFunctionCall(ZCC_ExprFuncCall *callop); + ZCC_Expression *Simplify(ZCC_Expression *root, PSymbolTable *Symbols); + ZCC_Expression *SimplifyUnary(ZCC_ExprUnary *unary, PSymbolTable *Symbols); + ZCC_Expression *SimplifyBinary(ZCC_ExprBinary *binary, PSymbolTable *Symbols); + ZCC_Expression *SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop, PSymbolTable *Symbols); + ZCC_Expression *SimplifyFunctionCall(ZCC_ExprFuncCall *callop, PSymbolTable *Symbols); ZCC_OpProto *PromoteUnary(EZCCExprType op, ZCC_Expression *&expr); ZCC_OpProto *PromoteBinary(EZCCExprType op, ZCC_Expression *&left, ZCC_Expression *&right); @@ -87,11 +97,10 @@ private: ZCC_Expression *ApplyConversion(ZCC_Expression *expr, const PType::Conversion **route, int routelen); ZCC_Expression *AddCastNode(PType *type, ZCC_Expression *expr); - ZCC_Expression *IdentifyIdentifier(ZCC_ExprID *idnode); + ZCC_Expression *IdentifyIdentifier(ZCC_ExprID *idnode, PSymbolTable *sym); ZCC_Expression *NodeFromSymbol(PSymbol *sym, ZCC_Expression *source, PSymbolTable *table); ZCC_ExprConstant *NodeFromSymbolConst(PSymbolConst *sym, ZCC_Expression *idnode); ZCC_ExprTypeRef *NodeFromSymbolType(PSymbolType *sym, ZCC_Expression *idnode); - PSymbol *CompileNode(ZCC_NamedNode *node); void Warn(ZCC_TreeNode *node, const char *msg, ...); diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index 4f226f3f9..ba08f91ef 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -338,7 +338,8 @@ static void DoParse(int lumpnum) #endif } - PSymbolTable symtable(&GlobalSymbols); + PSymbolTable symtable; + symtable.SetName("Global_Node"); ZCCCompiler cc(state, NULL, symtable, GlobalSymbols); cc.Compile(); // ... and another one afterward so we can see what the compiler does with the data. diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 8de0c3952..1da9f79ca 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -188,12 +188,14 @@ struct ZCC_Class : ZCC_NamedNode VM_UWORD Flags; ZCC_TreeNode *Body; PClass *Type; + PSymbolType *Symbol; }; struct ZCC_Struct : ZCC_NamedNode { ZCC_TreeNode *Body; PStruct *Type; + PSymbolType *Symbol; }; struct ZCC_Enum : ZCC_NamedNode diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index da22b4180..fdd1bf977 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -1,4 +1,4 @@ - +/* // Flags for A_PainAttack enum EPainAttackFlags { @@ -806,3 +806,4 @@ enum ERenderStyles STYLE_AddStencil, STYLE_AddShaded, }; +*/ \ No newline at end of file From efcd5a86833ff671e396c8ae0b84f9c3dd629188 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 22:18:51 +0200 Subject: [PATCH 010/255] - forgot to delete these lines. --- src/zscript/zcc_compile.cpp | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 59fcdf914..2a244d529 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -883,8 +883,6 @@ ZCC_Expression *ZCCCompiler::IdentifyIdentifier(ZCC_ExprID *idnode, PSymbolTable val->IntVal = spec; return val; } - symt->DumpSymbolTable(); - GlobalSymbols.DumpSymbolTable(); Error(idnode, "Unknown identifier '%s'", FName(idnode->Identifier).GetChars()); idnode->ToErrorNode(); From 6bad4809c1a479a988e3eb72b403abd441a970e6 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 8 Oct 2016 22:20:38 +0200 Subject: [PATCH 011/255] - uncommendted constants.txt after finishing work on the constants creation code. --- wadsrc/static/zscript/constants.txt | 2 -- 1 file changed, 2 deletions(-) diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index fdd1bf977..49ca667f7 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -1,4 +1,3 @@ -/* // Flags for A_PainAttack enum EPainAttackFlags { @@ -806,4 +805,3 @@ enum ERenderStyles STYLE_AddStencil, STYLE_AddShaded, }; -*/ \ No newline at end of file From 49f18c0a1912894a8fa8ada64b4a7be923acadb5 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 9 Oct 2016 09:09:17 +0200 Subject: [PATCH 012/255] - renamed the symbol tables holding the tree nodes so that the code becomes clearer to read. Necessary because the unclear naming caused: - fixed: The tree nodes for classes and struct members were stored in the global tree nodes table. - sort variable declarations into their own list for processing. --- src/dobjtype.h | 2 +- src/zscript/zcc_compile.cpp | 57 ++++++++++++++++------------- src/zscript/zcc_compile.h | 10 +++-- wadsrc/static/zscript/constants.txt | 2 +- 4 files changed, 39 insertions(+), 32 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index 1b230452b..92316107f 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -150,7 +150,7 @@ class PSymbolTreeNode : public PSymbol DECLARE_CLASS(PSymbolTreeNode, PSymbol); public: struct ZCC_NamedNode *Node; - PSymbolTable Symbols; + PSymbolTable TreeNodes; PSymbolTreeNode(FName name, struct ZCC_NamedNode *node) : PSymbol(name), Node(node) {} PSymbolTreeNode() : PSymbol(NAME_None) {} diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 2a244d529..0ecd60dee 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -53,12 +53,13 @@ // //========================================================================== -void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *tnode) +void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) { - Classes.Push(ZCC_ClassWork(static_cast(cnode), tnode)); + Classes.Push(ZCC_ClassWork(static_cast(cnode), treenode)); ZCC_ClassWork &cls = Classes.Last(); auto node = cnode->Body; + PSymbolTreeNode *childnode; do { @@ -66,12 +67,14 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *tnode) { case AST_Struct: case AST_ConstantDef: - if ((tnode = AddNamedNode(static_cast(node)))) + case AST_VarDeclarator: + if ((childnode = AddNamedNode(static_cast(node), &treenode->TreeNodes))) { switch (node->NodeType) { - case AST_Struct: cls.Structs.Push(ZCC_StructWork(static_cast(node), tnode)); break; + case AST_Struct: cls.Structs.Push(ZCC_StructWork(static_cast(node), childnode)); break; case AST_ConstantDef: cls.Constants.Push(static_cast(node)); break; + case AST_VarDeclarator: cls.Fields.Push(static_cast(node)); break; default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); } } @@ -82,7 +85,6 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *tnode) // todo case AST_States: - case AST_VarDeclarator: case AST_FuncDeclarator: case AST_Default: break; @@ -102,31 +104,34 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *tnode) // //========================================================================== -void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *tnode) +void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode) { - Structs.Push(ZCC_StructWork(static_cast(cnode), tnode)); + Structs.Push(ZCC_StructWork(static_cast(cnode), treenode)); ZCC_StructWork &cls = Structs.Last(); auto node = cnode->Body; + PSymbolTreeNode *childnode; do { switch (node->NodeType) { case AST_ConstantDef: - if ((tnode = AddNamedNode(static_cast(node)))) + case AST_VarDeclarator: + if ((childnode = AddNamedNode(static_cast(node), &treenode->TreeNodes))) { - cls.Constants.Push(static_cast(node)); break; + switch (node->NodeType) + { + case AST_ConstantDef: cls.Constants.Push(static_cast(node)); break; + case AST_VarDeclarator: cls.Fields.Push(static_cast(node)); break; + default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); + } } break; case AST_Enum: break; case AST_EnumTerminator:break; - // todo - case AST_VarDeclarator: - break; - default: assert(0 && "Unhandled AST node type"); break; @@ -143,7 +148,7 @@ void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *tnode) //========================================================================== ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, PSymbolTable &_outsymbols) -: Outer(_outer), Symbols(&_symbols), OutputSymbols(&_outsymbols), AST(ast), ErrorCount(0), WarnCount(0) +: Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast), ErrorCount(0), WarnCount(0) { // Group top-level nodes by type if (ast.TopNode != NULL) @@ -157,7 +162,7 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, case AST_Class: case AST_Struct: case AST_ConstantDef: - if ((tnode = AddNamedNode(static_cast(node), Symbols))) + if ((tnode = AddNamedNode(static_cast(node), GlobalTreeNodes))) { switch (node->NodeType) { @@ -191,10 +196,10 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, // //========================================================================== -PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *parentsym) +PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *treenodes) { FName name = node->NodeName; - PSymbol *check = Symbols->FindSymbol(name, false); + PSymbol *check = treenodes->FindSymbol(name, false); if (check != NULL) { assert(check->IsA(RUNTIME_CLASS(PSymbolTreeNode))); @@ -205,11 +210,10 @@ PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *pa else { auto sy = new PSymbolTreeNode(name, node); - sy->Symbols.SetParentTable(parentsym); FString name; name << "nodes - " << FName(node->NodeName); - sy->Symbols.SetName(name); - Symbols->AddSymbol(sy); + sy->TreeNodes.SetName(name); + treenodes->AddSymbol(sy); return sy; } } @@ -281,6 +285,7 @@ int ZCCCompiler::Compile() CreateClassTypes(); CreateStructTypes(); CompileAllConstants(); + //CompileAllFields(); return ErrorCount; } @@ -432,11 +437,11 @@ void ZCCCompiler::CreateClassTypes() // //========================================================================== -void ZCCCompiler::AddConstants(TArray &dest, TArray &Constants, PSymbolTable *nt, PSymbolTable *ot) +void ZCCCompiler::CopyConstants(TArray &dest, TArray &Constants, PSymbolTable *ot) { for (auto c : Constants) { - dest.Push({ c, nt, ot }); + dest.Push({ c, ot }); } } @@ -455,18 +460,18 @@ void ZCCCompiler::CompileAllConstants() // put all constants in one list to make resolving this easier. TArray constantwork; - AddConstants(constantwork, Constants, Symbols, OutputSymbols); + CopyConstants(constantwork, Constants, OutputSymbols); for (auto &c : Classes) { - AddConstants(constantwork, c.Constants, &c.node->Symbols, &c->Type->Symbols); + CopyConstants(constantwork, c.Constants, &c->Type->Symbols); for (auto &s : c.Structs) { - AddConstants(constantwork, s.Constants, &s.node->Symbols, &s->Type->Symbols); + CopyConstants(constantwork, s.Constants, &s->Type->Symbols); } } for (auto &s : Structs) { - AddConstants(constantwork, s.Constants, &s.node->Symbols, &s->Type->Symbols); + CopyConstants(constantwork, s.Constants, &s->Type->Symbols); } // Before starting to resolve the list, let's create symbols for all already resolved ones first (i.e. all literal constants), to reduce work. diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index fd6cdaee4..c21aabc2a 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -6,6 +6,7 @@ struct ZCC_StructWork ZCC_Struct *strct; PSymbolTreeNode *node; TArray Constants; + TArray Fields; ZCC_StructWork(ZCC_Struct * s, PSymbolTreeNode *n) { @@ -32,6 +33,7 @@ struct ZCC_ClassWork PSymbolTreeNode *node; TArray Constants; TArray Structs; + TArray Fields; ZCC_ClassWork(ZCC_Class * s, PSymbolTreeNode *n) { @@ -54,7 +56,6 @@ struct ZCC_ClassWork struct ZCC_ConstantWork { ZCC_ConstantDef *node; - PSymbolTable *nodetable; PSymbolTable *outputtable; }; @@ -69,10 +70,11 @@ private: void ProcessStruct(ZCC_Struct *node, PSymbolTreeNode *tnode); void CreateStructTypes(); void CreateClassTypes(); - void AddConstants(TArray &dest, TArray &Constants, PSymbolTable *nt, PSymbolTable *ot); + void CopyConstants(TArray &dest, TArray &Constants, PSymbolTable *ot); + void CompileAllFields(); void CompileAllConstants(); void AddConstant(ZCC_ConstantWork &constant); - int CompileConstants(const TArray &defs, PSymbolTable *Nodes, PSymbolTable *Output); + int CompileConstants(const TArray &defs, PSymbolTable *Output); bool CompileConstant(ZCC_ConstantDef *def, PSymbolTable *Symbols); TArray Constants; @@ -108,7 +110,7 @@ private: void MessageV(ZCC_TreeNode *node, const char *txtcolor, const char *msg, va_list argptr); DObject *Outer; - PSymbolTable *Symbols; + PSymbolTable *GlobalTreeNodes; PSymbolTable *OutputSymbols; ZCC_AST &AST; int ErrorCount; diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 49ca667f7..62ac81a76 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -788,7 +788,7 @@ enum EMaskRotationFlags VRF_NOPITCH = VRF_NOPITCHSTART|VRF_NOPITCHEND, }; -enum ERenderStyles +enum ERenderStyle { STYLE_None, STYLE_Normal, From ad43f2bc7ea41211214dc25ccfd166b3deb9af68 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 9 Oct 2016 15:47:31 +0200 Subject: [PATCH 013/255] - parse the list of class/struct fields and add the PField entries to their type. - fixed a few issues with trying to access a class's Type before it got initialized. --- src/dobjtype.cpp | 17 + src/dobjtype.h | 18 +- src/namedef.h | 2 + src/zscript/ast.cpp | 2 +- src/zscript/zcc-parse.lemon | 1 + src/zscript/zcc_compile.cpp | 506 ++++++++++++++++++++++++++-- src/zscript/zcc_compile.h | 19 +- src/zscript/zcc_parser.h | 4 +- wadsrc/static/zscript/constants.txt | 9 +- 9 files changed, 528 insertions(+), 50 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 800416612..78e57c229 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -82,6 +82,8 @@ PName *TypeName; PSound *TypeSound; PColor *TypeColor; PStatePointer *TypeState; +PStruct *TypeVector2; +PStruct *TypeVector3; // PRIVATE DATA DEFINITIONS ------------------------------------------------ @@ -590,6 +592,19 @@ void PType::StaticInit() TypeTable.AddType(TypeColor = new PColor); TypeTable.AddType(TypeState = new PStatePointer); + TypeVector2 = new PStruct(NAME_Vector2, nullptr); + TypeVector2->AddField(NAME_X, TypeFloat64); + TypeVector2->AddField(NAME_Y, TypeFloat64); + TypeTable.AddType(TypeVector2); + + TypeVector3 = new PStruct(NAME_Vector3, nullptr); + TypeVector3->AddField(NAME_X, TypeFloat64); + TypeVector3->AddField(NAME_Y, TypeFloat64); + TypeVector3->AddField(NAME_Z, TypeFloat64); + TypeTable.AddType(TypeVector3); + + + GlobalSymbols.AddSymbol(new PSymbolType(NAME_sByte, TypeSInt8)); GlobalSymbols.AddSymbol(new PSymbolType(NAME_Byte, TypeUInt8)); GlobalSymbols.AddSymbol(new PSymbolType(NAME_Short, TypeSInt16)); @@ -606,6 +621,8 @@ void PType::StaticInit() GlobalSymbols.AddSymbol(new PSymbolType(NAME_Sound, TypeSound)); GlobalSymbols.AddSymbol(new PSymbolType(NAME_Color, TypeColor)); GlobalSymbols.AddSymbol(new PSymbolType(NAME_State, TypeState)); + GlobalSymbols.AddSymbol(new PSymbolType(NAME_Vector2, TypeVector2)); + GlobalSymbols.AddSymbol(new PSymbolType(NAME_Vector3, TypeVector3)); } diff --git a/src/dobjtype.h b/src/dobjtype.h index 92316107f..b776fa165 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -14,11 +14,17 @@ typedef std::pair FTypeAndOffset; // Making all these different storage types use a common set of flags seems // like the simplest thing to do. -#define VARF_Optional (1<<0) // func param is optional -#define VARF_Method (1<<1) // func has an implied self parameter -#define VARF_Action (1<<2) // func has implied owner and state parameters -#define VARF_Native (1<<3) // func is native code/don't auto serialize field -#define VARF_ReadOnly (1<<4) // field is read only, do not write to it +enum +{ + VARF_Optional = (1<<0), // func param is optional + VARF_Method = (1<<1), // func has an implied self parameter + VARF_Action = (1<<2), // func has implied owner and state parameters + VARF_Native = (1<<3), // func is native code/don't auto serialize field + VARF_ReadOnly = (1<<4), // field is read only, do not write to it + VARF_Private = (1<<5), // field is private to containing class + VARF_Protected = (1<<6), // field is only accessible by containing class and children. + VARF_Deprecated = (1<<7), // Deprecated fields should output warnings when used. +}; // Symbol information ------------------------------------------------------- @@ -872,6 +878,8 @@ extern PString *TypeString; extern PName *TypeName; extern PSound *TypeSound; extern PColor *TypeColor; +extern PStruct *TypeVector2; +extern PStruct *TypeVector3; extern PStatePointer *TypeState; // A constant value --------------------------------------------------------- diff --git a/src/namedef.h b/src/namedef.h index 36953e385..f07db2ce9 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -697,6 +697,8 @@ xx(Array) xx(Sound) xx(State) xx(Fixed) +xx(Vector2) +xx(Vector3) xx(Min) xx(Max) diff --git a/src/zscript/ast.cpp b/src/zscript/ast.cpp index a0a823b13..26601d658 100644 --- a/src/zscript/ast.cpp +++ b/src/zscript/ast.cpp @@ -65,7 +65,7 @@ public: FLispString() { NestDepth = Column = 0; - WrapWidth = 72; + WrapWidth = 200; NeedSpace = false; ConsecOpens = 0; } diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 7acc39212..564b33b74 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -290,6 +290,7 @@ enum_def(X) ::= ENUM(T) IDENTIFIER(A) enum_type(B) LBRACE opt_enum_list(C) RBRAC def->NodeName = A.Name(); def->EnumType = (EZCCBuiltinType)B.Int; def->Elements = C; + def->Symbol = nullptr; // If the first element does not have an explicit value, make it 0. if (C != NULL) diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 0ecd60dee..10f84b1d3 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -60,28 +60,47 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) auto node = cnode->Body; PSymbolTreeNode *childnode; + ZCC_Enum *enumType = nullptr; - do + // Need to check if the class actually has a body. + if (node != nullptr) do { switch (node->NodeType) { case AST_Struct: case AST_ConstantDef: - case AST_VarDeclarator: + case AST_Enum: if ((childnode = AddNamedNode(static_cast(node), &treenode->TreeNodes))) { switch (node->NodeType) { - case AST_Struct: cls.Structs.Push(ZCC_StructWork(static_cast(node), childnode)); break; - case AST_ConstantDef: cls.Constants.Push(static_cast(node)); break; - case AST_VarDeclarator: cls.Fields.Push(static_cast(node)); break; - default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); + case AST_Enum: + enumType = static_cast(node); + cls.Enums.Push(enumType); + break; + + case AST_Struct: + ProcessStruct(static_cast(node), childnode, cls.cls); + break; + + case AST_ConstantDef: + cls.Constants.Push(static_cast(node)); + cls.Constants.Last()->Type = enumType; + break; + + default: + assert(0 && "Default case is just here to make GCC happy. It should never be reached"); } } break; - case AST_Enum: break; - case AST_EnumTerminator:break; + case AST_VarDeclarator: + cls.Fields.Push(static_cast(node)); + break; + + case AST_EnumTerminator: + enumType = nullptr; + break; // todo case AST_States: @@ -100,37 +119,53 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) //========================================================================== // -// ZCCCompiler :: ProcessClass +// ZCCCompiler :: ProcessStruct // //========================================================================== -void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode) +void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode, ZCC_Class *outer) { - Structs.Push(ZCC_StructWork(static_cast(cnode), treenode)); + Structs.Push(ZCC_StructWork(static_cast(cnode), treenode, outer)); ZCC_StructWork &cls = Structs.Last(); auto node = cnode->Body; PSymbolTreeNode *childnode; + ZCC_Enum *enumType = nullptr; - do + // Need to check if the struct actually has a body. + if (node != nullptr) do { switch (node->NodeType) { case AST_ConstantDef: - case AST_VarDeclarator: + case AST_Enum: if ((childnode = AddNamedNode(static_cast(node), &treenode->TreeNodes))) { switch (node->NodeType) { - case AST_ConstantDef: cls.Constants.Push(static_cast(node)); break; - case AST_VarDeclarator: cls.Fields.Push(static_cast(node)); break; - default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); + case AST_Enum: + enumType = static_cast(node); + cls.Enums.Push(enumType); + break; + + case AST_ConstantDef: + cls.Constants.Push(static_cast(node)); + cls.Constants.Last()->Type = enumType; + break; + + default: + assert(0 && "Default case is just here to make GCC happy. It should never be reached"); } } break; - case AST_Enum: break; - case AST_EnumTerminator:break; + case AST_VarDeclarator: + cls.Fields.Push(static_cast(node)); + break; + + case AST_EnumTerminator: + enumType = nullptr; + break; default: assert(0 && "Unhandled AST node type"); @@ -148,13 +183,16 @@ void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode) //========================================================================== ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, PSymbolTable &_outsymbols) -: Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast), ErrorCount(0), WarnCount(0) + : Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast), ErrorCount(0), WarnCount(0) { // Group top-level nodes by type if (ast.TopNode != NULL) { ZCC_TreeNode *node = ast.TopNode; PSymbolTreeNode *tnode; + PType *enumType = nullptr; + ZCC_Enum *zenumType = nullptr; + do { switch (node->NodeType) @@ -162,28 +200,46 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, case AST_Class: case AST_Struct: case AST_ConstantDef: + case AST_Enum: if ((tnode = AddNamedNode(static_cast(node), GlobalTreeNodes))) { switch (node->NodeType) { - case AST_Class: ProcessClass(static_cast(node), tnode); break; - case AST_Struct: ProcessStruct(static_cast(node), tnode); break; - case AST_ConstantDef: Constants.Push(static_cast(node)); break; - default: assert(0 && "Default case is just here to make GCC happy. It should never be reached"); + case AST_Enum: + zenumType = static_cast(node); + enumType = NewEnum(zenumType->NodeName, nullptr); + GlobalSymbols.AddSymbol(new PSymbolType(zenumType->NodeName, enumType)); + break; + + case AST_Class: + ProcessClass(static_cast(node), tnode); + break; + + case AST_Struct: + ProcessStruct(static_cast(node), tnode, nullptr); + break; + + case AST_ConstantDef: + Constants.Push(static_cast(node)); + Constants.Last()->Type = zenumType; + break; + + default: + assert(0 && "Default case is just here to make GCC happy. It should never be reached"); } } break; - case AST_Enum: break; - case AST_EnumTerminator:break; + case AST_EnumTerminator: + zenumType = nullptr; + break; default: assert(0 && "Unhandled AST node type"); break; } node = node->SiblingNext; - } - while (node != ast.TopNode); + } while (node != ast.TopNode); } } @@ -285,7 +341,7 @@ int ZCCCompiler::Compile() CreateClassTypes(); CreateStructTypes(); CompileAllConstants(); - //CompileAllFields(); + CompileAllFields(); return ErrorCount; } @@ -301,10 +357,17 @@ void ZCCCompiler::CreateStructTypes() { for(auto s : Structs) { - s->Type = NewStruct(s->NodeName, nullptr); + s.Outer = s.OuterDef == nullptr? nullptr : s.OuterDef->Type; + s->Type = NewStruct(s->NodeName, s.Outer); s->Symbol = new PSymbolType(s->NodeName, s->Type); s->Type->Symbols.SetName(FName(s->NodeName)); GlobalSymbols.AddSymbol(s->Symbol); + + for (auto e : s.Enums) + { + auto etype = NewEnum(e->NodeName, s->Type); + s->Type->Symbols.AddSymbol(new PSymbolType(e->NodeName, etype)); + } } } @@ -427,6 +490,16 @@ void ZCCCompiler::CreateClassTypes() GlobalSymbols.AddSymbol(c->Symbol); Classes.Push(c); } + + // Last but not least: Now that all classes have been created, we can create the symbols for the internal enums + for (auto cd : Classes) + { + for (auto e : cd.Enums) + { + auto etype = NewEnum(e->NodeName, cd->Type); + cd->Type->Symbols.AddSymbol(new PSymbolType(e->NodeName, etype)); + } + } } //========================================================================== @@ -464,10 +537,6 @@ void ZCCCompiler::CompileAllConstants() for (auto &c : Classes) { CopyConstants(constantwork, c.Constants, &c->Type->Symbols); - for (auto &s : c.Structs) - { - CopyConstants(constantwork, s.Constants, &s->Type->Symbols); - } } for (auto &s : Structs) { @@ -529,10 +598,16 @@ void ZCCCompiler::AddConstant(ZCC_ConstantWork &constant) } else if (cval->Type->IsA(RUNTIME_CLASS(PInt))) { + // How do we get an Enum type in here without screwing everything up??? + //auto type = def->Type != nullptr ? def->Type : cval->Type; def->Symbol = new PSymbolConstNumeric(def->NodeName, cval->Type, cval->IntVal); } else if (cval->Type->IsA(RUNTIME_CLASS(PFloat))) { + if (def->Type != nullptr) + { + Error(def, "Enum members must be integer values"); + } def->Symbol = new PSymbolConstNumeric(def->NodeName, cval->Type, cval->DoubleVal); } else @@ -974,3 +1049,368 @@ ZCC_ExprTypeRef *ZCCCompiler::NodeFromSymbolType(PSymbolType *sym, ZCC_Expressio ref->Type = NewClassPointer(RUNTIME_CLASS(PType)); return ref; } + +//========================================================================== +// +// ZCCCompiler :: CompileAllFields +// +// builds the internal structure of all classes and structs +// +//========================================================================== + +void ZCCCompiler::CompileAllFields() +{ + // Create copies of the arrays which can be altered + auto Classes = this->Classes; + auto Structs = this->Structs; + + // first step: Look for native classes with native children. + // These may not have any variables added to them because it'd clash with the native definitions. + for (unsigned i = 0; i < Classes.Size(); i++) + { + auto c = Classes[i]; + + if (c->Type->Size != TentativeClass && c.Fields.Size() > 0) + { + // We need to search the global class table here because not all children may have a scripted definition attached. + for (auto ac : PClass::AllClasses) + { + if (ac->ParentClass == c->Type && ac->Size != TentativeClass) + { + Error(c, "Trying to add fields to class '%s' with native children", c->Type->TypeName.GetChars()); + Classes.Delete(i); + i--; + break; + } + } + } + } + bool donesomething = true; + while (donesomething && (Structs.Size() > 0 || Classes.Size() > 0)) + { + donesomething = false; + for (unsigned i = 0; i < Structs.Size(); i++) + { + if (CompileFields(Structs[i]->Type, Structs[i].Fields, Structs[i].Outer, true)) + { + // Remove from the list if all fields got compiled. + Structs.Delete(i); + i--; + donesomething = true; + } + } + for (unsigned i = 0; i < Classes.Size(); i++) + { + if (Classes[i]->Type->Size == TentativeClass) + { + if (Classes[i]->Type->ParentClass->Size == TentativeClass) + { + // we do not know the parent class's size yet, so skip this class for now. + continue; + } + else + { + // Inherit the size of the parent class + Classes[i]->Type->Size = Classes[i]->Type->ParentClass->Size; + } + } + if (CompileFields(Classes[i]->Type, Classes[i].Fields, nullptr, false)) + { + // Remove from the list if all fields got compiled. + Classes.Delete(i); + i--; + donesomething = true; + } + } + } + // report all entries + if (Structs.Size() > 0) + { + } + if (Classes.Size() > 0) + { + } +} + +//========================================================================== +// +// ZCCCompiler :: CompileFields +// +// builds the internal structure of a single class or struct +// +//========================================================================== + +bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fields, PClass *Outer, bool forstruct) +{ + Printf("Adding fields to %s, original size is %d\n", type->TypeName.GetChars(), type->Size); + while (Fields.Size() > 0) + { + auto field = Fields[0]; + + PType *fieldtype = DetermineType(type, field, field->Type, true); + + // For structs only allow 'deprecated', for classes exclude function qualifiers. + int notallowed = forstruct? ~ZCC_Deprecated : ZCC_Latent | ZCC_Final | ZCC_Action | ZCC_Static | ZCC_FuncConst | ZCC_Abstract; + + if (field->Flags & notallowed) + { + Error(field, "Invalid qualifiers for %s (%s not allowed)", FName(field->Names->Name).GetChars(), FlagsToString(field->Flags & notallowed)); + field->Flags &= notallowed; + } + uint32_t varflags; + + // These map directly to implementation flags. + if (field->Flags & ZCC_Private) varflags |= VARF_Private; + if (field->Flags & ZCC_Protected) varflags |= VARF_Protected; + if (field->Flags & ZCC_Deprecated) varflags |= VARF_Deprecated; + if (field->Flags & ZCC_ReadOnly) varflags |= VARF_ReadOnly; + + if (field->Flags & ZCC_Native) + { + // todo: get the native address of this field. + } + if (field->Flags & ZCC_Meta) + { + varflags |= VARF_ReadOnly; // metadata implies readonly + // todo: this needs to go into the metaclass and needs some handling + } + + if (field->Type->ArraySize != nullptr) + { + fieldtype = ResolveArraySize(fieldtype, field->Type->ArraySize, &type->Symbols); + } + + auto name = field->Names; + do + { + auto thisfieldtype = fieldtype; + if (name->ArraySize != nullptr) + { + thisfieldtype = ResolveArraySize(thisfieldtype, name->ArraySize, &type->Symbols); + } + + type->AddField(name->Name, thisfieldtype, varflags); + Printf("Added field %s, new size is %d\n", FName(name->Name).GetChars(), type->Size); + name = static_cast(name->SiblingNext); + } while (name != field->Names); + Fields.Delete(0); + + + + + } + if (Fields.Size() > 0) + { + Printf("%d fields unprocessed\n", Fields.Size()); + } + return Fields.Size() == 0; +} + +//========================================================================== +// +// ZCCCompiler :: FieldFlagsToString +// +// creates a string for a field's flags +// +//========================================================================== + +FString ZCCCompiler::FlagsToString(uint32_t flags) +{ + const char *flagnames[] = { "native", "static", "private", "protected", "latent", "final", "meta", "action", "deprecated", "readonly", "funcconst", "abstract" }; + FString build; + + for (int i = 0; i < 12; i++) + { + if (flags & (1 << i)) + { + if (build.IsNotEmpty()) build += ", "; + build += flagnames[i]; + } + } + return build; +} + +//========================================================================== +// +// ZCCCompiler :: DetermineType +// +// retrieves the type for this field, for arrays the type of a single entry. +// +//========================================================================== + +PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZCC_Type *ztype, bool allowarraytypes) +{ + if (!allowarraytypes && ztype->ArraySize != nullptr) + { + Error(field, "%s: Array type not allowed", FName(field->Names->Name).GetChars()); + return TypeError; + } + switch (ztype->NodeType) + { + case AST_BasicType: + { + auto btype = static_cast(ztype); + switch (btype->Type) + { + case ZCC_SInt8: + return TypeSInt8; + + case ZCC_UInt8: + return TypeUInt8; + + case ZCC_SInt16: + return TypeSInt16; + + case ZCC_UInt16: + return TypeUInt16; + + case ZCC_SInt32: + case ZCC_IntAuto: // todo: for enums, autoselect appropriately sized int + return TypeSInt32; + + case ZCC_UInt32: + return TypeUInt32; + + case ZCC_Bool: + return TypeBool; + + // Do we really want to allow single precision floats, despite all the problems they cause? + // These are nearly guaranteed to desync between MSVC and GCC on x87, because GCC does not implement an IEEE compliant mode + case ZCC_Float32: + case ZCC_FloatAuto: + //return TypeFloat32; + case ZCC_Float64: + return TypeFloat64; + + case ZCC_String: + return TypeString; + + case ZCC_Name: + return TypeName; + + case ZCC_Vector2: + return TypeVector2; + + case ZCC_Vector3: + return TypeVector3; + + case ZCC_Vector4: + // This has almost no use, so we really shouldn't bother. + Error(field, "vector<4> not implemented for %s", FName(field->Names->Name).GetChars()); + return TypeError; + + case ZCC_UserType: + return ResolveUserType(btype, &outertype->Symbols); + break; + } + } + + case AST_MapType: + if (allowarraytypes) + { + Error(field, "%s: Map types not implemented yet", FName(field->Names->Name).GetChars()); + // Todo: Decide what we allow here and if it makes sense to allow more complex constructs. + auto mtype = static_cast(ztype); + return NewMap(DetermineType(outertype, field, mtype->KeyType, false), DetermineType(outertype, field, mtype->ValueType, false)); + } + break; + + case AST_DynArrayType: + if (allowarraytypes) + { + Error(field, "%s: Dynamic array types not implemented yet", FName(field->Names->Name).GetChars()); + auto atype = static_cast(ztype); + return NewDynArray(DetermineType(outertype, field, atype->ElementType, false)); + } + break; + + case AST_ClassType: + { + auto ctype = static_cast(ztype); + if (ctype->Restriction == nullptr) + { + return NewClassPointer(RUNTIME_CLASS(DObject)); + } + else + { + auto sym = outertype->Symbols.FindSymbol(ctype->Restriction->Id, true); + if (sym == nullptr) sym = GlobalSymbols.FindSymbol(ctype->Restriction->Id, false); + if (sym == nullptr) + { + Error(field, "%s: Unknown identifier", FName(ctype->Restriction->Id).GetChars()); + return TypeError; + } + auto typesym = dyn_cast(sym); + if (typesym == nullptr || !typesym->Type->IsKindOf(RUNTIME_CLASS(PClass))) + { + Error(field, "%s does not represent a class type", FName(ctype->Restriction->Id).GetChars()); + return TypeError; + } + return NewClassPointer(static_cast(typesym->Type)); + } + } + } + return TypeError; +} + +//========================================================================== +// +// ZCCCompiler :: ResolveUserType +// +// resolves a user type and returns a matching PType +// +//========================================================================== + +PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt) +{ + Printf("Resolving user type %s\n", FName(type->UserType->Id).GetChars()); + // Check the symbol table for the identifier. + PSymbolTable *table; + PSymbol *sym = symt->FindSymbolInTable(type->UserType->Id, table); + // GlobalSymbols cannot be the parent of a class's symbol table so we have to look for global symbols explicitly. + if (sym == nullptr && symt != &GlobalSymbols) sym = GlobalSymbols.FindSymbolInTable(type->UserType->Id, table); + if (sym != nullptr && sym->IsKindOf(RUNTIME_CLASS(PSymbolType))) + { + auto type = static_cast(sym)->Type; + if (type->IsKindOf(RUNTIME_CLASS(PEnum))) + { + return TypeSInt32; // hack this to an integer until we can resolve the enum mess. + } + return type; + } + return TypeError; +} + + +//========================================================================== +// +// ZCCCompiler :: ResolveArraySize +// +// resolves the array size and returns a matching type. +// +//========================================================================== + +PType *ZCCCompiler::ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym) +{ + // The duplicate Simplify call is necessary because if the head node gets replaced there is no way to detect the end of the list otherwise. + arraysize = Simplify(arraysize, sym); + ZCC_Expression *val; + do + { + val = Simplify(arraysize, sym); + if (val->Operation != PEX_ConstValue || !val->Type->IsA(RUNTIME_CLASS(PInt))) + { + Error(arraysize, "Array index must be an integer constant"); + return TypeError; + } + int size = static_cast(val)->IntVal; + if (size < 1) + { + Error(arraysize, "Array size must be positive"); + return TypeError; + } + baseType = NewArray(baseType, size); + val = static_cast(val->SiblingNext); + } while (val != arraysize); + return baseType; +} diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index c21aabc2a..cf871cfaa 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -4,14 +4,19 @@ struct ZCC_StructWork { ZCC_Struct *strct; + ZCC_Class *OuterDef; + PClass *Outer; PSymbolTreeNode *node; + TArray Enums; TArray Constants; TArray Fields; - ZCC_StructWork(ZCC_Struct * s, PSymbolTreeNode *n) + ZCC_StructWork(ZCC_Struct * s, PSymbolTreeNode *n, ZCC_Class *outer) { strct = s; node = n; + OuterDef = outer; + Outer = nullptr; }; ZCC_Struct *operator->() @@ -31,8 +36,8 @@ struct ZCC_ClassWork { ZCC_Class *cls; PSymbolTreeNode *node; + TArray Enums; TArray Constants; - TArray Structs; TArray Fields; ZCC_ClassWork(ZCC_Class * s, PSymbolTreeNode *n) @@ -67,16 +72,22 @@ public: private: void ProcessClass(ZCC_Class *node, PSymbolTreeNode *tnode); - void ProcessStruct(ZCC_Struct *node, PSymbolTreeNode *tnode); + void ProcessStruct(ZCC_Struct *node, PSymbolTreeNode *tnode, ZCC_Class *outer); void CreateStructTypes(); void CreateClassTypes(); void CopyConstants(TArray &dest, TArray &Constants, PSymbolTable *ot); - void CompileAllFields(); void CompileAllConstants(); void AddConstant(ZCC_ConstantWork &constant); int CompileConstants(const TArray &defs, PSymbolTable *Output); bool CompileConstant(ZCC_ConstantDef *def, PSymbolTable *Symbols); + void CompileAllFields(); + bool CompileFields(PStruct *type, TArray &Fields, PClass *Outer, bool forstruct); + FString FlagsToString(uint32_t flags); + PType *DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZCC_Type *ztype, bool allowarraytypes); + PType *ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym); + PType *ResolveUserType(ZCC_BasicType *type, PSymbolTable *sym); + TArray Constants; TArray Structs; TArray Classes; diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 1da9f79ca..8db0221ee 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -179,6 +179,7 @@ struct ZCC_Identifier : ZCC_TreeNode struct ZCC_NamedNode : ZCC_TreeNode { ENamedName NodeName; + PSymbolType *Symbol; }; struct ZCC_Class : ZCC_NamedNode @@ -188,14 +189,12 @@ struct ZCC_Class : ZCC_NamedNode VM_UWORD Flags; ZCC_TreeNode *Body; PClass *Type; - PSymbolType *Symbol; }; struct ZCC_Struct : ZCC_NamedNode { ZCC_TreeNode *Body; PStruct *Type; - PSymbolType *Symbol; }; struct ZCC_Enum : ZCC_NamedNode @@ -444,6 +443,7 @@ struct ZCC_ConstantDef : ZCC_NamedNode { ZCC_Expression *Value; PSymbolConst *Symbol; + ZCC_Enum *Type; // gets set when the constant originates from an enum. }; struct ZCC_Declarator : ZCC_TreeNode diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 62ac81a76..12604234d 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -74,6 +74,9 @@ enum EFireBulletsFlags FBF_NOPITCH = 8, FBF_NOFLASH = 16, FBF_NORANDOMPUFFZ = 32, + FBF_PUFFTARGET = 64, + FBF_PUFFMASTER = 128, + FBF_PUFFTRACER = 256, }; // Flags for A_SpawnItemEx @@ -283,15 +286,11 @@ enum ECustomPunchFlags CPF_STEALARMOR = 32, }; -// Flags for A_CustomMissile -enum ECustomMissileFlags +enum EFireCustomMissileFlags { FPF_AIMATANGLE = 1, FPF_TRANSFERTRANSLATION = 2, FPF_NOAUTOAIM = 4, - FBF_PUFFTARGET = 64, - FBF_PUFFMASTER = 128, - FBF_PUFFTRACER = 256, }; // Flags for A_Teleport From 4ecd7dd13ab409045dc15ef270ae7ac8ebb711a0 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 9 Oct 2016 22:01:23 +0200 Subject: [PATCH 014/255] - a bit of cleanup. --- src/zscript/zcc_compile.cpp | 19 +++++-------------- 1 file changed, 5 insertions(+), 14 deletions(-) diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 10f84b1d3..609236b49 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -1123,12 +1123,14 @@ void ZCCCompiler::CompileAllFields() } } } - // report all entries - if (Structs.Size() > 0) + // This really should never happen, but if it does, let's better print an error. + for (auto s : Structs) { + Error(s.strct, "Unable to resolve all fields for struct %s", FName(s->NodeName).GetChars()); } - if (Classes.Size() > 0) + for (auto s : Classes) { + Error(s.cls, "Unable to resolve all fields for class %s", FName(s->NodeName).GetChars()); } } @@ -1142,7 +1144,6 @@ void ZCCCompiler::CompileAllFields() bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fields, PClass *Outer, bool forstruct) { - Printf("Adding fields to %s, original size is %d\n", type->TypeName.GetChars(), type->Size); while (Fields.Size() > 0) { auto field = Fields[0]; @@ -1190,18 +1191,9 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel } type->AddField(name->Name, thisfieldtype, varflags); - Printf("Added field %s, new size is %d\n", FName(name->Name).GetChars(), type->Size); name = static_cast(name->SiblingNext); } while (name != field->Names); Fields.Delete(0); - - - - - } - if (Fields.Size() > 0) - { - Printf("%d fields unprocessed\n", Fields.Size()); } return Fields.Size() == 0; } @@ -1363,7 +1355,6 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZC PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt) { - Printf("Resolving user type %s\n", FName(type->UserType->Id).GetChars()); // Check the symbol table for the identifier. PSymbolTable *table; PSymbol *sym = symt->FindSymbolInTable(type->UserType->Id, table); From e84d6a06d8c4ba8aa67a9b48fe4a2e8e9030d712 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 10 Oct 2016 01:18:47 +0200 Subject: [PATCH 015/255] - changed PClass:AddField so that it doesn't create defaults if none are present. The ZScript compiler will not create any defaults until after all fields have been added and this function created bad data if it was run on a class without defaults. - added checks for duplicate field names. - moved the tree node symbol tables out of PSymbolTreeNode to the worker data. That symbol is a bad location because it restricts the usefulness of the symbol class which is also needed for variables which use different AST structs. - fixed some memory management issues with the work classes for the compiler that became apparent after moving the symbol tables in there. In several places these were copied around, possibly losing data. --- src/dobjtype.cpp | 29 +++-- src/dobjtype.h | 5 +- src/zscript/zcc_compile.cpp | 208 ++++++++++++++++++++---------------- src/zscript/zcc_compile.h | 35 +++--- 4 files changed, 156 insertions(+), 121 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 78e57c229..e27559902 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -1325,7 +1325,7 @@ bool PString::ReadValue(FSerializer &ar, const char *key, void *addr) const void PString::SetDefaultValue(void *base, unsigned offset, TArray *special) const { - new((BYTE *)base + offset) FString; + if (base != nullptr) new((BYTE *)base + offset) FString; if (special != NULL) { special->Push(std::make_pair(this, offset)); @@ -1340,7 +1340,14 @@ void PString::SetDefaultValue(void *base, unsigned offset, TArrayInitializeSpecials(addr); for (auto tao : SpecialInits) { - tao.first->InitializeValue((BYTE*)addr + tao.second, Defaults + tao.second); + tao.first->InitializeValue((BYTE*)addr + tao.second, Defaults == nullptr? nullptr : Defaults + tao.second); } } @@ -3113,15 +3120,15 @@ PField *PClass::AddField(FName name, PType *type, DWORD flags) { unsigned oldsize = Size; PField *field = Super::AddField(name, type, flags); - if (field != NULL) + + // Only initialize the defaults if they have already been created. + // For ZScript this is not the case, it will first define all fields before + // setting up any defaults for any class. + if (field != nullptr && !(flags & VARF_Native) && Defaults != nullptr) { - Defaults = (BYTE *)M_Realloc(Defaults, Size); - memset(Defaults + oldsize, 0, Size - oldsize); - // If this is a native class, then we must not initialize and - // destroy any of its members. We do, however, initialize the - // default instance since it's not a normal instance of the class. - type->SetDefaultValue(Defaults, field->Offset, - bRuntimeClass ? &SpecialInits : NULL); + Defaults = (BYTE *)M_Realloc(Defaults, Size); + memset(Defaults + oldsize, 0, Size - oldsize); + type->SetDefaultValue(Defaults, field->Offset, &SpecialInits); } return field; } diff --git a/src/dobjtype.h b/src/dobjtype.h index b776fa165..0b4235a76 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -155,10 +155,9 @@ class PSymbolTreeNode : public PSymbol { DECLARE_CLASS(PSymbolTreeNode, PSymbol); public: - struct ZCC_NamedNode *Node; - PSymbolTable TreeNodes; + struct ZCC_TreeNode *Node; - PSymbolTreeNode(FName name, struct ZCC_NamedNode *node) : PSymbol(name), Node(node) {} + PSymbolTreeNode(FName name, struct ZCC_TreeNode *node) : PSymbol(name), Node(node) {} PSymbolTreeNode() : PSymbol(NAME_None) {} }; diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 609236b49..7a8f7092d 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -55,13 +55,18 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) { - Classes.Push(ZCC_ClassWork(static_cast(cnode), treenode)); - ZCC_ClassWork &cls = Classes.Last(); + Classes.Push(new ZCC_ClassWork(static_cast(cnode), treenode)); + auto cls = Classes.Last(); auto node = cnode->Body; PSymbolTreeNode *childnode; ZCC_Enum *enumType = nullptr; + FString name; + name << "nodes - " << FName(cnode->NodeName); + cls->TreeNodes.SetName(name); + + // Need to check if the class actually has a body. if (node != nullptr) do { @@ -70,22 +75,22 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) case AST_Struct: case AST_ConstantDef: case AST_Enum: - if ((childnode = AddNamedNode(static_cast(node), &treenode->TreeNodes))) + if ((childnode = AddTreeNode(static_cast(node)->NodeName, node, &cls->TreeNodes))) { switch (node->NodeType) { case AST_Enum: enumType = static_cast(node); - cls.Enums.Push(enumType); + cls->Enums.Push(enumType); break; case AST_Struct: - ProcessStruct(static_cast(node), childnode, cls.cls); + ProcessStruct(static_cast(node), childnode, cls->cls); break; case AST_ConstantDef: - cls.Constants.Push(static_cast(node)); - cls.Constants.Last()->Type = enumType; + cls->Constants.Push(static_cast(node)); + cls->Constants.Last()->Type = enumType; break; default: @@ -95,7 +100,7 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) break; case AST_VarDeclarator: - cls.Fields.Push(static_cast(node)); + cls->Fields.Push(static_cast(node)); break; case AST_EnumTerminator: @@ -125,8 +130,8 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode, ZCC_Class *outer) { - Structs.Push(ZCC_StructWork(static_cast(cnode), treenode, outer)); - ZCC_StructWork &cls = Structs.Last(); + Structs.Push(new ZCC_StructWork(static_cast(cnode), treenode, outer)); + ZCC_StructWork *cls = Structs.Last(); auto node = cnode->Body; PSymbolTreeNode *childnode; @@ -139,18 +144,18 @@ void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode, ZC { case AST_ConstantDef: case AST_Enum: - if ((childnode = AddNamedNode(static_cast(node), &treenode->TreeNodes))) + if ((childnode = AddTreeNode(static_cast(node)->NodeName, node, &cls->TreeNodes))) { switch (node->NodeType) { case AST_Enum: enumType = static_cast(node); - cls.Enums.Push(enumType); + cls->Enums.Push(enumType); break; case AST_ConstantDef: - cls.Constants.Push(static_cast(node)); - cls.Constants.Last()->Type = enumType; + cls->Constants.Push(static_cast(node)); + cls->Constants.Last()->Type = enumType; break; default: @@ -160,7 +165,7 @@ void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode, ZC break; case AST_VarDeclarator: - cls.Fields.Push(static_cast(node)); + cls->Fields.Push(static_cast(node)); break; case AST_EnumTerminator: @@ -201,7 +206,7 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, case AST_Struct: case AST_ConstantDef: case AST_Enum: - if ((tnode = AddNamedNode(static_cast(node), GlobalTreeNodes))) + if ((tnode = AddTreeNode(static_cast(node)->NodeName, node, GlobalTreeNodes))) { switch (node->NodeType) { @@ -243,19 +248,32 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, } } +ZCCCompiler::~ZCCCompiler() +{ + for (auto s : Structs) + { + delete s; + } + for (auto c : Classes) + { + delete c; + } + Structs.Clear(); + Classes.Clear(); +} + //========================================================================== // -// ZCCCompiler :: AddNamedNode +// ZCCCompiler :: AddTreeNode // // Keeps track of definition nodes by their names. Ensures that all names // in this scope are unique. // //========================================================================== -PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *treenodes) +PSymbolTreeNode *ZCCCompiler::AddTreeNode(FName name, ZCC_TreeNode *node, PSymbolTable *treenodes, bool searchparents) { - FName name = node->NodeName; - PSymbol *check = treenodes->FindSymbol(name, false); + PSymbol *check = treenodes->FindSymbol(name, searchparents); if (check != NULL) { assert(check->IsA(RUNTIME_CLASS(PSymbolTreeNode))); @@ -267,8 +285,6 @@ PSymbolTreeNode *ZCCCompiler::AddNamedNode(ZCC_NamedNode *node, PSymbolTable *tr { auto sy = new PSymbolTreeNode(name, node); FString name; - name << "nodes - " << FName(node->NodeName); - sy->TreeNodes.SetName(name); treenodes->AddSymbol(sy); return sy; } @@ -357,16 +373,16 @@ void ZCCCompiler::CreateStructTypes() { for(auto s : Structs) { - s.Outer = s.OuterDef == nullptr? nullptr : s.OuterDef->Type; - s->Type = NewStruct(s->NodeName, s.Outer); - s->Symbol = new PSymbolType(s->NodeName, s->Type); - s->Type->Symbols.SetName(FName(s->NodeName)); - GlobalSymbols.AddSymbol(s->Symbol); + s->Outer = s->OuterDef == nullptr? nullptr : s->OuterDef->Type; + s->strct->Type = NewStruct(s->NodeName(), s->Outer); + s->strct->Symbol = new PSymbolType(s->NodeName(), s->Type()); + s->Type()->Symbols.SetName(FName(s->NodeName())); + GlobalSymbols.AddSymbol(s->strct->Symbol); - for (auto e : s.Enums) + for (auto e : s->Enums) { - auto etype = NewEnum(e->NodeName, s->Type); - s->Type->Symbols.AddSymbol(new PSymbolType(e->NodeName, etype)); + auto etype = NewEnum(e->NodeName, s->Type()); + s->Type()->Symbols.AddSymbol(new PSymbolType(e->NodeName, etype)); } } } @@ -384,6 +400,8 @@ void ZCCCompiler::CreateStructTypes() void ZCCCompiler::CreateClassTypes() { + // we are going to sort the classes array so that entries are sorted in order of inheritance. + auto OrigClasses = std::move(Classes); Classes.Clear(); bool donesomething = true; @@ -395,14 +413,15 @@ void ZCCCompiler::CreateClassTypes() auto c = OrigClasses[i]; // Check if we got the parent already defined. PClass *parent; + auto ParentName = c->cls->ParentName; - if (c->ParentName != nullptr && c->ParentName->SiblingNext == c->ParentName) parent = PClass::FindClass(c->ParentName->Id); - else if (c->ParentName == nullptr) parent = RUNTIME_CLASS(DObject); + if (ParentName != nullptr && ParentName->SiblingNext == ParentName) parent = PClass::FindClass(ParentName->Id); + else if (ParentName == nullptr) parent = RUNTIME_CLASS(DObject); else { // The parent is a dotted name which the type system currently does not handle. // Once it does this needs to be implemented here. - auto p = c->ParentName; + auto p = ParentName; FString build; do @@ -410,44 +429,43 @@ void ZCCCompiler::CreateClassTypes() if (build.IsNotEmpty()) build += '.'; build += FName(p->Id); p = static_cast(p->SiblingNext); - } while (p != c->ParentName); - Error(c, "Qualified name '%s' for base class not supported in '%s'", build.GetChars(), FName(c->NodeName).GetChars()); + } while (p != ParentName); + Error(c->cls, "Qualified name '%s' for base class not supported in '%s'", build.GetChars(), FName(c->NodeName()).GetChars()); parent = RUNTIME_CLASS(DObject); } if (parent != nullptr) { // The parent exists, we may create a type for this class - if (c->Flags & ZCC_Native) + if (c->cls->Flags & ZCC_Native) { // If this is a native class, its own type must also already exist and not be a runtime class. - auto me = PClass::FindClass(c->NodeName); + auto me = PClass::FindClass(c->NodeName()); if (me == nullptr) { - Error(c, "Unknown native class %s", FName(c->NodeName).GetChars()); - me = parent->FindClassTentative(c->NodeName); + Error(c->cls, "Unknown native class %s", c->NodeName().GetChars()); + me = parent->FindClassTentative(c->NodeName()); } else if (me->bRuntimeClass) { - Error(c, "%s is not a native class", FName(c->NodeName).GetChars()); + Error(c->cls, "%s is not a native class", c->NodeName().GetChars()); } else { DPrintf(DMSG_SPAMMY, "Registered %s as native with parent %s\n", me->TypeName.GetChars(), parent->TypeName.GetChars()); } - c->Type = me; + c->cls->Type = me; } else { // We will never get here if the name is a duplicate, so we can just do the assignment. - c->Type = parent->FindClassTentative(c->NodeName); + c->cls->Type = parent->FindClassTentative(c->NodeName()); } - c->Symbol = new PSymbolType(c->NodeName, c->Type); - GlobalSymbols.AddSymbol(c->Symbol); - c->Type->Symbols.SetName(FName(c->NodeName).GetChars()); + c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); + GlobalSymbols.AddSymbol(c->cls->Symbol); + c->Type()->Symbols.SetName(c->NodeName()); Classes.Push(c); - OrigClasses.Delete(i); - i--; + OrigClasses.Delete(i--); donesomething = true; } else @@ -457,7 +475,7 @@ void ZCCCompiler::CreateClassTypes() bool found = false; for (auto d : OrigClasses) { - if (d->NodeName == c->ParentName->Id) + if (d->NodeName() == c->cls->ParentName->Id) { found = true; break; @@ -465,14 +483,14 @@ void ZCCCompiler::CreateClassTypes() } if (!found) { - Error(c, "Class %s has unknown base class %s", FName(c->NodeName).GetChars(), FName(c->ParentName->Id).GetChars()); + Error(c->cls, "Class %s has unknown base class %s", c->NodeName().GetChars(), FName(c->cls->ParentName->Id).GetChars()); // create a placeholder so that the compiler can continue looking for errors. - c->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName); - c->Symbol = new PSymbolType(c->NodeName, c->Type); - GlobalSymbols.AddSymbol(c->Symbol); - c->Type->Symbols.SetName(FName(c->NodeName).GetChars()); + c->cls->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName()); + c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); + GlobalSymbols.AddSymbol(c->cls->Symbol); + c->Type()->Symbols.SetName(c->NodeName()); Classes.Push(c); - OrigClasses.Delete(i); + OrigClasses.Delete(i--); donesomething = true; } } @@ -483,21 +501,30 @@ void ZCCCompiler::CreateClassTypes() // This normally means a circular reference. for (auto c : OrigClasses) { - Error(c, "Class %s has circular inheritance", FName(c->NodeName).GetChars()); - c->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName); - c->Symbol = new PSymbolType(c->NodeName, c->Type); - c->Type->Symbols.SetName(FName(c->NodeName).GetChars()); - GlobalSymbols.AddSymbol(c->Symbol); + Error(c->cls, "Class %s has circular inheritance", FName(c->NodeName()).GetChars()); + c->cls->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName()); + c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); + c->Type()->Symbols.SetName(FName(c->NodeName()).GetChars()); + GlobalSymbols.AddSymbol(c->cls->Symbol); Classes.Push(c); } - // Last but not least: Now that all classes have been created, we can create the symbols for the internal enums + // Last but not least: Now that all classes have been created, we can create the symbols for the internal enums and link the treenode symbol tables for (auto cd : Classes) { - for (auto e : cd.Enums) + for (auto e : cd->Enums) { - auto etype = NewEnum(e->NodeName, cd->Type); - cd->Type->Symbols.AddSymbol(new PSymbolType(e->NodeName, etype)); + auto etype = NewEnum(e->NodeName, cd->Type()); + cd->Type()->Symbols.AddSymbol(new PSymbolType(e->NodeName, etype)); + } + // Link the tree node tables. We only can do this after we know the class relations. + for (auto cc : Classes) + { + if (cc->Type() == cd->Type()->ParentClass) + { + cd->TreeNodes.SetParentTable(&cc->TreeNodes); + break; + } } } } @@ -534,13 +561,13 @@ void ZCCCompiler::CompileAllConstants() TArray constantwork; CopyConstants(constantwork, Constants, OutputSymbols); - for (auto &c : Classes) + for (auto c : Classes) { - CopyConstants(constantwork, c.Constants, &c->Type->Symbols); + CopyConstants(constantwork, c->Constants, &c->Type()->Symbols); } - for (auto &s : Structs) + for (auto s : Structs) { - CopyConstants(constantwork, s.Constants, &s->Type->Symbols); + CopyConstants(constantwork, s->Constants, &s->Type()->Symbols); } // Before starting to resolve the list, let's create symbols for all already resolved ones first (i.e. all literal constants), to reduce work. @@ -1070,16 +1097,15 @@ void ZCCCompiler::CompileAllFields() { auto c = Classes[i]; - if (c->Type->Size != TentativeClass && c.Fields.Size() > 0) + if (c->Type()->Size != TentativeClass && c->Fields.Size() > 0) { // We need to search the global class table here because not all children may have a scripted definition attached. for (auto ac : PClass::AllClasses) { - if (ac->ParentClass == c->Type && ac->Size != TentativeClass) + if (ac->ParentClass == c->Type() && ac->Size != TentativeClass) { - Error(c, "Trying to add fields to class '%s' with native children", c->Type->TypeName.GetChars()); - Classes.Delete(i); - i--; + Error(c->cls, "Trying to add fields to class '%s' with native children", c->Type()->TypeName.GetChars()); + Classes.Delete(i--); break; } } @@ -1091,19 +1117,19 @@ void ZCCCompiler::CompileAllFields() donesomething = false; for (unsigned i = 0; i < Structs.Size(); i++) { - if (CompileFields(Structs[i]->Type, Structs[i].Fields, Structs[i].Outer, true)) + if (CompileFields(Structs[i]->Type(), Structs[i]->Fields, Structs[i]->Outer, &Structs[i]->TreeNodes, true)) { // Remove from the list if all fields got compiled. - Structs.Delete(i); - i--; + Structs.Delete(i--); donesomething = true; } } for (unsigned i = 0; i < Classes.Size(); i++) { - if (Classes[i]->Type->Size == TentativeClass) + auto type = Classes[i]->Type(); + if (type->Size == TentativeClass) { - if (Classes[i]->Type->ParentClass->Size == TentativeClass) + if (type->ParentClass->Size == TentativeClass) { // we do not know the parent class's size yet, so skip this class for now. continue; @@ -1111,14 +1137,13 @@ void ZCCCompiler::CompileAllFields() else { // Inherit the size of the parent class - Classes[i]->Type->Size = Classes[i]->Type->ParentClass->Size; + type->Size = Classes[i]->Type()->ParentClass->Size; } } - if (CompileFields(Classes[i]->Type, Classes[i].Fields, nullptr, false)) + if (CompileFields(type, Classes[i]->Fields, nullptr, &Classes[i]->TreeNodes, false)) { // Remove from the list if all fields got compiled. - Classes.Delete(i); - i--; + Classes.Delete(i--); donesomething = true; } } @@ -1126,11 +1151,11 @@ void ZCCCompiler::CompileAllFields() // This really should never happen, but if it does, let's better print an error. for (auto s : Structs) { - Error(s.strct, "Unable to resolve all fields for struct %s", FName(s->NodeName).GetChars()); + Error(s->strct, "Unable to resolve all fields for struct %s", FName(s->NodeName()).GetChars()); } for (auto s : Classes) { - Error(s.cls, "Unable to resolve all fields for class %s", FName(s->NodeName).GetChars()); + Error(s->cls, "Unable to resolve all fields for class %s", FName(s->NodeName()).GetChars()); } } @@ -1142,7 +1167,7 @@ void ZCCCompiler::CompileAllFields() // //========================================================================== -bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fields, PClass *Outer, bool forstruct) +bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fields, PClass *Outer, PSymbolTable *TreeNodes, bool forstruct) { while (Fields.Size() > 0) { @@ -1158,7 +1183,7 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel Error(field, "Invalid qualifiers for %s (%s not allowed)", FName(field->Names->Name).GetChars(), FlagsToString(field->Flags & notallowed)); field->Flags &= notallowed; } - uint32_t varflags; + uint32_t varflags = 0; // These map directly to implementation flags. if (field->Flags & ZCC_Private) varflags |= VARF_Private; @@ -1184,13 +1209,16 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel auto name = field->Names; do { - auto thisfieldtype = fieldtype; - if (name->ArraySize != nullptr) + if (AddTreeNode(name->Name, name, TreeNodes, !forstruct)) { - thisfieldtype = ResolveArraySize(thisfieldtype, name->ArraySize, &type->Symbols); - } + auto thisfieldtype = fieldtype; + if (name->ArraySize != nullptr) + { + thisfieldtype = ResolveArraySize(thisfieldtype, name->ArraySize, &type->Symbols); + } - type->AddField(name->Name, thisfieldtype, varflags); + type->AddField(name->Name, thisfieldtype, varflags); + } name = static_cast(name->SiblingNext); } while (name != field->Names); Fields.Delete(0); diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index cf871cfaa..2fb83d7e6 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -3,6 +3,7 @@ struct ZCC_StructWork { + PSymbolTable TreeNodes; ZCC_Struct *strct; ZCC_Class *OuterDef; PClass *Outer; @@ -19,22 +20,22 @@ struct ZCC_StructWork Outer = nullptr; }; - ZCC_Struct *operator->() + FName NodeName() const { - return strct; + return strct->NodeName; } - operator ZCC_Struct *() + PStruct *Type() { - return strct; + return strct->Type; } - }; struct ZCC_ClassWork { ZCC_Class *cls; + PSymbolTable TreeNodes; PSymbolTreeNode *node; TArray Enums; TArray Constants; @@ -44,16 +45,16 @@ struct ZCC_ClassWork { cls = s; node = n; - }; - - ZCC_Class *operator->() - { - return cls; } - operator ZCC_Class *() + FName NodeName() const { - return cls; + return cls->NodeName; + } + + PClass *Type() + { + return cls->Type; } }; @@ -68,6 +69,7 @@ class ZCCCompiler { public: ZCCCompiler(ZCC_AST &tree, DObject *outer, PSymbolTable &symbols, PSymbolTable &outsymbols); + ~ZCCCompiler(); int Compile(); private: @@ -78,21 +80,20 @@ private: void CopyConstants(TArray &dest, TArray &Constants, PSymbolTable *ot); void CompileAllConstants(); void AddConstant(ZCC_ConstantWork &constant); - int CompileConstants(const TArray &defs, PSymbolTable *Output); bool CompileConstant(ZCC_ConstantDef *def, PSymbolTable *Symbols); void CompileAllFields(); - bool CompileFields(PStruct *type, TArray &Fields, PClass *Outer, bool forstruct); + bool CompileFields(PStruct *type, TArray &Fields, PClass *Outer, PSymbolTable *TreeNodes, bool forstruct); FString FlagsToString(uint32_t flags); PType *DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZCC_Type *ztype, bool allowarraytypes); PType *ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym); PType *ResolveUserType(ZCC_BasicType *type, PSymbolTable *sym); TArray Constants; - TArray Structs; - TArray Classes; + TArray Structs; + TArray Classes; - PSymbolTreeNode *AddNamedNode(ZCC_NamedNode *node, PSymbolTable *parentsym = nullptr); + PSymbolTreeNode *AddTreeNode(FName name, ZCC_TreeNode *node, PSymbolTable *treenodes, bool searchparents = false); ZCC_Expression *Simplify(ZCC_Expression *root, PSymbolTable *Symbols); ZCC_Expression *SimplifyUnary(ZCC_ExprUnary *unary, PSymbolTable *Symbols); From 2b9af0176ce6429bc8746c50ded8233fd11b74e2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 10 Oct 2016 16:53:24 +0200 Subject: [PATCH 016/255] - changed grammar for a class's default block to look and act like DECORATE, so that it can hook into the same property dispatcher. This had been defined as a regular compound statement but in the context this will be used in, that makes very little sense, because all it can do is set some constant values. The most important thing here is that it doesn't provide an unnecessary learning curve to its users and doing it this way will not only ensure that but also avoid redundant documentation. To allow initialization of other user-defined properties it will require some extensions but that's a job for later and can just as easily be done in the current framework, rather than throwing everything out and start from zero. --- src/zscript/ast.cpp | 24 ++++++++++++- src/zscript/zcc-parse.lemon | 68 +++++++++++++++++++++++++++++++++++-- src/zscript/zcc_parser.h | 15 ++++++++ 3 files changed, 104 insertions(+), 3 deletions(-) diff --git a/src/zscript/ast.cpp b/src/zscript/ast.cpp index 26601d658..f80498738 100644 --- a/src/zscript/ast.cpp +++ b/src/zscript/ast.cpp @@ -814,6 +814,26 @@ static void PrintFuncDeclarator(FLispString &out, ZCC_TreeNode *node) out.Close(); } +static void PrintFlagStmt(FLispString &out, ZCC_TreeNode *node) +{ + auto dnode = (ZCC_FlagStmt *)node; + out.Break(); + out.Open("flag-stmt"); + PrintNodes(out, dnode->name, false); + out.AddInt(dnode->set); + out.Close(); +} + +static void PrintPropertyStmt(FLispString &out, ZCC_TreeNode *node) +{ + auto dnode = (ZCC_PropertyStmt *)node; + out.Break(); + out.Open("property-stmt"); + PrintNodes(out, dnode->Prop, false); + PrintNodes(out, dnode->Values, false); + out.Close(); +} + void (* const TreeNodePrinter[NUM_AST_NODE_TYPES])(FLispString &, ZCC_TreeNode *) = { PrintIdentifier, @@ -863,7 +883,9 @@ void (* const TreeNodePrinter[NUM_AST_NODE_TYPES])(FLispString &, ZCC_TreeNode * PrintDeclarator, PrintVarDeclarator, PrintFuncDeclarator, - PrintDefault + PrintDefault, + PrintFlagStmt, + PrintPropertyStmt }; FString ZCC_PrintAST(ZCC_TreeNode *root) diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 564b33b74..f54a4ba74 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -493,8 +493,72 @@ state_call_params(X) ::= . { X = NULL; } state_call_params(X) ::= LPAREN func_expr_list(A) RPAREN. { X = A; /*X-overwrites-A*/ } /* Definition of a default class instance. */ -%type default_def {ZCC_CompoundStmt *} -default_def(X) ::= DEFAULT compound_statement(A). { X = A; /*X-overwrites-A*/ X->NodeType = AST_Default; } +%type default_def {ZCC_Default *} +%type default_statement_list{ZCC_Statement *} +%type default_statement{ZCC_Statement *} + +default_def(X) ::= DEFAULT LBRACE(T) RBRACE. +{ + NEW_AST_NODE(Default,stmt,T); + stmt->Content = NULL; + X = stmt; +} +default_def(X) ::= DEFAULT LBRACE(T) default_statement_list(A) RBRACE. +{ + NEW_AST_NODE(Default,stmt,T); + stmt->Content = A; + X = stmt; +} +default_def(X) ::= DEFAULT LBRACE(T) error RBRACE. +{ + NEW_AST_NODE(Default,stmt,T); + stmt->Content = NULL; + X = stmt; +} + +default_statement_list(X) ::= default_statement(A). +{ + X = A; /*X-overwrites-A*/ +} +default_statement_list(X) ::= default_statement_list(X) default_statement(B). +{ + SAFE_APPEND(X,B); +} + + +default_statement(X) ::= SEMICOLON. { X = NULL; } +//default_statement(X) ::= assign_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } +default_statement(X) ::= property_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } +default_statement(X) ::= flag_statement(A). { X = A; /*X-overwrites-A*/ } + +%type flag_statement { ZCC_FlagStmt *} + +flag_statement(X) ::= ADD dottable_id(A). +{ + NEW_AST_NODE(FlagStmt, type, A); + type->set = true; + type->name = A; + X = type; +} +flag_statement(X) ::= SUB dottable_id(A). +{ + NEW_AST_NODE(FlagStmt, type, A); + type->set = false; + type->name = A; + X = type; +} + +%type property_statement{ZCC_PropertyStmt *} + +property_statement(X) ::= dottable_id(A) expr_list(B). +{ + NEW_AST_NODE(PropertyStmt,stmt,A); + stmt->Prop = A; + stmt->Values = B; + X = stmt; +} + + /* Type names */ %type type_name {ZCC_BasicType *} diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 8db0221ee..7500185f8 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -94,6 +94,8 @@ enum EZCCTreeNodeType AST_VarDeclarator, AST_FuncDeclarator, AST_Default, + AST_FlagStmt, + AST_PropertyStmt, NUM_AST_NODE_TYPES }; @@ -470,6 +472,19 @@ struct ZCC_Default : ZCC_CompoundStmt { }; +struct ZCC_PropertyStmt : ZCC_Statement +{ + ZCC_Identifier *Prop; + ZCC_Expression *Values; +}; + + +struct ZCC_FlagStmt : ZCC_Statement +{ + ZCC_Identifier *name; + bool set; +}; + typedef ZCC_ExprConstant *(*EvalConst1op)(ZCC_ExprConstant *); typedef ZCC_ExprConstant *(*EvalConst2op)(ZCC_ExprConstant *, ZCC_ExprConstant *, FSharedStringArena &); From 3b198876372976e3dbb00002a36dd65354909194 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 11 Oct 2016 00:56:47 +0200 Subject: [PATCH 017/255] - implemented the Defaults property initializer. This uses the same property and flag tables as DECORATE with a few changes: * it sets the parse mode to strict, so that several DECORATE warnings are now errors. * trying to change a deprecated flag will print a warning. * setting of editor numbers, spawn and conversation ID id not possible. Use MAPINFO to do this. * all subclass flags must use the qualified name now (e.g. +ALWAYSPICKUP will print an error.) * the scriptable Damage property is not yet implemented. This will require a special case with a differently named property in the processing function because in the AST it is no longer possible to distinguish between a damage value and a constant damage function. --- src/dobjtype.cpp | 1 + src/g_shared/a_pickups.cpp | 2 +- src/sc_man.cpp | 3 +- src/sc_man.h | 1 + src/thingdef/thingdef.h | 5 +- src/thingdef/thingdef_data.cpp | 5 +- src/thingdef/thingdef_parse.cpp | 4 +- src/thingdef/thingdef_properties.cpp | 17 +- src/zscript/zcc-parse.lemon | 12 +- src/zscript/zcc_compile.cpp | 395 ++++++++++++++++++++++++++- src/zscript/zcc_compile.h | 18 +- 11 files changed, 438 insertions(+), 25 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index e27559902..7709bfa8f 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -3163,6 +3163,7 @@ PClass *PClass::FindClassTentative(FName name, bool fatal) type->TypeName = name; type->ParentClass = this; + type->ConstructNative = ConstructNative; type->Size = TentativeClass; type->bRuntimeClass = true; type->Symbols.SetParentTable(&Symbols); diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index e80e54818..00a6692b2 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -1696,7 +1696,7 @@ PClassHealth::PClassHealth() //=========================================================================== // -// PClassHealth :: Derive +// PClassHealth :: DeriveData // //=========================================================================== diff --git a/src/sc_man.cpp b/src/sc_man.cpp index 3f5530ff3..97f384f3d 100644 --- a/src/sc_man.cpp +++ b/src/sc_man.cpp @@ -1006,6 +1006,7 @@ void FScanner::CheckOpen() // //========================================================================== int FScriptPosition::ErrorCounter; +bool FScriptPosition::StrictErrors; // makes all OPTERRPR messages real errors. FScriptPosition::FScriptPosition(const FScriptPosition &other) { @@ -1047,7 +1048,7 @@ void FScriptPosition::Message (int severity, const char *message, ...) const if ((severity == MSG_DEBUG || severity == MSG_DEBUGLOG) && developer < DMSG_NOTIFY) return; if (severity == MSG_OPTERROR) { - severity = strictdecorate ? MSG_ERROR : MSG_WARNING; + severity = StrictErrors || strictdecorate ? MSG_ERROR : MSG_WARNING; } if (message == NULL) diff --git a/src/sc_man.h b/src/sc_man.h index 359dd8140..c319a7a2f 100644 --- a/src/sc_man.h +++ b/src/sc_man.h @@ -140,6 +140,7 @@ enum struct FScriptPosition { static int ErrorCounter; + static bool StrictErrors; FString FileName; int ScriptLine; diff --git a/src/thingdef/thingdef.h b/src/thingdef/thingdef.h index 3a419b112..426eddd41 100644 --- a/src/thingdef/thingdef.h +++ b/src/thingdef/thingdef.h @@ -25,7 +25,7 @@ struct FFlagDef int fieldsize; }; -FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2); +FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bool strict = false); void HandleDeprecatedFlags(AActor *defaults, PClassActor *info, bool set, int index); bool CheckDeprecatedFlags(const AActor *actor, PClassActor *info, int index); const char *GetFlagName(unsigned int flagnum, int flagoffset); @@ -146,6 +146,7 @@ struct Baggage PClassActor *Info; bool DropItemSet; bool StateSet; + bool fromZScript; int CurrentState; int Lumpnum; FStateDefinitions statedef; @@ -272,7 +273,7 @@ typedef void (*PropHandler)(AActor *defaults, PClassActor *info, Baggage &bag, F enum ECategory { CAT_PROPERTY, // Inheritable property - CAT_INFO // non-inheritable info (spawn ID, Doomednum, game filter, conversation ID) + CAT_INFO // non-inheritable info (spawn ID, Doomednum, game filter, conversation ID, not usable in ZScript) }; struct FPropertyInfo diff --git a/src/thingdef/thingdef_data.cpp b/src/thingdef/thingdef_data.cpp index efdd64921..bdb992fba 100644 --- a/src/thingdef/thingdef_data.cpp +++ b/src/thingdef/thingdef_data.cpp @@ -436,14 +436,15 @@ static FFlagDef *FindFlag (FFlagDef *flags, int numflags, const char *flag) // //========================================================================== -FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2) +FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bool strict) { FFlagDef *def; size_t i; if (part2 == NULL) { // Search all lists - for (i = 0; i < NUM_FLAG_LISTS; ++i) + int max = strict ? 1 : NUM_FLAG_LISTS; + for (i = 0; i < max; ++i) { if (type->IsDescendantOf (*FlagLists[i].Type)) { diff --git a/src/thingdef/thingdef_parse.cpp b/src/thingdef/thingdef_parse.cpp index 963165ab1..5789038b7 100644 --- a/src/thingdef/thingdef_parse.cpp +++ b/src/thingdef/thingdef_parse.cpp @@ -1063,7 +1063,7 @@ static void ParseActorProperty(FScanner &sc, Baggage &bag) } else { - sc.ScriptMessage("\"%s\" requires an actor of type \"%s\"\n", propname.GetChars(), (*prop->cls)->TypeName.GetChars()); + sc.ScriptMessage("'%s' requires an actor of type '%s'\n", propname.GetChars(), (*prop->cls)->TypeName.GetChars()); FScriptPosition::ErrorCounter++; } } @@ -1073,7 +1073,7 @@ static void ParseActorProperty(FScanner &sc, Baggage &bag) } else { - sc.ScriptError("\"%s\" is an unknown actor property\n", propname.GetChars()); + sc.ScriptError("'%s' is an unknown actor property\n", propname.GetChars()); } } diff --git a/src/thingdef/thingdef_properties.cpp b/src/thingdef/thingdef_properties.cpp index d60cda823..bcae82671 100644 --- a/src/thingdef/thingdef_properties.cpp +++ b/src/thingdef/thingdef_properties.cpp @@ -514,10 +514,11 @@ DEFINE_INFO_PROPERTY(conversationid, IiI, Actor) //========================================================================== DEFINE_PROPERTY(skip_super, 0, Actor) { - if (info->IsDescendantOf(RUNTIME_CLASS(AInventory))) + auto actorclass = RUNTIME_CLASS(AActor); + if (info->Size != actorclass->Size) { - bag.ScriptPosition.Message(MSG_WARNING, - "'skip_super' in definition of inventory item '%s' ignored.", info->TypeName.GetChars() ); + bag.ScriptPosition.Message(MSG_OPTERROR, + "'skip_super' is only allowed in subclasses of AActor with no additional fields and will be ignored.", info->TypeName.GetChars()); return; } if (bag.StateSet) @@ -2484,7 +2485,7 @@ DEFINE_CLASS_PROPERTY_PREFIX(player, face, S, PlayerPawn) ); if (!valid) { - bag.ScriptPosition.Message(MSG_WARNING, + bag.ScriptPosition.Message(MSG_OPTERROR, "Invalid face '%s' for '%s';\nSTF replacement codes must be 3 alphanumeric characters.\n", tmp.GetChars(), info->TypeName.GetChars ()); } @@ -2551,13 +2552,13 @@ DEFINE_CLASS_PROPERTY_PREFIX(player, colorset, ISIIIiiiiiiiiiiiiiiiiiiiiiiii, Pl } if (count != 0) { - bag.ScriptPosition.Message(MSG_WARNING, "Extra ranges require 4 parameters each.\n"); + bag.ScriptPosition.Message(MSG_OPTERROR, "Extra ranges require 4 parameters each.\n"); } } if (setnum < 0) { - bag.ScriptPosition.Message(MSG_WARNING, "Color set number must not be negative.\n"); + bag.ScriptPosition.Message(MSG_OPTERROR, "Color set number must not be negative.\n"); } else { @@ -2584,7 +2585,7 @@ DEFINE_CLASS_PROPERTY_PREFIX(player, colorsetfile, ISSI, PlayerPawn) if (setnum < 0) { - bag.ScriptPosition.Message(MSG_WARNING, "Color set number must not be negative.\n"); + bag.ScriptPosition.Message(MSG_OPTERROR, "Color set number must not be negative.\n"); } else if (color.Lump >= 0) { @@ -2602,7 +2603,7 @@ DEFINE_CLASS_PROPERTY_PREFIX(player, clearcolorset, I, PlayerPawn) if (setnum < 0) { - bag.ScriptPosition.Message(MSG_WARNING, "Color set number must not be negative.\n"); + bag.ScriptPosition.Message(MSG_OPTERROR, "Color set number must not be negative.\n"); } else { diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index f54a4ba74..09fadedb4 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -528,7 +528,7 @@ default_statement_list(X) ::= default_statement_list(X) default_statement(B). default_statement(X) ::= SEMICOLON. { X = NULL; } //default_statement(X) ::= assign_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } -default_statement(X) ::= property_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } +default_statement(X) ::= property_statement(A). { X = A; /*X-overwrites-A*/ } default_statement(X) ::= flag_statement(A). { X = A; /*X-overwrites-A*/ } %type flag_statement { ZCC_FlagStmt *} @@ -550,7 +550,7 @@ flag_statement(X) ::= SUB dottable_id(A). %type property_statement{ZCC_PropertyStmt *} -property_statement(X) ::= dottable_id(A) expr_list(B). +property_statement(X) ::= dottable_id(A) expr_list(B) SEMICOLON. { NEW_AST_NODE(PropertyStmt,stmt,A); stmt->Prop = A; @@ -558,6 +558,14 @@ property_statement(X) ::= dottable_id(A) expr_list(B). X = stmt; } +property_statement(X) ::= dottable_id(A) SEMICOLON. +{ + NEW_AST_NODE(PropertyStmt,stmt,A); + stmt->Prop = A; + stmt->Values = nullptr; + X = stmt; +} + /* Type names */ diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 7a8f7092d..98448069a 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -32,10 +32,12 @@ ** */ -#include "dobject.h" +#include "actor.h" +#include "thingdef.h" #include "sc_man.h" #include "c_console.h" #include "c_dispatch.h" +#include "doomerrors.h" #include "w_wad.h" #include "cmdlib.h" #include "m_alloc.h" @@ -110,8 +112,11 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) // todo case AST_States: case AST_FuncDeclarator: + break; + case AST_Default: - break; + cls->Defaults.Push(static_cast(node)); + break; default: assert(0 && "Unhandled AST node type"); @@ -358,6 +363,7 @@ int ZCCCompiler::Compile() CreateStructTypes(); CompileAllConstants(); CompileAllFields(); + InitDefaults(); return ErrorCount; } @@ -1433,3 +1439,388 @@ PType *ZCCCompiler::ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, } while (val != arraysize); return baseType; } + +//========================================================================== +// +// ZCCCompiler :: GetInt - Input must be a constant expression +// +//========================================================================== + +int ZCCCompiler::GetInt(ZCC_Expression *expr) +{ + if (expr->Type == TypeError) + { + return 0; + } + const PType::Conversion *route[CONVERSION_ROUTE_SIZE]; + int routelen = expr->Type->FindConversion(TypeSInt32, route, countof(route)); + if (routelen < 0) + { + Error(expr, "Cannot convert to integer"); + return 0; + } + else + { + if (expr->Type->IsKindOf(RUNTIME_CLASS(PFloat))) + { + Warn(expr, "Truncation of floating point value"); + } + auto ex = static_cast(ApplyConversion(expr, route, routelen)); + return ex->IntVal; + } +} + +double ZCCCompiler::GetDouble(ZCC_Expression *expr) +{ + if (expr->Type == TypeError) + { + return 0; + } + const PType::Conversion *route[CONVERSION_ROUTE_SIZE]; + int routelen = expr->Type->FindConversion(TypeFloat64, route, countof(route)); + if (routelen < 0) + { + Error(expr, "Cannot convert to float"); + return 0; + } + else + { + auto ex = static_cast(ApplyConversion(expr, route, routelen)); + return ex->DoubleVal; + } +} + +const char *ZCCCompiler::GetString(ZCC_Expression *expr, bool silent) +{ + if (expr->Type == TypeError) + { + return 0; + } + else if (expr->Type->IsKindOf(RUNTIME_CLASS(PString))) + { + return static_cast(expr)->StringVal->GetChars(); + } + else if (expr->Type->IsKindOf(RUNTIME_CLASS(PName))) + { + // Ugh... What a mess... + return FName(ENamedName(static_cast(expr)->IntVal)).GetChars(); + } + else + { + if (!silent) Error(expr, "Cannot convert to string"); + return 0; + } +} + +//========================================================================== +// +// Parses an actor property's parameters and calls the handler +// +//========================================================================== + +void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *property, AActor *defaults, Baggage &bag) +{ + static TArray params; + static TArray strings; + + params.Clear(); + strings.Clear(); + params.Reserve(1); + params[0].i = 0; + if (prop->params[0] != '0') + { + if (property->Values == nullptr) + { + Error(property, "%s: arguments missing", prop->name); + return; + } + property->Values = Simplify(property->Values, &bag.Info->Symbols); // need to do this before the loop so that we can find the head node again. + const char * p = prop->params; + auto exp = property->Values; + + while (true) + { + FPropParam conv; + FPropParam pref; + + if (exp->NodeType != AST_ExprConstant) + { + Error(exp, "%s: non-constant parameter", prop->name); + } + conv.s = nullptr; + pref.s = nullptr; + pref.i = -1; + switch ((*p) & 223) + { + + case 'I': + case 'X': // Expression in parentheses or number. We only support the constant here. The function will have to be handled by a separate property to get past the parser. + case 'M': // special case for morph styles in DECORATE . This expression-aware parser will not need this. + case 'N': // special case for thing activations in DECORATE. This expression-aware parser will not need this. + conv.i = GetInt(exp); + break; + + case 'F': + conv.d = GetDouble(exp); + break; + + case 'Z': // an optional string. Does not allow any numerical value. + if (!GetString(exp, true)) + { + // apply this expression to the next argument on the list. + params.Push(conv); + params[0].i++; + p++; + continue; + } + // fall through + + case 'C': // this parser accepts colors only in string form. + pref.i = 1; + case 'S': + conv.s = GetString(exp); + break; + + case 'T': // a filtered string + conv.s = strings[strings.Reserve(1)] = strbin1(GetString(exp)); + break; + + case 'L': // Either a number or a list of strings + if (!GetString(exp, true)) + { + pref.i = 0; + conv.i = GetInt(exp); + } + else + { + pref.i = 1; + params.Push(pref); + params[0].i++; + + do + { + conv.s = GetString(exp); + if (conv.s != nullptr) + { + params.Push(conv); + params[0].i++; + } + exp = Simplify(static_cast(exp->SiblingNext), &bag.Info->Symbols); + } while (exp != property->Values); + goto endofparm; + } + break; + + default: + assert(false); + break; + + } + if (pref.i != -1) + { + params.Push(pref); + params[0].i++; + } + params.Push(conv); + params[0].i++; + exp = Simplify(static_cast(exp->SiblingNext), &bag.Info->Symbols); + endofparm: + p++; + // Skip the DECORATE 'no comma' marker + if (*p == '_') p++; + + else if (*p == 0) + { + if (exp != property->Values) + { + Error(property, "Too many values for '%s'", prop->name); + } + break; + } + else if (exp == property->Values) + { + if (*p < 'a') + { + Error(property, "Insufficient parameters for %s", prop->name); + } + break; + } + } + } + // call the handler + try + { + prop->Handler(defaults, bag.Info, bag, ¶ms[0]); + } + catch (CRecoverableError &error) + { + Error(property, "%s", error.GetMessage()); + } +} + +//========================================================================== +// +// Parses an actor property +// +//========================================================================== + +void ZCCCompiler::ProcessDefaultProperty(PClassActor *cls, ZCC_PropertyStmt *prop, Baggage &bag) +{ + auto namenode = prop->Prop; + FString propname; + + if (namenode->SiblingNext == namenode) + { + // a one-name property + propname = FName(namenode->Id); + } + else if (namenode->SiblingNext->SiblingNext == namenode) + { + // a two-name property + propname << FName(namenode->Id) << "." << FName(static_cast(namenode->SiblingNext)->Id); + } + else + { + Error(prop, "Property name may at most contain two parts"); + return; + } + + FPropertyInfo *property = FindProperty(propname); + + if (property != nullptr && property->category != CAT_INFO) + { + if (cls->IsDescendantOf(*property->cls)) + { + DispatchProperty(property, prop, (AActor *)bag.Info->Defaults, bag); + } + else + { + Error(prop, "'%s' requires an actor of type '%s'\n", propname.GetChars(), (*property->cls)->TypeName.GetChars()); + } + } + else + { + Error(prop, "'%s' is an unknown actor property\n", propname.GetChars()); + } +} + +//========================================================================== +// +// Finds a flag and sets or clears it +// +//========================================================================== + +void ZCCCompiler::ProcessDefaultFlag(PClassActor *cls, ZCC_FlagStmt *flg) +{ + auto namenode = flg->name; + const char *n1 = FName(namenode->Id).GetChars(), *n2; + + if (namenode->SiblingNext == namenode) + { + // a one-name flag + n2 = nullptr; + } + else if (namenode->SiblingNext->SiblingNext == namenode) + { + // a two-name flag + n2 = FName(static_cast(namenode->SiblingNext)->Id).GetChars(); + } + else + { + Error(flg, "Flag name may at most contain two parts"); + return; + } + + auto fd = FindFlag(cls, n1, n2, true); + if (fd != nullptr) + { + if (fd->structoffset == -1) + { + Warn(flg, "Deprecated flag '%s%s%s' used", n1, n2 ? "." : "", n2 ? n2 : ""); + HandleDeprecatedFlags((AActor*)cls->Defaults, cls, flg->set, fd->flagbit); + } + else + { + ModActorFlag((AActor*)cls->Defaults, fd, flg->set); + } + } + else + { + Error(flg, "Unknown flag '%s%s%s'", n1, n2 ? "." : "", n2 ? n2 : ""); + } +} + +//========================================================================== +// +// Parses the default list +// +//========================================================================== + +void ZCCCompiler::InitDefaults() +{ + for (auto c : Classes) + { + // This may be removed if the conditions change, but right now only subclasses of Actor can define a Default block. + if (!c->Type()->IsDescendantOf(RUNTIME_CLASS(AActor))) + { + if (c->Defaults.Size()) Error(c->cls, "%s: Non-actor classes may not have defaults", c->Type()->TypeName.GetChars()); + } + else + { + // This should never happen. + if (c->Type()->Defaults != nullptr) + { + Error(c->cls, "%s already has defaults", c->Type()->TypeName.GetChars()); + } + // This can only occur if a native parent is not initialized. In all other cases the sorting of the class list should prevent this from ever happening. + else if (c->Type()->ParentClass->Defaults == nullptr && c->Type() != RUNTIME_CLASS(AActor)) + { + Error(c->cls, "Parent class %s of %s is not initialized", c->Type()->ParentClass->TypeName.GetChars(), c->Type()->TypeName.GetChars()); + } + else + { + // Copy the parent's defaults and meta data. + auto ti = static_cast(c->Type()); + ti->InitializeNativeDefaults(); + ti->ParentClass->DeriveData(ti); + + + Baggage bag; + #ifdef _DEBUG + bag.ClassName = c->Type()->TypeName; + #endif + bag.Info = ti; + bag.DropItemSet = false; + bag.StateSet = false; + bag.fromZScript = true; + bag.CurrentState = 0; + bag.Lumpnum = Wads.CheckNumForFullName(*c->cls->SourceName, true); + bag.DropItemList = nullptr; + bag.ScriptPosition.StrictErrors = true; + // The actual script position needs to be set per property. + + for (auto d : c->Defaults) + { + auto content = d->Content; + do + { + switch (content->NodeType) + { + case AST_PropertyStmt: + bag.ScriptPosition.FileName = *content->SourceName; + bag.ScriptPosition.ScriptLine = content->SourceLoc; + ProcessDefaultProperty(ti, static_cast(content), bag); + break; + + case AST_FlagStmt: + ProcessDefaultFlag(ti, static_cast(content)); + break; + } + content = static_cast(content->SiblingNext); + } while (content != d->Content); + } + } + } + } +} + diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index 2fb83d7e6..9edd65b1d 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -1,6 +1,10 @@ #ifndef ZCC_COMPILE_H #define ZCC_COMPILE_H +struct Baggage; +struct FPropertyInfo; +class AActor; + struct ZCC_StructWork { PSymbolTable TreeNodes; @@ -40,6 +44,7 @@ struct ZCC_ClassWork TArray Enums; TArray Constants; TArray Fields; + TArray Defaults; ZCC_ClassWork(ZCC_Class * s, PSymbolTreeNode *n) { @@ -89,6 +94,14 @@ private: PType *ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym); PType *ResolveUserType(ZCC_BasicType *type, PSymbolTable *sym); + void InitDefaults(); + void ProcessDefaultFlag(PClassActor *cls, ZCC_FlagStmt *flg); + void ProcessDefaultProperty(PClassActor *cls, ZCC_PropertyStmt *flg, Baggage &bag); + void DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *pex, AActor *defaults, Baggage &bag); + int GetInt(ZCC_Expression *expr); + double GetDouble(ZCC_Expression *expr); + const char *GetString(ZCC_Expression *expr, bool silent = false); + TArray Constants; TArray Structs; TArray Classes; @@ -103,11 +116,6 @@ private: ZCC_OpProto *PromoteUnary(EZCCExprType op, ZCC_Expression *&expr); ZCC_OpProto *PromoteBinary(EZCCExprType op, ZCC_Expression *&left, ZCC_Expression *&right); - void PromoteToInt(ZCC_Expression *&expr); - void PromoteToUInt(ZCC_Expression *&expr); - void PromoteToDouble(ZCC_Expression *&expr); - void PromoteToString(ZCC_Expression *&expr); - ZCC_Expression *ApplyConversion(ZCC_Expression *expr, const PType::Conversion **route, int routelen); ZCC_Expression *AddCastNode(PType *type, ZCC_Expression *expr); From 6989b8168859a67dfb449ea51767cda727292940 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 11 Oct 2016 13:11:40 +0200 Subject: [PATCH 018/255] - extended the grammar so that the DECORATE function declaration list can almost be used as-is, with the sole exception of requiring any action function to declare a return type, even if it is void. This adds: * builtin types color, state and sound. * ending a parameter list with an ellipsis to declare a varargs list. (A_Jump uses this.) * allowing to declare optional arguments by giving them a default value. * adding an 'action' qualifier for function declarations. --- src/zscript/ast.cpp | 8 +++++++- src/zscript/zcc-parse.lemon | 26 ++++++++++++++++++++++++++ src/zscript/zcc_parser.cpp | 5 +++++ src/zscript/zcc_parser.h | 6 ++++++ wadsrc/static/zscript/constants.txt | 15 +++++++++++++++ 5 files changed, 59 insertions(+), 1 deletion(-) diff --git a/src/zscript/ast.cpp b/src/zscript/ast.cpp index f80498738..1f416f7ad 100644 --- a/src/zscript/ast.cpp +++ b/src/zscript/ast.cpp @@ -54,7 +54,12 @@ static const char *BuiltInTypeNames[] = "vector3", "vector4", "name", - "usertype" + "color", + "state", + "sound", + + "usertype", + }; class FLispString @@ -767,6 +772,7 @@ static void PrintFuncParamDecl(FLispString &out, ZCC_TreeNode *node) PrintNodes(out, dnode->Type); out.AddName(dnode->Name); out.AddHex(dnode->Flags); + PrintNodes(out, dnode->Default); out.Close(); } diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 09fadedb4..1861463f9 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -188,6 +188,7 @@ class_ancestry(X) ::= COLON dottable_id(A). { X = A; /*X-overwrites-A*/ } class_flags(X) ::= . { X.Flags = 0; X.Replaces = NULL; } class_flags(X) ::= class_flags(A) ABSTRACT. { X.Flags = A.Flags | ZCC_Abstract; X.Replaces = A.Replaces; } class_flags(X) ::= class_flags(A) NATIVE. { X.Flags = A.Flags | ZCC_Native; X.Replaces = A.Replaces; } +class_flags(X) ::= class_flags(A) ACTION. { X.Flags = A.Flags | ZCC_Action; X.Replaces = A.Replaces; } class_flags(X) ::= class_flags(A) REPLACES dottable_id(B). { X.Flags = A.Flags; X.Replaces = B; } /*----- Dottable Identifier -----*/ @@ -585,6 +586,9 @@ type_name1(X) ::= DOUBLE(T). { X.Int = ZCC_Float64; X.SourceLoc = T.SourceLoc type_name1(X) ::= STRING(T). { X.Int = ZCC_String; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= VECTOR(T) vector_size(A). { X.Int = A.Int; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= NAME(T). { X.Int = ZCC_Name; X.SourceLoc = T.SourceLoc; } +type_name1(X) ::= SOUND(T). { X.Int = ZCC_Sound; X.SourceLoc = T.SourceLoc; } +type_name1(X) ::= STATE(T). { X.Int = ZCC_State; X.SourceLoc = T.SourceLoc; } +type_name1(X) ::= COLOR(T). { X.Int = ZCC_Color; X.SourceLoc = T.SourceLoc; } type_name(X) ::= type_name1(A). { @@ -841,6 +845,17 @@ func_params(X) ::= . /* empty */ { X = NULL; } func_params(X) ::= VOID. { X = NULL; } func_params(X) ::= func_param_list(X). +func_params(X) ::= func_param_list(A) COMMA ELLIPSIS. +{ + NEW_AST_NODE(FuncParamDecl,parm,stat->sc->GetMessageLine()); + parm->Type = nullptr; + parm->Name = NAME_None; + parm->Flags = 0; + parm->Default = nullptr; + X = A; /*X-overwrites-A*/ + X->AppendSibling(parm); +} + func_param_list(X) ::= func_param(X). func_param_list(X) ::= func_param_list(A) COMMA func_param(B). { X = A; /*X-overwrites-A*/ X->AppendSibling(B); } @@ -850,6 +865,17 @@ func_param(X) ::= func_param_flags(A) type(B) IDENTIFIER(C). parm->Type = B; parm->Name = C.Name(); parm->Flags = A.Int; + parm->Default = nullptr; + X = parm; +} + +func_param(X) ::= func_param_flags(A) type(B) IDENTIFIER(C) EQ expr(D). +{ + NEW_AST_NODE(FuncParamDecl,parm,A.SourceLoc ? A.SourceLoc : B->SourceLoc); + parm->Type = B; + parm->Name = C.Name(); + parm->Flags = A.Int; + parm->Default = D; X = parm; } diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index ba08f91ef..ce2dc98e7 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -88,6 +88,7 @@ static void InitTokenMap() TOKENDEF (TK_LtGtEq, ZCC_LTGTEQ); TOKENDEF (TK_Is, ZCC_IS); TOKENDEF (TK_DotDot, ZCC_DOTDOT); + TOKENDEF (TK_Ellipsis, ZCC_ELLIPSIS); TOKENDEF ('|', ZCC_OR); TOKENDEF ('^', ZCC_XOR); TOKENDEF ('&', ZCC_AND); @@ -112,6 +113,7 @@ static void InitTokenMap() TOKENDEF (TK_Class, ZCC_CLASS); TOKENDEF (TK_Abstract, ZCC_ABSTRACT); TOKENDEF (TK_Native, ZCC_NATIVE); + TOKENDEF (TK_Action, ZCC_ACTION); TOKENDEF (TK_Replaces, ZCC_REPLACES); TOKENDEF (TK_Static, ZCC_STATIC); TOKENDEF (TK_Private, ZCC_PRIVATE); @@ -172,6 +174,9 @@ static void InitTokenMap() TOKENDEF (TK_Loop, ZCC_LOOP); TOKENDEF (TK_Goto, ZCC_GOTO); TOKENDEF (TK_States, ZCC_STATES); + TOKENDEF (TK_State, ZCC_STATE); + TOKENDEF (TK_Color, ZCC_COLOR); + TOKENDEF (TK_Sound, ZCC_SOUND); TOKENDEF (TK_Identifier, ZCC_IDENTIFIER); TOKENDEF (TK_StringConst, ZCC_STRCONST); diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 7500185f8..5d5c85827 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -119,6 +119,11 @@ enum EZCCBuiltinType ZCC_Vector3, ZCC_Vector4, ZCC_Name, + + ZCC_Color, // special types for ZDoom. + ZCC_State, + ZCC_Sound, + ZCC_UserType, ZCC_NUM_BUILT_IN_TYPES @@ -437,6 +442,7 @@ struct ZCC_LocalVarStmt : ZCC_Statement struct ZCC_FuncParamDecl : ZCC_TreeNode { ZCC_Type *Type; + ZCC_Expression *Default; ENamedName Name; int Flags; }; diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 12604234d..aa72ee8ec 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -804,3 +804,18 @@ enum ERenderStyle STYLE_AddStencil, STYLE_AddShaded, }; + +// Type definition for the implicit 'callingstate' parameter that gets passed to action functions. +enum EStateType +{ + STATE_Actor, + STATE_Psprite, + STATE_StateChain, +} + +struct FStateParamInfo +{ + state mCallingState; + EStateType mStateType; + int mPSPIndex; +} From d8c689d874a209728beddff319db6e9b4974ec92 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 11 Oct 2016 18:53:10 +0200 Subject: [PATCH 019/255] - initialize function symbols. At the moment all it does is process the existing native functions. Any further processing will be done once the base classes of the engine can be parsed from the scripting files. - switched the types of the internal 'self' and 'stateowner' parameters so that they get assigned correctly. I can't tell if this will error out if fields get accessed from the caller with the wrong class, but for actual scripting to work these must be correct. The committed 'actor.txt' can be parsed successfully, with the exception of a few subclass references that cannot be resolved yet. --- src/dobjtype.h | 5 + src/namedef.h | 5 + src/thingdef/thingdef.h | 2 +- src/thingdef/thingdef_parse.cpp | 12 +- src/zscript/zcc_compile.cpp | 158 ++++++++++++- src/zscript/zcc_compile.h | 5 +- wadsrc/static/zscript/actor.txt | 399 ++++++++++++++++++++++++++++++++ 7 files changed, 570 insertions(+), 16 deletions(-) create mode 100644 wadsrc/static/zscript/actor.txt diff --git a/src/dobjtype.h b/src/dobjtype.h index 0b4235a76..8ccb62aca 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -24,6 +24,11 @@ enum VARF_Private = (1<<5), // field is private to containing class VARF_Protected = (1<<6), // field is only accessible by containing class and children. VARF_Deprecated = (1<<7), // Deprecated fields should output warnings when used. + VARF_Virtual = (1<<8), // function is virtual + VARF_Final = (1<<9), // Function may not be overridden in subclasses + VARF_In = (1<<10), + VARF_Out = (1<<11), + VARF_Implicit = (1<<12), // implicitly created parameters (i.e. do not compare when checking function signatures) }; // Symbol information ------------------------------------------------------- diff --git a/src/namedef.h b/src/namedef.h index f07db2ce9..8d883d566 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -714,6 +714,11 @@ xx(Mant_Dig) xx(Min_10_Exp) xx(Max_10_Exp) +// implicit function parameters +xx(self) +xx(caller) +xx(stateinfo) + xx(__decorate_internal_int__) xx(__decorate_internal_bool__) xx(__decorate_internal_state__) diff --git a/src/thingdef/thingdef.h b/src/thingdef/thingdef.h index 426eddd41..107a496d8 100644 --- a/src/thingdef/thingdef.h +++ b/src/thingdef/thingdef.h @@ -195,7 +195,7 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArray *args, TArray *argflags, PClassActor *cls, DWORD funcflags); +void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls, DWORD funcflags); PFunction *FindGlobalActionFunction(const char *name); diff --git a/src/thingdef/thingdef_parse.cpp b/src/thingdef/thingdef_parse.cpp index 5789038b7..6d1077ffe 100644 --- a/src/thingdef/thingdef_parse.cpp +++ b/src/thingdef/thingdef_parse.cpp @@ -410,7 +410,7 @@ static void ParseArgListDef(FScanner &sc, PClassActor *cls, // //========================================================================== -void SetImplicitArgs(TArray *args, TArray *argflags, PClassActor *cls, DWORD funcflags) +void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls, DWORD funcflags) { // Must be called before adding any other arguments. assert(args == NULL || args->Size() == 0); @@ -419,21 +419,21 @@ void SetImplicitArgs(TArray *args, TArray *argflags, PClassActor if (funcflags & VARF_Method) { // implied self pointer - if (args != NULL) args->Push(NewClassPointer(cls)); - if (argflags != NULL) argflags->Push(0); + if (args != NULL) args->Push(NewClassPointer(RUNTIME_CLASS(AActor))); + if (argflags != NULL) argflags->Push(VARF_Implicit); } if (funcflags & VARF_Action) { // implied stateowner and callingstate pointers if (args != NULL) { - args->Push(NewClassPointer(RUNTIME_CLASS(AActor))); + args->Push(NewClassPointer(cls)); args->Push(TypeState); } if (argflags != NULL) { - argflags->Push(0); - argflags->Push(0); + argflags->Push(VARF_Implicit); + argflags->Push(VARF_Implicit); } } } diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 98448069a..7e718b42f 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -111,7 +111,10 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) // todo case AST_States: + break; + case AST_FuncDeclarator: + cls->Functions.Push(static_cast(node)); break; case AST_Default: @@ -364,6 +367,7 @@ int ZCCCompiler::Compile() CompileAllConstants(); CompileAllFields(); InitDefaults(); + InitFunctions(); return ErrorCount; } @@ -1179,7 +1183,7 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel { auto field = Fields[0]; - PType *fieldtype = DetermineType(type, field, field->Type, true); + PType *fieldtype = DetermineType(type, field, field->Names->Name, field->Type, true); // For structs only allow 'deprecated', for classes exclude function qualifiers. int notallowed = forstruct? ~ZCC_Deprecated : ZCC_Latent | ZCC_Final | ZCC_Action | ZCC_Static | ZCC_FuncConst | ZCC_Abstract; @@ -1264,11 +1268,11 @@ FString ZCCCompiler::FlagsToString(uint32_t flags) // //========================================================================== -PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZCC_Type *ztype, bool allowarraytypes) +PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName name, ZCC_Type *ztype, bool allowarraytypes) { if (!allowarraytypes && ztype->ArraySize != nullptr) { - Error(field, "%s: Array type not allowed", FName(field->Names->Name).GetChars()); + Error(field, "%s: Array type not allowed", name.GetChars()); return TypeError; } switch (ztype->NodeType) @@ -1322,9 +1326,18 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZC case ZCC_Vector4: // This has almost no use, so we really shouldn't bother. - Error(field, "vector<4> not implemented for %s", FName(field->Names->Name).GetChars()); + Error(field, "vector<4> not implemented for %s", name.GetChars()); return TypeError; + case ZCC_State: + return TypeState; + + case ZCC_Color: + return TypeColor; + + case ZCC_Sound: + return TypeSound; + case ZCC_UserType: return ResolveUserType(btype, &outertype->Symbols); break; @@ -1334,19 +1347,19 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZC case AST_MapType: if (allowarraytypes) { - Error(field, "%s: Map types not implemented yet", FName(field->Names->Name).GetChars()); + Error(field, "%s: Map types not implemented yet", name.GetChars()); // Todo: Decide what we allow here and if it makes sense to allow more complex constructs. auto mtype = static_cast(ztype); - return NewMap(DetermineType(outertype, field, mtype->KeyType, false), DetermineType(outertype, field, mtype->ValueType, false)); + return NewMap(DetermineType(outertype, field, name, mtype->KeyType, false), DetermineType(outertype, field, name, mtype->ValueType, false)); } break; case AST_DynArrayType: if (allowarraytypes) { - Error(field, "%s: Dynamic array types not implemented yet", FName(field->Names->Name).GetChars()); + Error(field, "%s: Dynamic array types not implemented yet", name.GetChars()); auto atype = static_cast(ztype); - return NewDynArray(DetermineType(outertype, field, atype->ElementType, false)); + return NewDynArray(DetermineType(outertype, field, name, atype->ElementType, false)); } break; @@ -1648,6 +1661,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper } } // call the handler + FScriptPosition::ErrorCounter = 0; try { prop->Handler(defaults, bag.Info, bag, ¶ms[0]); @@ -1656,6 +1670,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper { Error(property, "%s", error.GetMessage()); } + ErrorCount += FScriptPosition::ErrorCounter; } //========================================================================== @@ -1824,3 +1839,130 @@ void ZCCCompiler::InitDefaults() } } +//========================================================================== +// +// Parses the functions list +// +//========================================================================== + +void ZCCCompiler::InitFunctions() +{ + TArray rets(1); + TArray args; + TArray argflags; + TArray argnames; + + for (auto c : Classes) + { + for (auto f : c->Functions) + { + Printf("processing function %s\n", FName(f->Name).GetChars()); + rets.Clear(); + args.Clear(); + argflags.Clear(); + // For the time being, let's not allow overloading. This may be reconsidered later but really just adds an unnecessary amount of complexity here. + if (AddTreeNode(f->Name, f, &c->TreeNodes, false)) + { + auto t = f->Type; + if (t != nullptr) + { + do + { + auto type = DetermineType(c->Type(), f, f->Name, t, false); + // TBD: disallow certain types? For now, let everything pass that isn't an array. + rets.Push(type); + t = static_cast(t->SiblingNext); + } while (t != f->Type); + } + + int notallowed = ZCC_Latent | ZCC_Meta | ZCC_ReadOnly | ZCC_FuncConst | ZCC_Abstract; + + if (f->Flags & notallowed) + { + Error(f, "Invalid qualifiers for %s (%s not allowed)", FName(f->Name).GetChars(), FlagsToString(f->Flags & notallowed)); + f->Flags &= notallowed; + } + uint32_t varflags = VARF_Method; + AFuncDesc *afd = nullptr; + + // map to implementation flags. + if (f->Flags & ZCC_Private) varflags |= VARF_Private; + if (f->Flags & ZCC_Protected) varflags |= VARF_Protected; + if (f->Flags & ZCC_Deprecated) varflags |= VARF_Deprecated; + if (f->Flags & ZCC_Action) varflags |= VARF_Action|VARF_Final; // Action implies Final. + if (f->Flags & ZCC_Static) varflags = (varflags & ~VARF_Method) | VARF_Final; // Static implies Final. + if ((f->Flags & (ZCC_Action | ZCC_Static)) == (ZCC_Action | ZCC_Static)) + { + Error(f, "%s: Action and Static on the same function is not allowed.", FName(f->Name).GetChars()); + varflags |= VARF_Method; + } + + if (f->Flags & ZCC_Native) + { + varflags |= VARF_Native; + afd = FindFunction(FName(f->Name).GetChars()); + if (afd == nullptr) + { + Error(f, "The function '%s' has not been exported from the executable.", FName(f->Name).GetChars()); + } + } + SetImplicitArgs(&args, &argflags, c->Type(), varflags); + // Give names to the implicit parameters. + // Note that 'self' is the second argument on action functions, because this is the one referring to the owning class. + if (varflags & VARF_Action) + { + argnames.Push(NAME_caller); + argnames.Push(NAME_self); + argnames.Push(NAME_stateinfo); + } + else if (varflags & VARF_Method) + { + argnames.Push(NAME_self); + } + + auto p = f->Params; + if (p != nullptr) + { + do + { + if (p->Type != nullptr) + { + auto type = DetermineType(c->Type(), p, f->Name, p->Type, false); + int flags; + if (p->Flags & ZCC_In) flags |= VARF_In; + if (p->Flags & ZCC_Out) flags |= VARF_Out; + if (p->Default != nullptr) + { + auto val = Simplify(p->Default, &c->Type()->Symbols); + flags |= VARF_Optional; + if (val->Operation != PEX_ConstValue) + { + Error(c->cls, "Default parameter %s is not constant in %s", FName(p->Name).GetChars(), FName(f->Name).GetChars()); + } + // Todo: Store and handle the default value (native functions will discard it anyway but for scripted ones this should be done decently.) + } + // TBD: disallow certain types? For now, let everything pass that isn't an array. + args.Push(type); + argflags.Push(flags); + } + else + { + args.Push(nullptr); + argflags.Push(0); + } + p = static_cast(p->SiblingNext); + } while (p != f->Params); + } + + PFunction *sym = new PFunction(f->Name); + sym->AddVariant(NewPrototype(rets, args), argflags, afd == nullptr? nullptr : *(afd->VMPointer)); + sym->Flags = varflags; + c->Type()->Symbols.ReplaceSymbol(sym); + + // todo: Check inheritance. + // todo: Process function bodies. + } + } + } +} + diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index 9edd65b1d..e5fb241f3 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -45,6 +45,7 @@ struct ZCC_ClassWork TArray Constants; TArray Fields; TArray Defaults; + TArray Functions; ZCC_ClassWork(ZCC_Class * s, PSymbolTreeNode *n) { @@ -90,7 +91,7 @@ private: void CompileAllFields(); bool CompileFields(PStruct *type, TArray &Fields, PClass *Outer, PSymbolTable *TreeNodes, bool forstruct); FString FlagsToString(uint32_t flags); - PType *DetermineType(PType *outertype, ZCC_VarDeclarator *field, ZCC_Type *ztype, bool allowarraytypes); + PType *DetermineType(PType *outertype, ZCC_TreeNode *field, FName name, ZCC_Type *ztype, bool allowarraytypes); PType *ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym); PType *ResolveUserType(ZCC_BasicType *type, PSymbolTable *sym); @@ -102,6 +103,8 @@ private: double GetDouble(ZCC_Expression *expr); const char *GetString(ZCC_Expression *expr, bool silent = false); + void InitFunctions(); + TArray Constants; TArray Structs; TArray Classes; diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt new file mode 100644 index 000000000..34c1271e0 --- /dev/null +++ b/wadsrc/static/zscript/actor.txt @@ -0,0 +1,399 @@ +class Actor : Thinker native +{ + const DEFAULT_HEALTH = 1000; + + Default + { + Scale 1; + Health DEFAULT_HEALTH; + Reactiontime 8; + Radius 20; + Height 16; + Mass 100; + RenderStyle 'Normal'; + Alpha 1; + MinMissileChance 200; + MeleeRange 64 - 20; + MaxDropoffHeight 24; + MaxStepHeight 24; + BounceFactor 0.7; + WallBounceFactor 0.75; + BounceCount -1; + FloatSpeed 4; + FloatBobPhase -1; // randomly initialize by default + Gravity 1; + Friction 1; + DamageFactor 1.0; + PushFactor 0.25; + WeaveIndexXY 0; + WeaveIndexZ 16; + DesignatedTeam 255; + PainType "Normal"; + DeathType "Normal"; + TeleFogSourceType "TeleportFog"; + TeleFogDestType 'TeleportFog'; + RipperLevel 0; + RipLevelMin 0; + RipLevelMax 0; + DefThreshold 100; + BloodType "Blood", "BloodSplatter", "AxeBlood"; + ExplosionDamage 128; + MissileHeight 32; + SpriteAngle 0; + SpriteRotation 0; + StencilColor "00 00 00"; + VisibleAngles 0, 0; + VisiblePitch 0, 0; + } + + // Functions + native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); + native bool IsPointerEqual(int ptr_select1, int ptr_select2); + native int CountInv(class itemtype, int ptr_select = AAPTR_DEFAULT); + native float GetDistance(bool checkz, int ptr = AAPTR_DEFAULT); + native float GetAngle(int flags, int ptr = AAPTR_DEFAULT); + native float GetZAt(float px = 0, float py = 0, float angle = 0, int flags = 0, int pick_pointer = AAPTR_DEFAULT); + native int GetSpawnHealth(); + native int GetGibHealth(); + native float GetCrouchFactor(int ptr = AAPTR_PLAYER1); + native float GetCVar(string cvar); + native int GetPlayerInput(int inputnum, int ptr = AAPTR_DEFAULT); + native int CountProximity(class classname, float distance, int flags = 0, int ptr = AAPTR_DEFAULT); + native float GetSpriteAngle(int ptr = AAPTR_DEFAULT); + native float GetSpriteRotation(int ptr = AAPTR_DEFAULT); + native int GetMissileDamage(int mask, int add, int ptr = AAPTR_DEFAULT); + action native int OverlayID(); + action native float OverlayX(int layer = 0); + action native float OverlayY(int layer = 0); + + // Action functions + // Meh, MBF redundant functions. Only for DeHackEd support. + action native void A_Turn(float angle = 0); + action native bool A_LineEffect(int boomspecial = 0, int tag = 0); + // End of MBF redundant functions. + + action native void A_MonsterRail(); + action native void A_BFGSpray(class spraytype = "BFGExtra", int numrays = 40, int damagecount = 15, float angle = 90, float distance = 16*64, float vrange = 32, int damage = 0, int flags = 0); + action native void A_Pain(); + action native void A_NoBlocking(); + action native void A_XScream(); + action native void A_Look(); + action native void A_Chase(state melee = "*", state missile = "none", int flags = 0); + action native void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + action native void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + action native void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + action native void A_PosAttack(); + action native void A_Scream(); + action native void A_SPosAttack(); + action native void A_SPosAttackUseAtkSound(); + action native void A_VileChase(); + action native void A_VileStart(); + action native void A_VileTarget(class fire = "ArchvileFire"); + action native void A_VileAttack(sound snd = "vile/stop", int initialdmg = 20, int blastdmg = 70, int blastradius = 70, float thrustfac = 1.0, name damagetype = "Fire", int flags = 0); + action native void A_StartFire(); + action native void A_Fire(float spawnheight = 0); + action native void A_FireCrackle(); + action native void A_Tracer(); + action native void A_SkelWhoosh(); + action native void A_SkelFist(); + action native void A_SkelMissile(); + action native void A_FatRaise(); + action native void A_FatAttack1(class spawntype = "FatShot"); + action native void A_FatAttack2(class spawntype = "FatShot"); + action native void A_FatAttack3(class spawntype = "FatShot"); + action native void A_BossDeath(); + action native void A_CPosAttack(); + action native void A_CPosRefire(); + action native void A_TroopAttack(); + action native void A_SargAttack(); + action native void A_HeadAttack(); + action native void A_BruisAttack(); + action native void A_SkullAttack(float speed = 20); + action native void A_BetaSkullAttack(); + action native void A_Metal(); + action native void A_SpidRefire(); + action native void A_BabyMetal(); + action native void A_BspiAttack(); + action native void A_Hoof(); + action native void A_CyberAttack(); + action native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); + action native void A_DualPainAttack(class spawntype = "LostSoul"); + action native void A_PainDie(class spawntype = "LostSoul"); + action native void A_KeenDie(int doortag = 666); + action native void A_BrainPain(); + action native void A_BrainScream(); + action native void A_BrainDie(); + action native void A_BrainAwake(); + action native void A_BrainSpit(class spawntype = "none"); // needs special treatment for default + action native void A_SpawnSound(); + action native void A_SpawnFly(class spawntype = "none"); // needs special treatment for default + action native void A_BrainExplode(); + action native void A_Die(name damagetype = "none"); + action native void A_Detonate(); + action native void A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5); + native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); + + action native void A_SetFloorClip(); + action native void A_UnSetFloorClip(); + action native void A_HideThing(); + action native void A_UnHideThing(); + action native void A_SetInvulnerable(); + action native void A_UnSetInvulnerable(); + action native void A_SetReflective(); + action native void A_UnSetReflective(); + action native void A_SetReflectiveInvulnerable(); + action native void A_UnSetReflectiveInvulnerable(); + action native void A_SetShootable(); + action native void A_UnSetShootable(); + action native void A_NoGravity(); + action native void A_Gravity(); + action native void A_LowGravity(); + native void A_SetGravity(float gravity); + action native void A_Fall(); + action native void A_SetSolid(); + action native void A_UnsetSolid(); + action native void A_SetFloat(); + action native void A_UnsetFloat(); + + action native void A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); + + action native void A_ScreamAndUnblock(); + action native void A_ActiveAndUnblock(); + action native void A_ActiveSound(); + + action native void A_FastChase(); + action native void A_FreezeDeath(); + action native void A_FreezeDeathChunks(); + action native void A_GenericFreezeDeath(); + action native void A_IceGuyDie(); + action native void A_CentaurDefend(); + action native void A_BishopMissileWeave(); + action native void A_CStaffMissileSlither(); + action native void A_PlayerScream(); + action native void A_SkullPop(class skulltype = "BloodySkull"); + action native void A_CheckPlayerDone(); + + action native void A_Wander(int flags = 0); + action native void A_Look2(); + action native void A_TossGib(); + action native void A_SentinelBob(); + action native void A_SentinelRefire(); + action native void A_Tracer2(); + action native void A_SetShadow(); + action native void A_ClearShadow(); + action native void A_GetHurt(); + action native void A_TurretLook(); + action native void A_KlaxonBlare(); + action native void A_Countdown(); + action native void A_AlertMonsters(float maxdist = 0, int flags = 0); + action native void A_ClearSoundTarget(); + action native void A_FireAssaultGun(); + action native void A_CheckTerrain(); + action native void A_FaceConsolePlayer(float MaxTurnAngle = 0); // [TP] no-op + + deprecated action native void A_MissileAttack(); + deprecated action native void A_MeleeAttack(); + deprecated action native void A_ComboAttack(); + deprecated action native void A_BulletAttack(); + action native void A_WolfAttack(int flags = 0, sound whattoplay = "weapons/pistol", float snipe = 1.0, int maxdamage = 64, int blocksize = 128, int pointblank = 2, int longrange = 4, float runspeed = 160.0, class pufftype = "BulletPuff"); + action native void A_PlaySound(sound whattoplay = "weapons/pistol", int slot = CHAN_BODY, float volume = 1.0, bool looping = false, float attenuation = ATTN_NORM); + native void A_PlayWeaponSound(sound whattoplay); + action native void A_FLoopActiveSound(); + action native void A_LoopActiveSound(); + action native void A_StopSound(int slot = CHAN_VOICE); // Bad default but that's what is originally was... + deprecated native void A_PlaySoundEx(sound whattoplay, name slot, bool looping = false, int attenuation = 0); + deprecated native void A_StopSoundEx(name slot); + native void A_SeekerMissile(int threshold, int turnmax, int flags = 0, int chance = 50, int distance = 10); + native state A_Jump(int chance = 256, state label, ...); + native void A_CustomMissile(class missiletype, float spawnheight = 32, float spawnofs_xy = 0, float angle = 0, int flags = 0, float pitch = 0, int ptr = AAPTR_TARGET); + native void A_CustomBulletAttack(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); + native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = "", color color2 = "", int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); + native state A_JumpIfHealthLower(int health, state label, int ptr_selector = AAPTR_DEFAULT); + native state A_JumpIfCloser(float distance, state label, bool noz = false); + native state A_JumpIfTracerCloser(float distance, state label, bool noz = false); + native state A_JumpIfMasterCloser(float distance, state label, bool noz = false); + native state A_JumpIfTargetOutsideMeleeRange(state label); + native state A_JumpIfTargetInsideMeleeRange(state label); + native state A_JumpIfInventory(class itemtype, int itemamount, state label, int owner = AAPTR_DEFAULT); + native state A_JumpIfArmorType(name Type, state label, int amount = 1); + native bool A_GiveInventory(class itemtype, int amount = 0, int giveto = AAPTR_DEFAULT); + native bool A_TakeInventory(class itemtype, int amount = 0, int flags = 0, int giveto = AAPTR_DEFAULT); + action native bool A_SpawnItem(class itemtype = "Unknown", float distance = 0, float zheight = 0, bool useammo = true, bool transfer_translation = false); + native bool A_SpawnItemEx(class itemtype, float xofs = 0, float yofs = 0, float zofs = 0, float xvel = 0, float yvel = 0, float zvel = 0, float angle = 0, int flags = 0, int failchance = 0, int tid=0); + native void A_Print(string whattoprint, float time = 0, name fontname = ""); + native void A_PrintBold(string whattoprint, float time = 0, name fontname = ""); + native void A_Log(string whattoprint); + native void A_LogInt(int whattoprint); + native void A_LogFloat(float whattoprint); + native void A_SetTranslucent(float alpha, int style = 0); + native void A_SetRenderStyle(float alpha, int style); + action native void A_FadeIn(float reduce = 0.1, int flags = 0); + action native void A_FadeOut(float reduce = 0.1, int flags = 1); //bool remove == true + native void A_FadeTo(float target, float amount = 0.1, int flags = 0); + native void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false); + native void A_SetMass(int mass); + native void A_SpawnDebris(class spawntype, bool transfer_translation = false, float mult_h = 1, float mult_v = 1); + native void A_SpawnParticle(color color1, int flags = 0, int lifetime = 35, float size = 1, float angle = 0, float xoff = 0, float yoff = 0, float zoff = 0, float velx = 0, float vely = 0, float velz = 0, float accelx = 0, float accely = 0, float accelz = 0, float startalphaf = 1, float fadestepf = -1, float sizestep = 0); + native state A_CheckSight(state label); + native void A_ExtChase(bool usemelee, bool usemissile, bool playactive = true, bool nightmarefast = false); + native void A_DropInventory(class itemtype); + native void A_SetBlend(color color1, float alpha, int tics, color color2 = ""); + native void A_ChangeFlag(string flagname, bool value); + native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); + native state A_JumpIf(bool expression, state label); + action native void A_RaiseMaster(bool copy = 0); + action native void A_RaiseChildren(bool copy = 0); + action native void A_RaiseSiblings(bool copy = 0); + native state A_CheckFloor(state label); + native state A_CheckCeiling(state label); + native state A_PlayerSkinCheck(state label); + deprecated native void A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); + action native state, bool A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); + action native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = "", float heightoffset = 0, float radiusoffset = 0, float pitch = 0); + action native bool A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); + native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); + + native void A_Recoil(float xyvel); + native state A_JumpIfInTargetInventory(class itemtype, int amount, state label, int forward_ptr = AAPTR_DEFAULT); + native bool A_GiveToTarget(class itemtype, int amount = 0, int forward_ptr = AAPTR_DEFAULT); + native bool A_TakeFromTarget(class itemtype, int amount = 0, int flags = 0, int forward_ptr = AAPTR_DEFAULT); + native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = "None", name species = "None", float mindist = 0, int limit = 0); + native state A_CheckSpecies(state jump, name species = "", int ptr = AAPTR_DEFAULT); + native void A_CountdownArg(int argnum, state targstate = ""); + action native void A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); + native void A_CustomComboAttack(class missiletype, float spawnheight, int damage, sound meleesound = "", name damagetype = "none", bool bleed = true); + native void A_Burst(class chunktype); + action native void A_Blast(int flags = 0, float strength = 255, float radius = 255, float speed = 20, class blasteffect = "BlastEffect", sound blastsound = "BlastRadius"); + action native void A_RadiusThrust(int force = 128, int distance = -1, int flags = RTF_AFFECTSOURCE, int fullthrustdistance = 0); + action native void A_RadiusDamageSelf(int damage = 128, float distance = 128, int flags = 0, class flashtype = "None"); + action native int A_Explode(int damage = -1, int distance = -1, int flags = XF_HURTSOURCE, bool alert = false, int fulldamagedistance = 0, int nails = 0, int naildamage = 10, class pufftype = "BulletPuff", name damagetype = "none"); + action native void A_Stop(); + action native void A_Respawn(int flags = 1); + action native void A_BarrelDestroy(); + action native void A_QueueCorpse(); + action native void A_DeQueueCorpse(); + action native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = ""); + action native void A_ClearLastHeard(); + action native void A_ClearTarget(); + native state A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); + native state A_JumpIfTargetInLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); + native state A_JumpIfInTargetLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); + native bool A_SelectWeapon(class whichweapon, int flags = 0); + action native void A_Punch(); + action native void A_Feathers(); + action native void A_ClassBossHealth(); + action native void A_ShootGun(); + action native void A_RocketInFlight(); + action native void A_Bang4Cloud(); + action native void A_DropFire(); + native void A_GiveQuestItem(int itemno); + action native void A_RemoveForcefield(); + native void A_DropWeaponPieces(class p1, class p2, class p3); + action native void A_PigPain (); + native state A_MonsterRefire(int chance, state label); + action native void A_SetAngle(float angle = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_SetPitch(float pitch, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_SetRoll(float roll, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_ScaleVelocity(float scale, int ptr = AAPTR_DEFAULT); + action native void A_ChangeVelocity(float x = 0, float y = 0, float z = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_SetArg(int pos, int value); + native void A_SetUserVar(name varname, int value); + native void A_SetUserArray(name varname, int index, int value); + native void A_SetUserVarFloat(name varname, float value); + native void A_SetUserArrayFloat(name varname, int index, float value); + native void A_SetSpecial(int spec, int arg0 = 0, int arg1 = 0, int arg2 = 0, int arg3 = 0, int arg4 = 0); + native void A_Quake(int intensity, int duration, int damrad, int tremrad, sound sfx = "world/quake"); + native void A_QuakeEx(int intensityX, int intensityY, int intensityZ, int duration, int damrad, int tremrad, sound sfx = "world/quake", int flags = 0, float mulWaveX = 1, float mulWaveY = 1, float mulWaveZ = 1, int falloff = 0, int highpoint = 0, float rollIntensity = 0, float rollWave = 0); + action native void A_SetTics(int tics); + native void A_SetDamageType(name damagetype); + native void A_DropItem(class item, int dropamount = -1, int chance = 256); + native void A_SetSpeed(float speed, int ptr = AAPTR_DEFAULT); + native void A_SetFloatSpeed(float speed, int ptr = AAPTR_DEFAULT); + native void A_SetPainThreshold(int threshold, int ptr = AAPTR_DEFAULT); + native void A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + action native void A_KillTarget(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + action native void A_KillMaster(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + action native void A_KillTracer(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + action native void A_KillChildren(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + action native void A_KillSiblings(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + action native void A_RemoveTarget(int flags = 0, class filter = "None", name species = "None"); + action native void A_RemoveMaster(int flags = 0, class filter = "None", name species = "None"); + action native void A_RemoveTracer(int flags = 0, class filter = "None", name species = "None"); + action native void A_RemoveChildren(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); + action native void A_RemoveSiblings(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); + native void A_Remove(int removee, int flags = 0, class filter = "None", name species = "None"); + native int A_GiveToChildren(class itemtype, int amount = 0); + native int A_GiveToSiblings(class itemtype, int amount = 0); + native int A_TakeFromChildren(class itemtype, int amount = 0); + native int A_TakeFromSiblings(class itemtype, int amount = 0); + native void A_SetTeleFog(class oldpos, class newpos); + action native void A_SwapTeleFog(); + native void A_SetFloatBobPhase(int bob); + native void A_SetHealth(int health, int ptr = AAPTR_DEFAULT); + action native void A_ResetHealth(int ptr = AAPTR_DEFAULT); + native state A_JumpIfHigherOrLower(state high, state low, float offsethigh = 0, float offsetlow = 0, bool includeHeight = true, int ptr = AAPTR_TARGET); + native void A_SetSpecies(name species, int ptr = AAPTR_DEFAULT); + native void A_SetRipperLevel(int level); + native void A_SetRipMin(int mininum); + native void A_SetRipMax(int maximum); + native void A_SetChaseThreshold(int threshold, bool def = false, int ptr = AAPTR_DEFAULT); + native state A_CheckProximity(state jump, class classname, float distance, int count = 1, int flags = 0, int ptr = AAPTR_DEFAULT); + native state A_CheckBlock(state block, int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0); + native state A_CheckSightOrRange(float distance, state label, bool two_dimension = false); + native state A_CheckRange(float distance, state label, bool two_dimension = false); + action native bool A_FaceMovementDirection(float offset = 0, float anglelimit = 0, float pitchlimit = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + action native int A_ClearOverlays(int sstart = 0, int sstop = 0, bool safety = true); + action native bool A_CopySpriteFrame(int from, int to, int flags = 0); + action native bool A_SetSpriteAngle(float angle = 0, int ptr = AAPTR_DEFAULT); + action native bool A_SetSpriteRotation(float angle = 0, int ptr = AAPTR_DEFAULT); + action native bool A_SetVisibleRotation(float anglestart = 0, float angleend = 0, float pitchstart = 0, float pitchend = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_SetTranslation(string transname); + + native void A_RearrangePointers(int newtarget, int newmaster = AAPTR_DEFAULT, int newtracer = AAPTR_DEFAULT, int flags=0); + native void A_TransferPointer(int ptr_source, int ptr_recepient, int sourcefield, int recepientfield=AAPTR_DEFAULT, int flags=0); + action native void A_CopyFriendliness(int ptr_source = AAPTR_MASTER); + + action native bool A_Overlay(int layer, state start = "", bool nooverride = false); + action native void A_WeaponOffset(float wx = 0, float wy = 32, int flags = 0); + action native void A_OverlayOffset(int layer = PSP_WEAPON, float wx = 0, float wy = 32, int flags = 0); + action native void A_OverlayFlags(int layer, int flags, bool set); + + native int ACS_NamedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); + native int ACS_NamedSuspend(name script, int mapnum=0); + native int ACS_NamedTerminate(name script, int mapnum=0); + native int ACS_NamedLockedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0); + native int ACS_NamedLockedExecuteDoor(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0); + native int ACS_NamedExecuteWithResult(name script, int arg1=0, int arg2=0, int arg3=0, int arg4=0); + native void ACS_NamedExecuteAlways(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); + +/* + States + { + Spawn: + TNT1 A -1 + Stop + Null: + TNT1 A 1 + Stop + GenericFreezeDeath: + // Generic freeze death frames. Woo! + "####" "#" 5 A_GenericFreezeDeath + "----" A 1 A_FreezeDeathChunks + Wait + GenericCrush: + POL5 A -1 + Stop + } +*/ + + // Internal functions + deprecated private native state __decorate_internal_state__(state s); + deprecated private native int __decorate_internal_int__(int i); + deprecated private native bool __decorate_internal_bool__(bool b); + deprecated private native float __decorate_internal_float__(float f); +} From f46b6b5be5cabb089ebe6cd3ba83e8ba335add22 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 12 Oct 2016 00:04:30 +0200 Subject: [PATCH 020/255] - fixed some issues with the grammar for parsing states: * Goto did not support the class scope operator '::'. Like in DECORATE, this cannot be done with a simple '.' because it creates semantic problems with first part of a state label. This requires different syntax so that it can unambiguously distinguish between a scope identifier and the actual label * Goto used the incorrect token PLUS for '+' instead of ADD. * The state's duration was not stored in the AST. * Truncating the sprite name inside the parser is probably not the best idea because it used a simple Printf to report this. Let's do this during processing of the AST where this can be properly handled as an error. --- src/zscript/ast.cpp | 4 +++- src/zscript/zcc-parse.lemon | 28 +++++++++++++++++----------- src/zscript/zcc_parser.h | 4 +++- 3 files changed, 23 insertions(+), 13 deletions(-) diff --git a/src/zscript/ast.cpp b/src/zscript/ast.cpp index 1f416f7ad..45b8053ba 100644 --- a/src/zscript/ast.cpp +++ b/src/zscript/ast.cpp @@ -405,6 +405,7 @@ static void PrintStateGoto(FLispString &out, ZCC_TreeNode *node) { ZCC_StateGoto *snode = (ZCC_StateGoto *)node; out.Open("state-goto"); + PrintNodes(out, snode->Qualifier); PrintNodes(out, snode->Label); PrintNodes(out, snode->Offset); out.Close(); @@ -414,7 +415,8 @@ static void PrintStateLine(FLispString &out, ZCC_TreeNode *node) { ZCC_StateLine *snode = (ZCC_StateLine *)node; out.Open("state-line"); - out.Add(snode->Sprite, 4); + out.Add(*(snode->Sprite)); + PrintNodes(out, snode->Duration); if (snode->bNoDelay) out.Add("nodelay", 7); if (snode->bBright) out.Add("bright", 6); if (snode->bFast) out.Add("fast", 4); diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index 1861463f9..ae03248cc 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -430,25 +430,31 @@ state_flow_type(X) ::= GOTO(T) dottable_id(A) state_goto_offset(B). NEW_AST_NODE(StateGoto, flow, T); flow->Label = A; flow->Offset = B; + flow->Qualifier = nullptr; + X = flow; +} + +state_flow_type(X) ::= GOTO(T) IDENTIFIER(C) SCOPE dottable_id(A) state_goto_offset(B). +{ + NEW_AST_NODE(StateGoto, flow, T); + flow->Label = A; + flow->Offset = B; + + NEW_AST_NODE(Identifier,id,C); + id->Id = C.Name(); + flow->Qualifier =id; X = flow; } state_goto_offset(X) ::= . { X = NULL; } -state_goto_offset(X) ::= PLUS expr(A). { X = A; /*X-overwrites-A*/ } /* Must evaluate to a non-negative integer constant. */ +state_goto_offset(X) ::= ADD expr(A). { X = A; /*X-overwrites-A*/ } /* Must evaluate to a non-negative integer constant. */ -state_line(X) ::= NWS(A) NWS(B) expr state_opts(C) state_action(D). +state_line(X) ::= NWS(A) NWS(B) expr(E) state_opts(C) state_action(D). { NEW_AST_NODE(StateLine, line, A); - const char *sprite = FName(A.Name()).GetChars(); - if (strlen(sprite) != 4) - { - Printf("Sprite name '%s' must be four characters", sprite); - } - else - { - memcpy(line->Sprite, sprite, 4); - } + line->Sprite = stat->Strings.Alloc(FName(A.Name()).GetChars()); line->Frames = stat->Strings.Alloc(FName(B.Name()).GetChars()); + line->Duration = E; line->bBright = C.Bright; line->bFast = C.Fast; line->bSlow = C.Slow; diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 5d5c85827..0cb3f79ae 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -260,19 +260,21 @@ struct ZCC_Expression : ZCC_TreeNode struct ZCC_StateGoto : ZCC_StatePart { + ZCC_Identifier *Qualifier; ZCC_Identifier *Label; ZCC_Expression *Offset; }; struct ZCC_StateLine : ZCC_StatePart { - char Sprite[4]; + FString *Sprite; BITFIELD bBright : 1; BITFIELD bFast : 1; BITFIELD bSlow : 1; BITFIELD bNoDelay : 1; BITFIELD bCanRaise : 1; FString *Frames; + ZCC_Expression *Duration; ZCC_Expression *Offset; ZCC_TreeNode *Action; }; From 6a8ab9a4d32a61f535b87922b6f2460f119003cb Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 12 Oct 2016 17:50:23 +0200 Subject: [PATCH 021/255] - implemented the state compiler. So far all it can handle is parameter-less functions. To do the rest, some cleanup is needed first, to untangle the DECORATE parser from the actual code generation so that the low end stuff can actually be reused here instead of having to be redone. --- src/d_dehacked.cpp | 2 +- src/thingdef/thingdef_exp.cpp | 2 +- src/thingdef/thingdef_exp.h | 3 +- src/thingdef/thingdef_expression.cpp | 56 ++++-- src/thingdef/thingdef_states.cpp | 4 +- src/zscript/zcc-parse.lemon | 29 ++- src/zscript/zcc_compile.cpp | 279 ++++++++++++++++++++++++++- src/zscript/zcc_compile.h | 4 + src/zscript/zcc_parser.cpp | 17 -- src/zscript/zcc_parser.h | 8 + 10 files changed, 362 insertions(+), 42 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index dd71fdf75..d062ce533 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -804,7 +804,7 @@ void SetDehParams(FState *state, int codepointer) } else { - VMFunctionBuilder buildit; + VMFunctionBuilder buildit(true); // Allocate registers used to pass parameters in. // self, stateowner, state (all are pointers) buildit.Registers[REGT_POINTER].Get(NAP); diff --git a/src/thingdef/thingdef_exp.cpp b/src/thingdef/thingdef_exp.cpp index cad6198f0..11baef722 100644 --- a/src/thingdef/thingdef_exp.cpp +++ b/src/thingdef/thingdef_exp.cpp @@ -515,7 +515,7 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) args = nullptr; } - return new FxVMFunctionCall(func, args, sc); + return new FxVMFunctionCall(func, args, sc, false); } } diff --git a/src/thingdef/thingdef_exp.h b/src/thingdef/thingdef_exp.h index 5fe8f252f..65c3ace63 100644 --- a/src/thingdef/thingdef_exp.h +++ b/src/thingdef/thingdef_exp.h @@ -948,11 +948,12 @@ public: class FxVMFunctionCall : public FxExpression { bool EmitTail; + bool OwnerIsSelf; // ZSCRIPT makes the state's owner the self pointer to ensure proper type handling PFunction *Function; FArgumentList *ArgList; public: - FxVMFunctionCall(PFunction *func, FArgumentList *args, const FScriptPosition &pos); + FxVMFunctionCall(PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool ownerisself); ~FxVMFunctionCall(); FxExpression *Resolve(FCompileContext&); PPrototype *ReturnProto(); diff --git a/src/thingdef/thingdef_expression.cpp b/src/thingdef/thingdef_expression.cpp index c2b2d25e6..ae2639b73 100644 --- a/src/thingdef/thingdef_expression.cpp +++ b/src/thingdef/thingdef_expression.cpp @@ -3858,12 +3858,13 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) // //========================================================================== -FxVMFunctionCall::FxVMFunctionCall(PFunction *func, FArgumentList *args, const FScriptPosition &pos) +FxVMFunctionCall::FxVMFunctionCall(PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool ownerisself) : FxExpression(pos) { Function = func; ArgList = args; EmitTail = false; + OwnerIsSelf = ownerisself; } //========================================================================== @@ -3968,28 +3969,55 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) return reg; } } - // Emit code to pass implied parameters - if (Function->Flags & VARF_Method) + + // Passing the caller as 'self' is a serious design mistake in DECORATE because it mixes up the types of the two actors involved. + // For ZSCRIPT 'self' is properly used for the state's owning actor, meaning we have to pass the second argument here. + + // If both functions are non-action or both are action, there is no need for special treatment. + if (!OwnerIsSelf || (!!(Function->Flags & VARF_Action) == build->IsActionFunc)) { - build->Emit(OP_PARAM, 0, REGT_POINTER, 0); - count += 1; + // Emit code to pass implied parameters + if (Function->Flags & VARF_Method) + { + build->Emit(OP_PARAM, 0, REGT_POINTER, 0); + count += 1; + } + if (Function->Flags & VARF_Action) + { + static_assert(NAP == 3, "This code needs to be updated if NAP changes"); + if (build->IsActionFunc) + { + build->Emit(OP_PARAM, 0, REGT_POINTER, 1); + build->Emit(OP_PARAM, 0, REGT_POINTER, 2); + } + else + { + int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); + } + count += 2; + } } - if (Function->Flags & VARF_Action) + else { - static_assert(NAP == 3, "This code needs to be updated if NAP changes"); - if (build->IsActionFunc) + // There are two possibilities here: + // Calling a non-action function from an action function. + // In that case the 'stateowner' pointer needs to be used as self. + if (build->IsActionFunc && (Function->Flags & VARF_Method)) { build->Emit(OP_PARAM, 0, REGT_POINTER, 1); - build->Emit(OP_PARAM, 0, REGT_POINTER, 2); + count += 1; } - else + // and calling an action function from a non-action function. + // This must be blocked because it lacks crucial information. + if (!build->IsActionFunc && (Function->Flags & VARF_Action)) { - int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); + // This case should be eliminated in the analyzing stage. + I_Error("Cannot call action function from non-action functions."); } - count += 2; } + // Emit code to pass explicit parameters if (ArgList != NULL) { diff --git a/src/thingdef/thingdef_states.cpp b/src/thingdef/thingdef_states.cpp index 707de3045..3b692391c 100644 --- a/src/thingdef/thingdef_states.cpp +++ b/src/thingdef/thingdef_states.cpp @@ -100,7 +100,7 @@ FxVMFunctionCall *DoActionSpecials(FScanner &sc, FState & state, Baggage &bag) { sc.ScriptError ("Too many arguments to %s", specname.GetChars()); } - return new FxVMFunctionCall(FindGlobalActionFunction("A_CallSpecial"), args, sc); + return new FxVMFunctionCall(FindGlobalActionFunction("A_CallSpecial"), args, sc, false); } return NULL; } @@ -582,7 +582,7 @@ FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestring, B { FArgumentList *args = new FArgumentList; ParseFunctionParameters(sc, bag.Info, *args, afd, statestring, &bag.statedef); - call = new FxVMFunctionCall(afd, args->Size() > 0 ? args : NULL, sc); + call = new FxVMFunctionCall(afd, args->Size() > 0 ? args : NULL, sc, false); if (args->Size() == 0) { delete args; diff --git a/src/zscript/zcc-parse.lemon b/src/zscript/zcc-parse.lemon index ae03248cc..7213b4dbc 100644 --- a/src/zscript/zcc-parse.lemon +++ b/src/zscript/zcc-parse.lemon @@ -40,6 +40,7 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) struct StateOpts { ZCC_Expression *Offset; + ZCC_ExprConstant *Lights; bool Bright; bool Fast; bool Slow; @@ -47,7 +48,8 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) bool CanRaise; void Zero() { - Offset = NULL; + Offset = nullptr; + Lights = nullptr; Bright = false; Fast = false; Slow = false; @@ -461,6 +463,7 @@ state_line(X) ::= NWS(A) NWS(B) expr(E) state_opts(C) state_action(D). line->bNoDelay = C.NoDelay; line->bCanRaise = C.CanRaise; line->Offset = C.Offset; + line->Lights = C.Lights; line->Action = D; X = line; } @@ -472,10 +475,28 @@ state_opts(X) ::= state_opts(A) SLOW. { A.Slow = true; X = A; /*X-overwri state_opts(X) ::= state_opts(A) NODELAY. { A.NoDelay = true; X = A; /*X-overwrites-A*/ } state_opts(X) ::= state_opts(A) CANRAISE. { A.CanRaise = true; X = A; /*X-overwrites-A*/ } state_opts(X) ::= state_opts(A) OFFSET LPAREN expr(B) COMMA expr(C) RPAREN. { A.Offset = B; B->AppendSibling(C); X = A; /*X-overwrites-A*/ } -state_opts(X) ::= state_opts(A) LIGHT LPAREN light_list RPAREN. { X = A; /*X-overwrites-A*/ } ///FIXME: GZDoom would want to know this +state_opts(X) ::= state_opts(A) LIGHT LPAREN light_list(B) RPAREN. { X = A; /*X-overwrites-A*/ X.Lights = B; } -light_list ::= STRCONST. -light_list ::= light_list COMMA STRCONST. +%type light_list {ZCC_ExprConstant *} + +light_list(X) ::= STRCONST(A). +{ + NEW_AST_NODE(ExprConstant, strconst, A); + strconst->Operation = PEX_ConstValue; + strconst->Type = TypeString; + strconst->StringVal = A.String; + X = strconst; +} + +light_list(X) ::= light_list(A) COMMA STRCONST(B). +{ + NEW_AST_NODE(ExprConstant, strconst, B); + strconst->Operation = PEX_ConstValue; + strconst->Type = TypeString; + strconst->StringVal = B.String; + A->AppendSibling(strconst); + X = A; /*X-overwrites-A*/ +} /* A state action can be either a compound statement or a single action function call. */ state_action(X) ::= LBRACE statement_list(A) scanner_mode RBRACE. { X = A; /*X-overwrites-A*/ } diff --git a/src/zscript/zcc_compile.cpp b/src/zscript/zcc_compile.cpp index 7e718b42f..19af0e7c1 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/zscript/zcc_compile.cpp @@ -46,6 +46,7 @@ #include "v_text.h" #include "p_lnspec.h" #include "gdtoa.h" +#include "thingdef_exp.h" #define DEFINING_CONST ((PSymbolConst *)(void *)1) @@ -109,8 +110,8 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) enumType = nullptr; break; - // todo case AST_States: + cls->States.Push(static_cast(node)); break; case AST_FuncDeclarator: @@ -368,6 +369,7 @@ int ZCCCompiler::Compile() CompileAllFields(); InitDefaults(); InitFunctions(); + CompileStates(); return ErrorCount; } @@ -1856,7 +1858,6 @@ void ZCCCompiler::InitFunctions() { for (auto f : c->Functions) { - Printf("processing function %s\n", FName(f->Name).GetChars()); rets.Clear(); args.Clear(); argflags.Clear(); @@ -1966,3 +1967,277 @@ void ZCCCompiler::InitFunctions() } } +//========================================================================== +// +// very complicated check for random duration. +// +//========================================================================== + +static bool CheckRandom(ZCC_Expression *duration) +{ + if (duration->NodeType != AST_ExprFuncCall) return false; + auto func = static_cast(duration); + if (func->Function == nullptr) return false; + if (func->Function->NodeType != AST_ExprID) return false; + auto f2 = static_cast(func->Function); + return f2->Identifier == NAME_Random; +} + +//========================================================================== +// +// Sets up the action function call +// +//========================================================================== +FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *af) +{ + // We have 3 cases to consider here: + // 1. An action function without parameters. This can be called directly + // 2. An action functon with parameters or a non-action function. This needs to be wrapped into a helper function to set everything up. + // 3. An anonymous function. + + // 1. and 2. are exposed through AST_ExprFunctionCall + if (af->NodeType == AST_ExprFuncCall) + { + auto fc = static_cast(af); + assert(fc->Function->NodeType == AST_ExprID); + auto id = static_cast(fc->Function); + + PFunction *afd = dyn_cast(cls->Symbols.FindSymbol(id->Identifier, true)); + if (afd != nullptr) + { + if (fc->Parameters == nullptr && (afd->Flags & VARF_Action)) + { + // This is the simple case which doesn't require work on the tree. + return new FxVMFunctionCall(afd, nullptr, *af, true); + } + else + { + // need to generate a function from the information. + } + } + else + { + Error(af, "%s: action function not found in %s", FName(id->Identifier).GetChars(), cls->TypeName.GetChars()); + return nullptr; + } + } + Error(af, "Complex action functions not supported yet."); + return nullptr; + + /* + bool hasfinalret; + tcall->Code = ParseActions(sc, state, statestring, bag, hasfinalret); + if (!hasfinalret && tcall->Code != nullptr) + { + static_cast(tcall->Code)->Add(new FxReturnStatement(nullptr, sc)); + } + */ + +} + +//========================================================================== +// +// Compile the states +// +//========================================================================== + +void ZCCCompiler::CompileStates() +{ + for (auto c : Classes) + { + if (!c->Type()->IsDescendantOf(RUNTIME_CLASS(AActor))) + { + Error(c->cls, "%s: States can only be defined for actors.", c->Type()->TypeName.GetChars()); + continue; + } + FString statename; // The state builder wants the label as one complete string, not separated into tokens. + FStateDefinitions statedef; + for (auto s : c->States) + { + auto st = s->Body; + do + { + switch (st->NodeType) + { + case AST_StateLabel: + { + auto sl = static_cast(st); + statename = FName(sl->Label); + statedef.AddStateLabel(statename); + break; + } + case AST_StateLine: + { + auto sl = static_cast(st); + FState state; + memset(&state, 0, sizeof(state)); + if (sl->Sprite->Len() != 4) + { + Error(sl, "Sprite name must be exactly 4 characters. Found '%s'", sl->Sprite->GetChars()); + } + else + { + state.sprite = GetSpriteIndex(sl->Sprite->GetChars()); + } + // It is important to call CheckRandom before Simplify, because Simplify will resolve the function's name to nonsense + // and there is little point fixing it because it is essentially useless outside of resolving constants. + if (CheckRandom(sl->Duration)) + { + auto func = static_cast(Simplify(sl->Duration, &c->Type()->Symbols)); + if (func->Parameters == func->Parameters->SiblingNext || func->Parameters != func->Parameters->SiblingNext->SiblingNext) + { + Error(sl, "Random duration requires exactly 2 parameters"); + } + int v1 = GetInt(func->Parameters->Value); + int v2 = GetInt(static_cast(func->Parameters->SiblingNext)->Value); + if (v1 > v2) std::swap(v1, v2); + state.Tics = (int16_t)clamp(v1, 0, INT16_MAX); + state.TicRange = (uint16_t)clamp(v2 - v1, 0, UINT16_MAX); + } + else + { + auto duration = Simplify(sl->Duration, &c->Type()->Symbols); + if (duration->Operation == PEX_ConstValue) + { + state.Tics = (int16_t)clamp(GetInt(duration), -1, INT16_MAX); + state.TicRange = 0; + } + else + { + Error(sl, "Duration is not a constant"); + } + } + state.Fullbright = sl->bBright; + state.Fast = sl->bFast; + state.Slow = sl->bSlow; + state.CanRaise = sl->bCanRaise; + if ((state.NoDelay = sl->bNoDelay)) + { + if (statedef.GetStateLabelIndex(NAME_Spawn) != statedef.GetStateCount()) + { + Warn(sl, "NODELAY only has an effect on the first state after 'Spawn:'"); + } + } + if (sl->Offset != nullptr) + { + auto o1 = static_cast(Simplify(sl->Offset, &c->Type()->Symbols)); + auto o2 = static_cast(Simplify(static_cast(o1->SiblingNext), &c->Type()->Symbols)); + + if (o1->Operation != PEX_ConstValue || o2->Operation != PEX_ConstValue) + { + Error(o1, "State offsets must be constant"); + } + else + { + state.Misc1 = GetInt(o1); + state.Misc2 = GetInt(o2); + } + } +#ifdef DYNLIGHT + if (sl->Lights != nullptr) + { + auto l = sl->Lights; + do + { + AddStateLight(&state, GetString(l)); + l = static_cast(l->SiblingNext); + } while (l != sl->Lights); + } +#endif + + int count = statedef.AddStates(&state, sl->Frames->GetChars()); + if (count < 0) + { + Error(sl, "Invalid frame character string '%s'", sl->Frames->GetChars()); + count = -count; + } + + if (sl->Action != nullptr) + { + auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); + if (code != nullptr) + { + auto tcall = new FStateTempCall; + tcall->Code = code; + tcall->ActorClass = static_cast(c->Type()); + tcall->FirstState = statedef.GetStateCount() - count; + tcall->NumStates = count; + StateTempCalls.Push(tcall); + } + } + break; + } + case AST_StateGoto: + { + auto sg = static_cast(st); + statename = ""; + if (sg->Qualifier != nullptr) + { + statename << sg->Qualifier->Id << "::"; + } + auto part = sg->Label; + do + { + statename << part->Id << '.'; + part = static_cast(part->SiblingNext); + } while (part != sg->Label); + statename.Truncate((long)statename.Len() - 1); // remove the last '.' in the label name + if (sg->Offset != nullptr) + { + auto ofs = Simplify(sg->Offset, &c->Type()->Symbols); + if (ofs->Operation != PEX_ConstValue) + { + Error(sg, "Constant offset expected for GOTO"); + } + else + { + int offset = GetInt(ofs); + if (offset < 0) + { + Error(sg, "GOTO offset must be positive"); + offset = 0; + } + if (offset > 0) + { + statename.AppendFormat("+%d", offset); + } + } + } + if (!statedef.SetGotoLabel(statename)) + { + Error(sg, "GOTO before first state"); + } + break; + } + case AST_StateFail: + case AST_StateWait: + if (!statedef.SetWait()) + { + Error(st, "%s before first state", st->NodeType == AST_StateFail ? "Fail" : "Wait"); + continue; + } + break; + + case AST_StateLoop: + if (!statedef.SetLoop()) + { + Error(st, "LOOP before first state"); + continue; + } + break; + + case AST_StateStop: + if (!statedef.SetStop()) + { + Error(st, "STOP before first state"); + } + break; + + default: + assert(0 && "Bad AST node in state"); + } + st = static_cast(st->SiblingNext); + } while (st != s->Body); + } + } +} diff --git a/src/zscript/zcc_compile.h b/src/zscript/zcc_compile.h index e5fb241f3..74d83f529 100644 --- a/src/zscript/zcc_compile.h +++ b/src/zscript/zcc_compile.h @@ -4,6 +4,7 @@ struct Baggage; struct FPropertyInfo; class AActor; +class FxExpression; struct ZCC_StructWork { @@ -46,6 +47,7 @@ struct ZCC_ClassWork TArray Fields; TArray Defaults; TArray Functions; + TArray States; ZCC_ClassWork(ZCC_Class * s, PSymbolTreeNode *n) { @@ -104,6 +106,8 @@ private: const char *GetString(ZCC_Expression *expr, bool silent = false); void InitFunctions(); + void CompileStates(); + FxExpression *SetupActionFunction(PClassActor *cls, ZCC_TreeNode *sl); TArray Constants; TArray Structs; diff --git a/src/zscript/zcc_parser.cpp b/src/zscript/zcc_parser.cpp index ce2dc98e7..0d69141f0 100644 --- a/src/zscript/zcc_parser.cpp +++ b/src/zscript/zcc_parser.cpp @@ -347,23 +347,6 @@ static void DoParse(int lumpnum) symtable.SetName("Global_Node"); ZCCCompiler cc(state, NULL, symtable, GlobalSymbols); cc.Compile(); - // ... and another one afterward so we can see what the compiler does with the data. -#ifdef _DEBUG - if (f != NULL) - { - fclose(f); - } - FString ast = ZCC_PrintAST(state.TopNode); - FString filename = Wads.GetLumpFullName(lumpnum); - FString astfile = ExtractFileBase(filename, false); - astfile << "-after.ast"; - f = fopen(astfile, "w"); - if (f != NULL) - { - fputs(ast.GetChars(), f); - fclose(f); - } -#endif } void ParseScripts() diff --git a/src/zscript/zcc_parser.h b/src/zscript/zcc_parser.h index 0cb3f79ae..2a73c8681 100644 --- a/src/zscript/zcc_parser.h +++ b/src/zscript/zcc_parser.h @@ -2,6 +2,7 @@ #define ZCC_PARSER_H #include "memarena.h" +#include "sc_man.h" struct ZCCToken { @@ -176,6 +177,12 @@ struct ZCC_TreeNode SiblingPrev = siblingend; siblingend->SiblingNext = this; } + + operator FScriptPosition() + { + return FScriptPosition(*SourceName, SourceLoc); + } + }; struct ZCC_Identifier : ZCC_TreeNode @@ -276,6 +283,7 @@ struct ZCC_StateLine : ZCC_StatePart FString *Frames; ZCC_Expression *Duration; ZCC_Expression *Offset; + ZCC_ExprConstant *Lights; ZCC_TreeNode *Action; }; From b1a83bfd26450c44aec0ca293dfa2ed9fa90dadc Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 12 Oct 2016 19:22:33 +0200 Subject: [PATCH 022/255] - started with cleanup and separation of DECORATE code. * everything related to scripting is now placed in a subdirectory 'scripting', which itself is separated into DECORATE, ZSCRIPT, the VM and code generation. * a few items have been moved to different headers so that the DECORATE parser definitions can mostly be kept local. The only exception at the moment is the flags interface on which 3 source files depend. --- src/CMakeLists.txt | 70 ++++++++++--------- src/d_dehacked.cpp | 3 + src/d_main.cpp | 1 + src/dobjgc.cpp | 1 + src/dobjtype.h | 1 - src/g_doom/a_arachnotron.cpp | 2 +- src/g_doom/a_archvile.cpp | 2 +- src/g_doom/a_bossbrain.cpp | 2 +- src/g_doom/a_cacodemon.cpp | 2 +- src/g_doom/a_cyberdemon.cpp | 2 +- src/g_doom/a_demon.cpp | 2 +- src/g_doom/a_doomimp.cpp | 2 +- src/g_doom/a_doommisc.cpp | 3 +- src/g_doom/a_doomweaps.cpp | 2 +- src/g_doom/a_fatso.cpp | 2 +- src/g_doom/a_keen.cpp | 2 +- src/g_doom/a_lostsoul.cpp | 2 +- src/g_doom/a_painelemental.cpp | 2 +- src/g_doom/a_possessed.cpp | 2 +- src/g_doom/a_revenant.cpp | 2 +- src/g_doom/a_scriptedmarine.cpp | 2 +- src/g_doom/a_spidermaster.cpp | 2 +- src/g_heretic/a_chicken.cpp | 2 +- src/g_heretic/a_dsparil.cpp | 2 +- src/g_heretic/a_hereticartifacts.cpp | 2 +- src/g_heretic/a_hereticimp.cpp | 2 +- src/g_heretic/a_hereticmisc.cpp | 3 +- src/g_heretic/a_hereticweaps.cpp | 2 +- src/g_heretic/a_ironlich.cpp | 2 +- src/g_heretic/a_knight.cpp | 2 +- src/g_heretic/a_wizard.cpp | 2 +- src/g_hexen/a_bats.cpp | 2 +- src/g_hexen/a_bishop.cpp | 2 +- src/g_hexen/a_centaur.cpp | 2 +- src/g_hexen/a_clericflame.cpp | 2 +- src/g_hexen/a_clericholy.cpp | 2 +- src/g_hexen/a_clericmace.cpp | 2 +- src/g_hexen/a_clericstaff.cpp | 2 +- src/g_hexen/a_dragon.cpp | 2 +- src/g_hexen/a_fighteraxe.cpp | 4 +- src/g_hexen/a_fighterhammer.cpp | 2 +- src/g_hexen/a_fighterplayer.cpp | 2 +- src/g_hexen/a_fighterquietus.cpp | 2 +- src/g_hexen/a_firedemon.cpp | 2 +- src/g_hexen/a_flechette.cpp | 2 +- src/g_hexen/a_fog.cpp | 2 +- src/g_hexen/a_heresiarch.cpp | 2 +- src/g_hexen/a_hexenmisc.cpp | 3 +- src/g_hexen/a_hexenspecialdecs.cpp | 2 +- src/g_hexen/a_iceguy.cpp | 2 +- src/g_hexen/a_korax.cpp | 2 +- src/g_hexen/a_magecone.cpp | 2 +- src/g_hexen/a_magelightning.cpp | 2 +- src/g_hexen/a_magestaff.cpp | 2 +- src/g_hexen/a_pig.cpp | 2 +- src/g_hexen/a_serpent.cpp | 2 +- src/g_hexen/a_spike.cpp | 2 +- src/g_hexen/a_summon.cpp | 2 +- src/g_hexen/a_teleportother.cpp | 2 +- src/g_hexen/a_wraith.cpp | 2 +- src/g_raven/a_minotaur.cpp | 3 +- src/g_shared/a_action.cpp | 2 +- src/g_shared/a_bridge.cpp | 2 +- src/g_shared/a_pickups.cpp | 2 +- src/g_shared/a_randomspawner.cpp | 2 +- src/g_shared/a_specialspot.cpp | 2 +- src/g_shared/a_weapons.cpp | 2 +- src/g_shared/sbarinfo.cpp | 1 + src/g_shared/shared_hud.cpp | 1 + src/g_shared/shared_sbar.cpp | 1 + src/g_strife/a_acolyte.cpp | 2 +- src/g_strife/a_alienspectres.cpp | 2 +- src/g_strife/a_crusader.cpp | 2 +- src/g_strife/a_entityboss.cpp | 2 +- src/g_strife/a_inquisitor.cpp | 2 +- src/g_strife/a_loremaster.cpp | 2 +- src/g_strife/a_oracle.cpp | 2 +- src/g_strife/a_programmer.cpp | 2 +- src/g_strife/a_reaver.cpp | 2 +- src/g_strife/a_rebels.cpp | 2 +- src/g_strife/a_sentinel.cpp | 2 +- src/g_strife/a_spectral.cpp | 2 +- src/g_strife/a_stalker.cpp | 2 +- src/g_strife/a_strifeitems.cpp | 2 +- src/g_strife/a_strifestuff.cpp | 3 +- src/g_strife/a_strifeweapons.cpp | 2 +- src/g_strife/a_templar.cpp | 2 +- src/g_strife/a_thingstoblowup.cpp | 4 +- src/g_strife/strife_sbar.cpp | 1 + src/info.cpp | 2 +- src/info.h | 12 ++++ src/menu/menudef.cpp | 1 + src/menu/menuinput.cpp | 1 + src/menu/messagebox.cpp | 1 + src/p_acs.cpp | 1 + src/p_actionfunctions.cpp | 4 +- src/p_enemy.cpp | 3 +- src/p_enemy.h | 3 +- src/p_mobj.cpp | 3 +- src/p_pspr.cpp | 2 +- src/p_pspr.h | 3 +- src/p_states.cpp | 3 +- src/p_user.cpp | 2 +- .../codegeneration}/thingdef_exp.h | 0 .../codegeneration}/thingdef_expression.cpp | 0 .../decorate}/olddecorations.cpp | 2 +- .../decorate}/thingdef_exp.cpp | 2 +- .../decorate}/thingdef_parse.cpp | 2 +- .../decorate}/thingdef_states.cpp | 2 +- src/{thingdef => scripting}/thingdef.cpp | 2 +- src/{thingdef => scripting}/thingdef.h | 67 +----------------- src/{thingdef => scripting}/thingdef_data.cpp | 0 .../thingdef_properties.cpp | 0 src/{zscript => scripting/vm}/vm.h | 60 ++++++++++++++++ src/{zscript => scripting/vm}/vmbuilder.cpp | 0 src/{zscript => scripting/vm}/vmbuilder.h | 0 src/{zscript => scripting/vm}/vmdisasm.cpp | 0 src/{zscript => scripting/vm}/vmexec.cpp | 0 src/{zscript => scripting/vm}/vmexec.h | 0 src/{zscript => scripting/vm}/vmframe.cpp | 0 src/{zscript => scripting/vm}/vmops.h | 0 src/{ => scripting}/zscript/ast.cpp | 0 src/{ => scripting}/zscript/zcc-parse.lemon | 0 src/{ => scripting}/zscript/zcc_compile.cpp | 2 +- src/{ => scripting}/zscript/zcc_compile.h | 0 src/{ => scripting}/zscript/zcc_expr.cpp | 0 src/{ => scripting}/zscript/zcc_exprlist.h | 0 src/{ => scripting}/zscript/zcc_parser.cpp | 0 src/{ => scripting}/zscript/zcc_parser.h | 0 src/serializer.cpp | 1 + src/sound/oalsound.cpp | 1 + src/wi_stuff.cpp | 1 + 132 files changed, 234 insertions(+), 198 deletions(-) rename src/{thingdef => scripting/codegeneration}/thingdef_exp.h (100%) rename src/{thingdef => scripting/codegeneration}/thingdef_expression.cpp (100%) rename src/{thingdef => scripting/decorate}/olddecorations.cpp (99%) rename src/{thingdef => scripting/decorate}/thingdef_exp.cpp (99%) rename src/{thingdef => scripting/decorate}/thingdef_parse.cpp (99%) rename src/{thingdef => scripting/decorate}/thingdef_states.cpp (99%) rename src/{thingdef => scripting}/thingdef.cpp (99%) rename src/{thingdef => scripting}/thingdef.h (76%) rename src/{thingdef => scripting}/thingdef_data.cpp (100%) rename src/{thingdef => scripting}/thingdef_properties.cpp (100%) rename src/{zscript => scripting/vm}/vm.h (90%) rename src/{zscript => scripting/vm}/vmbuilder.cpp (100%) rename src/{zscript => scripting/vm}/vmbuilder.h (100%) rename src/{zscript => scripting/vm}/vmdisasm.cpp (100%) rename src/{zscript => scripting/vm}/vmexec.cpp (100%) rename src/{zscript => scripting/vm}/vmexec.h (100%) rename src/{zscript => scripting/vm}/vmframe.cpp (100%) rename src/{zscript => scripting/vm}/vmops.h (100%) rename src/{ => scripting}/zscript/ast.cpp (100%) rename src/{ => scripting}/zscript/zcc-parse.lemon (100%) rename src/{ => scripting}/zscript/zcc_compile.cpp (99%) rename src/{ => scripting}/zscript/zcc_compile.h (100%) rename src/{ => scripting}/zscript/zcc_expr.cpp (100%) rename src/{ => scripting}/zscript/zcc_exprlist.h (100%) rename src/{ => scripting}/zscript/zcc_parser.cpp (100%) rename src/{ => scripting}/zscript/zcc_parser.h (100%) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ebfac3050..bd01cad42 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -752,8 +752,8 @@ add_custom_command( OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.c ${CMAKE_CUR DEPENDS lemon ${CMAKE_CURRENT_SOURCE_DIR}/xlat/xlat_parser.y ) add_custom_command( OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.c ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.h - COMMAND lemon -C${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/zscript/zcc-parse.lemon - DEPENDS lemon ${CMAKE_CURRENT_SOURCE_DIR}/zscript/zcc-parse.lemon ) + COMMAND lemon -C${CMAKE_CURRENT_BINARY_DIR} ${CMAKE_CURRENT_SOURCE_DIR}/scripting/zscript/zcc-parse.lemon + DEPENDS lemon ${CMAKE_CURRENT_SOURCE_DIR}/scripting/zscript/zcc-parse.lemon ) add_custom_command( OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h COMMAND re2c --no-generation-date -s -o ${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h ${CMAKE_CURRENT_SOURCE_DIR}/sc_man_scanner.re @@ -819,9 +819,9 @@ file( GLOB HEADER_FILES sfmt/*.h sound/*.h textures/*.h - thingdef/*.h + scripting/*.h + scripting/vm/*.h xlat/*.h - zscript/*.h *.h ) @@ -910,7 +910,7 @@ set( NOT_COMPILED_SOURCE_FILES xlat/xlat_parser.y xlat_parser.c xlat_parser.h - zscript/zcc-parse.lemon + scripting/zscript/zcc-parse.lemon zcc-parse.c zcc-parse.h @@ -1226,14 +1226,6 @@ set (PCH_SOURCES textures/texturemanager.cpp textures/tgatexture.cpp textures/warptexture.cpp - thingdef/olddecorations.cpp - thingdef/thingdef.cpp - thingdef/thingdef_data.cpp - thingdef/thingdef_exp.cpp - thingdef/thingdef_expression.cpp - thingdef/thingdef_parse.cpp - thingdef/thingdef_properties.cpp - thingdef/thingdef_states.cpp xlat/parse_xlat.cpp fragglescript/t_func.cpp fragglescript/t_load.cpp @@ -1248,15 +1240,23 @@ set (PCH_SOURCES r_data/voxels.cpp r_data/renderstyle.cpp r_data/r_interpolate.cpp + scripting/thingdef.cpp + scripting/thingdef_data.cpp + scripting/thingdef_properties.cpp + scripting/codegeneration/thingdef_expression.cpp + scripting/decorate/olddecorations.cpp + scripting/decorate/thingdef_exp.cpp + scripting/decorate/thingdef_parse.cpp + scripting/decorate/thingdef_states.cpp + scripting/vm/vmbuilder.cpp + scripting/vm/vmdisasm.cpp + scripting/vm/vmexec.cpp + scripting/vm/vmframe.cpp + scripting/zscript/ast.cpp + scripting/zscript/zcc_compile.cpp + scripting/zscript/zcc_expr.cpp + scripting/zscript/zcc_parser.cpp sfmt/SFMT.cpp - zscript/ast.cpp - zscript/vmbuilder.cpp - zscript/vmdisasm.cpp - zscript/vmexec.cpp - zscript/vmframe.cpp - zscript/zcc_compile.cpp - zscript/zcc_expr.cpp - zscript/zcc_parser.cpp ) enable_precompiled_headers( g_pch.h PCH_SOURCES ) @@ -1316,11 +1316,11 @@ include_directories( . oplsynth sound textures - thingdef timidity wildmidi xlat - zscript + scripting + scripting/vm ../gdtoa ../dumb/include ${CMAKE_BINARY_DIR}/gdtoa @@ -1428,7 +1428,9 @@ source_group("Audio Files\\Timidity\\Headers" REGULAR_EXPRESSION "^${CMAKE_CURRE source_group("Audio Files\\Timidity\\Source" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/timidity/.+\\.cpp$") source_group("Audio Files\\WildMidi\\Headers" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/wildmidi/.+\\.h$") source_group("Audio Files\\WildMidi\\Source" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/wildmidi/.+\\.cpp$") -source_group("Decorate++" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/thingdef/.+") +source_group("External\\Math" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/math/.+") +source_group("External\\RapidJSON" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/rapidjson/.+") +source_group("Externak\\SFMT" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/sfmt/.+") source_group("FraggleScript" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/fragglescript/.+") source_group("Games\\Doom Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_doom/.+") source_group("Games\\Heretic Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_heretic/.+") @@ -1436,9 +1438,7 @@ source_group("Games\\Hexen Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR source_group("Games\\Raven Shared" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_raven/.+") source_group("Games\\Strife Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_strife/.+") source_group("Intermission" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/intermission/.+") -source_group("Math" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/math/.+") source_group("Menu" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/menu/.+") -source_group("RapidJSON" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/rapidjson/.+") source_group("Render Core\\Render Headers" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/r_.+\\.h$") source_group("Render Core\\Render Sources" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/r_.+\\.cpp$") source_group("Render Data\\Resource Headers" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/r_data/.+\\.h$") @@ -1446,15 +1446,17 @@ source_group("Render Data\\Resource Sources" REGULAR_EXPRESSION "^${CMAKE_CURREN source_group("Render Data\\Textures" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/textures/.+") source_group("Render Interface" FILES r_defs.h r_renderer.h r_sky.cpp r_sky.h r_state.h r_utility.cpp r_utility.h) source_group("Resource Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/resourcefiles/.+") -source_group("POSIX Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/.+") -source_group("Cocoa Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/cocoa/.+") -source_group("OS X Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/osx/.+") -source_group("Unix Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/unix/.+") -source_group("SDL Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/sdl/.+") -source_group("SFMT" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/sfmt/.+") +source_group("Platforms\\POSIX Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/.+") +source_group("Platforms\\Cocoa Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/cocoa/.+") +source_group("Platforms\\OS X Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/osx/.+") +source_group("Platforms\\Unix Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/unix/.+") +source_group("Platforms\\SDL Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/posix/sdl/.+") +source_group("Platforms\\Win32 Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/win32/.+") +source_group("Scripting\\Decorate" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/decorate/.+") +source_group("Scripting\\ZScript" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/zscript/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.c ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.h) +source_group("Scripting\\Code Generation" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/codegeneration/.+") +source_group("Scripting\\VM" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/vm/.+") source_group("Shared Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_shared/.+") source_group("Versioning" FILES version.h win32/zdoom.rc) -source_group("Win32 Files" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/win32/.+") source_group("Xlat" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/xlat/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.c ${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.h) -source_group("ZScript" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/zscript/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.c ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.h) source_group("Source Files" FILES ${CMAKE_CURRENT_BINARY_DIR}/sc_man_scanner.h sc_man_scanner.re) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index d062ce533..d5150e985 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -70,6 +70,9 @@ #include "doomerrors.h" #include "p_effect.h" #include "serializer.h" +#include "vm.h" +#include "thingdef.h" +#include "info.h" #include "vmbuilder.h" // [SO] Just the way Randy said to do it :) diff --git a/src/d_main.cpp b/src/d_main.cpp index dad2b86d9..d7757ddf4 100644 --- a/src/d_main.cpp +++ b/src/d_main.cpp @@ -109,6 +109,7 @@ #include "p_local.h" #include "autosegs.h" #include "fragglescript/t_fs.h" +#include "vm.h" EXTERN_CVAR(Bool, hud_althud) void DrawHUD(); diff --git a/src/dobjgc.cpp b/src/dobjgc.cpp index afdc75508..28715a0ec 100644 --- a/src/dobjgc.cpp +++ b/src/dobjgc.cpp @@ -77,6 +77,7 @@ #include "r_utility.h" #include "menu/menu.h" #include "intermission/intermission.h" +#include "vm.h" // MACROS ------------------------------------------------------------------ diff --git a/src/dobjtype.h b/src/dobjtype.h index 8ccb62aca..19aeca71b 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -68,7 +68,6 @@ struct StateCallData; class VMFrameStack; struct VMValue; struct VMReturn; -typedef int (*actionf_p)(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret);/*(VM_ARGS)*/ class VMFunction; // A VM function ------------------------------------------------------------ diff --git a/src/g_doom/a_arachnotron.cpp b/src/g_doom/a_arachnotron.cpp index 62660c7f5..e558b05b2 100644 --- a/src/g_doom/a_arachnotron.cpp +++ b/src/g_doom/a_arachnotron.cpp @@ -4,7 +4,7 @@ #include "p_local.h" #include "p_enemy.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ DEFINE_ACTION_FUNCTION(AActor, A_BspiAttack) diff --git a/src/g_doom/a_archvile.cpp b/src/g_doom/a_archvile.cpp index 84481e5f6..06be5cc0c 100644 --- a/src/g_doom/a_archvile.cpp +++ b/src/g_doom/a_archvile.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ // diff --git a/src/g_doom/a_bossbrain.cpp b/src/g_doom/a_bossbrain.cpp index b0e725910..8d4163c09 100644 --- a/src/g_doom/a_bossbrain.cpp +++ b/src/g_doom/a_bossbrain.cpp @@ -7,7 +7,7 @@ #include "s_sound.h" #include "statnums.h" #include "a_specialspot.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" #include "g_level.h" */ diff --git a/src/g_doom/a_cacodemon.cpp b/src/g_doom/a_cacodemon.cpp index 3532374cf..775580c29 100644 --- a/src/g_doom/a_cacodemon.cpp +++ b/src/g_doom/a_cacodemon.cpp @@ -7,7 +7,7 @@ #include "gstrings.h" #include "a_action.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_headattack ("HeadAttack"); diff --git a/src/g_doom/a_cyberdemon.cpp b/src/g_doom/a_cyberdemon.cpp index 9e0ddd1dd..55d9181bf 100644 --- a/src/g_doom/a_cyberdemon.cpp +++ b/src/g_doom/a_cyberdemon.cpp @@ -4,7 +4,7 @@ #include "s_sound.h" #include "p_enemy.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ DEFINE_ACTION_FUNCTION(AActor, A_CyberAttack) diff --git a/src/g_doom/a_demon.cpp b/src/g_doom/a_demon.cpp index 3f8e2f626..330b02b30 100644 --- a/src/g_doom/a_demon.cpp +++ b/src/g_doom/a_demon.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_sargattack ("SargAttack"); diff --git a/src/g_doom/a_doomimp.cpp b/src/g_doom/a_doomimp.cpp index f00b53a42..6130d39ca 100644 --- a/src/g_doom/a_doomimp.cpp +++ b/src/g_doom/a_doomimp.cpp @@ -7,7 +7,7 @@ #include "p_enemy.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_troopattack ("TroopAttack"); diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 129c32f1e..b68ded59d 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -7,7 +7,7 @@ #include "gi.h" #include "doomstat.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "p_enemy.h" #include "a_doomglobal.h" @@ -19,6 +19,7 @@ #include "p_maputl.h" #include "serializer.h" #include "g_shared/a_pickups.h" +#include "vm.h" // Include all the other Doom stuff here to reduce compile time #include "a_arachnotron.cpp" diff --git a/src/g_doom/a_doomweaps.cpp b/src/g_doom/a_doomweaps.cpp index a35a31b61..fd60e85d8 100644 --- a/src/g_doom/a_doomweaps.cpp +++ b/src/g_doom/a_doomweaps.cpp @@ -11,7 +11,7 @@ #include "p_effect.h" #include "gi.h" #include "templates.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_doom/a_fatso.cpp b/src/g_doom/a_fatso.cpp index 872e1982d..eeef39984 100644 --- a/src/g_doom/a_fatso.cpp +++ b/src/g_doom/a_fatso.cpp @@ -7,7 +7,7 @@ #include "p_enemy.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ // diff --git a/src/g_doom/a_keen.cpp b/src/g_doom/a_keen.cpp index d0a10da58..5c57128a3 100644 --- a/src/g_doom/a_keen.cpp +++ b/src/g_doom/a_keen.cpp @@ -5,7 +5,7 @@ #include "p_spec.h" #include "p_enemy.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ // diff --git a/src/g_doom/a_lostsoul.cpp b/src/g_doom/a_lostsoul.cpp index 056802fe0..35468ac08 100644 --- a/src/g_doom/a_lostsoul.cpp +++ b/src/g_doom/a_lostsoul.cpp @@ -9,7 +9,7 @@ #include "gi.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ FRandom pr_oldsoul ("BetaLostSoul"); diff --git a/src/g_doom/a_painelemental.cpp b/src/g_doom/a_painelemental.cpp index 3620b88db..8a0aa41bf 100644 --- a/src/g_doom/a_painelemental.cpp +++ b/src/g_doom/a_painelemental.cpp @@ -6,7 +6,7 @@ #include "a_action.h" #include "templates.h" #include "m_bbox.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_doom/a_possessed.cpp b/src/g_doom/a_possessed.cpp index f6b559c4b..e665e8f11 100644 --- a/src/g_doom/a_possessed.cpp +++ b/src/g_doom/a_possessed.cpp @@ -7,7 +7,7 @@ #include "p_enemy.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_posattack ("PosAttack"); diff --git a/src/g_doom/a_revenant.cpp b/src/g_doom/a_revenant.cpp index 9c8a38602..adb0ea100 100644 --- a/src/g_doom/a_revenant.cpp +++ b/src/g_doom/a_revenant.cpp @@ -8,7 +8,7 @@ #include "p_enemy.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_doom/a_scriptedmarine.cpp b/src/g_doom/a_scriptedmarine.cpp index 2c293a2de..76f3e4577 100644 --- a/src/g_doom/a_scriptedmarine.cpp +++ b/src/g_doom/a_scriptedmarine.cpp @@ -7,7 +7,7 @@ #include "a_doomglobal.h" #include "s_sound.h" #include "r_data/r_translate.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_doom/a_spidermaster.cpp b/src/g_doom/a_spidermaster.cpp index aaafc4d99..ab12db4f0 100644 --- a/src/g_doom/a_spidermaster.cpp +++ b/src/g_doom/a_spidermaster.cpp @@ -6,7 +6,7 @@ #include "p_local.h" #include "p_enemy.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_spidrefire ("SpidRefire"); diff --git a/src/g_heretic/a_chicken.cpp b/src/g_heretic/a_chicken.cpp index 7f62d5f0e..78eb7ca8d 100644 --- a/src/g_heretic/a_chicken.cpp +++ b/src/g_heretic/a_chicken.cpp @@ -11,7 +11,7 @@ #include "p_enemy.h" #include "d_event.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ void P_UpdateBeak (AActor *actor); diff --git a/src/g_heretic/a_dsparil.cpp b/src/g_heretic/a_dsparil.cpp index f5870f09e..632260648 100644 --- a/src/g_heretic/a_dsparil.cpp +++ b/src/g_heretic/a_dsparil.cpp @@ -9,7 +9,7 @@ #include "a_sharedglobal.h" #include "gstrings.h" #include "a_specialspot.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_heretic/a_hereticartifacts.cpp b/src/g_heretic/a_hereticartifacts.cpp index 518abb44a..1c4677cb6 100644 --- a/src/g_heretic/a_hereticartifacts.cpp +++ b/src/g_heretic/a_hereticartifacts.cpp @@ -5,7 +5,7 @@ #include "gstrings.h" #include "p_local.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ // Tome of power ------------------------------------------------------------ diff --git a/src/g_heretic/a_hereticimp.cpp b/src/g_heretic/a_hereticimp.cpp index 81185c0c1..41e207ef1 100644 --- a/src/g_heretic/a_hereticimp.cpp +++ b/src/g_heretic/a_hereticimp.cpp @@ -6,7 +6,7 @@ #include "s_sound.h" #include "p_local.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_impmsatk ("ImpMsAttack"); diff --git a/src/g_heretic/a_hereticmisc.cpp b/src/g_heretic/a_hereticmisc.cpp index 36969f6e7..d3ffbac23 100644 --- a/src/g_heretic/a_hereticmisc.cpp +++ b/src/g_heretic/a_hereticmisc.cpp @@ -6,7 +6,7 @@ #include "p_local.h" #include "s_sound.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "p_enemy.h" #include "a_specialspot.h" #include "g_level.h" @@ -18,6 +18,7 @@ #include "a_morph.h" #include "p_spec.h" #include "serializer.h" +#include "vm.h" // Include all the other Heretic stuff here to reduce compile time #include "a_chicken.cpp" diff --git a/src/g_heretic/a_hereticweaps.cpp b/src/g_heretic/a_hereticweaps.cpp index eb7d49983..c86cafce7 100644 --- a/src/g_heretic/a_hereticweaps.cpp +++ b/src/g_heretic/a_hereticweaps.cpp @@ -11,7 +11,7 @@ #include "gstrings.h" #include "gi.h" #include "r_data/r_translate.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_heretic/a_ironlich.cpp b/src/g_heretic/a_ironlich.cpp index a88748407..c80a7bbed 100644 --- a/src/g_heretic/a_ironlich.cpp +++ b/src/g_heretic/a_ironlich.cpp @@ -7,7 +7,7 @@ #include "p_enemy.h" #include "a_action.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_heretic/a_knight.cpp b/src/g_heretic/a_knight.cpp index 9f42a328a..9c4ae2473 100644 --- a/src/g_heretic/a_knight.cpp +++ b/src/g_heretic/a_knight.cpp @@ -7,7 +7,7 @@ #include "a_action.h" #include "a_sharedglobal.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_dripblood ("DripBlood"); diff --git a/src/g_heretic/a_wizard.cpp b/src/g_heretic/a_wizard.cpp index 704488f16..e66bc5531 100644 --- a/src/g_heretic/a_wizard.cpp +++ b/src/g_heretic/a_wizard.cpp @@ -7,7 +7,7 @@ #include "p_enemy.h" #include "a_action.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_wizatk3 ("WizAtk3"); diff --git a/src/g_hexen/a_bats.cpp b/src/g_hexen/a_bats.cpp index 56c7ac024..875910059 100644 --- a/src/g_hexen/a_bats.cpp +++ b/src/g_hexen/a_bats.cpp @@ -4,7 +4,7 @@ #include "m_random.h" #include "p_local.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_batspawn ("BatSpawn"); diff --git a/src/g_hexen/a_bishop.cpp b/src/g_hexen/a_bishop.cpp index 5fb95d8be..a88daa23b 100644 --- a/src/g_hexen/a_bishop.cpp +++ b/src/g_hexen/a_bishop.cpp @@ -6,7 +6,7 @@ #include "a_action.h" #include "m_random.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_boom ("BishopBoom"); diff --git a/src/g_hexen/a_centaur.cpp b/src/g_hexen/a_centaur.cpp index 692688b63..75049650d 100644 --- a/src/g_hexen/a_centaur.cpp +++ b/src/g_hexen/a_centaur.cpp @@ -3,7 +3,7 @@ #include "p_enemy.h" #include "a_action.h" #include "m_random.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_centaurdefend ("CentaurDefend"); diff --git a/src/g_hexen/a_clericflame.cpp b/src/g_hexen/a_clericflame.cpp index 5b4eba2e8..a9c8b6378 100644 --- a/src/g_hexen/a_clericflame.cpp +++ b/src/g_hexen/a_clericflame.cpp @@ -10,7 +10,7 @@ #include "p_pspr.h" #include "gstrings.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ const double FLAMESPEED = 0.45; diff --git a/src/g_hexen/a_clericholy.cpp b/src/g_hexen/a_clericholy.cpp index b08ab3e74..f660b1e7d 100644 --- a/src/g_hexen/a_clericholy.cpp +++ b/src/g_hexen/a_clericholy.cpp @@ -7,7 +7,7 @@ #include "a_hexenglobal.h" #include "gstrings.h" #include "a_weaponpiece.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "doomstat.h" */ diff --git a/src/g_hexen/a_clericmace.cpp b/src/g_hexen/a_clericmace.cpp index 69f1f729c..fce979af1 100644 --- a/src/g_hexen/a_clericmace.cpp +++ b/src/g_hexen/a_clericmace.cpp @@ -2,7 +2,7 @@ #include "m_random.h" #include "p_local.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_maceatk ("CMaceAttack"); diff --git a/src/g_hexen/a_clericstaff.cpp b/src/g_hexen/a_clericstaff.cpp index de4e1d75f..6b54d4de3 100644 --- a/src/g_hexen/a_clericstaff.cpp +++ b/src/g_hexen/a_clericstaff.cpp @@ -10,7 +10,7 @@ #include "p_pspr.h" #include "gstrings.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_staffcheck ("CStaffCheck"); diff --git a/src/g_hexen/a_dragon.cpp b/src/g_hexen/a_dragon.cpp index c94be3988..ca56525a9 100644 --- a/src/g_hexen/a_dragon.cpp +++ b/src/g_hexen/a_dragon.cpp @@ -6,7 +6,7 @@ #include "a_action.h" #include "m_random.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_dragonseek ("DragonSeek"); diff --git a/src/g_hexen/a_fighteraxe.cpp b/src/g_hexen/a_fighteraxe.cpp index f47ad6a9d..a194869f3 100644 --- a/src/g_hexen/a_fighteraxe.cpp +++ b/src/g_hexen/a_fighteraxe.cpp @@ -10,9 +10,11 @@ #include "p_pspr.h" #include "gstrings.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ +DECLARE_ACTION(A_Raise) + #define AXERANGE (2.25 * MELEERANGE) static FRandom pr_axeatk ("FAxeAtk"); diff --git a/src/g_hexen/a_fighterhammer.cpp b/src/g_hexen/a_fighterhammer.cpp index c33737bfd..f8fbe33e3 100644 --- a/src/g_hexen/a_fighterhammer.cpp +++ b/src/g_hexen/a_fighterhammer.cpp @@ -10,7 +10,7 @@ #include "p_pspr.h" #include "gstrings.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ const double HAMMER_RANGE = 1.5 * MELEERANGE; diff --git a/src/g_hexen/a_fighterplayer.cpp b/src/g_hexen/a_fighterplayer.cpp index 3624ed625..d946c689c 100644 --- a/src/g_hexen/a_fighterplayer.cpp +++ b/src/g_hexen/a_fighterplayer.cpp @@ -8,7 +8,7 @@ #include "p_local.h" #include "a_action.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ IMPLEMENT_CLASS (AFighterWeapon) diff --git a/src/g_hexen/a_fighterquietus.cpp b/src/g_hexen/a_fighterquietus.cpp index 3d04e984a..a86d4911a 100644 --- a/src/g_hexen/a_fighterquietus.cpp +++ b/src/g_hexen/a_fighterquietus.cpp @@ -10,7 +10,7 @@ #include "gstrings.h" #include "a_hexenglobal.h" #include "a_weaponpiece.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_quietusdrop ("QuietusDrop"); diff --git a/src/g_hexen/a_firedemon.cpp b/src/g_hexen/a_firedemon.cpp index 712363167..b60c904e3 100644 --- a/src/g_hexen/a_firedemon.cpp +++ b/src/g_hexen/a_firedemon.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "a_action.h" #include "m_random.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ #define FIREDEMON_ATTACK_RANGE (64*8.) diff --git a/src/g_hexen/a_flechette.cpp b/src/g_hexen/a_flechette.cpp index ccc2bf112..3d9555843 100644 --- a/src/g_hexen/a_flechette.cpp +++ b/src/g_hexen/a_flechette.cpp @@ -10,7 +10,7 @@ #include "a_action.h" #include "a_hexenglobal.h" #include "w_wad.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_hexen/a_fog.cpp b/src/g_hexen/a_fog.cpp index b89f8d38c..98dbf62b7 100644 --- a/src/g_hexen/a_fog.cpp +++ b/src/g_hexen/a_fog.cpp @@ -1,7 +1,7 @@ /* #include "m_random.h" #include "p_local.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_fogspawn ("FogSpawn"); diff --git a/src/g_hexen/a_heresiarch.cpp b/src/g_hexen/a_heresiarch.cpp index c96c4cc1f..267320029 100644 --- a/src/g_hexen/a_heresiarch.cpp +++ b/src/g_hexen/a_heresiarch.cpp @@ -7,7 +7,7 @@ #include "m_random.h" #include "a_hexenglobal.h" #include "i_system.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_hexen/a_hexenmisc.cpp b/src/g_hexen/a_hexenmisc.cpp index 31a17c3a3..2c91f37b2 100644 --- a/src/g_hexen/a_hexenmisc.cpp +++ b/src/g_hexen/a_hexenmisc.cpp @@ -7,7 +7,7 @@ #include "a_sharedglobal.h" #include "a_hexenglobal.h" #include "i_system.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "gi.h" #include "g_level.h" #include "p_enemy.h" @@ -24,6 +24,7 @@ #include "p_maputl.h" #include "p_spec.h" #include "serializer.h" +#include "vm.h" // Include all the Hexen stuff here to reduce compile time #include "a_bats.cpp" diff --git a/src/g_hexen/a_hexenspecialdecs.cpp b/src/g_hexen/a_hexenspecialdecs.cpp index 28de8d46a..61d5780d1 100644 --- a/src/g_hexen/a_hexenspecialdecs.cpp +++ b/src/g_hexen/a_hexenspecialdecs.cpp @@ -11,7 +11,7 @@ #include "p_local.h" #include "p_lnspec.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "doomstat.h" */ diff --git a/src/g_hexen/a_iceguy.cpp b/src/g_hexen/a_iceguy.cpp index d00e86041..d518c7db7 100644 --- a/src/g_hexen/a_iceguy.cpp +++ b/src/g_hexen/a_iceguy.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "a_action.h" #include "m_random.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_iceguylook ("IceGuyLook"); diff --git a/src/g_hexen/a_korax.cpp b/src/g_hexen/a_korax.cpp index 7f0d3a43c..01457b91c 100644 --- a/src/g_hexen/a_korax.cpp +++ b/src/g_hexen/a_korax.cpp @@ -25,7 +25,7 @@ #include "a_action.h" #include "m_random.h" #include "i_system.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_hexen/a_magecone.cpp b/src/g_hexen/a_magecone.cpp index f31e57e58..b33f93787 100644 --- a/src/g_hexen/a_magecone.cpp +++ b/src/g_hexen/a_magecone.cpp @@ -10,7 +10,7 @@ #include "p_pspr.h" #include "gstrings.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ const int SHARDSPAWN_LEFT = 1; diff --git a/src/g_hexen/a_magelightning.cpp b/src/g_hexen/a_magelightning.cpp index 896384f4e..f322d88a6 100644 --- a/src/g_hexen/a_magelightning.cpp +++ b/src/g_hexen/a_magelightning.cpp @@ -10,7 +10,7 @@ #include "p_pspr.h" #include "gstrings.h" #include "a_hexenglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_hexen/a_magestaff.cpp b/src/g_hexen/a_magestaff.cpp index d7b06d009..ca846d794 100644 --- a/src/g_hexen/a_magestaff.cpp +++ b/src/g_hexen/a_magestaff.cpp @@ -7,7 +7,7 @@ #include "a_hexenglobal.h" #include "gstrings.h" #include "a_weaponpiece.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_hexen/a_pig.cpp b/src/g_hexen/a_pig.cpp index ea767dccd..11bfe3ce8 100644 --- a/src/g_hexen/a_pig.cpp +++ b/src/g_hexen/a_pig.cpp @@ -11,7 +11,7 @@ #include "p_enemy.h" #include "d_event.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_snoutattack ("SnoutAttack"); diff --git a/src/g_hexen/a_serpent.cpp b/src/g_hexen/a_serpent.cpp index 998466053..1f6d1dd2b 100644 --- a/src/g_hexen/a_serpent.cpp +++ b/src/g_hexen/a_serpent.cpp @@ -7,7 +7,7 @@ #include "a_action.h" #include "m_random.h" #include "p_terrain.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_serpentchase ("SerpentChase"); diff --git a/src/g_hexen/a_spike.cpp b/src/g_hexen/a_spike.cpp index 9f7396399..1e81f568f 100644 --- a/src/g_hexen/a_spike.cpp +++ b/src/g_hexen/a_spike.cpp @@ -7,7 +7,7 @@ #include "a_sharedglobal.h" #include "s_sound.h" #include "m_bbox.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_thrustraise ("ThrustRaise"); diff --git a/src/g_hexen/a_summon.cpp b/src/g_hexen/a_summon.cpp index eb5d825bf..c9daad6ec 100644 --- a/src/g_hexen/a_summon.cpp +++ b/src/g_hexen/a_summon.cpp @@ -6,7 +6,7 @@ #include "p_local.h" #include "s_sound.h" #include "ravenshared.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_hexen/a_teleportother.cpp b/src/g_hexen/a_teleportother.cpp index 7333d9d91..a89e62b4b 100644 --- a/src/g_hexen/a_teleportother.cpp +++ b/src/g_hexen/a_teleportother.cpp @@ -7,7 +7,7 @@ #include "s_sound.h" #include "p_lnspec.h" #include "m_random.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "doomstat.h" */ diff --git a/src/g_hexen/a_wraith.cpp b/src/g_hexen/a_wraith.cpp index 460fa6503..f5c1f44f4 100644 --- a/src/g_hexen/a_wraith.cpp +++ b/src/g_hexen/a_wraith.cpp @@ -7,7 +7,7 @@ #include "a_action.h" #include "m_random.h" #include "a_sharedglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_stealhealth ("StealHealth"); diff --git a/src/g_raven/a_minotaur.cpp b/src/g_raven/a_minotaur.cpp index 9f58ce4c3..e3636fe1b 100644 --- a/src/g_raven/a_minotaur.cpp +++ b/src/g_raven/a_minotaur.cpp @@ -8,12 +8,13 @@ #include "a_action.h" #include "gi.h" #include "w_wad.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "doomstat.h" #include "a_pickups.h" #include "d_player.h" #include "serializer.h" +#include "vm.h" #define MAULATORTICS (25*35) diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index c0ec37d09..3b1191131 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -1,5 +1,5 @@ #include "actor.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "p_conversation.h" #include "p_lnspec.h" #include "a_action.h" diff --git a/src/g_shared/a_bridge.cpp b/src/g_shared/a_bridge.cpp index 178f004ca..3161c2a45 100644 --- a/src/g_shared/a_bridge.cpp +++ b/src/g_shared/a_bridge.cpp @@ -2,7 +2,7 @@ #include "info.h" #include "gi.h" #include "m_random.h" -#include "thingdef/thingdef.h" +#include "vm.h" static FRandom pr_orbit ("Orbit"); diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index 00a6692b2..906be04c4 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -14,7 +14,7 @@ #include "a_strifeglobal.h" #include "a_morph.h" #include "a_specialspot.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "g_game.h" #include "doomstat.h" diff --git a/src/g_shared/a_randomspawner.cpp b/src/g_shared/a_randomspawner.cpp index ac162a241..3ab67425d 100644 --- a/src/g_shared/a_randomspawner.cpp +++ b/src/g_shared/a_randomspawner.cpp @@ -14,7 +14,7 @@ #include "statnums.h" #include "gstrings.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "v_text.h" #include "doomstat.h" #include "doomdata.h" diff --git a/src/g_shared/a_specialspot.cpp b/src/g_shared/a_specialspot.cpp index 1d8d1f72d..48a8ce1a1 100644 --- a/src/g_shared/a_specialspot.cpp +++ b/src/g_shared/a_specialspot.cpp @@ -37,7 +37,7 @@ #include "p_local.h" #include "statnums.h" #include "i_system.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" #include "serializer.h" #include "a_pickups.h" diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index edd250deb..36ffbc271 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -13,7 +13,7 @@ #include "cmdlib.h" #include "templates.h" #include "sbar.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" #include "g_level.h" #include "d_net.h" diff --git a/src/g_shared/sbarinfo.cpp b/src/g_shared/sbarinfo.cpp index 42f28173c..2e764a403 100644 --- a/src/g_shared/sbarinfo.cpp +++ b/src/g_shared/sbarinfo.cpp @@ -57,6 +57,7 @@ #include "p_acs.h" #include "gstrings.h" #include "version.h" +#include "cmdlib.h" #define ARTIFLASH_OFFSET (statusBar->invBarOffset+6) enum diff --git a/src/g_shared/shared_hud.cpp b/src/g_shared/shared_hud.cpp index c4d8ec1ed..4733c6e41 100644 --- a/src/g_shared/shared_hud.cpp +++ b/src/g_shared/shared_hud.cpp @@ -52,6 +52,7 @@ #include "d_net.h" #include "d_player.h" #include "r_utility.h" +#include "cmdlib.h" #include diff --git a/src/g_shared/shared_sbar.cpp b/src/g_shared/shared_sbar.cpp index a3bb76b7f..191b097d2 100644 --- a/src/g_shared/shared_sbar.cpp +++ b/src/g_shared/shared_sbar.cpp @@ -54,6 +54,7 @@ #include "serializer.h" #include "gstrings.h" #include "r_utility.h" +#include "cmdlib.h" #include "../version.h" diff --git a/src/g_strife/a_acolyte.cpp b/src/g_strife/a_acolyte.cpp index e8049da1b..6f08a84c8 100644 --- a/src/g_strife/a_acolyte.cpp +++ b/src/g_strife/a_acolyte.cpp @@ -7,7 +7,7 @@ #include "s_sound.h" #include "a_strifeglobal.h" #include "doomdata.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_strife/a_alienspectres.cpp b/src/g_strife/a_alienspectres.cpp index a7624785b..d4103015c 100644 --- a/src/g_strife/a_alienspectres.cpp +++ b/src/g_strife/a_alienspectres.cpp @@ -9,7 +9,7 @@ #include "a_strifeglobal.h" #include "c_console.h" #include "gstrings.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_strife/a_crusader.cpp b/src/g_strife/a_crusader.cpp index b54fdd427..8e340b820 100644 --- a/src/g_strife/a_crusader.cpp +++ b/src/g_strife/a_crusader.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "s_sound.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static bool CrusaderCheckRange (AActor *self) diff --git a/src/g_strife/a_entityboss.cpp b/src/g_strife/a_entityboss.cpp index 72eeaac3a..b7f60e26f 100644 --- a/src/g_strife/a_entityboss.cpp +++ b/src/g_strife/a_entityboss.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "s_sound.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" */ diff --git a/src/g_strife/a_inquisitor.cpp b/src/g_strife/a_inquisitor.cpp index e372d8de1..16871300a 100644 --- a/src/g_strife/a_inquisitor.cpp +++ b/src/g_strife/a_inquisitor.cpp @@ -5,7 +5,7 @@ #include "p_local.h" #include "p_enemy.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_inq ("Inquisitor"); diff --git a/src/g_strife/a_loremaster.cpp b/src/g_strife/a_loremaster.cpp index ead116c63..2d695ac8d 100644 --- a/src/g_strife/a_loremaster.cpp +++ b/src/g_strife/a_loremaster.cpp @@ -5,7 +5,7 @@ #include "m_random.h" #include "p_local.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ // Loremaster (aka Priest) -------------------------------------------------- diff --git a/src/g_strife/a_oracle.cpp b/src/g_strife/a_oracle.cpp index f1f0b0b2b..139786d89 100644 --- a/src/g_strife/a_oracle.cpp +++ b/src/g_strife/a_oracle.cpp @@ -4,7 +4,7 @@ #include "a_strifeglobal.h" #include "p_enemy.h" #include "r_defs.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ diff --git a/src/g_strife/a_programmer.cpp b/src/g_strife/a_programmer.cpp index bed5f838b..9c8cb6be3 100644 --- a/src/g_strife/a_programmer.cpp +++ b/src/g_strife/a_programmer.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "s_sound.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "doomstat.h" */ diff --git a/src/g_strife/a_reaver.cpp b/src/g_strife/a_reaver.cpp index 372aea794..09d771a19 100644 --- a/src/g_strife/a_reaver.cpp +++ b/src/g_strife/a_reaver.cpp @@ -6,7 +6,7 @@ #include "m_random.h" #include "p_local.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_reaverattack ("ReaverAttack"); diff --git a/src/g_strife/a_rebels.cpp b/src/g_strife/a_rebels.cpp index f2031a7a3..c4df1cba1 100644 --- a/src/g_strife/a_rebels.cpp +++ b/src/g_strife/a_rebels.cpp @@ -8,7 +8,7 @@ #include "gi.h" #include "a_sharedglobal.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_strife/a_sentinel.cpp b/src/g_strife/a_sentinel.cpp index 91adbb01e..42a7aeb47 100644 --- a/src/g_strife/a_sentinel.cpp +++ b/src/g_strife/a_sentinel.cpp @@ -4,7 +4,7 @@ #include "a_action.h" #include "p_local.h" #include "m_random.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_sentinelrefire ("SentinelRefire"); diff --git a/src/g_strife/a_spectral.cpp b/src/g_strife/a_spectral.cpp index 00b19055c..1b1f13b1a 100644 --- a/src/g_strife/a_spectral.cpp +++ b/src/g_strife/a_spectral.cpp @@ -6,7 +6,7 @@ #include "s_sound.h" #include "m_random.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ class ASpectralMonster : public AActor diff --git a/src/g_strife/a_stalker.cpp b/src/g_strife/a_stalker.cpp index 8ee07de8a..210bd8c22 100644 --- a/src/g_strife/a_stalker.cpp +++ b/src/g_strife/a_stalker.cpp @@ -5,7 +5,7 @@ #include "p_local.h" #include "p_enemy.h" #include "s_sound.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_stalker ("Stalker"); diff --git a/src/g_strife/a_strifeitems.cpp b/src/g_strife/a_strifeitems.cpp index 26ac88393..20de58d4f 100644 --- a/src/g_strife/a_strifeitems.cpp +++ b/src/g_strife/a_strifeitems.cpp @@ -13,7 +13,7 @@ #include "a_keys.h" #include "c_console.h" #include "templates.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "doomstat.h" */ diff --git a/src/g_strife/a_strifestuff.cpp b/src/g_strife/a_strifestuff.cpp index ad6bbe133..32ce0e395 100644 --- a/src/g_strife/a_strifestuff.cpp +++ b/src/g_strife/a_strifestuff.cpp @@ -10,7 +10,7 @@ #include "p_enemy.h" #include "p_lnspec.h" #include "c_console.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" #include "gstrings.h" #include "a_keys.h" @@ -21,6 +21,7 @@ #include "serializer.h" #include "p_spec.h" #include "portal.h" +#include "vm.h" // Include all the other Strife stuff here to reduce compile time #include "a_acolyte.cpp" diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index be3c3bf2b..66d635aa5 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -6,7 +6,7 @@ #include "s_sound.h" #include "p_enemy.h" #include "templates.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_strife/a_templar.cpp b/src/g_strife/a_templar.cpp index 547d4d73e..5ca2ef862 100644 --- a/src/g_strife/a_templar.cpp +++ b/src/g_strife/a_templar.cpp @@ -6,7 +6,7 @@ #include "p_enemy.h" #include "s_sound.h" #include "a_strifeglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" */ static FRandom pr_templar ("Templar"); diff --git a/src/g_strife/a_thingstoblowup.cpp b/src/g_strife/a_thingstoblowup.cpp index fed1c4337..6d1294b53 100644 --- a/src/g_strife/a_thingstoblowup.cpp +++ b/src/g_strife/a_thingstoblowup.cpp @@ -6,8 +6,8 @@ #include "p_enemy.h" #include "a_action.h" #include "gstrings.h" -#include "thingdef/thingdef.h" -#include "thingdef/thingdef.h" +#include "vm.h" +#include "vm.h" #include "doomstat.h" */ diff --git a/src/g_strife/strife_sbar.cpp b/src/g_strife/strife_sbar.cpp index bcdf624d7..122846a82 100644 --- a/src/g_strife/strife_sbar.cpp +++ b/src/g_strife/strife_sbar.cpp @@ -17,6 +17,7 @@ #include "g_level.h" #include "colormatcher.h" #include "v_palette.h" +#include "cmdlib.h" // Number of tics to move the popscreen up and down. #define POP_TIME (TICRATE/8) diff --git a/src/info.cpp b/src/info.cpp index ea6701fac..191ed2bd5 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -52,7 +52,7 @@ #include "cmdlib.h" #include "g_level.h" #include "stats.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "d_player.h" extern void LoadActors (); diff --git a/src/info.h b/src/info.h index 0e49e1f8f..5ba7eafd9 100644 --- a/src/info.h +++ b/src/info.h @@ -54,6 +54,18 @@ class FScanner; struct FActorInfo; class FIntCVar; +enum EStateDefineFlags +{ + SDF_NEXT = 0, + SDF_STATE = 1, + SDF_STOP = 2, + SDF_WAIT = 3, + SDF_LABEL = 4, + SDF_INDEX = 5, + SDF_MASK = 7, + SDF_DEHACKED = 8, // Identify a state as having been modified by a dehacked lump +}; + enum EStateType { STATE_Actor, diff --git a/src/menu/menudef.cpp b/src/menu/menudef.cpp index 618189b4f..0fcf4e4d5 100644 --- a/src/menu/menudef.cpp +++ b/src/menu/menudef.cpp @@ -50,6 +50,7 @@ #include "m_joy.h" #include "gi.h" #include "i_sound.h" +#include "cmdlib.h" #include "optionmenuitems.h" diff --git a/src/menu/menuinput.cpp b/src/menu/menuinput.cpp index 892118742..39d7a8c0b 100644 --- a/src/menu/menuinput.cpp +++ b/src/menu/menuinput.cpp @@ -40,6 +40,7 @@ #include "d_gui.h" #include "v_font.h" #include "v_palette.h" +#include "cmdlib.h" // [TP] New #includes #include "v_text.h" diff --git a/src/menu/messagebox.cpp b/src/menu/messagebox.cpp index 601c3e736..a72a37740 100644 --- a/src/menu/messagebox.cpp +++ b/src/menu/messagebox.cpp @@ -32,6 +32,7 @@ ** */ +#include #include "menu/menu.h" #include "d_event.h" #include "d_gui.h" diff --git a/src/p_acs.cpp b/src/p_acs.cpp index 71ef65f22..29aee9e12 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -83,6 +83,7 @@ #include "a_morph.h" #include "i_music.h" #include "serializer.h" +#include "thingdef.h" #include "g_shared/a_pickups.h" diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index c6bc8215b..c8e110a68 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -61,7 +61,7 @@ #include "c_console.h" #include "doomerrors.h" #include "a_sharedglobal.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "v_video.h" #include "v_font.h" #include "doomstat.h" @@ -77,6 +77,8 @@ #include "p_maputl.h" #include "p_spec.h" #include "templates.h" +#include "vm.h" +#include "thingdef.h" #include "math/cmath.h" AActor *SingleActorFromTID(int tid, AActor *defactor); diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index b7ad54095..5f63ff1e5 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -43,7 +43,7 @@ #include "p_enemy.h" #include "a_sharedglobal.h" #include "a_action.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "d_dehacked.h" #include "g_level.h" #include "r_utility.h" @@ -53,6 +53,7 @@ #include "p_spec.h" #include "p_checkposition.h" #include "math/cmath.h" +#include "vm.h" #include "gi.h" diff --git a/src/p_enemy.h b/src/p_enemy.h index 1be77a4ec..7f4424fd6 100644 --- a/src/p_enemy.h +++ b/src/p_enemy.h @@ -1,7 +1,8 @@ #ifndef __P_ENEMY_H__ #define __P_ENEMY_H__ -#include "thingdef/thingdef.h" +#include "vm.h" +#include "vectors.h" struct sector_t; class AActor; diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 1ebec242e..e443db368 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -53,7 +53,7 @@ #include "a_action.h" #include "a_keys.h" #include "p_conversation.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_game.h" #include "teaminfo.h" #include "r_data/r_translate.h" @@ -71,6 +71,7 @@ #include "p_checkposition.h" #include "serializer.h" #include "r_utility.h" +#include "thingdef.h" // MACROS ------------------------------------------------------------------ diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index e5b076acd..db2059088 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -25,7 +25,7 @@ #include "gi.h" #include "p_pspr.h" #include "templates.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "d_player.h" #include "serializer.h" diff --git a/src/p_pspr.h b/src/p_pspr.h index ea03e109f..568c289d2 100644 --- a/src/p_pspr.h +++ b/src/p_pspr.h @@ -25,7 +25,7 @@ // Basic data types. // Needs fixed point, and BAM angles. -#include "thingdef/thingdef.h" +//#include "vm.h" #define WEAPONBOTTOM 128. @@ -120,7 +120,6 @@ void DoReadyWeaponToBob(AActor *self); void DoReadyWeaponToFire(AActor *self, bool primary = true, bool secondary = true); void DoReadyWeaponToSwitch(AActor *self, bool switchable = true); -DECLARE_ACTION(A_Raise) void A_ReFire(AActor *self, FState *state = NULL); #endif // __P_PSPR_H__ diff --git a/src/p_states.cpp b/src/p_states.cpp index 1a8116e53..007f7f5ce 100644 --- a/src/p_states.cpp +++ b/src/p_states.cpp @@ -39,7 +39,8 @@ #include "i_system.h" #include "c_dispatch.h" #include "v_text.h" -#include "thingdef/thingdef.h" +#include "vm.h" +#include "thingdef.h" // Each state is owned by an actor. Actors can own any number of // states, but a single state cannot be owned by more than one diff --git a/src/p_user.cpp b/src/p_user.cpp index 0f3b6a516..c60e4bff6 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -48,7 +48,7 @@ #include "doomdef.h" #include "c_dispatch.h" #include "tarray.h" -#include "thingdef/thingdef.h" +#include "vm.h" #include "g_level.h" #include "d_net.h" #include "gstrings.h" diff --git a/src/thingdef/thingdef_exp.h b/src/scripting/codegeneration/thingdef_exp.h similarity index 100% rename from src/thingdef/thingdef_exp.h rename to src/scripting/codegeneration/thingdef_exp.h diff --git a/src/thingdef/thingdef_expression.cpp b/src/scripting/codegeneration/thingdef_expression.cpp similarity index 100% rename from src/thingdef/thingdef_expression.cpp rename to src/scripting/codegeneration/thingdef_expression.cpp diff --git a/src/thingdef/olddecorations.cpp b/src/scripting/decorate/olddecorations.cpp similarity index 99% rename from src/thingdef/olddecorations.cpp rename to src/scripting/decorate/olddecorations.cpp index 9afbfc965..4bcb2c36c 100644 --- a/src/thingdef/olddecorations.cpp +++ b/src/scripting/decorate/olddecorations.cpp @@ -48,7 +48,7 @@ #include "decallib.h" #include "i_system.h" #include "thingdef.h" -#include "thingdef_exp.h" +#include "codegeneration/thingdef_exp.h" #include "r_data/r_translate.h" // TYPES ------------------------------------------------------------------- diff --git a/src/thingdef/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp similarity index 99% rename from src/thingdef/thingdef_exp.cpp rename to src/scripting/decorate/thingdef_exp.cpp index 11baef722..2f52fb260 100644 --- a/src/thingdef/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -48,7 +48,7 @@ #include "thingdef.h" #include "p_lnspec.h" #include "doomstat.h" -#include "thingdef_exp.h" +#include "codegeneration/thingdef_exp.h" FRandom pr_exrandom ("EX_Random"); diff --git a/src/thingdef/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp similarity index 99% rename from src/thingdef/thingdef_parse.cpp rename to src/scripting/decorate/thingdef_parse.cpp index 6d1077ffe..5fbe27a9d 100644 --- a/src/thingdef/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -49,7 +49,7 @@ #include "v_palette.h" #include "doomerrors.h" #include "i_system.h" -#include "thingdef_exp.h" +#include "codegeneration/thingdef_exp.h" #include "w_wad.h" #include "v_video.h" #include "version.h" diff --git a/src/thingdef/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp similarity index 99% rename from src/thingdef/thingdef_states.cpp rename to src/scripting/decorate/thingdef_states.cpp index 3b692391c..59d620b2a 100644 --- a/src/thingdef/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -54,7 +54,7 @@ #include "s_sound.h" #include "i_system.h" #include "colormatcher.h" -#include "thingdef_exp.h" +#include "codegeneration/thingdef_exp.h" #include "version.h" #include "templates.h" diff --git a/src/thingdef/thingdef.cpp b/src/scripting/thingdef.cpp similarity index 99% rename from src/thingdef/thingdef.cpp rename to src/scripting/thingdef.cpp index 8b174988d..175aa8990 100644 --- a/src/thingdef/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -61,7 +61,7 @@ #include "p_conversation.h" #include "v_text.h" #include "thingdef.h" -#include "thingdef_exp.h" +#include "codegeneration/thingdef_exp.h" #include "a_sharedglobal.h" #include "vmbuilder.h" #include "stats.h" diff --git a/src/thingdef/thingdef.h b/src/scripting/thingdef.h similarity index 76% rename from src/thingdef/thingdef.h rename to src/scripting/thingdef.h index 152f32431..84f1f7d06 100644 --- a/src/thingdef/thingdef.h +++ b/src/scripting/thingdef.h @@ -6,6 +6,7 @@ #include "s_sound.h" #include "sc_man.h" #include "cmdlib.h" +#include "vm.h" class FScanner; @@ -46,18 +47,6 @@ class FxExpression; struct FStateLabels; -enum EStateDefineFlags -{ - SDF_NEXT = 0, - SDF_STATE = 1, - SDF_STOP = 2, - SDF_WAIT = 3, - SDF_LABEL = 4, - SDF_INDEX = 5, - SDF_MASK = 7, - SDF_DEHACKED = 8, // Identify a state as having been modified by a dehacked lump -}; - struct FStateDefine { FName Label; @@ -171,13 +160,6 @@ inline void ResetBaggage (Baggage *bag, PClassActor *stateclass) // //========================================================================== -struct AFuncDesc -{ - const char *Name; - actionf_p Function; - VMNativeFunction **VMPointer; -}; - AFuncDesc *FindFunction(const char * string); @@ -189,8 +171,6 @@ class FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestr FName CheckCastKludges(FName in); void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls, DWORD funcflags); -PFunction *FindGlobalActionFunction(const char *name); - //========================================================================== // // Property parser @@ -232,23 +212,13 @@ enum EDefinitionType }; #if defined(_MSC_VER) -#pragma section(".areg$u",read) #pragma section(".greg$u",read) -#pragma section(".mreg$u",read) -#define MSVC_ASEG __declspec(allocate(".areg$u")) -#define GCC_ASEG #define MSVC_PSEG __declspec(allocate(".greg$u")) #define GCC_PSEG -#define MSVC_MSEG __declspec(allocate(".mreg$u")) -#define GCC_MSEG #else -#define MSVC_ASEG -#define GCC_ASEG __attribute__((section(SECTION_AREG))) __attribute__((used)) #define MSVC_PSEG #define GCC_PSEG __attribute__((section(SECTION_GREG))) __attribute__((used)) -#define MSVC_MSEG -#define GCC_MSEG __attribute__((section(SECTION_MREG))) __attribute__((used)) #endif @@ -322,39 +292,4 @@ int MatchString (const char *in, const char **strings); #define PROP_COLOR_PARM(var, no) \ int var = params[(no)+1].i== 0? params[(no)+2].i : V_GetColor(NULL, params[(no)+2].s); - -// Macros to handle action functions. These are here so that I don't have to -// change every single use in case the parameters change. -#define DECLARE_ACTION(name) extern VMNativeFunction *name##_VMPtr; - -// This distinction is here so that CALL_ACTION produces errors when trying to -// access a function that requires parameters. -#define DEFINE_ACTION_FUNCTION(cls, name) \ - static int AF_##name(VM_ARGS); \ - VMNativeFunction *name##_VMPtr; \ - static const AFuncDesc cls##_##name##_Hook = { #name, AF_##name, &name##_VMPtr }; \ - extern AFuncDesc const *const cls##_##name##_HookPtr; \ - MSVC_ASEG AFuncDesc const *const cls##_##name##_HookPtr GCC_ASEG = &cls##_##name##_Hook; \ - static int AF_##name(VM_ARGS) - -#define DEFINE_ACTION_FUNCTION_PARAMS(cls, name) DEFINE_ACTION_FUNCTION(cls, name) - -//#define DECLARE_PARAMINFO AActor *self, AActor *stateowner, FState *CallingState, int ParameterIndex, StateCallData *statecall -//#define PUSH_PARAMINFO self, stateowner, CallingState, ParameterIndex, statecall - -#define CALL_ACTION(name,self) { /*AF_##name(self, self, NULL, 0, NULL)*/ \ - VMValue params[3] = { self, self, VMValue(NULL, ATAG_STATEINFO) }; \ - stack->Call(name##_VMPtr, params, countof(params), NULL, 0, NULL); \ - } - - -#define ACTION_RETURN_STATE(v) do { FState *state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_STATE); return 1; } return 0; } while(0) -#define ACTION_RETURN_FLOAT(v) do { double u = v; if (numret > 0) { assert(ret != nullptr); ret->SetFloat(u); return 1; } return 0; } while(0) -#define ACTION_RETURN_INT(v) do { int u = v; if (numret > 0) { assert(ret != NULL); ret->SetInt(u); return 1; } return 0; } while(0) -#define ACTION_RETURN_BOOL(v) ACTION_RETURN_INT(v) - -// Checks to see what called the current action function -#define ACTION_CALL_FROM_ACTOR() (stateinfo == nullptr || stateinfo->mStateType == STATE_Actor) -#define ACTION_CALL_FROM_PSPRITE() (self->player && stateinfo != nullptr && stateinfo->mStateType == STATE_Psprite) -#define ACTION_CALL_FROM_INVENTORY() (stateinfo != nullptr && stateinfo->mStateType == STATE_StateChain) #endif diff --git a/src/thingdef/thingdef_data.cpp b/src/scripting/thingdef_data.cpp similarity index 100% rename from src/thingdef/thingdef_data.cpp rename to src/scripting/thingdef_data.cpp diff --git a/src/thingdef/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp similarity index 100% rename from src/thingdef/thingdef_properties.cpp rename to src/scripting/thingdef_properties.cpp diff --git a/src/zscript/vm.h b/src/scripting/vm/vm.h similarity index 90% rename from src/zscript/vm.h rename to src/scripting/vm/vm.h index a000e9533..28b555e4e 100644 --- a/src/zscript/vm.h +++ b/src/scripting/vm/vm.h @@ -3,6 +3,7 @@ #include "zstring.h" #include "dobject.h" +#include "autosegs.h" #define MAX_RETURNS 8 // Maximum number of results a function called by script code can return #define MAX_TRY_DEPTH 8 // Maximum number of nested TRYs in a single function @@ -960,4 +961,63 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_OBJECT_OPT(x,type) ++paramnum; PARAM_OBJECT_OPT_AT(paramnum,x,type) #define PARAM_CLASS_OPT(x,base) ++paramnum; PARAM_CLASS_OPT_AT(paramnum,x,base) +typedef int(*actionf_p)(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret);/*(VM_ARGS)*/ + +struct AFuncDesc +{ + const char *Name; + actionf_p Function; + VMNativeFunction **VMPointer; +}; + +#if defined(_MSC_VER) +#pragma section(".areg$u",read) + +#define MSVC_ASEG __declspec(allocate(".areg$u")) +#define GCC_ASEG +#else +#define MSVC_ASEG +#define GCC_ASEG __attribute__((section(SECTION_AREG))) __attribute__((used)) +#endif + +// Macros to handle action functions. These are here so that I don't have to +// change every single use in case the parameters change. +#define DECLARE_ACTION(name) extern VMNativeFunction *name##_VMPtr; + +// This distinction is here so that CALL_ACTION produces errors when trying to +// access a function that requires parameters. +#define DEFINE_ACTION_FUNCTION(cls, name) \ + static int AF_##name(VM_ARGS); \ + VMNativeFunction *name##_VMPtr; \ + static const AFuncDesc cls##_##name##_Hook = { #name, AF_##name, &name##_VMPtr }; \ + extern AFuncDesc const *const cls##_##name##_HookPtr; \ + MSVC_ASEG AFuncDesc const *const cls##_##name##_HookPtr GCC_ASEG = &cls##_##name##_Hook; \ + static int AF_##name(VM_ARGS) + +#define DEFINE_ACTION_FUNCTION_PARAMS(cls, name) DEFINE_ACTION_FUNCTION(cls, name) + +//#define DECLARE_PARAMINFO AActor *self, AActor *stateowner, FState *CallingState, int ParameterIndex, StateCallData *statecall +//#define PUSH_PARAMINFO self, stateowner, CallingState, ParameterIndex, statecall + +#define CALL_ACTION(name,self) { /*AF_##name(self, self, NULL, 0, NULL)*/ \ + VMValue params[3] = { self, self, VMValue(NULL, ATAG_STATEINFO) }; \ + stack->Call(name##_VMPtr, params, countof(params), NULL, 0, NULL); \ + } + + +#define ACTION_RETURN_STATE(v) do { FState *state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_STATE); return 1; } return 0; } while(0) +#define ACTION_RETURN_FLOAT(v) do { double u = v; if (numret > 0) { assert(ret != nullptr); ret->SetFloat(u); return 1; } return 0; } while(0) +#define ACTION_RETURN_INT(v) do { int u = v; if (numret > 0) { assert(ret != NULL); ret->SetInt(u); return 1; } return 0; } while(0) +#define ACTION_RETURN_BOOL(v) ACTION_RETURN_INT(v) + +// Checks to see what called the current action function +#define ACTION_CALL_FROM_ACTOR() (stateinfo == nullptr || stateinfo->mStateType == STATE_Actor) +#define ACTION_CALL_FROM_PSPRITE() (self->player && stateinfo != nullptr && stateinfo->mStateType == STATE_Psprite) +#define ACTION_CALL_FROM_INVENTORY() (stateinfo != nullptr && stateinfo->mStateType == STATE_StateChain) + +class PFunction; + +PFunction *FindGlobalActionFunction(const char *name); + + #endif diff --git a/src/zscript/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp similarity index 100% rename from src/zscript/vmbuilder.cpp rename to src/scripting/vm/vmbuilder.cpp diff --git a/src/zscript/vmbuilder.h b/src/scripting/vm/vmbuilder.h similarity index 100% rename from src/zscript/vmbuilder.h rename to src/scripting/vm/vmbuilder.h diff --git a/src/zscript/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp similarity index 100% rename from src/zscript/vmdisasm.cpp rename to src/scripting/vm/vmdisasm.cpp diff --git a/src/zscript/vmexec.cpp b/src/scripting/vm/vmexec.cpp similarity index 100% rename from src/zscript/vmexec.cpp rename to src/scripting/vm/vmexec.cpp diff --git a/src/zscript/vmexec.h b/src/scripting/vm/vmexec.h similarity index 100% rename from src/zscript/vmexec.h rename to src/scripting/vm/vmexec.h diff --git a/src/zscript/vmframe.cpp b/src/scripting/vm/vmframe.cpp similarity index 100% rename from src/zscript/vmframe.cpp rename to src/scripting/vm/vmframe.cpp diff --git a/src/zscript/vmops.h b/src/scripting/vm/vmops.h similarity index 100% rename from src/zscript/vmops.h rename to src/scripting/vm/vmops.h diff --git a/src/zscript/ast.cpp b/src/scripting/zscript/ast.cpp similarity index 100% rename from src/zscript/ast.cpp rename to src/scripting/zscript/ast.cpp diff --git a/src/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon similarity index 100% rename from src/zscript/zcc-parse.lemon rename to src/scripting/zscript/zcc-parse.lemon diff --git a/src/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp similarity index 99% rename from src/zscript/zcc_compile.cpp rename to src/scripting/zscript/zcc_compile.cpp index 19af0e7c1..0d9558a52 100644 --- a/src/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -46,7 +46,7 @@ #include "v_text.h" #include "p_lnspec.h" #include "gdtoa.h" -#include "thingdef_exp.h" +#include "codegeneration/thingdef_exp.h" #define DEFINING_CONST ((PSymbolConst *)(void *)1) diff --git a/src/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h similarity index 100% rename from src/zscript/zcc_compile.h rename to src/scripting/zscript/zcc_compile.h diff --git a/src/zscript/zcc_expr.cpp b/src/scripting/zscript/zcc_expr.cpp similarity index 100% rename from src/zscript/zcc_expr.cpp rename to src/scripting/zscript/zcc_expr.cpp diff --git a/src/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h similarity index 100% rename from src/zscript/zcc_exprlist.h rename to src/scripting/zscript/zcc_exprlist.h diff --git a/src/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp similarity index 100% rename from src/zscript/zcc_parser.cpp rename to src/scripting/zscript/zcc_parser.cpp diff --git a/src/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h similarity index 100% rename from src/zscript/zcc_parser.h rename to src/scripting/zscript/zcc_parser.h diff --git a/src/serializer.cpp b/src/serializer.cpp index 7861701c0..5564cdf50 100644 --- a/src/serializer.cpp +++ b/src/serializer.cpp @@ -63,6 +63,7 @@ #include "w_zip.h" #include "doomerrors.h" #include "v_text.h" +#include "cmdlib.h" char nulspace[1024 * 1024 * 4]; bool save_full = false; // for testing. Should be removed afterward. diff --git a/src/sound/oalsound.cpp b/src/sound/oalsound.cpp index 21370d082..42933e5db 100644 --- a/src/sound/oalsound.cpp +++ b/src/sound/oalsound.cpp @@ -58,6 +58,7 @@ #include "i_music.h" #include "i_musicinterns.h" #include "tempfiles.h" +#include "cmdlib.h" #include "oalload.h" diff --git a/src/wi_stuff.cpp b/src/wi_stuff.cpp index 108edff3b..12ca10e32 100644 --- a/src/wi_stuff.cpp +++ b/src/wi_stuff.cpp @@ -51,6 +51,7 @@ #include "r_data/r_translate.h" #include "templates.h" #include "gstrings.h" +#include "cmdlib.h" // States for the intermission typedef enum From 59ed26c0b61a0a3cd63e5b140b98db31973c6f70 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 12 Oct 2016 20:42:41 +0200 Subject: [PATCH 023/255] - resorted some of thingdef.cpp's contents into more appropriate files. - split FinishActor into several functions. While DECORATE can, ZSCRIPT cannot do all this in one go. - split the state finalization into several class-specific virtual functions. --- src/g_shared/a_pickups.cpp | 6 + src/g_shared/a_pickups.h | 2 + src/g_shared/a_weapons.cpp | 32 ++++ src/info.cpp | 71 +++++++ src/info.h | 4 + src/scripting/decorate/thingdef_parse.cpp | 131 ++++++++++++- src/scripting/thingdef.cpp | 215 +--------------------- src/scripting/thingdef.h | 2 - src/scripting/zscript/zcc_compile.cpp | 16 ++ wadsrc/static/zscript/actor.txt | 27 +-- 10 files changed, 286 insertions(+), 220 deletions(-) diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index 906be04c4..c4daae024 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -65,6 +65,12 @@ void PClassInventory::ReplaceClassRef(PClass *oldclass, PClass *newclass) } } +void PClassInventory::Finalize(FStateDefinitions &statedef) +{ + Super::Finalize(statedef); + ((AActor*)Defaults)->flags |= MF_SPECIAL; +} + IMPLEMENT_CLASS(PClassAmmo) PClassAmmo::PClassAmmo() diff --git a/src/g_shared/a_pickups.h b/src/g_shared/a_pickups.h index 9dba52639..45676a214 100644 --- a/src/g_shared/a_pickups.h +++ b/src/g_shared/a_pickups.h @@ -139,6 +139,7 @@ public: PClassInventory(); virtual void DeriveData(PClass *newclass); virtual void ReplaceClassRef(PClass *oldclass, PClass *newclass); + void Finalize(FStateDefinitions &statedef); FString PickupMessage; int GiveQuest; // Optionally give one of the quest items. @@ -274,6 +275,7 @@ protected: public: PClassWeapon(); virtual void ReplaceClassRef(PClass *oldclass, PClass *newclass); + void Finalize(FStateDefinitions &statedef); int SlotNumber; int SlotPriority; diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index 36ffbc271..84305b9cd 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -67,6 +67,38 @@ void PClassWeapon::ReplaceClassRef(PClass *oldclass, PClass *newclass) } } +void PClassWeapon::Finalize(FStateDefinitions &statedef) +{ + Super::Finalize(statedef); + FState *ready = FindState(NAME_Ready); + FState *select = FindState(NAME_Select); + FState *deselect = FindState(NAME_Deselect); + FState *fire = FindState(NAME_Fire); + + // Consider any weapon without any valid state abstract and don't output a warning + // This is for creating base classes for weapon groups that only set up some properties. + if (ready || select || deselect || fire) + { + if (!ready) + { + I_Error("Weapon %s doesn't define a ready state.", TypeName.GetChars()); + } + if (!select) + { + I_Error("Weapon %s doesn't define a select state.", TypeName.GetChars()); + } + if (!deselect) + { + I_Error("Weapon %s doesn't define a deselect state.", TypeName.GetChars()); + } + if (!fire) + { + I_Error("Weapon %s doesn't define a fire state.", TypeName.GetChars()); + } + } +} + + //=========================================================================== // // AWeapon :: Serialize diff --git a/src/info.cpp b/src/info.cpp index 191ed2bd5..8089e065b 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -53,7 +53,9 @@ #include "g_level.h" #include "stats.h" #include "vm.h" +#include "thingdef.h" #include "d_player.h" +#include "doomerrors.h" extern void LoadActors (); extern void InitBotStuff(); @@ -380,6 +382,75 @@ void PClassActor::InitializeNativeDefaults() } } +//========================================================================== +// +// PClassActor :: SetReplacement +// +// Sets as a replacement class for another class. +// +//========================================================================== + +bool PClassActor::SetReplacement(FName replaceName) +{ + // Check for "replaces" + if (replaceName != NAME_None) + { + // Get actor name + PClassActor *replacee = PClass::FindActor(replaceName); + + if (replacee == nullptr) + { + return false; + } + if (replacee != nullptr) + { + replacee->Replacement = this; + Replacee = replacee; + } + } + return true; +} + +//========================================================================== +// +// PClassActor :: SetDropItems +// +// Sets a new drop item list +// +//========================================================================== + +void PClassActor::SetDropItems(DDropItem *drops) +{ + DropItems = drops; + GC::WriteBarrier(this, DropItems); +} + + +//========================================================================== +// +// PClassActor :: Finalize +// +// Installs the parsed states and does some sanity checking +// +//========================================================================== + +void PClassActor::Finalize(FStateDefinitions &statedef) +{ + AActor *defaults = (AActor*)Defaults; + + try + { + statedef.FinishStates(this, defaults); + } + catch (CRecoverableError &) + { + statedef.MakeStateDefines(NULL); + throw; + } + statedef.InstallStates(this, defaults); + statedef.MakeStateDefines(NULL); +} + //========================================================================== // // PClassActor :: RegisterIDs diff --git a/src/info.h b/src/info.h index 5ba7eafd9..0fe479d20 100644 --- a/src/info.h +++ b/src/info.h @@ -53,6 +53,7 @@ struct Baggage; class FScanner; struct FActorInfo; class FIntCVar; +class FStateDefinitions; enum EStateDefineFlags { @@ -234,6 +235,9 @@ public: void SetPainChance(FName type, int chance); size_t PropagateMark(); void InitializeNativeDefaults(); + bool SetReplacement(FName replaceName); + void SetDropItems(DDropItem *drops); + virtual void Finalize(FStateDefinitions &statedef); FState *FindState(int numnames, FName *names, bool exact=false) const; FState *FindStateByString(const char *name, bool exact=false); diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index 5fbe27a9d..186b269ce 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -57,6 +57,45 @@ #include "m_argv.h" void ParseOldDecoration(FScanner &sc, EDefinitionType def); +EXTERN_CVAR(Bool, strictdecorate); + + +//========================================================================== +// +// DecoDerivedClass +// +// Create a derived class and performs some additional sanity checks +// +//========================================================================== + +PClassActor *DecoDerivedClass(const FScriptPosition &sc, PClassActor *parent, FName typeName) +{ + PClassActor *type = static_cast(parent->CreateDerivedClass(typeName, parent->Size)); + if (type == nullptr) + { + FString newname = typeName.GetChars(); + FString sourcefile = sc.FileName; + + sourcefile.Substitute(":", "@"); + newname << '@' << sourcefile; + if (strictdecorate) + { + sc.Message(MSG_ERROR, "Tried to define class '%s' more than once.", typeName.GetChars()); + } + else + { + // Due to backwards compatibility issues this cannot be an unconditional error. + sc.Message(MSG_WARNING, "Tried to define class '%s' more than once. Renaming class to '%s'", typeName.GetChars(), newname.GetChars()); + } + type = static_cast(parent->CreateDerivedClass(newname, parent->Size)); + if (type == nullptr) + { + // This we cannot handle cleanly anymore. Let's just abort and forget about the odd mod out that was this careless. + sc.Message(MSG_FATAL, "Tried to define class '%s' more than twice in the same file.", typeName.GetChars()); + } + } + return type; +} //========================================================================== // @@ -1126,6 +1165,80 @@ static void ParseActionDef (FScanner &sc, PClassActor *cls) ParseFunctionDef(sc, cls, funcname, rets, VARF_Method | VARF_Action); } +//========================================================================== +// +// Starts a new actor definition +// +//========================================================================== +PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName parentName, bool native) +{ + PClassActor *replacee = NULL; + PClassActor *ti = NULL; + + PClassActor *parent = RUNTIME_CLASS(AActor); + + if (parentName != NAME_None) + { + parent = PClass::FindActor(parentName); + + PClassActor *p = parent; + while (p != NULL) + { + if (p->TypeName == typeName) + { + sc.Message(MSG_ERROR, "'%s' inherits from a class with the same name", typeName.GetChars()); + break; + } + p = dyn_cast(p->ParentClass); + } + + if (parent == NULL) + { + sc.Message(MSG_ERROR, "Parent type '%s' not found in %s", parentName.GetChars(), typeName.GetChars()); + parent = RUNTIME_CLASS(AActor); + } + else if (!parent->IsDescendantOf(RUNTIME_CLASS(AActor))) + { + sc.Message(MSG_ERROR, "Parent type '%s' is not an actor in %s", parentName.GetChars(), typeName.GetChars()); + parent = RUNTIME_CLASS(AActor); + } + } + + if (native) + { + ti = PClass::FindActor(typeName); + if (ti == NULL) + { + extern void DumpTypeTable(); + DumpTypeTable(); + sc.Message(MSG_ERROR, "Unknown native actor '%s'", typeName.GetChars()); + goto create; + } + else if (ti != RUNTIME_CLASS(AActor) && ti->ParentClass->NativeClass() != parent->NativeClass()) + { + sc.Message(MSG_ERROR, "Native class '%s' does not inherit from '%s'", typeName.GetChars(), parentName.GetChars()); + parent = RUNTIME_CLASS(AActor); + goto create; + } + else if (ti->Defaults != NULL) + { + sc.Message(MSG_ERROR, "Redefinition of internal class '%s'", typeName.GetChars()); + goto create; + } + ti->InitializeNativeDefaults(); + ti->ParentClass->DeriveData(ti); + } + else + { + create: + ti = DecoDerivedClass(sc, parent, typeName); + } + + ti->Replacee = ti->Replacement = NULL; + ti->DoomEdNum = -1; + return ti; +} + //========================================================================== // // Starts a new actor definition @@ -1216,7 +1329,10 @@ static PClassActor *ParseActorHeader(FScanner &sc, Baggage *bag) info->DoomEdNum = DoomEdNum > 0 ? DoomEdNum : -1; info->SourceLumpName = Wads.GetLumpFullPath(sc.LumpNum); - SetReplacement(sc, info, replaceName); + if (!info->SetReplacement(replaceName)) + { + sc.ScriptMessage("Replaced type '%s' not found for %s", replaceName.GetChars(), info->TypeName.GetChars()); + } ResetBaggage (bag, info == RUNTIME_CLASS(AActor) ? NULL : static_cast(info->ParentClass)); bag->Info = info; @@ -1293,7 +1409,18 @@ static void ParseActor(FScanner &sc) break; } } - FinishActor(sc, info, bag); + if (bag.DropItemSet) + { + bag.Info->SetDropItems(bag.DropItemList); + } + try + { + info->Finalize(bag.statedef); + } + catch (CRecoverableError &err) + { + sc.ScriptError("%s", err.GetMessage()); + } sc.SetCMode (false); } diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 175aa8990..5227009e7 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -76,202 +76,6 @@ void ParseDecorate(FScanner &ctx); // STATIC FUNCTION PROTOTYPES -------------------------------------------- PClassActor *QuestItemClasses[31]; -EXTERN_CVAR(Bool, strictdecorate); - -PClassActor *DecoDerivedClass(const FScriptPosition &sc, PClassActor *parent, FName typeName) -{ - PClassActor *type = static_cast(parent->CreateDerivedClass(typeName, parent->Size)); - if (type == nullptr) - { - FString newname = typeName.GetChars(); - FString sourcefile = sc.FileName; - - sourcefile.Substitute(":", "@"); - newname << '@' << sourcefile; - if (strictdecorate) - { - sc.Message(MSG_ERROR, "Tried to define class '%s' more than once.", typeName.GetChars()); - } - else - { - // Due to backwards compatibility issues this cannot be an unconditional error. - sc.Message(MSG_WARNING, "Tried to define class '%s' more than once. Renaming class to '%s'", typeName.GetChars(), newname.GetChars()); - } - type = static_cast(parent->CreateDerivedClass(newname, parent->Size)); - if (type == nullptr) - { - // This we cannot handle cleanly anymore. Let's just abort and forget about the odd mod out that was this careless. - sc.Message(MSG_FATAL, "Tried to define class '%s' more than twice in the same file.", typeName.GetChars()); - } - } - return type; -} -//========================================================================== -// -// Starts a new actor definition -// -//========================================================================== -PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName parentName, bool native) -{ - PClassActor *replacee = NULL; - PClassActor *ti = NULL; - - PClassActor *parent = RUNTIME_CLASS(AActor); - - if (parentName != NAME_None) - { - parent = PClass::FindActor(parentName); - - PClassActor *p = parent; - while (p != NULL) - { - if (p->TypeName == typeName) - { - sc.Message(MSG_ERROR, "'%s' inherits from a class with the same name", typeName.GetChars()); - break; - } - p = dyn_cast(p->ParentClass); - } - - if (parent == NULL) - { - sc.Message(MSG_ERROR, "Parent type '%s' not found in %s", parentName.GetChars(), typeName.GetChars()); - parent = RUNTIME_CLASS(AActor); - } - else if (!parent->IsDescendantOf(RUNTIME_CLASS(AActor))) - { - sc.Message(MSG_ERROR, "Parent type '%s' is not an actor in %s", parentName.GetChars(), typeName.GetChars()); - parent = RUNTIME_CLASS(AActor); - } - } - - if (native) - { - ti = PClass::FindActor(typeName); - if (ti == NULL) - { - extern void DumpTypeTable(); - DumpTypeTable(); - sc.Message(MSG_ERROR, "Unknown native actor '%s'", typeName.GetChars()); - goto create; - } - else if (ti != RUNTIME_CLASS(AActor) && ti->ParentClass->NativeClass() != parent->NativeClass()) - { - sc.Message(MSG_ERROR, "Native class '%s' does not inherit from '%s'", typeName.GetChars(), parentName.GetChars()); - parent = RUNTIME_CLASS(AActor); - goto create; - } - else if (ti->Defaults != NULL) - { - sc.Message(MSG_ERROR, "Redefinition of internal class '%s'", typeName.GetChars()); - goto create; - } - ti->InitializeNativeDefaults(); - ti->ParentClass->DeriveData(ti); - } - else - { - create: - ti = DecoDerivedClass(sc, parent, typeName); - } - - ti->Replacee = ti->Replacement = NULL; - ti->DoomEdNum = -1; - return ti; -} - -//========================================================================== -// -// -// -//========================================================================== - -void SetReplacement(FScanner &sc, PClassActor *info, FName replaceName) -{ - // Check for "replaces" - if (replaceName != NAME_None) - { - // Get actor name - PClassActor *replacee = PClass::FindActor(replaceName); - - if (replacee == NULL) - { - sc.ScriptMessage("Replaced type '%s' not found for %s", replaceName.GetChars(), info->TypeName.GetChars()); - return; - } - if (replacee != NULL) - { - replacee->Replacement = info; - info->Replacee = replacee; - } - } - -} - -//========================================================================== -// -// Finalizes an actor definition -// -//========================================================================== - -void FinishActor(const FScriptPosition &sc, PClassActor *info, Baggage &bag) -{ - AActor *defaults = (AActor*)info->Defaults; - - try - { - bag.statedef.FinishStates (info, defaults); - } - catch (CRecoverableError &err) - { - sc.Message(MSG_ERROR, "%s", err.GetMessage()); - bag.statedef.MakeStateDefines(NULL); - return; - } - bag.statedef.InstallStates (info, defaults); - bag.statedef.MakeStateDefines(NULL); - if (bag.DropItemSet) - { - info->DropItems = bag.DropItemList; - GC::WriteBarrier(info, info->DropItems); - } - if (info->IsDescendantOf (RUNTIME_CLASS(AInventory))) - { - defaults->flags |= MF_SPECIAL; - } - - // Weapons must be checked for all relevant states. They may crash the game otherwise. - if (info->IsDescendantOf(RUNTIME_CLASS(AWeapon))) - { - FState *ready = info->FindState(NAME_Ready); - FState *select = info->FindState(NAME_Select); - FState *deselect = info->FindState(NAME_Deselect); - FState *fire = info->FindState(NAME_Fire); - - // Consider any weapon without any valid state abstract and don't output a warning - // This is for creating base classes for weapon groups that only set up some properties. - if (ready || select || deselect || fire) - { - if (!ready) - { - sc.Message(MSG_ERROR, "Weapon %s doesn't define a ready state.\n", info->TypeName.GetChars()); - } - if (!select) - { - sc.Message(MSG_ERROR, "Weapon %s doesn't define a select state.\n", info->TypeName.GetChars()); - } - if (!deselect) - { - sc.Message(MSG_ERROR, "Weapon %s doesn't define a deselect state.\n", info->TypeName.GetChars()); - } - if (!fire) - { - sc.Message(MSG_ERROR, "Weapon %s doesn't define a fire state.\n", info->TypeName.GetChars()); - } - } - } -} - //========================================================================== // // Do some postprocessing after everything has been defined @@ -426,14 +230,6 @@ static void FinishThingdef() ActorDamageFuncs.DeleteAndClear(); StateTempCalls.DeleteAndClear(); - - // Since these are defined in DECORATE now the table has to be initialized here. - for(int i = 0; i < 31; i++) - { - char fmt[20]; - mysnprintf(fmt, countof(fmt), "QuestItem%d", i+1); - QuestItemClasses[i] = PClass::FindActor(fmt); - } } @@ -454,10 +250,11 @@ void LoadActors () timer.Reset(); timer.Clock(); ActorDamageFuncs.Clear(); - FScriptPosition::ResetErrorCounter(); InitThingdef(); lastlump = 0; ParseScripts(); + + FScriptPosition::ResetErrorCounter(); while ((lump = Wads.FindLump ("DECORATE", &lastlump)) != -1) { FScanner sc(lump); @@ -471,4 +268,12 @@ void LoadActors () timer.Unclock(); if (!batchrun) Printf("DECORATE parsing took %.2f ms\n", timer.TimeMS()); // Base time: ~52 ms + + // Since these are defined in DECORATE now the table has to be initialized here. + for (int i = 0; i < 31; i++) + { + char fmt[20]; + mysnprintf(fmt, countof(fmt), "QuestItem%d", i + 1); + QuestItemClasses[i] = PClass::FindActor(fmt); + } } diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 84f1f7d06..714657d24 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -178,10 +178,8 @@ void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls //========================================================================== PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName parentName, bool native); -void SetReplacement(FScanner &sc, PClassActor *info, FName replaceName); void HandleActorFlag(FScanner &sc, Baggage &bag, const char *part1, const char *part2, int mod); -void FinishActor(const FScriptPosition &sc, PClassActor *info, Baggage &bag); FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool constant); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 0d9558a52..e8ea8a6e7 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -69,6 +69,10 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) name << "nodes - " << FName(cnode->NodeName); cls->TreeNodes.SetName(name); + if (!static_cast(cnode->Type)->SetReplacement(cnode->Replaces->Id)) + { + Warn(cnode, "Replaced type '%s' not found for %s", FName(cnode->Replaces->Id).GetChars(), cnode->Type->TypeName.GetChars()); + } // Need to check if the class actually has a body. if (node != nullptr) do @@ -1836,6 +1840,10 @@ void ZCCCompiler::InitDefaults() content = static_cast(content->SiblingNext); } while (content != d->Content); } + if (bag.DropItemSet) + { + bag.Info->SetDropItems(bag.DropItemList); + } } } } @@ -2239,5 +2247,13 @@ void ZCCCompiler::CompileStates() st = static_cast(st->SiblingNext); } while (st != s->Body); } + try + { + static_cast(c->Type())->Finalize(statedef); + } + catch (CRecoverableError &err) + { + Error(c->cls, "%s", err.GetMessage()); + } } } diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 34c1271e0..a15ec893a 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -371,25 +371,30 @@ class Actor : Thinker native native int ACS_NamedExecuteWithResult(name script, int arg1=0, int arg2=0, int arg3=0, int arg4=0); native void ACS_NamedExecuteAlways(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); -/* States { Spawn: - TNT1 A -1 - Stop + TNT1 A -1; + Stop; Null: - TNT1 A 1 - Stop + TNT1 A 1; + Stop; GenericFreezeDeath: // Generic freeze death frames. Woo! - "####" "#" 5 A_GenericFreezeDeath - "----" A 1 A_FreezeDeathChunks - Wait + #### # 5 A_GenericFreezeDeath; + ---- A 1 A_FreezeDeathChunks; + Wait; GenericCrush: - POL5 A -1 - Stop + POL5 A -1; + Stop; + Test.State: + &&&& A[\] 5 offset(4,4*2); + &&&& A[\] DEFAULT_HEALTH; + abcd efgh random(3, 6); + lght blahblah 5*3 light("furz", "bläh", "rülps"); + lght blahblah 5 light("boing"); + goto Actor::Spawn+1; } -*/ // Internal functions deprecated private native state __decorate_internal_state__(state s); From a72fbb771f1287f08530ca43a103a61656e76bba Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 13 Oct 2016 00:53:59 +0200 Subject: [PATCH 024/255] - separated the code generation from the DECORATE parser and cleaned up the interface to the code generator. Most importantly, the VMScriptFunctions are now preallocated when being added to the list of functions to compile and will be filled in later by the code generator. This allowed the removal of some ugly maintenance code. --- src/CMakeLists.txt | 4 + src/d_dehacked.cpp | 3 +- src/scripting/codegeneration/thingdef_exp.h | 11 +- .../codegeneration/thingdef_expression.cpp | 18 +- src/scripting/decorate/thingdef_parse.cpp | 47 +--- src/scripting/decorate/thingdef_states.cpp | 36 +-- src/scripting/thingdef.cpp | 225 +++++------------- src/scripting/thingdef.h | 19 -- src/scripting/thingdef_properties.cpp | 3 +- src/scripting/vm/vm.h | 1 + src/scripting/vm/vmbuilder.cpp | 120 +++++++++- src/scripting/vm/vmbuilder.h | 32 ++- src/scripting/vm/vmdisasm.cpp | 19 ++ src/scripting/zscript/zcc_compile.cpp | 8 +- src/zstring.cpp | 8 + src/zstring.h | 7 + 16 files changed, 287 insertions(+), 274 deletions(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index bd01cad42..b612684d5 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -815,11 +815,15 @@ file( GLOB HEADER_FILES posix/cocoa/*.h posix/sdl/*.h r_data/*.h + rapidjson/*.h resourcefiles/*.h sfmt/*.h sound/*.h textures/*.h scripting/*.h + scripting/codegeneration/*.h + scripting/decorate/*.h + scripting/zscript/*.h scripting/vm/*.h xlat/*.h *.h diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index d5150e985..8e69ecb06 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -820,7 +820,8 @@ void SetDehParams(FState *state, int codepointer) int argcount = MBFCodePointerFactories[codepointer](buildit, value1, value2); buildit.Emit(OP_TAIL_K, buildit.GetConstantAddress(sym->Variants[0].Implementation, ATAG_OBJECT), NAP + argcount, 0); // Attach it to the state. - VMScriptFunction *sfunc = buildit.MakeFunction(); + VMScriptFunction *sfunc = new VMScriptFunction; + buildit.MakeFunction(sfunc); sfunc->NumArgs = NAP; state->SetAction(sfunc); } diff --git a/src/scripting/codegeneration/thingdef_exp.h b/src/scripting/codegeneration/thingdef_exp.h index 65c3ace63..2e9af65b6 100644 --- a/src/scripting/codegeneration/thingdef_exp.h +++ b/src/scripting/codegeneration/thingdef_exp.h @@ -41,6 +41,9 @@ */ #include "m_random.h" +#include "sc_man.h" +#include "s_sound.h" +#include "actor.h" #define CHECKRESOLVED() if (isresolved) return this; isresolved=true; @@ -58,14 +61,15 @@ class FxJumpStatement; // // //========================================================================== +struct FScriptPosition; struct FCompileContext { TArray Jumps; PPrototype *ReturnProto; - PClassActor *Class; + PClass *Class; - FCompileContext(PClassActor *cls = nullptr, PPrototype *ret = nullptr); + FCompileContext(PClass *cls = nullptr, PPrototype *ret = nullptr); PSymbol *FindInClass(FName identifier); PSymbol *FindGlobal(FName identifier); @@ -1175,7 +1179,6 @@ public: class FxDamageValue : public FxExpression { FxExpression *val; - VMScriptFunction *MyFunction; public: @@ -1184,8 +1187,6 @@ public: FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); - VMScriptFunction *GetFunction() const { return MyFunction; } - void SetFunction(VMScriptFunction *func) { MyFunction = func; } }; //========================================================================== diff --git a/src/scripting/codegeneration/thingdef_expression.cpp b/src/scripting/codegeneration/thingdef_expression.cpp index ae2639b73..31acc391e 100644 --- a/src/scripting/codegeneration/thingdef_expression.cpp +++ b/src/scripting/codegeneration/thingdef_expression.cpp @@ -91,7 +91,7 @@ static const FLOP FxFlops[] = // //========================================================================== -FCompileContext::FCompileContext(PClassActor *cls, PPrototype *ret) : Class(cls), ReturnProto(ret) +FCompileContext::FCompileContext(PClass *cls, PPrototype *ret) : Class(cls), ReturnProto(ret) { } @@ -3902,7 +3902,7 @@ VMFunction *FxVMFunctionCall::GetDirectFunction() // then it can be a "direct" function. That is, the DECORATE // definition can call that function directly without wrapping // it inside VM code. - if (EmitTail && (ArgList ? ArgList->Size() : 0) == 0 && (Function->Flags & VARF_Action)) + if ((ArgList ? ArgList->Size() : 0) == 0 && (Function->Flags & VARF_Action)) { return Function->Variants[0].Implementation; } @@ -4922,20 +4922,19 @@ FxExpression *FxStateByIndex::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); ABORT(ctx.Class); + auto aclass = dyn_cast(ctx.Class); - if (ctx.Class->NumOwnedStates == 0) - { - // This can't really happen - assert(false); - } - if (ctx.Class->NumOwnedStates <= index) + // This expression type can only be used from DECORATE, so there's no need to consider the possibility of calling it from a non-actor. + assert(aclass != nullptr && aclass->NumOwnedStates > 0); + + if (aclass->NumOwnedStates <= index) { ScriptPosition.Message(MSG_ERROR, "%s: Attempt to jump to non existing state index %d", ctx.Class->TypeName.GetChars(), index); delete this; return NULL; } - FxExpression *x = new FxConstant(ctx.Class->OwnedStates + index, ScriptPosition); + FxExpression *x = new FxConstant(aclass->OwnedStates + index, ScriptPosition); delete this; return x; } @@ -5245,7 +5244,6 @@ FxDamageValue::FxDamageValue(FxExpression *v) { val = v; ValueType = TypeVoid; - MyFunction = NULL; } FxDamageValue::~FxDamageValue() diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index 186b269ce..a863c4a4e 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -441,42 +441,6 @@ static void ParseArgListDef(FScanner &sc, PClassActor *cls, sc.MustGetToken(';'); } -//========================================================================== -// -// SetImplicitArgs -// -// Adds the parameters implied by the function flags. -// -//========================================================================== - -void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls, DWORD funcflags) -{ - // Must be called before adding any other arguments. - assert(args == NULL || args->Size() == 0); - assert(argflags == NULL || argflags->Size() == 0); - - if (funcflags & VARF_Method) - { - // implied self pointer - if (args != NULL) args->Push(NewClassPointer(RUNTIME_CLASS(AActor))); - if (argflags != NULL) argflags->Push(VARF_Implicit); - } - if (funcflags & VARF_Action) - { - // implied stateowner and callingstate pointers - if (args != NULL) - { - args->Push(NewClassPointer(cls)); - args->Push(TypeState); - } - if (argflags != NULL) - { - argflags->Push(VARF_Implicit); - argflags->Push(VARF_Implicit); - } - } -} - //========================================================================== // // ParseFunctionDef @@ -1559,3 +1523,14 @@ void ParseDecorate (FScanner &sc) } } } + +void ParseAllDecorate() +{ + int lastlump, lump; + + while ((lump = Wads.FindLump("DECORATE", &lastlump)) != -1) + { + FScanner sc(lump); + ParseDecorate(sc); + } +} \ No newline at end of file diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 59d620b2a..143144aa5 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -57,8 +57,7 @@ #include "codegeneration/thingdef_exp.h" #include "version.h" #include "templates.h" - -TDeletingArray StateTempCalls; +#include "vmbuilder.h" //========================================================================== //*** @@ -141,13 +140,14 @@ void ParseStates(FScanner &sc, PClassActor * actor, AActor * defaults, Baggage & FString statestring; FState state; char lastsprite[5] = ""; - FStateTempCall *tcall = NULL; - FArgumentList *args = NULL; + FxExpression *ScriptCode; + FArgumentList *args = nullptr; sc.MustGetStringName ("{"); sc.SetEscape(false); // disable escape sequences in the state parser while (!sc.CheckString ("}") && !sc.End) { + ScriptCode = nullptr; memset(&state,0,sizeof(state)); statestring = ParseStateString(sc); if (!statestring.CompareNoCase("GOTO")) @@ -224,10 +224,6 @@ do_stop: sc.MustGetString(); statestring = sc.String; - if (tcall == NULL) - { - tcall = new FStateTempCall; - } if (sc.CheckString("RANDOM")) { int min, max; @@ -315,35 +311,27 @@ do_stop: } bool hasfinalret; - tcall->Code = ParseActions(sc, state, statestring, bag, hasfinalret); - if (!hasfinalret && tcall->Code != nullptr) + ScriptCode = ParseActions(sc, state, statestring, bag, hasfinalret); + if (!hasfinalret && ScriptCode != nullptr) { - static_cast(tcall->Code)->Add(new FxReturnStatement(nullptr, sc)); + static_cast(ScriptCode)->Add(new FxReturnStatement(nullptr, sc)); } goto endofstate; } sc.UnGet(); endofstate: + if (ScriptCode != nullptr) + { + state.ActionFunc = FunctionBuildList.AddFunction(actor, ScriptCode, FStringf("%s.StateFunction.%d", actor->TypeName.GetChars(), bag.statedef.GetStateCount()), true); + } int count = bag.statedef.AddStates(&state, statestring); if (count < 0) { - sc.ScriptError ("Invalid frame character string '%s'", statestring.GetChars()); + sc.ScriptError("Invalid frame character string '%s'", statestring.GetChars()); count = -count; } - if (tcall->Code != NULL) - { - tcall->ActorClass = actor; - tcall->FirstState = bag.statedef.GetStateCount() - count; - tcall->NumStates = count; - StateTempCalls.Push(tcall); - tcall = NULL; - } } } - if (tcall != NULL) - { - delete tcall; - } if (args != NULL) { delete args; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 5227009e7..1a761b8c2 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -66,174 +66,48 @@ #include "vmbuilder.h" #include "stats.h" -TDeletingArray ActorDamageFuncs; - - // EXTERNAL FUNCTION PROTOTYPES -------------------------------------------- void InitThingdef(); -void ParseDecorate(FScanner &ctx); // STATIC FUNCTION PROTOTYPES -------------------------------------------- PClassActor *QuestItemClasses[31]; //========================================================================== // -// Do some postprocessing after everything has been defined +// SetImplicitArgs +// +// Adds the parameters implied by the function flags. // //========================================================================== -static void DumpFunction(FILE *dump, VMScriptFunction *sfunc, const char *label, int labellen) +void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls, DWORD funcflags) { - const char *marks = "======================================================="; - fprintf(dump, "\n%.*s %s %.*s", MAX(3, 38 - labellen / 2), marks, label, MAX(3, 38 - labellen / 2), marks); - fprintf(dump, "\nInteger regs: %-3d Float regs: %-3d Address regs: %-3d String regs: %-3d\nStack size: %d\n", - sfunc->NumRegD, sfunc->NumRegF, sfunc->NumRegA, sfunc->NumRegS, sfunc->MaxParam); - VMDumpConstants(dump, sfunc); - fprintf(dump, "\nDisassembly @ %p:\n", sfunc->Code); - VMDisasm(dump, sfunc->Code, sfunc->CodeSize, sfunc); + // Must be called before adding any other arguments. + assert(args == NULL || args->Size() == 0); + assert(argflags == NULL || argflags->Size() == 0); + + if (funcflags & VARF_Method) + { + // implied self pointer + if (args != NULL) args->Push(NewClassPointer(cls)); + if (argflags != NULL) argflags->Push(VARF_Implicit); + } + if (funcflags & VARF_Action) + { + // implied caller and callingstate pointers + if (args != NULL) + { + args->Insert(0, NewClassPointer(RUNTIME_CLASS(AActor))); // the caller must go before self due to an old design mistake. + args->Push(TypeState); + } + if (argflags != NULL) + { + argflags->Push(VARF_Implicit); + argflags->Push(VARF_Implicit); + } + } } -static void FinishThingdef() -{ - int errorcount = 0; - unsigned i; - int codesize = 0; - FILE *dump = NULL; - - if (Args->CheckParm("-dumpdisasm")) dump = fopen("disasm.txt", "w"); - - for (i = 0; i < StateTempCalls.Size(); ++i) - { - FStateTempCall *tcall = StateTempCalls[i]; - VMFunction *func = nullptr; - - assert(tcall->Code != NULL); - - // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(tcall->ActorClass, nullptr); - tcall->Code = tcall->Code->Resolve(ctx); - tcall->Proto = ctx.ReturnProto; - - // Make sure resolving it didn't obliterate it. - if (tcall->Code != nullptr) - { - // Can we call this function directly without wrapping it in an - // anonymous function? e.g. Are we passing any parameters to it? - func = tcall->Code->GetDirectFunction(); - - if (func == nullptr) - { - VMFunctionBuilder buildit(true); - - assert(tcall->Proto != nullptr); - - // Allocate registers used to pass parameters in. - // self, stateowner, state (all are pointers) - buildit.Registers[REGT_POINTER].Get(3); - - // Emit code - tcall->Code->Emit(&buildit); - - VMScriptFunction *sfunc = buildit.MakeFunction(); - sfunc->NumArgs = NAP; - - // Generate prototype for this anonymous function - TArray args(3); - SetImplicitArgs(&args, NULL, tcall->ActorClass, VARF_Method | VARF_Action); - sfunc->Proto = NewPrototype(tcall->Proto->ReturnTypes, args); - - func = sfunc; - - if (dump != NULL) - { - char label[64]; - int labellen = mysnprintf(label, countof(label), "Function %s.States[%d] (*%d)", - tcall->ActorClass->TypeName.GetChars(), tcall->FirstState, tcall->NumStates); - DumpFunction(dump, sfunc, label, labellen); - codesize += sfunc->CodeSize; - } - } - - delete tcall->Code; - tcall->Code = nullptr; - for (int k = 0; k < tcall->NumStates; ++k) - { - tcall->ActorClass->OwnedStates[tcall->FirstState + k].SetAction(func); - } - } - } - - for (i = 0; i < PClassActor::AllActorClasses.Size(); i++) - { - PClassActor *ti = PClassActor::AllActorClasses[i]; - - if (ti->Size == TentativeClass) - { - Printf(TEXTCOLOR_RED "Class %s referenced but not defined\n", ti->TypeName.GetChars()); - errorcount++; - continue; - } - - AActor *def = GetDefaultByType(ti); - - if (!def) - { - Printf(TEXTCOLOR_RED "No ActorInfo defined for class '%s'\n", ti->TypeName.GetChars()); - errorcount++; - continue; - } - - if (def->DamageFunc != nullptr) - { - FxDamageValue *dmg = (FxDamageValue *)ActorDamageFuncs[(uintptr_t)def->DamageFunc - 1]; - VMScriptFunction *sfunc; - sfunc = dmg->GetFunction(); - if (sfunc == nullptr) - { - FCompileContext ctx(ti); - dmg = static_cast(dmg->Resolve(ctx)); - - if (dmg != nullptr) - { - VMFunctionBuilder buildit; - buildit.Registers[REGT_POINTER].Get(1); // The self pointer - dmg->Emit(&buildit); - sfunc = buildit.MakeFunction(); - sfunc->NumArgs = 1; - sfunc->Proto = nullptr; ///FIXME: Need a proper prototype here - // Save this function in case this damage value was reused - // (which happens quite easily with inheritance). - dmg->SetFunction(sfunc); - } - } - def->DamageFunc = sfunc; - - if (dump != nullptr && sfunc != nullptr) - { - char label[64]; - int labellen = mysnprintf(label, countof(label), "Function %s.Damage", - ti->TypeName.GetChars()); - DumpFunction(dump, sfunc, label, labellen); - codesize += sfunc->CodeSize; - } - } - } - if (dump != NULL) - { - fprintf(dump, "\n*************************************************************************\n%i code bytes\n", codesize * 4); - fclose(dump); - } - if (errorcount > 0) - { - I_Error("%d errors during actor postprocessing", errorcount); - } - - ActorDamageFuncs.DeleteAndClear(); - StateTempCalls.DeleteAndClear(); -} - - - //========================================================================== // // LoadActors @@ -242,29 +116,48 @@ static void FinishThingdef() // //========================================================================== void ParseScripts(); +void ParseAllDecorate(); void LoadActors () { - int lastlump, lump; cycle_t timer; timer.Reset(); timer.Clock(); - ActorDamageFuncs.Clear(); - InitThingdef(); - lastlump = 0; - ParseScripts(); - FScriptPosition::ResetErrorCounter(); - while ((lump = Wads.FindLump ("DECORATE", &lastlump)) != -1) - { - FScanner sc(lump); - ParseDecorate (sc); - } - FinishThingdef(); + + InitThingdef(); + ParseScripts(); + ParseAllDecorate(); + + FunctionBuildList.Build(); + if (FScriptPosition::ErrorCounter > 0) { I_Error("%d errors while parsing DECORATE scripts", FScriptPosition::ErrorCounter); } + + int errorcount = 0; + for (auto ti : PClassActor::AllActorClasses) + { + if (ti->Size == TentativeClass) + { + Printf(TEXTCOLOR_RED "Class %s referenced but not defined\n", ti->TypeName.GetChars()); + errorcount++; + continue; + } + + if (GetDefaultByType(ti) == nullptr) + { + Printf(TEXTCOLOR_RED "No ActorInfo defined for class '%s'\n", ti->TypeName.GetChars()); + errorcount++; + continue; + } + } + if (errorcount > 0) + { + I_Error("%d errors during actor postprocessing", errorcount); + } + timer.Unclock(); if (!batchrun) Printf("DECORATE parsing took %.2f ms\n", timer.TimeMS()); // Base time: ~52 ms diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 714657d24..4a984dd5c 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -101,25 +101,6 @@ public: int GetStateCount() const { return StateArray.Size(); } }; -//========================================================================== -// -// -// -//========================================================================== - -struct FStateTempCall -{ - FStateTempCall() : ActorClass(NULL), Code(NULL), FirstState(0), NumStates(0) {} - - PClassActor *ActorClass; - class FxExpression *Code; - class PPrototype *Proto; - int FirstState; - int NumStates; -}; -extern TDeletingArray StateTempCalls; -extern TDeletingArray ActorDamageFuncs; - //========================================================================== // // Extra info maintained while defining an actor. diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index 3c171be7f..084736c24 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -69,6 +69,7 @@ #include "teaminfo.h" #include "v_video.h" #include "r_data/colormaps.h" +#include "vmbuilder.h" //========================================================================== @@ -656,7 +657,7 @@ DEFINE_PROPERTY(damage, X, Actor) } else { - defaults->DamageFunc = (VMFunction *)(uintptr_t)(ActorDamageFuncs.Push(id) + 1); + defaults->DamageFunc = FunctionBuildList.AddFunction(bag.Info, id, FStringf("%s.DamageFunction", bag.Info->TypeName.GetChars()), false); } } diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 28b555e4e..69e5b81b3 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -1020,4 +1020,5 @@ class PFunction; PFunction *FindGlobalActionFunction(const char *name); + #endif diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index fd9a0063e..4a880cef6 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -32,6 +32,10 @@ */ #include "vmbuilder.h" +#include "codegeneration/thingdef_exp.h" +#include "info.h" +#include "m_argv.h" +#include "thingdef.h" //========================================================================== // @@ -68,10 +72,8 @@ VMFunctionBuilder::~VMFunctionBuilder() // //========================================================================== -VMScriptFunction *VMFunctionBuilder::MakeFunction() +void VMFunctionBuilder::MakeFunction(VMScriptFunction *func) { - VMScriptFunction *func = new VMScriptFunction; - func->Alloc(Code.Size(), NumIntConstants, NumFloatConstants, NumStringConstants, NumAddressConstants); // Copy code block. @@ -106,8 +108,6 @@ VMScriptFunction *VMFunctionBuilder::MakeFunction() // entries on the parameter stack, but it means the caller probably // did something wrong. assert(ActiveParam == 0); - - return func; } //========================================================================== @@ -634,3 +634,113 @@ void VMFunctionBuilder::BackpatchToHere(size_t loc) { Backpatch(loc, Code.Size()); } + +//========================================================================== +// +// FFunctionBuildList +// +// This list contains all functions yet to build. +// All adding functions return a VMFunction - either a complete one +// for native functions or an empty VMScriptFunction for scripted ones +// This VMScriptFunction object later gets filled in with the actual +// info, but we get the pointer right after registering the function +// with the builder. +// +//========================================================================== +FFunctionBuildList FunctionBuildList; + +VMFunction *FFunctionBuildList::AddFunction(PClass *cls, FxExpression *code, const FString &name, bool statecall) +{ + auto func = code->GetDirectFunction(); + if (func != nullptr) + { + delete code; + return func; + } + + Printf("Adding %s\n", name.GetChars()); + + Item it; + it.Class = cls; + it.Code = code; + it.DumpName = name; + it.Function = new VMScriptFunction; + it.Proto = nullptr; + it.type = statecall; + mItems.Push(it); + return it.Function; +} + + +void FFunctionBuildList::Build() +{ + int errorcount = 0; + int codesize = 0; + FILE *dump = nullptr; + + if (Args->CheckParm("-dumpdisasm")) dump = fopen("disasm.txt", "w"); + + for (auto &item : mItems) + { + assert(item.Code != NULL); + + // We don't know the return type in advance for anonymous functions. + FCompileContext ctx(item.Class, nullptr); + item.Code = item.Code->Resolve(ctx); + item.Proto = ctx.ReturnProto; + + // Make sure resolving it didn't obliterate it. + if (item.Code != nullptr) + { + VMFunctionBuilder buildit(true); + + assert(item.Proto != nullptr); + + int numargs; + int flags; + + // Kludge alert. This needs to be done in a more universal fashion. + // Right now there's only action and damage functions, so for the time being + // this will do to get the whole thing started first. + + if (item.type == 1) // anonymous action function + { + numargs = NAP; + flags = VARF_Method | VARF_Action; + } + else + { + numargs = 1; + flags = VARF_Method; + } + + // Generate prototype for this anonymous function + buildit.Registers[REGT_POINTER].Get(numargs); + TArray args(numargs); + SetImplicitArgs(&args, nullptr, item.Class, flags); + + VMScriptFunction *sfunc = item.Function; + item.Function->Proto = NewPrototype(item.Proto->ReturnTypes, args); + + // Emit code + item.Code->Emit(&buildit); + buildit.MakeFunction(item.Function); + item.Function->NumArgs = numargs; + + if (dump != nullptr) + { + char label[64]; + int labellen = mysnprintf(label, countof(label), item.DumpName, + item.Class->TypeName.GetChars()); + DumpFunction(dump, sfunc, label, labellen); + codesize += sfunc->CodeSize; + } + } + delete item.Code; + } + if (dump != nullptr) + { + fprintf(dump, "\n*************************************************************************\n%i code bytes\n", codesize * 4); + fclose(dump); + } +} \ No newline at end of file diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index ed2516c2a..59e9fbe79 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -26,7 +26,7 @@ public: VMFunctionBuilder(bool checkself = false); ~VMFunctionBuilder(); - VMScriptFunction *MakeFunction(); + void MakeFunction(VMScriptFunction *func); // Returns the constant register holding the value. int GetConstantInt(int val); @@ -87,4 +87,34 @@ private: }; +void DumpFunction(FILE *dump, VMScriptFunction *sfunc, const char *label, int labellen); + + +//========================================================================== +// +// +// +//========================================================================== +class FxExpression; + +class FFunctionBuildList +{ + struct Item + { + PClass *Class = nullptr; + FxExpression *Code = nullptr; + PPrototype *Proto = nullptr; + VMScriptFunction *Function = nullptr; + FString DumpName; + int type; // temporary kludge + }; + + TArray mItems; + +public: + VMFunction *AddFunction(PClass *cls, FxExpression *code, const FString &name, bool statecall = false); + void Build(); +}; + +extern FFunctionBuildList FunctionBuildList; #endif diff --git a/src/scripting/vm/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp index 68b92f9f3..0b84cf8c0 100644 --- a/src/scripting/vm/vmdisasm.cpp +++ b/src/scripting/vm/vmdisasm.cpp @@ -33,6 +33,7 @@ #include "vm.h" #include "c_console.h" +#include "templates.h" #define NOP MODE_AUNUSED | MODE_BUNUSED | MODE_CUNUSED @@ -598,3 +599,21 @@ static int print_reg(FILE *out, int col, int arg, int mode, int immshift, const } return col; } + +//========================================================================== +// +// Do some postprocessing after everything has been defined +// +//========================================================================== + +void DumpFunction(FILE *dump, VMScriptFunction *sfunc, const char *label, int labellen) +{ + const char *marks = "======================================================="; + fprintf(dump, "\n%.*s %s %.*s", MAX(3, 38 - labellen / 2), marks, label, MAX(3, 38 - labellen / 2), marks); + fprintf(dump, "\nInteger regs: %-3d Float regs: %-3d Address regs: %-3d String regs: %-3d\nStack size: %d\n", + sfunc->NumRegD, sfunc->NumRegF, sfunc->NumRegA, sfunc->NumRegS, sfunc->MaxParam); + VMDumpConstants(dump, sfunc); + fprintf(dump, "\nDisassembly @ %p:\n", sfunc->Code); + VMDisasm(dump, sfunc->Code, sfunc->CodeSize, sfunc); +} + diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e8ea8a6e7..d175bd917 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -47,6 +47,7 @@ #include "p_lnspec.h" #include "gdtoa.h" #include "codegeneration/thingdef_exp.h" +#include "vmbuilder.h" #define DEFINING_CONST ((PSymbolConst *)(void *)1) @@ -2165,12 +2166,7 @@ void ZCCCompiler::CompileStates() auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); if (code != nullptr) { - auto tcall = new FStateTempCall; - tcall->Code = code; - tcall->ActorClass = static_cast(c->Type()); - tcall->FirstState = statedef.GetStateCount() - count; - tcall->NumStates = count; - StateTempCalls.Push(tcall); + state.ActionFunc = FunctionBuildList.AddFunction(c->Type(), code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), true); } } break; diff --git a/src/zstring.cpp b/src/zstring.cpp index f4a3a1fbb..3794a472a 100644 --- a/src/zstring.cpp +++ b/src/zstring.cpp @@ -1192,3 +1192,11 @@ FStringData *FStringData::MakeCopy () FString::StrCopy (copy->Chars(), Chars(), Len); return copy; } + +FStringf::FStringf(const char *fmt, ...) +{ + va_list ap; + va_start(ap, fmt); + VFormat(fmt, ap); + va_end(ap); +} diff --git a/src/zstring.h b/src/zstring.h index 00f373b59..519b354bf 100644 --- a/src/zstring.h +++ b/src/zstring.h @@ -308,6 +308,13 @@ private: bool operator >= (const FString &illegal) const; }; +class FStringf : public FString +{ +public: + FStringf(const char *fmt, ...); +}; + + namespace StringFormat { enum From 433bf46010f45b178c753c7dddb526ec8a55fc31 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 13 Oct 2016 20:45:52 +0200 Subject: [PATCH 025/255] - removed token 'mode' because it isn't used anywhere and clashed with some actor properties. - fixed uninitialized counter variable in DECORATE parser. - allow dottable_id of xxx.color so that the property parser can parse 'powerup.color'. - fixed crash with actor replacement in script compiler. - add the lump number to tree nodes because parts of the property parser need that to make decisions. - removed test stuff. - converted inventory.txt, player.txt and specialspot.txt to ZSCRIPT. These were the minimal files required to allow actor.txt to parse successfully. - removed the converted files from the DECORATE include list so that these are entirely handled by ZSCRIPT now. --- src/sc_man_scanner.re | 1 - src/sc_man_tokens.h | 1 - src/scripting/decorate/thingdef_parse.cpp | 2 +- src/scripting/vm/vmbuilder.cpp | 2 +- src/scripting/zscript/zcc-parse.lemon | 10 + src/scripting/zscript/zcc_compile.cpp | 12 +- src/scripting/zscript/zcc_parser.cpp | 2 + src/scripting/zscript/zcc_parser.h | 1 + wadsrc/static/actors/actor.txt | 393 --------------- wadsrc/static/actors/shared/inventory.txt | 376 -------------- wadsrc/static/actors/shared/player.txt | 52 -- wadsrc/static/actors/shared/specialspot.txt | 5 - wadsrc/static/decorate.txt | 8 +- wadsrc/static/zscript.txt | 9 + wadsrc/static/zscript/actor.txt | 7 - wadsrc/static/zscript/shared/inventory.txt | 501 +++++++++++++++++++ wadsrc/static/zscript/shared/player.txt | 58 +++ wadsrc/static/zscript/shared/specialspot.txt | 5 + 18 files changed, 601 insertions(+), 844 deletions(-) delete mode 100644 wadsrc/static/actors/actor.txt delete mode 100644 wadsrc/static/actors/shared/inventory.txt delete mode 100644 wadsrc/static/actors/shared/player.txt delete mode 100644 wadsrc/static/actors/shared/specialspot.txt create mode 100644 wadsrc/static/zscript.txt create mode 100644 wadsrc/static/zscript/shared/inventory.txt create mode 100644 wadsrc/static/zscript/shared/player.txt create mode 100644 wadsrc/static/zscript/shared/specialspot.txt diff --git a/src/sc_man_scanner.re b/src/sc_man_scanner.re index 92702f918..ba0e9a8e5 100644 --- a/src/sc_man_scanner.re +++ b/src/sc_man_scanner.re @@ -118,7 +118,6 @@ std2: 'void' { RET(TK_Void); } 'struct' { RET(TK_Struct); } 'class' { RET(TK_Class); } - 'mode' { RET(TK_Mode); } 'enum' { RET(TK_Enum); } 'name' { RET(TK_Name); } 'string' { RET(TK_String); } diff --git a/src/sc_man_tokens.h b/src/sc_man_tokens.h index 246462940..934558d54 100644 --- a/src/sc_man_tokens.h +++ b/src/sc_man_tokens.h @@ -62,7 +62,6 @@ xx(TK_ULong, "'ulong'") xx(TK_Void, "'void'") xx(TK_Struct, "'struct'") xx(TK_Class, "'class'") -xx(TK_Mode, "'mode'") xx(TK_Enum, "'enum'") xx(TK_Name, "'name'") xx(TK_String, "'string'") diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index a863c4a4e..f567d91e0 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -1526,7 +1526,7 @@ void ParseDecorate (FScanner &sc) void ParseAllDecorate() { - int lastlump, lump; + int lastlump = 0, lump; while ((lump = Wads.FindLump("DECORATE", &lastlump)) != -1) { diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 4a880cef6..f111c4529 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -658,7 +658,7 @@ VMFunction *FFunctionBuildList::AddFunction(PClass *cls, FxExpression *code, con return func; } - Printf("Adding %s\n", name.GetChars()); + //Printf("Adding %s\n", name.GetChars()); Item it; it.Class = cls; diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 7213b4dbc..51a221af7 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -211,6 +211,16 @@ dottable_id(X) ::= dottable_id(A) DOT IDENTIFIER(B). A->AppendSibling(id2); X = A; /*X-overwrites-A*/ } +// a bit of a hack to allow the 'color' token to be used inside default properties. +// as a variable name it is practically meaningless because it cannot defined +// as such anywhere so it will always produce an error during processing. +dottable_id(X) ::= dottable_id(A) DOT COLOR. +{ + NEW_AST_NODE(Identifier,id2,A); + id2->Id = NAME_Color; + A->AppendSibling(id2); + X = A; /*X-overwrites-A*/ +} /*------ Class Body ------*/ // Body is a list of: diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index d175bd917..6e8447690 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -70,7 +70,7 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) name << "nodes - " << FName(cnode->NodeName); cls->TreeNodes.SetName(name); - if (!static_cast(cnode->Type)->SetReplacement(cnode->Replaces->Id)) + if (cnode->Replaces != nullptr && !static_cast(cnode->Type)->SetReplacement(cnode->Replaces->Id)) { Warn(cnode, "Replaced type '%s' not found for %s", FName(cnode->Replaces->Id).GetChars(), cnode->Type->TypeName.GetChars()); } @@ -1565,7 +1565,9 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper if (exp->NodeType != AST_ExprConstant) { - Error(exp, "%s: non-constant parameter", prop->name); + // If we get TypeError, there has already been a message from deeper down so do not print another one. + if (exp->Type != TypeError) Error(exp, "%s: non-constant parameter", prop->name); + return; } conv.s = nullptr; pref.s = nullptr; @@ -1654,6 +1656,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper if (exp != property->Values) { Error(property, "Too many values for '%s'", prop->name); + return; } break; } @@ -1662,6 +1665,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper if (*p < 'a') { Error(property, "Insufficient parameters for %s", prop->name); + return; } break; } @@ -1816,7 +1820,7 @@ void ZCCCompiler::InitDefaults() bag.StateSet = false; bag.fromZScript = true; bag.CurrentState = 0; - bag.Lumpnum = Wads.CheckNumForFullName(*c->cls->SourceName, true); + bag.Lumpnum = c->cls->SourceLump; bag.DropItemList = nullptr; bag.ScriptPosition.StrictErrors = true; // The actual script position needs to be set per property. @@ -2061,6 +2065,8 @@ void ZCCCompiler::CompileStates() } FString statename; // The state builder wants the label as one complete string, not separated into tokens. FStateDefinitions statedef; + statedef.MakeStateDefines(dyn_cast(c->Type()->ParentClass)); + for (auto s : c->States) { auto st = s->Body; diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 0d69141f0..b803b4158 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -399,6 +399,7 @@ ZCC_TreeNode *ZCC_AST::InitNode(size_t size, EZCCTreeNodeType type, ZCC_TreeNode if (basis != NULL) { node->SourceName = basis->SourceName; + node->SourceLump = basis->SourceLump; node->SourceLoc = basis->SourceLoc; } return node; @@ -408,5 +409,6 @@ ZCC_TreeNode *ZCCParseState::InitNode(size_t size, EZCCTreeNodeType type) { ZCC_TreeNode *node = ZCC_AST::InitNode(size, type, NULL); node->SourceName = Strings.Alloc(sc->ScriptName); + node->SourceLump = sc->LumpNum; return node; } diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 2a73c8681..5dae72ee0 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -149,6 +149,7 @@ struct ZCC_TreeNode // can't use FScriptPosition, because the string wouldn't have a chance to // destruct if we did that. FString *SourceName; + int SourceLump; int SourceLoc; // Node type is one of the node types above, which corresponds with diff --git a/wadsrc/static/actors/actor.txt b/wadsrc/static/actors/actor.txt deleted file mode 100644 index eecc843d3..000000000 --- a/wadsrc/static/actors/actor.txt +++ /dev/null @@ -1,393 +0,0 @@ -ACTOR Actor native //: Thinker -{ - Scale 1 - Health 1000 - Reactiontime 8 - Radius 20 - Height 16 - Mass 100 - RenderStyle Normal - Alpha 1 - MinMissileChance 200 - MeleeRange 44 - MaxDropoffHeight 24 - MaxStepHeight 24 - BounceFactor 0.7 - WallBounceFactor 0.75 - BounceCount -1 - FloatSpeed 4 - FloatBobPhase -1 // randomly initialize by default - Gravity 1 - Friction 1 - DamageFactor 1.0 - PushFactor 0.25 - WeaveIndexXY 0 - WeaveIndexZ 16 - DesignatedTeam 255 - PainType Normal - DeathType Normal - TeleFogSourceType "TeleportFog" - TeleFogDestType "TeleportFog" - RipperLevel 0 - RipLevelMin 0 - RipLevelMax 0 - DefThreshold 100 - BloodType "Blood", "BloodSplatter", "AxeBlood" - ExplosionDamage 128 - MissileHeight 32 - SpriteAngle 0 - SpriteRotation 0 - StencilColor "00 00 00" - VisibleAngles 0, 0 - VisiblePitch 0, 0 - - // Functions - native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); - native bool IsPointerEqual(int ptr_select1, int ptr_select2); - native int CountInv(class itemtype, int ptr_select = AAPTR_DEFAULT); - native float GetDistance(bool checkz, int ptr = AAPTR_DEFAULT); - native float GetAngle(int flags, int ptr = AAPTR_DEFAULT); - native float GetZAt(float px = 0, float py = 0, float angle = 0, int flags = 0, int pick_pointer = AAPTR_DEFAULT); - native int GetSpawnHealth(); - native int GetGibHealth(); - native float GetCrouchFactor(int ptr = AAPTR_PLAYER1); - native float GetCVar(string cvar); - native int GetPlayerInput(int inputnum, int ptr = AAPTR_DEFAULT); - native int CountProximity(class classname, float distance, int flags = 0, int ptr = AAPTR_DEFAULT); - native float GetSpriteAngle(int ptr = AAPTR_DEFAULT); - native float GetSpriteRotation(int ptr = AAPTR_DEFAULT); - native int GetMissileDamage(int mask, int add, int ptr = AAPTR_DEFAULT); - action native int OverlayID(); - action native float OverlayX(int layer = 0); - action native float OverlayY(int layer = 0); - - // Action functions - // Meh, MBF redundant functions. Only for DeHackEd support. - action native A_Turn(float angle = 0); - action native bool A_LineEffect(int boomspecial = 0, int tag = 0); - // End of MBF redundant functions. - - action native A_MonsterRail(); - action native A_BFGSpray(class spraytype = "BFGExtra", int numrays = 40, int damagecount = 15, float/*angle*/ angle = 90, float distance = 16*64, float/*angle*/ vrange = 32, int damage = 0, int flags = 0); - action native A_Pain(); - action native A_NoBlocking(); - action native A_XScream(); - action native A_Look(); - action native A_Chase(state melee = "*", state missile = "none", int flags = 0); - action native A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - action native A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - action native A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - action native A_PosAttack(); - action native A_Scream(); - action native A_SPosAttack(); - action native A_SPosAttackUseAtkSound(); - action native A_VileChase(); - action native A_VileStart(); - action native A_VileTarget(class fire = "ArchvileFire"); - action native A_VileAttack(sound snd = "vile/stop", int initialdmg = 20, int blastdmg = 70, int blastradius = 70, float thrustfac = 1.0, name damagetype = "Fire", int flags = 0); - action native A_StartFire(); - action native A_Fire(float spawnheight = 0); - action native A_FireCrackle(); - action native A_Tracer(); - action native A_SkelWhoosh(); - action native A_SkelFist(); - action native A_SkelMissile(); - action native A_FatRaise(); - action native A_FatAttack1(class spawntype = "FatShot"); - action native A_FatAttack2(class spawntype = "FatShot"); - action native A_FatAttack3(class spawntype = "FatShot"); - action native A_BossDeath(); - action native A_CPosAttack(); - action native A_CPosRefire(); - action native A_TroopAttack(); - action native A_SargAttack(); - action native A_HeadAttack(); - action native A_BruisAttack(); - action native A_SkullAttack(float speed = 20); - action native A_BetaSkullAttack(); - action native A_Metal(); - action native A_SpidRefire(); - action native A_BabyMetal(); - action native A_BspiAttack(); - action native A_Hoof(); - action native A_CyberAttack(); - action native A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); - action native A_DualPainAttack(class spawntype = "LostSoul"); - action native A_PainDie(class spawntype = "LostSoul"); - action native A_KeenDie(int doortag = 666); - action native A_BrainPain(); - action native A_BrainScream(); - action native A_BrainDie(); - action native A_BrainAwake(); - action native A_BrainSpit(class spawntype = "none"); // needs special treatment for default - action native A_SpawnSound(); - action native A_SpawnFly(class spawntype = "none"); // needs special treatment for default - action native A_BrainExplode(); - action native A_Die(name damagetype = "none"); - action native A_Detonate(); - action native A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5); - native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); - - action native A_SetFloorClip(); - action native A_UnSetFloorClip(); - action native A_HideThing(); - action native A_UnHideThing(); - action native A_SetInvulnerable(); - action native A_UnSetInvulnerable(); - action native A_SetReflective(); - action native A_UnSetReflective(); - action native A_SetReflectiveInvulnerable(); - action native A_UnSetReflectiveInvulnerable(); - action native A_SetShootable(); - action native A_UnSetShootable(); - action native A_NoGravity(); - action native A_Gravity(); - action native A_LowGravity(); - native void A_SetGravity(float gravity); - action native A_Fall(); - action native A_SetSolid(); - action native A_UnsetSolid(); - action native A_SetFloat(); - action native A_UnsetFloat(); - - action native A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); - - action native A_ScreamAndUnblock(); - action native A_ActiveAndUnblock(); - action native A_ActiveSound(); - - action native A_FastChase(); - action native A_FreezeDeath(); - action native A_FreezeDeathChunks(); - action native A_GenericFreezeDeath(); - action native A_IceGuyDie(); - action native A_CentaurDefend(); - action native A_BishopMissileWeave(); - action native A_CStaffMissileSlither(); - action native A_PlayerScream(); - action native A_SkullPop(class skulltype = "BloodySkull"); - action native A_CheckPlayerDone(); - - action native A_Wander(int flags = 0); - action native A_Look2(); - action native A_TossGib(); - action native A_SentinelBob(); - action native A_SentinelRefire(); - action native A_Tracer2(); - action native A_SetShadow(); - action native A_ClearShadow(); - action native A_GetHurt(); - action native A_TurretLook(); - action native A_KlaxonBlare(); - action native A_Countdown(); - action native A_AlertMonsters(float maxdist = 0, int flags = 0); - action native A_ClearSoundTarget(); - action native A_FireAssaultGun(); - action native A_CheckTerrain(); - action native A_FaceConsolePlayer(float MaxTurnAngle = 0); // [TP] no-op - - action native A_MissileAttack(); - action native A_MeleeAttack(); - action native A_ComboAttack(); - action native A_BulletAttack(); - action native A_WolfAttack(int flags = 0, sound whattoplay = "weapons/pistol", float snipe = 1.0, int maxdamage = 64, int blocksize = 128, int pointblank = 2, int longrange = 4, float runspeed = 160.0, class pufftype = "BulletPuff"); - action native A_PlaySound(sound whattoplay = "weapons/pistol", int slot = CHAN_BODY, float volume = 1.0, bool looping = false, float attenuation = ATTN_NORM); - native void A_PlayWeaponSound(sound whattoplay); - action native A_FLoopActiveSound(); - action native A_LoopActiveSound(); - action native A_StopSound(int slot = CHAN_VOICE); // Bad default but that's what is originally was... - native void A_PlaySoundEx(sound whattoplay, coerce name slot, bool looping = false, int attenuation = 0); - native void A_StopSoundEx(coerce name slot); - native void A_SeekerMissile(int threshold, int turnmax, int flags = 0, int chance = 50, int distance = 10); - native state A_Jump(int chance = 256, state label, ...); - native void A_CustomMissile(class missiletype, float spawnheight = 32, float spawnofs_xy = 0, float angle = 0, int flags = 0, float pitch = 0, int ptr = AAPTR_TARGET); - native void A_CustomBulletAttack(float/*angle*/ spread_xy, float/*angle*/ spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); - native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = "", color color2 = "", int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float/*angle*/ spread_xy = 0, float/*angle*/ spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); - native state A_JumpIfHealthLower(int health, state label, int ptr_selector = AAPTR_DEFAULT); - native state A_JumpIfCloser(float distance, state label, bool noz = false); - native state A_JumpIfTracerCloser(float distance, state label, bool noz = false); - native state A_JumpIfMasterCloser(float distance, state label, bool noz = false); - native state A_JumpIfTargetOutsideMeleeRange(state label); - native state A_JumpIfTargetInsideMeleeRange(state label); - native state A_JumpIfInventory(class itemtype, int itemamount, state label, int owner = AAPTR_DEFAULT); - native state A_JumpIfArmorType(name Type, state label, int amount = 1); - action native bool A_SetInventory(class itemtype, int amount, int ptr = AAPTR_DEFAULT, bool beyondMax = false); - native bool A_GiveInventory(class itemtype, int amount = 0, int giveto = AAPTR_DEFAULT); - native bool A_TakeInventory(class itemtype, int amount = 0, int flags = 0, int giveto = AAPTR_DEFAULT); - action native bool A_SpawnItem(class itemtype = "Unknown", float distance = 0, float zheight = 0, bool useammo = true, bool transfer_translation = false); - native bool A_SpawnItemEx(class itemtype, float xofs = 0, float yofs = 0, float zofs = 0, float xvel = 0, float yvel = 0, float zvel = 0, float angle = 0, int flags = 0, int failchance = 0, int tid=0); - native void A_Print(string whattoprint, float time = 0, name fontname = ""); - native void A_PrintBold(string whattoprint, float time = 0, name fontname = ""); - native void A_Log(string whattoprint); - native void A_LogInt(int whattoprint); - native void A_LogFloat(float whattoprint); - native void A_SetTranslucent(float alpha, int style = 0); - native void A_SetRenderStyle(float alpha, int style); - action native A_FadeIn(float reduce = 0.1, int flags = 0); - action native A_FadeOut(float reduce = 0.1, int flags = 1); //bool remove == true - native void A_FadeTo(float target, float amount = 0.1, int flags = 0); - native void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false); - native void A_SetMass(int mass); - native void A_SpawnDebris(class spawntype, bool transfer_translation = false, float mult_h = 1, float mult_v = 1); - native void A_SpawnParticle(color color1, int flags = 0, int lifetime = 35, float size = 1, float angle = 0, float xoff = 0, float yoff = 0, float zoff = 0, float velx = 0, float vely = 0, float velz = 0, float accelx = 0, float accely = 0, float accelz = 0, float startalphaf = 1, float fadestepf = -1, float sizestep = 0); - native state A_CheckSight(state label); - native void A_ExtChase(bool usemelee, bool usemissile, bool playactive = true, bool nightmarefast = false); - native void A_DropInventory(class itemtype); - native void A_SetBlend(color color1, float alpha, int tics, color color2 = ""); - native void A_ChangeFlag(string flagname, bool value); - native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); - native state A_JumpIf(bool expression, state label); - action native A_RaiseMaster(bool copy = 0); - action native A_RaiseChildren(bool copy = 0); - action native A_RaiseSiblings(bool copy = 0); - native state A_CheckFloor(state label); - native state A_CheckCeiling(state label); - native state A_PlayerSkinCheck(state label); - native void A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); - action native state, bool A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); - action native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = "", float heightoffset = 0, float radiusoffset = 0, float pitch = 0); - action native bool A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); - native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); - - native void A_Recoil(float xyvel); - native state A_JumpIfInTargetInventory(class itemtype, int amount, state label, int forward_ptr = AAPTR_DEFAULT); - native bool A_GiveToTarget(class itemtype, int amount = 0, int forward_ptr = AAPTR_DEFAULT); - native bool A_TakeFromTarget(class itemtype, int amount = 0, int flags = 0, int forward_ptr = AAPTR_DEFAULT); - native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = "None", name species = "None", float mindist = 0, int limit = 0); - native state A_CheckSpecies(state jump, name species = "", int ptr = AAPTR_DEFAULT); - native void A_CountdownArg(int argnum, state targstate = ""); - action native A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); - native void A_CustomComboAttack(class missiletype, float spawnheight, int damage, sound meleesound = "", name damagetype = "none", bool bleed = true); - native void A_Burst(class chunktype); - action native A_Blast(int flags = 0, float strength = 255, float radius = 255, float speed = 20, class blasteffect = "BlastEffect", sound blastsound = "BlastRadius"); - action native A_RadiusThrust(int force = 128, int distance = -1, int flags = RTF_AFFECTSOURCE, int fullthrustdistance = 0); - action native A_RadiusDamageSelf(int damage = 128, float distance = 128, int flags = 0, class flashtype = "None"); - action native int A_Explode(int damage = -1, int distance = -1, int flags = XF_HURTSOURCE, bool alert = false, int fulldamagedistance = 0, int nails = 0, int naildamage = 10, class pufftype = "BulletPuff", name damagetype = "none"); - action native A_Stop(); - action native A_Respawn(int flags = 1); - action native A_BarrelDestroy(); - action native A_QueueCorpse(); - action native A_DeQueueCorpse(); - action native A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = ""); - action native A_ClearLastHeard(); - action native A_ClearTarget(); - native state A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); - native state A_JumpIfTargetInLOS (state label, float/*angle*/ fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); - native state A_JumpIfInTargetLOS (state label, float/*angle*/ fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); - native bool A_SelectWeapon(class whichweapon, int flags = 0); - action native A_Punch(); - action native A_Feathers(); - action native A_ClassBossHealth(); - action native A_ShootGun(); - action native A_RocketInFlight(); - action native A_Bang4Cloud(); - action native A_DropFire(); - native void A_GiveQuestItem(int itemno); - action native A_RemoveForcefield(); - native void A_DropWeaponPieces(class p1, class p2, class p3); - action native A_PigPain (); - native state A_MonsterRefire(int chance, state label); - action native A_SetAngle(float angle = 0, int flags = 0, int ptr = AAPTR_DEFAULT); - native void A_SetPitch(float pitch, int flags = 0, int ptr = AAPTR_DEFAULT); - native void A_SetRoll(float/*angle*/ roll, int flags = 0, int ptr = AAPTR_DEFAULT); - native void A_ScaleVelocity(float scale, int ptr = AAPTR_DEFAULT); - action native A_ChangeVelocity(float x = 0, float y = 0, float z = 0, int flags = 0, int ptr = AAPTR_DEFAULT); - native void A_SetArg(int pos, int value); - native void A_SetUserVar(name varname, int value); - native void A_SetUserArray(name varname, int index, int value); - native void A_SetUserVarFloat(name varname, float value); - native void A_SetUserArrayFloat(name varname, int index, float value); - native void A_SetSpecial(int spec, int arg0 = 0, int arg1 = 0, int arg2 = 0, int arg3 = 0, int arg4 = 0); - native void A_Quake(int intensity, int duration, int damrad, int tremrad, sound sfx = "world/quake"); - native void A_QuakeEx(int intensityX, int intensityY, int intensityZ, int duration, int damrad, int tremrad, sound sfx = "world/quake", int flags = 0, float mulWaveX = 1, float mulWaveY = 1, float mulWaveZ = 1, int falloff = 0, int highpoint = 0, float rollIntensity = 0, float rollWave = 0); - action native A_SetTics(int tics); - native void A_SetDamageType(name damagetype); - native void A_DropItem(class item, int dropamount = -1, int chance = 256); - native void A_SetSpeed(float speed, int ptr = AAPTR_DEFAULT); - native void A_SetFloatSpeed(float speed, int ptr = AAPTR_DEFAULT); - native void A_SetPainThreshold(int threshold, int ptr = AAPTR_DEFAULT); - native void A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native A_KillTarget(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native A_KillMaster(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native A_KillTracer(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native A_KillChildren(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native A_KillSiblings(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native A_RemoveTarget(int flags = 0, class filter = "None", name species = "None"); - action native A_RemoveMaster(int flags = 0, class filter = "None", name species = "None"); - action native A_RemoveTracer(int flags = 0, class filter = "None", name species = "None"); - action native A_RemoveChildren(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); - action native A_RemoveSiblings(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); - native void A_Remove(int removee, int flags = 0, class filter = "None", name species = "None"); - native int A_GiveToChildren(class itemtype, int amount = 0); - native int A_GiveToSiblings(class itemtype, int amount = 0); - native int A_TakeFromChildren(class itemtype, int amount = 0); - native int A_TakeFromSiblings(class itemtype, int amount = 0); - native void A_SetTeleFog(class oldpos, class newpos); - action native A_SwapTeleFog(); - native void A_SetFloatBobPhase(int bob); - native void A_SetHealth(int health, int ptr = AAPTR_DEFAULT); - action native A_ResetHealth(int ptr = AAPTR_DEFAULT); - native state A_JumpIfHigherOrLower(state high, state low, float offsethigh = 0, float offsetlow = 0, bool includeHeight = true, int ptr = AAPTR_TARGET); - native void A_SetSpecies(name species, int ptr = AAPTR_DEFAULT); - native void A_SetRipperLevel(int level); - native void A_SetRipMin(int mininum); - native void A_SetRipMax(int maximum); - native void A_SetChaseThreshold(int threshold, bool def = false, int ptr = AAPTR_DEFAULT); - native state A_CheckProximity(state jump, class classname, float distance, int count = 1, int flags = 0, int ptr = AAPTR_DEFAULT); - native state A_CheckBlock(state block, int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0); - native state A_CheckSightOrRange(float distance, state label, bool two_dimension = false); - native state A_CheckRange(float distance, state label, bool two_dimension = false); - action native bool A_FaceMovementDirection(float offset = 0, float anglelimit = 0, float pitchlimit = 0, int flags = 0, int ptr = AAPTR_DEFAULT); - action native int A_ClearOverlays(int sstart = 0, int sstop = 0, bool safety = true); - action native bool A_CopySpriteFrame(int from, int to, int flags = 0); - action native bool A_SetSpriteAngle(float angle = 0, int ptr = AAPTR_DEFAULT); - action native bool A_SetSpriteRotation(float angle = 0, int ptr = AAPTR_DEFAULT); - action native bool A_SetVisibleRotation(float anglestart = 0, float angleend = 0, float pitchstart = 0, float pitchend = 0, int flags = 0, int ptr = AAPTR_DEFAULT); - native void A_SetTranslation(string transname); - - native void A_RearrangePointers(int newtarget, int newmaster = AAPTR_DEFAULT, int newtracer = AAPTR_DEFAULT, int flags=0); - native void A_TransferPointer(int ptr_source, int ptr_recepient, int sourcefield, int recepientfield=AAPTR_DEFAULT, int flags=0); - action native A_CopyFriendliness(int ptr_source = AAPTR_MASTER); - - action native bool A_Overlay(int layer, state start = "", bool nooverride = false); - action native A_WeaponOffset(float wx = 0, float wy = 32, int flags = 0); - action native A_OverlayOffset(int layer = PSP_WEAPON, float wx = 0, float wy = 32, int flags = 0); - action native A_OverlayFlags(int layer, int flags, bool set); - - native int ACS_NamedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); - native int ACS_NamedSuspend(name script, int mapnum=0); - native int ACS_NamedTerminate(name script, int mapnum=0); - native int ACS_NamedLockedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0); - native int ACS_NamedLockedExecuteDoor(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0); - native int ACS_NamedExecuteWithResult(name script, int arg1=0, int arg2=0, int arg3=0, int arg4=0); - native void ACS_NamedExecuteAlways(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); - - States - { - Spawn: - TNT1 A -1 - Stop - Null: - TNT1 A 1 - Stop - GenericFreezeDeath: - // Generic freeze death frames. Woo! - "####" "#" 5 A_GenericFreezeDeath - "----" A 1 A_FreezeDeathChunks - Wait - GenericCrush: - POL5 A -1 - Stop - } - - // Internal functions - native state __decorate_internal_state__(state); - native int __decorate_internal_int__(int); - native bool __decorate_internal_bool__(bool); - native float __decorate_internal_float__(float); -} diff --git a/wadsrc/static/actors/shared/inventory.txt b/wadsrc/static/actors/shared/inventory.txt deleted file mode 100644 index 43a33f93a..000000000 --- a/wadsrc/static/actors/shared/inventory.txt +++ /dev/null @@ -1,376 +0,0 @@ -ACTOR Inventory native -{ - Inventory.Amount 1 - Inventory.MaxAmount 1 - Inventory.InterHubAmount 1 - Inventory.UseSound "misc/invuse" - Inventory.PickupSound "misc/i_pkup" - Inventory.PickupMessage "$TXT_DEFAULTPICKUPMSG" - - action native state A_JumpIfNoAmmo(state label); - action native A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = "", sound MissSound = ""); - action native A_FireBullets(float/*angle*/ spread_xy, float/*angle*/ spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); - action native A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); - action native A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = "", color color2 = "", int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float/*angle*/ spread_xy = 0, float/*angle*/ spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); - action native A_Light(int extralight); - action native A_Light0(); - action native A_Light1(); - action native A_Light2(); - action native A_LightInverse(); - action native A_WeaponReady(int flags = 0); - action native A_Lower(); - action native A_Raise(); - action native A_FirePistol(); - action native A_FireShotgun(); - action native A_FireShotgun2(); - action native A_OpenShotgun2(); - action native A_LoadShotgun2(); - action native A_CloseShotgun2(); - action native A_FireCGun(); - action native A_FireSTGrenade(class grenadetype = "Grenade"); - action native A_FireMissile(); - action native A_FirePlasma(); - action native A_FireRailgun(); - action native A_FireRailgunLeft(); - action native A_FireRailgunRight(); - action native A_RailWait(); - action native A_BFGsound(); - action native A_FireBFG(); - action native A_FireOldBFG(); - action native A_ReFire(state flash = ""); - action native A_ClearReFire(); - action native A_CheckReload(); - action native A_GunFlash(state flash = "", int flags = 0); - action native A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float/*angle*/ spread_xy = 2.8125, float/*angle*/ spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); - action native state A_CheckForReload(int counter, state label, bool dontincrement = false); - action native A_ResetReloadCounter(); - action native A_RestoreSpecialPosition(); - action native A_RestoreSpecialDoomThing(); - action native A_RestoreSpecialThing1(); - action native A_RestoreSpecialThing2(); - - States - { - HideDoomish: - TNT1 A 1050 - TNT1 A 0 A_RestoreSpecialPosition - TNT1 A 1 A_RestoreSpecialDoomThing - Stop - HideSpecial: - ACLO E 1400 - ACLO A 0 A_RestoreSpecialPosition - ACLO A 4 A_RestoreSpecialThing1 - ACLO BABCBCDC 4 - ACLO D 4 A_RestoreSpecialThing2 - Stop - Held: - TNT1 A -1 - Stop - HoldAndDestroy: - TNT1 A 1 - Stop - } -} - -Actor ScoreItem : Inventory native -{ - Height 10 - +COUNTITEM - Inventory.Amount 1 - +Inventory.ALWAYSPICKUP -} - -Actor Ammo : Inventory native -{ - +INVENTORY.KEEPDEPLETED - Inventory.PickupSound "misc/ammo_pkup" -} - -Actor BackpackItem : Inventory native -{ -} - -ACTOR Armor : Inventory native -{ - Inventory.PickupSound "misc/armor_pkup" -} - -ACTOR BasicArmor : Armor native -{ - +Inventory.KEEPDEPLETED -} - -ACTOR BasicArmorBonus : Armor native -{ - +Inventory.AUTOACTIVATE - +Inventory.ALWAYSPICKUP - Inventory.MaxAmount 0 - Armor.SavePercent 33.335 - -} - -ACTOR BasicArmorPickup : Armor native -{ - +Inventory.AUTOACTIVATE - Inventory.MaxAmount 0 -} - -ACTOR HexenArmor : Armor native -{ - +Inventory.KEEPDEPLETED - +Inventory.UNDROPPABLE -} - -ACTOR DehackedPickup : Inventory native {} - -ACTOR FakeInventory : Inventory native {} - -ACTOR CustomInventory : Inventory native {} - -Actor Health : Inventory native -{ - Inventory.Amount 1 - Inventory.MaxAmount 0 - Inventory.PickupSound "misc/health_pkup" -} - -Actor HealthPickup : Inventory native -{ - Inventory.DefMaxAmount - +INVENTORY.INVBAR -} - -Actor Key : Inventory native -{ - +DONTGIB // Don't disappear due to a crusher - +INVENTORY.INTERHUBSTRIP - Inventory.PickupSound "misc/k_pkup" -} - -ACTOR PowerupGiver : Inventory native -{ - Inventory.DefMaxAmount - +INVENTORY.INVBAR - +INVENTORY.FANCYPICKUPSOUND - Inventory.PickupSound "misc/p_pkup" -} - -ACTOR Powerup : Inventory native {} - -ACTOR PowerInvulnerable : Powerup native -{ - Powerup.Duration -30 - inventory.icon "SPSHLD0" -} - -ACTOR PowerStrength : Powerup native -{ - Powerup.Duration 1 - Powerup.Color 255,0,0,0.5 - +INVENTORY.HUBPOWER -} - -ACTOR PowerInvisibility : Powerup native -{ - +SHADOW - Powerup.Duration -60 - Powerup.Strength 80 - Powerup.Mode "Fuzzy" -} - -ACTOR PowerGhost : PowerInvisibility -{ - +GHOST - Powerup.Duration -60 - Powerup.Strength 60 - Powerup.Mode "None" -} - -ACTOR PowerShadow : PowerInvisibility -{ - +INVENTORY.HUBPOWER - Powerup.Duration -55 - Powerup.Strength 75 - Powerup.Mode "Cumulative" -} - -ACTOR PowerIronFeet : Powerup native -{ - Powerup.Duration -60 - Powerup.Color 0, 255, 0, 0.125 -} - -ACTOR PowerMask : PowerIronFeet native -{ - Powerup.Duration -80 - Powerup.Color 0,0,0,0 - +INVENTORY.HUBPOWER - Inventory.Icon "I_MASK" -} - -ACTOR PowerLightAmp : Powerup native -{ - Powerup.Duration -120 -} - -ACTOR PowerTorch : PowerLightAmp native {} - -ACTOR PowerFlight : Powerup native -{ - Powerup.Duration -60 - +INVENTORY.HUBPOWER -} - -ACTOR PowerWeaponLevel2 : Powerup native -{ - Powerup.Duration -40 - Inventory.Icon "SPINBK0" - +INVENTORY.NOTELEPORTFREEZE -} - -ACTOR PowerSpeed : Powerup native -{ - Powerup.Duration -45 - Speed 1.5 - Inventory.Icon "SPBOOT0" - +INVENTORY.NOTELEPORTFREEZE -} - -// Player Speed Trail (used by the Speed Powerup) ---------------------------- - -ACTOR PlayerSpeedTrail native -{ - +NOBLOCKMAP - +NOGRAVITY - Alpha 0.6 - RenderStyle Translucent -} - -ACTOR PowerMinotaur : Powerup native -{ - Powerup.Duration -25 - Inventory.Icon "SPMINO0" -} - -ACTOR PowerTargeter : Powerup native -{ - Powerup.Duration -160 - +INVENTORY.HUBPOWER - States - { - Targeter: - TRGT A -1 - Stop - TRGT B -1 - Stop - TRGT C -1 - Stop - } -} - -ACTOR PowerFrightener : Powerup native -{ - Powerup.Duration -60 -} - -ACTOR PowerBuddha : Powerup native -{ - Powerup.Duration -60 -} - -ACTOR PowerScanner : Powerup native -{ - Powerup.Duration -80 - +INVENTORY.HUBPOWER -} - -ACTOR PowerTimeFreezer : Powerup native -{ - Powerup.Duration -12 -} - -ACTOR PowerDamage : Powerup native -{ - Powerup.Duration -25 -} - -ACTOR PowerProtection : Powerup native -{ - Powerup.Duration -25 -} - -ACTOR PowerDrain : Powerup native -{ - Powerup.Duration -60 -} - -ACTOR PowerRegeneration : Powerup native -{ - Powerup.Duration -120 - Powerup.Strength 5 -} - -ACTOR PowerHighJump : Powerup native {} - -ACTOR PowerDoubleFiringSpeed : Powerup native {} - -ACTOR PowerMorph : Powerup native -{ - Powerup.Duration -40 -} - -ACTOR PowerInfiniteAmmo : Powerup native -{ - Powerup.Duration -30 -} - -ACTOR MapRevealer : Inventory native {} - -ACTOR PuzzleItem : Inventory native -{ - +NOGRAVITY - +INVENTORY.INVBAR - Inventory.DefMaxAmount - Inventory.UseSound "PuzzleSuccess" - Inventory.PickupSound "misc/i_pkup" -} - -Actor Weapon : Inventory native -{ - Inventory.PickupSound "misc/w_pkup" - Weapon.DefaultKickback - Weapon.BobSpeed 1.0 - Weapon.BobRangeX 1.0 - Weapon.BobRangeY 1.0 - +WEAPONSPAWN - States - { - LightDone: - SHTG E 0 A_Light0 - Stop - } - - action native A_ZoomFactor(float scale = 1, int flags = 0); - const int ZOOM_INSTANT = 1; - const int ZOOM_NOSCALETURNING = 2; - - action native A_SetCrosshair(int xhair); -} - -ACTOR WeaponGiver : Weapon native -{ - Weapon.AmmoGive1 -1 - Weapon.AmmoGive2 -1 -} - -Actor WeaponHolder : Inventory native -{ - +NOBLOCKMAP - +NOSECTOR - +INVENTORY.UNDROPPABLE -} - -Actor WeaponPiece : Inventory native -{ - +WEAPONSPAWN -} diff --git a/wadsrc/static/actors/shared/player.txt b/wadsrc/static/actors/shared/player.txt deleted file mode 100644 index ac5ceb0a7..000000000 --- a/wadsrc/static/actors/shared/player.txt +++ /dev/null @@ -1,52 +0,0 @@ -Actor PlayerPawn : Actor native -{ - Health 100 - Radius 16 - Height 56 - Mass 100 - Painchance 255 - Speed 1 - +SOLID - +SHOOTABLE - +DROPOFF - +PICKUP - +NOTDMATCH - +FRIENDLY - +SLIDESONWALLS - +CANPASS - +CANPUSHWALLS - +FLOORCLIP - +WINDTHRUST - +TELESTOMP - +NOBLOCKMONST - Player.AttackZOffset 8 - Player.JumpZ 8 - Player.GruntSpeed 12 - Player.FallingScreamSpeed 35,40 - Player.ViewHeight 41 - Player.UseRange 64 - Player.ForwardMove 1,1 - Player.SideMove 1,1 - Player.ColorRange 0,0 - Player.SoundClass "player" - Player.DamageScreenColor "ff 00 00" - Player.MugShotMaxHealth 0 - Player.FlechetteType "ArtiPoisonBag3" - Player.AirCapacity 1 - Obituary "$OB_MPDEFAULT" -} - -Actor PlayerChunk : PlayerPawn native -{ - +NOSKIN - -SOLID - -SHOOTABLE - -PICKUP - -NOTDMATCH - -FRIENDLY - -SLIDESONWALLS - -CANPUSHWALLS - -FLOORCLIP - -WINDTHRUST - -TELESTOMP -} diff --git a/wadsrc/static/actors/shared/specialspot.txt b/wadsrc/static/actors/shared/specialspot.txt deleted file mode 100644 index fc2bd254a..000000000 --- a/wadsrc/static/actors/shared/specialspot.txt +++ /dev/null @@ -1,5 +0,0 @@ - -ACTOR SpecialSpot native -{ - action native A_SpawnSingleItem(class type, int fail_sp = 0, int fail_co = 0, int fail_dm = 0); -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index a77a4d583..e921b5508 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,7 +1,7 @@ -#include "actors/actor.txt" +//#include "actors/actor.txt" -#include "actors/shared/inventory.txt" -#include "actors/shared/player.txt" +//#include "actors/shared/inventory.txt" +//#include "actors/shared/player.txt" #include "actors/shared/morph.txt" #include "actors/shared/botstuff.txt" #include "actors/shared/sharedmisc.txt" @@ -15,7 +15,7 @@ #include "actors/shared/soundsequence.txt" #include "actors/shared/soundenvironment.txt" #include "actors/shared/bridge.txt" -#include "actors/shared/specialspot.txt" +//#include "actors/shared/specialspot.txt" #include "actors/shared/teleport.txt" #include "actors/shared/camera.txt" #include "actors/shared/movingcamera.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt new file mode 100644 index 000000000..b0d3ec925 --- /dev/null +++ b/wadsrc/static/zscript.txt @@ -0,0 +1,9 @@ +zscript/constants.txt +zscript/actor.txt + +zscript/shared/inventory.txt +zscript/shared/player.txt +zscript/shared/specialspot.txt + +//zscript/test1.txt + diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index a15ec893a..9352028b3 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -387,13 +387,6 @@ class Actor : Thinker native GenericCrush: POL5 A -1; Stop; - Test.State: - &&&& A[\] 5 offset(4,4*2); - &&&& A[\] DEFAULT_HEALTH; - abcd efgh random(3, 6); - lght blahblah 5*3 light("furz", "bläh", "rülps"); - lght blahblah 5 light("boing"); - goto Actor::Spawn+1; } // Internal functions diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt new file mode 100644 index 000000000..fe60fdc1a --- /dev/null +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -0,0 +1,501 @@ +class Inventory : Actor native +{ + Default + { + Inventory.Amount 1; + Inventory.MaxAmount 1; + Inventory.InterHubAmount 1; + Inventory.UseSound "misc/invuse"; + Inventory.PickupSound "misc/i_pkup"; + Inventory.PickupMessage "$TXT_DEFAULTPICKUPMSG"; + } + + // functions that can be used from weapons and CustomInventory. These require that 'self' is of type class and be treated as such in the scripts. + /*inventory*/ action native state A_JumpIfNoAmmo(state label); + /*inventory*/ action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = "", sound MissSound = ""); + /*inventory*/ action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); + /*inventory*/ action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); + /*inventory*/ action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = "", color color2 = "", int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); + /*inventory*/ action native void A_Light(int extralight); + /*inventory*/ action native void A_Light0(); + /*inventory*/ action native void A_Light1(); + /*inventory*/ action native void A_Light2(); + /*inventory*/ action native void A_LightInverse(); + /*inventory*/ action native void A_WeaponReady(int flags = 0); + /*inventory*/ action native void A_Lower(); + /*inventory*/ action native void A_Raise(); + /*inventory*/ action native void A_FirePistol(); + /*inventory*/ action native void A_FireShotgun(); + /*inventory*/ action native void A_FireShotgun2(); + /*inventory*/ action native void A_OpenShotgun2(); + /*inventory*/ action native void A_LoadShotgun2(); + /*inventory*/ action native void A_CloseShotgun2(); + /*inventory*/ action native void A_FireCGun(); + /*inventory*/ action native void A_FireSTGrenade(class grenadetype = "Grenade"); + /*inventory*/ action native void A_FireMissile(); + /*inventory*/ action native void A_FirePlasma(); + /*inventory*/ action native void A_FireRailgun(); + /*inventory*/ action native void A_FireRailgunLeft(); + /*inventory*/ action native void A_FireRailgunRight(); + /*inventory*/ action native void A_RailWait(); + /*inventory*/ action native void A_BFGsound(); + /*inventory*/ action native void A_FireBFG(); + /*inventory*/ action native void A_FireOldBFG(); + /*inventory*/ action native void A_ReFire(state flash = ""); + /*inventory*/ action native void A_ClearReFire(); + /*inventory*/ action native void A_CheckReload(); + /*inventory*/ action native void A_GunFlash(state flash = "", int flags = 0); + /*inventory*/ action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); + /*inventory*/ action native state A_CheckForReload(int counter, state label, bool dontincrement = false); + /*inventory*/ action native void A_ResetReloadCounter(); + + // These are regular functions for the item itself. + action native void A_RestoreSpecialPosition(); + action native void A_RestoreSpecialDoomThing(); + action native void A_RestoreSpecialThing1(); + action native void A_RestoreSpecialThing2(); + + States + { + HideDoomish: + TNT1 A 1050; + TNT1 A 0 A_RestoreSpecialPosition; + TNT1 A 1 A_RestoreSpecialDoomThing; + Stop; + HideSpecial: + ACLO E 1400; + ACLO A 0 A_RestoreSpecialPosition; + ACLO A 4 A_RestoreSpecialThing1; + ACLO BABCBCDC 4; + ACLO D 4 A_RestoreSpecialThing2; + Stop; + Held: + TNT1 A -1; + Stop; + HoldAndDestroy: + TNT1 A 1; + Stop; + } +} + +class ScoreItem : Inventory native +{ + Default + { + Height 10; + +COUNTITEM; + Inventory.Amount 1; + +Inventory.ALWAYSPICKUP; + } +} + +class Ammo : Inventory native +{ + Default + { + +INVENTORY.KEEPDEPLETED; + Inventory.PickupSound "misc/ammo_pkup"; + } +} + +class BackpackItem : Inventory native +{ +} + +class Armor : Inventory native +{ + Default + { + Inventory.PickupSound "misc/armor_pkup"; + } +} + +class BasicArmor : Armor native +{ + Default + { + +Inventory.KEEPDEPLETED; + } +} + +class BasicArmorBonus : Armor native +{ + Default + { + +Inventory.AUTOACTIVATE; + +Inventory.ALWAYSPICKUP; + Inventory.MaxAmount 0; + Armor.SavePercent 33.335; + } +} + +class BasicArmorPickup : Armor native +{ + Default + { + +Inventory.AUTOACTIVATE; + Inventory.MaxAmount 0; + } +} + +class HexenArmor : Armor native +{ + Default + { + +Inventory.KEEPDEPLETED; + +Inventory.UNDROPPABLE; + } +} + +class DehackedPickup : Inventory native {} + +class FakeInventory : Inventory native {} + +class CustomInventory : Inventory native {} + +class Health : Inventory native +{ + Default + { + Inventory.Amount 1; + Inventory.MaxAmount 0; + Inventory.PickupSound "misc/health_pkup"; + } +} + +class HealthPickup : Inventory native +{ + Default + { + Inventory.DefMaxAmount; + +INVENTORY.INVBAR; + } +} + +class Key : Inventory native +{ + Default + { + +DONTGIB; // Don't disappear due to a crusher + Inventory.InterHubAmount 0; + Inventory.PickupSound "misc/k_pkup"; + } +} + +class PowerupGiver : Inventory native +{ + Default + { + Inventory.DefMaxAmount; + +INVENTORY.INVBAR; + +INVENTORY.FANCYPICKUPSOUND; + Inventory.PickupSound "misc/p_pkup"; + } +} + +class Powerup : Inventory native {} + +class PowerInvulnerable : Powerup native +{ + Default + { + Powerup.Duration -30; + inventory.icon "SPSHLD0"; + } +} + +class PowerStrength : Powerup native +{ + Default + { + Powerup.Duration 1; + Powerup.Color "ff 00 00", 0.5; + +INVENTORY.HUBPOWER; + } +} + +class PowerInvisibility : Powerup native +{ + Default + { + +SHADOW; + Powerup.Duration -60; + Powerup.Strength 80; + Powerup.Mode "Fuzzy"; + } +} + +class PowerGhost : PowerInvisibility +{ + Default + { + +GHOST; + Powerup.Duration -60; + Powerup.Strength 60; + Powerup.Mode "None"; + } +} + +class PowerShadow : PowerInvisibility +{ + Default + { + +INVENTORY.HUBPOWER; + Powerup.Duration -55; + Powerup.Strength 75; + Powerup.Mode "Cumulative"; + } +} + +class PowerIronFeet : Powerup native +{ + Default + { + Powerup.Duration -60; + Powerup.Color "00 ff 00", 0.125; + } +} + +class PowerMask : PowerIronFeet native +{ + Default + { + Powerup.Duration -80; + Powerup.Color "00 00 00", 0; + +INVENTORY.HUBPOWER; + Inventory.Icon "I_MASK"; + } +} + +class PowerLightAmp : Powerup native +{ + Default + { + Powerup.Duration -120; + } +} + +class PowerTorch : PowerLightAmp native {} + +class PowerFlight : Powerup native +{ + Default + { + Powerup.Duration -60; + +INVENTORY.HUBPOWER; + } +} + +class PowerWeaponLevel2 : Powerup native +{ + Default + { + Powerup.Duration -40; + Inventory.Icon "SPINBK0"; + +INVENTORY.NOTELEPORTFREEZE; + } +} + +class PowerSpeed : Powerup native +{ + Default + { + Powerup.Duration -45; + Speed 1.5; + Inventory.Icon "SPBOOT0"; + +INVENTORY.NOTELEPORTFREEZE; + } +} + +// Player Speed Trail (used by the Speed Powerup) ---------------------------- + +class PlayerSpeedTrail native +{ + Default + { + +NOBLOCKMAP; + +NOGRAVITY; + Alpha 0.6; + RenderStyle "Translucent"; + } +} + +class PowerMinotaur : Powerup native +{ + Default + { + Powerup.Duration -25; + Inventory.Icon "SPMINO0"; + } +} + +class PowerTargeter : Powerup native +{ + Default + { + Powerup.Duration -160; + +INVENTORY.HUBPOWER; + } + States + { + Targeter: + TRGT A -1; + Stop; + TRGT B -1; + Stop; + TRGT C -1; + Stop; + } +} + +class PowerFrightener : Powerup native +{ + Default + { + Powerup.Duration -60; + } +} + +class PowerBuddha : Powerup native +{ + Default + { + Powerup.Duration -60; + } +} + +class PowerScanner : Powerup native +{ + Default + { + Powerup.Duration -80; + +INVENTORY.HUBPOWER; + } +} + +class PowerTimeFreezer : Powerup native +{ + Default + { + Powerup.Duration -12; + } +} + +class PowerDamage : Powerup native +{ + Default + { + Powerup.Duration -25; + } +} + +class PowerProtection : Powerup native +{ + Default + { + Powerup.Duration -25; + } +} + +class PowerDrain : Powerup native +{ + Default + { + Powerup.Duration -60; + } +} + +class PowerRegeneration : Powerup native +{ + Default + { + Powerup.Duration -120; + Powerup.Strength 5; + } +} + +class PowerHighJump : Powerup native {} + +class PowerDoubleFiringSpeed : Powerup native {} + +class PowerMorph : Powerup native +{ + Default + { + Powerup.Duration -40; + } +} + +class PowerInfiniteAmmo : Powerup native +{ + Default + { + Powerup.Duration -30; + } +} + +class MapRevealer : Inventory native {} + +class PuzzleItem : Inventory native +{ + Default + { + +NOGRAVITY; + +INVENTORY.INVBAR; + Inventory.DefMaxAmount; + Inventory.UseSound "PuzzleSuccess"; + Inventory.PickupSound "misc/i_pkup"; + } +} + +class Weapon : Inventory native +{ + Default + { + Inventory.PickupSound "misc/w_pkup"; + Weapon.DefaultKickback; + Weapon.BobSpeed 1.0; + Weapon.BobRangeX 1.0; + Weapon.BobRangeY 1.0; + +WEAPONSPAWN; + } + States + { + LightDone: + SHTG E 0 A_Light0; + Stop; + } + + /*inventory*/ action native void A_ZoomFactor(float scale = 1, int flags = 0); + const ZOOM_INSTANT = 1; + const ZOOM_NOSCALETURNING = 2; + + /*inventory*/ action native void A_SetCrosshair(int xhair); +} + +class WeaponGiver : Weapon native +{ + Default + { + Weapon.AmmoGive1 -1; + Weapon.AmmoGive2 -1; + } +} + +class WeaponHolder : Inventory native +{ + Default + { + +NOBLOCKMAP; + +NOSECTOR; + +INVENTORY.UNDROPPABLE; + } +} + +class WeaponPiece : Inventory native +{ + Default + { + +WEAPONSPAWN; + } +} diff --git a/wadsrc/static/zscript/shared/player.txt b/wadsrc/static/zscript/shared/player.txt new file mode 100644 index 000000000..b205a2a37 --- /dev/null +++ b/wadsrc/static/zscript/shared/player.txt @@ -0,0 +1,58 @@ +class PlayerPawn : Actor native +{ + Default + { + Health 100; + Radius 16; + Height 56; + Mass 100; + Painchance 255; + Speed 1; + +SOLID + +SHOOTABLE + +DROPOFF + +PICKUP + +NOTDMATCH + +FRIENDLY + +SLIDESONWALLS + +CANPASS + +CANPUSHWALLS + +FLOORCLIP + +WINDTHRUST + +TELESTOMP + +NOBLOCKMONST + Player.AttackZOffset 8; + Player.JumpZ 8; + Player.GruntSpeed 12; + Player.FallingScreamSpeed 35,40; + Player.ViewHeight 41; + Player.UseRange 64; + Player.ForwardMove 1,1; + Player.SideMove 1,1; + Player.ColorRange 0,0; + Player.SoundClass "player"; + Player.DamageScreenColor "ff 00 00"; + Player.MugShotMaxHealth 0; + Player.FlechetteType "ArtiPoisonBag3"; + Player.AirCapacity 1; + Obituary "$OB_MPDEFAULT"; + } +} + +class PlayerChunk : PlayerPawn native +{ + Default + { + +NOSKIN + -SOLID + -SHOOTABLE + -PICKUP + -NOTDMATCH + -FRIENDLY + -SLIDESONWALLS + -CANPUSHWALLS + -FLOORCLIP + -WINDTHRUST + -TELESTOMP + } +} diff --git a/wadsrc/static/zscript/shared/specialspot.txt b/wadsrc/static/zscript/shared/specialspot.txt new file mode 100644 index 000000000..a06d41c27 --- /dev/null +++ b/wadsrc/static/zscript/shared/specialspot.txt @@ -0,0 +1,5 @@ + +class SpecialSpot : Actor native +{ + action native void A_SpawnSingleItem(class type, int fail_sp = 0, int fail_co = 0, int fail_dm = 0); +} From 7e8d7eb2ecc74c07f61fdb753bf820b2f540e8e8 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 13 Oct 2016 22:52:31 +0200 Subject: [PATCH 026/255] - fixed parsing of 'damage' default property. - fixed processing of goto labels. --- src/scripting/zscript/zcc_compile.cpp | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 6e8447690..5e0e64856 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1575,8 +1575,13 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper switch ((*p) & 223) { - case 'I': case 'X': // Expression in parentheses or number. We only support the constant here. The function will have to be handled by a separate property to get past the parser. + conv.i = GetInt(exp); + params.Push(conv); + conv.exp = nullptr; + break; + + case 'I': case 'M': // special case for morph styles in DECORATE . This expression-aware parser will not need this. case 'N': // special case for thing activations in DECORATE. This expression-aware parser will not need this. conv.i = GetInt(exp); @@ -2188,7 +2193,7 @@ void ZCCCompiler::CompileStates() auto part = sg->Label; do { - statename << part->Id << '.'; + statename << FName(part->Id) << '.'; part = static_cast(part->SiblingNext); } while (part != sg->Label); statename.Truncate((long)statename.Len() - 1); // remove the last '.' in the label name From 7de683f9f52b86d89ef91d08f149bba7c81fd80c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 00:40:20 +0200 Subject: [PATCH 027/255] - converted a few more DECORATE files. - started with the AST converter. So far it only deals with direct function calls with simple constants as parameters. - added an error condition for the defaults block to get rid of some asserts. --- .../codegeneration/thingdef_expression.cpp | 9 +- src/scripting/zscript/zcc-parse.lemon | 1 + src/scripting/zscript/zcc_compile.cpp | 91 ++++- src/scripting/zscript/zcc_compile.h | 6 + wadsrc/static/actors/shared/action.txt | 56 --- wadsrc/static/actors/shared/blood.txt | 69 ---- wadsrc/static/actors/shared/botstuff.txt | 19 - wadsrc/static/actors/shared/debris.txt | 331 ---------------- wadsrc/static/actors/shared/morph.txt | 15 - wadsrc/static/actors/shared/sharedmisc.txt | 178 --------- wadsrc/static/decorate.txt | 12 +- wadsrc/static/zscript.txt | 6 + wadsrc/static/zscript/shared/blood.txt | 78 ++++ wadsrc/static/zscript/shared/botstuff.txt | 25 ++ wadsrc/static/zscript/shared/debris.txt | 364 ++++++++++++++++++ wadsrc/static/zscript/shared/ice.txt | 61 +++ wadsrc/static/zscript/shared/morph.txt | 21 + wadsrc/static/zscript/shared/sharedmisc.txt | 220 +++++++++++ 18 files changed, 881 insertions(+), 681 deletions(-) delete mode 100644 wadsrc/static/actors/shared/action.txt delete mode 100644 wadsrc/static/actors/shared/blood.txt delete mode 100644 wadsrc/static/actors/shared/botstuff.txt delete mode 100644 wadsrc/static/actors/shared/debris.txt delete mode 100644 wadsrc/static/actors/shared/morph.txt delete mode 100644 wadsrc/static/actors/shared/sharedmisc.txt create mode 100644 wadsrc/static/zscript/shared/blood.txt create mode 100644 wadsrc/static/zscript/shared/botstuff.txt create mode 100644 wadsrc/static/zscript/shared/debris.txt create mode 100644 wadsrc/static/zscript/shared/ice.txt create mode 100644 wadsrc/static/zscript/shared/morph.txt create mode 100644 wadsrc/static/zscript/shared/sharedmisc.txt diff --git a/src/scripting/codegeneration/thingdef_expression.cpp b/src/scripting/codegeneration/thingdef_expression.cpp index 31acc391e..77b062ed6 100644 --- a/src/scripting/codegeneration/thingdef_expression.cpp +++ b/src/scripting/codegeneration/thingdef_expression.cpp @@ -3622,12 +3622,19 @@ FxFunctionCall::~FxFunctionCall() //========================================================================== // -// +// Note: This currently only deals with the simple cases and needs some changes. // //========================================================================== FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { + // This part is mostly a kludge, it really needs to get the class type from Self. + PFunction *afd = dyn_cast(ctx.Class->Symbols.FindSymbol(MethodName, true)); + if (afd != nullptr) + { + return new FxVMFunctionCall(afd, ArgList, ScriptPosition, false); + } + for (size_t i = 0; i < countof(FxFlops); ++i) { if (MethodName == FxFlops[i].Name) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 51a221af7..96b4b66c1 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -565,6 +565,7 @@ default_statement_list(X) ::= default_statement_list(X) default_statement(B). default_statement(X) ::= SEMICOLON. { X = NULL; } +default_statement(X) ::= error SEMICOLON. { X = NULL; } //default_statement(X) ::= assign_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } default_statement(X) ::= property_statement(A). { X = A; /*X-overwrites-A*/ } default_statement(X) ::= flag_statement(A). { X = A; /*X-overwrites-A*/ } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 5e0e64856..904f938ca 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -45,6 +45,7 @@ #include "zcc_compile.h" #include "v_text.h" #include "p_lnspec.h" +#include "i_system.h" #include "gdtoa.h" #include "codegeneration/thingdef_exp.h" #include "vmbuilder.h" @@ -2028,10 +2029,6 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a // This is the simple case which doesn't require work on the tree. return new FxVMFunctionCall(afd, nullptr, *af, true); } - else - { - // need to generate a function from the information. - } } else { @@ -2039,8 +2036,10 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a return nullptr; } } - Error(af, "Complex action functions not supported yet."); - return nullptr; + return ConvertAST(af); + + //Error(af, "Complex action functions not supported yet."); + //return nullptr; /* bool hasfinalret; @@ -2264,3 +2263,83 @@ void ZCCCompiler::CompileStates() } } } + +//========================================================================== +// +// Convert the AST data for the code generator. +// +//========================================================================== + +FxExpression *ZCCCompiler::ConvertAST(ZCC_TreeNode *ast) +{ + // FxReturnStatement will have to be done more intelligently, of course. + return new FxReturnStatement(ConvertNode(ast), *ast); +} + +FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) +{ + // Note: Do not call 'Simplify' here because that function tends to destroy identifiers due to lack of context in which to resolve them. + // The Fx nodes created here will be better suited for that. + switch (ast->NodeType) + { + case AST_ExprFuncCall: + { + auto fcall = static_cast(ast); + assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. + auto fname = static_cast(fcall->Function)->Identifier; + return new FxFunctionCall(nullptr, fname, ConvertNodeList(fcall->Parameters), *ast); + } + + case AST_FuncParm: + { + auto fparm = static_cast(ast); + // ignore the label for now, that's stuff for far later, when a bit more here is working. + return ConvertNode(fparm->Value); + } + + case AST_ExprConstant: + { + auto cnst = static_cast(ast); + if (cnst->Type->IsKindOf(RUNTIME_CLASS(PInt))) + { + return new FxConstant(cnst->IntVal, *ast); + } + else if (cnst->Type->IsKindOf(RUNTIME_CLASS(PFloat))) + { + return new FxConstant(cnst->DoubleVal, *ast); + } + else if (cnst->Type->IsKindOf(RUNTIME_CLASS(PString))) + { + return new FxConstant(*cnst->StringVal, *ast); + } + else if (cnst->Type->IsKindOf(RUNTIME_CLASS(PName))) + { + return new FxConstant(ENamedName(cnst->IntVal), *ast); + } + else + { + // can there be other types? + Error(cnst, "Unknown constant type"); + return new FxConstant(0, *ast); + } + } + + default: + // only for development. I_Error is more convenient here than a normal error. + I_Error("ConvertNode encountered unsupported node of type %d", ast->NodeType); + return nullptr; + } +} + + +FArgumentList *ZCCCompiler::ConvertNodeList(ZCC_TreeNode *head) +{ + FArgumentList *list = new FArgumentList; + auto node = head; + do + { + list->Push(ConvertNode(node)); + node = node->SiblingNext; + } while (node != head); + return list; +} \ No newline at end of file diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 74d83f529..2ca00459a 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -5,6 +5,8 @@ struct Baggage; struct FPropertyInfo; class AActor; class FxExpression; +typedef TDeletingArray FArgumentList; + struct ZCC_StructWork { @@ -136,6 +138,10 @@ private: void Error(ZCC_TreeNode *node, const char *msg, ...); void MessageV(ZCC_TreeNode *node, const char *txtcolor, const char *msg, va_list argptr); + FxExpression *ConvertAST(ZCC_TreeNode *ast); + FxExpression *ConvertNode(ZCC_TreeNode *node); + FArgumentList *ConvertNodeList(ZCC_TreeNode *head); + DObject *Outer; PSymbolTable *GlobalTreeNodes; PSymbolTable *OutputSymbols; diff --git a/wadsrc/static/actors/shared/action.txt b/wadsrc/static/actors/shared/action.txt deleted file mode 100644 index fc0e71313..000000000 --- a/wadsrc/static/actors/shared/action.txt +++ /dev/null @@ -1,56 +0,0 @@ - - -//========================================================================== -// -// Ice chunk -// -//========================================================================== - -ACTOR IceChunk -{ - Radius 3 - Height 4 - Mass 5 - Gravity 0.125 - +DROPOFF - +CANNOTPUSH - +FLOORCLIP - +NOTELEPORT - +NOBLOCKMAP - +MOVEWITHSECTOR - - action native A_IceSetTics (); - - States - { - Spawn: - ICEC A 1 - ICEC ABCD 10 A_IceSetTics - Stop - } -} - -//========================================================================== -// -// A chunk of ice that is also a player -// -//========================================================================== - -ACTOR IceChunkHead : PlayerChunk -{ - Radius 3 - Height 4 - Mass 5 - Gravity 0.125 - DamageType Ice - +DROPOFF - +CANNOTPUSH - States - { - Spawn: - ICEC A 0 - ICEC A 10 A_CheckPlayerDone - wait - } -} - diff --git a/wadsrc/static/actors/shared/blood.txt b/wadsrc/static/actors/shared/blood.txt deleted file mode 100644 index ab33fee75..000000000 --- a/wadsrc/static/actors/shared/blood.txt +++ /dev/null @@ -1,69 +0,0 @@ - -// Blood sprite ------------------------------------------------------------ - -ACTOR Blood -{ - Mass 5 - +NOBLOCKMAP - +NOTELEPORT - +ALLOWPARTICLES - States - { - Spawn: - BLUD CBA 8 - Stop - Spray: - SPRY ABCDEF 3 - SPRY G 2 - Stop - } -} - -// Blood splatter ----------------------------------------------------------- - -ACTOR BloodSplatter -{ - Radius 2 - Height 4 - +NOBLOCKMAP - +MISSILE - +DROPOFF - +NOTELEPORT - +CANNOTPUSH - +ALLOWPARTICLES - Mass 5 - States - { - Spawn: - BLUD CBA 8 - Stop - Death: - BLUD A 6 - Stop - } -} - -// Axe Blood ---------------------------------------------------------------- - -ACTOR AxeBlood -{ - Radius 2 - Height 4 - +NOBLOCKMAP - +NOGRAVITY - +DROPOFF - +NOTELEPORT - +CANNOTPUSH - +ALLOWPARTICLES - Mass 5 - States - { - Spawn: - FAXE FGHIJ 3 - Death: - FAXE K 3 - Stop - } -} - - \ No newline at end of file diff --git a/wadsrc/static/actors/shared/botstuff.txt b/wadsrc/static/actors/shared/botstuff.txt deleted file mode 100644 index 4b1992bde..000000000 --- a/wadsrc/static/actors/shared/botstuff.txt +++ /dev/null @@ -1,19 +0,0 @@ - -ACTOR CajunBodyNode -{ - +NOSECTOR - +NOGRAVITY - +INVISIBLE -} - -ACTOR CajunTrace -{ - Speed 12 - Radius 6 - Height 8 - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOGRAVITY - +NOTELEPORT -} diff --git a/wadsrc/static/actors/shared/debris.txt b/wadsrc/static/actors/shared/debris.txt deleted file mode 100644 index 5d14a48fa..000000000 --- a/wadsrc/static/actors/shared/debris.txt +++ /dev/null @@ -1,331 +0,0 @@ - -// Rocks -------------------------------------------------------------------- - -ACTOR Rock1 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK A 20 - Loop - Death: - ROKK A 10 - Stop - } -} - -ACTOR Rock2 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK B 20 - Loop - Death: - ROKK B 10 - Stop - } -} - - -ACTOR Rock3 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK C 20 - Loop - Death: - ROKK C 10 - Stop - } -} - - -// Dirt -------------------------------------------------------------------- - -ACTOR Dirt1 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK D 20 - Loop - Death: - ROKK D 10 - Stop - } -} - -ACTOR Dirt2 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK E 20 - Loop - Death: - ROKK E 10 - Stop - } -} - -ACTOR Dirt3 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK F 20 - Loop - Death: - ROKK F 10 - Stop - } -} - -ACTOR Dirt4 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK G 20 - Loop - Death: - ROKK G 10 - Stop - } -} - -ACTOR Dirt5 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK H 20 - Loop - Death: - ROKK H 10 - Stop - } -} - -ACTOR Dirt6 -{ - +NOBLOCKMAP - +DROPOFF - +MISSILE - +NOTELEPORT - States - { - Spawn: - ROKK I 20 - Loop - Death: - ROKK I 10 - Stop - } -} - -// Stained glass ------------------------------------------------------------ - -ACTOR GlassShard native -{ - Radius 5 - Mass 5 - Projectile - -ACTIVATEPCROSS - -ACTIVATEIMPACT - BounceType "HexenCompat" - BounceFactor 0.3 -} - -ACTOR SGShard1 : GlassShard -{ - States - { - Spawn: - SGSA ABCDE 4 - Loop - Death: - SGSA E 30 - Stop - } -} - -ACTOR SGShard2 : GlassShard -{ - States - { - Spawn: - SGSA FGHIJ 4 - Loop - Death: - SGSA J 30 - Stop - } -} - -ACTOR SGShard3 : GlassShard -{ - States - { - Spawn: - SGSA KLMNO 4 - Loop - Death: - SGSA O 30 - Stop - } -} - -ACTOR SGShard4 : GlassShard -{ - States - { - Spawn: - SGSA PQRST 4 - Loop - Death: - SGSA T 30 - Stop - } -} - -ACTOR SGShard5 : GlassShard -{ - States - { - Spawn: - SGSA UVWXY 4 - Loop - Death: - SGSA Y 30 - Stop - } -} - -ACTOR SGShard6 : GlassShard -{ - States - { - Spawn: - SGSB A 4 - Loop - Death: - SGSB A 30 - Stop - } -} - -ACTOR SGShard7 : GlassShard -{ - States - { - Spawn: - SGSB B 4 - Loop - Death: - SGSB B 30 - Stop - } -} - -ACTOR SGShard8 : GlassShard -{ - States - { - Spawn: - SGSB C 4 - Loop - Death: - SGSB C 30 - Stop - } -} - -ACTOR SGShard9 : GlassShard -{ - States - { - Spawn: - SGSB D 4 - Loop - Death: - SGSB D 30 - Stop - } -} - -ACTOR SGShard0 : GlassShard -{ - States - { - Spawn: - SGSB E 4 - Loop - Death: - SGSB E 30 - Stop - } -} - -ACTOR GlassJunk -{ - +NOCLIP - +NOBLOCKMAP - RenderStyle Translucent - Alpha 0.4 - Health 3 // Number of different shards - States - { - // Are the first three frames used anywhere? - SHAR A 128 - Goto Death - SHAR B 128 - Goto Death - SHAR C 128 - Goto Death - Spawn: - SHAR D 128 - Goto Death - SHAR E 128 - Goto Death - SHAR F 128 - Goto Death - Death: - "----" A 1 A_FadeOut(0.03) - Wait - } -} diff --git a/wadsrc/static/actors/shared/morph.txt b/wadsrc/static/actors/shared/morph.txt deleted file mode 100644 index f5aac48d2..000000000 --- a/wadsrc/static/actors/shared/morph.txt +++ /dev/null @@ -1,15 +0,0 @@ -ACTOR MorphProjectile native -{ - Damage 1 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS -} - -ACTOR MorphedMonster native -{ - Monster - -COUNTKILL - +FLOORCLIP -} - diff --git a/wadsrc/static/actors/shared/sharedmisc.txt b/wadsrc/static/actors/shared/sharedmisc.txt deleted file mode 100644 index fe5ac72d8..000000000 --- a/wadsrc/static/actors/shared/sharedmisc.txt +++ /dev/null @@ -1,178 +0,0 @@ - -// Default actor for unregistered doomednums ------------------------------- - -ACTOR Unknown -{ - Radius 32 - Height 56 - +NOGRAVITY - +NOBLOCKMAP - +DONTSPLASH - States - { - Spawn: - UNKN A -1 - Stop - } -} - -// Route node for monster patrols ------------------------------------------- - -ACTOR PatrolPoint -{ - Radius 8 - Height 8 - Mass 10 - +NOGRAVITY - +NOBLOCKMAP - +DONTSPLASH - RenderStyle None -} - -// A special to execute when a monster reaches a matching patrol point ------ - -ACTOR PatrolSpecial -{ - Radius 8 - Height 8 - Mass 10 - +NOGRAVITY - +NOBLOCKMAP - +DONTSPLASH - RenderStyle None -} - -// Map spot ---------------------------------------------------------------- - -ACTOR MapSpot -{ - +NOBLOCKMAP - +NOSECTOR - +NOGRAVITY - +DONTSPLASH - RenderStyle None - CameraHeight 0 -} - -// same with different editor number for Legacy maps ----------------------- - -ACTOR FS_Mapspot : Mapspot -{ -} - -// Map spot with gravity --------------------------------------------------- - -ACTOR MapSpotGravity : MapSpot -{ - -NOBLOCKMAP - -NOSECTOR - -NOGRAVITY -} - -// Point Pushers ----------------------------------------------------------- - -ACTOR PointPusher -{ - +NOBLOCKMAP - +INVISIBLE - +NOCLIP -} - -ACTOR PointPuller -{ - +NOBLOCKMAP - +INVISIBLE - +NOCLIP -} - -// Bloody gibs ------------------------------------------------------------- - -ACTOR RealGibs -{ - +DROPOFF - +CORPSE - +NOTELEPORT - +DONTGIB - States - { - Spawn: - goto GenericCrush - } -} - -// Gibs that can be placed on a map. --------------------------------------- -// -// These need to be a separate class from the above, in case someone uses -// a deh patch to change the gibs, since ZDoom actually creates a gib actor -// for actors that get crushed instead of changing their state as Doom did. - -ACTOR Gibs : RealGibs -{ - ClearFlags -} - -// Needed for loading Build maps ------------------------------------------- - -ACTOR CustomSprite native -{ - +NOBLOCKMAP - +NOGRAVITY - States - { - Spawn: - TNT1 A -1 - Stop - } -} - -// SwitchableDecoration: Activate and Deactivate change state -------------- - -ACTOR SwitchableDecoration native -{ -} - - -ACTOR SwitchingDecoration : SwitchableDecoration native -{ -} - -// Random spawner ---------------------------------------------------------- - -ACTOR RandomSpawner native -{ - +NOBLOCKMAP - +NOSECTOR - +NOGRAVITY - +THRUACTORS -} - -// Fast projectiles -------------------------------------------------------- - -ACTOR FastProjectile native -{ - Projectile - MissileHeight 0 -} - -// Sector flag setter ------------------------------------------------------ - -ACTOR SectorFlagSetter native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - RenderStyle None -} - -// Marker for sounds ------------------------------------------------------- - -ACTOR SpeakerIcon : Unknown -{ - States - { - Spawn: - SPKR A -1 BRIGHT - Stop - } - Scale 0.125 -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index e921b5508..4fe719c62 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -2,11 +2,11 @@ //#include "actors/shared/inventory.txt" //#include "actors/shared/player.txt" -#include "actors/shared/morph.txt" -#include "actors/shared/botstuff.txt" -#include "actors/shared/sharedmisc.txt" -#include "actors/shared/blood.txt" -#include "actors/shared/debris.txt" +//#include "actors/shared/morph.txt" +//#include "actors/shared/botstuff.txt" +//#include "actors/shared/sharedmisc.txt" +//#include "actors/shared/blood.txt" +//#include "actors/shared/debris.txt" #include "actors/shared/decal.txt" #include "actors/shared/splashes.txt" #include "actors/shared/pickups.txt" @@ -26,7 +26,7 @@ #include "actors/shared/secrettrigger.txt" #include "actors/shared/setcolor.txt" #include "actors/shared/sectoraction.txt" -#include "actors/shared/action.txt" +//#include "actors/shared/action.txt" #include "actors/shared/dog.txt" #include "actors/shared/damagetypes.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index b0d3ec925..9604812aa 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -3,6 +3,12 @@ zscript/actor.txt zscript/shared/inventory.txt zscript/shared/player.txt +zscript/shared/morph.txt +zscript/shared/botstuff.txt +zscript/shared/sharedmisc.txt +zscript/shared/blood.txt +zscript/shared/ice.txt +zscript/shared/debris.txt zscript/shared/specialspot.txt //zscript/test1.txt diff --git a/wadsrc/static/zscript/shared/blood.txt b/wadsrc/static/zscript/shared/blood.txt new file mode 100644 index 000000000..e5f05de05 --- /dev/null +++ b/wadsrc/static/zscript/shared/blood.txt @@ -0,0 +1,78 @@ + +// Blood sprite ------------------------------------------------------------ + +class Blood : Actor +{ + Default + { + Mass 5; + +NOBLOCKMAP + +NOTELEPORT + +ALLOWPARTICLES + } + States + { + Spawn: + BLUD CBA 8; + Stop; + Spray: + SPRY ABCDEF 3; + SPRY G 2; + Stop; + } +} + +// Blood splatter ----------------------------------------------------------- + +class BloodSplatter : Actor +{ + Default + { + Radius 2; + Height 4; + +NOBLOCKMAP + +MISSILE + +DROPOFF + +NOTELEPORT + +CANNOTPUSH + +ALLOWPARTICLES + Mass 5; + } + States + { + Spawn: + BLUD CBA 8; + Stop; + Death: + BLUD A 6; + Stop; + } +} + +// Axe Blood ---------------------------------------------------------------- + +class AxeBlood : Actor +{ + Default + { + Radius 2; + Height 4; + +NOBLOCKMAP + +NOGRAVITY + +DROPOFF + +NOTELEPORT + +CANNOTPUSH + +ALLOWPARTICLES + Mass 5; + } + States + { + Spawn: + FAXE FGHIJ 3; + Death: + FAXE K 3; + Stop; + } +} + + \ No newline at end of file diff --git a/wadsrc/static/zscript/shared/botstuff.txt b/wadsrc/static/zscript/shared/botstuff.txt new file mode 100644 index 000000000..cf671ea8b --- /dev/null +++ b/wadsrc/static/zscript/shared/botstuff.txt @@ -0,0 +1,25 @@ + +class CajunBodyNode : Actor +{ + Default + { + +NOSECTOR + +NOGRAVITY + +INVISIBLE + } +} + +class CajunTrace : Actor +{ + Default + { + Speed 12; + Radius 6; + Height 8; + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOGRAVITY + +NOTELEPORT + } +} diff --git a/wadsrc/static/zscript/shared/debris.txt b/wadsrc/static/zscript/shared/debris.txt new file mode 100644 index 000000000..24eae25be --- /dev/null +++ b/wadsrc/static/zscript/shared/debris.txt @@ -0,0 +1,364 @@ + +// Rocks -------------------------------------------------------------------- + +class Rock1 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK A 20; + Loop; + Death: + ROKK A 10; + Stop; + } +} + +class Rock2 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK B 20; + Loop; + Death: + ROKK B 10; + Stop; + } +} + + +class Rock3 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK C 20; + Loop; + Death: + ROKK C 10; + Stop; + } +} + + +// Dirt -------------------------------------------------------------------- + +class Dirt1 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK D 20; + Loop; + Death: + ROKK D 10; + Stop; + } +} + +class Dirt2 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK E 20; + Loop; + Death: + ROKK E 10; + Stop; + } +} + +class Dirt3 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK F 20; + Loop; + Death: + ROKK F 10; + Stop; + } +} + +class Dirt4 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK G 20; + Loop; + Death: + ROKK G 10; + Stop; + } +} + +class Dirt5 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK H 20; + Loop; + Death: + ROKK H 10; + Stop; + } +} + +class Dirt6 : Actor +{ + Default + { + +NOBLOCKMAP + +DROPOFF + +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ROKK I 20; + Loop; + Death: + ROKK I 10; + Stop; + } +} + +// Stained glass ------------------------------------------------------------ + +class GlassShard : Actor native +{ + Default + { + Radius 5; + Mass 5; + Projectile; + -ACTIVATEPCROSS + -ACTIVATEIMPACT + BounceType "HexenCompat"; + BounceFactor 0.3; + } +} + +class SGShard1 : GlassShard +{ + States + { + Spawn: + SGSA ABCDE 4; + Loop; + Death: + SGSA E 30; + Stop; + } +} + +class SGShard2 : GlassShard +{ + States + { + Spawn: + SGSA FGHIJ 4; + Loop; + Death: + SGSA J 30; + Stop; + } +} + +class SGShard3 : GlassShard +{ + States + { + Spawn: + SGSA KLMNO 4; + Loop; + Death: + SGSA O 30; + Stop; + } +} + +class SGShard4 : GlassShard +{ + States + { + Spawn: + SGSA PQRST 4; + Loop; + Death: + SGSA T 30; + Stop; + } +} + +class SGShard5 : GlassShard +{ + States + { + Spawn: + SGSA UVWXY 4; + Loop; + Death: + SGSA Y 30; + Stop; + } +} + +class SGShard6 : GlassShard +{ + States + { + Spawn: + SGSB A 4; + Loop; + Death: + SGSB A 30; + Stop; + } +} + +class SGShard7 : GlassShard +{ + States + { + Spawn: + SGSB B 4; + Loop; + Death: + SGSB B 30; + Stop; + } +} + +class SGShard8 : GlassShard +{ + States + { + Spawn: + SGSB C 4; + Loop; + Death: + SGSB C 30; + Stop; + } +} + +class SGShard9 : GlassShard +{ + States + { + Spawn: + SGSB D 4; + Loop; + Death: + SGSB D 30; + Stop; + } +} + +class SGShard0 : GlassShard +{ + States + { + Spawn: + SGSB E 4; + Loop; + Death: + SGSB E 30; + Stop; + } +} + +class GlassJunk : Actor +{ + Default + { + +NOCLIP + +NOBLOCKMAP + RenderStyle "Translucent"; + Alpha 0.4; + Health 3; // Number of different shards + } + States + { + // Are the first three frames used anywhere? + SHAR A 128; + Goto Death; + SHAR B 128; + Goto Death; + SHAR C 128; + Goto Death; + Spawn: + SHAR D 128; + Goto Death; + SHAR E 128; + Goto Death; + SHAR F 128; + Goto Death; + Death: + "----" A 1 A_FadeOut(0.03); + Wait; + } +} diff --git a/wadsrc/static/zscript/shared/ice.txt b/wadsrc/static/zscript/shared/ice.txt new file mode 100644 index 000000000..9668466cb --- /dev/null +++ b/wadsrc/static/zscript/shared/ice.txt @@ -0,0 +1,61 @@ + + +//========================================================================== +// +// Ice chunk +// +//========================================================================== + +class IceChunk : Actor +{ + Default + { + Radius 3; + Height 4; + Mass 5; + Gravity 0.125; + +DROPOFF + +CANNOTPUSH + +FLOORCLIP + +NOTELEPORT + +NOBLOCKMAP + +MOVEWITHSECTOR + } + action native void A_IceSetTics (); + + States + { + Spawn: + ICEC A 1; + ICEC ABCD 10 A_IceSetTics; + Stop; + } +} + +//========================================================================== +// +// A chunk of ice that is also a player +// +//========================================================================== + +class IceChunkHead : PlayerChunk +{ + Default + { + Radius 3; + Height 4; + Mass 5; + Gravity 0.125; + DamageType "Ice"; + +DROPOFF + +CANNOTPUSH + } + States + { + Spawn: + ICEC A 0; + ICEC A 10 A_CheckPlayerDone; + wait; + } +} + diff --git a/wadsrc/static/zscript/shared/morph.txt b/wadsrc/static/zscript/shared/morph.txt new file mode 100644 index 000000000..ff58d897b --- /dev/null +++ b/wadsrc/static/zscript/shared/morph.txt @@ -0,0 +1,21 @@ +class MorphProjectile : Actor native +{ + Default + { + Damage 1; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + } +} + +class MorphedMonster : Actor native +{ + Default + { + Monster; + -COUNTKILL + +FLOORCLIP + } +} + diff --git a/wadsrc/static/zscript/shared/sharedmisc.txt b/wadsrc/static/zscript/shared/sharedmisc.txt new file mode 100644 index 000000000..bebf28549 --- /dev/null +++ b/wadsrc/static/zscript/shared/sharedmisc.txt @@ -0,0 +1,220 @@ + +// Default class for unregistered doomednums ------------------------------- + +class Unknown : Actor +{ + Default + { + Radius 32; + Height 56; + +NOGRAVITY + +NOBLOCKMAP + +DONTSPLASH + } + States + { + Spawn: + UNKN A -1; + Stop; + } +} + +// Route node for monster patrols ------------------------------------------- + +class PatrolPoint : Actor +{ + Default + { + Radius 8; + Height 8; + Mass 10; + +NOGRAVITY + +NOBLOCKMAP + +DONTSPLASH + RenderStyle "None"; + } +} + +// A special to execute when a monster reaches a matching patrol point ------ + +class PatrolSpecial : Actor +{ + Default + { + Radius 8; + Height 8; + Mass 10; + +NOGRAVITY + +NOBLOCKMAP + +DONTSPLASH + RenderStyle "None"; + } +} + +// Map spot ---------------------------------------------------------------- + +class MapSpot : Actor +{ + Default + { + +NOBLOCKMAP + +NOSECTOR + +NOGRAVITY + +DONTSPLASH + RenderStyle "None"; + CameraHeight 0; + } +} + +// same with different editor number for Legacy maps ----------------------- + +class FS_Mapspot : Mapspot +{ +} + +// Map spot with gravity --------------------------------------------------- + +class MapSpotGravity : MapSpot +{ + Default + { + -NOBLOCKMAP + -NOSECTOR + -NOGRAVITY + } +} + +// Point Pushers ----------------------------------------------------------- + +class PointPusher : Actor +{ + Default + { + +NOBLOCKMAP + +INVISIBLE + +NOCLIP + } +} + +class PointPuller : Actor +{ + Default + { + +NOBLOCKMAP + +INVISIBLE + +NOCLIP + } +} + +// Bloody gibs ------------------------------------------------------------- + +class RealGibs : Actor +{ + Default + { + +DROPOFF + +CORPSE + +NOTELEPORT + +DONTGIB + } + States + { + Spawn: + goto GenericCrush; + } +} + +// Gibs that can be placed on a map. --------------------------------------- +// +// These need to be a separate class from the above, in case someone uses +// a deh patch to change the gibs, since ZDoom actually creates a gib class +// for actors that get crushed instead of changing their state as Doom did. + +class Gibs : RealGibs +{ + Default + { + ClearFlags; + } +} + +// Needed for loading Build maps ------------------------------------------- + +class CustomSprite : Actor native +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + } + States + { + Spawn: + TNT1 A -1; + Stop; + } +} + +// SwitchableDecoration: Activate and Deactivate change state -------------- + +class SwitchableDecoration : Actor native +{ +} + + +class SwitchingDecoration : SwitchableDecoration native +{ +} + +// Random spawner ---------------------------------------------------------- + +class RandomSpawner : Actor native +{ + Default + { + +NOBLOCKMAP + +NOSECTOR + +NOGRAVITY + +THRUACTORS + } +} + +// Fast projectiles -------------------------------------------------------- + +class FastProjectile : Actor native +{ + Default + { + Projectile; + MissileHeight 0; + } +} + +// Sector flag setter ------------------------------------------------------ + +class SectorFlagSetter : Actor native +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + RenderStyle "None"; + } +} + +// Marker for sounds : Actor ------------------------------------------------------- + +class SpeakerIcon : Unknown +{ + States + { + Spawn: + SPKR A -1 BRIGHT; + Stop; + } + Default + { + Scale 0.125; + } +} From 905e44713faa63e3efd4f22eb837851f5081c8d4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 09:32:45 +0200 Subject: [PATCH 028/255] - deprecated A_SetUserVar family for ZSCRIPT due to its muddled semantics. Better use direct variable access which is a lot safer and also provides better error checking. --- wadsrc/static/zscript/actor.txt | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 9352028b3..4c09e8664 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -297,10 +297,10 @@ class Actor : Thinker native native void A_ScaleVelocity(float scale, int ptr = AAPTR_DEFAULT); action native void A_ChangeVelocity(float x = 0, float y = 0, float z = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetArg(int pos, int value); - native void A_SetUserVar(name varname, int value); - native void A_SetUserArray(name varname, int index, int value); - native void A_SetUserVarFloat(name varname, float value); - native void A_SetUserArrayFloat(name varname, int index, float value); + deprecated native void A_SetUserVar(name varname, int value); + deprecated native void A_SetUserArray(name varname, int index, int value); + deprecated native void A_SetUserVarFloat(name varname, float value); + deprecated native void A_SetUserArrayFloat(name varname, int index, float value); native void A_SetSpecial(int spec, int arg0 = 0, int arg1 = 0, int arg2 = 0, int arg3 = 0, int arg4 = 0); native void A_Quake(int intensity, int duration, int damrad, int tremrad, sound sfx = "world/quake"); native void A_QuakeEx(int intensityX, int intensityY, int intensityZ, int duration, int damrad, int tremrad, sound sfx = "world/quake", int flags = 0, float mulWaveX = 1, float mulWaveY = 1, float mulWaveZ = 1, int falloff = 0, int highpoint = 0, float rollIntensity = 0, float rollWave = 0); From 9e2830a3db663b83d47dcbc421de217cf52bbd78 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 10:46:15 +0200 Subject: [PATCH 029/255] - converted the rest of actors/shared. - moved damagetype definitions to MAPINFO. These were in DECORATE which is not correct. The old code is left for compatibility. --- src/g_level.h | 1 + src/g_mapinfo.cpp | 12 + src/info.cpp | 40 +++ src/p_states.cpp | 5 + wadsrc/static/actors/shared/bridge.txt | 105 ------- wadsrc/static/actors/shared/camera.txt | 23 -- wadsrc/static/actors/shared/damagetypes.txt | 4 - wadsrc/static/actors/shared/decal.txt | 3 - wadsrc/static/actors/shared/dog.txt | 44 --- wadsrc/static/actors/shared/fountain.txt | 42 --- wadsrc/static/actors/shared/hatetarget.txt | 19 -- wadsrc/static/actors/shared/mapmarker.txt | 15 - wadsrc/static/actors/shared/movingcamera.txt | 34 --- wadsrc/static/actors/shared/secrettrigger.txt | 9 - wadsrc/static/actors/shared/setcolor.txt | 16 - wadsrc/static/actors/shared/skies.txt | 40 --- .../static/actors/shared/soundenvironment.txt | 9 - wadsrc/static/actors/shared/soundsequence.txt | 79 ----- wadsrc/static/actors/shared/spark.txt | 8 - wadsrc/static/actors/shared/splashes.txt | 237 --------------- wadsrc/static/actors/shared/teleport.txt | 42 --- wadsrc/static/actors/shared/waterzone.txt | 7 - wadsrc/static/decorate.txt | 32 -- wadsrc/static/mapinfo/common.txt | 5 + wadsrc/static/zscript.txt | 20 ++ wadsrc/static/zscript/shared/bridge.txt | 129 +++++++++ wadsrc/static/zscript/shared/camera.txt | 29 ++ wadsrc/static/zscript/shared/decal.txt | 3 + wadsrc/static/zscript/shared/dog.txt | 47 +++ wadsrc/static/zscript/shared/fountain.txt | 66 +++++ wadsrc/static/zscript/shared/hatetarget.txt | 22 ++ wadsrc/static/zscript/shared/mapmarker.txt | 18 ++ wadsrc/static/zscript/shared/movingcamera.txt | 46 +++ .../{actors => zscript}/shared/pickups.txt | 24 +- .../static/zscript/shared/secrettrigger.txt | 12 + .../shared/sectoraction.txt | 37 +-- wadsrc/static/zscript/shared/setcolor.txt | 22 ++ wadsrc/static/zscript/shared/skies.txt | 49 ++++ .../zscript/shared/soundenvironment.txt | 12 + .../static/zscript/shared/soundsequence.txt | 121 ++++++++ wadsrc/static/zscript/shared/spark.txt | 11 + wadsrc/static/zscript/shared/splashes.txt | 273 ++++++++++++++++++ wadsrc/static/zscript/shared/teleport.txt | 54 ++++ wadsrc/static/zscript/shared/waterzone.txt | 10 + 44 files changed, 1042 insertions(+), 794 deletions(-) delete mode 100644 wadsrc/static/actors/shared/bridge.txt delete mode 100644 wadsrc/static/actors/shared/camera.txt delete mode 100644 wadsrc/static/actors/shared/damagetypes.txt delete mode 100644 wadsrc/static/actors/shared/decal.txt delete mode 100644 wadsrc/static/actors/shared/dog.txt delete mode 100644 wadsrc/static/actors/shared/fountain.txt delete mode 100644 wadsrc/static/actors/shared/hatetarget.txt delete mode 100644 wadsrc/static/actors/shared/mapmarker.txt delete mode 100644 wadsrc/static/actors/shared/movingcamera.txt delete mode 100644 wadsrc/static/actors/shared/secrettrigger.txt delete mode 100644 wadsrc/static/actors/shared/setcolor.txt delete mode 100644 wadsrc/static/actors/shared/skies.txt delete mode 100644 wadsrc/static/actors/shared/soundenvironment.txt delete mode 100644 wadsrc/static/actors/shared/soundsequence.txt delete mode 100644 wadsrc/static/actors/shared/spark.txt delete mode 100644 wadsrc/static/actors/shared/splashes.txt delete mode 100644 wadsrc/static/actors/shared/teleport.txt delete mode 100644 wadsrc/static/actors/shared/waterzone.txt create mode 100644 wadsrc/static/zscript/shared/bridge.txt create mode 100644 wadsrc/static/zscript/shared/camera.txt create mode 100644 wadsrc/static/zscript/shared/decal.txt create mode 100644 wadsrc/static/zscript/shared/dog.txt create mode 100644 wadsrc/static/zscript/shared/fountain.txt create mode 100644 wadsrc/static/zscript/shared/hatetarget.txt create mode 100644 wadsrc/static/zscript/shared/mapmarker.txt create mode 100644 wadsrc/static/zscript/shared/movingcamera.txt rename wadsrc/static/{actors => zscript}/shared/pickups.txt (65%) create mode 100644 wadsrc/static/zscript/shared/secrettrigger.txt rename wadsrc/static/{actors => zscript}/shared/sectoraction.txt (61%) create mode 100644 wadsrc/static/zscript/shared/setcolor.txt create mode 100644 wadsrc/static/zscript/shared/skies.txt create mode 100644 wadsrc/static/zscript/shared/soundenvironment.txt create mode 100644 wadsrc/static/zscript/shared/soundsequence.txt create mode 100644 wadsrc/static/zscript/shared/spark.txt create mode 100644 wadsrc/static/zscript/shared/splashes.txt create mode 100644 wadsrc/static/zscript/shared/teleport.txt create mode 100644 wadsrc/static/zscript/shared/waterzone.txt diff --git a/src/g_level.h b/src/g_level.h index 9f8c5efd5..2b0de7b68 100644 --- a/src/g_level.h +++ b/src/g_level.h @@ -110,6 +110,7 @@ struct FMapInfoParser void ParseAMColors(bool); FName CheckEndSequence(); FName ParseEndGame(); + void ParseDamageDefinition(); }; #define DEFINE_MAP_OPTION(name, old) \ diff --git a/src/g_mapinfo.cpp b/src/g_mapinfo.cpp index bc0470474..814a36435 100644 --- a/src/g_mapinfo.cpp +++ b/src/g_mapinfo.cpp @@ -1873,6 +1873,18 @@ void FMapInfoParser::ParseMapInfo (int lump, level_info_t &gamedefaults, level_i sc.ScriptError("doomednums definitions not supported with old MAPINFO syntax"); } } + else if (sc.Compare("damagetype")) + { + if (format_type != FMT_Old) + { + format_type = FMT_New; + ParseDamageDefinition(); + } + else + { + sc.ScriptError("damagetype definitions not supported with old MAPINFO syntax"); + } + } else if (sc.Compare("spawnnums")) { if (format_type != FMT_Old) diff --git a/src/info.cpp b/src/info.cpp index 8089e065b..44f485e6c 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -817,3 +817,43 @@ int DamageTypeDefinition::ApplyMobjDamageFactor(int damage, FName type, DmgFacto double factor = GetMobjDamageFactor(type, factors); return int(damage * factor); } + +//========================================================================== +// +// Reads a damage definition +// +//========================================================================== + +void FMapInfoParser::ParseDamageDefinition() +{ + sc.MustGetString(); + FName damageType = sc.String; + + DamageTypeDefinition dtd; + + ParseOpenBrace(); + while (sc.MustGetAnyToken(), sc.TokenType != '}') + { + if (sc.Compare("FACTOR")) + { + sc.MustGetStringName("="); + sc.MustGetFloat(); + dtd.DefaultFactor = sc.Float; + if (dtd.DefaultFactor == 0) dtd.ReplaceFactor = true; + } + else if (sc.Compare("REPLACEFACTOR")) + { + dtd.ReplaceFactor = true; + } + else if (sc.Compare("NOARMOR")) + { + dtd.NoArmor = true; + } + else + { + sc.ScriptError("Unexpected data (%s) in damagetype definition.", sc.String); + } + } + + dtd.Apply(damageType); +} diff --git a/src/p_states.cpp b/src/p_states.cpp index 007f7f5ce..00b011e3d 100644 --- a/src/p_states.cpp +++ b/src/p_states.cpp @@ -433,6 +433,11 @@ FStateLabels *FStateDefinitions::CreateStateLabelList(TArray & sta void FStateDefinitions::InstallStates(PClassActor *info, AActor *defaults) { + if (defaults == nullptr) + { + I_Error("Called InstallStates without actor defaults in %s", info->TypeName.GetChars()); + } + // First ensure we have a valid spawn state. FState *state = FindState("Spawn"); diff --git a/wadsrc/static/actors/shared/bridge.txt b/wadsrc/static/actors/shared/bridge.txt deleted file mode 100644 index 97d4c22ad..000000000 --- a/wadsrc/static/actors/shared/bridge.txt +++ /dev/null @@ -1,105 +0,0 @@ -// Bridge ball ------------------------------------------------------------- - -ACTOR BridgeBall -{ - +NOBLOCKMAP - +NOTELEPORT - +NOGRAVITY - - action native A_BridgeOrbit(); - - States - { - Spawn: - TLGL A 2 Bright - TLGL A 1 Bright A_BridgeOrbit - Wait - } - -} - -// The bridge itself ------------------------------------------------------- - -ACTOR CustomBridge native -{ - +SOLID - +NOGRAVITY - +NOLIFTDROP - +ACTLIKEBRIDGE - Radius 32 - Height 2 - RenderStyle None - - action native A_BridgeInit(class balltype = "BridgeBall"); - - states - { - Spawn: - TLGL ABCDE 3 Bright - Loop - See: - TLGL A 2 - TLGL A 2 A_BridgeInit - TLGL A -1 - Stop - Death: - TLGL A 2 - TLGL A 300 - Stop - } -} - -// The Hexen bridge ------------------------------------------------------- - -ACTOR Bridge : CustomBridge -{ - RenderStyle None - Args 32, 2, 3, 0 -} - -// The ZDoom bridge ------------------------------------------------------- - -ACTOR ZBridge : CustomBridge -{ - Args 36, 4, 0, 0 -} - - -// Invisible bridge -------------------------------------------------------- - -ACTOR InvisibleBridge native -{ - RenderStyle None - Radius 32 - Height 4 - +SOLID - +NOGRAVITY - +NOLIFTDROP - +ACTLIKEBRIDGE - States - { - Spawn: - TNT1 A -1 - Stop - } -} - -// And some invisible bridges from Skull Tag ------------------------------- - -ACTOR InvisibleBridge32 : InvisibleBridge -{ - Radius 32 - Height 8 -} - -ACTOR InvisibleBridge16 : InvisibleBridge -{ - Radius 16 - Height 8 -} - -ACTOR InvisibleBridge8 : InvisibleBridge -{ - Radius 8 - Height 8 -} diff --git a/wadsrc/static/actors/shared/camera.txt b/wadsrc/static/actors/shared/camera.txt deleted file mode 100644 index 46816f9ea..000000000 --- a/wadsrc/static/actors/shared/camera.txt +++ /dev/null @@ -1,23 +0,0 @@ -ACTOR DoomBuilderCamera -{ - States - { - Spawn: - TNT1 A 1 - Stop - } -} - - -ACTOR SecurityCamera native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - RenderStyle None - CameraHeight 0 -} - -ACTOR AimingCamera : SecurityCamera native -{ -} diff --git a/wadsrc/static/actors/shared/damagetypes.txt b/wadsrc/static/actors/shared/damagetypes.txt deleted file mode 100644 index 9e5f1e254..000000000 --- a/wadsrc/static/actors/shared/damagetypes.txt +++ /dev/null @@ -1,4 +0,0 @@ -damagetype Drowning -{ - NoArmor -} diff --git a/wadsrc/static/actors/shared/decal.txt b/wadsrc/static/actors/shared/decal.txt deleted file mode 100644 index 25e7062c8..000000000 --- a/wadsrc/static/actors/shared/decal.txt +++ /dev/null @@ -1,3 +0,0 @@ -ACTOR Decal native -{ -} diff --git a/wadsrc/static/actors/shared/dog.txt b/wadsrc/static/actors/shared/dog.txt deleted file mode 100644 index 1004fba20..000000000 --- a/wadsrc/static/actors/shared/dog.txt +++ /dev/null @@ -1,44 +0,0 @@ -ACTOR MBFHelperDog -{ - Health 500 - Speed 10 - PainChance 180 - Radius 12 - Height 28 - Mass 100 - Monster - +JUMPDOWN - ActiveSound "dog/active" - AttackSound "dog/attack" - DeathSound "dog/death" - PainSound "dog/pain" - SeeSound "dog/sight" - Obituary "$OB_DOG" - States - { - Spawn: - DOGS AB 10 A_Look - Loop - See: - DOGS AABBCCDD 2 A_Chase - Loop - Melee: - DOGS EF 8 A_FaceTarget - DOGS G 8 A_SargAttack - Goto See - Pain: - DOGS H 2 - DOGS H 2 A_Pain - Goto See - Death: - DOGS I 8 - DOGS J 8 A_Scream - DOGS K 4 - DOGS L 4 A_Fall - DOGS M 4 - DOGS N -1 - Raise: - DOGS NMLKJI 5 - Goto See - } -} diff --git a/wadsrc/static/actors/shared/fountain.txt b/wadsrc/static/actors/shared/fountain.txt deleted file mode 100644 index d9c31e88e..000000000 --- a/wadsrc/static/actors/shared/fountain.txt +++ /dev/null @@ -1,42 +0,0 @@ -ACTOR ParticleFountain native -{ - Height 0 - +NOBLOCKMAP - +NOGRAVITY - +INVISIBLE -} - -ACTOR RedParticleFountain : ParticleFountain -{ - Health 1 -} - -ACTOR GreenParticleFountain : ParticleFountain -{ - Health 2 -} - -ACTOR BlueParticleFountain : ParticleFountain -{ - Health 3 -} - -ACTOR YellowParticleFountain : ParticleFountain -{ - Health 4 -} - -ACTOR PurpleParticleFountain : ParticleFountain -{ - Health 5 -} - -ACTOR BlackParticleFountain : ParticleFountain -{ - Health 6 -} - -ACTOR WhiteParticleFountain : ParticleFountain -{ - Health 7 -} diff --git a/wadsrc/static/actors/shared/hatetarget.txt b/wadsrc/static/actors/shared/hatetarget.txt deleted file mode 100644 index 75442c65c..000000000 --- a/wadsrc/static/actors/shared/hatetarget.txt +++ /dev/null @@ -1,19 +0,0 @@ - - -// Hate Target -------------------------------------------------------------- - -ACTOR HateTarget native -{ - Radius 20 - Height 56 - +SHOOTABLE - +NOGRAVITY - +NOBLOOD - +DONTSPLASH - Mass 0x7fffffff - States - { - Spawn: - TNT1 A -1 - } -} \ No newline at end of file diff --git a/wadsrc/static/actors/shared/mapmarker.txt b/wadsrc/static/actors/shared/mapmarker.txt deleted file mode 100644 index 9c5e36b44..000000000 --- a/wadsrc/static/actors/shared/mapmarker.txt +++ /dev/null @@ -1,15 +0,0 @@ - -ACTOR MapMarker native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - +INVISIBLE - Scale 0.5 - States - { - Spawn: - AMRK A -1 - Stop - } -} \ No newline at end of file diff --git a/wadsrc/static/actors/shared/movingcamera.txt b/wadsrc/static/actors/shared/movingcamera.txt deleted file mode 100644 index 4ba229154..000000000 --- a/wadsrc/static/actors/shared/movingcamera.txt +++ /dev/null @@ -1,34 +0,0 @@ -ACTOR InterpolationPoint native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - RenderStyle None -} - -ACTOR InterpolationSpecial native -{ - +NOBLOCKMAP - +NOSECTOR - +NOGRAVITY - +DONTSPLASH -} - -ACTOR PathFollower native -{ - +NOBLOCKMAP - +NOSECTOR - +NOGRAVITY - +DONTSPLASH -} - -ACTOR ActorMover : PathFollower native -{ -} - -ACTOR MovingCamera : PathFollower native -{ - CameraHeight 0 -} - - diff --git a/wadsrc/static/actors/shared/secrettrigger.txt b/wadsrc/static/actors/shared/secrettrigger.txt deleted file mode 100644 index 8db323993..000000000 --- a/wadsrc/static/actors/shared/secrettrigger.txt +++ /dev/null @@ -1,9 +0,0 @@ - -ACTOR SecretTrigger native -{ - +NOBLOCKMAP - +NOSECTOR - +NOGRAVITY - +DONTSPLASH -} - diff --git a/wadsrc/static/actors/shared/setcolor.txt b/wadsrc/static/actors/shared/setcolor.txt deleted file mode 100644 index 136b0bbf4..000000000 --- a/wadsrc/static/actors/shared/setcolor.txt +++ /dev/null @@ -1,16 +0,0 @@ -ACTOR ColorSetter native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - RenderStyle None -} - - -ACTOR FadeSetter native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - RenderStyle None -} diff --git a/wadsrc/static/actors/shared/skies.txt b/wadsrc/static/actors/shared/skies.txt deleted file mode 100644 index 89f742573..000000000 --- a/wadsrc/static/actors/shared/skies.txt +++ /dev/null @@ -1,40 +0,0 @@ -ACTOR SkyViewpoint native -{ - +NOSECTOR - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH -} - -ACTOR SkyPicker native -{ - +NOSECTOR - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH -} - -Actor SkyCamCompat : SkyViewpoint native -{ -} - -ACTOR StackPoint : SkyViewpoint native -{ -} - -ACTOR UpperStackLookOnly : StackPoint -{ -} - -ACTOR LowerStackLookOnly : StackPoint -{ -} - - -ACTOR SectorSilencer native -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - RenderStyle None -} diff --git a/wadsrc/static/actors/shared/soundenvironment.txt b/wadsrc/static/actors/shared/soundenvironment.txt deleted file mode 100644 index 822a723f8..000000000 --- a/wadsrc/static/actors/shared/soundenvironment.txt +++ /dev/null @@ -1,9 +0,0 @@ - -ACTOR SoundEnvironment native -{ - +NOSECTOR - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH -} - diff --git a/wadsrc/static/actors/shared/soundsequence.txt b/wadsrc/static/actors/shared/soundsequence.txt deleted file mode 100644 index 5fe34b326..000000000 --- a/wadsrc/static/actors/shared/soundsequence.txt +++ /dev/null @@ -1,79 +0,0 @@ - -ACTOR AmbientSound native -{ - +NOBLOCKMAP - +NOSECTOR - +DONTSPLASH -} - -ACTOR AmbientSoundNoGravity : AmbientSound -{ - +NOGRAVITY -} - -ACTOR SoundSequenceSlot native -{ - +NOSECTOR - +NOBLOCKMAP - +DONTSPLASH -} - -ACTOR SoundSequence native -{ - +NOSECTOR - +NOBLOCKMAP - +DONTSPLASH -} - -// Heretic Sound sequences ----------------------------------------------------------- - -ACTOR HereticSoundSequence1 : SoundSequence -{ - Args 0 -} - -ACTOR HereticSoundSequence2 : SoundSequence -{ - Args 1 -} - -ACTOR HereticSoundSequence3 : SoundSequence -{ - Args 2 -} - -ACTOR HereticSoundSequence4 : SoundSequence -{ - Args 3 -} - -ACTOR HereticSoundSequence5 : SoundSequence -{ - Args 4 -} - -ACTOR HereticSoundSequence6 : SoundSequence -{ - Args 5 -} - -ACTOR HereticSoundSequence7 : SoundSequence -{ - Args 6 -} - -ACTOR HereticSoundSequence8 : SoundSequence -{ - Args 7 -} - -ACTOR HereticSoundSequence9 : SoundSequence -{ - Args 8 -} - -ACTOR HereticSoundSequence10 : SoundSequence -{ - Args 9 -} - diff --git a/wadsrc/static/actors/shared/spark.txt b/wadsrc/static/actors/shared/spark.txt deleted file mode 100644 index 240d98152..000000000 --- a/wadsrc/static/actors/shared/spark.txt +++ /dev/null @@ -1,8 +0,0 @@ - -ACTOR Spark native -{ - +NOSECTOR - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH -} \ No newline at end of file diff --git a/wadsrc/static/actors/shared/splashes.txt b/wadsrc/static/actors/shared/splashes.txt deleted file mode 100644 index 4c71b4565..000000000 --- a/wadsrc/static/actors/shared/splashes.txt +++ /dev/null @@ -1,237 +0,0 @@ - -// Water -------------------------------------------------------------------- - -ACTOR WaterSplash -{ - Radius 2 - Height 4 - +NOBLOCKMAP - +MISSILE - +DROPOFF - +NOTELEPORT - +LOWGRAVITY - +CANNOTPUSH - +DONTSPLASH - +DONTBLAST - States - { - Spawn: - SPSH ABC 8 - SPSH D 16 - Stop - Death: - SPSH D 10 - Stop - } -} - - -ACTOR WaterSplashBase -{ - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - +DONTBLAST - States - { - Spawn: - SPSH EFGHIJK 5 - Stop - } -} - -// Lava --------------------------------------------------------------------- - -ACTOR LavaSplash -{ - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - +DONTBLAST - States - { - Spawn: - LVAS ABCDEF 5 Bright - Stop - } -} - -ACTOR LavaSmoke -{ - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - RenderStyle Translucent - DefaultAlpha - States - { - Spawn: - LVAS GHIJK 5 Bright - Stop - } -} - -// Sludge ------------------------------------------------------------------- - -ACTOR SludgeChunk -{ - Radius 2 - Height 4 - +NOBLOCKMAP - +MISSILE - +DROPOFF - +NOTELEPORT - +LOWGRAVITY - +CANNOTPUSH - +DONTSPLASH - States - { - Spawn: - SLDG ABCD 8 - Stop - Death: - SLDG D 6 - Stop - } -} - -ACTOR SludgeSplash -{ - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - States - { - Spawn: - SLDG EFGH 6 - Stop - } -} - -/* - * These next four classes are not used by me anywhere. - * They are for people who want to use them in a TERRAIN lump. - */ - -// Blood (water with a different sprite) ------------------------------------ - -ACTOR BloodSplash -{ - Radius 2 - Height 4 - +NOBLOCKMAP - +MISSILE - +DROPOFF - +NOTELEPORT - +LOWGRAVITY - +CANNOTPUSH - +DONTSPLASH - +DONTBLAST - States - { - Spawn: - BSPH ABC 8 - BSPH D 16 - Stop - Death: - BSPH D 10 - Stop - } -} - - -ACTOR BloodSplashBase -{ - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - +DONTBLAST - States - { - Spawn: - BSPH EFGHIJK 5 - Stop - } -} - -// Slime (sludge with a different sprite) ----------------------------------- - -ACTOR SlimeChunk -{ - Radius 2 - Height 4 - +NOBLOCKMAP - +MISSILE - +DROPOFF - +NOTELEPORT - +LOWGRAVITY - +CANNOTPUSH - +DONTSPLASH - States - { - Spawn: - SLIM ABCD 8 - Stop - Death: - SLIM D 6 - Stop - } -} - -ACTOR SlimeSplash -{ - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - States - { - Spawn: - SLIM EFGH 6 - Stop - } -} - -// Smoke trail for rocket ----------------------------------- - -ACTOR RocketSmokeTrail -{ - RenderStyle Translucent - Alpha 0.4 - VSpeed 1 - +NOBLOCKMAP - +NOCLIP - +NOGRAVITY - +DONTSPLASH - +NOTELEPORT - States - { - Spawn: - RSMK ABCDE 5 - Stop - } -} - -ACTOR GrenadeSmokeTrail -{ - RenderStyle Translucent - Alpha 0.4 - +NOBLOCKMAP - +NOCLIP - +DONTSPLASH - +NOTELEPORT - Gravity 0.1 - VSpeed 0.5 - Scale 0.6 - States - { - Spawn: - RSMK ABCDE 4 - Stop - } -} diff --git a/wadsrc/static/actors/shared/teleport.txt b/wadsrc/static/actors/shared/teleport.txt deleted file mode 100644 index 0bce22ea3..000000000 --- a/wadsrc/static/actors/shared/teleport.txt +++ /dev/null @@ -1,42 +0,0 @@ - -ACTOR TeleportFog native -{ - +NOBLOCKMAP - +NOTELEPORT - +NOGRAVITY - RenderStyle Add - States - { - Spawn: - TFOG ABABCDEFGHIJ 6 Bright - Stop - - Raven: - TELE ABCDEFGHGFEDC 6 Bright - Stop - - Strife: - TFOG ABCDEFEDCB 6 Bright - Stop - } -} - - - -ACTOR TeleportDest -{ - +NOBLOCKMAP - +NOSECTOR - +DONTSPLASH -} - -ACTOR TeleportDest2 : TeleportDest -{ - +NOGRAVITY -} - -ACTOR TeleportDest3 : TeleportDest2 -{ - -NOGRAVITY -} - diff --git a/wadsrc/static/actors/shared/waterzone.txt b/wadsrc/static/actors/shared/waterzone.txt deleted file mode 100644 index b6cf4bd29..000000000 --- a/wadsrc/static/actors/shared/waterzone.txt +++ /dev/null @@ -1,7 +0,0 @@ -ACTOR WaterZone native -{ - +NOSECTOR - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 4fe719c62..079d8fa6a 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,35 +1,3 @@ -//#include "actors/actor.txt" - -//#include "actors/shared/inventory.txt" -//#include "actors/shared/player.txt" -//#include "actors/shared/morph.txt" -//#include "actors/shared/botstuff.txt" -//#include "actors/shared/sharedmisc.txt" -//#include "actors/shared/blood.txt" -//#include "actors/shared/debris.txt" -#include "actors/shared/decal.txt" -#include "actors/shared/splashes.txt" -#include "actors/shared/pickups.txt" -#include "actors/shared/fountain.txt" -#include "actors/shared/spark.txt" -#include "actors/shared/soundsequence.txt" -#include "actors/shared/soundenvironment.txt" -#include "actors/shared/bridge.txt" -//#include "actors/shared/specialspot.txt" -#include "actors/shared/teleport.txt" -#include "actors/shared/camera.txt" -#include "actors/shared/movingcamera.txt" -#include "actors/shared/mapmarker.txt" -#include "actors/shared/waterzone.txt" -#include "actors/shared/skies.txt" -#include "actors/shared/hatetarget.txt" -#include "actors/shared/secrettrigger.txt" -#include "actors/shared/setcolor.txt" -#include "actors/shared/sectoraction.txt" -//#include "actors/shared/action.txt" -#include "actors/shared/dog.txt" -#include "actors/shared/damagetypes.txt" - #include "actors/doom/doomplayer.txt" #include "actors/doom/possessed.txt" #include "actors/doom/doomimp.txt" diff --git a/wadsrc/static/mapinfo/common.txt b/wadsrc/static/mapinfo/common.txt index 347f424f9..986b8e48c 100644 --- a/wadsrc/static/mapinfo/common.txt +++ b/wadsrc/static/mapinfo/common.txt @@ -585,3 +585,8 @@ Intermission Inter_Chess Position = 5, 135 } } + +DamageType Drowning +{ + NoArmor +} diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 9604812aa..9ba69ceef 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -10,6 +10,26 @@ zscript/shared/blood.txt zscript/shared/ice.txt zscript/shared/debris.txt zscript/shared/specialspot.txt +zscript/shared/decal.txt +zscript/shared/splashes.txt +zscript/shared/pickups.txt +zscript/shared/fountain.txt +zscript/shared/spark.txt +zscript/shared/soundsequence.txt +zscript/shared/soundenvironment.txt +zscript/shared/bridge.txt +zscript/shared/teleport.txt +zscript/shared/camera.txt +zscript/shared/movingcamera.txt +zscript/shared/mapmarker.txt +zscript/shared/waterzone.txt +zscript/shared/skies.txt +zscript/shared/hatetarget.txt +zscript/shared/secrettrigger.txt +zscript/shared/setcolor.txt +zscript/shared/sectoraction.txt +zscript/shared/dog.txt + //zscript/test1.txt diff --git a/wadsrc/static/zscript/shared/bridge.txt b/wadsrc/static/zscript/shared/bridge.txt new file mode 100644 index 000000000..08c788f8e --- /dev/null +++ b/wadsrc/static/zscript/shared/bridge.txt @@ -0,0 +1,129 @@ +// Bridge ball ------------------------------------------------------------- + +class BridgeBall : Actor +{ + default + { + +NOBLOCKMAP + +NOTELEPORT + +NOGRAVITY + } + + action native void A_BridgeOrbit(); + + States + { + Spawn: + TLGL A 2 Bright; + TLGL A 1 Bright A_BridgeOrbit; + Wait; + } + +} + +// The bridge itself ------------------------------------------------------- + +class CustomBridge : Actor native +{ + default + { + +SOLID + +NOGRAVITY + +NOLIFTDROP + +ACTLIKEBRIDGE + Radius 32; + Height 2; + RenderStyle "None"; + } + + action native void A_BridgeInit(class balltype = "BridgeBall"); + + states + { + Spawn: + TLGL ABCDE 3 Bright; + Loop; + See: + TLGL A 2; + TLGL A 2 A_BridgeInit; + TLGL A -1; + Stop; + Death: + TLGL A 2; + TLGL A 300; + Stop; + } +} + +// The Hexen bridge ------------------------------------------------------- + +class Bridge : CustomBridge +{ + default + { + RenderStyle "None"; + Args 32, 2, 3, 0; + } +} + +// The ZDoom bridge ------------------------------------------------------- + +class ZBridge : CustomBridge +{ + default + { + Args 36, 4, 0, 0; + } +} + + +// Invisible bridge -------------------------------------------------------- + +class InvisibleBridge : Actor native +{ + default + { + RenderStyle "None"; + Radius 32; + Height 4; + +SOLID + +NOGRAVITY + +NOLIFTDROP + +ACTLIKEBRIDGE + } + States + { + Spawn: + TNT1 A -1; + Stop; + } +} + +// And some invisible bridges from Skull Tag ------------------------------- + +class InvisibleBridge32 : InvisibleBridge +{ + default + { + Radius 32; + Height 8; + } +} + +class InvisibleBridge16 : InvisibleBridge +{ + default + { + Radius 16; + Height 8; + } +} + +class InvisibleBridge8 : InvisibleBridge +{ + default + { + Radius 8; + Height 8; + } +} diff --git a/wadsrc/static/zscript/shared/camera.txt b/wadsrc/static/zscript/shared/camera.txt new file mode 100644 index 000000000..9420c98d5 --- /dev/null +++ b/wadsrc/static/zscript/shared/camera.txt @@ -0,0 +1,29 @@ +class DoomBuilderCamera : Actor +{ + States + { + Spawn: + TNT1 A 1; + Stop; + } +} + + +class SecurityCamera : Actor native +{ + default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + } + default + { + RenderStyle "None"; + CameraHeight 0; + } +} + +class AimingCamera : SecurityCamera native +{ +} diff --git a/wadsrc/static/zscript/shared/decal.txt b/wadsrc/static/zscript/shared/decal.txt new file mode 100644 index 000000000..0614f6235 --- /dev/null +++ b/wadsrc/static/zscript/shared/decal.txt @@ -0,0 +1,3 @@ +class Decal : Actor native +{ +} diff --git a/wadsrc/static/zscript/shared/dog.txt b/wadsrc/static/zscript/shared/dog.txt new file mode 100644 index 000000000..663dd6b98 --- /dev/null +++ b/wadsrc/static/zscript/shared/dog.txt @@ -0,0 +1,47 @@ +class MBFHelperDog : Actor +{ + default + { + Health 500; + Speed 10; + PainChance 180; + Radius 12; + Height 28; + Mass 100; + Monster; + +JUMPDOWN + ActiveSound "dog/active"; + AttackSound "dog/attack"; + DeathSound "dog/death"; + PainSound "dog/pain"; + SeeSound "dog/sight"; + Obituary "$OB_DOG"; + } + States + { + Spawn: + DOGS AB 10 A_Look; + Loop; + See: + DOGS AABBCCDD 2 A_Chase; + Loop; + Melee: + DOGS EF 8 A_FaceTarget; + DOGS G 8 A_SargAttack; + Goto See; + Pain: + DOGS H 2; + DOGS H 2 A_Pain; + Goto See; + Death: + DOGS I 8; + DOGS J 8 A_Scream; + DOGS K 4; + DOGS L 4 A_Fall; + DOGS M 4; + DOGS N -1; + Raise: + DOGS NMLKJI 5; + Goto See; + } +} diff --git a/wadsrc/static/zscript/shared/fountain.txt b/wadsrc/static/zscript/shared/fountain.txt new file mode 100644 index 000000000..60129a8c5 --- /dev/null +++ b/wadsrc/static/zscript/shared/fountain.txt @@ -0,0 +1,66 @@ +class ParticleFountain : Actor native +{ + default + { + Height 0; + +NOBLOCKMAP + +NOGRAVITY + +INVISIBLE + } +} + +class RedParticleFountain : ParticleFountain +{ + default + { + Health 1; + } +} + +class GreenParticleFountain : ParticleFountain +{ + default + { + Health 2; + } +} + +class BlueParticleFountain : ParticleFountain +{ + default + { + Health 3; + } +} + +class YellowParticleFountain : ParticleFountain +{ + default + { + Health 4; + } +} + +class PurpleParticleFountain : ParticleFountain +{ + default + { + Health 5; + } +} + +class BlackParticleFountain : ParticleFountain +{ + default + { + Health 6; + } +} + +class WhiteParticleFountain : ParticleFountain +{ + default + { + Health 7; + } +} diff --git a/wadsrc/static/zscript/shared/hatetarget.txt b/wadsrc/static/zscript/shared/hatetarget.txt new file mode 100644 index 000000000..6d2263f61 --- /dev/null +++ b/wadsrc/static/zscript/shared/hatetarget.txt @@ -0,0 +1,22 @@ + + +// Hate Target -------------------------------------------------------------- + +class HateTarget : Actor native +{ + default + { + Radius 20; + Height 56; + +SHOOTABLE + +NOGRAVITY + +NOBLOOD + +DONTSPLASH + Mass 0x7fffffff; + } + States + { + Spawn: + TNT1 A -1; + } +} \ No newline at end of file diff --git a/wadsrc/static/zscript/shared/mapmarker.txt b/wadsrc/static/zscript/shared/mapmarker.txt new file mode 100644 index 000000000..1afa00459 --- /dev/null +++ b/wadsrc/static/zscript/shared/mapmarker.txt @@ -0,0 +1,18 @@ + +class MapMarker : Actor native +{ + default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + +INVISIBLE + Scale 0.5; + } + States + { + Spawn: + AMRK A -1; + Stop; + } +} diff --git a/wadsrc/static/zscript/shared/movingcamera.txt b/wadsrc/static/zscript/shared/movingcamera.txt new file mode 100644 index 000000000..c5b8534db --- /dev/null +++ b/wadsrc/static/zscript/shared/movingcamera.txt @@ -0,0 +1,46 @@ +class InterpolationPoint : Actor native +{ + default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + RenderStyle "None"; + } +} + +class InterpolationSpecial : Actor native +{ + default + { + +NOBLOCKMAP + +NOSECTOR + +NOGRAVITY + +DONTSPLASH + } +} + +class PathFollower : Actor native +{ + default + { + +NOBLOCKMAP + +NOSECTOR + +NOGRAVITY + +DONTSPLASH + } +} + +class ActorMover : PathFollower native +{ +} + +class MovingCamera : PathFollower native +{ + default + { + CameraHeight 0; + } +} + + diff --git a/wadsrc/static/actors/shared/pickups.txt b/wadsrc/static/zscript/shared/pickups.txt similarity index 65% rename from wadsrc/static/actors/shared/pickups.txt rename to wadsrc/static/zscript/shared/pickups.txt index a9ee0b2d7..8e1e88233 100644 --- a/wadsrc/static/actors/shared/pickups.txt +++ b/wadsrc/static/zscript/shared/pickups.txt @@ -4,28 +4,34 @@ // /***************************************************************************/ -ACTOR ItemFog +class ItemFog : Actor { - +NOBLOCKMAP - +NOGRAVITY + default + { + +NOBLOCKMAP + +NOGRAVITY + } States { Spawn: - IFOG ABABCDE 6 BRIGHT - Stop + IFOG ABABCDE 6 BRIGHT; + Stop; } } // Pickup flash ------------------------------------------------------------- -ACTOR PickupFlash +class PickupFlash : Actor { - +NOGRAVITY + default + { + +NOGRAVITY + } States { Spawn: - ACLO DCDCBCBABA 3 - Stop + ACLO DCDCBCBABA 3; + Stop; } } diff --git a/wadsrc/static/zscript/shared/secrettrigger.txt b/wadsrc/static/zscript/shared/secrettrigger.txt new file mode 100644 index 000000000..48c93686e --- /dev/null +++ b/wadsrc/static/zscript/shared/secrettrigger.txt @@ -0,0 +1,12 @@ + +class SecretTrigger : Actor native +{ + default + { + +NOBLOCKMAP + +NOSECTOR + +NOGRAVITY + +DONTSPLASH + } +} + diff --git a/wadsrc/static/actors/shared/sectoraction.txt b/wadsrc/static/zscript/shared/sectoraction.txt similarity index 61% rename from wadsrc/static/actors/shared/sectoraction.txt rename to wadsrc/static/zscript/shared/sectoraction.txt index f8db34323..03278f2d3 100644 --- a/wadsrc/static/actors/shared/sectoraction.txt +++ b/wadsrc/static/zscript/shared/sectoraction.txt @@ -1,81 +1,84 @@ -ACTOR SectorAction native +class SectorAction : Actor native { - +NOBLOCKMAP - +NOSECTOR - +NOGRAVITY - +DONTSPLASH + default + { + +NOBLOCKMAP + +NOSECTOR + +NOGRAVITY + +DONTSPLASH + } } // Triggered when entering sector ------------------------------------------- -ACTOR SecActEnter : SectorAction native +class SecActEnter : SectorAction native { } // Triggered when leaving sector -------------------------------------------- -ACTOR SecActExit : SectorAction native +class SecActExit : SectorAction native { } // Triggered when hitting sector's floor ------------------------------------ -ACTOR SecActHitFloor : SectorAction native +class SecActHitFloor : SectorAction native { } // Triggered when hitting sector's ceiling ---------------------------------- -ACTOR SecActHitCeil : SectorAction native +class SecActHitCeil : SectorAction native { } // Triggered when using inside sector --------------------------------------- -ACTOR SecActUse : SectorAction native +class SecActUse : SectorAction native { } // Triggered when using a sector's wall ------------------------------------- -ACTOR SecActUseWall : SectorAction native +class SecActUseWall : SectorAction native { } // Triggered when eyes go below fake floor ---------------------------------- -ACTOR SecActEyesDive : SectorAction native +class SecActEyesDive : SectorAction native { } // Triggered when eyes go above fake floor ---------------------------------- -ACTOR SecActEyesSurface : SectorAction native +class SecActEyesSurface : SectorAction native { } // Triggered when eyes go below fake floor ---------------------------------- -ACTOR SecActEyesBelowC : SectorAction native +class SecActEyesBelowC : SectorAction native { } // Triggered when eyes go above fake floor ---------------------------------- -ACTOR SecActEyesAboveC : SectorAction native +class SecActEyesAboveC : SectorAction native { } // Triggered when eyes go below fake floor ---------------------------------- -ACTOR SecActHitFakeFloor : SectorAction native +class SecActHitFakeFloor : SectorAction native { } // Music changer ---------------------------------- -ACTOR MusicChanger : SectorAction native +class MusicChanger : SectorAction native { } diff --git a/wadsrc/static/zscript/shared/setcolor.txt b/wadsrc/static/zscript/shared/setcolor.txt new file mode 100644 index 000000000..8689e5fd1 --- /dev/null +++ b/wadsrc/static/zscript/shared/setcolor.txt @@ -0,0 +1,22 @@ +class ColorSetter : Actor native +{ + default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + RenderStyle "None"; + } +} + + +class FadeSetter : Actor native +{ + default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + RenderStyle "None"; + } +} diff --git a/wadsrc/static/zscript/shared/skies.txt b/wadsrc/static/zscript/shared/skies.txt new file mode 100644 index 000000000..35077ee5c --- /dev/null +++ b/wadsrc/static/zscript/shared/skies.txt @@ -0,0 +1,49 @@ +class SkyViewpoint : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + } +} + +class SkyPicker : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + } +} + +class SkyCamCompat : SkyViewpoint native +{ +} + +class StackPoint : SkyViewpoint native +{ +} + +class UpperStackLookOnly : StackPoint +{ +} + +class LowerStackLookOnly : StackPoint +{ +} + + +class SectorSilencer native +{ + default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + RenderStyle "None"; + } +} diff --git a/wadsrc/static/zscript/shared/soundenvironment.txt b/wadsrc/static/zscript/shared/soundenvironment.txt new file mode 100644 index 000000000..2a4d66adb --- /dev/null +++ b/wadsrc/static/zscript/shared/soundenvironment.txt @@ -0,0 +1,12 @@ + +class SoundEnvironment : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + } +} + diff --git a/wadsrc/static/zscript/shared/soundsequence.txt b/wadsrc/static/zscript/shared/soundsequence.txt new file mode 100644 index 000000000..97ff8e9aa --- /dev/null +++ b/wadsrc/static/zscript/shared/soundsequence.txt @@ -0,0 +1,121 @@ + +class AmbientSound : Actor native +{ + default + { + +NOBLOCKMAP + +NOSECTOR + +DONTSPLASH + } +} + +class AmbientSoundNoGravity : AmbientSound +{ + default + { + +NOGRAVITY + } +} + +class SoundSequenceSlot : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +DONTSPLASH + } +} + +class SoundSequence : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +DONTSPLASH + } +} + +// Heretic Sound sequences ----------------------------------------------------------- + +class HereticSoundSequence1 : SoundSequence +{ + default + { + Args 0; + } +} + +class HereticSoundSequence2 : SoundSequence +{ + default + { + Args 1; + } +} + +class HereticSoundSequence3 : SoundSequence +{ + default + { + Args 2; + } +} + +class HereticSoundSequence4 : SoundSequence +{ + default + { + Args 3; + } +} + +class HereticSoundSequence5 : SoundSequence +{ + default + { + Args 4; + } +} + +class HereticSoundSequence6 : SoundSequence +{ + default + { + Args 5; + } +} + +class HereticSoundSequence7 : SoundSequence +{ + default + { + Args 6; + } +} + +class HereticSoundSequence8 : SoundSequence +{ + default + { + Args 7; + } +} + +class HereticSoundSequence9 : SoundSequence +{ + default + { + Args 8; + } +} + +class HereticSoundSequence10 : SoundSequence +{ + default + { + Args 9; + } +} + diff --git a/wadsrc/static/zscript/shared/spark.txt b/wadsrc/static/zscript/shared/spark.txt new file mode 100644 index 000000000..5adffdfe1 --- /dev/null +++ b/wadsrc/static/zscript/shared/spark.txt @@ -0,0 +1,11 @@ + +class Spark : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + } +} \ No newline at end of file diff --git a/wadsrc/static/zscript/shared/splashes.txt b/wadsrc/static/zscript/shared/splashes.txt new file mode 100644 index 000000000..8b16d85b8 --- /dev/null +++ b/wadsrc/static/zscript/shared/splashes.txt @@ -0,0 +1,273 @@ + +// Water -------------------------------------------------------------------- + +class WaterSplash : Actor +{ + default + { + Radius 2; + Height 4; + Gravity 0.125; + +NOBLOCKMAP + +MISSILE + +DROPOFF + +NOTELEPORT + +CANNOTPUSH + +DONTSPLASH + +DONTBLAST + } + States + { + Spawn: + SPSH ABC 8; + SPSH D 16; + Stop; + Death: + SPSH D 10; + Stop; + } +} + + +class WaterSplashBase : Actor +{ + default + { + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + +DONTBLAST + } + States + { + Spawn: + SPSH EFGHIJK 5; + Stop; + } +} + +// Lava --------------------------------------------------------------------- + +class LavaSplash : Actor +{ + default + { + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + +DONTBLAST + } + States + { + Spawn: + LVAS ABCDEF 5 Bright; + Stop; + } +} + +class LavaSmoke : Actor +{ + default + { + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + RenderStyle "Translucent"; + DefaultAlpha; + } + States + { + Spawn: + LVAS GHIJK 5 Bright; + Stop; + } +} + +// Sludge ------------------------------------------------------------------- + +class SludgeChunk : Actor +{ + default + { + Radius 2; + Height 4; + Gravity 0.125; + +NOBLOCKMAP + +MISSILE + +DROPOFF + +NOTELEPORT + +CANNOTPUSH + +DONTSPLASH + } + States + { + Spawn: + SLDG ABCD 8; + Stop; + Death: + SLDG D 6; + Stop; + } +} + +class SludgeSplash : Actor +{ + default + { + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + } + States + { + Spawn: + SLDG EFGH 6; + Stop; + } +} + +/* + * These next four classes are not used by me anywhere. + * They are for people who want to use them in a TERRAIN lump. + */ + +// Blood (water with a different sprite) ------------------------------------ + +class BloodSplash : Actor +{ + default + { + Radius 2; + Height 4; + Gravity 0.125; + +NOBLOCKMAP + +MISSILE + +DROPOFF + +NOTELEPORT + +CANNOTPUSH + +DONTSPLASH + +DONTBLAST + } + States + { + Spawn: + BSPH ABC 8; + BSPH D 16; + Stop; + Death: + BSPH D 10; + Stop; + } +} + + +class BloodSplashBase : Actor +{ + default + { + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + +DONTBLAST + } + States + { + Spawn: + BSPH EFGHIJK 5; + Stop; + } +} + +// Slime (sludge with a different sprite) ----------------------------------- + +class SlimeChunk : Actor +{ + default + { + Radius 2; + Height 4; + Gravity 0.125; + +NOBLOCKMAP + +MISSILE + +DROPOFF + +NOTELEPORT + +CANNOTPUSH + +DONTSPLASH + } + States + { + Spawn: + SLIM ABCD 8; + Stop; + Death: + SLIM D 6; + Stop; + } +} + +class SlimeSplash : Actor +{ + default + { + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + } + States + { + Spawn: + SLIM EFGH 6; + Stop; + } +} + +// Smoke trail for rocket ----------------------------------- + +class RocketSmokeTrail : Actor +{ + default + { + RenderStyle "Translucent"; + Alpha 0.4; + VSpeed 1; + +NOBLOCKMAP + +NOCLIP + +NOGRAVITY + +DONTSPLASH + +NOTELEPORT + } + States + { + Spawn: + RSMK ABCDE 5; + Stop; + } +} + +class GrenadeSmokeTrail : Actor +{ + default + { + RenderStyle "Translucent"; + Alpha 0.4; + +NOBLOCKMAP + +NOCLIP + +DONTSPLASH + +NOTELEPORT + Gravity 0.1; + VSpeed 0.5; + Scale 0.6; + } + States + { + Spawn: + RSMK ABCDE 4; + Stop; + } +} diff --git a/wadsrc/static/zscript/shared/teleport.txt b/wadsrc/static/zscript/shared/teleport.txt new file mode 100644 index 000000000..55308415f --- /dev/null +++ b/wadsrc/static/zscript/shared/teleport.txt @@ -0,0 +1,54 @@ + +class TeleportFog : Actor native +{ + default + { + +NOBLOCKMAP + +NOTELEPORT + +NOGRAVITY + RenderStyle "Add"; + } + States + { + Spawn: + TFOG ABABCDEFGHIJ 6 Bright; + Stop; + + Raven: + TELE ABCDEFGHGFEDC 6 Bright; + Stop; + + Strife: + TFOG ABCDEFEDCB 6 Bright; + Stop; + } +} + + + +class TeleportDest : Actor +{ + default + { + +NOBLOCKMAP + +NOSECTOR + +DONTSPLASH + } +} + +class TeleportDest2 : TeleportDest +{ + default + { + +NOGRAVITY + } +} + +class TeleportDest3 : TeleportDest2 +{ + default + { + -NOGRAVITY + } +} + diff --git a/wadsrc/static/zscript/shared/waterzone.txt b/wadsrc/static/zscript/shared/waterzone.txt new file mode 100644 index 000000000..975c8a473 --- /dev/null +++ b/wadsrc/static/zscript/shared/waterzone.txt @@ -0,0 +1,10 @@ +class WaterZone : Actor native +{ + default + { + +NOSECTOR + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + } +} From 784f7ed67180af87e188ae658307fd48dee22060 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 20:08:41 +0200 Subject: [PATCH 030/255] - converted all of Doom's actors. - fixed a few problems that were encountered during conversion: * action specials as action functions were not recognized by the parser. * Player.StartItem could not be parsed. * disabled the naming hack for PowerupType. ZScript, unlike DECORATE will never prepend 'Power' to the power's name, it always needs to specified by its full name. * states and defaults were not checked for empty bodies. * the scope qualifier for goto labels was not properly converted to a string, because it is an ENamedName, not an FName. --- src/scripting/thingdef_properties.cpp | 2 +- src/scripting/zscript/zcc-parse.lemon | 12 + src/scripting/zscript/zcc_compile.cpp | 19 +- wadsrc/static/actors/doom/arachnotron.txt | 85 -- wadsrc/static/actors/doom/archvile.txt | 83 -- wadsrc/static/actors/doom/bossbrain.txt | 120 --- wadsrc/static/actors/doom/bruiser.txt | 131 --- wadsrc/static/actors/doom/cacodemon.txt | 82 -- wadsrc/static/actors/doom/cyberdemon.txt | 61 -- wadsrc/static/actors/doom/demon.txt | 71 -- wadsrc/static/actors/doom/doomammo.txt | 142 --- wadsrc/static/actors/doom/doomarmor.txt | 60 -- wadsrc/static/actors/doom/doomartifacts.txt | 171 ---- wadsrc/static/actors/doom/doomdecorations.txt | 753 --------------- wadsrc/static/actors/doom/doomhealth.txt | 45 - wadsrc/static/actors/doom/doomimp.txt | 87 -- wadsrc/static/actors/doom/doomkeys.txt | 98 -- wadsrc/static/actors/doom/doommisc.txt | 104 -- wadsrc/static/actors/doom/doomplayer.txt | 90 -- wadsrc/static/actors/doom/doomweapons.txt | 574 ----------- wadsrc/static/actors/doom/fatso.txt | 89 -- wadsrc/static/actors/doom/keen.txt | 41 - wadsrc/static/actors/doom/lostsoul.txt | 80 -- wadsrc/static/actors/doom/painelemental.txt | 50 - wadsrc/static/actors/doom/possessed.txt | 241 ----- wadsrc/static/actors/doom/revenant.txt | 113 --- wadsrc/static/actors/doom/scriptedmarine.txt | 306 ------ wadsrc/static/actors/doom/spidermaster.txt | 59 -- wadsrc/static/actors/doom/stealthmonsters.txt | 103 -- wadsrc/static/decorate.txt | 29 - wadsrc/static/zscript.txt | 28 + wadsrc/static/zscript/doom/arachnotron.txt | 91 ++ wadsrc/static/zscript/doom/archvile.txt | 89 ++ wadsrc/static/zscript/doom/bossbrain.txt | 135 +++ wadsrc/static/zscript/doom/bruiser.txt | 140 +++ wadsrc/static/zscript/doom/cacodemon.txt | 88 ++ wadsrc/static/zscript/doom/cyberdemon.txt | 64 ++ .../{actors => zscript}/doom/deadthings.txt | 72 +- wadsrc/static/zscript/doom/demon.txt | 77 ++ wadsrc/static/zscript/doom/doomammo.txt | 169 ++++ wadsrc/static/zscript/doom/doomarmor.txt | 69 ++ wadsrc/static/zscript/doom/doomartifacts.txt | 201 ++++ .../static/zscript/doom/doomdecorations.txt | 900 ++++++++++++++++++ wadsrc/static/zscript/doom/doomhealth.txt | 54 ++ wadsrc/static/zscript/doom/doomimp.txt | 93 ++ wadsrc/static/zscript/doom/doomkeys.txt | 119 +++ wadsrc/static/zscript/doom/doommisc.txt | 116 +++ wadsrc/static/zscript/doom/doomplayer.txt | 93 ++ wadsrc/static/zscript/doom/doomweapons.txt | 621 ++++++++++++ wadsrc/static/zscript/doom/fatso.txt | 95 ++ wadsrc/static/zscript/doom/keen.txt | 44 + wadsrc/static/zscript/doom/lostsoul.txt | 83 ++ wadsrc/static/zscript/doom/painelemental.txt | 53 ++ wadsrc/static/zscript/doom/possessed.txt | 253 +++++ wadsrc/static/zscript/doom/revenant.txt | 122 +++ wadsrc/static/zscript/doom/scriptedmarine.txt | 309 ++++++ wadsrc/static/zscript/doom/spidermaster.txt | 62 ++ .../static/zscript/doom/stealthmonsters.txt | 139 +++ 58 files changed, 4377 insertions(+), 3903 deletions(-) delete mode 100644 wadsrc/static/actors/doom/arachnotron.txt delete mode 100644 wadsrc/static/actors/doom/archvile.txt delete mode 100644 wadsrc/static/actors/doom/bossbrain.txt delete mode 100644 wadsrc/static/actors/doom/bruiser.txt delete mode 100644 wadsrc/static/actors/doom/cacodemon.txt delete mode 100644 wadsrc/static/actors/doom/cyberdemon.txt delete mode 100644 wadsrc/static/actors/doom/demon.txt delete mode 100644 wadsrc/static/actors/doom/doomammo.txt delete mode 100644 wadsrc/static/actors/doom/doomarmor.txt delete mode 100644 wadsrc/static/actors/doom/doomartifacts.txt delete mode 100644 wadsrc/static/actors/doom/doomdecorations.txt delete mode 100644 wadsrc/static/actors/doom/doomhealth.txt delete mode 100644 wadsrc/static/actors/doom/doomimp.txt delete mode 100644 wadsrc/static/actors/doom/doomkeys.txt delete mode 100644 wadsrc/static/actors/doom/doommisc.txt delete mode 100644 wadsrc/static/actors/doom/doomplayer.txt delete mode 100644 wadsrc/static/actors/doom/doomweapons.txt delete mode 100644 wadsrc/static/actors/doom/fatso.txt delete mode 100644 wadsrc/static/actors/doom/keen.txt delete mode 100644 wadsrc/static/actors/doom/lostsoul.txt delete mode 100644 wadsrc/static/actors/doom/painelemental.txt delete mode 100644 wadsrc/static/actors/doom/possessed.txt delete mode 100644 wadsrc/static/actors/doom/revenant.txt delete mode 100644 wadsrc/static/actors/doom/scriptedmarine.txt delete mode 100644 wadsrc/static/actors/doom/spidermaster.txt delete mode 100644 wadsrc/static/actors/doom/stealthmonsters.txt create mode 100644 wadsrc/static/zscript/doom/arachnotron.txt create mode 100644 wadsrc/static/zscript/doom/archvile.txt create mode 100644 wadsrc/static/zscript/doom/bossbrain.txt create mode 100644 wadsrc/static/zscript/doom/bruiser.txt create mode 100644 wadsrc/static/zscript/doom/cacodemon.txt create mode 100644 wadsrc/static/zscript/doom/cyberdemon.txt rename wadsrc/static/{actors => zscript}/doom/deadthings.txt (67%) create mode 100644 wadsrc/static/zscript/doom/demon.txt create mode 100644 wadsrc/static/zscript/doom/doomammo.txt create mode 100644 wadsrc/static/zscript/doom/doomarmor.txt create mode 100644 wadsrc/static/zscript/doom/doomartifacts.txt create mode 100644 wadsrc/static/zscript/doom/doomdecorations.txt create mode 100644 wadsrc/static/zscript/doom/doomhealth.txt create mode 100644 wadsrc/static/zscript/doom/doomimp.txt create mode 100644 wadsrc/static/zscript/doom/doomkeys.txt create mode 100644 wadsrc/static/zscript/doom/doommisc.txt create mode 100644 wadsrc/static/zscript/doom/doomplayer.txt create mode 100644 wadsrc/static/zscript/doom/doomweapons.txt create mode 100644 wadsrc/static/zscript/doom/fatso.txt create mode 100644 wadsrc/static/zscript/doom/keen.txt create mode 100644 wadsrc/static/zscript/doom/lostsoul.txt create mode 100644 wadsrc/static/zscript/doom/painelemental.txt create mode 100644 wadsrc/static/zscript/doom/possessed.txt create mode 100644 wadsrc/static/zscript/doom/revenant.txt create mode 100644 wadsrc/static/zscript/doom/scriptedmarine.txt create mode 100644 wadsrc/static/zscript/doom/spidermaster.txt create mode 100644 wadsrc/static/zscript/doom/stealthmonsters.txt diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index 084736c24..833a2d381 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -2431,7 +2431,7 @@ DEFINE_CLASS_PROPERTY_PREFIX(powerup, type, S, PowerupGiver) // Yuck! What was I thinking when I decided to prepend "Power" to the name? // Now it's too late to change it... PClassActor *cls = PClass::FindActor(str); - if (cls == NULL || !cls->IsDescendantOf(RUNTIME_CLASS(APowerup))) + if (cls == NULL || !cls->IsDescendantOf(RUNTIME_CLASS(APowerup)) && !bag.fromZScript) { FString st; st.Format("%s%s", strnicmp(str, "power", 5)? "Power" : "", str); diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index dba30af5f..cd1cbce14 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -458,6 +458,18 @@ state_flow_type(X) ::= GOTO(T) IDENTIFIER(C) SCOPE dottable_id(A) state_goto_off X = flow; } +state_flow_type(X) ::= GOTO(T) SUPER(C) SCOPE dottable_id(A) state_goto_offset(B). +{ + NEW_AST_NODE(StateGoto, flow, T); + flow->Label = A; + flow->Offset = B; + + NEW_AST_NODE(Identifier,id,C); + id->Id = NAME_Super; + flow->Qualifier =id; + X = flow; +} + state_goto_offset(X) ::= . { X = NULL; } state_goto_offset(X) ::= ADD expr(A). { X = A; /*X-overwrites-A*/ } /* Must evaluate to a non-negative integer constant. */ diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 904f938ca..f24bce20c 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1657,7 +1657,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper // Skip the DECORATE 'no comma' marker if (*p == '_') p++; - else if (*p == 0) + if (*p == 0) { if (exp != property->Values) { @@ -1834,7 +1834,7 @@ void ZCCCompiler::InitDefaults() for (auto d : c->Defaults) { auto content = d->Content; - do + if (content != nullptr) do { switch (content->NodeType) { @@ -1870,7 +1870,7 @@ void ZCCCompiler::InitFunctions() { TArray rets(1); TArray args; - TArray argflags; + TArray argflags; TArray argnames; for (auto c : Classes) @@ -2032,8 +2032,13 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a } else { - Error(af, "%s: action function not found in %s", FName(id->Identifier).GetChars(), cls->TypeName.GetChars()); - return nullptr; + // it may also be an action special so check that first before printing an error. + if (!P_FindLineSpecial(FName(id->Identifier).GetChars())) + { + Error(af, "%s: action function not found in %s", FName(id->Identifier).GetChars(), cls->TypeName.GetChars()); + return nullptr; + } + // Action specials fall through to the code generator. } } return ConvertAST(af); @@ -2074,7 +2079,7 @@ void ZCCCompiler::CompileStates() for (auto s : c->States) { auto st = s->Body; - do + if (st != nullptr) do { switch (st->NodeType) { @@ -2187,7 +2192,7 @@ void ZCCCompiler::CompileStates() statename = ""; if (sg->Qualifier != nullptr) { - statename << sg->Qualifier->Id << "::"; + statename << FName(sg->Qualifier->Id) << "::"; } auto part = sg->Label; do diff --git a/wadsrc/static/actors/doom/arachnotron.txt b/wadsrc/static/actors/doom/arachnotron.txt deleted file mode 100644 index 1a70a11d1..000000000 --- a/wadsrc/static/actors/doom/arachnotron.txt +++ /dev/null @@ -1,85 +0,0 @@ -//=========================================================================== -// -// Arachnotron -// -//=========================================================================== -ACTOR Arachnotron -{ - Health 500 - Radius 64 - Height 64 - Mass 600 - Speed 12 - PainChance 128 - Monster - +FLOORCLIP - +BOSSDEATH - SeeSound "baby/sight" - PainSound "baby/pain" - DeathSound "baby/death" - ActiveSound "baby/active" - Obituary "$OB_BABY" - States - { - Spawn: - BSPI AB 10 A_Look - Loop - See: - BSPI A 20 - BSPI A 3 A_BabyMetal - BSPI ABBCC 3 A_Chase - BSPI D 3 A_BabyMetal - BSPI DEEFF 3 A_Chase - Goto See+1 - Missile: - BSPI A 20 BRIGHT A_FaceTarget - BSPI G 4 BRIGHT A_BspiAttack - BSPI H 4 BRIGHT - BSPI H 1 BRIGHT A_SpidRefire - Goto Missile+1 - Pain: - BSPI I 3 - BSPI I 3 A_Pain - Goto See+1 - Death: - BSPI J 20 A_Scream - BSPI K 7 A_NoBlocking - BSPI LMNO 7 - BSPI P -1 A_BossDeath - Stop - Raise: - BSPI P 5 - BSPI ONMLKJ 5 - Goto See+1 - } -} - -//=========================================================================== -// -// Arachnotron plasma -// -//=========================================================================== -ACTOR ArachnotronPlasma -{ - Radius 13 - Height 8 - Speed 25 - Damage 5 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 0.75 - SeeSound "baby/attack" - DeathSound "baby/shotx" - States - { - Spawn: - APLS AB 5 BRIGHT - Loop - Death: - APBX ABCDE 5 BRIGHT - Stop - } -} - - diff --git a/wadsrc/static/actors/doom/archvile.txt b/wadsrc/static/actors/doom/archvile.txt deleted file mode 100644 index f2c5d6ab4..000000000 --- a/wadsrc/static/actors/doom/archvile.txt +++ /dev/null @@ -1,83 +0,0 @@ -//=========================================================================== -// -// Arch Vile -// -//=========================================================================== - -ACTOR Archvile -{ - Health 700 - Radius 20 - Height 56 - Mass 500 - Speed 15 - PainChance 10 - Monster - MaxTargetRange 896 - +QUICKTORETALIATE - +FLOORCLIP - +NOTARGET - SeeSound "vile/sight" - PainSound "vile/pain" - DeathSound "vile/death" - ActiveSound "vile/active" - MeleeSound "vile/stop" - Obituary "$OB_VILE" - States - { - Spawn: - VILE AB 10 A_Look - Loop - See: - VILE AABBCCDDEEFF 2 A_VileChase - Loop - Missile: - VILE G 0 BRIGHT A_VileStart - VILE G 10 BRIGHT A_FaceTarget - VILE H 8 BRIGHT A_VileTarget - VILE IJKLMN 8 BRIGHT A_FaceTarget - VILE O 8 BRIGHT A_VileAttack - VILE P 20 BRIGHT - Goto See - Heal: - VILE "[\]" 10 BRIGHT - Goto See - Pain: - VILE Q 5 - VILE Q 5 A_Pain - Goto See - Death: - VILE Q 7 - VILE R 7 A_Scream - VILE S 7 A_NoBlocking - VILE TUVWXY 7 - VILE Z -1 - Stop - } -} - - -//=========================================================================== -// -// Arch Vile Fire -// -//=========================================================================== - -ACTOR ArchvileFire -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Add - Alpha 1 - States - { - Spawn: - FIRE A 2 BRIGHT A_StartFire - FIRE BAB 2 BRIGHT A_Fire - FIRE C 2 BRIGHT A_FireCrackle - FIRE BCBCDCDCDEDED 2 BRIGHT A_Fire - FIRE E 2 BRIGHT A_FireCrackle - FIRE FEFEFGHGHGH 2 BRIGHT A_Fire - Stop - } -} - diff --git a/wadsrc/static/actors/doom/bossbrain.txt b/wadsrc/static/actors/doom/bossbrain.txt deleted file mode 100644 index 67b6da7d6..000000000 --- a/wadsrc/static/actors/doom/bossbrain.txt +++ /dev/null @@ -1,120 +0,0 @@ - -//=========================================================================== -// -// Boss Brain -// -//=========================================================================== - -ACTOR BossBrain -{ - Health 250 - Mass 10000000 - PainChance 255 - +SOLID +SHOOTABLE - +NOICEDEATH - +OLDRADIUSDMG - PainSound "brain/pain" - DeathSound "brain/death" - States - { - BrainExplode: - MISL BC 10 Bright - MISL D 10 A_BrainExplode - Stop - Spawn: - BBRN A -1 - Stop - Pain: - BBRN B 36 A_BrainPain - Goto Spawn - Death: - BBRN A 100 A_BrainScream - BBRN AA 10 - BBRN A -1 A_BrainDie - Stop - } -} - - -//=========================================================================== -// -// Boss Eye -// -//=========================================================================== - -ACTOR BossEye -{ - Height 32 - +NOBLOCKMAP - +NOSECTOR - States - { - Spawn: - SSWV A 10 A_Look - Loop - See: - SSWV A 181 A_BrainAwake - SSWV A 150 A_BrainSpit - Wait - } -} - -//=========================================================================== -// -// Boss Target -// -//=========================================================================== - -ACTOR BossTarget : SpecialSpot -{ - Height 32 - +NOBLOCKMAP - +NOSECTOR -} - -//=========================================================================== -// -// Spawn shot -// -//=========================================================================== - -ACTOR SpawnShot -{ - Radius 6 - Height 32 - Speed 10 - Damage 3 - Projectile - +NOCLIP - -ACTIVATEPCROSS - +RANDOMIZE - SeeSound "brain/spit" - DeathSound "brain/cubeboom" - States - { - Spawn: - BOSF A 3 BRIGHT A_SpawnSound - BOSF BCD 3 BRIGHT A_SpawnFly - Loop - } -} - -//=========================================================================== -// -// Spawn fire -// -//=========================================================================== - -ACTOR SpawnFire -{ - Height 78 - +NOBLOCKMAP - +NOGRAVITY - RenderStyle Add - States - { - Spawn: - FIRE ABCDEFGH 4 Bright A_Fire - Stop - } -} diff --git a/wadsrc/static/actors/doom/bruiser.txt b/wadsrc/static/actors/doom/bruiser.txt deleted file mode 100644 index 0a2bdcff6..000000000 --- a/wadsrc/static/actors/doom/bruiser.txt +++ /dev/null @@ -1,131 +0,0 @@ -//=========================================================================== -// -// Baron of Hell -// -//=========================================================================== -ACTOR BaronOfHell -{ - Health 1000 - Radius 24 - Height 64 - Mass 1000 - Speed 8 - PainChance 50 - Monster - +FLOORCLIP - +BOSSDEATH - SeeSound "baron/sight" - PainSound "baron/pain" - DeathSound "baron/death" - ActiveSound "baron/active" - Obituary "$OB_BARON" - HitObituary "$OB_BARONHIT" - States - { - Spawn: - BOSS AB 10 A_Look - Loop - See: - BOSS AABBCCDD 3 A_Chase - Loop - Melee: - Missile: - BOSS EF 8 A_FaceTarget - BOSS G 8 A_BruisAttack - Goto See - Pain: - BOSS H 2 - BOSS H 2 A_Pain - Goto See - Death: - BOSS I 8 - BOSS J 8 A_Scream - BOSS K 8 - BOSS L 8 A_NoBlocking - BOSS MN 8 - BOSS O -1 A_BossDeath - Stop - Raise: - BOSS O 8 - BOSS NMLKJI 8 - Goto See - } -} - -//=========================================================================== -// -// Hell Knight -// -//=========================================================================== -ACTOR HellKnight : BaronOfHell -{ - Health 500 - -BOSSDEATH - SeeSound "knight/sight" - ActiveSound "knight/active" - PainSound "knight/pain" - DeathSound "knight/death" - HitObituary "$OB_KNIGHTHIT" - Obituary "$OB_KNIGHT" - States - { - Spawn: - BOS2 AB 10 A_Look - Loop - See: - BOS2 AABBCCDD 3 A_Chase - Loop - Melee: - Missile: - BOS2 EF 8 A_FaceTarget - BOS2 G 8 A_BruisAttack - Goto See - Pain: - BOS2 H 2 - BOS2 H 2 A_Pain - Goto See - Death: - BOS2 I 8 - BOS2 J 8 A_Scream - BOS2 K 8 - BOS2 L 8 A_NoBlocking - BOS2 MN 8 - BOS2 O -1 - Stop - Raise: - BOS2 O 8 - BOS2 NMLKJI 8 - Goto See - } -} - -//=========================================================================== -// -// Baron slime ball -// -//=========================================================================== -ACTOR BaronBall -{ - Radius 6 - Height 16 - Speed 15 - FastSpeed 20 - Damage 8 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 1 - SeeSound "baron/attack" - DeathSound "baron/shotx" - Decal "BaronScorch" - States - { - Spawn: - BAL7 AB 4 BRIGHT - Loop - Death: - BAL7 CDE 6 BRIGHT - Stop - } -} - diff --git a/wadsrc/static/actors/doom/cacodemon.txt b/wadsrc/static/actors/doom/cacodemon.txt deleted file mode 100644 index db2ee7657..000000000 --- a/wadsrc/static/actors/doom/cacodemon.txt +++ /dev/null @@ -1,82 +0,0 @@ -//=========================================================================== -// -// Cacodemon -// -//=========================================================================== -ACTOR Cacodemon -{ - Health 400 - Radius 31 - Height 56 - Mass 400 - Speed 8 - PainChance 128 - Monster - +FLOAT +NOGRAVITY - SeeSound "caco/sight" - PainSound "caco/pain" - DeathSound "caco/death" - ActiveSound "caco/active" - Obituary "$OB_CACO" - HitObituary "$OB_CACOHIT" - States - { - Spawn: - HEAD A 10 A_Look - Loop - See: - HEAD A 3 A_Chase - Loop - Missile: - HEAD B 5 A_FaceTarget - HEAD C 5 A_FaceTarget - HEAD D 5 BRIGHT A_HeadAttack - Goto See - Pain: - HEAD E 3 - HEAD E 3 A_Pain - HEAD F 6 - Goto See - Death: - HEAD G 8 - HEAD H 8 A_Scream - HEAD I 8 - HEAD J 8 - HEAD K 8 A_NoBlocking - HEAD L -1 A_SetFloorClip - Stop - Raise: - HEAD L 8 A_UnSetFloorClip - HEAD KJIHG 8 - Goto See - } -} - -//=========================================================================== -// -// Cacodemon plasma ball -// -//=========================================================================== -ACTOR CacodemonBall -{ - Radius 6 - Height 8 - Speed 10 - FastSpeed 20 - Damage 5 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 1 - SeeSound "caco/attack" - DeathSound "caco/shotx" - States - { - Spawn: - BAL2 AB 4 BRIGHT - Loop - Death: - BAL2 CDE 6 BRIGHT - Stop - } -} diff --git a/wadsrc/static/actors/doom/cyberdemon.txt b/wadsrc/static/actors/doom/cyberdemon.txt deleted file mode 100644 index 9f9c986f4..000000000 --- a/wadsrc/static/actors/doom/cyberdemon.txt +++ /dev/null @@ -1,61 +0,0 @@ - -//=========================================================================== -// -// Cyberdemon -// -//=========================================================================== -ACTOR Cyberdemon -{ - Health 4000 - Radius 40 - Height 110 - Mass 1000 - Speed 16 - PainChance 20 - Monster - MinMissileChance 160 - +BOSS - +MISSILEMORE - +FLOORCLIP - +NORADIUSDMG - +DONTMORPH - +BOSSDEATH - SeeSound "cyber/sight" - PainSound "cyber/pain" - DeathSound "cyber/death" - ActiveSound "cyber/active" - Obituary "$OB_CYBORG" - States - { - Spawn: - CYBR AB 10 A_Look - Loop - See: - CYBR A 3 A_Hoof - CYBR ABBCC 3 A_Chase - CYBR D 3 A_Metal - CYBR D 3 A_Chase - Loop - Missile: - CYBR E 6 A_FaceTarget - CYBR F 12 A_CyberAttack - CYBR E 12 A_FaceTarget - CYBR F 12 A_CyberAttack - CYBR E 12 A_FaceTarget - CYBR F 12 A_CyberAttack - Goto See - Pain: - CYBR G 10 A_Pain - Goto See - Death: - CYBR H 10 - CYBR I 10 A_Scream - CYBR JKL 10 - CYBR M 10 A_NoBlocking - CYBR NO 10 - CYBR P 30 - CYBR P -1 A_BossDeath - Stop - } -} - diff --git a/wadsrc/static/actors/doom/demon.txt b/wadsrc/static/actors/doom/demon.txt deleted file mode 100644 index 3680b24e9..000000000 --- a/wadsrc/static/actors/doom/demon.txt +++ /dev/null @@ -1,71 +0,0 @@ -//=========================================================================== -// -// Pink Demon -// -//=========================================================================== -ACTOR Demon -{ - Health 150 - PainChance 180 - Speed 10 - Radius 30 - Height 56 - Mass 400 - Monster - +FLOORCLIP - SeeSound "demon/sight" - AttackSound "demon/melee" - PainSound "demon/pain" - DeathSound "demon/death" - ActiveSound "demon/active" - Obituary "$OB_DEMONHIT" - States - { - Spawn: - SARG AB 10 A_Look - Loop - See: - SARG AABBCCDD 2 Fast A_Chase - Loop - Melee: - SARG EF 8 Fast A_FaceTarget - SARG G 8 Fast A_SargAttack - Goto See - Pain: - SARG H 2 Fast - SARG H 2 Fast A_Pain - Goto See - Death: - SARG I 8 - SARG J 8 A_Scream - SARG K 4 - SARG L 4 A_NoBlocking - SARG M 4 - SARG N -1 - Stop - Raise: - SARG N 5 - SARG MLKJI 5 - Goto See - } -} - -//=========================================================================== -// -// Spectre -// -//=========================================================================== -ACTOR Spectre : Demon -{ - +SHADOW - RenderStyle OptFuzzy - Alpha 0.5 - SeeSound "spectre/sight" - AttackSound "spectre/melee" - PainSound "spectre/pain" - DeathSound "spectre/death" - ActiveSound "spectre/active" - HitObituary "$OB_SPECTREHIT" -} - - diff --git a/wadsrc/static/actors/doom/doomammo.txt b/wadsrc/static/actors/doom/doomammo.txt deleted file mode 100644 index bc931c08f..000000000 --- a/wadsrc/static/actors/doom/doomammo.txt +++ /dev/null @@ -1,142 +0,0 @@ -// Clip -------------------------------------------------------------------- - -ACTOR Clip : Ammo -{ - Inventory.PickupMessage "$GOTCLIP" - Inventory.Amount 10 - Inventory.MaxAmount 200 - Ammo.BackpackAmount 10 - Ammo.BackpackMaxAmount 400 - Inventory.Icon "CLIPA0" - States - { - Spawn: - CLIP A -1 - Stop - } -} - -// Clip box ---------------------------------------------------------------- - -ACTOR ClipBox : Clip -{ - Inventory.PickupMessage "$GOTCLIPBOX" - Inventory.Amount 50 - States - { - Spawn: - AMMO A -1 - Stop - } -} - -// Rocket ------------------------------------------------------------------ - -ACTOR RocketAmmo : Ammo -{ - Inventory.PickupMessage "$GOTROCKET" - Inventory.Amount 1 - Inventory.MaxAmount 50 - Ammo.BackpackAmount 1 - Ammo.BackpackMaxAmount 100 - Inventory.Icon "ROCKA0" - States - { - Spawn: - ROCK A -1 - Stop - } -} - -// Rocket box -------------------------------------------------------------- - -ACTOR RocketBox : RocketAmmo -{ - Inventory.PickupMessage "$GOTROCKBOX" - Inventory.Amount 5 - States - { - Spawn: - BROK A -1 - Stop - } -} - -// Cell -------------------------------------------------------------------- - -ACTOR Cell : Ammo -{ - Inventory.PickupMessage "$GOTCELL" - Inventory.Amount 20 - Inventory.MaxAmount 300 - Ammo.BackpackAmount 20 - Ammo.BackpackMaxAmount 600 - Inventory.Icon "CELLA0" - States - { - Spawn: - CELL A -1 - Stop - } -} - -// Cell pack --------------------------------------------------------------- - -ACTOR CellPack : Cell -{ - Inventory.PickupMessage "$GOTCELLBOX" - Inventory.Amount 100 - States - { - Spawn: - CELP A -1 - Stop - } -} - -// Shells ------------------------------------------------------------------ - -ACTOR Shell : Ammo -{ - Inventory.PickupMessage "$GOTSHELLS" - Inventory.Amount 4 - Inventory.MaxAmount 50 - Ammo.BackpackAmount 4 - Ammo.BackpackMaxAmount 100 - Inventory.Icon "SHELA0" - States - { - Spawn: - SHEL A -1 - Stop - } -} - -// Shell box --------------------------------------------------------------- - -ACTOR ShellBox : Shell -{ - Inventory.PickupMessage "$GOTSHELLBOX" - Inventory.Amount 20 - States - { - Spawn: - SBOX A -1 - Stop - } -} - -// Backpack --------------------------------------------------------------- - -ACTOR Backpack : BackpackItem -{ - Height 26 - Inventory.PickupMessage "$GOTBACKPACK" - States - { - Spawn: - BPAK A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/doom/doomarmor.txt b/wadsrc/static/actors/doom/doomarmor.txt deleted file mode 100644 index c676f9131..000000000 --- a/wadsrc/static/actors/doom/doomarmor.txt +++ /dev/null @@ -1,60 +0,0 @@ - -// Armor bonus -------------------------------------------------------------- - -Actor ArmorBonus : BasicArmorBonus -{ - Radius 20 - Height 16 - Inventory.Pickupmessage "$GOTARMBONUS" - Inventory.Icon "ARM1A0" - Armor.Savepercent 33.335 - Armor.Saveamount 1 - Armor.Maxsaveamount 200 - +COUNTITEM - +INVENTORY.ALWAYSPICKUP - States - { - Spawn: - BON2 ABCDCB 6 - loop - } -} - -// Green armor -------------------------------------------------------------- - -Actor GreenArmor : BasicArmorPickup -{ - Radius 20 - Height 16 - Inventory.Pickupmessage "$GOTARMOR" - Inventory.Icon "ARM1A0" - Armor.SavePercent 33.335 - Armor.SaveAmount 100 - States - { - Spawn: - ARM1 A 6 - ARM1 B 7 bright - loop - } -} - -// Blue armor --------------------------------------------------------------- - -Actor BlueArmor : BasicArmorPickup -{ - Radius 20 - Height 16 - Inventory.Pickupmessage "$GOTMEGA" - Inventory.Icon "ARM2A0" - Armor.Savepercent 50 - Armor.Saveamount 200 - States - { - Spawn: - ARM2 A 6 - ARM2 B 6 bright - loop - } -} - diff --git a/wadsrc/static/actors/doom/doomartifacts.txt b/wadsrc/static/actors/doom/doomartifacts.txt deleted file mode 100644 index e9caa5f11..000000000 --- a/wadsrc/static/actors/doom/doomartifacts.txt +++ /dev/null @@ -1,171 +0,0 @@ -// Invulnerability Sphere --------------------------------------------------- - -ACTOR InvulnerabilitySphere : PowerupGiver -{ - +COUNTITEM - +INVENTORY.AUTOACTIVATE - +INVENTORY.ALWAYSPICKUP - +INVENTORY.BIGPOWERUP - Inventory.MaxAmount 0 - Powerup.Type Invulnerable - Powerup.Color InverseMap - Inventory.PickupMessage "$GOTINVUL" - States - { - Spawn: - PINV ABCD 6 Bright - Loop - } -} - -// Soulsphere -------------------------------------------------------------- - -ACTOR Soulsphere : Health -{ - +COUNTITEM - +INVENTORY.AUTOACTIVATE - +INVENTORY.ALWAYSPICKUP - +INVENTORY.FANCYPICKUPSOUND - Inventory.Amount 100 - Inventory.MaxAmount 200 - Inventory.PickupMessage "$GOTSUPER" - Inventory.PickupSound "misc/p_pkup" - States - { - Spawn: - SOUL ABCDCB 6 Bright - Loop - } -} - -// Mega sphere -------------------------------------------------------------- - -ACTOR MegasphereHealth : Health // for manipulation by Dehacked -{ - Inventory.Amount 200 - Inventory.MaxAmount 200 - +INVENTORY.ALWAYSPICKUP -} - -// DeHackEd can only modify the blue armor's type, not the megasphere's. -actor BlueArmorForMegasphere : BlueArmor -{ - Armor.SavePercent 50 - Armor.SaveAmount 200 -} - -ACTOR Megasphere : CustomInventory -{ - +COUNTITEM - +INVENTORY.ALWAYSPICKUP - Inventory.PickupMessage "$GOTMSPHERE" - Inventory.PickupSound "misc/p_pkup" - States - { - Spawn: - MEGA ABCD 6 BRIGHT - Loop - Pickup: - TNT1 A 0 A_GiveInventory("BlueArmorForMegasphere", 1) - TNT1 A 0 A_GiveInventory("MegasphereHealth", 1) - Stop - } -} - -// Invisibility ------------------------------------------------------------- - -ACTOR BlurSphere : PowerupGiver -{ - +COUNTITEM - +VISIBILITYPULSE - +INVENTORY.AUTOACTIVATE - +INVENTORY.ALWAYSPICKUP - +INVENTORY.BIGPOWERUP - Inventory.MaxAmount 0 - Powerup.Type Invisibility - RenderStyle Translucent - Inventory.PickupMessage "$GOTINVIS" - States - { - Spawn: - PINS ABCD 6 Bright - Loop - } -} - -// Radiation suit (aka iron feet) ------------------------------------------- - -ACTOR RadSuit : PowerupGiver -{ - Height 46 - +INVENTORY.AUTOACTIVATE - +INVENTORY.ALWAYSPICKUP - Inventory.MaxAmount 0 - Inventory.PickupMessage "$GOTSUIT" - Powerup.Type IronFeet - States - { - Spawn: - SUIT A -1 Bright - Stop - } -} - -// infrared ----------------------------------------------------------------- - -ACTOR Infrared : PowerupGiver -{ - +COUNTITEM - +INVENTORY.AUTOACTIVATE - +INVENTORY.ALWAYSPICKUP - Inventory.MaxAmount 0 - Powerup.Type LightAmp - Inventory.PickupMessage "$GOTVISOR" - States - { - Spawn: - PVIS A 6 Bright - PVIS B 6 - Loop - } -} - -// Allmap ------------------------------------------------------------------- - -ACTOR Allmap : MapRevealer -{ - +COUNTITEM - +INVENTORY.FANCYPICKUPSOUND - +INVENTORY.ALWAYSPICKUP - Inventory.MaxAmount 0 - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$GOTMAP" - States - { - Spawn: - PMAP ABCDCB 6 Bright - Loop - } -} - -// Berserk ------------------------------------------------------------------ - -ACTOR Berserk : CustomInventory -{ - +COUNTITEM - +INVENTORY.ALWAYSPICKUP - Inventory.PickupMessage "$GOTBERSERK" - Inventory.PickupSound "misc/p_pkup" - States - { - Spawn: - PSTR A -1 - Stop - Pickup: - TNT1 A 0 A_GiveInventory("PowerStrength") - TNT1 A 0 HealThing(100, 0) - TNT1 A 0 A_SelectWeapon("Fist") - Stop - } -} - diff --git a/wadsrc/static/actors/doom/doomdecorations.txt b/wadsrc/static/actors/doom/doomdecorations.txt deleted file mode 100644 index 4206c09ed..000000000 --- a/wadsrc/static/actors/doom/doomdecorations.txt +++ /dev/null @@ -1,753 +0,0 @@ - -// Tech lamp --------------------------------------------------------------- - -ACTOR TechLamp -{ - Radius 16 - Height 80 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TLMP ABCD 4 BRIGHT - Loop - } -} - -// Tech lamp 2 ------------------------------------------------------------- - -ACTOR TechLamp2 -{ - Radius 16 - Height 60 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TLP2 ABCD 4 BRIGHT - Loop - } -} - -// Column ------------------------------------------------------------------ - -ACTOR Column -{ - Radius 16 - Height 48 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COLU A -1 BRIGHT - Stop - } -} - -// Tall green column ------------------------------------------------------- - -ACTOR TallGreenColumn -{ - Radius 16 - Height 52 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COL1 A -1 - Stop - } -} - -// Short green column ------------------------------------------------------ - -ACTOR ShortGreenColumn -{ - Radius 16 - Height 40 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COL2 A -1 - Stop - } -} - -// Tall red column --------------------------------------------------------- - -ACTOR TallRedColumn -{ - Radius 16 - Height 52 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COL3 A -1 - Stop - } -} - -// Short red column -------------------------------------------------------- - -ACTOR ShortRedColumn -{ - Radius 16 - Height 40 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COL4 A -1 - Stop - } -} - -// Skull column ------------------------------------------------------------ - -ACTOR SkullColumn -{ - Radius 16 - Height 40 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COL6 A -1 - Stop - } -} - -// Heart column ------------------------------------------------------------ - -ACTOR HeartColumn -{ - Radius 16 - Height 40 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - COL5 AB 14 - Loop - } -} - -// Evil eye ---------------------------------------------------------------- - -ACTOR EvilEye -{ - Radius 16 - Height 54 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - CEYE ABCB 6 BRIGHT - Loop - } -} - -// Floating skull ---------------------------------------------------------- - -ACTOR FloatingSkull -{ - Radius 16 - Height 26 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - FSKU ABC 6 BRIGHT - Loop - } -} - -// Torch tree -------------------------------------------------------------- - -ACTOR TorchTree -{ - Radius 16 - Height 56 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TRE1 A -1 - Stop - } -} - -// Blue torch -------------------------------------------------------------- - -ACTOR BlueTorch -{ - Radius 16 - Height 68 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TBLU ABCD 4 BRIGHT - Loop - } -} - -// Green torch ------------------------------------------------------------- - -ACTOR GreenTorch -{ - Radius 16 - Height 68 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TGRN ABCD 4 BRIGHT - Loop - } -} - -// Red torch --------------------------------------------------------------- - -ACTOR RedTorch -{ - Radius 16 - Height 68 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TRED ABCD 4 BRIGHT - Loop - } -} - -// Short blue torch -------------------------------------------------------- - -ACTOR ShortBlueTorch -{ - Radius 16 - Height 37 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - SMBT ABCD 4 BRIGHT - Loop - } -} - -// Short green torch ------------------------------------------------------- - -ACTOR ShortGreenTorch -{ - Radius 16 - Height 37 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - SMGT ABCD 4 BRIGHT - Loop - } -} - -// Short red torch --------------------------------------------------------- - -ACTOR ShortRedTorch -{ - Radius 16 - Height 37 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - SMRT ABCD 4 BRIGHT - Loop - } -} - -// Stalagtite -------------------------------------------------------------- - -ACTOR Stalagtite -{ - Radius 16 - Height 40 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - SMIT A -1 - Stop - } -} - -// Tech pillar ------------------------------------------------------------- - -ACTOR TechPillar -{ - Radius 16 - Height 128 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - ELEC A -1 - Stop - } -} - -// Candle stick ------------------------------------------------------------ - -ACTOR Candlestick -{ - Radius 20 - Height 14 - ProjectilePassHeight -16 - States - { - Spawn: - CAND A -1 BRIGHT - Stop - } -} - -// Candelabra -------------------------------------------------------------- - -ACTOR Candelabra -{ - Radius 16 - Height 60 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - CBRA A -1 BRIGHT - Stop - } -} - -// Bloody twitch ----------------------------------------------------------- - -ACTOR BloodyTwitch -{ - Radius 16 - Height 68 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - GOR1 A 10 - GOR1 B 15 - GOR1 C 8 - GOR1 B 6 - Loop - } -} - -// Meat 2 ------------------------------------------------------------------ - -ACTOR Meat2 -{ - Radius 16 - Height 84 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - GOR2 A -1 - Stop - } -} - -// Meat 3 ------------------------------------------------------------------ - -ACTOR Meat3 -{ - Radius 16 - Height 84 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - GOR3 A -1 - Stop - } -} - -// Meat 4 ------------------------------------------------------------------ - -ACTOR Meat4 -{ - Radius 16 - Height 68 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - GOR4 A -1 - Stop - } -} - -// Meat 5 ------------------------------------------------------------------ - -ACTOR Meat5 -{ - Radius 16 - Height 52 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - GOR5 A -1 - Stop - } -} - -// Nonsolid meat ----------------------------------------------------------- - -ACTOR NonsolidMeat2 : Meat2 -{ - -SOLID - Radius 20 -} - -ACTOR NonsolidMeat3 : Meat3 -{ - -SOLID - Radius 20 -} - -ACTOR NonsolidMeat4 : Meat4 -{ - -SOLID - Radius 20 -} - -ACTOR NonsolidMeat5 : Meat5 -{ - -SOLID - Radius 20 -} - -// Nonsolid bloody twitch -------------------------------------------------- - -ACTOR NonsolidTwitch : BloodyTwitch -{ - -SOLID - Radius 20 -} - -// Head on a stick --------------------------------------------------------- - -ACTOR HeadOnAStick -{ - Radius 16 - Height 56 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - POL4 A -1 - Stop - } -} - -// Heads (plural!) on a stick ---------------------------------------------- - -ACTOR HeadsOnAStick -{ - Radius 16 - Height 64 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - POL2 A -1 - Stop - } -} - -// Head candles ------------------------------------------------------------ - -ACTOR HeadCandles -{ - Radius 16 - Height 42 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - POL3 AB 6 BRIGHT - Loop - } -} - -// Dead on a stick --------------------------------------------------------- - -ACTOR DeadStick -{ - Radius 16 - Height 64 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - POL1 A -1 - Stop - } -} - -// Still alive on a stick -------------------------------------------------- - -ACTOR LiveStick -{ - Radius 16 - Height 64 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - POL6 A 6 - POL6 B 8 - Loop - } -} - -// Big tree ---------------------------------------------------------------- - -ACTOR BigTree -{ - Radius 32 - Height 108 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - TRE2 A -1 - Stop - } -} - -// Burning barrel ---------------------------------------------------------- - -ACTOR BurningBarrel -{ - Radius 16 - Height 32 - ProjectilePassHeight -16 - +SOLID - States - { - Spawn: - FCAN ABC 4 BRIGHT - Loop - } -} - -// Hanging with no guts ---------------------------------------------------- - -ACTOR HangNoGuts -{ - Radius 16 - Height 88 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - HDB1 A -1 - Stop - } -} - -// Hanging from bottom with no brain --------------------------------------- - -ACTOR HangBNoBrain -{ - Radius 16 - Height 88 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - HDB2 A -1 - Stop - } -} - -// Hanging from top, looking down ------------------------------------------ - -ACTOR HangTLookingDown -{ - Radius 16 - Height 64 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - HDB3 A -1 - Stop - } -} - -// Hanging from top, looking up -------------------------------------------- - -ACTOR HangTLookingUp -{ - Radius 16 - Height 64 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - HDB5 A -1 - Stop - } -} - -// Hanging from top, skully ------------------------------------------------ - -ACTOR HangTSkull -{ - Radius 16 - Height 64 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - HDB4 A -1 - Stop - } -} - -// Hanging from top without a brain ---------------------------------------- - -ACTOR HangTNoBrain -{ - Radius 16 - Height 64 - +SOLID - +NOGRAVITY - +SPAWNCEILING - States - { - Spawn: - HDB6 A -1 - Stop - } -} - -// Colon gibs -------------------------------------------------------------- - -ACTOR ColonGibs -{ - Radius 20 - Height 4 - +NOBLOCKMAP - +MOVEWITHSECTOR - States - { - Spawn: - POB1 A -1 - Stop - } -} - -// Small pool o' blood ----------------------------------------------------- - -ACTOR SmallBloodPool -{ - Radius 20 - Height 1 - +NOBLOCKMAP - +MOVEWITHSECTOR - States - { - Spawn: - POB2 A -1 - Stop - } -} - -// brain stem lying on the ground ------------------------------------------ - -ACTOR BrainStem -{ - Radius 20 - Height 4 - +NOBLOCKMAP - +MOVEWITHSECTOR - States - { - Spawn: - BRS1 A -1 - Stop - } -} - - -// Grey stalagmite (unused Doom sprite, definition taken from Skulltag ----- - -ACTOR Stalagmite -{ - Radius 16 - Height 48 - +SOLID - States - { - Spawn: - SMT2 A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/doom/doomhealth.txt b/wadsrc/static/actors/doom/doomhealth.txt deleted file mode 100644 index c1a8d96ff..000000000 --- a/wadsrc/static/actors/doom/doomhealth.txt +++ /dev/null @@ -1,45 +0,0 @@ -// Health bonus ------------------------------------------------------------- - -ACTOR HealthBonus : Health -{ - +COUNTITEM - +INVENTORY.ALWAYSPICKUP - Inventory.Amount 1 - Inventory.MaxAmount 200 - Inventory.PickupMessage "$GOTHTHBONUS" - States - { - Spawn: - BON1 ABCDCB 6 - Loop - } -} - -// Stimpack ----------------------------------------------------------------- - -ACTOR Stimpack : Health -{ - Inventory.Amount 10 - Inventory.PickupMessage "$GOTSTIM" - States - { - Spawn: - STIM A -1 - Stop - } -} - -// Medikit ----------------------------------------------------------------- - -ACTOR Medikit : Health -{ - Inventory.Amount 25 - Inventory.PickupMessage "$GOTMEDIKIT" - Health.LowMessage 25, "$GOTMEDINEED" - States - { - Spawn: - MEDI A -1 - Stop - } -} diff --git a/wadsrc/static/actors/doom/doomimp.txt b/wadsrc/static/actors/doom/doomimp.txt deleted file mode 100644 index a5725e724..000000000 --- a/wadsrc/static/actors/doom/doomimp.txt +++ /dev/null @@ -1,87 +0,0 @@ -//=========================================================================== -// -// Imp -// -//=========================================================================== -ACTOR DoomImp -{ - Health 60 - Radius 20 - Height 56 - Mass 100 - Speed 8 - PainChance 200 - Monster - +FLOORCLIP - SeeSound "imp/sight" - PainSound "imp/pain" - DeathSound "imp/death" - ActiveSound "imp/active" - HitObituary "$OB_IMPHIT" - Obituary "$OB_IMP" - States - { - Spawn: - TROO AB 10 A_Look - Loop - See: - TROO AABBCCDD 3 A_Chase - Loop - Melee: - Missile: - TROO EF 8 A_FaceTarget - TROO G 6 A_TroopAttack - Goto See - Pain: - TROO H 2 - TROO H 2 A_Pain - Goto See - Death: - TROO I 8 - TROO J 8 A_Scream - TROO K 6 - TROO L 6 A_NoBlocking - TROO M -1 - Stop - XDeath: - TROO N 5 - TROO O 5 A_XScream - TROO P 5 - TROO Q 5 A_NoBlocking - TROO RST 5 - TROO U -1 - Stop - Raise: - TROO MLKJI 8 - Goto See - } -} - -//=========================================================================== -// -// Imp fireball -// -//=========================================================================== -ACTOR DoomImpBall -{ - Radius 6 - Height 8 - Speed 10 - FastSpeed 20 - Damage 3 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 1 - SeeSound "imp/attack" - DeathSound "imp/shotx" - States - { - Spawn: - BAL1 AB 4 BRIGHT - Loop - Death: - BAL1 CDE 6 BRIGHT - Stop - } -} diff --git a/wadsrc/static/actors/doom/doomkeys.txt b/wadsrc/static/actors/doom/doomkeys.txt deleted file mode 100644 index d24392559..000000000 --- a/wadsrc/static/actors/doom/doomkeys.txt +++ /dev/null @@ -1,98 +0,0 @@ - -Actor DoomKey : Key -{ - Radius 20 - Height 16 - +NOTDMATCH -} - -// Blue key card ------------------------------------------------------------ - -Actor BlueCard : DoomKey -{ - Inventory.Pickupmessage "$GOTBLUECARD" - Inventory.Icon "STKEYS0" - States - { - Spawn: - BKEY A 10 - BKEY B 10 bright - loop - } -} - -// Yellow key card ---------------------------------------------------------- - -Actor YellowCard : DoomKey -{ - Inventory.Pickupmessage "$GOTYELWCARD" - Inventory.Icon "STKEYS1" - States - { - Spawn: - YKEY A 10 - YKEY B 10 bright - loop - } -} - -// Red key card ------------------------------------------------------------- - -Actor RedCard : DoomKey -{ - Inventory.Pickupmessage "$GOTREDCARD" - Inventory.Icon "STKEYS2" - States - { - Spawn: - RKEY A 10 - RKEY B 10 bright - loop - } -} - -// Blue skull key ----------------------------------------------------------- - -Actor BlueSkull : DoomKey -{ - Inventory.Pickupmessage "$GOTBLUESKUL" - Inventory.Icon "STKEYS3" - States - { - Spawn: - BSKU A 10 - BSKU B 10 bright - loop - } -} - -// Yellow skull key --------------------------------------------------------- - -Actor YellowSkull : DoomKey -{ - Inventory.Pickupmessage "$GOTYELWSKUL" - Inventory.Icon "STKEYS4" - States - { - Spawn: - YSKU A 10 - YSKU B 10 bright - loop - } -} - -// Red skull key ------------------------------------------------------------ - -Actor RedSkull : DoomKey -{ - Inventory.Pickupmessage "$GOTREDSKUL" - Inventory.Icon "STKEYS5" - States - { - Spawn: - RSKU A 10 - RSKU B 10 bright - loop - } -} - diff --git a/wadsrc/static/actors/doom/doommisc.txt b/wadsrc/static/actors/doom/doommisc.txt deleted file mode 100644 index cb22474b9..000000000 --- a/wadsrc/static/actors/doom/doommisc.txt +++ /dev/null @@ -1,104 +0,0 @@ -// The barrel of green goop ------------------------------------------------ - -ACTOR ExplosiveBarrel -{ - Health 20 - Radius 10 - Height 42 - +SOLID - +SHOOTABLE - +NOBLOOD - +ACTIVATEMCROSS - +DONTGIB - +NOICEDEATH - +OLDRADIUSDMG - DeathSound "world/barrelx" - Obituary "$OB_BARREL" - States - { - Spawn: - BAR1 AB 6 - Loop - Death: - BEXP A 5 BRIGHT - BEXP B 5 BRIGHT A_Scream - BEXP C 5 BRIGHT - BEXP D 5 BRIGHT A_Explode - BEXP E 10 BRIGHT - TNT1 A 1050 BRIGHT A_BarrelDestroy - TNT1 A 5 A_Respawn - Wait - } -} - -// Bullet puff ------------------------------------------------------------- - -ACTOR BulletPuff -{ - +NOBLOCKMAP - +NOGRAVITY - +ALLOWPARTICLES - +RANDOMIZE - RenderStyle Translucent - Alpha 0.5 - VSpeed 1 - Mass 5 - States - { - Spawn: - PUFF A 4 Bright - PUFF B 4 - Melee: - PUFF CD 4 - Stop - } -} - -// Container for an unused state ------------------------------------------- - -/* Doom defined the states S_STALAG, S_DEADTORSO, and S_DEADBOTTOM but never - * actually used them. For compatibility with DeHackEd patches, they still - * need to be kept around. This actor serves that purpose. - */ - -ACTOR DoomUnusedStates -{ - States - { - Label1: - SMT2 A -1 - stop - Label2: - PLAY N -1 - stop - PLAY S -1 - stop - TNT: // MBF compatibility - TNT1 A -1 - Loop - } -} - -// MBF Beta emulation items - -Actor EvilSceptre : ScoreItem -{ - Inventory.PickupMessage "$BETA_BONUS3" - States - { - Spawn: - BON3 A 6 - Loop - } -} - -Actor UnholyBible : ScoreItem -{ - Inventory.PickupMessage "$BETA_BONUS4" - States - { - Spawn: - BON4 A 6 - Loop - } -} diff --git a/wadsrc/static/actors/doom/doomplayer.txt b/wadsrc/static/actors/doom/doomplayer.txt deleted file mode 100644 index e31c10ea7..000000000 --- a/wadsrc/static/actors/doom/doomplayer.txt +++ /dev/null @@ -1,90 +0,0 @@ -//=========================================================================== -// -// Player -// -//=========================================================================== -ACTOR DoomPlayer : PlayerPawn -{ - Speed 1 - Health 100 - Radius 16 - Height 56 - Mass 100 - PainChance 255 - Player.DisplayName "Marine" - Player.CrouchSprite "PLYC" - Player.StartItem "Pistol" - Player.StartItem "Fist" - Player.StartItem "Clip", 50 - Player.WeaponSlot 1, Fist, Chainsaw - Player.WeaponSlot 2, Pistol - Player.WeaponSlot 3, Shotgun, SuperShotgun - Player.WeaponSlot 4, Chaingun - Player.WeaponSlot 5, RocketLauncher - Player.WeaponSlot 6, PlasmaRifle - Player.WeaponSlot 7, BFG9000 - - Player.ColorRange 112, 127 - Player.Colorset 0, "Green", 0x70, 0x7F, 0x72 - Player.Colorset 1, "Gray", 0x60, 0x6F, 0x62 - Player.Colorset 2, "Brown", 0x40, 0x4F, 0x42 - Player.Colorset 3, "Red", 0x20, 0x2F, 0x22 - // Doom Legacy additions - Player.Colorset 4, "Light Gray", 0x58, 0x67, 0x5A - Player.Colorset 5, "Light Brown", 0x38, 0x47, 0x3A - Player.Colorset 6, "Light Red", 0xB0, 0xBF, 0xB2 - Player.Colorset 7, "Light Blue", 0xC0, 0xCF, 0xC2 - - States - { - Spawn: - PLAY A -1 - Loop - See: - PLAY ABCD 4 - Loop - Missile: - PLAY E 12 - Goto Spawn - Melee: - PLAY F 6 BRIGHT - Goto Missile - Pain: - PLAY G 4 - PLAY G 4 A_Pain - Goto Spawn - Death: - PLAY H 0 A_PlayerSkinCheck("AltSkinDeath") - Death1: - PLAY H 10 - PLAY I 10 A_PlayerScream - PLAY J 10 A_NoBlocking - PLAY KLM 10 - PLAY N -1 - Stop - XDeath: - PLAY O 0 A_PlayerSkinCheck("AltSkinXDeath") - XDeath1: - PLAY O 5 - PLAY P 5 A_XScream - PLAY Q 5 A_NoBlocking - PLAY RSTUV 5 - PLAY W -1 - Stop - AltSkinDeath: - PLAY H 6 - PLAY I 6 A_PlayerScream - PLAY JK 6 - PLAY L 6 A_NoBlocking - PLAY MNO 6 - PLAY P -1 - Stop - AltSkinXDeath: - PLAY Q 5 A_PlayerScream - PLAY R 0 A_NoBlocking - PLAY R 5 A_SkullPop - PLAY STUVWX 5 - PLAY Y -1 - Stop - } -} diff --git a/wadsrc/static/actors/doom/doomweapons.txt b/wadsrc/static/actors/doom/doomweapons.txt deleted file mode 100644 index 16369572b..000000000 --- a/wadsrc/static/actors/doom/doomweapons.txt +++ /dev/null @@ -1,574 +0,0 @@ -// -------------------------------------------------------------------------- -// -// Doom weapon base class -// -// -------------------------------------------------------------------------- - -ACTOR DoomWeapon : Weapon -{ - Weapon.Kickback 100 -} - -// -------------------------------------------------------------------------- -// -// Fist -// -// -------------------------------------------------------------------------- - -ACTOR Fist : Weapon -{ - Weapon.SelectionOrder 3700 - Weapon.Kickback 100 - Obituary "$OB_MPFIST" - Tag "$TAG_FIST" - +WEAPON.WIMPY_WEAPON - +WEAPON.MELEEWEAPON - States - { - Ready: - PUNG A 1 A_WeaponReady - Loop - Deselect: - PUNG A 1 A_Lower - Loop - Select: - PUNG A 1 A_Raise - Loop - Fire: - PUNG B 4 - PUNG C 4 A_Punch - PUNG D 5 - PUNG C 4 - PUNG B 5 A_ReFire - Goto Ready - } -} - - -// -------------------------------------------------------------------------- -// -// Pistol -// -// -------------------------------------------------------------------------- - -ACTOR Pistol : DoomWeapon -{ - Weapon.SelectionOrder 1900 - Weapon.AmmoUse 1 - Weapon.AmmoGive 20 - Weapon.AmmoType "Clip" - Obituary "$OB_MPPISTOL" - +WEAPON.WIMPY_WEAPON - Inventory.Pickupmessage "$PICKUP_PISTOL_DROPPED" - Tag "$TAG_PISTOL" - States - { - Ready: - PISG A 1 A_WeaponReady - Loop - Deselect: - PISG A 1 A_Lower - Loop - Select: - PISG A 1 A_Raise - Loop - Fire: - PISG A 4 - PISG B 6 A_FirePistol - PISG C 4 - PISG B 5 A_ReFire - Goto Ready - Flash: - PISF A 7 Bright A_Light1 - Goto LightDone - PISF A 7 Bright A_Light1 - Goto LightDone - Spawn: - PIST A -1 - Stop - } -} - -// -------------------------------------------------------------------------- -// -// Chainsaw -// -// -------------------------------------------------------------------------- - -ACTOR Chainsaw : Weapon -{ - Weapon.Kickback 0 - Weapon.SelectionOrder 2200 - Weapon.UpSound "weapons/sawup" - Weapon.ReadySound "weapons/sawidle" - Inventory.PickupMessage "$GOTCHAINSAW" - Obituary "$OB_MPCHAINSAW" - Tag "$TAG_CHAINSAW" - +WEAPON.MELEEWEAPON - States - { - Ready: - SAWG CD 4 A_WeaponReady - Loop - Deselect: - SAWG C 1 A_Lower - Loop - Select: - SAWG C 1 A_Raise - Loop - Fire: - SAWG AB 4 A_Saw - SAWG B 0 A_ReFire - Goto Ready - Spawn: - CSAW A -1 - Stop - } -} - - -// -------------------------------------------------------------------------- -// -// Shotgun -// -// -------------------------------------------------------------------------- - -ACTOR Shotgun : DoomWeapon -{ - Weapon.SelectionOrder 1300 - Weapon.AmmoUse 1 - Weapon.AmmoGive 8 - Weapon.AmmoType "Shell" - Inventory.PickupMessage "$GOTSHOTGUN" - Obituary "$OB_MPSHOTGUN" - Tag "$TAG_SHOTGUN" - States - { - Ready: - SHTG A 1 A_WeaponReady - Loop - Deselect: - SHTG A 1 A_Lower - Loop - Select: - SHTG A 1 A_Raise - Loop - Fire: - SHTG A 3 - SHTG A 7 A_FireShotgun - SHTG BC 5 - SHTG D 4 - SHTG CB 5 - SHTG A 3 - SHTG A 7 A_ReFire - Goto Ready - Flash: - SHTF A 4 Bright A_Light1 - SHTF B 3 Bright A_Light2 - Goto LightDone - Spawn: - SHOT A -1 - Stop - } -} - -// -------------------------------------------------------------------------- -// -// Shotgun -// -// -------------------------------------------------------------------------- - -ACTOR SuperShotgun : DoomWeapon -{ - Weapon.SelectionOrder 400 - Weapon.AmmoUse 2 - Weapon.AmmoGive 8 - Weapon.AmmoType "Shell" - Inventory.PickupMessage "$GOTSHOTGUN2" - Obituary "$OB_MPSSHOTGUN" - Tag "$TAG_SUPERSHOTGUN" - States - { - Ready: - SHT2 A 1 A_WeaponReady - Loop - Deselect: - SHT2 A 1 A_Lower - Loop - Select: - SHT2 A 1 A_Raise - Loop - Fire: - SHT2 A 3 - SHT2 A 7 A_FireShotgun2 - SHT2 B 7 - SHT2 C 7 A_CheckReload - SHT2 D 7 A_OpenShotgun2 - SHT2 E 7 - SHT2 F 7 A_LoadShotgun2 - SHT2 G 6 - SHT2 H 6 A_CloseShotgun2 - SHT2 A 5 A_ReFire - Goto Ready - // unused states - SHT2 B 7 - SHT2 A 3 - Goto Deselect - Flash: - SHT2 I 4 Bright A_Light1 - SHT2 J 3 Bright A_Light2 - Goto LightDone - Spawn: - SGN2 A -1 - Stop - } -} - -// -------------------------------------------------------------------------- -// -// Chaingun -// -// -------------------------------------------------------------------------- - -ACTOR Chaingun : DoomWeapon -{ - Weapon.SelectionOrder 700 - Weapon.AmmoUse 1 - Weapon.AmmoGive 20 - Weapon.AmmoType "Clip" - Inventory.PickupMessage "$GOTCHAINGUN" - Obituary "$OB_MPCHAINGUN" - Tag "$TAG_CHAINGUN" - States - { - Ready: - CHGG A 1 A_WeaponReady - Loop - Deselect: - CHGG A 1 A_Lower - Loop - Select: - CHGG A 1 A_Raise - Loop - Fire: - CHGG AB 4 A_FireCGun - CHGG B 0 A_ReFire - Goto Ready - Flash: - CHGF A 5 Bright A_Light1 - Goto LightDone - CHGF B 5 Bright A_Light2 - Goto LightDone - Spawn: - MGUN A -1 - Stop - } -} - -// -------------------------------------------------------------------------- -// -// Rocket launcher -// -// -------------------------------------------------------------------------- - -ACTOR RocketLauncher : DoomWeapon -{ - Weapon.SelectionOrder 2500 - Weapon.AmmoUse 1 - Weapon.AmmoGive 2 - Weapon.AmmoType "RocketAmmo" - +WEAPON.NOAUTOFIRE - Inventory.PickupMessage "$GOTLAUNCHER" - Tag "$TAG_ROCKETLAUNCHER" - States - { - Ready: - MISG A 1 A_WeaponReady - Loop - Deselect: - MISG A 1 A_Lower - Loop - Select: - MISG A 1 A_Raise - Loop - Fire: - MISG B 8 A_GunFlash - MISG B 12 A_FireMissile - MISG B 0 A_ReFire - Goto Ready - Flash: - MISF A 3 Bright A_Light1 - MISF B 4 Bright - MISF CD 4 Bright A_Light2 - Goto LightDone - Spawn: - LAUN A -1 - Stop - } -} - -ACTOR Rocket -{ - Radius 11 - Height 8 - Speed 20 - Damage 20 - Projectile - +RANDOMIZE - +DEHEXPLOSION - +ROCKETTRAIL - SeeSound "weapons/rocklf" - DeathSound "weapons/rocklx" - Obituary "$OB_MPROCKET" - States - { - Spawn: - MISL A 1 Bright - Loop - Death: - MISL B 8 Bright A_Explode - MISL C 6 Bright - MISL D 4 Bright - Stop - } -} - -// -------------------------------------------------------------------------- -// -// Grenade -- Taken and adapted from Skulltag, with MBF stuff added to it -// -// -------------------------------------------------------------------------- - -ACTOR Grenade -{ - Radius 8 - Height 8 - Speed 25 - Damage 20 - Projectile - -NOGRAVITY - +RANDOMIZE - +DEHEXPLOSION - +GRENADETRAIL - BounceType "Doom" - Gravity 0.25 - SeeSound "weapons/grenlf" - DeathSound "weapons/grenlx" - BounceSound "weapons/grbnce" - Obituary "$OB_GRENADE" - DamageType Grenade - - States - { - Spawn: - SGRN A 1 Bright - Loop - Death: - MISL B 8 Bright A_Explode - MISL C 6 Bright - MISL D 4 Bright - Stop - Grenade: - MISL A 1000 A_Die - Wait - Detonate: - MISL B 4 A_Scream - MISL C 6 A_Detonate - MISL D 10 - Stop - Mushroom: - MISL B 8 A_Mushroom - Goto Death+1 - } -} - -// -------------------------------------------------------------------------- -// -// Plasma rifle -// -// -------------------------------------------------------------------------- - -ACTOR PlasmaRifle : DoomWeapon -{ - Weapon.SelectionOrder 100 - Weapon.AmmoUse 1 - Weapon.AmmoGive 40 - Weapon.AmmoType "Cell" - Inventory.PickupMessage "$GOTPLASMA" - Tag "$TAG_PLASMARIFLE" - States - { - Ready: - PLSG A 1 A_WeaponReady - Loop - Deselect: - PLSG A 1 A_Lower - Loop - Select: - PLSG A 1 A_Raise - Loop - Fire: - PLSG A 3 A_FirePlasma - PLSG B 20 A_ReFire - Goto Ready - Flash: - PLSF A 4 Bright A_Light1 - Goto LightDone - PLSF B 4 Bright A_Light1 - Goto LightDone - Spawn: - PLAS A -1 - Stop - } -} - -ACTOR PlasmaBall -{ - Radius 13 - Height 8 - Speed 25 - Damage 5 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 0.75 - SeeSound "weapons/plasmaf" - DeathSound "weapons/plasmax" - Obituary "$OB_MPPLASMARIFLE" - States - { - Spawn: - PLSS AB 6 Bright - Loop - Death: - PLSE ABCDE 4 Bright - Stop - } -} - -// -------------------------------------------------------------------------- -// -// BFG 2704 -// -// -------------------------------------------------------------------------- - -ACTOR PlasmaBall1 : PlasmaBall -{ - Damage 4 - BounceType "Classic" - BounceFactor 1.0 - Obituary "$OB_MPBFG_MBF" - States - { - Spawn: - PLS1 AB 6 Bright - Loop - Death: - PLS1 CDEFG 4 Bright - Stop - } -} - -ACTOR PlasmaBall2 : PlasmaBall1 -{ - States - { - Spawn: - PLS2 AB 6 Bright - Loop - Death: - PLS2 CDE 4 Bright - Stop - } -} - -// -------------------------------------------------------------------------- -// -// BFG 9000 -// -// -------------------------------------------------------------------------- - -ACTOR BFG9000 : DoomWeapon -{ - Height 20 - Weapon.SelectionOrder 2800 - Weapon.AmmoUse 40 - Weapon.AmmoGive 40 - Weapon.AmmoType "Cell" - +WEAPON.NOAUTOFIRE - Inventory.PickupMessage "$GOTBFG9000" - Tag "$TAG_BFG9000" - States - { - Ready: - BFGG A 1 A_WeaponReady - Loop - Deselect: - BFGG A 1 A_Lower - Loop - Select: - BFGG A 1 A_Raise - Loop - Fire: - BFGG A 20 A_BFGsound - BFGG B 10 A_GunFlash - BFGG B 10 A_FireBFG - BFGG B 20 A_ReFire - Goto Ready - Flash: - BFGF A 11 Bright A_Light1 - BFGF B 6 Bright A_Light2 - Goto LightDone - Spawn: - BFUG A -1 - Stop - OldFire: - BFGG A 10 A_BFGsound - BFGG BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB 1 A_FireOldBFG - BFGG B 0 A_Light0 - BFGG B 20 A_ReFire - Goto Ready - } -} - - -ACTOR BFGBall -{ - Radius 13 - Height 8 - Speed 25 - Damage 100 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 0.75 - DeathSound "weapons/bfgx" - Obituary "$OB_MPBFG_BOOM" - States - { - Spawn: - BFS1 AB 4 Bright - Loop - Death: - BFE1 AB 8 Bright - BFE1 C 8 Bright A_BFGSpray - BFE1 DEF 8 Bright - Stop - } -} - -ACTOR BFGExtra -{ - +NOBLOCKMAP - +NOGRAVITY - RenderStyle Add - Alpha 0.75 - DamageType "BFGSplash" - States - { - Spawn: - BFE2 ABCD 8 Bright - Stop - } -} - diff --git a/wadsrc/static/actors/doom/fatso.txt b/wadsrc/static/actors/doom/fatso.txt deleted file mode 100644 index 9b3a7d26a..000000000 --- a/wadsrc/static/actors/doom/fatso.txt +++ /dev/null @@ -1,89 +0,0 @@ -//=========================================================================== -// -// Mancubus -// -//=========================================================================== -ACTOR Fatso -{ - Health 600 - Radius 48 - Height 64 - Mass 1000 - Speed 8 - PainChance 80 - Monster - +FLOORCLIP - +BOSSDEATH - SeeSound "fatso/sight" - PainSound "fatso/pain" - DeathSound "fatso/death" - ActiveSound "fatso/active" - Obituary "$OB_FATSO" - States - { - Spawn: - FATT AB 15 A_Look - Loop - See: - FATT AABBCCDDEEFF 4 A_Chase - Loop - Missile: - FATT G 20 A_FatRaise - FATT H 10 BRIGHT A_FatAttack1 - FATT IG 5 A_FaceTarget - FATT H 10 BRIGHT A_FatAttack2 - FATT IG 5 A_FaceTarget - FATT H 10 BRIGHT A_FatAttack3 - FATT IG 5 A_FaceTarget - Goto See - Pain: - FATT J 3 - FATT J 3 A_Pain - Goto See - Death: - FATT K 6 - FATT L 6 A_Scream - FATT M 6 A_NoBlocking - FATT NOPQRS 6 - FATT T -1 A_BossDeath - Stop - Raise: - FATT R 5 - FATT QPONMLK 5 - Goto See - } -} - - - -//=========================================================================== -// -// Mancubus fireball -// -//=========================================================================== -ACTOR FatShot -{ - Radius 6 - Height 8 - Speed 20 - Damage 8 - Projectile - +RANDOMIZE - RenderStyle Add - Alpha 1 - SeeSound "fatso/attack" - DeathSound "fatso/shotx" - States - { - Spawn: - MANF AB 4 BRIGHT - Loop - Death: - MISL B 8 BRIGHT - MISL C 6 BRIGHT - MISL D 4 BRIGHT - Stop - } -} - - diff --git a/wadsrc/static/actors/doom/keen.txt b/wadsrc/static/actors/doom/keen.txt deleted file mode 100644 index 7ad41d2ce..000000000 --- a/wadsrc/static/actors/doom/keen.txt +++ /dev/null @@ -1,41 +0,0 @@ -//=========================================================================== -// -// Commander Keen -// -//=========================================================================== -ACTOR CommanderKeen -{ - Health 100 - Radius 16 - Height 72 - Mass 10000000 - PainChance 256 - +SOLID - +SPAWNCEILING - +NOGRAVITY - +SHOOTABLE - +COUNTKILL - +NOICEDEATH - +ISMONSTER - PainSound "keen/pain" - DeathSound "keen/death" - States - { - Spawn: - KEEN A -1 - Loop - Death: - KEEN AB 6 - KEEN C 6 A_Scream - KEEN DEFGH 6 - KEEN I 6 - KEEN J 6 - KEEN K 6 A_KeenDie - KEEN L -1 - Stop - Pain: - KEEN M 4 - KEEN M 8 A_Pain - Goto Spawn - } -} diff --git a/wadsrc/static/actors/doom/lostsoul.txt b/wadsrc/static/actors/doom/lostsoul.txt deleted file mode 100644 index bd6212cf2..000000000 --- a/wadsrc/static/actors/doom/lostsoul.txt +++ /dev/null @@ -1,80 +0,0 @@ -//=========================================================================== -// -// Lost Soul -// -//=========================================================================== -ACTOR LostSoul -{ - Health 100 - Radius 16 - Height 56 - Mass 50 - Speed 8 - Damage 3 - PainChance 256 - Monster - +FLOAT +NOGRAVITY +MISSILEMORE +DONTFALL +NOICEDEATH - AttackSound "skull/melee" - PainSound "skull/pain" - DeathSound "skull/death" - ActiveSound "skull/active" - RenderStyle SoulTrans - Obituary "$OB_SKULL" - States - { - Spawn: - SKUL AB 10 BRIGHT A_Look - Loop - See: - SKUL AB 6 BRIGHT A_Chase - Loop - Missile: - SKUL C 10 BRIGHT A_FaceTarget - SKUL D 4 BRIGHT A_SkullAttack - SKUL CD 4 BRIGHT - Goto Missile+2 - Pain: - SKUL E 3 BRIGHT - SKUL E 3 BRIGHT A_Pain - Goto See - Death: - SKUL F 6 BRIGHT - SKUL G 6 BRIGHT A_Scream - SKUL H 6 BRIGHT - SKUL I 6 BRIGHT A_NoBlocking - SKUL J 6 - SKUL K 6 - Stop - } -} - -Actor BetaSkull : LostSoul -{ - States - { - Spawn: - SKUL A 10 A_Look - Loop - See: - SKUL BCDA 5 A_Chase - Loop - Missile: - SKUL E 4 A_FaceTarget - SKUL F 5 A_BetaSkullAttack - SKUL F 4 - Goto See - Pain: - SKUL G 4 - SKUL H 2 A_Pain - Goto See - SKUL I 4 - Goto See - Death: - SKUL JKLM 5 - SKUL N 5 A_Scream - SKUL O 5 - SKUL P 5 A_Fall - SKUL Q 5 A_Stop - Wait - } -} diff --git a/wadsrc/static/actors/doom/painelemental.txt b/wadsrc/static/actors/doom/painelemental.txt deleted file mode 100644 index bba475650..000000000 --- a/wadsrc/static/actors/doom/painelemental.txt +++ /dev/null @@ -1,50 +0,0 @@ -//=========================================================================== -// -// Pain Elemental -// -//=========================================================================== -ACTOR PainElemental -{ - Health 400 - Radius 31 - Height 56 - Mass 400 - Speed 8 - PainChance 128 - Monster - +FLOAT - +NOGRAVITY - SeeSound "pain/sight" - PainSound "pain/pain" - DeathSound "pain/death" - ActiveSound "pain/active" - States - { - Spawn: - PAIN A 10 A_Look - Loop - See: - PAIN AABBCC 3 A_Chase - Loop - Missile: - PAIN D 5 A_FaceTarget - PAIN E 5 A_FaceTarget - PAIN F 5 BRIGHT A_FaceTarget - PAIN F 0 BRIGHT A_PainAttack - Goto See - Pain: - PAIN G 6 - PAIN G 6 A_Pain - Goto See - Death: - PAIN H 8 BRIGHT - PAIN I 8 BRIGHT A_Scream - PAIN JK 8 BRIGHT - PAIN L 8 BRIGHT A_PainDie - PAIN M 8 BRIGHT - Stop - Raise: - PAIN MLKJIH 8 - Goto See - } -} diff --git a/wadsrc/static/actors/doom/possessed.txt b/wadsrc/static/actors/doom/possessed.txt deleted file mode 100644 index 6961cc8a5..000000000 --- a/wadsrc/static/actors/doom/possessed.txt +++ /dev/null @@ -1,241 +0,0 @@ - -//=========================================================================== -// -// Zombie man -// -//=========================================================================== -ACTOR ZombieMan -{ - Health 20 - Radius 20 - Height 56 - Speed 8 - PainChance 200 - Monster - +FLOORCLIP - SeeSound "grunt/sight" - AttackSound "grunt/attack" - PainSound "grunt/pain" - DeathSound "grunt/death" - ActiveSound "grunt/active" - Obituary "$OB_ZOMBIE" - DropItem "Clip" - States - { - Spawn: - POSS AB 10 A_Look - Loop - See: - POSS AABBCCDD 4 A_Chase - Loop - Missile: - POSS E 10 A_FaceTarget - POSS F 8 A_PosAttack - POSS E 8 - Goto See - Pain: - POSS G 3 - POSS G 3 A_Pain - Goto See - Death: - POSS H 5 - POSS I 5 A_Scream - POSS J 5 A_NoBlocking - POSS K 5 - POSS L -1 - Stop - XDeath: - POSS M 5 - POSS N 5 A_XScream - POSS O 5 A_NoBlocking - POSS PQRST 5 - POSS U -1 - Stop - Raise: - POSS K 5 - POSS JIH 5 - Goto See - } -} - -//=========================================================================== -// -// Sergeant / Shotgun guy -// -//=========================================================================== -ACTOR ShotgunGuy -{ - Health 30 - Radius 20 - Height 56 - Mass 100 - Speed 8 - PainChance 170 - Monster - +FLOORCLIP - SeeSound "shotguy/sight" - AttackSound "shotguy/attack" - PainSound "shotguy/pain" - DeathSound "shotguy/death" - ActiveSound "shotguy/active" - Obituary "$OB_SHOTGUY" - DropItem "Shotgun" - States - { - Spawn: - SPOS AB 10 A_Look - Loop - See: - SPOS AABBCCDD 3 A_Chase - Loop - Missile: - SPOS E 10 A_FaceTarget - SPOS F 10 BRIGHT A_SposAttackUseAtkSound - SPOS E 10 - Goto See - Pain: - SPOS G 3 - SPOS G 3 A_Pain - Goto See - Death: - SPOS H 5 - SPOS I 5 A_Scream - SPOS J 5 A_NoBlocking - SPOS K 5 - SPOS L -1 - Stop - XDeath: - SPOS M 5 - SPOS N 5 A_XScream - SPOS O 5 A_NoBlocking - SPOS PQRST 5 - SPOS U -1 - Stop - Raise: - SPOS L 5 - SPOS KJIH 5 - Goto See - } -} - -//=========================================================================== -// -// Chaingunner -// -//=========================================================================== -ACTOR ChaingunGuy -{ - Health 70 - Radius 20 - Height 56 - Mass 100 - Speed 8 - PainChance 170 - Monster - +FLOORCLIP - SeeSound "chainguy/sight" - PainSound "chainguy/pain" - DeathSound "chainguy/death" - ActiveSound "chainguy/active" - AttackSound "chainguy/attack" - Obituary "$OB_CHAINGUY" - Dropitem "Chaingun" - States - { - Spawn: - CPOS AB 10 A_Look - Loop - See: - CPOS AABBCCDD 3 A_Chase - Loop - Missile: - CPOS E 10 A_FaceTarget - CPOS FE 4 BRIGHT A_CPosAttack - CPOS F 1 A_CPosRefire - Goto Missile+1 - Pain: - CPOS G 3 - CPOS G 3 A_Pain - Goto See - Death: - CPOS H 5 - CPOS I 5 A_Scream - CPOS J 5 A_NoBlocking - CPOS KLM 5 - CPOS N -1 - Stop - XDeath: - CPOS O 5 - CPOS P 5 A_XScream - CPOS Q 5 A_NoBlocking - CPOS RS 5 - CPOS T -1 - Stop - Raise: - CPOS N 5 - CPOS MLKJIH 5 - Goto See - } -} - -//=========================================================================== -// -// SS Nazi -// -//=========================================================================== -ACTOR WolfensteinSS -{ - Health 50 - Radius 20 - Height 56 - Speed 8 - PainChance 170 - Monster - +FLOORCLIP - SeeSound "wolfss/sight" - PainSound "wolfss/pain" - DeathSound "wolfss/death" - ActiveSound "wolfss/active" - AttackSound "wolfss/attack" - Obituary "$OB_WOLFSS" - Dropitem "Clip" - States - { - Spawn: - SSWV AB 10 A_Look - Loop - See: - SSWV AABBCCDD 3 A_Chase - Loop - Missile: - SSWV E 10 A_FaceTarget - SSWV F 10 A_FaceTarget - SSWV G 4 BRIGHT A_CPosAttack - SSWV F 6 A_FaceTarget - SSWV G 4 BRIGHT A_CPosAttack - SSWV F 1 A_CPosRefire - Goto Missile+1 - Pain: - SSWV H 3 - SSWV H 3 A_Pain - Goto See - Death: - SSWV I 5 - SSWV J 5 A_Scream - SSWV K 5 A_NoBlocking - SSWV L 5 - SSWV M -1 - Stop - XDeath: - SSWV N 5 - SSWV O 5 A_XScream - SSWV P 5 A_NoBlocking - SSWV QRSTU 5 - SSWV V -1 - Stop - Raise: - SSWV M 5 - SSWV LKJI 5 - Goto See - } -} diff --git a/wadsrc/static/actors/doom/revenant.txt b/wadsrc/static/actors/doom/revenant.txt deleted file mode 100644 index 4062647f4..000000000 --- a/wadsrc/static/actors/doom/revenant.txt +++ /dev/null @@ -1,113 +0,0 @@ -//=========================================================================== -// -// Revenant -// -//=========================================================================== -ACTOR Revenant -{ - Health 300 - Radius 20 - Height 56 - Mass 500 - Speed 10 - PainChance 100 - Monster - MeleeThreshold 196 - +MISSILEMORE - +FLOORCLIP - SeeSound "skeleton/sight" - PainSound "skeleton/pain" - DeathSound "skeleton/death" - ActiveSound "skeleton/active" - MeleeSound "skeleton/melee" - HitObituary "$OB_UNDEADHIT" - Obituary "$OB_UNDEAD" - States - { - Spawn: - SKEL AB 10 A_Look - Loop - See: - SKEL AABBCCDDEEFF 2 A_Chase - Loop - Melee: - SKEL G 0 A_FaceTarget - SKEL G 6 A_SkelWhoosh - SKEL H 6 A_FaceTarget - SKEL I 6 A_SkelFist - Goto See - Missile: - SKEL J 0 BRIGHT A_FaceTarget - SKEL J 10 BRIGHT A_FaceTarget - SKEL K 10 A_SkelMissile - SKEL K 10 A_FaceTarget - Goto See - Pain: - SKEL L 5 - SKEL L 5 A_Pain - Goto See - Death: - SKEL LM 7 - SKEL N 7 A_Scream - SKEL O 7 A_NoBlocking - SKEL P 7 - SKEL Q -1 - Stop - Raise: - SKEL Q 5 - SKEL PONML 5 - Goto See - } -} - - -//=========================================================================== -// -// Revenant Tracer -// -//=========================================================================== -ACTOR RevenantTracer -{ - Radius 11 - Height 8 - Speed 10 - Damage 10 - Projectile - +SEEKERMISSILE - +RANDOMIZE - SeeSound "skeleton/attack" - DeathSound "skeleton/tracex" - RenderStyle Add - States - { - Spawn: - FATB AB 2 BRIGHT A_Tracer - Loop - Death: - FBXP A 8 BRIGHT - FBXP B 6 BRIGHT - FBXP C 4 BRIGHT - Stop - } -} - - -//=========================================================================== -// -// Revenant Tracer Smoke -// -//=========================================================================== -ACTOR RevenantTracerSmoke -{ - +NOBLOCKMAP - +NOGRAVITY - +NOTELEPORT - RenderStyle Translucent - Alpha 0.5 - States - { - Spawn: - PUFF ABABC 4 - Stop - } -} diff --git a/wadsrc/static/actors/doom/scriptedmarine.txt b/wadsrc/static/actors/doom/scriptedmarine.txt deleted file mode 100644 index 73de9a49d..000000000 --- a/wadsrc/static/actors/doom/scriptedmarine.txt +++ /dev/null @@ -1,306 +0,0 @@ - -// Scriptable marine ------------------------------------------------------- - -ACTOR ScriptedMarine native -{ - Health 100 - Radius 16 - Height 56 - Mass 100 - Speed 8 - Painchance 160 - MONSTER - -COUNTKILL - Translation 0 - Damage 100 - DeathSound "*death" - PainSound "*pain50" - - action native A_M_Refire (bool ignoremissile=false); - action native A_M_CheckAttack (); - action native A_MarineChase (); - action native A_MarineLook (); - action native A_MarineNoise (); - action native A_M_Punch (int force); - action native A_M_SawRefire (); - action native A_M_FirePistol (bool accurate); - action native A_M_FireShotgun (); - action native A_M_FireShotgun2 (); - action native A_M_FireCGun(bool accurate); - action native A_M_FireMissile (); - action native A_M_FirePlasma (); - action native A_M_FireRailgun (); - action native A_M_BFGsound (); - action native A_M_FireBFG (); - - States - { - Spawn: - PLAY A 4 A_MarineLook - PLAY A 4 A_MarineNoise - Loop - Idle: - PLAY A 4 A_MarineLook - PLAY A 4 A_MarineNoise - PLAY A 4 A_MarineLook - PLAY B 4 A_MarineNoise - PLAY B 4 A_MarineLook - PLAY B 4 A_MarineNoise - Loop - See: - PLAY ABCD 4 A_MarineChase - Loop - - Melee.Fist: - PLAY E 4 A_FaceTarget - PLAY E 4 A_M_Punch(1) - PLAY A 9 - PLAY A 0 A_M_Refire(1) - Loop - PLAY A 5 A_FaceTarget - Goto See - Melee.Berserk: - PLAY E 4 A_FaceTarget - PLAY E 4 A_M_Punch(10) - PLAY A 9 - PLAY A 0 A_M_Refire(1) - Loop - PLAY A 5 A_FaceTarget - Goto See - Melee.Chainsaw: - PLAY E 4 A_MarineNoise - PLAY E 4 A_M_Saw - PLAY E 0 A_M_SawRefire - goto Melee.Chainsaw+1 - PLAY A 0 - Goto See - - Missile: - Missile.None: - PLAY E 12 A_FaceTarget - Goto Idle - PLAY F 6 BRIGHT - Loop - Missile.Pistol: - PLAY E 4 A_FaceTarget - PLAY F 6 BRIGHT A_M_FirePistol(1) - PLAY A 4 A_FaceTarget - PLAY A 0 A_M_Refire - PLAY A 5 - Goto See - Fireloop.Pistol: - PLAY F 6 BRIGHT A_M_FirePistol(0) - PLAY A 4 A_FaceTarget - PLAY A 0 A_M_Refire - Goto Fireloop.Pistol - PLAY A 5 - Goto See - Missile.Shotgun: - PLAY E 3 A_M_CheckAttack - PLAY F 7 BRIGHT A_M_FireShotgun - Goto See - Missile.SSG: - PLAY E 3 A_M_CheckAttack - PLAY F 7 BRIGHT A_M_FireShotgun2 - Goto See - Missile.Chaingun: - PLAY E 4 A_FaceTarget - PLAY FF 4 BRIGHT A_M_FireCGun(1) - PLAY FF 4 BRIGHT A_M_FireCGun(0) - PLAY A 0 A_M_Refire - Goto Missile.Chaingun+3 - PLAY A 0 - Goto See - Missile.Rocket: - PLAY E 8 - PLAY F 6 BRIGHT A_M_FireMissile - PLAY E 6 - PLAY A 0 A_M_Refire - Loop - PLAY A 0 - Goto See - Missile.Plasma: - PLAY E 2 A_FaceTarget - PLAY E 0 A_FaceTarget - PLAY F 3 BRIGHT A_M_FirePlasma - PLAY A 0 A_M_Refire - Goto Missile.Plasma+1 - PLAY A 0 - Goto See - Missile.Railgun: - PLAY E 4 A_M_CheckAttack - PLAY F 6 BRIGHT A_M_FireRailgun - Goto See - Missile.BFG: - PLAY E 5 A_M_BFGSound - PLAY EEEEE 5 A_FaceTarget - PLAY F 6 BRIGHT A_M_FireBFG - PLAY A 4 A_FaceTarget - PLAY A 0 A_M_Refire - Loop - PLAY A 0 - Goto See - - SkipAttack: - PLAY A 1 - Goto See - Pain: - PLAY G 4 - PLAY G 4 A_Pain - Goto Idle - Death: - PLAY H 10 - PLAY I 10 A_Scream - PLAY J 10 A_NoBlocking - PLAY KLM 10 - PLAY N -1 - Stop - XDeath: - PLAY O 5 - PLAY P 5 A_XScream - PLAY Q 5 A_NoBlocking - PLAY RSTUV 5 - PLAY W -1 - Stop - Raise: - PLAY MLKJIH 5 - Goto See - } -} - -//--------------------------------------------------------------------------- - -ACTOR MarineFist : ScriptedMarine -{ - States - { - Melee: - Goto Super::Melee.Fist - Missile: - Stop - } -} - - -//--------------------------------------------------------------------------- - -ACTOR MarineBerserk : MarineFist -{ - States - { - Melee: - Goto Super::Melee.Berserk - Missile: - Stop - } -} -//--------------------------------------------------------------------------- - -ACTOR MarineChainsaw : ScriptedMarine -{ - States - { - Melee: - Goto Super::Melee.Chainsaw - Missile: - Stop - } -} - - - -//--------------------------------------------------------------------------- - -ACTOR MarinePistol : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.Pistol - } - -} - -//--------------------------------------------------------------------------- - -ACTOR MarineShotgun : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.Shotgun - } - -} - - - -//--------------------------------------------------------------------------- - -ACTOR MarineSSG : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.SSG - } -} - -//--------------------------------------------------------------------------- - -ACTOR MarineChaingun : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.Chaingun - } -} - - -//--------------------------------------------------------------------------- - -ACTOR MarineRocket : MarineFist -{ - States - { - Missile: - Goto Super::Missile.Rocket - } - -} - -//--------------------------------------------------------------------------- - -ACTOR MarinePlasma : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.Plasma - } - -} - -//--------------------------------------------------------------------------- - -ACTOR MarineRailgun : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.Railgun - } - -} - -//--------------------------------------------------------------------------- - -ACTOR MarineBFG : ScriptedMarine -{ - States - { - Missile: - Goto Super::Missile.BFG - } -} diff --git a/wadsrc/static/actors/doom/spidermaster.txt b/wadsrc/static/actors/doom/spidermaster.txt deleted file mode 100644 index e087b3fb3..000000000 --- a/wadsrc/static/actors/doom/spidermaster.txt +++ /dev/null @@ -1,59 +0,0 @@ -//=========================================================================== -// -// Spider boss -// -//=========================================================================== -ACTOR SpiderMastermind -{ - Health 3000 - Radius 128 - Height 100 - Mass 1000 - Speed 12 - PainChance 40 - Monster - MinMissileChance 160 - +BOSS - +MISSILEMORE - +FLOORCLIP - +NORADIUSDMG - +DONTMORPH - +BOSSDEATH - SeeSound "spider/sight" - AttackSound "spider/attack" - PainSound "spider/pain" - DeathSound "spider/death" - ActiveSound "spider/active" - Obituary "$OB_SPIDER" - States - { - Spawn: - SPID AB 10 A_Look - Loop - See: - SPID A 3 A_Metal - SPID ABB 3 A_Chase - SPID C 3 A_Metal - SPID CDD 3 A_Chase - SPID E 3 A_Metal - SPID EFF 3 A_Chase - Loop - Missile: - SPID A 20 BRIGHT A_FaceTarget - SPID G 4 BRIGHT A_SPosAttackUseAtkSound - SPID H 4 BRIGHT A_SposAttackUseAtkSound - SPID H 1 BRIGHT A_SpidRefire - Goto Missile+1 - Pain: - SPID I 3 - SPID I 3 A_Pain - Goto See - Death: - SPID J 20 A_Scream - SPID K 10 A_NoBlocking - SPID LMNOPQR 10 - SPID S 30 - SPID S -1 A_BossDeath - Stop - } -} diff --git a/wadsrc/static/actors/doom/stealthmonsters.txt b/wadsrc/static/actors/doom/stealthmonsters.txt deleted file mode 100644 index 275537485..000000000 --- a/wadsrc/static/actors/doom/stealthmonsters.txt +++ /dev/null @@ -1,103 +0,0 @@ - -ACTOR StealthArachnotron : Arachnotron -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHBABY" -} - -ACTOR StealthArchvile : Archvile -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHVILE" -} - -ACTOR StealthBaron : BaronOfHell -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHBARON" - HitObituary "$OB_STEALTHBARON" -} - -ACTOR StealthCacodemon : Cacodemon -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHCACO" - HitObituary "$OB_STEALTHCACO" -} - -ACTOR StealthChaingunGuy : ChaingunGuy -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHCHAINGUY" -} - -ACTOR StealthDemon : Demon -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHDEMON" - HitObituary "$OB_STEALTHDEMON" -} - -ACTOR StealthHellKnight : HellKnight -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHKNIGHT" - HitObituary "$OB_STEALTHKNIGHT" -} - -ACTOR StealthDoomImp : DoomImp -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHIMP" - HitObituary "$OB_STEALTHIMP" -} - -ACTOR StealthFatso : Fatso -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHFATSO" -} - -ACTOR StealthRevenant : Revenant -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHUNDEAD" - HitObituary "$OB_STEALTHUNDEAD" -} - -ACTOR StealthShotgunGuy : ShotgunGuy -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHSHOTGUNGUY" -} - -ACTOR StealthZombieMan : ZombieMan -{ - +STEALTH - RenderStyle Translucent - Alpha 0 - Obituary "$OB_STEALTHZOMBIE" -} - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 079d8fa6a..1ae7d7328 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,32 +1,3 @@ -#include "actors/doom/doomplayer.txt" -#include "actors/doom/possessed.txt" -#include "actors/doom/doomimp.txt" -#include "actors/doom/demon.txt" -#include "actors/doom/lostsoul.txt" -#include "actors/doom/cacodemon.txt" -#include "actors/doom/bruiser.txt" -#include "actors/doom/revenant.txt" -#include "actors/doom/arachnotron.txt" -#include "actors/doom/fatso.txt" -#include "actors/doom/painelemental.txt" -#include "actors/doom/archvile.txt" -#include "actors/doom/cyberdemon.txt" -#include "actors/doom/spidermaster.txt" -#include "actors/doom/keen.txt" -#include "actors/doom/bossbrain.txt" - -#include "actors/doom/deadthings.txt" -#include "actors/doom/doomammo.txt" -#include "actors/doom/doomarmor.txt" -#include "actors/doom/doomartifacts.txt" -#include "actors/doom/doomhealth.txt" -#include "actors/doom/doomkeys.txt" -#include "actors/doom/doommisc.txt" -#include "actors/doom/doomdecorations.txt" -#include "actors/doom/doomweapons.txt" -#include "actors/doom/stealthmonsters.txt" -#include "actors/doom/scriptedmarine.txt" - #include "actors/raven/artiegg.txt" #include "actors/raven/artitele.txt" #include "actors/raven/ravenartifacts.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 9ba69ceef..73bb467d8 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -30,6 +30,34 @@ zscript/shared/setcolor.txt zscript/shared/sectoraction.txt zscript/shared/dog.txt +zscript/doom/doomplayer.txt +zscript/doom/possessed.txt +zscript/doom/doomimp.txt +zscript/doom/demon.txt +zscript/doom/lostsoul.txt +zscript/doom/cacodemon.txt +zscript/doom/bruiser.txt +zscript/doom/revenant.txt +zscript/doom/arachnotron.txt +zscript/doom/fatso.txt +zscript/doom/painelemental.txt +zscript/doom/archvile.txt +zscript/doom/cyberdemon.txt +zscript/doom/spidermaster.txt +zscript/doom/keen.txt +zscript/doom/bossbrain.txt + +zscript/doom/deadthings.txt +zscript/doom/doomammo.txt +zscript/doom/doomarmor.txt +zscript/doom/doomartifacts.txt +zscript/doom/doomhealth.txt +zscript/doom/doomkeys.txt +zscript/doom/doommisc.txt +zscript/doom/doomdecorations.txt +zscript/doom/doomweapons.txt +zscript/doom/stealthmonsters.txt +zscript/doom/scriptedmarine.txt //zscript/test1.txt diff --git a/wadsrc/static/zscript/doom/arachnotron.txt b/wadsrc/static/zscript/doom/arachnotron.txt new file mode 100644 index 000000000..e3aa17d48 --- /dev/null +++ b/wadsrc/static/zscript/doom/arachnotron.txt @@ -0,0 +1,91 @@ +//=========================================================================== +// +// Arachnotron +// +//=========================================================================== +class Arachnotron : Actor +{ + Default + { + Health 500; + Radius 64; + Height 64; + Mass 600; + Speed 12; + PainChance 128; + Monster; + +FLOORCLIP + +BOSSDEATH + SeeSound "baby/sight"; + PainSound "baby/pain"; + DeathSound "baby/death"; + ActiveSound "baby/active"; + Obituary "$OB_BABY"; + } + States + { + Spawn: + BSPI AB 10 A_Look; + Loop; + See: + BSPI A 20; + BSPI A 3 A_BabyMetal; + BSPI ABBCC 3 A_Chase; + BSPI D 3 A_BabyMetal; + BSPI DEEFF 3 A_Chase; + Goto See+1; + Missile: + BSPI A 20 BRIGHT A_FaceTarget; + BSPI G 4 BRIGHT A_BspiAttack; + BSPI H 4 BRIGHT; + BSPI H 1 BRIGHT A_SpidRefire; + Goto Missile+1; + Pain: + BSPI I 3; + BSPI I 3 A_Pain; + Goto See+1; + Death: + BSPI J 20 A_Scream; + BSPI K 7 A_NoBlocking; + BSPI LMNO 7; + BSPI P -1 A_BossDeath; + Stop; + Raise: + BSPI P 5; + BSPI ONMLKJ 5; + Goto See+1; + } +} + +//=========================================================================== +// +// Arachnotron plasma +// +//=========================================================================== +class ArachnotronPlasma : Actor +{ + Default + { + Radius 13; + Height 8; + Speed 25; + Damage 5; + Projectile; + +RANDOMIZE + RenderStyle "Add"; + Alpha 0.75; + SeeSound "baby/attack"; + DeathSound "baby/shotx"; + } + States + { + Spawn: + APLS AB 5 BRIGHT; + Loop; + Death: + APBX ABCDE 5 BRIGHT; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/doom/archvile.txt b/wadsrc/static/zscript/doom/archvile.txt new file mode 100644 index 000000000..bdca2b05f --- /dev/null +++ b/wadsrc/static/zscript/doom/archvile.txt @@ -0,0 +1,89 @@ +//=========================================================================== +// +// Arch Vile +// +//=========================================================================== + +class Archvile : Actor +{ + Default + { + Health 700; + Radius 20; + Height 56; + Mass 500; + Speed 15; + PainChance 10; + Monster; + MaxTargetRange 896; + +QUICKTORETALIATE + +FLOORCLIP + +NOTARGET + SeeSound "vile/sight"; + PainSound "vile/pain"; + DeathSound "vile/death"; + ActiveSound "vile/active"; + MeleeSound "vile/stop"; + Obituary "$OB_VILE"; + } + States + { + Spawn: + VILE AB 10 A_Look; + Loop; + See: + VILE AABBCCDDEEFF 2 A_VileChase; + Loop; + Missile: + VILE G 0 BRIGHT A_VileStart; + VILE G 10 BRIGHT A_FaceTarget; + VILE H 8 BRIGHT A_VileTarget; + VILE IJKLMN 8 BRIGHT A_FaceTarget; + VILE O 8 BRIGHT A_VileAttack; + VILE P 20 BRIGHT; + Goto See; + Heal: + VILE [\] 10 BRIGHT; + Goto See; + Pain: + VILE Q 5; + VILE Q 5 A_Pain; + Goto See; + Death: + VILE Q 7; + VILE R 7 A_Scream; + VILE S 7 A_NoBlocking; + VILE TUVWXY 7; + VILE Z -1; + Stop; + } +} + + +//=========================================================================== +// +// Arch Vile Fire +// +//=========================================================================== + +class ArchvileFire : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Add"; + Alpha 1; + } + States + { + Spawn: + FIRE A 2 BRIGHT A_StartFire; + FIRE BAB 2 BRIGHT A_Fire; + FIRE C 2 BRIGHT A_FireCrackle; + FIRE BCBCDCDCDEDED 2 BRIGHT A_Fire; + FIRE E 2 BRIGHT A_FireCrackle; + FIRE FEFEFGHGHGH 2 BRIGHT A_Fire; + Stop; + } +} + diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt new file mode 100644 index 000000000..533d0fa01 --- /dev/null +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -0,0 +1,135 @@ + +//=========================================================================== +// +// Boss Brain +// +//=========================================================================== + +class BossBrain : Actor +{ + Default + { + Health 250; + Mass 10000000; + PainChance 255; + +SOLID +SHOOTABLE + +NOICEDEATH + +OLDRADIUSDMG + PainSound "brain/pain"; + DeathSound "brain/death"; + } + States + { + BrainExplode: + MISL BC 10 Bright; + MISL D 10 A_BrainExplode; + Stop; + Spawn: + BBRN A -1; + Stop; + Pain: + BBRN B 36 A_BrainPain; + Goto Spawn; + Death: + BBRN A 100 A_BrainScream; + BBRN AA 10; + BBRN A -1 A_BrainDie; + Stop; + } +} + + +//=========================================================================== +// +// Boss Eye +// +//=========================================================================== + +class BossEye : Actor +{ + Default + { + Height 32; + +NOBLOCKMAP + +NOSECTOR + } + States + { + Spawn: + SSWV A 10 A_Look; + Loop; + See: + SSWV A 181 A_BrainAwake; + SSWV A 150 A_BrainSpit; + Wait; + } +} + +//=========================================================================== +// +// Boss Target +// +//=========================================================================== + +class BossTarget : SpecialSpot +{ + Default + { + Height 32; + +NOBLOCKMAP; + +NOSECTOR; + } +} + +//=========================================================================== +// +// Spawn shot +// +//=========================================================================== + +class SpawnShot : Actor +{ + Default + { + Radius 6; + Height 32; + Speed 10; + Damage 3; + Projectile; + +NOCLIP + -ACTIVATEPCROSS + +RANDOMIZE + SeeSound "brain/spit"; + DeathSound "brain/cubeboom"; + } + States + { + Spawn: + BOSF A 3 BRIGHT A_SpawnSound; + BOSF BCD 3 BRIGHT A_SpawnFly; + Loop; + } +} + +//=========================================================================== +// +// Spawn fire +// +//=========================================================================== + +class SpawnFire : Actor +{ + Default + { + Height 78; + +NOBLOCKMAP + +NOGRAVITY + RenderStyle "Add"; + } + States + { + Spawn: + FIRE ABCDEFGH 4 Bright A_Fire; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/bruiser.txt b/wadsrc/static/zscript/doom/bruiser.txt new file mode 100644 index 000000000..bbeb319f6 --- /dev/null +++ b/wadsrc/static/zscript/doom/bruiser.txt @@ -0,0 +1,140 @@ +//=========================================================================== +// +// Baron of Hell +// +//=========================================================================== +class BaronOfHell : Actor +{ + Default + { + Health 1000; + Radius 24; + Height 64; + Mass 1000; + Speed 8; + PainChance 50; + Monster; + +FLOORCLIP + +BOSSDEATH + SeeSound "baron/sight"; + PainSound "baron/pain"; + DeathSound "baron/death"; + ActiveSound "baron/active"; + Obituary "$OB_BARON"; + HitObituary "$OB_BARONHIT"; + } + States + { + Spawn: + BOSS AB 10 A_Look ; + Loop; + See: + BOSS AABBCCDD 3 A_Chase; + Loop; + Melee: + Missile: + BOSS EF 8 A_FaceTarget; + BOSS G 8 A_BruisAttack; + Goto See; + Pain: + BOSS H 2; + BOSS H 2 A_Pain; + Goto See; + Death: + BOSS I 8; + BOSS J 8 A_Scream; + BOSS K 8; + BOSS L 8 A_NoBlocking; + BOSS MN 8; + BOSS O -1 A_BossDeath; + Stop; + Raise: + BOSS O 8; + BOSS NMLKJI 8; + Goto See; + } +} + +//=========================================================================== +// +// Hell Knight +// +//=========================================================================== +class HellKnight : BaronOfHell +{ + Default + { + Health 500; + -BOSSDEATH; + SeeSound "knight/sight"; + ActiveSound "knight/active"; + PainSound "knight/pain"; + DeathSound "knight/death"; + HitObituary "$OB_KNIGHTHIT"; + Obituary "$OB_KNIGHT"; + } + States + { + Spawn: + BOS2 AB 10 A_Look; + Loop; + See: + BOS2 AABBCCDD 3 A_Chase; + Loop; + Melee: + Missile: + BOS2 EF 8 A_FaceTarget; + BOS2 G 8 A_BruisAttack; + Goto See; + Pain: + BOS2 H 2; + BOS2 H 2 A_Pain; + Goto See; + Death: + BOS2 I 8; + BOS2 J 8 A_Scream; + BOS2 K 8; + BOS2 L 8 A_NoBlocking; + BOS2 MN 8; + BOS2 O -1; + Stop; + Raise: + BOS2 O 8; + BOS2 NMLKJI 8; + Goto See; + } +} + +//=========================================================================== +// +// Baron slime ball +// +//=========================================================================== +class BaronBall : Actor +{ + Default + { + Radius 6; + Height 16; + Speed 15; + FastSpeed 20; + Damage 8; + Projectile ; + +RANDOMIZE + RenderStyle "Add"; + Alpha 1; + SeeSound "baron/attack"; + DeathSound "baron/shotx"; + Decal "BaronScorch"; + } + States + { + Spawn: + BAL7 AB 4 BRIGHT; + Loop; + Death: + BAL7 CDE 6 BRIGHT; + Stop; + } +} + diff --git a/wadsrc/static/zscript/doom/cacodemon.txt b/wadsrc/static/zscript/doom/cacodemon.txt new file mode 100644 index 000000000..6a07feb70 --- /dev/null +++ b/wadsrc/static/zscript/doom/cacodemon.txt @@ -0,0 +1,88 @@ +//=========================================================================== +// +// Cacodemon +// +//=========================================================================== +class Cacodemon : Actor +{ + Default + { + Health 400; + Radius 31; + Height 56; + Mass 400; + Speed 8; + PainChance 128; + Monster; + +FLOAT +NOGRAVITY + SeeSound "caco/sight"; + PainSound "caco/pain"; + DeathSound "caco/death"; + ActiveSound "caco/active"; + Obituary "$OB_CACO"; + HitObituary "$OB_CACOHIT"; + } + States + { + Spawn: + HEAD A 10 A_Look; + Loop; + See: + HEAD A 3 A_Chase; + Loop; + Missile: + HEAD B 5 A_FaceTarget; + HEAD C 5 A_FaceTarget; + HEAD D 5 BRIGHT A_HeadAttack; + Goto See; + Pain: + HEAD E 3; + HEAD E 3 A_Pain; + HEAD F 6; + Goto See; + Death: + HEAD G 8; + HEAD H 8 A_Scream; + HEAD I 8; + HEAD J 8; + HEAD K 8 A_NoBlocking; + HEAD L -1 A_SetFloorClip; + Stop; + Raise: + HEAD L 8 A_UnSetFloorClip; + HEAD KJIHG 8; + Goto See; + } +} + +//=========================================================================== +// +// Cacodemon plasma ball +// +//=========================================================================== +class CacodemonBall : Actor +{ + Default + { + Radius 6; + Height 8; + Speed 10; + FastSpeed 20; + Damage 5; + Projectile; + +RANDOMIZE + RenderStyle "Add"; + Alpha 1; + SeeSound "caco/attack"; + DeathSound "caco/shotx"; + } + States + { + Spawn: + BAL2 AB 4 BRIGHT; + Loop; + Death: + BAL2 CDE 6 BRIGHT; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/cyberdemon.txt b/wadsrc/static/zscript/doom/cyberdemon.txt new file mode 100644 index 000000000..75f4fd211 --- /dev/null +++ b/wadsrc/static/zscript/doom/cyberdemon.txt @@ -0,0 +1,64 @@ + +//=========================================================================== +// +// Cyberdemon +// +//=========================================================================== +class Cyberdemon : Actor +{ + Default + { + Health 4000; + Radius 40; + Height 110; + Mass 1000; + Speed 16; + PainChance 20; + Monster; + MinMissileChance 160; + +BOSS + +MISSILEMORE + +FLOORCLIP + +NORADIUSDMG + +DONTMORPH + +BOSSDEATH + SeeSound "cyber/sight"; + PainSound "cyber/pain"; + DeathSound "cyber/death"; + ActiveSound "cyber/active"; + Obituary "$OB_CYBORG"; + } + States + { + Spawn: + CYBR AB 10 A_Look; + Loop; + See: + CYBR A 3 A_Hoof; + CYBR ABBCC 3 A_Chase; + CYBR D 3 A_Metal; + CYBR D 3 A_Chase; + Loop; + Missile: + CYBR E 6 A_FaceTarget; + CYBR F 12 A_CyberAttack; + CYBR E 12 A_FaceTarget; + CYBR F 12 A_CyberAttack; + CYBR E 12 A_FaceTarget; + CYBR F 12 A_CyberAttack; + Goto See; + Pain: + CYBR G 10 A_Pain; + Goto See; + Death: + CYBR H 10; + CYBR I 10 A_Scream; + CYBR JKL 10; + CYBR M 10 A_NoBlocking; + CYBR NO 10; + CYBR P 30; + CYBR P -1 A_BossDeath; + Stop; + } +} + diff --git a/wadsrc/static/actors/doom/deadthings.txt b/wadsrc/static/zscript/doom/deadthings.txt similarity index 67% rename from wadsrc/static/actors/doom/deadthings.txt rename to wadsrc/static/zscript/doom/deadthings.txt index f90d35eef..3a7e47610 100644 --- a/wadsrc/static/actors/doom/deadthings.txt +++ b/wadsrc/static/zscript/doom/deadthings.txt @@ -1,30 +1,30 @@ // Gibbed marine ----------------------------------------------------------- -actor GibbedMarine +class GibbedMarine : Actor { States { Spawn: - PLAY W -1 - Stop + PLAY W -1; + Stop; } } // Gibbed marine (extra copy) ---------------------------------------------- -actor GibbedMarineExtra : GibbedMarine +class GibbedMarineExtra : GibbedMarine { } // Dead marine ------------------------------------------------------------- -actor DeadMarine +class DeadMarine : Actor { States { Spawn: - PLAY N -1 - Stop + PLAY N -1; + Stop; } } @@ -35,63 +35,78 @@ actor DeadMarine // Dead zombie man --------------------------------------------------------- -actor DeadZombieMan : ZombieMan +class DeadZombieMan : ZombieMan { - Skip_Super - DropItem None + Default + { + Skip_Super; + DropItem "None"; + } States { Spawn: - Goto Super::Death+4 + Goto Super::Death+4; } } // Dead shotgun guy -------------------------------------------------------- -actor DeadShotgunGuy : ShotgunGuy +class DeadShotgunGuy : ShotgunGuy { - Skip_Super - DropItem None + Default + { + Skip_Super; + DropItem "None"; + } States { Spawn: - Goto Super::Death+4 + Goto Super::Death+4; } } // Dead imp ---------------------------------------------------------------- -actor DeadDoomImp : DoomImp +class DeadDoomImp : DoomImp { - Skip_Super + Default + { + Skip_Super; + } States { Spawn: - Goto Super::Death+4 + Goto Super::Death+4; } } // Dead demon -------------------------------------------------------------- -actor DeadDemon : Demon +class DeadDemon : Demon { - Skip_Super + Default + { + Skip_Super; + } States { Spawn: - Goto Super::Death+5 + Goto Super::Death+5; } } // Dead cacodemon ---------------------------------------------------------- -actor DeadCacodemon : Cacodemon +class DeadCacodemon : Cacodemon { - Skip_Super + Default + { + Skip_Super; + } States { Spawn: - Goto Super::Death+5 + Goto Super::Death+5; } } @@ -103,12 +118,15 @@ actor DeadCacodemon : Cacodemon * a holdover from that.) */ -actor DeadLostSoul : LostSoul +class DeadLostSoul : LostSoul { - Skip_Super + Default + { + Skip_Super; + } States { Spawn: - Goto Super::Death+5 + Goto Super::Death+5; } } diff --git a/wadsrc/static/zscript/doom/demon.txt b/wadsrc/static/zscript/doom/demon.txt new file mode 100644 index 000000000..398888e45 --- /dev/null +++ b/wadsrc/static/zscript/doom/demon.txt @@ -0,0 +1,77 @@ +//=========================================================================== +// +// Pink Demon +// +//=========================================================================== +class Demon : Actor +{ + Default + { + Health 150; + PainChance 180; + Speed 10; + Radius 30; + Height 56; + Mass 400; + Monster; + +FLOORCLIP + SeeSound "demon/sight"; + AttackSound "demon/melee"; + PainSound "demon/pain"; + DeathSound "demon/death"; + ActiveSound "demon/active"; + Obituary "$OB_DEMONHIT"; + } + States + { + Spawn: + SARG AB 10 A_Look; + Loop; + See: + SARG AABBCCDD 2 Fast A_Chase; + Loop; + Melee: + SARG EF 8 Fast A_FaceTarget; + SARG G 8 Fast A_SargAttack; + Goto See; + Pain: + SARG H 2 Fast; + SARG H 2 Fast A_Pain; + Goto See; + Death: + SARG I 8; + SARG J 8 A_Scream; + SARG K 4; + SARG L 4 A_NoBlocking; + SARG M 4; + SARG N -1; + Stop; + Raise: + SARG N 5; + SARG MLKJI 5; + Goto See; + } +} + +//=========================================================================== +// +// Spectre +// +//=========================================================================== +class Spectre : Demon +{ + Default + { + +SHADOW + RenderStyle "OptFuzzy"; + Alpha 0.5; + SeeSound "spectre/sight"; + AttackSound "spectre/melee"; + PainSound "spectre/pain"; + DeathSound "spectre/death"; + ActiveSound "spectre/active"; + HitObituary "$OB_SPECTREHIT"; + } +} + + diff --git a/wadsrc/static/zscript/doom/doomammo.txt b/wadsrc/static/zscript/doom/doomammo.txt new file mode 100644 index 000000000..394f13e94 --- /dev/null +++ b/wadsrc/static/zscript/doom/doomammo.txt @@ -0,0 +1,169 @@ +// Clip -------------------------------------------------------------------- + +class Clip : Ammo +{ + Default + { + Inventory.PickupMessage "$GOTCLIP"; + Inventory.Amount 10; + Inventory.MaxAmount 200; + Ammo.BackpackAmount 10; + Ammo.BackpackMaxAmount 400; + Inventory.Icon "CLIPA0"; + } + States + { + Spawn: + CLIP A -1; + Stop; + } +} + +// Clip box ---------------------------------------------------------------- + +class ClipBox : Clip +{ + Default + { + Inventory.PickupMessage "$GOTCLIPBOX"; + Inventory.Amount 50; + } + States + { + Spawn: + AMMO A -1; + Stop; + } +} + +// Rocket ------------------------------------------------------------------ + +class RocketAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$GOTROCKET"; + Inventory.Amount 1; + Inventory.MaxAmount 50; + Ammo.BackpackAmount 1; + Ammo.BackpackMaxAmount 100; + Inventory.Icon "ROCKA0"; + } + States + { + Spawn: + ROCK A -1; + Stop; + } +} + +// Rocket box -------------------------------------------------------------- + +class RocketBox : RocketAmmo +{ + Default + { + Inventory.PickupMessage "$GOTROCKBOX"; + Inventory.Amount 5; + } + States + { + Spawn: + BROK A -1; + Stop; + } +} + +// Cell -------------------------------------------------------------------- + +class Cell : Ammo +{ + Default + { + Inventory.PickupMessage "$GOTCELL"; + Inventory.Amount 20; + Inventory.MaxAmount 300; + Ammo.BackpackAmount 20; + Ammo.BackpackMaxAmount 600; + Inventory.Icon "CELLA0"; + } + States + { + Spawn: + CELL A -1; + Stop; + } +} + +// Cell pack --------------------------------------------------------------- + +class CellPack : Cell +{ + Default + { + Inventory.PickupMessage "$GOTCELLBOX"; + Inventory.Amount 100; + } + States + { + Spawn: + CELP A -1; + Stop; + } +} + +// Shells ------------------------------------------------------------------ + +class Shell : Ammo +{ + Default + { + Inventory.PickupMessage "$GOTSHELLS"; + Inventory.Amount 4; + Inventory.MaxAmount 50; + Ammo.BackpackAmount 4; + Ammo.BackpackMaxAmount 100; + Inventory.Icon "SHELA0"; + } + States + { + Spawn: + SHEL A -1; + Stop; + } +} + +// Shell box --------------------------------------------------------------- + +class ShellBox : Shell +{ + Default + { + Inventory.PickupMessage "$GOTSHELLBOX"; + Inventory.Amount 20; + } + States + { + Spawn: + SBOX A -1; + Stop; + } +} + +// Backpack --------------------------------------------------------------- + +class Backpack : BackpackItem +{ + Default + { + Height 26; + Inventory.PickupMessage "$GOTBACKPACK"; + } + States + { + Spawn: + BPAK A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/doom/doomarmor.txt b/wadsrc/static/zscript/doom/doomarmor.txt new file mode 100644 index 000000000..8c3d52cc9 --- /dev/null +++ b/wadsrc/static/zscript/doom/doomarmor.txt @@ -0,0 +1,69 @@ + +// Armor bonus -------------------------------------------------------------- + +class ArmorBonus : BasicArmorBonus +{ + Default + { + Radius 20; + Height 16; + Inventory.Pickupmessage "$GOTARMBONUS"; + Inventory.Icon "ARM1A0"; + Armor.Savepercent 33.335; + Armor.Saveamount 1; + Armor.Maxsaveamount 200; + +COUNTITEM + +INVENTORY.ALWAYSPICKUP + } + States + { + Spawn: + BON2 ABCDCB 6; + loop; + } +} + +// Green armor -------------------------------------------------------------- + +class GreenArmor : BasicArmorPickup +{ + Default + { + Radius 20; + Height 16; + Inventory.Pickupmessage "$GOTARMOR"; + Inventory.Icon "ARM1A0"; + Armor.SavePercent 33.335; + Armor.SaveAmount 100; + } + States + { + Spawn: + ARM1 A 6; + ARM1 B 7 bright; + loop; + } +} + +// Blue armor --------------------------------------------------------------- + +class BlueArmor : BasicArmorPickup +{ + Default + { + Radius 20; + Height 16; + Inventory.Pickupmessage "$GOTMEGA"; + Inventory.Icon "ARM2A0"; + Armor.Savepercent 50; + Armor.Saveamount 200; + } + States + { + Spawn: + ARM2 A 6; + ARM2 B 6 bright; + loop; + } +} + diff --git a/wadsrc/static/zscript/doom/doomartifacts.txt b/wadsrc/static/zscript/doom/doomartifacts.txt new file mode 100644 index 000000000..ad5e304c6 --- /dev/null +++ b/wadsrc/static/zscript/doom/doomartifacts.txt @@ -0,0 +1,201 @@ +// Invulnerability Sphere --------------------------------------------------- + +class InvulnerabilitySphere : PowerupGiver +{ + Default + { + +COUNTITEM + +INVENTORY.AUTOACTIVATE + +INVENTORY.ALWAYSPICKUP + +INVENTORY.BIGPOWERUP + Inventory.MaxAmount 0; + Powerup.Type "PowerInvulnerable"; + Powerup.Color "InverseMap"; + Inventory.PickupMessage "$GOTINVUL"; + } + States + { + Spawn: + PINV ABCD 6 Bright; + Loop; + } +} + +// Soulsphere -------------------------------------------------------------- + +class Soulsphere : Health +{ + Default + { + +COUNTITEM; + +INVENTORY.AUTOACTIVATE; + +INVENTORY.ALWAYSPICKUP; + +INVENTORY.FANCYPICKUPSOUND; + Inventory.Amount 100; + Inventory.MaxAmount 200; + Inventory.PickupMessage "$GOTSUPER"; + Inventory.PickupSound "misc/p_pkup"; + } + States + { + Spawn: + SOUL ABCDCB 6 Bright; + Loop; + } +} + +// Mega sphere -------------------------------------------------------------- + +class MegasphereHealth : Health // for manipulation by Dehacked +{ + Default + { + Inventory.Amount 200; + Inventory.MaxAmount 200; + +INVENTORY.ALWAYSPICKUP + } +} + +// DeHackEd can only modify the blue armor's type, not the megasphere's. +class BlueArmorForMegasphere : BlueArmor +{ + Default + { + Armor.SavePercent 50; + Armor.SaveAmount 200; + } +} + +class Megasphere : CustomInventory +{ + Default + { + +COUNTITEM + +INVENTORY.ALWAYSPICKUP + Inventory.PickupMessage "$GOTMSPHERE"; + Inventory.PickupSound "misc/p_pkup"; + } + States + { + Spawn: + MEGA ABCD 6 BRIGHT; + Loop; + Pickup: + TNT1 A 0 A_GiveInventory("BlueArmorForMegasphere", 1); + TNT1 A 0 A_GiveInventory("MegasphereHealth", 1); + Stop; + } +} + +// Invisibility ------------------------------------------------------------- + +class BlurSphere : PowerupGiver +{ + Default + { + +COUNTITEM + +VISIBILITYPULSE + +INVENTORY.AUTOACTIVATE + +INVENTORY.ALWAYSPICKUP + +INVENTORY.BIGPOWERUP + Inventory.MaxAmount 0; + Powerup.Type "PowerInvisibility"; + RenderStyle "Translucent"; + Inventory.PickupMessage "$GOTINVIS"; + } + States + { + Spawn: + PINS ABCD 6 Bright; + Loop; + } +} + +// Radiation suit (aka iron feet) ------------------------------------------- + +class RadSuit : PowerupGiver +{ + Default + { + Height 46; + +INVENTORY.AUTOACTIVATE + +INVENTORY.ALWAYSPICKUP + Inventory.MaxAmount 0; + Inventory.PickupMessage "$GOTSUIT"; + Powerup.Type "PowerIronFeet"; + } + States + { + Spawn: + SUIT A -1 Bright; + Stop; + } +} + +// infrared ----------------------------------------------------------------- + +class Infrared : PowerupGiver +{ + Default + { + +COUNTITEM + +INVENTORY.AUTOACTIVATE + +INVENTORY.ALWAYSPICKUP + Inventory.MaxAmount 0; + Powerup.Type "PowerLightAmp"; + Inventory.PickupMessage "$GOTVISOR"; + } + States + { + Spawn: + PVIS A 6 Bright; + PVIS B 6; + Loop; + } +} + +// Allmap ------------------------------------------------------------------- + +class Allmap : MapRevealer +{ + Default + { + +COUNTITEM + +INVENTORY.FANCYPICKUPSOUND + +INVENTORY.ALWAYSPICKUP + Inventory.MaxAmount 0; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$GOTMAP"; + } + States + { + Spawn: + PMAP ABCDCB 6 Bright; + Loop; + } +} + +// Berserk ------------------------------------------------------------------ + +class Berserk : CustomInventory +{ + Default + { + +COUNTITEM + +INVENTORY.ALWAYSPICKUP + Inventory.PickupMessage "$GOTBERSERK"; + Inventory.PickupSound "misc/p_pkup"; + } + States + { + Spawn: + PSTR A -1; + Stop; + Pickup: + TNT1 A 0 A_GiveInventory("PowerStrength"); + TNT1 A 0 HealThing(100, 0); + TNT1 A 0 A_SelectWeapon("Fist"); + Stop; + } +} + diff --git a/wadsrc/static/zscript/doom/doomdecorations.txt b/wadsrc/static/zscript/doom/doomdecorations.txt new file mode 100644 index 000000000..8eec812f6 --- /dev/null +++ b/wadsrc/static/zscript/doom/doomdecorations.txt @@ -0,0 +1,900 @@ + +// Tech lamp --------------------------------------------------------------- + +class TechLamp : Actor +{ + Default + { + Radius 16; + Height 80; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TLMP ABCD 4 BRIGHT; + Loop; + } +} + +// Tech lamp 2 ------------------------------------------------------------- + +class TechLamp2 : Actor +{ + Default + { + Radius 16; + Height 60; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TLP2 ABCD 4 BRIGHT; + Loop; + } +} + +// Column ------------------------------------------------------------------ + +class Column : Actor +{ + Default + { + Radius 16; + Height 48; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COLU A -1 BRIGHT; + Stop; + } +} + +// Tall green column ------------------------------------------------------- + +class TallGreenColumn : Actor +{ + Default + { + Radius 16; + Height 52; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COL1 A -1; + Stop; + } +} + +// Short green column ------------------------------------------------------ + +class ShortGreenColumn : Actor +{ + Default + { + Radius 16; + Height 40;; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COL2 A -1; + Stop; + } +} + +// Tall red column --------------------------------------------------------- + +class TallRedColumn : Actor +{ + Default + { + Radius 16; + Height 52; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COL3 A -1; + Stop; + } +} + +// Short red column -------------------------------------------------------- + +class ShortRedColumn : Actor +{ + Default + { + Radius 16; + Height 40; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COL4 A -1; + Stop; + } +} + +// Skull column ------------------------------------------------------------ + +class SkullColumn : Actor +{ + Default + { + Radius 16; + Height 40; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COL6 A -1; + Stop; + } +} + +// Heart column ------------------------------------------------------------ + +class HeartColumn : Actor +{ + Default + { + Radius 16; + Height 40; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + COL5 AB 14; + Loop; + } +} + +// Evil eye ---------------------------------------------------------------- + +class EvilEye : Actor +{ + Default + { + Radius 16; + Height 54; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + CEYE ABCB 6 BRIGHT; + Loop; + } +} + +// Floating skull ---------------------------------------------------------- + +class FloatingSkull : Actor +{ + Default + { + Radius 16; + Height 26; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + FSKU ABC 6 BRIGHT; + Loop; + } +} + +// Torch tree -------------------------------------------------------------- + +class TorchTree : Actor +{ + Default + { + Radius 16; + Height 56; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TRE1 A -1; + Stop; + } +} + +// Blue torch -------------------------------------------------------------- + +class BlueTorch : Actor +{ + Default + { + Radius 16; + Height 68;; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TBLU ABCD 4 BRIGHT; + Loop; + } +} + +// Green torch ------------------------------------------------------------- + +class GreenTorch : Actor +{ + Default + { + Radius 16; + Height 68; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TGRN ABCD 4 BRIGHT; + Loop; + } +} + +// Red torch --------------------------------------------------------------- + +class RedTorch : Actor +{ + Default + { + Radius 16; + Height 68; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TRED ABCD 4 BRIGHT; + Loop; + } +} + +// Short blue torch -------------------------------------------------------- + +class ShortBlueTorch : Actor +{ + Default + { + Radius 16; + Height 37; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + SMBT ABCD 4 BRIGHT; + Loop; + } +} + +// Short green torch ------------------------------------------------------- + +class ShortGreenTorch : Actor +{ + Default + { + Radius 16; + Height 37; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + SMGT ABCD 4 BRIGHT; + Loop; + } +} + +// Short red torch --------------------------------------------------------- + +class ShortRedTorch : Actor +{ + Default + { + Radius 16; + Height 37; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + SMRT ABCD 4 BRIGHT; + Loop; + } +} + +// Stalagtite -------------------------------------------------------------- + +class Stalagtite : Actor +{ + Default + { + Radius 16; + Height 40; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + SMIT A -1; + Stop; + } +} + +// Tech pillar ------------------------------------------------------------- + +class TechPillar : Actor +{ + Default + { + Radius 16; + Height 128; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + ELEC A -1; + Stop; + } +} + +// Candle stick ------------------------------------------------------------ + +class Candlestick : Actor +{ + Default + { + Radius 20; + Height 14; + ProjectilePassHeight -16; + } + States + { + Spawn: + CAND A -1 BRIGHT; + Stop; + } +} + +// Candelabra -------------------------------------------------------------- + +class Candelabra : Actor +{ + Default + { + Radius 16; + Height 60; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + CBRA A -1 BRIGHT; + Stop; + } +} + +// Bloody twitch ----------------------------------------------------------- + +class BloodyTwitch : Actor +{ + Default + { + Radius 16; + Height 68; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + GOR1 A 10; + GOR1 B 15; + GOR1 C 8; + GOR1 B 6; + Loop; + } +} + +// Meat 2 ------------------------------------------------------------------ + +class Meat2 : Actor +{ + Default + { + Radius 16; + Height 84; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + GOR2 A -1; + Stop; + } +} + +// Meat 3 ------------------------------------------------------------------ + +class Meat3 : Actor +{ + Default + { + Radius 16; + Height 84; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + GOR3 A -1; + Stop; + } +} + +// Meat 4 ------------------------------------------------------------------ + +class Meat4 : Actor +{ + Default + { + Radius 16; + Height 68; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + GOR4 A -1; + Stop; + } +} + +// Meat 5 ------------------------------------------------------------------ + +class Meat5 : Actor +{ + Default + { + Radius 16; + Height 52; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + GOR5 A -1; + Stop; + } +} + +// Nonsolid meat ----------------------------------------------------------- + +class NonsolidMeat2 : Meat2 +{ + Default + { + -SOLID + Radius 20; + } +} + +class NonsolidMeat3 : Meat3 +{ + Default + { + -SOLID + Radius 20; + } +} + +class NonsolidMeat4 : Meat4 +{ + Default + { + -SOLID + Radius 20; + } +} + +class NonsolidMeat5 : Meat5 +{ + Default + { + -SOLID + Radius 20; + } +} + +// Nonsolid bloody twitch -------------------------------------------------- + +class NonsolidTwitch : BloodyTwitch +{ + Default + { + -SOLID + Radius 20; + } +} + +// Head on a stick --------------------------------------------------------- + +class HeadOnAStick : Actor +{ + Default + { + Radius 16; + Height 56; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + POL4 A -1; + Stop; + } +} + +// Heads (plural!) on a stick ---------------------------------------------- + +class HeadsOnAStick : Actor +{ + Default + { + Radius 16; + Height 64;; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + POL2 A -1; + Stop; + } +} + +// Head candles ------------------------------------------------------------ + +class HeadCandles : Actor +{ + Default + { + Radius 16; + Height 42; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + POL3 AB 6 BRIGHT; + Loop; + } +} + +// Dead on a stick --------------------------------------------------------- + +class DeadStick : Actor +{ + Default + { + Radius 16; + Height 64; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + POL1 A -1; + Stop; + } +} + +// Still alive on a stick -------------------------------------------------- + +class LiveStick : Actor +{ + Default + { + Radius 16; + Height 64; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + POL6 A 6; + POL6 B 8; + Loop; + } +} + +// Big tree ---------------------------------------------------------------- + +class BigTree : Actor +{ + Default + { + Radius 32; + Height 108; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + TRE2 A -1; + Stop; + } +} + +// Burning barrel ---------------------------------------------------------- + +class BurningBarrel : Actor +{ + Default + { + Radius 16; + Height 32; + ProjectilePassHeight -16; + +SOLID + } + States + { + Spawn: + FCAN ABC 4 BRIGHT; + Loop; + } +} + +// Hanging with no guts ---------------------------------------------------- + +class HangNoGuts : Actor +{ + Default + { + Radius 16; + Height 88; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + HDB1 A -1; + Stop; + } +} + +// Hanging from bottom with no brain --------------------------------------- + +class HangBNoBrain : Actor +{ + Default + { + Radius 16; + Height 88; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + HDB2 A -1; + Stop; + } +} + +// Hanging from top, looking down ------------------------------------------ + +class HangTLookingDown : Actor +{ + Default + { + Radius 16; + Height 64; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + HDB3 A -1; + Stop; + } +} + +// Hanging from top, looking up -------------------------------------------- + +class HangTLookingUp : Actor +{ + Default + { + Radius 16; + Height 64; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + HDB5 A -1; + Stop; + } +} + +// Hanging from top, skully ------------------------------------------------ + +class HangTSkull : Actor +{ + Default + { + Radius 16; + Height 64; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + HDB4 A -1; + Stop; + } +} + +// Hanging from top without a brain ---------------------------------------- + +class HangTNoBrain : Actor +{ + Default + { + Radius 16; + Height 64; + +SOLID + +NOGRAVITY + +SPAWNCEILING + } + States + { + Spawn: + HDB6 A -1; + Stop; + } +} + +// Colon gibs -------------------------------------------------------------- + +class ColonGibs : Actor +{ + Default + { + Radius 20; + Height 4; + +NOBLOCKMAP + +MOVEWITHSECTOR + } + States + { + Spawn: + POB1 A -1; + Stop; + } +} + +// Small pool o' blood ----------------------------------------------------- + +class SmallBloodPool : Actor +{ + Default + { + Radius 20; + Height 1; + +NOBLOCKMAP + +MOVEWITHSECTOR + } + States + { + Spawn: + POB2 A -1; + Stop; + } +} + +// brain stem lying on the ground ------------------------------------------ + +class BrainStem : Actor +{ + Default + { + Radius 20; + Height 4; + +NOBLOCKMAP + +MOVEWITHSECTOR + } + States + { + Spawn: + BRS1 A -1; + Stop; + } +} + + +// Grey stalagmite (unused Doom sprite, definition taken from Skulltag ----- + +class Stalagmite : Actor +{ + Default + { + Radius 16; + Height 48; + +SOLID + } + States + { + Spawn: + SMT2 A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/doom/doomhealth.txt b/wadsrc/static/zscript/doom/doomhealth.txt new file mode 100644 index 000000000..c0ecf2dc0 --- /dev/null +++ b/wadsrc/static/zscript/doom/doomhealth.txt @@ -0,0 +1,54 @@ +// Health bonus ------------------------------------------------------------- + +class HealthBonus : Health +{ + Default + { + +COUNTITEM + +INVENTORY.ALWAYSPICKUP + Inventory.Amount 1; + Inventory.MaxAmount 200; + Inventory.PickupMessage "$GOTHTHBONUS"; + } + States + { + Spawn: + BON1 ABCDCB 6; + Loop; + } +} + +// Stimpack ----------------------------------------------------------------- + +class Stimpack : Health +{ + Default + { + Inventory.Amount 10; + Inventory.PickupMessage "$GOTSTIM"; + } + States + { + Spawn: + STIM A -1; + Stop; + } +} + +// Medikit ----------------------------------------------------------------- + +class Medikit : Health +{ + Default + { + Inventory.Amount 25; + Inventory.PickupMessage "$GOTMEDIKIT"; + Health.LowMessage 25, "$GOTMEDINEED"; + } + States + { + Spawn: + MEDI A -1; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/doomimp.txt b/wadsrc/static/zscript/doom/doomimp.txt new file mode 100644 index 000000000..244ae70ea --- /dev/null +++ b/wadsrc/static/zscript/doom/doomimp.txt @@ -0,0 +1,93 @@ +//=========================================================================== +// +// Imp +// +//=========================================================================== +class DoomImp : Actor +{ + Default + { + Health 60; + Radius 20; + Height 56; + Mass 100; + Speed 8; + PainChance 200; + Monster; + +FLOORCLIP + SeeSound "imp/sight"; + PainSound "imp/pain"; + DeathSound "imp/death"; + ActiveSound "imp/active"; + HitObituary "$OB_IMPHIT"; + Obituary "$OB_IMP"; + } + States + { + Spawn: + TROO AB 10 A_Look; + Loop; + See: + TROO AABBCCDD 3 A_Chase; + Loop; + Melee: + Missile: + TROO EF 8 A_FaceTarget; + TROO G 6 A_TroopAttack ; + Goto See; + Pain: + TROO H 2; + TROO H 2 A_Pain; + Goto See; + Death: + TROO I 8; + TROO J 8 A_Scream; + TROO K 6; + TROO L 6 A_NoBlocking; + TROO M -1; + Stop; + XDeath: + TROO N 5; + TROO O 5 A_XScream; + TROO P 5; + TROO Q 5 A_NoBlocking; + TROO RST 5; + TROO U -1; + Stop; + Raise: + TROO MLKJI 8; + Goto See; + } +} + +//=========================================================================== +// +// Imp fireball +// +//=========================================================================== +class DoomImpBall : Actor +{ + Default + { + Radius 6; + Height 8; + Speed 10; + FastSpeed 20; + Damage 3; + Projectile; + +RANDOMIZE + RenderStyle "Add"; + Alpha 1; + SeeSound "imp/attack"; + DeathSound "imp/shotx"; + } + States + { + Spawn: + BAL1 AB 4 BRIGHT; + Loop; + Death: + BAL1 CDE 6 BRIGHT; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/doomkeys.txt b/wadsrc/static/zscript/doom/doomkeys.txt new file mode 100644 index 000000000..9ae88dade --- /dev/null +++ b/wadsrc/static/zscript/doom/doomkeys.txt @@ -0,0 +1,119 @@ + +class DoomKey : Key +{ + Default + { + Radius 20; + Height 16; + +NOTDMATCH + } +} + +// Blue key card ------------------------------------------------------------ + +class BlueCard : DoomKey +{ + Default + { + Inventory.Pickupmessage "$GOTBLUECARD"; + Inventory.Icon "STKEYS0"; + } + States + { + Spawn: + BKEY A 10; + BKEY B 10 bright; + loop; + } +} + +// Yellow key card ---------------------------------------------------------- + +class YellowCard : DoomKey +{ + Default + { + Inventory.Pickupmessage "$GOTYELWCARD"; + Inventory.Icon "STKEYS1"; + } + States + { + Spawn: + YKEY A 10; + YKEY B 10 bright; + loop; + } +} + +// Red key card ------------------------------------------------------------- + +class RedCard : DoomKey +{ + Default + { + Inventory.Pickupmessage "$GOTREDCARD"; + Inventory.Icon "STKEYS2"; + } + States + { + Spawn: + RKEY A 10; + RKEY B 10 bright; + loop; + } +} + +// Blue skull key ----------------------------------------------------------- + +class BlueSkull : DoomKey +{ + Default + { + Inventory.Pickupmessage "$GOTBLUESKUL"; + Inventory.Icon "STKEYS3"; + } + States + { + Spawn: + BSKU A 10; + BSKU B 10 bright; + loop; + } +} + +// Yellow skull key --------------------------------------------------------- + +class YellowSkull : DoomKey +{ + Default + { + Inventory.Pickupmessage "$GOTYELWSKUL"; + Inventory.Icon "STKEYS4"; + } + States + { + Spawn: + YSKU A 10; + YSKU B 10 bright; + loop; + } +} + +// Red skull key ------------------------------------------------------------ + +class RedSkull : DoomKey +{ + Default + { + Inventory.Pickupmessage "$GOTREDSKUL"; + Inventory.Icon "STKEYS5"; + } + States + { + Spawn: + RSKU A 10; + RSKU B 10 bright; + loop; + } +} + diff --git a/wadsrc/static/zscript/doom/doommisc.txt b/wadsrc/static/zscript/doom/doommisc.txt new file mode 100644 index 000000000..80e330a68 --- /dev/null +++ b/wadsrc/static/zscript/doom/doommisc.txt @@ -0,0 +1,116 @@ +// The barrel of green goop ------------------------------------------------ + +class ExplosiveBarrel : Actor +{ + Default + { + Health 20; + Radius 10; + Height 42; + +SOLID + +SHOOTABLE + +NOBLOOD + +ACTIVATEMCROSS + +DONTGIB + +NOICEDEATH + +OLDRADIUSDMG + DeathSound "world/barrelx"; + Obituary "$OB_BARREL"; + } + States + { + Spawn: + BAR1 AB 6; + Loop; + Death: + BEXP A 5 BRIGHT; + BEXP B 5 BRIGHT A_Scream; + BEXP C 5 BRIGHT; + BEXP D 5 BRIGHT A_Explode; + BEXP E 10 BRIGHT; + TNT1 A 1050 BRIGHT A_BarrelDestroy; + TNT1 A 5 A_Respawn; + Wait; + } +} + +// Bullet puff ------------------------------------------------------------- + +class BulletPuff : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +ALLOWPARTICLES + +RANDOMIZE + RenderStyle "Translucent"; + Alpha 0.5; + VSpeed 1; + Mass 5; + } + States + { + Spawn: + PUFF A 4 Bright; + PUFF B 4; + Melee: + PUFF CD 4; + Stop; + } +} + +// Container for an unused state ------------------------------------------- + +/* Doom defined the states S_STALAG, S_DEADTORSO, and S_DEADBOTTOM but never + * actually used them. For compatibility with DeHackEd patches, they still + * need to be kept around. This class serves that purpose. + */ + +class DoomUnusedStates : Actor +{ + States + { + Label1: + SMT2 A -1; + stop; + Label2: + PLAY N -1; + stop; + PLAY S -1; + stop; + TNT: // MBF compatibility + TNT1 A -1; + Loop; + } +} + +// MBF Beta emulation items + +class EvilSceptre : ScoreItem +{ + Default + { + Inventory.PickupMessage "$BETA_BONUS3"; + } + States + { + Spawn: + BON3 A 6; + Loop; + } +} + +class UnholyBible : ScoreItem +{ + Default + { + Inventory.PickupMessage "$BETA_BONUS4"; + } + States + { + Spawn: + BON4 A 6; + Loop; + } +} diff --git a/wadsrc/static/zscript/doom/doomplayer.txt b/wadsrc/static/zscript/doom/doomplayer.txt new file mode 100644 index 000000000..6ec0d5f90 --- /dev/null +++ b/wadsrc/static/zscript/doom/doomplayer.txt @@ -0,0 +1,93 @@ +//=========================================================================== +// +// Player +// +//=========================================================================== +class DoomPlayer : PlayerPawn +{ + Default + { + Speed 1; + Health 100; + Radius 16; + Height 56; + Mass 100; + PainChance 255; + Player.DisplayName "Marine"; + Player.CrouchSprite "PLYC"; + Player.StartItem "Pistol"; + Player.StartItem "Fist"; + Player.StartItem "Clip", 50; + Player.WeaponSlot 1, "Fist", "Chainsaw"; + Player.WeaponSlot 2, "Pistol"; + Player.WeaponSlot 3, "Shotgun", "SuperShotgun"; + Player.WeaponSlot 4, "Chaingun"; + Player.WeaponSlot 5, "RocketLauncher"; + Player.WeaponSlot 6, "PlasmaRifle"; + Player.WeaponSlot 7, "BFG9000"; + + Player.ColorRange 112, 127; + Player.Colorset 0, "Green", 0x70, 0x7F, 0x72; + Player.Colorset 1, "Gray", 0x60, 0x6F, 0x62; + Player.Colorset 2, "Brown", 0x40, 0x4F, 0x42; + Player.Colorset 3, "Red", 0x20, 0x2F, 0x22; + // Doom Legacy additions + Player.Colorset 4, "Light Gray", 0x58, 0x67, 0x5A; + Player.Colorset 5, "Light Brown", 0x38, 0x47, 0x3A; + Player.Colorset 6, "Light Red", 0xB0, 0xBF, 0xB2; + Player.Colorset 7, "Light Blue", 0xC0, 0xCF, 0xC2; + } + + States + { + Spawn: + PLAY A -1; + Loop; + See: + PLAY ABCD 4; + Loop; + Missile: + PLAY E 12; + Goto Spawn; + Melee: + PLAY F 6 BRIGHT; + Goto Missile; + Pain: + PLAY G 4; + PLAY G 4 A_Pain; + Goto Spawn; + Death: + PLAY H 0 A_PlayerSkinCheck("AltSkinDeath"); + Death1: + PLAY H 10; + PLAY I 10 A_PlayerScream; + PLAY J 10 A_NoBlocking; + PLAY KLM 10; + PLAY N -1; + Stop; + XDeath: + PLAY O 0 A_PlayerSkinCheck("AltSkinXDeath"); + XDeath1: + PLAY O 5; + PLAY P 5 A_XScream; + PLAY Q 5 A_NoBlocking; + PLAY RSTUV 5; + PLAY W -1; + Stop; + AltSkinDeath: + PLAY H 6; + PLAY I 6 A_PlayerScream; + PLAY JK 6; + PLAY L 6 A_NoBlocking; + PLAY MNO 6; + PLAY P -1; + Stop; + AltSkinXDeath: + PLAY Q 5 A_PlayerScream; + PLAY R 0 A_NoBlocking; + PLAY R 5 A_SkullPop; + PLAY STUVWX 5; + PLAY Y -1; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/doomweapons.txt b/wadsrc/static/zscript/doom/doomweapons.txt new file mode 100644 index 000000000..41f2c434f --- /dev/null +++ b/wadsrc/static/zscript/doom/doomweapons.txt @@ -0,0 +1,621 @@ +// -------------------------------------------------------------------------- +// +// Doom weapon base class +// +// -------------------------------------------------------------------------- + +class DoomWeapon : Weapon +{ + Default + { + Weapon.Kickback 100; + } +} + +// -------------------------------------------------------------------------- +// +// Fist +// +// -------------------------------------------------------------------------- + +class Fist : Weapon +{ + Default + { + Weapon.SelectionOrder 3700; + Weapon.Kickback 100; + Obituary "$OB_MPFIST"; + Tag "$TAG_FIST"; + +WEAPON.WIMPY_WEAPON + +WEAPON.MELEEWEAPON + } + States + { + Ready: + PUNG A 1 A_WeaponReady; + Loop; + Deselect: + PUNG A 1 A_Lower; + Loop; + Select: + PUNG A 1 A_Raise; + Loop; + Fire: + PUNG B 4; + PUNG C 4 A_Punch; + PUNG D 5; + PUNG C 4; + PUNG B 5 A_ReFire; + Goto Ready; + } +} + + +// -------------------------------------------------------------------------- +// +// Pistol +// +// -------------------------------------------------------------------------- + +class Pistol : DoomWeapon +{ + Default + { + Weapon.SelectionOrder 1900; + Weapon.AmmoUse 1; + Weapon.AmmoGive 20; + Weapon.AmmoType "Clip"; + Obituary "$OB_MPPISTOL"; + +WEAPON.WIMPY_WEAPON + Inventory.Pickupmessage "$PICKUP_PISTOL_DROPPED"; + Tag "$TAG_PISTOL"; + } + States + { + Ready: + PISG A 1 A_WeaponReady; + Loop; + Deselect: + PISG A 1 A_Lower; + Loop; + Select: + PISG A 1 A_Raise; + Loop; + Fire: + PISG A 4; + PISG B 6 A_FirePistol; + PISG C 4; + PISG B 5 A_ReFire; + Goto Ready; + Flash: + PISF A 7 Bright A_Light1; + Goto LightDone; + PISF A 7 Bright A_Light1; + Goto LightDone; + Spawn: + PIST A -1; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// Chainsaw +// +// -------------------------------------------------------------------------- + +class Chainsaw : Weapon +{ + Default + { + Weapon.Kickback 0; + Weapon.SelectionOrder 2200; + Weapon.UpSound "weapons/sawup"; + Weapon.ReadySound "weapons/sawidle"; + Inventory.PickupMessage "$GOTCHAINSAW"; + Obituary "$OB_MPCHAINSAW"; + Tag "$TAG_CHAINSAW"; + +WEAPON.MELEEWEAPON + } + States + { + Ready: + SAWG CD 4 A_WeaponReady; + Loop; + Deselect: + SAWG C 1 A_Lower; + Loop; + Select: + SAWG C 1 A_Raise; + Loop; + Fire: + SAWG AB 4 A_Saw; + SAWG B 0 A_ReFire; + Goto Ready; + Spawn: + CSAW A -1; + Stop; + } +} + + +// -------------------------------------------------------------------------- +// +// Shotgun +// +// -------------------------------------------------------------------------- + +class Shotgun : DoomWeapon +{ + Default + { + Weapon.SelectionOrder 1300; + Weapon.AmmoUse 1; + Weapon.AmmoGive 8; + Weapon.AmmoType "Shell"; + Inventory.PickupMessage "$GOTSHOTGUN"; + Obituary "$OB_MPSHOTGUN"; + Tag "$TAG_SHOTGUN"; + } + States + { + Ready: + SHTG A 1 A_WeaponReady; + Loop; + Deselect: + SHTG A 1 A_Lower; + Loop; + Select: + SHTG A 1 A_Raise; + Loop; + Fire: + SHTG A 3; + SHTG A 7 A_FireShotgun; + SHTG BC 5; + SHTG D 4; + SHTG CB 5; + SHTG A 3; + SHTG A 7 A_ReFire; + Goto Ready; + Flash: + SHTF A 4 Bright A_Light1; + SHTF B 3 Bright A_Light2; + Goto LightDone; + Spawn: + SHOT A -1; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// Shotgun +// +// -------------------------------------------------------------------------- + +class SuperShotgun : DoomWeapon +{ + Default + { + Weapon.SelectionOrder 400; + Weapon.AmmoUse 2; + Weapon.AmmoGive 8; + Weapon.AmmoType "Shell"; + Inventory.PickupMessage "$GOTSHOTGUN2"; + Obituary "$OB_MPSSHOTGUN"; + Tag "$TAG_SUPERSHOTGUN"; + } + States + { + Ready: + SHT2 A 1 A_WeaponReady; + Loop; + Deselect: + SHT2 A 1 A_Lower; + Loop; + Select: + SHT2 A 1 A_Raise; + Loop; + Fire: + SHT2 A 3; + SHT2 A 7 A_FireShotgun2; + SHT2 B 7; + SHT2 C 7 A_CheckReload; + SHT2 D 7 A_OpenShotgun2; + SHT2 E 7; + SHT2 F 7 A_LoadShotgun2; + SHT2 G 6; + SHT2 H 6 A_CloseShotgun2; + SHT2 A 5 A_ReFire; + Goto Ready; + // unused states + SHT2 B 7; + SHT2 A 3; + Goto Deselect; + Flash: + SHT2 I 4 Bright A_Light1; + SHT2 J 3 Bright A_Light2; + Goto LightDone; + Spawn: + SGN2 A -1; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// Chaingun +// +// -------------------------------------------------------------------------- + +class Chaingun : DoomWeapon +{ + Default + { + Weapon.SelectionOrder 700; + Weapon.AmmoUse 1; + Weapon.AmmoGive 20; + Weapon.AmmoType "Clip"; + Inventory.PickupMessage "$GOTCHAINGUN"; + Obituary "$OB_MPCHAINGUN"; + Tag "$TAG_CHAINGUN"; + } + States + { + Ready: + CHGG A 1 A_WeaponReady; + Loop; + Deselect: + CHGG A 1 A_Lower; + Loop; + Select: + CHGG A 1 A_Raise; + Loop; + Fire: + CHGG AB 4 A_FireCGun; + CHGG B 0 A_ReFire; + Goto Ready; + Flash: + CHGF A 5 Bright A_Light1; + Goto LightDone; + CHGF B 5 Bright A_Light2; + Goto LightDone; + Spawn: + MGUN A -1; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// Rocket launcher +// +// -------------------------------------------------------------------------- + +class RocketLauncher : DoomWeapon +{ + Default + { + Weapon.SelectionOrder 2500; + Weapon.AmmoUse 1; + Weapon.AmmoGive 2; + Weapon.AmmoType "RocketAmmo"; + +WEAPON.NOAUTOFIRE + Inventory.PickupMessage "$GOTLAUNCHER"; + Tag "$TAG_ROCKETLAUNCHER"; + } + States + { + Ready: + MISG A 1 A_WeaponReady; + Loop; + Deselect: + MISG A 1 A_Lower; + Loop; + Select: + MISG A 1 A_Raise; + Loop; + Fire: + MISG B 8 A_GunFlash; + MISG B 12 A_FireMissile; + MISG B 0 A_ReFire; + Goto Ready; + Flash: + MISF A 3 Bright A_Light1; + MISF B 4 Bright; + MISF CD 4 Bright A_Light2; + Goto LightDone; + Spawn: + LAUN A -1; + Stop; + } +} + +class Rocket : Actor +{ + Default + { + Radius 11; + Height 8; + Speed 20; + Damage 20; + Projectile; + +RANDOMIZE + +DEHEXPLOSION + +ROCKETTRAIL + SeeSound "weapons/rocklf"; + DeathSound "weapons/rocklx"; + Obituary "$OB_MPROCKET"; + } + States + { + Spawn: + MISL A 1 Bright; + Loop; + Death: + MISL B 8 Bright A_Explode; + MISL C 6 Bright; + MISL D 4 Bright; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// Grenade -- Taken and adapted from Skulltag, with MBF stuff added to it +// +// -------------------------------------------------------------------------- + +class Grenade : Actor +{ + Default + { + Radius 8; + Height 8; + Speed 25; + Damage 20; + Projectile; + -NOGRAVITY + +RANDOMIZE + +DEHEXPLOSION + +GRENADETRAIL + BounceType "Doom"; + Gravity 0.25; + SeeSound "weapons/grenlf"; + DeathSound "weapons/grenlx"; + BounceSound "weapons/grbnce"; + Obituary "$OB_GRENADE"; + DamageType "Grenade"; + } + States + { + Spawn: + SGRN A 1 Bright; + Loop; + Death: + MISL B 8 Bright A_Explode; + MISL C 6 Bright; + MISL D 4 Bright; + Stop; + Grenade: + MISL A 1000 A_Die; + Wait; + Detonate: + MISL B 4 A_Scream; + MISL C 6 A_Detonate; + MISL D 10; + Stop; + Mushroom: + MISL B 8 A_Mushroom; + Goto Death+1; + } +} + +// -------------------------------------------------------------------------- +// +// Plasma rifle +// +// -------------------------------------------------------------------------- + +class PlasmaRifle : DoomWeapon +{ + Default + { + Weapon.SelectionOrder 100; + Weapon.AmmoUse 1; + Weapon.AmmoGive 40; + Weapon.AmmoType "Cell"; + Inventory.PickupMessage "$GOTPLASMA"; + Tag "$TAG_PLASMARIFLE"; + } + States + { + Ready: + PLSG A 1 A_WeaponReady; + Loop; + Deselect: + PLSG A 1 A_Lower; + Loop; + Select: + PLSG A 1 A_Raise; + Loop; + Fire: + PLSG A 3 A_FirePlasma; + PLSG B 20 A_ReFire; + Goto Ready; + Flash: + PLSF A 4 Bright A_Light1; + Goto LightDone; + PLSF B 4 Bright A_Light1; + Goto LightDone; + Spawn: + PLAS A -1; + Stop; + } +} + +class PlasmaBall : Actor +{ + Default + { + Radius 13; + Height 8; + Speed 25; + Damage 5; + Projectile; + +RANDOMIZE + RenderStyle "Add"; + Alpha 0.75; + SeeSound "weapons/plasmaf"; + DeathSound "weapons/plasmax"; + Obituary "$OB_MPPLASMARIFLE"; + } + States + { + Spawn: + PLSS AB 6 Bright; + Loop; + Death: + PLSE ABCDE 4 Bright; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// BFG 2704 +// +// -------------------------------------------------------------------------- + +class PlasmaBall1 : PlasmaBall +{ + Default + { + Damage 4; + BounceType "Classic"; + BounceFactor 1.0; + Obituary "$OB_MPBFG_MBF"; + } + States + { + Spawn: + PLS1 AB 6 Bright; + Loop; + Death: + PLS1 CDEFG 4 Bright; + Stop; + } +} + +class PlasmaBall2 : PlasmaBall1 +{ + States + { + Spawn: + PLS2 AB 6 Bright; + Loop; + Death: + PLS2 CDE 4 Bright; + Stop; + } +} + +// -------------------------------------------------------------------------- +// +// BFG 9000 +// +// -------------------------------------------------------------------------- + +class BFG9000 : DoomWeapon +{ + Default + { + Height 20; + Weapon.SelectionOrder 2800; + Weapon.AmmoUse 40; + Weapon.AmmoGive 40; + Weapon.AmmoType "Cell"; + +WEAPON.NOAUTOFIRE; + Inventory.PickupMessage "$GOTBFG9000"; + Tag "$TAG_BFG9000"; + } + States + { + Ready: + BFGG A 1 A_WeaponReady; + Loop; + Deselect: + BFGG A 1 A_Lower; + Loop; + Select: + BFGG A 1 A_Raise; + Loop; + Fire: + BFGG A 20 A_BFGsound; + BFGG B 10 A_GunFlash; + BFGG B 10 A_FireBFG; + BFGG B 20 A_ReFire; + Goto Ready; + Flash: + BFGF A 11 Bright A_Light1; + BFGF B 6 Bright A_Light2; + Goto LightDone; + Spawn: + BFUG A -1; + Stop; + OldFire: + BFGG A 10 A_BFGsound; + BFGG BBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBBB 1 A_FireOldBFG; + BFGG B 0 A_Light0; + BFGG B 20 A_ReFire; + Goto Ready; + } +} + + +class BFGBall : Actor +{ + Default + { + Radius 13; + Height 8; + Speed 25; + Damage 100; + Projectile; + +RANDOMIZE + RenderStyle "Add"; + Alpha 0.75; + DeathSound "weapons/bfgx"; + Obituary "$OB_MPBFG_BOOM"; + } + States + { + Spawn: + BFS1 AB 4 Bright; + Loop; + Death: + BFE1 AB 8 Bright; + BFE1 C 8 Bright A_BFGSpray; + BFE1 DEF 8 Bright; + Stop; + } +} + +class BFGExtra : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + RenderStyle "Add"; + Alpha 0.75; + DamageType "BFGSplash"; + } + States + { + Spawn: + BFE2 ABCD 8 Bright; + Stop; + } +} + diff --git a/wadsrc/static/zscript/doom/fatso.txt b/wadsrc/static/zscript/doom/fatso.txt new file mode 100644 index 000000000..46d013d7f --- /dev/null +++ b/wadsrc/static/zscript/doom/fatso.txt @@ -0,0 +1,95 @@ +//=========================================================================== +// +// Mancubus +// +//=========================================================================== +class Fatso : Actor +{ + Default + { + Health 600; + Radius 48; + Height 64; + Mass 1000; + Speed 8; + PainChance 80; + Monster; + +FLOORCLIP + +BOSSDEATH + SeeSound "fatso/sight"; + PainSound "fatso/pain"; + DeathSound "fatso/death"; + ActiveSound "fatso/active"; + Obituary "$OB_FATSO"; + } + States + { + Spawn: + FATT AB 15 A_Look; + Loop; + See: + FATT AABBCCDDEEFF 4 A_Chase; + Loop; + Missile: + FATT G 20 A_FatRaise; + FATT H 10 BRIGHT A_FatAttack1; + FATT IG 5 A_FaceTarget; + FATT H 10 BRIGHT A_FatAttack2; + FATT IG 5 A_FaceTarget; + FATT H 10 BRIGHT A_FatAttack3; + FATT IG 5 A_FaceTarget; + Goto See; + Pain: + FATT J 3; + FATT J 3 A_Pain; + Goto See; + Death: + FATT K 6; + FATT L 6 A_Scream; + FATT M 6 A_NoBlocking; + FATT NOPQRS 6; + FATT T -1 A_BossDeath; + Stop; + Raise: + FATT R 5; + FATT QPONMLK 5; + Goto See; + } +} + + + +//=========================================================================== +// +// Mancubus fireball +// +//=========================================================================== +class FatShot : Actor +{ + Default + { + Radius 6; + Height 8; + Speed 20; + Damage 8; + Projectile; + +RANDOMIZE + RenderStyle "Add"; + Alpha 1; + SeeSound "fatso/attack"; + DeathSound "fatso/shotx"; + } + States + { + Spawn: + MANF AB 4 BRIGHT; + Loop; + Death: + MISL B 8 BRIGHT; + MISL C 6 BRIGHT; + MISL D 4 BRIGHT; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/doom/keen.txt b/wadsrc/static/zscript/doom/keen.txt new file mode 100644 index 000000000..a60e924ef --- /dev/null +++ b/wadsrc/static/zscript/doom/keen.txt @@ -0,0 +1,44 @@ +//=========================================================================== +// +// Commander Keen +// +//=========================================================================== +class CommanderKeen : Actor +{ + Default + { + Health 100; + Radius 16; + Height 72; + Mass 10000000; + PainChance 256; + +SOLID + +SPAWNCEILING + +NOGRAVITY + +SHOOTABLE + +COUNTKILL + +NOICEDEATH + +ISMONSTER + PainSound "keen/pain"; + DeathSound "keen/death"; + } + States + { + Spawn: + KEEN A -1; + Loop; + Death: + KEEN AB 6; + KEEN C 6 A_Scream; + KEEN DEFGH 6; + KEEN I 6; + KEEN J 6; + KEEN K 6 A_KeenDie; + KEEN L -1; + Stop; + Pain: + KEEN M 4; + KEEN M 8 A_Pain; + Goto Spawn; + } +} diff --git a/wadsrc/static/zscript/doom/lostsoul.txt b/wadsrc/static/zscript/doom/lostsoul.txt new file mode 100644 index 000000000..69574e5c7 --- /dev/null +++ b/wadsrc/static/zscript/doom/lostsoul.txt @@ -0,0 +1,83 @@ +//=========================================================================== +// +// Lost Soul +// +//=========================================================================== +class LostSoul : Actor +{ + Default + { + Health 100; + Radius 16; + Height 56; + Mass 50; + Speed 8; + Damage 3; + PainChance 256; + Monster; + +FLOAT +NOGRAVITY +MISSILEMORE +DONTFALL +NOICEDEATH; + AttackSound "skull/melee"; + PainSound "skull/pain"; + DeathSound "skull/death"; + ActiveSound "skull/active"; + RenderStyle "SoulTrans"; + Obituary "$OB_SKULL"; + } + States + { + Spawn: + SKUL AB 10 BRIGHT A_Look; + Loop; + See: + SKUL AB 6 BRIGHT A_Chase; + Loop; + Missile: + SKUL C 10 BRIGHT A_FaceTarget; + SKUL D 4 BRIGHT A_SkullAttack; + SKUL CD 4 BRIGHT; + Goto Missile+2; + Pain: + SKUL E 3 BRIGHT; + SKUL E 3 BRIGHT A_Pain; + Goto See; + Death: + SKUL F 6 BRIGHT; + SKUL G 6 BRIGHT A_Scream; + SKUL H 6 BRIGHT; + SKUL I 6 BRIGHT A_NoBlocking; + SKUL J 6; + SKUL K 6; + Stop; + } +} + +class BetaSkull : LostSoul +{ + States + { + Spawn: + SKUL A 10 A_Look; + Loop; + See: + SKUL BCDA 5 A_Chase; + Loop; + Missile: + SKUL E 4 A_FaceTarget; + SKUL F 5 A_BetaSkullAttack; + SKUL F 4; + Goto See; + Pain: + SKUL G 4; + SKUL H 2 A_Pain; + Goto See; + SKUL I 4; + Goto See; + Death: + SKUL JKLM 5; + SKUL N 5 A_Scream; + SKUL O 5; + SKUL P 5 A_Fall; + SKUL Q 5 A_Stop; + Wait; + } +} diff --git a/wadsrc/static/zscript/doom/painelemental.txt b/wadsrc/static/zscript/doom/painelemental.txt new file mode 100644 index 000000000..ce30bbfd3 --- /dev/null +++ b/wadsrc/static/zscript/doom/painelemental.txt @@ -0,0 +1,53 @@ +//=========================================================================== +// +// Pain Elemental +// +//=========================================================================== +class PainElemental : Actor +{ + Default + { + Health 400; + Radius 31; + Height 56; + Mass 400; + Speed 8; + PainChance 128; + Monster; + +FLOAT + +NOGRAVITY + SeeSound "pain/sight"; + PainSound "pain/pain"; + DeathSound "pain/death"; + ActiveSound "pain/active"; + } + States + { + Spawn: + PAIN A 10 A_Look; + Loop; + See: + PAIN AABBCC 3 A_Chase; + Loop; + Missile: + PAIN D 5 A_FaceTarget; + PAIN E 5 A_FaceTarget; + PAIN F 5 BRIGHT A_FaceTarget; + PAIN F 0 BRIGHT A_PainAttack; + Goto See; + Pain: + PAIN G 6; + PAIN G 6 A_Pain; + Goto See; + Death: + PAIN H 8 BRIGHT; + PAIN I 8 BRIGHT A_Scream; + PAIN JK 8 BRIGHT; + PAIN L 8 BRIGHT A_PainDie; + PAIN M 8 BRIGHT; + Stop; + Raise: + PAIN MLKJIH 8; + Goto See; + } +} diff --git a/wadsrc/static/zscript/doom/possessed.txt b/wadsrc/static/zscript/doom/possessed.txt new file mode 100644 index 000000000..de1e50ff2 --- /dev/null +++ b/wadsrc/static/zscript/doom/possessed.txt @@ -0,0 +1,253 @@ + +//=========================================================================== +// +// Zombie man +// +//=========================================================================== +class ZombieMan : Actor +{ + Default + { + Health 20; + Radius 20; + Height 56; + Speed 8; + PainChance 200; + Monster; + +FLOORCLIP + SeeSound "grunt/sight"; + AttackSound "grunt/attack"; + PainSound "grunt/pain"; + DeathSound "grunt/death"; + ActiveSound "grunt/active"; + Obituary "$OB_ZOMBIE"; + DropItem "Clip"; + } + States + { + Spawn: + POSS AB 10 A_Look; + Loop; + See: + POSS AABBCCDD 4 A_Chase; + Loop; + Missile: + POSS E 10 A_FaceTarget; + POSS F 8 A_PosAttack; + POSS E 8; + Goto See; + Pain: + POSS G 3; + POSS G 3 A_Pain; + Goto See; + Death: + POSS H 5; + POSS I 5 A_Scream; + POSS J 5 A_NoBlocking; + POSS K 5; + POSS L -1; + Stop; + XDeath: + POSS M 5; + POSS N 5 A_XScream; + POSS O 5 A_NoBlocking; + POSS PQRST 5; + POSS U -1; + Stop; + Raise: + POSS K 5; + POSS JIH 5; + Goto See; + } +} + +//=========================================================================== +// +// Sergeant / Shotgun guy +// +//=========================================================================== +class ShotgunGuy : Actor +{ + Default + { + Health 30; + Radius 20; + Height 56; + Mass 100; + Speed 8; + PainChance 170; + Monster; + +FLOORCLIP + SeeSound "shotguy/sight"; + AttackSound "shotguy/attack"; + PainSound "shotguy/pain"; + DeathSound "shotguy/death"; + ActiveSound "shotguy/active"; + Obituary "$OB_SHOTGUY"; + DropItem "Shotgun"; + } + States + { + Spawn: + SPOS AB 10 A_Look; + Loop; + See: + SPOS AABBCCDD 3 A_Chase; + Loop; + Missile: + SPOS E 10 A_FaceTarget; + SPOS F 10 BRIGHT A_SposAttackUseAtkSound; + SPOS E 10; + Goto See; + Pain: + SPOS G 3; + SPOS G 3 A_Pain; + Goto See; + Death: + SPOS H 5; + SPOS I 5 A_Scream; + SPOS J 5 A_NoBlocking; + SPOS K 5; + SPOS L -1; + Stop; + XDeath: + SPOS M 5; + SPOS N 5 A_XScream; + SPOS O 5 A_NoBlocking; + SPOS PQRST 5; + SPOS U -1; + Stop; + Raise: + SPOS L 5; + SPOS KJIH 5; + Goto See; + } +} + +//=========================================================================== +// +// Chaingunner +// +//=========================================================================== +class ChaingunGuy : Actor +{ + Default + { + Health 70; + Radius 20; + Height 56; + Mass 100; + Speed 8; + PainChance 170; + Monster; + +FLOORCLIP + SeeSound "chainguy/sight"; + PainSound "chainguy/pain"; + DeathSound "chainguy/death"; + ActiveSound "chainguy/active"; + AttackSound "chainguy/attack"; + Obituary "$OB_CHAINGUY"; + Dropitem "Chaingun"; + } + States + { + Spawn: + CPOS AB 10 A_Look; + Loop; + See: + CPOS AABBCCDD 3 A_Chase; + Loop; + Missile: + CPOS E 10 A_FaceTarget; + CPOS FE 4 BRIGHT A_CPosAttack; + CPOS F 1 A_CPosRefire; + Goto Missile+1; + Pain: + CPOS G 3; + CPOS G 3 A_Pain; + Goto See; + Death: + CPOS H 5; + CPOS I 5 A_Scream; + CPOS J 5 A_NoBlocking; + CPOS KLM 5; + CPOS N -1; + Stop; + XDeath: + CPOS O 5; + CPOS P 5 A_XScream; + CPOS Q 5 A_NoBlocking; + CPOS RS 5; + CPOS T -1; + Stop; + Raise: + CPOS N 5; + CPOS MLKJIH 5; + Goto See; + } +} + +//=========================================================================== +// +// SS Nazi +// +//=========================================================================== +class WolfensteinSS : Actor +{ + Default + { + Health 50; + Radius 20; + Height 56; + Speed 8; + PainChance 170; + Monster; + +FLOORCLIP + SeeSound "wolfss/sight"; + PainSound "wolfss/pain"; + DeathSound "wolfss/death"; + ActiveSound "wolfss/active"; + AttackSound "wolfss/attack"; + Obituary "$OB_WOLFSS"; + Dropitem "Clip"; + } + States + { + Spawn: + SSWV AB 10 A_Look; + Loop; + See: + SSWV AABBCCDD 3 A_Chase; + Loop; + Missile: + SSWV E 10 A_FaceTarget; + SSWV F 10 A_FaceTarget; + SSWV G 4 BRIGHT A_CPosAttack; + SSWV F 6 A_FaceTarget; + SSWV G 4 BRIGHT A_CPosAttack; + SSWV F 1 A_CPosRefire; + Goto Missile+1; + Pain: + SSWV H 3; + SSWV H 3 A_Pain; + Goto See; + Death: + SSWV I 5; + SSWV J 5 A_Scream; + SSWV K 5 A_NoBlocking; + SSWV L 5; + SSWV M -1; + Stop; + XDeath: + SSWV N 5 ; + SSWV O 5 A_XScream; + SSWV P 5 A_NoBlocking; + SSWV QRSTU 5; + SSWV V -1; + Stop; + Raise: + SSWV M 5; + SSWV LKJI 5; + Goto See ; + } +} diff --git a/wadsrc/static/zscript/doom/revenant.txt b/wadsrc/static/zscript/doom/revenant.txt new file mode 100644 index 000000000..7fc8b8e0d --- /dev/null +++ b/wadsrc/static/zscript/doom/revenant.txt @@ -0,0 +1,122 @@ +//=========================================================================== +// +// Revenant +// +//=========================================================================== +class Revenant : Actor +{ + Default + { + Health 300; + Radius 20; + Height 56; + Mass 500; + Speed 10; + PainChance 100; + Monster; + MeleeThreshold 196; + +MISSILEMORE + +FLOORCLIP + SeeSound "skeleton/sight"; + PainSound "skeleton/pain"; + DeathSound "skeleton/death"; + ActiveSound "skeleton/active"; + MeleeSound "skeleton/melee"; + HitObituary "$OB_UNDEADHIT"; + Obituary "$OB_UNDEAD"; + } + States + { + Spawn: + SKEL AB 10 A_Look; + Loop; + See: + SKEL AABBCCDDEEFF 2 A_Chase; + Loop; + Melee: + SKEL G 0 A_FaceTarget; + SKEL G 6 A_SkelWhoosh; + SKEL H 6 A_FaceTarget; + SKEL I 6 A_SkelFist; + Goto See; + Missile: + SKEL J 0 BRIGHT A_FaceTarget; + SKEL J 10 BRIGHT A_FaceTarget; + SKEL K 10 A_SkelMissile; + SKEL K 10 A_FaceTarget; + Goto See; + Pain: + SKEL L 5; + SKEL L 5 A_Pain; + Goto See; + Death: + SKEL LM 7; + SKEL N 7 A_Scream; + SKEL O 7 A_NoBlocking; + SKEL P 7; + SKEL Q -1; + Stop; + Raise: + SKEL Q 5; + SKEL PONML 5; + Goto See; + } +} + + +//=========================================================================== +// +// Revenant Tracer +// +//=========================================================================== +class RevenantTracer : Actor +{ + Default + { + Radius 11; + Height 8; + Speed 10; + Damage 10; + Projectile; + +SEEKERMISSILE + +RANDOMIZE + SeeSound "skeleton/attack"; + DeathSound "skeleton/tracex"; + RenderStyle "Add"; + } + States + { + Spawn: + FATB AB 2 BRIGHT A_Tracer; + Loop; + Death: + FBXP A 8 BRIGHT; + FBXP B 6 BRIGHT; + FBXP C 4 BRIGHT; + Stop; + } +} + + +//=========================================================================== +// +// Revenant Tracer Smoke +// +//=========================================================================== +class RevenantTracerSmoke : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.5; + } + States + { + Spawn: + PUFF ABABC 4; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/scriptedmarine.txt b/wadsrc/static/zscript/doom/scriptedmarine.txt new file mode 100644 index 000000000..358bf4ea4 --- /dev/null +++ b/wadsrc/static/zscript/doom/scriptedmarine.txt @@ -0,0 +1,309 @@ + +// Scriptable marine ------------------------------------------------------- + +class ScriptedMarine : Actor native +{ + Default + { + Health 100; + Radius 16; + Height 56; + Mass 100; + Speed 8; + Painchance 160; + MONSTER; + -COUNTKILL + Translation 0; + Damage 100; + DeathSound "*death"; + PainSound "*pain50"; + } + + action native void A_M_Refire (bool ignoremissile=false); + action native void A_M_CheckAttack (); + action native void A_MarineChase (); + action native void A_MarineLook (); + action native void A_MarineNoise (); + action native void A_M_Punch (int force); + action native void A_M_SawRefire (); + action native void A_M_FirePistol (bool accurate); + action native void A_M_FireShotgun (); + action native void A_M_FireShotgun2 (); + action native void A_M_FireCGun(bool accurate); + action native void A_M_FireMissile (); + action native void A_M_FirePlasma (); + action native void A_M_FireRailgun (); + action native void A_M_BFGsound (); + action native void A_M_FireBFG (); + + States + { + Spawn: + PLAY A 4 A_MarineLook; + PLAY A 4 A_MarineNoise; + Loop; + Idle: + PLAY A 4 A_MarineLook; + PLAY A 4 A_MarineNoise; + PLAY A 4 A_MarineLook; + PLAY B 4 A_MarineNoise; + PLAY B 4 A_MarineLook; + PLAY B 4 A_MarineNoise; + Loop; + See: + PLAY ABCD 4 A_MarineChase; + Loop; + + Melee.Fist: + PLAY E 4 A_FaceTarget; + PLAY E 4 A_M_Punch(1); + PLAY A 9; + PLAY A 0 A_M_Refire(1); + Loop; + PLAY A 5 A_FaceTarget; + Goto See; + Melee.Berserk: + PLAY E 4 A_FaceTarget; + PLAY E 4 A_M_Punch(10); + PLAY A 9; + PLAY A 0 A_M_Refire(1); + Loop; + PLAY A 5 A_FaceTarget; + Goto See; + Melee.Chainsaw: + PLAY E 4 A_MarineNoise; + PLAY E 4 A_M_Saw; + PLAY E 0 A_M_SawRefire; + goto Melee.Chainsaw+1; + PLAY A 0; + Goto See; + + Missile: + Missile.None: + PLAY E 12 A_FaceTarget; + Goto Idle; + PLAY F 6 BRIGHT; + Loop; + Missile.Pistol: + PLAY E 4 A_FaceTarget; + PLAY F 6 BRIGHT A_M_FirePistol(1); + PLAY A 4 A_FaceTarget; + PLAY A 0 A_M_Refire; + PLAY A 5; + Goto See; + Fireloop.Pistol: + PLAY F 6 BRIGHT A_M_FirePistol(0); + PLAY A 4 A_FaceTarget; + PLAY A 0 A_M_Refire; + Goto Fireloop.Pistol; + PLAY A 5; + Goto See; + Missile.Shotgun: + PLAY E 3 A_M_CheckAttack; + PLAY F 7 BRIGHT A_M_FireShotgun; + Goto See; + Missile.SSG: + PLAY E 3 A_M_CheckAttack; + PLAY F 7 BRIGHT A_M_FireShotgun2; + Goto See; + Missile.Chaingun: + PLAY E 4 A_FaceTarget; + PLAY FF 4 BRIGHT A_M_FireCGun(1); + PLAY FF 4 BRIGHT A_M_FireCGun(0); + PLAY A 0 A_M_Refire; + Goto Missile.Chaingun+3; + PLAY A 0; + Goto See; + Missile.Rocket: + PLAY E 8; + PLAY F 6 BRIGHT A_M_FireMissile; + PLAY E 6; + PLAY A 0 A_M_Refire; + Loop; + PLAY A 0; + Goto See; + Missile.Plasma: + PLAY E 2 A_FaceTarget; + PLAY E 0 A_FaceTarget; + PLAY F 3 BRIGHT A_M_FirePlasma; + PLAY A 0 A_M_Refire; + Goto Missile.Plasma+1; + PLAY A 0; + Goto See; + Missile.Railgun: + PLAY E 4 A_M_CheckAttack; + PLAY F 6 BRIGHT A_M_FireRailgun; + Goto See; + Missile.BFG: + PLAY E 5 A_M_BFGSound; + PLAY EEEEE 5 A_FaceTarget; + PLAY F 6 BRIGHT A_M_FireBFG; + PLAY A 4 A_FaceTarget; + PLAY A 0 A_M_Refire; + Loop; + PLAY A 0; + Goto See; + + SkipAttack: + PLAY A 1; + Goto See; + Pain: + PLAY G 4; + PLAY G 4 A_Pain; + Goto Idle; + Death: + PLAY H 10; + PLAY I 10 A_Scream; + PLAY J 10 A_NoBlocking; + PLAY KLM 10; + PLAY N -1; + Stop; + XDeath: + PLAY O 5; + PLAY P 5 A_XScream; + PLAY Q 5 A_NoBlocking; + PLAY RSTUV 5; + PLAY W -1; + Stop; + Raise: + PLAY MLKJIH 5; + Goto See; + } +} + +//--------------------------------------------------------------------------- + +class MarineFist : ScriptedMarine +{ + States + { + Melee: + Goto Super::Melee.Fist; + Missile: + Stop; + } +} + + +//--------------------------------------------------------------------------- + +class MarineBerserk : MarineFist +{ + States + { + Melee: + Goto Super::Melee.Berserk; + Missile: + Stop; + } +} +//--------------------------------------------------------------------------- + +class MarineChainsaw : ScriptedMarine +{ + States + { + Melee: + Goto Super::Melee.Chainsaw; + Missile: + Stop; + } +} + + + +//--------------------------------------------------------------------------- + +class MarinePistol : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.Pistol; + } + +} + +//--------------------------------------------------------------------------- + +class MarineShotgun : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.Shotgun; + } + +} + + + +//--------------------------------------------------------------------------- + +class MarineSSG : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.SSG; + } +} + +//--------------------------------------------------------------------------- + +class MarineChaingun : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.Chaingun; + } +} + + +//--------------------------------------------------------------------------- + +class MarineRocket : MarineFist +{ + States + { + Missile: + Goto Super::Missile.Rocket; + } + +} + +//--------------------------------------------------------------------------- + +class MarinePlasma : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.Plasma; + } + +} + +//--------------------------------------------------------------------------- + +class MarineRailgun : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.Railgun; + } + +} + +//--------------------------------------------------------------------------- + +class MarineBFG : ScriptedMarine +{ + States + { + Missile: + Goto Super::Missile.BFG; + } +} diff --git a/wadsrc/static/zscript/doom/spidermaster.txt b/wadsrc/static/zscript/doom/spidermaster.txt new file mode 100644 index 000000000..b9f060068 --- /dev/null +++ b/wadsrc/static/zscript/doom/spidermaster.txt @@ -0,0 +1,62 @@ +//=========================================================================== +// +// Spider boss +// +//=========================================================================== +class SpiderMastermind : Actor +{ + Default + { + Health 3000; + Radius 128; + Height 100; + Mass 1000; + Speed 12; + PainChance 40; + Monster; + MinMissileChance 160; + +BOSS + +MISSILEMORE + +FLOORCLIP + +NORADIUSDMG + +DONTMORPH + +BOSSDEATH + SeeSound "spider/sight"; + AttackSound "spider/attack"; + PainSound "spider/pain"; + DeathSound "spider/death"; + ActiveSound "spider/active"; + Obituary "$OB_SPIDER"; + } + States + { + Spawn: + SPID AB 10 A_Look; + Loop; + See: + SPID A 3 A_Metal; + SPID ABB 3 A_Chase; + SPID C 3 A_Metal; + SPID CDD 3 A_Chase; + SPID E 3 A_Metal; + SPID EFF 3 A_Chase; + Loop; + Missile: + SPID A 20 BRIGHT A_FaceTarget; + SPID G 4 BRIGHT A_SPosAttackUseAtkSound; + SPID H 4 BRIGHT A_SposAttackUseAtkSound; + SPID H 1 BRIGHT A_SpidRefire; + Goto Missile+1; + Pain: + SPID I 3; + SPID I 3 A_Pain; + Goto See; + Death: + SPID J 20 A_Scream; + SPID K 10 A_NoBlocking; + SPID LMNOPQR 10; + SPID S 30; + SPID S -1 A_BossDeath; + Stop; + } +} diff --git a/wadsrc/static/zscript/doom/stealthmonsters.txt b/wadsrc/static/zscript/doom/stealthmonsters.txt new file mode 100644 index 000000000..785261fbb --- /dev/null +++ b/wadsrc/static/zscript/doom/stealthmonsters.txt @@ -0,0 +1,139 @@ + +class StealthArachnotron : Arachnotron +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHBABY"; + } +} + +class StealthArchvile : Archvile +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHVILE"; + } +} + +class StealthBaron : BaronOfHell +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHBARON"; + HitObituary "$OB_STEALTHBARON"; + } +} + +class StealthCacodemon : Cacodemon +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHCACO"; + HitObituary "$OB_STEALTHCACO"; + } +} + +class StealthChaingunGuy : ChaingunGuy +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHCHAINGUY"; + } +} + +class StealthDemon : Demon +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHDEMON"; + HitObituary "$OB_STEALTHDEMON"; + } +} + +class StealthHellKnight : HellKnight +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHKNIGHT"; + HitObituary "$OB_STEALTHKNIGHT"; + } +} + +class StealthDoomImp : DoomImp +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHIMP"; + HitObituary "$OB_STEALTHIMP"; + } +} + +class StealthFatso : Fatso +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHFATSO"; + } +} + +class StealthRevenant : Revenant +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHUNDEAD"; + HitObituary "$OB_STEALTHUNDEAD"; + } +} + +class StealthShotgunGuy : ShotgunGuy +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHSHOTGUNGUY"; + } +} + +class StealthZombieMan : ZombieMan +{ + Default + { + +STEALTH + RenderStyle "Translucent"; + Alpha 0; + Obituary "$OB_STEALTHZOMBIE"; + } +} + From 52005214c1ecd93e81cc6feabee2656314e839d4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 21:15:46 +0200 Subject: [PATCH 031/255] - Added some fudging so that A_PlayerSkinCheck creates proper code until I can rewrite the FunctionCall expression to match what the script compiler needs. The current version of this class is too much geared toward DECORATE. --- src/namedef.h | 4 +-- .../codegeneration/thingdef_expression.cpp | 33 ++++++++++++++----- 2 files changed, 27 insertions(+), 10 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index 8d883d566..8d60c97ee 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -672,8 +672,8 @@ xx(DecoRandom) xx(DecoFRandom) xx(DecoCallLineSpecial) xx(DecoNameToClass) -xx(DecoFindMultiNameState) -xx(DecoFindSingleNameState) +xx(BuiltinFindMultiNameState) +xx(BuiltinFindSingleNameState) xx(DecoHandleRuntimeState) xx(Damage) diff --git a/src/scripting/codegeneration/thingdef_expression.cpp b/src/scripting/codegeneration/thingdef_expression.cpp index 77b062ed6..a352c7b87 100644 --- a/src/scripting/codegeneration/thingdef_expression.cpp +++ b/src/scripting/codegeneration/thingdef_expression.cpp @@ -3632,7 +3632,10 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) PFunction *afd = dyn_cast(ctx.Class->Symbols.FindSymbol(MethodName, true)); if (afd != nullptr) { - return new FxVMFunctionCall(afd, ArgList, ScriptPosition, false); + auto x = new FxVMFunctionCall(afd, ArgList, ScriptPosition, false); + ArgList = nullptr; + delete this; + return x->Resolve(ctx); } for (size_t i = 0; i < countof(FxFlops); ++i) @@ -3927,11 +3930,25 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); bool failed = false; + auto proto = Function->Variants[0].Implementation->Proto; + auto argtypes = proto->ArgumentTypes; + + int implicit; + if (Function->Flags & VARF_Action) implicit = 3; + else if (Function->Flags & VARF_Method) implicit = 1; + else implicit = 0; if (ArgList != NULL) { for (unsigned i = 0; i < ArgList->Size(); i++) { + // temporary hack to let strings get compiled as state. This will have to be done more intelligently. + if (i+implicit < argtypes.Size() && argtypes[i+implicit] == TypeState && (*ArgList)[i]->isConstant() && static_cast((*ArgList)[i])->ValueType == TypeString) + { + auto statenode = new FxMultiNameState(static_cast((*ArgList)[i])->GetValue().GetString(), ScriptPosition); + delete (*ArgList)[i]; + (*ArgList)[i] = statenode; + } (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); if ((*ArgList)[i] == NULL) failed = true; } @@ -3941,7 +3958,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) delete this; return NULL; } - TArray &rets = Function->Variants[0].Implementation->Proto->ReturnTypes; + TArray &rets = proto->ReturnTypes; if (rets.Size() > 0) { ValueType = rets[0]; @@ -5175,7 +5192,7 @@ static int DoFindState(VMFrameStack *stack, VMValue *param, int numparam, VMRetu } // Find a state with any number of dots in its name. -int DecoFindMultiNameState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int BuiltinFindMultiNameState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) { assert(numparam > 1); assert(numret == 1); @@ -5191,7 +5208,7 @@ int DecoFindMultiNameState(VMFrameStack *stack, VMValue *param, int numparam, VM } // Find a state without any dots in its name. -int DecoFindSingleNameState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int BuiltinFindSingleNameState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) { assert(numparam == 2); assert(numret == 1); @@ -5217,18 +5234,18 @@ ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) build->EmitParamInt(names[i]); } - // For one name, use the DecoFindSingleNameState function. For more than - // one name, use the DecoFindMultiNameState function. + // For one name, use the BuiltinFindSingleNameState function. For more than + // one name, use the BuiltinFindMultiNameState function. VMFunction *callfunc; PSymbol *sym; if (names.Size() == 1) { - sym = FindDecorateBuiltinFunction(NAME_DecoFindSingleNameState, DecoFindSingleNameState); + sym = FindDecorateBuiltinFunction(NAME_BuiltinFindSingleNameState, BuiltinFindSingleNameState); } else { - sym = FindDecorateBuiltinFunction(NAME_DecoFindMultiNameState, DecoFindMultiNameState); + sym = FindDecorateBuiltinFunction(NAME_BuiltinFindMultiNameState, BuiltinFindMultiNameState); } assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); From d00e93bdab779548413f49385bb13d1908d6f7e9 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 21:56:45 +0200 Subject: [PATCH 032/255] - fixed order of state setup. It looks like the setup of the action function and the adding of the states got inverted by something I tried, leaving the ActionFunc member empty on the real states. --- src/scripting/zscript/zcc_compile.cpp | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f24bce20c..d034c51cc 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2169,13 +2169,6 @@ void ZCCCompiler::CompileStates() } #endif - int count = statedef.AddStates(&state, sl->Frames->GetChars()); - if (count < 0) - { - Error(sl, "Invalid frame character string '%s'", sl->Frames->GetChars()); - count = -count; - } - if (sl->Action != nullptr) { auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); @@ -2184,6 +2177,13 @@ void ZCCCompiler::CompileStates() state.ActionFunc = FunctionBuildList.AddFunction(c->Type(), code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), true); } } + + int count = statedef.AddStates(&state, sl->Frames->GetChars()); + if (count < 0) + { + Error(sl, "Invalid frame character string '%s'", sl->Frames->GetChars()); + count = -count; + } break; } case AST_StateGoto: From 9def9ec095864dbcc71792adafe6d5b4cdfb31e1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 22:54:22 +0200 Subject: [PATCH 033/255] - added more casting kludges so that I can run some tests with Heretic's definitions. --- src/dobjtype.h | 11 ----- .../codegeneration/thingdef_expression.cpp | 40 ++++++++++++++++--- 2 files changed, 35 insertions(+), 16 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index 19aeca71b..b41ffe0e6 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -824,17 +824,6 @@ inline PClass::MetaClass *PClass::GetClass() const return static_cast(DObject::GetClass()); } -// A class that hasn't had its parent class defined yet --------------------- - -class PClassWaitingForParent : public PClass -{ - DECLARE_CLASS(PClassWaitingForParent, PClass); -public: - PClassWaitingForParent(FName myname, FName parentname); - - FName ParentName; -}; - // Type tables -------------------------------------------------------------- struct FTypeTable diff --git a/src/scripting/codegeneration/thingdef_expression.cpp b/src/scripting/codegeneration/thingdef_expression.cpp index a352c7b87..323ca083e 100644 --- a/src/scripting/codegeneration/thingdef_expression.cpp +++ b/src/scripting/codegeneration/thingdef_expression.cpp @@ -3942,13 +3942,43 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) { for (unsigned i = 0; i < ArgList->Size(); i++) { - // temporary hack to let strings get compiled as state. This will have to be done more intelligently. - if (i+implicit < argtypes.Size() && argtypes[i+implicit] == TypeState && (*ArgList)[i]->isConstant() && static_cast((*ArgList)[i])->ValueType == TypeString) + if ((*ArgList)[i]->isConstant()) { - auto statenode = new FxMultiNameState(static_cast((*ArgList)[i])->GetValue().GetString(), ScriptPosition); - delete (*ArgList)[i]; - (*ArgList)[i] = statenode; + if (i + implicit < argtypes.Size()) + { + auto type = static_cast((*ArgList)[i])->ValueType; + // temporary hack to add the casts which get used by the internal definitions + if (argtypes[i + implicit] == TypeState && type == TypeString) + { + ScriptPosition.Message(MSG_WARNING, "Converting %s to state", static_cast((*ArgList)[i])->GetValue().GetString()); + auto statenode = new FxMultiNameState(static_cast((*ArgList)[i])->GetValue().GetString(), ScriptPosition); + delete (*ArgList)[i]; + (*ArgList)[i] = statenode; + } + if (argtypes[i + implicit] == TypeSound && type == TypeString) + { + ScriptPosition.Message(MSG_WARNING, "Converting %s to sound", static_cast((*ArgList)[i])->GetValue().GetString()); + auto statenode = new FxConstant(FSoundID(static_cast((*ArgList)[i])->GetValue().GetString()), ScriptPosition); + delete (*ArgList)[i]; + (*ArgList)[i] = statenode; + } + if (argtypes[i + implicit] == TypeSInt32 && type == TypeFloat64) + { + ScriptPosition.Message(MSG_WARNING, "Converting %f to int", static_cast((*ArgList)[i])->GetValue().GetFloat()); + auto statenode = new FxConstant(static_cast((*ArgList)[i])->GetValue().GetInt(), ScriptPosition); + delete (*ArgList)[i]; + (*ArgList)[i] = statenode; + } + if (argtypes[i + implicit] == TypeFloat64 && type == TypeSInt32) + { + ScriptPosition.Message(MSG_WARNING, "Converting %d to float", static_cast((*ArgList)[i])->GetValue().GetInt()); + auto statenode = new FxConstant(static_cast((*ArgList)[i])->GetValue().GetFloat(), ScriptPosition); + delete (*ArgList)[i]; + (*ArgList)[i] = statenode; + } + } } + (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); if ((*ArgList)[i] == NULL) failed = true; } From 7bdd320f13ec6362d97b1147a5286c4eee77ca85 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 14 Oct 2016 23:51:38 +0200 Subject: [PATCH 034/255] - forgot to save this. --- src/dobjtype.h | 1 - 1 file changed, 1 deletion(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index b41ffe0e6..aee2d0ae2 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -852,7 +852,6 @@ PArray *NewArray(PType *type, unsigned int count); PDynArray *NewDynArray(PType *type); PPointer *NewPointer(PType *type); PClassPointer *NewClassPointer(PClass *restrict); -PClassWaitingForParent *NewUnknownClass(FName myname, FName parentname); PEnum *NewEnum(FName name, PTypeBase *outer); PStruct *NewStruct(FName name, PTypeBase *outer); PPrototype *NewPrototype(const TArray &rettypes, const TArray &argtypes); From d8a8b590061c839f90774ca98018658d941b5b78 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 10:34:26 +0200 Subject: [PATCH 035/255] - cleaned up the loop statement nodes in the code generator, which put some handling in FCompileContext and some of their data into the base FxExpression class instead of having an intermediate base class for all loops which is responsible for the relevant data. All this is now encapsulated in a new FxLoopStatement class which serves as base for the actual loop statements. --- src/scripting/codegeneration/thingdef_exp.h | 34 ++++++--- .../codegeneration/thingdef_expression.cpp | 72 +++++++++++-------- 2 files changed, 65 insertions(+), 41 deletions(-) diff --git a/src/scripting/codegeneration/thingdef_exp.h b/src/scripting/codegeneration/thingdef_exp.h index 2e9af65b6..3c52547c5 100644 --- a/src/scripting/codegeneration/thingdef_exp.h +++ b/src/scripting/codegeneration/thingdef_exp.h @@ -198,9 +198,6 @@ protected: FxExpression(const FScriptPosition &pos) : ScriptPosition(pos) { - isresolved = false; - ScriptPosition = pos; - ValueType = NULL; } public: virtual ~FxExpression() {} @@ -215,12 +212,10 @@ public: virtual ExpEmit Emit(VMFunctionBuilder *build); - TArray JumpAddresses; - FScriptPosition ScriptPosition; - PType *ValueType; + PType *ValueType = nullptr; - bool isresolved; + bool isresolved = false; }; //========================================================================== @@ -1003,13 +998,32 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// Base class for loops +// +//========================================================================== + +class FxLoopStatement : public FxExpression +{ +protected: + FxLoopStatement(const FScriptPosition &pos) + : FxExpression(pos) + { + } + + void HandleJumps(int token, FCompileContext &ctx); + + TArray JumpAddresses; +}; + //========================================================================== // // FxWhileLoop // //========================================================================== -class FxWhileLoop : public FxExpression +class FxWhileLoop : public FxLoopStatement { FxExpression *Condition; FxExpression *Code; @@ -1027,7 +1041,7 @@ public: // //========================================================================== -class FxDoWhileLoop : public FxExpression +class FxDoWhileLoop : public FxLoopStatement { FxExpression *Condition; FxExpression *Code; @@ -1045,7 +1059,7 @@ public: // //========================================================================== -class FxForLoop : public FxExpression +class FxForLoop : public FxLoopStatement { FxExpression *Init; FxExpression *Condition; diff --git a/src/scripting/codegeneration/thingdef_expression.cpp b/src/scripting/codegeneration/thingdef_expression.cpp index 323ca083e..2a6cf51aa 100644 --- a/src/scripting/codegeneration/thingdef_expression.cpp +++ b/src/scripting/codegeneration/thingdef_expression.cpp @@ -104,20 +104,6 @@ PSymbol *FCompileContext::FindGlobal(FName identifier) return GlobalSymbols.FindSymbol(identifier, true); } -void FCompileContext::HandleJumps(int token, FxExpression *handler) -{ - for (unsigned int i = 0; i < Jumps.Size(); i++) - { - if (Jumps[i]->Token == token) - { - Jumps[i]->AddressResolver = handler; - handler->JumpAddresses.Push(Jumps[i]); - Jumps.Delete(i); - i--; - } - } -} - void FCompileContext::CheckReturn(PPrototype *proto, FScriptPosition &pos) { assert(proto != nullptr); @@ -4398,6 +4384,27 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) return ExpEmit(); } + +//========================================================================== +// +// FxLoopStatement +// +//========================================================================== + +void FxLoopStatement::HandleJumps(int token, FCompileContext &ctx) +{ + for (unsigned int i = 0; i < ctx.Jumps.Size(); i++) + { + if (ctx.Jumps[i]->Token == token) + { + ctx.Jumps[i]->AddressResolver = this; + JumpAddresses.Push(ctx.Jumps[i]); + ctx.Jumps.Delete(i); + i--; + } + } +} + //========================================================================== // // FxWhileLoop @@ -4405,7 +4412,7 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) //========================================================================== FxWhileLoop::FxWhileLoop(FxExpression *condition, FxExpression *code, const FScriptPosition &pos) -: FxExpression(pos), Condition(condition), Code(code) +: FxLoopStatement(pos), Condition(condition), Code(code) { ValueType = TypeVoid; } @@ -4422,8 +4429,8 @@ FxExpression *FxWhileLoop::Resolve(FCompileContext &ctx) SAFE_RESOLVE(Condition, ctx); SAFE_RESOLVE_OPT(Code, ctx); - ctx.HandleJumps(TK_Break, this); - ctx.HandleJumps(TK_Continue, this); + HandleJumps(TK_Break, ctx); + HandleJumps(TK_Continue, ctx); if (Condition->ValueType != TypeBool) { @@ -4506,7 +4513,7 @@ ExpEmit FxWhileLoop::Emit(VMFunctionBuilder *build) //========================================================================== FxDoWhileLoop::FxDoWhileLoop(FxExpression *condition, FxExpression *code, const FScriptPosition &pos) -: FxExpression(pos), Condition(condition), Code(code) +: FxLoopStatement(pos), Condition(condition), Code(code) { ValueType = TypeVoid; } @@ -4523,8 +4530,8 @@ FxExpression *FxDoWhileLoop::Resolve(FCompileContext &ctx) SAFE_RESOLVE(Condition, ctx); SAFE_RESOLVE_OPT(Code, ctx); - ctx.HandleJumps(TK_Break, this); - ctx.HandleJumps(TK_Continue, this); + HandleJumps(TK_Break, ctx); + HandleJumps(TK_Continue, ctx); if (Condition->ValueType != TypeBool) { @@ -4608,7 +4615,7 @@ ExpEmit FxDoWhileLoop::Emit(VMFunctionBuilder *build) //========================================================================== FxForLoop::FxForLoop(FxExpression *init, FxExpression *condition, FxExpression *iteration, FxExpression *code, const FScriptPosition &pos) -: FxExpression(pos), Init(init), Condition(condition), Iteration(iteration), Code(code) +: FxLoopStatement(pos), Init(init), Condition(condition), Iteration(iteration), Code(code) { ValueType = TypeVoid; } @@ -4629,8 +4636,8 @@ FxExpression *FxForLoop::Resolve(FCompileContext &ctx) SAFE_RESOLVE_OPT(Iteration, ctx); SAFE_RESOLVE_OPT(Code, ctx); - ctx.HandleJumps(TK_Break, this); - ctx.HandleJumps(TK_Continue, this); + HandleJumps(TK_Break, ctx); + HandleJumps(TK_Continue, ctx); if (Condition != nullptr) { @@ -5041,17 +5048,20 @@ static bool VerifyJumpTarget(AActor *stateowner, FStateParamInfo *stateinfo, int { PClassActor *cls = stateowner->GetClass(); - while (cls != RUNTIME_CLASS(AActor)) + if (stateinfo->mCallingState != nullptr) { - // both calling and target state need to belong to the same class. - if (cls->OwnsState(stateinfo->mCallingState)) + while (cls != RUNTIME_CLASS(AActor)) { - return cls->OwnsState(stateinfo->mCallingState + index); - } + // both calling and target state need to belong to the same class. + if (cls->OwnsState(stateinfo->mCallingState)) + { + return cls->OwnsState(stateinfo->mCallingState + index); + } - // We can safely assume the ParentClass is of type PClassActor - // since we stop when we see the Actor base class. - cls = static_cast(cls->ParentClass); + // We can safely assume the ParentClass is of type PClassActor + // since we stop when we see the Actor base class. + cls = static_cast(cls->ParentClass); + } } return false; } From f86e64e712ab1af01467f7c324c7ba834b44754f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 10:39:58 +0200 Subject: [PATCH 036/255] - renamed thingdef_expression to codegen. Eventually this needs to be split up into smaller units because the file is already quite large and there's still a lot to add here. --- src/CMakeLists.txt | 2 +- .../codegeneration/{thingdef_expression.cpp => codegen.cpp} | 0 src/scripting/codegeneration/{thingdef_exp.h => codegen.h} | 0 3 files changed, 1 insertion(+), 1 deletion(-) rename src/scripting/codegeneration/{thingdef_expression.cpp => codegen.cpp} (100%) rename src/scripting/codegeneration/{thingdef_exp.h => codegen.h} (100%) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index b612684d5..ab9306447 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1247,7 +1247,7 @@ set (PCH_SOURCES scripting/thingdef.cpp scripting/thingdef_data.cpp scripting/thingdef_properties.cpp - scripting/codegeneration/thingdef_expression.cpp + scripting/codegeneration/codegen.cpp scripting/decorate/olddecorations.cpp scripting/decorate/thingdef_exp.cpp scripting/decorate/thingdef_parse.cpp diff --git a/src/scripting/codegeneration/thingdef_expression.cpp b/src/scripting/codegeneration/codegen.cpp similarity index 100% rename from src/scripting/codegeneration/thingdef_expression.cpp rename to src/scripting/codegeneration/codegen.cpp diff --git a/src/scripting/codegeneration/thingdef_exp.h b/src/scripting/codegeneration/codegen.h similarity index 100% rename from src/scripting/codegeneration/thingdef_exp.h rename to src/scripting/codegeneration/codegen.h From 3b0d687b22b8e04ae13b348af389097882d2df44 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 10:43:02 +0200 Subject: [PATCH 037/255] - committed from the wrong subdirectory and missed all files that just changed the #include line. --- src/scripting/decorate/olddecorations.cpp | 2 +- src/scripting/decorate/thingdef_exp.cpp | 2 +- src/scripting/decorate/thingdef_parse.cpp | 2 +- src/scripting/decorate/thingdef_states.cpp | 2 +- src/scripting/thingdef.cpp | 2 +- src/scripting/vm/vmbuilder.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 3 ++- 7 files changed, 8 insertions(+), 7 deletions(-) diff --git a/src/scripting/decorate/olddecorations.cpp b/src/scripting/decorate/olddecorations.cpp index 4bcb2c36c..75e49dbaa 100644 --- a/src/scripting/decorate/olddecorations.cpp +++ b/src/scripting/decorate/olddecorations.cpp @@ -48,7 +48,7 @@ #include "decallib.h" #include "i_system.h" #include "thingdef.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" #include "r_data/r_translate.h" // TYPES ------------------------------------------------------------------- diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 2f52fb260..5dc909cd0 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -48,7 +48,7 @@ #include "thingdef.h" #include "p_lnspec.h" #include "doomstat.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" FRandom pr_exrandom ("EX_Random"); diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index f567d91e0..e48d4d856 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -49,7 +49,7 @@ #include "v_palette.h" #include "doomerrors.h" #include "i_system.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" #include "w_wad.h" #include "v_video.h" #include "version.h" diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 143144aa5..f2dda5548 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -54,7 +54,7 @@ #include "s_sound.h" #include "i_system.h" #include "colormatcher.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" #include "version.h" #include "templates.h" #include "vmbuilder.h" diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 1a761b8c2..1ed0ea910 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -61,7 +61,7 @@ #include "p_conversation.h" #include "v_text.h" #include "thingdef.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" #include "a_sharedglobal.h" #include "vmbuilder.h" #include "stats.h" diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index f111c4529..4351723f8 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -32,7 +32,7 @@ */ #include "vmbuilder.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" #include "info.h" #include "m_argv.h" #include "thingdef.h" diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index d034c51cc..2016659fa 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -47,7 +47,7 @@ #include "p_lnspec.h" #include "i_system.h" #include "gdtoa.h" -#include "codegeneration/thingdef_exp.h" +#include "codegeneration/codegen.h" #include "vmbuilder.h" #define DEFINING_CONST ((PSymbolConst *)(void *)1) @@ -2290,6 +2290,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case AST_ExprFuncCall: { auto fcall = static_cast(ast); + //return ConvertFunctionCall(fcall); assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. auto fname = static_cast(fcall->Function)->Identifier; return new FxFunctionCall(nullptr, fname, ConvertNodeList(fcall->Parameters), *ast); From 2cb5839c1133a44378ff277e0bc2d6d340aa2abf Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 12:15:25 +0200 Subject: [PATCH 038/255] - count errors in the parser and abort afterward if there were some. - use FScriptPosition's error counter throughout the compiler so that there is only one counter for everything, not two. Parts of the compiler use FScriptPosition, so this is easier to handle than having a separate counter in the compiler class. It also avoids having to pass the compiler object to any function where an error may be output. The TreeNodes contain sufficient data to be converted to an FScriptPosition and using that for error message formatting. --- src/CMakeLists.txt | 1 + src/sc_man.cpp | 2 ++ src/sc_man.h | 2 ++ src/scripting/thingdef.cpp | 1 + src/scripting/zscript/zcc-parse.lemon | 1 + src/scripting/zscript/zcc_compile.cpp | 11 +++++------ src/scripting/zscript/zcc_compile.h | 2 -- src/scripting/zscript/zcc_parser.cpp | 20 ++++++++++++++++++++ 8 files changed, 32 insertions(+), 8 deletions(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ab9306447..545400b1c 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1248,6 +1248,7 @@ set (PCH_SOURCES scripting/thingdef_data.cpp scripting/thingdef_properties.cpp scripting/codegeneration/codegen.cpp + scripting/codegeneration/functioncalls.cpp scripting/decorate/olddecorations.cpp scripting/decorate/thingdef_exp.cpp scripting/decorate/thingdef_parse.cpp diff --git a/src/sc_man.cpp b/src/sc_man.cpp index 97f384f3d..f48d6b461 100644 --- a/src/sc_man.cpp +++ b/src/sc_man.cpp @@ -1006,6 +1006,7 @@ void FScanner::CheckOpen() // //========================================================================== int FScriptPosition::ErrorCounter; +int FScriptPosition::WarnCounter; bool FScriptPosition::StrictErrors; // makes all OPTERRPR messages real errors. FScriptPosition::FScriptPosition(const FScriptPosition &other) @@ -1072,6 +1073,7 @@ void FScriptPosition::Message (int severity, const char *message, ...) const return; case MSG_WARNING: + WarnCounter++; type = "warning"; color = TEXTCOLOR_YELLOW; break; diff --git a/src/sc_man.h b/src/sc_man.h index c319a7a2f..5eeacd892 100644 --- a/src/sc_man.h +++ b/src/sc_man.h @@ -139,6 +139,7 @@ enum struct FScriptPosition { + static int WarnCounter; static int ErrorCounter; static bool StrictErrors; FString FileName; @@ -155,6 +156,7 @@ struct FScriptPosition void Message(int severity, const char *message,...) const; static void ResetErrorCounter() { + WarnCounter = 0; ErrorCounter = 0; } }; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 1ed0ea910..f62997816 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -127,6 +127,7 @@ void LoadActors () InitThingdef(); ParseScripts(); + ParseAllDecorate(); FunctionBuildList.Build(); diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index cd1cbce14..78a4d29ea 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -99,6 +99,7 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) } } stat->sc->ScriptMessage("%s\n%s\n", unexpected.GetChars(), expecting.GetChars()); + FScriptPosition::ErrorCounter++; } %parse_accept { DPrintf(DMSG_SPAMMY, "Input accepted\n"); } %parse_failure { /**failed = true;*/ } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 2016659fa..f2f7b4d4b 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -203,8 +203,9 @@ void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode, ZC //========================================================================== ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, PSymbolTable &_outsymbols) - : Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast), ErrorCount(0), WarnCount(0) + : Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast) { + FScriptPosition::ResetErrorCounter(); // Group top-level nodes by type if (ast.TopNode != NULL) { @@ -320,7 +321,7 @@ void ZCCCompiler::Warn(ZCC_TreeNode *node, const char *msg, ...) MessageV(node, TEXTCOLOR_ORANGE, msg, argptr); va_end(argptr); - WarnCount++; + FScriptPosition::WarnCounter++; } //========================================================================== @@ -338,7 +339,7 @@ void ZCCCompiler::Error(ZCC_TreeNode *node, const char *msg, ...) MessageV(node, TEXTCOLOR_RED, msg, argptr); va_end(argptr); - ErrorCount++; + FScriptPosition::ErrorCounter++; } //========================================================================== @@ -376,7 +377,7 @@ int ZCCCompiler::Compile() InitDefaults(); InitFunctions(); CompileStates(); - return ErrorCount; + return FScriptPosition::ErrorCounter; } //========================================================================== @@ -1678,7 +1679,6 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper } } // call the handler - FScriptPosition::ErrorCounter = 0; try { prop->Handler(defaults, bag.Info, bag, ¶ms[0]); @@ -1687,7 +1687,6 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper { Error(property, "%s", error.GetMessage()); } - ErrorCount += FScriptPosition::ErrorCounter; } //========================================================================== diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 2ca00459a..12e570330 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -146,8 +146,6 @@ private: PSymbolTable *GlobalTreeNodes; PSymbolTable *OutputSymbols; ZCC_AST &AST; - int ErrorCount; - int WarnCount; }; void ZCC_InitConversions(); diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index b803b4158..c3f75b2b0 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -39,6 +39,7 @@ #include "cmdlib.h" #include "m_alloc.h" #include "i_system.h" +#include "v_text.h" #include "zcc_parser.h" #include "zcc_compile.h" @@ -323,6 +324,12 @@ static void DoParse(int lumpnum) ZCCParse(parser, 0, value, &state); ZCCParseFree(parser, free); + // If the parser fails, there is no point starting the compiler, because it'd only flood the output with endless errors. + if (FScriptPosition::ErrorCounter > 0) + { + I_Error("%d errors while parsing %s", FScriptPosition::ErrorCounter, Wads.GetLumpFullPath(lumpnum)); + } + { // Make a dump of the AST before running the compiler for diagnostic purposes. #ifdef _DEBUG @@ -347,11 +354,24 @@ static void DoParse(int lumpnum) symtable.SetName("Global_Node"); ZCCCompiler cc(state, NULL, symtable, GlobalSymbols); cc.Compile(); + + if (FScriptPosition::ErrorCounter > 0) + { + // Abort if the compiler produced any errors. Also do not compile further lumps, because they very likely miss some stuff. + I_Error("%d errors, %d warnings while compiling %s", FScriptPosition::ErrorCounter, FScriptPosition::WarnCounter, Wads.GetLumpFullPath(lumpnum)); + } + else if (FScriptPosition::WarnCounter > 0) + { + // If we got warnings, but no errors, print the information but continue. + Printf(TEXTCOLOR_ORANGE, "%d warnings while compiling %s", FScriptPosition::WarnCounter, Wads.GetLumpFullPath(lumpnum)); + } + } void ParseScripts() { int lump, lastlump = 0; + FScriptPosition::ResetErrorCounter(); while ((lump = Wads.FindLump("ZSCRIPT", &lastlump)) != -1) { DoParse(lump); From 32a3f57a5474244702f1b2084fce83a0142635cb Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 14:36:08 +0200 Subject: [PATCH 039/255] - more preparations to compile functions: * Allow PFunction to work without a VMFunction being attached. * The Variant for a function must store the prototype itself instead of relying on the VMFunction it points to. Otherwise it would not be possible to reference a prototype during compilation of the function because it does not exist yet. * Give the variant a list of the function's argument's names, because these are also needed to compile the function. * create an anonymous function symbol when the function gets registered to the builder. At this point we have all the needed information to set it up correctly, but later this is no longer the case. This is the most convenient info to have here because it contains everything that's needed to compile the function in the proper context, so it has to be present when starting compilation. * added some preparations to implement special handling for weapons and custom inventory items, which can run action functions in another actor's context. This part is not active yet but the basics are present in SetImplicitArgs. --- src/dobjtype.cpp | 6 +-- src/dobjtype.h | 5 +- src/namedef.h | 2 +- src/scripting/codegeneration/codegen.cpp | 4 +- src/scripting/decorate/thingdef_parse.cpp | 6 ++- src/scripting/decorate/thingdef_states.cpp | 5 +- src/scripting/thingdef.cpp | 58 ++++++++++++++++++---- src/scripting/thingdef.h | 3 +- src/scripting/thingdef_properties.cpp | 3 +- src/scripting/vm/vmbuilder.cpp | 36 ++++---------- src/scripting/vm/vmbuilder.h | 4 +- src/scripting/zscript/zcc_compile.cpp | 27 +++------- src/scripting/zscript/zcc_compile.h | 1 + 13 files changed, 91 insertions(+), 69 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 7709bfa8f..4dcb904d5 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2490,14 +2490,14 @@ size_t PFunction::PropagateMark() // //========================================================================== -unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, VMFunction *impl) +unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl) { Variant variant; - //variant.Proto = proto; + variant.Proto = proto; variant.ArgFlags = argflags; variant.Implementation = impl; - impl->Proto = proto; + if (impl != nullptr) impl->Proto = proto; return Variants.Push(variant); } diff --git a/src/dobjtype.h b/src/dobjtype.h index aee2d0ae2..9a51fa88a 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -692,14 +692,15 @@ class PFunction : public PSymbol public: struct Variant { - //PPrototype *Proto; + PPrototype *Proto; VMFunction *Implementation; TArray ArgFlags; // Should be the same length as Proto->ArgumentTypes + TArray ArgNames; // we need the names to access them later when the function gets compiled. }; TArray Variants; DWORD Flags; - unsigned AddVariant(PPrototype *proto, TArray &argflags, VMFunction *impl); + unsigned AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl); size_t PropagateMark(); diff --git a/src/namedef.h b/src/namedef.h index eedbaf899..43856aad1 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -717,7 +717,7 @@ xx(Max_10_Exp) // implicit function parameters xx(self) -xx(caller) +xx(invoker) xx(stateinfo) xx(__decorate_internal_int__) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 2a6cf51aa..0034de8a4 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3883,7 +3883,7 @@ FxVMFunctionCall::~FxVMFunctionCall() PPrototype *FxVMFunctionCall::ReturnProto() { EmitTail = true; - return Function->Variants[0].Implementation->Proto; + return Function->Variants[0].Proto; } //========================================================================== @@ -3916,7 +3916,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); bool failed = false; - auto proto = Function->Variants[0].Implementation->Proto; + auto proto = Function->Variants[0].Proto; auto argtypes = proto->ArgumentTypes; int implicit; diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index e48d4d856..f547956dd 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -458,6 +458,7 @@ void ParseFunctionDef(FScanner &sc, PClassActor *cls, FName funcname, const AFuncDesc *afd; TArray args; TArray argflags; + TArray argnames; afd = FindFunction(funcname); if (afd == NULL) @@ -467,13 +468,14 @@ void ParseFunctionDef(FScanner &sc, PClassActor *cls, FName funcname, } sc.MustGetToken('('); - SetImplicitArgs(&args, &argflags, cls, funcflags); + SetImplicitArgs(&args, &argflags, &argnames, cls, funcflags); + // This function will be removed once all internal classes have been ported so don't bother filling in the function's argument names, because for anything going through here they'll never be used. ParseArgListDef(sc, cls, args, argflags); if (afd != NULL) { PFunction *sym = new PFunction(funcname); - sym->AddVariant(NewPrototype(rets, args), argflags, *(afd->VMPointer)); + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, *(afd->VMPointer)); sym->Flags = funcflags; if (cls->Symbols.AddSymbol(sym) == NULL) { diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index f2dda5548..ada9462e0 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -322,7 +322,8 @@ do_stop: endofstate: if (ScriptCode != nullptr) { - state.ActionFunc = FunctionBuildList.AddFunction(actor, ScriptCode, FStringf("%s.StateFunction.%d", actor->TypeName.GetChars(), bag.statedef.GetStateCount()), true); + auto funcsym = CreateAnonymousFunction(actor, nullptr, VARF_Method | VARF_Action); + state.ActionFunc = FunctionBuildList.AddFunction(funcsym, ScriptCode, FStringf("%s.StateFunction.%d", actor->TypeName.GetChars(), bag.statedef.GetStateCount()), true); } int count = bag.statedef.AddStates(&state, statestring); if (count < 0) @@ -595,7 +596,7 @@ FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestring, B void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArray &out_params, PFunction *afd, FString statestring, FStateDefinitions *statedef) { - const TArray ¶ms = afd->Variants[0].Implementation->Proto->ArgumentTypes; + const TArray ¶ms = afd->Variants[0].Proto->ArgumentTypes; const TArray ¶mflags = afd->Variants[0].ArgFlags; int numparams = (int)params.Size(); int pnum = 0; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index f62997816..182bfbd12 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -80,34 +80,74 @@ PClassActor *QuestItemClasses[31]; // //========================================================================== -void SetImplicitArgs(TArray *args, TArray *argflags, PClass *cls, DWORD funcflags) +void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags) { // Must be called before adding any other arguments. - assert(args == NULL || args->Size() == 0); - assert(argflags == NULL || argflags->Size() == 0); + assert(args == nullptr || args->Size() == 0); + assert(argflags == nullptr || argflags->Size() == 0); if (funcflags & VARF_Method) { // implied self pointer - if (args != NULL) args->Push(NewClassPointer(cls)); - if (argflags != NULL) argflags->Push(VARF_Implicit); + if (args != nullptr) args->Push(cls); + if (argflags != nullptr) argflags->Push(VARF_Implicit); + if (argnames != nullptr) argnames->Push(NAME_self); } if (funcflags & VARF_Action) { // implied caller and callingstate pointers - if (args != NULL) + if (args != nullptr) { - args->Insert(0, NewClassPointer(RUNTIME_CLASS(AActor))); // the caller must go before self due to an old design mistake. - args->Push(TypeState); + // Special treatment for weapons and CustomInventorys: 'self' is not the defining class but the actual user of the item, so this pointer must be of type 'Actor' + /* if (cls->IsDescendantOf(RUNTIME_CLASS(AStateProvider))) + { + args->Insert(0, RUNTIME_CLASS(AActor)); // this must go in before the real pointer to the containing class. + } + else*/ + { + args->Push(cls); + } + args->Push(TypeState/*Info*/); // fixme: TypeState is not the correct type here!!! } - if (argflags != NULL) + if (argflags != nullptr) { argflags->Push(VARF_Implicit); argflags->Push(VARF_Implicit); } + if (argnames != nullptr) + { + argnames->Push(NAME_invoker); + argnames->Push(NAME_stateinfo); + } } } +//========================================================================== +// +// CreateAnonymousFunction +// +// Creates a function symbol for an anonymous function +// This contains actual info about the implied variables which is needed +// during code generation. +// +//========================================================================== + +PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags) +{ + TArray rets(1); + TArray args; + TArray argflags; + TArray argnames; + + rets[0] = returntype != nullptr? returntype : TypeError; // Use TypeError as placeholder if we do not know the return type yet. + SetImplicitArgs(&args, &argflags, &argnames, containingclass, flags); + + PFunction *sym = new PFunction(NAME_None); // anonymous functions do not have names. + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr); + sym->Flags = VARF_Action; + return sym; +} + //========================================================================== // // LoadActors diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 4a984dd5c..d5b189d47 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -150,7 +150,8 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArray *args, TArray *argflags, PClass *cls, DWORD funcflags); +void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); +PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); //========================================================================== // diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index 833a2d381..34f424ab4 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -657,7 +657,8 @@ DEFINE_PROPERTY(damage, X, Actor) } else { - defaults->DamageFunc = FunctionBuildList.AddFunction(bag.Info, id, FStringf("%s.DamageFunction", bag.Info->TypeName.GetChars()), false); + auto funcsym = CreateAnonymousFunction(bag.Info, TypeSInt32, VARF_Method); + defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, id, FStringf("%s.DamageFunction", bag.Info->TypeName.GetChars()), false); } } diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 4351723f8..76fd84072 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -649,7 +649,7 @@ void VMFunctionBuilder::BackpatchToHere(size_t loc) //========================================================================== FFunctionBuildList FunctionBuildList; -VMFunction *FFunctionBuildList::AddFunction(PClass *cls, FxExpression *code, const FString &name, bool statecall) +VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool statecall) { auto func = code->GetDirectFunction(); if (func != nullptr) @@ -661,7 +661,7 @@ VMFunction *FFunctionBuildList::AddFunction(PClass *cls, FxExpression *code, con //Printf("Adding %s\n", name.GetChars()); Item it; - it.Class = cls; + it.Func = functype; it.Code = code; it.DumpName = name; it.Function = new VMScriptFunction; @@ -684,8 +684,11 @@ void FFunctionBuildList::Build() { assert(item.Code != NULL); + // This needs to be fixed, so that the compile context receives the entire function symbol, including the containing class, the prototype and argument names, which will be needed to run the code generator + // As a first step this just needs to get working so fetch the class type from the prototype's argument list. + auto cls = static_cast(item.Func->Variants[0].Proto->ArgumentTypes[!!(item.Func->Flags & VARF_Action)]); // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(item.Class, nullptr); + FCompileContext ctx(cls, nullptr); item.Code = item.Code->Resolve(ctx); item.Proto = ctx.ReturnProto; @@ -695,32 +698,15 @@ void FFunctionBuildList::Build() VMFunctionBuilder buildit(true); assert(item.Proto != nullptr); - - int numargs; - int flags; - - // Kludge alert. This needs to be done in a more universal fashion. - // Right now there's only action and damage functions, so for the time being - // this will do to get the whole thing started first. - - if (item.type == 1) // anonymous action function - { - numargs = NAP; - flags = VARF_Method | VARF_Action; - } - else - { - numargs = 1; - flags = VARF_Method; - } + auto numargs = item.Func->Variants[0].Proto->ArgumentTypes.Size(); // Generate prototype for this anonymous function + // Fixme: This later needs to do proper allocation for the function's entire argument list, once non-anonymous functions can be done. buildit.Registers[REGT_POINTER].Get(numargs); - TArray args(numargs); - SetImplicitArgs(&args, nullptr, item.Class, flags); VMScriptFunction *sfunc = item.Function; - item.Function->Proto = NewPrototype(item.Proto->ReturnTypes, args); + // create a new prototype from the now known return type and the argument list of the function's template prototype. + item.Function->Proto = NewPrototype(item.Proto->ReturnTypes, item.Func->Variants[0].Proto->ArgumentTypes); // Emit code item.Code->Emit(&buildit); @@ -731,7 +717,7 @@ void FFunctionBuildList::Build() { char label[64]; int labellen = mysnprintf(label, countof(label), item.DumpName, - item.Class->TypeName.GetChars()); + cls->TypeName.GetChars()); DumpFunction(dump, sfunc, label, labellen); codesize += sfunc->CodeSize; } diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index 59e9fbe79..6b9a0aa68 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -101,7 +101,7 @@ class FFunctionBuildList { struct Item { - PClass *Class = nullptr; + PFunction *Func = nullptr; FxExpression *Code = nullptr; PPrototype *Proto = nullptr; VMScriptFunction *Function = nullptr; @@ -112,7 +112,7 @@ class FFunctionBuildList TArray mItems; public: - VMFunction *AddFunction(PClass *cls, FxExpression *code, const FString &name, bool statecall = false); + VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool statecall = false); void Build(); }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f2f7b4d4b..23bdce3b5 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1870,7 +1870,7 @@ void ZCCCompiler::InitFunctions() TArray rets(1); TArray args; TArray argflags; - TArray argnames; + TArray argnames; for (auto c : Classes) { @@ -1925,20 +1925,7 @@ void ZCCCompiler::InitFunctions() Error(f, "The function '%s' has not been exported from the executable.", FName(f->Name).GetChars()); } } - SetImplicitArgs(&args, &argflags, c->Type(), varflags); - // Give names to the implicit parameters. - // Note that 'self' is the second argument on action functions, because this is the one referring to the owning class. - if (varflags & VARF_Action) - { - argnames.Push(NAME_caller); - argnames.Push(NAME_self); - argnames.Push(NAME_stateinfo); - } - else if (varflags & VARF_Method) - { - argnames.Push(NAME_self); - } - + SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags); auto p = f->Params; if (p != nullptr) { @@ -1974,7 +1961,7 @@ void ZCCCompiler::InitFunctions() } PFunction *sym = new PFunction(f->Name); - sym->AddVariant(NewPrototype(rets, args), argflags, afd == nullptr? nullptr : *(afd->VMPointer)); + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, afd == nullptr? nullptr : *(afd->VMPointer)); sym->Flags = varflags; c->Type()->Symbols.ReplaceSymbol(sym); @@ -2025,7 +2012,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a { if (fc->Parameters == nullptr && (afd->Flags & VARF_Action)) { - // This is the simple case which doesn't require work on the tree. + // We can use this function directly without wrapping it in a caller. return new FxVMFunctionCall(afd, nullptr, *af, true); } } @@ -2040,6 +2027,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a // Action specials fall through to the code generator. } } + ConvertClass = cls; return ConvertAST(af); //Error(af, "Complex action functions not supported yet."); @@ -2173,7 +2161,8 @@ void ZCCCompiler::CompileStates() auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); if (code != nullptr) { - state.ActionFunc = FunctionBuildList.AddFunction(c->Type(), code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), true); + auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action); + state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), true); } } @@ -2289,10 +2278,10 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case AST_ExprFuncCall: { auto fcall = static_cast(ast); - //return ConvertFunctionCall(fcall); assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. auto fname = static_cast(fcall->Function)->Identifier; return new FxFunctionCall(nullptr, fname, ConvertNodeList(fcall->Parameters), *ast); + //return ConvertFunctionCall(fcall->Function, ConvertNodeList(fcall->Parameters), ConvertClass, *ast); } case AST_FuncParm: diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 12e570330..4ecd63227 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -143,6 +143,7 @@ private: FArgumentList *ConvertNodeList(ZCC_TreeNode *head); DObject *Outer; + PClass *ConvertClass; // class type to be used when resoving symbold while converting an AST PSymbolTable *GlobalTreeNodes; PSymbolTable *OutputSymbols; ZCC_AST &AST; From 091da92819fed1559fba584ba4840fdbf60169b1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 15:10:48 +0200 Subject: [PATCH 040/255] - Added AStateProvider class which is used to define the special action function behavior of weapons and custom inventorys. The class itself does not do anything, but the compiler will use it to set up the action function prototypes differently which in turn will be used to do type checking during code generation. --- src/CMakeLists.txt | 1 + src/g_shared/a_pickups.cpp | 1 + src/g_shared/a_pickups.h | 15 ++-- src/scripting/thingdef.cpp | 4 +- wadsrc/static/zscript/shared/inventory.txt | 95 +++++++++++----------- 5 files changed, 63 insertions(+), 53 deletions(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 545400b1c..ae2f19960 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1461,6 +1461,7 @@ source_group("Scripting\\Decorate" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_D source_group("Scripting\\ZScript" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/zscript/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.c ${CMAKE_CURRENT_BINARY_DIR}/zcc-parse.h) source_group("Scripting\\Code Generation" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/codegeneration/.+") source_group("Scripting\\VM" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/vm/.+") +source_group("Scripting" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/scripting/.+") source_group("Shared Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_shared/.+") source_group("Versioning" FILES version.h win32/zdoom.rc) source_group("Xlat" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/xlat/.+" FILES ${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.c ${CMAKE_CURRENT_BINARY_DIR}/xlat_parser.h) diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index c4daae024..38f0a5130 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -1642,6 +1642,7 @@ void AInventory::DetachFromOwner () { } +IMPLEMENT_CLASS(AStateProvider) IMPLEMENT_CLASS (ACustomInventory) //=========================================================================== diff --git a/src/g_shared/a_pickups.h b/src/g_shared/a_pickups.h index 45676a214..6dc2d0bc5 100644 --- a/src/g_shared/a_pickups.h +++ b/src/g_shared/a_pickups.h @@ -226,10 +226,15 @@ private: static const char *StaticLastMessage; }; -// CustomInventory: Supports the Use, Pickup, and Drop states from 96x -class ACustomInventory : public AInventory +class AStateProvider : public AInventory { - DECLARE_CLASS (ACustomInventory, AInventory) + DECLARE_CLASS(AStateProvider, AInventory) +}; + +// CustomInventory: Supports the Use, Pickup, and Drop states from 96x +class ACustomInventory : public AStateProvider +{ + DECLARE_CLASS (ACustomInventory, AStateProvider) public: // This is used when an inventory item's use state sequence is executed. @@ -281,9 +286,9 @@ public: int SlotPriority; }; -class AWeapon : public AInventory +class AWeapon : public AStateProvider { - DECLARE_CLASS_WITH_META(AWeapon, AInventory, PClassWeapon) + DECLARE_CLASS_WITH_META(AWeapon, AStateProvider, PClassWeapon) HAS_OBJECT_POINTERS public: DWORD WeaponFlags; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 182bfbd12..21f690f6c 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -99,11 +99,11 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArrayIsDescendantOf(RUNTIME_CLASS(AStateProvider))) + if (cls->IsDescendantOf(RUNTIME_CLASS(AStateProvider))) { args->Insert(0, RUNTIME_CLASS(AActor)); // this must go in before the real pointer to the containing class. } - else*/ + else { args->Push(cls); } diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index fe60fdc1a..bf2f7e188 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -10,50 +10,49 @@ class Inventory : Actor native Inventory.PickupMessage "$TXT_DEFAULTPICKUPMSG"; } - // functions that can be used from weapons and CustomInventory. These require that 'self' is of type class and be treated as such in the scripts. - /*inventory*/ action native state A_JumpIfNoAmmo(state label); - /*inventory*/ action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = "", sound MissSound = ""); - /*inventory*/ action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); - /*inventory*/ action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); - /*inventory*/ action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = "", color color2 = "", int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); - /*inventory*/ action native void A_Light(int extralight); - /*inventory*/ action native void A_Light0(); - /*inventory*/ action native void A_Light1(); - /*inventory*/ action native void A_Light2(); - /*inventory*/ action native void A_LightInverse(); - /*inventory*/ action native void A_WeaponReady(int flags = 0); - /*inventory*/ action native void A_Lower(); - /*inventory*/ action native void A_Raise(); - /*inventory*/ action native void A_FirePistol(); - /*inventory*/ action native void A_FireShotgun(); - /*inventory*/ action native void A_FireShotgun2(); - /*inventory*/ action native void A_OpenShotgun2(); - /*inventory*/ action native void A_LoadShotgun2(); - /*inventory*/ action native void A_CloseShotgun2(); - /*inventory*/ action native void A_FireCGun(); - /*inventory*/ action native void A_FireSTGrenade(class grenadetype = "Grenade"); - /*inventory*/ action native void A_FireMissile(); - /*inventory*/ action native void A_FirePlasma(); - /*inventory*/ action native void A_FireRailgun(); - /*inventory*/ action native void A_FireRailgunLeft(); - /*inventory*/ action native void A_FireRailgunRight(); - /*inventory*/ action native void A_RailWait(); - /*inventory*/ action native void A_BFGsound(); - /*inventory*/ action native void A_FireBFG(); - /*inventory*/ action native void A_FireOldBFG(); - /*inventory*/ action native void A_ReFire(state flash = ""); - /*inventory*/ action native void A_ClearReFire(); - /*inventory*/ action native void A_CheckReload(); - /*inventory*/ action native void A_GunFlash(state flash = "", int flags = 0); - /*inventory*/ action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); - /*inventory*/ action native state A_CheckForReload(int counter, state label, bool dontincrement = false); - /*inventory*/ action native void A_ResetReloadCounter(); + action native state A_JumpIfNoAmmo(state label); + action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = "", sound MissSound = ""); + action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); + action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); + action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = "", color color2 = "", int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); + action native void A_Light(int extralight); + action native void A_Light0(); + action native void A_Light1(); + action native void A_Light2(); + action native void A_LightInverse(); + action native void A_WeaponReady(int flags = 0); + action native void A_Lower(); + action native void A_Raise(); + action native void A_FirePistol(); + action native void A_FireShotgun(); + action native void A_FireShotgun2(); + action native void A_OpenShotgun2(); + action native void A_LoadShotgun2(); + action native void A_CloseShotgun2(); + action native void A_FireCGun(); + action native void A_FireSTGrenade(class grenadetype = "Grenade"); + action native void A_FireMissile(); + action native void A_FirePlasma(); + action native void A_FireRailgun(); + action native void A_FireRailgunLeft(); + action native void A_FireRailgunRight(); + action native void A_RailWait(); + action native void A_BFGsound(); + action native void A_FireBFG(); + action native void A_FireOldBFG(); + action native void A_ReFire(state flash = ""); + action native void A_ClearReFire(); + action native void A_CheckReload(); + action native void A_GunFlash(state flash = "", int flags = 0); + action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); + action native state A_CheckForReload(int counter, state label, bool dontincrement = false); + action native void A_ResetReloadCounter(); // These are regular functions for the item itself. - action native void A_RestoreSpecialPosition(); - action native void A_RestoreSpecialDoomThing(); - action native void A_RestoreSpecialThing1(); - action native void A_RestoreSpecialThing2(); + private action native void A_RestoreSpecialPosition(); + private action native void A_RestoreSpecialDoomThing(); + private action native void A_RestoreSpecialThing1(); + private action native void A_RestoreSpecialThing2(); States { @@ -78,6 +77,10 @@ class Inventory : Actor native } } +class StateProvider : Inventory native +{ +} + class ScoreItem : Inventory native { Default @@ -151,7 +154,7 @@ class DehackedPickup : Inventory native {} class FakeInventory : Inventory native {} -class CustomInventory : Inventory native {} +class CustomInventory : StateProvider native {} class Health : Inventory native { @@ -448,7 +451,7 @@ class PuzzleItem : Inventory native } } -class Weapon : Inventory native +class Weapon : StateProvider native { Default { @@ -466,11 +469,11 @@ class Weapon : Inventory native Stop; } - /*inventory*/ action native void A_ZoomFactor(float scale = 1, int flags = 0); + action native void A_ZoomFactor(float scale = 1, int flags = 0); const ZOOM_INSTANT = 1; const ZOOM_NOSCALETURNING = 2; - /*inventory*/ action native void A_SetCrosshair(int xhair); + action native void A_SetCrosshair(int xhair); } class WeaponGiver : Weapon native From db8ab1bc4ac269606bdb50743c4a8f2b896cf8c5 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 15:50:45 +0200 Subject: [PATCH 041/255] - give PFunction a bit more information: * explicitly require passing the owning class when creating it. * extract self pointer class when adding a variant. * put the flags on the single variants, we can not fully rule out that they will be 100% identical, if variants ever get allowed. --- src/d_dehacked.cpp | 4 +- src/dobjtype.cpp | 19 ++- src/dobjtype.h | 9 +- src/scripting/codegeneration/codegen.cpp | 21 ++- .../codegeneration/functioncalls.cpp | 153 ++++++++++++++++++ src/scripting/decorate/thingdef_parse.cpp | 5 +- src/scripting/decorate/thingdef_states.cpp | 4 +- src/scripting/thingdef.cpp | 5 +- src/scripting/vm/vmbuilder.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 7 +- 10 files changed, 196 insertions(+), 33 deletions(-) create mode 100644 src/scripting/codegeneration/functioncalls.cpp diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 8e69ecb06..81ee907f4 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -2119,7 +2119,7 @@ static int PatchCodePtrs (int dummy) else { TArray &args = sym->Variants[0].ArgFlags; - if ((sym->Flags & (VARF_Method | VARF_Action)) != (VARF_Method | VARF_Action) || (args.Size() > NAP && !(args[NAP] & VARF_Optional))) + if ((sym->Variants[0].Flags & (VARF_Method | VARF_Action)) != (VARF_Method | VARF_Action) || (args.Size() > NAP && !(args[NAP] & VARF_Optional))) { Printf("Frame %d: Incompatible code pointer '%s'\n", frame, Line2); sym = NULL; @@ -2731,7 +2731,7 @@ static bool LoadDehSupp () else { TArray &args = sym->Variants[0].ArgFlags; - if ((sym->Flags & (VARF_Method|VARF_Action)) != (VARF_Method | VARF_Action) || (args.Size() > NAP && !(args[NAP] & VARF_Optional))) + if ((sym->Variants[0].Flags & (VARF_Method|VARF_Action)) != (VARF_Method | VARF_Action) || (args.Size() > NAP && !(args[NAP] & VARF_Optional))) { sc.ScriptMessage("Incompatible code pointer '%s'", sc.String); } diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 4dcb904d5..c43abf9a7 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2475,7 +2475,7 @@ size_t PFunction::PropagateMark() { for (unsigned i = 0; i < Variants.Size(); ++i) { - //GC::Mark(Variants[i].Proto); + GC::Mark(Variants[i].Proto); GC::Mark(Variants[i].Implementation); } return Variants.Size() * sizeof(Variants[0]) + Super::PropagateMark(); @@ -2490,14 +2490,29 @@ size_t PFunction::PropagateMark() // //========================================================================== -unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl) +unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl, int flags) { Variant variant; + // I do not think we really want to deal with overloading here... + assert(Variants.Size() == 0); + + variant.Flags = flags; variant.Proto = proto; variant.ArgFlags = argflags; variant.Implementation = impl; if (impl != nullptr) impl->Proto = proto; + + // SelfClass can differ from OwningClass, but this is variant-dependent. + // Unlike the owner there can be cases where different variants can have different SelfClasses. + // (Of course only if this ever gets enabled...) + if (flags & VARF_Method) + { + assert(proto->ArgumentTypes.Size() > 0); + variant.SelfClass = dyn_cast(proto->ArgumentTypes[0]); + assert(variant.SelfClass != nullptr); + } + return Variants.Push(variant); } diff --git a/src/dobjtype.h b/src/dobjtype.h index 9a51fa88a..07d7ae10f 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -696,16 +696,17 @@ public: VMFunction *Implementation; TArray ArgFlags; // Should be the same length as Proto->ArgumentTypes TArray ArgNames; // we need the names to access them later when the function gets compiled. + DWORD Flags; + PClass *SelfClass; }; TArray Variants; - DWORD Flags; + PClass *OwningClass = nullptr; - unsigned AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl); + unsigned AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl, int flags); size_t PropagateMark(); - PFunction(FName name) : PSymbol(name), Flags(0) {} - PFunction() : PSymbol(NAME_None), Flags(0) {} + PFunction(PClass *owner = nullptr, FName name = NAME_None) : PSymbol(name), OwningClass(owner) {} }; // Meta-info for every class derived from DObject --------------------------- diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 0034de8a4..801df8c65 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3898,7 +3898,7 @@ VMFunction *FxVMFunctionCall::GetDirectFunction() // then it can be a "direct" function. That is, the DECORATE // definition can call that function directly without wrapping // it inside VM code. - if ((ArgList ? ArgList->Size() : 0) == 0 && (Function->Flags & VARF_Action)) + if ((ArgList ? ArgList->Size() : 0) == 0 && (Function->Variants[0].Flags & VARF_Action)) { return Function->Variants[0].Implementation; } @@ -3920,8 +3920,8 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) auto argtypes = proto->ArgumentTypes; int implicit; - if (Function->Flags & VARF_Action) implicit = 3; - else if (Function->Flags & VARF_Method) implicit = 1; + if (Function->Variants[0].Flags & VARF_Action) implicit = 3; + else if (Function->Variants[0].Flags & VARF_Method) implicit = 1; else implicit = 0; if (ArgList != NULL) @@ -4014,15 +4014,15 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) // For ZSCRIPT 'self' is properly used for the state's owning actor, meaning we have to pass the second argument here. // If both functions are non-action or both are action, there is no need for special treatment. - if (!OwnerIsSelf || (!!(Function->Flags & VARF_Action) == build->IsActionFunc)) + if (!OwnerIsSelf || (!!(Function->Variants[0].Flags & VARF_Action) == build->IsActionFunc)) { // Emit code to pass implied parameters - if (Function->Flags & VARF_Method) + if (Function->Variants[0].Flags & VARF_Method) { build->Emit(OP_PARAM, 0, REGT_POINTER, 0); count += 1; } - if (Function->Flags & VARF_Action) + if (Function->Variants[0].Flags & VARF_Action) { static_assert(NAP == 3, "This code needs to be updated if NAP changes"); if (build->IsActionFunc) @@ -4041,17 +4041,14 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } else { - // There are two possibilities here: - // Calling a non-action function from an action function. - // In that case the 'stateowner' pointer needs to be used as self. - if (build->IsActionFunc && (Function->Flags & VARF_Method)) + if (build->IsActionFunc && (Function->Variants[0].Flags & VARF_Method)) { - build->Emit(OP_PARAM, 0, REGT_POINTER, 1); + build->Emit(OP_PARAM, 0, REGT_POINTER, 0); count += 1; } // and calling an action function from a non-action function. // This must be blocked because it lacks crucial information. - if (!build->IsActionFunc && (Function->Flags & VARF_Action)) + if (!build->IsActionFunc && (Function->Variants[0].Flags & VARF_Action)) { // This case should be eliminated in the analyzing stage. I_Error("Cannot call action function from non-action functions."); diff --git a/src/scripting/codegeneration/functioncalls.cpp b/src/scripting/codegeneration/functioncalls.cpp new file mode 100644 index 000000000..d085635cd --- /dev/null +++ b/src/scripting/codegeneration/functioncalls.cpp @@ -0,0 +1,153 @@ +#if 0 +/* +** cg_functioncall.cpp +** +**--------------------------------------------------------------------------- +** Copyright 2016 Christoph Oelckers +** All rights reserved. +** +** Redistribution and use in source and binary forms, with or without +** modification, are permitted provided that the following conditions +** are met: +** +** 1. Redistributions of source code must retain the above copyright +** notice, this list of conditions and the following disclaimer. +** 2. Redistributions in binary form must reproduce the above copyright +** notice, this list of conditions and the following disclaimer in the +** documentation and/or other materials provided with the distribution. +** 3. The name of the author may not be used to endorse or promote products +** derived from this software without specific prior written permission. +** +** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR +** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES +** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. +** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, +** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT +** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, +** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY +** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT +** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF +** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +**--------------------------------------------------------------------------- +** +*/ + +#include "doomtype.h" +#include "codegen.h" +#include "thingdef.h" +#include "zscript/zcc_parser.h" + +// just some rough concepts for now... + +//========================================================================== +// +// FindClassMemberFunction +// +// Looks for a name in a class's +// +//========================================================================== + +PFunction *FindClassMemberFunction(PClass *cls, FName name, FScriptPosition &sc) +{ + PSymbolTable *symtable; + auto symbol = cls->Symbols.FindSymbolInTable(name, symtable); + auto funcsym = dyn_cast(symbol); + + if (symbol != nullptr) + { + if (funcsym == nullptr) + { + sc.Message(MSG_ERROR, "%s is not a member function of %s", name.GetChars(), cls->TypeName.GetChars()); + } + else if (funcsym->Flags & VARF_Private && symtable != &cls->Symbols) + { + sc.Message(MSG_ERROR, "%s is declared private and not accessible", symbol->SymbolName.GetChars()); + } + else if (funcsym->Flags & VARF_Deprecated) + { + sc.Message(MSG_WARNING, "Call to deprecated function %s", symbol->SymbolName.GetChars()); + } + } + return funcsym; +} + + +//========================================================================== +// +// let's save some work down the line by analyzing the type of function +// that's being called right here and create appropriate nodes. +// A simple function call expression must be immediately resolvable in +// the context it gets compiled in, if the function name cannot be +// resolved here, it will never. +// +//========================================================================== + +FxExpression *ConvertSimpleFunctionCall(ZCC_ExprID *function, FArgumentList *args, PClass *cls, FScriptPosition &sc) +{ + // Priority is as follows: + //1. member functions of the containing class. + //2. action specials. + //3. floating point operations + //4. global builtins + + if (cls != nullptr) + { + // There is an action function ACS_NamedExecuteWithResult which must be ignored here for this to work. + if (function->Identifier != NAME_ACS_NamedExecuteWithResult) + { + { + args = ConvertNodeList(fcall->Parameters); + if (args->Size() == 0) + { + delete args; + args = nullptr; + } + + return new FxMemberunctionCall(new FxSelf(), new FxInvoker(), func, args, sc, false); + } + } + +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *ConvertFunctionCall(ZCC_Expression *function, FArgumentList *args, PClass *cls, FScriptPosition &sc) +{ + // function names can either be + // - plain identifiers + // - class members + // - array syntax for random() calls. + + switch(function->NodeType) + { + case AST_ExprID: + return ConvertSimpleFunctionCall(static_cast(function), args, cls, sc); + + case AST_ExprMemberAccess: + return ConvertMemberCall(fcall); + + case AST_ExprBinary: + // Array access syntax is wrapped into a ZCC_ExprBinary object. + if (fcall->Function->Operation == PEX_ArrayAccess) + { + return ConvertArrayFunctionCall(fcall); + } + break; + + default: + break; + } + Error(fcall, "Invalid function identifier"); + return new FxNop(*fcall); // return something so that we can continue +} + + + assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. + auto fname = static_cast(fcall->Function)->Identifier; + return new FxFunctionCall(nullptr, fname, ConvertNodeList(fcall->Parameters), *ast); + +#endif \ No newline at end of file diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index f547956dd..b2f1cac07 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -474,9 +474,8 @@ void ParseFunctionDef(FScanner &sc, PClassActor *cls, FName funcname, if (afd != NULL) { - PFunction *sym = new PFunction(funcname); - sym->AddVariant(NewPrototype(rets, args), argflags, argnames, *(afd->VMPointer)); - sym->Flags = funcflags; + PFunction *sym = new PFunction(cls, funcname); + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, *(afd->VMPointer), funcflags); if (cls->Symbols.AddSymbol(sym) == NULL) { delete sym; diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index ada9462e0..d5a3395d7 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -602,12 +602,12 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArrayFlags & VARF_Method) + if (afd->Variants[0].Flags & VARF_Method) { numparams--; pnum++; } - if (afd->Flags & VARF_Action) + if (afd->Variants[0].Flags & VARF_Action) { numparams -= 2; pnum += 2; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 21f690f6c..f80a8f87a 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -142,9 +142,8 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i rets[0] = returntype != nullptr? returntype : TypeError; // Use TypeError as placeholder if we do not know the return type yet. SetImplicitArgs(&args, &argflags, &argnames, containingclass, flags); - PFunction *sym = new PFunction(NAME_None); // anonymous functions do not have names. - sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr); - sym->Flags = VARF_Action; + PFunction *sym = new PFunction(containingclass, NAME_None); // anonymous functions do not have names. + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, VARF_Action|VARF_Method); return sym; } diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 76fd84072..f366ec650 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -686,7 +686,7 @@ void FFunctionBuildList::Build() // This needs to be fixed, so that the compile context receives the entire function symbol, including the containing class, the prototype and argument names, which will be needed to run the code generator // As a first step this just needs to get working so fetch the class type from the prototype's argument list. - auto cls = static_cast(item.Func->Variants[0].Proto->ArgumentTypes[!!(item.Func->Flags & VARF_Action)]); + auto cls = static_cast(item.Func->Variants[0].Proto->ArgumentTypes[!!(item.Func->Variants[0].Flags & VARF_Action)]); // We don't know the return type in advance for anonymous functions. FCompileContext ctx(cls, nullptr); item.Code = item.Code->Resolve(ctx); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 23bdce3b5..ee40868d3 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1960,9 +1960,8 @@ void ZCCCompiler::InitFunctions() } while (p != f->Params); } - PFunction *sym = new PFunction(f->Name); - sym->AddVariant(NewPrototype(rets, args), argflags, argnames, afd == nullptr? nullptr : *(afd->VMPointer)); - sym->Flags = varflags; + PFunction *sym = new PFunction(c->Type(), f->Name); + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, afd == nullptr? nullptr : *(afd->VMPointer), varflags); c->Type()->Symbols.ReplaceSymbol(sym); // todo: Check inheritance. @@ -2010,7 +2009,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a PFunction *afd = dyn_cast(cls->Symbols.FindSymbol(id->Identifier, true)); if (afd != nullptr) { - if (fc->Parameters == nullptr && (afd->Flags & VARF_Action)) + if (fc->Parameters == nullptr && (afd->Variants[0].Flags & VARF_Action)) { // We can use this function directly without wrapping it in a caller. return new FxVMFunctionCall(afd, nullptr, *af, true); From cbb990a79e625357dee848bbc98d653f6fc9e09b Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 17:40:27 +0200 Subject: [PATCH 042/255] - pass the current function to the compile context instead of just the containing class. --- src/dobjtype.cpp | 4 +- src/dobjtype.h | 1 + src/scripting/codegeneration/codegen.cpp | 116 ++++++++++++++++------- src/scripting/codegeneration/codegen.h | 9 +- src/scripting/thingdef.cpp | 6 +- src/scripting/vm/vmbuilder.cpp | 8 +- src/scripting/zscript/zcc_compile.cpp | 5 + 7 files changed, 101 insertions(+), 48 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index c43abf9a7..966663f12 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2509,7 +2509,9 @@ unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArra if (flags & VARF_Method) { assert(proto->ArgumentTypes.Size() > 0); - variant.SelfClass = dyn_cast(proto->ArgumentTypes[0]); + auto selftypeptr = dyn_cast(proto->ArgumentTypes[0]); + assert(selftypeptr != nullptr); + variant.SelfClass = dyn_cast(selftypeptr->PointedType); assert(variant.SelfClass != nullptr); } diff --git a/src/dobjtype.h b/src/dobjtype.h index 07d7ae10f..a5da177a4 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -29,6 +29,7 @@ enum VARF_In = (1<<10), VARF_Out = (1<<11), VARF_Implicit = (1<<12), // implicitly created parameters (i.e. do not compare when checking function signatures) + VARF_Static = (1<<13), // static class data (by necessity read only.) }; // Symbol information ------------------------------------------------------- diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 801df8c65..4ed712834 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -49,7 +49,7 @@ #include "thingdef.h" #include "p_lnspec.h" #include "doomstat.h" -#include "thingdef_exp.h" +#include "codegen.h" #include "m_fixed.h" #include "vmbuilder.h" #include "v_text.h" @@ -91,13 +91,25 @@ static const FLOP FxFlops[] = // //========================================================================== -FCompileContext::FCompileContext(PClass *cls, PPrototype *ret) : Class(cls), ReturnProto(ret) +FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret) : ReturnProto(ret), Function(fnc), Class(nullptr) +{ + if (fnc != nullptr) Class = fnc->OwningClass; +} + +FCompileContext::FCompileContext(PClass *cls) : ReturnProto(nullptr), Function(nullptr), Class(cls) { } -PSymbol *FCompileContext::FindInClass(FName identifier) +PSymbol *FCompileContext::FindInClass(FName identifier, PSymbolTable *&symt) { - return Class ? Class->Symbols.FindSymbol(identifier, true) : nullptr; + return Class != nullptr? Class->Symbols.FindSymbolInTable(identifier, symt) : nullptr; +} + +PSymbol *FCompileContext::FindInSelfClass(FName identifier, PSymbolTable *&symt) +{ + // If we have no self we cannot retrieve any values from it. + if (Function == nullptr || Function->Variants[0].SelfClass == nullptr) return nullptr; + return Function->Variants[0].SelfClass->Symbols.FindSymbolInTable(identifier, symt); } PSymbol *FCompileContext::FindGlobal(FName identifier) { @@ -3178,15 +3190,16 @@ FxIdentifier::FxIdentifier(FName name, const FScriptPosition &pos) FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) { PSymbol * sym; - FxExpression *newex = NULL; - //FBaseCVar * cv = NULL; - //FString s; + FxExpression *newex = nullptr; int num; - //const PClass *Class; CHECKRESOLVED(); + + // Ugh, the horror. Constants need to be taken from the owning class, but members from the self class to catch invalid accesses here... + // see if the current class (if valid) defines something with this name. - if ((sym = ctx.FindInClass(Identifier)) != NULL) + PSymbolTable *symtbl; + if ((sym = ctx.FindInClass(Identifier, symtbl)) != nullptr) { if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) { @@ -3195,15 +3208,64 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } else if (sym->IsKindOf(RUNTIME_CLASS(PField))) { + ABORT(ctx.Function); // only valid when resolving a function. PField *vsym = static_cast(sym); - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as member variable, index %d\n", Identifier.GetChars(), vsym->Offset); - newex = new FxClassMember((new FxSelf(ScriptPosition))->Resolve(ctx), vsym, ScriptPosition); + + // We have 4 cases to consider here: + // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. + // 2. This is a static function + // 3. This is an action function with a restricted self pointer + // 4. This is a normal member or unrestricted action function. + if (vsym->Flags & VARF_Deprecated) + { + ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + } + if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) + { + ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); + delete this; + return nullptr; + } + + if (vsym->Flags & VARF_Static) + { + // todo. For now these cannot be defined so let's just exit. + delete this; + return nullptr; + } + + if (ctx.Function->Variants[0].SelfClass == nullptr) + { + ScriptPosition.Message(MSG_ERROR, "Unable to access class member from static function"); + delete this; + return nullptr; + } + else + { + if (ctx.Function->Variants[0].SelfClass != ctx.Class) + { + // Check if the restricted class can access it. + PSymbol *sym2; + if ((sym2 = ctx.FindInSelfClass(Identifier, symtbl)) != nullptr) + { + if (sym != sym2) + { + ScriptPosition.Message(MSG_ERROR, "Member variable of %s not accessible through restricted self pointer", ctx.Class->TypeName.GetChars()); + delete this; + return nullptr; + } + } + } + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as member variable, index %d\n", Identifier.GetChars(), vsym->Offset); + newex = new FxClassMember((new FxSelf(ScriptPosition))->Resolve(ctx), vsym, ScriptPosition); + } } else { ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); } } + // now check the global identifiers. else if ((sym = ctx.FindGlobal(Identifier)) != NULL) { @@ -3217,23 +3279,7 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) ScriptPosition.Message(MSG_ERROR, "Invalid global identifier '%s'\n", Identifier.GetChars()); } } - /* - else if ((Class = PClass::FindClass(Identifier))) - { - pos.Message(MSG_DEBUGLOG, "Resolving name '%s' as class name\n", Identifier.GetChars()); - newex = new FxClassType(Class, ScriptPosition); - } - } - */ - // also check for CVars - /* - else if ((cv = FindCVar(Identifier, NULL)) != NULL) - { - CLOG(CL_RESOLVE, LPrintf("Resolving name '%s' as cvar\n", Identifier.GetChars())); - newex = new FxCVar(cv, ScriptPosition); - } - */ // and line specials else if ((num = P_FindLineSpecial(Identifier, NULL, NULL))) { @@ -3270,15 +3316,13 @@ FxSelf::FxSelf(const FScriptPosition &pos) FxExpression *FxSelf::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ctx.Class) + if (ctx.Function == nullptr || ctx.Function->Variants[0].SelfClass == nullptr) { - // can't really happen with DECORATE's expression evaluator. ScriptPosition.Message(MSG_ERROR, "self used outside of a member function"); delete this; - return NULL; + return nullptr; } - ValueType = ctx.Class; - ValueType = NewPointer(RUNTIME_CLASS(DObject)); + ValueType = NewPointer(ctx.Function->Variants[0].SelfClass); return this; } @@ -3614,8 +3658,10 @@ FxFunctionCall::~FxFunctionCall() FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { - // This part is mostly a kludge, it really needs to get the class type from Self. + ABORT(ctx.Class); + PFunction *afd = dyn_cast(ctx.Class->Symbols.FindSymbol(MethodName, true)); + // Todo: More checks are needed here to make it work as expected. if (afd != nullptr) { auto x = new FxVMFunctionCall(afd, ArgList, ScriptPosition, false); @@ -5172,9 +5218,9 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) delete this; return NULL; } - else if (!scope->IsDescendantOf(ctx.Class)) + else if (!scope->IsAncestorOf(ctx.Class)) { - ScriptPosition.Message(MSG_ERROR, "'%s' is not an ancestor of '%s'", names[0].GetChars(),ctx.Class->TypeName.GetChars()); + ScriptPosition.Message(MSG_ERROR, "'%s' is not an ancestor of '%s'", names[0].GetChars(), ctx.Class->TypeName.GetChars()); delete this; return NULL; } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 3c52547c5..d69323ce0 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -67,11 +67,14 @@ struct FCompileContext { TArray Jumps; PPrototype *ReturnProto; - PClass *Class; + PFunction *Function; // The function that is currently being compiled (or nullptr for constant evaluation.) + PClass *Class; // The type of the owning class. - FCompileContext(PClass *cls = nullptr, PPrototype *ret = nullptr); + FCompileContext(PFunction *func = nullptr, PPrototype *ret = nullptr); + FCompileContext(PClass *cls); // only to be used to resolve constants! - PSymbol *FindInClass(FName identifier); + PSymbol *FindInClass(FName identifier, PSymbolTable *&symt); + PSymbol *FindInSelfClass(FName identifier, PSymbolTable *&symt); PSymbol *FindGlobal(FName identifier); void HandleJumps(int token, FxExpression *handler); diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index f80a8f87a..413999ddc 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -89,7 +89,7 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArrayPush(cls); + if (args != nullptr) args->Push(NewPointer(cls)); if (argflags != nullptr) argflags->Push(VARF_Implicit); if (argnames != nullptr) argnames->Push(NAME_self); } @@ -101,11 +101,11 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArrayIsDescendantOf(RUNTIME_CLASS(AStateProvider))) { - args->Insert(0, RUNTIME_CLASS(AActor)); // this must go in before the real pointer to the containing class. + args->Insert(0, NewPointer(RUNTIME_CLASS(AActor))); // this must go in before the real pointer to the containing class. } else { - args->Push(cls); + args->Push(NewPointer(cls)); } args->Push(TypeState/*Info*/); // fixme: TypeState is not the correct type here!!! } diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index f366ec650..7c5118467 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -686,9 +686,8 @@ void FFunctionBuildList::Build() // This needs to be fixed, so that the compile context receives the entire function symbol, including the containing class, the prototype and argument names, which will be needed to run the code generator // As a first step this just needs to get working so fetch the class type from the prototype's argument list. - auto cls = static_cast(item.Func->Variants[0].Proto->ArgumentTypes[!!(item.Func->Variants[0].Flags & VARF_Action)]); // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(cls, nullptr); + FCompileContext ctx(item.Func, nullptr); item.Code = item.Code->Resolve(ctx); item.Proto = ctx.ReturnProto; @@ -715,10 +714,7 @@ void FFunctionBuildList::Build() if (dump != nullptr) { - char label[64]; - int labellen = mysnprintf(label, countof(label), item.DumpName, - cls->TypeName.GetChars()); - DumpFunction(dump, sfunc, label, labellen); + DumpFunction(dump, sfunc, item.DumpName.GetChars(), (int)item.DumpName.Len()); codesize += sfunc->CodeSize; } } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index ee40868d3..aee7e8b76 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1888,6 +1888,11 @@ void ZCCCompiler::InitFunctions() do { auto type = DetermineType(c->Type(), f, f->Name, t, false); + if (type->IsKindOf(RUNTIME_CLASS(PStruct))) + { + // structs and classes only get passed by pointer. + type = NewPointer(type); + } // TBD: disallow certain types? For now, let everything pass that isn't an array. rets.Push(type); t = static_cast(t->SiblingNext); From c3e693b507619c66728cae43a9f2f66b8098ff18 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 20:16:44 +0200 Subject: [PATCH 043/255] - added FindClassMemberFunction which retrieves a function symbol and performs some verification. - removed Self parameter from FxFunctionCall. Actual member function calls through an object require quite different handling so lumping these two together makes no sense. - added a workaround to deal with ACS_NamedExecuteWithResult to both the compiler and FindClassMemberFunction. The way the ZScript compiler sets this up means that it will call the builtin, not the actual action function, so the parser needs to do some explicit check to get past the same-named action function. - pass a proper self pointer to FxActionSpecial. Although it's still not being used, propagating design shortcuts through several function levels is a very, very bad idea. --- src/scripting/codegeneration/codegen.cpp | 35 ++++----- src/scripting/codegeneration/codegen.h | 3 +- .../codegeneration/functioncalls.cpp | 71 +------------------ src/scripting/decorate/thingdef_exp.cpp | 2 +- src/scripting/thingdef.cpp | 37 ++++++++++ src/scripting/thingdef.h | 1 + src/scripting/zscript/zcc_compile.cpp | 48 +++++++------ 7 files changed, 83 insertions(+), 114 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4ed712834..9cdd9c1f2 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3630,10 +3630,9 @@ ExpEmit FxArrayElement::Emit(VMFunctionBuilder *build) // //========================================================================== -FxFunctionCall::FxFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos) +FxFunctionCall::FxFunctionCall(FName methodname, FArgumentList *args, const FScriptPosition &pos) : FxExpression(pos) { - Self = self; MethodName = methodname; ArgList = args; } @@ -3646,7 +3645,6 @@ FxFunctionCall::FxFunctionCall(FxExpression *self, FName methodname, FArgumentLi FxFunctionCall::~FxFunctionCall() { - SAFE_DELETE(Self); SAFE_DELETE(ArgList); } @@ -3659,9 +3657,9 @@ FxFunctionCall::~FxFunctionCall() FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { ABORT(ctx.Class); - - PFunction *afd = dyn_cast(ctx.Class->Symbols.FindSymbol(MethodName, true)); - // Todo: More checks are needed here to make it work as expected. + + PFunction *afd = FindClassMemberFunction(ctx.Class, ctx.Class, MethodName, ScriptPosition); + if (afd != nullptr) { auto x = new FxVMFunctionCall(afd, ArgList, ScriptPosition, false); @@ -3674,14 +3672,8 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { if (MethodName == FxFlops[i].Name) { - if (Self != NULL) - { - ScriptPosition.Message(MSG_ERROR, "Global functions cannot have a self pointer"); - delete this; - return NULL; - } FxExpression *x = new FxFlopFunctionCall(i, ArgList, ScriptPosition); - ArgList = NULL; + ArgList = nullptr; delete this; return x->Resolve(ctx); } @@ -3706,24 +3698,25 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) ScriptPosition.Message(MSG_ERROR, "Not enough parameters for '%s' (expected %d, got %d)", MethodName.GetChars(), min, paramcount); delete this; - return NULL; + return nullptr; } else if (paramcount > max) { ScriptPosition.Message(MSG_ERROR, "too many parameters for '%s' (expected %d, got %d)", MethodName.GetChars(), max, paramcount); delete this; - return NULL; + return nullptr; } - FxExpression *x = new FxActionSpecialCall(Self, special, ArgList, ScriptPosition); - ArgList = NULL; + FxExpression *self = (ctx.Function && ctx.Function->Variants[0].Flags & VARF_Method) ? new FxSelf(ScriptPosition) : nullptr; + FxExpression *x = new FxActionSpecialCall(self, special, ArgList, ScriptPosition); + ArgList = nullptr; delete this; return x->Resolve(ctx); } ScriptPosition.Message(MSG_ERROR, "Call to unknown function '%s'", MethodName.GetChars()); delete this; - return NULL; + return nullptr; } @@ -3780,6 +3773,7 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) CHECKRESOLVED(); bool failed = false; + SAFE_RESOLVE_OPT(Self, ctx); if (ArgList != NULL) { for (unsigned i = 0; i < ArgList->Size(); i++) @@ -3840,11 +3834,12 @@ int DecoCallLineSpecial(VMFrameStack *stack, VMValue *param, int numparam, VMRet ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) { - assert(Self == NULL); unsigned i = 0; build->Emit(OP_PARAMI, abs(Special)); // pass special number - build->Emit(OP_PARAM, 0, REGT_POINTER, 0); // pass self + // fixme: This really should use the Self pointer that got passed to this class instead of just using the first argument from the function. + // Once static functions are possible, or specials can be called through a member access operator this won't work anymore. + build->Emit(OP_PARAM, 0, REGT_POINTER, 0); // pass self if (ArgList != NULL) { for (; i < ArgList->Size(); ++i) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index d69323ce0..7f00020c1 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -888,13 +888,12 @@ typedef TDeletingArray FArgumentList; class FxFunctionCall : public FxExpression { - FxExpression *Self; FName MethodName; FArgumentList *ArgList; public: - FxFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos); + FxFunctionCall(FName methodname, FArgumentList *args, const FScriptPosition &pos); ~FxFunctionCall(); FxExpression *Resolve(FCompileContext&); }; diff --git a/src/scripting/codegeneration/functioncalls.cpp b/src/scripting/codegeneration/functioncalls.cpp index d085635cd..1c8dfb3f5 100644 --- a/src/scripting/codegeneration/functioncalls.cpp +++ b/src/scripting/codegeneration/functioncalls.cpp @@ -39,75 +39,6 @@ // just some rough concepts for now... -//========================================================================== -// -// FindClassMemberFunction -// -// Looks for a name in a class's -// -//========================================================================== - -PFunction *FindClassMemberFunction(PClass *cls, FName name, FScriptPosition &sc) -{ - PSymbolTable *symtable; - auto symbol = cls->Symbols.FindSymbolInTable(name, symtable); - auto funcsym = dyn_cast(symbol); - - if (symbol != nullptr) - { - if (funcsym == nullptr) - { - sc.Message(MSG_ERROR, "%s is not a member function of %s", name.GetChars(), cls->TypeName.GetChars()); - } - else if (funcsym->Flags & VARF_Private && symtable != &cls->Symbols) - { - sc.Message(MSG_ERROR, "%s is declared private and not accessible", symbol->SymbolName.GetChars()); - } - else if (funcsym->Flags & VARF_Deprecated) - { - sc.Message(MSG_WARNING, "Call to deprecated function %s", symbol->SymbolName.GetChars()); - } - } - return funcsym; -} - - -//========================================================================== -// -// let's save some work down the line by analyzing the type of function -// that's being called right here and create appropriate nodes. -// A simple function call expression must be immediately resolvable in -// the context it gets compiled in, if the function name cannot be -// resolved here, it will never. -// -//========================================================================== - -FxExpression *ConvertSimpleFunctionCall(ZCC_ExprID *function, FArgumentList *args, PClass *cls, FScriptPosition &sc) -{ - // Priority is as follows: - //1. member functions of the containing class. - //2. action specials. - //3. floating point operations - //4. global builtins - - if (cls != nullptr) - { - // There is an action function ACS_NamedExecuteWithResult which must be ignored here for this to work. - if (function->Identifier != NAME_ACS_NamedExecuteWithResult) - { - { - args = ConvertNodeList(fcall->Parameters); - if (args->Size() == 0) - { - delete args; - args = nullptr; - } - - return new FxMemberunctionCall(new FxSelf(), new FxInvoker(), func, args, sc, false); - } - } - -} //========================================================================== // @@ -125,7 +56,7 @@ FxExpression *ConvertFunctionCall(ZCC_Expression *function, FArgumentList *args, switch(function->NodeType) { case AST_ExprID: - return ConvertSimpleFunctionCall(static_cast(function), args, cls, sc); + return new FxFunctionCall( ConvertSimpleFunctionCall(static_cast(function), args, cls, sc); case AST_ExprMemberAccess: return ConvertMemberCall(fcall); diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 5dc909cd0..8b12e1c1e 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -548,7 +548,7 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) while (sc.CheckToken(',')); sc.MustGetToken(')'); } - return new FxFunctionCall(NULL, identifier, args, sc); + return new FxFunctionCall(identifier, args, sc); } catch (...) { diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 413999ddc..fc281e8e8 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -147,6 +147,43 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i return sym; } +//========================================================================== +// +// FindClassMemberFunction +// +// Looks for a name in a class's symbol table and outputs appropriate messages +// +//========================================================================== + +PFunction *FindClassMemberFunction(PClass *selfcls, PClass *funccls, FName name, FScriptPosition &sc) +{ + // Skip ACS_NamedExecuteWithResult. Anything calling this should use the builtin instead. + if (name == NAME_ACS_NamedExecuteWithResult) return nullptr; + + PSymbolTable *symtable; + auto symbol = selfcls->Symbols.FindSymbolInTable(name, symtable); + auto funcsym = dyn_cast(symbol); + + if (symbol != nullptr) + { + if (funcsym == nullptr) + { + sc.Message(MSG_ERROR, "%s is not a member function of %s", name.GetChars(), selfcls->TypeName.GetChars()); + } + else if (funcsym->Variants[0].Flags & VARF_Private && symtable != &funccls->Symbols) + { + // private access is only allowed if the symbol table belongs to the class in which the current function is being defined. + sc.Message(MSG_ERROR, "%s is declared private and not accessible", symbol->SymbolName.GetChars()); + } + else if (funcsym->Variants[0].Flags & VARF_Deprecated) + { + sc.Message(MSG_WARNING, "Call to deprecated function %s", symbol->SymbolName.GetChars()); + } + } + // return nullptr if the name cannot be found in the symbol table so that the calling code can do other checks. + return funcsym; +} + //========================================================================== // // LoadActors diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index d5b189d47..7c2b90e50 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -152,6 +152,7 @@ class FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestr FName CheckCastKludges(FName in); void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); +PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc); //========================================================================== // diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index aee7e8b76..1561bc096 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2011,24 +2011,30 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a assert(fc->Function->NodeType == AST_ExprID); auto id = static_cast(fc->Function); - PFunction *afd = dyn_cast(cls->Symbols.FindSymbol(id->Identifier, true)); - if (afd != nullptr) + // We must skip ACS_NamedExecuteWithResult here, because this name both exists as an action function and as a builtin. + // The code which gets called from here can easily make use of the builtin, so let's just pass this name without any checks. + // The actual action function is still needed by DECORATE: + if (id->Identifier != NAME_ACS_NamedExecuteWithResult) { - if (fc->Parameters == nullptr && (afd->Variants[0].Flags & VARF_Action)) + PFunction *afd = dyn_cast(cls->Symbols.FindSymbol(id->Identifier, true)); + if (afd != nullptr) { - // We can use this function directly without wrapping it in a caller. - return new FxVMFunctionCall(afd, nullptr, *af, true); + if (fc->Parameters == nullptr && (afd->Variants[0].Flags & VARF_Action)) + { + // We can use this function directly without wrapping it in a caller. + return new FxVMFunctionCall(afd, nullptr, *af, true); + } } - } - else - { - // it may also be an action special so check that first before printing an error. - if (!P_FindLineSpecial(FName(id->Identifier).GetChars())) + else { - Error(af, "%s: action function not found in %s", FName(id->Identifier).GetChars(), cls->TypeName.GetChars()); - return nullptr; + // it may also be an action special so check that first before printing an error. + if (!P_FindLineSpecial(FName(id->Identifier).GetChars())) + { + Error(af, "%s: action function not found in %s", FName(id->Identifier).GetChars(), cls->TypeName.GetChars()); + return nullptr; + } + // Action specials fall through to the code generator. } - // Action specials fall through to the code generator. } } ConvertClass = cls; @@ -2284,7 +2290,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) auto fcall = static_cast(ast); assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. auto fname = static_cast(fcall->Function)->Identifier; - return new FxFunctionCall(nullptr, fname, ConvertNodeList(fcall->Parameters), *ast); + return new FxFunctionCall(fname, ConvertNodeList(fcall->Parameters), *ast); //return ConvertFunctionCall(fcall->Function, ConvertNodeList(fcall->Parameters), ConvertClass, *ast); } @@ -2298,22 +2304,22 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case AST_ExprConstant: { auto cnst = static_cast(ast); - if (cnst->Type->IsKindOf(RUNTIME_CLASS(PInt))) + if (cnst->Type->IsA(RUNTIME_CLASS(PName))) + { + return new FxConstant(FName(ENamedName(cnst->IntVal)), *ast); + } + else if (cnst->Type->IsA(RUNTIME_CLASS(PInt))) { return new FxConstant(cnst->IntVal, *ast); } - else if (cnst->Type->IsKindOf(RUNTIME_CLASS(PFloat))) + else if (cnst->Type->IsA(RUNTIME_CLASS(PFloat))) { return new FxConstant(cnst->DoubleVal, *ast); } - else if (cnst->Type->IsKindOf(RUNTIME_CLASS(PString))) + else if (cnst->Type->IsA(RUNTIME_CLASS(PString))) { return new FxConstant(*cnst->StringVal, *ast); } - else if (cnst->Type->IsKindOf(RUNTIME_CLASS(PName))) - { - return new FxConstant(ENamedName(cnst->IntVal), *ast); - } else { // can there be other types? From b299b64e47736227a098aa42bd5c5292c165dfd3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 15 Oct 2016 21:35:31 +0200 Subject: [PATCH 044/255] - the compile context now knows if it is invoked by ZScript or DECORATE, so that it can be more strict with ZScript if needed. - added a truncation warning to FxIntCast, which only occurs with ZScript, not with DECORATE. FxBoolCast is intentionally left out because it would defeat the reason for this cast type. --- src/scripting/codegeneration/codegen.cpp | 49 ++++++++++++++-------- src/scripting/codegeneration/codegen.h | 12 +++--- src/scripting/decorate/thingdef_exp.cpp | 8 ++-- src/scripting/decorate/thingdef_parse.cpp | 4 +- src/scripting/decorate/thingdef_states.cpp | 2 +- src/scripting/thingdef_properties.cpp | 2 +- src/scripting/vm/vmbuilder.cpp | 6 +-- src/scripting/vm/vmbuilder.h | 4 +- src/scripting/zscript/zcc_compile.cpp | 2 +- 9 files changed, 52 insertions(+), 37 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9cdd9c1f2..c66c96f32 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -91,12 +91,12 @@ static const FLOP FxFlops[] = // //========================================================================== -FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret) : ReturnProto(ret), Function(fnc), Class(nullptr) +FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret, bool fromdecorate) : ReturnProto(ret), Function(fnc), Class(nullptr), FromDecorate(fromdecorate) { if (fnc != nullptr) Class = fnc->OwningClass; } -FCompileContext::FCompileContext(PClass *cls) : ReturnProto(nullptr), Function(nullptr), Class(cls) +FCompileContext::FCompileContext(PClass *cls) : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(true) // only used by DECORATE constants. { } @@ -495,11 +495,12 @@ ExpEmit FxBoolCast::Emit(VMFunctionBuilder *build) // //========================================================================== -FxIntCast::FxIntCast(FxExpression *x) +FxIntCast::FxIntCast(FxExpression *x, bool nowarn) : FxExpression(x->ScriptPosition) { basex=x; ValueType = TypeSInt32; + NoWarn = nowarn; } //========================================================================== @@ -536,6 +537,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) else { // Ugh. This should abort, but too many mods fell into this logic hole somewhere, so this seroious error needs to be reduced to a warning. :( + // At least in ZScript, MSG_OPTERROR always means to report an error, not a warning so the problem only exists in DECORATE. if (!basex->isConstant()) ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got a name"); else ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got \"%s\"", static_cast(basex)->GetValue().GetName().GetChars()); FxExpression * x = new FxConstant(0, ScriptPosition); @@ -549,9 +551,19 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) { ExpVal constval = static_cast(basex)->GetValue(); FxExpression *x = new FxConstant(constval.GetInt(), ScriptPosition); + if (!NoWarn && constval.GetInt() != constval.GetFloat()) + { + ScriptPosition.Message(MSG_WARNING, "Truncation of floating point constant %f", constval.GetFloat()); + } + delete this; return x; } + else if (!NoWarn) + { + ScriptPosition.Message(MSG_WARNING, "Truncation of floating point value"); + } + return this; } ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); @@ -634,6 +646,7 @@ FxExpression *FxFloatCast::Resolve(FCompileContext &ctx) else { // Ugh. This should abort, but too many mods fell into this logic hole somewhere, so this seroious error needs to be reduced to a warning. :( + // At least in ZScript, MSG_OPTERROR always means to report an error, not a warning so the problem only exists in DECORATE. if (!basex->isConstant()) ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got a name"); else ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got \"%s\"", static_cast(basex)->GetValue().GetName().GetChars()); FxExpression *x = new FxConstant(0.0, ScriptPosition); @@ -837,7 +850,7 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) if (Operand->ValueType->GetRegType() == REGT_FLOAT /* lax */) { // DECORATE allows floats here so cast them to int. - Operand = new FxIntCast(Operand); + Operand = new FxIntCast(Operand, ctx.FromDecorate); Operand = Operand->Resolve(ctx); if (Operand == NULL) { @@ -1165,7 +1178,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) } else if (ValueType->GetRegType() == REGT_INT) { - Right = new FxIntCast(Right); + Right = new FxIntCast(Right, ctx.FromDecorate); } else { @@ -1840,12 +1853,12 @@ FxExpression *FxBinaryInt::Resolve(FCompileContext& ctx) // For DECORATE which allows floats here. if (left->ValueType->GetRegType() != REGT_INT) { - left = new FxIntCast(left); + left = new FxIntCast(left, ctx.FromDecorate); left = left->Resolve(ctx); } if (right->ValueType->GetRegType() != REGT_INT) { - right = new FxIntCast(right); + right = new FxIntCast(right, ctx.FromDecorate); right = right->Resolve(ctx); } if (left == NULL || right == NULL) @@ -2710,14 +2723,14 @@ ExpEmit FxMinMax::Emit(VMFunctionBuilder *build) // // //========================================================================== -FxRandom::FxRandom(FRandom * r, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos) +FxRandom::FxRandom(FRandom * r, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos, bool nowarn) : FxExpression(pos) { EmitTail = false; if (mi != NULL && ma != NULL) { - min = new FxIntCast(mi); - max = new FxIntCast(ma); + min = new FxIntCast(mi, nowarn); + max = new FxIntCast(ma, nowarn); } else min = max = NULL; rng = r; @@ -2843,7 +2856,7 @@ ExpEmit FxRandom::Emit(VMFunctionBuilder *build) // // //========================================================================== -FxRandomPick::FxRandomPick(FRandom *r, TArray &expr, bool floaty, const FScriptPosition &pos) +FxRandomPick::FxRandomPick(FRandom *r, TArray &expr, bool floaty, const FScriptPosition &pos, bool nowarn) : FxExpression(pos) { assert(expr.Size() > 0); @@ -2856,7 +2869,7 @@ FxRandomPick::FxRandomPick(FRandom *r, TArray &expr, bool floaty, } else { - choices[index] = new FxIntCast(expr[index]); + choices[index] = new FxIntCast(expr[index], nowarn); } } @@ -3008,7 +3021,7 @@ ExpEmit FxRandomPick::Emit(VMFunctionBuilder *build) // //========================================================================== FxFRandom::FxFRandom(FRandom *r, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos) -: FxRandom(r, NULL, NULL, pos) +: FxRandom(r, NULL, NULL, pos, true) { if (mi != NULL && ma != NULL) { @@ -3089,12 +3102,12 @@ ExpEmit FxFRandom::Emit(VMFunctionBuilder *build) // //========================================================================== -FxRandom2::FxRandom2(FRandom *r, FxExpression *m, const FScriptPosition &pos) +FxRandom2::FxRandom2(FRandom *r, FxExpression *m, const FScriptPosition &pos, bool nowarn) : FxExpression(pos) { EmitTail = false; rng = r; - if (m) mask = new FxIntCast(m); + if (m) mask = new FxIntCast(m, nowarn); else mask = new FxConstant(-1, pos); ValueType = TypeSInt32; } @@ -3505,7 +3518,7 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) if (index->ValueType->GetRegType() == REGT_FLOAT /* lax */) { // DECORATE allows floats here so cast them to int. - index = new FxIntCast(index); + index = new FxIntCast(index, ctx.FromDecorate); index = index->Resolve(ctx); if (index == NULL) { @@ -3792,7 +3805,7 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) { if ((*ArgList)[i]->ValueType->GetRegType() == REGT_FLOAT /* lax */) { - (*ArgList)[i] = new FxIntCast((*ArgList)[i]); + (*ArgList)[i] = new FxIntCast((*ArgList)[i], ctx.FromDecorate); } else { @@ -5075,7 +5088,7 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) } else if (Index->ValueType->GetRegType() != REGT_INT) { // Float. - Index = new FxIntCast(Index); + Index = new FxIntCast(Index, ctx.FromDecorate); SAFE_RESOLVE(Index, ctx); } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 7f00020c1..9ee8704cc 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -69,8 +69,9 @@ struct FCompileContext PPrototype *ReturnProto; PFunction *Function; // The function that is currently being compiled (or nullptr for constant evaluation.) PClass *Class; // The type of the owning class. + bool FromDecorate; - FCompileContext(PFunction *func = nullptr, PPrototype *ret = nullptr); + FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate); FCompileContext(PClass *cls); // only to be used to resolve constants! PSymbol *FindInClass(FName identifier, PSymbolTable *&symt); @@ -383,10 +384,11 @@ public: class FxIntCast : public FxExpression { FxExpression *basex; + bool NoWarn; public: - FxIntCast(FxExpression *x); + FxIntCast(FxExpression *x, bool nowarn); ~FxIntCast(); FxExpression *Resolve(FCompileContext&); @@ -759,7 +761,7 @@ protected: public: - FxRandom(FRandom *, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos); + FxRandom(FRandom *, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos, bool nowarn); ~FxRandom(); FxExpression *Resolve(FCompileContext&); PPrototype *ReturnProto(); @@ -780,7 +782,7 @@ protected: public: - FxRandomPick(FRandom *, TArray &expr, bool floaty, const FScriptPosition &pos); + FxRandomPick(FRandom *, TArray &expr, bool floaty, const FScriptPosition &pos, bool nowarn); ~FxRandomPick(); FxExpression *Resolve(FCompileContext&); @@ -814,7 +816,7 @@ class FxRandom2 : public FxExpression public: - FxRandom2(FRandom *, FxExpression *m, const FScriptPosition &pos); + FxRandom2(FRandom *, FxExpression *m, const FScriptPosition &pos, bool nowarn); ~FxRandom2(); FxExpression *Resolve(FCompileContext&); PPrototype *ReturnProto(); diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 8b12e1c1e..c10ef9ad8 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -448,7 +448,7 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) sc.MustGetToken('('); FxExpression *exp = ParseExpressionM(sc, cls); sc.MustGetToken(')'); - return new FxIntCast(exp); + return new FxIntCast(exp, true); } else if (sc.CheckToken(TK_Float)) { @@ -600,7 +600,7 @@ static FxExpression *ParseRandom(FScanner &sc, FName identifier, PClassActor *cl if (identifier == NAME_Random) { - return new FxRandom(rng, min, max, sc); + return new FxRandom(rng, min, max, sc, true); } else { @@ -627,7 +627,7 @@ static FxExpression *ParseRandomPick(FScanner &sc, FName identifier, PClassActor break; sc.MustGetToken(','); } - return new FxRandomPick(rng, list, floaty, sc); + return new FxRandomPick(rng, list, floaty, sc, true); } static FxExpression *ParseRandom2(FScanner &sc, PClassActor *cls) @@ -642,7 +642,7 @@ static FxExpression *ParseRandom2(FScanner &sc, PClassActor *cls) mask = ParseExpressionM(sc, cls); sc.MustGetToken(')'); } - return new FxRandom2(rng, mask, sc); + return new FxRandom2(rng, mask, sc, true); } static FxExpression *ParseAbs(FScanner &sc, PClassActor *cls) diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index b2f1cac07..534c74d18 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -131,7 +131,7 @@ FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool c } else if (type == TypeSInt32) { - x = new FxIntCast(x); + x = new FxIntCast(x, true); } else { @@ -871,7 +871,7 @@ static bool ParsePropertyParams(FScanner &sc, FPropertyInfo *prop, AActor *defau { conv.i = -1; params.Push(conv); - x = new FxDamageValue(new FxIntCast(ParseExpression(sc, bag.Info))); + x = new FxDamageValue(new FxIntCast(ParseExpression(sc, bag.Info), true)); sc.MustGetStringName(")"); conv.exp = x; params.Push(conv); diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index d5a3395d7..59ec3e39d 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -84,7 +84,7 @@ FxVMFunctionCall *DoActionSpecials(FScanner &sc, FState & state, Baggage &bag) { while (i < 5) { - args->Push(new FxIntCast(ParseExpression(sc, bag.Info))); + args->Push(new FxIntCast(ParseExpression(sc, bag.Info), true)); i++; if (!sc.CheckToken (',')) break; } diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index 34f424ab4..8fc660913 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -658,7 +658,7 @@ DEFINE_PROPERTY(damage, X, Actor) else { auto funcsym = CreateAnonymousFunction(bag.Info, TypeSInt32, VARF_Method); - defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, id, FStringf("%s.DamageFunction", bag.Info->TypeName.GetChars()), false); + defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, id, FStringf("%s.DamageFunction", bag.Info->TypeName.GetChars()), !bag.fromZScript); } } diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 7c5118467..7e946a17c 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -649,7 +649,7 @@ void VMFunctionBuilder::BackpatchToHere(size_t loc) //========================================================================== FFunctionBuildList FunctionBuildList; -VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool statecall) +VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool fromdecorate) { auto func = code->GetDirectFunction(); if (func != nullptr) @@ -666,7 +666,7 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c it.DumpName = name; it.Function = new VMScriptFunction; it.Proto = nullptr; - it.type = statecall; + it.FromDecorate = fromdecorate; mItems.Push(it); return it.Function; } @@ -687,7 +687,7 @@ void FFunctionBuildList::Build() // This needs to be fixed, so that the compile context receives the entire function symbol, including the containing class, the prototype and argument names, which will be needed to run the code generator // As a first step this just needs to get working so fetch the class type from the prototype's argument list. // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(item.Func, nullptr); + FCompileContext ctx(item.Func, nullptr, item.FromDecorate); item.Code = item.Code->Resolve(ctx); item.Proto = ctx.ReturnProto; diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index 6b9a0aa68..c5ca868e0 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -106,13 +106,13 @@ class FFunctionBuildList PPrototype *Proto = nullptr; VMScriptFunction *Function = nullptr; FString DumpName; - int type; // temporary kludge + bool FromDecorate; }; TArray mItems; public: - VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool statecall = false); + VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool fromdecorate); void Build(); }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 1561bc096..cbf6b08c1 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2172,7 +2172,7 @@ void ZCCCompiler::CompileStates() if (code != nullptr) { auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action); - state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), true); + state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false); } } From 55f6661c87d0d54353e3f695541ff3354ec0f43c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 00:12:33 +0200 Subject: [PATCH 045/255] - added handling for all the builtins supported by DECORATE to FxFunctionCall. For the random functions this class only handles the default-RNG version. The one with an explicit RNG needs to be done separately because the parser produces different output for them. --- src/scripting/codegeneration/codegen.cpp | 114 ++++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 5 +- src/scripting/zscript/zcc_compile.cpp | 6 ++ 3 files changed, 122 insertions(+), 3 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index c66c96f32..8d2fa10a2 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -2541,7 +2541,7 @@ FxExpression *FxMinMax::Resolve(FCompileContext &ctx) { floatcount++; } - else if (choices[i]->ValueType->GetRegType() == REGT_INT) + else if (choices[i]->ValueType->GetRegType() == REGT_INT && choices[i]->ValueType != TypeName) { intcount++; } @@ -3663,7 +3663,29 @@ FxFunctionCall::~FxFunctionCall() //========================================================================== // -// Note: This currently only deals with the simple cases and needs some changes. +// Check function that gets called +// +//========================================================================== + +static bool CheckArgSize(FName fname, FArgumentList *args, int min, int max, FScriptPosition &sc) +{ + int s = args ? args->Size() : 0; + if (s < min) + { + sc.Message(MSG_ERROR, "Insufficient arguments in call to %s, expected %d, got %d", fname.GetChars(), min, s); + return false; + } + else if (s > max && max >= 0) + { + sc.Message(MSG_ERROR, "Too many arguments in call to %s, expected %d, got %d", fname.GetChars(), min, s); + return false; + } + return true; +} + +//========================================================================== +// +// // //========================================================================== @@ -3727,6 +3749,94 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) return x->Resolve(ctx); } + // Last but not least: Check builtins. The random functions will have to be duplicated for the case where an RNG is specified. + // Note that for all builtins the used arguments have to be nulled in the ArgList so that they won't get deleted before they get used. + FxExpression *func = nullptr; + + Printf("Resolving %s with %d args\n", MethodName.GetChars(), ArgList->Size()); + switch (MethodName) + { + case NAME_Random: + if (CheckArgSize(NAME_Random, ArgList, 2, 2, ScriptPosition)) + { + func = new FxRandom(nullptr, (*ArgList)[0], (*ArgList)[1], ScriptPosition, ctx.FromDecorate); + (*ArgList)[0] = (*ArgList)[1] = nullptr; + } + break; + + case NAME_FRandom: + if (CheckArgSize(NAME_FRandom, ArgList, 2, 2, ScriptPosition)) + { + func = new FxFRandom(nullptr, (*ArgList)[0], (*ArgList)[1], ScriptPosition); + (*ArgList)[0] = (*ArgList)[1] = nullptr; + } + break; + + case NAME_RandomPick: + case NAME_FRandomPick: + if (CheckArgSize(MethodName, ArgList, 1, -1, ScriptPosition)) + { + func = new FxRandomPick(nullptr, *ArgList, MethodName == NAME_FRandomPick, ScriptPosition, ctx.FromDecorate); + for (auto &i : *ArgList) i = nullptr; // Ownership of items is transferred to FxMinMax but not ownership of the array itself, so Clear cannot be called here. + } + break; + + case NAME_Random2: + if (CheckArgSize(NAME_Random2, ArgList, 1, 1, ScriptPosition)) + { + func = new FxRandom2(nullptr, (*ArgList)[0], ScriptPosition, ctx.FromDecorate); + (*ArgList)[0] = nullptr; + } + break; + + case NAME_Min: + case NAME_Max: + if (CheckArgSize(MethodName, ArgList, 2, -1, ScriptPosition)) + { + func = new FxMinMax(*ArgList, MethodName, ScriptPosition); + for (auto &i : *ArgList) i = nullptr; // Ownership of items is transferred to FxMinMax but not ownership of the array itself, so Clear cannot be called here. + } + break; + + case NAME_Clamp: + if (CheckArgSize(MethodName, ArgList, 3, 3, ScriptPosition)) + { + TArray pass; + pass.Resize(2); + pass[0] = (*ArgList)[0]; + pass[1] = (*ArgList)[1]; + pass[0] = new FxMinMax(pass, NAME_Max, ScriptPosition); + pass[1] = (*ArgList)[2]; + func = new FxMinMax(*ArgList, NAME_Min, ScriptPosition); + (*ArgList)[0] = (*ArgList)[1] = (*ArgList)[2] = nullptr; + } + break; + + case NAME_Abs: + if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) + { + func = new FxAbs((*ArgList)[0]); + (*ArgList)[0] = nullptr; + } + break; + + case NAME_ATan2: + case NAME_VectorAngle: + if (CheckArgSize(MethodName, ArgList, 2, 2, ScriptPosition)) + { + func = MethodName == NAME_ATan2 ? new FxATan2((*ArgList)[0], (*ArgList)[1], ScriptPosition) : new FxATan2((*ArgList)[1], (*ArgList)[0], ScriptPosition); + (*ArgList)[0] = (*ArgList)[1] = nullptr; + } + break; + + default: + break; + } + if (func != nullptr) + { + delete this; + return func->Resolve(ctx); + } ScriptPosition.Message(MSG_ERROR, "Call to unknown function '%s'", MethodName.GetChars()); delete this; return nullptr; diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 9ee8704cc..6645d8c8a 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -203,7 +203,10 @@ protected: : ScriptPosition(pos) { } -public: + +public: + FxExpression *CheckIntForName(); + virtual ~FxExpression() {} virtual FxExpression *Resolve(FCompileContext &ctx); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index cbf6b08c1..26964381b 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2301,6 +2301,12 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return ConvertNode(fparm->Value); } + case AST_ExprID: + { + auto id = static_cast(ast); + return new FxIdentifier(id->Identifier, *ast); + } + case AST_ExprConstant: { auto cnst = static_cast(ast); From d6ce60f63a517a11f645d6876a47805d6fd80b2d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 01:08:02 +0200 Subject: [PATCH 046/255] - added named RNG support to FxFunctionCall. This looks simpler than duplicating all that stuff and avoids a lot code duplication. --- src/scripting/codegeneration/codegen.cpp | 31 +++++++++++++++++++----- src/scripting/codegeneration/codegen.h | 3 ++- src/scripting/decorate/thingdef_exp.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 2 +- 4 files changed, 29 insertions(+), 9 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 8d2fa10a2..7eaecb82d 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3643,11 +3643,30 @@ ExpEmit FxArrayElement::Emit(VMFunctionBuilder *build) // //========================================================================== -FxFunctionCall::FxFunctionCall(FName methodname, FArgumentList *args, const FScriptPosition &pos) +FxFunctionCall::FxFunctionCall(FName methodname, FName rngname, FArgumentList *args, const FScriptPosition &pos) : FxExpression(pos) { MethodName = methodname; + RNG = nullptr; ArgList = args; + if (rngname != NAME_None) + { + switch (MethodName) + { + case NAME_Random: + case NAME_FRandom: + case NAME_RandomPick: + case NAME_FRandomPick: + case NAME_Random2: + RNG = FRandom::StaticFindRNG(rngname.GetChars()); + break; + + default: + pos.Message(MSG_ERROR, "Cannot use named RNGs with %s", MethodName.GetChars()); + break; + + } + } } //========================================================================== @@ -3749,7 +3768,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) return x->Resolve(ctx); } - // Last but not least: Check builtins. The random functions will have to be duplicated for the case where an RNG is specified. + // Last but not least: Check builtins. The random functions can take a named RNG if specified. // Note that for all builtins the used arguments have to be nulled in the ArgList so that they won't get deleted before they get used. FxExpression *func = nullptr; @@ -3759,7 +3778,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Random: if (CheckArgSize(NAME_Random, ArgList, 2, 2, ScriptPosition)) { - func = new FxRandom(nullptr, (*ArgList)[0], (*ArgList)[1], ScriptPosition, ctx.FromDecorate); + func = new FxRandom(RNG, (*ArgList)[0], (*ArgList)[1], ScriptPosition, ctx.FromDecorate); (*ArgList)[0] = (*ArgList)[1] = nullptr; } break; @@ -3767,7 +3786,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_FRandom: if (CheckArgSize(NAME_FRandom, ArgList, 2, 2, ScriptPosition)) { - func = new FxFRandom(nullptr, (*ArgList)[0], (*ArgList)[1], ScriptPosition); + func = new FxFRandom(RNG, (*ArgList)[0], (*ArgList)[1], ScriptPosition); (*ArgList)[0] = (*ArgList)[1] = nullptr; } break; @@ -3776,7 +3795,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_FRandomPick: if (CheckArgSize(MethodName, ArgList, 1, -1, ScriptPosition)) { - func = new FxRandomPick(nullptr, *ArgList, MethodName == NAME_FRandomPick, ScriptPosition, ctx.FromDecorate); + func = new FxRandomPick(RNG, *ArgList, MethodName == NAME_FRandomPick, ScriptPosition, ctx.FromDecorate); for (auto &i : *ArgList) i = nullptr; // Ownership of items is transferred to FxMinMax but not ownership of the array itself, so Clear cannot be called here. } break; @@ -3784,7 +3803,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Random2: if (CheckArgSize(NAME_Random2, ArgList, 1, 1, ScriptPosition)) { - func = new FxRandom2(nullptr, (*ArgList)[0], ScriptPosition, ctx.FromDecorate); + func = new FxRandom2(RNG, (*ArgList)[0], ScriptPosition, ctx.FromDecorate); (*ArgList)[0] = nullptr; } break; diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 6645d8c8a..213fe388a 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -894,11 +894,12 @@ typedef TDeletingArray FArgumentList; class FxFunctionCall : public FxExpression { FName MethodName; + FRandom *RNG; FArgumentList *ArgList; public: - FxFunctionCall(FName methodname, FArgumentList *args, const FScriptPosition &pos); + FxFunctionCall(FName methodname, FName rngname, FArgumentList *args, const FScriptPosition &pos); ~FxFunctionCall(); FxExpression *Resolve(FCompileContext&); }; diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index c10ef9ad8..5be69390e 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -548,7 +548,7 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) while (sc.CheckToken(',')); sc.MustGetToken(')'); } - return new FxFunctionCall(identifier, args, sc); + return new FxFunctionCall(identifier, NAME_None, args, sc); } catch (...) { diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 26964381b..e9e806907 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2290,7 +2290,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) auto fcall = static_cast(ast); assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. auto fname = static_cast(fcall->Function)->Identifier; - return new FxFunctionCall(fname, ConvertNodeList(fcall->Parameters), *ast); + return new FxFunctionCall(fname, NAME_None, ConvertNodeList(fcall->Parameters), *ast); //return ConvertFunctionCall(fcall->Function, ConvertNodeList(fcall->Parameters), ConvertClass, *ast); } From 847b8c45efac8d98922fef6e981352a516c5e265 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 01:33:36 +0200 Subject: [PATCH 047/255] - Changed ZCCCompiler::Simplify to allow running in constant and non-constant mode. The difference is that non-constant mode does not attempt to simplify function name expressions because these cannot be processed without destroying them, if some identifier in there is not referencing a symbol, which is quite common. --- src/scripting/zscript/zcc_compile.cpp | 52 ++++++++++++++++----------- src/scripting/zscript/zcc_compile.h | 4 ++- 2 files changed, 35 insertions(+), 21 deletions(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e9e806907..6d0295696 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -685,7 +685,7 @@ bool ZCCCompiler::CompileConstant(ZCC_ConstantDef *def, PSymbolTable *sym) assert(def->Symbol == nullptr); def->Symbol = DEFINING_CONST; // avoid recursion - ZCC_Expression *val = Simplify(def->Value, sym); + ZCC_Expression *val = Simplify(def->Value, sym, true); def->Value = val; if (def->Symbol == DEFINING_CONST) def->Symbol = nullptr; return (val->NodeType == AST_ExprConstant); @@ -705,7 +705,13 @@ bool ZCCCompiler::CompileConstant(ZCC_ConstantDef *def, PSymbolTable *sym) // //========================================================================== -ZCC_Expression *ZCCCompiler::Simplify(ZCC_Expression *root, PSymbolTable *sym) +ZCC_Expression *ZCCCompiler::Simplify(ZCC_Expression *root, PSymbolTable *sym, bool wantconstant) +{ + SimplifyingConstant = wantconstant; + return DoSimplify(root, sym); +} + +ZCC_Expression *ZCCCompiler::DoSimplify(ZCC_Expression *root, PSymbolTable *sym) { if (root->NodeType == AST_ExprUnary) { @@ -738,7 +744,7 @@ ZCC_Expression *ZCCCompiler::Simplify(ZCC_Expression *root, PSymbolTable *sym) ZCC_Expression *ZCCCompiler::SimplifyUnary(ZCC_ExprUnary *unary, PSymbolTable *sym) { - unary->Operand = Simplify(unary->Operand, sym); + unary->Operand = DoSimplify(unary->Operand, sym); if (unary->Operand->Type == nullptr) { return unary; @@ -763,8 +769,8 @@ ZCC_Expression *ZCCCompiler::SimplifyUnary(ZCC_ExprUnary *unary, PSymbolTable *s ZCC_Expression *ZCCCompiler::SimplifyBinary(ZCC_ExprBinary *binary, PSymbolTable *sym) { - binary->Left = Simplify(binary->Left, sym); - binary->Right = Simplify(binary->Right, sym); + binary->Left = DoSimplify(binary->Left, sym); + binary->Right = DoSimplify(binary->Right, sym); if (binary->Left->Type == nullptr || binary->Right->Type == nullptr) { // We do not know yet what this is so we cannot promote it (yet.) @@ -794,7 +800,8 @@ ZCC_Expression *ZCCCompiler::SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop, P { PSymbolTable *symtable; - dotop->Left = Simplify(dotop->Left, symt); + // TBD: Is it safe to simplify the left side here when not processing a constant? + dotop->Left = DoSimplify(dotop->Left, symt); if (dotop->Left->Operation == PEX_TypeRef) { // Type refs can be evaluated now. @@ -842,7 +849,6 @@ ZCC_Expression *ZCCCompiler::SimplifyFunctionCall(ZCC_ExprFuncCall *callop, PSym ZCC_FuncParm *parm; int parmcount = 0; - callop->Function = Simplify(callop->Function, sym); parm = callop->Parameters; if (parm != NULL) { @@ -850,11 +856,18 @@ ZCC_Expression *ZCCCompiler::SimplifyFunctionCall(ZCC_ExprFuncCall *callop, PSym { parmcount++; assert(parm->NodeType == AST_FuncParm); - parm->Value = Simplify(parm->Value, sym); + parm->Value = DoSimplify(parm->Value, sym); parm = static_cast(parm->SiblingNext); } while (parm != callop->Parameters); } + // Only simplify the 'function' part if we want to retrieve a constant. + // This is necessary to evaluate the type casts, but for actual functions + // the simplification process is destructive and has to be avoided. + if (SimplifyingConstant) + { + callop->Function = DoSimplify(callop->Function, sym); + } // If the left side is a type ref, then this is actually a cast // and not a function call. if (callop->Function->Operation == PEX_TypeRef) @@ -1440,11 +1453,11 @@ PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt) PType *ZCCCompiler::ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym) { // The duplicate Simplify call is necessary because if the head node gets replaced there is no way to detect the end of the list otherwise. - arraysize = Simplify(arraysize, sym); + arraysize = Simplify(arraysize, sym, true); ZCC_Expression *val; do { - val = Simplify(arraysize, sym); + val = Simplify(arraysize, sym, true); if (val->Operation != PEX_ConstValue || !val->Type->IsA(RUNTIME_CLASS(PInt))) { Error(arraysize, "Array index must be an integer constant"); @@ -1556,7 +1569,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper Error(property, "%s: arguments missing", prop->name); return; } - property->Values = Simplify(property->Values, &bag.Info->Symbols); // need to do this before the loop so that we can find the head node again. + property->Values = Simplify(property->Values, &bag.Info->Symbols, true); // need to do this before the loop so that we can find the head node again. const char * p = prop->params; auto exp = property->Values; @@ -1634,7 +1647,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper params.Push(conv); params[0].i++; } - exp = Simplify(static_cast(exp->SiblingNext), &bag.Info->Symbols); + exp = Simplify(static_cast(exp->SiblingNext), &bag.Info->Symbols, true); } while (exp != property->Values); goto endofparm; } @@ -1652,7 +1665,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper } params.Push(conv); params[0].i++; - exp = Simplify(static_cast(exp->SiblingNext), &bag.Info->Symbols); + exp = Simplify(static_cast(exp->SiblingNext), &bag.Info->Symbols, true); endofparm: p++; // Skip the DECORATE 'no comma' marker @@ -1944,7 +1957,7 @@ void ZCCCompiler::InitFunctions() if (p->Flags & ZCC_Out) flags |= VARF_Out; if (p->Default != nullptr) { - auto val = Simplify(p->Default, &c->Type()->Symbols); + auto val = Simplify(p->Default, &c->Type()->Symbols, true); flags |= VARF_Optional; if (val->Operation != PEX_ConstValue) { @@ -2101,10 +2114,9 @@ void ZCCCompiler::CompileStates() state.sprite = GetSpriteIndex(sl->Sprite->GetChars()); } // It is important to call CheckRandom before Simplify, because Simplify will resolve the function's name to nonsense - // and there is little point fixing it because it is essentially useless outside of resolving constants. if (CheckRandom(sl->Duration)) { - auto func = static_cast(Simplify(sl->Duration, &c->Type()->Symbols)); + auto func = static_cast(Simplify(sl->Duration, &c->Type()->Symbols, true)); if (func->Parameters == func->Parameters->SiblingNext || func->Parameters != func->Parameters->SiblingNext->SiblingNext) { Error(sl, "Random duration requires exactly 2 parameters"); @@ -2117,7 +2129,7 @@ void ZCCCompiler::CompileStates() } else { - auto duration = Simplify(sl->Duration, &c->Type()->Symbols); + auto duration = Simplify(sl->Duration, &c->Type()->Symbols, true); if (duration->Operation == PEX_ConstValue) { state.Tics = (int16_t)clamp(GetInt(duration), -1, INT16_MAX); @@ -2141,8 +2153,8 @@ void ZCCCompiler::CompileStates() } if (sl->Offset != nullptr) { - auto o1 = static_cast(Simplify(sl->Offset, &c->Type()->Symbols)); - auto o2 = static_cast(Simplify(static_cast(o1->SiblingNext), &c->Type()->Symbols)); + auto o1 = static_cast(Simplify(sl->Offset, &c->Type()->Symbols, true)); + auto o2 = static_cast(Simplify(static_cast(o1->SiblingNext), &c->Type()->Symbols, true)); if (o1->Operation != PEX_ConstValue || o2->Operation != PEX_ConstValue) { @@ -2201,7 +2213,7 @@ void ZCCCompiler::CompileStates() statename.Truncate((long)statename.Len() - 1); // remove the last '.' in the label name if (sg->Offset != nullptr) { - auto ofs = Simplify(sg->Offset, &c->Type()->Symbols); + auto ofs = Simplify(sg->Offset, &c->Type()->Symbols, true); if (ofs->Operation != PEX_ConstValue) { Error(sg, "Constant offset expected for GOTO"); diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 4ecd63227..7a0246ea1 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -111,13 +111,15 @@ private: void CompileStates(); FxExpression *SetupActionFunction(PClassActor *cls, ZCC_TreeNode *sl); + bool SimplifyingConstant; TArray Constants; TArray Structs; TArray Classes; PSymbolTreeNode *AddTreeNode(FName name, ZCC_TreeNode *node, PSymbolTable *treenodes, bool searchparents = false); - ZCC_Expression *Simplify(ZCC_Expression *root, PSymbolTable *Symbols); + ZCC_Expression *Simplify(ZCC_Expression *root, PSymbolTable *Symbols, bool wantconstant); + ZCC_Expression *DoSimplify(ZCC_Expression *root, PSymbolTable *Symbols); ZCC_Expression *SimplifyUnary(ZCC_ExprUnary *unary, PSymbolTable *Symbols); ZCC_Expression *SimplifyBinary(ZCC_ExprBinary *binary, PSymbolTable *Symbols); ZCC_Expression *SimplifyMemberAccess(ZCC_ExprMemberAccess *dotop, PSymbolTable *Symbols); From 2c7c04e803aef5c7dd186a287efc37c9961544b2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 09:31:03 +0200 Subject: [PATCH 048/255] - when simplifying a non-constant expression, leave any identifier that cannot be trivially simplified to a constant alone. It is better to defer resolution to more context-aware code for those. --- src/scripting/zscript/zcc_compile.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 6d0295696..e184ccaa1 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1009,7 +1009,7 @@ ZCC_Expression *ZCCCompiler::IdentifyIdentifier(ZCC_ExprID *idnode, PSymbolTable return node; } } - else + else if (SimplifyingConstant) // leave unknown identifiers alone when simplifying non-constants. It is impossible to know what they are here. { // Also handle line specials. // To call this like a function this needs to be done differently, but for resolving constants this is ok. From 59ab8b7ccdc86291d4ec17963798f533667c1d7b Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 10:59:12 +0200 Subject: [PATCH 049/255] - implemented array-style syntax for Random calls. - implemented handling of the basic math operators so that heretic/beast.txt can be processed. This is working, aside from still needing the type casts to properly transform the strings to class pointers. --- src/scripting/codegeneration/codegen.cpp | 10 +-- .../codegeneration/functioncalls.cpp | 8 -- src/scripting/zscript/zcc_compile.cpp | 81 ++++++++++++++++--- 3 files changed, 73 insertions(+), 26 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 7eaecb82d..91153f3ac 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3796,15 +3796,15 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) if (CheckArgSize(MethodName, ArgList, 1, -1, ScriptPosition)) { func = new FxRandomPick(RNG, *ArgList, MethodName == NAME_FRandomPick, ScriptPosition, ctx.FromDecorate); - for (auto &i : *ArgList) i = nullptr; // Ownership of items is transferred to FxMinMax but not ownership of the array itself, so Clear cannot be called here. + for (auto &i : *ArgList) i = nullptr; } break; case NAME_Random2: - if (CheckArgSize(NAME_Random2, ArgList, 1, 1, ScriptPosition)) + if (CheckArgSize(NAME_Random2, ArgList, 0, 1, ScriptPosition)) { - func = new FxRandom2(RNG, (*ArgList)[0], ScriptPosition, ctx.FromDecorate); - (*ArgList)[0] = nullptr; + func = new FxRandom2(RNG, ArgList->Size() == 0? nullptr : (*ArgList)[0], ScriptPosition, ctx.FromDecorate); + if (ArgList->Size() > 0) (*ArgList)[0] = nullptr; } break; @@ -3813,7 +3813,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) if (CheckArgSize(MethodName, ArgList, 2, -1, ScriptPosition)) { func = new FxMinMax(*ArgList, MethodName, ScriptPosition); - for (auto &i : *ArgList) i = nullptr; // Ownership of items is transferred to FxMinMax but not ownership of the array itself, so Clear cannot be called here. + for (auto &i : *ArgList) i = nullptr; } break; diff --git a/src/scripting/codegeneration/functioncalls.cpp b/src/scripting/codegeneration/functioncalls.cpp index 1c8dfb3f5..ca2b437e7 100644 --- a/src/scripting/codegeneration/functioncalls.cpp +++ b/src/scripting/codegeneration/functioncalls.cpp @@ -48,10 +48,6 @@ FxExpression *ConvertFunctionCall(ZCC_Expression *function, FArgumentList *args, PClass *cls, FScriptPosition &sc) { - // function names can either be - // - plain identifiers - // - class members - // - array syntax for random() calls. switch(function->NodeType) { @@ -63,10 +59,6 @@ FxExpression *ConvertFunctionCall(ZCC_Expression *function, FArgumentList *args, case AST_ExprBinary: // Array access syntax is wrapped into a ZCC_ExprBinary object. - if (fcall->Function->Operation == PEX_ArrayAccess) - { - return ConvertArrayFunctionCall(fcall); - } break; default: diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e184ccaa1..b2f22555f 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2300,10 +2300,40 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case AST_ExprFuncCall: { auto fcall = static_cast(ast); - assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. - auto fname = static_cast(fcall->Function)->Identifier; - return new FxFunctionCall(fname, NAME_None, ConvertNodeList(fcall->Parameters), *ast); - //return ConvertFunctionCall(fcall->Function, ConvertNodeList(fcall->Parameters), ConvertClass, *ast); + + // function names can either be + // - plain identifiers + // - class members + // - array syntax for random() calls. + // Everything else coming here is a syntax error. + switch (fcall->Function->NodeType) + { + case AST_ExprID: + // The function name is a simple identifier. + return new FxFunctionCall(static_cast(fcall->Function)->Identifier, NAME_None, ConvertNodeList(fcall->Parameters), *ast); + + case AST_ExprMemberAccess: + // calling a class member through its pointer + // todo. + break; + + case AST_ExprBinary: + // Array syntax for randoms. They are internally stored as ExprBinary with both an identifier on the left and right side. + if (fcall->Function->Operation == PEX_ArrayAccess) + { + auto binary = static_cast(fcall->Function); + if (binary->Left->NodeType == AST_ExprID && binary->Right->NodeType == AST_ExprID) + { + return new FxFunctionCall(static_cast(binary->Left)->Identifier, static_cast(binary->Right)->Identifier, ConvertNodeList(fcall->Parameters), *ast); + } + } + // fall through if this isn't an array access node. + + default: + Error(fcall, "Invalid function identifier"); + return new FxNop(*ast); // return something so that the compiler can continue. + } + break; } case AST_FuncParm: @@ -2346,22 +2376,47 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } } - default: - // only for development. I_Error is more convenient here than a normal error. - I_Error("ConvertNode encountered unsupported node of type %d", ast->NodeType); - return nullptr; + case AST_ExprBinary: + { + auto binary = static_cast(ast); + auto left = ConvertNode(binary->Left); + auto right = ConvertNode(binary->Right); + auto op = binary->Operation; + switch (op) + { + case PEX_Add: + case PEX_Sub: + return new FxAddSub(op == PEX_Add ? '+' : '-', left, right); + + case PEX_Mul: + case PEX_Div: + case PEX_Mod: + return new FxMulDiv(op == PEX_Mul ? '*' : op == PEX_Div ? '/' : '%', left, right); + + default: + I_Error("Binary operator %d not implemented yet", op); + } + break; } + } + + // only for development. I_Error is more convenient here than a normal error. + I_Error("ConvertNode encountered unsupported node of type %d", ast->NodeType); + return nullptr; } FArgumentList *ZCCCompiler::ConvertNodeList(ZCC_TreeNode *head) { FArgumentList *list = new FArgumentList; - auto node = head; - do + if (head != nullptr) { - list->Push(ConvertNode(node)); - node = node->SiblingNext; - } while (node != head); + auto node = head; + do + { + list->Push(ConvertNode(node)); + node = node->SiblingNext; + } while (node != head); + } return list; } \ No newline at end of file From 2da52cedc960babe42ab17a04023b3265782e988 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 12:47:26 +0200 Subject: [PATCH 050/255] - restrict 8 and 16 bit integer types to struct and class members - and I am not really sure if they should even be allowed there, aside from legacy readonly properties. For 32 bit floats the same would hold, but those are already mapped to 64 bit doubles silently. ZDoom only uses these types in a very few isolated places, and even those can be removed without problems, so it's very doubtful that having support for these types is of any benefit - on the other hand, having them will most likely introduce more code than is saved in the data by using them... --- src/dobjtype.cpp | 2 + src/dobjtype.h | 1 + src/scripting/zscript/zcc_compile.cpp | 75 ++++++++++++++++++--------- src/scripting/zscript/zcc_compile.h | 2 +- 4 files changed, 54 insertions(+), 26 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 966663f12..b023a2693 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -727,6 +727,7 @@ PInt::PInt() PInt::PInt(unsigned int size, bool unsign) : PBasicType(size, size), Unsigned(unsign) { + MemberOnly = (size < 4); if (!unsign) { int maxval = (1 << ((8 * size) - 1)) - 1; @@ -1018,6 +1019,7 @@ PFloat::PFloat(unsigned int size) else { assert(size == 4); + MemberOnly = true; SetSingleSymbols(); } } diff --git a/src/dobjtype.h b/src/dobjtype.h index a5da177a4..885e1ea0e 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -221,6 +221,7 @@ public: unsigned int Align; // this type's preferred alignment PType *HashNext; // next type in this type table PSymbolTable Symbols; + bool MemberOnly = false; // type may only be used as a struct/class member but not as a local variable or function argument. PType(); PType(unsigned int size, unsigned int align); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index b2f22555f..f6d23a99b 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1205,7 +1205,7 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel { auto field = Fields[0]; - PType *fieldtype = DetermineType(type, field, field->Names->Name, field->Type, true); + PType *fieldtype = DetermineType(type, field, field->Names->Name, field->Type, true, true); // For structs only allow 'deprecated', for classes exclude function qualifiers. int notallowed = forstruct? ~ZCC_Deprecated : ZCC_Latent | ZCC_Final | ZCC_Action | ZCC_Static | ZCC_FuncConst | ZCC_Abstract; @@ -1290,8 +1290,9 @@ FString ZCCCompiler::FlagsToString(uint32_t flags) // //========================================================================== -PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName name, ZCC_Type *ztype, bool allowarraytypes) +PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName name, ZCC_Type *ztype, bool allowarraytypes, bool formember) { + PType *retval = TypeError; if (!allowarraytypes && ztype->ArraySize != nullptr) { Error(field, "%s: Array type not allowed", name.GetChars()); @@ -1305,26 +1306,33 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n switch (btype->Type) { case ZCC_SInt8: - return TypeSInt8; + retval = TypeSInt8; + break; case ZCC_UInt8: - return TypeUInt8; + retval = TypeUInt8; + break; case ZCC_SInt16: - return TypeSInt16; + retval = TypeSInt16; + break; case ZCC_UInt16: - return TypeUInt16; + retval = TypeUInt16; + break; case ZCC_SInt32: case ZCC_IntAuto: // todo: for enums, autoselect appropriately sized int - return TypeSInt32; + retval = TypeSInt32; + break; case ZCC_UInt32: - return TypeUInt32; + retval = TypeUInt32; + break; case ZCC_Bool: - return TypeBool; + retval = TypeBool; + break; // Do we really want to allow single precision floats, despite all the problems they cause? // These are nearly guaranteed to desync between MSVC and GCC on x87, because GCC does not implement an IEEE compliant mode @@ -1332,19 +1340,24 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n case ZCC_FloatAuto: //return TypeFloat32; case ZCC_Float64: - return TypeFloat64; + retval = TypeFloat64; + return; case ZCC_String: - return TypeString; + retval = TypeString; + break; case ZCC_Name: - return TypeName; + retval = TypeName; + break; case ZCC_Vector2: - return TypeVector2; + retval = TypeVector2; + break; case ZCC_Vector3: - return TypeVector3; + retval = TypeVector3; + break; case ZCC_Vector4: // This has almost no use, so we really shouldn't bother. @@ -1352,18 +1365,22 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n return TypeError; case ZCC_State: - return TypeState; + retval = TypeState; + break; case ZCC_Color: - return TypeColor; + retval = TypeColor; + break; case ZCC_Sound: - return TypeSound; + retval = TypeSound; + break; case ZCC_UserType: - return ResolveUserType(btype, &outertype->Symbols); + retval = ResolveUserType(btype, &outertype->Symbols); break; } + break; } case AST_MapType: @@ -1372,7 +1389,8 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n Error(field, "%s: Map types not implemented yet", name.GetChars()); // Todo: Decide what we allow here and if it makes sense to allow more complex constructs. auto mtype = static_cast(ztype); - return NewMap(DetermineType(outertype, field, name, mtype->KeyType, false), DetermineType(outertype, field, name, mtype->ValueType, false)); + retval = NewMap(DetermineType(outertype, field, name, mtype->KeyType, false, false), DetermineType(outertype, field, name, mtype->ValueType, false, false)); + break; } break; @@ -1381,7 +1399,8 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n { Error(field, "%s: Dynamic array types not implemented yet", name.GetChars()); auto atype = static_cast(ztype); - return NewDynArray(DetermineType(outertype, field, name, atype->ElementType, false)); + retval = NewDynArray(DetermineType(outertype, field, name, atype->ElementType, false, false)); + break; } break; @@ -1390,7 +1409,7 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n auto ctype = static_cast(ztype); if (ctype->Restriction == nullptr) { - return NewClassPointer(RUNTIME_CLASS(DObject)); + retval = NewClassPointer(RUNTIME_CLASS(DObject)); } else { @@ -1407,11 +1426,17 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n Error(field, "%s does not represent a class type", FName(ctype->Restriction->Id).GetChars()); return TypeError; } - return NewClassPointer(static_cast(typesym->Type)); + retval = NewClassPointer(static_cast(typesym->Type)); } + break; } } - return TypeError; + if (retval != TypeError && retval->MemberOnly && !formember) + { + Error(field, "Invalid type"); // fixme: Types need a descriptive name that can be output here. + return TypeError; + } + return retval; } //========================================================================== @@ -1900,7 +1925,7 @@ void ZCCCompiler::InitFunctions() { do { - auto type = DetermineType(c->Type(), f, f->Name, t, false); + auto type = DetermineType(c->Type(), f, f->Name, t, false, false); if (type->IsKindOf(RUNTIME_CLASS(PStruct))) { // structs and classes only get passed by pointer. @@ -1951,7 +1976,7 @@ void ZCCCompiler::InitFunctions() { if (p->Type != nullptr) { - auto type = DetermineType(c->Type(), p, f->Name, p->Type, false); + auto type = DetermineType(c->Type(), p, f->Name, p->Type, false, false); int flags; if (p->Flags & ZCC_In) flags |= VARF_In; if (p->Flags & ZCC_Out) flags |= VARF_Out; diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 7a0246ea1..cf2775834 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -95,7 +95,7 @@ private: void CompileAllFields(); bool CompileFields(PStruct *type, TArray &Fields, PClass *Outer, PSymbolTable *TreeNodes, bool forstruct); FString FlagsToString(uint32_t flags); - PType *DetermineType(PType *outertype, ZCC_TreeNode *field, FName name, ZCC_Type *ztype, bool allowarraytypes); + PType *DetermineType(PType *outertype, ZCC_TreeNode *field, FName name, ZCC_Type *ztype, bool allowarraytypes, bool formember); PType *ResolveArraySize(PType *baseType, ZCC_Expression *arraysize, PSymbolTable *sym); PType *ResolveUserType(ZCC_BasicType *type, PSymbolTable *sym); From afd9347087eb62e5c996247ab2da8291d7449ed3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 19:42:22 +0200 Subject: [PATCH 051/255] - changed order of script files to match the old DECORATE list for easy comparison of the disassembly. - added a descriptive name to all types for error messages. - added a generic type cast node to the code generator. - added a few more cast operations to the 'cast' VM instruction. - extended FxClassTypeCast to handle all possible input that can be cast to a class pointer, not just names. --- src/dobjtype.cpp | 47 ++ src/dobjtype.h | 11 +- src/scripting/codegeneration/codegen.cpp | 545 +++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 74 ++- src/scripting/decorate/thingdef_parse.cpp | 2 +- src/scripting/vm/vm.h | 6 + src/scripting/vm/vmdisasm.cpp | 6 + src/scripting/vm/vmexec.cpp | 2 + src/scripting/vm/vmexec.h | 33 ++ src/scripting/zscript/zcc_compile.cpp | 6 +- wadsrc/static/zscript.txt | 6 +- 11 files changed, 723 insertions(+), 15 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index b023a2693..3d42059ca 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -199,6 +199,7 @@ END_POINTERS PType::PType() : Size(0), Align(1), HashNext(NULL) { + mDescriptiveName = "Type"; } //========================================================================== @@ -210,6 +211,7 @@ PType::PType() PType::PType(unsigned int size, unsigned int align) : Size(size), Align(align), HashNext(NULL) { + mDescriptiveName = "Type"; } //========================================================================== @@ -533,6 +535,17 @@ void PType::GetTypeIDs(intptr_t &id1, intptr_t &id2) const id2 = 0; } +//========================================================================== +// +// PType :: GetTypeIDs +// +//========================================================================== + +const char *PType::DescriptiveName() const +{ + return mDescriptiveName.GetChars(); +} + //========================================================================== // // PType :: StaticInit STATIC @@ -649,6 +662,7 @@ PBasicType::PBasicType() PBasicType::PBasicType(unsigned int size, unsigned int align) : PType(size, align) { + mDescriptiveName = "BasicType"; } /* PCompoundType **********************************************************/ @@ -714,6 +728,7 @@ IMPLEMENT_CLASS(PInt) PInt::PInt() : PBasicType(4, 4), Unsigned(false) { + mDescriptiveName = "SInt32"; Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Min, this, -0x7FFFFFFF - 1)); Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Max, this, 0x7FFFFFFF)); } @@ -727,6 +742,8 @@ PInt::PInt() PInt::PInt(unsigned int size, bool unsign) : PBasicType(size, size), Unsigned(unsign) { + mDescriptiveName.Format("%cInt%d", unsign? 'U':'S', size); + MemberOnly = (size < 4); if (!unsign) { @@ -981,6 +998,8 @@ IMPLEMENT_CLASS(PBool) PBool::PBool() : PInt(sizeof(bool), true) { + mDescriptiveName = "Bool"; + MemberOnly = false; // Override the default max set by PInt's constructor PSymbolConstNumeric *maxsym = static_cast(Symbols.FindSymbol(NAME_Max, false)); assert(maxsym != NULL && maxsym->IsKindOf(RUNTIME_CLASS(PSymbolConstNumeric))); @@ -1000,6 +1019,7 @@ IMPLEMENT_CLASS(PFloat) PFloat::PFloat() : PBasicType(8, 8) { + mDescriptiveName = "Float"; SetDoubleSymbols(); } @@ -1012,6 +1032,7 @@ PFloat::PFloat() PFloat::PFloat(unsigned int size) : PBasicType(size, size) { + mDescriptiveName.Format("Float%d", size); if (size == 8) { SetDoubleSymbols(); @@ -1274,6 +1295,7 @@ IMPLEMENT_CLASS(PString) PString::PString() : PBasicType(sizeof(FString), __alignof(FString)) { + mDescriptiveName = "String"; } //========================================================================== @@ -1376,6 +1398,7 @@ IMPLEMENT_CLASS(PName) PName::PName() : PInt(sizeof(FName), true) { + mDescriptiveName = "Name"; assert(sizeof(FName) == __alignof(FName)); } @@ -1425,6 +1448,7 @@ IMPLEMENT_CLASS(PSound) PSound::PSound() : PInt(sizeof(FSoundID), true) { + mDescriptiveName = "Sound"; assert(sizeof(FSoundID) == __alignof(FSoundID)); } @@ -1474,6 +1498,7 @@ IMPLEMENT_CLASS(PColor) PColor::PColor() : PInt(sizeof(PalEntry), true) { + mDescriptiveName = "Color"; assert(sizeof(PalEntry) == __alignof(PalEntry)); } @@ -1490,6 +1515,7 @@ IMPLEMENT_CLASS(PStatePointer) PStatePointer::PStatePointer() : PBasicType(sizeof(FState *), __alignof(FState *)) { + mDescriptiveName = "State"; } //========================================================================== @@ -1564,6 +1590,7 @@ END_POINTERS PPointer::PPointer() : PBasicType(sizeof(void *), __alignof(void *)), PointedType(NULL) { + mDescriptiveName = "Pointer"; } //========================================================================== @@ -1575,6 +1602,7 @@ PPointer::PPointer() PPointer::PPointer(PType *pointsat) : PBasicType(sizeof(void *), __alignof(void *)), PointedType(pointsat) { + mDescriptiveName.Format("Pointer<%s>", pointsat->DescriptiveName()); } //========================================================================== @@ -1708,6 +1736,7 @@ END_POINTERS PClassPointer::PClassPointer() : PPointer(RUNTIME_CLASS(PClass)), ClassRestriction(NULL) { + mDescriptiveName = "ClassPointer"; } //========================================================================== @@ -1719,6 +1748,7 @@ PClassPointer::PClassPointer() PClassPointer::PClassPointer(PClass *restrict) : PPointer(RUNTIME_CLASS(PClass)), ClassRestriction(restrict) { + mDescriptiveName.Format("ClassPointer<%s>", restrict->TypeName.GetChars()); } //========================================================================== @@ -1784,6 +1814,7 @@ END_POINTERS PEnum::PEnum() : ValueType(NULL) { + mDescriptiveName = "Enum"; } //========================================================================== @@ -1795,6 +1826,7 @@ PEnum::PEnum() PEnum::PEnum(FName name, PTypeBase *outer) : PNamedType(name, outer), ValueType(NULL) { + mDescriptiveName.Format("Enum<%s>", name.GetChars()); } //========================================================================== @@ -1833,6 +1865,7 @@ END_POINTERS PArray::PArray() : ElementType(NULL), ElementCount(0) { + mDescriptiveName = "Array"; } //========================================================================== @@ -1844,6 +1877,8 @@ PArray::PArray() PArray::PArray(PType *etype, unsigned int ecount) : ElementType(etype), ElementCount(ecount) { + mDescriptiveName.Format("Array<%s>[%d]", etype->DescriptiveName(), ecount); + Align = etype->Align; // Since we are concatenating elements together, the element size should // also be padded to the nearest alignment. @@ -1975,6 +2010,7 @@ IMPLEMENT_CLASS(PVector) PVector::PVector() : PArray(TypeFloat32, 3) { + mDescriptiveName = "Vector"; } //========================================================================== @@ -1986,6 +2022,7 @@ PVector::PVector() PVector::PVector(unsigned int size) : PArray(TypeFloat32, size) { + mDescriptiveName.Format("Vector<%d>", size); assert(size >= 2 && size <= 4); } @@ -2025,6 +2062,7 @@ END_POINTERS PDynArray::PDynArray() : ElementType(NULL) { + mDescriptiveName = "DynArray"; Size = sizeof(FArray); Align = __alignof(FArray); } @@ -2038,6 +2076,7 @@ PDynArray::PDynArray() PDynArray::PDynArray(PType *etype) : ElementType(etype) { + mDescriptiveName.Format("DynArray<%s>", etype->DescriptiveName()); Size = sizeof(FArray); Align = __alignof(FArray); } @@ -2105,6 +2144,7 @@ END_POINTERS PMap::PMap() : KeyType(NULL), ValueType(NULL) { + mDescriptiveName = "Map"; Size = sizeof(FMap); Align = __alignof(FMap); } @@ -2118,6 +2158,7 @@ PMap::PMap() PMap::PMap(PType *keytype, PType *valtype) : KeyType(keytype), ValueType(valtype) { + mDescriptiveName.Format("Map<%s, %s>", keytype->DescriptiveName(), valtype->DescriptiveName()); Size = sizeof(FMap); Align = __alignof(FMap); } @@ -2181,6 +2222,7 @@ IMPLEMENT_CLASS(PStruct) PStruct::PStruct() { + mDescriptiveName = "Struct"; } //========================================================================== @@ -2192,6 +2234,7 @@ PStruct::PStruct() PStruct::PStruct(FName name, PTypeBase *outer) : PNamedType(name, outer) { + mDescriptiveName.Format("Struct<%s>", name.GetChars()); } //========================================================================== @@ -2804,6 +2847,7 @@ PClass::PClass() Defaults = NULL; bRuntimeClass = false; ConstructNative = NULL; + mDescriptiveName = "Class"; PClass::AllClasses.Push(this); } @@ -2896,6 +2940,7 @@ void ClassReg::SetupClass(PClass *cls) cls->Size = SizeOf; cls->Pointers = Pointers; cls->ConstructNative = ConstructNative; + cls->mDescriptiveName.Format("Class<%s>", cls->TypeName.GetChars()); } //========================================================================== @@ -3108,6 +3153,7 @@ PClass *PClass::CreateDerivedClass(FName name, unsigned int size) type->TypeName = name; type->Size = size; type->bRuntimeClass = true; + type->mDescriptiveName.Format("Class<%s>", name.GetChars()); Derive(type); DeriveData(type); if (!notnew) @@ -3185,6 +3231,7 @@ PClass *PClass::FindClassTentative(FName name, bool fatal) type->ConstructNative = ConstructNative; type->Size = TentativeClass; type->bRuntimeClass = true; + type->mDescriptiveName.Format("Class<%s>", name.GetChars()); type->Symbols.SetParentTable(&Symbols); TypeTable.AddType(type, RUNTIME_CLASS(PClass), (intptr_t)type->Outer, name, bucket); return type; diff --git a/src/dobjtype.h b/src/dobjtype.h index 885e1ea0e..fd6e078ea 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -222,6 +222,7 @@ public: PType *HashNext; // next type in this type table PSymbolTable Symbols; bool MemberOnly = false; // type may only be used as a struct/class member but not as a local variable or function argument. + FString mDescriptiveName; PType(); PType(unsigned int size, unsigned int align); @@ -285,6 +286,8 @@ public: // Get the type IDs used by IsMatch virtual void GetTypeIDs(intptr_t &id1, intptr_t &id2) const; + const char *DescriptiveName() const; + size_t PropagateMark(); static void StaticInit(); @@ -377,8 +380,12 @@ public: PTypeBase *Outer; // object this type is contained within FName TypeName; // this type's name - PNamedType() : Outer(NULL) {} - PNamedType(FName name, PTypeBase *outer) : Outer(outer), TypeName(name) {} + PNamedType() : Outer(NULL) { + mDescriptiveName = "NamedType"; + } + PNamedType(FName name, PTypeBase *outer) : Outer(outer), TypeName(name) { + mDescriptiveName = name.GetChars(); + } virtual bool IsMatch(intptr_t id1, intptr_t id2) const; virtual void GetTypeIDs(intptr_t &id1, intptr_t &id2) const; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 91153f3ac..9b8a87eed 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -595,9 +595,9 @@ ExpEmit FxIntCast::Emit(VMFunctionBuilder *build) //========================================================================== FxFloatCast::FxFloatCast(FxExpression *x) -: FxExpression(x->ScriptPosition) + : FxExpression(x->ScriptPosition) { - basex=x; + basex = x; ValueType = TypeFloat64; } @@ -685,6 +685,519 @@ ExpEmit FxFloatCast::Emit(VMFunctionBuilder *build) // //========================================================================== +FxNameCast::FxNameCast(FxExpression *x) + : FxExpression(x->ScriptPosition) +{ + basex = x; + ValueType = TypeName; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxNameCast::~FxNameCast() +{ + SAFE_DELETE(basex); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxNameCast::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(basex, ctx); + + if (basex->ValueType == TypeName) + { + FxExpression *x = basex; + basex = NULL; + delete this; + return x; + } + else if (basex->ValueType == TypeString) + { + if (basex->isConstant()) + { + ExpVal constval = static_cast(basex)->GetValue(); + FxExpression *x = new FxConstant(constval.GetName(), ScriptPosition); + delete this; + return x; + } + return this; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Cannot convert to name"); + delete this; + return NULL; + } +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxNameCast::Emit(VMFunctionBuilder *build) +{ + ExpEmit from = basex->Emit(build); + assert(!from.Konst); + assert(basex->ValueType == TypeString); + from.Free(build); + ExpEmit to(build, REGT_INT); + build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_S2N); + return to; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxStringCast::FxStringCast(FxExpression *x) + : FxExpression(x->ScriptPosition) +{ + basex = x; + ValueType = TypeString; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxStringCast::~FxStringCast() +{ + SAFE_DELETE(basex); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxStringCast::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(basex, ctx); + + if (basex->ValueType == TypeString) + { + FxExpression *x = basex; + basex = NULL; + delete this; + return x; + } + else if (basex->ValueType == TypeName) + { + if (basex->isConstant()) + { + ExpVal constval = static_cast(basex)->GetValue(); + FxExpression *x = new FxConstant(constval.GetString(), ScriptPosition); + delete this; + return x; + } + return this; + } + else if (basex->ValueType == TypeSound) + { + if (basex->isConstant()) + { + ExpVal constval = static_cast(basex)->GetValue(); + FxExpression *x = new FxConstant(S_sfx[constval.GetInt()].name, ScriptPosition); + delete this; + return x; + } + return this; + } + // although it could be done, let's not convert colors back to strings. + else + { + ScriptPosition.Message(MSG_ERROR, "Cannot convert to string"); + delete this; + return NULL; + } +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxStringCast::Emit(VMFunctionBuilder *build) +{ + ExpEmit from = basex->Emit(build); + assert(!from.Konst); + + from.Free(build); + ExpEmit to(build, REGT_STRING); + if (ValueType == TypeName) + { + build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_N2S); + } + else if (ValueType == TypeSound) + { + build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_So2S); + } + return to; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxColorCast::FxColorCast(FxExpression *x) + : FxExpression(x->ScriptPosition) +{ + basex = x; + ValueType = TypeColor; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxColorCast::~FxColorCast() +{ + SAFE_DELETE(basex); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxColorCast::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(basex, ctx); + + if (basex->ValueType == TypeColor || basex->ValueType->GetClass() == RUNTIME_CLASS(PInt)) + { + FxExpression *x = basex; + x->ValueType = TypeColor; + basex = NULL; + delete this; + return x; + } + else if (basex->ValueType == TypeString) + { + if (basex->isConstant()) + { + ExpVal constval = static_cast(basex)->GetValue(); + FxExpression *x = new FxConstant(V_GetColor(nullptr, constval.GetString()), ScriptPosition); + delete this; + return x; + } + return this; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Cannot convert to color"); + delete this; + return NULL; + } +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxColorCast::Emit(VMFunctionBuilder *build) +{ + ExpEmit from = basex->Emit(build); + assert(!from.Konst); + assert(basex->ValueType == TypeString); + from.Free(build); + ExpEmit to(build, REGT_INT); + build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_S2Co); + return to; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxSoundCast::FxSoundCast(FxExpression *x) + : FxExpression(x->ScriptPosition) +{ + basex = x; + ValueType = TypeSound; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxSoundCast::~FxSoundCast() +{ + SAFE_DELETE(basex); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxSoundCast::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(basex, ctx); + + if (basex->ValueType == TypeSound || basex->ValueType->GetClass() == RUNTIME_CLASS(PInt)) + { + FxExpression *x = basex; + x->ValueType = TypeSound; + basex = NULL; + delete this; + return x; + } + else if (basex->ValueType == TypeString) + { + if (basex->isConstant()) + { + ExpVal constval = static_cast(basex)->GetValue(); + FxExpression *x = new FxConstant(FSoundID(constval.GetString()), ScriptPosition); + delete this; + return x; + } + return this; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Cannot convert to sound"); + delete this; + return NULL; + } +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxSoundCast::Emit(VMFunctionBuilder *build) +{ + ExpEmit from = basex->Emit(build); + assert(!from.Konst); + assert(basex->ValueType == TypeString); + from.Free(build); + ExpEmit to(build, REGT_INT); + build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_S2So); + return to; +} + +//========================================================================== +// +// generic type cast operator +// +//========================================================================== + +FxTypeCast::FxTypeCast(FxExpression *x, PType *type, bool nowarn) + : FxExpression(x->ScriptPosition) +{ + basex = x; + ValueType = type; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxTypeCast::~FxTypeCast() +{ + SAFE_DELETE(basex); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(basex, ctx); + + // first deal with the simple types + if (ValueType == TypeError || basex->ValueType == TypeError) + { + delete this; + return nullptr; + } + else if (ValueType == TypeVoid) // this should never happen + { + goto errormsg; + } + else if (basex->ValueType == TypeVoid) + { + goto errormsg; + } + else if (basex->ValueType == ValueType) + { + // don't go through the entire list if the types are the same. + goto basereturn; + } + else if (ValueType->GetRegType() == REGT_FLOAT) + { + FxExpression *x = new FxFloatCast(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType->IsA(RUNTIME_CLASS(PInt))) + { + // This is only for casting to actual ints. Subtypes representing an int will be handled elsewhere. + FxExpression *x = new FxIntCast(basex, NoWarn); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType == TypeBool) + { + FxExpression *x = new FxBoolCast(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType == TypeString) + { + FxExpression *x = new FxStringCast(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType == TypeName) + { + FxExpression *x = new FxNameCast(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType == TypeSound) + { + FxExpression *x = new FxSoundCast(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType == TypeColor) + { + FxExpression *x = new FxColorCast(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else if (ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) + { + FxExpression *x = new FxClassTypeCast(static_cast(ValueType), basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + /* else if (ValueType->IsKindOf(RUNTIME_CLASS(PEnum))) + { + // this is not yet ready and does not get assigned to actual values. + } + */ + else if (ValueType->IsKindOf(RUNTIME_CLASS(PClass))) // this should never happen because the VM doesn't handle plain class types - just pointers + { + if (basex->ValueType->IsKindOf(RUNTIME_CLASS(PClass))) + { + // class types are only compatible if the base type is a descendant of the result type. + auto fromtype = static_cast(basex->ValueType); + auto totype = static_cast(ValueType); + if (fromtype->IsDescendantOf(totype)) goto basereturn; + } + } + else if (ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) + { + // Pointers to different types are only compatible if both point to an object and the source type is a child of the destination type. + if (basex->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) + { + auto fromtype = static_cast(basex->ValueType); + auto totype = static_cast(ValueType); + if (fromtype->PointedType->IsKindOf(RUNTIME_CLASS(PClass)) && totype->PointedType->IsKindOf(RUNTIME_CLASS(PClass))) + { + + auto fromcls = static_cast(fromtype->PointedType); + auto tocls = static_cast(totype->PointedType); + if (fromcls->IsDescendantOf(tocls)) goto basereturn; + } + } + } + // todo: pointers to class objects. + // All other types are only compatible to themselves and have already been handled above by the equality check. + // Anything that falls through here is not compatible and must print an error. + +errormsg: + ScriptPosition.Message(MSG_ERROR, "Cannot convert %s to %s", basex->ValueType->DescriptiveName(), ValueType->DescriptiveName()); + delete this; + return nullptr; + +basereturn: + auto x = basex; + basex = nullptr; + delete this; + return x; + +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxTypeCast::Emit(VMFunctionBuilder *build) +{ + assert(false); + // This should never be reached + return ExpEmit(); +} + +//========================================================================== +// +// +// +//========================================================================== + FxPlusSign::FxPlusSign(FxExpression *operand) : FxExpression(operand->ScriptPosition) { @@ -5030,10 +5543,11 @@ VMFunction *FxReturnStatement::GetDirectFunction() // //========================================================================== -FxClassTypeCast::FxClassTypeCast(PClass *dtype, FxExpression *x) +FxClassTypeCast::FxClassTypeCast(PClassPointer *dtype, FxExpression *x) : FxExpression(x->ScriptPosition) { - desttype = dtype; + ValueType = dtype; + desttype = dtype->ClassRestriction; basex=x; } @@ -5058,8 +5572,25 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); SAFE_RESOLVE(basex, ctx); + + if (basex->ValueType->GetClass() == RUNTIME_CLASS(PClassPointer)) + { + auto to = static_cast(ValueType); + auto from = static_cast(basex->ValueType); + if (from->ClassRestriction->IsDescendantOf(to->ClassRestriction)) + { + basex->ValueType = to; + auto x = basex; + basex = nullptr; + delete this; + return x; + } + ScriptPosition.Message(MSG_ERROR, "Cannot convert from %s to %s: Incompatible class types", from->ClassRestriction->TypeName.GetChars(), to->ClassRestriction->TypeName.GetChars()); + delete this; + return nullptr; + } - if (basex->ValueType != TypeName) + if (basex->ValueType != TypeName && basex->ValueType != TypeString) { ScriptPosition.Message(MSG_ERROR, "Cannot convert to class type"); delete this; @@ -5097,6 +5628,10 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) delete this; return x; } + if (basex->ValueType == TypeString) + { + basex = new FxNameCast(basex); + } return this; } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 213fe388a..7d6465e75 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -411,6 +411,78 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +class FxNameCast : public FxExpression +{ + FxExpression *basex; + +public: + + FxNameCast(FxExpression *x); + ~FxNameCast(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + +class FxStringCast : public FxExpression +{ + FxExpression *basex; + +public: + + FxStringCast(FxExpression *x); + ~FxStringCast(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + +class FxColorCast : public FxExpression +{ + FxExpression *basex; + +public: + + FxColorCast(FxExpression *x); + ~FxColorCast(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + +class FxSoundCast : public FxExpression +{ + FxExpression *basex; + +public: + + FxSoundCast(FxExpression *x); + ~FxSoundCast(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + +//========================================================================== +// +// FxTypeCast +// +//========================================================================== + +class FxTypeCast : public FxExpression +{ + FxExpression *basex; + bool NoWarn; + +public: + + FxTypeCast(FxExpression *x, PType *type, bool nowarn); + ~FxTypeCast(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxSign @@ -1130,7 +1202,7 @@ class FxClassTypeCast : public FxExpression public: - FxClassTypeCast(PClass *dtype, FxExpression *x); + FxClassTypeCast(PClassPointer *dtype, FxExpression *x); ~FxClassTypeCast(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index 534c74d18..f416d6103 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -207,7 +207,7 @@ FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool c sc.SetEscape(true); sc.MustGetString(); sc.SetEscape(false); - x = new FxClassTypeCast(static_cast(type)->ClassRestriction, new FxConstant(FName(sc.String), sc)); + x = new FxClassTypeCast(static_cast(type), new FxConstant(FName(sc.String), sc)); } else { diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 69e5b81b3..425eba531 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -116,6 +116,12 @@ enum CAST_P2S, CAST_S2I, CAST_S2F, + CAST_S2N, + CAST_N2S, + CAST_S2Co, + CAST_S2So, + CAST_Co2S, + CAST_So2S, }; // Register types for VMParam diff --git a/src/scripting/vm/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp index 0b84cf8c0..563f89f28 100644 --- a/src/scripting/vm/vmdisasm.cpp +++ b/src/scripting/vm/vmdisasm.cpp @@ -379,6 +379,9 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction case CAST_I2F: mode = MODE_AF | MODE_BI | MODE_CUNUSED; break; + case CAST_Co2S: + case CAST_So2S: + case CAST_N2S: case CAST_I2S: mode = MODE_AS | MODE_BI | MODE_CUNUSED; break; @@ -391,6 +394,9 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction case CAST_P2S: mode = MODE_AS | MODE_BP | MODE_CUNUSED; break; + case CAST_S2Co: + case CAST_S2So: + case CAST_S2N: case CAST_S2I: mode = MODE_AI | MODE_BS | MODE_CUNUSED; break; diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index 651090c6b..b1393382a 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -32,6 +32,8 @@ */ #include +#include +#include #include "vm.h" #include "xs_Float.h" #include "math/cmath.h" diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index adf2986c5..1d1764c6e 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1466,6 +1466,39 @@ static void DoCast(const VMRegisters ®, const VMFrame *f, int a, int b, int c reg.f[a] = reg.s[b].ToDouble(); break; + case CAST_S2N: + ASSERTD(a); ASSERTS(b); + reg.d[a] = FName(reg.s[b]); + break; + + case CAST_N2S: + { + ASSERTS(a); ASSERTD(b); + FName name = FName(ENamedName(reg.d[b])); + reg.s[a] = name.IsValidName() ? name.GetChars() : ""; + break; + } + + case CAST_S2Co: + ASSERTD(a); ASSERTS(b); + reg.d[a] = V_GetColor(NULL, reg.s[b]); + break; + + case CAST_Co2S: + ASSERTS(a); ASSERTD(b); + reg.s[a].Format("%02x %02x %02x", PalEntry(reg.d[b]).r, PalEntry(reg.d[b]).g, PalEntry(reg.d[b]).b); + break; + + case CAST_S2So: + ASSERTD(a); ASSERTS(b); + reg.d[a] = FSoundID(reg.s[b]); + break; + + case CAST_So2S: + ASSERTS(a); ASSERTD(b); + reg.s[a] = S_sfx[reg.d[b]].name; + break; + default: assert(0); } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f6d23a99b..1992587c8 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -885,7 +885,7 @@ ZCC_Expression *ZCCCompiler::SimplifyFunctionCall(ZCC_ExprFuncCall *callop, PSym if (routelen < 0) { ///FIXME: Need real type names - Error(callop, "Cannot convert type 1 to type 2"); + Error(callop, "Cannot convert %s to %s", parm->Value->Type->DescriptiveName(), dest->DescriptiveName()); callop->ToErrorNode(); } else @@ -1341,7 +1341,7 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n //return TypeFloat32; case ZCC_Float64: retval = TypeFloat64; - return; + break; case ZCC_String: retval = TypeString; @@ -1433,7 +1433,7 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n } if (retval != TypeError && retval->MemberOnly && !formember) { - Error(field, "Invalid type"); // fixme: Types need a descriptive name that can be output here. + Error(field, "Invalid type %s", retval->DescriptiveName()); // fixme: Types need a descriptive name that can be output here. return TypeError; } return retval; diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 73bb467d8..a349d7ed5 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -7,9 +7,7 @@ zscript/shared/morph.txt zscript/shared/botstuff.txt zscript/shared/sharedmisc.txt zscript/shared/blood.txt -zscript/shared/ice.txt zscript/shared/debris.txt -zscript/shared/specialspot.txt zscript/shared/decal.txt zscript/shared/splashes.txt zscript/shared/pickups.txt @@ -18,6 +16,7 @@ zscript/shared/spark.txt zscript/shared/soundsequence.txt zscript/shared/soundenvironment.txt zscript/shared/bridge.txt +zscript/shared/specialspot.txt zscript/shared/teleport.txt zscript/shared/camera.txt zscript/shared/movingcamera.txt @@ -28,6 +27,7 @@ zscript/shared/hatetarget.txt zscript/shared/secrettrigger.txt zscript/shared/setcolor.txt zscript/shared/sectoraction.txt +zscript/shared/ice.txt zscript/shared/dog.txt zscript/doom/doomplayer.txt @@ -59,5 +59,5 @@ zscript/doom/doomweapons.txt zscript/doom/stealthmonsters.txt zscript/doom/scriptedmarine.txt -//zscript/test1.txt +zscript/heretic/beast.txt From 6650e2bbfb9ff35e11b95d0caa47e3ac075ce4ed Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 16 Oct 2016 22:32:52 +0200 Subject: [PATCH 052/255] - converted some Heretic stuff to ZScript for testing. - added type casts to the arguments of function calls. - added string constant to state conversion to FxTypeCast. --- src/dobjtype.cpp | 3 +- src/scripting/codegeneration/codegen.cpp | 59 ++-- src/scripting/codegeneration/codegen.h | 6 +- wadsrc/static/actors/heretic/hereticammo.txt | 204 ------------ wadsrc/static/actors/heretic/hereticarmor.txt | 35 -- .../actors/heretic/hereticartifacts.txt | 103 ------ .../actors/heretic/hereticdecorations.txt | 248 -------------- wadsrc/static/actors/heretic/heretickeys.txt | 144 --------- wadsrc/static/actors/heretic/hereticmisc.txt | 229 ------------- .../static/actors/heretic/hereticplayer.txt | 129 -------- wadsrc/static/decorate.txt | 14 +- wadsrc/static/zscript.txt | 19 ++ wadsrc/static/zscript/doom/doomimp.txt | 3 +- wadsrc/static/zscript/heretic/beast.txt | 118 +++++++ wadsrc/static/zscript/heretic/hereticammo.txt | 243 ++++++++++++++ .../static/zscript/heretic/hereticarmor.txt | 41 +++ .../zscript/heretic/hereticartifacts.txt | 118 +++++++ .../zscript/heretic/hereticdecorations.txt | 302 ++++++++++++++++++ wadsrc/static/zscript/heretic/heretickeys.txt | 174 ++++++++++ wadsrc/static/zscript/heretic/hereticmisc.txt | 255 +++++++++++++++ .../static/zscript/heretic/hereticplayer.txt | 135 ++++++++ 21 files changed, 1438 insertions(+), 1144 deletions(-) delete mode 100644 wadsrc/static/actors/heretic/hereticammo.txt delete mode 100644 wadsrc/static/actors/heretic/hereticarmor.txt delete mode 100644 wadsrc/static/actors/heretic/hereticartifacts.txt delete mode 100644 wadsrc/static/actors/heretic/hereticdecorations.txt delete mode 100644 wadsrc/static/actors/heretic/heretickeys.txt delete mode 100644 wadsrc/static/actors/heretic/hereticmisc.txt delete mode 100644 wadsrc/static/actors/heretic/hereticplayer.txt create mode 100644 wadsrc/static/zscript/heretic/beast.txt create mode 100644 wadsrc/static/zscript/heretic/hereticammo.txt create mode 100644 wadsrc/static/zscript/heretic/hereticarmor.txt create mode 100644 wadsrc/static/zscript/heretic/hereticartifacts.txt create mode 100644 wadsrc/static/zscript/heretic/hereticdecorations.txt create mode 100644 wadsrc/static/zscript/heretic/heretickeys.txt create mode 100644 wadsrc/static/zscript/heretic/hereticmisc.txt create mode 100644 wadsrc/static/zscript/heretic/hereticplayer.txt diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 3d42059ca..317694e20 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -1748,7 +1748,8 @@ PClassPointer::PClassPointer() PClassPointer::PClassPointer(PClass *restrict) : PPointer(RUNTIME_CLASS(PClass)), ClassRestriction(restrict) { - mDescriptiveName.Format("ClassPointer<%s>", restrict->TypeName.GetChars()); + if (restrict) mDescriptiveName.Format("ClassPointer<%s>", restrict->TypeName.GetChars()); + else mDescriptiveName = "ClassPointer"; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9b8a87eed..d7a3a56b0 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1123,6 +1123,18 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) delete this; return x; } + else if (ValueType == TypeState) + { + // Right now this only supports string constants. There should be an option to pass a string variable, too. + if (basex->isConstant() && (basex->ValueType == TypeString || basex->ValueType == TypeName)) + { + FxExpression *x = new FxMultiNameState(static_cast(basex)->GetValue().GetString(), basex->ScriptPosition); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + } else if (ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) { FxExpression *x = new FxClassTypeCast(static_cast(ValueType), basex); @@ -4624,45 +4636,10 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) { for (unsigned i = 0; i < ArgList->Size(); i++) { - if ((*ArgList)[i]->isConstant()) - { - if (i + implicit < argtypes.Size()) - { - auto type = static_cast((*ArgList)[i])->ValueType; - // temporary hack to add the casts which get used by the internal definitions - if (argtypes[i + implicit] == TypeState && type == TypeString) - { - ScriptPosition.Message(MSG_WARNING, "Converting %s to state", static_cast((*ArgList)[i])->GetValue().GetString()); - auto statenode = new FxMultiNameState(static_cast((*ArgList)[i])->GetValue().GetString(), ScriptPosition); - delete (*ArgList)[i]; - (*ArgList)[i] = statenode; - } - if (argtypes[i + implicit] == TypeSound && type == TypeString) - { - ScriptPosition.Message(MSG_WARNING, "Converting %s to sound", static_cast((*ArgList)[i])->GetValue().GetString()); - auto statenode = new FxConstant(FSoundID(static_cast((*ArgList)[i])->GetValue().GetString()), ScriptPosition); - delete (*ArgList)[i]; - (*ArgList)[i] = statenode; - } - if (argtypes[i + implicit] == TypeSInt32 && type == TypeFloat64) - { - ScriptPosition.Message(MSG_WARNING, "Converting %f to int", static_cast((*ArgList)[i])->GetValue().GetFloat()); - auto statenode = new FxConstant(static_cast((*ArgList)[i])->GetValue().GetInt(), ScriptPosition); - delete (*ArgList)[i]; - (*ArgList)[i] = statenode; - } - if (argtypes[i + implicit] == TypeFloat64 && type == TypeSInt32) - { - ScriptPosition.Message(MSG_WARNING, "Converting %d to float", static_cast((*ArgList)[i])->GetValue().GetInt()); - auto statenode = new FxConstant(static_cast((*ArgList)[i])->GetValue().GetFloat(), ScriptPosition); - delete (*ArgList)[i]; - (*ArgList)[i] = statenode; - } - } - } - - (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); - if ((*ArgList)[i] == NULL) failed = true; + FxExpression *x = new FxTypeCast((*ArgList)[i], argtypes[i + implicit], false); + x = x->Resolve(ctx); + failed |= (x == nullptr); + (*ArgList)[i] = x; } } if (failed) @@ -5592,7 +5569,7 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) if (basex->ValueType != TypeName && basex->ValueType != TypeString) { - ScriptPosition.Message(MSG_ERROR, "Cannot convert to class type"); + ScriptPosition.Message(MSG_ERROR, "Cannot convert %s to class type", basex->ValueType->DescriptiveName()); delete this; return NULL; } @@ -5855,7 +5832,7 @@ FxMultiNameState::FxMultiNameState(const char *_statestring, const FScriptPositi } else { - scopename = NULL; + scopename = NAME_None; } names = MakeStateNameList(statestring); names.Insert(0, scopename); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 7d6465e75..ce4f11bb1 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -174,6 +174,7 @@ struct ExpVal FName GetName() const { + if (Type == TypeString) return FName(*(FString *)&pointer); return Type == TypeName ? ENamedName(Int) : NAME_None; } }; @@ -338,8 +339,9 @@ public: FxConstant(PClass *val, const FScriptPosition &pos) : FxExpression(pos) { value.pointer = (void*)val; - ValueType = val; - value.Type = NewClassPointer(RUNTIME_CLASS(AActor)); + if (val != nullptr) ValueType = NewClassPointer(val); + else ValueType = NewClassPointer(RUNTIME_CLASS(DObject)); + value.Type = NewClassPointer(RUNTIME_CLASS(DObject)); isresolved = true; } diff --git a/wadsrc/static/actors/heretic/hereticammo.txt b/wadsrc/static/actors/heretic/hereticammo.txt deleted file mode 100644 index 35f404274..000000000 --- a/wadsrc/static/actors/heretic/hereticammo.txt +++ /dev/null @@ -1,204 +0,0 @@ - -// Wimpy ammo --------------------------------------------------------------- - -ACTOR GoldWandAmmo : Ammo -{ - Inventory.PickupMessage "$TXT_AMMOGOLDWAND1" - Inventory.Amount 10 - Inventory.MaxAmount 100 - Ammo.BackpackAmount 10 - Ammo.BackpackMaxAmount 200 - Inventory.Icon "INAMGLD" - States - { - Spawn: - AMG1 A -1 - Stop - } -} - -// Hefty ammo --------------------------------------------------------------- - -ACTOR GoldWandHefty : GoldWandAmmo -{ - Inventory.PickupMessage "$TXT_AMMOGOLDWAND2" - Inventory.Amount 50 - States - { - Spawn: - AMG2 ABC 4 - Loop - } -} -// Wimpy ammo --------------------------------------------------------------- - -ACTOR CrossbowAmmo : Ammo -{ - Inventory.PickupMessage "$TXT_AMMOCROSSBOW1" - Inventory.Amount 5 - Inventory.MaxAmount 50 - Ammo.BackpackAmount 5 - Ammo.BackpackMaxAmount 100 - Inventory.Icon "INAMBOW" - States - { - Spawn: - AMC1 A -1 - Stop - } -} - -// Hefty ammo --------------------------------------------------------------- - -ACTOR CrossbowHefty : CrossbowAmmo -{ - Inventory.PickupMessage "$TXT_AMMOCROSSBOW2" - Inventory.Amount 20 - States - { - Spawn: - AMC2 ABC 5 - Loop - } -} -// Wimpy ammo --------------------------------------------------------------- - -ACTOR MaceAmmo : Ammo -{ - Inventory.PickupMessage "$TXT_AMMOMACE1" - Inventory.Amount 20 - Inventory.MaxAmount 150 - Ammo.BackpackAmount 20 - Ammo.BackpackMaxAmount 300 - Inventory.Icon "INAMLOB" - States - { - Spawn: - AMM1 A -1 - Stop - } -} - -// Hefty ammo --------------------------------------------------------------- - -ACTOR MaceHefty : MaceAmmo -{ - Inventory.PickupMessage "$TXT_AMMOMACE2" - Inventory.Amount 100 - States - { - Spawn: - AMM2 A -1 - Stop - } -} - -// Wimpy ammo --------------------------------------------------------------- - -ACTOR BlasterAmmo : Ammo -{ - Inventory.PickupMessage "$TXT_AMMOBLASTER1" - Inventory.Amount 10 - Inventory.MaxAmount 200 - Ammo.BackpackAmount 10 - Ammo.BackpackMaxAmount 400 - Inventory.Icon "INAMBST" - States - { - Spawn: - AMB1 ABC 4 - Loop - } -} - -// Hefty ammo --------------------------------------------------------------- - -ACTOR BlasterHefty : BlasterAmmo -{ - Inventory.PickupMessage "$TXT_AMMOBLASTER2" - Inventory.Amount 25 - States - { - Spawn: - AMB2 ABC 4 - Loop - } -} - -// Wimpy ammo --------------------------------------------------------------- - -ACTOR SkullRodAmmo : Ammo -{ - Inventory.PickupMessage "$TXT_AMMOSKULLROD1" - Inventory.Amount 20 - Inventory.MaxAmount 200 - Ammo.BackpackAmount 20 - Ammo.BackpackMaxAmount 400 - Inventory.Icon "INAMRAM" - States - { - Spawn: - AMS1 AB 5 - Loop - } -} - -// Hefty ammo --------------------------------------------------------------- - -ACTOR SkullRodHefty : SkullRodAmmo -{ - Inventory.PickupMessage "$TXT_AMMOSKULLROD2" - Inventory.Amount 100 - States - { - Spawn: - AMS2 AB 5 - Loop - } -} - -// Wimpy ammo --------------------------------------------------------------- - -ACTOR PhoenixRodAmmo : Ammo -{ - Inventory.PickupMessage "$TXT_AMMOPHOENIXROD1" - Inventory.Amount 1 - Inventory.MaxAmount 20 - Ammo.BackpackAmount 1 - Ammo.BackpackMaxAmount 40 - Inventory.Icon "INAMPNX" - States - { - Spawn: - AMP1 ABC 4 - Loop - } -} -// Hefty ammo --------------------------------------------------------------- - -ACTOR PhoenixRodHefty : PhoenixRodAmmo -{ - Inventory.PickupMessage "$TXT_AMMOPHOENIXROD2" - Inventory.Amount 10 - States - { - Spawn: - AMP2 ABC 4 - Loop - } -} - -// --- Bag of holding ------------------------------------------------------- - -ACTOR BagOfHolding : BackpackItem -{ - Inventory.PickupMessage "$TXT_ITEMBAGOFHOLDING" - +COUNTITEM - +FLOATBOB - States - { - Spawn: - BAGH A -1 - Stop - } -} diff --git a/wadsrc/static/actors/heretic/hereticarmor.txt b/wadsrc/static/actors/heretic/hereticarmor.txt deleted file mode 100644 index 91684cc0e..000000000 --- a/wadsrc/static/actors/heretic/hereticarmor.txt +++ /dev/null @@ -1,35 +0,0 @@ - -// Silver Shield (Shield1) -------------------------------------------------- - -Actor SilverShield : BasicArmorPickup -{ - +FLOATBOB - Inventory.Pickupmessage "$TXT_ITEMSHIELD1" - Inventory.Icon "SHLDA0" - Armor.Savepercent 50 - Armor.Saveamount 100 - States - { - Spawn: - SHLD A -1 - stop - } -} - -// Enchanted shield (Shield2) ----------------------------------------------- - -Actor EnchantedShield : BasicArmorPickup -{ - +FLOATBOB - Inventory.Pickupmessage "$TXT_ITEMSHIELD2" - Inventory.Icon "SHD2A0" - Armor.Savepercent 75 - Armor.Saveamount 200 - States - { - Spawn: - SHD2 A -1 - stop - } -} - diff --git a/wadsrc/static/actors/heretic/hereticartifacts.txt b/wadsrc/static/actors/heretic/hereticartifacts.txt deleted file mode 100644 index 9555415fd..000000000 --- a/wadsrc/static/actors/heretic/hereticartifacts.txt +++ /dev/null @@ -1,103 +0,0 @@ -// Super map ---------------------------------------------------------------- - -ACTOR SuperMap : MapRevealer -{ - +COUNTITEM - +INVENTORY.ALWAYSPICKUP - +FLOATBOB - Inventory.MaxAmount 0 - Inventory.PickupMessage "$TXT_ITEMSUPERMAP" - States - { - Spawn: - SPMP A -1 - Stop - } -} - - -// Invisibility ------------------------------------------------------------- - -ACTOR ArtiInvisibility : PowerupGiver -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - RenderStyle Translucent - Alpha 0.4 - Inventory.RespawnTics 4230 - Inventory.Icon ARTIINVS - Powerup.Type Ghost - Inventory.PickupMessage "$TXT_ARTIINVISIBILITY" - Tag "$TAG_ARTIINVISIBILITY" - States - { - Spawn: - INVS A 350 Bright - Loop - } -} - - -// Tome of power ------------------------------------------------------------ - -ACTOR ArtiTomeOfPower : PowerupGiver native -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - Inventory.Icon "ARTIPWBK" - Powerup.Type Weaponlevel2 - Inventory.PickupMessage "$TXT_ARTITOMEOFPOWER" - Tag "$TAG_ARTITOMEOFPOWER" - States - { - Spawn: - PWBK A 350 - Loop - } -} - - -// Time bomb ---------------------------------------------------------------- - -ACTOR ActivatedTimeBomb -{ - +NOGRAVITY - RenderStyle Translucent - Alpha 0.4 - DeathSound "misc/timebomb" - - action native A_Timebomb(); - - States - { - Spawn: - FBMB ABCD 10 - FBMB E 6 A_Scream - XPL1 A 4 BRIGHT A_Timebomb - XPL1 BCDEF 4 BRIGHT - Stop - } -} - - -ACTOR ArtiTimeBomb : Inventory native -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - +INVENTORY.INVBAR - +INVENTORY.FANCYPICKUPSOUND - Inventory.Icon "ARTIFBMB" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIFIREBOMB" - Tag "$TAG_ARTIFIREBOMB" - Inventory.DefMaxAmount - States - { - Spawn: - FBMB E 350 - Loop - } -} diff --git a/wadsrc/static/actors/heretic/hereticdecorations.txt b/wadsrc/static/actors/heretic/hereticdecorations.txt deleted file mode 100644 index 032ee33a1..000000000 --- a/wadsrc/static/actors/heretic/hereticdecorations.txt +++ /dev/null @@ -1,248 +0,0 @@ -ACTOR SkullHang70 -{ - Radius 20 - Height 70 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SKH1 A -1 - Stop - } -} - -ACTOR SkullHang60 -{ - Radius 20 - Height 60 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SKH2 A -1 - Stop - } -} - -ACTOR SkullHang45 -{ - Radius 20 - Height 45 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SKH3 A -1 - Stop - } -} - -ACTOR SkullHang35 -{ - Radius 20 - Height 35 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SKH4 A -1 - Stop - } -} - -ACTOR Chandelier -{ - Radius 20 - Height 60 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - CHDL ABC 4 - Loop - } -} - -ACTOR SerpentTorch -{ - Radius 12 - Height 54 - +SOLID - States - { - Spawn: - SRTC ABC 4 - Loop - } -} - -ACTOR SmallPillar -{ - Radius 16 - Height 34 - +SOLID - States - { - Spawn: - SMPL A -1 - Stop - } -} - -ACTOR StalagmiteSmall -{ - Radius 8 - Height 32 - +SOLID - States - { - Spawn: - STGS A -1 - Stop - } -} - -ACTOR StalagmiteLarge -{ - Radius 12 - Height 64 - +SOLID - States - { - Spawn: - STGL A -1 - Stop - } -} - -ACTOR StalactiteSmall -{ - Radius 8 - Height 36 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - STCS A -1 - Stop - } -} - -ACTOR StalactiteLarge -{ - Radius 12 - Height 68 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - STCL A -1 - Stop - } -} - -ACTOR FireBrazier -{ - Radius 16 - Height 44 - +SOLID - States - { - Spawn: - KFR1 ABCDEFGH 3 Bright - Loop - } -} - -ACTOR Barrel -{ - Radius 12 - Height 32 - +SOLID - States - { - Spawn: - BARL A -1 - Stop - } -} - -ACTOR BrownPillar -{ - Radius 14 - Height 128 - +SOLID - States - { - Spawn: - BRPL A -1 - Stop - } -} - -ACTOR Moss1 -{ - Radius 20 - Height 23 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - MOS1 A -1 - Stop - } -} - -ACTOR Moss2 -{ - Radius 20 - Height 27 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - MOS2 A -1 - Stop - } -} - -ACTOR WallTorch -{ - Radius 6 - Height 16 - +NOGRAVITY - +FIXMAPTHINGPOS - States - { - Spawn: - WTRH ABC 6 Bright - Loop - } -} - -ACTOR HangingCorpse -{ - Radius 8 - Height 104 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - HCOR A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/heretickeys.txt b/wadsrc/static/actors/heretic/heretickeys.txt deleted file mode 100644 index 1bda24dcc..000000000 --- a/wadsrc/static/actors/heretic/heretickeys.txt +++ /dev/null @@ -1,144 +0,0 @@ - -ACTOR HereticKey : Key -{ - +NOTDMATCH - Radius 20 - Height 16 -} - -// Green key ------------------------------------------------------------ - -ACTOR KeyGreen : HereticKey -{ - Inventory.PickupMessage "$TXT_GOTGREENKEY" - Inventory.Icon "GKEYICON" - States - { - Spawn: - AKYY ABCDEFGHIJ 3 Bright - Loop - } -} - -// Blue key ----------------------------------------------------------------- - -ACTOR KeyBlue : HereticKey -{ - Inventory.PickupMessage "$TXT_GOTBLUEKEY" - Inventory.Icon "BKEYICON" - States - { - Spawn: - BKYY ABCDEFGHIJ 3 Bright - Loop - } -} - -// Yellow key --------------------------------------------------------------- - -ACTOR KeyYellow : HereticKey -{ - Inventory.PickupMessage "$TXT_GOTYELLOWKEY" - Inventory.Icon "YKEYICON" - States - { - Spawn: - CKYY ABCDEFGHI 3 Bright - Loop - } -} - - -// --- Blue Key gizmo ----------------------------------------------------------- - -ACTOR KeyGizmoBlue -{ - Radius 16 - Height 50 - +SOLID - States - { - Spawn: - KGZ1 A 1 - KGZ1 A 1 A_SpawnItemEx("KeyGizmoFloatBlue", 0, 0, 60) - KGZ1 A -1 - Stop - } -} - -ACTOR KeyGizmoFloatBlue -{ - Radius 16 - Height 16 - +SOLID - +NOGRAVITY - States - { - Spawn: - KGZB A -1 Bright - Stop - } -} - -// --- Green Key gizmo ----------------------------------------------------------- - -ACTOR KeyGizmoGreen -{ - Radius 16 - Height 50 - +SOLID - States - { - Spawn: - KGZ1 A 1 - KGZ1 A 1 A_SpawnItemEx("KeyGizmoFloatGreen", 0, 0, 60) - KGZ1 A -1 - Stop - } -} - -ACTOR KeyGizmoFloatGreen -{ - Radius 16 - Height 16 - +SOLID - +NOGRAVITY - States - { - Spawn: - KGZG A -1 Bright - Stop - } -} - -// --- Yellow Key gizmo ----------------------------------------------------------- - -ACTOR KeyGizmoYellow -{ - Radius 16 - Height 50 - +SOLID - States - { - Spawn: - KGZ1 A 1 - KGZ1 A 1 A_SpawnItemEx("KeyGizmoFloatYellow", 0, 0, 60) - KGZ1 A -1 - Stop - } -} - -ACTOR KeyGizmoFloatYellow -{ - Radius 16 - Height 16 - +SOLID - +NOGRAVITY - States - { - Spawn: - KGZY A -1 Bright - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/hereticmisc.txt b/wadsrc/static/actors/heretic/hereticmisc.txt deleted file mode 100644 index 9b000ede3..000000000 --- a/wadsrc/static/actors/heretic/hereticmisc.txt +++ /dev/null @@ -1,229 +0,0 @@ - -// Pod ---------------------------------------------------------------------- - -ACTOR Pod -{ - Health 45 - Radius 16 - Height 54 - Painchance 255 - +SOLID +NOBLOOD +SHOOTABLE +DROPOFF - +WINDTHRUST +PUSHABLE +SLIDESONWALLS - +CANPASS +TELESTOMP +DONTMORPH - +NOBLOCKMONST +DONTGIB +OLDRADIUSDMG - DeathSound "world/podexplode" - PushFactor 0.5 - - action native A_PodPain (class podtype = "PodGoo"); - action native A_RemovePod (); - - States - { - Spawn: - PPOD A 10 - Loop - Pain: - PPOD B 14 A_PodPain - Goto Spawn - Death: - PPOD C 5 BRIGHT A_RemovePod - PPOD D 5 BRIGHT A_Scream - PPOD E 5 BRIGHT A_Explode - PPOD F 10 BRIGHT - Stop - Grow: - PPOD IJKLMNOP 3 - Goto Spawn - } -} - - -// Pod goo (falls from pod when damaged) ------------------------------------ - -ACTOR PodGoo -{ - Radius 2 - Height 4 - Gravity 0.125 - +NOBLOCKMAP +MISSILE +DROPOFF - +NOTELEPORT +CANNOTPUSH - States - { - Spawn: - PPOD GH 8 - Loop - Death: - PPOD G 10 - Stop - } -} - -// Pod generator ------------------------------------------------------------ - -ACTOR PodGenerator -{ - +NOBLOCKMAP - +NOSECTOR - +DONTSPLASH - AttackSound "world/podgrow" - - action native A_MakePod (class podtype = "Pod"); - - States - { - Spawn: - TNT1 A 35 A_MakePod - Loop - } -} - - -// Teleglitter generator 1 -------------------------------------------------- - -ACTOR TeleGlitterGenerator1 -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - +MOVEWITHSECTOR - States - { - Spawn: - TNT1 A 8 A_SpawnItemEx("TeleGlitter1", random[TeleGlitter](0,31)-16, random[TeleGlitter](0,31)-16, 0, 0,0,0.25) - Loop - } -} - -// Teleglitter generator 2 -------------------------------------------------- - -ACTOR TeleGlitterGenerator2 -{ - +NOBLOCKMAP - +NOGRAVITY - +DONTSPLASH - +MOVEWITHSECTOR - States - { - Spawn: - TNT1 A 8 A_SpawnItemEx("TeleGlitter2", random[TeleGlitter2](0,31)-16, random[TeleGlitter2](0,31)-16, 0, 0,0,0.25) - Loop - } -} - - -// Teleglitter 1 ------------------------------------------------------------ - -ACTOR TeleGlitter1 -{ - +NOBLOCKMAP +NOGRAVITY +MISSILE - RenderStyle Add - Damage 0 - - action native A_AccTeleGlitter (); - - States - { - Spawn: - TGLT A 2 BRIGHT - TGLT B 2 BRIGHT A_AccTeleGlitter - TGLT C 2 BRIGHT - TGLT D 2 BRIGHT A_AccTeleGlitter - TGLT E 2 BRIGHT - Loop - } -} - -// Teleglitter 2 ------------------------------------------------------------ - -ACTOR TeleGlitter2 : TeleGlitter1 -{ - States - { - Spawn: - TGLT F 2 BRIGHT - TGLT G 2 BRIGHT A_AccTeleGlitter - TGLT H 2 BRIGHT - TGLT I 2 BRIGHT A_AccTeleGlitter - TGLT J 2 BRIGHT - Loop - } -} - - -// --- Volcano -------------------------------------------------------------- - -ACTOR Volcano -{ - Radius 12 - Height 20 - +SOLID - - action native A_VolcanoSet (); - action native A_VolcanoBlast (); - - States - { - Spawn: - VLCO A 350 - VLCO A 35 A_VolcanoSet - VLCO BCDBCD 3 - VLCO E 10 A_VolcanoBlast - Goto Spawn+1 - } - -} - -// Volcano blast ------------------------------------------------------------ - -ACTOR VolcanoBlast -{ - Radius 8 - Height 8 - Speed 2 - Damage 2 - DamageType Fire - Gravity 0.125 - +NOBLOCKMAP +MISSILE +DROPOFF - +NOTELEPORT - DeathSound "world/volcano/blast" - - action native A_VolcBallImpact (); - - States - { - Spawn: - VFBL AB 4 BRIGHT A_SpawnItemEx("Puffy", random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, - 0,0,0,0,SXF_ABSOLUTEPOSITION, 64) - Loop - - Death: - XPL1 A 4 BRIGHT A_VolcBallImpact - XPL1 BCDEF 4 BRIGHT - Stop - } -} - -// Volcano T Blast ---------------------------------------------------------- - -ACTOR VolcanoTBlast -{ - Radius 8 - Height 6 - Speed 2 - Damage 1 - DamageType Fire - Gravity 0.125 - +NOBLOCKMAP +MISSILE +DROPOFF - +NOTELEPORT - States - { - Spawn: - VTFB AB 4 BRIGHT - Loop - Death: - SFFI CBABCDE 4 BRIGHT - Stop - } -} - - diff --git a/wadsrc/static/actors/heretic/hereticplayer.txt b/wadsrc/static/actors/heretic/hereticplayer.txt deleted file mode 100644 index 5a3e43772..000000000 --- a/wadsrc/static/actors/heretic/hereticplayer.txt +++ /dev/null @@ -1,129 +0,0 @@ -ACTOR HereticPlayer : PlayerPawn -{ - Health 100 - Radius 16 - Height 56 - Mass 100 - Painchance 255 - Speed 1 - Player.DisplayName "Corvus" - Player.StartItem "GoldWand" - Player.StartItem "Staff" - Player.StartItem "GoldWandAmmo", 50 - Player.WeaponSlot 1, Staff, Gauntlets - Player.WeaponSlot 2, GoldWand - Player.WeaponSlot 3, Crossbow - Player.WeaponSlot 4, Blaster - Player.WeaponSlot 5, SkullRod - Player.WeaponSlot 6, PhoenixRod - Player.WeaponSlot 7, Mace - - Player.ColorRange 225, 240 - Player.Colorset 0, "Green", 225, 240, 238 - Player.Colorset 1, "Yellow", 114, 129, 127 - Player.Colorset 2, "Red", 145, 160, 158 - Player.Colorset 3, "Blue", 190, 205, 203 - // Doom Legacy additions - Player.Colorset 4, "Brown", 67, 82, 80 - Player.Colorset 5, "Light Gray", 9, 24, 22 - Player.Colorset 6, "Light Brown", 74, 89, 87 - Player.Colorset 7, "Light Red", 150, 165, 163 - Player.Colorset 8, "Light Blue", 192, 207, 205 - Player.Colorset 9, "Beige", 95, 110, 108 - - States - { - Spawn: - PLAY A -1 - Stop - See: - PLAY ABCD 4 - Loop - Melee: - Missile: - PLAY F 6 BRIGHT - PLAY E 12 - Goto Spawn - Pain: - PLAY G 4 - PLAY G 4 A_Pain - Goto Spawn - Death: - PLAY H 6 A_PlayerSkinCheck("AltSkinDeath") - PLAY I 6 A_PlayerScream - PLAY JK 6 - PLAY L 6 A_NoBlocking - PLAY MNO 6 - PLAY P -1 - Stop - XDeath: - PLAY Q 0 A_PlayerSkinCheck("AltSkinXDeath") - PLAY Q 5 A_PlayerScream - PLAY R 0 A_NoBlocking - PLAY R 5 A_SkullPop - PLAY STUVWX 5 - PLAY Y -1 - Stop - Burn: - FDTH A 5 BRIGHT A_PlaySound("*burndeath") - FDTH B 4 BRIGHT - FDTH C 5 BRIGHT - FDTH D 4 BRIGHT A_PlayerScream - FDTH E 5 BRIGHT - FDTH F 4 BRIGHT - FDTH G 5 BRIGHT A_PlaySound("*burndeath") - FDTH H 4 BRIGHT - FDTH I 5 BRIGHT - FDTH J 4 BRIGHT - FDTH K 5 BRIGHT - FDTH L 4 BRIGHT - FDTH M 5 BRIGHT - FDTH N 4 BRIGHT - FDTH O 5 BRIGHT A_NoBlocking - FDTH P 4 BRIGHT - FDTH Q 5 BRIGHT - FDTH R 4 BRIGHT - ACLO E 35 A_CheckPlayerDone - Wait - AltSkinDeath: - PLAY H 10 - PLAY I 10 A_PlayerScream - PLAY J 10 A_NoBlocking - PLAY KLM 10 - PLAY N -1 - Stop - AltSkinXDeath: - PLAY O 5 - PLAY P 5 A_XScream - PLAY Q 5 A_NoBlocking - PLAY RSTUV 5 - PLAY W -1 - Stop - } -} - -// The player's skull ------------------------------------------------------- - -ACTOR BloodySkull : PlayerChunk -{ - Radius 4 - Height 4 - +NOBLOCKMAP - +DROPOFF - +LOWGRAVITY - +CANNOTPUSH - +SKYEXPLODE - +NOBLOCKMONST - +NOSKIN - States - { - Spawn: - BSKL A 0 - BSKL ABCDE 5 A_CheckFloor("Hit") - Goto Spawn+1 - Hit: - BSKL F 16 A_CheckPlayerDone - Wait - } -} - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 1ae7d7328..960b28558 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -5,13 +5,13 @@ #include "actors/raven/ravenambient.txt" #include "actors/raven/minotaur.txt" -#include "actors/heretic/hereticplayer.txt" -#include "actors/heretic/hereticammo.txt" -#include "actors/heretic/hereticarmor.txt" -#include "actors/heretic/hereticartifacts.txt" -#include "actors/heretic/heretickeys.txt" -#include "actors/heretic/hereticdecorations.txt" -#include "actors/heretic/hereticmisc.txt" +//#include "actors/heretic/hereticplayer.txt" +//#include "actors/heretic/hereticammo.txt" +//#include "actors/heretic/hereticarmor.txt" +//#include "actors/heretic/hereticartifacts.txt" +//#include "actors/heretic/heretickeys.txt" +//#include "actors/heretic/hereticdecorations.txt" +//#include "actors/heretic/hereticmisc.txt" #include "actors/heretic/hereticweaps.txt" #include "actors/heretic/mummy.txt" #include "actors/heretic/clink.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index a349d7ed5..decf9241c 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -59,5 +59,24 @@ zscript/doom/doomweapons.txt zscript/doom/stealthmonsters.txt zscript/doom/scriptedmarine.txt +zscript/heretic/hereticplayer.txt +zscript/heretic/hereticammo.txt +zscript/heretic/hereticarmor.txt +zscript/heretic/hereticartifacts.txt +zscript/heretic/heretickeys.txt +zscript/heretic/hereticdecorations.txt +zscript/heretic/hereticmisc.txt +/* +zscript/heretic/hereticweaps.txt +zscript/heretic/mummy.txt +zscript/heretic/clink.txt zscript/heretic/beast.txt +zscript/heretic/snake.txt +zscript/heretic/hereticimp.txt +zscript/heretic/knight.txt +zscript/heretic/wizard.txt +zscript/heretic/ironlich.txt +zscript/heretic/dsparil.txt +zscript/heretic/chicken.txt +*/ diff --git a/wadsrc/static/zscript/doom/doomimp.txt b/wadsrc/static/zscript/doom/doomimp.txt index 244ae70ea..318e81471 100644 --- a/wadsrc/static/zscript/doom/doomimp.txt +++ b/wadsrc/static/zscript/doom/doomimp.txt @@ -55,7 +55,8 @@ class DoomImp : Actor TROO U -1; Stop; Raise: - TROO MLKJI 8; + TROO ML 8; + TROO KJI 6; Goto See; } } diff --git a/wadsrc/static/zscript/heretic/beast.txt b/wadsrc/static/zscript/heretic/beast.txt new file mode 100644 index 000000000..209b2da56 --- /dev/null +++ b/wadsrc/static/zscript/heretic/beast.txt @@ -0,0 +1,118 @@ + +// Beast -------------------------------------------------------------------- + +class Beast : Actor +{ + Default + { + Health 220; + Radius 32; + Height 74; + Mass 200; + Speed 14; + Painchance 100; + Monster; + +FLOORCLIP + SeeSound "beast/sight"; + AttackSound "beast/attack"; + PainSound "beast/pain"; + DeathSound "beast/death"; + ActiveSound "beast/active"; + Obituary "$OB_BEAST"; + DropItem "CrossbowAmmo", 84, 10; + } + States + { + Spawn: + BEAS AB 10 A_Look; + Loop; + See: + BEAS ABCDEF 3 A_Chase; + Loop; + Missile: + BEAS H 10 A_FaceTarget; + BEAS I 10 A_CustomComboAttack("BeastBall", 32, random[BeastAttack](1,8)*3, "beast/attack"); + Goto See; + Pain: + BEAS G 3; + BEAS G 3 A_Pain; + Goto See; + Death: + BEAS R 6; + BEAS S 6 A_Scream; + BEAS TUV 6; + BEAS W 6 A_NoBlocking; + BEAS XY 6; + BEAS Z -1; + Stop; + XDeath: + BEAS J 5; + BEAS K 6 A_Scream; + BEAS L 5; + BEAS M 6; + BEAS N 5; + BEAS O 6 A_NoBlocking; + BEAS P 5; + BEAS Q -1; + Stop; + } +} + +// Beast ball --------------------------------------------------------------- + +class BeastBall : Actor +{ + Default + { + Radius 9; + Height 8; + Speed 12; + FastSpeed 20; + Damage 4; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + -NOBLOCKMAP + +WINDTHRUST + +SPAWNSOUNDSOURCE + RenderStyle "Add"; + SeeSound "beast/attack"; + } + States + { + Spawn: + FRB1 AABBCC 2 A_SpawnItemEx("Puffy", random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, + 0,0,0,0,SXF_ABSOLUTEPOSITION, 64); + Loop; + Death: + FRB1 DEFGH 4; + Stop; + } +} + +// Puffy -------------------------------------------------------------------- + +class Puffy : Actor +{ + Default + { + Radius 6; + Height 8; + Speed 10; + +NOBLOCKMAP + +NOGRAVITY + +MISSILE + +NOTELEPORT + +DONTSPLASH + RenderStyle "Add"; + } + States + { + Spawn: + FRB1 DEFGH 4; + Stop; + } +} + + + diff --git a/wadsrc/static/zscript/heretic/hereticammo.txt b/wadsrc/static/zscript/heretic/hereticammo.txt new file mode 100644 index 000000000..cf1e50a3d --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticammo.txt @@ -0,0 +1,243 @@ + +// Wimpy ammo --------------------------------------------------------------- + +Class GoldWandAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOGOLDWAND1"; + Inventory.Amount 10; + Inventory.MaxAmount 100; + Ammo.BackpackAmount 10; + Ammo.BackpackMaxAmount 200; + Inventory.Icon "INAMGLD"; + } + States + { + Spawn: + AMG1 A -1; + Stop; + } +} + +// Hefty ammo --------------------------------------------------------------- + +Class GoldWandHefty : GoldWandAmmo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOGOLDWAND2"; + Inventory.Amount 50; + } + States + { + Spawn: + AMG2 ABC 4; + Loop; + } +} +// Wimpy ammo --------------------------------------------------------------- + +Class CrossbowAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOCROSSBOW1"; + Inventory.Amount 5; + Inventory.MaxAmount 50; + Ammo.BackpackAmount 5; + Ammo.BackpackMaxAmount 100; + Inventory.Icon "INAMBOW"; + } + States + { + Spawn: + AMC1 A -1; + Stop; + } +} + +// Hefty ammo --------------------------------------------------------------- + +Class CrossbowHefty : CrossbowAmmo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOCROSSBOW2"; + Inventory.Amount 20; + } + States + { + Spawn: + AMC2 ABC 5; + Loop; + } +} +// Wimpy ammo --------------------------------------------------------------- + +Class MaceAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOMACE1"; + Inventory.Amount 20; + Inventory.MaxAmount 150; + Ammo.BackpackAmount 20; + Ammo.BackpackMaxAmount 300; + Inventory.Icon "INAMLOB"; + } + States + { + Spawn: + AMM1 A -1; + Stop; + } +} + +// Hefty ammo --------------------------------------------------------------- + +Class MaceHefty : MaceAmmo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOMACE2"; + Inventory.Amount 100; + } + States + { + Spawn: + AMM2 A -1; + Stop; + } +} + +// Wimpy ammo --------------------------------------------------------------- + +Class BlasterAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOBLASTER1"; + Inventory.Amount 10; + Inventory.MaxAmount 200; + Ammo.BackpackAmount 10; + Ammo.BackpackMaxAmount 400; + Inventory.Icon "INAMBST"; + } + States + { + Spawn: + AMB1 ABC 4; + Loop; + } +} + +// Hefty ammo --------------------------------------------------------------- + +Class BlasterHefty : BlasterAmmo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOBLASTER2"; + Inventory.Amount 25; + } + States + { + Spawn: + AMB2 ABC 4; + Loop; + } +} + +// Wimpy ammo --------------------------------------------------------------- + +Class SkullRodAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOSKULLROD1"; + Inventory.Amount 20; + Inventory.MaxAmount 200; + Ammo.BackpackAmount 20; + Ammo.BackpackMaxAmount 400; + Inventory.Icon "INAMRAM"; + } + States + { + Spawn: + AMS1 AB 5; + Loop; + } +} + +// Hefty ammo --------------------------------------------------------------- + +Class SkullRodHefty : SkullRodAmmo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOSKULLROD2"; + Inventory.Amount 100; + } + States + { + Spawn: + AMS2 AB 5; + Loop; + } +} + +// Wimpy ammo --------------------------------------------------------------- + +Class PhoenixRodAmmo : Ammo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOPHOENIXROD1"; + Inventory.Amount 1; + Inventory.MaxAmount 20; + Ammo.BackpackAmount 1; + Ammo.BackpackMaxAmount 40; + Inventory.Icon "INAMPNX"; + } + States + { + Spawn: + AMP1 ABC 4; + Loop; + } +} +// Hefty ammo --------------------------------------------------------------- + +Class PhoenixRodHefty : PhoenixRodAmmo +{ + Default + { + Inventory.PickupMessage "$TXT_AMMOPHOENIXROD2"; + Inventory.Amount 10; + } + States + { + Spawn: + AMP2 ABC 4; + Loop; + } +} + +// --- Bag of holding ------------------------------------------------------- + +Class BagOfHolding : BackpackItem +{ + Default + { + Inventory.PickupMessage "$TXT_ITEMBAGOFHOLDING"; + +COUNTITEM + +FLOATBOB + } + States + { + Spawn: + BAGH A -1; + Stop; + } +} diff --git a/wadsrc/static/zscript/heretic/hereticarmor.txt b/wadsrc/static/zscript/heretic/hereticarmor.txt new file mode 100644 index 000000000..8cbcb9fbc --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticarmor.txt @@ -0,0 +1,41 @@ + +// Silver Shield (Shield1) -------------------------------------------------- + +Class SilverShield : BasicArmorPickup +{ + Default + { + +FLOATBOB + Inventory.Pickupmessage "$TXT_ITEMSHIELD1"; + Inventory.Icon "SHLDA0"; + Armor.Savepercent 50; + Armor.Saveamount 100; + } + States + { + Spawn: + SHLD A -1; + stop; + } +} + +// Enchanted shield (Shield2) ----------------------------------------------- + +Class EnchantedShield : BasicArmorPickup +{ + Default + { + +FLOATBOB + Inventory.Pickupmessage "$TXT_ITEMSHIELD2"; + Inventory.Icon "SHD2A0"; + Armor.Savepercent 75; + Armor.Saveamount 200; + } + States + { + Spawn: + SHD2 A -1; + stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/hereticartifacts.txt b/wadsrc/static/zscript/heretic/hereticartifacts.txt new file mode 100644 index 000000000..e04426f05 --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticartifacts.txt @@ -0,0 +1,118 @@ +// Super map ---------------------------------------------------------------- + +Class SuperMap : MapRevealer +{ + Default + { + +COUNTITEM + +INVENTORY.ALWAYSPICKUP + +FLOATBOB + Inventory.MaxAmount 0; + Inventory.PickupMessage "$TXT_ITEMSUPERMAP"; + } + States + { + Spawn: + SPMP A -1; + Stop; + } +} + + +// Invisibility ------------------------------------------------------------- + +Class ArtiInvisibility : PowerupGiver +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + RenderStyle "Translucent"; + Alpha 0.4; + Inventory.RespawnTics 4230; + Inventory.Icon "ARTIINVS"; + Powerup.Type "Ghost"; + Inventory.PickupMessage "$TXT_ARTIINVISIBILITY"; + Tag "$TAG_ARTIINVISIBILITY"; + } + States + { + Spawn: + INVS A 350 Bright; + Loop; + } +} + + +// Tome of power ------------------------------------------------------------ + +Class ArtiTomeOfPower : PowerupGiver native +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + Inventory.Icon "ARTIPWBK"; + Powerup.Type "Weaponlevel2"; + Inventory.PickupMessage "$TXT_ARTITOMEOFPOWER"; + Tag "$TAG_ARTITOMEOFPOWER"; + } + States + { + Spawn: + PWBK A 350; + Loop; + } +} + + +// Time bomb ---------------------------------------------------------------- + +Class ActivatedTimeBomb : Actor +{ + Default + { + +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.4; + DeathSound "misc/timebomb"; + } + + action native void A_Timebomb(); + + States + { + Spawn: + FBMB ABCD 10; + FBMB E 6 A_Scream; + XPL1 A 4 BRIGHT A_Timebomb; + XPL1 BCDEF 4 BRIGHT; + Stop; + } +} + + +Class ArtiTimeBomb : Inventory native +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.INVBAR + +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIFBMB"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIFIREBOMB"; + Tag "$TAG_ARTIFIREBOMB"; + Inventory.DefMaxAmount; + } + States + { + Spawn: + FBMB E 350; + Loop; + } +} diff --git a/wadsrc/static/zscript/heretic/hereticdecorations.txt b/wadsrc/static/zscript/heretic/hereticdecorations.txt new file mode 100644 index 000000000..d38f47a39 --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticdecorations.txt @@ -0,0 +1,302 @@ +Class SkullHang70 : Actor +{ + Default + { + Radius 20; + Height 70; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SKH1 A -1; + Stop; + } +} + +Class SkullHang60 : Actor +{ + Default + { + Radius 20; + Height 60; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SKH2 A -1; + Stop; + } +} + +Class SkullHang45 : Actor +{ + Default + { + Radius 20; + Height 45; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SKH3 A -1; + Stop; + } +} + +Class SkullHang35 : Actor +{ + Default + { + Radius 20; + Height 35; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SKH4 A -1; + Stop; + } +} + +Class Chandelier : Actor +{ + Default + { + Radius 20; + Height 60; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + CHDL ABC 4; + Loop; + } +} + +Class SerpentTorch : Actor +{ + Default + { + Radius 12; + Height 54; + +SOLID + } + States + { + Spawn: + SRTC ABC 4; + Loop; + } +} + +Class SmallPillar : Actor +{ + Default + { + Radius 16; + Height 34; + +SOLID + } + States + { + Spawn: + SMPL A -1; + Stop; + } +} + +Class StalagmiteSmall : Actor +{ + Default + { + Radius 8; + Height 32; + +SOLID + } + States + { + Spawn: + STGS A -1; + Stop; + } +} + +Class StalagmiteLarge : Actor +{ + Default + { + Radius 12; + Height 64; + +SOLID + } + States + { + Spawn: + STGL A -1; + Stop; + } +} + +Class StalactiteSmall : Actor +{ + Default + { + Radius 8; + Height 36; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + STCS A -1; + Stop; + } +} + +Class StalactiteLarge : Actor +{ + Default + { + Radius 12; + Height 68; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + STCL A -1; + Stop; + } +} + +Class FireBrazier : Actor +{ + Default + { + Radius 16; + Height 44; + +SOLID + } + States + { + Spawn: + KFR1 ABCDEFGH 3 Bright; + Loop; + } +} + +Class Barrel : Actor +{ + Default + { + Radius 12; + Height 32; + +SOLID + } + States + { + Spawn: + BARL A -1; + Stop; + } +} + +Class BrownPillar : Actor +{ + Default + { + Radius 14; + Height 128; + +SOLID + } + States + { + Spawn: + BRPL A -1; + Stop; + } +} + +Class Moss1 : Actor +{ + Default + { + Radius 20; + Height 23; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + MOS1 A -1; + Stop; + } +} + +Class Moss2 : Actor +{ + Default + { + Radius 20; + Height 27; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + MOS2 A -1; + Stop; + } +} + +Class WallTorch : Actor +{ + Default + { + Radius 6; + Height 16; + +NOGRAVITY + +FIXMAPTHINGPOS + } + States + { + Spawn: + WTRH ABC 6 Bright; + Loop; + } +} + +Class HangingCorpse : Actor +{ + Default + { + Radius 8; + Height 104; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + HCOR A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/heretickeys.txt b/wadsrc/static/zscript/heretic/heretickeys.txt new file mode 100644 index 000000000..d5532ce01 --- /dev/null +++ b/wadsrc/static/zscript/heretic/heretickeys.txt @@ -0,0 +1,174 @@ + +Class HereticKey : Key +{ + Default + { + +NOTDMATCH + Radius 20; + Height 16; + } +} + +// Green key ------------------------------------------------------------ + +Class KeyGreen : HereticKey +{ + Default + { + Inventory.PickupMessage "$TXT_GOTGREENKEY"; + Inventory.Icon "GKEYICON"; + } + States + { + Spawn: + AKYY ABCDEFGHIJ 3 Bright; + Loop; + } +} + +// Blue key ----------------------------------------------------------------- + +Class KeyBlue : HereticKey +{ + Default + { + Inventory.PickupMessage "$TXT_GOTBLUEKEY"; + Inventory.Icon "BKEYICON"; + } + States + { + Spawn: + BKYY ABCDEFGHIJ 3 Bright; + Loop; + } +} + +// Yellow key --------------------------------------------------------------- + +Class KeyYellow : HereticKey +{ + Default + { + Inventory.PickupMessage "$TXT_GOTYELLOWKEY"; + Inventory.Icon "YKEYICON"; + } + States + { + Spawn: + CKYY ABCDEFGHI 3 Bright; + Loop; + } +} + + +// --- Blue Key gizmo ----------------------------------------------------------- + +Class KeyGizmoBlue : Actor +{ + Default + { + Radius 16; + Height 50; + +SOLID + } + States + { + Spawn: + KGZ1 A 1; + KGZ1 A 1 A_SpawnItemEx("KeyGizmoFloatBlue", 0, 0, 60); + KGZ1 A -1; + Stop; + } +} + +Class KeyGizmoFloatBlue : Actor +{ + Default + { + Radius 16; + Height 16; + +SOLID + +NOGRAVITY + } + States + { + Spawn: + KGZB A -1 Bright; + Stop; + } +} + +// --- Green Key gizmo ----------------------------------------------------------- + +Class KeyGizmoGreen : Actor +{ + Default + { + Radius 16; + Height 50; + +SOLID + } + States + { + Spawn: + KGZ1 A 1; + KGZ1 A 1 A_SpawnItemEx("KeyGizmoFloatGreen", 0, 0, 60); + KGZ1 A -1; + Stop; + } +} + +Class KeyGizmoFloatGreen : Actor +{ + Default + { + Radius 16; + Height 16; + +SOLID + +NOGRAVITY + } + States + { + Spawn: + KGZG A -1 Bright; + Stop; + } +} + +// --- Yellow Key gizmo ----------------------------------------------------------- + +Class KeyGizmoYellow : Actor +{ + Default + { + Radius 16; + Height 50; + +SOLID + } + States + { + Spawn: + KGZ1 A 1; + KGZ1 A 1 A_SpawnItemEx("KeyGizmoFloatYellow", 0, 0, 60); + KGZ1 A -1; + Stop; + } +} + +Class KeyGizmoFloatYellow : Actor +{ + Default + { + Radius 16; + Height 16; + +SOLID + +NOGRAVITY + } + States + { + Spawn: + KGZY A -1 Bright; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/hereticmisc.txt b/wadsrc/static/zscript/heretic/hereticmisc.txt new file mode 100644 index 000000000..0b90208b9 --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticmisc.txt @@ -0,0 +1,255 @@ + +// Pod ---------------------------------------------------------------------- + +class Pod : Actor +{ + Default + { + Health 45; + Radius 16; + Height 54; + Painchance 255; + +SOLID +NOBLOOD +SHOOTABLE +DROPOFF + +WINDTHRUST +PUSHABLE +SLIDESONWALLS + +CANPASS +TELESTOMP +DONTMORPH + +NOBLOCKMONST +DONTGIB +OLDRADIUSDMG + DeathSound "world/podexplode"; + PushFactor 0.5; + } + action native void A_PodPain (class podtype = "PodGoo"); + action native void A_RemovePod (); + + States + { + Spawn: + PPOD A 10; + Loop; + Pain: + PPOD B 14 A_PodPain; + Goto Spawn; + Death: + PPOD C 5 BRIGHT A_RemovePod; + PPOD D 5 BRIGHT A_Scream; + PPOD E 5 BRIGHT A_Explode; + PPOD F 10 BRIGHT; + Stop; + Grow: + PPOD IJKLMNOP 3; + Goto Spawn; + } +} + + +// Pod goo (falls from pod when damaged) ------------------------------------ + +class PodGoo : Actor +{ + Default + { + Radius 2; + Height 4; + Gravity 0.125; + +NOBLOCKMAP +MISSILE +DROPOFF + +NOTELEPORT +CANNOTPUSH + } + States + { + Spawn: + PPOD GH 8; + Loop; + Death: + PPOD G 10; + Stop; + } +} + +// Pod generator ------------------------------------------------------------ + +class PodGenerator : Actor +{ + Default + { + +NOBLOCKMAP + +NOSECTOR + +DONTSPLASH + AttackSound "world/podgrow"; + } + + action native void A_MakePod (class podtype = "Pod"); + + States + { + Spawn: + TNT1 A 35 A_MakePod; + Loop; + } +} + + +// Teleglitter generator 1 -------------------------------------------------- + +class TeleGlitterGenerator1 : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + +MOVEWITHSECTOR + } + States + { + Spawn: + TNT1 A 8 A_SpawnItemEx("TeleGlitter1", random[TeleGlitter](0,31)-16, random[TeleGlitter](0,31)-16, 0, 0,0,0.25); + Loop; + } +} + +// Teleglitter generator 2 -------------------------------------------------- + +class TeleGlitterGenerator2 : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +DONTSPLASH + +MOVEWITHSECTOR + } + States + { + Spawn: + TNT1 A 8 A_SpawnItemEx("TeleGlitter2", random[TeleGlitter2](0,31)-16, random[TeleGlitter2](0,31)-16, 0, 0,0,0.25); + Loop; + } +} + + +// Teleglitter 1 ------------------------------------------------------------ + +class TeleGlitter1 : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY +MISSILE + RenderStyle "Add"; + Damage 0; + } + + action native void A_AccTeleGlitter (); + + States + { + Spawn: + TGLT A 2 BRIGHT; + TGLT B 2 BRIGHT A_AccTeleGlitter; + TGLT C 2 BRIGHT; + TGLT D 2 BRIGHT A_AccTeleGlitter; + TGLT E 2 BRIGHT; + Loop; + } +} + +// Teleglitter 2 ------------------------------------------------------------ + +class TeleGlitter2 : TeleGlitter1 +{ + States + { + Spawn: + TGLT F 2 BRIGHT; + TGLT G 2 BRIGHT A_AccTeleGlitter; + TGLT H 2 BRIGHT; + TGLT I 2 BRIGHT A_AccTeleGlitter; + TGLT J 2 BRIGHT; + Loop; + } +} + + +// --- Volcano -------------------------------------------------------------- + +class Volcano : Actor +{ + Default + { + Radius 12; + Height 20; + +SOLID + } + + action native void A_VolcanoSet (); + action native void A_VolcanoBlast (); + + States + { + Spawn: + VLCO A 350; + VLCO A 35 A_VolcanoSet; + VLCO BCDBCD 3; + VLCO E 10 A_VolcanoBlast; + Goto Spawn+1; + } + +} + +// Volcano blast ------------------------------------------------------------ + +class VolcanoBlast : Actor +{ + Default + { + Radius 8; + Height 8; + Speed 2; + Damage 2; + DamageType "Fire"; + Gravity 0.125; + +NOBLOCKMAP +MISSILE +DROPOFF + +NOTELEPORT + DeathSound "world/volcano/blast"; + } + + action native void A_VolcBallImpact (); + + States + { + Spawn: + VFBL AB 4 BRIGHT A_SpawnItemEx("Puffy", random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, + 0,0,0,0,SXF_ABSOLUTEPOSITION, 64); + Loop; + + Death: + XPL1 A 4 BRIGHT A_VolcBallImpact; + XPL1 BCDEF 4 BRIGHT; + Stop; + } +} + +// Volcano T Blast ---------------------------------------------------------- + +class VolcanoTBlast : Actor +{ + Default + { + Radius 8; + Height 6; + Speed 2; + Damage 1; + DamageType "Fire"; + Gravity 0.125; + +NOBLOCKMAP +MISSILE +DROPOFF + +NOTELEPORT + } + States + { + Spawn: + VTFB AB 4 BRIGHT; + Loop; + Death: + SFFI CBABCDE 4 BRIGHT; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/heretic/hereticplayer.txt b/wadsrc/static/zscript/heretic/hereticplayer.txt new file mode 100644 index 000000000..26ff684f3 --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticplayer.txt @@ -0,0 +1,135 @@ +class HereticPlayer : PlayerPawn +{ + Default + { + Health 100; + Radius 16; + Height 56; + Mass 100; + Painchance 255; + Speed 1; + Player.DisplayName "Corvus"; + Player.StartItem "GoldWand"; + Player.StartItem "Staff"; + Player.StartItem "GoldWandAmmo", 50; + Player.WeaponSlot 1, "Staff", "Gauntlets"; + Player.WeaponSlot 2, "GoldWand"; + Player.WeaponSlot 3, "Crossbow"; + Player.WeaponSlot 4, "Blaster"; + Player.WeaponSlot 5, "SkullRod"; + Player.WeaponSlot 6, "PhoenixRod"; + Player.WeaponSlot 7, "Mace"; + + Player.ColorRange 225, 240; + Player.Colorset 0, "Green", 225, 240, 238; + Player.Colorset 1, "Yellow", 114, 129, 127; + Player.Colorset 2, "Red", 145, 160, 158; + Player.Colorset 3, "Blue", 190, 205, 203; + // Doom Legacy additions + Player.Colorset 4, "Brown", 67, 82, 80; + Player.Colorset 5, "Light Gray", 9, 24, 22; + Player.Colorset 6, "Light Brown", 74, 89, 87; + Player.Colorset 7, "Light Red", 150, 165, 163; + Player.Colorset 8, "Light Blue", 192, 207, 205; + Player.Colorset 9, "Beige", 95, 110, 108; + } + + States + { + Spawn: + PLAY A -1; + Stop; + See: + PLAY ABCD 4; + Loop; + Melee: + Missile: + PLAY F 6 BRIGHT; + PLAY E 12; + Goto Spawn; + Pain: + PLAY G 4; + PLAY G 4 A_Pain; + Goto Spawn; + Death: + PLAY H 6 A_PlayerSkinCheck("AltSkinDeath"); + PLAY I 6 A_PlayerScream; + PLAY JK 6; + PLAY L 6 A_NoBlocking; + PLAY MNO 6; + PLAY P -1; + Stop; + XDeath: + PLAY Q 0 A_PlayerSkinCheck("AltSkinXDeath"); + PLAY Q 5 A_PlayerScream; + PLAY R 0 A_NoBlocking; + PLAY R 5 A_SkullPop; + PLAY STUVWX 5; + PLAY Y -1; + Stop; + Burn: + FDTH A 5 BRIGHT A_PlaySound("*burndeath"); + FDTH B 4 BRIGHT; + FDTH C 5 BRIGHT; + FDTH D 4 BRIGHT A_PlayerScream; + FDTH E 5 BRIGHT; + FDTH F 4 BRIGHT; + FDTH G 5 BRIGHT A_PlaySound("*burndeath"); + FDTH H 4 BRIGHT; + FDTH I 5 BRIGHT; + FDTH J 4 BRIGHT; + FDTH K 5 BRIGHT; + FDTH L 4 BRIGHT; + FDTH M 5 BRIGHT; + FDTH N 4 BRIGHT; + FDTH O 5 BRIGHT A_NoBlocking; + FDTH P 4 BRIGHT; + FDTH Q 5 BRIGHT; + FDTH R 4 BRIGHT; + ACLO E 35 A_CheckPlayerDone; + Wait; + AltSkinDeath: + PLAY H 10; + PLAY I 10 A_PlayerScream; + PLAY J 10 A_NoBlocking; + PLAY KLM 10; + PLAY N -1; + Stop; + AltSkinXDeath: + PLAY O 5; + PLAY P 5 A_XScream; + PLAY Q 5 A_NoBlocking; + PLAY RSTUV 5; + PLAY W -1; + Stop; + } +} + +// The player's skull ------------------------------------------------------- + +class BloodySkull : PlayerChunk +{ + Default + { + Radius 4; + Height 4; + Gravity 0.125; + +NOBLOCKMAP + +DROPOFF + +CANNOTPUSH + +SKYEXPLODE + +NOBLOCKMONST + +NOSKIN + } + States + { + Spawn: + BSKL A 0; + BSKL ABCDE 5 A_CheckFloor("Hit"); + Goto Spawn+1; + Hit: + BSKL F 16 A_CheckPlayerDone; + Wait; + } +} + From 76f1b9d3f8407a1bd6f752884832b37cc4598c77 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 00:21:52 +0200 Subject: [PATCH 053/255] - converted the raven actors. --- wadsrc/static/actors/raven/artiegg.txt | 102 -------- wadsrc/static/actors/raven/artitele.txt | 24 -- wadsrc/static/actors/raven/minotaur.txt | 218 ---------------- wadsrc/static/actors/raven/ravenambient.txt | 36 --- wadsrc/static/actors/raven/ravenartifacts.txt | 125 ---------- wadsrc/static/actors/raven/ravenhealth.txt | 13 - wadsrc/static/decorate.txt | 14 -- wadsrc/static/zscript.txt | 7 + .../zscript/heretic/hereticartifacts.txt | 2 +- wadsrc/static/zscript/raven/artiegg.txt | 114 +++++++++ wadsrc/static/zscript/raven/artitele.txt | 27 ++ wadsrc/static/zscript/raven/minotaur.txt | 236 ++++++++++++++++++ wadsrc/static/zscript/raven/ravenambient.txt | 42 ++++ .../static/zscript/raven/ravenartifacts.txt | 143 +++++++++++ wadsrc/static/zscript/raven/ravenhealth.txt | 16 ++ 15 files changed, 586 insertions(+), 533 deletions(-) delete mode 100644 wadsrc/static/actors/raven/artiegg.txt delete mode 100644 wadsrc/static/actors/raven/artitele.txt delete mode 100644 wadsrc/static/actors/raven/minotaur.txt delete mode 100644 wadsrc/static/actors/raven/ravenambient.txt delete mode 100644 wadsrc/static/actors/raven/ravenartifacts.txt delete mode 100644 wadsrc/static/actors/raven/ravenhealth.txt create mode 100644 wadsrc/static/zscript/raven/artiegg.txt create mode 100644 wadsrc/static/zscript/raven/artitele.txt create mode 100644 wadsrc/static/zscript/raven/minotaur.txt create mode 100644 wadsrc/static/zscript/raven/ravenambient.txt create mode 100644 wadsrc/static/zscript/raven/ravenartifacts.txt create mode 100644 wadsrc/static/zscript/raven/ravenhealth.txt diff --git a/wadsrc/static/actors/raven/artiegg.txt b/wadsrc/static/actors/raven/artiegg.txt deleted file mode 100644 index 1c4a8f190..000000000 --- a/wadsrc/static/actors/raven/artiegg.txt +++ /dev/null @@ -1,102 +0,0 @@ - -// Egg missile -------------------------------------------------------------- - -ACTOR EggFX : MorphProjectile -{ - Radius 8 - Height 8 - Speed 18 - MorphProjectile.PlayerClass "ChickenPlayer" - MorphProjectile.MonsterClass "Chicken" - MorphProjectile.MorphStyle MRF_UNDOBYTOMEOFPOWER - States - { - Spawn: - EGGM ABCDE 4 - Loop - Death: - FX01 FFGH 3 Bright - Stop - } -} - - -// Morph Ovum ---------------------------------------------------------------- - -ACTOR ArtiEgg : CustomInventory -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.INVBAR - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.Icon "ARTIEGGC" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIEGG" - Inventory.DefMaxAmount - Tag "$TAG_ARTIEGG" - States - { - Spawn: - EGGC ABCB 6 - Loop - Use: - TNT1 A 0 A_FireCustomMissile("EggFX", -15, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("EggFX", -7.5, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("EggFX", 0, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("EggFX", 7.5, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("EggFX", 15, 0, 0, 0, 1) - Stop - } -} - -// Pork missile -------------------------------------------------------------- - -ACTOR PorkFX : MorphProjectile -{ - Radius 8 - Height 8 - Speed 18 - MorphProjectile.PlayerClass "PigPlayer" - MorphProjectile.MonsterClass "Pig" - MorphProjectile.MorphStyle MRF_UNDOBYTOMEOFPOWER|MRF_UNDOBYCHAOSDEVICE - States - { - Spawn: - PRKM ABCDE 4 - Loop - Death: - FHFX IJKL 3 Bright - Stop - } -} - -// Porkalator --------------------------------------------------------------- - -ACTOR ArtiPork : CustomInventory -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.INVBAR - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.Icon "ARTIPORK" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIEGG2" - Inventory.DefMaxAmount - Tag "$TAG_ARTIPORK" - States - { - Spawn: - PORK ABCDEFGH 5 - Loop - Use: - TNT1 A 0 A_FireCustomMissile("PorkFX", -15, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("PorkFX", -7.5, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("PorkFX", 0, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("PorkFX", 7.5, 0, 0, 0, 1) - TNT1 A 0 A_FireCustomMissile("PorkFX", 15, 0, 0, 0, 1) - Stop - } -} - diff --git a/wadsrc/static/actors/raven/artitele.txt b/wadsrc/static/actors/raven/artitele.txt deleted file mode 100644 index 569926d16..000000000 --- a/wadsrc/static/actors/raven/artitele.txt +++ /dev/null @@ -1,24 +0,0 @@ - -// Teleport (self) ---------------------------------------------------------- - -ACTOR ArtiTeleport : Inventory native -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.INVBAR - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.DefMaxAmount - Inventory.Icon "ARTIATLP" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTITELEPORT" - Tag "$TAG_ARTITELEPORT" - States - { - Spawn: - ATLP ABCB 4 - Loop - } -} - - diff --git a/wadsrc/static/actors/raven/minotaur.txt b/wadsrc/static/actors/raven/minotaur.txt deleted file mode 100644 index 134bf9d52..000000000 --- a/wadsrc/static/actors/raven/minotaur.txt +++ /dev/null @@ -1,218 +0,0 @@ -ACTOR Minotaur native -{ - Health 3000 - Radius 28 - Height 100 - Mass 800 - Speed 16 - Damage 7 - Painchance 25 - Monster - +DROPOFF - +FLOORCLIP - +BOSS - +NORADIUSDMG - +DONTMORPH - +NOTARGET - +BOSSDEATH - SeeSound "minotaur/sight" - AttackSound "minotaur/attack1" - PainSound "minotaur/pain" - DeathSound "minotaur/death" - ActiveSound "minotaur/active" - DropItem "ArtiSuperHealth", 51 - DropItem "PhoenixRodAmmo", 84, 10 - - action native A_MinotaurDecide(); - action native A_MinotaurAtk1(); - action native A_MinotaurAtk2(); - action native A_MinotaurAtk3(); - action native A_MinotaurCharge(); - action native A_MinotaurLook(); - action native A_MinotaurRoam(); - action native A_MinotaurChase(); - action native A_MinotaurDeath(); - - States - { - Spawn: - MNTR AB 10 A_MinotaurLook - Loop - Roam: - MNTR ABCD 5 A_MinotaurRoam - Loop - See: - MNTR ABCD 5 A_MinotaurChase - Loop - Melee: - MNTR V 10 A_FaceTarget - MNTR W 7 A_FaceTarget - MNTR X 12 A_MinotaurAtk1 - Goto See - Missile: - MNTR V 10 A_MinotaurDecide - MNTR Y 4 A_FaceTarget - MNTR Z 9 A_MinotaurAtk2 - Goto See - Hammer: - MNTR V 10 A_FaceTarget - MNTR W 7 A_FaceTarget - MNTR X 12 A_MinotaurAtk3 - Goto See - HammerLoop: - MNTR X 12 - Goto Hammer - Charge: - MNTR U 2 A_MinotaurCharge - Loop - Pain: - MNTR E 3 - MNTR E 6 A_Pain - Goto See - Death: - MNTR F 6 A_MinotaurDeath - MNTR G 5 - MNTR H 6 A_Scream - MNTR I 5 - MNTR J 6 - MNTR K 5 - MNTR L 6 - MNTR M 5 A_NoBlocking - MNTR N 6 - MNTR O 5 - MNTR P 6 - MNTR Q 5 - MNTR R 6 - MNTR S 5 - MNTR T -1 A_BossDeath - Stop - FadeOut: - MNTR E 6 - MNTR E 2 A_Scream - MNTR E 5 A_SpawnItemEx("MinotaurSmokeExit") - MNTR E 5 - MNTR E 5 A_NoBlocking - MNTR E 5 - MNTR E 5 A_SetTranslucent(0.66, 0) - MNTR E 5 A_SetTranslucent(0.33, 0) - MNTR E 10 A_BossDeath - Stop - } -} - -ACTOR MinotaurFriend : Minotaur native -{ - Health 2500 - -DROPOFF - -BOSS - -DONTMORPH - +FRIENDLY - +NOTARGETSWITCH - +STAYMORPHED - +TELESTOMP - +SUMMONEDMONSTER - RenderStyle Translucent - Alpha 0.3333 - DropItem "None" - States - { - Spawn: - MNTR A 15 - MNTR A 15 A_SetTranslucent(0.66, 0) - MNTR A 3 A_SetTranslucent(1, 0) - Goto Super::Spawn - Idle: - Goto Super::Spawn - Death: - Goto FadeOut - } -} - -// Minotaur FX 1 ------------------------------------------------------------ - -ACTOR MinotaurFX1 -{ - Radius 10 - Height 6 - Speed 20 - FastSpeed 26 - Damage 3 - DamageType Fire - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - States - { - Spawn: - FX12 AB 6 Bright - Loop - Death: - FX12 CDEFGH 5 Bright - Stop - } -} - - -// Minotaur FX 2 ------------------------------------------------------------ - -ACTOR MinotaurFX2 : MinotaurFX1 -{ - Radius 5 - Height 12 - Speed 14 - FastSpeed 20 - Damage 4 - +FLOORHUGGER - ExplosionDamage 24 - DeathSound "minotaur/fx2hit" - - action native A_MntrFloorFire(); - - states - { - Spawn: - FX13 A 2 Bright A_MntrFloorFire - Loop - Death: - FX13 I 4 Bright A_Explode - FX13 JKLM 4 Bright - Stop - } -} - -// Minotaur FX 3 ------------------------------------------------------------ - -ACTOR MinotaurFX3 : MinotaurFX2 -{ - Radius 8 - Height 16 - Speed 0 - DeathSound "minotaur/fx3hit" - ExplosionDamage 128 - States - { - Spawn: - FX13 DC 4 Bright - FX13 BCDE 5 Bright - FX13 FGH 4 Bright - Stop - } -} - -// Minotaur Smoke Exit ------------------------------------------------------ - -ACTOR MinotaurSmokeExit -{ - +NOBLOCKMAP - +NOTELEPORT - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - MNSM ABCDEFGHIJIHGFEDCBA 3 - Stop - } -} - diff --git a/wadsrc/static/actors/raven/ravenambient.txt b/wadsrc/static/actors/raven/ravenambient.txt deleted file mode 100644 index f7312de02..000000000 --- a/wadsrc/static/actors/raven/ravenambient.txt +++ /dev/null @@ -1,36 +0,0 @@ - - -// Wind --------------------------------------------------------------------- - -ACTOR SoundWind -{ - +NOBLOCKMAP - +NOSECTOR - +DONTSPLASH - States - { - Spawn: - TNT1 A 2 A_PlaySoundEx("world/wind", "SoundSlot6", 1) - Loop - } -} - -ACTOR SoundWindHexen : SoundWind -{ -} - - -// Waterfall ---------------------------------------------------------------- - -ACTOR SoundWaterfall -{ - +NOBLOCKMAP - +NOSECTOR - +DONTSPLASH - States - { - Spawn: - TNT1 A 2 A_PlaySoundEx("world/waterfall", "SoundSlot6", 1) - Loop - } -} diff --git a/wadsrc/static/actors/raven/ravenartifacts.txt b/wadsrc/static/actors/raven/ravenartifacts.txt deleted file mode 100644 index 43a5e87fc..000000000 --- a/wadsrc/static/actors/raven/ravenartifacts.txt +++ /dev/null @@ -1,125 +0,0 @@ - -// Health ------------------------------------------------------------------- - -ACTOR ArtiHealth : HealthPickup -{ - Health 25 - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.Icon ARTIPTN2 - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIHEALTH" - Tag "$TAG_ARTIHEALTH" - HealthPickup.Autouse 1 - States - { - Spawn: - PTN2 ABC 4 - Loop - } -} - -// Super health ------------------------------------------------------------- - -ACTOR ArtiSuperHealth : HealthPickup -{ - Health 100 - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.Icon ARTISPHL - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTISUPERHEALTH" - Tag "$TAG_ARTISUPERHEALTH" - HealthPickup.Autouse 2 - States - { - Spawn: - SPHL A 350 - Loop - } -} - -// Flight ------------------------------------------------------------------- - -ACTOR ArtiFly : PowerupGiver -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - +INVENTORY.INTERHUBSTRIP - Inventory.RespawnTics 4230 - Inventory.Icon ARTISOAR - Inventory.PickupMessage "$TXT_ARTIFLY" - Tag "$TAG_ARTIFLY" - Powerup.Type Flight - States - { - Spawn: - SOAR ABCB 5 - Loop - } -} - -// Invulnerability Heretic (Ring of invincibility) -------------------------- - -ACTOR ArtiInvulnerability : PowerupGiver -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - Inventory.RespawnTics 4230 - Inventory.Icon ARTIINVU - Inventory.PickupMessage "$TXT_ARTIINVULNERABILITY" - Tag "$TAG_ARTIINVULNERABILITY" - Powerup.Type Invulnerable - Powerup.Color GoldMap - States - { - Spawn: - INVU ABCD 3 - Loop - } -} - -// Invulnerability Hexen (Icon of the defender) ----------------------------- - -ACTOR ArtiInvulnerability2 : PowerupGiver -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - Inventory.RespawnTics 4230 - Inventory.Icon ARTIDEFN - Inventory.PickupMessage "$TXT_ARTIINVULNERABILITY2" - Powerup.Type Invulnerable - Tag "$TAG_ARTIDEFENDER" - States - { - Spawn: - DEFN ABCD 3 - Loop - } -} - -// Torch -------------------------------------------------------------------- - -ACTOR ArtiTorch : PowerupGiver -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.PICKUPFLASH - Inventory.Icon ARTITRCH - Inventory.PickupMessage "$TXT_ARTITORCH" - Tag "$TAG_ARTITORCH" - Powerup.Type Torch - States - { - Spawn: - TRCH ABC 3 Bright - Loop - } -} diff --git a/wadsrc/static/actors/raven/ravenhealth.txt b/wadsrc/static/actors/raven/ravenhealth.txt deleted file mode 100644 index 99e6692ba..000000000 --- a/wadsrc/static/actors/raven/ravenhealth.txt +++ /dev/null @@ -1,13 +0,0 @@ -ACTOR CrystalVial : Health -{ - +FLOATBOB - Inventory.Amount 10 - Inventory.PickupMessage "$TXT_ITEMHEALTH" - States - { - Spawn: - PTN1 ABC 3 - Loop - } -} - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 960b28558..52906258c 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,17 +1,3 @@ -#include "actors/raven/artiegg.txt" -#include "actors/raven/artitele.txt" -#include "actors/raven/ravenartifacts.txt" -#include "actors/raven/ravenhealth.txt" -#include "actors/raven/ravenambient.txt" -#include "actors/raven/minotaur.txt" - -//#include "actors/heretic/hereticplayer.txt" -//#include "actors/heretic/hereticammo.txt" -//#include "actors/heretic/hereticarmor.txt" -//#include "actors/heretic/hereticartifacts.txt" -//#include "actors/heretic/heretickeys.txt" -//#include "actors/heretic/hereticdecorations.txt" -//#include "actors/heretic/hereticmisc.txt" #include "actors/heretic/hereticweaps.txt" #include "actors/heretic/mummy.txt" #include "actors/heretic/clink.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index decf9241c..bd7b914b5 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -59,6 +59,13 @@ zscript/doom/doomweapons.txt zscript/doom/stealthmonsters.txt zscript/doom/scriptedmarine.txt +zscript/raven/artiegg.txt +zscript/raven/artitele.txt +zscript/raven/ravenartifacts.txt +zscript/raven/ravenhealth.txt +zscript/raven/ravenambient.txt +zscript/raven/minotaur.txt + zscript/heretic/hereticplayer.txt zscript/heretic/hereticammo.txt zscript/heretic/hereticarmor.txt diff --git a/wadsrc/static/zscript/heretic/hereticartifacts.txt b/wadsrc/static/zscript/heretic/hereticartifacts.txt index e04426f05..154f48ad3 100644 --- a/wadsrc/static/zscript/heretic/hereticartifacts.txt +++ b/wadsrc/static/zscript/heretic/hereticartifacts.txt @@ -32,7 +32,7 @@ Class ArtiInvisibility : PowerupGiver Alpha 0.4; Inventory.RespawnTics 4230; Inventory.Icon "ARTIINVS"; - Powerup.Type "Ghost"; + Powerup.Type "PowerGhost"; Inventory.PickupMessage "$TXT_ARTIINVISIBILITY"; Tag "$TAG_ARTIINVISIBILITY"; } diff --git a/wadsrc/static/zscript/raven/artiegg.txt b/wadsrc/static/zscript/raven/artiegg.txt new file mode 100644 index 000000000..ef3c6e2be --- /dev/null +++ b/wadsrc/static/zscript/raven/artiegg.txt @@ -0,0 +1,114 @@ + +// Egg missile -------------------------------------------------------------- + +class EggFX : MorphProjectile +{ + Default + { + Radius 8; + Height 8; + Speed 18; + MorphProjectile.PlayerClass "ChickenPlayer"; + MorphProjectile.MonsterClass "Chicken"; + MorphProjectile.MorphStyle MRF_UNDOBYTOMEOFPOWER; + } + States + { + Spawn: + EGGM ABCDE 4; + Loop; + Death: + FX01 FFGH 3 Bright; + Stop; + } +} + + +// Morph Ovum ---------------------------------------------------------------- + +class ArtiEgg : CustomInventory +{ + Default + { + +COUNTITEM + +FLOATBOB + +INVENTORY.INVBAR + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIEGGC"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIEGG"; + Inventory.DefMaxAmount; + Tag "$TAG_ARTIEGG"; + } + States + { + Spawn: + EGGC ABCB 6; + Loop; + Use: + TNT1 A 0 A_FireCustomMissile("EggFX", -15, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("EggFX", -7.5, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("EggFX", 0, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("EggFX", 7.5, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("EggFX", 15, 0, 0, 0, 1); + Stop; + } +} + +// Pork missile -------------------------------------------------------------- + +class PorkFX : MorphProjectile +{ + Default + { + Radius 8; + Height 8; + Speed 18; + MorphProjectile.PlayerClass "PigPlayer"; + MorphProjectile.MonsterClass "Pig"; + MorphProjectile.MorphStyle MRF_UNDOBYTOMEOFPOWER|MRF_UNDOBYCHAOSDEVICE; + } + States + { + Spawn: + PRKM ABCDE 4; + Loop; + Death: + FHFX IJKL 3 Bright; + Stop; + } +} + +// Porkalator --------------------------------------------------------------- + +class ArtiPork : CustomInventory +{ + Default + { + +COUNTITEM + +FLOATBOB + +INVENTORY.INVBAR + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIPORK"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIEGG2"; + Inventory.DefMaxAmount; + Tag "$TAG_ARTIPORK"; + } + States + { + Spawn: + PORK ABCDEFGH 5; + Loop; + Use: + TNT1 A 0 A_FireCustomMissile("PorkFX", -15, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("PorkFX", -7.5, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("PorkFX", 0, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("PorkFX", 7.5, 0, 0, 0, 1); + TNT1 A 0 A_FireCustomMissile("PorkFX", 15, 0, 0, 0, 1); + Stop; + } +} + diff --git a/wadsrc/static/zscript/raven/artitele.txt b/wadsrc/static/zscript/raven/artitele.txt new file mode 100644 index 000000000..9f21bd733 --- /dev/null +++ b/wadsrc/static/zscript/raven/artitele.txt @@ -0,0 +1,27 @@ + +// Teleport (self) ---------------------------------------------------------- + +class ArtiTeleport : Inventory native +{ + Default + { + +COUNTITEM + +FLOATBOB + +INVENTORY.INVBAR + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.FANCYPICKUPSOUND + Inventory.DefMaxAmount; + Inventory.Icon "ARTIATLP"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTITELEPORT"; + Tag "$TAG_ARTITELEPORT"; + } + States + { + Spawn: + ATLP ABCB 4; + Loop; + } +} + + diff --git a/wadsrc/static/zscript/raven/minotaur.txt b/wadsrc/static/zscript/raven/minotaur.txt new file mode 100644 index 000000000..9bc02fced --- /dev/null +++ b/wadsrc/static/zscript/raven/minotaur.txt @@ -0,0 +1,236 @@ +class Minotaur : Actor native +{ + Default + { + Health 3000; + Radius 28; + Height 100; + Mass 800; + Speed 16; + Damage 7; + Painchance 25; + Monster; + +DROPOFF + +FLOORCLIP + +BOSS + +NORADIUSDMG + +DONTMORPH + +NOTARGET + +BOSSDEATH + SeeSound "minotaur/sight"; + AttackSound "minotaur/attack1"; + PainSound "minotaur/pain"; + DeathSound "minotaur/death"; + ActiveSound "minotaur/active"; + DropItem "ArtiSuperHealth", 51; + DropItem "PhoenixRodAmmo", 84, 10; + } + + action native void A_MinotaurDecide(); + action native void A_MinotaurAtk1(); + action native void A_MinotaurAtk2(); + action native void A_MinotaurAtk3(); + action native void A_MinotaurCharge(); + action native void A_MinotaurLook(); + action native void A_MinotaurRoam(); + action native void A_MinotaurChase(); + action native void A_MinotaurDeath(); + + States + { + Spawn: + MNTR AB 10 A_MinotaurLook; + Loop; + Roam: + MNTR ABCD 5 A_MinotaurRoam; + Loop; + See: + MNTR ABCD 5 A_MinotaurChase; + Loop; + Melee: + MNTR V 10 A_FaceTarget; + MNTR W 7 A_FaceTarget; + MNTR X 12 A_MinotaurAtk1; + Goto See; + Missile: + MNTR V 10 A_MinotaurDecide; + MNTR Y 4 A_FaceTarget; + MNTR Z 9 A_MinotaurAtk2; + Goto See; + Hammer: + MNTR V 10 A_FaceTarget; + MNTR W 7 A_FaceTarget; + MNTR X 12 A_MinotaurAtk3; + Goto See; + HammerLoop: + MNTR X 12; + Goto Hammer; + Charge: + MNTR U 2 A_MinotaurCharge; + Loop; + Pain: + MNTR E 3; + MNTR E 6 A_Pain; + Goto See; + Death: + MNTR F 6 A_MinotaurDeath; + MNTR G 5; + MNTR H 6 A_Scream; + MNTR I 5; + MNTR J 6; + MNTR K 5; + MNTR L 6; + MNTR M 5 A_NoBlocking; + MNTR N 6; + MNTR O 5; + MNTR P 6; + MNTR Q 5; + MNTR R 6; + MNTR S 5; + MNTR T -1 A_BossDeath; + Stop; + FadeOut: + MNTR E 6; + MNTR E 2 A_Scream; + MNTR E 5 A_SpawnItemEx("MinotaurSmokeExit"); + MNTR E 5; + MNTR E 5 A_NoBlocking; + MNTR E 5; + MNTR E 5 A_SetTranslucent(0.66, 0); + MNTR E 5 A_SetTranslucent(0.33, 0); + MNTR E 10 A_BossDeath; + Stop; + } +} + +class MinotaurFriend : Minotaur native +{ + Default + { + Health 2500; + -DROPOFF + -BOSS + -DONTMORPH + +FRIENDLY + +NOTARGETSWITCH + +STAYMORPHED + +TELESTOMP + +SUMMONEDMONSTER + RenderStyle "Translucent"; + Alpha 0.3333; + DropItem "None"; + } + States + { + Spawn: + MNTR A 15; + MNTR A 15 A_SetTranslucent(0.66, 0); + MNTR A 3 A_SetTranslucent(1, 0); + Goto Super::Spawn; + Idle: + Goto Super::Spawn; + Death: + Goto FadeOut; + } +} + +// Minotaur FX 1 ------------------------------------------------------------ + +class MinotaurFX1 : Actor +{ + Default + { + Radius 10; + Height 6; + Speed 20; + FastSpeed 26; + Damage 3; + DamageType "Fire"; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + } + States + { + Spawn: + FX12 AB 6 Bright; + Loop; + Death: + FX12 CDEFGH 5 Bright; + Stop; + } +} + + +// Minotaur FX 2 ------------------------------------------------------------ + +class MinotaurFX2 : MinotaurFX1 +{ + Default + { + Radius 5; + Height 12; + Speed 14; + FastSpeed 20; + Damage 4; + +FLOORHUGGER + ExplosionDamage 24; + DeathSound "minotaur/fx2hit"; + } + + action native void A_MntrFloorFire(); + + states + { + Spawn: + FX13 A 2 Bright A_MntrFloorFire; + Loop; + Death: + FX13 I 4 Bright A_Explode; + FX13 JKLM 4 Bright; + Stop; + } +} + +// Minotaur FX 3 ------------------------------------------------------------ + +class MinotaurFX3 : MinotaurFX2 +{ + Default + { + Radius 8; + Height 16; + Speed 0; + DeathSound "minotaur/fx3hit"; + ExplosionDamage 128; + } + States + { + Spawn: + FX13 DC 4 Bright; + FX13 BCDE 5 Bright; + FX13 FGH 4 Bright; + Stop; + } +} + +// Minotaur Smoke Exit ------------------------------------------------------ + +class MinotaurSmokeExit : Actor +{ + Default + { + +NOBLOCKMAP + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Spawn: + MNSM ABCDEFGHIJIHGFEDCBA 3; + Stop; + } +} + diff --git a/wadsrc/static/zscript/raven/ravenambient.txt b/wadsrc/static/zscript/raven/ravenambient.txt new file mode 100644 index 000000000..3495dc4e0 --- /dev/null +++ b/wadsrc/static/zscript/raven/ravenambient.txt @@ -0,0 +1,42 @@ + + +// Wind --------------------------------------------------------------------- + +class SoundWind : Actor +{ + Default + { + +NOBLOCKMAP + +NOSECTOR + +DONTSPLASH + } + States + { + Spawn: + TNT1 A 2 A_PlaySound("world/wind", CHAN_6); + Loop; + } +} + +class SoundWindHexen : SoundWind +{ +} + + +// Waterfall ---------------------------------------------------------------- + +class SoundWaterfall : Actor +{ + Default + { + +NOBLOCKMAP + +NOSECTOR + +DONTSPLASH + } + States + { + Spawn: + TNT1 A 2 A_PlaySound("world/waterfall", CHAN_6); + Loop; + } +} diff --git a/wadsrc/static/zscript/raven/ravenartifacts.txt b/wadsrc/static/zscript/raven/ravenartifacts.txt new file mode 100644 index 000000000..443816788 --- /dev/null +++ b/wadsrc/static/zscript/raven/ravenartifacts.txt @@ -0,0 +1,143 @@ + +// Health ------------------------------------------------------------------- + +class ArtiHealth : HealthPickup +{ + Default + { + Health 25; + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIPTN2"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIHEALTH"; + Tag "$TAG_ARTIHEALTH"; + HealthPickup.Autouse 1; + } + States + { + Spawn: + PTN2 ABC 4; + Loop; + } +} + +// Super health ------------------------------------------------------------- + +class ArtiSuperHealth : HealthPickup +{ + Default + { + Health 100; + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTISPHL"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTISUPERHEALTH"; + Tag "$TAG_ARTISUPERHEALTH"; + HealthPickup.Autouse 2; + } + States + { + Spawn: + SPHL A 350; + Loop; + } +} + +// Flight ------------------------------------------------------------------- + +class ArtiFly : PowerupGiver +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + Inventory.InterHubAmount 0; + Inventory.RespawnTics 4230; + Inventory.Icon "ARTISOAR"; + Inventory.PickupMessage "$TXT_ARTIFLY"; + Tag "$TAG_ARTIFLY"; + Powerup.Type "PowerFlight"; + } + States + { + Spawn: + SOAR ABCB 5; + Loop; + } +} + +// Invulnerability Heretic (Ring of invincibility) -------------------------- + +class ArtiInvulnerability : PowerupGiver +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + Inventory.RespawnTics 4230; + Inventory.Icon "ARTIINVU"; + Inventory.PickupMessage "$TXT_ARTIINVULNERABILITY"; + Tag "$TAG_ARTIINVULNERABILITY"; + Powerup.Type "PowerInvulnerable"; + Powerup.Color "GoldMap"; + } + States + { + Spawn: + INVU ABCD 3; + Loop; + } +} + +// Invulnerability Hexen (Icon of the defender) ----------------------------- + +class ArtiInvulnerability2 : PowerupGiver +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + Inventory.RespawnTics 4230; + Inventory.Icon "ARTIDEFN"; + Inventory.PickupMessage "$TXT_ARTIINVULNERABILITY2"; + Powerup.Type "PowerInvulnerable"; + Tag "$TAG_ARTIDEFENDER"; + } + States + { + Spawn: + DEFN ABCD 3; + Loop; + } +} + +// Torch -------------------------------------------------------------------- + +class ArtiTorch : PowerupGiver +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.PickupFlash "PickupFlash"; + Inventory.Icon "ARTITRCH"; + Inventory.PickupMessage "$TXT_ARTITORCH"; + Tag "$TAG_ARTITORCH"; + Powerup.Type "PowerTorch"; + } + States + { + Spawn: + TRCH ABC 3 Bright; + Loop; + } +} diff --git a/wadsrc/static/zscript/raven/ravenhealth.txt b/wadsrc/static/zscript/raven/ravenhealth.txt new file mode 100644 index 000000000..cf7c79d0a --- /dev/null +++ b/wadsrc/static/zscript/raven/ravenhealth.txt @@ -0,0 +1,16 @@ +class CrystalVial : Health +{ + Default + { + +FLOATBOB + Inventory.Amount 10; + Inventory.PickupMessage "$TXT_ITEMHEALTH"; + } + States + { + Spawn: + PTN1 ABC 3; + Loop; + } +} + From c13916ea1801388b840f83b0f14e3e6e1e688940 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 10:07:12 +0200 Subject: [PATCH 054/255] - converted more Heretic actors. --- src/scripting/codegeneration/codegen.cpp | 1 - wadsrc/static/actors/heretic/beast.txt | 109 -- wadsrc/static/actors/heretic/clink.txt | 46 - wadsrc/static/actors/heretic/hereticimp.txt | 156 -- wadsrc/static/actors/heretic/hereticweaps.txt | 1133 --------------- wadsrc/static/actors/heretic/mummy.txt | 133 -- wadsrc/static/actors/heretic/snake.txt | 95 -- wadsrc/static/decorate.txt | 6 - wadsrc/static/zscript.txt | 2 +- wadsrc/static/zscript/heretic/clink.txt | 48 + wadsrc/static/zscript/heretic/hereticimp.txt | 171 +++ .../static/zscript/heretic/hereticweaps.txt | 1286 +++++++++++++++++ wadsrc/static/zscript/heretic/mummy.txt | 151 ++ wadsrc/static/zscript/heretic/snake.txt | 104 ++ 14 files changed, 1761 insertions(+), 1680 deletions(-) delete mode 100644 wadsrc/static/actors/heretic/beast.txt delete mode 100644 wadsrc/static/actors/heretic/clink.txt delete mode 100644 wadsrc/static/actors/heretic/hereticimp.txt delete mode 100644 wadsrc/static/actors/heretic/hereticweaps.txt delete mode 100644 wadsrc/static/actors/heretic/mummy.txt delete mode 100644 wadsrc/static/actors/heretic/snake.txt create mode 100644 wadsrc/static/zscript/heretic/clink.txt create mode 100644 wadsrc/static/zscript/heretic/hereticimp.txt create mode 100644 wadsrc/static/zscript/heretic/hereticweaps.txt create mode 100644 wadsrc/static/zscript/heretic/mummy.txt create mode 100644 wadsrc/static/zscript/heretic/snake.txt diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d7a3a56b0..f56735797 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4297,7 +4297,6 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) // Note that for all builtins the used arguments have to be nulled in the ArgList so that they won't get deleted before they get used. FxExpression *func = nullptr; - Printf("Resolving %s with %d args\n", MethodName.GetChars(), ArgList->Size()); switch (MethodName) { case NAME_Random: diff --git a/wadsrc/static/actors/heretic/beast.txt b/wadsrc/static/actors/heretic/beast.txt deleted file mode 100644 index 73eb630ec..000000000 --- a/wadsrc/static/actors/heretic/beast.txt +++ /dev/null @@ -1,109 +0,0 @@ - -// Beast -------------------------------------------------------------------- - -ACTOR Beast -{ - Health 220 - Radius 32 - Height 74 - Mass 200 - Speed 14 - Painchance 100 - Monster - +FLOORCLIP - SeeSound "beast/sight" - AttackSound "beast/attack" - PainSound "beast/pain" - DeathSound "beast/death" - ActiveSound "beast/active" - Obituary "$OB_BEAST" - DropItem "CrossbowAmmo", 84, 10 - States - { - Spawn: - BEAS AB 10 A_Look - Loop - See: - BEAS ABCDEF 3 A_Chase - Loop - Missile: - BEAS H 10 A_FaceTarget - BEAS I 10 A_CustomComboAttack("BeastBall", 32, random[BeastAttack](1,8)*3, "beast/attack") - Goto See - Pain: - BEAS G 3 - BEAS G 3 A_Pain - Goto See - Death: - BEAS R 6 - BEAS S 6 A_Scream - BEAS TUV 6 - BEAS W 6 A_NoBlocking - BEAS XY 6 - BEAS Z -1 - Stop - XDeath: - BEAS J 5 - BEAS K 6 A_Scream - BEAS L 5 - BEAS M 6 - BEAS N 5 - BEAS O 6 A_NoBlocking - BEAS P 5 - BEAS Q -1 - Stop - } -} - -// Beast ball --------------------------------------------------------------- - -ACTOR BeastBall -{ - Radius 9 - Height 8 - Speed 12 - FastSpeed 20 - Damage 4 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - -NOBLOCKMAP - +WINDTHRUST - +SPAWNSOUNDSOURCE - RenderStyle Add - SeeSound "beast/attack" - States - { - Spawn: - FRB1 AABBCC 2 A_SpawnItemEx("Puffy", random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, random2[BeastPuff]()*0.015625, - 0,0,0,0,SXF_ABSOLUTEPOSITION, 64) - Loop - Death: - FRB1 DEFGH 4 - Stop - } -} - -// Puffy -------------------------------------------------------------------- - -ACTOR Puffy -{ - Radius 6 - Height 8 - Speed 10 - +NOBLOCKMAP - +NOGRAVITY - +MISSILE - +NOTELEPORT - +DONTSPLASH - RenderStyle Add - States - { - Spawn: - FRB1 DEFGH 4 - Stop - } -} - - - diff --git a/wadsrc/static/actors/heretic/clink.txt b/wadsrc/static/actors/heretic/clink.txt deleted file mode 100644 index 7f3e4370d..000000000 --- a/wadsrc/static/actors/heretic/clink.txt +++ /dev/null @@ -1,46 +0,0 @@ - -ACTOR Clink -{ - Health 150 - Radius 20 - Height 64 - Mass 75 - Speed 14 - Painchance 32 - Monster - +NOBLOOD - +FLOORCLIP - SeeSound "clink/sight" - AttackSound "clink/attack" - PainSound "clink/pain" - DeathSound "clink/death" - ActiveSound "clink/active" - Obituary "$OB_CLINK" - DropItem "SkullRodAmmo", 84, 20 - States - { - Spawn: - CLNK AB 10 A_Look - Loop - See: - CLNK ABCD 3 A_Chase - Loop - Melee: - CLNK E 5 A_FaceTarget - CLNK F 4 A_FaceTarget - CLNK G 7 A_CustomMeleeAttack(random[ClinkAttack](3,9), "clink/attack", "clink/attack") - Goto See - Pain: - CLNK H 3 - CLNK H 3 A_Pain - Goto See - Death: - CLNK IJ 6 - CLNK K 5 A_Scream - CLNK L 5 A_NoBlocking - CLNK MN 5 - CLNK O -1 - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/hereticimp.txt b/wadsrc/static/actors/heretic/hereticimp.txt deleted file mode 100644 index fdbdeb9b7..000000000 --- a/wadsrc/static/actors/heretic/hereticimp.txt +++ /dev/null @@ -1,156 +0,0 @@ - -// Heretic imp (as opposed to the Doom variety) ----------------------------- - -ACTOR HereticImp -{ - Health 40 - Radius 16 - Height 36 - Mass 50 - Speed 10 - Painchance 200 - Monster - +FLOAT - +NOGRAVITY - +SPAWNFLOAT - +DONTOVERLAP - +MISSILEMORE - SeeSound "himp/sight" - AttackSound "himp/attack" - PainSound "himp/pain" - DeathSound "himp/death" - ActiveSound "himp/active" - Obituary "$OB_HERETICIMP" - HitObituary "$OB_HERETICIMPHIT" - - action native A_ImpMsAttack(); - action native A_ImpDeath(); - action native A_ImpXDeath1(); - action native A_ImpExplode(); - - - States - { - Spawn: - IMPX ABCB 10 A_Look - Loop - See: - IMPX AABBCCBB 3 A_Chase - Loop - Melee: - IMPX DE 6 A_FaceTarget - IMPX F 6 A_CustomMeleeAttack(random[ImpMeAttack](5,12), "himp/attack", "himp/attack") - Goto See - Missile: - IMPX A 10 A_FaceTarget - IMPX B 6 A_ImpMsAttack - IMPX CBAB 6 - Goto Missile+2 - Pain: - IMPX G 3 - IMPX G 3 A_Pain - Goto See - Death: - IMPX G 4 A_ImpDeath - IMPX H 5 - Wait - XDeath: - IMPX S 5 A_ImpXDeath1 - IMPX TU 5 - IMPX V 5 A_Gravity - IMPX W 5 - Wait - Crash: - IMPX I 7 A_ImpExplode - IMPX J 7 A_Scream - IMPX K 7 - IMPX L -1 - Stop - XCrash: - IMPX X 7 - IMPX Y 7 - IMPX Z -1 - Stop - } -} - -// Heretic imp leader ------------------------------------------------------- - -ACTOR HereticImpLeader : HereticImp -{ - Species "HereticImpLeader" - Health 80 - -MISSILEMORE - AttackSound "himp/leaderattack" - States - { - Melee: - Stop - Missile: - IMPX DE 6 A_FaceTarget - IMPX F 6 A_CustomComboAttack("HereticImpBall", 32, random[ImpMsAttack2](5,12), "himp/leaderattack") - Goto See - } -} - -// Heretic imp chunk 1 ------------------------------------------------------ - -ACTOR HereticImpChunk1 -{ - Mass 5 - Radius 4 - +NOBLOCKMAP - +MOVEWITHSECTOR - States - { - Spawn: - IMPX M 5 - IMPX NO 700 - Stop - } -} - -// Heretic imp chunk 2 ------------------------------------------------------ - -ACTOR HereticImpChunk2 -{ - Mass 5 - Radius 4 - +NOBLOCKMAP - +MOVEWITHSECTOR - States - { - Spawn: - IMPX P 5 - IMPX QR 700 - Stop - } -} - -// Heretic imp ball --------------------------------------------------------- - -ACTOR HereticImpBall -{ - Radius 8 - Height 8 - Speed 10 - FastSpeed 20 - Damage 1 - Projectile - SeeSound "himp/leaderattack" - +SPAWNSOUNDSOURCE - -ACTIVATEPCROSS - -ACTIVATEIMPACT - RenderStyle Add - States - { - Spawn: - FX10 ABC 6 Bright - Loop - Death: - FX10 DEFG 5 Bright - Stop - } -} - - diff --git a/wadsrc/static/actors/heretic/hereticweaps.txt b/wadsrc/static/actors/heretic/hereticweaps.txt deleted file mode 100644 index 41461379a..000000000 --- a/wadsrc/static/actors/heretic/hereticweaps.txt +++ /dev/null @@ -1,1133 +0,0 @@ - -ACTOR HereticWeapon : Weapon -{ - Weapon.Kickback 150 -} - - -// Staff -------------------------------------------------------------------- - -ACTOR Staff : HereticWeapon -{ - Weapon.SelectionOrder 3800 - +THRUGHOST - +WIMPY_WEAPON - +MELEEWEAPON - Weapon.sisterweapon "StaffPowered" - Obituary "$OB_MPSTAFF" - Tag "$TAG_STAFF" - - action native A_StaffAttack (int damage, class puff); - - States - { - Ready: - STFF A 1 A_WeaponReady - Loop - Deselect: - STFF A 1 A_Lower - Loop - Select: - STFF A 1 A_Raise - Loop - Fire: - STFF B 6 - STFF C 8 A_StaffAttack(random[StaffAttack](5, 20), "StaffPuff") - STFF B 8 A_ReFire - Goto Ready - } -} - -ACTOR StaffPowered : Staff -{ - Weapon.sisterweapon "Staff" - Weapon.ReadySound "weapons/staffcrackle" - +WEAPON.POWERED_UP - +WEAPON.READYSNDHALF - +WEAPON.STAFF2_KICKBACK - Obituary "$OB_MPPSTAFF" - Tag "$TAG_STAFFP" - States - { - Ready: - STFF DEF 4 A_WeaponReady - Loop - Deselect: - STFF D 1 A_Lower - Loop - Select: - STFF D 1 A_Raise - Loop - Fire: - STFF G 6 - STFF H 8 A_StaffAttack(random[StaffAttack](18, 81), "StaffPuff2") - STFF G 8 A_ReFire - Goto Ready - } -} - - -// Staff puff --------------------------------------------------------------- - -ACTOR StaffPuff -{ - RenderStyle Translucent - Alpha 0.4 - VSpeed 1 - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - AttackSound "weapons/staffhit" - States - { - Spawn: - PUF3 A 4 BRIGHT - PUF3 BCD 4 - Stop - } -} - -// Staff puff 2 ------------------------------------------------------------- - -ACTOR StaffPuff2 -{ - RenderStyle Add - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - AttackSound "weapons/staffpowerhit" - States - { - Spawn: - PUF4 ABCDEF 4 BRIGHT - Stop - } -} - - - -// Gold wand ---------------------------------------------------------------- - -ACTOR GoldWand : HereticWeapon -{ - +BLOODSPLATTER - Weapon.SelectionOrder 2000 - Weapon.AmmoGive 25 - Weapon.AmmoUse 1 - Weapon.AmmoType "GoldWandAmmo" - Weapon.SisterWeapon "GoldWandPowered" - Weapon.YAdjust 5 - Inventory.PickupMessage "$TXT_WPNGOLDWAND" - Obituary "$OB_MPGOLDWAND" - Tag "$TAG_GOLDWAND" - - action native A_FireGoldWandPL1 (); - - States - { - Spawn: - GWAN A -1 - Stop - Ready: - GWND A 1 A_WeaponReady - Loop - Deselect: - GWND A 1 A_Lower - Loop - Select: - GWND A 1 A_Raise - Loop - Fire: - GWND B 3 - GWND C 5 A_FireGoldWandPL1 - GWND D 3 - GWND D 0 A_ReFire - Goto Ready - } -} - -ACTOR GoldWandPowered : GoldWand -{ - +WEAPON.POWERED_UP - Weapon.AmmoGive 0 - Weapon.SisterWeapon "GoldWand" - Obituary "$OB_MPPGOLDWAND" - Tag "$TAG_GOLDWANDP" - - action native A_FireGoldWandPL2 (); - - States - { - Fire: - GWND B 3 - GWND C 4 A_FireGoldWandPL2 - GWND D 3 - GWND D 0 A_ReFire - Goto Ready - } -} - - -// Gold wand FX1 ------------------------------------------------------------ - -ACTOR GoldWandFX1 -{ - Radius 10 - Height 6 - Speed 22 - Damage 2 - Projectile - RenderStyle Add - DeathSound "weapons/wandhit" - Obituary "$OB_MPPGOLDWAND" - States - { - Spawn: - FX01 AB 6 BRIGHT - Loop - Death: - FX01 EFGH 3 BRIGHT - Stop - } -} - -// Gold wand FX2 ------------------------------------------------------------ - -ACTOR GoldWandFX2 : GoldWandFX1 -{ - Speed 18 - Damage 1 - DeathSound "" - States - { - Spawn: - FX01 CD 6 BRIGHT - Loop - } -} - -// Gold wand puff 1 --------------------------------------------------------- - -ACTOR GoldWandPuff1 -{ - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - RenderStyle Add - States - { - Spawn: - PUF2 ABCDE 3 BRIGHT - Stop - } -} - -// Gold wand puff 2 --------------------------------------------------------- - -ACTOR GoldWandPuff2 : GoldWandFX1 -{ - Skip_Super - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - States - { - Spawn: - Goto Super::Death - } -} - - -// Crossbow ----------------------------------------------------------------- - -ACTOR Crossbow : HereticWeapon -{ - Weapon.SelectionOrder 800 - Weapon.AmmoUse 1 - Weapon.AmmoGive 10 - Weapon.AmmoType "CrossbowAmmo" - Weapon.SisterWeapon "CrossbowPowered" - Weapon.YAdjust 15 - Inventory.PickupMessage "$TXT_WPNCROSSBOW" - Tag "$TAG_CROSSBOW" - - action native A_FireCrossbowPL1 (); - - States - { - Spawn: - WBOW A -1 - Stop - Ready: - CRBW AAAAAABBBBBBCCCCCC 1 A_WeaponReady - Loop - Deselect: - CRBW A 1 A_Lower - Loop - Select: - CRBW A 1 A_Raise - Loop - Fire: - CRBW D 6 A_FireCrossbowPL1 - CRBW EFGH 3 - CRBW AB 4 - CRBW C 5 A_ReFire - Goto Ready - } -} - - -ACTOR CrossbowPowered : Crossbow -{ - +WEAPON.POWERED_UP - Weapon.AmmoGive 0 - Weapon.SisterWeapon "Crossbow" - Tag "$TAG_CROSSBOWP" - - action native A_FireCrossbowPL2(); - - States - { - Fire: - CRBW D 5 A_FireCrossbowPL2 - CRBW E 3 - CRBW F 2 - CRBW G 3 - CRBW H 2 - CRBW A 3 - CRBW B 3 - CRBW C 4 A_ReFire - Goto Ready - } -} - - -// Crossbow FX1 ------------------------------------------------------------- - -ACTOR CrossbowFX1 -{ - Radius 11 - Height 8 - Speed 30 - Damage 10 - Projectile - RenderStyle Add - SeeSound "weapons/bowshoot" - DeathSound "weapons/bowhit" - Obituary "$OB_MPCROSSBOW" - States - { - Spawn: - FX03 B 1 BRIGHT - Loop - Death: - FX03 HIJ 8 BRIGHT - Stop - } -} - - -// Crossbow FX2 ------------------------------------------------------------- - -ACTOR CrossbowFX2 : CrossbowFX1 -{ - Speed 32 - Damage 6 - Obituary "$OB_MPPCROSSBOW" - States - { - Spawn: - FX03 B 1 BRIGHT A_SpawnItemEx("CrossbowFX4", random2[BoltSpark]()*0.015625, random2[BoltSpark]()*0.015625, 0, 0,0,0,0,SXF_ABSOLUTEPOSITION, 50) - Loop - } -} - -// Crossbow FX3 ------------------------------------------------------------- - -ACTOR CrossbowFX3 : CrossbowFX1 -{ - Speed 20 - Damage 2 - SeeSound "" - -NOBLOCKMAP - +WINDTHRUST - +THRUGHOST - States - { - Spawn: - FX03 A 1 BRIGHT - Loop - Death: - FX03 CDE 8 BRIGHT - Stop - } -} - -// Crossbow FX4 ------------------------------------------------------------- - -ACTOR CrossbowFX4 -{ - +NOBLOCKMAP - Gravity 0.125 - RenderStyle Add - States - { - Spawn: - FX03 FG 8 BRIGHT - Stop - } -} - - - - -// Gauntlets ---------------------------------------------------------------- - -ACTOR Gauntlets : Weapon -{ - +BLOODSPLATTER - Weapon.SelectionOrder 2300 - +WEAPON.WIMPY_WEAPON - +WEAPON.MELEEWEAPON - Weapon.Kickback 0 - Weapon.YAdjust 15 - Weapon.UpSound "weapons/gauntletsactivate" - Weapon.SisterWeapon "GauntletsPowered" - Inventory.PickupMessage "$TXT_WPNGAUNTLETS" - Tag "$TAG_GAUNTLETS" - Obituary "$OB_MPGAUNTLETS" - - action native A_GauntletAttack (int power); - - States - { - Spawn: - WGNT A -1 - Stop - Ready: - GAUN A 1 A_WeaponReady - Loop - Deselect: - GAUN A 1 A_Lower - Loop - Select: - GAUN A 1 A_Raise - Loop - Fire: - GAUN B 4 A_PlayWeaponSound("weapons/gauntletsuse") - GAUN C 4 - Hold: - GAUN DEF 4 BRIGHT A_GauntletAttack(0) - GAUN C 4 A_ReFire - GAUN B 4 A_Light0 - Goto Ready - } -} - - -ACTOR GauntletsPowered : Gauntlets -{ - +POWERED_UP - Tag "$TAG_GAUNTLETSP" - Obituary "$OB_MPPGAUNTLETS" - Weapon.SisterWeapon "Gauntlets" - States - { - Ready: - GAUN GHI 4 A_WeaponReady - Loop - Deselect: - GAUN G 1 A_Lower - Loop - Select: - GAUN G 1 A_Raise - Loop - Fire: - GAUN J 4 A_PlayWeaponSound("weapons/gauntletsuse") - GAUN K 4 - Hold: - GAUN LMN 4 BRIGHT A_GauntletAttack(1) - GAUN K 4 A_ReFire - GAUN J 4 A_Light0 - Goto Ready - } -} - - -// Gauntlet puff 1 ---------------------------------------------------------- - -ACTOR GauntletPuff1 -{ - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - RenderStyle Translucent - Alpha 0.4 - VSpeed 0.8 - States - { - Spawn: - PUF1 ABCD 4 BRIGHT - Stop - } -} - -// Gauntlet puff 2 --------------------------------------------------------- - -ACTOR GauntletPuff2 : GauntletPuff1 -{ - States - { - Spawn: - PUF1 EFGH 4 BRIGHT - Stop - } -} - - -// The mace itself ---------------------------------------------------------- - -ACTOR Mace : HereticWeapon -{ - Weapon.SelectionOrder 1400 - Weapon.AmmoUse 1 - Weapon.AmmoGive1 50 - Weapon.YAdjust 15 - Weapon.AmmoType "MaceAmmo" - Weapon.SisterWeapon "MacePowered" - Inventory.PickupMessage "$TXT_WPNMACE" - Tag "$TAG_MACE" - - action native A_FireMacePL1(); - - States - { - Spawn: - WMCE A -1 - Stop - Ready: - MACE A 1 A_WeaponReady - Loop - Deselect: - MACE A 1 A_Lower - Loop - Select: - MACE A 1 A_Raise - Loop - Fire: - MACE B 4 - Hold: - MACE CDEF 3 A_FireMacePL1 - MACE C 4 A_ReFire - MACE DEFB 4 - Goto Ready - } -} - -ACTOR MacePowered : Mace -{ - +WEAPON.POWERED_UP - Weapon.AmmoUse 5 - Weapon.AmmoGive 0 - Weapon.SisterWeapon "Mace" - Tag "$TAG_MACEP" - - action native A_FireMacePL2(); - - States - { - Fire: - Hold: - MACE B 4 - MACE D 4 A_FireMacePL2 - MACE B 4 - MACE A 8 A_ReFire - Goto Ready - } -} - -// Mace FX1 ----------------------------------------------------------------- - -ACTOR MaceFX1 -{ - Radius 8 - Height 6 - Speed 20 - Damage 2 - Projectile - +THRUGHOST - BounceType "HereticCompat" - SeeSound "weapons/maceshoot" - Obituary "$OB_MPMACE" - - action native A_MacePL1Check(); - action native A_MaceBallImpact(); - - States - { - Spawn: - FX02 AB 4 A_MacePL1Check - Loop - Death: - FX02 F 4 BRIGHT A_MaceBallImpact - FX02 GHIJ 4 BRIGHT - Stop - } -} - -// Mace FX2 ----------------------------------------------------------------- - -ACTOR MaceFX2 : MaceFX1 -{ - Speed 10 - Damage 6 - Gravity 0.125 - -NOGRAVITY - SeeSound "" - - action native A_MaceBallImpact2(); - - States - { - Spawn: - FX02 CD 4 - Loop - Death: - FX02 F 4 A_MaceBallImpact2 - goto Super::Death+1 - } -} - -// Mace FX3 ----------------------------------------------------------------- - -ACTOR MaceFX3 : MaceFX1 -{ - Speed 7 - Damage 4 - -NOGRAVITY - Gravity 0.125 - States - { - Spawn: - FX02 AB 4 - Loop - } -} - - -// Mace FX4 ----------------------------------------------------------------- - -ACTOR MaceFX4 native -{ - Radius 8 - Height 6 - Speed 7 - Damage 18 - Gravity 0.125 - Projectile - -NOGRAVITY - +TELESTOMP - +THRUGHOST - -NOTELEPORT - BounceType "HereticCompat" - SeeSound "" - Obituary "$OB_MPPMACE" - - action native A_DeathBallImpact(); - - States - { - Spawn: - FX02 E 99 - Loop - Death: - FX02 C 4 A_DeathBallImpact - FX02 GHIJ 4 BRIGHT - Stop - } -} - - -// Mace spawn spot ---------------------------------------------------------- - -ACTOR MaceSpawner : SpecialSpot -{ - +NOSECTOR - +NOBLOCKMAP - States - { - Spawn: - TNT1 A 1 - TNT1 A -1 A_SpawnSingleItem("Mace", 64, 64, 0) - Stop - } -} - - -// Blaster ------------------------------------------------------------------ - -ACTOR Blaster : HereticWeapon -{ - +BLOODSPLATTER - Weapon.SelectionOrder 500 - Weapon.AmmoUse 1 - Weapon.AmmoGive 30 - Weapon.YAdjust 15 - Weapon.AmmoType "BlasterAmmo" - Weapon.SisterWeapon "BlasterPowered" - Inventory.PickupMessage "$TXT_WPNBLASTER" - Tag "$TAG_BLASTER" - Obituary "$OB_MPBLASTER" - - action native A_FireBlasterPL1(); - - States - { - Spawn: - WBLS A -1 - Stop - Ready: - BLSR A 1 A_WeaponReady - Loop - Deselect: - BLSR A 1 A_Lower - Loop - Select: - BLSR A 1 A_Raise - Loop - Fire: - BLSR BC 3 - Hold: - BLSR D 2 A_FireBlasterPL1 - BLSR CB 2 - BLSR A 0 A_ReFire - Goto Ready - } -} - -ACTOR BlasterPowered : Blaster -{ - +WEAPON.POWERED_UP - Weapon.AmmoUse 5 - Weapon.AmmoGive 0 - Weapon.SisterWeapon "Blaster" - Tag "$TAG_BLASTERP" - States - { - Fire: - BLSR BC 0 - Hold: - BLSR D 3 A_FireCustomMissile("BlasterFX1") - BLSR CB 4 - BLSR A 0 A_ReFire - Goto Ready - } -} - -// Blaster FX 1 ------------------------------------------------------------- - -ACTOR BlasterFX1 : FastProjectile native -{ - Radius 12 - Height 8 - Speed 184 - Damage 2 - SeeSound "weapons/blastershoot" - DeathSound "weapons/blasterhit" - +SPAWNSOUNDSOURCE - Obituary "$OB_MPPBLASTER" - - action native A_SpawnRippers(); - - States - { - Spawn: - ACLO E 200 - Loop - Death: - FX18 A 3 BRIGHT A_SpawnRippers - FX18 B 3 BRIGHT - FX18 CDEFG 4 BRIGHT - Stop - } -} - -// Blaster smoke ------------------------------------------------------------ - -ACTOR BlasterSmoke -{ - +NOBLOCKMAP - +NOGRAVITY - +NOTELEPORT - +CANNOTPUSH - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - FX18 HIJKL 4 - Stop - } -} - -// Ripper ------------------------------------------------------------------- - -ACTOR Ripper native -{ - Radius 8 - Height 6 - Speed 14 - Damage 1 - Projectile - +RIPPER - DeathSound "weapons/blasterpowhit" - Obituary "$OB_MPPBLASTER" - States - { - Spawn: - FX18 M 4 - FX18 N 5 - Loop - Death: - FX18 OPQRS 4 BRIGHT - Stop - } -} - -// Blaster Puff ------------------------------------------------------------- - -ACTOR BlasterPuff -{ - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - RenderStyle Add - SeeSound "weapons/blasterhit" - States - { - Crash: - FX17 ABCDE 4 BRIGHT - Stop - Spawn: - FX17 FG 3 BRIGHT - FX17 HIJKL 4 BRIGHT - Stop - } -} - - -// Skull (Horn) Rod --------------------------------------------------------- - -ACTOR SkullRod : HereticWeapon -{ - Weapon.SelectionOrder 200 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 50 - Weapon.YAdjust 15 - Weapon.AmmoType1 "SkullRodAmmo" - Weapon.SisterWeapon "SkullRodPowered" - Inventory.PickupMessage "$TXT_WPNSKULLROD" - Tag "$TAG_SKULLROD" - - action native A_FireSkullRodPL1(); - - States - { - Spawn: - WSKL A -1 - Stop - Ready: - HROD A 1 A_WeaponReady - Loop - Deselect: - HROD A 1 A_Lower - Loop - Select: - HROD A 1 A_Raise - Loop - Fire: - HROD AB 4 A_FireSkullRodPL1 - HROD B 0 A_ReFire - Goto Ready - } -} - -ACTOR SkullRodPowered : SkullRod -{ - +WEAPON.POWERED_UP - Weapon.AmmoUse1 5 - Weapon.AmmoGive1 0 - Weapon.SisterWeapon "SkullRod" - Tag "$TAG_SKULLRODP" - - action native A_FireSkullRodPL2(); - - States - { - Fire: - HROD C 2 - HROD D 3 - HROD E 2 - HROD F 3 - HROD G 4 A_FireSkullRodPL2 - HROD F 2 - HROD E 3 - HROD D 2 - HROD C 2 A_ReFire - Goto Ready - } -} - -// Horn Rod FX 1 ------------------------------------------------------------ - -ACTOR HornRodFX1 -{ - Radius 12 - Height 8 - Speed 22 - Damage 3 - Projectile - +WINDTHRUST - -NOBLOCKMAP - RenderStyle Add - SeeSound "weapons/hornrodshoot" - DeathSound "weapons/hornrodhit" - Obituary "$OB_MPSKULLROD" - States - { - Spawn: - FX00 AB 6 BRIGHT - Loop - Death: - FX00 HI 5 BRIGHT - FX00 JK 4 BRIGHT - FX00 LM 3 BRIGHT - Stop - } -} - - -// Horn Rod FX 2 ------------------------------------------------------------ - -ACTOR HornRodFX2 native -{ - Radius 12 - Height 8 - Speed 22 - Damage 10 - Health 140 - Projectile - RenderStyle Add - SeeSound "weapons/hornrodpowshoot" - DeathSound "weapons/hornrodpowhit" - Obituary "$OB_MPPSKULLROD" - - action native A_AddPlayerRain(); - action native A_HideInCeiling(); - action native A_SkullRodStorm(); - - States - { - Spawn: - FX00 C 3 BRIGHT - FX00 D 3 BRIGHT A_SeekerMissile(10, 30) - FX00 E 3 BRIGHT - FX00 F 3 BRIGHT A_SeekerMissile(10, 30) - Loop - Death: - FX00 H 5 BRIGHT A_AddPlayerRain - FX00 I 5 BRIGHT - FX00 J 4 BRIGHT - FX00 KLM 3 BRIGHT - FX00 G 1 A_HideInCeiling - FX00 G 1 A_SkullRodStorm - Wait - } -} - -// Rain pillar 1 ------------------------------------------------------------ - -ACTOR RainPillar native -{ - Radius 5 - Height 12 - Speed 12 - Damage 5 - Mass 5 - Projectile - -ACTIVATEPCROSS - -ACTIVATEIMPACT - RenderStyle Add - Obituary "$OB_MPPSKULLROD" - - action native A_RainImpact(); - - States - { - Spawn: - FX22 A -1 BRIGHT - Stop - Death: - FX22 B 4 BRIGHT A_RainImpact - FX22 CDEF 4 BRIGHT - Stop - NotFloor: - FX22 GHI 4 BRIGHT - Stop - } -} - -// Rain tracker "inventory" item -------------------------------------------- - -ACTOR RainTracker : Inventory native -{ - +INVENTORY.UNDROPPABLE -} - - -// Phoenix Rod -------------------------------------------------------------- - -ACTOR PhoenixRod : Weapon native -{ - +WEAPON.NOAUTOFIRE - Weapon.SelectionOrder 2600 - Weapon.Kickback 150 - Weapon.YAdjust 15 - Weapon.AmmoUse 1 - Weapon.AmmoGive 2 - Weapon.AmmoType "PhoenixRodAmmo" - Weapon.Sisterweapon "PhoenixRodPowered" - Inventory.PickupMessage "$TXT_WPNPHOENIxROD" - Tag "$TAG_PHOENIxROD" - - action native A_FirePhoenixPL1(); - - States - { - Spawn: - WPHX A -1 - Stop - Ready: - PHNX A 1 A_WeaponReady - Loop - Deselect: - PHNX A 1 A_Lower - Loop - Select: - PHNX A 1 A_Raise - Loop - Fire: - PHNX B 5 - PHNX C 7 A_FirePhoenixPL1 - PHNX DB 4 - PHNX B 0 A_ReFire - Goto Ready - } -} - -ACTOR PhoenixRodPowered : PhoenixRod native -{ - +WEAPON.POWERED_UP - +WEAPON.MELEEWEAPON - Weapon.SisterWeapon "PhoenixRod" - Weapon.AmmoGive 0 - Tag "$TAG_PHOENIxRODP" - - action native A_InitPhoenixPL2(); - action native A_FirePhoenixPL2(); - action native A_ShutdownPhoenixPL2(); - - States - { - Fire: - PHNX B 3 A_InitPhoenixPL2 - Hold: - PHNX C 1 A_FirePhoenixPL2 - PHNX B 4 A_ReFire - Powerdown: - PHNX B 4 A_ShutdownPhoenixPL2 - Goto Ready - } -} - -// Phoenix FX 1 ------------------------------------------------------------- - -ACTOR PhoenixFX1 native -{ - Radius 11 - Height 8 - Speed 20 - Damage 20 - DamageType Fire - Projectile - +THRUGHOST - +SPECIALFIREDAMAGE - SeeSound "weapons/phoenixshoot" - DeathSound "weapons/phoenixhit" - Obituary "$OB_MPPHOENIXROD" - - action native A_PhoenixPuff(); - - States - { - Spawn: - FX04 A 4 BRIGHT A_PhoenixPuff - Loop - Death: - FX08 A 6 BRIGHT A_Explode - FX08 BC 5 BRIGHT - FX08 DEFGH 4 BRIGHT - Stop - } -} - -// Phoenix puff ------------------------------------------------------------- - -ACTOR PhoenixPuff -{ - +NOBLOCKMAP - +NOGRAVITY - +NOTELEPORT - +CANNOTPUSH - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - FX04 BCDEF 4 - Stop - } -} - -// Phoenix FX 2 ------------------------------------------------------------- - -ACTOR PhoenixFX2 native -{ - Radius 6 - Height 8 - Speed 10 - Damage 2 - DamageType Fire - Projectile - RenderStyle Add - Obituary "$OB_MPPPHOENIXROD" - - action native A_FlameEnd(); - action native A_FloatPuff(); - - States - { - Spawn: - FX09 ABABA 2 BRIGHT - FX09 B 2 BRIGHT A_FlameEnd - FX09 CDEF 2 BRIGHT - Stop - Death: - FX09 G 3 BRIGHT - FX09 H 3 BRIGHT A_FloatPuff - FX09 I 4 BRIGHT - FX09 JK 5 BRIGHT - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/mummy.txt b/wadsrc/static/actors/heretic/mummy.txt deleted file mode 100644 index 331f315cd..000000000 --- a/wadsrc/static/actors/heretic/mummy.txt +++ /dev/null @@ -1,133 +0,0 @@ - -// Mummy -------------------------------------------------------------------- - -ACTOR Mummy -{ - Health 80 - Radius 22 - Height 62 - Mass 75 - Speed 12 - Painchance 128 - Monster - +FLOORCLIP - SeeSound "mummy/sight" - AttackSound "mummy/attack1" - PainSound "mummy/pain" - DeathSound "mummy/death" - ActiveSound "mummy/active" - HitObituary "$OB_MUMMY" - DropItem "GoldWandAmmo", 84, 3 - States - { - Spawn: - MUMM AB 10 A_Look - Loop - See: - MUMM ABCD 4 A_Chase - Loop - Melee: - MUMM E 6 A_FaceTarget - MUMM F 6 A_CustomMeleeAttack(random[MummyAttack](1,8)*2, "mummy/attack2", "mummy/attack") - MUMM G 6 - Goto See - Pain: - MUMM H 4 - MUMM H 4 A_Pain - Goto See - Death: - MUMM I 5 - MUMM J 5 A_Scream - MUMM K 5 A_SpawnItemEx("MummySoul", 0,0,10, 0,0,1) - MUMM L 5 - MUMM M 5 A_NoBlocking - MUMM NO 5 - MUMM P -1 - Stop - } -} - -// Mummy leader ------------------------------------------------------------- - -ACTOR MummyLeader : Mummy -{ - Species "MummyLeader" - Health 100 - Painchance 64 - Obituary "$OB_MUMMYLEADER" - States - { - Missile: - MUMM X 5 A_FaceTarget - MUMM Y 5 Bright A_FaceTarget - MUMM X 5 A_FaceTarget - MUMM Y 5 Bright A_FaceTarget - MUMM X 5 A_FaceTarget - MUMM Y 5 Bright A_CustomComboAttack("MummyFX1", 32, random[MummyAttack2](1,8)*2, "mummy/attack2") - Goto See - } -} - -// Mummy ghost -------------------------------------------------------------- - -ACTOR MummyGhost : Mummy -{ - +SHADOW - +GHOST - RenderStyle Translucent - Alpha 0.4 -} - -// Mummy leader ghost ------------------------------------------------------- - -ACTOR MummyLeaderGhost : MummyLeader -{ - Species "MummyLeaderGhost" - +SHADOW - +GHOST - RenderStyle Translucent - Alpha 0.4 -} - -// Mummy soul --------------------------------------------------------------- - -ACTOR MummySoul -{ - +NOBLOCKMAP - +NOGRAVITY - States - { - Spawn: - MUMM QRS 5 - MUMM TUVW 9 - Stop - } -} - -// Mummy FX 1 (flying head) ------------------------------------------------- - -ACTOR MummyFX1 -{ - Radius 8 - Height 14 - Speed 9 - FastSpeed 18 - Damage 4 - RenderStyle Add - Projectile - -ACTIVATEPCROSS - -ACTIVATEIMPACT - +SEEKERMISSILE - States - { - Spawn: - FX15 A 5 Bright A_PlaySound("mummy/head") - FX15 B 5 Bright A_SeekerMissile(10,20) - FX15 C 5 Bright - FX15 B 5 Bright A_SeekerMissile(10,20) - Loop - Death: - FX15 DEFG 5 Bright - Stop - } -} diff --git a/wadsrc/static/actors/heretic/snake.txt b/wadsrc/static/actors/heretic/snake.txt deleted file mode 100644 index bb9beb3dd..000000000 --- a/wadsrc/static/actors/heretic/snake.txt +++ /dev/null @@ -1,95 +0,0 @@ - -ACTOR Snake -{ - Health 280 - Radius 22 - Height 70 - Speed 10 - Painchance 48 - Monster - +FLOORCLIP - AttackSound "snake/attack" - SeeSound "snake/sight" - PainSound "snake/pain" - DeathSound "snake/death" - ActiveSound "snake/active" - Obituary "$OB_SNAKE" - DropItem "PhoenixRodAmmo", 84, 5 - States - { - Spawn: - SNKE AB 10 A_Look - Loop - See: - SNKE ABCD 4 A_Chase - Loop - Missile: - SNKE FF 5 A_FaceTarget - SNKE FFF 4 A_CustomMissile("SnakeProjA", 32, 0, 0, CMF_CHECKTARGETDEAD) - SNKE FFF 5 A_FaceTarget - SNKE F 4 A_CustomMissile("SnakeProjB", 32, 0, 0, CMF_CHECKTARGETDEAD) - Goto See - Pain: - SNKE E 3 - SNKE E 3 A_Pain - Goto See - Death: - SNKE G 5 - SNKE H 5 A_Scream - SNKE IJKL 5 - SNKE M 5 A_NoBlocking - SNKE NO 5 - SNKE P -1 - Stop - } -} - -// Snake projectile A ------------------------------------------------------- - -ACTOR SnakeProjA -{ - Radius 12 - Height 8 - Speed 14 - FastSpeed 20 - Damage 1 - Projectile - -NOBLOCKMAP - -ACTIVATEIMPACT - -ACTIVATEPCROSS - +WINDTHRUST - +SPAWNSOUNDSOURCE - RenderStyle Add - SeeSound "snake/attack" - States - { - Spawn: - SNFX ABCD 5 Bright - Loop - Death: - SNFX EF 5 Bright - SNFX G 4 Bright - SNFX HI 3 Bright - Stop - } -} - -// Snake projectile B ------------------------------------------------------- - -ACTOR SnakeProjB : SnakeProjA -{ - Damage 3 - +NOBLOCKMAP - -WINDTHRUST - States - { - Spawn: - SNFX JK 6 Bright - Loop - Death: - SNFX LM 5 Bright - SNFX N 4 Bright - SNFX O 3 Bright - Stop - } -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 52906258c..69b2fbb55 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,9 +1,3 @@ -#include "actors/heretic/hereticweaps.txt" -#include "actors/heretic/mummy.txt" -#include "actors/heretic/clink.txt" -#include "actors/heretic/beast.txt" -#include "actors/heretic/snake.txt" -#include "actors/heretic/hereticimp.txt" #include "actors/heretic/knight.txt" #include "actors/heretic/wizard.txt" #include "actors/heretic/ironlich.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index bd7b914b5..e65e49fea 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -73,13 +73,13 @@ zscript/heretic/hereticartifacts.txt zscript/heretic/heretickeys.txt zscript/heretic/hereticdecorations.txt zscript/heretic/hereticmisc.txt -/* zscript/heretic/hereticweaps.txt zscript/heretic/mummy.txt zscript/heretic/clink.txt zscript/heretic/beast.txt zscript/heretic/snake.txt zscript/heretic/hereticimp.txt +/* zscript/heretic/knight.txt zscript/heretic/wizard.txt zscript/heretic/ironlich.txt diff --git a/wadsrc/static/zscript/heretic/clink.txt b/wadsrc/static/zscript/heretic/clink.txt new file mode 100644 index 000000000..7549ff097 --- /dev/null +++ b/wadsrc/static/zscript/heretic/clink.txt @@ -0,0 +1,48 @@ +class Clink : Actor +{ + Default + { + Health 150; + Radius 20; + Height 64; + Mass 75; + Speed 14; + Painchance 32; + Monster; + +NOBLOOD + +FLOORCLIP + SeeSound "clink/sight"; + AttackSound "clink/attack"; + PainSound "clink/pain"; + DeathSound "clink/death"; + ActiveSound "clink/active"; + Obituary "$OB_CLINK"; + DropItem "SkullRodAmmo", 84, 20; + } + States + { + Spawn: + CLNK AB 10 A_Look; + Loop; + See: + CLNK ABCD 3 A_Chase; + Loop; + Melee: + CLNK E 5 A_FaceTarget; + CLNK F 4 A_FaceTarget; + CLNK G 7 A_CustomMeleeAttack(random[ClinkAttack](3,9), "clink/attack", "clink/attack"); + Goto See; + Pain: + CLNK H 3; + CLNK H 3 A_Pain; + Goto See; + Death: + CLNK IJ 6; + CLNK K 5 A_Scream; + CLNK L 5 A_NoBlocking; + CLNK MN 5; + CLNK O -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/hereticimp.txt b/wadsrc/static/zscript/heretic/hereticimp.txt new file mode 100644 index 000000000..9f5c0a23e --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticimp.txt @@ -0,0 +1,171 @@ + +// Heretic imp (as opposed to the Doom variety) ----------------------------- + +class HereticImp : Actor +{ + Default + { + Health 40; + Radius 16; + Height 36; + Mass 50; + Speed 10; + Painchance 200; + Monster; + +FLOAT + +NOGRAVITY + +SPAWNFLOAT + +DONTOVERLAP + +MISSILEMORE + SeeSound "himp/sight"; + AttackSound "himp/attack"; + PainSound "himp/pain"; + DeathSound "himp/death"; + ActiveSound "himp/active"; + Obituary "$OB_HERETICIMP"; + HitObituary "$OB_HERETICIMPHIT"; + } + + action native void A_ImpMsAttack(); + action native void A_ImpDeath(); + action native void A_ImpXDeath1(); + action native void A_ImpExplode(); + + + States + { + Spawn: + IMPX ABCB 10 A_Look; + Loop; + See: + IMPX AABBCCBB 3 A_Chase; + Loop; + Melee: + IMPX DE 6 A_FaceTarget; + IMPX F 6 A_CustomMeleeAttack(random[ImpMeAttack](5,12), "himp/attack", "himp/attack"); + Goto See; + Missile: + IMPX A 10 A_FaceTarget; + IMPX B 6 A_ImpMsAttack; + IMPX CBAB 6; + Goto Missile+2; + Pain: + IMPX G 3; + IMPX G 3 A_Pain; + Goto See; + Death: + IMPX G 4 A_ImpDeath; + IMPX H 5; + Wait; + XDeath: + IMPX S 5 A_ImpXDeath1; + IMPX TU 5; + IMPX V 5 A_Gravity; + IMPX W 5; + Wait; + Crash: + IMPX I 7 A_ImpExplode; + IMPX J 7 A_Scream; + IMPX K 7; + IMPX L -1; + Stop; + XCrash: + IMPX X 7; + IMPX Y 7; + IMPX Z -1; + Stop; + } +} + +// Heretic imp leader ------------------------------------------------------- + +class HereticImpLeader : HereticImp +{ + Default + { + Species "HereticImpLeader"; + Health 80; + -MISSILEMORE + AttackSound "himp/leaderattack"; + } + States + { + Melee: + Stop; + Missile: + IMPX DE 6 A_FaceTarget; + IMPX F 6 A_CustomComboAttack("HereticImpBall", 32, random[ImpMsAttack2](5,12), "himp/leaderattack"); + Goto See; + } +} + +// Heretic imp chunk 1 ------------------------------------------------------ + +class HereticImpChunk1 : Actor +{ + Default + { + Mass 5; + Radius 4; + +NOBLOCKMAP + +MOVEWITHSECTOR + } + States + { + Spawn: + IMPX M 5; + IMPX NO 700; + Stop; + } +} + +// Heretic imp chunk 2 ------------------------------------------------------ + +class HereticImpChunk2 : Actor +{ + Default + { + Mass 5; + Radius 4; + +NOBLOCKMAP + +MOVEWITHSECTOR + } + States + { + Spawn: + IMPX P 5; + IMPX QR 700; + Stop; + } +} + +// Heretic imp ball --------------------------------------------------------- + +class HereticImpBall : Actor +{ + Default + { + Radius 8; + Height 8; + Speed 10; + FastSpeed 20; + Damage 1; + Projectile; + SeeSound "himp/leaderattack"; + +SPAWNSOUNDSOURCE + -ACTIVATEPCROSS + -ACTIVATEIMPACT + RenderStyle "Add"; + } + States + { + Spawn: + FX10 ABC 6 Bright; + Loop; + Death: + FX10 DEFG 5 Bright; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/heretic/hereticweaps.txt b/wadsrc/static/zscript/heretic/hereticweaps.txt new file mode 100644 index 000000000..eabecd9d8 --- /dev/null +++ b/wadsrc/static/zscript/heretic/hereticweaps.txt @@ -0,0 +1,1286 @@ + +class HereticWeapon : Weapon +{ + Default + { + Weapon.Kickback 150; + } +} + + +// Staff -------------------------------------------------------------------- + +class Staff : HereticWeapon +{ + Default + { + Weapon.SelectionOrder 3800; + +THRUGHOST + +WEAPON.WIMPY_WEAPON + +WEAPON.MELEEWEAPON + Weapon.sisterweapon "StaffPowered"; + Obituary "$OB_MPSTAFF"; + Tag "$TAG_STAFF"; + } + + action native void A_StaffAttack (int damage, class puff); + + States + { + Ready: + STFF A 1 A_WeaponReady; + Loop; + Deselect: + STFF A 1 A_Lower; + Loop; + Select: + STFF A 1 A_Raise; + Loop; + Fire: + STFF B 6; + STFF C 8 A_StaffAttack(random[StaffAttack](5, 20), "StaffPuff"); + STFF B 8 A_ReFire; + Goto Ready; + } +} + +class StaffPowered : Staff +{ + Default + { + Weapon.sisterweapon "Staff"; + Weapon.ReadySound "weapons/staffcrackle"; + +WEAPON.POWERED_UP + +WEAPON.READYSNDHALF + +WEAPON.STAFF2_KICKBACK + Obituary "$OB_MPPSTAFF"; + Tag "$TAG_STAFFP"; + } + + States + { + Ready: + STFF DEF 4 A_WeaponReady; + Loop; + Deselect: + STFF D 1 A_Lower; + Loop; + Select: + STFF D 1 A_Raise; + Loop; + Fire: + STFF G 6; + STFF H 8 A_StaffAttack(random[StaffAttack](18, 81), "StaffPuff2"); + STFF G 8 A_ReFire; + Goto Ready; + } +} + + +// Staff puff --------------------------------------------------------------- + +class StaffPuff : Actor +{ + Default + { + RenderStyle "Translucent"; + Alpha 0.4; + VSpeed 1; + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + AttackSound "weapons/staffhit"; + } + + States + { + Spawn: + PUF3 A 4 BRIGHT; + PUF3 BCD 4; + Stop; + } +} + +// Staff puff 2 ------------------------------------------------------------- + +class StaffPuff2 : Actor +{ + Default + { + RenderStyle "Add"; + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + AttackSound "weapons/staffpowerhit"; + } + + States + { + Spawn: + PUF4 ABCDEF 4 BRIGHT; + Stop; + } +} + + + +// Gold wand ---------------------------------------------------------------- + +class GoldWand : HereticWeapon +{ + Default + { + +BLOODSPLATTER + Weapon.SelectionOrder 2000; + Weapon.AmmoGive 25; + Weapon.AmmoUse 1; + Weapon.AmmoType "GoldWandAmmo"; + Weapon.SisterWeapon "GoldWandPowered"; + Weapon.YAdjust 5; + Inventory.PickupMessage "$TXT_WPNGOLDWAND"; + Obituary "$OB_MPGOLDWAND"; + Tag "$TAG_GOLDWAND"; + } + + action native void A_FireGoldWandPL1 (); + + States + { + Spawn: + GWAN A -1; + Stop; + Ready: + GWND A 1 A_WeaponReady; + Loop; + Deselect: + GWND A 1 A_Lower; + Loop; + Select: + GWND A 1 A_Raise; + Loop; + Fire: + GWND B 3; + GWND C 5 A_FireGoldWandPL1; + GWND D 3; + GWND D 0 A_ReFire; + Goto Ready; + } +} + +class GoldWandPowered : GoldWand +{ + Default + { + +WEAPON.POWERED_UP + Weapon.AmmoGive 0; + Weapon.SisterWeapon "GoldWand"; + Obituary "$OB_MPPGOLDWAND"; + Tag "$TAG_GOLDWANDP"; + } + + action native void A_FireGoldWandPL2 (); + + States + { + Fire: + GWND B 3; + GWND C 4 A_FireGoldWandPL2; + GWND D 3; + GWND D 0 A_ReFire; + Goto Ready; + } +} + + +// Gold wand FX1 ------------------------------------------------------------ + +class GoldWandFX1 : Actor +{ + Default + { + Radius 10; + Height 6; + Speed 22; + Damage 2; + Projectile; + RenderStyle "Add"; + DeathSound "weapons/wandhit"; + Obituary "$OB_MPPGOLDWAND"; + } + + States + { + Spawn: + FX01 AB 6 BRIGHT; + Loop; + Death: + FX01 EFGH 3 BRIGHT; + Stop; + } +} + +// Gold wand FX2 ------------------------------------------------------------ + +class GoldWandFX2 : GoldWandFX1 +{ + Default + { + Speed 18; + Damage 1; + DeathSound ""; + } + + States + { + Spawn: + FX01 CD 6 BRIGHT; + Loop; + } +} + +// Gold wand puff 1 --------------------------------------------------------- + +class GoldWandPuff1 : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + RenderStyle "Add"; + } + + States + { + Spawn: + PUF2 ABCDE 3 BRIGHT; + Stop; + } +} + +// Gold wand puff 2 --------------------------------------------------------- + +class GoldWandPuff2 : GoldWandFX1 +{ + Default + { + Skip_Super; + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + } + + States + { + Spawn: + Goto Super::Death; + } +} + + +// Crossbow ----------------------------------------------------------------- + +class Crossbow : HereticWeapon +{ + Default + { + Weapon.SelectionOrder 800; + Weapon.AmmoUse 1; + Weapon.AmmoGive 10; + Weapon.AmmoType "CrossbowAmmo"; + Weapon.SisterWeapon "CrossbowPowered"; + Weapon.YAdjust 15; + Inventory.PickupMessage "$TXT_WPNCROSSBOW"; + Tag "$TAG_CROSSBOW"; + } + + action native void A_FireCrossbowPL1 (); + + States + { + Spawn: + WBOW A -1; + Stop; + Ready: + CRBW AAAAAABBBBBBCCCCCC 1 A_WeaponReady; + Loop; + Deselect: + CRBW A 1 A_Lower; + Loop; + Select: + CRBW A 1 A_Raise; + Loop; + Fire: + CRBW D 6 A_FireCrossbowPL1; + CRBW EFGH 3; + CRBW AB 4; + CRBW C 5 A_ReFire; + Goto Ready; + } +} + + +class CrossbowPowered : Crossbow +{ + Default + { + +WEAPON.POWERED_UP + Weapon.AmmoGive 0; + Weapon.SisterWeapon "Crossbow"; + Tag "$TAG_CROSSBOWP"; + } + + action native void A_FireCrossbowPL2(); + + States + { + Fire: + CRBW D 5 A_FireCrossbowPL2; + CRBW E 3; + CRBW F 2; + CRBW G 3; + CRBW H 2; + CRBW A 3; + CRBW B 3; + CRBW C 4 A_ReFire; + Goto Ready; + } +} + + +// Crossbow FX1 ------------------------------------------------------------- + +class CrossbowFX1 : Actor +{ + Default + { + Radius 11; + Height 8; + Speed 30; + Damage 10; + Projectile; + RenderStyle "Add"; + SeeSound "weapons/bowshoot"; + DeathSound "weapons/bowhit"; + Obituary "$OB_MPCROSSBOW"; + } + + States + { + Spawn: + FX03 B 1 BRIGHT; + Loop; + Death: + FX03 HIJ 8 BRIGHT; + Stop; + } +} + + +// Crossbow FX2 ------------------------------------------------------------- + +class CrossbowFX2 : CrossbowFX1 +{ + Default + { + Speed 32; + Damage 6; + Obituary "$OB_MPPCROSSBOW"; + } + + States + { + Spawn: + FX03 B 1 BRIGHT A_SpawnItemEx("CrossbowFX4", random2[BoltSpark]()*0.015625, random2[BoltSpark]()*0.015625, 0, 0,0,0,0,SXF_ABSOLUTEPOSITION, 50); + Loop; + } +} + +// Crossbow FX3 ------------------------------------------------------------- + +class CrossbowFX3 : CrossbowFX1 +{ + Default + { + Speed 20; + Damage 2; + SeeSound ""; + -NOBLOCKMAP + +WINDTHRUST + +THRUGHOST + } + + States + { + Spawn: + FX03 A 1 BRIGHT; + Loop; + Death: + FX03 CDE 8 BRIGHT; + Stop; + } +} + +// Crossbow FX4 ------------------------------------------------------------- + +class CrossbowFX4 : Actor +{ + Default + { + +NOBLOCKMAP + Gravity 0.125; + RenderStyle "Add"; + } + + States + { + Spawn: + FX03 FG 8 BRIGHT; + Stop; + } +} + + + + +// Gauntlets ---------------------------------------------------------------- + +class Gauntlets : Weapon +{ + Default + { + +BLOODSPLATTER + Weapon.SelectionOrder 2300; + +WEAPON.WIMPY_WEAPON + +WEAPON.MELEEWEAPON + Weapon.Kickback 0; + Weapon.YAdjust 15; + Weapon.UpSound "weapons/gauntletsactivate"; + Weapon.SisterWeapon "GauntletsPowered"; + Inventory.PickupMessage "$TXT_WPNGAUNTLETS"; + Tag "$TAG_GAUNTLETS"; + Obituary "$OB_MPGAUNTLETS"; + } + + action native void A_GauntletAttack (int power); + + States + { + Spawn: + WGNT A -1; + Stop; + Ready: + GAUN A 1 A_WeaponReady; + Loop; + Deselect: + GAUN A 1 A_Lower; + Loop; + Select: + GAUN A 1 A_Raise; + Loop; + Fire: + GAUN B 4 A_PlayWeaponSound("weapons/gauntletsuse"); + GAUN C 4; + Hold: + GAUN DEF 4 BRIGHT A_GauntletAttack(0); + GAUN C 4 A_ReFire; + GAUN B 4 A_Light0; + Goto Ready; + } +} + + +class GauntletsPowered : Gauntlets +{ + Default + { + +WEAPON.POWERED_UP + Tag "$TAG_GAUNTLETSP"; + Obituary "$OB_MPPGAUNTLETS"; + Weapon.SisterWeapon "Gauntlets"; + } + + States + { + Ready: + GAUN GHI 4 A_WeaponReady; + Loop; + Deselect: + GAUN G 1 A_Lower; + Loop; + Select: + GAUN G 1 A_Raise; + Loop; + Fire: + GAUN J 4 A_PlayWeaponSound("weapons/gauntletsuse"); + GAUN K 4; + Hold: + GAUN LMN 4 BRIGHT A_GauntletAttack(1); + GAUN K 4 A_ReFire; + GAUN J 4 A_Light0; + Goto Ready; + } +} + + +// Gauntlet puff 1 ---------------------------------------------------------- + +class GauntletPuff1 : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + RenderStyle "Translucent"; + Alpha 0.4; + VSpeed 0.8; + } + + States + { + Spawn: + PUF1 ABCD 4 BRIGHT; + Stop; + } +} + +// Gauntlet puff 2 --------------------------------------------------------- + +class GauntletPuff2 : GauntletPuff1 +{ + States + { + Spawn: + PUF1 EFGH 4 BRIGHT; + Stop; + } +} + + +// The mace itself ---------------------------------------------------------- + +class Mace : HereticWeapon +{ + Default + { + Weapon.SelectionOrder 1400; + Weapon.AmmoUse 1; + Weapon.AmmoGive1 50; + Weapon.YAdjust 15; + Weapon.AmmoType "MaceAmmo"; + Weapon.SisterWeapon "MacePowered"; + Inventory.PickupMessage "$TXT_WPNMACE"; + Tag "$TAG_MACE"; + } + + action native void A_FireMacePL1(); + + States + { + Spawn: + WMCE A -1; + Stop; + Ready: + MACE A 1 A_WeaponReady; + Loop; + Deselect: + MACE A 1 A_Lower; + Loop; + Select: + MACE A 1 A_Raise; + Loop; + Fire: + MACE B 4; + Hold: + MACE CDEF 3 A_FireMacePL1; + MACE C 4 A_ReFire; + MACE DEFB 4; + Goto Ready; + } +} + +class MacePowered : Mace +{ + Default + { + +WEAPON.POWERED_UP + Weapon.AmmoUse 5; + Weapon.AmmoGive 0; + Weapon.SisterWeapon "Mace"; + Tag "$TAG_MACEP"; + } + + action native void A_FireMacePL2(); + + States + { + Fire: + Hold: + MACE B 4; + MACE D 4 A_FireMacePL2; + MACE B 4; + MACE A 8 A_ReFire; + Goto Ready; + } +} + +// Mace FX1 ----------------------------------------------------------------- + +class MaceFX1 : Actor +{ + Default + { + Radius 8; + Height 6; + Speed 20; + Damage 2; + Projectile; + +THRUGHOST + BounceType "HereticCompat"; + SeeSound "weapons/maceshoot"; + Obituary "$OB_MPMACE"; + } + + action native void A_MacePL1Check(); + action native void A_MaceBallImpact(); + + States + { + Spawn: + FX02 AB 4 A_MacePL1Check; + Loop; + Death: + FX02 F 4 BRIGHT A_MaceBallImpact; + FX02 GHIJ 4 BRIGHT; + Stop; + } +} + +// Mace FX2 ----------------------------------------------------------------- + +class MaceFX2 : MaceFX1 +{ + Default + { + Speed 10; + Damage 6; + Gravity 0.125; + -NOGRAVITY + SeeSound ""; + } + + action native void A_MaceBallImpact2(); + + States + { + Spawn: + FX02 CD 4; + Loop; + Death: + FX02 F 4 A_MaceBallImpact2; + goto Super::Death+1; + } +} + +// Mace FX3 ----------------------------------------------------------------- + +class MaceFX3 : MaceFX1 +{ + Default + { + Speed 7; + Damage 4; + -NOGRAVITY; + Gravity 0.125; + } + + States + { + Spawn: + FX02 AB 4; + Loop; + } +} + + +// Mace FX4 ----------------------------------------------------------------- + +class MaceFX4 : Actor native +{ + Default + { + Radius 8; + Height 6; + Speed 7; + Damage 18; + Gravity 0.125; + Projectile; + -NOGRAVITY + +TELESTOMP + +THRUGHOST + -NOTELEPORT + BounceType "HereticCompat"; + SeeSound ""; + Obituary "$OB_MPPMACE"; + } + + action native void A_DeathBallImpact(); + + States + { + Spawn: + FX02 E 99; + Loop; + Death: + FX02 C 4 A_DeathBallImpact; + FX02 GHIJ 4 BRIGHT; + Stop; + } +} + + +// Mace spawn spot ---------------------------------------------------------- + +class MaceSpawner : SpecialSpot +{ + Default + { + +NOSECTOR + +NOBLOCKMAP + } + + States + { + Spawn: + TNT1 A 1; + TNT1 A -1 A_SpawnSingleItem("Mace", 64, 64, 0); + Stop; + } +} + + +// Blaster ------------------------------------------------------------------ + +class Blaster : HereticWeapon +{ + Default + { + +BLOODSPLATTER + Weapon.SelectionOrder 500; + Weapon.AmmoUse 1; + Weapon.AmmoGive 30; + Weapon.YAdjust 15; + Weapon.AmmoType "BlasterAmmo"; + Weapon.SisterWeapon "BlasterPowered"; + Inventory.PickupMessage "$TXT_WPNBLASTER"; + Tag "$TAG_BLASTER"; + Obituary "$OB_MPBLASTER"; + } + + action native void A_FireBlasterPL1(); + + States + { + Spawn: + WBLS A -1; + Stop; + Ready: + BLSR A 1 A_WeaponReady; + Loop; + Deselect: + BLSR A 1 A_Lower; + Loop; + Select: + BLSR A 1 A_Raise; + Loop; + Fire: + BLSR BC 3; + Hold: + BLSR D 2 A_FireBlasterPL1; + BLSR CB 2; + BLSR A 0 A_ReFire; + Goto Ready; + } +} + +class BlasterPowered : Blaster +{ + Default + { + +WEAPON.POWERED_UP + Weapon.AmmoUse 5; + Weapon.AmmoGive 0; + Weapon.SisterWeapon "Blaster"; + Tag "$TAG_BLASTERP"; + } + + States + { + Fire: + BLSR BC 0; + Hold: + BLSR D 3 A_FireCustomMissile("BlasterFX1"); + BLSR CB 4; + BLSR A 0 A_ReFire; + Goto Ready; + } +} + +// Blaster FX 1 ------------------------------------------------------------- + +class BlasterFX1 : FastProjectile native +{ + Default + { + Radius 12; + Height 8; + Speed 184; + Damage 2; + SeeSound "weapons/blastershoot"; + DeathSound "weapons/blasterhit"; + +SPAWNSOUNDSOURCE + Obituary "$OB_MPPBLASTER"; + } + + action native void A_SpawnRippers(); + + States + { + Spawn: + ACLO E 200; + Loop; + Death: + FX18 A 3 BRIGHT A_SpawnRippers; + FX18 B 3 BRIGHT; + FX18 CDEFG 4 BRIGHT; + Stop; + } +} + +// Blaster smoke ------------------------------------------------------------ + +class BlasterSmoke : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +NOTELEPORT + +CANNOTPUSH + RenderStyle "Translucent"; + Alpha 0.4; + } + + States + { + Spawn: + FX18 HIJKL 4; + Stop; + } +} + +// Ripper ------------------------------------------------------------------- + +class Ripper : Actor native +{ + Default + { + Radius 8; + Height 6; + Speed 14; + Damage 1; + Projectile; + +RIPPER + DeathSound "weapons/blasterpowhit"; + Obituary "$OB_MPPBLASTER"; + } + + States + { + Spawn: + FX18 M 4; + FX18 N 5; + Loop; + Death: + FX18 OPQRS 4 BRIGHT; + Stop; + } +} + +// Blaster Puff ------------------------------------------------------------- + +class BlasterPuff : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + RenderStyle "Add"; + SeeSound "weapons/blasterhit"; + } + + States + { + Crash: + FX17 ABCDE 4 BRIGHT; + Stop; + Spawn: + FX17 FG 3 BRIGHT; + FX17 HIJKL 4 BRIGHT; + Stop; + } +} + + +// Skull (Horn) Rod --------------------------------------------------------- + +class SkullRod : HereticWeapon +{ + Default + { + Weapon.SelectionOrder 200; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 50; + Weapon.YAdjust 15; + Weapon.AmmoType1 "SkullRodAmmo"; + Weapon.SisterWeapon "SkullRodPowered"; + Inventory.PickupMessage "$TXT_WPNSKULLROD"; + Tag "$TAG_SKULLROD"; + } + + action native void A_FireSkullRodPL1(); + + States + { + Spawn: + WSKL A -1; + Stop; + Ready: + HROD A 1 A_WeaponReady; + Loop; + Deselect: + HROD A 1 A_Lower; + Loop; + Select: + HROD A 1 A_Raise; + Loop; + Fire: + HROD AB 4 A_FireSkullRodPL1; + HROD B 0 A_ReFire; + Goto Ready; + } +} + +class SkullRodPowered : SkullRod +{ + Default + { + +WEAPON.POWERED_UP + Weapon.AmmoUse1 5; + Weapon.AmmoGive1 0; + Weapon.SisterWeapon "SkullRod"; + Tag "$TAG_SKULLRODP"; + } + + action native void A_FireSkullRodPL2(); + + States + { + Fire: + HROD C 2; + HROD D 3; + HROD E 2; + HROD F 3; + HROD G 4 A_FireSkullRodPL2; + HROD F 2; + HROD E 3; + HROD D 2; + HROD C 2 A_ReFire; + Goto Ready; + } +} + +// Horn Rod FX 1 ------------------------------------------------------------ + +class HornRodFX1 : Actor +{ + Default + { + Radius 12; + Height 8; + Speed 22; + Damage 3; + Projectile; + +WINDTHRUST + -NOBLOCKMAP + RenderStyle "Add"; + SeeSound "weapons/hornrodshoot"; + DeathSound "weapons/hornrodhit"; + Obituary "$OB_MPSKULLROD"; + } + + States + { + Spawn: + FX00 AB 6 BRIGHT; + Loop; + Death: + FX00 HI 5 BRIGHT; + FX00 JK 4 BRIGHT; + FX00 LM 3 BRIGHT; + Stop; + } +} + + +// Horn Rod FX 2 ------------------------------------------------------------ + +class HornRodFX2 : Actor native +{ + Default + { + Radius 12; + Height 8; + Speed 22; + Damage 10; + Health 140; + Projectile; + RenderStyle "Add"; + SeeSound "weapons/hornrodpowshoot"; + DeathSound "weapons/hornrodpowhit"; + Obituary "$OB_MPPSKULLROD"; + } + + action native void A_AddPlayerRain(); + action native void A_HideInCeiling(); + action native void A_SkullRodStorm(); + + States + { + Spawn: + FX00 C 3 BRIGHT; + FX00 D 3 BRIGHT A_SeekerMissile(10, 30); + FX00 E 3 BRIGHT; + FX00 F 3 BRIGHT A_SeekerMissile(10, 30); + Loop; + Death: + FX00 H 5 BRIGHT A_AddPlayerRain; + FX00 I 5 BRIGHT; + FX00 J 4 BRIGHT; + FX00 KLM 3 BRIGHT; + FX00 G 1 A_HideInCeiling; + FX00 G 1 A_SkullRodStorm; + Wait; + } +} + +// Rain pillar 1 ------------------------------------------------------------ + +class RainPillar : Actor native +{ + Default + { + Radius 5; + Height 12; + Speed 12; + Damage 5; + Mass 5; + Projectile; + -ACTIVATEPCROSS + -ACTIVATEIMPACT + RenderStyle "Add"; + Obituary "$OB_MPPSKULLROD"; + } + + action native void A_RainImpact(); + + States + { + Spawn: + FX22 A -1 BRIGHT; + Stop; + Death: + FX22 B 4 BRIGHT A_RainImpact; + FX22 CDEF 4 BRIGHT; + Stop; + NotFloor: + FX22 GHI 4 BRIGHT; + Stop; + } +} + +// Rain tracker "inventory" item -------------------------------------------- + +class RainTracker : Inventory native +{ + Default + { + +INVENTORY.UNDROPPABLE + } +} + + +// Phoenix Rod -------------------------------------------------------------- + +class PhoenixRod : Weapon native +{ + Default + { + +WEAPON.NOAUTOFIRE + Weapon.SelectionOrder 2600; + Weapon.Kickback 150; + Weapon.YAdjust 15; + Weapon.AmmoUse 1; + Weapon.AmmoGive 2; + Weapon.AmmoType "PhoenixRodAmmo"; + Weapon.Sisterweapon "PhoenixRodPowered"; + Inventory.PickupMessage "$TXT_WPNPHOENIXROD"; + Tag "$TAG_PHOENIXROD"; + } + + action native void A_FirePhoenixPL1(); + + States + { + Spawn: + WPHX A -1; + Stop; + Ready: + PHNX A 1 A_WeaponReady; + Loop; + Deselect: + PHNX A 1 A_Lower; + Loop; + Select: + PHNX A 1 A_Raise; + Loop; + Fire: + PHNX B 5; + PHNX C 7 A_FirePhoenixPL1; + PHNX DB 4; + PHNX B 0 A_ReFire; + Goto Ready; + } +} + +class PhoenixRodPowered : PhoenixRod native +{ + Default + { + +WEAPON.POWERED_UP + +WEAPON.MELEEWEAPON + Weapon.SisterWeapon "PhoenixRod"; + Weapon.AmmoGive 0; + Tag "$TAG_PHOENIXRODP"; + } + + action native void A_InitPhoenixPL2(); + action native void A_FirePhoenixPL2(); + action native void A_ShutdownPhoenixPL2(); + + States + { + Fire: + PHNX B 3 A_InitPhoenixPL2; + Hold: + PHNX C 1 A_FirePhoenixPL2; + PHNX B 4 A_ReFire; + Powerdown: + PHNX B 4 A_ShutdownPhoenixPL2; + Goto Ready; + } +} + +// Phoenix FX 1 ------------------------------------------------------------- + +class PhoenixFX1 : Actor native +{ + Default + { + Radius 11; + Height 8; + Speed 20; + Damage 20; + DamageType "Fire"; + Projectile; + +THRUGHOST + +SPECIALFIREDAMAGE + SeeSound "weapons/phoenixshoot"; + DeathSound "weapons/phoenixhit"; + Obituary "$OB_MPPHOENIXROD"; + } + + action native void A_PhoenixPuff(); + + States + { + Spawn: + FX04 A 4 BRIGHT A_PhoenixPuff; + Loop; + Death: + FX08 A 6 BRIGHT A_Explode; + FX08 BC 5 BRIGHT; + FX08 DEFGH 4 BRIGHT; + Stop; + } +} + +// Phoenix puff ------------------------------------------------------------- + +class PhoenixPuff : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +NOTELEPORT + +CANNOTPUSH + RenderStyle "Translucent"; + Alpha 0.4; + } + + States + { + Spawn: + FX04 BCDEF 4; + Stop; + } +} + +// Phoenix FX 2 ------------------------------------------------------------- + +class PhoenixFX2 : Actor native +{ + Default + { + Radius 6; + Height 8; + Speed 10; + Damage 2; + DamageType "Fire"; + Projectile; + RenderStyle "Add"; + Obituary "$OB_MPPPHOENIXROD"; + } + + action native void A_FlameEnd(); + action native void A_FloatPuff(); + + States + { + Spawn: + FX09 ABABA 2 BRIGHT; + FX09 B 2 BRIGHT A_FlameEnd; + FX09 CDEF 2 BRIGHT; + Stop; + Death: + FX09 G 3 BRIGHT; + FX09 H 3 BRIGHT A_FloatPuff; + FX09 I 4 BRIGHT; + FX09 JK 5 BRIGHT; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/mummy.txt b/wadsrc/static/zscript/heretic/mummy.txt new file mode 100644 index 000000000..6d01fcea4 --- /dev/null +++ b/wadsrc/static/zscript/heretic/mummy.txt @@ -0,0 +1,151 @@ + +// Mummy -------------------------------------------------------------------- + +class Mummy : Actor +{ + Default + { + Health 80; + Radius 22; + Height 62; + Mass 75; + Speed 12; + Painchance 128; + Monster; + +FLOORCLIP + SeeSound "mummy/sight"; + AttackSound "mummy/attack1"; + PainSound "mummy/pain"; + DeathSound "mummy/death"; + ActiveSound "mummy/active"; + HitObituary "$OB_MUMMY"; + DropItem "GoldWandAmmo", 84, 3; + } + States + { + Spawn: + MUMM AB 10 A_Look; + Loop; + See: + MUMM ABCD 4 A_Chase; + Loop; + Melee: + MUMM E 6 A_FaceTarget; + MUMM F 6 A_CustomMeleeAttack(random[MummyAttack](1,8)*2, "mummy/attack2", "mummy/attack"); + MUMM G 6; + Goto See; + Pain: + MUMM H 4; + MUMM H 4 A_Pain; + Goto See; + Death: + MUMM I 5; + MUMM J 5 A_Scream; + MUMM K 5 A_SpawnItemEx("MummySoul", 0,0,10, 0,0,1); + MUMM L 5; + MUMM M 5 A_NoBlocking; + MUMM NO 5; + MUMM P -1; + Stop; + } +} + +// Mummy leader ------------------------------------------------------------- + +class MummyLeader : Mummy +{ + Default + { + Species "MummyLeader"; + Health 100; + Painchance 64; + Obituary "$OB_MUMMYLEADER"; + } + States + { + Missile: + MUMM X 5 A_FaceTarget; + MUMM Y 5 Bright A_FaceTarget; + MUMM X 5 A_FaceTarget; + MUMM Y 5 Bright A_FaceTarget; + MUMM X 5 A_FaceTarget; + MUMM Y 5 Bright A_CustomComboAttack("MummyFX1", 32, random[MummyAttack2](1,8)*2, "mummy/attack2"); + Goto See; + } +} + +// Mummy ghost -------------------------------------------------------------- + +class MummyGhost : Mummy +{ + Default + { + +SHADOW + +GHOST + RenderStyle "Translucent"; + Alpha 0.4; + } +} + +// Mummy leader ghost ------------------------------------------------------- + +class MummyLeaderGhost : MummyLeader +{ + Default + { + Species "MummyLeaderGhost"; + +SHADOW + +GHOST + RenderStyle "Translucent"; + Alpha 0.4; + } +} + +// Mummy soul --------------------------------------------------------------- + +class MummySoul : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + } + States + { + Spawn: + MUMM QRS 5; + MUMM TUVW 9; + Stop; + } +} + +// Mummy FX 1 (flying head) ------------------------------------------------- + +class MummyFX1 : Actor +{ + Default + { + Radius 8; + Height 14; + Speed 9; + FastSpeed 18; + Damage 4; + RenderStyle "Add"; + Projectile; + -ACTIVATEPCROSS + -ACTIVATEIMPACT + +SEEKERMISSILE + } + States + { + Spawn: + FX15 A 5 Bright A_PlaySound("mummy/head"); + FX15 B 5 Bright A_SeekerMissile(10,20); + FX15 C 5 Bright; + FX15 B 5 Bright A_SeekerMissile(10,20); + Loop; + Death: + FX15 DEFG 5 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/heretic/snake.txt b/wadsrc/static/zscript/heretic/snake.txt new file mode 100644 index 000000000..613559a86 --- /dev/null +++ b/wadsrc/static/zscript/heretic/snake.txt @@ -0,0 +1,104 @@ + +class Snake : Actor +{ + Default + { + Health 280; + Radius 22; + Height 70; + Speed 10; + Painchance 48; + Monster; + +FLOORCLIP + AttackSound "snake/attack"; + SeeSound "snake/sight"; + PainSound "snake/pain"; + DeathSound "snake/death"; + ActiveSound "snake/active"; + Obituary "$OB_SNAKE"; + DropItem "PhoenixRodAmmo", 84, 5; + } + States + { + Spawn: + SNKE AB 10 A_Look; + Loop; + See: + SNKE ABCD 4 A_Chase; + Loop; + Missile: + SNKE FF 5 A_FaceTarget; + SNKE FFF 4 A_CustomMissile("SnakeProjA", 32, 0, 0, CMF_CHECKTARGETDEAD); + SNKE FFF 5 A_FaceTarget; + SNKE F 4 A_CustomMissile("SnakeProjB", 32, 0, 0, CMF_CHECKTARGETDEAD); + Goto See; + Pain: + SNKE E 3; + SNKE E 3 A_Pain; + Goto See; + Death: + SNKE G 5; + SNKE H 5 A_Scream; + SNKE IJKL 5; + SNKE M 5 A_NoBlocking; + SNKE NO 5; + SNKE P -1; + Stop; + } +} + +// Snake projectile A ------------------------------------------------------- + +class SnakeProjA : Actor +{ + Default + { + Radius 12; + Height 8; + Speed 14; + FastSpeed 20; + Damage 1; + Projectile; + -NOBLOCKMAP + -ACTIVATEIMPACT + -ACTIVATEPCROSS + +WINDTHRUST + +SPAWNSOUNDSOURCE + RenderStyle "Add"; + SeeSound "snake/attack"; + } + States + { + Spawn: + SNFX ABCD 5 Bright; + Loop; + Death: + SNFX EF 5 Bright; + SNFX G 4 Bright; + SNFX HI 3 Bright; + Stop; + } +} + +// Snake projectile B ------------------------------------------------------- + +class SnakeProjB : SnakeProjA +{ + Default + { + Damage 3; + +NOBLOCKMAP + -WINDTHRUST + } + States + { + Spawn: + SNFX JK 6 Bright; + Loop; + Death: + SNFX LM 5 Bright; + SNFX N 4 Bright; + SNFX O 3 Bright; + Stop; + } +} From 552f094ec15bb0d5ed2348da50f8171565df182c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 12:58:23 +0200 Subject: [PATCH 055/255] - converted the rest of Heretic's actors. - fixed: Boolean constants were not properly handled. --- src/scripting/zscript/zcc_compile.cpp | 6 +- wadsrc/static/actors/heretic/chicken.txt | 181 ------------- wadsrc/static/actors/heretic/dsparil.txt | 270 ------------------- wadsrc/static/actors/heretic/ironlich.txt | 175 ------------ wadsrc/static/actors/heretic/knight.txt | 118 -------- wadsrc/static/actors/heretic/wizard.txt | 96 ------- wadsrc/static/decorate.txt | 6 - wadsrc/static/zscript.txt | 3 - wadsrc/static/zscript/heretic/chicken.txt | 201 ++++++++++++++ wadsrc/static/zscript/heretic/dsparil.txt | 297 +++++++++++++++++++++ wadsrc/static/zscript/heretic/ironlich.txt | 191 +++++++++++++ wadsrc/static/zscript/heretic/knight.txt | 131 +++++++++ wadsrc/static/zscript/heretic/wizard.txt | 103 +++++++ 13 files changed, 928 insertions(+), 850 deletions(-) delete mode 100644 wadsrc/static/actors/heretic/chicken.txt delete mode 100644 wadsrc/static/actors/heretic/dsparil.txt delete mode 100644 wadsrc/static/actors/heretic/ironlich.txt delete mode 100644 wadsrc/static/actors/heretic/knight.txt delete mode 100644 wadsrc/static/actors/heretic/wizard.txt create mode 100644 wadsrc/static/zscript/heretic/chicken.txt create mode 100644 wadsrc/static/zscript/heretic/dsparil.txt create mode 100644 wadsrc/static/zscript/heretic/ironlich.txt create mode 100644 wadsrc/static/zscript/heretic/knight.txt create mode 100644 wadsrc/static/zscript/heretic/wizard.txt diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 1992587c8..5511898f7 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2385,6 +2385,10 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { return new FxConstant(cnst->IntVal, *ast); } + else if (cnst->Type->IsA(RUNTIME_CLASS(PBool))) + { + return new FxConstant(!!cnst->IntVal, *ast); + } else if (cnst->Type->IsA(RUNTIME_CLASS(PFloat))) { return new FxConstant(cnst->DoubleVal, *ast); @@ -2396,7 +2400,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) else { // can there be other types? - Error(cnst, "Unknown constant type"); + Error(cnst, "Unknown constant type %s", cnst->Type->DescriptiveName()); return new FxConstant(0, *ast); } } diff --git a/wadsrc/static/actors/heretic/chicken.txt b/wadsrc/static/actors/heretic/chicken.txt deleted file mode 100644 index 8d3b1e71d..000000000 --- a/wadsrc/static/actors/heretic/chicken.txt +++ /dev/null @@ -1,181 +0,0 @@ - -// Beak puff ---------------------------------------------------------------- - -ACTOR BeakPuff : StaffPuff -{ - Mass 5 - Renderstyle Translucent - Alpha 0.4 - AttackSound "chicken/attack" - VSpeed 1 -} - -// Beak --------------------------------------------------------------------- - -ACTOR Beak : Weapon -{ - Weapon.SelectionOrder 10000 - +WEAPON.DONTBOB - +WEAPON.MELEEWEAPON - Weapon.YAdjust 15 - Weapon.SisterWeapon "BeakPowered" - - action native A_BeakRaise (); - action native A_BeakAttackPL1(); - - States - { - Ready: - BEAK A 1 A_WeaponReady - Loop - Deselect: - BEAK A 1 A_Lower - Loop - Select: - BEAK A 1 A_BeakRaise - Loop - Fire: - BEAK A 18 A_BeakAttackPL1 - Goto Ready - } -} - - -ACTOR BeakPowered : Beak -{ - +WEAPON.POWERED_UP - Weapon.SisterWeapon "Beak" - - action native A_BeakAttackPL2(); - - States - { - Fire: - BEAK A 12 A_BeakAttackPL2 - Goto Ready - } -} - -// Chicken player ----------------------------------------------------------- - -ACTOR ChickenPlayer : PlayerPawn native -{ - Health 30 - ReactionTime 0 - PainChance 255 - Radius 16 - Height 24 - Speed 1 - Gravity 0.125 - +NOSKIN - +CANSUPERMORPH - PainSound "chicken/pain" - DeathSound "chicken/death" - Player.JumpZ 1 - Player.Viewheight 21 - Player.ForwardMove 1.22, 1.22 - Player.SideMove 1.22, 1.22 - Player.SpawnClass "Chicken" - Player.SoundClass "Chicken" - Player.DisplayName "Chicken" - Player.MorphWeapon "Beak" - -PICKUP - States - { - Spawn: - CHKN A -1 - Stop - See: - CHKN ABAB 3 - Loop - Melee: - Missile: - CHKN C 12 - Goto Spawn - Pain: - CHKN D 4 A_Feathers - CHKN C 4 A_Pain - Goto Spawn - Death: - CHKN E 6 A_Scream - CHKN F 6 A_Feathers - CHKN G 6 - CHKN H 6 A_NoBlocking - CHKN IJK 6 - CHKN L -1 - Stop - } -} - - - -// Chicken (non-player) ----------------------------------------------------- - -ACTOR Chicken : MorphedMonster -{ - Health 10 - Radius 9 - Height 22 - Mass 40 - Speed 4 - Painchance 200 - Monster - -COUNTKILL - +WINDTHRUST - +DONTMORPH - +FLOORCLIP - SeeSound "chicken/pain" - AttackSound "chicken/attack" - PainSound "chicken/pain" - DeathSound "chicken/death" - ActiveSound "chicken/active" - Obituary "$OB_CHICKEN" - States - { - Spawn: - CHKN AB 10 A_Look - Loop - See: - CHKN AB 3 A_Chase - Loop - Pain: - CHKN D 5 A_Feathers - CHKN C 5 A_Pain - Goto See - Melee: - CHKN A 8 A_FaceTarget - CHKN C 10 A_CustomMeleeAttack(random[ChicAttack](1,2)) - Goto See - Death: - CHKN E 6 A_Scream - CHKN F 6 A_Feathers - CHKN G 6 - CHKN H 6 A_NoBlocking - CHKN IJK 6 - CHKN L -1 - Stop - } -} - - -// Feather ------------------------------------------------------------------ - -ACTOR Feather -{ - Radius 2 - Height 4 - +MISSILE +DROPOFF - +NOTELEPORT +CANNOTPUSH - +WINDTHRUST +DONTSPLASH - Gravity 0.125 - States - { - Spawn: - CHKN MNOPQPON 3 - Loop - Death: - CHKN N 6 - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/dsparil.txt b/wadsrc/static/actors/heretic/dsparil.txt deleted file mode 100644 index 8b2f4dc5c..000000000 --- a/wadsrc/static/actors/heretic/dsparil.txt +++ /dev/null @@ -1,270 +0,0 @@ - -// Boss spot ---------------------------------------------------------------- - -ACTOR BossSpot : SpecialSpot -{ - +INVISIBLE -} - -// Sorcerer (D'Sparil on his serpent) --------------------------------------- - -ACTOR Sorcerer1 -{ - Health 2000 - Radius 28 - Height 100 - Mass 800 - Speed 16 - PainChance 56 - Monster - +BOSS - +DONTMORPH - +NORADIUSDMG - +NOTARGET - +NOICEDEATH - +FLOORCLIP - +DONTGIB - SeeSound "dsparilserpent/sight" - AttackSound "dsparilserpent/attack" - PainSound "dsparilserpent/pain" - DeathSound "dsparilserpent/death" - ActiveSound "dsparilserpent/active" - Obituary "$OB_DSPARIL1" - HitObituary "$OB_DSPARIL1HIT" - - action native A_Sor1Pain (); - action native A_Sor1Chase (); - action native A_Srcr1Attack (); - action native A_SorcererRise (); - - States - { - Spawn: - SRCR AB 10 A_Look - Loop - See: - SRCR ABCD 5 A_Sor1Chase - Loop - Pain: - SRCR Q 6 A_Sor1Pain - Goto See - Missile: - SRCR Q 7 A_FaceTarget - SRCR R 6 A_FaceTarget - SRCR S 10 A_Srcr1Attack - Goto See - Missile2: - SRCR S 10 A_FaceTarget - SRCR Q 7 A_FaceTarget - SRCR R 6 A_FaceTarget - SRCR S 10 A_Srcr1Attack - Goto See - Death: - SRCR E 7 - SRCR F 7 A_Scream - SRCR G 7 - SRCR HIJK 6 - SRCR L 25 A_PlaySound("dsparil/zap", CHAN_BODY, 1, false, ATTN_NONE) - SRCR MN 5 - SRCR O 4 - SRCR L 20 A_PlaySound("dsparil/zap", CHAN_BODY, 1, false, ATTN_NONE) - SRCR MN 5 - SRCR O 4 - SRCR L 12 - SRCR P -1 A_SorcererRise - } -} - - -// Sorcerer FX 1 ------------------------------------------------------------ - -ACTOR SorcererFX1 -{ - Radius 10 - Height 10 - Speed 20 - FastSpeed 28 - Damage 10 - DamageType Fire - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - States - { - Spawn: - FX14 ABC 6 BRIGHT - Loop - Death: - FX14 DEFGH 5 BRIGHT - Stop - } -} - - -// Sorcerer 2 (D'Sparil without his serpent) -------------------------------- - -ACTOR Sorcerer2 -{ - Health 3500 - Radius 16 - Height 70 - Mass 300 - Speed 14 - Painchance 32 - Monster - +DROPOFF - +BOSS - +DONTMORPH - +FULLVOLACTIVE - +NORADIUSDMG - +NOTARGET - +NOICEDEATH - +FLOORCLIP - +BOSSDEATH - SeeSound "dsparil/sight" - AttackSound "dsparil/attack" - PainSound "dsparil/pain" - ActiveSound "dsparil/active" - Obituary "$OB_DSPARIL2" - HitObituary "$OB_DSPARIL2HIT" - - action native A_Srcr2Decide (); - action native A_Srcr2Attack (); - action native A_Sor2DthInit (); - action native A_Sor2DthLoop (); - - States - { - Spawn: - SOR2 MN 10 A_Look - Loop - See: - SOR2 MNOP 4 A_Chase - Loop - Rise: - SOR2 AB 4 - SOR2 C 4 A_PlaySound("dsparil/rise", CHAN_BODY, 1, false, ATTN_NONE) - SOR2 DEF 4 - SOR2 G 12 A_PlaySound("dsparil/sight", CHAN_BODY, 1, false, ATTN_NONE) - Goto See - Pain: - SOR2 Q 3 - SOR2 Q 6 A_Pain - Goto See - Missile: - SOR2 R 9 A_Srcr2Decide - SOR2 S 9 A_FaceTarget - SOR2 T 20 A_Srcr2Attack - Goto See - Teleport: - SOR2 LKJIHG 6 - Goto See - Death: - SDTH A 8 A_Sor2DthInit - SDTH B 8 - SDTH C 8 A_PlaySound("dsparil/scream", CHAN_BODY, 1, false, ATTN_NONE) - DeathLoop: - SDTH DE 7 - SDTH F 7 A_Sor2DthLoop - SDTH G 6 A_PlaySound("dsparil/explode", CHAN_BODY, 1, false, ATTN_NONE) - SDTH H 6 - SDTH I 18 - SDTH J 6 A_NoBlocking - SDTH K 6 A_PlaySound("dsparil/bones", CHAN_BODY, 1, false, ATTN_NONE) - SDTH LMN 6 - SDTH O -1 A_BossDeath - Stop - } -} - - - -// Sorcerer 2 FX 1 ---------------------------------------------------------- - -ACTOR Sorcerer2FX1 -{ - Radius 10 - Height 6 - Speed 20 - FastSpeed 28 - Damage 1 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - - action native A_BlueSpark (); - - States - { - Spawn: - FX16 ABC 3 BRIGHT A_BlueSpark - Loop - Death: - FX16 G 5 BRIGHT A_Explode(random[S2FX1](80,111)) - FX16 HIJKL 5 BRIGHT - Stop - } -} - -// Sorcerer 2 FX Spark ------------------------------------------------------ - -ACTOR Sorcerer2FXSpark -{ - Radius 20 - Height 16 - +NOBLOCKMAP - +NOGRAVITY - +NOTELEPORT - +CANNOTPUSH - RenderStyle Add - States - { - Spawn: - FX16 DEF 12 BRIGHT - Stop - } -} - -// Sorcerer 2 FX 2 ---------------------------------------------------------- - -ACTOR Sorcerer2FX2 -{ - Radius 10 - Height 6 - Speed 6 - Damage 10 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - - action native A_GenWizard (); - - States - { - Spawn: - FX11 A 35 BRIGHT - FX11 A 5 BRIGHT A_GenWizard - FX11 B 5 BRIGHT - Goto Spawn+1 - Death: - FX11 CDEFG 5 BRIGHT - Stop - - } -} -// Sorcerer 2 Telefade ------------------------------------------------------ - -ACTOR Sorcerer2Telefade -{ - +NOBLOCKMAP - States - { - Spawn: - SOR2 GHIJKL 6 - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/ironlich.txt b/wadsrc/static/actors/heretic/ironlich.txt deleted file mode 100644 index 43d7c16c5..000000000 --- a/wadsrc/static/actors/heretic/ironlich.txt +++ /dev/null @@ -1,175 +0,0 @@ - -// Ironlich ----------------------------------------------------------------- - -ACTOR Ironlich -{ - Health 700 - Radius 40 - Height 72 - Mass 325 - Speed 6 - Painchance 32 - Monster - +NOBLOOD - +DONTMORPH - +DONTSQUASH - +BOSSDEATH - SeeSound "ironlich/sight" - AttackSound "ironlich/attack" - PainSound "ironlich/pain" - DeathSound "ironlich/death" - ActiveSound "ironlich/active" - Obituary "$OB_IRONLICH" - HitObituary "$OB_IRONLICHHIT" - DropItem "BlasterAmmo", 84, 10 - DropItem "ArtiEgg", 51, 0 - - action native A_LichAttack (); - - States - { - Spawn: - LICH A 10 A_Look - Loop - See: - LICH A 4 A_Chase - Loop - Missile: - LICH A 5 A_FaceTarget - LICH B 20 A_LichAttack - Goto See - Pain: - LICH A 4 - LICH A 4 A_Pain - Goto See - Death: - LICH C 7 - LICH D 7 A_Scream - LICH EF 7 - LICH G 7 A_NoBlocking - LICH H 7 - LICH I -1 A_BossDeath - Stop - } -} - -// Head FX 1 ---------------------------------------------------------------- - -ACTOR HeadFX1 -{ - Radius 12 - Height 6 - Speed 13 - FastSpeed 20 - Damage 1 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - +THRUGHOST - RenderStyle Add - - action native A_LichIceImpact(); - - States - { - Spawn: - FX05 ABC 6 BRIGHT - Loop - Death: - FX05 D 5 BRIGHT A_LichIceImpact - FX05 EFG 5 BRIGHT - Stop - } -} - -// Head FX 2 ---------------------------------------------------------------- - -ACTOR HeadFX2 -{ - Radius 12 - Height 6 - Speed 8 - Damage 3 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - States - { - Spawn: - FX05 HIJ 6 BRIGHT - Loop - Death: - FX05 DEFG 5 BRIGHT - Stop - } -} - - -// Head FX 3 ---------------------------------------------------------------- - -ACTOR HeadFX3 -{ - Radius 14 - Height 12 - Speed 10 - FastSpeed 18 - Damage 5 - Projectile - +WINDTHRUST - -ACTIVATEIMPACT - -ACTIVATEPCROSS - -NOBLOCKMAP - RenderStyle Add - - action native A_LichFireGrow (); - - States - { - Spawn: - FX06 ABC 4 BRIGHT A_LichFireGrow - Loop - NoGrow: - FX06 ABC 5 BRIGHT - Loop - Death: - FX06 DEFG 5 BRIGHT - Stop - } -} - - -// Whirlwind ---------------------------------------------------------------- - -ACTOR Whirlwind native -{ - Radius 16 - Height 74 - Speed 10 - Damage 1 - Projectile - -ACTIVATEIMPACT - -ACTIVATEMCROSS - +SEEKERMISSILE - +EXPLOCOUNT - +StepMissile - RenderStyle Translucent - DefThreshold 60 - Threshold 50 - Alpha 0.4 - - action native A_WhirlwindSeek(); - - States - { - Spawn: - FX07 DEFG 3 - FX07 ABC 3 A_WhirlwindSeek - Goto Spawn+4 - Death: - FX07 GFED 4 - Stop - } -} - - diff --git a/wadsrc/static/actors/heretic/knight.txt b/wadsrc/static/actors/heretic/knight.txt deleted file mode 100644 index 863c67b75..000000000 --- a/wadsrc/static/actors/heretic/knight.txt +++ /dev/null @@ -1,118 +0,0 @@ - -// Knight ------------------------------------------------------------------- - -ACTOR Knight -{ - Health 200 - Radius 24 - Height 78 - Mass 150 - Speed 12 - Painchance 100 - Monster - +FLOORCLIP - SeeSound "hknight/sight" - AttackSound "hknight/attack" - PainSound "hknight/pain" - DeathSound "hknight/death" - ActiveSound "hknight/active" - Obituary "$OB_BONEKNIGHT" - HitObituary "$OB_BONEKNIGHTHIT" - DropItem "CrossbowAmmo", 84, 5 - - action native A_KnightAttack (); - - States - { - Spawn: - KNIG AB 10 A_Look - Loop - See: - KNIG ABCD 4 A_Chase - Loop - Melee: - Missile: - KNIG E 10 A_FaceTarget - KNIG F 8 A_FaceTarget - KNIG G 8 A_KnightAttack - KNIG E 10 A_FaceTarget - KNIG F 8 A_FaceTarget - KNIG G 8 A_KnightAttack - Goto See - Pain: - KNIG H 3 - KNIG H 3 A_Pain - Goto See - Death: - KNIG I 6 - KNIG J 6 A_Scream - KNIG K 6 - KNIG L 6 A_NoBlocking - KNIG MN 6 - KNIG O -1 - Stop - } - -} - - -// Knight ghost ------------------------------------------------------------- - -ACTOR KnightGhost : Knight -{ - +SHADOW - +GHOST - RenderStyle Translucent - Alpha 0.4 -} - -// Knight axe --------------------------------------------------------------- - -ACTOR KnightAxe -{ - Radius 10 - Height 8 - Speed 9 - FastSpeed 18 - Damage 2 - Projectile - -NOBLOCKMAP - -ACTIVATEIMPACT - -ACTIVATEPCROSS - +WINDTHRUST - +THRUGHOST - DeathSound "hknight/hit" - States - { - Spawn: - SPAX A 3 BRIGHT A_PlaySound("hknight/axewhoosh") - SPAX BC 3 BRIGHT - Loop - Death: - SPAX DEF 6 BRIGHT - Stop - } -} - - -// Red axe ------------------------------------------------------------------ - -ACTOR RedAxe : KnightAxe -{ - +NOBLOCKMAP - -WINDTHRUST - Damage 7 - - action native A_DripBlood (); - - States - { - Spawn: - RAXE AB 5 BRIGHT A_DripBlood - Loop - Death: - RAXE CDE 6 BRIGHT - Stop - } -} - diff --git a/wadsrc/static/actors/heretic/wizard.txt b/wadsrc/static/actors/heretic/wizard.txt deleted file mode 100644 index 11ef0ad67..000000000 --- a/wadsrc/static/actors/heretic/wizard.txt +++ /dev/null @@ -1,96 +0,0 @@ - -// Wizard -------------------------------------------------------- - -ACTOR Wizard -{ - Health 180 - Radius 16 - Height 68 - Mass 100 - Speed 12 - Painchance 64 - Monster - +FLOAT - +NOGRAVITY - +DONTOVERLAP - SeeSound "wizard/sight" - AttackSound "wizard/attack" - PainSound "wizard/pain" - DeathSound "wizard/death" - ActiveSound "wizard/active" - Obituary "$OB_WIZARD" - HitObituary "$OB_WIZARDHIT" - DropItem "BlasterAmmo", 84, 10 - DropItem "ArtiTomeOfPower", 4, 0 - - action native A_GhostOff (); - action native A_WizAtk1 (); - action native A_WizAtk2 (); - action native A_WizAtk3 (); - - States - { - Spawn: - WZRD AB 10 A_Look - Loop - See: - WZRD A 3 A_Chase - WZRD A 4 A_Chase - WZRD A 3 A_Chase - WZRD A 4 A_Chase - WZRD B 3 A_Chase - WZRD B 4 A_Chase - WZRD B 3 A_Chase - WZRD B 4 A_Chase - Loop - Missile: - WZRD C 4 A_WizAtk1 - WZRD C 4 A_WizAtk2 - WZRD C 4 A_WizAtk1 - WZRD C 4 A_WizAtk2 - WZRD C 4 A_WizAtk1 - WZRD C 4 A_WizAtk2 - WZRD C 4 A_WizAtk1 - WZRD C 4 A_WizAtk2 - WZRD D 12 A_WizAtk3 - Goto See - Pain: - WZRD E 3 A_GhostOff - WZRD E 3 A_Pain - Goto See - Death: - WZRD F 6 A_GhostOff - WZRD G 6 A_Scream - WZRD HI 6 - WZRD J 6 A_NoBlocking - WZRD KL 6 - WZRD M -1 A_SetFloorClip - Stop - } -} - -// Projectile -------------------------------------------------------- - -ACTOR WizardFX1 -{ - Radius 10 - Height 6 - Speed 18 - FastSpeed 24 - Damage 3 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - States - { - Spawn: - FX11 AB 6 BRIGHT - Loop - Death: - FX11 CDEFG 5 BRIGHT - Stop - } -} - - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 69b2fbb55..b8586d3ee 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,9 +1,3 @@ -#include "actors/heretic/knight.txt" -#include "actors/heretic/wizard.txt" -#include "actors/heretic/ironlich.txt" -#include "actors/heretic/dsparil.txt" -#include "actors/heretic/chicken.txt" - #include "actors/hexen/baseweapons.txt" #include "actors/hexen/korax.txt" #include "actors/hexen/fighterplayer.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index e65e49fea..8fef6819a 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -79,11 +79,8 @@ zscript/heretic/clink.txt zscript/heretic/beast.txt zscript/heretic/snake.txt zscript/heretic/hereticimp.txt -/* zscript/heretic/knight.txt zscript/heretic/wizard.txt zscript/heretic/ironlich.txt zscript/heretic/dsparil.txt zscript/heretic/chicken.txt -*/ - diff --git a/wadsrc/static/zscript/heretic/chicken.txt b/wadsrc/static/zscript/heretic/chicken.txt new file mode 100644 index 000000000..2e5ada81c --- /dev/null +++ b/wadsrc/static/zscript/heretic/chicken.txt @@ -0,0 +1,201 @@ + +// Beak puff ---------------------------------------------------------------- + +class BeakPuff : StaffPuff +{ + Default + { + Mass 5; + Renderstyle "Translucent"; + Alpha 0.4; + AttackSound "chicken/attack"; + VSpeed 1; + } +} + +// Beak --------------------------------------------------------------------- + +class Beak : Weapon +{ + Default + { + Weapon.SelectionOrder 10000; + +WEAPON.DONTBOB + +WEAPON.MELEEWEAPON + Weapon.YAdjust 15; + Weapon.SisterWeapon "BeakPowered"; + } + + action native void A_BeakRaise (); + action native void A_BeakAttackPL1(); + + States + { + Ready: + BEAK A 1 A_WeaponReady; + Loop; + Deselect: + BEAK A 1 A_Lower; + Loop; + Select: + BEAK A 1 A_BeakRaise; + Loop; + Fire: + BEAK A 18 A_BeakAttackPL1; + Goto Ready; + } +} + + +class BeakPowered : Beak +{ + Default + { + +WEAPON.POWERED_UP + Weapon.SisterWeapon "Beak"; + } + + action native void A_BeakAttackPL2(); + + States + { + Fire: + BEAK A 12 A_BeakAttackPL2; + Goto Ready; + } +} + +// Chicken player ----------------------------------------------------------- + +class ChickenPlayer : PlayerPawn native +{ + Default + { + Health 30; + ReactionTime 0; + PainChance 255; + Radius 16; + Height 24; + Speed 1; + Gravity 0.125; + +NOSKIN + +PLAYERPAWN.CANSUPERMORPH + PainSound "chicken/pain"; + DeathSound "chicken/death"; + Player.JumpZ 1; + Player.Viewheight 21; + Player.ForwardMove 1.22, 1.22; + Player.SideMove 1.22, 1.22; + Player.SpawnClass "Chicken"; + Player.SoundClass "Chicken"; + Player.DisplayName "Chicken"; + Player.MorphWeapon "Beak"; + -PICKUP + } + + States + { + Spawn: + CHKN A -1; + Stop; + See: + CHKN ABAB 3; + Loop; + Melee: + Missile: + CHKN C 12; + Goto Spawn; + Pain: + CHKN D 4 A_Feathers; + CHKN C 4 A_Pain; + Goto Spawn; + Death: + CHKN E 6 A_Scream; + CHKN F 6 A_Feathers; + CHKN G 6; + CHKN H 6 A_NoBlocking; + CHKN IJK 6; + CHKN L -1; + Stop; + } +} + + + +// Chicken (non-player) ----------------------------------------------------- + +class Chicken : MorphedMonster +{ + Default + { + Health 10; + Radius 9; + Height 22; + Mass 40; + Speed 4; + Painchance 200; + Monster; + -COUNTKILL + +WINDTHRUST + +DONTMORPH + +FLOORCLIP + SeeSound "chicken/pain"; + AttackSound "chicken/attack"; + PainSound "chicken/pain"; + DeathSound "chicken/death"; + ActiveSound "chicken/active"; + Obituary "$OB_CHICKEN"; + } + States + { + Spawn: + CHKN AB 10 A_Look; + Loop; + See: + CHKN AB 3 A_Chase; + Loop; + Pain: + CHKN D 5 A_Feathers; + CHKN C 5 A_Pain; + Goto See; + Melee: + CHKN A 8 A_FaceTarget; + CHKN C 10 A_CustomMeleeAttack(random[ChicAttack](1,2)); + Goto See; + Death: + CHKN E 6 A_Scream; + CHKN F 6 A_Feathers; + CHKN G 6; + CHKN H 6 A_NoBlocking; + CHKN IJK 6; + CHKN L -1; + Stop; + } +} + + +// Feather ------------------------------------------------------------------ + +class Feather : Actor +{ + Default + { + Radius 2; + Height 4; + +MISSILE +DROPOFF + +NOTELEPORT +CANNOTPUSH + +WINDTHRUST +DONTSPLASH + Gravity 0.125; + } + + States + { + Spawn: + CHKN MNOPQPON 3; + Loop; + Death: + CHKN N 6; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/dsparil.txt b/wadsrc/static/zscript/heretic/dsparil.txt new file mode 100644 index 000000000..ebf60eb47 --- /dev/null +++ b/wadsrc/static/zscript/heretic/dsparil.txt @@ -0,0 +1,297 @@ + +// Boss spot ---------------------------------------------------------------- + +class BossSpot : SpecialSpot +{ + Default + { + +INVISIBLE + } +} + +// Sorcerer (D'Sparil on his serpent) --------------------------------------- + +class Sorcerer1 : Actor +{ + Default + { + Health 2000; + Radius 28; + Height 100; + Mass 800; + Speed 16; + PainChance 56; + Monster; + +BOSS + +DONTMORPH + +NORADIUSDMG + +NOTARGET + +NOICEDEATH + +FLOORCLIP + +DONTGIB + SeeSound "dsparilserpent/sight"; + AttackSound "dsparilserpent/attack"; + PainSound "dsparilserpent/pain"; + DeathSound "dsparilserpent/death"; + ActiveSound "dsparilserpent/active"; + Obituary "$OB_DSPARIL1"; + HitObituary "$OB_DSPARIL1HIT"; + } + + action native void A_Sor1Pain (); + action native void A_Sor1Chase (); + action native void A_Srcr1Attack (); + action native void A_SorcererRise (); + + States + { + Spawn: + SRCR AB 10 A_Look; + Loop; + See: + SRCR ABCD 5 A_Sor1Chase; + Loop; + Pain: + SRCR Q 6 A_Sor1Pain; + Goto See; + Missile: + SRCR Q 7 A_FaceTarget; + SRCR R 6 A_FaceTarget; + SRCR S 10 A_Srcr1Attack; + Goto See; + Missile2: + SRCR S 10 A_FaceTarget; + SRCR Q 7 A_FaceTarget; + SRCR R 6 A_FaceTarget; + SRCR S 10 A_Srcr1Attack; + Goto See; + Death: + SRCR E 7; + SRCR F 7 A_Scream; + SRCR G 7; + SRCR HIJK 6; + SRCR L 25 A_PlaySound("dsparil/zap", CHAN_BODY, 1, false, ATTN_NONE); + SRCR MN 5; + SRCR O 4; + SRCR L 20 A_PlaySound("dsparil/zap", CHAN_BODY, 1, false, ATTN_NONE); + SRCR MN 5; + SRCR O 4; + SRCR L 12; + SRCR P -1 A_SorcererRise; + } +} + + +// Sorcerer FX 1 ------------------------------------------------------------ + +class SorcererFX1 : Actor +{ + Default + { + Radius 10; + Height 10; + Speed 20; + FastSpeed 28; + Damage 10; + DamageType "Fire"; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + } + + States + { + Spawn: + FX14 ABC 6 BRIGHT; + Loop; + Death: + FX14 DEFGH 5 BRIGHT; + Stop; + } +} + + +// Sorcerer 2 (D'Sparil without his serpent) -------------------------------- + +class Sorcerer2 : Actor +{ + Default + { + Health 3500; + Radius 16; + Height 70; + Mass 300; + Speed 14; + Painchance 32; + Monster; + +DROPOFF + +BOSS + +DONTMORPH + +FULLVOLACTIVE + +NORADIUSDMG + +NOTARGET + +NOICEDEATH + +FLOORCLIP + +BOSSDEATH + SeeSound "dsparil/sight"; + AttackSound "dsparil/attack"; + PainSound "dsparil/pain"; + ActiveSound "dsparil/active"; + Obituary "$OB_DSPARIL2"; + HitObituary "$OB_DSPARIL2HIT"; + } + + action native void A_Srcr2Decide (); + action native void A_Srcr2Attack (); + action native void A_Sor2DthInit (); + action native void A_Sor2DthLoop (); + + States + { + Spawn: + SOR2 MN 10 A_Look; + Loop; + See: + SOR2 MNOP 4 A_Chase; + Loop; + Rise: + SOR2 AB 4; + SOR2 C 4 A_PlaySound("dsparil/rise", CHAN_BODY, 1, false, ATTN_NONE); + SOR2 DEF 4; + SOR2 G 12 A_PlaySound("dsparil/sight", CHAN_BODY, 1, false, ATTN_NONE); + Goto See; + Pain: + SOR2 Q 3; + SOR2 Q 6 A_Pain; + Goto See; + Missile: + SOR2 R 9 A_Srcr2Decide; + SOR2 S 9 A_FaceTarget; + SOR2 T 20 A_Srcr2Attack; + Goto See; + Teleport: + SOR2 LKJIHG 6; + Goto See; + Death: + SDTH A 8 A_Sor2DthInit; + SDTH B 8; + SDTH C 8 A_PlaySound("dsparil/scream", CHAN_BODY, 1, false, ATTN_NONE); + DeathLoop: + SDTH DE 7; + SDTH F 7 A_Sor2DthLoop; + SDTH G 6 A_PlaySound("dsparil/explode", CHAN_BODY, 1, false, ATTN_NONE); + SDTH H 6; + SDTH I 18; + SDTH J 6 A_NoBlocking; + SDTH K 6 A_PlaySound("dsparil/bones", CHAN_BODY, 1, false, ATTN_NONE); + SDTH LMN 6; + SDTH O -1 A_BossDeath; + Stop; + } +} + + + +// Sorcerer 2 FX 1 ---------------------------------------------------------- + +class Sorcerer2FX1 : Actor +{ + Default + { + Radius 10; + Height 6; + Speed 20; + FastSpeed 28; + Damage 1; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + } + + action native void A_BlueSpark (); + + States + { + Spawn: + FX16 ABC 3 BRIGHT A_BlueSpark; + Loop; + Death: + FX16 G 5 BRIGHT A_Explode(random[S2FX1](80,111)); + FX16 HIJKL 5 BRIGHT; + Stop; + } +} + +// Sorcerer 2 FX Spark ------------------------------------------------------ + +class Sorcerer2FXSpark : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + +NOGRAVITY + +NOTELEPORT + +CANNOTPUSH + RenderStyle "Add"; + } + + States + { + Spawn: + FX16 DEF 12 BRIGHT; + Stop; + } +} + +// Sorcerer 2 FX 2 ---------------------------------------------------------- + +class Sorcerer2FX2 : Actor +{ + Default + { + Radius 10; + Height 6; + Speed 6; + Damage 10; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + } + + action native void A_GenWizard (); + + States + { + Spawn: + FX11 A 35 BRIGHT; + FX11 A 5 BRIGHT A_GenWizard; + FX11 B 5 BRIGHT; + Goto Spawn+1; + Death: + FX11 CDEFG 5 BRIGHT; + Stop; + + } +} +// Sorcerer 2 Telefade ------------------------------------------------------ + +class Sorcerer2Telefade : Actor +{ + Default + { + +NOBLOCKMAP + } + + States + { + Spawn: + SOR2 GHIJKL 6; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/ironlich.txt b/wadsrc/static/zscript/heretic/ironlich.txt new file mode 100644 index 000000000..9b66bcb0d --- /dev/null +++ b/wadsrc/static/zscript/heretic/ironlich.txt @@ -0,0 +1,191 @@ + +// Ironlich ----------------------------------------------------------------- + +class Ironlich : Actor +{ + Default + { + Health 700; + Radius 40; + Height 72; + Mass 325; + Speed 6; + Painchance 32; + Monster; + +NOBLOOD + +DONTMORPH + +DONTSQUASH + +BOSSDEATH + SeeSound "ironlich/sight"; + AttackSound "ironlich/attack"; + PainSound "ironlich/pain"; + DeathSound "ironlich/death"; + ActiveSound "ironlich/active"; + Obituary "$OB_IRONLICH"; + HitObituary "$OB_IRONLICHHIT"; + DropItem "BlasterAmmo", 84, 10; + DropItem "ArtiEgg", 51, 0; + } + + action native void A_LichAttack (); + + States + { + Spawn: + LICH A 10 A_Look; + Loop; + See: + LICH A 4 A_Chase; + Loop; + Missile: + LICH A 5 A_FaceTarget; + LICH B 20 A_LichAttack; + Goto See; + Pain: + LICH A 4; + LICH A 4 A_Pain; + Goto See; + Death: + LICH C 7; + LICH D 7 A_Scream; + LICH EF 7; + LICH G 7 A_NoBlocking; + LICH H 7; + LICH I -1 A_BossDeath; + Stop; + } +} + +// Head FX 1 ---------------------------------------------------------------- + +class HeadFX1 : Actor +{ + Default + { + Radius 12; + Height 6; + Speed 13; + FastSpeed 20; + Damage 1; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + +THRUGHOST + RenderStyle "Add"; + } + + action native void A_LichIceImpact(); + + States + { + Spawn: + FX05 ABC 6 BRIGHT; + Loop; + Death: + FX05 D 5 BRIGHT A_LichIceImpact; + FX05 EFG 5 BRIGHT; + Stop; + } +} + +// Head FX 2 ---------------------------------------------------------------- + +class HeadFX2 : Actor +{ + Default + { + Radius 12; + Height 6; + Speed 8; + Damage 3; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + } + + States + { + Spawn: + FX05 HIJ 6 BRIGHT; + Loop; + Death: + FX05 DEFG 5 BRIGHT; + Stop; + } +} + + +// Head FX 3 ---------------------------------------------------------------- + +class HeadFX3 : Actor +{ + Default + { + Radius 14; + Height 12; + Speed 10; + FastSpeed 18; + Damage 5; + Projectile; + +WINDTHRUST + -ACTIVATEIMPACT + -ACTIVATEPCROSS + -NOBLOCKMAP + RenderStyle "Add"; + } + + action native void A_LichFireGrow (); + + States + { + Spawn: + FX06 ABC 4 BRIGHT A_LichFireGrow; + Loop; + NoGrow: + FX06 ABC 5 BRIGHT; + Loop; + Death: + FX06 DEFG 5 BRIGHT; + Stop; + } +} + + +// Whirlwind ---------------------------------------------------------------- + +class Whirlwind : Actor native +{ + Default + { + Radius 16; + Height 74; + Speed 10; + Damage 1; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEMCROSS + +SEEKERMISSILE + +EXPLOCOUNT + +StepMissile + RenderStyle "Translucent"; + DefThreshold 60; + Threshold 50; + Alpha 0.4; + } + + action native void A_WhirlwindSeek(); + + States + { + Spawn: + FX07 DEFG 3; + FX07 ABC 3 A_WhirlwindSeek; + Goto Spawn+4; + Death: + FX07 GFED 4; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/heretic/knight.txt b/wadsrc/static/zscript/heretic/knight.txt new file mode 100644 index 000000000..f8b84b9aa --- /dev/null +++ b/wadsrc/static/zscript/heretic/knight.txt @@ -0,0 +1,131 @@ + +// Knight ------------------------------------------------------------------- + +class Knight : Actor +{ + Default + { + Health 200; + Radius 24; + Height 78; + Mass 150; + Speed 12; + Painchance 100; + Monster; + +FLOORCLIP + SeeSound "hknight/sight"; + AttackSound "hknight/attack"; + PainSound "hknight/pain"; + DeathSound "hknight/death"; + ActiveSound "hknight/active"; + Obituary "$OB_BONEKNIGHT"; + HitObituary "$OB_BONEKNIGHTHIT"; + DropItem "CrossbowAmmo", 84, 5; + } + + action native void A_KnightAttack (); + + States + { + Spawn: + KNIG AB 10 A_Look; + Loop; + See: + KNIG ABCD 4 A_Chase; + Loop; + Melee: + Missile: + KNIG E 10 A_FaceTarget; + KNIG F 8 A_FaceTarget; + KNIG G 8 A_KnightAttack; + KNIG E 10 A_FaceTarget; + KNIG F 8 A_FaceTarget; + KNIG G 8 A_KnightAttack; + Goto See; + Pain: + KNIG H 3; + KNIG H 3 A_Pain; + Goto See; + Death: + KNIG I 6; + KNIG J 6 A_Scream; + KNIG K 6; + KNIG L 6 A_NoBlocking; + KNIG MN 6; + KNIG O -1; + Stop; + } + +} + + +// Knight ghost ------------------------------------------------------------- + +class KnightGhost : Knight +{ + Default + { + +SHADOW + +GHOST + RenderStyle "Translucent"; + Alpha 0.4; + } +} + +// Knight axe --------------------------------------------------------------- + +class KnightAxe : Actor +{ + Default + { + Radius 10; + Height 8; + Speed 9; + FastSpeed 18; + Damage 2; + Projectile; + -NOBLOCKMAP + -ACTIVATEIMPACT + -ACTIVATEPCROSS + +WINDTHRUST + +THRUGHOST + DeathSound "hknight/hit"; + } + + States + { + Spawn: + SPAX A 3 BRIGHT A_PlaySound("hknight/axewhoosh"); + SPAX BC 3 BRIGHT; + Loop; + Death: + SPAX DEF 6 BRIGHT; + Stop; + } +} + + +// Red axe ------------------------------------------------------------------ + +class RedAxe : KnightAxe +{ + Default + { + +NOBLOCKMAP + -WINDTHRUST + Damage 7; + } + + action native void A_DripBlood (); + + States + { + Spawn: + RAXE AB 5 BRIGHT A_DripBlood; + Loop; + Death: + RAXE CDE 6 BRIGHT; + Stop; + } +} + diff --git a/wadsrc/static/zscript/heretic/wizard.txt b/wadsrc/static/zscript/heretic/wizard.txt new file mode 100644 index 000000000..3599354ad --- /dev/null +++ b/wadsrc/static/zscript/heretic/wizard.txt @@ -0,0 +1,103 @@ + +// Wizard -------------------------------------------------------- + +class Wizard : Actor +{ + Default + { + Health 180; + Radius 16; + Height 68; + Mass 100; + Speed 12; + Painchance 64; + Monster; + +FLOAT + +NOGRAVITY + +DONTOVERLAP + SeeSound "wizard/sight"; + AttackSound "wizard/attack"; + PainSound "wizard/pain"; + DeathSound "wizard/death"; + ActiveSound "wizard/active"; + Obituary "$OB_WIZARD"; + HitObituary "$OB_WIZARDHIT"; + DropItem "BlasterAmmo", 84, 10; + DropItem "ArtiTomeOfPower", 4, 0; + } + + action native void A_GhostOff (); + action native void A_WizAtk1 (); + action native void A_WizAtk2 (); + action native void A_WizAtk3 (); + + States + { + Spawn: + WZRD AB 10 A_Look; + Loop; + See: + WZRD A 3 A_Chase; + WZRD A 4 A_Chase; + WZRD A 3 A_Chase; + WZRD A 4 A_Chase; + WZRD B 3 A_Chase; + WZRD B 4 A_Chase; + WZRD B 3 A_Chase; + WZRD B 4 A_Chase; + Loop; + Missile: + WZRD C 4 A_WizAtk1; + WZRD C 4 A_WizAtk2; + WZRD C 4 A_WizAtk1; + WZRD C 4 A_WizAtk2; + WZRD C 4 A_WizAtk1; + WZRD C 4 A_WizAtk2; + WZRD C 4 A_WizAtk1; + WZRD C 4 A_WizAtk2; + WZRD D 12 A_WizAtk3; + Goto See; + Pain: + WZRD E 3 A_GhostOff; + WZRD E 3 A_Pain; + Goto See; + Death: + WZRD F 6 A_GhostOff; + WZRD G 6 A_Scream; + WZRD HI 6; + WZRD J 6 A_NoBlocking; + WZRD KL 6; + WZRD M -1 A_SetFloorClip; + Stop; + } +} + +// Projectile -------------------------------------------------------- + +class WizardFX1 : Actor +{ + Default + { + Radius 10; + Height 6; + Speed 18; + FastSpeed 24; + Damage 3; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + } + + States + { + Spawn: + FX11 AB 6 BRIGHT; + Loop; + Death: + FX11 CDEFG 5 BRIGHT; + Stop; + } +} + + From d0a8960f61b727bdade1c385c7720931a8497bac Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 14:38:51 +0200 Subject: [PATCH 056/255] - added genuine PEX_GT, PEX_GTEQ and PEX_NEQ operations to the parser. These were previously faked with the inverse plus a boolean not. Although this works, it either leads to sub-optimal code generation or some fudging to avoid the inefficient handling. Just adding proper handling to the parser seems the easiest and most straightforward way to get around this. The code generator already can deal with these operations properly so there's no good reason to do it differently. --- src/scripting/zscript/zcc-parse.lemon | 15 ++++++--------- src/scripting/zscript/zcc_expr.cpp | 12 ++++++++++++ src/scripting/zscript/zcc_exprlist.h | 3 +++ 3 files changed, 21 insertions(+), 9 deletions(-) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 78a4d29ea..215670c82 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -1161,9 +1161,8 @@ expr(X) ::= expr(A) LT expr(B). /* a < b */ } expr(X) ::= expr(A) GT expr(B). /* a > b */ { - BINARY_EXPR(A,B,PEX_LTEQ); - UNARY_EXPR(expr2,PEX_BoolNot); - X = expr1; + BINARY_EXPR(A,B,PEX_GT); + X = expr2; } expr(X) ::= expr(A) LTEQ expr(B). /* a <= b */ { @@ -1172,9 +1171,8 @@ expr(X) ::= expr(A) LTEQ expr(B). /* a <= b */ } expr(X) ::= expr(A) GTEQ expr(B). /* a >= b */ { - BINARY_EXPR(A,B,PEX_LT); - UNARY_EXPR(expr1,PEX_BoolNot); - X = expr1; + BINARY_EXPR(A,B,PEX_GTEQ); + X = expr2; } expr(X) ::= expr(A) LTGTEQ expr(B). /* a <>= b */ { @@ -1194,9 +1192,8 @@ expr(X) ::= expr(A) EQEQ expr(B). /* a == b */ } expr(X) ::= expr(A) NEQ expr(B). /* a != b */ { - BINARY_EXPR(A,B,PEX_EQEQ); - UNARY_EXPR(expr2,PEX_BoolNot); - X = expr1; + BINARY_EXPR(A,B,PEX_NEQ); + X = expr2; } expr(X) ::= expr(A) APPROXEQ expr(B). /* a ~== b */ { diff --git a/src/scripting/zscript/zcc_expr.cpp b/src/scripting/zscript/zcc_expr.cpp index 6f640d8f1..b34251061 100644 --- a/src/scripting/zscript/zcc_expr.cpp +++ b/src/scripting/zscript/zcc_expr.cpp @@ -365,6 +365,18 @@ void ZCC_InitOperators() { PEX_LTEQ , (PType **)&TypeBool, (PType **)&TypeUInt32, (PType **)&TypeUInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->UIntVal <= r->UIntVal; l->Type = TypeBool; return l; } }, { PEX_LTEQ , (PType **)&TypeBool, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->IntVal = l->DoubleVal <= r->DoubleVal; l->Type = TypeBool; return l; } }, + { PEX_GT , (PType **)&TypeBool, (PType **)&TypeSInt32, (PType **)&TypeSInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->IntVal > r->IntVal; l->Type = TypeBool; return l; } }, + { PEX_GT , (PType **)&TypeBool, (PType **)&TypeUInt32, (PType **)&TypeUInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->UIntVal > r->UIntVal; l->Type = TypeBool; return l; } }, + { PEX_GT , (PType **)&TypeBool, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->IntVal = l->DoubleVal > r->DoubleVal; l->Type = TypeBool; return l; } }, + + { PEX_GTEQ , (PType **)&TypeBool, (PType **)&TypeSInt32, (PType **)&TypeSInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->IntVal >= r->IntVal; l->Type = TypeBool; return l; } }, + { PEX_GTEQ , (PType **)&TypeBool, (PType **)&TypeUInt32, (PType **)&TypeUInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->UIntVal >= r->UIntVal; l->Type = TypeBool; return l; } }, + { PEX_GTEQ , (PType **)&TypeBool, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->IntVal = l->DoubleVal >= r->DoubleVal; l->Type = TypeBool; return l; } }, + + { PEX_NEQ , (PType **)&TypeBool, (PType **)&TypeSInt32, (PType **)&TypeSInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->IntVal != r->IntVal; l->Type = TypeBool; return l; } }, + { PEX_NEQ , (PType **)&TypeBool, (PType **)&TypeUInt32, (PType **)&TypeUInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->UIntVal != r->UIntVal; l->Type = TypeBool; return l; } }, + { PEX_NEQ , (PType **)&TypeBool, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->IntVal = l->DoubleVal != r->DoubleVal; l->Type = TypeBool; return l; } }, + { PEX_EQEQ , (PType **)&TypeBool, (PType **)&TypeSInt32, (PType **)&TypeSInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->IntVal == r->IntVal; l->Type = TypeBool; return l; } }, { PEX_EQEQ , (PType **)&TypeBool, (PType **)&TypeUInt32, (PType **)&TypeUInt32, [](auto *l, auto *r, auto &) { l->IntVal = l->UIntVal == r->UIntVal; l->Type = TypeBool; return l; } }, { PEX_EQEQ , (PType **)&TypeBool, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->IntVal = l->DoubleVal == r->DoubleVal; l->Type = TypeBool; return l; } }, diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index e36aedea6..2df687798 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -36,10 +36,13 @@ xx(Concat, ) xx(LT, ) xx(LTEQ, ) +xx(GT, ) +xx(GTEQ, ) xx(LTGTEQ, ) xx(Is, ) xx(EQEQ, ) +xx(NEQ, ) xx(APREQ, ) xx(BitAnd, ) From 938ab4ca706c278d34f03ce37eda262bbde100ca Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 15:17:48 +0200 Subject: [PATCH 057/255] - implemented '**' (power) operator. To ensure reliability, acustom 'pow' function will be used to calculate it. - fixed: FxBinary::ResolveLR' check for numeric operations was incomplete. Like far too many other places it just assumed that everything with ValueType->GetRegType() == REGT_INT is a numeric type, but for names this is not the case. --- src/CMakeLists.txt | 2 + src/fragglescript/t_func.cpp | 2 +- src/math/cmath.h | 3 + src/math/pow.c | 756 +++++++++++++++++++++++ src/math/powi.c | 186 ++++++ src/scripting/codegeneration/codegen.cpp | 67 +- src/scripting/codegeneration/codegen.h | 15 + src/scripting/vm/vmexec.h | 6 +- src/scripting/zscript/zcc_compile.cpp | 3 + src/scripting/zscript/zcc_expr.cpp | 3 +- 10 files changed, 1033 insertions(+), 10 deletions(-) create mode 100644 src/math/pow.c create mode 100644 src/math/powi.c diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ae2f19960..ddd027c80 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1287,6 +1287,8 @@ add_executable( zdoom WIN32 MACOSX_BUNDLE math/log10.c math/mtherr.c math/polevl.c + math/pow.c + math/powi.c math/sin.c math/sinh.c math/sqrt.c diff --git a/src/fragglescript/t_func.cpp b/src/fragglescript/t_func.cpp index a02ec947f..4897d8fdb 100644 --- a/src/fragglescript/t_func.cpp +++ b/src/fragglescript/t_func.cpp @@ -3636,7 +3636,7 @@ void FParser::SF_Pow() { if (CheckArgs(2)) { - t_return.setDouble(pow(floatvalue(t_argv[0]), floatvalue(t_argv[1]))); + t_return.setDouble(g_pow(floatvalue(t_argv[0]), floatvalue(t_argv[1]))); } } diff --git a/src/math/cmath.h b/src/math/cmath.h index 9fd0b570d..5c02c4e87 100644 --- a/src/math/cmath.h +++ b/src/math/cmath.h @@ -23,6 +23,7 @@ double c_tanh(double); double c_exp(double); double c_log(double); double c_log10(double); +double c_pow(double, double); } @@ -114,6 +115,7 @@ inline double cosdeg(double v) #define g_exp exp #define g_log log #define g_log10 log10 +#define g_pow pow #else #define g_asin c_asin #define g_acos c_acos @@ -139,6 +141,7 @@ inline double cosdeg(double v) #define g_exp c_exp #define g_log c_log #define g_log10 c_log10 +#define g_pow c_pow #endif diff --git a/src/math/pow.c b/src/math/pow.c new file mode 100644 index 000000000..c55fa81fd --- /dev/null +++ b/src/math/pow.c @@ -0,0 +1,756 @@ +/* pow.c + * + * Power function + * + * + * + * SYNOPSIS: + * + * double x, y, z, pow(); + * + * z = pow( x, y ); + * + * + * + * DESCRIPTION: + * + * Computes x raised to the yth power. Analytically, + * + * x**y = exp( y log(x) ). + * + * Following Cody and Waite, this program uses a lookup table + * of 2**-i/16 and pseudo extended precision arithmetic to + * obtain an extra three bits of accuracy in both the logarithm + * and the exponential. + * + * + * + * ACCURACY: + * + * Relative error: + * arithmetic domain # trials peak rms + * IEEE -26,26 30000 4.2e-16 7.7e-17 + * DEC -26,26 60000 4.8e-17 9.1e-18 + * 1/26 < x < 26, with log(x) uniformly distributed. + * -26 < y < 26, y uniformly distributed. + * IEEE 0,8700 30000 1.5e-14 2.1e-15 + * 0.99 < x < 1.01, 0 < y < 8700, uniformly distributed. + * + * + * ERROR MESSAGES: + * + * message condition value returned + * pow overflow x**y > MAXNUM INFINITY + * pow underflow x**y < 1/MAXNUM 0.0 + * pow domain x<0 and y noninteger 0.0 + * + */ + +/* +Cephes Math Library Release 2.8: June, 2000 +Copyright 1984, 1995, 2000 by Stephen L. Moshier +*/ + + +#include "mconf.h" +static char fname[] = {"pow"}; + +#define SQRTH 0.70710678118654752440 + +#ifdef UNK +static double P[] = { + 4.97778295871696322025E-1, + 3.73336776063286838734E0, + 7.69994162726912503298E0, + 4.66651806774358464979E0 +}; +static double Q[] = { +/* 1.00000000000000000000E0, */ + 9.33340916416696166113E0, + 2.79999886606328401649E1, + 3.35994905342304405431E1, + 1.39995542032307539578E1 +}; +/* 2^(-i/16), IEEE precision */ +static double A[] = { + 1.00000000000000000000E0, + 9.57603280698573700036E-1, + 9.17004043204671215328E-1, + 8.78126080186649726755E-1, + 8.40896415253714502036E-1, + 8.05245165974627141736E-1, + 7.71105412703970372057E-1, + 7.38413072969749673113E-1, + 7.07106781186547572737E-1, + 6.77127773468446325644E-1, + 6.48419777325504820276E-1, + 6.20928906036742001007E-1, + 5.94603557501360513449E-1, + 5.69394317378345782288E-1, + 5.45253866332628844837E-1, + 5.22136891213706877402E-1, + 5.00000000000000000000E-1 +}; +static double B[] = { + 0.00000000000000000000E0, + 1.64155361212281360176E-17, + 4.09950501029074826006E-17, + 3.97491740484881042808E-17, +-4.83364665672645672553E-17, + 1.26912513974441574796E-17, + 1.99100761573282305549E-17, +-1.52339103990623557348E-17, + 0.00000000000000000000E0 +}; +static double R[] = { + 1.49664108433729301083E-5, + 1.54010762792771901396E-4, + 1.33335476964097721140E-3, + 9.61812908476554225149E-3, + 5.55041086645832347466E-2, + 2.40226506959099779976E-1, + 6.93147180559945308821E-1 +}; + +#define douba(k) A[k] +#define doubb(k) B[k] +#define MEXP 16383.0 +#ifdef DENORMAL +#define MNEXP -17183.0 +#else +#define MNEXP -16383.0 +#endif +#endif + +#ifdef DEC +static unsigned short P[] = { +0037776,0156313,0175332,0163602, +0040556,0167577,0052366,0174245, +0040766,0062753,0175707,0055564, +0040625,0052035,0131344,0155636, +}; +static unsigned short Q[] = { +/*0040200,0000000,0000000,0000000,*/ +0041025,0052644,0154404,0105155, +0041337,0177772,0007016,0047646, +0041406,0062740,0154273,0020020, +0041137,0177054,0106127,0044555, +}; +static unsigned short A[] = { +0040200,0000000,0000000,0000000, +0040165,0022575,0012444,0103314, +0040152,0140306,0163735,0022071, +0040140,0146336,0166052,0112341, +0040127,0042374,0145326,0116553, +0040116,0022214,0012437,0102201, +0040105,0063452,0010525,0003333, +0040075,0004243,0117530,0006067, +0040065,0002363,0031771,0157145, +0040055,0054076,0165102,0120513, +0040045,0177326,0124661,0050471, +0040036,0172462,0060221,0120422, +0040030,0033760,0050615,0134251, +0040021,0141723,0071653,0010703, +0040013,0112701,0161752,0105727, +0040005,0125303,0063714,0044173, +0040000,0000000,0000000,0000000 +}; +static unsigned short B[] = { +0000000,0000000,0000000,0000000, +0021473,0040265,0153315,0140671, +0121074,0062627,0042146,0176454, +0121413,0003524,0136332,0066212, +0121767,0046404,0166231,0012553, +0121257,0015024,0002357,0043574, +0021736,0106532,0043060,0056206, +0121310,0020334,0165705,0035326, +0000000,0000000,0000000,0000000 +}; + +static unsigned short R[] = { +0034173,0014076,0137624,0115771, +0035041,0076763,0003744,0111311, +0035656,0141766,0041127,0074351, +0036435,0112533,0073611,0116664, +0037143,0054106,0134040,0152223, +0037565,0176757,0176026,0025551, +0040061,0071027,0173721,0147572 +}; + +/* +static double R[] = { +0.14928852680595608186e-4, +0.15400290440989764601e-3, +0.13333541313585784703e-2, +0.96181290595172416964e-2, +0.55504108664085595326e-1, +0.24022650695909537056e0, +0.69314718055994529629e0 +}; +*/ +#define douba(k) (*(double *)&A[(k)<<2]) +#define doubb(k) (*(double *)&B[(k)<<2]) +#define MEXP 2031.0 +#define MNEXP -2031.0 +#endif + +#ifdef IBMPC +static unsigned short P[] = { +0x5cf0,0x7f5b,0xdb99,0x3fdf, +0xdf15,0xea9e,0xddef,0x400d, +0xeb6f,0x7f78,0xccbd,0x401e, +0x9b74,0xb65c,0xaa83,0x4012, +}; +static unsigned short Q[] = { +/*0x0000,0x0000,0x0000,0x3ff0,*/ +0x914e,0x9b20,0xaab4,0x4022, +0xc9f5,0x41c1,0xffff,0x403b, +0x6402,0x1b17,0xccbc,0x4040, +0xe92e,0x918a,0xffc5,0x402b, +}; +static unsigned short A[] = { +0x0000,0x0000,0x0000,0x3ff0, +0x90da,0xa2a4,0xa4af,0x3fee, +0xa487,0xdcfb,0x5818,0x3fed, +0x529c,0xdd85,0x199b,0x3fec, +0xd3ad,0x995a,0xe89f,0x3fea, +0xf090,0x82a3,0xc491,0x3fe9, +0xa0db,0x422a,0xace5,0x3fe8, +0x0187,0x73eb,0xa114,0x3fe7, +0x3bcd,0x667f,0xa09e,0x3fe6, +0x5429,0xdd48,0xab07,0x3fe5, +0x2a27,0xd536,0xbfda,0x3fe4, +0x3422,0x4c12,0xdea6,0x3fe3, +0xb715,0x0a31,0x06fe,0x3fe3, +0x6238,0x6e75,0x387a,0x3fe2, +0x517b,0x3c7d,0x72b8,0x3fe1, +0x890f,0x6cf9,0xb558,0x3fe0, +0x0000,0x0000,0x0000,0x3fe0 +}; +static unsigned short B[] = { +0x0000,0x0000,0x0000,0x0000, +0x3707,0xd75b,0xed02,0x3c72, +0xcc81,0x345d,0xa1cd,0x3c87, +0x4b27,0x5686,0xe9f1,0x3c86, +0x6456,0x13b2,0xdd34,0xbc8b, +0x42e2,0xafec,0x4397,0x3c6d, +0x82e4,0xd231,0xf46a,0x3c76, +0x8a76,0xb9d7,0x9041,0xbc71, +0x0000,0x0000,0x0000,0x0000 +}; +static unsigned short R[] = { +0x937f,0xd7f2,0x6307,0x3eef, +0x9259,0x60fc,0x2fbe,0x3f24, +0xef1d,0xc84a,0xd87e,0x3f55, +0x33b7,0x6ef1,0xb2ab,0x3f83, +0x1a92,0xd704,0x6b08,0x3fac, +0xc56d,0xff82,0xbfbd,0x3fce, +0x39ef,0xfefa,0x2e42,0x3fe6 +}; + +#define douba(k) (*(double *)&A[(k)<<2]) +#define doubb(k) (*(double *)&B[(k)<<2]) +#define MEXP 16383.0 +#ifdef DENORMAL +#define MNEXP -17183.0 +#else +#define MNEXP -16383.0 +#endif +#endif + +#ifdef MIEEE +static unsigned short P[] = { +0x3fdf,0xdb99,0x7f5b,0x5cf0, +0x400d,0xddef,0xea9e,0xdf15, +0x401e,0xccbd,0x7f78,0xeb6f, +0x4012,0xaa83,0xb65c,0x9b74 +}; +static unsigned short Q[] = { +0x4022,0xaab4,0x9b20,0x914e, +0x403b,0xffff,0x41c1,0xc9f5, +0x4040,0xccbc,0x1b17,0x6402, +0x402b,0xffc5,0x918a,0xe92e +}; +static unsigned short A[] = { +0x3ff0,0x0000,0x0000,0x0000, +0x3fee,0xa4af,0xa2a4,0x90da, +0x3fed,0x5818,0xdcfb,0xa487, +0x3fec,0x199b,0xdd85,0x529c, +0x3fea,0xe89f,0x995a,0xd3ad, +0x3fe9,0xc491,0x82a3,0xf090, +0x3fe8,0xace5,0x422a,0xa0db, +0x3fe7,0xa114,0x73eb,0x0187, +0x3fe6,0xa09e,0x667f,0x3bcd, +0x3fe5,0xab07,0xdd48,0x5429, +0x3fe4,0xbfda,0xd536,0x2a27, +0x3fe3,0xdea6,0x4c12,0x3422, +0x3fe3,0x06fe,0x0a31,0xb715, +0x3fe2,0x387a,0x6e75,0x6238, +0x3fe1,0x72b8,0x3c7d,0x517b, +0x3fe0,0xb558,0x6cf9,0x890f, +0x3fe0,0x0000,0x0000,0x0000 +}; +static unsigned short B[] = { +0x0000,0x0000,0x0000,0x0000, +0x3c72,0xed02,0xd75b,0x3707, +0x3c87,0xa1cd,0x345d,0xcc81, +0x3c86,0xe9f1,0x5686,0x4b27, +0xbc8b,0xdd34,0x13b2,0x6456, +0x3c6d,0x4397,0xafec,0x42e2, +0x3c76,0xf46a,0xd231,0x82e4, +0xbc71,0x9041,0xb9d7,0x8a76, +0x0000,0x0000,0x0000,0x0000 +}; +static unsigned short R[] = { +0x3eef,0x6307,0xd7f2,0x937f, +0x3f24,0x2fbe,0x60fc,0x9259, +0x3f55,0xd87e,0xc84a,0xef1d, +0x3f83,0xb2ab,0x6ef1,0x33b7, +0x3fac,0x6b08,0xd704,0x1a92, +0x3fce,0xbfbd,0xff82,0xc56d, +0x3fe6,0x2e42,0xfefa,0x39ef +}; + +#define douba(k) (*(double *)&A[(k)<<2]) +#define doubb(k) (*(double *)&B[(k)<<2]) +#define MEXP 16383.0 +#ifdef DENORMAL +#define MNEXP -17183.0 +#else +#define MNEXP -16383.0 +#endif +#endif + +/* log2(e) - 1 */ +#define LOG2EA 0.44269504088896340736 + +#define F W +#define Fa Wa +#define Fb Wb +#define G W +#define Ga Wa +#define Gb u +#define H W +#define Ha Wb +#define Hb Wb + +#ifdef ANSIPROT +extern double floor ( double ); +extern double fabs ( double ); +extern double frexp ( double, int * ); +extern double ldexp ( double, int ); +extern double polevl ( double, void *, int ); +extern double p1evl ( double, void *, int ); +extern double c_powi ( double, int ); +extern int signbit ( double ); +extern int isnan ( double ); +extern int isfinite ( double ); +static double reduc ( double ); +#else +double floor(), fabs(), frexp(), ldexp(); +double polevl(), p1evl(), c_powi(); +int signbit(), isnan(), isfinite(); +static double reduc(); +#endif +extern double MAXNUM; +#ifdef INFINITIES +extern double INFINITY; +#endif +#ifdef NANS +extern double NAN; +#endif +#ifdef MINUSZERO +extern double NEGZERO; +#endif + +double c_pow( x, y ) +double x, y; +{ +double w, z, W, Wa, Wb, ya, yb, u; +/* double F, Fa, Fb, G, Ga, Gb, H, Ha, Hb */ +double aw, ay, wy; +int e, i, nflg, iyflg, yoddint; + +if( y == 0.0 ) + return( 1.0 ); +#ifdef NANS +if( isnan(x) ) + return( x ); +if( isnan(y) ) + return( y ); +#endif +if( y == 1.0 ) + return( x ); + + +#ifdef INFINITIES +if( !isfinite(y) && (x == 1.0 || x == -1.0) ) + { + mtherr( "pow", DOMAIN ); +#ifdef NANS + return( NAN ); +#else + return( INFINITY ); +#endif + } +#endif + +if( x == 1.0 ) + return( 1.0 ); + +if( y >= MAXNUM ) + { +#ifdef INFINITIES + if( x > 1.0 ) + return( INFINITY ); +#else + if( x > 1.0 ) + return( MAXNUM ); +#endif + if( x > 0.0 && x < 1.0 ) + return( 0.0); + if( x < -1.0 ) + { +#ifdef INFINITIES + return( INFINITY ); +#else + return( MAXNUM ); +#endif + } + if( x > -1.0 && x < 0.0 ) + return( 0.0 ); + } +if( y <= -MAXNUM ) + { + if( x > 1.0 ) + return( 0.0 ); +#ifdef INFINITIES + if( x > 0.0 && x < 1.0 ) + return( INFINITY ); +#else + if( x > 0.0 && x < 1.0 ) + return( MAXNUM ); +#endif + if( x < -1.0 ) + return( 0.0 ); +#ifdef INFINITIES + if( x > -1.0 && x < 0.0 ) + return( INFINITY ); +#else + if( x > -1.0 && x < 0.0 ) + return( MAXNUM ); +#endif + } +if( x >= MAXNUM ) + { +#if INFINITIES + if( y > 0.0 ) + return( INFINITY ); +#else + if( y > 0.0 ) + return( MAXNUM ); +#endif + return(0.0); + } +/* Set iyflg to 1 if y is an integer. */ +iyflg = 0; +w = floor(y); +if( w == y ) + iyflg = 1; + +/* Test for odd integer y. */ +yoddint = 0; +if( iyflg ) + { + ya = fabs(y); + ya = floor(0.5 * ya); + yb = 0.5 * fabs(w); + if( ya != yb ) + yoddint = 1; + } + +if( x <= -MAXNUM ) + { + if( y > 0.0 ) + { +#ifdef INFINITIES + if( yoddint ) + return( -INFINITY ); + return( INFINITY ); +#else + if( yoddint ) + return( -MAXNUM ); + return( MAXNUM ); +#endif + } + if( y < 0.0 ) + { +#ifdef MINUSZERO + if( yoddint ) + return( NEGZERO ); +#endif + return( 0.0 ); + } + } + +nflg = 0; /* flag = 1 if x<0 raised to integer power */ +if( x <= 0.0 ) + { + if( x == 0.0 ) + { + if( y < 0.0 ) + { +#ifdef MINUSZERO + if( signbit(x) && yoddint ) + return( -INFINITY ); +#endif +#ifdef INFINITIES + return( INFINITY ); +#else + return( MAXNUM ); +#endif + } + if( y > 0.0 ) + { +#ifdef MINUSZERO + if( signbit(x) && yoddint ) + return( NEGZERO ); +#endif + return( 0.0 ); + } + return( 1.0 ); + } + else + { + if( iyflg == 0 ) + { /* noninteger power of negative number */ + mtherr( fname, DOMAIN ); +#ifdef NANS + return(NAN); +#else + return(0.0L); +#endif + } + nflg = 1; + } + } + +/* Integer power of an integer. */ + +if( iyflg ) + { + i = (int)w; + w = floor(x); + if( (w == x) && (fabs(y) < 32768.0) ) + { + w = c_powi( x, (int) y ); + return( w ); + } + } + +if( nflg ) + x = fabs(x); + +/* For results close to 1, use a series expansion. */ +w = x - 1.0; +aw = fabs(w); +ay = fabs(y); +wy = w * y; +ya = fabs(wy); +if((aw <= 1.0e-3 && ay <= 1.0) + || (ya <= 1.0e-3 && ay >= 1.0)) + { + z = (((((w*(y-5.)/720. + 1./120.)*w*(y-4.) + 1./24.)*w*(y-3.) + + 1./6.)*w*(y-2.) + 0.5)*w*(y-1.) )*wy + wy + 1.; + goto done; + } +/* These are probably too much trouble. */ +#if 0 +w = y * log(x); +if (aw > 1.0e-3 && fabs(w) < 1.0e-3) + { + z = (((((( + w/7. + 1.)*w/6. + 1.)*w/5. + 1.)*w/4. + 1.)*w/3. + 1.)*w/2. + 1.)*w + 1.; + goto done; + } + +if(ya <= 1.0e-3 && aw <= 1.0e-4) + { + z = ((((( + wy*1./720. + + (-w*1./48. + 1./120.) )*wy + + ((w*17./144. - 1./12.)*w + 1./24.) )*wy + + (((-w*5./16. + 7./24.)*w - 1./4.)*w + 1./6.) )*wy + + ((((w*137./360. - 5./12.)*w + 11./24.)*w - 1./2.)*w + 1./2.) )*wy + + (((((-w*1./6. + 1./5.)*w - 1./4)*w + 1./3.)*w -1./2.)*w ) )*wy + + wy + 1.0; + goto done; + } +#endif + +/* separate significand from exponent */ +x = frexp( x, &e ); + +#if 0 +/* For debugging, check for gross overflow. */ +if( (e * y) > (MEXP + 1024) ) + goto overflow; +#endif + +/* Find significand of x in antilog table A[]. */ +i = 1; +if( x <= douba(9) ) + i = 9; +if( x <= douba(i+4) ) + i += 4; +if( x <= douba(i+2) ) + i += 2; +if( x >= douba(1) ) + i = -1; +i += 1; + + +/* Find (x - A[i])/A[i] + * in order to compute log(x/A[i]): + * + * log(x) = log( a x/a ) = log(a) + log(x/a) + * + * log(x/a) = log(1+v), v = x/a - 1 = (x-a)/a + */ +x -= douba(i); +x -= doubb(i/2); +x /= douba(i); + + +/* rational approximation for log(1+v): + * + * log(1+v) = v - v**2/2 + v**3 P(v) / Q(v) + */ +z = x*x; +w = x * ( z * polevl( x, P, 3 ) / p1evl( x, Q, 4 ) ); +w = w - ldexp( z, -1 ); /* w - 0.5 * z */ + +/* Convert to base 2 logarithm: + * multiply by log2(e) + */ +w = w + LOG2EA * w; +/* Note x was not yet added in + * to above rational approximation, + * so do it now, while multiplying + * by log2(e). + */ +z = w + LOG2EA * x; +z = z + x; + +/* Compute exponent term of the base 2 logarithm. */ +w = -i; +w = ldexp( w, -4 ); /* divide by 16 */ +w += e; +/* Now base 2 log of x is w + z. */ + +/* Multiply base 2 log by y, in extended precision. */ + +/* separate y into large part ya + * and small part yb less than 1/16 + */ +ya = reduc(y); +yb = y - ya; + + +F = z * y + w * yb; +Fa = reduc(F); +Fb = F - Fa; + +G = Fa + w * ya; +Ga = reduc(G); +Gb = G - Ga; + +H = Fb + Gb; +Ha = reduc(H); +w = ldexp( Ga+Ha, 4 ); + +/* Test the power of 2 for overflow */ +if( w > MEXP ) + { +#ifndef INFINITIES + mtherr( fname, OVERFLOW ); +#endif +#ifdef INFINITIES + if( nflg && yoddint ) + return( -INFINITY ); + return( INFINITY ); +#else + if( nflg && yoddint ) + return( -MAXNUM ); + return( MAXNUM ); +#endif + } + +if( w < (MNEXP - 1) ) + { +#ifndef DENORMAL + mtherr( fname, UNDERFLOW ); +#endif +#ifdef MINUSZERO + if( nflg && yoddint ) + return( NEGZERO ); +#endif + return( 0.0 ); + } + +e = (int)w; +Hb = H - Ha; + +if( Hb > 0.0 ) + { + e += 1; + Hb -= 0.0625; + } + +/* Now the product y * log2(x) = Hb + e/16.0. + * + * Compute base 2 exponential of Hb, + * where -0.0625 <= Hb <= 0. + */ +z = Hb * polevl( Hb, R, 6 ); /* z = 2**Hb - 1 */ + +/* Express e/16 as an integer plus a negative number of 16ths. + * Find lookup table entry for the fractional power of 2. + */ +if( e < 0 ) + i = 0; +else + i = 1; +i = e/16 + i; +e = 16*i - e; +w = douba( e ); +z = w + w * z; /* 2**-e * ( 1 + (2**Hb-1) ) */ +z = ldexp( z, i ); /* multiply by integer power of 2 */ + +done: + +/* Negate if odd integer power of negative number */ +if( nflg && yoddint ) + { +#ifdef MINUSZERO + if( z == 0.0 ) + z = NEGZERO; + else +#endif + z = -z; + } +return( z ); +} + + +/* Find a multiple of 1/16 that is within 1/16 of x. */ +static double reduc(x) +double x; +{ +double t; + +t = ldexp( x, 4 ); +t = floor( t ); +t = ldexp( t, -4 ); +return(t); +} diff --git a/src/math/powi.c b/src/math/powi.c new file mode 100644 index 000000000..ec80dc1d5 --- /dev/null +++ b/src/math/powi.c @@ -0,0 +1,186 @@ +/* powi.c + * + * Real raised to integer power + * + * + * + * SYNOPSIS: + * + * double x, y, powi(); + * int n; + * + * y = powi( x, n ); + * + * + * + * DESCRIPTION: + * + * Returns argument x raised to the nth power. + * The routine efficiently decomposes n as a sum of powers of + * two. The desired power is a product of two-to-the-kth + * powers of x. Thus to compute the 32767 power of x requires + * 28 multiplications instead of 32767 multiplications. + * + * + * + * ACCURACY: + * + * + * Relative error: + * arithmetic x domain n domain # trials peak rms + * DEC .04,26 -26,26 100000 2.7e-16 4.3e-17 + * IEEE .04,26 -26,26 50000 2.0e-15 3.8e-16 + * IEEE 1,2 -1022,1023 50000 8.6e-14 1.6e-14 + * + * Returns MAXNUM on overflow, zero on underflow. + * + */ + +/* powi.c */ + +/* +Cephes Math Library Release 2.8: June, 2000 +Copyright 1984, 1995, 2000 by Stephen L. Moshier +*/ + +#include "mconf.h" +#ifdef ANSIPROT +extern double log ( double ); +extern double frexp ( double, int * ); +extern int signbit ( double ); +#else +double log(), frexp(); +int signbit(); +#endif +extern double NEGZERO, INFINITY, MAXNUM, MAXLOG, MINLOG, LOGE2; + +double c_powi( x, nn ) +double x; +int nn; +{ +int n, e, sign, asign, lx; +double w, y, s; + +/* See pow.c for these tests. */ +if( x == 0.0 ) + { + if( nn == 0 ) + return( 1.0 ); + else if( nn < 0 ) + return( INFINITY ); + else + { + if( nn & 1 ) + return( x ); + else + return( 0.0 ); + } + } + +if( nn == 0 ) + return( 1.0 ); + +if( nn == -1 ) + return( 1.0/x ); + +if( x < 0.0 ) + { + asign = -1; + x = -x; + } +else + asign = 0; + + +if( nn < 0 ) + { + sign = -1; + n = -nn; + } +else + { + sign = 1; + n = nn; + } + +/* Even power will be positive. */ +if( (n & 1) == 0 ) + asign = 0; + +/* Overflow detection */ + +/* Calculate approximate logarithm of answer */ +s = frexp( x, &lx ); +e = (lx - 1)*n; +if( (e == 0) || (e > 64) || (e < -64) ) + { + s = (s - 7.0710678118654752e-1) / (s + 7.0710678118654752e-1); + s = (2.9142135623730950 * s - 0.5 + lx) * nn * LOGE2; + } +else + { + s = LOGE2 * e; + } + +if( s > MAXLOG ) + { + mtherr( "powi", OVERFLOW ); + y = INFINITY; + goto done; + } + +#if DENORMAL +if( s < MINLOG ) + { + y = 0.0; + goto done; + } + +/* Handle tiny denormal answer, but with less accuracy + * since roundoff error in 1.0/x will be amplified. + * The precise demarcation should be the gradual underflow threshold. + */ +if( (s < (-MAXLOG+2.0)) && (sign < 0) ) + { + x = 1.0/x; + sign = -sign; + } +#else +/* do not produce denormal answer */ +if( s < -MAXLOG ) + return(0.0); +#endif + + +/* First bit of the power */ +if( n & 1 ) + y = x; + +else + y = 1.0; + +w = x; +n >>= 1; +while( n ) + { + w = w * w; /* arg to the 2-to-the-kth power */ + if( n & 1 ) /* if that bit is set, then include in product */ + y *= w; + n >>= 1; + } + +if( sign < 0 ) + y = 1.0/y; + +done: + +if( asign ) + { + /* odd power of negative number */ + if( y == 0.0 ) + y = NEGZERO; + else + y = -y; + } +return(y); +} diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f56735797..fceee42c0 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1824,13 +1824,16 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) { ValueType = TypeBool; } - if (left->ValueType->GetRegType() == REGT_INT && right->ValueType->GetRegType() == REGT_INT) - { - ValueType = TypeSInt32; - } else if (left->IsNumeric() && right->IsNumeric()) { - ValueType = TypeFloat64; + if (left->ValueType->GetRegType() == REGT_INT && right->ValueType->GetRegType() == REGT_INT) + { + ValueType = TypeSInt32; + } + else + { + ValueType = TypeFloat64; + } } else if (left->ValueType->GetRegType() == REGT_POINTER && left->ValueType == right->ValueType) { @@ -2137,6 +2140,60 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) // //========================================================================== +FxPow::FxPow(FxExpression *l, FxExpression *r) + : FxBinary(TK_MulMul, new FxFloatCast(l), new FxFloatCast(r)) +{ +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxPow::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + + if (!ResolveLR(ctx, true)) return NULL; + + if (left->isConstant() && right->isConstant()) + { + double v1 = static_cast(left)->GetValue().GetFloat(); + double v2 = static_cast(right)->GetValue().GetFloat(); + return new FxConstant(g_pow(v1, v2), left->ScriptPosition); + } + return this; +} + + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxPow::Emit(VMFunctionBuilder *build) +{ + ExpEmit op1 = left->Emit(build); + ExpEmit op2 = right->Emit(build); + + // Pow is not commutative, so either side may be constant (but not both). + assert(!op1.Konst || !op2.Konst); + op1.Free(build); + op2.Free(build); + assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); + ExpEmit to(build, REGT_FLOAT); + build->Emit((op1.Konst ? OP_POWF_KR : op2.Konst ? OP_POWF_RK : OP_POWF_RR), to.RegNum, op1.RegNum, op2.RegNum); + return to; +} + +//========================================================================== +// +// +// +//========================================================================== + FxCompareRel::FxCompareRel(int o, FxExpression *l, FxExpression *r) : FxBinary(o, l, r) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index ce4f11bb1..8d4936185 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -686,6 +686,21 @@ public: // //========================================================================== +class FxPow : public FxBinary +{ +public: + + FxPow(FxExpression*, FxExpression*); + FxExpression *Resolve(FCompileContext&); + ExpEmit Emit(VMFunctionBuilder *build); +}; + +//========================================================================== +// +// FxBinary +// +//========================================================================== + class FxCompareRel : public FxBinary { public: diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 1d1764c6e..8f8a21295 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1055,15 +1055,15 @@ begin: OP(POWF_RR): ASSERTF(a); ASSERTF(B); ASSERTF(C); - reg.f[a] = pow(reg.f[B], reg.f[C]); + reg.f[a] = g_pow(reg.f[B], reg.f[C]); NEXTOP; OP(POWF_RK): ASSERTF(a); ASSERTF(B); ASSERTKF(C); - reg.f[a] = pow(reg.f[B], konstf[C]); + reg.f[a] = g_pow(reg.f[B], konstf[C]); NEXTOP; OP(POWF_KR): ASSERTF(a); ASSERTKF(B); ASSERTF(C); - reg.f[a] = pow(konstf[B], reg.f[C]); + reg.f[a] = g_pow(konstf[B], reg.f[C]); NEXTOP; OP(MINF_RR): diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 5511898f7..6ec463490 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2422,6 +2422,9 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_Mod: return new FxMulDiv(op == PEX_Mul ? '*' : op == PEX_Div ? '/' : '%', left, right); + case PEX_Pow: + return new FxPow(left, right); + default: I_Error("Binary operator %d not implemented yet", op); } diff --git a/src/scripting/zscript/zcc_expr.cpp b/src/scripting/zscript/zcc_expr.cpp index b34251061..0c2c6baee 100644 --- a/src/scripting/zscript/zcc_expr.cpp +++ b/src/scripting/zscript/zcc_expr.cpp @@ -41,6 +41,7 @@ #include "m_alloc.h" #include "zcc_parser.h" #include "templates.h" +#include "math/cmath.h" #define luai_nummod(a,b) ((a) - floor((a)/(b))*(b)) @@ -332,7 +333,7 @@ void ZCC_InitOperators() { PEX_Mod , (PType **)&TypeUInt32, (PType **)&TypeUInt32, (PType **)&TypeUInt32, [](auto *l, auto *r, auto &) { l->UIntVal %= r->UIntVal; return l; } }, { PEX_Mod , (PType **)&TypeFloat64, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->DoubleVal = luai_nummod(l->DoubleVal, r->DoubleVal); return l; } }, - { PEX_Pow , (PType **)&TypeFloat64, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->DoubleVal = pow(l->DoubleVal, r->DoubleVal); return l; } }, + { PEX_Pow , (PType **)&TypeFloat64, (PType **)&TypeFloat64, (PType **)&TypeFloat64, [](auto *l, auto *r, auto &) { l->DoubleVal = g_pow(l->DoubleVal, r->DoubleVal); return l; } }, { PEX_Concat , (PType **)&TypeString, (PType **)&TypeString, (PType **)&TypeString, EvalConcat }, From 23a2a19a784d52b9f0a4efe43cc737c8db34fc39 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 15:52:29 +0200 Subject: [PATCH 058/255] - added handling for shift and bit operators. - added the '>>>' (unsigned shift) operator. Although, with unsigned numbers available, this is technically not really needed, DECORATE supports this so ZScript should, too, if only for the benefit of making conversion tools easier to handle. --- src/scripting/codegeneration/codegen.cpp | 4 ++-- src/scripting/zscript/zcc-parse.lemon | 7 ++++++- src/scripting/zscript/zcc_compile.cpp | 8 ++++++++ src/scripting/zscript/zcc_exprlist.h | 3 ++- src/scripting/zscript/zcc_parser.cpp | 1 + 5 files changed, 19 insertions(+), 4 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index fceee42c0..c68fc3723 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -2430,9 +2430,9 @@ FxExpression *FxBinaryInt::Resolve(FCompileContext& ctx) CHECKRESOLVED(); if (!ResolveLR(ctx, false)) return NULL; - if (ValueType->GetRegType() == REGT_FLOAT /* lax */) + if (ValueType->GetRegType() == REGT_FLOAT && ctx.FromDecorate) { - // For DECORATE which allows floats here. + // For DECORATE which allows floats here. ZScript does not. if (left->ValueType->GetRegType() != REGT_INT) { left = new FxIntCast(left, ctx.FromDecorate); diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 215670c82..1e10103a0 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -114,7 +114,7 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) %left OR. /* Note that this is like the Ruby precedence for these */ %left XOR. /* three operators and not the C precedence, since */ %left AND. /* they are higher priority than the comparisons. */ -%left LSH RSH. +%left LSH RSH URSH. %left SUB ADD. %left MUL DIV MOD CROSSPROD DOTPROD. %left POW. @@ -1148,6 +1148,11 @@ expr(X) ::= expr(A) RSH expr(B). /* a >> b */ BINARY_EXPR(A,B,PEX_RightShift); X = expr2; } +expr(X) ::= expr(A) URSH expr(B). /* a >>> b */ +{ + BINARY_EXPR(A,B,PEX_URightShift); + X = expr2; +} expr(X) ::= expr(A) DOTDOT expr(B). /* a .. b */ { BINARY_EXPR(A,B,PEX_Concat); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 6ec463490..9d0ff5428 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2425,6 +2425,14 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_Pow: return new FxPow(left, right); + case PEX_LeftShift: + case PEX_RightShift: + case PEX_URightShift: + case PEX_BitAnd: + case PEX_BitOr: + case PEX_BitXor: + return new FxBinaryInt(op == PEX_LeftShift ? TK_LShift : op == PEX_RightShift ? TK_RShift : op == PEX_URightShift? TK_URShift : op == PEX_BitAnd ? '&' : op == PEX_BitOr ? '|' : '^', left, right); + default: I_Error("Binary operator %d not implemented yet", op); } diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index 2df687798..46a1b9c69 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -32,6 +32,7 @@ xx(CrossProduct, ) xx(DotProduct, ) xx(LeftShift, ) xx(RightShift, ) +xx(URightShift, ) xx(Concat, ) xx(LT, ) @@ -42,7 +43,7 @@ xx(LTGTEQ, ) xx(Is, ) xx(EQEQ, ) -xx(NEQ, ) +xx(NEQ, ) xx(APREQ, ) xx(BitAnd, ) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index c3f75b2b0..cc8d187d3 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -95,6 +95,7 @@ static void InitTokenMap() TOKENDEF ('&', ZCC_AND); TOKENDEF (TK_LShift, ZCC_LSH); TOKENDEF (TK_RShift, ZCC_RSH); + TOKENDEF (TK_URShift, ZCC_URSH); TOKENDEF ('-', ZCC_SUB); TOKENDEF ('+', ZCC_ADD); TOKENDEF ('*', ZCC_MUL); From a6a0c4b93c9b163cc185d59495720d9831efbacb Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 20:33:35 +0200 Subject: [PATCH 059/255] - handle all unary operators. - handle all binary operators which are already implemented in the code generator. - implemented sizeof/alignof operators in code generator. - rewrote RequestAddress so that its return value is not the writability of an address but the mere existence. Also changed it to not output errors itself because those cannot be dealt with by the calling function. --- src/scripting/codegeneration/codegen.cpp | 101 +++++++++++++++++++---- src/scripting/codegeneration/codegen.h | 28 +++++-- src/scripting/zscript/zcc_compile.cpp | 65 +++++++++++++++ 3 files changed, 174 insertions(+), 20 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index c68fc3723..14f1627d9 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -264,9 +264,9 @@ FxExpression *FxExpression::Resolve(FCompileContext &ctx) // //========================================================================== -bool FxExpression::RequestAddress() +bool FxExpression::RequestAddress(bool *writable) { - ScriptPosition.Message(MSG_ERROR, "invalid dereference\n"); + if (writable != nullptr) *writable = false; return false; } @@ -1488,6 +1488,67 @@ ExpEmit FxUnaryNotBoolean::Emit(VMFunctionBuilder *build) return from; } +//========================================================================== +// +// +// +//========================================================================== + +FxSizeAlign::FxSizeAlign(FxExpression *operand, int which) + : FxExpression(operand->ScriptPosition) +{ + Operand = operand; + Which = which; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxSizeAlign::~FxSizeAlign() +{ + SAFE_DELETE(Operand); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxSizeAlign::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(Operand, ctx); + + auto type = Operand->ValueType; + if (Operand->isConstant()) + { + ScriptPosition.Message(MSG_ERROR, "cannot determine %s of a constant", Which == 'a'? "alignment" : "size"); + delete this; + return NULL; + } + else if (!Operand->RequestAddress(nullptr)) + { + ScriptPosition.Message(MSG_ERROR, "Operand must be addressable to determine %s", Which == 'a' ? "alignment" : "size"); + delete this; + return NULL; + } + else + { + FxExpression *x = new FxConstant(Which == 'a' ? int(type->Align) : int(type->Size), Operand->ScriptPosition); + delete this; + return x->Resolve(ctx); + } +} + +ExpEmit FxSizeAlign::Emit(VMFunctionBuilder *build) +{ + return ExpEmit(); +} + //========================================================================== // // FxPreIncrDecr @@ -1506,10 +1567,11 @@ FxPreIncrDecr::~FxPreIncrDecr() SAFE_DELETE(Base); } -bool FxPreIncrDecr::RequestAddress() +bool FxPreIncrDecr::RequestAddress(bool *writable) { AddressRequested = true; - return AddressWritable; + if (writable != nullptr) *writable = AddressWritable; + return true; } FxExpression *FxPreIncrDecr::Resolve(FCompileContext &ctx) @@ -1531,7 +1593,7 @@ FxExpression *FxPreIncrDecr::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (!(AddressWritable = Base->RequestAddress())) + if (!Base->RequestAddress(&AddressWritable) || !AddressWritable ) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); delete this; @@ -1594,6 +1656,7 @@ FxExpression *FxPostIncrDecr::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); SAFE_RESOLVE(Base, ctx); + bool AddressWritable; ValueType = Base->ValueType; @@ -1609,7 +1672,7 @@ FxExpression *FxPostIncrDecr::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (!Base->RequestAddress()) + if (!Base->RequestAddress(&AddressWritable) || !AddressWritable) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); delete this; @@ -1667,10 +1730,11 @@ FxAssign::~FxAssign() SAFE_DELETE(Right); } -bool FxAssign::RequestAddress() +bool FxAssign::RequestAddress(bool *writable) { AddressRequested = true; - return AddressWritable; + if (writable != nullptr) *writable = AddressWritable; + return true; } FxExpression *FxAssign::Resolve(FCompileContext &ctx) @@ -1688,7 +1752,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (!(AddressWritable = Base->RequestAddress())) + if (!Base->RequestAddress(&AddressWritable) || !AddressWritable) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); delete this; @@ -3968,10 +4032,11 @@ FxClassMember::~FxClassMember() // //========================================================================== -bool FxClassMember::RequestAddress() +bool FxClassMember::RequestAddress(bool *writable) { AddressRequested = true; - return !!(~membervar->Flags & VARF_ReadOnly); + if (writable != nullptr) *writable = !(membervar->Flags & VARF_ReadOnly); + return true; } //========================================================================== @@ -4079,10 +4144,11 @@ FxArrayElement::~FxArrayElement() // //========================================================================== -bool FxArrayElement::RequestAddress() +bool FxArrayElement::RequestAddress(bool *writable) { AddressRequested = true; - return AddressWritable; + if (writable != nullptr) *writable = AddressWritable; + return true; } //========================================================================== @@ -4108,7 +4174,7 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) return NULL; } } - if (index->ValueType->GetRegType() != REGT_INT) + if (index->ValueType->GetRegType() != REGT_INT && index->ValueType != TypeName) { ScriptPosition.Message(MSG_ERROR, "Array index must be integer"); delete this; @@ -4141,7 +4207,12 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) delete this; return NULL; } - AddressWritable = Array->RequestAddress(); + if (!Array->RequestAddress(&AddressWritable)) + { + ScriptPosition.Message(MSG_ERROR, "Unable to dereference array."); + delete this; + return NULL; + } return this; } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 8d4936185..1a2d2045d 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -212,7 +212,7 @@ public: virtual FxExpression *Resolve(FCompileContext &ctx); virtual bool isConstant() const; - virtual bool RequestAddress(); + virtual bool RequestAddress(bool *writable); virtual PPrototype *ReturnProto(); virtual VMFunction *GetDirectFunction(); bool IsNumeric() const { return ValueType != TypeName && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT); } @@ -553,6 +553,24 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxSign +// +//========================================================================== + +class FxSizeAlign : public FxExpression +{ + FxExpression *Operand; + int Which; + +public: + FxSizeAlign(FxExpression*, int which); + ~FxSizeAlign(); + FxExpression *Resolve(FCompileContext&); + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxPreIncrDecr @@ -570,7 +588,7 @@ public: FxPreIncrDecr(FxExpression *base, int token); ~FxPreIncrDecr(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(); + bool RequestAddress(bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -609,7 +627,7 @@ public: FxAssign(FxExpression *base, FxExpression *right); ~FxAssign(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(); + bool RequestAddress(bool *writable); ExpEmit Emit(VMFunctionBuilder *build); ExpEmit Address; @@ -932,7 +950,7 @@ public: FxClassMember(FxExpression*, PField*, const FScriptPosition&); ~FxClassMember(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(); + bool RequestAddress(bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -967,7 +985,7 @@ public: FxArrayElement(FxExpression*, FxExpression*); ~FxArrayElement(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(); + bool RequestAddress(bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 9d0ff5428..c55d6994a 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2405,6 +2405,46 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } } + case AST_ExprUnary: + { + auto unary = static_cast(ast); + auto operand = ConvertNode(unary->Operand); + auto op = unary->Operation; + switch (op) + { + case PEX_PostDec: + case PEX_PostInc: + return new FxPostIncrDecr(operand, op == PEX_PostDec ? TK_Decr : TK_Incr); + + case PEX_PreDec: + case PEX_PreInc: + return new FxPreIncrDecr(operand, op == PEX_PostDec ? TK_Decr : TK_Incr); + + case PEX_Negate: + return new FxMinusSign(operand); + + case PEX_AntiNegate: + return new FxPlusSign(operand); + + case PEX_BitNot: + return new FxUnaryNotBitwise(operand); + + case PEX_BoolNot: + return new FxUnaryNotBoolean(operand); + + case PEX_SizeOf: + case PEX_AlignOf: + return new FxSizeAlign(operand, op == PEX_AlignOf ? 'a' : 's'); + + default: + assert(0 && "Unknown unary operator."); // should never happen + Error(unary, "Unknown unary operator ID #%d", op); + return new FxNop(*ast); + } + break; + } + + case AST_ExprBinary: { auto binary = static_cast(ast); @@ -2433,6 +2473,31 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_BitXor: return new FxBinaryInt(op == PEX_LeftShift ? TK_LShift : op == PEX_RightShift ? TK_RShift : op == PEX_URightShift? TK_URShift : op == PEX_BitAnd ? '&' : op == PEX_BitOr ? '|' : '^', left, right); + case PEX_BoolOr: + case PEX_BoolAnd: + return new FxBinaryLogical(op == PEX_BoolAnd ? TK_AndAnd : TK_OrOr, left, right); + + case PEX_LT: + case PEX_LTEQ: + case PEX_GT: + case PEX_GTEQ: + return new FxCompareRel(op == PEX_LT ? '<' : op == PEX_RightShift ? '>' : op == PEX_LTEQ ? TK_Leq : TK_Geq, left, right); + + case PEX_EQEQ: + case PEX_NEQ: + return new FxCompareEq(op == PEX_NEQ ? TK_Neq : TK_Eq, left, right); + + + // todo: These do not have representations in DECORATE and no implementation exists yet. + case PEX_LTGTEQ: + case PEX_Concat: + case PEX_Is: + // more esoteric operators + case PEX_APREQ: + + // vector operations will be done later. + case PEX_CrossProduct: + case PEX_DotProduct: default: I_Error("Binary operator %d not implemented yet", op); } From 1c21dbc44cc21d0f44cc4f819ff971f94793fdf3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 21:43:14 +0200 Subject: [PATCH 060/255] - handle trinary conditional statement. --- src/scripting/zscript/zcc_compile.cpp | 18 ++++++++++++++---- 1 file changed, 14 insertions(+), 4 deletions(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index c55d6994a..39597c513 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2471,7 +2471,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_BitAnd: case PEX_BitOr: case PEX_BitXor: - return new FxBinaryInt(op == PEX_LeftShift ? TK_LShift : op == PEX_RightShift ? TK_RShift : op == PEX_URightShift? TK_URShift : op == PEX_BitAnd ? '&' : op == PEX_BitOr ? '|' : '^', left, right); + return new FxBinaryInt(op == PEX_LeftShift ? TK_LShift : op == PEX_RightShift ? TK_RShift : op == PEX_URightShift ? TK_URShift : op == PEX_BitAnd ? '&' : op == PEX_BitOr ? '|' : '^', left, right); case PEX_BoolOr: case PEX_BoolAnd: @@ -2485,17 +2485,17 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_EQEQ: case PEX_NEQ: - return new FxCompareEq(op == PEX_NEQ ? TK_Neq : TK_Eq, left, right); + return new FxCompareEq(op == PEX_NEQ ? TK_Neq : TK_Eq, left, right); - // todo: These do not have representations in DECORATE and no implementation exists yet. + // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_LTGTEQ: case PEX_Concat: case PEX_Is: // more esoteric operators case PEX_APREQ: - // vector operations will be done later. + // vector operations will be done later. case PEX_CrossProduct: case PEX_DotProduct: default: @@ -2503,6 +2503,16 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } break; } + + case AST_ExprTrinary: + { + auto trinary = static_cast(ast); + auto condition = ConvertNode(trinary->Test); + auto left = ConvertNode(trinary->Left); + auto right = ConvertNode(trinary->Right); + + return new FxConditional(condition, left, right); + } } // only for development. I_Error is more convenient here than a normal error. From d66631478a47e7047d1e2e79d9ffaebe678f1b59 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 17 Oct 2016 23:27:34 +0200 Subject: [PATCH 061/255] - converted some Hexen stuff. --- wadsrc/static/actors/hexen/baseweapons.txt | 20 --- wadsrc/static/actors/hexen/clericplayer.txt | 103 ----------- wadsrc/static/actors/hexen/fighterplayer.txt | 126 ------------- wadsrc/static/actors/hexen/flame.txt | 106 ----------- wadsrc/static/actors/hexen/flies.txt | 27 --- wadsrc/static/actors/hexen/korax.txt | 124 ------------- wadsrc/static/actors/hexen/mageplayer.txt | 104 ----------- wadsrc/static/actors/hexen/pig.txt | 155 ---------------- wadsrc/static/decorate.txt | 8 - wadsrc/static/zscript.txt | 53 ++++++ wadsrc/static/zscript/hexen/baseweapons.txt | 29 +++ wadsrc/static/zscript/hexen/clericplayer.txt | 106 +++++++++++ wadsrc/static/zscript/hexen/fighterplayer.txt | 133 ++++++++++++++ wadsrc/static/zscript/hexen/flame.txt | 122 +++++++++++++ wadsrc/static/zscript/hexen/flies.txt | 30 ++++ wadsrc/static/zscript/hexen/korax.txt | 133 ++++++++++++++ wadsrc/static/zscript/hexen/mageplayer.txt | 107 +++++++++++ wadsrc/static/zscript/hexen/pig.txt | 170 ++++++++++++++++++ 18 files changed, 883 insertions(+), 773 deletions(-) delete mode 100644 wadsrc/static/actors/hexen/baseweapons.txt delete mode 100644 wadsrc/static/actors/hexen/clericplayer.txt delete mode 100644 wadsrc/static/actors/hexen/fighterplayer.txt delete mode 100644 wadsrc/static/actors/hexen/flame.txt delete mode 100644 wadsrc/static/actors/hexen/flies.txt delete mode 100644 wadsrc/static/actors/hexen/korax.txt delete mode 100644 wadsrc/static/actors/hexen/mageplayer.txt delete mode 100644 wadsrc/static/actors/hexen/pig.txt create mode 100644 wadsrc/static/zscript/hexen/baseweapons.txt create mode 100644 wadsrc/static/zscript/hexen/clericplayer.txt create mode 100644 wadsrc/static/zscript/hexen/fighterplayer.txt create mode 100644 wadsrc/static/zscript/hexen/flame.txt create mode 100644 wadsrc/static/zscript/hexen/flies.txt create mode 100644 wadsrc/static/zscript/hexen/korax.txt create mode 100644 wadsrc/static/zscript/hexen/mageplayer.txt create mode 100644 wadsrc/static/zscript/hexen/pig.txt diff --git a/wadsrc/static/actors/hexen/baseweapons.txt b/wadsrc/static/actors/hexen/baseweapons.txt deleted file mode 100644 index d40536316..000000000 --- a/wadsrc/static/actors/hexen/baseweapons.txt +++ /dev/null @@ -1,20 +0,0 @@ -// The Doom and Heretic players are not excluded from pickup in case -// somebody wants to use these weapons with either of those games. - -ACTOR FighterWeapon : Weapon native -{ - Weapon.Kickback 150 - Inventory.ForbiddenTo ClericPlayer, MagePlayer -} - -ACTOR ClericWeapon : Weapon native -{ - Weapon.Kickback 150 - Inventory.ForbiddenTo FighterPlayer, MagePlayer -} - -ACTOR MageWeapon : Weapon native -{ - Weapon.Kickback 150 - Inventory.ForbiddenTo FighterPlayer, ClericPlayer -} diff --git a/wadsrc/static/actors/hexen/clericplayer.txt b/wadsrc/static/actors/hexen/clericplayer.txt deleted file mode 100644 index 4b762af5d..000000000 --- a/wadsrc/static/actors/hexen/clericplayer.txt +++ /dev/null @@ -1,103 +0,0 @@ -// The cleric --------------------------------------------------------------- - -ACTOR ClericPlayer : PlayerPawn -{ - Health 100 - ReactionTime 0 - PainChance 255 - Radius 16 - Height 64 - Speed 1 - +NOSKIN - +NODAMAGETHRUST - +NOTHRUSTWHENINVUL - PainSound "PlayerClericPain" - RadiusDamageFactor 0.25 - Player.JumpZ 9 - Player.Viewheight 48 - Player.SpawnClass "Cleric" - Player.DisplayName "Cleric" - Player.SoundClass "cleric" - Player.ScoreIcon "CLERFACE" - Player.InvulnerabilityMode "Ghost" - Player.HealRadiusType "Health" - Player.Hexenarmor 10, 10, 25, 5, 20 - Player.StartItem "CWeapMace" - Player.Portrait "P_CWALK1" - Player.WeaponSlot 1, CWeapMace - Player.WeaponSlot 2, CWeapStaff - Player.WeaponSlot 3, CWeapFlame - Player.WeaponSlot 4, CWeapWraithverge - Player.FlechetteType "ArtiPoisonBag1" - - Player.ColorRange 146, 163 - Player.Colorset 0, "Blue", 146, 163, 161 - Player.ColorsetFile 1, "Red", "TRANTBL7", 0xB3 - Player.ColorsetFile 2, "Gold", "TRANTBL8", 0x8C - Player.ColorsetFile 3, "Dull Green", "TRANTBL9", 0x41 - Player.ColorsetFile 4, "Green", "TRANTBLA", 0xC9 - Player.ColorsetFile 5, "Gray", "TRANTBLB", 0x30 - Player.ColorsetFile 6, "Brown", "TRANTBLC", 0x72 - Player.ColorsetFile 7, "Purple", "TRANTBLD", 0xEE - - States - { - Spawn: - CLER A -1 - Stop - See: - CLER ABCD 4 - Loop - Pain: - CLER H 4 - CLER H 4 A_Pain - Goto Spawn - Missile: - Melee: - CLER EFG 6 - Goto Spawn - Death: - CLER I 6 - CLER J 6 A_PlayerScream - CLER KL 6 - CLER M 6 A_NoBlocking - CLER NOP 6 - CLER Q -1 - Stop - XDeath: - CLER R 5 A_PlayerScream - CLER S 5 - CLER T 5 A_NoBlocking - CLER UVWXYZ 5 - CLER [ -1 - Stop - Ice: - CLER "\" 5 A_FreezeDeath - CLER "\" 1 A_FreezeDeathChunks - Wait - Burn: - FDTH C 5 BRIGHT A_PlaySound("*burndeath") - FDTH D 4 BRIGHT - FDTH G 5 BRIGHT - FDTH H 4 BRIGHT A_PlayerScream - FDTH I 5 BRIGHT - FDTH J 4 BRIGHT - FDTH K 5 BRIGHT - FDTH L 4 BRIGHT - FDTH M 5 BRIGHT - FDTH N 4 BRIGHT - FDTH O 5 BRIGHT - FDTH P 4 BRIGHT - FDTH Q 5 BRIGHT - FDTH R 4 BRIGHT - FDTH S 5 BRIGHT A_NoBlocking - FDTH T 4 BRIGHT - FDTH U 5 BRIGHT - FDTH V 4 BRIGHT - ACLO E 35 A_CheckPlayerDone - Wait - ACLO E 8 - Stop - } -} - diff --git a/wadsrc/static/actors/hexen/fighterplayer.txt b/wadsrc/static/actors/hexen/fighterplayer.txt deleted file mode 100644 index 29de1f3a3..000000000 --- a/wadsrc/static/actors/hexen/fighterplayer.txt +++ /dev/null @@ -1,126 +0,0 @@ -// The fighter -------------------------------------------------------------- - -ACTOR FighterPlayer : PlayerPawn -{ - Health 100 - PainChance 255 - Radius 16 - Height 64 - Speed 1 - +NOSKIN - +NODAMAGETHRUST - +NOTHRUSTWHENINVUL - PainSound "PlayerFighterPain" - RadiusDamageFactor 0.25 - Player.JumpZ 9 - Player.Viewheight 48 - Player.SpawnClass "Fighter" - Player.DisplayName "Fighter" - Player.SoundClass "fighter" - Player.ScoreIcon "FITEFACE" - Player.HealRadiusType "Armor" - Player.Hexenarmor 15, 25, 20, 15, 5 - Player.StartItem "FWeapFist" - Player.ForwardMove 1.08, 1.2 - Player.SideMove 1.125, 1.475 - Player.Portrait "P_FWALK1" - Player.WeaponSlot 1, FWeapFist - Player.WeaponSlot 2, FWeapAxe - Player.WeaponSlot 3, FWeapHammer - Player.WeaponSlot 4, FWeapQuietus - - Player.ColorRange 246, 254 - Player.Colorset 0, "Gold", 246, 254, 253 - Player.ColorsetFile 1, "Red", "TRANTBL0", 0xAC - Player.ColorsetFile 2, "Blue", "TRANTBL1", 0x9D - Player.ColorsetFile 3, "Dull Green", "TRANTBL2", 0x3E - Player.ColorsetFile 4, "Green", "TRANTBL3", 0xC8 - Player.ColorsetFile 5, "Gray", "TRANTBL4", 0x2D - Player.ColorsetFile 6, "Brown", "TRANTBL5", 0x6F - Player.ColorsetFile 7, "Purple", "TRANTBL6", 0xEE - - States - { - Spawn: - PLAY A -1 - Stop - See: - PLAY ABCD 4 - Loop - Missile: - Melee: - PLAY EF 8 - Goto Spawn - Pain: - PLAY G 4 - PLAY G 4 A_Pain - Goto Spawn - Death: - PLAY H 6 - PLAY I 6 A_PlayerScream - PLAY JK 6 - PLAY L 6 A_NoBlocking - PLAY M 6 - PLAY N -1 - Stop - XDeath: - PLAY O 5 A_PlayerScream - PLAY P 5 A_SkullPop("BloodyFighterSkull") - PLAY R 5 A_NoBlocking - PLAY STUV 5 - PLAY W -1 - Stop - Ice: - PLAY X 5 A_FreezeDeath - PLAY X 1 A_FreezeDeathChunks - Wait - Burn: - FDTH A 5 BRIGHT A_PlaySound("*burndeath") - FDTH B 4 BRIGHT - FDTH G 5 BRIGHT - FDTH H 4 BRIGHT A_PlayerScream - FDTH I 5 BRIGHT - FDTH J 4 BRIGHT - FDTH K 5 BRIGHT - FDTH L 4 BRIGHT - FDTH M 5 BRIGHT - FDTH N 4 BRIGHT - FDTH O 5 BRIGHT - FDTH P 4 BRIGHT - FDTH Q 5 BRIGHT - FDTH R 4 BRIGHT - FDTH S 5 BRIGHT A_NoBlocking - FDTH T 4 BRIGHT - FDTH U 5 BRIGHT - FDTH V 4 BRIGHT - ACLO E 35 A_CheckPlayerDone - Wait - ACLO E 8 - Stop - } -} - -// The fighter's bloody skull -------------------------------------------------------------- - -Actor BloodyFighterSkull : PlayerChunk -{ - Radius 4 - Height 4 - +NOBLOCKMAP - +DROPOFF - +LOWGRAVITY - +CANNOTPUSH - +SKYEXPLODE - +NOBLOCKMONST - +NOSKIN - States - { - Spawn: - BSKL A 0 - BSKL ABCDFGH 5 A_CheckFloor("Hit") - Goto Spawn+1 - Hit: - BSKL I 16 A_CheckPlayerDone - Wait - } -} diff --git a/wadsrc/static/actors/hexen/flame.txt b/wadsrc/static/actors/hexen/flame.txt deleted file mode 100644 index b3e369a2e..000000000 --- a/wadsrc/static/actors/hexen/flame.txt +++ /dev/null @@ -1,106 +0,0 @@ -// Temp Small Flame -------------------------------------------------------- - -ACTOR FlameSmallTemp -{ - +NOTELEPORT - RenderStyle Add - States - { - Spawn: - FFSM AB 3 Bright - FFSM C 2 Bright A_CountdownArg(0) - FFSM C 2 Bright - FFSM D 3 Bright - FFSM E 3 Bright A_CountdownArg(0) - Loop - } -} - - -// Temp Large Flame --------------------------------------------------------- - -ACTOR FlameLargeTemp -{ - +NOTELEPORT - RenderStyle Add - States - { - Spawn: - FFLG A 4 Bright - FFLG B 4 Bright A_CountdownArg(0) - FFLG C 4 Bright - FFLG D 4 Bright A_CountdownArg(0) - FFLG E 4 Bright - FFLG F 4 Bright A_CountdownArg(0) - FFLG G 4 Bright - FFLG H 4 Bright A_CountdownArg(0) - FFLG I 4 Bright - FFLG J 4 Bright A_CountdownArg(0) - FFLG K 4 Bright - FFLG L 4 Bright A_CountdownArg(0) - FFLG M 4 Bright - FFLG N 4 Bright A_CountdownArg(0) - FFLG O 4 Bright - FFLG P 4 Bright A_CountdownArg(0) - Goto Spawn+4 - } -} - -// Small Flame -------------------------------------------------------------- - -ACTOR FlameSmall : SwitchableDecoration -{ - +NOTELEPORT - +INVISIBLE - Radius 15 - RenderStyle Add - States - { - Active: - FFSM A 0 Bright A_PlaySound("Ignite") - Spawn: - FFSM A 3 Bright - FFSM A 3 Bright A_UnHideThing - FFSM ABCDE 3 Bright - Goto Spawn+2 - Inactive: - FFSM A 2 - FFSM B 2 A_HideThing - FFSM C 200 - Wait - } -} - -ACTOR FlameSmall2 : FlameSmall -{ -} - -// Large Flame -------------------------------------------------------------- - -ACTOR FlameLarge : SwitchableDecoration -{ - +NOTELEPORT - +INVISIBLE - Radius 15 - RenderStyle Add - States - { - Active: - FFLG A 0 Bright A_PlaySound("Ignite") - Spawn: - FFLG A 2 Bright - FFLG A 2 Bright A_UnHideThing - FFLG ABCDEFGHIJKLMNOP 4 Bright - Goto Spawn+6 - Inactive: - FFLG DCB 2 - FFLG A 2 A_HideThing - FFLG A 200 - Wait - } -} - -ACTOR FlameLarge2 : FlameLarge -{ -} - diff --git a/wadsrc/static/actors/hexen/flies.txt b/wadsrc/static/actors/hexen/flies.txt deleted file mode 100644 index e297cc289..000000000 --- a/wadsrc/static/actors/hexen/flies.txt +++ /dev/null @@ -1,27 +0,0 @@ - -// Buzzy fly ---------------------------------------------------------------- - -ACTOR LittleFly -{ - +NOBLOCKMAP +NOGRAVITY - +CANPASS - - Speed 6 - Radius 5 - Height 5 - Mass 2 - ActiveSound "FlyBuzz" - - action native A_FlySearch(); - action native A_FlyBuzz(); - - States - { - Spawn: - TNT1 A 20 A_FlySearch // [RH] Invisible when not flying - Loop - Buzz: - AFLY ABCD 3 A_FlyBuzz - Loop - } -} diff --git a/wadsrc/static/actors/hexen/korax.txt b/wadsrc/static/actors/hexen/korax.txt deleted file mode 100644 index a35183ad6..000000000 --- a/wadsrc/static/actors/hexen/korax.txt +++ /dev/null @@ -1,124 +0,0 @@ -ACTOR Korax -{ - Health 5000 - Painchance 20 - Speed 10 - Radius 65 - Height 115 - Mass 2000 - Damage 15 - Monster - +BOSS - +FLOORCLIP - +TELESTOMP - +DONTMORPH - +NOTARGET - +NOICEDEATH - SeeSound "KoraxSight" - AttackSound "KoraxAttack" - PainSound "KoraxPain" - DeathSound "KoraxDeath" - ActiveSound "KoraxActive" - Obituary "$OB_KORAX" // "%o was swept from the board by Korax." - - action native A_KoraxChase(); - action native A_KoraxDecide(); - action native A_KoraxBonePop(); - action native A_KoraxMissile(); - action native A_KoraxCommand(); - - States - { - Spawn: - KORX A 5 A_Look - Loop - See: - KORX AAA 3 A_KoraxChase - KORX B 3 A_Chase - KORX BBB 3 A_KoraxChase - KORX C 0 A_PlaySound("KoraxStep") - KORX C 3 A_Chase - KORX CCC 3 A_KoraxChase - KORX D 3 A_Chase - KORX DDD 3 A_KoraxChase - KORX A 0 A_PlaySound("KoraxStep") - KORX A 3 A_Chase - Loop - Pain: - KORX H 5 A_Pain - KORX H 5 - Goto See - Missile: - KORX E 2 Bright A_FaceTarget - KORX E 5 Bright A_KoraxDecide - Wait - Death: - KORX I 5 - KORX J 5 A_FaceTarget - KORX K 5 A_Scream - KORX LMNOP 5 - KORX Q 10 - KORX R 5 A_KoraxBonePop - KORX S 5 A_NoBlocking - KORX TU 5 - KORX V -1 - Stop - Attack: - KORX E 4 Bright A_FaceTarget - KORX F 8 Bright A_KoraxMissile - KORX E 8 Bright - Goto See - Command: - KORX E 5 Bright A_FaceTarget - KORX W 10 Bright A_FaceTarget - KORX G 15 Bright A_KoraxCommand - KORX W 10 Bright - KORX E 5 Bright - Goto See - } -} - -ACTOR KoraxSpirit -{ - Speed 8 - Projectile - +NOCLIP - -ACTIVATEPCROSS - -ACTIVATEIMPACT - RenderStyle Translucent - Alpha 0.4 - - action native A_KSpiritRoam(); - - States - { - Spawn: - SPIR AB 5 A_KSpiritRoam - Loop - Death: - SPIR DEFGHI 5 - Stop - } -} - -ACTOR KoraxBolt -{ - Radius 15 - Height 35 - Projectile - -ACTIVATEPCROSS - -ACTIVATEIMPACT - RenderStyle Add - - action native A_KBolt(); - action native A_KBoltRaise(); - - States - { - Spawn: - MLFX I 2 Bright - MLFX J 2 Bright A_KBoltRaise - MLFX IJKLM 2 Bright A_KBolt - Stop - } -} diff --git a/wadsrc/static/actors/hexen/mageplayer.txt b/wadsrc/static/actors/hexen/mageplayer.txt deleted file mode 100644 index 9cf4117a5..000000000 --- a/wadsrc/static/actors/hexen/mageplayer.txt +++ /dev/null @@ -1,104 +0,0 @@ -// The mage ----------------------------------------------------------------- - -ACTOR MagePlayer : PlayerPawn -{ - Health 100 - ReactionTime 0 - PainChance 255 - Radius 16 - Height 64 - Speed 1 - +NOSKIN - +NODAMAGETHRUST - +NOTHRUSTWHENINVUL - PainSound "PlayerMagePain" - RadiusDamageFactor 0.25 - Player.JumpZ 9 - Player.Viewheight 48 - Player.SpawnClass "Mage" - Player.DisplayName "Mage" - Player.SoundClass "mage" - Player.ScoreIcon "MAGEFACE" - Player.InvulnerabilityMode "Reflective" - Player.HealRadiusType "Mana" - Player.Hexenarmor 5, 5, 15, 10, 25 - Player.StartItem "MWeapWand" - Player.ForwardMove 0.88, 0.92 - Player.SideMove 0.875, 0.925 - Player.Portrait "P_MWALK1" - Player.WeaponSlot 1, MWeapWand - Player.WeaponSlot 2, MWeapFrost - Player.WeaponSlot 3, MWeapLightning - Player.WeaponSlot 4, MWeapBloodscourge - Player.FlechetteType "ArtiPoisonBag2" - - Player.ColorRange 146, 163 - Player.Colorset 0, "Blue", 146, 163, 161 - Player.ColorsetFile 1, "Red", "TRANTBL7", 0xB3 - Player.ColorsetFile 2, "Gold", "TRANTBL8", 0x8C - Player.ColorsetFile 3, "Dull Green", "TRANTBL9", 0x41 - Player.ColorsetFile 4, "Green", "TRANTBLA", 0xC9 - Player.ColorsetFile 5, "Gray", "TRANTBLB", 0x30 - Player.ColorsetFile 6, "Brown", "TRANTBLC", 0x72 - Player.ColorsetFile 7, "Purple", "TRANTBLD", 0xEE - - States - { - Spawn: - MAGE A -1 - Stop - See: - MAGE ABCD 4 - Loop - Missile: - Melee: - MAGE EF 8 - Goto Spawn - Pain: - MAGE G 4 - MAGE G 4 A_Pain - Goto Spawn - Death: - MAGE H 6 - MAGE I 6 A_PlayerScream - MAGE JK 6 - MAGE L 6 A_NoBlocking - MAGE M 6 - MAGE N -1 - Stop - XDeath: - MAGE O 5 A_PlayerScream - MAGE P 5 - MAGE R 5 A_NoBlocking - MAGE STUVW 5 - MAGE X -1 - Stop - Ice: - MAGE Y 5 A_FreezeDeath - MAGE Y 1 A_FreezeDeathChunks - Wait - Burn: - FDTH E 5 BRIGHT A_PlaySound("*burndeath") - FDTH F 4 BRIGHT - FDTH G 5 BRIGHT - FDTH H 4 BRIGHT A_PlayerScream - FDTH I 5 BRIGHT - FDTH J 4 BRIGHT - FDTH K 5 BRIGHT - FDTH L 4 BRIGHT - FDTH M 5 BRIGHT - FDTH N 4 BRIGHT - FDTH O 5 BRIGHT - FDTH P 4 BRIGHT - FDTH Q 5 BRIGHT - FDTH R 4 BRIGHT - FDTH S 5 BRIGHT A_NoBlocking - FDTH T 4 BRIGHT - FDTH U 5 BRIGHT - FDTH V 4 BRIGHT - ACLO E 35 A_CheckPlayerDone - Wait - ACLO E 8 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/pig.txt b/wadsrc/static/actors/hexen/pig.txt deleted file mode 100644 index 9d986e7eb..000000000 --- a/wadsrc/static/actors/hexen/pig.txt +++ /dev/null @@ -1,155 +0,0 @@ - - -// Snout puff --------------------------------------------------------------- - -ACTOR SnoutPuff -{ - +NOBLOCKMAP - +NOGRAVITY - Renderstyle Translucent - Alpha 0.6 - States - { - Spawn: - FHFX STUVW 4 - Stop - } -} - - -// Snout -------------------------------------------------------------------- - -ACTOR Snout : Weapon -{ - Weapon.SelectionOrder 10000 - +WEAPON.DONTBOB - +WEAPON.MELEEWEAPON - Weapon.Kickback 150 - Weapon.YAdjust 10 - - action native A_SnoutAttack (); - - States - { - Ready: - WPIG A 1 A_WeaponReady - Loop - Deselect: - WPIG A 1 A_Lower - Loop - Select: - WPIG A 1 A_Raise - Fire: - WPIG A 4 A_SnoutAttack - WPIG B 8 A_SnoutAttack - Goto Ready - Grunt: - WPIG B 8 - Goto Ready - } -} - - -// Pig player --------------------------------------------------------------- - -ACTOR PigPlayer : PlayerPawn native -{ - Health 30 - ReactionTime 0 - PainChance 255 - Radius 16 - Height 24 - Speed 1 - +WINDTHRUST - +NOSKIN - -PICKUP - PainSound "PigPain" - DeathSound "PigDeath" - Player.JumpZ 6 - Player.Viewheight 28 - Player.ForwardMove 0.96, 0.98 - Player.SideMove 0.95833333, 0.975 - Player.SpawnClass "Pig" - Player.SoundClass "Pig" - Player.DisplayName "Pig" - Player.MorphWeapon "Snout" - States - { - Spawn: - PIGY A -1 - Stop - See: - PIGY ABCD 3 - Loop - Pain: - PIGY D 4 A_PigPain - Goto Spawn - Melee: - Missile: - PIGY A 12 - Goto Spawn - Death: - PIGY E 4 A_Scream - PIGY F 3 A_NoBlocking - PIGY G 4 - PIGY H 3 - PIGY IJK 4 - PIGY L -1 - Stop - Ice: - PIGY M 5 A_FreezeDeath - PIGY M 1 A_FreezeDeathChunks - Wait - } -} - - - -// Pig (non-player) --------------------------------------------------------- - -ACTOR Pig : MorphedMonster -{ - Health 25 - Painchance 128 - Speed 10 - Radius 12 - Height 22 - Mass 60 - Monster - -COUNTKILL - +WINDTHRUST - +DONTMORPH - SeeSound "PigActive1" - PainSound "PigPain" - DeathSound "PigDeath" - ActiveSound "PigActive1" - States - { - Spawn: - PIGY B 10 A_Look - Loop - See: - PIGY ABCD 3 A_Chase - Loop - Pain: - PIGY D 4 A_PigPain - Goto See - Melee: - PIGY A 5 A_FaceTarget - PIGY A 10 A_CustomMeleeAttack(random[PigAttack](2,3), "PigAttack") - Goto See - Death: - PIGY E 4 A_Scream - PIGY F 3 A_NoBlocking - PIGY G 4 A_QueueCorpse - PIGY H 3 - PIGY IJK 4 - PIGY L -1 - Stop - Ice: - PIGY M 5 A_FreezeDeath - PIGY M 1 A_FreezeDeathChunks - Wait - } -} - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index b8586d3ee..450cc37a7 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,11 +1,3 @@ -#include "actors/hexen/baseweapons.txt" -#include "actors/hexen/korax.txt" -#include "actors/hexen/fighterplayer.txt" -#include "actors/hexen/clericplayer.txt" -#include "actors/hexen/mageplayer.txt" -#include "actors/hexen/pig.txt" -#include "actors/hexen/flame.txt" -#include "actors/hexen/flies.txt" #include "actors/hexen/hexenarmor.txt" #include "actors/hexen/hexendecorations.txt" #include "actors/hexen/hexenkeys.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 8fef6819a..787cb661f 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -84,3 +84,56 @@ zscript/heretic/wizard.txt zscript/heretic/ironlich.txt zscript/heretic/dsparil.txt zscript/heretic/chicken.txt + +zscript/hexen/baseweapons.txt +zscript/hexen/korax.txt +zscript/hexen/fighterplayer.txt +zscript/hexen/clericplayer.txt +zscript/hexen/mageplayer.txt +zscript/hexen/pig.txt +zscript/hexen/flame.txt +zscript/hexen/flies.txt +/* +zscript/hexen/hexenarmor.txt +zscript/hexen/hexendecorations.txt +zscript/hexen/hexenkeys.txt +zscript/hexen/hexenspecialdecs.txt +zscript/hexen/mana.txt +zscript/hexen/puzzleitems.txt +zscript/hexen/scriptprojectiles.txt +zscript/hexen/speedboots.txt +zscript/hexen/ettin.txt +zscript/hexen/centaur.txt +zscript/hexen/demons.txt +zscript/hexen/firedemon.txt +zscript/hexen/fog.txt +zscript/hexen/summon.txt +zscript/hexen/flechette.txt +zscript/hexen/clericboss.txt +zscript/hexen/fighterboss.txt +zscript/hexen/mageboss.txt +zscript/hexen/bats.txt +zscript/hexen/bishop.txt +zscript/hexen/blastradius.txt +zscript/hexen/boostarmor.txt +zscript/hexen/clericmace.txt +zscript/hexen/clericflame.txt +zscript/hexen/clericholy.txt +zscript/hexen/clericstaff.txt +zscript/hexen/magewand.txt +zscript/hexen/magecone.txt +zscript/hexen/magelightning.txt +zscript/hexen/magestaff.txt +zscript/hexen/fighterfist.txt +zscript/hexen/fighteraxe.txt +zscript/hexen/fighterhammer.txt +zscript/hexen/fighterquietus.txt +zscript/hexen/dragon.txt +zscript/hexen/healingradius.txt +zscript/hexen/teleportother.txt +zscript/hexen/iceguy.txt +zscript/hexen/serpent.txt +zscript/hexen/spike.txt +zscript/hexen/wraith.txt +zscript/hexen/heresiarch.txt +*/ \ No newline at end of file diff --git a/wadsrc/static/zscript/hexen/baseweapons.txt b/wadsrc/static/zscript/hexen/baseweapons.txt new file mode 100644 index 000000000..eb685a873 --- /dev/null +++ b/wadsrc/static/zscript/hexen/baseweapons.txt @@ -0,0 +1,29 @@ +// The Doom and Heretic players are not excluded from pickup in case +// somebody wants to use these weapons with either of those games. + +class FighterWeapon : Weapon native +{ + Default + { + Weapon.Kickback 150; + Inventory.ForbiddenTo "ClericPlayer", "MagePlayer"; + } +} + +class ClericWeapon : Weapon native +{ + Default + { + Weapon.Kickback 150; + Inventory.ForbiddenTo "FighterPlayer", "MagePlayer"; + } +} + +class MageWeapon : Weapon native +{ + Default + { + Weapon.Kickback 150; + Inventory.ForbiddenTo "FighterPlayer", "ClericPlayer"; + } +} diff --git a/wadsrc/static/zscript/hexen/clericplayer.txt b/wadsrc/static/zscript/hexen/clericplayer.txt new file mode 100644 index 000000000..1b47ad3f5 --- /dev/null +++ b/wadsrc/static/zscript/hexen/clericplayer.txt @@ -0,0 +1,106 @@ +// The cleric --------------------------------------------------------------- + +class ClericPlayer : PlayerPawn +{ + Default + { + Health 100; + ReactionTime 0; + PainChance 255; + Radius 16; + Height 64; + Speed 1; + +NOSKIN + +NODAMAGETHRUST + +PLAYERPAWN.NOTHRUSTWHENINVUL + PainSound "PlayerClericPain"; + RadiusDamageFactor 0.25; + Player.JumpZ 9; + Player.Viewheight 48; + Player.SpawnClass "Cleric"; + Player.DisplayName "Cleric"; + Player.SoundClass "cleric"; + Player.ScoreIcon "CLERFACE"; + Player.InvulnerabilityMode "Ghost"; + Player.HealRadiusType "Health"; + Player.Hexenarmor 10, 10, 25, 5, 20; + Player.StartItem "CWeapMace"; + Player.Portrait "P_CWALK1"; + Player.WeaponSlot 1, "CWeapMace"; + Player.WeaponSlot 2, "CWeapStaff"; + Player.WeaponSlot 3, "CWeapFlame"; + Player.WeaponSlot 4, "CWeapWraithverge"; + Player.FlechetteType "ArtiPoisonBag1"; + + Player.ColorRange 146, 163; + Player.Colorset 0, "Blue", 146, 163, 161; + Player.ColorsetFile 1, "Red", "TRANTBL7", 0xB3; + Player.ColorsetFile 2, "Gold", "TRANTBL8", 0x8C; + Player.ColorsetFile 3, "Dull Green", "TRANTBL9", 0x41; + Player.ColorsetFile 4, "Green", "TRANTBLA", 0xC9; + Player.ColorsetFile 5, "Gray", "TRANTBLB", 0x30; + Player.ColorsetFile 6, "Brown", "TRANTBLC", 0x72; + Player.ColorsetFile 7, "Purple", "TRANTBLD", 0xEE; + } + + States + { + Spawn: + CLER A -1; + Stop; + See: + CLER ABCD 4; + Loop; + Pain: + CLER H 4; + CLER H 4 A_Pain; + Goto Spawn; + Missile: + Melee: + CLER EFG 6; + Goto Spawn; + Death: + CLER I 6; + CLER J 6 A_PlayerScream; + CLER KL 6; + CLER M 6 A_NoBlocking; + CLER NOP 6; + CLER Q -1; + Stop; + XDeath: + CLER R 5 A_PlayerScream; + CLER S 5; + CLER T 5 A_NoBlocking; + CLER UVWXYZ 5; + CLER [ -1; + Stop; + Ice: + CLER \ 5 A_FreezeDeath; + CLER \ 1 A_FreezeDeathChunks; + Wait; + Burn: + FDTH C 5 BRIGHT A_PlaySound("*burndeath"); + FDTH D 4 BRIGHT; + FDTH G 5 BRIGHT; + FDTH H 4 BRIGHT A_PlayerScream; + FDTH I 5 BRIGHT; + FDTH J 4 BRIGHT; + FDTH K 5 BRIGHT; + FDTH L 4 BRIGHT; + FDTH M 5 BRIGHT; + FDTH N 4 BRIGHT; + FDTH O 5 BRIGHT; + FDTH P 4 BRIGHT; + FDTH Q 5 BRIGHT; + FDTH R 4 BRIGHT; + FDTH S 5 BRIGHT A_NoBlocking; + FDTH T 4 BRIGHT; + FDTH U 5 BRIGHT; + FDTH V 4 BRIGHT; + ACLO E 35 A_CheckPlayerDone; + Wait; + ACLO E 8; + Stop; + } +} + diff --git a/wadsrc/static/zscript/hexen/fighterplayer.txt b/wadsrc/static/zscript/hexen/fighterplayer.txt new file mode 100644 index 000000000..3aa5607d3 --- /dev/null +++ b/wadsrc/static/zscript/hexen/fighterplayer.txt @@ -0,0 +1,133 @@ +// The fighter -------------------------------------------------------------- + +class FighterPlayer : PlayerPawn +{ + Default + { + Health 100; + PainChance 255; + Radius 16; + Height 64; + Speed 1; + +NOSKIN + +NODAMAGETHRUST + +PLAYERPAWN.NOTHRUSTWHENINVUL + PainSound "PlayerFighterPain"; + RadiusDamageFactor 0.25; + Player.JumpZ 9; + Player.Viewheight 48; + Player.SpawnClass "Fighter"; + Player.DisplayName "Fighter"; + Player.SoundClass "fighter"; + Player.ScoreIcon "FITEFACE"; + Player.HealRadiusType "Armor"; + Player.Hexenarmor 15, 25, 20, 15, 5; + Player.StartItem "FWeapFist"; + Player.ForwardMove 1.08, 1.2; + Player.SideMove 1.125, 1.475; + Player.Portrait "P_FWALK1"; + Player.WeaponSlot 1, "FWeapFist"; + Player.WeaponSlot 2, "FWeapAxe"; + Player.WeaponSlot 3, "FWeapHammer"; + Player.WeaponSlot 4, "FWeapQuietus"; + + Player.ColorRange 246, 254; + Player.Colorset 0, "Gold", 246, 254, 253; + Player.ColorsetFile 1, "Red", "TRANTBL0", 0xAC; + Player.ColorsetFile 2, "Blue", "TRANTBL1", 0x9D; + Player.ColorsetFile 3, "Dull Green", "TRANTBL2", 0x3E; + Player.ColorsetFile 4, "Green", "TRANTBL3", 0xC8; + Player.ColorsetFile 5, "Gray", "TRANTBL4", 0x2D; + Player.ColorsetFile 6, "Brown", "TRANTBL5", 0x6F; + Player.ColorsetFile 7, "Purple", "TRANTBL6", 0xEE; + } + + States + { + Spawn: + PLAY A -1; + Stop; + See: + PLAY ABCD 4; + Loop; + Missile: + Melee: + PLAY EF 8; + Goto Spawn; + Pain: + PLAY G 4; + PLAY G 4 A_Pain; + Goto Spawn; + Death: + PLAY H 6; + PLAY I 6 A_PlayerScream; + PLAY JK 6; + PLAY L 6 A_NoBlocking; + PLAY M 6; + PLAY N -1; + Stop; + XDeath: + PLAY O 5 A_PlayerScream; + PLAY P 5 A_SkullPop("BloodyFighterSkull"); + PLAY R 5 A_NoBlocking; + PLAY STUV 5; + PLAY W -1; + Stop; + Ice: + PLAY X 5 A_FreezeDeath; + PLAY X 1 A_FreezeDeathChunks; + Wait; + Burn: + FDTH A 5 BRIGHT A_PlaySound("*burndeath"); + FDTH B 4 BRIGHT; + FDTH G 5 BRIGHT; + FDTH H 4 BRIGHT A_PlayerScream; + FDTH I 5 BRIGHT; + FDTH J 4 BRIGHT; + FDTH K 5 BRIGHT; + FDTH L 4 BRIGHT; + FDTH M 5 BRIGHT; + FDTH N 4 BRIGHT; + FDTH O 5 BRIGHT; + FDTH P 4 BRIGHT; + FDTH Q 5 BRIGHT; + FDTH R 4 BRIGHT; + FDTH S 5 BRIGHT A_NoBlocking; + FDTH T 4 BRIGHT; + FDTH U 5 BRIGHT; + FDTH V 4 BRIGHT; + ACLO E 35 A_CheckPlayerDone; + Wait; + ACLO E 8; + Stop; + } +} + +// The fighter's bloody skull -------------------------------------------------------------- + +class BloodyFighterSkull : PlayerChunk +{ + Default + { + Radius 4; + Height 4; + Gravity 0.125; + +NOBLOCKMAP + +DROPOFF + +CANNOTPUSH + +SKYEXPLODE + +NOBLOCKMONST + +NOSKIN + } + + States + { + Spawn: + BSKL A 0; + BSKL ABCDFGH 5 A_CheckFloor("Hit"); + Goto Spawn+1; + Hit: + BSKL I 16 A_CheckPlayerDone; + Wait; + } +} diff --git a/wadsrc/static/zscript/hexen/flame.txt b/wadsrc/static/zscript/hexen/flame.txt new file mode 100644 index 000000000..4eab6c6d3 --- /dev/null +++ b/wadsrc/static/zscript/hexen/flame.txt @@ -0,0 +1,122 @@ +// Temp Small Flame -------------------------------------------------------- + +class FlameSmallTemp : Actor +{ + Default + { + +NOTELEPORT + RenderStyle "Add"; + } + + States + { + Spawn: + FFSM AB 3 Bright; + FFSM C 2 Bright A_CountdownArg(0); + FFSM C 2 Bright; + FFSM D 3 Bright; + FFSM E 3 Bright A_CountdownArg(0); + Loop; + } +} + + +// Temp Large Flame --------------------------------------------------------- + +class FlameLargeTemp : Actor +{ + Default + { + +NOTELEPORT + RenderStyle "Add"; + } + + States + { + Spawn: + FFLG A 4 Bright; + FFLG B 4 Bright A_CountdownArg(0); + FFLG C 4 Bright; + FFLG D 4 Bright A_CountdownArg(0); + FFLG E 4 Bright; + FFLG F 4 Bright A_CountdownArg(0); + FFLG G 4 Bright; + FFLG H 4 Bright A_CountdownArg(0); + FFLG I 4 Bright; + FFLG J 4 Bright A_CountdownArg(0); + FFLG K 4 Bright; + FFLG L 4 Bright A_CountdownArg(0); + FFLG M 4 Bright; + FFLG N 4 Bright A_CountdownArg(0); + FFLG O 4 Bright; + FFLG P 4 Bright A_CountdownArg(0); + Goto Spawn+4; + } +} + +// Small Flame -------------------------------------------------------------- + +class FlameSmall : SwitchableDecoration +{ + Default + { + +NOTELEPORT + +INVISIBLE + Radius 15; + RenderStyle "Add"; + } + + States + { + Active: + FFSM A 0 Bright A_PlaySound("Ignite"); + Spawn: + FFSM A 3 Bright; + FFSM A 3 Bright A_UnHideThing; + FFSM ABCDE 3 Bright; + Goto Spawn+2; + Inactive: + FFSM A 2; + FFSM B 2 A_HideThing; + FFSM C 200; + Wait; + } +} + +class FlameSmall2 : FlameSmall +{ +} + +// Large Flame -------------------------------------------------------------- + +class FlameLarge : SwitchableDecoration +{ + Default + { + +NOTELEPORT + +INVISIBLE + Radius 15; + RenderStyle "Add"; + } + + States + { + Active: + FFLG A 0 Bright A_PlaySound("Ignite"); + Spawn: + FFLG A 2 Bright; + FFLG A 2 Bright A_UnHideThing; + FFLG ABCDEFGHIJKLMNOP 4 Bright; + Goto Spawn+6; + Inactive: + FFLG DCB 2; + FFLG A 2 A_HideThing; + FFLG A 200; + Wait; + } +} + +class FlameLarge2 : FlameLarge +{ +} + diff --git a/wadsrc/static/zscript/hexen/flies.txt b/wadsrc/static/zscript/hexen/flies.txt new file mode 100644 index 000000000..35c52a124 --- /dev/null +++ b/wadsrc/static/zscript/hexen/flies.txt @@ -0,0 +1,30 @@ + +// Buzzy fly ---------------------------------------------------------------- + +class LittleFly : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + +CANPASS + + Speed 6; + Radius 5; + Height 5; + Mass 2; + ActiveSound "FlyBuzz"; + } + + action native void A_FlySearch(); + action native void A_FlyBuzz(); + + States + { + Spawn: + TNT1 A 20 A_FlySearch; // [RH] Invisible when not flying + Loop; + Buzz: + AFLY ABCD 3 A_FlyBuzz; + Loop; + } +} diff --git a/wadsrc/static/zscript/hexen/korax.txt b/wadsrc/static/zscript/hexen/korax.txt new file mode 100644 index 000000000..3928de884 --- /dev/null +++ b/wadsrc/static/zscript/hexen/korax.txt @@ -0,0 +1,133 @@ +class Korax : Actor +{ + Default + { + Health 5000; + Painchance 20; + Speed 10; + Radius 65; + Height 115; + Mass 2000; + Damage 15; + Monster; + +BOSS + +FLOORCLIP + +TELESTOMP + +DONTMORPH + +NOTARGET + +NOICEDEATH + SeeSound "KoraxSight"; + AttackSound "KoraxAttack"; + PainSound "KoraxPain"; + DeathSound "KoraxDeath"; + ActiveSound "KoraxActive"; + Obituary "$OB_KORAX"; + } + + action native void A_KoraxChase(); + action native void A_KoraxDecide(); + action native void A_KoraxBonePop(); + action native void A_KoraxMissile(); + action native void A_KoraxCommand(); + + States + { + Spawn: + KORX A 5 A_Look; + Loop; + See: + KORX AAA 3 A_KoraxChase; + KORX B 3 A_Chase; + KORX BBB 3 A_KoraxChase; + KORX C 0 A_PlaySound("KoraxStep"); + KORX C 3 A_Chase; + KORX CCC 3 A_KoraxChase; + KORX D 3 A_Chase; + KORX DDD 3 A_KoraxChase; + KORX A 0 A_PlaySound("KoraxStep"); + KORX A 3 A_Chase; + Loop; + Pain: + KORX H 5 A_Pain; + KORX H 5; + Goto See; + Missile: + KORX E 2 Bright A_FaceTarget; + KORX E 5 Bright A_KoraxDecide; + Wait; + Death: + KORX I 5; + KORX J 5 A_FaceTarget; + KORX K 5 A_Scream; + KORX LMNOP 5; + KORX Q 10; + KORX R 5 A_KoraxBonePop; + KORX S 5 A_NoBlocking; + KORX TU 5; + KORX V -1; + Stop; + Attack: + KORX E 4 Bright A_FaceTarget; + KORX F 8 Bright A_KoraxMissile; + KORX E 8 Bright; + Goto See; + Command: + KORX E 5 Bright A_FaceTarget; + KORX W 10 Bright A_FaceTarget; + KORX G 15 Bright A_KoraxCommand; + KORX W 10 Bright; + KORX E 5 Bright; + Goto See; + } +} + +class KoraxSpirit : Actor +{ + Default + { + Speed 8; + Projectile; + +NOCLIP + -ACTIVATEPCROSS + -ACTIVATEIMPACT + RenderStyle "Translucent"; + Alpha 0.4; + } + + action native void A_KSpiritRoam(); + + States + { + Spawn: + SPIR AB 5 A_KSpiritRoam; + Loop; + Death: + SPIR DEFGHI 5; + Stop; + } +} + +class KoraxBolt : Actor +{ + Default + { + Radius 15; + Height 35; + Projectile; + -ACTIVATEPCROSS + -ACTIVATEIMPACT + RenderStyle "Add"; + } + + action native void A_KBolt(); + action native void A_KBoltRaise(); + + States + { + Spawn: + MLFX I 2 Bright; + MLFX J 2 Bright A_KBoltRaise; + MLFX IJKLM 2 Bright A_KBolt; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/mageplayer.txt b/wadsrc/static/zscript/hexen/mageplayer.txt new file mode 100644 index 000000000..33b34633e --- /dev/null +++ b/wadsrc/static/zscript/hexen/mageplayer.txt @@ -0,0 +1,107 @@ +// The mage ----------------------------------------------------------------- + +class MagePlayer : PlayerPawn +{ + Default + { + Health 100; + ReactionTime 0; + PainChance 255; + Radius 16; + Height 64; + Speed 1; + +NOSKIN + +NODAMAGETHRUST + +PLAYERPAWN.NOTHRUSTWHENINVUL + PainSound "PlayerMagePain"; + RadiusDamageFactor 0.25; + Player.JumpZ 9; + Player.Viewheight 48; + Player.SpawnClass "Mage"; + Player.DisplayName "Mage"; + Player.SoundClass "mage"; + Player.ScoreIcon "MAGEFACE"; + Player.InvulnerabilityMode "Reflective"; + Player.HealRadiusType "Mana"; + Player.Hexenarmor 5, 5, 15, 10, 25; + Player.StartItem "MWeapWand"; + Player.ForwardMove 0.88, 0.92; + Player.SideMove 0.875, 0.925; + Player.Portrait "P_MWALK1"; + Player.WeaponSlot 1, "MWeapWand"; + Player.WeaponSlot 2, "MWeapFrost"; + Player.WeaponSlot 3, "MWeapLightning"; + Player.WeaponSlot 4, "MWeapBloodscourge"; + Player.FlechetteType "ArtiPoisonBag2"; + + Player.ColorRange 146, 163; + Player.Colorset 0, "Blue", 146, 163, 161; + Player.ColorsetFile 1, "Red", "TRANTBL7", 0xB3; + Player.ColorsetFile 2, "Gold", "TRANTBL8", 0x8C; + Player.ColorsetFile 3, "Dull Green", "TRANTBL9", 0x41; + Player.ColorsetFile 4, "Green", "TRANTBLA", 0xC9; + Player.ColorsetFile 5, "Gray", "TRANTBLB", 0x30; + Player.ColorsetFile 6, "Brown", "TRANTBLC", 0x72; + Player.ColorsetFile 7, "Purple", "TRANTBLD", 0xEE; + } + + States + { + Spawn: + MAGE A -1; + Stop; + See: + MAGE ABCD 4; + Loop; + Missile: + Melee: + MAGE EF 8; + Goto Spawn; + Pain: + MAGE G 4; + MAGE G 4 A_Pain; + Goto Spawn; + Death: + MAGE H 6; + MAGE I 6 A_PlayerScream; + MAGE JK 6; + MAGE L 6 A_NoBlocking; + MAGE M 6; + MAGE N -1; + Stop; + XDeath: + MAGE O 5 A_PlayerScream; + MAGE P 5; + MAGE R 5 A_NoBlocking; + MAGE STUVW 5; + MAGE X -1; + Stop; + Ice: + MAGE Y 5 A_FreezeDeath; + MAGE Y 1 A_FreezeDeathChunks; + Wait; + Burn: + FDTH E 5 BRIGHT A_PlaySound("*burndeath"); + FDTH F 4 BRIGHT; + FDTH G 5 BRIGHT; + FDTH H 4 BRIGHT A_PlayerScream; + FDTH I 5 BRIGHT; + FDTH J 4 BRIGHT; + FDTH K 5 BRIGHT; + FDTH L 4 BRIGHT; + FDTH M 5 BRIGHT; + FDTH N 4 BRIGHT; + FDTH O 5 BRIGHT; + FDTH P 4 BRIGHT; + FDTH Q 5 BRIGHT; + FDTH R 4 BRIGHT; + FDTH S 5 BRIGHT A_NoBlocking; + FDTH T 4 BRIGHT; + FDTH U 5 BRIGHT; + FDTH V 4 BRIGHT; + ACLO E 35 A_CheckPlayerDone; + Wait; + ACLO E 8; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/pig.txt b/wadsrc/static/zscript/hexen/pig.txt new file mode 100644 index 000000000..8fa446882 --- /dev/null +++ b/wadsrc/static/zscript/hexen/pig.txt @@ -0,0 +1,170 @@ + + +// Snout puff --------------------------------------------------------------- + +class SnoutPuff : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + Renderstyle "Translucent"; + Alpha 0.6; + } + + States + { + Spawn: + FHFX STUVW 4; + Stop; + } +} + + +// Snout -------------------------------------------------------------------- + +class Snout : Weapon +{ + Default + { + Weapon.SelectionOrder 10000; + +WEAPON.DONTBOB + +WEAPON.MELEEWEAPON + Weapon.Kickback 150; + Weapon.YAdjust 10; + } + + action native void A_SnoutAttack (); + + States + { + Ready: + WPIG A 1 A_WeaponReady; + Loop; + Deselect: + WPIG A 1 A_Lower; + Loop; + Select: + WPIG A 1 A_Raise; + Fire: + WPIG A 4 A_SnoutAttack; + WPIG B 8 A_SnoutAttack; + Goto Ready; + Grunt: + WPIG B 8; + Goto Ready; + } +} + + +// Pig player --------------------------------------------------------------- + +class PigPlayer : PlayerPawn native +{ + Default + { + Health 30; + ReactionTime 0; + PainChance 255; + Radius 16; + Height 24; + Speed 1; + +WINDTHRUST + +NOSKIN + -PICKUP + PainSound "PigPain"; + DeathSound "PigDeath"; + Player.JumpZ 6; + Player.Viewheight 28; + Player.ForwardMove 0.96, 0.98; + Player.SideMove 0.95833333, 0.975; + Player.SpawnClass "Pig"; + Player.SoundClass "Pig"; + Player.DisplayName "Pig"; + Player.MorphWeapon "Snout"; + } + + States + { + Spawn: + PIGY A -1; + Stop; + See: + PIGY ABCD 3; + Loop; + Pain: + PIGY D 4 A_PigPain; + Goto Spawn; + Melee: + Missile: + PIGY A 12; + Goto Spawn; + Death: + PIGY E 4 A_Scream; + PIGY F 3 A_NoBlocking; + PIGY G 4; + PIGY H 3; + PIGY IJK 4; + PIGY L -1; + Stop; + Ice: + PIGY M 5 A_FreezeDeath; + PIGY M 1 A_FreezeDeathChunks; + Wait; + } +} + + + +// Pig (non-player) --------------------------------------------------------- + +class Pig : MorphedMonster +{ + Default + { + Health 25; + Painchance 128; + Speed 10; + Radius 12; + Height 22; + Mass 60; + Monster; + -COUNTKILL + +WINDTHRUST + +DONTMORPH + SeeSound "PigActive1"; + PainSound "PigPain"; + DeathSound "PigDeath"; + ActiveSound "PigActive1"; + } + + States + { + Spawn: + PIGY B 10 A_Look; + Loop; + See: + PIGY ABCD 3 A_Chase; + Loop; + Pain: + PIGY D 4 A_PigPain; + Goto See; + Melee: + PIGY A 5 A_FaceTarget; + PIGY A 10 A_CustomMeleeAttack(random[PigAttack](2,3), "PigAttack"); + Goto See; + Death: + PIGY E 4 A_Scream; + PIGY F 3 A_NoBlocking; + PIGY G 4 A_QueueCorpse; + PIGY H 3; + PIGY IJK 4; + PIGY L -1; + Stop; + Ice: + PIGY M 5 A_FreezeDeath; + PIGY M 1 A_FreezeDeathChunks; + Wait; + } +} + From 4aecc4f5657e5e5bc7be31c653078ba61ed07771 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 00:49:13 +0200 Subject: [PATCH 062/255] - more Hexen conversions. --- wadsrc/static/actors/hexen/hexenarmor.txt | 65 - .../static/actors/hexen/hexendecorations.txt | 1396 -------------- wadsrc/static/actors/hexen/hexenkeys.txt | 139 -- .../static/actors/hexen/hexenspecialdecs.txt | 684 ------- wadsrc/static/decorate.txt | 4 - wadsrc/static/zscript.txt | 2 +- wadsrc/static/zscript/hexen/hexenarmor.txt | 77 + .../static/zscript/hexen/hexendecorations.txt | 1705 +++++++++++++++++ wadsrc/static/zscript/hexen/hexenkeys.txt | 175 ++ .../static/zscript/hexen/hexenspecialdecs.txt | 756 ++++++++ 10 files changed, 2714 insertions(+), 2289 deletions(-) delete mode 100644 wadsrc/static/actors/hexen/hexenarmor.txt delete mode 100644 wadsrc/static/actors/hexen/hexendecorations.txt delete mode 100644 wadsrc/static/actors/hexen/hexenkeys.txt delete mode 100644 wadsrc/static/actors/hexen/hexenspecialdecs.txt create mode 100644 wadsrc/static/zscript/hexen/hexenarmor.txt create mode 100644 wadsrc/static/zscript/hexen/hexendecorations.txt create mode 100644 wadsrc/static/zscript/hexen/hexenkeys.txt create mode 100644 wadsrc/static/zscript/hexen/hexenspecialdecs.txt diff --git a/wadsrc/static/actors/hexen/hexenarmor.txt b/wadsrc/static/actors/hexen/hexenarmor.txt deleted file mode 100644 index 53be60fe0..000000000 --- a/wadsrc/static/actors/hexen/hexenarmor.txt +++ /dev/null @@ -1,65 +0,0 @@ - -// Mesh Armor (1) ----------------------------------------------------------- - -ACTOR MeshArmor : HexenArmor -{ - +NOGRAVITY - Health 0 // Armor class - Inventory.Amount 0 - Inventory.PickupMessage "$TXT_ARMOR1" - States - { - Spawn: - AR_1 A -1 - Stop - } -} - -// Falcon Shield (2) -------------------------------------------------------- - -ACTOR FalconShield : HexenArmor -{ - +NOGRAVITY - Health 1 // Armor class - Inventory.Amount 0 - Inventory.PickupMessage "$TXT_ARMOR2" - States - { - Spawn: - AR_2 A -1 - Stop - } -} - -// Platinum Helm (3) -------------------------------------------------------- - -ACTOR PlatinumHelm : HexenArmor -{ - +NOGRAVITY - Health 2 // Armor class - Inventory.Amount 0 - Inventory.PickupMessage "$TXT_ARMOR3" - States - { - Spawn: - AR_3 A -1 - Stop - } -} - -// Amulet of Warding (4) ---------------------------------------------------- - -ACTOR AmuletOfWarding : HexenArmor -{ - +NOGRAVITY - Health 3 // Armor class - Inventory.Amount 0 - Inventory.PickupMessage "$TXT_ARMOR4" - States - { - Spawn: - AR_4 A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/hexen/hexendecorations.txt b/wadsrc/static/actors/hexen/hexendecorations.txt deleted file mode 100644 index 87af4eff5..000000000 --- a/wadsrc/static/actors/hexen/hexendecorations.txt +++ /dev/null @@ -1,1396 +0,0 @@ -ACTOR ZWingedStatue -{ - Radius 10 - Height 62 - +SOLID - States - { - Spawn: - STTW A -1 - Stop - } -} - -ACTOR ZRock1 -{ - Radius 20 - Height 16 - States - { - Spawn: - RCK1 A -1 - Stop - } -} - -ACTOR ZRock2 -{ - Radius 20 - Height 16 - States - { - Spawn: - RCK2 A -1 - Stop - } -} - -ACTOR ZRock3 -{ - Radius 20 - Height 16 - States - { - Spawn: - RCK3 A -1 - Stop - } -} - -ACTOR ZRock4 -{ - Radius 20 - Height 16 - States - { - Spawn: - RCK4 A -1 - Stop - } -} - -ACTOR ZChandelier -{ - Radius 20 - Height 60 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - CDLR ABC 4 - Loop - } -} - -ACTOR ZChandelierUnlit -{ - Radius 20 - Height 60 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - CDLR D -1 - Stop - } -} - -ACTOR ZTreeDead -{ - Radius 10 - Height 96 - +SOLID - States - { - Spawn: - ZTRE A -1 - Stop - } -} - -ACTOR ZTree -{ - Radius 15 - Height 128 - +SOLID - States - { - Spawn: - ZTRE A -1 - Stop - } -} - -ACTOR ZTreeSwamp150 -{ - Radius 10 - Height 150 - +SOLID - States - { - Spawn: - TRES A -1 - Stop - } -} - -ACTOR ZTreeSwamp120 -{ - Radius 10 - Height 120 - +SOLID - States - { - Spawn: - TRE3 A -1 - Stop - } -} - -ACTOR ZStumpBurned -{ - Radius 12 - Height 20 - +SOLID - States - { - Spawn: - STM1 A -1 - Stop - } -} - -ACTOR ZStumpBare -{ - Radius 12 - Height 20 - +SOLID - States - { - Spawn: - STM2 A -1 - Stop - } -} - -ACTOR ZStumpSwamp1 -{ - Radius 20 - Height 16 - States - { - Spawn: - STM3 A -1 - Stop - } -} - -ACTOR ZStumpSwamp2 -{ - Radius 20 - Height 16 - States - { - Spawn: - STM4 A -1 - Stop - } -} - -ACTOR ZShroomLarge1 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH1 A -1 - Stop - } -} - -ACTOR ZShroomLarge2 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH2 A -1 - Stop - } -} - -ACTOR ZShroomLarge3 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH3 A -1 - Stop - } -} - -ACTOR ZShroomSmall1 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH4 A -1 - Stop - } -} - -ACTOR ZShroomSmall2 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH5 A -1 - Stop - } -} - -ACTOR ZShroomSmall3 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH6 A -1 - Stop - } -} - -ACTOR ZShroomSmall4 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH7 A -1 - Stop - } -} - -ACTOR ZShroomSmall5 -{ - Radius 20 - Height 16 - States - { - Spawn: - MSH8 A -1 - Stop - } -} - -ACTOR ZStalagmitePillar -{ - Radius 8 - Height 138 - +SOLID - States - { - Spawn: - SGMP A -1 - Stop - } -} - -ACTOR ZStalagmiteLarge -{ - Radius 8 - Height 48 - +SOLID - States - { - Spawn: - SGM1 A -1 - Stop - } -} - -ACTOR ZStalagmiteMedium -{ - Radius 6 - Height 40 - +SOLID - States - { - Spawn: - SGM2 A -1 - Stop - } -} - -ACTOR ZStalagmiteSmall -{ - Radius 8 - Height 36 - +SOLID - States - { - Spawn: - SGM3 A -1 - Stop - } -} - -ACTOR ZStalactiteLarge -{ - Radius 8 - Height 66 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SLC1 A -1 - Stop - } -} - -ACTOR ZStalactiteMedium -{ - Radius 6 - Height 50 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SLC2 A -1 - Stop - } -} - -ACTOR ZStalactiteSmall -{ - Radius 8 - Height 40 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - SLC3 A -1 - Stop - } -} - -ACTOR ZMossCeiling1 -{ - Radius 20 - Height 20 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - MSS1 A -1 - Stop - } -} - -ACTOR ZMossCeiling2 -{ - Radius 20 - Height 24 - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - MSS2 A -1 - Stop - } -} - -ACTOR ZSwampVine -{ - Radius 8 - Height 52 - +SOLID - States - { - Spawn: - SWMV A -1 - Stop - } -} - -ACTOR ZCorpseKabob -{ - Radius 10 - Height 92 - +SOLID - States - { - Spawn: - CPS1 A -1 - Stop - } -} - -ACTOR ZCorpseSleeping -{ - Radius 20 - Height 16 - States - { - Spawn: - CPS2 A -1 - Stop - } -} - -ACTOR ZTombstoneRIP -{ - Radius 10 - Height 46 - +SOLID - States - { - Spawn: - TMS1 A -1 - Stop - } -} - -ACTOR ZTombstoneShane -{ - Radius 10 - Height 46 - +SOLID - States - { - Spawn: - TMS2 A -1 - Stop - } -} - -ACTOR ZTombstoneBigCross -{ - Radius 10 - Height 46 - +SOLID - States - { - Spawn: - TMS3 A -1 - Stop - } -} - -ACTOR ZTombstoneBrianR -{ - Radius 10 - Height 52 - +SOLID - States - { - Spawn: - TMS4 A -1 - Stop - } -} - -ACTOR ZTombstoneCrossCircle -{ - Radius 10 - Height 52 - +SOLID - States - { - Spawn: - TMS5 A -1 - Stop - } -} - -ACTOR ZTombstoneSmallCross -{ - Radius 8 - Height 46 - +SOLID - States - { - Spawn: - TMS6 A -1 - Stop - } -} - -ACTOR ZTombstoneBrianP -{ - Radius 8 - Height 46 - +SOLID - States - { - Spawn: - TMS7 A -1 - Stop - } -} - -ACTOR ZCorpseHanging -{ - Radius 6 - Height 75 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - CPS3 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleGreenTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - STT2 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleBlueTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - STT3 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleGreenShort -{ - Radius 14 - Height 62 - +SOLID - States - { - Spawn: - STT4 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleBlueShort -{ - Radius 14 - Height 62 - +SOLID - States - { - Spawn: - STT5 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleStripeTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - GAR1 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleDarkRedTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - GAR2 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleRedTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - GAR3 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleTanTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - GAR4 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleRustTall -{ - Radius 14 - Height 108 - +SOLID - States - { - Spawn: - GAR5 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleDarkRedShort -{ - Radius 14 - Height 62 - +SOLID - States - { - Spawn: - GAR6 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleRedShort -{ - Radius 14 - Height 62 - +SOLID - States - { - Spawn: - GAR7 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleTanShort -{ - Radius 14 - Height 62 - +SOLID - States - { - Spawn: - GAR8 A -1 - Stop - } -} - -ACTOR ZStatueGargoyleRustShort -{ - Radius 14 - Height 62 - +SOLID - States - { - Spawn: - GAR9 A -1 - Stop - } -} - -ACTOR ZBannerTattered -{ - Radius 8 - Height 120 - +SOLID - States - { - Spawn: - BNR1 A -1 - Stop - } -} - -ACTOR ZTreeLarge1 -{ - Radius 15 - Height 180 - +SOLID - States - { - Spawn: - TRE4 A -1 - Stop - } -} - -ACTOR ZTreeLarge2 -{ - Radius 15 - Height 180 - +SOLID - States - { - Spawn: - TRE5 A -1 - Stop - } -} - -ACTOR ZTreeGnarled1 -{ - Radius 22 - Height 100 - +SOLID - States - { - Spawn: - TRE6 A -1 - Stop - } -} - -ACTOR ZTreeGnarled2 -{ - Radius 22 - Height 100 - +SOLID - States - { - Spawn: - TRE7 A -1 - Stop - } -} - -ACTOR ZLog -{ - Radius 20 - Height 25 - +SOLID - States - { - Spawn: - LOGG A -1 - Stop - } -} - -ACTOR ZStalactiteIceLarge -{ - Radius 8 - Height 66 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - ICT1 A -1 - Stop - } -} - -ACTOR ZStalactiteIceMedium -{ - Radius 5 - Height 50 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - ICT2 A -1 - Stop - } -} - -ACTOR ZStalactiteIceSmall -{ - Radius 4 - Height 32 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - ICT3 A -1 - Stop - } -} - -ACTOR ZStalactiteIceTiny -{ - Radius 4 - Height 8 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - ICT4 A -1 - Stop - } -} - -ACTOR ZStalagmiteIceLarge -{ - Radius 8 - Height 66 - +SOLID - States - { - Spawn: - ICM1 A -1 - Stop - } -} - -ACTOR ZStalagmiteIceMedium -{ - Radius 5 - Height 50 - +SOLID - States - { - Spawn: - ICM2 A -1 - Stop - } -} - -ACTOR ZStalagmiteIceSmall -{ - Radius 4 - Height 32 - +SOLID - States - { - Spawn: - ICM3 A -1 - Stop - } -} - -ACTOR ZStalagmiteIceTiny -{ - Radius 4 - Height 8 - +SOLID - States - { - Spawn: - ICM4 A -1 - Stop - } -} - -ACTOR ZRockBrown1 -{ - Radius 17 - Height 72 - +SOLID - States - { - Spawn: - RKBL A -1 - Stop - } -} - -ACTOR ZRockBrown2 -{ - Radius 15 - Height 50 - +SOLID - States - { - Spawn: - RKBS A -1 - Stop - } -} - -ACTOR ZRockBlack -{ - Radius 20 - Height 40 - +SOLID - States - { - Spawn: - RKBK A -1 - Stop - } -} - -ACTOR ZRubble1 -{ - Radius 20 - Height 16 - States - { - Spawn: - RBL1 A -1 - Stop - } -} - -ACTOR ZRubble2 -{ - Radius 20 - Height 16 - States - { - Spawn: - RBL2 A -1 - Stop - } -} - -ACTOR ZRubble3 -{ - Radius 20 - Height 16 - States - { - Spawn: - RBL3 A -1 - Stop - } -} - -ACTOR ZVasePillar -{ - Radius 12 - Height 54 - +SOLID - States - { - Spawn: - VASE A -1 - Stop - } -} - -ACTOR ZCorpseLynched -{ - Radius 11 - Height 95 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - CPS4 A -1 - Stop - } -} - -ACTOR ZCandle -{ - Radius 20 - Height 16 - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CNDL ABC 4 Bright - Loop - } -} - -ACTOR ZBarrel -{ - Radius 15 - Height 32 - +SOLID - States - { - Spawn: - ZBAR A -1 - Stop - } -} - -ACTOR ZBucket -{ - Radius 8 - Height 72 - +SOLID - +SPAWNCEILING - +NOGRAVITY - States - { - Spawn: - BCKT A -1 - Stop - } -} - -ACTOR FireThing -{ - Radius 5 - Height 10 - +SOLID - States - { - Spawn: - FSKL A 4 Bright - FSKL B 3 Bright - FSKL C 4 Bright - FSKL D 3 Bright - FSKL E 4 Bright - FSKL F 3 Bright - FSKL G 4 Bright - FSKL H 3 Bright - FSKL I 4 Bright - Loop - } -} - -ACTOR BrassTorch -{ - Radius 6 - Height 35 - +SOLID - States - { - Spawn: - BRTR ABCDEFGHIJKLM 4 Bright - Loop - } -} - -ACTOR ZBlueCandle -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - BCAN ABCDE 5 Bright - Loop - } -} - -ACTOR ZIronMaiden -{ - Radius 12 - Height 60 - +SOLID - States - { - Spawn: - IRON A -1 - Stop - } -} - -ACTOR ZChainBit32 -{ - Radius 4 - Height 32 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS A -1 - Stop - } -} - -ACTOR ZChainBit64 -{ - Radius 4 - Height 64 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS B -1 - Stop - } -} - -ACTOR ZChainEndHeart -{ - Radius 4 - Height 32 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS C -1 - Stop - } -} - -ACTOR ZChainEndHook1 -{ - Radius 4 - Height 32 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS D -1 - Stop - } -} - -ACTOR ZChainEndHook2 -{ - Radius 4 - Height 32 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS E -1 - Stop - } -} - -ACTOR ZChainEndSpike -{ - Radius 4 - Height 32 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS F -1 - Stop - } -} - -ACTOR ZChainEndSkull -{ - Radius 4 - Height 32 - +SPAWNCEILING - +NOGRAVITY - +NOBLOCKMAP - States - { - Spawn: - CHNS G -1 - Stop - } -} - -ACTOR TableShit1 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST1 A -1 - Stop - } -} - -ACTOR TableShit2 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST2 A -1 - Stop - } -} - -ACTOR TableShit3 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST3 A -1 - Stop - } -} - -ACTOR TableShit4 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST4 A -1 - Stop - } -} - -ACTOR TableShit5 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST5 A -1 - Stop - } -} - -ACTOR TableShit6 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST6 A -1 - Stop - } -} - -ACTOR TableShit7 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST7 A -1 - Stop - } -} - -ACTOR TableShit8 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST8 A -1 - Stop - } -} - -ACTOR TableShit9 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST9 A -1 - Stop - } -} - -ACTOR TableShit10 -{ - Radius 20 - Height 16 - +NOBLOCKMAP - States - { - Spawn: - TST0 A -1 - Stop - } -} - -ACTOR TeleSmoke -{ - Radius 20 - Height 16 - +NOGRAVITY - +NOBLOCKMAP - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - TSMK A 4 - TSMK B 3 - TSMK C 4 - TSMK D 3 - TSMK E 4 - TSMK F 3 - TSMK G 4 - TSMK H 3 - TSMK I 4 - TSMK J 3 - TSMK K 4 - TSMK L 3 - TSMK M 4 - TSMK N 3 - TSMK O 4 - TSMK P 3 - TSMK Q 4 - TSMK R 3 - TSMK S 4 - TSMK T 3 - TSMK U 4 - TSMK V 3 - TSMK W 4 - TSMK X 3 - TSMK Y 4 - TSMK Z 3 - Loop - } -} - diff --git a/wadsrc/static/actors/hexen/hexenkeys.txt b/wadsrc/static/actors/hexen/hexenkeys.txt deleted file mode 100644 index b65d59e16..000000000 --- a/wadsrc/static/actors/hexen/hexenkeys.txt +++ /dev/null @@ -1,139 +0,0 @@ - -ACTOR HexenKey : Key -{ - Radius 8 - Height 20 -} - -ACTOR KeySteel : HexenKey -{ - Inventory.Icon KEYSLOT1 - Inventory.PickupMessage "$TXT_KEY_STEEL" - States - { - Spawn: - KEY1 A -1 - Stop - } -} - -ACTOR KeyCave : HexenKey -{ - Inventory.Icon KEYSLOT2 - Inventory.PickupMessage "$TXT_KEY_CAVE" - States - { - Spawn: - KEY2 A -1 - Stop - } -} - -ACTOR KeyAxe : HexenKey -{ - Inventory.Icon KEYSLOT3 - Inventory.PickupMessage "$TXT_KEY_AXE" - States - { - Spawn: - KEY3 A -1 - Stop - } -} - -ACTOR KeyFire : HexenKey -{ - Inventory.Icon KEYSLOT4 - Inventory.PickupMessage "$TXT_KEY_FIRE" - States - { - Spawn: - KEY4 A -1 - Stop - } -} - -ACTOR KeyEmerald : HexenKey -{ - Inventory.Icon KEYSLOT5 - Inventory.PickupMessage "$TXT_KEY_EMERALD" - States - { - Spawn: - KEY5 A -1 - Stop - } -} - -ACTOR KeyDungeon : HexenKey -{ - Inventory.Icon KEYSLOT6 - Inventory.PickupMessage "$TXT_KEY_DUNGEON" - States - { - Spawn: - KEY6 A -1 - Stop - } -} - -ACTOR KeySilver : HexenKey -{ - Inventory.Icon KEYSLOT7 - Inventory.PickupMessage "$TXT_KEY_SILVER" - States - { - Spawn: - KEY7 A -1 - Stop - } -} - -ACTOR KeyRusted : HexenKey -{ - Inventory.Icon KEYSLOT8 - Inventory.PickupMessage "$TXT_KEY_RUSTED" - States - { - Spawn: - KEY8 A -1 - Stop - } -} - -ACTOR KeyHorn : HexenKey -{ - Inventory.Icon KEYSLOT9 - Inventory.PickupMessage "$TXT_KEY_HORN" - States - { - Spawn: - KEY9 A -1 - Stop - } -} - -ACTOR KeySwamp : HexenKey -{ - Inventory.Icon KEYSLOTA - Inventory.PickupMessage "$TXT_KEY_SWAMP" - States - { - Spawn: - KEYA A -1 - Stop - } -} - -ACTOR KeyCastle : HexenKey -{ - Inventory.Icon KEYSLOTB - Inventory.PickupMessage "$TXT_KEY_CASTLE" - States - { - Spawn: - KEYB A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/hexen/hexenspecialdecs.txt b/wadsrc/static/actors/hexen/hexenspecialdecs.txt deleted file mode 100644 index cd5063385..000000000 --- a/wadsrc/static/actors/hexen/hexenspecialdecs.txt +++ /dev/null @@ -1,684 +0,0 @@ - -// Winged Statue (no skull) ------------------------------------------------- - -ACTOR ZWingedStatueNoSkull : SwitchingDecoration -{ - Radius 10 - Height 62 - +SOLID - States - { - Spawn: - STWN A -1 - Stop - Active: - STWN B -1 - Stop - } -} - - -// Gem pedestal ------------------------------------------------------------- - -ACTOR ZGemPedestal : SwitchingDecoration -{ - Radius 10 - Height 40 - +SOLID - States - { - Spawn: - GMPD A -1 - Stop - Active: - GMPD B -1 - Stop - } -} - - -// Tree (destructible) ------------------------------------------------------ - -ACTOR TreeDestructible -{ - Health 70 - Radius 15 - Height 180 - DeathHeight 24 - Mass 0x7fffffff - PainSound "TreeExplode" - DeathSound "TreeBreak" - +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH - States - { - Spawn: - TRDT A -1 - Stop - Death: - TRDT B 5 - TRDT C 5 A_Scream - TRDT DEF 5 - TRDT G -1 - Stop - Burn: - TRDT H 5 Bright A_Pain - TRDT IJKL 5 Bright - TRDT M 5 Bright A_Explode(10, 128) - TRDT N 5 Bright - TRDT OP 5 - TRDT Q -1 - Stop - } -} - - -// Pottery1 ------------------------------------------------------------------ - -ACTOR Pottery1 native -{ - Health 15 - Speed 10 - Height 32 - +SOLID +SHOOTABLE +NOBLOOD +DROPOFF - +SLIDESONWALLS +PUSHABLE +TELESTOMP +CANPASS - +NOICEDEATH - - action native A_PotteryExplode(); - - States - { - Spawn: - POT1 A -1 - Loop - Death: - POT1 A 0 A_PotteryExplode - Stop - } -} - -// Pottery2 ----------------------------------------------------------------- - -ACTOR Pottery2 : Pottery1 -{ - Height 25 - States - { - Spawn: - POT2 A -1 - Stop - } -} - -// Pottery3 ----------------------------------------------------------------- - -ACTOR Pottery3 : Pottery1 -{ - Height 25 - States - { - Spawn: - POT3 A -1 - Stop - } -} - -// Pottery Bit -------------------------------------------------------------- - -ACTOR PotteryBit -{ - Radius 5 - Height 5 - +MISSILE - +NOTELEPORT - +NOICEDEATH - - action native A_PotteryChooseBit(); - action native A_PotteryCheck(); - - States - { - Spawn: - PBIT ABCDE -1 - Stop - Death: - PBIT F 0 A_PotteryChooseBit - Stop - Pottery1: - PBIT F 140 - PBIT F 1 A_PotteryCheck - Stop - Pottery2: - PBIT G 140 - PBIT G 1 A_PotteryCheck - Stop - Pottery3: - PBIT H 140 - PBIT H 1 A_PotteryCheck - Stop - Pottery4: - PBIT I 140 - PBIT I 1 A_PotteryCheck - Stop - Pottery5: - PBIT J 140 - PBIT J 1 A_PotteryCheck - Stop - } -} - - -// Blood pool --------------------------------------------------------------- - -ACTOR BloodPool -{ - States - { - Spawn: - BDPL A -1 - Stop - } -} - - -// Lynched corpse (no heart) ------------------------------------------------ - -ACTOR ZCorpseLynchedNoHeart native -{ - Radius 10 - Height 100 - +SOLID +SPAWNCEILING +NOGRAVITY - - action native A_CorpseBloodDrip(); - - States - { - Spawn: - CPS5 A 140 A_CorpseBloodDrip - Loop - } -} - - -// CorpseBloodDrip ---------------------------------------------------------- - -ACTOR CorpseBloodDrip -{ - Radius 1 - Height 4 - Gravity 0.125 - +MISSILE - +NOICEDEATH - DeathSound "Drip" - States - { - Spawn: - BDRP A -1 - Stop - Death: - BDSH AB 3 - BDSH CD 2 - Stop - } -} - - -// Corpse bit --------------------------------------------------------------- - -ACTOR CorpseBit -{ - Radius 5 - Height 5 - +NOBLOCKMAP - +TELESTOMP - States - { - Spawn: - CPB1 A -1 - Stop - CPB2 A -1 - Stop - CPB3 A -1 - Stop - CPB4 A -1 - Stop - } -} - - -// Corpse (sitting, splatterable) ------------------------------------------- - -ACTOR ZCorpseSitting -{ - Health 30 - Radius 15 - Height 35 - +SOLID +SHOOTABLE +NOBLOOD - +NOICEDEATH - DeathSound "FireDemonDeath" - - action native A_CorpseExplode(); - - States - { - Spawn: - CPS6 A -1 - Stop - Death: - CPS6 A 1 A_CorpseExplode - Stop - } -} - - -// Leaf Spawner ------------------------------------------------------------- - -ACTOR LeafSpawner -{ - +NOBLOCKMAP +NOSECTOR - +INVISIBLE - - action native A_LeafSpawn(); - - States - { - Spawn: - TNT1 A 20 A_LeafSpawn - Loop - } -} - - -// Leaf 1 ------------------------------------------------------------------- - -ACTOR Leaf1 -{ - Radius 2 - Height 4 - Gravity 0.125 - +NOBLOCKMAP +MISSILE - +NOTELEPORT +DONTSPLASH - +NOICEDEATH - - action native A_LeafThrust(); - action native A_LeafCheck(); - - States - { - Spawn: - LEF1 ABC 4 - LEF1 D 4 A_LeafThrust - LEF1 EFG 4 - LEF1 H 4 A_LeafThrust - LEF1 I 4 - LEF1 AB 4 - LEF1 C 4 A_LeafThrust - LEF1 DEF 4 - LEF1 G 4 A_LeafThrust - LEF1 HI 4 - Stop - Death: - LEF3 D 10 A_LeafCheck - Wait - } -} - - -// Leaf 2 ------------------------------------------------------------------- - -ACTOR Leaf2 : Leaf1 -{ - States - { - Spawn: - LEF2 ABC 4 - LEF2 D 4 A_LeafThrust - LEF2 EFG 4 - LEF2 H 4 A_LeafThrust - LEF2 I 4 - LEF2 AB 4 - LEF2 C 4 A_LeafThrust - LEF2 DEF 4 - LEF2 G 4 A_LeafThrust - LEF2 HI 4 - Stop - } -} - - -// Twined torch ------------------------------------------------------------- - -ACTOR ZTwinedTorch : SwitchableDecoration -{ - Radius 10 - Height 64 - +SOLID - States - { - Active: - TWTR A 0 Bright A_PlaySound("Ignite") - Spawn: - TWTR ABCDEFGH 4 Bright - Loop - Inactive: - TWTR I -1 - Stop - } -} - -ACTOR ZTwinedTorchUnlit : ZTwinedTorch -{ - States - { - Spawn: - Goto Super::Inactive - } -} - - -// Wall torch --------------------------------------------------------------- - -ACTOR ZWallTorch : SwitchableDecoration -{ - +NOBLOCKMAP - +NOGRAVITY - +FIXMAPTHINGPOS - Radius 6.5 - States - { - Active: - WLTR A 0 Bright A_PlaySound("Ignite") - Spawn: - WLTR ABCDEFGH 5 Bright - Loop - Inactive: - WLTR I -1 - Stop - } -} - -ACTOR ZWallTorchUnlit : ZWallTorch -{ - States - { - Spawn: - Goto Super::Inactive - } -} - - -// Shrub1 ------------------------------------------------------------------- - -ACTOR ZShrub1 -{ - Radius 8 - Height 24 - Health 20 - Mass 0x7fffffff - +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH - DeathSound "TreeExplode" - States - { - Spawn: - SHB1 A -1 - Stop - Burn: - SHB1 B 7 Bright - SHB1 C 6 Bright A_Scream - SHB1 D 5 Bright - Stop - } -} - - -// Shrub2 ------------------------------------------------------------------- - -ACTOR ZShrub2 -{ - Radius 16 - Height 40 - Health 20 - Mass 0x7fffffff - +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH - DeathSound "TreeExplode" - States - { - Spawn: - SHB2 A -1 - Stop - Burn: - SHB2 B 7 Bright - SHB2 C 6 Bright A_Scream - SHB2 D 5 Bright A_Explode(30, 64) - SHB2 E 5 Bright - Stop - } -} - - -// Fire Bull ---------------------------------------------------------------- - -ACTOR ZFireBull : SwitchableDecoration -{ - Radius 20 - Height 80 - +SOLID - States - { - Active: - FBUL I 4 Bright A_PlaySound("Ignite") - FBUL J 4 Bright - Spawn: - FBUL ABCDEFG 4 Bright - Loop - Inactive: - FBUL JI 4 Bright - FBUL H -1 - Stop - } -} - -ACTOR ZFireBullUnlit : ZFireBull -{ - States - { - Spawn: - Goto Super::Inactive+2 - } -} - - -// Suit of armor ------------------------------------------------------------ - -ACTOR ZSuitOfArmor -{ - Health 60 - Radius 16 - Height 72 - Mass 0x7fffffff - +SOLID +SHOOTABLE +NOBLOOD - +NOICEDEATH - DeathSound "SuitofArmorBreak" - - action native A_SoAExplode(); - - States - { - Spawn: - ZSUI A -1 - Stop - Death: - ZSUI A 1 A_SoAExplode - Stop - } -} - - -// Armor chunk -------------------------------------------------------------- - -ACTOR ZArmorChunk -{ - Radius 4 - Height 8 - States - { - Spawn: - ZSUI B -1 - Stop - ZSUI C -1 - Stop - ZSUI D -1 - Stop - ZSUI E -1 - Stop - ZSUI F -1 - Stop - ZSUI G -1 - Stop - ZSUI H -1 - Stop - ZSUI I -1 - Stop - ZSUI J -1 - Stop - ZSUI K -1 - Stop - } -} - - -// Bell --------------------------------------------------------------------- - -ACTOR ZBell native -{ - Health 5 - Radius 56 - Height 120 - Mass 0x7fffffff - +SOLID +SHOOTABLE +NOBLOOD +NOGRAVITY +SPAWNCEILING - +NOICEDEATH - DeathSound "BellRing" - - action native A_BellReset1(); - action native A_BellReset2(); - - States - { - Spawn: - BBLL F -1 - Stop - Death: - BBLL A 4 A_BellReset1 - BBLL BC 4 - BBLL D 5 A_Scream - BBLL CB 4 - BBLL A 3 - BBLL E 4 - BBLL F 5 - BBLL G 6 A_Scream - BBLL F 5 - BBLL EA 4 - BBLL BC 5 - BBLL D 6 A_Scream - BBLL CB 5 - BBLL A 4 - BBLL EF 5 - BBLL G 7 A_Scream - BBLL FEA 5 - BBLL B 6 - BBLL C 6 - BBLL D 7 A_Scream - BBLL CB 6 - BBLL A 5 - BBLL EF 6 - BBLL G 7 A_Scream - BBLL FEABC 6 - BBLL B 7 - BBLL A 8 - BBLL E 12 - BBLL A 10 - BBLL B 12 - BBLL A 12 - BBLL E 14 - BBLL A 1 A_BellReset2 - Goto Spawn - } -} - - -// "Christmas" Tree --------------------------------------------------------- - -ACTOR ZXmasTree -{ - Radius 11 - Height 130 - Health 20 - Mass 0x7fffffff - +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH - DeathSound "TreeExplode" - States - { - Spawn: - XMAS A -1 - Stop - Burn: - XMAS B 6 Bright - XMAS C 6 Bright A_Scream - XMAS D 5 Bright - XMAS E 5 Bright A_Explode(30, 64) - XMAS F 5 Bright - XMAS G 4 Bright - XMAS H 5 - XMAS I 4 A_NoBlocking - XMAS J 4 - XMAS K -1 - Stop - } -} - -// Cauldron ----------------------------------------------------------------- - -ACTOR ZCauldron : SwitchableDecoration -{ - Radius 12 - Height 26 - +SOLID - States - { - Active: - CDRN B 0 Bright A_PlaySound("Ignite") - Spawn: - CDRN BCDEFGH 4 Bright - Loop - Inactive: - CDRN A -1 - Stop - } -} - -ACTOR ZCauldronUnlit : ZCauldron -{ - States - { - Spawn: - Goto Super::Inactive - } -} - - -// Water Drip --------------------------------------------------------------- - -ACTOR HWaterDrip -{ - +MISSILE - +LOWGRAVITY - +NOTELEPORT - Mass 1 - DeathSound "Drip" - States - { - Spawn: - HWAT A -1 - Stop - } -} - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 450cc37a7..146600f34 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,7 +1,3 @@ -#include "actors/hexen/hexenarmor.txt" -#include "actors/hexen/hexendecorations.txt" -#include "actors/hexen/hexenkeys.txt" -#include "actors/hexen/hexenspecialdecs.txt" #include "actors/hexen/mana.txt" #include "actors/hexen/puzzleitems.txt" #include "actors/hexen/scriptprojectiles.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 787cb661f..50ecf6212 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -93,11 +93,11 @@ zscript/hexen/mageplayer.txt zscript/hexen/pig.txt zscript/hexen/flame.txt zscript/hexen/flies.txt -/* zscript/hexen/hexenarmor.txt zscript/hexen/hexendecorations.txt zscript/hexen/hexenkeys.txt zscript/hexen/hexenspecialdecs.txt +/* zscript/hexen/mana.txt zscript/hexen/puzzleitems.txt zscript/hexen/scriptprojectiles.txt diff --git a/wadsrc/static/zscript/hexen/hexenarmor.txt b/wadsrc/static/zscript/hexen/hexenarmor.txt new file mode 100644 index 000000000..13b674fbf --- /dev/null +++ b/wadsrc/static/zscript/hexen/hexenarmor.txt @@ -0,0 +1,77 @@ + +// Mesh Armor (1) ----------------------------------------------------------- + +class MeshArmor : HexenArmor +{ + Default + { + +NOGRAVITY + Health 0; // Armor class + Inventory.Amount 0; + Inventory.PickupMessage "$TXT_ARMOR1"; + } + States + { + Spawn: + AR_1 A -1; + Stop; + } +} + +// Falcon Shield (2) -------------------------------------------------------- + +class FalconShield : HexenArmor +{ + Default + { + +NOGRAVITY + Health 1; // Armor class + Inventory.Amount 0; + Inventory.PickupMessage "$TXT_ARMOR2"; + } + States + { + Spawn: + AR_2 A -1; + Stop; + } +} + +// Platinum Helm (3) -------------------------------------------------------- + +class PlatinumHelm : HexenArmor +{ + Default + { + +NOGRAVITY + Health 2; // Armor class + Inventory.Amount 0; + Inventory.PickupMessage "$TXT_ARMOR3"; + } + States + { + Spawn: + AR_3 A -1; + Stop; + } +} + +// Amulet of Warding (4) ---------------------------------------------------- + +class AmuletOfWarding : HexenArmor +{ + Default + { + +NOGRAVITY + Health 3; // Armor class + Inventory.Amount 0; + Inventory.PickupMessage "$TXT_ARMOR4"; + } + States + { + Spawn: + AR_4 A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/hexen/hexendecorations.txt b/wadsrc/static/zscript/hexen/hexendecorations.txt new file mode 100644 index 000000000..937034bd8 --- /dev/null +++ b/wadsrc/static/zscript/hexen/hexendecorations.txt @@ -0,0 +1,1705 @@ +class ZWingedStatue : Actor +{ + Default + { + Radius 10; + Height 62; + +SOLID + } + States + { + Spawn: + STTW A -1; + Stop; + } +} + +class ZRock1 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RCK1 A -1; + Stop; + } +} + +class ZRock2 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RCK2 A -1; + Stop; + } +} + +class ZRock3 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RCK3 A -1; + Stop; + } +} + +class ZRock4 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RCK4 A -1; + Stop; + } +} + +class ZChandelier : Actor +{ + Default + { + Radius 20; + Height 60; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + CDLR ABC 4; + Loop; + } +} + +class ZChandelierUnlit : Actor +{ + Default + { + Radius 20; + Height 60; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + CDLR D -1; + Stop; + } +} + +class ZTreeDead : Actor +{ + Default + { + Radius 10; + Height 96; + +SOLID + } + States + { + Spawn: + ZTRE A -1; + Stop; + } +} + +class ZTree : Actor +{ + Default + { + Radius 15; + Height 128; + +SOLID + } + States + { + Spawn: + ZTRE A -1; + Stop; + } +} + +class ZTreeSwamp150 : Actor +{ + Default + { + Radius 10; + Height 150; + +SOLID + } + States + { + Spawn: + TRES A -1; + Stop; + } +} + +class ZTreeSwamp120 : Actor +{ + Default + { + Radius 10; + Height 120; + +SOLID + } + States + { + Spawn: + TRE3 A -1; + Stop; + } +} + +class ZStumpBurned : Actor +{ + Default + { + Radius 12; + Height 20; + +SOLID + } + States + { + Spawn: + STM1 A -1; + Stop; + } +} + +class ZStumpBare : Actor +{ + Default + { + Radius 12; + Height 20; + +SOLID + } + States + { + Spawn: + STM2 A -1; + Stop; + } +} + +class ZStumpSwamp1 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + STM3 A -1; + Stop; + } +} + +class ZStumpSwamp2 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + STM4 A -1; + Stop; + } +} + +class ZShroomLarge1 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH1 A -1; + Stop; + } +} + +class ZShroomLarge2 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH2 A -1; + Stop; + } +} + +class ZShroomLarge3 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH3 A -1; + Stop; + } +} + +class ZShroomSmall1 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH4 A -1; + Stop; + } +} + +class ZShroomSmall2 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH5 A -1; + Stop; + } +} + +class ZShroomSmall3 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH6 A -1; + Stop; + } +} + +class ZShroomSmall4 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH7 A -1; + Stop; + } +} + +class ZShroomSmall5 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + MSH8 A -1; + Stop; + } +} + +class ZStalagmitePillar : Actor +{ + Default + { + Radius 8; + Height 138; + +SOLID + } + States + { + Spawn: + SGMP A -1; + Stop; + } +} + +class ZStalagmiteLarge : Actor +{ + Default + { + Radius 8; + Height 48; + +SOLID + } + States + { + Spawn: + SGM1 A -1; + Stop; + } +} + +class ZStalagmiteMedium : Actor +{ + Default + { + Radius 6; + Height 40; + +SOLID + } + States + { + Spawn: + SGM2 A -1; + Stop; + } +} + +class ZStalagmiteSmall : Actor +{ + Default + { + Radius 8; + Height 36; + +SOLID + } + States + { + Spawn: + SGM3 A -1; + Stop; + } +} + +class ZStalactiteLarge : Actor +{ + Default + { + Radius 8; + Height 66; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SLC1 A -1; + Stop; + } +} + +class ZStalactiteMedium : Actor +{ + Default + { + Radius 6; + Height 50; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SLC2 A -1; + Stop; + } +} + +class ZStalactiteSmall : Actor +{ + Default + { + Radius 8; + Height 40; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + SLC3 A -1; + Stop; + } +} + +class ZMossCeiling1 : Actor +{ + Default + { + Radius 20; + Height 20; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + MSS1 A -1; + Stop; + } +} + +class ZMossCeiling2 : Actor +{ + Default + { + Radius 20; + Height 24; + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + MSS2 A -1; + Stop; + } +} + +class ZSwampVine : Actor +{ + Default + { + Radius 8; + Height 52; + +SOLID + } + States + { + Spawn: + SWMV A -1; + Stop; + } +} + +class ZCorpseKabob : Actor +{ + Default + { + Radius 10; + Height 92; + +SOLID + } + States + { + Spawn: + CPS1 A -1; + Stop; + } +} + +class ZCorpseSleeping : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + CPS2 A -1; + Stop; + } +} + +class ZTombstoneRIP : Actor +{ + Default + { + Radius 10; + Height 46; + +SOLID + } + States + { + Spawn: + TMS1 A -1; + Stop; + } +} + +class ZTombstoneShane : Actor +{ + Default + { + Radius 10; + Height 46; + +SOLID + } + States + { + Spawn: + TMS2 A -1; + Stop; + } +} + +class ZTombstoneBigCross : Actor +{ + Default + { + Radius 10; + Height 46; + +SOLID + } + States + { + Spawn: + TMS3 A -1; + Stop; + } +} + +class ZTombstoneBrianR : Actor +{ + Default + { + Radius 10; + Height 52; + +SOLID + } + States + { + Spawn: + TMS4 A -1; + Stop; + } +} + +class ZTombstoneCrossCircle : Actor +{ + Default + { + Radius 10; + Height 52; + +SOLID + } + States + { + Spawn: + TMS5 A -1; + Stop; + } +} + +class ZTombstoneSmallCross : Actor +{ + Default + { + Radius 8; + Height 46; + +SOLID + } + States + { + Spawn: + TMS6 A -1; + Stop; + } +} + +class ZTombstoneBrianP : Actor +{ + Default + { + Radius 8; + Height 46; + +SOLID + } + States + { + Spawn: + TMS7 A -1; + Stop; + } +} + +class ZCorpseHanging : Actor +{ + Default + { + Radius 6; + Height 75; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + CPS3 A -1; + Stop; + } +} + +class ZStatueGargoyleGreenTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + STT2 A -1; + Stop; + } +} + +class ZStatueGargoyleBlueTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + STT3 A -1; + Stop; + } +} + +class ZStatueGargoyleGreenShort : Actor +{ + Default + { + Radius 14; + Height 62; + +SOLID + } + States + { + Spawn: + STT4 A -1; + Stop; + } +} + +class ZStatueGargoyleBlueShort : Actor +{ + Default + { + Radius 14; + Height 62; + +SOLID + } + States + { + Spawn: + STT5 A -1; + Stop; + } +} + +class ZStatueGargoyleStripeTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + GAR1 A -1; + Stop; + } +} + +class ZStatueGargoyleDarkRedTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + GAR2 A -1; + Stop; + } +} + +class ZStatueGargoyleRedTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + GAR3 A -1; + Stop; + } +} + +class ZStatueGargoyleTanTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + GAR4 A -1; + Stop; + } +} + +class ZStatueGargoyleRustTall : Actor +{ + Default + { + Radius 14; + Height 108; + +SOLID + } + States + { + Spawn: + GAR5 A -1; + Stop; + } +} + +class ZStatueGargoyleDarkRedShort : Actor +{ + Default + { + Radius 14; + Height 62; + +SOLID + } + States + { + Spawn: + GAR6 A -1; + Stop; + } +} + +class ZStatueGargoyleRedShort : Actor +{ + Default + { + Radius 14; + Height 62; + +SOLID + } + States + { + Spawn: + GAR7 A -1; + Stop; + } +} + +class ZStatueGargoyleTanShort : Actor +{ + Default + { + Radius 14; + Height 62; + +SOLID + } + States + { + Spawn: + GAR8 A -1; + Stop; + } +} + +class ZStatueGargoyleRustShort : Actor +{ + Default + { + Radius 14; + Height 62; + +SOLID + } + States + { + Spawn: + GAR9 A -1; + Stop; + } +} + +class ZBannerTattered : Actor +{ + Default + { + Radius 8; + Height 120; + +SOLID + } + States + { + Spawn: + BNR1 A -1; + Stop; + } +} + +class ZTreeLarge1 : Actor +{ + Default + { + Radius 15; + Height 180; + +SOLID + } + States + { + Spawn: + TRE4 A -1; + Stop; + } +} + +class ZTreeLarge2 : Actor +{ + Default + { + Radius 15; + Height 180; + +SOLID + } + States + { + Spawn: + TRE5 A -1; + Stop; + } +} + +class ZTreeGnarled1 : Actor +{ + Default + { + Radius 22; + Height 100; + +SOLID + } + States + { + Spawn: + TRE6 A -1; + Stop; + } +} + +class ZTreeGnarled2 : Actor +{ + Default + { + Radius 22; + Height 100; + +SOLID + } + States + { + Spawn: + TRE7 A -1; + Stop; + } +} + +class ZLog : Actor +{ + Default + { + Radius 20; + Height 25; + +SOLID + } + States + { + Spawn: + LOGG A -1; + Stop; + } +} + +class ZStalactiteIceLarge : Actor +{ + Default + { + Radius 8; + Height 66; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + ICT1 A -1; + Stop; + } +} + +class ZStalactiteIceMedium : Actor +{ + Default + { + Radius 5; + Height 50; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + ICT2 A -1; + Stop; + } +} + +class ZStalactiteIceSmall : Actor +{ + Default + { + Radius 4; + Height 32; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + ICT3 A -1; + Stop; + } +} + +class ZStalactiteIceTiny : Actor +{ + Default + { + Radius 4; + Height 8; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + ICT4 A -1; + Stop; + } +} + +class ZStalagmiteIceLarge : Actor +{ + Default + { + Radius 8; + Height 66; + +SOLID + } + States + { + Spawn: + ICM1 A -1; + Stop; + } +} + +class ZStalagmiteIceMedium : Actor +{ + Default + { + Radius 5; + Height 50; + +SOLID + } + States + { + Spawn: + ICM2 A -1; + Stop; + } +} + +class ZStalagmiteIceSmall : Actor +{ + Default + { + Radius 4; + Height 32; + +SOLID + } + States + { + Spawn: + ICM3 A -1; + Stop; + } +} + +class ZStalagmiteIceTiny : Actor +{ + Default + { + Radius 4; + Height 8; + +SOLID + } + States + { + Spawn: + ICM4 A -1; + Stop; + } +} + +class ZRockBrown1 : Actor +{ + Default + { + Radius 17; + Height 72; + +SOLID + } + States + { + Spawn: + RKBL A -1; + Stop; + } +} + +class ZRockBrown2 : Actor +{ + Default + { + Radius 15; + Height 50; + +SOLID + } + States + { + Spawn: + RKBS A -1; + Stop; + } +} + +class ZRockBlack : Actor +{ + Default + { + Radius 20; + Height 40; + +SOLID + } + States + { + Spawn: + RKBK A -1; + Stop; + } +} + +class ZRubble1 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RBL1 A -1; + Stop; + } +} + +class ZRubble2 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RBL2 A -1; + Stop; + } +} + +class ZRubble3 : Actor +{ + Default + { + Radius 20; + Height 16; + } + States + { + Spawn: + RBL3 A -1; + Stop; + } +} + +class ZVasePillar : Actor +{ + Default + { + Radius 12; + Height 54; + +SOLID + } + States + { + Spawn: + VASE A -1; + Stop; + } +} + +class ZCorpseLynched : Actor +{ + Default + { + Radius 11; + Height 95; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + CPS4 A -1; + Stop; + } +} + +class ZCandle : Actor +{ + Default + { + Radius 20; + Height 16; + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CNDL ABC 4 Bright; + Loop; + } +} + +class ZBarrel : Actor +{ + Default + { + Radius 15; + Height 32; + +SOLID + } + States + { + Spawn: + ZBAR A -1; + Stop; + } +} + +class ZBucket : Actor +{ + Default + { + Radius 8; + Height 72; + +SOLID + +SPAWNCEILING + +NOGRAVITY + } + States + { + Spawn: + BCKT A -1; + Stop; + } +} + +class FireThing : Actor +{ + Default + { + Radius 5; + Height 10; + +SOLID + } + States + { + Spawn: + FSKL A 4 Bright; + FSKL B 3 Bright; + FSKL C 4 Bright; + FSKL D 3 Bright; + FSKL E 4 Bright; + FSKL F 3 Bright; + FSKL G 4 Bright; + FSKL H 3 Bright; + FSKL I 4 Bright; + Loop; + } +} + +class BrassTorch : Actor +{ + Default + { + Radius 6; + Height 35; + +SOLID + } + States + { + Spawn: + BRTR ABCDEFGHIJKLM 4 Bright; + Loop; + } +} + +class ZBlueCandle : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + BCAN ABCDE 5 Bright; + Loop; + } +} + +class ZIronMaiden : Actor +{ + Default + { + Radius 12; + Height 60; + +SOLID + } + States + { + Spawn: + IRON A -1; + Stop; + } +} + +class ZChainBit32 : Actor +{ + Default + { + Radius 4; + Height 32; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS A -1; + Stop; + } +} + +class ZChainBit64 : Actor +{ + Default + { + Radius 4; + Height 64; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS B -1; + Stop; + } +} + +class ZChainEndHeart : Actor +{ + Default + { + Radius 4; + Height 32; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS C -1; + Stop; + } +} + +class ZChainEndHook1 : Actor +{ + Default + { + Radius 4; + Height 32; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS D -1; + Stop; + } +} + +class ZChainEndHook2 : Actor +{ + Default + { + Radius 4; + Height 32; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS E -1; + Stop; + } +} + +class ZChainEndSpike : Actor +{ + Default + { + Radius 4; + Height 32; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS F -1; + Stop; + } +} + +class ZChainEndSkull : Actor +{ + Default + { + Radius 4; + Height 32; + +SPAWNCEILING + +NOGRAVITY + +NOBLOCKMAP + } + States + { + Spawn: + CHNS G -1; + Stop; + } +} + +class TableShit1 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST1 A -1; + Stop; + } +} + +class TableShit2 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST2 A -1; + Stop; + } +} + +class TableShit3 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST3 A -1; + Stop; + } +} + +class TableShit4 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST4 A -1; + Stop; + } +} + +class TableShit5 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST5 A -1; + Stop; + } +} + +class TableShit6 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST6 A -1; + Stop; + } +} + +class TableShit7 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST7 A -1; + Stop; + } +} + +class TableShit8 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST8 A -1; + Stop; + } +} + +class TableShit9 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST9 A -1; + Stop; + } +} + +class TableShit10 : Actor +{ + Default + { + Radius 20; + Height 16; + +NOBLOCKMAP + } + States + { + Spawn: + TST0 A -1; + Stop; + } +} + +class TeleSmoke : Actor +{ + Default + { + Radius 20; + Height 16; + +NOGRAVITY + +NOBLOCKMAP + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + TSMK A 4; + TSMK B 3; + TSMK C 4; + TSMK D 3; + TSMK E 4; + TSMK F 3; + TSMK G 4; + TSMK H 3; + TSMK I 4; + TSMK J 3; + TSMK K 4; + TSMK L 3; + TSMK M 4; + TSMK N 3; + TSMK O 4; + TSMK P 3; + TSMK Q 4; + TSMK R 3; + TSMK S 4; + TSMK T 3; + TSMK U 4; + TSMK V 3; + TSMK W 4; + TSMK X 3; + TSMK Y 4; + TSMK Z 3; + Loop; + } +} + diff --git a/wadsrc/static/zscript/hexen/hexenkeys.txt b/wadsrc/static/zscript/hexen/hexenkeys.txt new file mode 100644 index 000000000..9bf9f426c --- /dev/null +++ b/wadsrc/static/zscript/hexen/hexenkeys.txt @@ -0,0 +1,175 @@ + +class HexenKey : Key +{ + Default + { + Radius 8; + Height 20; + } +} + +class KeySteel : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT1"; + Inventory.PickupMessage "$TXT_KEY_STEEL"; + } + States + { + Spawn: + KEY1 A -1; + Stop; + } +} + +class KeyCave : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT2"; + Inventory.PickupMessage "$TXT_KEY_CAVE"; + } + States + { + Spawn: + KEY2 A -1; + Stop; + } +} + +class KeyAxe : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT3"; + Inventory.PickupMessage "$TXT_KEY_AXE"; + } + States + { + Spawn: + KEY3 A -1; + Stop; + } +} + +class KeyFire : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT4"; + Inventory.PickupMessage "$TXT_KEY_FIRE"; + } + States + { + Spawn: + KEY4 A -1; + Stop; + } +} + +class KeyEmerald : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT5"; + Inventory.PickupMessage "$TXT_KEY_EMERALD"; + } + States + { + Spawn: + KEY5 A -1; + Stop; + } +} + +class KeyDungeon : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT6"; + Inventory.PickupMessage "$TXT_KEY_DUNGEON"; + } + States + { + Spawn: + KEY6 A -1; + Stop; + } +} + +class KeySilver : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT7"; + Inventory.PickupMessage "$TXT_KEY_SILVER"; + } + States + { + Spawn: + KEY7 A -1; + Stop; + } +} + +class KeyRusted : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT8"; + Inventory.PickupMessage "$TXT_KEY_RUSTED"; + } + States + { + Spawn: + KEY8 A -1; + Stop; + } +} + +class KeyHorn : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOT9"; + Inventory.PickupMessage "$TXT_KEY_HORN"; + } + States + { + Spawn: + KEY9 A -1; + Stop; + } +} + +class KeySwamp : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOTA"; + Inventory.PickupMessage "$TXT_KEY_SWAMP"; + } + States + { + Spawn: + KEYA A -1; + Stop; + } +} + +class KeyCastle : HexenKey +{ + Default + { + Inventory.Icon "KEYSLOTB"; + Inventory.PickupMessage "$TXT_KEY_CASTLE"; + } + States + { + Spawn: + KEYB A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/hexen/hexenspecialdecs.txt b/wadsrc/static/zscript/hexen/hexenspecialdecs.txt new file mode 100644 index 000000000..97c6ea41e --- /dev/null +++ b/wadsrc/static/zscript/hexen/hexenspecialdecs.txt @@ -0,0 +1,756 @@ + +// Winged Statue (no skull) ------------------------------------------------- + +class ZWingedStatueNoSkull : SwitchingDecoration +{ + Default + { + Radius 10; + Height 62; + +SOLID + } + States + { + Spawn: + STWN A -1; + Stop; + Active: + STWN B -1; + Stop; + } +} + + +// Gem pedestal ------------------------------------------------------------- + +class ZGemPedestal : SwitchingDecoration +{ + Default + { + Radius 10; + Height 40; + +SOLID + } + States + { + Spawn: + GMPD A -1; + Stop; + Active: + GMPD B -1; + Stop; + } +} + + +// Tree (destructible) ------------------------------------------------------ + +class TreeDestructible : Actor +{ + Default + { + Health 70; + Radius 15; + Height 180; + DeathHeight 24; + Mass 0x7fffffff; + PainSound "TreeExplode"; + DeathSound "TreeBreak"; + +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH + } + States + { + Spawn: + TRDT A -1; + Stop; + Death: + TRDT B 5; + TRDT C 5 A_Scream; + TRDT DEF 5; + TRDT G -1; + Stop; + Burn: + TRDT H 5 Bright A_Pain; + TRDT IJKL 5 Bright; + TRDT M 5 Bright A_Explode(10, 128); + TRDT N 5 Bright; + TRDT OP 5; + TRDT Q -1; + Stop; + } +} + + +// Pottery1 ------------------------------------------------------------------ + +class Pottery1 : Actor native +{ + Default + { + Health 15; + Speed 10; + Height 32; + +SOLID +SHOOTABLE +NOBLOOD +DROPOFF + +SLIDESONWALLS +PUSHABLE +TELESTOMP +CANPASS + +NOICEDEATH + } + + action native void A_PotteryExplode(); + + States + { + Spawn: + POT1 A -1; + Loop; + Death: + POT1 A 0 A_PotteryExplode; + Stop; + } +} + +// Pottery2 ----------------------------------------------------------------- + +class Pottery2 : Pottery1 +{ + Default + { + Height 25; + } + States + { + Spawn: + POT2 A -1; + Stop; + } +} + +// Pottery3 ----------------------------------------------------------------- + +class Pottery3 : Pottery1 +{ + Default + { + Height 25; + } + States + { + Spawn: + POT3 A -1; + Stop; + } +} + +// Pottery Bit -------------------------------------------------------------- + +class PotteryBit : Actor +{ + Default + { + Radius 5; + Height 5; + +MISSILE + +NOTELEPORT + +NOICEDEATH + } + + action native void A_PotteryChooseBit(); + action native void A_PotteryCheck(); + + States + { + Spawn: + PBIT ABCDE -1; + Stop; + Death: + PBIT F 0 A_PotteryChooseBit; + Stop; + Pottery1: + PBIT F 140; + PBIT F 1 A_PotteryCheck; + Stop; + Pottery2: + PBIT G 140; + PBIT G 1 A_PotteryCheck; + Stop; + Pottery3: + PBIT H 140; + PBIT H 1 A_PotteryCheck; + Stop; + Pottery4: + PBIT I 140; + PBIT I 1 A_PotteryCheck; + Stop; + Pottery5: + PBIT J 140; + PBIT J 1 A_PotteryCheck; + Stop; + } +} + + +// Blood pool --------------------------------------------------------------- + +class BloodPool : Actor +{ + States + { + Spawn: + BDPL A -1; + Stop; + } +} + + +// Lynched corpse (no heart) ------------------------------------------------ + +class ZCorpseLynchedNoHeart : Actor native +{ + Default + { + Radius 10; + Height 100; + +SOLID +SPAWNCEILING +NOGRAVITY + } + + action native void A_CorpseBloodDrip(); + + States + { + Spawn: + CPS5 A 140 A_CorpseBloodDrip; + Loop; + } +} + + +// CorpseBloodDrip ---------------------------------------------------------- + +class CorpseBloodDrip : Actor +{ + Default + { + Radius 1; + Height 4; + Gravity 0.125; + +MISSILE + +NOICEDEATH + DeathSound "Drip"; + } + States + { + Spawn: + BDRP A -1; + Stop; + Death: + BDSH AB 3; + BDSH CD 2; + Stop; + } +} + + +// Corpse bit --------------------------------------------------------------- + +class CorpseBit : Actor +{ + Default + { + Radius 5; + Height 5; + +NOBLOCKMAP + +TELESTOMP + } + States + { + Spawn: + CPB1 A -1; + Stop; + CPB2 A -1; + Stop; + CPB3 A -1; + Stop; + CPB4 A -1; + Stop; + } +} + + +// Corpse (sitting, splatterable) ------------------------------------------- + +class ZCorpseSitting : Actor +{ + Default + { + Health 30; + Radius 15; + Height 35; + +SOLID +SHOOTABLE +NOBLOOD + +NOICEDEATH + DeathSound "FireDemonDeath"; + } + + action native void A_CorpseExplode(); + + States + { + Spawn: + CPS6 A -1; + Stop; + Death: + CPS6 A 1 A_CorpseExplode; + Stop; + } +} + + +// Leaf Spawner ------------------------------------------------------------- + +class LeafSpawner : Actor +{ + Default + { + +NOBLOCKMAP +NOSECTOR + +INVISIBLE + } + + action native void A_LeafSpawn(); + + States + { + Spawn: + TNT1 A 20 A_LeafSpawn; + Loop; + } +} + + +// Leaf 1 ------------------------------------------------------------------- + +class Leaf1 : Actor +{ + Default + { + Radius 2; + Height 4; + Gravity 0.125; + +NOBLOCKMAP +MISSILE + +NOTELEPORT +DONTSPLASH + +NOICEDEATH + } + + action native void A_LeafThrust(); + action native void A_LeafCheck(); + + States + { + Spawn: + LEF1 ABC 4; + LEF1 D 4 A_LeafThrust; + LEF1 EFG 4; + LEF1 H 4 A_LeafThrust; + LEF1 I 4; + LEF1 AB 4; + LEF1 C 4 A_LeafThrust; + LEF1 DEF 4; + LEF1 G 4 A_LeafThrust; + LEF1 HI 4; + Stop; + Death: + LEF3 D 10 A_LeafCheck; + Wait; + } +} + + +// Leaf 2 ------------------------------------------------------------------- + +class Leaf2 : Leaf1 +{ + States + { + Spawn: + LEF2 ABC 4; + LEF2 D 4 A_LeafThrust; + LEF2 EFG 4; + LEF2 H 4 A_LeafThrust; + LEF2 I 4; + LEF2 AB 4; + LEF2 C 4 A_LeafThrust; + LEF2 DEF 4; + LEF2 G 4 A_LeafThrust; + LEF2 HI 4; + Stop; + } +} + + +// Twined torch ------------------------------------------------------------- + +class ZTwinedTorch : SwitchableDecoration +{ + Default + { + Radius 10; + Height 64; + +SOLID + } + States + { + Active: + TWTR A 0 Bright A_PlaySound("Ignite"); + Spawn: + TWTR ABCDEFGH 4 Bright; + Loop; + Inactive: + TWTR I -1; + Stop; + } +} + +class ZTwinedTorchUnlit : ZTwinedTorch +{ + States + { + Spawn: + Goto Super::Inactive; + } +} + + +// Wall torch --------------------------------------------------------------- + +class ZWallTorch : SwitchableDecoration +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +FIXMAPTHINGPOS + Radius 6.5; + } + States + { + Active: + WLTR A 0 Bright A_PlaySound("Ignite"); + Spawn: + WLTR ABCDEFGH 5 Bright; + Loop; + Inactive: + WLTR I -1; + Stop; + } +} + +class ZWallTorchUnlit : ZWallTorch +{ + States + { + Spawn: + Goto Super::Inactive; + } +} + + +// Shrub1 ------------------------------------------------------------------- + +class ZShrub1 : Actor +{ + Default + { + Radius 8; + Height 24; + Health 20; + Mass 0x7fffffff; + +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH + DeathSound "TreeExplode"; + } + States + { + Spawn: + SHB1 A -1; + Stop; + Burn: + SHB1 B 7 Bright; + SHB1 C 6 Bright A_Scream; + SHB1 D 5 Bright; + Stop; + } +} + + +// Shrub2 ------------------------------------------------------------------- + +class ZShrub2 : Actor +{ + Default + { + Radius 16; + Height 40; + Health 20; + Mass 0x7fffffff; + +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH + DeathSound "TreeExplode"; + } + States + { + Spawn: + SHB2 A -1; + Stop; + Burn: + SHB2 B 7 Bright; + SHB2 C 6 Bright A_Scream; + SHB2 D 5 Bright A_Explode(30, 64); + SHB2 E 5 Bright; + Stop; + } +} + + +// Fire Bull ---------------------------------------------------------------- + +class ZFireBull : SwitchableDecoration +{ + Default + { + Radius 20; + Height 80; + +SOLID + } + States + { + Active: + FBUL I 4 Bright A_PlaySound("Ignite"); + FBUL J 4 Bright; + Spawn: + FBUL ABCDEFG 4 Bright; + Loop; + Inactive: + FBUL JI 4 Bright; + FBUL H -1; + Stop; + } +} + +class ZFireBullUnlit : ZFireBull +{ + States + { + Spawn: + Goto Super::Inactive+2; + } +} + + +// Suit of armor ------------------------------------------------------------ + +class ZSuitOfArmor : Actor +{ + Default + { + Health 60; + Radius 16; + Height 72; + Mass 0x7fffffff; + +SOLID +SHOOTABLE +NOBLOOD + +NOICEDEATH + DeathSound "SuitofArmorBreak"; + } + + action native void A_SoAExplode(); + + States + { + Spawn: + ZSUI A -1; + Stop; + Death: + ZSUI A 1 A_SoAExplode; + Stop; + } +} + + +// Armor chunk -------------------------------------------------------------- + +class ZArmorChunk : Actor +{ + Default + { + Radius 4; + Height 8; + } + States + { + Spawn: + ZSUI B -1; + Stop; + ZSUI C -1; + Stop; + ZSUI D -1; + Stop; + ZSUI E -1; + Stop; + ZSUI F -1; + Stop; + ZSUI G -1; + Stop; + ZSUI H -1; + Stop; + ZSUI I -1; + Stop; + ZSUI J -1; + Stop; + ZSUI K -1; + Stop; + } +} + + +// Bell --------------------------------------------------------------------- + +class ZBell : Actor native +{ + Default + { + Health 5; + Radius 56; + Height 120; + Mass 0x7fffffff; + +SOLID +SHOOTABLE +NOBLOOD +NOGRAVITY +SPAWNCEILING + +NOICEDEATH + DeathSound "BellRing"; + } + + action native void A_BellReset1(); + action native void A_BellReset2(); + + States + { + Spawn: + BBLL F -1; + Stop; + Death: + BBLL A 4 A_BellReset1; + BBLL BC 4; + BBLL D 5 A_Scream; + BBLL CB 4; + BBLL A 3; + BBLL E 4; + BBLL F 5; + BBLL G 6 A_Scream; + BBLL F 5; + BBLL EA 4; + BBLL BC 5; + BBLL D 6 A_Scream; + BBLL CB 5; + BBLL A 4; + BBLL EF 5; + BBLL G 7 A_Scream; + BBLL FEA 5; + BBLL B 6; + BBLL C 6; + BBLL D 7 A_Scream; + BBLL CB 6; + BBLL A 5; + BBLL EF 6; + BBLL G 7 A_Scream; + BBLL FEABC 6; + BBLL B 7; + BBLL A 8; + BBLL E 12; + BBLL A 10; + BBLL B 12; + BBLL A 12; + BBLL E 14; + BBLL A 1 A_BellReset2; + Goto Spawn; + } +} + + +// "Christmas" Tree --------------------------------------------------------- + +class ZXmasTree : Actor +{ + Default + { + Radius 11; + Height 130; + Health 20; + Mass 0x7fffffff; + +SOLID +SHOOTABLE +NOBLOOD +NOICEDEATH + DeathSound "TreeExplode"; + } + States + { + Spawn: + XMAS A -1; + Stop; + Burn: + XMAS B 6 Bright; + XMAS C 6 Bright A_Scream; + XMAS D 5 Bright; + XMAS E 5 Bright A_Explode(30, 64); + XMAS F 5 Bright; + XMAS G 4 Bright; + XMAS H 5; + XMAS I 4 A_NoBlocking; + XMAS J 4; + XMAS K -1; + Stop; + } +} + +// Cauldron ----------------------------------------------------------------- + +class ZCauldron : SwitchableDecoration +{ + Default + { + Radius 12; + Height 26; + +SOLID + } + States + { + Active: + CDRN B 0 Bright A_PlaySound("Ignite"); + Spawn: + CDRN BCDEFGH 4 Bright; + Loop; + Inactive: + CDRN A -1; + Stop; + } +} + +class ZCauldronUnlit : ZCauldron +{ + States + { + Spawn: + Goto Super::Inactive; + } +} + + +// Water Drip --------------------------------------------------------------- + +class HWaterDrip : Actor +{ + Default + { + +MISSILE + +NOTELEPORT + Gravity 0.125; + Mass 1; + DeathSound "Drip"; + } + States + { + Spawn: + HWAT A -1; + Stop; + } +} + From 1652c02a08337fec5281ddbbbce6b1bf1ae5fd8b Mon Sep 17 00:00:00 2001 From: Marisa Heit Date: Mon, 17 Oct 2016 22:37:49 -0500 Subject: [PATCH 063/255] Add unsigned division opcodes to the VM --- src/scripting/vm/vmexec.h | 50 +++++++++++++++++++++++++++++++++++++++ src/scripting/vm/vmops.h | 10 ++++++-- 2 files changed, 58 insertions(+), 2 deletions(-) diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 8f8a21295..9dbea7c51 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -813,6 +813,31 @@ begin: reg.d[a] = konstd[B] / reg.d[C]; NEXTOP; + OP(DIVU_RR): + ASSERTD(a); ASSERTD(B); ASSERTD(C); + if (reg.d[C] == 0) + { + THROW(X_DIVISION_BY_ZERO); + } + reg.d[a] = int((unsigned)reg.d[B] / (unsigned)reg.d[C]); + NEXTOP; + OP(DIVU_RK): + ASSERTD(a); ASSERTD(B); ASSERTKD(C); + if (konstd[C] == 0) + { + THROW(X_DIVISION_BY_ZERO); + } + reg.d[a] = int((unsigned)reg.d[B] / (unsigned)konstd[C]); + NEXTOP; + OP(DIVU_KR): + ASSERTD(a); ASSERTKD(B); ASSERTD(C); + if (reg.d[C] == 0) + { + THROW(X_DIVISION_BY_ZERO); + } + reg.d[a] = int((unsigned)konstd[B] / (unsigned)reg.d[C]); + NEXTOP; + OP(MOD_RR): ASSERTD(a); ASSERTD(B); ASSERTD(C); if (reg.d[C] == 0) @@ -838,6 +863,31 @@ begin: reg.d[a] = konstd[B] % reg.d[C]; NEXTOP; + OP(MODU_RR): + ASSERTD(a); ASSERTD(B); ASSERTD(C); + if (reg.d[C] == 0) + { + THROW(X_DIVISION_BY_ZERO); + } + reg.d[a] = int((unsigned)reg.d[B] % (unsigned)reg.d[C]); + NEXTOP; + OP(MODU_RK): + ASSERTD(a); ASSERTD(B); ASSERTKD(C); + if (konstd[C] == 0) + { + THROW(X_DIVISION_BY_ZERO); + } + reg.d[a] = int((unsigned)reg.d[B] % (unsigned)konstd[C]); + NEXTOP; + OP(MODU_KR): + ASSERTD(a); ASSERTKD(B); ASSERTD(C); + if (reg.d[C] == 0) + { + THROW(X_DIVISION_BY_ZERO); + } + reg.d[a] = int((unsigned)konstd[B] % (unsigned)reg.d[C]); + NEXTOP; + OP(AND_RR): ASSERTD(a); ASSERTD(B); ASSERTD(C); reg.d[a] = reg.d[B] & reg.d[C]; diff --git a/src/scripting/vm/vmops.h b/src/scripting/vm/vmops.h index 39d224f5c..1b34dcc0f 100644 --- a/src/scripting/vm/vmops.h +++ b/src/scripting/vm/vmops.h @@ -115,12 +115,18 @@ xx(SUB_RK, sub, RIRIKI), xx(SUB_KR, sub, RIKIRI), xx(MUL_RR, mul, RIRIRI), // dA = dB * dkC xx(MUL_RK, mul, RIRIKI), -xx(DIV_RR, div, RIRIRI), // dA = dkB / dkC +xx(DIV_RR, div, RIRIRI), // dA = dkB / dkC (signed) xx(DIV_RK, div, RIRIKI), xx(DIV_KR, div, RIKIRI), -xx(MOD_RR, mod, RIRIRI), // dA = dkB % dkC +xx(DIVU_RR, divu, RIRIRI), // dA = dkB / dkC (unsigned) +xx(DIVU_RK, divu, RIRIKI), +xx(DIVU_KR, divu, RIKIRI), +xx(MOD_RR, mod, RIRIRI), // dA = dkB % dkC (signed) xx(MOD_RK, mod, RIRIKI), xx(MOD_KR, mod, RIKIRI), +xx(MODU_RR, modu, RIRIRI), // dA = dkB % dkC (unsigned) +xx(MODU_RK, modu, RIRIKI), +xx(MODU_KR, modu, RIKIRI), xx(AND_RR, and, RIRIRI), // dA = dB & dkC xx(AND_RK, and, RIRIKI), xx(OR_RR, or, RIRIRI), // dA = dB | dkC From 61cc7dbb2907e148c04b4bc24da48976425c773d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 10:09:02 +0200 Subject: [PATCH 064/255] - another batch of Hexen items converted. - fixed parsing of named damage types and pain chances. --- src/scripting/zscript/zcc_compile.cpp | 9 +- wadsrc/static/actors/hexen/centaur.txt | 186 -------- wadsrc/static/actors/hexen/demons.txt | 385 ----------------- wadsrc/static/actors/hexen/ettin.txt | 106 ----- wadsrc/static/actors/hexen/mana.txt | 87 ---- wadsrc/static/actors/hexen/puzzleitems.txt | 287 ------------ .../static/actors/hexen/scriptprojectiles.txt | 123 ------ wadsrc/static/actors/hexen/speedboots.txt | 18 - wadsrc/static/decorate.txt | 7 - wadsrc/static/zscript.txt | 2 +- wadsrc/static/zscript/hexen/centaur.txt | 204 +++++++++ wadsrc/static/zscript/hexen/demons.txt | 408 ++++++++++++++++++ wadsrc/static/zscript/hexen/ettin.txt | 115 +++++ wadsrc/static/zscript/hexen/mana.txt | 99 +++++ wadsrc/static/zscript/hexen/puzzleitems.txt | 338 +++++++++++++++ .../zscript/hexen/scriptprojectiles.txt | 141 ++++++ wadsrc/static/zscript/hexen/speedboots.txt | 21 + 17 files changed, 1332 insertions(+), 1204 deletions(-) delete mode 100644 wadsrc/static/actors/hexen/centaur.txt delete mode 100644 wadsrc/static/actors/hexen/demons.txt delete mode 100644 wadsrc/static/actors/hexen/ettin.txt delete mode 100644 wadsrc/static/actors/hexen/mana.txt delete mode 100644 wadsrc/static/actors/hexen/puzzleitems.txt delete mode 100644 wadsrc/static/actors/hexen/scriptprojectiles.txt delete mode 100644 wadsrc/static/actors/hexen/speedboots.txt create mode 100644 wadsrc/static/zscript/hexen/centaur.txt create mode 100644 wadsrc/static/zscript/hexen/demons.txt create mode 100644 wadsrc/static/zscript/hexen/ettin.txt create mode 100644 wadsrc/static/zscript/hexen/mana.txt create mode 100644 wadsrc/static/zscript/hexen/puzzleitems.txt create mode 100644 wadsrc/static/zscript/hexen/scriptprojectiles.txt create mode 100644 wadsrc/static/zscript/hexen/speedboots.txt diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 39597c513..43219acb1 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1554,7 +1554,7 @@ const char *ZCCCompiler::GetString(ZCC_Expression *expr, bool silent) { if (expr->Type == TypeError) { - return 0; + return nullptr; } else if (expr->Type->IsKindOf(RUNTIME_CLASS(PString))) { @@ -1568,7 +1568,7 @@ const char *ZCCCompiler::GetString(ZCC_Expression *expr, bool silent) else { if (!silent) Error(expr, "Cannot convert to string"); - return 0; + return nullptr; } } @@ -1631,7 +1631,7 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper conv.d = GetDouble(exp); break; - case 'Z': // an optional string. Does not allow any numerical value. + case 'Z': // an optional string. Does not allow any numeric value. if (!GetString(exp, true)) { // apply this expression to the next argument on the list. @@ -1640,7 +1640,8 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper p++; continue; } - // fall through + conv.s = GetString(exp); + break; case 'C': // this parser accepts colors only in string form. pref.i = 1; diff --git a/wadsrc/static/actors/hexen/centaur.txt b/wadsrc/static/actors/hexen/centaur.txt deleted file mode 100644 index d036566bd..000000000 --- a/wadsrc/static/actors/hexen/centaur.txt +++ /dev/null @@ -1,186 +0,0 @@ -// Centaur ------------------------------------------------------------------ - -ACTOR Centaur -{ - Health 200 - Painchance 135 - Speed 13 - Height 64 - Mass 120 - Monster - +FLOORCLIP - +TELESTOMP - +SHIELDREFLECT - SeeSound "CentaurSight" - AttackSound "CentaurAttack" - PainSound "CentaurPain" - DeathSound "CentaurDeath" - ActiveSound "CentaurActive" - HowlSound "PuppyBeat" - Obituary "$OB_CENTAUR" - DamageFactor "Electric", 3 - States - { - Spawn: - CENT AB 10 A_Look - Loop - See: - CENT ABCD 4 A_Chase - Loop - Pain: - CENT G 6 A_Pain - CENT G 6 A_SetReflectiveInvulnerable - CENT EEE 15 A_CentaurDefend - CENT E 1 A_UnsetReflectiveInvulnerable - Goto See - Melee: - CENT H 5 A_FaceTarget - CENT I 4 A_FaceTarget - CENT J 7 A_CustomMeleeAttack(random[CentaurAttack](3,9)) - Goto See - Death: - CENT K 4 - CENT L 4 A_Scream - CENT MN 4 - CENT O 4 A_NoBlocking - CENT PQ 4 - CENT R 4 A_QueueCorpse - CENT S 4 - CENT T -1 - Stop - XDeath: - CTXD A 4 - CTXD B 4 A_NoBlocking - CTXD C 0 A_SpawnItemEx("CentaurSword", 0, 0, 45, - 1 + random[CentaurDrop](-128,127)*0.03125, - 1 + random[CentaurDrop](-128,127)*0.03125, - 8 + random[CentaurDrop](0,255)*0.015625, 270) - CTXD C 4 A_SpawnItemEx("CentaurShield", 0, 0, 45, - 1 + random[CentaurDrop](-128,127)*0.03125, - 1 + random[CentaurDrop](-128,127)*0.03125, - 8 + random[CentaurDrop](0,255)*0.015625, 90) - CTXD D 3 A_Scream - CTXD E 4 A_QueueCorpse - CTXD F 3 - CTXD G 4 - CTXD H 3 - CTXD I 4 - CTXD J 3 - CTXD K -1 - Ice: - CENT U 5 A_FreezeDeath - CENT U 1 A_FreezeDeathChunks - Wait - } -} - -// Centaur Leader ----------------------------------------------------------- - -ACTOR CentaurLeader : Centaur -{ - Health 250 - PainChance 96 - Speed 10 - Obituary "$OB_SLAUGHTAUR" - HitObituary "$OB_SLAUGHTAURHIT" - States - { - Missile: - CENT E 10 A_FaceTarget - CENT F 8 Bright A_CustomMissile("CentaurFX", 45, 0, 0, CMF_AIMOFFSET) - CENT E 10 A_FaceTarget - CENT F 8 Bright A_CustomMissile("CentaurFX", 45, 0, 0, CMF_AIMOFFSET) - Goto See - } -} - -// Mashed centaur ----------------------------------------------------------- -// -// The mashed centaur is only placed through ACS. Nowhere in the game source -// is it ever referenced. - -ACTOR CentaurMash : Centaur -{ - +NOBLOOD - +BLASTED - -TELESTOMP - +NOICEDEATH - RenderStyle Translucent - Alpha 0.4 - States - { - Death: - XDeath: - Ice: - Stop - } -} - -// Centaur projectile ------------------------------------------------------- - -ACTOR CentaurFX -{ - Speed 20 - Damage 4 - Projectile - +SPAWNSOUNDSOURCE - RenderStyle Add - SeeSound "CentaurLeaderAttack" - DeathSound "CentaurMissileExplode" - States - { - Spawn: - CTFX A -1 Bright - Stop - Death: - CTFX B 4 Bright - CTFX C 3 Bright - CTFX D 4 Bright - CTFX E 3 Bright - CTFX F 2 Bright - Stop - } -} - -// Centaur shield (debris) -------------------------------------------------- - -ACTOR CentaurShield -{ - +DROPOFF - +CORPSE - +NOTELEPORT - States - { - Spawn: - CTDP ABCDEF 3 - Goto Spawn+2 - Crash: - CTDP G 4 - CTDP H 4 A_QueueCorpse - CTDP I 4 - CTDP J -1 - Stop - } -} - -// Centaur sword (debris) --------------------------------------------------- - -ACTOR CentaurSword -{ - +DROPOFF - +CORPSE - +NOTELEPORT - States - { - Spawn: - CTDP KLMNOPQ 3 - Goto Spawn+2 - Crash: - CTDP R 4 - CTDP S 4 A_QueueCorpse - CTDP T -1 - Stop - } -} - - diff --git a/wadsrc/static/actors/hexen/demons.txt b/wadsrc/static/actors/hexen/demons.txt deleted file mode 100644 index 39da26e1d..000000000 --- a/wadsrc/static/actors/hexen/demons.txt +++ /dev/null @@ -1,385 +0,0 @@ - -// Demon, type 1 (green, like D'Sparil's) ----------------------------------- - -ACTOR Demon1 -{ - Health 250 - Painchance 50 - Speed 13 - Radius 32 - Height 64 - Mass 220 - Monster - +TELESTOMP - +FLOORCLIP - SeeSound "DemonSight" - AttackSound "DemonAttack" - PainSound "DemonPain" - DeathSound "DemonDeath" - ActiveSound "DemonActive" - Obituary "$OB_DEMON1" - const int ChunkFlags = SXF_TRANSFERTRANSLATION | SXF_ABSOLUTEVELOCITY; - States - { - Spawn: - DEMN AA 10 A_Look - Loop - See: - DEMN ABCD 4 A_Chase - Loop - Pain: - DEMN E 4 - DEMN E 4 A_Pain - Goto See - Melee: - DEMN E 6 A_FaceTarget - DEMN F 8 A_FaceTarget - DEMN G 6 A_CustomMeleeAttack(random[DemonAttack1](1,8)*2) - Goto See - Missile: - DEMN E 5 A_FaceTarget - DEMN F 6 A_FaceTarget - DEMN G 5 A_CustomMissile("Demon1FX1", 62, 0) - Goto See - Death: - DEMN HI 6 - DEMN J 6 A_Scream - DEMN K 6 A_NoBlocking - DEMN L 6 A_QueueCorpse - DEMN MNO 6 - DEMN P -1 - Stop - XDeath: - DEMN H 6 - DEMN I 0 A_SpawnItemEx("Demon1Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags) - DEMN I 0 A_SpawnItemEx("Demon1Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - DEMN I 0 A_SpawnItemEx("Demon1Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - DEMN I 0 A_SpawnItemEx("Demon1Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - DEMN I 6 A_SpawnItemEx("Demon1Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - Goto Death+2 - Ice: - DEMN Q 5 A_FreezeDeath - DEMN Q 1 A_FreezeDeathChunks - Wait - } -} - -// Demon, type 1, mashed ---------------------------------------------------- - -ACTOR Demon1Mash : Demon1 -{ - +NOBLOOD - +BLASTED - -TELESTOMP - +NOICEDEATH - RenderStyle Translucent - Alpha 0.4 - States - { - Death: - XDeath: - Ice: - Stop - } -} - -// Demon chunk, base class -------------------------------------------------- - -ACTOR DemonChunk -{ - Radius 5 - Height 5 - +NOBLOCKMAP - +DROPOFF - +MISSILE - +CORPSE - +FLOORCLIP - +NOTELEPORT -} - -// Demon, type 1, chunk 1 --------------------------------------------------- - -ACTOR Demon1Chunk1 : DemonChunk -{ - States - { - Spawn: - DEMA A 4 - DEMA A 10 A_QueueCorpse - DEMA A 20 - Wait - Death: - DEMA A -1 - Stop - } -} - -// Demon, type 1, chunk 2 --------------------------------------------------- - -ACTOR Demon1Chunk2 : DemonChunk -{ - States - { - Spawn: - DEMB A 4 - DEMB A 10 A_QueueCorpse - DEMB A 20 - Wait - Death: - DEMB A -1 - Stop - } -} - -ACTOR Demon1Chunk3 : DemonChunk -{ - States - { - Spawn: - DEMC A 4 - DEMC A 10 A_QueueCorpse - DEMC A 20 - Wait - Death: - DEMC A -1 - Stop - } -} - -// Demon, type 1, chunk 4 --------------------------------------------------- - -ACTOR Demon1Chunk4 : DemonChunk -{ - States - { - Spawn: - DEMD A 4 - DEMD A 10 A_QueueCorpse - DEMD A 20 - Wait - Death: - DEMD A -1 - Stop - } -} - -// Demon, type 1, chunk 5 --------------------------------------------------- - -ACTOR Demon1Chunk5 : DemonChunk -{ - States - { - Spawn: - DEME A 4 - DEME A 10 A_QueueCorpse - DEME A 20 - Wait - Death: - DEME A -1 - Stop - } -} - -// Demon, type 1, projectile ------------------------------------------------ - -ACTOR Demon1FX1 -{ - Speed 15 - Radius 10 - Height 6 - Damage 5 - DamageType Fire - Projectile - +SPAWNSOUNDSOURCE - RenderStyle Add - SeeSound "DemonMissileFire" - DeathSound "DemonMissileExplode" - States - { - Spawn: - DMFX ABC 4 Bright - Loop - Death: - DMFX DE 4 Bright - DMFX FGH 3 Bright - Stop - } -} - -// Demon, type 2 (brown) ---------------------------------------------------- - -ACTOR Demon2 : Demon1 -{ - Obituary "$OB_DEMON2" - Species "Demon2" - States - { - Spawn: - DEM2 AA 10 A_Look - Loop - See: - DEM2 ABCD 4 A_Chase - Loop - Pain: - DEM2 E 4 - DEM2 E 4 A_Pain - Goto See - Melee: - DEM2 E 6 A_FaceTarget - DEM2 F 8 A_FaceTarget - DEM2 G 6 A_CustomMeleeAttack(random[DemonAttack1](1,8)*2) - Goto See - Missile: - DEM2 E 5 A_FaceTarget - DEM2 F 6 A_FaceTarget - DEM2 G 5 A_CustomMissile("Demon2FX1", 62, 0) - Goto See - Death: - DEM2 HI 6 - DEM2 J 6 A_Scream - DEM2 K 6 A_NoBlocking - DEM2 L 6 A_QueueCorpse - DEM2 MNO 6 - DEM2 P -1 - Stop - XDeath: - DEM2 H 6 - DEM2 I 0 A_SpawnItemEx("Demon2Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags) - DEM2 I 0 A_SpawnItemEx("Demon2Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - DEM2 I 0 A_SpawnItemEx("Demon2Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - DEM2 I 0 A_SpawnItemEx("Demon2Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - DEM2 I 6 A_SpawnItemEx("Demon2Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags) - Goto Death+2 - } -} - -// Demon, type 2, mashed ---------------------------------------------------- - -ACTOR Demon2Mash : Demon2 -{ - +NOBLOOD - +BLASTED - -TELESTOMP - +NOICEDEATH - RenderStyle Translucent - Alpha 0.4 - States - { - Death: - XDeath: - Ice: - Stop - } -} - -// Demon, type 2, chunk 1 --------------------------------------------------- - -ACTOR Demon2Chunk1 : DemonChunk -{ - States - { - Spawn: - DMBA A 4 - DMBA A 10 A_QueueCorpse - DMBA A 20 - Wait - Death: - DMBA A -1 - Stop - } -} - -// Demon, type 2, chunk 2 --------------------------------------------------- - -ACTOR Demon2Chunk2 : DemonChunk -{ - States - { - Spawn: - DMBB A 4 - DMBB A 10 A_QueueCorpse - DMBB A 20 - Wait - Death: - DMBB A -1 - Stop - } -} - -// Demon, type 2, chunk 3 --------------------------------------------------- - -ACTOR Demon2Chunk3 : DemonChunk -{ - States - { - Spawn: - DMBC A 4 - DMBC A 10 A_QueueCorpse - DMBC A 20 - Wait - Death: - DMBC A -1 - Stop - } -} - -// Demon, type 2, chunk 4 --------------------------------------------------- - -ACTOR Demon2Chunk4 : DemonChunk -{ - States - { - Spawn: - DMBD A 4 - DMBD A 10 A_QueueCorpse - DMBD A 20 - Wait - Death: - DMBD A -1 - Stop - } -} - -// Demon, type 2, chunk 5 --------------------------------------------------- - -ACTOR Demon2Chunk5 : DemonChunk -{ - States - { - Spawn: - DMBE A 4 - DMBE A 10 A_QueueCorpse - DMBE A 20 - Wait - Death: - DMBE A -1 - Stop - } -} - -// Demon, type 2, projectile ------------------------------------------------ - -ACTOR Demon2FX1 -{ - Speed 15 - Radius 10 - Height 6 - Damage 5 - DamageType Fire - Projectile - +SPAWNSOUNDSOURCE - RenderStyle Add - SeeSound "DemonMissileFire" - DeathSound "DemonMissileExplode" - States - { - Spawn: - D2FX ABCDEF 4 Bright - Loop - Death: - D2FX GHIJ 4 Bright - D2FX KL 3 Bright - Stop - } -} - diff --git a/wadsrc/static/actors/hexen/ettin.txt b/wadsrc/static/actors/hexen/ettin.txt deleted file mode 100644 index 4ce13406c..000000000 --- a/wadsrc/static/actors/hexen/ettin.txt +++ /dev/null @@ -1,106 +0,0 @@ - -// Ettin -------------------------------------------------------------------- - -ACTOR Ettin -{ - Health 175 - Radius 25 - Height 68 - Mass 175 - Speed 13 - Damage 3 - Painchance 60 - Monster - +FLOORCLIP - +TELESTOMP - SeeSound "EttinSight" - AttackSound "EttinAttack" - PainSound "EttinPain" - DeathSound "EttinDeath" - ActiveSound "EttinActive" - HowlSound "PuppyBeat" - Obituary "$OB_ETTIN" - States - { - Spawn: - ETTN AA 10 A_Look - Loop - See: - ETTN ABCD 5 A_Chase - Loop - Pain: - ETTN H 7 A_Pain - Goto See - Melee: - ETTN EF 6 A_FaceTarget - ETTN G 8 A_CustomMeleeAttack(random[EttinAttack](1,8)*2) - Goto See - Death: - ETTN IJ 4 - ETTN K 4 A_Scream - ETTN L 4 A_NoBlocking - ETTN M 4 A_QueueCorpse - ETTN NOP 4 - ETTN Q -1 - Stop - XDeath: - ETTB A 4 - ETTB B 4 A_NoBlocking - ETTB C 4 A_SpawnItemEx("EttinMace", 0,0,8.5, - random[DropMace](-128,127) * 0.03125, - random[DropMace](-128,127) * 0.03125, - 10 + random[DropMace](0,255) * 0.015625, 0, SXF_ABSOLUTEVELOCITY) - ETTB D 4 A_Scream - ETTB E 4 A_QueueCorpse - ETTB FGHIJK 4 - ETTB L -1 - Stop - Ice: - ETTN R 5 A_FreezeDeath - ETTN R 1 A_FreezeDeathChunks - Wait - } -} - -// Ettin mace --------------------------------------------------------------- - -ACTOR EttinMace -{ - Radius 5 - Height 5 - +DROPOFF - +CORPSE - +NOTELEPORT - +FLOORCLIP - States - { - Spawn: - ETTB MNOP 5 - Loop - Crash: - ETTB Q 5 - ETTB R 5 A_QueueCorpse - ETTB S -1 - Stop - } -} - -// Ettin mash --------------------------------------------------------------- - -ACTOR EttinMash : Ettin -{ - +NOBLOOD - +NOICEDEATH - RenderStyle Translucent - Alpha 0.4 - States - { - Death: - XDeath: - Ice: - Stop - } -} - - - diff --git a/wadsrc/static/actors/hexen/mana.txt b/wadsrc/static/actors/hexen/mana.txt deleted file mode 100644 index 4a50e368a..000000000 --- a/wadsrc/static/actors/hexen/mana.txt +++ /dev/null @@ -1,87 +0,0 @@ -// Blue mana ---------------------------------------------------------------- - -ACTOR Mana1 : Ammo -{ - Inventory.Amount 15 - Inventory.MaxAmount 200 - Ammo.BackpackAmount 15 - Ammo.BackpackMaxAmount 200 - Radius 8 - Height 8 - +FLOATBOB - Inventory.Icon "MAN1I0" - Inventory.PickupMessage "$TXT_MANA_1" - States - { - Spawn: - MAN1 ABCDEFGHI 4 Bright - Loop - } -} - -// Green mana --------------------------------------------------------------- - -ACTOR Mana2 : Ammo -{ - Inventory.Amount 15 - Inventory.MaxAmount 200 - Ammo.BackpackAmount 15 - Ammo.BackpackMaxAmount 200 - Radius 8 - Height 8 - +FLOATBOB - Inventory.Icon "MAN2G0" - Inventory.PickupMessage "$TXT_MANA_2" - States - { - Spawn: - MAN2 ABCDEFGHIJKLMNOP 4 Bright - Loop - } -} - -// Combined mana ------------------------------------------------------------ - -ACTOR Mana3 : CustomInventory -{ - Radius 8 - Height 8 - +FLOATBOB - Inventory.PickupMessage "$TXT_MANA_BOTH" - States - { - Spawn: - MAN3 ABCDEFGHIJKLMNOP 4 Bright - Loop - Pickup: - TNT1 A 0 A_GiveInventory("Mana1", 20) - TNT1 A 0 A_GiveInventory("Mana2", 20) - Stop - } -} - -// Boost Mana Artifact Krater of Might ------------------------------------ - -ACTOR ArtiBoostMana : CustomInventory -{ - +FLOATBOB - +COUNTITEM - +INVENTORY.INVBAR - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.DefMaxAmount - Inventory.Icon "ARTIBMAN" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIBOOSTMANA" - Tag "$TAG_ARTIBOOSTMANA" - States - { - Spawn: - BMAN A -1 - Stop - Use: - TNT1 A 0 A_GiveInventory("Mana1", 200) - TNT1 A 0 A_GiveInventory("Mana2", 200) - Stop - } -} diff --git a/wadsrc/static/actors/hexen/puzzleitems.txt b/wadsrc/static/actors/hexen/puzzleitems.txt deleted file mode 100644 index ad1187da0..000000000 --- a/wadsrc/static/actors/hexen/puzzleitems.txt +++ /dev/null @@ -1,287 +0,0 @@ - -// Yorick's Skull ----------------------------------------------------------- - -ACTOR PuzzSkull : PuzzleItem -{ - PuzzleItem.Number 0 - Inventory.Icon ARTISKLL - Inventory.PickupMessage "$TXT_ARTIPUZZSKULL" - Tag "$TAG_ARTIPUZZSKULL" - States - { - Spawn: - ASKU A -1 - Stop - } -} - - -// Heart of D'Sparil -------------------------------------------------------- - -ACTOR PuzzGemBig : PuzzleItem -{ - PuzzleItem.Number 1 - Inventory.Icon ARTIBGEM - Inventory.PickupMessage "$TXT_ARTIPUZZGEMBIG" - Tag "$TAG_ARTIPUZZGEMBIG" - States - { - Spawn: - ABGM A -1 - Stop - } -} - -// Red Gem (Ruby Planet) ---------------------------------------------------- - -ACTOR PuzzGemRed : PuzzleItem -{ - PuzzleItem.Number 2 - Inventory.Icon ARTIGEMR - Inventory.PickupMessage "$TXT_ARTIPUZZGEMRED" - Tag "$TAG_ARTIPUZZGEMRED" - States - { - Spawn: - AGMR A -1 - Stop - } -} - - -// Green Gem 1 (Emerald Planet) --------------------------------------------- - -ACTOR PuzzGemGreen1 : PuzzleItem -{ - PuzzleItem.Number 3 - Inventory.Icon ARTIGEMG - Inventory.PickupMessage "$TXT_ARTIPUZZGEMGREEN1" - Tag "$TAG_ARTIPUZZGEMGREEN1" - States - { - Spawn: - AGMG A -1 - Stop - } -} - - -// Green Gem 2 (Emerald Planet) --------------------------------------------- - -ACTOR PuzzGemGreen2 : PuzzleItem -{ - PuzzleItem.Number 4 - Inventory.Icon ARTIGMG2 - Inventory.PickupMessage "$TXT_ARTIPUZZGEMGREEN2" - Tag "$TAG_ARTIPUZZGEMGREEN2" - States - { - Spawn: - AGG2 A -1 - Stop - } -} - - -// Blue Gem 1 (Sapphire Planet) --------------------------------------------- - -ACTOR PuzzGemBlue1 : PuzzleItem -{ - PuzzleItem.Number 5 - Inventory.Icon ARTIGEMB - Inventory.PickupMessage "$TXT_ARTIPUZZGEMBLUE1" - Tag "$TAG_ARTIPUZZGEMBLUE1" - States - { - Spawn: - AGMB A -1 - Stop - } -} - - -// Blue Gem 2 (Sapphire Planet) --------------------------------------------- - -ACTOR PuzzGemBlue2 : PuzzleItem -{ - PuzzleItem.Number 6 - Inventory.Icon ARTIGMB2 - Inventory.PickupMessage "$TXT_ARTIPUZZGEMBLUE2" - Tag "$TAG_ARTIPUZZGEMBLUE2" - States - { - Spawn: - AGB2 A -1 - Stop - } -} - - -// Book 1 (Daemon Codex) ---------------------------------------------------- - -ACTOR PuzzBook1 : PuzzleItem -{ - PuzzleItem.Number 7 - Inventory.Icon ARTIBOK1 - Inventory.PickupMessage "$TXT_ARTIPUZZBOOK1" - Tag "$TAG_ARTIPUZZBOOK1" - States - { - Spawn: - ABK1 A -1 - Stop - } -} - - -// Book 2 (Liber Oscura) ---------------------------------------------------- - -ACTOR PuzzBook2 : PuzzleItem -{ - PuzzleItem.Number 8 - Inventory.Icon ARTIBOK2 - Inventory.PickupMessage "$TXT_ARTIPUZZBOOK2" - Tag "$TAG_ARTIPUZZBOOK2" - States - { - Spawn: - ABK2 A -1 - Stop - } -} - - -// Flame Mask --------------------------------------------------------------- - - -ACTOR PuzzFlameMask : PuzzleItem -{ - PuzzleItem.Number 9 - Inventory.Icon ARTISKL2 - Inventory.PickupMessage "$TXT_ARTIPUZZSKULL2" - Tag "$TAG_ARTIPUZZSKULL2" - States - { - Spawn: - ASK2 A -1 - Stop - } -} - -// Fighter Weapon (Glaive Seal) --------------------------------------------- - -ACTOR PuzzFWeapon : PuzzleItem -{ - PuzzleItem.Number 10 - Inventory.Icon ARTIFWEP - Inventory.PickupMessage "$TXT_ARTIPUZZFWEAPON" - Tag "$TAG_ARTIPUZZFWEAPON" - States - { - Spawn: - AFWP A -1 - Stop - } -} - - -// Cleric Weapon (Holy Relic) ----------------------------------------------- - -ACTOR PuzzCWeapon : PuzzleItem -{ - PuzzleItem.Number 11 - Inventory.Icon ARTICWEP - Inventory.PickupMessage "$TXT_ARTIPUZZCWEAPON" - Tag "$TAG_ARTIPUZZCWEAPON" - States - { - Spawn: - ACWP A -1 - Stop - } -} - - -// Mage Weapon (Sigil of the Magus) ----------------------------------------- - -ACTOR PuzzMWeapon : PuzzleItem -{ - PuzzleItem.Number 12 - Inventory.Icon ARTIMWEP - Inventory.PickupMessage "$TXT_ARTIPUZZMWEAPON" - Tag "$TAG_ARTIPUZZMWEAPON" - States - { - Spawn: - AMWP A -1 - Stop - } -} - -// Clock Gear 1 ------------------------------------------------------------- - -ACTOR PuzzGear1 : PuzzleItem -{ - PuzzleItem.Number 13 - Inventory.Icon ARTIGEAR - Inventory.PickupMessage "$TXT_ARTIPUZZGEAR" - Tag "$TAG_ARTIPUZZGEAR1" - States - { - Spawn: - AGER ABCDEFGH 4 Bright - Loop - } -} - - -// Clock Gear 2 ------------------------------------------------------------- - -ACTOR PuzzGear2 : PuzzleItem -{ - PuzzleItem.Number 14 - Inventory.Icon ARTIGER2 - Inventory.PickupMessage "$TXT_ARTIPUZZGEAR" - Tag "$TAG_ARTIPUZZGEAR2" - States - { - Spawn: - AGR2 ABCDEFGH 4 Bright - Loop - } -} - - -// Clock Gear 3 ------------------------------------------------------------- - -ACTOR PuzzGear3 : PuzzleItem -{ - PuzzleItem.Number 15 - Inventory.Icon ARTIGER3 - Inventory.PickupMessage "$TXT_ARTIPUZZGEAR" - Tag "$TAG_ARTIPUZZGEAR3" - States - { - Spawn: - AGR3 ABCDEFGH 4 Bright - Loop - } -} - - -// Clock Gear 4 ------------------------------------------------------------- - -ACTOR PuzzGear4 : PuzzleItem -{ - PuzzleItem.Number 16 - Inventory.Icon ARTIGER4 - Inventory.PickupMessage "$TXT_ARTIPUZZGEAR" - Tag "$TAG_ARTIPUZZGEAR4" - States - { - Spawn: - AGR4 ABCDEFGH 4 Bright - Loop - } -} - diff --git a/wadsrc/static/actors/hexen/scriptprojectiles.txt b/wadsrc/static/actors/hexen/scriptprojectiles.txt deleted file mode 100644 index d031be3ee..000000000 --- a/wadsrc/static/actors/hexen/scriptprojectiles.txt +++ /dev/null @@ -1,123 +0,0 @@ -// Fire Ball ---------------------------------------------------------------- - -ACTOR FireBall -{ - Speed 2 - Radius 8 - Height 8 - Damage 4 - DamageType Fire - +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE - +NOTELEPORT - RenderStyle Add - DeathSound "Fireball" - States - { - Spawn: - FBL1 AB 4 Bright - Loop - Death: - XPL1 ABCDEF 4 Bright - Stop - } -} - -// Arrow -------------------------------------------------------------------- - -ACTOR Arrow -{ - Speed 6 - Radius 8 - Height 4 - Damage 4 - +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE - +NOTELEPORT - States - { - Spawn: - ARRW A -1 - Stop - Death: - ARRW A 1 - Stop - } -} - -// Dart --------------------------------------------------------------------- - -ACTOR Dart -{ - Speed 6 - Radius 8 - Height 4 - Damage 2 - +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE - +NOTELEPORT - States - { - Spawn: - DART A -1 - Stop - Death: - DART A 1 - Stop - } -} - -// Poison Dart -------------------------------------------------------------- - -ACTOR PoisonDart : Dart -{ - PoisonDamage 20 -} - -// Ripper Ball -------------------------------------------------------------- - -ACTOR RipperBall -{ - Speed 6 - Radius 8 - Damage 2 - +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE - +NOTELEPORT +RIPPER - States - { - Spawn: - RIPP ABC 3 - Loop - Death: - CFCF Q 4 Bright - CFCF R 3 Bright - CFCF S 4 Bright - CFCF T 3 Bright - CFCF U 4 Bright - CFCF V 3 Bright - CFCF W 4 Bright - CFCF X 3 Bright - CFCF Y 4 Bright - CFCF Z 3 Bright - Stop - } -} - -// Projectile Blade --------------------------------------------------------- - -ACTOR ProjectileBlade -{ - Speed 6 - Radius 6 - Height 6 - Damage 3 - +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE - +NOTELEPORT - States - { - Spawn: - BLAD A -1 - Stop - Death: - BLAD A 1 - Stop - } -} - diff --git a/wadsrc/static/actors/hexen/speedboots.txt b/wadsrc/static/actors/hexen/speedboots.txt deleted file mode 100644 index 2ae4dcd01..000000000 --- a/wadsrc/static/actors/hexen/speedboots.txt +++ /dev/null @@ -1,18 +0,0 @@ - - -ACTOR ArtiSpeedBoots : PowerupGiver -{ - +FLOATBOB - +COUNTITEM - +INVENTORY.PICKUPFLASH - Inventory.Icon ARTISPED - Inventory.PickupMessage "$TXT_ARTISPEED" - Tag "$TAG_ARTISPEED" - Powerup.Type Speed - States - { - Spawn: - SPED ABCDEFGH 3 Bright - Loop - } -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 146600f34..92802dc7e 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,10 +1,3 @@ -#include "actors/hexen/mana.txt" -#include "actors/hexen/puzzleitems.txt" -#include "actors/hexen/scriptprojectiles.txt" -#include "actors/hexen/speedboots.txt" -#include "actors/hexen/ettin.txt" -#include "actors/hexen/centaur.txt" -#include "actors/hexen/demons.txt" #include "actors/hexen/firedemon.txt" #include "actors/hexen/fog.txt" #include "actors/hexen/summon.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 50ecf6212..531c353f5 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -97,7 +97,6 @@ zscript/hexen/hexenarmor.txt zscript/hexen/hexendecorations.txt zscript/hexen/hexenkeys.txt zscript/hexen/hexenspecialdecs.txt -/* zscript/hexen/mana.txt zscript/hexen/puzzleitems.txt zscript/hexen/scriptprojectiles.txt @@ -105,6 +104,7 @@ zscript/hexen/speedboots.txt zscript/hexen/ettin.txt zscript/hexen/centaur.txt zscript/hexen/demons.txt +/* zscript/hexen/firedemon.txt zscript/hexen/fog.txt zscript/hexen/summon.txt diff --git a/wadsrc/static/zscript/hexen/centaur.txt b/wadsrc/static/zscript/hexen/centaur.txt new file mode 100644 index 000000000..37a8d6b11 --- /dev/null +++ b/wadsrc/static/zscript/hexen/centaur.txt @@ -0,0 +1,204 @@ +// Centaur ------------------------------------------------------------------ + +class Centaur : Actor +{ + Default + { + Health 200; + Painchance 135; + Speed 13; + Height 64; + Mass 120; + Monster; + +FLOORCLIP + +TELESTOMP + +SHIELDREFLECT + SeeSound "CentaurSight"; + AttackSound "CentaurAttack"; + PainSound "CentaurPain"; + DeathSound "CentaurDeath"; + ActiveSound "CentaurActive"; + HowlSound "PuppyBeat"; + Obituary "$OB_CENTAUR"; + DamageFactor "Electric", 3; + } + States + { + Spawn: + CENT AB 10 A_Look; + Loop; + See: + CENT ABCD 4 A_Chase; + Loop; + Pain: + CENT G 6 A_Pain; + CENT G 6 A_SetReflectiveInvulnerable; + CENT EEE 15 A_CentaurDefend; + CENT E 1 A_UnsetReflectiveInvulnerable; + Goto See; + Melee: + CENT H 5 A_FaceTarget; + CENT I 4 A_FaceTarget; + CENT J 7 A_CustomMeleeAttack(random[CentaurAttack](3,9)); + Goto See; + Death: + CENT K 4; + CENT L 4 A_Scream; + CENT MN 4; + CENT O 4 A_NoBlocking; + CENT PQ 4; + CENT R 4 A_QueueCorpse; + CENT S 4; + CENT T -1; + Stop; + XDeath: + CTXD A 4; + CTXD B 4 A_NoBlocking; + CTXD C 0 A_SpawnItemEx("CentaurSword", 0, 0, 45, + 1 + random[CentaurDrop](-128,127)*0.03125, + 1 + random[CentaurDrop](-128,127)*0.03125, + 8 + random[CentaurDrop](0,255)*0.015625, 270); + CTXD C 4 A_SpawnItemEx("CentaurShield", 0, 0, 45, + 1 + random[CentaurDrop](-128,127)*0.03125, + 1 + random[CentaurDrop](-128,127)*0.03125, + 8 + random[CentaurDrop](0,255)*0.015625, 90); + CTXD D 3 A_Scream; + CTXD E 4 A_QueueCorpse; + CTXD F 3; + CTXD G 4; + CTXD H 3; + CTXD I 4; + CTXD J 3; + CTXD K -1; + Ice: + CENT U 5 A_FreezeDeath; + CENT U 1 A_FreezeDeathChunks; + Wait; + } +} + +// Centaur Leader ----------------------------------------------------------- + +class CentaurLeader : Centaur +{ + Default + { + Health 250; + PainChance 96; + Speed 10; + Obituary "$OB_SLAUGHTAUR"; + HitObituary "$OB_SLAUGHTAURHIT"; + } + States + { + Missile: + CENT E 10 A_FaceTarget; + CENT F 8 Bright A_CustomMissile("CentaurFX", 45, 0, 0, CMF_AIMOFFSET); + CENT E 10 A_FaceTarget; + CENT F 8 Bright A_CustomMissile("CentaurFX", 45, 0, 0, CMF_AIMOFFSET); + Goto See; + } +} + +// Mashed centaur ----------------------------------------------------------- +// +// The mashed centaur is only placed through ACS. Nowhere in the game source +// is it ever referenced. + +class CentaurMash : Centaur +{ + Default + { + +NOBLOOD + +BLASTED + -TELESTOMP + +NOICEDEATH + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Death: + XDeath: + Ice: + Stop; + } +} + +// Centaur projectile ------------------------------------------------------- + +class CentaurFX : Actor +{ + Default + { + Speed 20; + Damage 4; + Projectile; + +SPAWNSOUNDSOURCE + RenderStyle "Add"; + SeeSound "CentaurLeaderAttack"; + DeathSound "CentaurMissileExplode"; + } + States + { + Spawn: + CTFX A -1 Bright; + Stop; + Death: + CTFX B 4 Bright; + CTFX C 3 Bright; + CTFX D 4 Bright; + CTFX E 3 Bright; + CTFX F 2 Bright; + Stop; + } +} + +// Centaur shield (debris) -------------------------------------------------- + +class CentaurShield : Actor +{ + Default + { + +DROPOFF + +CORPSE + +NOTELEPORT + } + States + { + Spawn: + CTDP ABCDEF 3; + Goto Spawn+2; + Crash: + CTDP G 4; + CTDP H 4 A_QueueCorpse; + CTDP I 4; + CTDP J -1; + Stop; + } +} + +// Centaur sword (debris) --------------------------------------------------- + +class CentaurSword : Actor +{ + Default + { + +DROPOFF + +CORPSE + +NOTELEPORT + } + States + { + Spawn: + CTDP KLMNOPQ 3; + Goto Spawn+2; + Crash: + CTDP R 4; + CTDP S 4 A_QueueCorpse; + CTDP T -1; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/hexen/demons.txt b/wadsrc/static/zscript/hexen/demons.txt new file mode 100644 index 000000000..56b4f3bda --- /dev/null +++ b/wadsrc/static/zscript/hexen/demons.txt @@ -0,0 +1,408 @@ + +// Demon, type 1 (green, like D'Sparil's) ----------------------------------- + +class Demon1 : Actor +{ + Default + { + Health 250; + Painchance 50; + Speed 13; + Radius 32; + Height 64; + Mass 220; + Monster; + +TELESTOMP + +FLOORCLIP + SeeSound "DemonSight"; + AttackSound "DemonAttack"; + PainSound "DemonPain"; + DeathSound "DemonDeath"; + ActiveSound "DemonActive"; + Obituary "$OB_DEMON1"; + } + + const ChunkFlags = SXF_TRANSFERTRANSLATION | SXF_ABSOLUTEVELOCITY; + + States + { + Spawn: + DEMN AA 10 A_Look; + Loop; + See: + DEMN ABCD 4 A_Chase; + Loop; + Pain: + DEMN E 4; + DEMN E 4 A_Pain; + Goto See; + Melee: + DEMN E 6 A_FaceTarget; + DEMN F 8 A_FaceTarget; + DEMN G 6 A_CustomMeleeAttack(random[DemonAttack1](1,8)*2); + Goto See; + Missile: + DEMN E 5 A_FaceTarget; + DEMN F 6 A_FaceTarget; + DEMN G 5 A_CustomMissile("Demon1FX1", 62, 0); + Goto See; + Death: + DEMN HI 6; + DEMN J 6 A_Scream; + DEMN K 6 A_NoBlocking; + DEMN L 6 A_QueueCorpse; + DEMN MNO 6; + DEMN P -1; + Stop; + XDeath: + DEMN H 6; + DEMN I 0 A_SpawnItemEx("Demon1Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags); + DEMN I 0 A_SpawnItemEx("Demon1Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEMN I 0 A_SpawnItemEx("Demon1Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEMN I 0 A_SpawnItemEx("Demon1Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEMN I 6 A_SpawnItemEx("Demon1Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + Goto Death+2; + Ice: + DEMN Q 5 A_FreezeDeath; + DEMN Q 1 A_FreezeDeathChunks; + Wait; + } +} + +// Demon, type 1, mashed ---------------------------------------------------- + +class Demon1Mash : Demon1 +{ + Default + { + +NOBLOOD + +BLASTED + -TELESTOMP + +NOICEDEATH + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Death: + XDeath: + Ice: + Stop; + } +} + +// Demon chunk, base class -------------------------------------------------- + +class DemonChunk : Actor +{ + Default + { + Radius 5; + Height 5; + +NOBLOCKMAP + +DROPOFF + +MISSILE + +CORPSE + +FLOORCLIP + +NOTELEPORT + } +} + +// Demon, type 1, chunk 1 --------------------------------------------------- + +class Demon1Chunk1 : DemonChunk +{ + States + { + Spawn: + DEMA A 4; + DEMA A 10 A_QueueCorpse; + DEMA A 20; + Wait; + Death: + DEMA A -1; + Stop; + } +} + +// Demon, type 1, chunk 2 --------------------------------------------------- + +class Demon1Chunk2 : DemonChunk +{ + States + { + Spawn: + DEMB A 4; + DEMB A 10 A_QueueCorpse; + DEMB A 20; + Wait; + Death: + DEMB A -1; + Stop; + } +} + +class Demon1Chunk3 : DemonChunk +{ + States + { + Spawn: + DEMC A 4; + DEMC A 10 A_QueueCorpse; + DEMC A 20; + Wait; + Death: + DEMC A -1; + Stop; + } +} + +// Demon, type 1, chunk 4 --------------------------------------------------- + +class Demon1Chunk4 : DemonChunk +{ + States + { + Spawn: + DEMD A 4; + DEMD A 10 A_QueueCorpse; + DEMD A 20; + Wait; + Death: + DEMD A -1; + Stop; + } +} + +// Demon, type 1, chunk 5 --------------------------------------------------- + +class Demon1Chunk5 : DemonChunk +{ + States + { + Spawn: + DEME A 4; + DEME A 10 A_QueueCorpse; + DEME A 20; + Wait; + Death: + DEME A -1; + Stop; + } +} + +// Demon, type 1, projectile ------------------------------------------------ + +class Demon1FX1 : Actor +{ + Default + { + Speed 15; + Radius 10; + Height 6; + Damage 5; + DamageType "Fire"; + Projectile; + +SPAWNSOUNDSOURCE + RenderStyle "Add"; + SeeSound "DemonMissileFire"; + DeathSound "DemonMissileExplode"; + } + States + { + Spawn: + DMFX ABC 4 Bright; + Loop; + Death: + DMFX DE 4 Bright; + DMFX FGH 3 Bright; + Stop; + } +} + +// Demon, type 2 (brown) ---------------------------------------------------- + +class Demon2 : Demon1 +{ + Default + { + Obituary "$OB_DEMON2"; + Species "Demon2"; + } + States + { + Spawn: + DEM2 AA 10 A_Look; + Loop; + See: + DEM2 ABCD 4 A_Chase; + Loop; + Pain: + DEM2 E 4; + DEM2 E 4 A_Pain; + Goto See; + Melee: + DEM2 E 6 A_FaceTarget; + DEM2 F 8 A_FaceTarget; + DEM2 G 6 A_CustomMeleeAttack(random[DemonAttack1](1,8)*2); + Goto See; + Missile: + DEM2 E 5 A_FaceTarget; + DEM2 F 6 A_FaceTarget; + DEM2 G 5 A_CustomMissile("Demon2FX1", 62, 0); + Goto See; + Death: + DEM2 HI 6; + DEM2 J 6 A_Scream; + DEM2 K 6 A_NoBlocking; + DEM2 L 6 A_QueueCorpse; + DEM2 MNO 6; + DEM2 P -1; + Stop; + XDeath: + DEM2 H 6; + DEM2 I 0 A_SpawnItemEx("Demon2Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags); + DEM2 I 0 A_SpawnItemEx("Demon2Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEM2 I 0 A_SpawnItemEx("Demon2Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEM2 I 0 A_SpawnItemEx("Demon2Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEM2 I 6 A_SpawnItemEx("Demon2Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + Goto Death+2; + } +} + +// Demon, type 2, mashed ---------------------------------------------------- + +class Demon2Mash : Demon2 +{ + Default + { + +NOBLOOD + +BLASTED + -TELESTOMP + +NOICEDEATH + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Death: + XDeath: + Ice: + Stop; + } +} + +// Demon, type 2, chunk 1 --------------------------------------------------- + +class Demon2Chunk1 : DemonChunk +{ + States + { + Spawn: + DMBA A 4; + DMBA A 10 A_QueueCorpse; + DMBA A 20; + Wait; + Death: + DMBA A -1; + Stop; + } +} + +// Demon, type 2, chunk 2 --------------------------------------------------- + +class Demon2Chunk2 : DemonChunk +{ + States + { + Spawn: + DMBB A 4; + DMBB A 10 A_QueueCorpse; + DMBB A 20; + Wait; + Death: + DMBB A -1; + Stop; + } +} + +// Demon, type 2, chunk 3 --------------------------------------------------- + +class Demon2Chunk3 : DemonChunk +{ + States + { + Spawn: + DMBC A 4; + DMBC A 10 A_QueueCorpse; + DMBC A 20; + Wait; + Death: + DMBC A -1; + Stop; + } +} + +// Demon, type 2, chunk 4 --------------------------------------------------- + +class Demon2Chunk4 : DemonChunk +{ + States + { + Spawn: + DMBD A 4; + DMBD A 10 A_QueueCorpse; + DMBD A 20; + Wait; + Death: + DMBD A -1; + Stop; + } +} + +// Demon, type 2, chunk 5 --------------------------------------------------- + +class Demon2Chunk5 : DemonChunk +{ + States + { + Spawn: + DMBE A 4; + DMBE A 10 A_QueueCorpse; + DMBE A 20; + Wait; + Death: + DMBE A -1; + Stop; + } +} + +// Demon, type 2, projectile ------------------------------------------------ + +class Demon2FX1 : Actor +{ + Default + { + Speed 15; + Radius 10; + Height 6; + Damage 5; + DamageType "Fire"; + Projectile; + +SPAWNSOUNDSOURCE + RenderStyle "Add"; + SeeSound "DemonMissileFire"; + DeathSound "DemonMissileExplode"; + } + States + { + Spawn: + D2FX ABCDEF 4 Bright; + Loop; + Death: + D2FX GHIJ 4 Bright; + D2FX KL 3 Bright; + Stop; + } +} + diff --git a/wadsrc/static/zscript/hexen/ettin.txt b/wadsrc/static/zscript/hexen/ettin.txt new file mode 100644 index 000000000..8ddf9e7d2 --- /dev/null +++ b/wadsrc/static/zscript/hexen/ettin.txt @@ -0,0 +1,115 @@ + +// Ettin -------------------------------------------------------------------- + +class Ettin : Actor +{ + Default + { + Health 175; + Radius 25; + Height 68; + Mass 175; + Speed 13; + Damage 3; + Painchance 60; + Monster; + +FLOORCLIP + +TELESTOMP + SeeSound "EttinSight"; + AttackSound "EttinAttack"; + PainSound "EttinPain"; + DeathSound "EttinDeath"; + ActiveSound "EttinActive"; + HowlSound "PuppyBeat"; + Obituary "$OB_ETTIN"; + } + States + { + Spawn: + ETTN AA 10 A_Look; + Loop; + See: + ETTN ABCD 5 A_Chase; + Loop; + Pain: + ETTN H 7 A_Pain; + Goto See; + Melee: + ETTN EF 6 A_FaceTarget; + ETTN G 8 A_CustomMeleeAttack(random[EttinAttack](1,8)*2); + Goto See; + Death: + ETTN IJ 4; + ETTN K 4 A_Scream; + ETTN L 4 A_NoBlocking; + ETTN M 4 A_QueueCorpse; + ETTN NOP 4; + ETTN Q -1; + Stop; + XDeath: + ETTB A 4; + ETTB B 4 A_NoBlocking; + ETTB C 4 A_SpawnItemEx("EttinMace", 0,0,8.5, + random[DropMace](-128,127) * 0.03125, + random[DropMace](-128,127) * 0.03125, + 10 + random[DropMace](0,255) * 0.015625, 0, SXF_ABSOLUTEVELOCITY); + ETTB D 4 A_Scream; + ETTB E 4 A_QueueCorpse; + ETTB FGHIJK 4; + ETTB L -1; + Stop; + Ice: + ETTN R 5 A_FreezeDeath; + ETTN R 1 A_FreezeDeathChunks; + Wait; + } +} + +// Ettin mace --------------------------------------------------------------- + +class EttinMace : Actor +{ + Default + { + Radius 5; + Height 5; + +DROPOFF + +CORPSE + +NOTELEPORT + +FLOORCLIP + } + States + { + Spawn: + ETTB MNOP 5; + Loop; + Crash: + ETTB Q 5; + ETTB R 5 A_QueueCorpse; + ETTB S -1; + Stop; + } +} + +// Ettin mash --------------------------------------------------------------- + +class EttinMash : Ettin +{ + Default + { + +NOBLOOD + +NOICEDEATH + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Death: + XDeath: + Ice: + Stop; + } +} + + + diff --git a/wadsrc/static/zscript/hexen/mana.txt b/wadsrc/static/zscript/hexen/mana.txt new file mode 100644 index 000000000..0a43a21dd --- /dev/null +++ b/wadsrc/static/zscript/hexen/mana.txt @@ -0,0 +1,99 @@ +// Blue mana ---------------------------------------------------------------- + +class Mana1 : Ammo +{ + Default + { + Inventory.Amount 15; + Inventory.MaxAmount 200; + Ammo.BackpackAmount 15; + Ammo.BackpackMaxAmount 200; + Radius 8; + Height 8; + +FLOATBOB + Inventory.Icon "MAN1I0"; + Inventory.PickupMessage "$TXT_MANA_1"; + } + States + { + Spawn: + MAN1 ABCDEFGHI 4 Bright; + Loop; + } +} + +// Green mana --------------------------------------------------------------- + +class Mana2 : Ammo +{ + Default + { + Inventory.Amount 15; + Inventory.MaxAmount 200; + Ammo.BackpackAmount 15; + Ammo.BackpackMaxAmount 200; + Radius 8; + Height 8; + +FLOATBOB + Inventory.Icon "MAN2G0"; + Inventory.PickupMessage "$TXT_MANA_2"; + } + States + { + Spawn: + MAN2 ABCDEFGHIJKLMNOP 4 Bright; + Loop; + } +} + +// Combined mana ------------------------------------------------------------ + +class Mana3 : CustomInventory +{ + Default + { + Radius 8; + Height 8; + +FLOATBOB + Inventory.PickupMessage "$TXT_MANA_BOTH"; + } + States + { + Spawn: + MAN3 ABCDEFGHIJKLMNOP 4 Bright; + Loop; + Pickup: + TNT1 A 0 A_GiveInventory("Mana1", 20); + TNT1 A 0 A_GiveInventory("Mana2", 20); + Stop; + } +} + +// Boost Mana Artifact Krater of Might ------------------------------------ + +class ArtiBoostMana : CustomInventory +{ + Default + { + +FLOATBOB + +COUNTITEM + +INVENTORY.INVBAR + +INVENTORY.FANCYPICKUPSOUND + Inventory.PickupFlash "PickupFlash"; + Inventory.DefMaxAmount; + Inventory.Icon "ARTIBMAN"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIBOOSTMANA"; + Tag "$TAG_ARTIBOOSTMANA"; + } + States + { + Spawn: + BMAN A -1; + Stop; + Use: + TNT1 A 0 A_GiveInventory("Mana1", 200); + TNT1 A 0 A_GiveInventory("Mana2", 200); + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/puzzleitems.txt b/wadsrc/static/zscript/hexen/puzzleitems.txt new file mode 100644 index 000000000..f502664d7 --- /dev/null +++ b/wadsrc/static/zscript/hexen/puzzleitems.txt @@ -0,0 +1,338 @@ + +// Yorick's Skull ----------------------------------------------------------- + +class PuzzSkull : PuzzleItem +{ + Default + { + PuzzleItem.Number 0; + Inventory.Icon "ARTISKLL"; + Inventory.PickupMessage "$TXT_ARTIPUZZSKULL"; + Tag "$TAG_ARTIPUZZSKULL"; + } + States + { + Spawn: + ASKU A -1; + Stop; + } +} + + +// Heart of D'Sparil -------------------------------------------------------- + +class PuzzGemBig : PuzzleItem +{ + Default + { + PuzzleItem.Number 1; + Inventory.Icon "ARTIBGEM"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEMBIG"; + Tag "$TAG_ARTIPUZZGEMBIG"; + } + States + { + Spawn: + ABGM A -1; + Stop; + } +} + +// Red Gem (Ruby Planet) ---------------------------------------------------- + +class PuzzGemRed : PuzzleItem +{ + Default + { + PuzzleItem.Number 2; + Inventory.Icon "ARTIGEMR"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEMRED"; + Tag "$TAG_ARTIPUZZGEMRED"; + } + States + { + Spawn: + AGMR A -1; + Stop; + } +} + + +// Green Gem 1 (Emerald Planet) --------------------------------------------- + +class PuzzGemGreen1 : PuzzleItem +{ + Default + { + PuzzleItem.Number 3; + Inventory.Icon "ARTIGEMG"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEMGREEN1"; + Tag "$TAG_ARTIPUZZGEMGREEN1"; + } + States + { + Spawn: + AGMG A -1; + Stop; + } +} + + +// Green Gem 2 (Emerald Planet) --------------------------------------------- + +class PuzzGemGreen2 : PuzzleItem +{ + Default + { + PuzzleItem.Number 4; + Inventory.Icon "ARTIGMG2"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEMGREEN2"; + Tag "$TAG_ARTIPUZZGEMGREEN2"; + } + States + { + Spawn: + AGG2 A -1; + Stop; + } +} + + +// Blue Gem 1 (Sapphire Planet) --------------------------------------------- + +class PuzzGemBlue1 : PuzzleItem +{ + Default + { + PuzzleItem.Number 5; + Inventory.Icon "ARTIGEMB"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEMBLUE1"; + Tag "$TAG_ARTIPUZZGEMBLUE1"; + } + States + { + Spawn: + AGMB A -1; + Stop; + } +} + + +// Blue Gem 2 (Sapphire Planet) --------------------------------------------- + +class PuzzGemBlue2 : PuzzleItem +{ + Default + { + PuzzleItem.Number 6; + Inventory.Icon "ARTIGMB2"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEMBLUE2"; + Tag "$TAG_ARTIPUZZGEMBLUE2"; + } + States + { + Spawn: + AGB2 A -1; + Stop; + } +} + + +// Book 1 (Daemon Codex) ---------------------------------------------------- + +class PuzzBook1 : PuzzleItem +{ + Default + { + PuzzleItem.Number 7; + Inventory.Icon "ARTIBOK1"; + Inventory.PickupMessage "$TXT_ARTIPUZZBOOK1"; + Tag "$TAG_ARTIPUZZBOOK1"; + } + States + { + Spawn: + ABK1 A -1; + Stop; + } +} + + +// Book 2 (Liber Oscura) ---------------------------------------------------- + +class PuzzBook2 : PuzzleItem +{ + Default + { + PuzzleItem.Number 8; + Inventory.Icon "ARTIBOK2"; + Inventory.PickupMessage "$TXT_ARTIPUZZBOOK2"; + Tag "$TAG_ARTIPUZZBOOK2"; + } + States + { + Spawn: + ABK2 A -1; + Stop; + } +} + + +// Flame Mask --------------------------------------------------------------- + + +class PuzzFlameMask : PuzzleItem +{ + Default + { + PuzzleItem.Number 9; + Inventory.Icon "ARTISKL2"; + Inventory.PickupMessage "$TXT_ARTIPUZZSKULL2"; + Tag "$TAG_ARTIPUZZSKULL2"; + } + States + { + Spawn: + ASK2 A -1; + Stop; + } +} + +// Fighter Weapon (Glaive Seal) --------------------------------------------- + +class PuzzFWeapon : PuzzleItem +{ + Default + { + PuzzleItem.Number 10; + Inventory.Icon "ARTIFWEP"; + Inventory.PickupMessage "$TXT_ARTIPUZZFWEAPON"; + Tag "$TAG_ARTIPUZZFWEAPON"; + } + States + { + Spawn: + AFWP A -1; + Stop; + } +} + + +// Cleric Weapon (Holy Relic) ----------------------------------------------- + +class PuzzCWeapon : PuzzleItem +{ + Default + { + PuzzleItem.Number 11; + Inventory.Icon "ARTICWEP"; + Inventory.PickupMessage "$TXT_ARTIPUZZCWEAPON"; + Tag "$TAG_ARTIPUZZCWEAPON"; + } + States + { + Spawn: + ACWP A -1; + Stop; + } +} + + +// Mage Weapon (Sigil of the Magus) ----------------------------------------- + +class PuzzMWeapon : PuzzleItem +{ + Default + { + PuzzleItem.Number 12; + Inventory.Icon "ARTIMWEP"; + Inventory.PickupMessage "$TXT_ARTIPUZZMWEAPON"; + Tag "$TAG_ARTIPUZZMWEAPON"; + } + States + { + Spawn: + AMWP A -1; + Stop; + } +} + +// Clock Gear 1 ------------------------------------------------------------- + +class PuzzGear1 : PuzzleItem +{ + Default + { + PuzzleItem.Number 13; + Inventory.Icon "ARTIGEAR"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEAR"; + Tag "$TAG_ARTIPUZZGEAR1"; + } + States + { + Spawn: + AGER ABCDEFGH 4 Bright; + Loop; + } +} + + +// Clock Gear 2 ------------------------------------------------------------- + +class PuzzGear2 : PuzzleItem +{ + Default + { + PuzzleItem.Number 14; + Inventory.Icon "ARTIGER2"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEAR"; + Tag "$TAG_ARTIPUZZGEAR2"; + } + States + { + Spawn: + AGR2 ABCDEFGH 4 Bright; + Loop; + } +} + + +// Clock Gear 3 ------------------------------------------------------------- + +class PuzzGear3 : PuzzleItem +{ + Default + { + PuzzleItem.Number 15; + Inventory.Icon "ARTIGER3"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEAR"; + Tag "$TAG_ARTIPUZZGEAR3"; + } + States + { + Spawn: + AGR3 ABCDEFGH 4 Bright; + Loop; + } +} + + +// Clock Gear 4 ------------------------------------------------------------- + +class PuzzGear4 : PuzzleItem +{ + Default + { + PuzzleItem.Number 16; + Inventory.Icon "ARTIGER4"; + Inventory.PickupMessage "$TXT_ARTIPUZZGEAR"; + Tag "$TAG_ARTIPUZZGEAR4"; + } + States + { + Spawn: + AGR4 ABCDEFGH 4 Bright; + Loop; + } +} + diff --git a/wadsrc/static/zscript/hexen/scriptprojectiles.txt b/wadsrc/static/zscript/hexen/scriptprojectiles.txt new file mode 100644 index 000000000..5bf3f254f --- /dev/null +++ b/wadsrc/static/zscript/hexen/scriptprojectiles.txt @@ -0,0 +1,141 @@ +// Fire Ball ---------------------------------------------------------------- + +class FireBall : Actor +{ + Default + { + Speed 2; + Radius 8; + Height 8; + Damage 4; + DamageType "Fire"; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE + +NOTELEPORT + RenderStyle "Add"; + DeathSound "Fireball"; + } + States + { + Spawn: + FBL1 AB 4 Bright; + Loop; + Death: + XPL1 ABCDEF 4 Bright; + Stop; + } +} + +// Arrow -------------------------------------------------------------------- + +class Arrow : Actor +{ + Default + { + Speed 6; + Radius 8; + Height 4; + Damage 4; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE + +NOTELEPORT + } + States + { + Spawn: + ARRW A -1; + Stop; + Death: + ARRW A 1; + Stop; + } +} + +// Dart --------------------------------------------------------------------- + +class Dart : Actor +{ + Default + { + Speed 6; + Radius 8; + Height 4; + Damage 2; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE + +NOTELEPORT + } + States + { + Spawn: + DART A -1; + Stop; + Death: + DART A 1; + Stop; + } +} + +// Poison Dart -------------------------------------------------------------- + +class PoisonDart : Dart +{ + Default + { + PoisonDamage 20; + } +} + +// Ripper Ball -------------------------------------------------------------- + +class RipperBall : Actor +{ + Default + { + Speed 6; + Radius 8; + Damage 2; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE + +NOTELEPORT +RIPPER + } + States + { + Spawn: + RIPP ABC 3; + Loop; + Death: + CFCF Q 4 Bright; + CFCF R 3 Bright; + CFCF S 4 Bright; + CFCF T 3 Bright; + CFCF U 4 Bright; + CFCF V 3 Bright; + CFCF W 4 Bright; + CFCF X 3 Bright; + CFCF Y 4 Bright; + CFCF Z 3 Bright; + Stop; + } +} + +// Projectile Blade --------------------------------------------------------- + +class ProjectileBlade : Actor +{ + Default + { + Speed 6; + Radius 6; + Height 6; + Damage 3; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE + +NOTELEPORT + } + States + { + Spawn: + BLAD A -1; + Stop; + Death: + BLAD A 1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/hexen/speedboots.txt b/wadsrc/static/zscript/hexen/speedboots.txt new file mode 100644 index 000000000..e5a0364ec --- /dev/null +++ b/wadsrc/static/zscript/hexen/speedboots.txt @@ -0,0 +1,21 @@ + + +class ArtiSpeedBoots : PowerupGiver +{ + Default + { + +FLOATBOB + +COUNTITEM + Inventory.PickupFlash "PickupFlash"; + Inventory.Icon "ARTISPED"; + Inventory.PickupMessage "$TXT_ARTISPEED"; + Tag "$TAG_ARTISPEED"; + Powerup.Type "PowerSpeed"; + } + States + { + Spawn: + SPED ABCDEFGH 3 Bright; + Loop; + } +} From bef71f29e27421fd9850baf04a91aeb6759d6fea Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 10:17:09 +0200 Subject: [PATCH 065/255] - make generation of the AST dump a command line parameter instead of having it depend on running a debug build. - disable generation of the parser's trace file in debug builds. This increases parsing time by a factor of 15 and is only needed when debugging a problem in the grammar. --- src/scripting/zscript/zcc_parser.cpp | 31 +++++++++++++++------------- 1 file changed, 17 insertions(+), 14 deletions(-) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index cc8d187d3..9fefa537d 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -39,6 +39,7 @@ #include "cmdlib.h" #include "m_alloc.h" #include "i_system.h" +#include "m_argv.h" #include "v_text.h" #include "zcc_parser.h" #include "zcc_compile.h" @@ -297,7 +298,7 @@ static void DoParse(int lumpnum) parser = ZCCParseAlloc(malloc); ZCCParseState state; -#ifdef _DEBUG +#if 0 // this costs a lot of time and should only be activated when it's really needed. FILE *f = fopen("trace.txt", "w"); char prompt = '\0'; ZCCParseTrace(f, &prompt); @@ -331,24 +332,26 @@ static void DoParse(int lumpnum) I_Error("%d errors while parsing %s", FScriptPosition::ErrorCounter, Wads.GetLumpFullPath(lumpnum)); } - { - // Make a dump of the AST before running the compiler for diagnostic purposes. -#ifdef _DEBUG +#if 0 if (f != NULL) { fclose(f); } - FString ast = ZCC_PrintAST(state.TopNode); - FString filename = Wads.GetLumpFullName(lumpnum); - FString astfile = ExtractFileBase(filename, false); - astfile << "-before.ast"; - f = fopen(astfile, "w"); - if (f != NULL) - { - fputs(ast.GetChars(), f); - fclose(f); - } #endif + + // Make a dump of the AST before running the compiler for diagnostic purposes. + if (Args->CheckParm("-dumpast")) + { + FString ast = ZCC_PrintAST(state.TopNode); + FString filename = Wads.GetLumpFullName(lumpnum); + FString astfile = ExtractFileBase(filename, false); + astfile << ".ast"; + FILE *ff = fopen(astfile, "w"); + if (ff != NULL) + { + fputs(ast.GetChars(), ff); + fclose(ff); + } } PSymbolTable symtable; From 2c1d9a7a960269b590ea40d98caf86d269dee824 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 15:15:06 +0200 Subject: [PATCH 066/255] - another bunch of Hexen actors converted. --- wadsrc/static/actors/hexen/bats.txt | 47 ---- wadsrc/static/actors/hexen/bishop.txt | 151 ------------ wadsrc/static/actors/hexen/blastradius.txt | 36 --- wadsrc/static/actors/hexen/boostarmor.txt | 21 -- wadsrc/static/actors/hexen/clericboss.txt | 79 ------ wadsrc/static/actors/hexen/clericmace.txt | 46 ---- wadsrc/static/actors/hexen/fighterboss.txt | 80 ------ wadsrc/static/actors/hexen/firedemon.txt | 227 ----------------- wadsrc/static/actors/hexen/flechette.txt | 222 ----------------- wadsrc/static/actors/hexen/fog.txt | 72 ------ wadsrc/static/actors/hexen/mageboss.txt | 83 ------- wadsrc/static/actors/hexen/summon.txt | 61 ----- wadsrc/static/decorate.txt | 12 - wadsrc/static/zscript.txt | 2 +- wadsrc/static/zscript/hexen/bats.txt | 53 ++++ wadsrc/static/zscript/hexen/bishop.txt | 166 +++++++++++++ wadsrc/static/zscript/hexen/blastradius.txt | 42 ++++ wadsrc/static/zscript/hexen/boostarmor.txt | 24 ++ wadsrc/static/zscript/hexen/clericboss.txt | 82 +++++++ wadsrc/static/zscript/hexen/clericmace.txt | 49 ++++ wadsrc/static/zscript/hexen/fighterboss.txt | 83 +++++++ wadsrc/static/zscript/hexen/firedemon.txt | 236 ++++++++++++++++++ wadsrc/static/zscript/hexen/flechette.txt | 254 ++++++++++++++++++++ wadsrc/static/zscript/hexen/fog.txt | 78 ++++++ wadsrc/static/zscript/hexen/mageboss.txt | 86 +++++++ wadsrc/static/zscript/hexen/summon.txt | 71 ++++++ 26 files changed, 1225 insertions(+), 1138 deletions(-) delete mode 100644 wadsrc/static/actors/hexen/bats.txt delete mode 100644 wadsrc/static/actors/hexen/bishop.txt delete mode 100644 wadsrc/static/actors/hexen/blastradius.txt delete mode 100644 wadsrc/static/actors/hexen/boostarmor.txt delete mode 100644 wadsrc/static/actors/hexen/clericboss.txt delete mode 100644 wadsrc/static/actors/hexen/clericmace.txt delete mode 100644 wadsrc/static/actors/hexen/fighterboss.txt delete mode 100644 wadsrc/static/actors/hexen/firedemon.txt delete mode 100644 wadsrc/static/actors/hexen/flechette.txt delete mode 100644 wadsrc/static/actors/hexen/fog.txt delete mode 100644 wadsrc/static/actors/hexen/mageboss.txt delete mode 100644 wadsrc/static/actors/hexen/summon.txt create mode 100644 wadsrc/static/zscript/hexen/bats.txt create mode 100644 wadsrc/static/zscript/hexen/bishop.txt create mode 100644 wadsrc/static/zscript/hexen/blastradius.txt create mode 100644 wadsrc/static/zscript/hexen/boostarmor.txt create mode 100644 wadsrc/static/zscript/hexen/clericboss.txt create mode 100644 wadsrc/static/zscript/hexen/clericmace.txt create mode 100644 wadsrc/static/zscript/hexen/fighterboss.txt create mode 100644 wadsrc/static/zscript/hexen/firedemon.txt create mode 100644 wadsrc/static/zscript/hexen/flechette.txt create mode 100644 wadsrc/static/zscript/hexen/fog.txt create mode 100644 wadsrc/static/zscript/hexen/mageboss.txt create mode 100644 wadsrc/static/zscript/hexen/summon.txt diff --git a/wadsrc/static/actors/hexen/bats.txt b/wadsrc/static/actors/hexen/bats.txt deleted file mode 100644 index 521d46e6e..000000000 --- a/wadsrc/static/actors/hexen/bats.txt +++ /dev/null @@ -1,47 +0,0 @@ - -// Bat Spawner -------------------------------------------------------------- - -ACTOR BatSpawner : SwitchableDecoration -{ - +NOBLOCKMAP +NOSECTOR +NOGRAVITY - RenderStyle None - - action native A_BatSpawnInit(); - action native A_BatSpawn(); - - States - { - Spawn: - Active: - TNT1 A 2 - TNT1 A 2 A_BatSpawnInit - TNT1 A 2 A_BatSpawn - Wait - Inactive: - TNT1 A -1 - Stop - } -} - -// Bat ---------------------------------------------------------------------- - -ACTOR Bat -{ - Speed 5 - Radius 3 - Height 3 - +NOBLOCKMAP +NOGRAVITY +MISSILE - +NOTELEPORT +CANPASS - - action native A_BatMove(); - - States - { - Spawn: - ABAT ABC 2 A_BatMove - Loop - Death: - ABAT A 2 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/bishop.txt b/wadsrc/static/actors/hexen/bishop.txt deleted file mode 100644 index 435420ddd..000000000 --- a/wadsrc/static/actors/hexen/bishop.txt +++ /dev/null @@ -1,151 +0,0 @@ - -// Bishop ------------------------------------------------------------------- - -ACTOR Bishop -{ - Health 130 - Radius 22 - Height 65 - Speed 10 - PainChance 110 - Monster - +FLOAT +NOGRAVITY +NOBLOOD - +TELESTOMP - +DONTOVERLAP - +NOTARGETSWITCH - SeeSound "BishopSight" - AttackSound "BishopAttack" - PainSound "BishopPain" - DeathSound "BishopDeath" - ActiveSound "BishopActiveSounds" - Obituary"$OB_BISHOP" - - action native A_BishopChase(); - action native A_BishopDecide(); - action native A_BishopDoBlur(); - action native A_BishopSpawnBlur(); - action native A_BishopPainBlur(); - action native A_BishopAttack(); - action native A_BishopAttack2(); - - States - { - Spawn: - BISH A 10 A_Look - Loop - See: - BISH A 2 A_Chase - BISH A 2 A_BishopChase - BISH A 2 - BISH B 2 A_BishopChase - BISH B 2 A_Chase - BISH B 2 A_BishopChase - BISH A 1 A_BishopDecide - Loop - Blur: - BISH A 2 A_BishopDoBlur - BISH A 4 A_BishopSpawnBlur - Wait - Pain: - BISH C 6 A_Pain - BISH CCC 6 A_BishopPainBlur - BISH C 0 - Goto See - Missile: - BISH A 3 A_FaceTarget - BISH DE 3 A_FaceTarget - BISH F 3 A_BishopAttack - BISH F 5 A_BishopAttack2 - Wait - Death: - BISH G 6 - BISH H 6 Bright A_Scream - BISH I 5 Bright A_NoBlocking - BISH J 5 BRIGHT A_Explode(random[BishopBoom](25,40)) - BISH K 5 Bright - BISH LM 4 Bright - BISH N 4 A_SpawnItemEx("BishopPuff", 0,0,40, 0,0,0.5) - BISH O 4 A_QueueCorpse - BISH P -1 - Stop - Ice: - BISH X 5 A_FreezeDeath - BISH X 1 A_FreezeDeathChunks - Wait - } -} - -// Bishop puff -------------------------------------------------------------- - -ACTOR BishopPuff -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - BISH QRST 5 - BISH UV 6 - BISH W 5 - Stop - } -} - -// Bishop pain blur --------------------------------------------------------- - -ACTOR BishopPainBlur -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - BISH C 8 - Stop - } -} - -// Bishop FX ---------------------------------------------------------------- - -ACTOR BishopFX -{ - Radius 10 - Height 6 - Speed 10 - Damage 1 - Projectile - +SEEKERMISSILE - -ACTIVATEIMPACT -ACTIVATEPCROSS - +STRIFEDAMAGE - RenderStyle Add - DeathSound "BishopMissileExplode" - States - { - Spawn: - BPFX ABAB 1 Bright A_BishopMissileWeave - BPFX B 0 Bright A_SeekerMissile(2,3) - Loop - Death: - BPFX CDEF 4 Bright - BPFX GH 3 Bright - Stop - } -} - -// Bishop blur -------------------------------------------------------------- - -ACTOR BishopBlur -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - BISH A 16 - BISH A 8 A_SetTranslucent(0.4) - Stop - } -} diff --git a/wadsrc/static/actors/hexen/blastradius.txt b/wadsrc/static/actors/hexen/blastradius.txt deleted file mode 100644 index 561240438..000000000 --- a/wadsrc/static/actors/hexen/blastradius.txt +++ /dev/null @@ -1,36 +0,0 @@ - -ACTOR ArtiBlastRadius : CustomInventory -{ - +FLOATBOB - Inventory.DefMaxAmount - Inventory.PickupFlash "PickupFlash" - +INVBAR +FANCYPICKUPSOUND - Inventory.Icon "ARTIBLST" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIBLASTRADIUS" - Tag "$TAG_ARTIBLASTRADIUS" - States - { - Spawn: - BLST ABCDEFGH 4 Bright - Loop - Use: - TNT1 A 0 A_Blast - } -} - -// Blast Effect ------------------------------------------------------------- - -ACTOR BlastEffect -{ - +NOBLOCKMAP +NOGRAVITY +NOCLIP - +NOTELEPORT - RenderStyle Translucent - Alpha 0.666 - States - { - Spawn: - RADE ABCDEFGHI 4 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/boostarmor.txt b/wadsrc/static/actors/hexen/boostarmor.txt deleted file mode 100644 index b55c29f88..000000000 --- a/wadsrc/static/actors/hexen/boostarmor.txt +++ /dev/null @@ -1,21 +0,0 @@ - -// Boost Armor Artifact (Dragonskin Bracers) -------------------------------- - -ACTOR ArtiBoostArmor : Inventory native -{ - +COUNTITEM - +FLOATBOB - Inventory.DefMaxAmount - Inventory.PickupFlash "PickupFlash" - +INVBAR +FANCYPICKUPSOUND - Inventory.Icon "ARTIBRAC" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIBOOSTARMOR" - Tag "$TAG_ARTIBOOSTARMOR" - States - { - Spawn: - BRAC ABCDEFGH 4 Bright - Loop - } -} diff --git a/wadsrc/static/actors/hexen/clericboss.txt b/wadsrc/static/actors/hexen/clericboss.txt deleted file mode 100644 index dac0f741c..000000000 --- a/wadsrc/static/actors/hexen/clericboss.txt +++ /dev/null @@ -1,79 +0,0 @@ - -// Cleric Boss (Traductus) -------------------------------------------------- - -ACTOR ClericBoss -{ - Health 800 - PainChance 50 - Speed 25 - Radius 16 - Height 64 - Monster - +FLOORCLIP +TELESTOMP - +DONTMORPH - PainSound "PlayerClericPain" - DeathSound "PlayerClericCrazyDeath" - Obituary "$OBCBOSS" - - action native A_ClericAttack(); - - States - { - Spawn: - CLER A 2 - CLER A 3 A_ClassBossHealth - CLER A 5 A_Look - Wait - See: - CLER ABCD 4 A_FastChase - Loop - Pain: - CLER H 4 - CLER H 4 A_Pain - Goto See - Melee: - Missile: - CLER EF 8 A_FaceTarget - CLER G 10 A_ClericAttack - Goto See - Death: - CLER I 6 - CLER K 6 A_Scream - CLER LL 6 - CLER M 6 A_NoBlocking - CLER NOP 6 - CLER Q -1 - Stop - XDeath: - CLER R 5 A_Scream - CLER S 5 - CLER T 5 A_NoBlocking - CLER UVWXYZ 5 - CLER "[" -1 - Stop - Ice: - CLER "\" 5 A_FreezeDeath - CLER "\" 1 A_FreezeDeathChunks - Wait - Burn: - CLER C 5 Bright A_PlaySound("PlayerClericBurnDeath") - FDTH D 4 Bright - FDTH G 5 Bright - FDTH H 4 Bright A_Scream - FDTH I 5 Bright - FDTH J 4 Bright - FDTH K 5 Bright - FDTH L 4 Bright - FDTH M 5 Bright - FDTH N 4 Bright - FDTH O 5 Bright - FDTH P 4 Bright - FDTH Q 5 Bright - FDTH R 4 Bright - FDTH S 5 Bright A_NoBlocking - FDTH T 4 Bright - FDTH U 5 Bright - FDTH V 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/clericmace.txt b/wadsrc/static/actors/hexen/clericmace.txt deleted file mode 100644 index dfb06d958..000000000 --- a/wadsrc/static/actors/hexen/clericmace.txt +++ /dev/null @@ -1,46 +0,0 @@ - -// The Cleric's Mace -------------------------------------------------------- - -ACTOR CWeapMace : ClericWeapon -{ - Weapon.SelectionOrder 3500 - Weapon.KickBack 150 - Weapon.YAdjust -8 - +BLOODSPLATTER - Obituary "$OB_MPCWEAPMACE" - Tag "$TAG_CWEAPMACE" - - action native A_CMaceAttack(); - - States - { - Select: - CMCE A 1 A_Raise - Loop - Deselect: - CMCE A 1 A_Lower - Loop - Ready: - CMCE A 1 A_WeaponReady - Loop - Fire: - CMCE B 2 Offset (60, 20) - CMCE B 1 Offset (30, 33) - CMCE B 2 Offset (8, 45) - CMCE C 1 Offset (8, 45) - CMCE D 1 Offset (8, 45) - CMCE E 1 Offset (8, 45) - CMCE E 1 Offset (-11, 58) A_CMaceAttack - CMCE F 1 Offset (8, 45) - CMCE F 2 Offset (-8, 74) - CMCE F 1 Offset (-20, 96) - CMCE F 8 Offset (-33, 160) - CMCE A 2 Offset (8, 75) A_ReFire - CMCE A 1 Offset (8, 65) - CMCE A 2 Offset (8, 60) - CMCE A 1 Offset (8, 55) - CMCE A 2 Offset (8, 50) - CMCE A 1 Offset (8, 45) - Goto Ready - } -} diff --git a/wadsrc/static/actors/hexen/fighterboss.txt b/wadsrc/static/actors/hexen/fighterboss.txt deleted file mode 100644 index 195c0a1a3..000000000 --- a/wadsrc/static/actors/hexen/fighterboss.txt +++ /dev/null @@ -1,80 +0,0 @@ - -// Fighter Boss (Zedek) ----------------------------------------------------- - -ACTOR FighterBoss -{ - health 800 - PainChance 50 - Speed 25 - Radius 16 - Height 64 - Monster - +FLOORCLIP - +TELESTOMP - +DONTMORPH - PainSound "PlayerFighterPain" - DeathSound "PlayerFighterCrazyDeath" - Obituary "$OB_FBOSS" - - action native A_FighterAttack(); - - States - { - Spawn: - PLAY A 2 - PLAY A 3 A_ClassBossHealth - PLAY A 5 A_Look - Wait - See: - PLAY ABCD 4 A_FastChase - Loop - Pain: - PLAY G 4 - PLAY G 4 A_Pain - Goto See - Melee: - Missile: - PLAY E 8 A_FaceTarget - PLAY F 8 A_FighterAttack - Goto See - Death: - PLAY H 6 - PLAY I 6 A_Scream - PLAY JK 6 - PLAY L 6 A_NoBlocking - PLAY M 6 - PLAY N -1 - Stop - XDeath: - PLAY O 5 A_Scream - PLAY P 5 A_SkullPop - PLAY R 5 A_NoBlocking - PLAY STUV 5 - PLAY W -1 - Stop - Ice: - PLAY X 5 A_FreezeDeath - PLAY X 1 A_FreezeDeathChunks - Wait - Burn: - FDTH A 5 Bright A_PlaySound("PlayerFighterBurnDeath") - FDTH B 4 Bright - FDTH G 5 Bright - FDTH H 4 Bright A_Scream - FDTH I 5 Bright - FDTH J 4 Bright - FDTH K 5 Bright - FDTH L 4 Bright - FDTH M 5 Bright - FDTH N 4 Bright - FDTH O 5 Bright - FDTH P 4 Bright - FDTH Q 5 Bright - FDTH R 4 Bright - FDTH S 5 Bright A_NoBlocking - FDTH T 4 Bright - FDTH U 5 Bright - FDTH V 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/firedemon.txt b/wadsrc/static/actors/hexen/firedemon.txt deleted file mode 100644 index 3f96d22ac..000000000 --- a/wadsrc/static/actors/hexen/firedemon.txt +++ /dev/null @@ -1,227 +0,0 @@ - -// FireDemon ---------------------------------------------------------------- - -ACTOR FireDemon -{ - Health 80 - ReactionTime 8 - PainChance 1 - Speed 13 - Radius 20 - Height 68 - Mass 75 - Damage 1 - Monster - +DROPOFF +NOGRAVITY +FLOAT - +FLOORCLIP +INVULNERABLE +TELESTOMP - SeeSound "FireDemonSpawn" - PainSound "FireDemonPain" - DeathSound "FireDemonDeath" - ActiveSound "FireDemonActive" - Obituary "$OB_FIREDEMON" - - action native A_FiredRocks(); - action native A_FiredChase(); - action native A_FiredAttack(); - action native A_FiredSplotch(); - - States - { - Spawn: - FDMN X 5 Bright - FDMN EFG 10 Bright A_Look - Goto Spawn + 1 - See: - FDMN E 8 Bright - FDMN F 6 Bright - FDMN G 5 Bright - FDMN F 8 Bright - FDMN E 6 Bright - FDMN G 7 Bright A_FiredRocks - FDMN HI 5 Bright - FDMN J 5 Bright A_UnSetInvulnerable - Chase: - FDMN ABC 5 Bright A_FiredChase - Loop - Pain: - FDMN D 0 Bright A_UnSetInvulnerable - FDMN D 6 Bright A_Pain - Goto Chase - Missile: - FDMN K 3 Bright A_FaceTarget - FDMN KKK 5 Bright A_FiredAttack - Goto Chase - Crash: - XDeath: - FDMN M 5 A_FaceTarget - FDMN N 5 A_NoBlocking - FDMN O 5 A_FiredSplotch - Stop - Death: - FDMN D 4 Bright A_FaceTarget - FDMN L 4 Bright A_Scream - FDMN L 4 Bright A_NoBlocking - FDMN L 200 Bright - Stop - Ice: - FDMN R 5 A_FreezeDeath - FDMN R 1 A_FreezeDeathChunks - Wait - } -} - -// FireDemonSplotch1 ------------------------------------------------------- - -ACTOR FireDemonSplotch1 -{ - Health 1000 - ReactionTime 8 - Radius 3 - Height 16 - Mass 100 - +DROPOFF +CORPSE - +NOTELEPORT +FLOORCLIP - States - { - Spawn: - FDMN P 3 - FDMN P 6 A_QueueCorpse - FDMN Y -1 - Stop - } -} - -// FireDemonSplotch2 ------------------------------------------------------- - -ACTOR FireDemonSplotch2 : FireDemonSplotch1 -{ - States - { - Spawn: - FDMN Q 3 - FDMN Q 6 A_QueueCorpse - FDMN Z -1 - Stop - } -} - -// FireDemonRock1 ------------------------------------------------------------ - -ACTOR FireDemonRock1 -{ - Health 1000 - ReactionTime 8 - Radius 3 - Height 5 - Mass 16 - +NOBLOCKMAP +DROPOFF +MISSILE - +NOTELEPORT - - action native A_SmBounce(); - - States - { - Spawn: - FDMN S 4 - Loop - Death: - FDMN S 5 A_SmBounce - XDeath: - FDMN S 200 - Stop - } -} - -// FireDemonRock2 ------------------------------------------------------------ - -ACTOR FireDemonRock2 : FireDemonRock1 -{ - States - { - Spawn: - FDMN T 4 - Loop - Death: - FDMN T 5 A_SmBounce - XDeath: - FDMN T 200 - Stop - } -} - -// FireDemonRock3 ------------------------------------------------------------ - -ACTOR FireDemonRock3 : FireDemonRock1 -{ - States - { - Spawn: - FDMN U 4 - Loop - Death: - FDMN U 5 A_SmBounce - XDeath: - FDMN U 200 - Stop - } -} - -// FireDemonRock4 ------------------------------------------------------------ - -ACTOR FireDemonRock4 : FireDemonRock1 -{ - States - { - Spawn: - FDMN V 4 - Loop - Death: - FDMN V 5 A_SmBounce - XDeath: - FDMN V 200 - Stop - } -} - -// FireDemonRock5 ------------------------------------------------------------ - -ACTOR FireDemonRock5 : FireDemonRock1 -{ - States - { - Spawn: - FDMN W 4 - Loop - Death: - FDMN W 5 A_SmBounce - XDeath: - FDMN W 200 - Stop - } -} - -// FireDemonMissile ----------------------------------------------------------- - -ACTOR FireDemonMissile -{ - Health 1000 - ReactionTime 8 - Speed 10 - Radius 10 - Height 6 - Mass 5 - Damage 1 - DamageType "Fire" - Projectile - RenderStyle Add - DeathSound "FireDemonMissileHit" - States - { - Spawn: - FDMB A 5 Bright - Loop - Death: - FDMB BCDE 5 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/flechette.txt b/wadsrc/static/actors/hexen/flechette.txt deleted file mode 100644 index 2c7fbdc2b..000000000 --- a/wadsrc/static/actors/hexen/flechette.txt +++ /dev/null @@ -1,222 +0,0 @@ - -// Poison Bag (Flechette used by Cleric) ------------------------------------ - -ACTOR PoisonBag -{ - Radius 5 - Height 5 - +NOBLOCKMAP +NOGRAVITY - - action native A_PoisonBagInit(); - - States - { - Spawn: - PSBG A 18 Bright - PSBG B 4 Bright - PSBG C 3 - PSBG C 1 A_PoisonBagInit - Stop - } -} - -// Fire Bomb (Flechette used by Mage) --------------------------------------- - -ACTOR FireBomb -{ - DamageType "Fire" - +NOGRAVITY - +FOILINVUL - RenderStyle Translucent - Alpha 0.6 - DeathSound "FlechetteExplode" - - action native A_TimeBomb(); - - States - { - Spawn: - PSBG A 20 - PSBG AA 10 - PSBG B 4 - PSBG C 4 A_Scream - XPL1 A 4 Bright A_TimeBomb - XPL1 BCDEF 4 Bright - Stop - } -} - -// Throwing Bomb (Flechette used by Fighter) -------------------------------- - -ACTOR ThrowingBomb -{ - Health 48 - Speed 12 - Radius 8 - Height 10 - DamageType "Fire" - +NOBLOCKMAP +DROPOFF +MISSILE - BounceType "HexenCompat" - SeeSound "FlechetteBounce" - DeathSound "FlechetteExplode" - - action native A_CheckThrowBomb(); - action native A_CheckThrowBomb2(); - - States - { - Spawn: - THRW A 4 A_CheckThrowBomb - THRW BCDE 3 A_CheckThrowBomb - THRW F 3 A_CheckThrowBomb2 - Loop - THRW G 6 A_CheckThrowBomb - THRW F 4 A_CheckThrowBomb - THRW H 6 A_CheckThrowBomb - THRW F 4 A_CheckThrowBomb - THRW G 6 A_CheckThrowBomb - THRW F 3 A_CheckThrowBomb - Wait - Death: - CFCF Q 4 Bright A_NoGravity - CFCF R 3 Bright A_Scream - CFCF S 4 Bright A_Explode - CFCF T 3 Bright - CFCF U 4 Bright - CFCF W 3 Bright - CFCF X 4 Bright - CFCF Z 3 Bright - Stop - } -} - -// Poison Bag Artifact (Flechette) ------------------------------------------ - -ACTOR ArtiPoisonBag : Inventory native -{ - +FLOATBOB - Inventory.DefMaxAmount - Inventory.PickupFlash "PickupFlash" - +INVBAR +FANCYPICKUPSOUND - Inventory.Icon "ARTIPSBG" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIPOISONBAG" - Tag "$TAG_ARTIPOISONBAG" - States - { - Spawn: - PSBG A -1 - Stop - } -} - -// Poison Bag 1 (The Cleric's) ---------------------------------------------- - -ACTOR ArtiPoisonBag1 : ArtiPoisonBag native -{ - Inventory.Icon "ARTIPSB1" - Tag "$TAG_ARTIPOISONBAG1" -} - -// Poison Bag 2 (The Mage's) ------------------------------------------------ - -ACTOR ArtiPoisonBag2 : ArtiPoisonBag native -{ - Inventory.Icon "ARTIPSB2" - Tag "$TAG_ARTIPOISONBAG2" -} - -// Poison Bag 3 (The Fighter's) --------------------------------------------- - -ACTOR ArtiPoisonBag3 : ArtiPoisonBag native -{ - Inventory.Icon "ARTIPSB3" - Tag "$TAG_ARTIPOISONBAG3" -} - - -// Poison Bag 4 (Custom Giver) ---------------------------------------------- - -ACTOR ArtiPoisonBagGiver : ArtiPoisonBag native -{ - Inventory.Icon "ARTIPSB4" -} - -// Poison Bag 5 (Custom Thrower) -------------------------------------------- - -ACTOR ArtiPoisonBagShooter : ArtiPoisonBag native -{ - Inventory.Icon "ARTIPSB5" -} - -// Poison Cloud ------------------------------------------------------------- - -ACTOR PoisonCloud native -{ - Radius 20 - Height 30 - Mass 0x7fffffff - +NOBLOCKMAP +NOGRAVITY +DROPOFF - +NODAMAGETHRUST - +DONTSPLASH +FOILINVUL +CANBLAST +BLOODLESSIMPACT +BLOCKEDBYSOLIDACTORS - RenderStyle Translucent - Alpha 0.6 - DeathSound "PoisonShroomDeath" - DamageType PoisonCloud - - action native A_PoisonBagDamage(); - action native A_PoisonBagCheck(); - - States - { - Spawn: - PSBG D 1 - PSBG D 1 A_Scream - PSBG DEEEFFFGGGHHHII 2 A_PoisonBagDamage - PSBG I 2 A_PoisonBagCheck - PSBG I 1 A_PoisonBagCheck - Goto Spawn + 3 - Death: - PSBG HG 7 - PSBG FD 6 - Stop - } -} - -// Poison Shroom ------------------------------------------------------------ - -ACTOR ZPoisonShroom : PoisonBag -{ - Radius 6 - Height 20 - PainChance 255 - Health 30 - Mass 0x7fffffff - +SHOOTABLE - +SOLID - +NOBLOOD - +NOICEDEATH - -NOBLOCKMAP - -NOGRAVITY - PainSound "PoisonShroomPain" - DeathSound "PoisonShroomDeath" - - action native A_PoisonShroom(); - - States - { - Spawn: - SHRM A 5 A_PoisonShroom - Goto Pain+1 - Pain: - SHRM A 6 - SHRM B 8 A_Pain - Goto Spawn - Death: - SHRM CD 5 - SHRM E 5 A_PoisonBagInit - SHRM F -1 - Stop - } -} - diff --git a/wadsrc/static/actors/hexen/fog.txt b/wadsrc/static/actors/hexen/fog.txt deleted file mode 100644 index 18effbb77..000000000 --- a/wadsrc/static/actors/hexen/fog.txt +++ /dev/null @@ -1,72 +0,0 @@ - -// Fog Spawner -------------------------------------------------------------- - -ACTOR FogSpawner -{ - +NOSECTOR +NOBLOCKMAP - +FLOATBOB - +NOGRAVITY - +INVISIBLE - - action native A_FogSpawn(); - - States - { - Spawn: - TNT1 A 20 A_FogSpawn - Loop - } -} - -// Small Fog Patch ---------------------------------------------------------- - -ACTOR FogPatchSmall -{ - Speed 1 - +NOBLOCKMAP +NOGRAVITY +NOCLIP +FLOAT - +NOTELEPORT - RenderStyle Translucent - Alpha 0.6 - - action native A_FogMove(); - - States - { - Spawn: - FOGS ABCDE 7 A_FogMove - Loop - Death: - FOGS E 5 - Stop - } -} - -// Medium Fog Patch --------------------------------------------------------- - -ACTOR FogPatchMedium : FogPatchSmall -{ - States - { - Spawn: - FOGM ABCDE 7 A_FogMove - Loop - Death: - FOGS ABCDE 5 - Goto Super::Death - } -} - -// Large Fog Patch ---------------------------------------------------------- - -ACTOR FogPatchLarge : FogPatchMedium -{ - States - { - Spawn: - FOGL ABCDE 7 A_FogMove - Loop - Death: - FOGM ABCDEF 4 - Goto Super::Death - } -} diff --git a/wadsrc/static/actors/hexen/mageboss.txt b/wadsrc/static/actors/hexen/mageboss.txt deleted file mode 100644 index 95f36954b..000000000 --- a/wadsrc/static/actors/hexen/mageboss.txt +++ /dev/null @@ -1,83 +0,0 @@ - -// Mage Boss (Menelkir) ----------------------------------------------------- - -ACTOR MageBoss -{ - Health 800 - PainChance 50 - Speed 25 - Radius 16 - Height 64 - Monster - +FLOORCLIP +TELESTOMP - +DONTMORPH - PainSound "PlayerMagePain" - DeathSound "PlayerMageCrazyDeath" - Obituary "$OB_MBOSS" - - action native A_MageAttack(); - - States - { - Spawn: - MAGE A 2 - MAGE A 3 A_ClassBossHealth - MAGE A 5 A_Look - Wait - See: - MAGE ABCD 4 A_FastChase - Loop - Pain: - MAGE G 4 - MAGE G 4 A_Pain - Goto See - Melee: - Missile: - MAGE E 8 A_FaceTarget - MAGE F 8 Bright A_MageAttack - Goto See - Death: - MAGE H 6 - MAGE I 6 A_Scream - MAGE JK 6 - MAGE L 6 A_NoBlocking - MAGE M 6 - MAGE N -1 - Stop - XDeath: - MAGE O 5 A_Scream - MAGE P 5 - MAGE R 5 A_NoBlocking - MAGE S 5 - MAGE T 5 - MAGE U 5 - MAGE V 5 - MAGE W 5 - MAGE X -1 - Stop - Ice: - MAGE Y 5 A_FreezeDeath - MAGE Y 1 A_FreezeDeathChunks - Wait - Burn: - FDTH E 5 Bright A_PlaySound("PlayerMageBurnDeath") - FDTH F 4 Bright - FDTH G 5 Bright - FDTH H 4 Bright A_Scream - FDTH I 5 Bright - FDTH J 4 Bright - FDTH K 5 Bright - FDTH L 4 Bright - FDTH M 5 Bright - FDTH N 4 Bright - FDTH O 5 Bright - FDTH P 4 Bright - FDTH Q 5 Bright - FDTH R 4 Bright - FDTH S 5 Bright A_NoBlocking - FDTH T 4 Bright - FDTH U 5 Bright - FDTH V 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/summon.txt b/wadsrc/static/actors/hexen/summon.txt deleted file mode 100644 index 7a2971562..000000000 --- a/wadsrc/static/actors/hexen/summon.txt +++ /dev/null @@ -1,61 +0,0 @@ - -// Dark Servant Artifact ---------------------------------------------------- - -ACTOR ArtiDarkServant : Inventory native -{ - +COUNTITEM - +FLOATBOB - Inventory.RespawnTics 4230 - Inventory.DefMaxAmount - Inventory.PickupFlash "PickupFlash" - +INVBAR +FANCYPICKUPSOUND - Inventory.Icon "ARTISUMN" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTISUMMON" - Tag "$TAG_ARTISUMMON" - States - { - Spawn: - SUMN A 350 - Loop - } -} - -// Summoning Doll ----------------------------------------------------------- - -ACTOR SummoningDoll -{ - Speed 20 - +NOBLOCKMAP +DROPOFF +MISSILE - +NOTELEPORT - - action native A_Summon(); - - States - { - Spawn: - SUMN A 4 - Loop - Death: - SUMN AA 4 - SUMN A 4 A_Summon - Stop - } -} - -// Minotaur Smoke ----------------------------------------------------------- - -ACTOR MinotaurSmoke -{ - +NOBLOCKMAP +NOGRAVITY - +NOTELEPORT - RenderStyle Translucent - Alpha 0.6 - - States - { - Spawn: - MNSM ABCDEFGHIJKLMNOPQ 3 - Stop - } -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 92802dc7e..88ce6a2c7 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,15 +1,3 @@ -#include "actors/hexen/firedemon.txt" -#include "actors/hexen/fog.txt" -#include "actors/hexen/summon.txt" -#include "actors/hexen/flechette.txt" -#include "actors/hexen/clericboss.txt" -#include "actors/hexen/fighterboss.txt" -#include "actors/hexen/mageboss.txt" -#include "actors/hexen/bats.txt" -#include "actors/hexen/bishop.txt" -#include "actors/hexen/blastradius.txt" -#include "actors/hexen/boostarmor.txt" -#include "actors/hexen/clericmace.txt" #include "actors/hexen/clericflame.txt" #include "actors/hexen/clericholy.txt" #include "actors/hexen/clericstaff.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 531c353f5..570d6eee3 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -104,7 +104,6 @@ zscript/hexen/speedboots.txt zscript/hexen/ettin.txt zscript/hexen/centaur.txt zscript/hexen/demons.txt -/* zscript/hexen/firedemon.txt zscript/hexen/fog.txt zscript/hexen/summon.txt @@ -117,6 +116,7 @@ zscript/hexen/bishop.txt zscript/hexen/blastradius.txt zscript/hexen/boostarmor.txt zscript/hexen/clericmace.txt +/* zscript/hexen/clericflame.txt zscript/hexen/clericholy.txt zscript/hexen/clericstaff.txt diff --git a/wadsrc/static/zscript/hexen/bats.txt b/wadsrc/static/zscript/hexen/bats.txt new file mode 100644 index 000000000..f96f93272 --- /dev/null +++ b/wadsrc/static/zscript/hexen/bats.txt @@ -0,0 +1,53 @@ + +// Bat Spawner -------------------------------------------------------------- + +class BatSpawner : SwitchableDecoration +{ + Default + { + +NOBLOCKMAP +NOSECTOR +NOGRAVITY + RenderStyle "None"; + } + + action native void A_BatSpawnInit(); + action native void A_BatSpawn(); + + States + { + Spawn: + Active: + TNT1 A 2; + TNT1 A 2 A_BatSpawnInit; + TNT1 A 2 A_BatSpawn; + Wait; + Inactive: + TNT1 A -1; + Stop; + } +} + +// Bat ---------------------------------------------------------------------- + +class Bat : Actor +{ + Default + { + Speed 5; + Radius 3; + Height 3; + +NOBLOCKMAP +NOGRAVITY +MISSILE + +NOTELEPORT +CANPASS + } + + action native void A_BatMove(); + + States + { + Spawn: + ABAT ABC 2 A_BatMove; + Loop; + Death: + ABAT A 2; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/bishop.txt b/wadsrc/static/zscript/hexen/bishop.txt new file mode 100644 index 000000000..4dbb0d226 --- /dev/null +++ b/wadsrc/static/zscript/hexen/bishop.txt @@ -0,0 +1,166 @@ + +// Bishop ------------------------------------------------------------------- + +class Bishop : Actor +{ + Default + { + Health 130; + Radius 22; + Height 65; + Speed 10; + PainChance 110; + Monster; + +FLOAT +NOGRAVITY +NOBLOOD + +TELESTOMP + +DONTOVERLAP + +NOTARGETSWITCH + SeeSound "BishopSight"; + AttackSound "BishopAttack"; + PainSound "BishopPain"; + DeathSound "BishopDeath"; + ActiveSound "BishopActiveSounds"; + Obituary"$OB_BISHOP"; + } + + action native void A_BishopChase(); + action native void A_BishopDecide(); + action native void A_BishopDoBlur(); + action native void A_BishopSpawnBlur(); + action native void A_BishopPainBlur(); + action native void A_BishopAttack(); + action native void A_BishopAttack2(); + + States + { + Spawn: + BISH A 10 A_Look; + Loop; + See: + BISH A 2 A_Chase; + BISH A 2 A_BishopChase; + BISH A 2; + BISH B 2 A_BishopChase; + BISH B 2 A_Chase; + BISH B 2 A_BishopChase; + BISH A 1 A_BishopDecide; + Loop; + Blur: + BISH A 2 A_BishopDoBlur; + BISH A 4 A_BishopSpawnBlur; + Wait; + Pain: + BISH C 6 A_Pain; + BISH CCC 6 A_BishopPainBlur; + BISH C 0; + Goto See; + Missile: + BISH A 3 A_FaceTarget; + BISH DE 3 A_FaceTarget; + BISH F 3 A_BishopAttack; + BISH F 5 A_BishopAttack2; + Wait; + Death: + BISH G 6; + BISH H 6 Bright A_Scream; + BISH I 5 Bright A_NoBlocking; + BISH J 5 BRIGHT A_Explode(random[BishopBoom](25,40)); + BISH K 5 Bright; + BISH LM 4 Bright; + BISH N 4 A_SpawnItemEx("BishopPuff", 0,0,40, 0,0,0.5); + BISH O 4 A_QueueCorpse; + BISH P -1; + Stop; + Ice: + BISH X 5 A_FreezeDeath; + BISH X 1 A_FreezeDeathChunks; + Wait; + } +} + +// Bishop puff -------------------------------------------------------------- + +class BishopPuff : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + BISH QRST 5; + BISH UV 6; + BISH W 5; + Stop; + } +} + +// Bishop pain blur --------------------------------------------------------- + +class BishopPainBlur : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + BISH C 8; + Stop; + } +} + +// Bishop FX ---------------------------------------------------------------- + +class BishopFX : Actor +{ + Default + { + Radius 10; + Height 6; + Speed 10; + Damage 1; + Projectile; + +SEEKERMISSILE + -ACTIVATEIMPACT -ACTIVATEPCROSS + +STRIFEDAMAGE + RenderStyle "Add"; + DeathSound "BishopMissileExplode"; + } + States + { + Spawn: + BPFX ABAB 1 Bright A_BishopMissileWeave; + BPFX B 0 Bright A_SeekerMissile(2,3); + Loop; + Death: + BPFX CDEF 4 Bright; + BPFX GH 3 Bright; + Stop; + } +} + +// Bishop blur -------------------------------------------------------------- + +class BishopBlur : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + BISH A 16; + BISH A 8 A_SetTranslucent(0.4); + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/blastradius.txt b/wadsrc/static/zscript/hexen/blastradius.txt new file mode 100644 index 000000000..17ac75dc3 --- /dev/null +++ b/wadsrc/static/zscript/hexen/blastradius.txt @@ -0,0 +1,42 @@ + +class ArtiBlastRadius : CustomInventory +{ + Default + { + +FLOATBOB + Inventory.DefMaxAmount; + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.INVBAR +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIBLST"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIBLASTRADIUS"; + Tag "$TAG_ARTIBLASTRADIUS"; + } + States + { + Spawn: + BLST ABCDEFGH 4 Bright; + Loop; + Use: + TNT1 A 0 A_Blast; + } +} + +// Blast Effect ------------------------------------------------------------- + +class BlastEffect : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY +NOCLIP + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.666; + } + States + { + Spawn: + RADE ABCDEFGHI 4; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/boostarmor.txt b/wadsrc/static/zscript/hexen/boostarmor.txt new file mode 100644 index 000000000..4c14b69bc --- /dev/null +++ b/wadsrc/static/zscript/hexen/boostarmor.txt @@ -0,0 +1,24 @@ + +// Boost Armor Artifact (Dragonskin Bracers) -------------------------------- + +class ArtiBoostArmor : Inventory native +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.DefMaxAmount; + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.INVBAR +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIBRAC"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIBOOSTARMOR"; + Tag "$TAG_ARTIBOOSTARMOR"; + } + States + { + Spawn: + BRAC ABCDEFGH 4 Bright; + Loop; + } +} diff --git a/wadsrc/static/zscript/hexen/clericboss.txt b/wadsrc/static/zscript/hexen/clericboss.txt new file mode 100644 index 000000000..6493cde89 --- /dev/null +++ b/wadsrc/static/zscript/hexen/clericboss.txt @@ -0,0 +1,82 @@ + +// Cleric Boss (Traductus) -------------------------------------------------- + +class ClericBoss : Actor +{ + Default + { + Health 800; + PainChance 50; + Speed 25; + Radius 16; + Height 64; + Monster; + +FLOORCLIP +TELESTOMP + +DONTMORPH + PainSound "PlayerClericPain"; + DeathSound "PlayerClericCrazyDeath"; + Obituary "$OBCBOSS"; + } + + action native void A_ClericAttack(); + + States + { + Spawn: + CLER A 2; + CLER A 3 A_ClassBossHealth; + CLER A 5 A_Look; + Wait; + See: + CLER ABCD 4 A_FastChase; + Loop; + Pain: + CLER H 4; + CLER H 4 A_Pain; + Goto See; + Melee: + Missile: + CLER EF 8 A_FaceTarget; + CLER G 10 A_ClericAttack; + Goto See; + Death: + CLER I 6; + CLER K 6 A_Scream; + CLER LL 6; + CLER M 6 A_NoBlocking; + CLER NOP 6; + CLER Q -1; + Stop; + XDeath: + CLER R 5 A_Scream; + CLER S 5; + CLER T 5 A_NoBlocking; + CLER UVWXYZ 5; + CLER [ -1; + Stop; + Ice: + CLER \ 5 A_FreezeDeath; + CLER \ 1 A_FreezeDeathChunks; + Wait; + Burn: + CLER C 5 Bright A_PlaySound("PlayerClericBurnDeath"); + FDTH D 4 Bright ; + FDTH G 5 Bright ; + FDTH H 4 Bright A_Scream; + FDTH I 5 Bright ; + FDTH J 4 Bright ; + FDTH K 5 Bright ; + FDTH L 4 Bright ; + FDTH M 5 Bright ; + FDTH N 4 Bright ; + FDTH O 5 Bright ; + FDTH P 4 Bright ; + FDTH Q 5 Bright ; + FDTH R 4 Bright ; + FDTH S 5 Bright A_NoBlocking; + FDTH T 4 Bright ; + FDTH U 5 Bright ; + FDTH V 4 Bright ; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/clericmace.txt b/wadsrc/static/zscript/hexen/clericmace.txt new file mode 100644 index 000000000..5e00b9c3b --- /dev/null +++ b/wadsrc/static/zscript/hexen/clericmace.txt @@ -0,0 +1,49 @@ + +// The Cleric's Mace -------------------------------------------------------- + +class CWeapMace : ClericWeapon +{ + Default + { + Weapon.SelectionOrder 3500; + Weapon.KickBack 150; + Weapon.YAdjust -8; + +BLOODSPLATTER + Obituary "$OB_MPCWEAPMACE"; + Tag "$TAG_CWEAPMACE"; + } + + action native void A_CMaceAttack(); + + States + { + Select: + CMCE A 1 A_Raise; + Loop; + Deselect: + CMCE A 1 A_Lower; + Loop; + Ready: + CMCE A 1 A_WeaponReady; + Loop; + Fire: + CMCE B 2 Offset (60, 20); + CMCE B 1 Offset (30, 33); + CMCE B 2 Offset (8, 45); + CMCE C 1 Offset (8, 45); + CMCE D 1 Offset (8, 45); + CMCE E 1 Offset (8, 45); + CMCE E 1 Offset (-11, 58) A_CMaceAttack; + CMCE F 1 Offset (8, 45); + CMCE F 2 Offset (-8, 74); + CMCE F 1 Offset (-20, 96); + CMCE F 8 Offset (-33, 160); + CMCE A 2 Offset (8, 75) A_ReFire; + CMCE A 1 Offset (8, 65); + CMCE A 2 Offset (8, 60); + CMCE A 1 Offset (8, 55); + CMCE A 2 Offset (8, 50); + CMCE A 1 Offset (8, 45); + Goto Ready; + } +} diff --git a/wadsrc/static/zscript/hexen/fighterboss.txt b/wadsrc/static/zscript/hexen/fighterboss.txt new file mode 100644 index 000000000..aa3e28ce7 --- /dev/null +++ b/wadsrc/static/zscript/hexen/fighterboss.txt @@ -0,0 +1,83 @@ + +// Fighter Boss (Zedek) ----------------------------------------------------- + +class FighterBoss : Actor +{ + Default + { + health 800; + PainChance 50; + Speed 25; + Radius 16; + Height 64; + Monster; + +FLOORCLIP + +TELESTOMP + +DONTMORPH + PainSound "PlayerFighterPain"; + DeathSound "PlayerFighterCrazyDeath"; + Obituary "$OB_FBOSS"; + } + + action native void A_FighterAttack(); + + States + { + Spawn: + PLAY A 2; + PLAY A 3 A_ClassBossHealth; + PLAY A 5 A_Look; + Wait; + See: + PLAY ABCD 4 A_FastChase; + Loop; + Pain: + PLAY G 4; + PLAY G 4 A_Pain; + Goto See; + Melee: + Missile: + PLAY E 8 A_FaceTarget; + PLAY F 8 A_FighterAttack; + Goto See; + Death: + PLAY H 6; + PLAY I 6 A_Scream; + PLAY JK 6; + PLAY L 6 A_NoBlocking; + PLAY M 6; + PLAY N -1; + Stop; + XDeath: + PLAY O 5 A_Scream; + PLAY P 5 A_SkullPop; + PLAY R 5 A_NoBlocking; + PLAY STUV 5; + PLAY W -1; + Stop; + Ice: + PLAY X 5 A_FreezeDeath; + PLAY X 1 A_FreezeDeathChunks; + Wait; + Burn: + FDTH A 5 Bright A_PlaySound("PlayerFighterBurnDeath"); + FDTH B 4 Bright; + FDTH G 5 Bright; + FDTH H 4 Bright A_Scream; + FDTH I 5 Bright; + FDTH J 4 Bright; + FDTH K 5 Bright; + FDTH L 4 Bright; + FDTH M 5 Bright; + FDTH N 4 Bright; + FDTH O 5 Bright; + FDTH P 4 Bright; + FDTH Q 5 Bright; + FDTH R 4 Bright; + FDTH S 5 Bright A_NoBlocking; + FDTH T 4 Bright; + FDTH U 5 Bright; + FDTH V 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/firedemon.txt b/wadsrc/static/zscript/hexen/firedemon.txt new file mode 100644 index 000000000..f79303400 --- /dev/null +++ b/wadsrc/static/zscript/hexen/firedemon.txt @@ -0,0 +1,236 @@ + +// FireDemon ---------------------------------------------------------------- + +class FireDemon : Actor +{ + Default + { + Health 80; + ReactionTime 8; + PainChance 1; + Speed 13; + Radius 20; + Height 68; + Mass 75; + Damage 1; + Monster; + +DROPOFF +NOGRAVITY +FLOAT + +FLOORCLIP +INVULNERABLE +TELESTOMP + SeeSound "FireDemonSpawn"; + PainSound "FireDemonPain"; + DeathSound "FireDemonDeath"; + ActiveSound "FireDemonActive"; + Obituary "$OB_FIREDEMON"; + } + + action native void A_FiredRocks(); + action native void A_FiredChase(); + action native void A_FiredAttack(); + action native void A_FiredSplotch(); + + States + { + Spawn: + FDMN X 5 Bright; + FDMN EFG 10 Bright A_Look; + Goto Spawn + 1; + See: + FDMN E 8 Bright; + FDMN F 6 Bright; + FDMN G 5 Bright; + FDMN F 8 Bright; + FDMN E 6 Bright; + FDMN G 7 Bright A_FiredRocks; + FDMN HI 5 Bright; + FDMN J 5 Bright A_UnSetInvulnerable; + Chase: + FDMN ABC 5 Bright A_FiredChase; + Loop; + Pain: + FDMN D 0 Bright A_UnSetInvulnerable; + FDMN D 6 Bright A_Pain; + Goto Chase; + Missile: + FDMN K 3 Bright A_FaceTarget; + FDMN KKK 5 Bright A_FiredAttack; + Goto Chase; + Crash: + XDeath: + FDMN M 5 A_FaceTarget; + FDMN N 5 A_NoBlocking; + FDMN O 5 A_FiredSplotch; + Stop; + Death: + FDMN D 4 Bright A_FaceTarget; + FDMN L 4 Bright A_Scream; + FDMN L 4 Bright A_NoBlocking; + FDMN L 200 Bright; + Stop; + Ice: + FDMN R 5 A_FreezeDeath; + FDMN R 1 A_FreezeDeathChunks; + Wait; + } +} + +// FireDemonSplotch1 ------------------------------------------------------- + +class FireDemonSplotch1 : Actor +{ + Default + { + ReactionTime 8; + Radius 3; + Height 16; + Mass 100; + +DROPOFF +CORPSE + +NOTELEPORT +FLOORCLIP + } + States + { + Spawn: + FDMN P 3; + FDMN P 6 A_QueueCorpse; + FDMN Y -1; + Stop; + } +} + +// FireDemonSplotch2 ------------------------------------------------------- + +class FireDemonSplotch2 : FireDemonSplotch1 +{ + States + { + Spawn: + FDMN Q 3; + FDMN Q 6 A_QueueCorpse; + FDMN Z -1; + Stop; + } +} + +// FireDemonRock1 ------------------------------------------------------------ + +class FireDemonRock1 : Actor +{ + Default + { + ReactionTime 8; + Radius 3; + Height 5; + Mass 16; + +NOBLOCKMAP +DROPOFF +MISSILE + +NOTELEPORT + } + + action native void A_SmBounce(); + + States + { + Spawn: + FDMN S 4; + Loop; + Death: + FDMN S 5 A_SmBounce; + XDeath: + FDMN S 200; + Stop; + } +} + +// FireDemonRock2 ------------------------------------------------------------ + +class FireDemonRock2 : FireDemonRock1 +{ + States + { + Spawn: + FDMN T 4; + Loop; + Death: + FDMN T 5 A_SmBounce; + XDeath: + FDMN T 200; + Stop; + } +} + +// FireDemonRock3 ------------------------------------------------------------ + +class FireDemonRock3 : FireDemonRock1 +{ + States + { + Spawn: + FDMN U 4; + Loop; + Death: + FDMN U 5 A_SmBounce; + XDeath: + FDMN U 200; + Stop; + } +} + +// FireDemonRock4 ------------------------------------------------------------ + +class FireDemonRock4 : FireDemonRock1 +{ + States + { + Spawn: + FDMN V 4; + Loop; + Death: + FDMN V 5 A_SmBounce; + XDeath: + FDMN V 200; + Stop; + } +} + +// FireDemonRock5 ------------------------------------------------------------ + +class FireDemonRock5 : FireDemonRock1 +{ + States + { + Spawn: + FDMN W 4; + Loop; + Death: + FDMN W 5 A_SmBounce; + XDeath: + FDMN W 200; + Stop; + } +} + +// FireDemonMissile ----------------------------------------------------------- + +class FireDemonMissile : Actor +{ + Default + { + ReactionTime 8; + Speed 10; + Radius 10; + Height 6; + Mass 5; + Damage 1; + DamageType "Fire"; + Projectile; + RenderStyle "Add"; + DeathSound "FireDemonMissileHit"; + } + States + { + Spawn: + FDMB A 5 Bright; + Loop; + Death: + FDMB BCDE 5 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/flechette.txt b/wadsrc/static/zscript/hexen/flechette.txt new file mode 100644 index 000000000..4b3cd914c --- /dev/null +++ b/wadsrc/static/zscript/hexen/flechette.txt @@ -0,0 +1,254 @@ + +// Poison Bag (Flechette used by Cleric) ------------------------------------ + +class PoisonBag : Actor +{ + Default + { + Radius 5; + Height 5; + +NOBLOCKMAP +NOGRAVITY + } + + action native void A_PoisonBagInit(); + + States + { + Spawn: + PSBG A 18 Bright; + PSBG B 4 Bright; + PSBG C 3; + PSBG C 1 A_PoisonBagInit; + Stop; + } +} + +// Fire Bomb (Flechette used by Mage) --------------------------------------- + +class FireBomb : Actor +{ + Default + { + DamageType "Fire"; + +NOGRAVITY + +FOILINVUL + RenderStyle "Translucent"; + Alpha 0.6; + DeathSound "FlechetteExplode"; + } + + action native void A_TimeBomb(); + + States + { + Spawn: + PSBG A 20; + PSBG AA 10; + PSBG B 4; + PSBG C 4 A_Scream; + XPL1 A 4 Bright A_TimeBomb; + XPL1 BCDEF 4 Bright; + Stop; + } +} + +// Throwing Bomb (Flechette used by Fighter) -------------------------------- + +class ThrowingBomb : Actor +{ + Default + { + Health 48; + Speed 12; + Radius 8; + Height 10; + DamageType "Fire"; + +NOBLOCKMAP +DROPOFF +MISSILE + BounceType "HexenCompat"; + SeeSound "FlechetteBounce"; + DeathSound "FlechetteExplode"; + } + + action native void A_CheckThrowBomb(); + action native void A_CheckThrowBomb2(); + + States + { + Spawn: + THRW A 4 A_CheckThrowBomb; + THRW BCDE 3 A_CheckThrowBomb; + THRW F 3 A_CheckThrowBomb2; + Loop; + THRW G 6 A_CheckThrowBomb; + THRW F 4 A_CheckThrowBomb; + THRW H 6 A_CheckThrowBomb; + THRW F 4 A_CheckThrowBomb; + THRW G 6 A_CheckThrowBomb; + THRW F 3 A_CheckThrowBomb; + Wait; + Death: + CFCF Q 4 Bright A_NoGravity; + CFCF R 3 Bright A_Scream; + CFCF S 4 Bright A_Explode; + CFCF T 3 Bright; + CFCF U 4 Bright; + CFCF W 3 Bright; + CFCF X 4 Bright; + CFCF Z 3 Bright; + Stop; + } +} + +// Poison Bag Artifact (Flechette) ------------------------------------------ + +class ArtiPoisonBag : Inventory native +{ + Default + { + +FLOATBOB + Inventory.DefMaxAmount; + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.INVBAR +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTIPSBG"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIPOISONBAG"; + Tag "$TAG_ARTIPOISONBAG"; + } + States + { + Spawn: + PSBG A -1; + Stop; + } +} + +// Poison Bag 1 (The Cleric's) ---------------------------------------------- + +class ArtiPoisonBag1 : ArtiPoisonBag native +{ + Default + { + Inventory.Icon "ARTIPSB1"; + Tag "$TAG_ARTIPOISONBAG1"; + } +} + +// Poison Bag 2 (The Mage's) ------------------------------------------------ + +class ArtiPoisonBag2 : ArtiPoisonBag native +{ + Default + { + Inventory.Icon "ARTIPSB2"; + Tag "$TAG_ARTIPOISONBAG2"; + } +} + +// Poison Bag 3 (The Fighter's) --------------------------------------------- + +class ArtiPoisonBag3 : ArtiPoisonBag native +{ + Default + { + Inventory.Icon "ARTIPSB3"; + Tag "$TAG_ARTIPOISONBAG3"; + } +} + +// Poison Bag 4 (Custom Giver) ---------------------------------------------- + +class ArtiPoisonBagGiver : ArtiPoisonBag native +{ + Default + { + Inventory.Icon "ARTIPSB4"; + } +} + +// Poison Bag 5 (Custom Thrower) -------------------------------------------- + +class ArtiPoisonBagShooter : ArtiPoisonBag native +{ + Default + { + Inventory.Icon "ARTIPSB5"; + } +} + +// Poison Cloud ------------------------------------------------------------- + +class PoisonCloud : Actor native +{ + Default + { + Radius 20; + Height 30; + Mass 0x7fffffff; + +NOBLOCKMAP +NOGRAVITY +DROPOFF + +NODAMAGETHRUST + +DONTSPLASH +FOILINVUL +CANBLAST +BLOODLESSIMPACT +BLOCKEDBYSOLIDACTORS + RenderStyle "Translucent"; + Alpha 0.6; + DeathSound "PoisonShroomDeath"; + DamageType "PoisonCloud"; + } + + action native void A_PoisonBagDamage(); + action native void A_PoisonBagCheck(); + + States + { + Spawn: + PSBG D 1; + PSBG D 1 A_Scream; + PSBG DEEEFFFGGGHHHII 2 A_PoisonBagDamage; + PSBG I 2 A_PoisonBagCheck; + PSBG I 1 A_PoisonBagCheck; + Goto Spawn + 3; + Death: + PSBG HG 7; + PSBG FD 6; + Stop; + } +} + +// Poison Shroom ------------------------------------------------------------ + +class ZPoisonShroom : PoisonBag +{ + Default + { + Radius 6; + Height 20; + PainChance 255; + Health 30; + Mass 0x7fffffff; + +SHOOTABLE + +SOLID + +NOBLOOD + +NOICEDEATH + -NOBLOCKMAP + -NOGRAVITY + PainSound "PoisonShroomPain"; + DeathSound "PoisonShroomDeath"; + } + + action native void A_PoisonShroom(); + + States + { + Spawn: + SHRM A 5 A_PoisonShroom; + Goto Pain+1; + Pain: + SHRM A 6; + SHRM B 8 A_Pain; + Goto Spawn; + Death: + SHRM CD 5; + SHRM E 5 A_PoisonBagInit; + SHRM F -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/hexen/fog.txt b/wadsrc/static/zscript/hexen/fog.txt new file mode 100644 index 000000000..84cc6c03e --- /dev/null +++ b/wadsrc/static/zscript/hexen/fog.txt @@ -0,0 +1,78 @@ + +// Fog Spawner -------------------------------------------------------------- + +class FogSpawner : Actor +{ + Default + { + +NOSECTOR +NOBLOCKMAP + +FLOATBOB + +NOGRAVITY + +INVISIBLE + } + + action native void A_FogSpawn(); + + States + { + Spawn: + TNT1 A 20 A_FogSpawn; + Loop; + } +} + +// Small Fog Patch ---------------------------------------------------------- + +class FogPatchSmall : Actor +{ + Default + { + Speed 1; + +NOBLOCKMAP +NOGRAVITY +NOCLIP +FLOAT + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.6; + } + + action native void A_FogMove(); + + States + { + Spawn: + FOGS ABCDE 7 A_FogMove; + Loop; + Death: + FOGS E 5; + Stop; + } +} + +// Medium Fog Patch --------------------------------------------------------- + +class FogPatchMedium : FogPatchSmall +{ + States + { + Spawn: + FOGM ABCDE 7 A_FogMove; + Loop; + Death: + FOGS ABCDE 5; + Goto Super::Death; + } +} + +// Large Fog Patch ---------------------------------------------------------- + +class FogPatchLarge : FogPatchMedium +{ + States + { + Spawn: + FOGL ABCDE 7 A_FogMove; + Loop; + Death: + FOGM ABCDEF 4; + Goto Super::Death; + } +} diff --git a/wadsrc/static/zscript/hexen/mageboss.txt b/wadsrc/static/zscript/hexen/mageboss.txt new file mode 100644 index 000000000..083d21016 --- /dev/null +++ b/wadsrc/static/zscript/hexen/mageboss.txt @@ -0,0 +1,86 @@ + +// Mage Boss (Menelkir) ----------------------------------------------------- + +class MageBoss : Actor +{ + Default + { + Health 800; + PainChance 50; + Speed 25; + Radius 16; + Height 64; + Monster; + +FLOORCLIP +TELESTOMP + +DONTMORPH + PainSound "PlayerMagePain"; + DeathSound "PlayerMageCrazyDeath"; + Obituary "$OB_MBOSS"; + } + + action native void A_MageAttack(); + + States + { + Spawn: + MAGE A 2; + MAGE A 3 A_ClassBossHealth; + MAGE A 5 A_Look; + Wait; + See: + MAGE ABCD 4 A_FastChase; + Loop; + Pain: + MAGE G 4; + MAGE G 4 A_Pain; + Goto See; + Melee: + Missile: + MAGE E 8 A_FaceTarget; + MAGE F 8 Bright A_MageAttack; + Goto See; + Death: + MAGE H 6; + MAGE I 6 A_Scream; + MAGE JK 6; + MAGE L 6 A_NoBlocking; + MAGE M 6; + MAGE N -1; + Stop; + XDeath: + MAGE O 5 A_Scream; + MAGE P 5; + MAGE R 5 A_NoBlocking; + MAGE S 5; + MAGE T 5; + MAGE U 5; + MAGE V 5; + MAGE W 5; + MAGE X -1; + Stop; + Ice: + MAGE Y 5 A_FreezeDeath; + MAGE Y 1 A_FreezeDeathChunks; + Wait; + Burn: + FDTH E 5 Bright A_PlaySound("PlayerMageBurnDeath"); + FDTH F 4 Bright; + FDTH G 5 Bright; + FDTH H 4 Bright A_Scream; + FDTH I 5 Bright; + FDTH J 4 Bright; + FDTH K 5 Bright; + FDTH L 4 Bright; + FDTH M 5 Bright; + FDTH N 4 Bright; + FDTH O 5 Bright; + FDTH P 4 Bright; + FDTH Q 5 Bright; + FDTH R 4 Bright; + FDTH S 5 Bright A_NoBlocking; + FDTH T 4 Bright; + FDTH U 5 Bright; + FDTH V 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/summon.txt b/wadsrc/static/zscript/hexen/summon.txt new file mode 100644 index 000000000..395d4760d --- /dev/null +++ b/wadsrc/static/zscript/hexen/summon.txt @@ -0,0 +1,71 @@ + +// Dark Servant Artifact ---------------------------------------------------- + +class ArtiDarkServant : Inventory native +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.RespawnTics 4230; + Inventory.DefMaxAmount; + Inventory.PickupFlash "PickupFlash"; + +INVENTORY.INVBAR + +INVENTORY.FANCYPICKUPSOUND + Inventory.Icon "ARTISUMN"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTISUMMON"; + Tag "$TAG_ARTISUMMON"; + } + States + { + Spawn: + SUMN A 350; + Loop; + } +} + +// Summoning Doll ----------------------------------------------------------- + +class SummoningDoll : Actor +{ + Default + { + Speed 20; + +NOBLOCKMAP +DROPOFF +MISSILE + +NOTELEPORT + } + + action native void A_Summon(); + + States + { + Spawn: + SUMN A 4; + Loop; + Death: + SUMN AA 4; + SUMN A 4 A_Summon; + Stop; + } +} + +// Minotaur Smoke ----------------------------------------------------------- + +class MinotaurSmoke : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.6; + + } + States + { + Spawn: + MNSM ABCDEFGHIJKLMNOPQ 3; + Stop; + } +} From 1bdc1ccb6c8832be1558271fcd81d9365861b794 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 18:11:13 +0200 Subject: [PATCH 067/255] - converted the remaining Hexen actors. --- wadsrc/static/actors/hexen/clericflame.txt | 196 ---------- wadsrc/static/actors/hexen/clericholy.txt | 237 ------------ wadsrc/static/actors/hexen/clericstaff.txt | 96 ----- wadsrc/static/actors/hexen/dragon.txt | 117 ------ wadsrc/static/actors/hexen/fighteraxe.txt | 113 ------ wadsrc/static/actors/hexen/fighterfist.txt | 64 ---- wadsrc/static/actors/hexen/fighterhammer.txt | 101 ----- wadsrc/static/actors/hexen/fighterquietus.txt | 164 -------- wadsrc/static/actors/hexen/healingradius.txt | 23 -- wadsrc/static/actors/hexen/heresiarch.txt | 335 ---------------- wadsrc/static/actors/hexen/iceguy.txt | 167 -------- wadsrc/static/actors/hexen/magecone.txt | 89 ----- wadsrc/static/actors/hexen/magelightning.txt | 154 -------- wadsrc/static/actors/hexen/magestaff.txt | 142 ------- wadsrc/static/actors/hexen/magewand.txt | 73 ---- wadsrc/static/actors/hexen/serpent.txt | 224 ----------- wadsrc/static/actors/hexen/spike.txt | 104 ----- wadsrc/static/actors/hexen/teleportother.txt | 112 ------ wadsrc/static/actors/hexen/wraith.txt | 218 ----------- wadsrc/static/actors/strife/strifestuff.txt | 4 +- wadsrc/static/decorate.txt | 20 - wadsrc/static/zscript.txt | 2 - wadsrc/static/zscript/hexen/clericflame.txt | 211 ++++++++++ wadsrc/static/zscript/hexen/clericholy.txt | 267 +++++++++++++ wadsrc/static/zscript/hexen/clericstaff.txt | 105 +++++ wadsrc/static/zscript/hexen/dragon.txt | 126 ++++++ wadsrc/static/zscript/hexen/fighteraxe.txt | 122 ++++++ wadsrc/static/zscript/hexen/fighterfist.txt | 70 ++++ wadsrc/static/zscript/hexen/fighterhammer.txt | 110 ++++++ .../static/zscript/hexen/fighterquietus.txt | 185 +++++++++ wadsrc/static/zscript/hexen/healingradius.txt | 26 ++ wadsrc/static/zscript/hexen/heresiarch.txt | 362 ++++++++++++++++++ wadsrc/static/zscript/hexen/iceguy.txt | 185 +++++++++ wadsrc/static/zscript/hexen/magecone.txt | 98 +++++ wadsrc/static/zscript/hexen/magelightning.txt | 169 ++++++++ wadsrc/static/zscript/hexen/magestaff.txt | 160 ++++++++ wadsrc/static/zscript/hexen/magewand.txt | 81 ++++ wadsrc/static/zscript/hexen/serpent.txt | 238 ++++++++++++ wadsrc/static/zscript/hexen/spike.txt | 116 ++++++ wadsrc/static/zscript/hexen/teleportother.txt | 130 +++++++ wadsrc/static/zscript/hexen/wraith.txt | 236 ++++++++++++ 41 files changed, 2999 insertions(+), 2753 deletions(-) delete mode 100644 wadsrc/static/actors/hexen/clericflame.txt delete mode 100644 wadsrc/static/actors/hexen/clericholy.txt delete mode 100644 wadsrc/static/actors/hexen/clericstaff.txt delete mode 100644 wadsrc/static/actors/hexen/dragon.txt delete mode 100644 wadsrc/static/actors/hexen/fighteraxe.txt delete mode 100644 wadsrc/static/actors/hexen/fighterfist.txt delete mode 100644 wadsrc/static/actors/hexen/fighterhammer.txt delete mode 100644 wadsrc/static/actors/hexen/fighterquietus.txt delete mode 100644 wadsrc/static/actors/hexen/healingradius.txt delete mode 100644 wadsrc/static/actors/hexen/heresiarch.txt delete mode 100644 wadsrc/static/actors/hexen/iceguy.txt delete mode 100644 wadsrc/static/actors/hexen/magecone.txt delete mode 100644 wadsrc/static/actors/hexen/magelightning.txt delete mode 100644 wadsrc/static/actors/hexen/magestaff.txt delete mode 100644 wadsrc/static/actors/hexen/magewand.txt delete mode 100644 wadsrc/static/actors/hexen/serpent.txt delete mode 100644 wadsrc/static/actors/hexen/spike.txt delete mode 100644 wadsrc/static/actors/hexen/teleportother.txt delete mode 100644 wadsrc/static/actors/hexen/wraith.txt create mode 100644 wadsrc/static/zscript/hexen/clericflame.txt create mode 100644 wadsrc/static/zscript/hexen/clericholy.txt create mode 100644 wadsrc/static/zscript/hexen/clericstaff.txt create mode 100644 wadsrc/static/zscript/hexen/dragon.txt create mode 100644 wadsrc/static/zscript/hexen/fighteraxe.txt create mode 100644 wadsrc/static/zscript/hexen/fighterfist.txt create mode 100644 wadsrc/static/zscript/hexen/fighterhammer.txt create mode 100644 wadsrc/static/zscript/hexen/fighterquietus.txt create mode 100644 wadsrc/static/zscript/hexen/healingradius.txt create mode 100644 wadsrc/static/zscript/hexen/heresiarch.txt create mode 100644 wadsrc/static/zscript/hexen/iceguy.txt create mode 100644 wadsrc/static/zscript/hexen/magecone.txt create mode 100644 wadsrc/static/zscript/hexen/magelightning.txt create mode 100644 wadsrc/static/zscript/hexen/magestaff.txt create mode 100644 wadsrc/static/zscript/hexen/magewand.txt create mode 100644 wadsrc/static/zscript/hexen/serpent.txt create mode 100644 wadsrc/static/zscript/hexen/spike.txt create mode 100644 wadsrc/static/zscript/hexen/teleportother.txt create mode 100644 wadsrc/static/zscript/hexen/wraith.txt diff --git a/wadsrc/static/actors/hexen/clericflame.txt b/wadsrc/static/actors/hexen/clericflame.txt deleted file mode 100644 index b6688a6ed..000000000 --- a/wadsrc/static/actors/hexen/clericflame.txt +++ /dev/null @@ -1,196 +0,0 @@ - -// The Cleric's Flame Strike ------------------------------------------------ - -ACTOR CWeapFlame : ClericWeapon -{ - +NOGRAVITY - Weapon.SelectionOrder 1000 - Weapon.AmmoUse 4 - Weapon.AmmoGive 25 - Weapon.KickBack 150 - Weapon.YAdjust 10 - Weapon.AmmoType1 "Mana2" - Inventory.PickupMessage "$TXT_WEAPON_C3" - Tag "$TAG_CWEAPFLAME" - - action native A_CFlameAttack(); - - States - { - Spawn: - WCFM ABCDEFGH 4 Bright - Loop - Select: - CFLM A 1 A_Raise - Loop - Deselect: - CFLM A 1 A_Lower - Loop - Ready: - CFLM AAAABBBBCCCC 1 A_WeaponReady - Loop - Fire: - CFLM A 2 Offset (0, 40) - CFLM D 2 Offset (0, 50) - CFLM D 2 Offset (0, 36) - CFLM E 4 Bright - CFLM F 4 Bright A_CFlameAttack - CFLM E 4 Bright - CFLM G 2 Offset (0, 40) - CFLM G 2 - Goto Ready - } -} - -// Floor Flame -------------------------------------------------------------- - -ACTOR CFlameFloor -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Add - States - { - Spawn: - CFFX N 5 Bright - CFFX O 4 Bright - CFFX P 3 Bright - Stop - } -} - -// Flame Puff --------------------------------------------------------------- - -ACTOR FlamePuff -{ - Radius 1 - Height 1 - +NOBLOCKMAP +NOGRAVITY - RenderStyle Add - SeeSound "ClericFlameExplode" - AttackSound "ClericFlameExplode" - States - { - Spawn: - CFFX ABC 3 Bright - CFFX D 4 Bright - CFFX E 3 Bright - CFFX F 4 Bright - CFFX G 3 Bright - CFFX H 4 Bright - CFFX I 3 Bright - CFFX J 4 Bright - CFFX K 3 Bright - CFFX L 4 Bright - CFFX M 3 Bright - Stop - } -} - -// Flame Puff 2 ------------------------------------------------------------- - -ACTOR FlamePuff2 : FlamePuff -{ - States - { - Spawn: - CFFX ABC 3 Bright - CFFX D 4 Bright - CFFX E 3 Bright - CFFX F 4 Bright - CFFX G 3 Bright - CFFX H 4 Bright - CFFX IC 3 Bright - CFFX D 4 Bright - CFFX E 3 Bright - CFFX F 4 Bright - CFFX G 3 Bright - CFFX H 4 Bright - CFFX I 3 Bright - CFFX J 4 Bright - CFFX K 3 Bright - CFFX L 4 Bright - CFFX M 3 Bright - Stop - } -} - -// Circle Flame ------------------------------------------------------------- - -ACTOR CircleFlame -{ - Radius 6 - Damage 2 - DamageType "Fire" - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - DeathSound "ClericFlameCircle" - Obituary "$OB_MPCWEAPFLAME" - - action native A_CFlameRotate(); - - States - { - Spawn: - CFCF A 4 Bright - CFCF B 2 Bright A_CFlameRotate - CFCF C 2 Bright - CFCF D 1 Bright - CFCF E 2 Bright - CFCF F 2 Bright A_CFlameRotate - CFCF G 1 Bright - CFCF HI 2 Bright - CFCF J 1 Bright A_CFlameRotate - CFCF K 2 Bright - CFCF LM 3 Bright - CFCF N 2 Bright A_CFlameRotate - CFCF O 3 Bright - CFCF P 2 Bright - Stop - Death: - CFCF QR 3 Bright - CFCF S 3 Bright A_Explode(20, 20, 0) - CFCF TUVWXYZ 3 Bright - Stop - } -} - -// Flame Missile ------------------------------------------------------------ - -ACTOR CFlameMissile : FastProjectile native -{ - Speed 200 - Radius 14 - Height 8 - Damage 8 - DamageType "Fire" - +INVISIBLE - RenderStyle Add - Obituary "$OB_MPCWEAPFLAME" - - action native A_CFlamePuff(); - action native A_CFlameMissile(); - - States - { - Spawn: - CFFX A 4 Bright - CFFX A 1 A_CFlamePuff - Goto Death + 1 - Death: - CFFX A 1 Bright A_CFlameMissile - CFFX ABC 3 Bright - CFFX D 4 Bright - CFFX E 3 Bright - CFFX F 4 Bright - CFFX G 3 Bright - CFFX H 4 Bright - CFFX I 3 Bright - CFFX J 4 Bright - CFFX K 3 Bright - CFFX L 4 Bright - CFFX M 3 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/clericholy.txt b/wadsrc/static/actors/hexen/clericholy.txt deleted file mode 100644 index f24a846b3..000000000 --- a/wadsrc/static/actors/hexen/clericholy.txt +++ /dev/null @@ -1,237 +0,0 @@ - -// Cleric Weapon Piece ------------------------------------------------------ - -ACTOR ClericWeaponPiece : WeaponPiece -{ - Inventory.PickupSound "misc/w_pkup" - Inventory.PickupMessage "$TXT_WRAITHVERGE_PIECE" - Inventory.ForbiddenTo FighterPlayer, MagePlayer - WeaponPiece.Weapon CWeapWraithverge - +FLOATBOB -} - -// Cleric Weapon Piece 1 ---------------------------------------------------- - -ACTOR CWeaponPiece1 : ClericWeaponPiece -{ - WeaponPiece.Number 1 - States - { - Spawn: - WCH1 A -1 - Stop - } -} - -// Cleric Weapon Piece 2 ---------------------------------------------------- - -ACTOR CWeaponPiece2 : ClericWeaponPiece -{ - WeaponPiece.Number 2 - States - { - Spawn: - WCH2 A -1 - Stop - } -} - -// Cleric Weapon Piece 3 ---------------------------------------------------- - -ACTOR CWeaponPiece3 : ClericWeaponPiece -{ - WeaponPiece.Number 3 - States - { - Spawn: - WCH3 A -1 - Stop - } -} - -// Wraithverge Drop --------------------------------------------------------- - -ACTOR WraithvergeDrop -{ - States - { - Spawn: - TNT1 A 1 - TNT1 A 1 A_DropWeaponPieces("CWeaponPiece1", "CWeaponPiece2", "CWeaponPiece3") - Stop - } -} - -// Cleric's Wraithverge (Holy Symbol?) -------------------------------------- - -ACTOR CWeapWraithverge : ClericWeapon native -{ - Health 3 - Weapon.SelectionOrder 3000 - +WEAPON.PRIMARY_USES_BOTH - +Inventory.NoAttenPickupSound - Weapon.AmmoUse1 18 - Weapon.AmmoUse2 18 - Weapon.AmmoGive1 20 - Weapon.AmmoGive2 20 - Weapon.KickBack 150 - Weapon.AmmoType1 "Mana1" - Weapon.AmmoType2 "Mana2" - Inventory.PickupMessage "$TXT_WEAPON_C4" - Tag "$TAG_CWEAPWRAITHVERGE" - Inventory.PickupSound "WeaponBuild" - - action native A_CHolyAttack(); - action native A_CHolyPalette(); - - States - { - Spawn: - TNT1 A -1 - Stop - Ready: - CHLY A 1 A_WeaponReady - Loop - Select: - CHLY A 1 A_Raise - Loop - Deselect: - CHLY A 1 A_Lower - Loop - Fire: - CHLY AB 1 Bright Offset (0, 40) - CHLY CD 2 Bright Offset (0, 43) - CHLY E 2 Bright Offset (0, 45) - CHLY F 6 Bright Offset (0, 48) A_CHolyAttack - CHLY GG 2 Bright Offset (0, 40) A_CHolyPalette - CHLY G 2 Offset (0, 36) A_CHolyPalette - Goto Ready - } -} - -// Holy Missile ------------------------------------------------------------- - -ACTOR HolyMissile -{ - Speed 30 - Radius 15 - Height 8 - Damage 4 - Projectile - -ACTIVATEIMPACT -ACTIVATEPCROSS - +EXTREMEDEATH - - action native A_CHolyAttack2(); - - States - { - Spawn: - SPIR PPPP 3 Bright A_SpawnItemEx("HolyMissilePuff") - Death: - SPIR P 1 Bright A_CHolyAttack2 - Stop - } -} - -// Holy Missile Puff -------------------------------------------------------- - -ACTOR HolyMissilePuff -{ - Radius 4 - Height 8 - +NOBLOCKMAP +NOGRAVITY +DROPOFF - +NOTELEPORT - RenderStyle "Translucent" - Alpha 0.4 - States - { - Spawn: - SPIR QRSTU 3 - Stop - } -} - -// Holy Puff ---------------------------------------------------------------- - -ACTOR HolyPuff -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - SPIR KLMNO 3 - Stop - } -} - -// Holy Spirit -------------------------------------------------------------- - -ACTOR HolySpirit native -{ - Health 105 - Speed 12 - Radius 10 - Height 6 - Damage 3 - Projectile - +RIPPER +SEEKERMISSILE - +FOILINVUL +SKYEXPLODE +NOEXPLODEFLOOR +CANBLAST - +EXTREMEDEATH - RenderStyle Translucent - Alpha 0.4 - DeathSound "SpiritDie" - Obituary "$OB_MPCWEAPWRAITHVERGE" - - action native A_CHolySeek(); - action native A_CHolyCheckScream(); - - States - { - Spawn: - SPIR AAB 2 A_CHolySeek - SPIR B 2 A_CHolyCheckScream - Loop - Death: - SPIR D 4 - SPIR E 4 A_Scream - SPIR FGHI 4 - Stop - } -} - -// Holy Tail ---------------------------------------------------------------- - -ACTOR HolyTail -{ - Radius 1 - Height 1 - +NOBLOCKMAP +NOGRAVITY +DROPOFF +NOCLIP - +NOTELEPORT - RenderStyle Translucent - Alpha 0.6 - - action native A_CHolyTail(); - - States - { - Spawn: - SPIR C 1 A_CHolyTail - Loop - TailTrail: - SPIR D -1 - Stop - } -} - -// Holy Tail Trail --------------------------------------------------------- - -ACTOR HolyTailTrail : HolyTail -{ - States - { - Spawn: - Goto TailTrail - } -} diff --git a/wadsrc/static/actors/hexen/clericstaff.txt b/wadsrc/static/actors/hexen/clericstaff.txt deleted file mode 100644 index bd848b5c6..000000000 --- a/wadsrc/static/actors/hexen/clericstaff.txt +++ /dev/null @@ -1,96 +0,0 @@ - -// The Cleric's Serpent Staff ----------------------------------------------- - -ACTOR CWeapStaff : ClericWeapon -{ - Weapon.SelectionOrder 1600 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 25 - Weapon.KickBack 150 - Weapon.YAdjust 10 - Weapon.AmmoType1 "Mana1" - Inventory.PickupMessage "$TXT_WEAPON_C2" - Obituary "$OB_MPCWEAPSTAFFM" - Tag "$TAG_CWEAPSTAFF" - - action native A_CStaffInitBlink(); - action native A_CStaffCheckBlink(); - action native A_CStaffCheck(); - action native A_CStaffAttack(); - - States - { - Spawn: - WCSS A -1 - Stop - Select: - CSSF C 1 A_Raise - Loop - Deselect: - CSSF B 3 - CSSF C 4 - CSSF C 1 A_Lower - Wait - Ready: - CSSF C 4 - CSSF B 3 A_CStaffInitBlink - CSSF AAAAAAA 1 A_WeaponReady - CSSF A 1 A_CStaffCheckBlink - Goto Ready + 2 - Fire: - CSSF A 1 Offset (0, 45) A_CStaffCheck - CSSF J 1 Offset (0, 50) A_CStaffAttack - CSSF J 2 Offset (0, 50) - CSSF J 2 Offset (0, 45) - CSSF A 2 Offset (0, 40) - CSSF A 2 Offset (0, 36) - Goto Ready + 2 - Blink: - CSSF BBBCCCCCBBB 1 A_WeaponReady - Goto Ready + 2 - Drain: - CSSF K 10 Offset (0, 36) - Goto Ready + 2 - } -} - -// Serpent Staff Missile ---------------------------------------------------- - -ACTOR CStaffMissile native -{ - Speed 22 - Radius 12 - Height 10 - Damage 5 - RenderStyle Add - Projectile - DeathSound "ClericCStaffExplode" - Obituary "$OB_MPCWEAPSTAFFR" - States - { - Spawn: - CSSF DDEE 1 Bright A_CStaffMissileSlither - Loop - Death: - CSSF FG 4 Bright - CSSF HI 3 Bright - Stop - } -} - -// Serpent Staff Puff ------------------------------------------------------- - -ACTOR CStaffPuff -{ - +NOBLOCKMAP +NOGRAVITY - +PUFFONACTORS - RenderStyle Translucent - Alpha 0.6 - SeeSound "ClericCStaffHitThing" - States - { - Spawn: - FHFX STUVW 4 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/dragon.txt b/wadsrc/static/actors/hexen/dragon.txt deleted file mode 100644 index f6c3746f2..000000000 --- a/wadsrc/static/actors/hexen/dragon.txt +++ /dev/null @@ -1,117 +0,0 @@ - -// Dragon ------------------------------------------------------------------- - -ACTOR Dragon -{ - Health 640 - PainChance 128 - Speed 10 - Height 65 - Mass 0x7fffffff - Monster - +NOGRAVITY +FLOAT +NOBLOOD - +BOSS - +DONTMORPH +NOTARGET - +NOICEDEATH - SeeSound "DragonSight" - AttackSound "DragonAttack" - PainSound "DragonPain" - DeathSound "DragonDeath" - ActiveSound "DragonActive" - Obituary "$OB_DRAGON" - - action native A_DragonInitFlight(); - action native A_DragonFlap(); - action native A_DragonFlight(); - action native A_DragonPain(); - action native A_DragonAttack(); - action native A_DragonCheckCrash(); - - States - { - Spawn: - DRAG D 10 A_Look - Loop - See: - DRAG CB 5 - DRAG A 5 A_DragonInitFlight - DRAG B 3 A_DragonFlap - DRAG BCCDDCCBBAA 3 A_DragonFlight - Goto See + 3 - Pain: - DRAG F 10 A_DragonPain - Goto See + 3 - Missile: - DRAG E 8 A_DragonAttack - Goto See + 3 - Death: - DRAG G 5 A_Scream - DRAG H 4 A_NoBlocking - DRAG I 4 - DRAG J 4 A_DragonCheckCrash - Wait - Crash: - DRAG KL 5 - DRAG M -1 - Stop - } -} - -// Dragon Fireball ---------------------------------------------------------- - -ACTOR DragonFireball -{ - Speed 24 - Radius 12 - Height 10 - Damage 6 - DamageType "Fire" - Projectile - -ACTIVATEIMPACT -ACTIVATEPCROSS - RenderStyle Add - DeathSound "DragonFireballExplode" - - action native A_DragonFX2(); - - States - { - Spawn: - DRFX ABCDEF 4 Bright - Loop - Death: - DRFX GHI 4 Bright - DRFX J 4 Bright A_DragonFX2 - DRFX KL 3 Bright - Stop - } -} - -// Dragon Fireball Secondary Explosion -------------------------------------- - -ACTOR DragonExplosion -{ - Radius 8 - Height 8 - DamageType "Fire" - +NOBLOCKMAP - +NOTELEPORT - +INVISIBLE - RenderStyle Add - DeathSound "DragonFireballExplode" - States - { - Spawn: - CFCF Q 1 Bright - CFCF Q 4 Bright A_UnHideThing - CFCF R 3 Bright A_Scream - CFCF S 4 Bright - CFCF T 3 Bright A_Explode (80, 128, 0) - CFCF U 4 Bright - CFCF V 3 Bright - CFCF W 4 Bright - CFCF X 3 Bright - CFCF Y 4 Bright - CFCF Z 3 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/fighteraxe.txt b/wadsrc/static/actors/hexen/fighteraxe.txt deleted file mode 100644 index 28642c7d1..000000000 --- a/wadsrc/static/actors/hexen/fighteraxe.txt +++ /dev/null @@ -1,113 +0,0 @@ - -// The Fighter's Axe -------------------------------------------------------- - -ACTOR FWeapAxe : FighterWeapon native -{ - Weapon.SelectionOrder 1500 - +WEAPON.AXEBLOOD +WEAPON.AMMO_OPTIONAL +WEAPON.MELEEWEAPON - Weapon.AmmoUse1 2 - Weapon.AmmoGive1 25 - Weapon.KickBack 150 - Weapon.YAdjust -12 - Weapon.AmmoType1 "Mana1" - Inventory.PickupMessage "$TXT_WEAPON_F2" - Obituary "$OB_MPFWEAPAXE" - Tag "$TAG_FWEAPAXE" - - action native A_FAxeCheckUp(); - action native A_FAxeCheckReady(); - action native A_FAxeCheckAtk(); - action native A_FAxeAttack(); - action native A_FAxeCheckUpG(); - action native A_FAxeCheckReadyG(); - - States - { - Spawn: - WFAX A -1 - Stop - Select: - FAXE A 1 A_FAxeCheckUp - Loop - Deselect: - FAXE A 1 A_Lower - Loop - Ready: - FAXE A 1 A_FAxeCheckReady - Loop - Fire: - FAXE B 4 Offset (15, 32) A_FAxeCheckAtk - FAXE C 3 Offset (15, 32) - FAXE D 2 Offset (15, 32) - FAXE D 1 Offset (-5, 70) A_FAxeAttack - FAXE D 2 Offset (-25, 90) - FAXE E 1 Offset (15, 32) - FAXE E 2 Offset (10, 54) - FAXE E 7 Offset (10, 150) - FAXE A 1 Offset (0, 60) A_ReFire - FAXE A 1 Offset (0, 52) - FAXE A 1 Offset (0, 44) - FAXE A 1 Offset (0, 36) - FAXE A 1 - Goto Ready - SelectGlow: - FAXE L 1 A_FAxeCheckUpG - Loop - DeselectGlow: - FAXE L 1 A_Lower - Loop - ReadyGlow: - FAXE LLL 1 A_FAxeCheckReadyG - FAXE MMM 1 A_FAxeCheckReadyG - Loop - FireGlow: - FAXE N 4 Offset (15, 32) - FAXE O 3 Offset (15, 32) - FAXE P 2 Offset (15, 32) - FAXE P 1 Offset (-5, 70) A_FAxeAttack - FAXE P 2 Offset (-25, 90) - FAXE Q 1 Offset (15, 32) - FAXE Q 2 Offset (10, 54) - FAXE Q 7 Offset (10, 150) - FAXE A 1 Offset (0, 60) A_ReFire - FAXE A 1 Offset (0, 52) - FAXE A 1 Offset (0, 44) - FAXE A 1 Offset (0, 36) - FAXE A 1 - Goto ReadyGlow - } -} - -// Axe Puff ----------------------------------------------------------------- - -ACTOR AxePuff -{ - +NOBLOCKMAP +NOGRAVITY - +PUFFONACTORS - RenderStyle Translucent - Alpha 0.6 - SeeSound "FighterAxeHitThing" - AttackSound "FighterHammerHitWall" - ActiveSound "FighterHammerMiss" - States - { - Spawn: - FHFX STUVW 4 - Stop - } -} - -// Glowing Axe Puff --------------------------------------------------------- - -ACTOR AxePuffGlow : AxePuff -{ - +PUFFONACTORS - RenderStyle Add - Alpha 1 - States - { - Spawn: - FAXE RSTUVWX 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/fighterfist.txt b/wadsrc/static/actors/hexen/fighterfist.txt deleted file mode 100644 index b6a27332d..000000000 --- a/wadsrc/static/actors/hexen/fighterfist.txt +++ /dev/null @@ -1,64 +0,0 @@ - -// Fist (first weapon) ------------------------------------------------------ - -ACTOR FWeapFist : FighterWeapon -{ - +BLOODSPLATTER - Weapon.SelectionOrder 3400 - +WEAPON.MELEEWEAPON - Weapon.KickBack 150 - Obituary "$OB_MPFWEAPFIST" - Tag "$TAG_FWEAPFIST" - - action native A_FPunchAttack(); - - States - { - Select: - FPCH A 1 A_Raise - Loop - Deselect: - FPCH A 1 A_Lower - Loop - Ready: - FPCH A 1 A_WeaponReady - Loop - Fire: - FPCH B 5 Offset (5, 40) - FPCH C 4 Offset (5, 40) - FPCH D 4 Offset (5, 40) A_FPunchAttack - FPCH C 4 Offset (5, 40) - FPCH B 5 Offset (5, 40) A_ReFire - Goto Ready - Fire2: - FPCH DE 4 Offset (5, 40) - FPCH E 1 Offset (15, 50) - FPCH E 1 Offset (25, 60) - FPCH E 1 Offset (35, 70) - FPCH E 1 Offset (45, 80) - FPCH E 1 Offset (55, 90) - FPCH E 1 Offset (65, 90) - FPCH E 10 Offset (0, 150) - Goto Ready - } -} - -// Punch puff --------------------------------------------------------------- - -ACTOR PunchPuff -{ - +NOBLOCKMAP +NOGRAVITY - +PUFFONACTORS - RenderStyle Translucent - Alpha 0.6 - SeeSound "FighterPunchHitThing" - AttackSound "FighterPunchHitWall" - ActiveSound "FighterPunchMiss" - VSpeed 1 - States - { - Spawn: - FHFX STUVW 4 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/fighterhammer.txt b/wadsrc/static/actors/hexen/fighterhammer.txt deleted file mode 100644 index d9932ae5f..000000000 --- a/wadsrc/static/actors/hexen/fighterhammer.txt +++ /dev/null @@ -1,101 +0,0 @@ - -// The Fighter's Hammer ----------------------------------------------------- - -ACTOR FWeapHammer : FighterWeapon -{ - +BLOODSPLATTER - Weapon.SelectionOrder 900 - +WEAPON.AMMO_OPTIONAL +WEAPON.MELEEWEAPON - Weapon.AmmoUse1 3 - Weapon.AmmoGive1 25 - Weapon.KickBack 150 - Weapon.YAdjust -10 - Weapon.AmmoType1 "Mana2" - Inventory.PickupMessage "$TXT_WEAPON_F3" - Obituary "$OB_MPFWEAPHAMMERM" - Tag "$TAG_FWEAPHAMMER" - - action native A_FHammerAttack(); - action native A_FHammerThrow(); - - States - { - Spawn: - WFHM A -1 - Stop - Select: - FHMR A 1 A_Raise - Loop - Deselect: - FHMR A 1 A_Lower - Loop - Ready: - FHMR A 1 A_WeaponReady - Loop - Fire: - FHMR B 6 Offset (5, 0) - FHMR C 3 Offset (5, 0) A_FHammerAttack - FHMR D 3 Offset (5, 0) - FHMR E 2 Offset (5, 0) - FHMR E 10 Offset (5, 150) A_FHammerThrow - FHMR A 1 Offset (0, 60) - FHMR A 1 Offset (0, 55) - FHMR A 1 Offset (0, 50) - FHMR A 1 Offset (0, 45) - FHMR A 1 Offset (0, 40) - FHMR A 1 Offset (0, 35) - FHMR A 1 - Goto Ready - } -} - -// Hammer Missile ----------------------------------------------------------- - -ACTOR HammerMissile -{ - Speed 25 - Radius 14 - Height 20 - Damage 10 - DamageType "Fire" - Projectile - DeathSound "FighterHammerExplode" - Obituary "$OB_MPFWEAPHAMMERR" - - States - { - Spawn: - FHFX A 2 Bright - FHFX B 2 Bright A_PlaySound ("FighterHammerContinuous") - FHFX CDEFGH 2 Bright - Loop - Death: - FHFX I 3 Bright A_SetTranslucent(1,1) - FHFX J 3 Bright - FHFX K 3 Bright A_Explode (128, 128, 0) - FHFX LM 3 Bright - FHFX N 3 - FHFX OPQR 3 Bright - Stop - } -} - -// Hammer Puff (also used by fist) ------------------------------------------ - -ACTOR HammerPuff -{ - +NOBLOCKMAP +NOGRAVITY - +PUFFONACTORS - RenderStyle "Translucent" - Alpha 0.6 - VSpeed 0.8 - SeeSound "FighterHammerHitThing" - AttackSound "FighterHammerHitWall" - ActiveSound "FighterHammerMiss" - States - { - Spawn: - FHFX STUVW 4 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/fighterquietus.txt b/wadsrc/static/actors/hexen/fighterquietus.txt deleted file mode 100644 index 8d784ebf5..000000000 --- a/wadsrc/static/actors/hexen/fighterquietus.txt +++ /dev/null @@ -1,164 +0,0 @@ - -// Fighter Weapon Piece ----------------------------------------------------- - -ACTOR FighterWeaponPiece : WeaponPiece -{ - Inventory.PickupSound "misc/w_pkup" - Inventory.PickupMessage "$TXT_QUIETUS_PIECE" - Inventory.ForbiddenTo ClericPlayer, MagePlayer - WeaponPiece.Weapon FWeapQuietus - +FLOATBOB -} - -// Fighter Weapon Piece 1 --------------------------------------------------- - -ACTOR FWeaponPiece1 : FighterWeaponPiece -{ - WeaponPiece.Number 1 - States - { - Spawn: - WFR1 A -1 Bright - Stop - } -} - -// Fighter Weapon Piece 2 --------------------------------------------------- - -ACTOR FWeaponPiece2 : FighterWeaponPiece -{ - WeaponPiece.Number 2 - States - { - Spawn: - WFR2 A -1 Bright - Stop - } -} - -// Fighter Weapon Piece 3 --------------------------------------------------- - -ACTOR FWeaponPiece3 : FighterWeaponPiece -{ - WeaponPiece.Number 3 - States - { - Spawn: - WFR3 A -1 Bright - Stop - } -} - -// Quietus Drop ------------------------------------------------------------- - -ACTOR QuietusDrop -{ - States - { - Spawn: - TNT1 A 1 - TNT1 A 1 A_DropWeaponPieces("FWeaponPiece1", "FWeaponPiece2", "FWeaponPiece3") - Stop - } -} - -// The Fighter's Sword (Quietus) -------------------------------------------- - -ACTOR FWeapQuietus : FighterWeapon -{ - Health 3 - Weapon.SelectionOrder 2900 - +WEAPON.PRIMARY_USES_BOTH - +Inventory.NoAttenPickupSound - Weapon.AmmoUse1 14 - Weapon.AmmoUse2 14 - Weapon.AmmoGive1 20 - Weapon.AmmoGive2 20 - Weapon.KickBack 150 - Weapon.YAdjust 10 - Weapon.AmmoType1 "Mana1" - Weapon.AmmoType2 "Mana2" - Inventory.PickupMessage "$TXT_WEAPON_F4" - Inventory.PickupSound "WeaponBuild" - Tag "$TAG_FWEAPQUIETUS" - - action native A_FSwordAttack(); - - States - { - Spawn: - TNT1 A -1 - Stop - Select: - FSRD A 1 Bright A_Raise - Loop - Deselect: - FSRD A 1 Bright A_Lower - Loop - Ready: - FSRD AAAABBBBCCCC 1 Bright A_WeaponReady - Loop - Fire: - FSRD DE 3 Bright Offset (5, 36) - FSRD F 2 Bright Offset (5, 36) - FSRD G 3 Bright Offset (5, 36) A_FSwordAttack - FSRD H 2 Bright Offset (5, 36) - FSRD I 2 Bright Offset (5, 36) - FSRD I 10 Bright Offset (5, 150) - FSRD A 1 Bright Offset (5, 60) - FSRD B 1 Bright Offset (5, 55) - FSRD C 1 Bright Offset (5, 50) - FSRD A 1 Bright Offset (5, 45) - FSRD B 1 Bright Offset (5, 40) - Goto Ready - } -} - -// Fighter Sword Missile ---------------------------------------------------- - -ACTOR FSwordMissile native -{ - Speed 30 - Radius 16 - Height 8 - Damage 8 - Projectile - +EXTREMEDEATH - RenderStyle Add - DeathSound "FighterSwordExplode" - Obituary "$OB_MPFWEAPQUIETUS" - - action native A_FSwordFlames(); - - States - { - Spawn: - FSFX ABC 3 Bright - Loop - Death: - FSFX D 4 Bright - FSFX E 3 Bright A_FSwordFlames - FSFX F 4 Bright A_Explode (64, 128, 0) - FSFX G 3 Bright - FSFX H 4 Bright - FSFX I 3 Bright - FSFX J 4 Bright - FSFX KLM 3 Bright - Stop - } -} - -// Fighter Sword Flame ------------------------------------------------------ - -ACTOR FSwordFlame -{ - +NOBLOCKMAP +NOGRAVITY - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - FSFX NOPQRSTUVW 3 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/healingradius.txt b/wadsrc/static/actors/hexen/healingradius.txt deleted file mode 100644 index cc921f59c..000000000 --- a/wadsrc/static/actors/hexen/healingradius.txt +++ /dev/null @@ -1,23 +0,0 @@ - -// Healing Radius Artifact -------------------------------------------------- - -ACTOR ArtiHealingRadius : Inventory native -{ - +COUNTITEM - +FLOATBOB - Inventory.DefMaxAmount - +INVENTORY.INVBAR - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.Icon "ARTIHRAD" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTIHEALINGRADIUS" - Tag "$TAG_ARTIHEALINGRADIUS" - States - { - Spawn: - HRAD ABCDEFGHIJKLMNOP 4 Bright - Loop - } -} - diff --git a/wadsrc/static/actors/hexen/heresiarch.txt b/wadsrc/static/actors/hexen/heresiarch.txt deleted file mode 100644 index 4d32f701e..000000000 --- a/wadsrc/static/actors/hexen/heresiarch.txt +++ /dev/null @@ -1,335 +0,0 @@ - -// The Heresiarch him/itself ------------------------------------------------ - -ACTOR Heresiarch native -{ - Health 5000 - Painchance 10 - Speed 16 - Radius 40 - Height 110 - Mass 500 - Damage 9 - Monster - +FLOORCLIP - +BOSS - +DONTMORPH - +NOTARGET - +NOICEDEATH - +DEFLECT - +NOBLOOD - SeeSound "SorcererSight" - PainSound "SorcererPain" - DeathSound "SorcererDeathScream" - ActiveSound "SorcererActive" - Obituary "$OB_HERESIARCH" - - action native A_SorcSpinBalls(); - action native A_SpeedBalls(); - action native A_SorcBossAttack(); - action native A_SpawnFizzle(); - - States - { - Spawn: - SORC A 3 - SORC A 2 A_SorcSpinBalls - Idle: - SORC A 10 A_Look - Wait - See: - SORC ABCD 5 A_Chase - Loop - Pain: - SORC G 8 - SORC G 8 A_Pain - Goto See - Missile: - SORC F 6 Bright A_FaceTarget - SORC F 6 Bright A_SpeedBalls - SORC F 6 Bright A_FaceTarget - Wait - Attack1: - SORC E 6 Bright - SORC E 6 Bright A_SpawnFizzle - SORC E 5 Bright A_FaceTarget - Goto Attack1+1 - Attack2: - SORC E 2 Bright - SORC E 2 Bright A_SorcBossAttack - Goto See - Death: - SORC H 5 Bright - SORC I 5 Bright A_FaceTarget - SORC J 5 Bright A_Scream - SORC KLMNOPQRST 5 Bright - SORC U 5 Bright A_NoBlocking - SORC VWXY 5 Bright - SORC Z -1 Bright - Stop - } -} - -// Base class for the balls flying around the Heresiarch's head ------------- - -ACTOR SorcBall native -{ - Speed 10 - Radius 5 - Height 5 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - +FULLVOLDEATH - +CANBOUNCEWATER - +NOWALLBOUNCESND - BounceType "HexenCompat" - SeeSound "SorcererBallBounce" - DeathSound "SorcererBigBallExplode" - - action native A_SorcBallOrbit(); - action native A_SorcBallPop(); - action native A_BounceCheck (); -} - -// First ball (purple) - fires projectiles ---------------------------------- - -ACTOR SorcBall1 : SorcBall native -{ - States - { - Spawn: - SBMP ABCDEFGHIJKLMNOP 2 A_SorcBallOrbit - Loop - Pain: - SBMP A 5 A_SorcBallPop - SBMP B 2 A_BounceCheck - Wait - Death: - SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1) - SBS4 D 5 A_Explode(255,255) - SBS4 E 5 - SBS4 FGH 6 - Stop - } -} - - -// Second ball (blue) - generates the shield -------------------------------- - -ACTOR SorcBall2 : SorcBall native -{ - States - { - Spawn: - SBMB ABCDEFGHIJKLMNOP 2 A_SorcBallOrbit - Loop - Pain: - SBMB A 5 A_SorcBallPop - SBMB B 2 A_BounceCheck - Wait - Death: - SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1) - SBS3 D 5 A_Explode(255,255) - SBS3 E 5 - SBS3 FGH 6 - Stop - } -} - -// Third ball (green) - summons Bishops ------------------------------------- - -ACTOR SorcBall3 : SorcBall native -{ - States - { - Spawn: - SBMG ABCDEFGHIJKLMNOP 2 A_SorcBallOrbit - Loop - Pain: - SBMG A 5 A_SorcBallPop - SBMG B 2 A_BounceCheck - Wait - Death: - SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1) - SBS3 D 5 A_Explode(255,255) - SBS3 E 5 - SBS3 FGH 6 - Stop - } -} - - -// Sorcerer spell 1 (The burning, bouncing head thing) ---------------------- - -ACTOR SorcFX1 -{ - Speed 7 - Radius 5 - Height 5 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - -NOGRAVITY - +FULLVOLDEATH - +CANBOUNCEWATER - +NOWALLBOUNCESND - BounceFactor 1.0 - +HEXENBOUNCE - SeeSound "SorcererBallBounce" - DeathSound "SorcererHeadScream" - - action native A_SorcFX1Seek(); - - States - { - Spawn: - SBS1 A 2 Bright - SBS1 BCD 3 Bright A_SorcFX1Seek - Loop - Death: - FHFX S 2 Bright A_Explode(30, 128) - FHFX SS 6 Bright - Stop - } -} - - -// Sorcerer spell 2 (The visible part of the shield) ------------------------ - -ACTOR SorcFX2 -{ - Speed 15 - Radius 5 - Height 5 - +NOBLOCKMAP - +NOGRAVITY - +NOTELEPORT - - action native A_SorcFX2Split(); - action native A_SorcFX2Orbit (); - - states - { - Spawn: - SBS2 A 3 Bright A_SorcFX2Split - Loop - Orbit: - SBS2 A 2 Bright - SBS2 BCDEFGHIJKLMNOPA 2 Bright A_SorcFX2Orbit - Goto Orbit+1 - Death: - SBS2 A 10 - Stop - } -} - -// The translucent trail behind SorcFX2 ------------------------------------- - -ACTOR SorcFX2T1 : SorcFX2 -{ - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - Goto Death - } -} - - -// Sorcerer spell 3 (The Bishop spawner) ------------------------------------ - -ACTOR SorcFX3 -{ - Speed 15 - Radius 22 - Height 65 - +NOBLOCKMAP - +MISSILE - +NOTELEPORT - SeeSound "SorcererBishopSpawn" - - action native A_SpawnBishop(); - action native A_SorcererBishopEntry(); - - States - { - Spawn: - SBS3 ABC 2 Bright - Loop - Death: - SBS3 A 4 Bright - BISH P 4 A_SorcererBishopEntry - BISH ON 4 - BISH MLKJIH 3 - BISH G 3 A_SpawnBishop - Stop - } -} - - -// The Bishop spawner's explosion animation --------------------------------- - -ACTOR SorcFX3Explosion -{ - +NOBLOCKMAP - +NOGRAVITY - +NOTELEPORT - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - SBS3 DEFGH 3 - Stop - } -} - - -// Sorcerer spell 4 (The purple projectile) --------------------------------- - -ACTOR SorcFX4 -{ - Speed 12 - Radius 10 - Height 10 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - DeathSound "SorcererBallExplode" - - action native A_SorcFX4Check(); - - States - { - Spawn: - SBS4 ABC 2 Bright A_SorcFX4Check - Loop - Death: - SBS4 D 2 Bright - SBS4 E 2 Bright A_Explode(20, 128) - SBS4 FGH 2 Bright - Stop - } -} - - -// Spark that appears when shooting SorcFX4 --------------------------------- - -ACTOR SorcSpark1 -{ - Radius 5 - Height 5 - Gravity 0.125 - +NOBLOCKMAP - +DROPOFF - +NOTELEPORT - RenderStyle Add - States - { - Spawn: - SBFX ABCDEFG 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/iceguy.txt b/wadsrc/static/actors/hexen/iceguy.txt deleted file mode 100644 index 235be474f..000000000 --- a/wadsrc/static/actors/hexen/iceguy.txt +++ /dev/null @@ -1,167 +0,0 @@ - -// Ice Guy ------------------------------------------------------------------ - -ACTOR IceGuy -{ - Health 120 - PainChance 144 - Speed 14 - Radius 22 - Height 75 - Mass 150 - DamageType "Ice" - Monster - +NOBLOOD - +TELESTOMP - +NOICEDEATH - SeeSound "IceGuySight" - AttackSound "IceGuyAttack" - ActiveSound "IceGuyActive" - Obituary "$OB_ICEGUY" - - action native A_IceGuyLook(); - action native A_IceGuyChase(); - action native A_IceGuyAttack(); - - States - { - Spawn: - ICEY A 10 A_IceGuyLook - Loop - See: - ICEY A 4 A_Chase - ICEY B 4 A_IceGuyChase - ICEY CD 4 A_Chase - Loop - Pain: - ICEY A 1 A_Pain - Goto See - Missile: - ICEY EF 3 A_FaceTarget - ICEY G 8 Bright A_IceGuyAttack - ICEY F 4 A_FaceTarget - Goto See - Death: - ICEY A 1 A_IceGuyDie - Stop - Inactive: - ICEY A -1 - Goto See - } -} - -// Ice Guy Projectile ------------------------------------------------------- - -ACTOR IceGuyFX -{ - Speed 14 - Radius 8 - Height 10 - Damage 1 - DamageType "Ice" - Projectile - -ACTIVATEIMPACT -ACTIVATEPCROSS - DeathSound "IceGuyMissileExplode" - - action native A_IceGuyMissileExplode(); - - States - { - Spawn: - ICPR ABC 3 Bright A_SpawnItemEx("IceFXPuff", 0,0,2) - Loop - Death: - ICPR D 4 Bright - ICPR E 4 Bright A_IceGuyMissileExplode - ICPR FG 4 Bright - ICPR H 3 Bright - Stop - } -} - -// Ice Guy Projectile's Puff ------------------------------------------------ - -ACTOR IceFXPuff -{ - Radius 1 - Height 1 - +NOBLOCKMAP +NOGRAVITY +DROPOFF +SHADOW - +NOTELEPORT - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - ICPR IJK 3 - ICPR LM 2 - Stop - } -} - -// Secondary Ice Guy Projectile (ejected by the primary projectile) --------- - -ACTOR IceGuyFX2 -{ - Speed 10 - Radius 4 - Height 4 - Damage 1 - DamageType "Ice" - Gravity 0.125 - +NOBLOCKMAP +DROPOFF +MISSILE - +NOTELEPORT - +STRIFEDAMAGE - States - { - Spawn: - ICPR NOP 3 Bright - Loop - } -} - -// Ice Guy Bit -------------------------------------------------------------- - -ACTOR IceGuyBit -{ - Radius 1 - Height 1 - Gravity 0.125 - +NOBLOCKMAP +DROPOFF - +NOTELEPORT - States - { - Spawn: - ICPR Q 50 Bright - Stop - ICPR R 50 Bright - Stop - } -} - -// Ice Guy Wisp 1 ----------------------------------------------------------- - -ACTOR IceGuyWisp1 -{ - +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE - +NOTELEPORT - RenderStyle Translucent - Alpha 0.4 - States - { - Spawn: - ICWS ABCDEFGHI 2 - Stop - } -} - -// Ice Guy Wisp 2 ----------------------------------------------------------- - -ACTOR IceGuyWisp2 : IceGuyWisp1 -{ - States - { - Spawn: - ICWS JKLMNOPQR 2 - Stop - } -} diff --git a/wadsrc/static/actors/hexen/magecone.txt b/wadsrc/static/actors/hexen/magecone.txt deleted file mode 100644 index 72c37c38c..000000000 --- a/wadsrc/static/actors/hexen/magecone.txt +++ /dev/null @@ -1,89 +0,0 @@ - -// The Mage's Frost Cone ---------------------------------------------------- - -ACTOR MWeapFrost : MageWeapon -{ - +BLOODSPLATTER - Weapon.SelectionOrder 1700 - Weapon.AmmoUse1 3 - Weapon.AmmoGive1 25 - Weapon.KickBack 150 - Weapon.YAdjust 20 - Weapon.AmmoType1 "Mana1" - Inventory.PickupMessage "$TXT_WEAPON_M2" - Obituary "$OB_MPMWEAPFROST" - Tag "$TAG_MWEAPFROST" - - action native A_FireConePL1(); - - States - { - Spawn: - WMCS ABC 8 Bright - Loop - Select: - CONE A 1 A_Raise - Loop - Deselect: - CONE A 1 A_Lower - Loop - Ready: - CONE A 1 A_WeaponReady - Loop - Fire: - CONE B 3 - CONE C 4 - Hold: - CONE D 3 - CONE E 5 - CONE F 3 A_FireConePL1 - CONE G 3 - CONE A 9 - CONE A 10 A_ReFire - Goto Ready - } -} - -// Frost Missile ------------------------------------------------------------ - -ACTOR FrostMissile native -{ - Speed 25 - Radius 13 - Height 8 - Damage 1 - DamageType "Ice" - Projectile - DeathSound "MageShardsExplode" - Obituary "$OB_MPMWEAPFROST" - - action native A_ShedShard(); - - States - { - Spawn: - SHRD A 2 Bright - SHRD A 3 Bright A_ShedShard - SHRD B 3 Bright - SHRD C 3 Bright - Loop - Death: - SHEX ABCDE 5 Bright - Stop - } -} - -// Ice Shard ---------------------------------------------------------------- - -ACTOR IceShard : FrostMissile -{ - DamageType "Ice" - -ACTIVATEIMPACT - -ACTIVATEPCROSS - States - { - Spawn: - SHRD ABC 3 Bright - Loop - } -} diff --git a/wadsrc/static/actors/hexen/magelightning.txt b/wadsrc/static/actors/hexen/magelightning.txt deleted file mode 100644 index d12b7d389..000000000 --- a/wadsrc/static/actors/hexen/magelightning.txt +++ /dev/null @@ -1,154 +0,0 @@ - -// The Mage's Lightning Arc of Death ---------------------------------------- - -ACTOR MWeapLightning : MageWeapon -{ - +NOGRAVITY - Weapon.SelectionOrder 1100 - Weapon.AmmoUse1 5 - Weapon.AmmoGive1 25 - Weapon.KickBack 0 - Weapon.YAdjust 20 - Weapon.AmmoType1 "Mana2" - Inventory.PickupMessage "$TXT_WEAPON_M3" - Tag "$TAG_MWEAPLIGHTNING" - - action native A_LightningReady(); - action native A_MLightningAttack(class floor = "LightningFloor", class ceiling = "LightningCeiling"); - - States - { - Spawn: - WMLG ABCDEFGH 4 Bright - Loop - Select: - MLNG A 1 Bright A_Raise - Loop - Deselect: - MLNG A 1 Bright A_Lower - Loop - Ready: - MLNG AAAAA 1 Bright A_WeaponReady - MLNG A 1 Bright A_LightningReady - MLNG BBBBBB 1 Bright A_WeaponReady - MLNG CCCCC 1 Bright A_WeaponReady - MLNG C 1 Bright A_LightningReady - MLNG BBBBBB 1 Bright A_WeaponReady - Loop - Fire: - MLNG DE 3 Bright - MLNG F 4 Bright A_MLightningAttack - MLNG G 4 Bright - MLNG HI 3 Bright - MLNG I 6 Bright Offset (0, 199) - MLNG C 2 Bright Offset (0, 55) - MLNG B 2 Bright Offset (0, 50) - MLNG B 2 Bright Offset (0, 45) - MLNG B 2 Bright Offset (0, 40) - Goto Ready - } -} - -// Ceiling Lightning -------------------------------------------------------- - -ACTOR Lightning native -{ - MissileType "LightningZap" - AttackSound "MageLightningZap" - ActiveSound "MageLightningContinuous" - Obituary "$OB_MPMWEAPLIGHTNING" -} - -ACTOR LightningCeiling : Lightning -{ - Health 144 - Speed 25 - Radius 16 - Height 40 - Damage 8 - Projectile - +CEILINGHUGGER - RenderStyle Add - - action native A_LightningZap(); - action native A_LightningClip(); - action native A_LightningRemove(); - - States - { - Spawn: - MLFX A 2 Bright A_LightningZap - MLFX BCD 2 Bright A_LightningClip - Loop - Death: - MLF2 A 2 Bright A_LightningRemove - MLF2 BCDEKLM 3 Bright - ACLO E 35 - MLF2 NO 3 Bright - MLF2 P 4 Bright - MLF2 QP 3 Bright - MLF2 Q 4 Bright - MLF2 P 3 Bright - MLF2 O 3 Bright - MLF2 P 3 Bright - MLF2 P 1 Bright A_HideThing - ACLO E 1050 - Stop - } -} - -// Floor Lightning ---------------------------------------------------------- - -ACTOR LightningFloor : LightningCeiling -{ - -CEILINGHUGGER - +FLOORHUGGER - RenderStyle Add - - action native A_LastZap(); - - States - { - Spawn: - MLFX E 2 Bright A_LightningZap - MLFX FGH 2 Bright A_LightningClip - Loop - Death: - MLF2 F 2 Bright A_LightningRemove - MLF2 GHIJKLM 3 Bright - ACLO E 20 - MLF2 NO 3 Bright - MLF2 P 4 Bright - MLF2 QP 3 Bright - MLF2 Q 4 Bright A_LastZap - MLF2 POP 3 Bright - MLF2 P 1 Bright A_HideThing - Goto Super::Death + 19 - } -} - -// Lightning Zap ------------------------------------------------------------ - -ACTOR LightningZap native -{ - Radius 15 - Height 35 - Damage 2 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - RenderStyle Add - Obituary "$OB_MPMWEAPLIGHTNING" - - action native A_ZapMimic(); - - States - { - Spawn: - MLFX IJKLM 2 Bright A_ZapMimic - Loop - Death: - MLFX NOPQRSTU 2 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/magestaff.txt b/wadsrc/static/actors/hexen/magestaff.txt deleted file mode 100644 index 381588ce5..000000000 --- a/wadsrc/static/actors/hexen/magestaff.txt +++ /dev/null @@ -1,142 +0,0 @@ - -// Mage Weapon Piece -------------------------------------------------------- - -ACTOR MageWeaponPiece : WeaponPiece -{ - Inventory.PickupSound "misc/w_pkup" - Inventory.PickupMessage "$TXT_BLOODSCOURGE_PIECE" - Inventory.ForbiddenTo FighterPlayer, ClericPlayer - WeaponPiece.Weapon MWeapBloodscourge - +FLOATBOB -} - -// Mage Weapon Piece 1 ------------------------------------------------------ - -ACTOR MWeaponPiece1 : MageWeaponPiece -{ - WeaponPiece.Number 1 - States - { - Spawn: - WMS1 A -1 Bright - Stop - } -} - -// Mage Weapon Piece 2 ------------------------------------------------------ - -ACTOR MWeaponPiece2 : MageWeaponPiece -{ - WeaponPiece.Number 2 - States - { - Spawn: - WMS2 A -1 Bright - Stop - } -} - -// Mage Weapon Piece 3 ------------------------------------------------------ - -ACTOR MWeaponPiece3 : MageWeaponPiece -{ - WeaponPiece.Number 3 - States - { - Spawn: - WMS3 A -1 Bright - Stop - } -} - -// Bloodscourge Drop -------------------------------------------------------- - -ACTOR BloodscourgeDrop -{ - States - { - Spawn: - TNT1 A 1 - TNT1 A 1 A_DropWeaponPieces("MWeaponPiece1", "MWeaponPiece2", "MWeaponPiece3") - Stop - } -} - -// The Mages's Staff (Bloodscourge) ----------------------------------------- - -ACTOR MWeapBloodscourge : MageWeapon native -{ - Health 3 - Weapon.SelectionOrder 3100 - Weapon.AmmoUse1 15 - Weapon.AmmoUse2 15 - Weapon.AmmoGive1 20 - Weapon.AmmoGive2 20 - Weapon.KickBack 150 - Weapon.YAdjust 20 - Weapon.AmmoType1 "Mana1" - Weapon.AmmoType2 "Mana2" - +WEAPON.PRIMARY_USES_BOTH - +Inventory.NoAttenPickupSound - Inventory.PickupMessage "$TXT_WEAPON_M4" - Inventory.PickupSound "WeaponBuild" - Tag "$TAG_MWEAPBLOODSCOURGE" - - action native A_MStaffAttack(); - action native A_MStaffPalette(); - - States - { - Spawn: - TNT1 A -1 - Stop - Select: - MSTF A 1 A_Raise - Loop - Deselect: - MSTF A 1 A_Lower - Loop - Ready: - MSTF AAAAAABBBBBBCCCCCCDDDDDDEEEEEEFFFFF 1 A_WeaponReady - Loop - Fire: - MSTF G 4 Offset (0, 40) - MSTF H 4 Bright Offset (0, 48) A_MStaffAttack - MSTF H 2 Bright Offset (0, 48) A_MStaffPalette - MSTF II 2 Offset (0, 48) A_MStaffPalette - MSTF I 1 Offset (0, 40) - MSTF J 5 Offset (0, 36) - Goto Ready - } -} - -// Mage Staff FX2 (Bloodscourge) -------------------------------------------- - -ACTOR MageStaffFX2 native -{ - Speed 17 - Height 8 - Damage 4 - DamageType "Fire" - Projectile - +SEEKERMISSILE - +SCREENSEEKER - +EXTREMEDEATH - DeathSound "MageStaffExplode" - Obituary "$OB_MPMWEAPBLOODSCOURGE" - - action native A_MStaffTrack(); - - States - { - Spawn: - MSP2 ABCD 2 Bright A_MStaffTrack - Loop - Death: - MSP2 E 4 Bright A_SetTranslucent(1,1) - MSP2 F 5 Bright A_Explode (80, 192, 0) - MSP2 GH 5 Bright - MSP2 I 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/magewand.txt b/wadsrc/static/actors/hexen/magewand.txt deleted file mode 100644 index e9a1f339b..000000000 --- a/wadsrc/static/actors/hexen/magewand.txt +++ /dev/null @@ -1,73 +0,0 @@ - -// The Mage's Wand ---------------------------------------------------------- - -ACTOR MWeapWand : MageWeapon -{ - Weapon.SelectionOrder 3600 - Weapon.KickBack 0 - Weapon.YAdjust 9 - Tag "$TAG_MWEAPWAND" - - States - { - Select: - MWND A 1 A_Raise - Loop - Deselect: - MWND A 1 A_Lower - Loop - Ready: - MWND A 1 A_WeaponReady - Loop - Fire: - MWND A 6 - MWND B 6 Bright Offset (0, 48) A_FireCustomMissile ("MageWandMissile") - MWND A 3 Offset (0, 40) - MWND A 3 Offset (0, 36) A_ReFire - Goto Ready - } -} - -// Wand Smoke --------------------------------------------------------------- - -ACTOR MageWandSmoke -{ - +NOBLOCKMAP +NOGRAVITY +SHADOW - +NOTELEPORT +CANNOTPUSH +NODAMAGETHRUST - RenderStyle Translucent - Alpha 0.6 - States - { - Spawn: - MWND CDCD 4 - Stop - } -} - -// Wand Missile ------------------------------------------------------------- - -ACTOR MageWandMissile : FastProjectile -{ - Speed 184 - Radius 12 - Height 8 - Damage 2 - +RIPPER +CANNOTPUSH +NODAMAGETHRUST - +SPAWNSOUNDSOURCE - MissileType "MageWandSmoke" - SeeSound "MageWandFire" - Obituary "$OB_MPMWEAPWAND" - States - { - Spawn: - MWND CD 4 Bright - Loop - Death: - MWND E 4 Bright - MWND F 3 Bright - MWND G 4 Bright - MWND H 3 Bright - MWND I 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/hexen/serpent.txt b/wadsrc/static/actors/hexen/serpent.txt deleted file mode 100644 index 50d81bf8a..000000000 --- a/wadsrc/static/actors/hexen/serpent.txt +++ /dev/null @@ -1,224 +0,0 @@ - -// Serpent ------------------------------------------------------------------ - -ACTOR Serpent -{ - Health 90 - PainChance 96 - Speed 12 - Radius 32 - Height 70 - Mass 0x7fffffff - Monster - -SHOOTABLE - +NOBLOOD - +CANTLEAVEFLOORPIC +NONSHOOTABLE - +STAYMORPHED +DONTBLAST +NOTELEOTHER - +INVISIBLE - SeeSound "SerpentSight" - AttackSound "SerpentAttack" - PainSound "SerpentPain" - DeathSound "SerpentDeath" - HitObituary "$OB_SERPENTHIT" - - action native A_SerpentHumpDecide(); - action native A_SerpentHide(); - action native A_SerpentCheckForAttack(); - action native A_SerpentSpawnGibs(); - action native A_SerpentUnHide(); - action native A_SerpentRaiseHump(); - action native A_SerpentLowerHump(); - action native A_SerpentChooseAttack(); - action native A_SerpentMeleeAttack(); - - States - { - Spawn: - SSPT H 10 A_Look - Loop - See: - SSPT HH 1 A_Chase("Melee", "None", CHF_NIGHTMAREFAST|CHF_NOPLAYACTIVE) - SSPT H 2 A_SerpentHumpDecide - Loop - Pain: - SSPT L 5 - SSPT L 5 A_Pain - Dive: - SSDV ABC 4 - SSDV D 4 A_UnSetShootable - SSDV E 3 A_PlaySoundEx("SerpentActive", "Body") - SSDV F 3 - SSDV GH 4 - SSDV I 3 - SSDV J 3 A_SerpentHide - Goto See - Melee: - SSPT A 1 A_UnHideThing - SSPT A 1 A_PlaySoundEx("SerpentBirth", "Voice") - SSPT B 3 A_SetShootable - SSPT C 3 - SSPT D 4 A_SerpentCheckForAttack - Goto Dive - Death: - SSPT O 4 - SSPT P 4 A_Scream - SSPT Q 4 A_NoBlocking - SSPT RSTUVWXYZ 4 - Stop - XDeath: - SSXD A 4 - SSXD B 4 A_SpawnItemEx("SerpentHead", 0, 0, 45) - SSXD C 4 A_NoBlocking - SSXD DE 4 - SSXD FG 3 - SSXD H 3 A_SerpentSpawnGibs - Stop - Ice: - SSPT [ 5 A_FreezeDeath - SSPT [ 1 A_FreezeDeathChunks - Wait - Walk: - SSPT IJI 5 A_Chase("Attack", "None", CHF_NIGHTMAREFAST) - SSPT J 5 A_SerpentCheckForAttack - Goto Dive - Hump: - SSPT H 3 A_SerpentUnHide - SSPT EFGEF 3 A_SerpentRaiseHump - SSPT GEF 3 - SSPT GEFGE 3 A_SerpentLowerHump - SSPT F 3 A_SerpentHide - Goto See - Attack: - SSPT K 6 A_FaceTarget - SSPT L 5 A_SerpentChooseAttack - Goto MeleeAttack - MeleeAttack: - SSPT N 5 A_SerpentMeleeAttack - Goto Dive - } -} - -// Serpent Leader ----------------------------------------------------------- - -ACTOR SerpentLeader : Serpent -{ - Mass 200 - Obituary "$OB_SERPENT" - States - { - Missile: - SSPT N 5 A_CustomMissile("SerpentFX", 32, 0) - Goto Dive - } -} - -// Serpent Missile Ball ----------------------------------------------------- - -ACTOR SerpentFX -{ - Speed 15 - Radius 8 - Height 10 - Damage 4 - Projectile - -ACTIVATEIMPACT -ACTIVATEPCROSS - RenderStyle Add - DeathSound "SerpentFXHit" - - States - { - Spawn: - SSFX A 0 - SSFX A 3 Bright A_PlaySoundEx("SerpentFXContinuous", "Body", 1) - SSFX BAB 3 Bright - Goto Spawn+1 - Death: - SSFX C 4 Bright A_StopSoundEx("Body") - SSFX DEFGH 4 Bright - Stop - } -} - -// Serpent Head ------------------------------------------------------------- - -ACTOR SerpentHead -{ - Radius 5 - Height 10 - Gravity 0.125 - +NOBLOCKMAP - - action native A_SerpentHeadCheck(); - - States - { - Spawn: - SSXD IJKLMNOP 4 A_SerpentHeadCheck - Loop - Death: - SSXD S -1 - Loop - } -} - -// Serpent Gib 1 ------------------------------------------------------------ - -ACTOR SerpentGib1 -{ - Radius 3 - Height 3 - +NOBLOCKMAP +NOGRAVITY - - action native A_FloatGib(); - action native A_DelayGib(); - action native A_SinkGib(); - - States - { - Spawn: - SSXD Q 6 - SSXD Q 6 A_FloatGib - SSXD QQ 8 A_FloatGib - SSXD QQ 12 A_FloatGib - SSXD Q 232 A_DelayGib - SSXD QQ 12 A_SinkGib - SSXD QQQ 8 A_SinkGib - Stop - } -} - -// Serpent Gib 2 ------------------------------------------------------------ - -ACTOR SerpentGib2 : SerpentGib1 -{ - States - { - Spawn: - SSXD R 6 - SSXD R 6 A_FloatGib - SSXD RR 8 A_FloatGib - SSXD RR 12 A_FloatGib - SSXD R 232 A_DelayGib - SSXD RR 12 A_SinkGib - SSXD RRR 8 A_SinkGib - Stop - } -} - -// Serpent Gib 3 ------------------------------------------------------------ - -ACTOR SerpentGib3 : SerpentGib1 -{ - States - { - Spawn: - SSXD T 6 - SSXD T 6 A_FloatGib - SSXD TT 8 A_FloatGib - SSXD TT 12 A_FloatGib - SSXD T 232 A_DelayGib - SSXD TT 12 A_SinkGib - SSXD TTT 8 A_SinkGib - Stop - } -} diff --git a/wadsrc/static/actors/hexen/spike.txt b/wadsrc/static/actors/hexen/spike.txt deleted file mode 100644 index eaadfe012..000000000 --- a/wadsrc/static/actors/hexen/spike.txt +++ /dev/null @@ -1,104 +0,0 @@ - -// Dirt clump (spawned by spike) -------------------------------------------- - -ACTOR DirtClump -{ - +NOBLOCKMAP - +NOTELEPORT - States - { - Spawn: - TSPK C 20 - Loop - } -} - -// Spike (thrust floor) ----------------------------------------------------- - -ACTOR ThrustFloor native -{ - Radius 20 - Height 128 - - action native A_ThrustRaise(); - action native A_ThrustImpale(); - action native A_ThrustLower(); - action native A_ThrustInitDn(); - action native A_ThrustInitUp(); - - States - { - ThrustRaising: - TSPK A 2 A_ThrustRaise - Loop - BloodThrustRaising: - TSPK B 2 A_ThrustRaise - Loop - ThrustLower: - TSPK A 2 A_ThrustLower - Loop - BloodThrustLower: - TSPK B 2 A_ThrustLower - Loop - ThrustInit1: - TSPK A 3 - TSPK A 4 A_ThrustInitDn - TSPK A -1 - Loop - BloodThrustInit1: - TSPK B 3 - TSPK B 4 A_ThrustInitDn - TSPK B -1 - Loop - ThrustInit2: - TSPK A 3 - TSPK A 4 A_ThrustInitUp - TSPK A 10 - Loop - BloodThrustInit2: - TSPK B 3 - TSPK B 4 A_ThrustInitUp - TSPK B 10 - Loop - ThrustRaise: - TSPK A 8 A_ThrustRaise - TSPK A 6 A_ThrustRaise - TSPK A 4 A_ThrustRaise - TSPK A 3 A_SetSolid - TSPK A 2 A_ThrustImpale - Loop - BloodThrustRaise: - TSPK B 8 A_ThrustRaise - TSPK B 6 A_ThrustRaise - TSPK B 4 A_ThrustRaise - TSPK B 3 A_SetSolid - TSPK B 2 A_ThrustImpale - Loop - } -} - -// Spike up ----------------------------------------------------------------- - -ACTOR ThrustFloorUp : ThrustFloor -{ - +SOLID - +NOTELEPORT +FLOORCLIP - States - { - Spawn: - Goto ThrustInit2 - } -} - -// Spike down --------------------------------------------------------------- - -ACTOR ThrustFloorDown : ThrustFloor -{ - +NOTELEPORT +FLOORCLIP - +INVISIBLE - States - { - Spawn: - Goto ThrustInit1 - } -} diff --git a/wadsrc/static/actors/hexen/teleportother.txt b/wadsrc/static/actors/hexen/teleportother.txt deleted file mode 100644 index 7ef86636d..000000000 --- a/wadsrc/static/actors/hexen/teleportother.txt +++ /dev/null @@ -1,112 +0,0 @@ - -// Teleport Other Artifact -------------------------------------------------- - -ACTOR ArtiTeleportOther : Inventory native -{ - +COUNTITEM - +FLOATBOB - +INVENTORY.INVBAR - +INVENTORY.PICKUPFLASH - +INVENTORY.FANCYPICKUPSOUND - Inventory.DefMaxAmount - Inventory.Icon "ARTITELO" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_ARTITELEPORTOTHER" - Tag "$TAG_ARTITELEPORTOTHER" - States - { - Spawn: - TELO ABCD 5 - Loop - } -} - - -// Teleport Other FX -------------------------------------------------------- - -ACTOR TelOtherFX1 native -{ - Damage 10001 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - +BLOODLESSIMPACT - Radius 16 - Height 16 - Speed 20 - - action native A_TeloSpawnA (); - action native A_TeloSpawnB (); - action native A_TeloSpawnC (); - action native A_TeloSpawnD (); - action native A_CheckTeleRing (); - - States - { - Spawn: - TRNG E 5 Bright - TRNG D 4 Bright - TRNG C 3 Bright A_TeloSpawnC - TRNG B 3 Bright A_TeloSpawnB - TRNG A 3 Bright A_TeloSpawnA - TRNG B 3 Bright A_TeloSpawnB - TRNG C 3 Bright A_TeloSpawnC - TRNG D 3 Bright A_TeloSpawnD - Goto Spawn+2 - Death: - TRNG E 3 Bright - Stop - } -} - - -ACTOR TelOtherFX2 : TelOtherFX1 -{ - Speed 16 - States - { - Spawn: - TRNG BCDCB 4 Bright - TRNG A 4 Bright A_CheckTeleRing - Loop - } -} - -ACTOR TelOtherFX3 : TelOtherFX1 -{ - Speed 16 - States - { - Spawn: - TRNG CDCBA 4 Bright - TRNG B 4 Bright A_CheckTeleRing - Loop - } -} - -ACTOR TelOtherFX4 : TelOtherFX1 -{ - Speed 16 - States - { - Spawn: - TRNG DCBAB 4 Bright - TRNG C 4 Bright A_CheckTeleRing - Loop - } - -} - -ACTOR TelOtherFX5 : TelOtherFX1 -{ - Speed 16 - States - { - Spawn: - TRNG CBABC 4 Bright - TRNG D 4 Bright A_CheckTeleRing - Loop - } -} - - diff --git a/wadsrc/static/actors/hexen/wraith.txt b/wadsrc/static/actors/hexen/wraith.txt deleted file mode 100644 index 8d25bc74a..000000000 --- a/wadsrc/static/actors/hexen/wraith.txt +++ /dev/null @@ -1,218 +0,0 @@ - -// Wraith ------------------------------------------------------------------- - -ACTOR Wraith -{ - Health 150 - PainChance 25 - Speed 11 - Height 55 - Mass 75 - Damage 10 - Monster - +NOGRAVITY +DROPOFF +FLOAT - +FLOORCLIP +TELESTOMP - SeeSound "WraithSight" - AttackSound "WraithAttack" - PainSound "WraithPain" - DeathSound "WraithDeath" - ActiveSound "WraithActive" - HitObituary "$OB_WRAITHHIT" - Obituary "$OB_WRAITH" - - action native A_WraithInit(); - action native A_WraithChase(); - action native A_WraithFX3(); - action native A_WraithMelee(); - - States - { - Spawn: - WRTH A 10 - WRTH B 5 A_WraithInit - Goto Look - Look: - WRTH AB 15 A_Look - Loop - See: - WRTH ABCD 4 A_WraithChase - Loop - Pain: - WRTH A 2 - WRTH H 6 A_Pain - Goto See - Melee: - WRTH E 6 A_FaceTarget - WRTH F 6 A_WraithFX3 - WRTH G 6 A_WraithMelee - Goto See - Missile: - WRTH E 6 A_FaceTarget - WRTH F 6 - WRTH G 6 A_CustomMissile("WraithFX1", 32, 0) - Goto See - Death: - WRTH I 4 - WRTH J 4 A_Scream - WRTH KL 4 - WRTH M 4 A_NoBlocking - WRTH N 4 A_QueueCorpse - WRTH O 4 - WRTH PQ 5 - WRTH R -1 - Stop - XDeath: - WRT2 A 5 - WRT2 B 5 A_Scream - WRT2 CD 5 - WRT2 E 5 A_NoBlocking - WRT2 F 5 A_QueueCorpse - WRT2 G 5 - WRT2 H -1 - Stop - Ice: - WRT2 I 5 A_FreezeDeath - WRT2 I 1 A_FreezeDeathChunks - Wait - } -} - -// Buried wraith ------------------------------------------------------------ - -ACTOR WraithBuried : Wraith -{ - Height 68 - -SHOOTABLE - -SOLID - +DONTMORPH - +DONTBLAST - +SPECIALFLOORCLIP - +STAYMORPHED - +INVISIBLE - PainChance 0 - - action native A_WraithRaiseInit(); - action native A_WraithRaise(); - - States - { - Spawn: - Goto Super::Look - See: - WRTH A 2 A_WraithRaiseInit - WRTH A 2 A_WraithRaise - WRTH A 2 A_FaceTarget - WRTH BB 2 A_WraithRaise - Goto See + 1 - Chase: - Goto Super::See - } -} - -// Wraith FX 1 -------------------------------------------------------------- - -ACTOR WraithFX1 -{ - Speed 14 - Radius 10 - Height 6 - Mass 5 - Damage 5 - DamageType "Fire" - Projectile - +FLOORCLIP - SeeSound "WraithMissileFire" - DeathSound "WraithMissileExplode" - - action native A_WraithFX2(); - - States - { - Spawn: - WRBL A 3 Bright - WRBL B 3 Bright A_WraithFX2 - WRBL C 3 Bright - Loop - Death: - WRBL D 4 Bright - WRBL E 4 Bright A_WraithFX2 - WRBL F 4 Bright - WRBL GH 3 Bright A_WraithFX2 - WRBL I 3 Bright - Stop - } -} - -// Wraith FX 2 -------------------------------------------------------------- - -ACTOR WraithFX2 -{ - Radius 2 - Height 5 - Mass 5 - +NOBLOCKMAP +DROPOFF - +FLOORCLIP +NOTELEPORT - States - { - Spawn: - WRBL JKLMNOP 4 Bright - Stop - } -} - -// Wraith FX 3 -------------------------------------------------------------- - -ACTOR WraithFX3 -{ - Radius 2 - Height 5 - Mass 5 - +NOBLOCKMAP +DROPOFF +MISSILE - +FLOORCLIP +NOTELEPORT - DeathSound "Drip" - States - { - Spawn: - WRBL QRS 4 Bright - Loop - Death: - WRBL S 4 Bright - Stop - } -} - -// Wraith FX 4 -------------------------------------------------------------- - -ACTOR WraithFX4 -{ - Radius 2 - Height 5 - Mass 5 - +NOBLOCKMAP +DROPOFF +MISSILE - +NOTELEPORT - DeathSound "Drip" - States - { - Spawn: - WRBL TUVW 4 - Loop - Death: - WRBL W 10 - Stop - } -} - -// Wraith FX 5 -------------------------------------------------------------- - -ACTOR WraithFX5 : WraithFX4 -{ - States - { - Spawn: - WRBL XYZ 7 - Loop - Death: - WRBL Z 35 - Stop - } -} diff --git a/wadsrc/static/actors/strife/strifestuff.txt b/wadsrc/static/actors/strife/strifestuff.txt index 95d6d93cd..3bbc1fb90 100644 --- a/wadsrc/static/actors/strife/strifestuff.txt +++ b/wadsrc/static/actors/strife/strifestuff.txt @@ -1675,8 +1675,8 @@ ACTOR Meat native ACTOR Junk : Meat { -states -{ + States + { Spawn: JUNK A 700 Stop diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 88ce6a2c7..6ecac49c6 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,23 +1,3 @@ -#include "actors/hexen/clericflame.txt" -#include "actors/hexen/clericholy.txt" -#include "actors/hexen/clericstaff.txt" -#include "actors/hexen/magewand.txt" -#include "actors/hexen/magecone.txt" -#include "actors/hexen/magelightning.txt" -#include "actors/hexen/magestaff.txt" -#include "actors/hexen/fighterfist.txt" -#include "actors/hexen/fighteraxe.txt" -#include "actors/hexen/fighterhammer.txt" -#include "actors/hexen/fighterquietus.txt" -#include "actors/hexen/dragon.txt" -#include "actors/hexen/healingradius.txt" -#include "actors/hexen/teleportother.txt" -#include "actors/hexen/iceguy.txt" -#include "actors/hexen/serpent.txt" -#include "actors/hexen/spike.txt" -#include "actors/hexen/wraith.txt" -#include "actors/hexen/heresiarch.txt" - #include "actors/strife/strifehumanoid.txt" #include "actors/strife/strifeplayer.txt" #include "actors/strife/strifeweapons.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 570d6eee3..c4dac2b95 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -116,7 +116,6 @@ zscript/hexen/bishop.txt zscript/hexen/blastradius.txt zscript/hexen/boostarmor.txt zscript/hexen/clericmace.txt -/* zscript/hexen/clericflame.txt zscript/hexen/clericholy.txt zscript/hexen/clericstaff.txt @@ -136,4 +135,3 @@ zscript/hexen/serpent.txt zscript/hexen/spike.txt zscript/hexen/wraith.txt zscript/hexen/heresiarch.txt -*/ \ No newline at end of file diff --git a/wadsrc/static/zscript/hexen/clericflame.txt b/wadsrc/static/zscript/hexen/clericflame.txt new file mode 100644 index 000000000..ae5ecaac3 --- /dev/null +++ b/wadsrc/static/zscript/hexen/clericflame.txt @@ -0,0 +1,211 @@ + +// The Cleric's Flame Strike ------------------------------------------------ + +class CWeapFlame : ClericWeapon +{ + Default + { + +NOGRAVITY + Weapon.SelectionOrder 1000; + Weapon.AmmoUse 4; + Weapon.AmmoGive 25; + Weapon.KickBack 150; + Weapon.YAdjust 10; + Weapon.AmmoType1 "Mana2"; + Inventory.PickupMessage "$TXT_WEAPON_C3"; + Tag "$TAG_CWEAPFLAME"; + } + + action native void A_CFlameAttack(); + + States + { + Spawn: + WCFM ABCDEFGH 4 Bright; + Loop; + Select: + CFLM A 1 A_Raise; + Loop; + Deselect: + CFLM A 1 A_Lower; + Loop; + Ready: + CFLM AAAABBBBCCCC 1 A_WeaponReady; + Loop; + Fire: + CFLM A 2 Offset (0, 40); + CFLM D 2 Offset (0, 50); + CFLM D 2 Offset (0, 36); + CFLM E 4 Bright; + CFLM F 4 Bright A_CFlameAttack; + CFLM E 4 Bright; + CFLM G 2 Offset (0, 40); + CFLM G 2; + Goto Ready; + } +} + +// Floor Flame -------------------------------------------------------------- + +class CFlameFloor : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Add"; + } + States + { + Spawn: + CFFX N 5 Bright; + CFFX O 4 Bright; + CFFX P 3 Bright; + Stop; + } +} + +// Flame Puff --------------------------------------------------------------- + +class FlamePuff : Actor +{ + Default + { + Radius 1; + Height 1; + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Add";; + SeeSound "ClericFlameExplode"; + AttackSound "ClericFlameExplode"; + } + States + { + Spawn: + CFFX ABC 3 Bright; + CFFX D 4 Bright; + CFFX E 3 Bright; + CFFX F 4 Bright; + CFFX G 3 Bright; + CFFX H 4 Bright; + CFFX I 3 Bright; + CFFX J 4 Bright; + CFFX K 3 Bright; + CFFX L 4 Bright; + CFFX M 3 Bright; + Stop; + } +} + +// Flame Puff 2 ------------------------------------------------------------- + +class FlamePuff2 : FlamePuff +{ + States + { + Spawn: + CFFX ABC 3 Bright; + CFFX D 4 Bright; + CFFX E 3 Bright; + CFFX F 4 Bright; + CFFX G 3 Bright; + CFFX H 4 Bright; + CFFX IC 3 Bright; + CFFX D 4 Bright; + CFFX E 3 Bright; + CFFX F 4 Bright; + CFFX G 3 Bright; + CFFX H 4 Bright; + CFFX I 3 Bright; + CFFX J 4 Bright; + CFFX K 3 Bright; + CFFX L 4 Bright; + CFFX M 3 Bright; + Stop; + } +} + +// Circle Flame ------------------------------------------------------------- + +class CircleFlame : Actor +{ + Default + { + Radius 6; + Damage 2; + DamageType "Fire"; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + DeathSound "ClericFlameCircle"; + Obituary "$OB_MPCWEAPFLAME"; + } + + action native void A_CFlameRotate(); + + States + { + Spawn: + CFCF A 4 Bright; + CFCF B 2 Bright A_CFlameRotate; + CFCF C 2 Bright; + CFCF D 1 Bright; + CFCF E 2 Bright; + CFCF F 2 Bright A_CFlameRotate; + CFCF G 1 Bright; + CFCF HI 2 Bright; + CFCF J 1 Bright A_CFlameRotate; + CFCF K 2 Bright; + CFCF LM 3 Bright; + CFCF N 2 Bright A_CFlameRotate; + CFCF O 3 Bright; + CFCF P 2 Bright; + Stop; + Death: + CFCF QR 3 Bright; + CFCF S 3 Bright A_Explode(20, 20, 0); + CFCF TUVWXYZ 3 Bright; + Stop; + } +} + +// Flame Missile ------------------------------------------------------------ + +class CFlameMissile : FastProjectile native +{ + Default + { + Speed 200; + Radius 14; + Height 8; + Damage 8; + DamageType "Fire"; + +INVISIBLE + RenderStyle "Add"; + Obituary "$OB_MPCWEAPFLAME"; + } + + action native void A_CFlamePuff(); + action native void A_CFlameMissile(); + + States + { + Spawn: + CFFX A 4 Bright; + CFFX A 1 A_CFlamePuff; + Goto Death + 1; + Death: + CFFX A 1 Bright A_CFlameMissile; + CFFX ABC 3 Bright; + CFFX D 4 Bright; + CFFX E 3 Bright; + CFFX F 4 Bright; + CFFX G 3 Bright; + CFFX H 4 Bright; + CFFX I 3 Bright; + CFFX J 4 Bright; + CFFX K 3 Bright; + CFFX L 4 Bright; + CFFX M 3 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/clericholy.txt b/wadsrc/static/zscript/hexen/clericholy.txt new file mode 100644 index 000000000..b238ce09b --- /dev/null +++ b/wadsrc/static/zscript/hexen/clericholy.txt @@ -0,0 +1,267 @@ + +// Cleric Weapon Piece ------------------------------------------------------ + +class ClericWeaponPiece : WeaponPiece +{ + Default + { + Inventory.PickupSound "misc/w_pkup"; + Inventory.PickupMessage "$TXT_WRAITHVERGE_PIECE"; + Inventory.ForbiddenTo "FighterPlayer", "MagePlayer"; + WeaponPiece.Weapon "CWeapWraithverge"; + +FLOATBOB + } +} + +// Cleric Weapon Piece 1 ---------------------------------------------------- + +class CWeaponPiece1 : ClericWeaponPiece +{ + Default + { + WeaponPiece.Number 1; + } + States + { + Spawn: + WCH1 A -1; + Stop; + } +} + +// Cleric Weapon Piece 2 ---------------------------------------------------- + +class CWeaponPiece2 : ClericWeaponPiece +{ + Default + { + WeaponPiece.Number 2; + } + States + { + Spawn: + WCH2 A -1; + Stop; + } +} + +// Cleric Weapon Piece 3 ---------------------------------------------------- + +class CWeaponPiece3 : ClericWeaponPiece +{ + Default + { + WeaponPiece.Number 3; + } + States + { + Spawn: + WCH3 A -1; + Stop; + } +} + +// Wraithverge Drop --------------------------------------------------------- + +class WraithvergeDrop : Actor +{ + States + { + Spawn: + TNT1 A 1; + TNT1 A 1 A_DropWeaponPieces("CWeaponPiece1", "CWeaponPiece2", "CWeaponPiece3"); + Stop; + } +} + +// Cleric's Wraithverge (Holy Symbol?) -------------------------------------- + +class CWeapWraithverge : ClericWeapon native +{ + Default + { + Health 3; + Weapon.SelectionOrder 3000; + +WEAPON.PRIMARY_USES_BOTH; + +Inventory.NoAttenPickupSound + Weapon.AmmoUse1 18; + Weapon.AmmoUse2 18; + Weapon.AmmoGive1 20; + Weapon.AmmoGive2 20; + Weapon.KickBack 150; + Weapon.AmmoType1 "Mana1"; + Weapon.AmmoType2 "Mana2"; + Inventory.PickupMessage "$TXT_WEAPON_C4"; + Tag "$TAG_CWEAPWRAITHVERGE"; + Inventory.PickupSound "WeaponBuild"; + } + + action native void A_CHolyAttack(); + action native void A_CHolyPalette(); + + States + { + Spawn: + TNT1 A -1; + Stop; + Ready: + CHLY A 1 A_WeaponReady; + Loop; + Select: + CHLY A 1 A_Raise; + Loop; + Deselect: + CHLY A 1 A_Lower; + Loop; + Fire: + CHLY AB 1 Bright Offset (0, 40); + CHLY CD 2 Bright Offset (0, 43); + CHLY E 2 Bright Offset (0, 45); + CHLY F 6 Bright Offset (0, 48) A_CHolyAttack; + CHLY GG 2 Bright Offset (0, 40) A_CHolyPalette; + CHLY G 2 Offset (0, 36) A_CHolyPalette; + Goto Ready; + } +} + +// Holy Missile ------------------------------------------------------------- + +class HolyMissile : Actor +{ + Default + { + Speed 30; + Radius 15; + Height 8; + Damage 4; + Projectile; + -ACTIVATEIMPACT -ACTIVATEPCROSS + +EXTREMEDEATH + } + + action native void A_CHolyAttack2(); + + States + { + Spawn: + SPIR PPPP 3 Bright A_SpawnItemEx("HolyMissilePuff"); + Death: + SPIR P 1 Bright A_CHolyAttack2; + Stop; + } +} + +// Holy Missile Puff -------------------------------------------------------- + +class HolyMissilePuff : Actor +{ + Default + { + Radius 4; + Height 8; + +NOBLOCKMAP +NOGRAVITY +DROPOFF + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Spawn: + SPIR QRSTU 3; + Stop; + } +} + +// Holy Puff ---------------------------------------------------------------- + +class HolyPuff : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + SPIR KLMNO 3; + Stop; + } +} + +// Holy Spirit -------------------------------------------------------------- + +class HolySpirit : Actor native +{ + Default + { + Health 105; + Speed 12; + Radius 10; + Height 6; + Damage 3; + Projectile; + +RIPPER +SEEKERMISSILE + +FOILINVUL +SKYEXPLODE +NOEXPLODEFLOOR +CANBLAST + +EXTREMEDEATH + RenderStyle "Translucent"; + Alpha 0.4; + DeathSound "SpiritDie"; + Obituary "$OB_MPCWEAPWRAITHVERGE"; + } + + action native void A_CHolySeek(); + action native void A_CHolyCheckScream(); + + States + { + Spawn: + SPIR AAB 2 A_CHolySeek; + SPIR B 2 A_CHolyCheckScream; + Loop; + Death: + SPIR D 4; + SPIR E 4 A_Scream; + SPIR FGHI 4; + Stop; + } +} + +// Holy Tail ---------------------------------------------------------------- + +class HolyTail : Actor +{ + Default + { + Radius 1; + Height 1; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +NOCLIP + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.6; + } + + action native void A_CHolyTail(); + + States + { + Spawn: + SPIR C 1 A_CHolyTail; + Loop; + TailTrail: + SPIR D -1; + Stop; + } +} + +// Holy Tail Trail --------------------------------------------------------- + +class HolyTailTrail : HolyTail +{ + States + { + Spawn: + Goto TailTrail; + } +} diff --git a/wadsrc/static/zscript/hexen/clericstaff.txt b/wadsrc/static/zscript/hexen/clericstaff.txt new file mode 100644 index 000000000..7ae0e9da3 --- /dev/null +++ b/wadsrc/static/zscript/hexen/clericstaff.txt @@ -0,0 +1,105 @@ + +// The Cleric's Serpent Staff ----------------------------------------------- + +class CWeapStaff : ClericWeapon +{ + Default + { + Weapon.SelectionOrder 1600; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 25; + Weapon.KickBack 150; + Weapon.YAdjust 10; + Weapon.AmmoType1 "Mana1"; + Inventory.PickupMessage "$TXT_WEAPON_C2"; + Obituary "$OB_MPCWEAPSTAFFM"; + Tag "$TAG_CWEAPSTAFF"; + } + + action native void A_CStaffInitBlink(); + action native void A_CStaffCheckBlink(); + action native void A_CStaffCheck(); + action native void A_CStaffAttack(); + + States + { + Spawn: + WCSS A -1; + Stop; + Select: + CSSF C 1 A_Raise; + Loop; + Deselect: + CSSF B 3; + CSSF C 4; + CSSF C 1 A_Lower; + Wait; + Ready: + CSSF C 4; + CSSF B 3 A_CStaffInitBlink; + CSSF AAAAAAA 1 A_WeaponReady; + CSSF A 1 A_CStaffCheckBlink; + Goto Ready + 2; + Fire: + CSSF A 1 Offset (0, 45) A_CStaffCheck; + CSSF J 1 Offset (0, 50) A_CStaffAttack; + CSSF J 2 Offset (0, 50); + CSSF J 2 Offset (0, 45); + CSSF A 2 Offset (0, 40); + CSSF A 2 Offset (0, 36); + Goto Ready + 2; + Blink: + CSSF BBBCCCCCBBB 1 A_WeaponReady; + Goto Ready + 2; + Drain: + CSSF K 10 Offset (0, 36); + Goto Ready + 2; + } +} + +// Serpent Staff Missile ---------------------------------------------------- + +class CStaffMissile : Actor native +{ + Default + { + Speed 22; + Radius 12; + Height 10; + Damage 5; + RenderStyle "Add"; + Projectile; + DeathSound "ClericCStaffExplode"; + Obituary "$OB_MPCWEAPSTAFFR"; + } + States + { + Spawn: + CSSF DDEE 1 Bright A_CStaffMissileSlither; + Loop; + Death: + CSSF FG 4 Bright; + CSSF HI 3 Bright; + Stop; + } +} + +// Serpent Staff Puff ------------------------------------------------------- + +class CStaffPuff : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + +PUFFONACTORS + RenderStyle "Translucent"; + Alpha 0.6; + SeeSound "ClericCStaffHitThing"; + } + States + { + Spawn: + FHFX STUVW 4; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/dragon.txt b/wadsrc/static/zscript/hexen/dragon.txt new file mode 100644 index 000000000..bfc037e71 --- /dev/null +++ b/wadsrc/static/zscript/hexen/dragon.txt @@ -0,0 +1,126 @@ + +// Dragon ------------------------------------------------------------------- + +class Dragon : Actor +{ + Default + { + Health 640; + PainChance 128; + Speed 10; + Height 65; + Mass 0x7fffffff; + Monster; + +NOGRAVITY +FLOAT +NOBLOOD + +BOSS + +DONTMORPH +NOTARGET + +NOICEDEATH + SeeSound "DragonSight"; + AttackSound "DragonAttack"; + PainSound "DragonPain"; + DeathSound "DragonDeath"; + ActiveSound "DragonActive"; + Obituary "$OB_DRAGON"; + } + + action native void A_DragonInitFlight(); + action native void A_DragonFlap(); + action native void A_DragonFlight(); + action native void A_DragonPain(); + action native void A_DragonAttack(); + action native void A_DragonCheckCrash(); + + States + { + Spawn: + DRAG D 10 A_Look; + Loop; + See: + DRAG CB 5; + DRAG A 5 A_DragonInitFlight; + DRAG B 3 A_DragonFlap; + DRAG BCCDDCCBBAA 3 A_DragonFlight; + Goto See + 3; + Pain: + DRAG F 10 A_DragonPain; + Goto See + 3; + Missile: + DRAG E 8 A_DragonAttack; + Goto See + 3; + Death: + DRAG G 5 A_Scream; + DRAG H 4 A_NoBlocking; + DRAG I 4; + DRAG J 4 A_DragonCheckCrash; + Wait; + Crash: + DRAG KL 5; + DRAG M -1; + Stop; + } +} + +// Dragon Fireball ---------------------------------------------------------- + +class DragonFireball : Actor +{ + Default + { + Speed 24; + Radius 12; + Height 10; + Damage 6; + DamageType "Fire"; + Projectile; + -ACTIVATEIMPACT -ACTIVATEPCROSS + RenderStyle "Add"; + DeathSound "DragonFireballExplode"; + } + + action native void A_DragonFX2(); + + States + { + Spawn: + DRFX ABCDEF 4 Bright; + Loop; + Death: + DRFX GHI 4 Bright; + DRFX J 4 Bright A_DragonFX2; + DRFX KL 3 Bright; + Stop; + } +} + +// Dragon Fireball Secondary Explosion -------------------------------------- + +class DragonExplosion : Actor +{ + Default + { + Radius 8; + Height 8; + DamageType "Fire"; + +NOBLOCKMAP + +NOTELEPORT + +INVISIBLE + RenderStyle "Add"; + DeathSound "DragonFireballExplode"; + } + States + { + Spawn: + CFCF Q 1 Bright; + CFCF Q 4 Bright A_UnHideThing; + CFCF R 3 Bright A_Scream; + CFCF S 4 Bright; + CFCF T 3 Bright A_Explode (80, 128, 0); + CFCF U 4 Bright; + CFCF V 3 Bright; + CFCF W 4 Bright; + CFCF X 3 Bright; + CFCF Y 4 Bright; + CFCF Z 3 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/fighteraxe.txt b/wadsrc/static/zscript/hexen/fighteraxe.txt new file mode 100644 index 000000000..30b235192 --- /dev/null +++ b/wadsrc/static/zscript/hexen/fighteraxe.txt @@ -0,0 +1,122 @@ + +// The Fighter's Axe -------------------------------------------------------- + +class FWeapAxe : FighterWeapon native +{ + Default + { + Weapon.SelectionOrder 1500; + +WEAPON.AXEBLOOD +WEAPON.AMMO_OPTIONAL +WEAPON.MELEEWEAPON + Weapon.AmmoUse1 2; + Weapon.AmmoGive1 25; + Weapon.KickBack 150; + Weapon.YAdjust -12; + Weapon.AmmoType1 "Mana1"; + Inventory.PickupMessage "$TXT_WEAPON_F2"; + Obituary "$OB_MPFWEAPAXE"; + Tag "$TAG_FWEAPAXE"; + } + + action native void A_FAxeCheckUp(); + action native void A_FAxeCheckReady(); + action native void A_FAxeCheckAtk(); + action native void A_FAxeAttack(); + action native void A_FAxeCheckUpG(); + action native void A_FAxeCheckReadyG(); + + States + { + Spawn: + WFAX A -1; + Stop; + Select: + FAXE A 1 A_FAxeCheckUp; + Loop; + Deselect: + FAXE A 1 A_Lower; + Loop; + Ready: + FAXE A 1 A_FAxeCheckReady; + Loop; + Fire: + FAXE B 4 Offset (15, 32) A_FAxeCheckAtk; + FAXE C 3 Offset (15, 32); + FAXE D 2 Offset (15, 32); + FAXE D 1 Offset (-5, 70) A_FAxeAttack; + FAXE D 2 Offset (-25, 90); + FAXE E 1 Offset (15, 32); + FAXE E 2 Offset (10, 54); + FAXE E 7 Offset (10, 150); + FAXE A 1 Offset (0, 60) A_ReFire; + FAXE A 1 Offset (0, 52); + FAXE A 1 Offset (0, 44); + FAXE A 1 Offset (0, 36); + FAXE A 1; + Goto Ready; + SelectGlow: + FAXE L 1 A_FAxeCheckUpG; + Loop; + DeselectGlow: + FAXE L 1 A_Lower; + Loop; + ReadyGlow: + FAXE LLL 1 A_FAxeCheckReadyG; + FAXE MMM 1 A_FAxeCheckReadyG; + Loop; + FireGlow: + FAXE N 4 Offset (15, 32); + FAXE O 3 Offset (15, 32); + FAXE P 2 Offset (15, 32); + FAXE P 1 Offset (-5, 70) A_FAxeAttack; + FAXE P 2 Offset (-25, 90); + FAXE Q 1 Offset (15, 32); + FAXE Q 2 Offset (10, 54); + FAXE Q 7 Offset (10, 150); + FAXE A 1 Offset (0, 60) A_ReFire; + FAXE A 1 Offset (0, 52); + FAXE A 1 Offset (0, 44); + FAXE A 1 Offset (0, 36); + FAXE A 1; + Goto ReadyGlow; + } +} + +// Axe Puff ----------------------------------------------------------------- + +class AxePuff : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + +PUFFONACTORS + RenderStyle "Translucent"; + Alpha 0.6; + SeeSound "FighterAxeHitThing"; + AttackSound "FighterHammerHitWall"; + ActiveSound "FighterHammerMiss"; + } + States + { + Spawn: + FHFX STUVW 4; + Stop; + } +} + +// Glowing Axe Puff --------------------------------------------------------- + +class AxePuffGlow : AxePuff +{ + Default + { + +PUFFONACTORS + RenderStyle "Add"; + Alpha 1; + } + States + { + Spawn: + FAXE RSTUVWX 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/fighterfist.txt b/wadsrc/static/zscript/hexen/fighterfist.txt new file mode 100644 index 000000000..8428ebe7d --- /dev/null +++ b/wadsrc/static/zscript/hexen/fighterfist.txt @@ -0,0 +1,70 @@ + +// Fist (first weapon) ------------------------------------------------------ + +class FWeapFist : FighterWeapon +{ + Default + { + +BLOODSPLATTER + Weapon.SelectionOrder 3400; + +WEAPON.MELEEWEAPON + Weapon.KickBack 150; + Obituary "$OB_MPFWEAPFIST"; + Tag "$TAG_FWEAPFIST"; + } + + action native void A_FPunchAttack(); + + States + { + Select: + FPCH A 1 A_Raise; + Loop; + Deselect: + FPCH A 1 A_Lower; + Loop; + Ready: + FPCH A 1 A_WeaponReady; + Loop; + Fire: + FPCH B 5 Offset (5, 40); + FPCH C 4 Offset (5, 40); + FPCH D 4 Offset (5, 40) A_FPunchAttack; + FPCH C 4 Offset (5, 40); + FPCH B 5 Offset (5, 40) A_ReFire; + Goto Ready; + Fire2: + FPCH DE 4 Offset (5, 40); + FPCH E 1 Offset (15, 50); + FPCH E 1 Offset (25, 60); + FPCH E 1 Offset (35, 70); + FPCH E 1 Offset (45, 80); + FPCH E 1 Offset (55, 90); + FPCH E 1 Offset (65, 90); + FPCH E 10 Offset (0, 150); + Goto Ready; + } +} + +// Punch puff --------------------------------------------------------------- + +class PunchPuff : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + +PUFFONACTORS + RenderStyle "Translucent"; + Alpha 0.6; + SeeSound "FighterPunchHitThing"; + AttackSound "FighterPunchHitWall"; + ActiveSound "FighterPunchMiss"; + VSpeed 1; + } + States + { + Spawn: + FHFX STUVW 4; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/fighterhammer.txt b/wadsrc/static/zscript/hexen/fighterhammer.txt new file mode 100644 index 000000000..f415cbb72 --- /dev/null +++ b/wadsrc/static/zscript/hexen/fighterhammer.txt @@ -0,0 +1,110 @@ + +// The Fighter's Hammer ----------------------------------------------------- + +class FWeapHammer : FighterWeapon +{ + Default + { + +BLOODSPLATTER + Weapon.SelectionOrder 900; + +WEAPON.AMMO_OPTIONAL +WEAPON.MELEEWEAPON + Weapon.AmmoUse1 3; + Weapon.AmmoGive1 25; + Weapon.KickBack 150; + Weapon.YAdjust -10; + Weapon.AmmoType1 "Mana2"; + Inventory.PickupMessage "$TXT_WEAPON_F3"; + Obituary "$OB_MPFWEAPHAMMERM"; + Tag "$TAG_FWEAPHAMMER"; + } + + action native void A_FHammerAttack(); + action native void A_FHammerThrow(); + + States + { + Spawn: + WFHM A -1; + Stop; + Select: + FHMR A 1 A_Raise; + Loop; + Deselect: + FHMR A 1 A_Lower; + Loop; + Ready: + FHMR A 1 A_WeaponReady; + Loop; + Fire: + FHMR B 6 Offset (5, 0); + FHMR C 3 Offset (5, 0) A_FHammerAttack; + FHMR D 3 Offset (5, 0); + FHMR E 2 Offset (5, 0); + FHMR E 10 Offset (5, 150) A_FHammerThrow; + FHMR A 1 Offset (0, 60); + FHMR A 1 Offset (0, 55); + FHMR A 1 Offset (0, 50); + FHMR A 1 Offset (0, 45); + FHMR A 1 Offset (0, 40); + FHMR A 1 Offset (0, 35); + FHMR A 1; + Goto Ready; + } +} + +// Hammer Missile ----------------------------------------------------------- + +class HammerMissile : Actor +{ + Default + { + Speed 25; + Radius 14; + Height 20; + Damage 10; + DamageType "Fire"; + Projectile; + DeathSound "FighterHammerExplode"; + Obituary "$OB_MPFWEAPHAMMERR"; + } + + States + { + Spawn: + FHFX A 2 Bright; + FHFX B 2 Bright A_PlaySound ("FighterHammerContinuous"); + FHFX CDEFGH 2 Bright; + Loop; + Death: + FHFX I 3 Bright A_SetTranslucent(1,1); + FHFX J 3 Bright; + FHFX K 3 Bright A_Explode (128, 128, 0); + FHFX LM 3 Bright; + FHFX N 3; + FHFX OPQR 3 Bright; + Stop; + } +} + +// Hammer Puff (also used by fist) ------------------------------------------ + +class HammerPuff : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + +PUFFONACTORS + RenderStyle "Translucent"; + Alpha 0.6; + VSpeed 0.8; + SeeSound "FighterHammerHitThing"; + AttackSound "FighterHammerHitWall"; + ActiveSound "FighterHammerMiss"; + } + States + { + Spawn: + FHFX STUVW 4; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/fighterquietus.txt b/wadsrc/static/zscript/hexen/fighterquietus.txt new file mode 100644 index 000000000..5fe132237 --- /dev/null +++ b/wadsrc/static/zscript/hexen/fighterquietus.txt @@ -0,0 +1,185 @@ + +// Fighter Weapon Piece ----------------------------------------------------- + +class FighterWeaponPiece : WeaponPiece +{ + Default + { + Inventory.PickupSound "misc/w_pkup"; + Inventory.PickupMessage "$TXT_QUIETUS_PIECE"; + Inventory.ForbiddenTo "ClericPlayer", "MagePlayer"; + WeaponPiece.Weapon "FWeapQuietus"; + +FLOATBOB + } +} + +// Fighter Weapon Piece 1 --------------------------------------------------- + +class FWeaponPiece1 : FighterWeaponPiece +{ + Default + { + WeaponPiece.Number 1; + } + States + { + Spawn: + WFR1 A -1 Bright; + Stop; + } +} + +// Fighter Weapon Piece 2 --------------------------------------------------- + +class FWeaponPiece2 : FighterWeaponPiece +{ + Default + { + WeaponPiece.Number 2; + } + States + { + Spawn: + WFR2 A -1 Bright; + Stop; + } +} + +// Fighter Weapon Piece 3 --------------------------------------------------- + +class FWeaponPiece3 : FighterWeaponPiece +{ + Default + { + WeaponPiece.Number 3; + } + States + { + Spawn: + WFR3 A -1 Bright; + Stop; + } +} + +// Quietus Drop ------------------------------------------------------------- + +class QuietusDrop : Actor +{ + States + { + Spawn: + TNT1 A 1; + TNT1 A 1 A_DropWeaponPieces("FWeaponPiece1", "FWeaponPiece2", "FWeaponPiece3"); + Stop; + } +} + +// The Fighter's Sword (Quietus) -------------------------------------------- + +class FWeapQuietus : FighterWeapon +{ + Default + { + Health 3; + Weapon.SelectionOrder 2900; + +WEAPON.PRIMARY_USES_BOTH; + +Inventory.NoAttenPickupSound + Weapon.AmmoUse1 14; + Weapon.AmmoUse2 14; + Weapon.AmmoGive1 20; + Weapon.AmmoGive2 20; + Weapon.KickBack 150; + Weapon.YAdjust 10; + Weapon.AmmoType1 "Mana1"; + Weapon.AmmoType2 "Mana2"; + Inventory.PickupMessage "$TXT_WEAPON_F4"; + Inventory.PickupSound "WeaponBuild"; + Tag "$TAG_FWEAPQUIETUS"; + } + + action native void A_FSwordAttack(); + + States + { + Spawn: + TNT1 A -1; + Stop; + Select: + FSRD A 1 Bright A_Raise; + Loop; + Deselect: + FSRD A 1 Bright A_Lower; + Loop; + Ready: + FSRD AAAABBBBCCCC 1 Bright A_WeaponReady; + Loop; + Fire: + FSRD DE 3 Bright Offset (5, 36); + FSRD F 2 Bright Offset (5, 36); + FSRD G 3 Bright Offset (5, 36) A_FSwordAttack; + FSRD H 2 Bright Offset (5, 36); + FSRD I 2 Bright Offset (5, 36); + FSRD I 10 Bright Offset (5, 150); + FSRD A 1 Bright Offset (5, 60); + FSRD B 1 Bright Offset (5, 55); + FSRD C 1 Bright Offset (5, 50); + FSRD A 1 Bright Offset (5, 45); + FSRD B 1 Bright Offset (5, 40); + Goto Ready; + } +} + +// Fighter Sword Missile ---------------------------------------------------- + +class FSwordMissile : Actor native +{ + Default + { + Speed 30; + Radius 16; + Height 8; + Damage 8; + Projectile; + +EXTREMEDEATH + RenderStyle "Add"; + DeathSound "FighterSwordExplode"; + Obituary "$OB_MPFWEAPQUIETUS"; + } + + action native void A_FSwordFlames(); + + States + { + Spawn: + FSFX ABC 3 Bright; + Loop; + Death: + FSFX D 4 Bright; + FSFX E 3 Bright A_FSwordFlames; + FSFX F 4 Bright A_Explode (64, 128, 0); + FSFX G 3 Bright; + FSFX H 4 Bright; + FSFX I 3 Bright; + FSFX J 4 Bright; + FSFX KLM 3 Bright; + Stop; + } +} + +// Fighter Sword Flame ------------------------------------------------------ + +class FSwordFlame : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + FSFX NOPQRSTUVW 3 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/healingradius.txt b/wadsrc/static/zscript/hexen/healingradius.txt new file mode 100644 index 000000000..94d8e2dd5 --- /dev/null +++ b/wadsrc/static/zscript/hexen/healingradius.txt @@ -0,0 +1,26 @@ + +// Healing Radius Artifact -------------------------------------------------- + +class ArtiHealingRadius : Inventory native +{ + Default + { + +COUNTITEM + +FLOATBOB + Inventory.DefMaxAmount; + +INVENTORY.INVBAR + +INVENTORY.FANCYPICKUPSOUND + Inventory.PickupFlash "PickupFlash"; + Inventory.Icon "ARTIHRAD"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTIHEALINGRADIUS"; + Tag "$TAG_ARTIHEALINGRADIUS"; + } + States + { + Spawn: + HRAD ABCDEFGHIJKLMNOP 4 Bright; + Loop; + } +} + diff --git a/wadsrc/static/zscript/hexen/heresiarch.txt b/wadsrc/static/zscript/hexen/heresiarch.txt new file mode 100644 index 000000000..076bc01ca --- /dev/null +++ b/wadsrc/static/zscript/hexen/heresiarch.txt @@ -0,0 +1,362 @@ + +// The Heresiarch him/itself ------------------------------------------------ + +class Heresiarch native +{ + Default + { + Health 5000; + Painchance 10; + Speed 16; + Radius 40; + Height 110; + Mass 500; + Damage 9; + Monster; + +FLOORCLIP + +BOSS + +DONTMORPH + +NOTARGET + +NOICEDEATH + +DEFLECT + +NOBLOOD + SeeSound "SorcererSight"; + PainSound "SorcererPain"; + DeathSound "SorcererDeathScream"; + ActiveSound "SorcererActive"; + Obituary "$OB_HERESIARCH"; + } + + action native void A_SorcSpinBalls(); + action native void A_SpeedBalls(); + action native void A_SorcBossAttack(); + action native void A_SpawnFizzle(); + + States + { + Spawn: + SORC A 3; + SORC A 2 A_SorcSpinBalls; + Idle: + SORC A 10 A_Look; + Wait; + See: + SORC ABCD 5 A_Chase; + Loop; + Pain: + SORC G 8; + SORC G 8 A_Pain; + Goto See; + Missile: + SORC F 6 Bright A_FaceTarget; + SORC F 6 Bright A_SpeedBalls; + SORC F 6 Bright A_FaceTarget; + Wait; + Attack1: + SORC E 6 Bright; + SORC E 6 Bright A_SpawnFizzle; + SORC E 5 Bright A_FaceTarget; + Goto Attack1+1; + Attack2: + SORC E 2 Bright; + SORC E 2 Bright A_SorcBossAttack; + Goto See; + Death: + SORC H 5 Bright; + SORC I 5 Bright A_FaceTarget; + SORC J 5 Bright A_Scream; + SORC KLMNOPQRST 5 Bright; + SORC U 5 Bright A_NoBlocking; + SORC VWXY 5 Bright; + SORC Z -1 Bright; + Stop; + } +} + +// Base class for the balls flying around the Heresiarch's head ------------- + +class SorcBall native +{ + Default + { + Speed 10; + Radius 5; + Height 5; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + +FULLVOLDEATH + +CANBOUNCEWATER + +NOWALLBOUNCESND + BounceType "HexenCompat"; + SeeSound "SorcererBallBounce"; + DeathSound "SorcererBigBallExplode"; + } + + action native void A_SorcBallOrbit(); + action native void A_SorcBallPop(); + action native void A_BounceCheck (); +} + +// First ball (purple) - fires projectiles ---------------------------------- + +class SorcBall1 : SorcBall native +{ + States + { + Spawn: + SBMP ABCDEFGHIJKLMNOP 2 A_SorcBallOrbit; + Loop; + Pain: + SBMP A 5 A_SorcBallPop; + SBMP B 2 A_BounceCheck; + Wait; + Death: + SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1); + SBS4 D 5 A_Explode(255,255); + SBS4 E 5; + SBS4 FGH 6; + Stop; + } +} + + +// Second ball (blue) - generates the shield -------------------------------- + +class SorcBall2 : SorcBall native +{ + States + { + Spawn: + SBMB ABCDEFGHIJKLMNOP 2 A_SorcBallOrbit; + Loop; + Pain: + SBMB A 5 A_SorcBallPop; + SBMB B 2 A_BounceCheck; + Wait; + Death: + SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1); + SBS3 D 5 A_Explode(255,255); + SBS3 E 5; + SBS3 FGH 6; + Stop; + } +} + +// Third ball (green) - summons Bishops ------------------------------------- + +class SorcBall3 : SorcBall native +{ + States + { + Spawn: + SBMG ABCDEFGHIJKLMNOP 2 A_SorcBallOrbit; + Loop; + Pain: + SBMG A 5 A_SorcBallPop; + SBMG B 2 A_BounceCheck; + Wait; + Death: + SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1); + SBS3 D 5 A_Explode(255,255); + SBS3 E 5; + SBS3 FGH 6; + Stop; + } +} + + +// Sorcerer spell 1 (The burning, bouncing head thing) ---------------------- + +class SorcFX1 : Actor +{ + Default + { + Speed 7; + Radius 5; + Height 5; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + -NOGRAVITY + +FULLVOLDEATH + +CANBOUNCEWATER + +NOWALLBOUNCESND + BounceFactor 1.0; + BounceType "HexenCompat"; + SeeSound "SorcererBallBounce"; + DeathSound "SorcererHeadScream"; + } + + action native void A_SorcFX1Seek(); + + States + { + Spawn: + SBS1 A 2 Bright; + SBS1 BCD 3 Bright A_SorcFX1Seek; + Loop; + Death: + FHFX S 2 Bright A_Explode(30, 128); + FHFX SS 6 Bright; + Stop; + } +} + + +// Sorcerer spell 2 (The visible part of the shield) ------------------------ + +class SorcFX2 : Actor +{ + Default + { + Speed 15; + Radius 5; + Height 5; + +NOBLOCKMAP + +NOGRAVITY + +NOTELEPORT + } + + action native void A_SorcFX2Split(); + action native void A_SorcFX2Orbit (); + + states + { + Spawn: + SBS2 A 3 Bright A_SorcFX2Split; + Loop; + Orbit: + SBS2 A 2 Bright; + SBS2 BCDEFGHIJKLMNOPA 2 Bright A_SorcFX2Orbit; + Goto Orbit+1; + Death: + SBS2 A 10; + Stop; + } +} + +// The translucent trail behind SorcFX2 ------------------------------------- + +class SorcFX2T1 : SorcFX2 +{ + Default + { + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Spawn: + Goto Death; + } +} + + +// Sorcerer spell 3 (The Bishop spawner) ------------------------------------ + +class SorcFX3 : Actor +{ + Default + { + Speed 15; + Radius 22; + Height 65; + +NOBLOCKMAP + +MISSILE + +NOTELEPORT + SeeSound "SorcererBishopSpawn"; + } + + action native void A_SpawnBishop(); + action native void A_SorcererBishopEntry(); + + States + { + Spawn: + SBS3 ABC 2 Bright; + Loop; + Death: + SBS3 A 4 Bright; + BISH P 4 A_SorcererBishopEntry; + BISH ON 4; + BISH MLKJIH 3; + BISH G 3 A_SpawnBishop; + Stop; + } +} + + +// The Bishop spawner's explosion animation --------------------------------- + +class SorcFX3Explosion : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Spawn: + SBS3 DEFGH 3; + Stop; + } +} + + +// Sorcerer spell 4 (The purple projectile) --------------------------------- + +class SorcFX4 : Actor +{ + Default + { + Speed 12; + Radius 10; + Height 10; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + DeathSound "SorcererBallExplode"; + } + + action native void A_SorcFX4Check(); + + States + { + Spawn: + SBS4 ABC 2 Bright A_SorcFX4Check; + Loop; + Death: + SBS4 D 2 Bright; + SBS4 E 2 Bright A_Explode(20, 128); + SBS4 FGH 2 Bright; + Stop; + } +} + + +// Spark that appears when shooting SorcFX4 --------------------------------- + +class SorcSpark1 : Actor +{ + Default + { + Radius 5; + Height 5; + Gravity 0.125; + +NOBLOCKMAP + +DROPOFF + +NOTELEPORT + RenderStyle "Add"; + } + States + { + Spawn: + SBFX ABCDEFG 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/iceguy.txt b/wadsrc/static/zscript/hexen/iceguy.txt new file mode 100644 index 000000000..635aea07f --- /dev/null +++ b/wadsrc/static/zscript/hexen/iceguy.txt @@ -0,0 +1,185 @@ + +// Ice Guy ------------------------------------------------------------------ + +class IceGuy : Actor +{ + Default + { + Health 120; + PainChance 144; + Speed 14; + Radius 22; + Height 75; + Mass 150; + DamageType "Ice"; + Monster; + +NOBLOOD + +TELESTOMP + +NOICEDEATH + SeeSound "IceGuySight"; + AttackSound "IceGuyAttack"; + ActiveSound "IceGuyActive"; + Obituary "$OB_ICEGUY"; + } + + action native void A_IceGuyLook(); + action native void A_IceGuyChase(); + action native void A_IceGuyAttack(); + + States + { + Spawn: + ICEY A 10 A_IceGuyLook; + Loop; + See: + ICEY A 4 A_Chase; + ICEY B 4 A_IceGuyChase; + ICEY CD 4 A_Chase; + Loop; + Pain: + ICEY A 1 A_Pain; + Goto See; + Missile: + ICEY EF 3 A_FaceTarget; + ICEY G 8 Bright A_IceGuyAttack; + ICEY F 4 A_FaceTarget; + Goto See; + Death: + ICEY A 1 A_IceGuyDie; + Stop; + Inactive: + ICEY A -1; + Goto See; + } +} + +// Ice Guy Projectile ------------------------------------------------------- + +class IceGuyFX : Actor +{ + Default + { + Speed 14; + Radius 8; + Height 10; + Damage 1; + DamageType "Ice"; + Projectile; + -ACTIVATEIMPACT -ACTIVATEPCROSS + DeathSound "IceGuyMissileExplode"; + } + + action native void A_IceGuyMissileExplode(); + + States + { + Spawn: + ICPR ABC 3 Bright A_SpawnItemEx("IceFXPuff", 0,0,2); + Loop; + Death: + ICPR D 4 Bright; + ICPR E 4 Bright A_IceGuyMissileExplode; + ICPR FG 4 Bright; + ICPR H 3 Bright; + Stop; + } +} + +// Ice Guy Projectile's Puff ------------------------------------------------ + +class IceFXPuff : Actor +{ + Default + { + Radius 1; + Height 1; + +NOBLOCKMAP +NOGRAVITY +DROPOFF +SHADOW + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Spawn: + ICPR IJK 3; + ICPR LM 2; + Stop; + } +} + +// Secondary Ice Guy Projectile (ejected by the primary projectile) --------- + +class IceGuyFX2 : Actor +{ + Default + { + Speed 10; + Radius 4; + Height 4; + Damage 1; + DamageType "Ice"; + Gravity 0.125; + +NOBLOCKMAP +DROPOFF +MISSILE + +NOTELEPORT + +STRIFEDAMAGE + } + States + { + Spawn: + ICPR NOP 3 Bright; + Loop; + } +} + +// Ice Guy Bit -------------------------------------------------------------- + +class IceGuyBit : Actor +{ + Default + { + Radius 1; + Height 1; + Gravity 0.125; + +NOBLOCKMAP +DROPOFF + +NOTELEPORT + } + States + { + Spawn: + ICPR Q 50 Bright; + Stop; + ICPR R 50 Bright; + Stop; + } +} + +// Ice Guy Wisp 1 ----------------------------------------------------------- + +class IceGuyWisp1 : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY +DROPOFF +MISSILE + +NOTELEPORT + RenderStyle "Translucent"; + Alpha 0.4; + } + States + { + Spawn: + ICWS ABCDEFGHI 2; + Stop; + } +} + +// Ice Guy Wisp 2 ----------------------------------------------------------- + +class IceGuyWisp2 : IceGuyWisp1 +{ + States + { + Spawn: + ICWS JKLMNOPQR 2; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/magecone.txt b/wadsrc/static/zscript/hexen/magecone.txt new file mode 100644 index 000000000..94452985c --- /dev/null +++ b/wadsrc/static/zscript/hexen/magecone.txt @@ -0,0 +1,98 @@ + +// The Mage's Frost Cone ---------------------------------------------------- + +class MWeapFrost : MageWeapon +{ + Default + { + +BLOODSPLATTER + Weapon.SelectionOrder 1700; + Weapon.AmmoUse1 3; + Weapon.AmmoGive1 25; + Weapon.KickBack 150; + Weapon.YAdjust 20; + Weapon.AmmoType1 "Mana1"; + Inventory.PickupMessage "$TXT_WEAPON_M2"; + Obituary "$OB_MPMWEAPFROST"; + Tag "$TAG_MWEAPFROST"; + } + + action native void A_FireConePL1(); + + States + { + Spawn: + WMCS ABC 8 Bright; + Loop; + Select: + CONE A 1 A_Raise; + Loop; + Deselect: + CONE A 1 A_Lower; + Loop; + Ready: + CONE A 1 A_WeaponReady; + Loop; + Fire: + CONE B 3; + CONE C 4; + Hold: + CONE D 3; + CONE E 5; + CONE F 3 A_FireConePL1; + CONE G 3; + CONE A 9; + CONE A 10 A_ReFire; + Goto Ready; + } +} + +// Frost Missile ------------------------------------------------------------ + +class FrostMissile : Actor native +{ + Default + { + Speed 25; + Radius 13; + Height 8; + Damage 1; + DamageType "Ice"; + Projectile; + DeathSound "MageShardsExplode"; + Obituary "$OB_MPMWEAPFROST"; + } + + action native void A_ShedShard(); + + States + { + Spawn: + SHRD A 2 Bright; + SHRD A 3 Bright A_ShedShard; + SHRD B 3 Bright; + SHRD C 3 Bright; + Loop; + Death: + SHEX ABCDE 5 Bright; + Stop; + } +} + +// Ice Shard ---------------------------------------------------------------- + +class IceShard : FrostMissile +{ + Default + { + DamageType "Ice"; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + } + States + { + Spawn: + SHRD ABC 3 Bright; + Loop; + } +} diff --git a/wadsrc/static/zscript/hexen/magelightning.txt b/wadsrc/static/zscript/hexen/magelightning.txt new file mode 100644 index 000000000..2c35a41e5 --- /dev/null +++ b/wadsrc/static/zscript/hexen/magelightning.txt @@ -0,0 +1,169 @@ + +// The Mage's Lightning Arc of Death ---------------------------------------- + +class MWeapLightning : MageWeapon +{ + Default + { + +NOGRAVITY + Weapon.SelectionOrder 1100; + Weapon.AmmoUse1 5; + Weapon.AmmoGive1 25; + Weapon.KickBack 0; + Weapon.YAdjust 20; + Weapon.AmmoType1 "Mana2"; + Inventory.PickupMessage "$TXT_WEAPON_M3"; + Tag "$TAG_MWEAPLIGHTNING"; + } + + action native void A_LightningReady(); + action native void A_MLightningAttack(class floor = "LightningFloor", class ceiling = "LightningCeiling"); + + States + { + Spawn: + WMLG ABCDEFGH 4 Bright; + Loop; + Select: + MLNG A 1 Bright A_Raise; + Loop; + Deselect: + MLNG A 1 Bright A_Lower; + Loop; + Ready: + MLNG AAAAA 1 Bright A_WeaponReady; + MLNG A 1 Bright A_LightningReady; + MLNG BBBBBB 1 Bright A_WeaponReady; + MLNG CCCCC 1 Bright A_WeaponReady; + MLNG C 1 Bright A_LightningReady; + MLNG BBBBBB 1 Bright A_WeaponReady; + Loop; + Fire: + MLNG DE 3 Bright; + MLNG F 4 Bright A_MLightningAttack; + MLNG G 4 Bright; + MLNG HI 3 Bright; + MLNG I 6 Bright Offset (0, 199); + MLNG C 2 Bright Offset (0, 55); + MLNG B 2 Bright Offset (0, 50); + MLNG B 2 Bright Offset (0, 45); + MLNG B 2 Bright Offset (0, 40); + Goto Ready; + } +} + +// Ceiling Lightning -------------------------------------------------------- + +class Lightning : Actor native +{ + Default + { + MissileType "LightningZap"; + AttackSound "MageLightningZap"; + ActiveSound "MageLightningContinuous"; + Obituary "$OB_MPMWEAPLIGHTNING"; + } +} + +class LightningCeiling : Lightning +{ + Default + { + Health 144; + Speed 25; + Radius 16; + Height 40; + Damage 8; + Projectile; + +CEILINGHUGGER + RenderStyle "Add"; + } + + action native void A_LightningZap(); + action native void A_LightningClip(); + action native void A_LightningRemove(); + + States + { + Spawn: + MLFX A 2 Bright A_LightningZap; + MLFX BCD 2 Bright A_LightningClip; + Loop; + Death: + MLF2 A 2 Bright A_LightningRemove; + MLF2 BCDEKLM 3 Bright; + ACLO E 35; + MLF2 NO 3 Bright; + MLF2 P 4 Bright; + MLF2 QP 3 Bright; + MLF2 Q 4 Bright; + MLF2 P 3 Bright; + MLF2 O 3 Bright; + MLF2 P 3 Bright; + MLF2 P 1 Bright A_HideThing; + ACLO E 1050; + Stop; + } +} + +// Floor Lightning ---------------------------------------------------------- + +class LightningFloor : LightningCeiling +{ + Default + { + -CEILINGHUGGER + +FLOORHUGGER + RenderStyle "Add"; + } + + action native void A_LastZap(); + + States + { + Spawn: + MLFX E 2 Bright A_LightningZap; + MLFX FGH 2 Bright A_LightningClip; + Loop; + Death: + MLF2 F 2 Bright A_LightningRemove; + MLF2 GHIJKLM 3 Bright; + ACLO E 20; + MLF2 NO 3 Bright; + MLF2 P 4 Bright; + MLF2 QP 3 Bright; + MLF2 Q 4 Bright A_LastZap; + MLF2 POP 3 Bright; + MLF2 P 1 Bright A_HideThing; + Goto Super::Death + 19; + } +} + +// Lightning Zap ------------------------------------------------------------ + +class LightningZap : Actor native +{ + Default + { + Radius 15; + Height 35; + Damage 2; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + RenderStyle "Add"; + Obituary "$OB_MPMWEAPLIGHTNING"; + } + + action native void A_ZapMimic(); + + States + { + Spawn: + MLFX IJKLM 2 Bright A_ZapMimic; + Loop; + Death: + MLFX NOPQRSTU 2 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/magestaff.txt b/wadsrc/static/zscript/hexen/magestaff.txt new file mode 100644 index 000000000..b71c1e3dc --- /dev/null +++ b/wadsrc/static/zscript/hexen/magestaff.txt @@ -0,0 +1,160 @@ + +// Mage Weapon Piece -------------------------------------------------------- + +class MageWeaponPiece : WeaponPiece +{ + Default + { + Inventory.PickupSound "misc/w_pkup"; + Inventory.PickupMessage "$TXT_BLOODSCOURGE_PIECE"; + Inventory.ForbiddenTo "FighterPlayer", "ClericPlayer"; + WeaponPiece.Weapon "MWeapBloodscourge"; + +FLOATBOB + } +} + +// Mage Weapon Piece 1 ------------------------------------------------------ + +class MWeaponPiece1 : MageWeaponPiece +{ + Default + { + WeaponPiece.Number 1; + } + States + { + Spawn: + WMS1 A -1 Bright; + Stop; + } +} + +// Mage Weapon Piece 2 ------------------------------------------------------ + +class MWeaponPiece2 : MageWeaponPiece +{ + Default + { + WeaponPiece.Number 2; + } + States + { + Spawn: + WMS2 A -1 Bright; + Stop; + } +} + +// Mage Weapon Piece 3 ------------------------------------------------------ + +class MWeaponPiece3 : MageWeaponPiece +{ + Default + { + WeaponPiece.Number 3; + } + States + { + Spawn: + WMS3 A -1 Bright; + Stop; + } +} + +// Bloodscourge Drop -------------------------------------------------------- + +class BloodscourgeDrop : Actor +{ + States + { + Spawn: + TNT1 A 1; + TNT1 A 1 A_DropWeaponPieces("MWeaponPiece1", "MWeaponPiece2", "MWeaponPiece3"); + Stop; + } +} + +// The Mages's Staff (Bloodscourge) ----------------------------------------- + +class MWeapBloodscourge : MageWeapon native +{ + Default + { + Health 3; + Weapon.SelectionOrder 3100; + Weapon.AmmoUse1 15; + Weapon.AmmoUse2 15; + Weapon.AmmoGive1 20; + Weapon.AmmoGive2 20; + Weapon.KickBack 150; + Weapon.YAdjust 20; + Weapon.AmmoType1 "Mana1"; + Weapon.AmmoType2 "Mana2"; + +WEAPON.PRIMARY_USES_BOTH; + +Inventory.NoAttenPickupSound + Inventory.PickupMessage "$TXT_WEAPON_M4"; + Inventory.PickupSound "WeaponBuild"; + Tag "$TAG_MWEAPBLOODSCOURGE"; + } + + action native void A_MStaffAttack(); + action native void A_MStaffPalette(); + + States + { + Spawn: + TNT1 A -1; + Stop; + Select: + MSTF A 1 A_Raise; + Loop; + Deselect: + MSTF A 1 A_Lower; + Loop; + Ready: + MSTF AAAAAABBBBBBCCCCCCDDDDDDEEEEEEFFFFF 1 A_WeaponReady; + Loop; + Fire: + MSTF G 4 Offset (0, 40); + MSTF H 4 Bright Offset (0, 48) A_MStaffAttack; + MSTF H 2 Bright Offset (0, 48) A_MStaffPalette; + MSTF II 2 Offset (0, 48) A_MStaffPalette; + MSTF I 1 Offset (0, 40); + MSTF J 5 Offset (0, 36); + Goto Ready; + } +} + +// Mage Staff FX2 (Bloodscourge) -------------------------------------------- + +class MageStaffFX2 : Actor native +{ + Default + { + Speed 17; + Height 8; + Damage 4; + DamageType "Fire"; + Projectile; + +SEEKERMISSILE + +SCREENSEEKER + +EXTREMEDEATH + DeathSound "MageStaffExplode"; + Obituary "$OB_MPMWEAPBLOODSCOURGE"; + } + + action native void A_MStaffTrack(); + + States + { + Spawn: + MSP2 ABCD 2 Bright A_MStaffTrack; + Loop; + Death: + MSP2 E 4 Bright A_SetTranslucent(1,1); + MSP2 F 5 Bright A_Explode (80, 192, 0); + MSP2 GH 5 Bright; + MSP2 I 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/magewand.txt b/wadsrc/static/zscript/hexen/magewand.txt new file mode 100644 index 000000000..3feb96ae1 --- /dev/null +++ b/wadsrc/static/zscript/hexen/magewand.txt @@ -0,0 +1,81 @@ + +// The Mage's Wand ---------------------------------------------------------- + +class MWeapWand : MageWeapon +{ + Default + { + Weapon.SelectionOrder 3600; + Weapon.KickBack 0; + Weapon.YAdjust 9; + Tag "$TAG_MWEAPWAND"; + } + States + { + Select: + MWND A 1 A_Raise; + Loop; + Deselect: + MWND A 1 A_Lower; + Loop; + Ready: + MWND A 1 A_WeaponReady; + Loop; + Fire: + MWND A 6; + MWND B 6 Bright Offset (0, 48) A_FireCustomMissile ("MageWandMissile"); + MWND A 3 Offset (0, 40); + MWND A 3 Offset (0, 36) A_ReFire; + Goto Ready; + } +} + +// Wand Smoke --------------------------------------------------------------- + +class MageWandSmoke : Actor +{ + Default + { + +NOBLOCKMAP +NOGRAVITY +SHADOW + +NOTELEPORT +CANNOTPUSH +NODAMAGETHRUST + RenderStyle "Translucent"; + Alpha 0.6; + } + States + { + Spawn: + MWND CDCD 4; + Stop; + } +} + +// Wand Missile ------------------------------------------------------------- + +class MageWandMissile : FastProjectile +{ + Default + { + Speed 184; + Radius 12; + Height 8; + Damage 2; + +RIPPER +CANNOTPUSH +NODAMAGETHRUST + +SPAWNSOUNDSOURCE + MissileType "MageWandSmoke"; + SeeSound "MageWandFire"; + Obituary "$OB_MPMWEAPWAND"; + } + States + { + Spawn: + MWND CD 4 Bright; + Loop; + Death: + MWND E 4 Bright; + MWND F 3 Bright; + MWND G 4 Bright; + MWND H 3 Bright; + MWND I 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/serpent.txt b/wadsrc/static/zscript/hexen/serpent.txt new file mode 100644 index 000000000..516d0c703 --- /dev/null +++ b/wadsrc/static/zscript/hexen/serpent.txt @@ -0,0 +1,238 @@ + +// Serpent ------------------------------------------------------------------ + +class Serpent : Actor +{ + Default + { + Health 90; + PainChance 96; + Speed 12; + Radius 32; + Height 70; + Mass 0x7fffffff; + Monster; + -SHOOTABLE + +NOBLOOD + +CANTLEAVEFLOORPIC +NONSHOOTABLE + +STAYMORPHED +DONTBLAST +NOTELEOTHER + +INVISIBLE + SeeSound "SerpentSight"; + AttackSound "SerpentAttack"; + PainSound "SerpentPain"; + DeathSound "SerpentDeath"; + HitObituary "$OB_SERPENTHIT"; + } + + action native void A_SerpentHumpDecide(); + action native void A_SerpentHide(); + action native void A_SerpentCheckForAttack(); + action native void A_SerpentSpawnGibs(); + action native void A_SerpentUnHide(); + action native void A_SerpentRaiseHump(); + action native void A_SerpentLowerHump(); + action native void A_SerpentChooseAttack(); + action native void A_SerpentMeleeAttack(); + + States + { + Spawn: + SSPT H 10 A_Look; + Loop; + See: + SSPT HH 1 A_Chase("Melee", "None", CHF_NIGHTMAREFAST|CHF_NOPLAYACTIVE); + SSPT H 2 A_SerpentHumpDecide; + Loop; + Pain: + SSPT L 5; + SSPT L 5 A_Pain; + Dive: + SSDV ABC 4; + SSDV D 4 A_UnSetShootable; + SSDV E 3 A_PlaySound("SerpentActive", CHAN_BODY); + SSDV F 3; + SSDV GH 4; + SSDV I 3; + SSDV J 3 A_SerpentHide; + Goto See; + Melee: + SSPT A 1 A_UnHideThing; + SSPT A 1 A_PlaySound("SerpentBirth", CHAN_BODY); + SSPT B 3 A_SetShootable; + SSPT C 3; + SSPT D 4 A_SerpentCheckForAttack; + Goto Dive; + Death: + SSPT O 4; + SSPT P 4 A_Scream; + SSPT Q 4 A_NoBlocking; + SSPT RSTUVWXYZ 4; + Stop; + XDeath: + SSXD A 4; + SSXD B 4 A_SpawnItemEx("SerpentHead", 0, 0, 45); + SSXD C 4 A_NoBlocking; + SSXD DE 4; + SSXD FG 3; + SSXD H 3 A_SerpentSpawnGibs; + Stop; + Ice: + SSPT [ 5 A_FreezeDeath; + SSPT [ 1 A_FreezeDeathChunks; + Wait; + Walk: + SSPT IJI 5 A_Chase("Attack", "None", CHF_NIGHTMAREFAST); + SSPT J 5 A_SerpentCheckForAttack; + Goto Dive; + Hump: + SSPT H 3 A_SerpentUnHide; + SSPT EFGEF 3 A_SerpentRaiseHump; + SSPT GEF 3; + SSPT GEFGE 3 A_SerpentLowerHump; + SSPT F 3 A_SerpentHide; + Goto See; + Attack: + SSPT K 6 A_FaceTarget; + SSPT L 5 A_SerpentChooseAttack; + Goto MeleeAttack; + MeleeAttack: + SSPT N 5 A_SerpentMeleeAttack; + Goto Dive; + } +} + +// Serpent Leader ----------------------------------------------------------- + +class SerpentLeader : Serpent +{ + Default + { + Mass 200; + Obituary "$OB_SERPENT"; + } + States + { + Missile: + SSPT N 5 A_CustomMissile("SerpentFX", 32, 0); + Goto Dive; + } +} + +// Serpent Missile Ball ----------------------------------------------------- + +class SerpentFX : Actor +{ + Default + { + Speed 15; + Radius 8; + Height 10; + Damage 4; + Projectile; + -ACTIVATEIMPACT -ACTIVATEPCROSS + RenderStyle "Add"; + DeathSound "SerpentFXHit"; + } + States + { + Spawn: + SSFX A 0; + SSFX A 3 Bright A_PlaySound("SerpentFXContinuous", CHAN_BODY, 1.0, 1); + SSFX BAB 3 Bright; + Goto Spawn+1; + Death: + SSFX C 4 Bright A_StopSound(CHAN_BODY); + SSFX DEFGH 4 Bright; + Stop; + } +} + +// Serpent Head ------------------------------------------------------------- + +class SerpentHead : Actor +{ + Default + { + Radius 5; + Height 10; + Gravity 0.125; + +NOBLOCKMAP + } + + action native void A_SerpentHeadCheck(); + + States + { + Spawn: + SSXD IJKLMNOP 4 A_SerpentHeadCheck; + Loop; + Death: + SSXD S -1; + Loop; + } +} + +// Serpent Gib 1 ------------------------------------------------------------ + +class SerpentGib1 : Actor +{ + Default + { + Radius 3; + Height 3; + +NOBLOCKMAP +NOGRAVITY + } + + action native void A_FloatGib(); + action native void A_DelayGib(); + action native void A_SinkGib(); + + States + { + Spawn: + SSXD Q 6; + SSXD Q 6 A_FloatGib; + SSXD QQ 8 A_FloatGib; + SSXD QQ 12 A_FloatGib; + SSXD Q 232 A_DelayGib; + SSXD QQ 12 A_SinkGib; + SSXD QQQ 8 A_SinkGib; + Stop; + } +} + +// Serpent Gib 2 ------------------------------------------------------------ + +class SerpentGib2 : SerpentGib1 +{ + States + { + Spawn: + SSXD R 6; + SSXD R 6 A_FloatGib; + SSXD RR 8 A_FloatGib; + SSXD RR 12 A_FloatGib; + SSXD R 232 A_DelayGib; + SSXD RR 12 A_SinkGib; + SSXD RRR 8 A_SinkGib; + Stop; + } +} + +// Serpent Gib 3 ------------------------------------------------------------ + +class SerpentGib3 : SerpentGib1 +{ + States + { + Spawn: + SSXD T 6; + SSXD T 6 A_FloatGib; + SSXD TT 8 A_FloatGib; + SSXD TT 12 A_FloatGib; + SSXD T 232 A_DelayGib; + SSXD TT 12 A_SinkGib; + SSXD TTT 8 A_SinkGib; + Stop; + } +} diff --git a/wadsrc/static/zscript/hexen/spike.txt b/wadsrc/static/zscript/hexen/spike.txt new file mode 100644 index 000000000..2c8b4e80a --- /dev/null +++ b/wadsrc/static/zscript/hexen/spike.txt @@ -0,0 +1,116 @@ + +// Dirt clump (spawned by spike) -------------------------------------------- + +class DirtClump : Actor +{ + Default + { + +NOBLOCKMAP + +NOTELEPORT + } + States + { + Spawn: + TSPK C 20; + Loop; + } +} + +// Spike (thrust floor) ----------------------------------------------------- + +class ThrustFloor : Actor native +{ + Default + { + Radius 20; + Height 128; + } + + action native void A_ThrustRaise(); + action native void A_ThrustImpale(); + action native void A_ThrustLower(); + action native void A_ThrustInitDn(); + action native void A_ThrustInitUp(); + + States + { + ThrustRaising: + TSPK A 2 A_ThrustRaise; + Loop; + BloodThrustRaising: + TSPK B 2 A_ThrustRaise; + Loop; + ThrustLower: + TSPK A 2 A_ThrustLower; + Loop; + BloodThrustLower: + TSPK B 2 A_ThrustLower; + Loop; + ThrustInit1: + TSPK A 3; + TSPK A 4 A_ThrustInitDn; + TSPK A -1; + Loop; + BloodThrustInit1: + TSPK B 3; + TSPK B 4 A_ThrustInitDn; + TSPK B -1; + Loop; + ThrustInit2: + TSPK A 3; + TSPK A 4 A_ThrustInitUp; + TSPK A 10; + Loop; + BloodThrustInit2: + TSPK B 3; + TSPK B 4 A_ThrustInitUp; + TSPK B 10; + Loop; + ThrustRaise: + TSPK A 8 A_ThrustRaise; + TSPK A 6 A_ThrustRaise; + TSPK A 4 A_ThrustRaise; + TSPK A 3 A_SetSolid; + TSPK A 2 A_ThrustImpale; + Loop; + BloodThrustRaise: + TSPK B 8 A_ThrustRaise; + TSPK B 6 A_ThrustRaise; + TSPK B 4 A_ThrustRaise; + TSPK B 3 A_SetSolid; + TSPK B 2 A_ThrustImpale; + Loop; + } +} + +// Spike up ----------------------------------------------------------------- + +class ThrustFloorUp : ThrustFloor +{ + Default + { + +SOLID + +NOTELEPORT +FLOORCLIP + } + States + { + Spawn: + Goto ThrustInit2; + } +} + +// Spike down --------------------------------------------------------------- + +class ThrustFloorDown : ThrustFloor +{ + Default + { + +NOTELEPORT +FLOORCLIP + +INVISIBLE + } + States + { + Spawn: + Goto ThrustInit1; + } +} diff --git a/wadsrc/static/zscript/hexen/teleportother.txt b/wadsrc/static/zscript/hexen/teleportother.txt new file mode 100644 index 000000000..90015b207 --- /dev/null +++ b/wadsrc/static/zscript/hexen/teleportother.txt @@ -0,0 +1,130 @@ + +// Teleport Other Artifact -------------------------------------------------- + +class ArtiTeleportOther : Inventory native +{ + Default + { + +COUNTITEM + +FLOATBOB + +INVENTORY.INVBAR + +INVENTORY.FANCYPICKUPSOUND + Inventory.PickupFlash "PickupFlash"; + Inventory.DefMaxAmount; + Inventory.Icon "ARTITELO"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_ARTITELEPORTOTHER"; + Tag "$TAG_ARTITELEPORTOTHER"; + } + States + { + Spawn: + TELO ABCD 5; + Loop; + } +} + + +// Teleport Other FX -------------------------------------------------------- + +class TelOtherFX1 : Actor native +{ + Default + { + Damage 10001; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + +BLOODLESSIMPACT + Radius 16; + Height 16; + Speed 20; + } + + action native void A_TeloSpawnA(); + action native void A_TeloSpawnB(); + action native void A_TeloSpawnC(); + action native void A_TeloSpawnD(); + action native void A_CheckTeleRing (); + + States + { + Spawn: + TRNG E 5 Bright; + TRNG D 4 Bright; + TRNG C 3 Bright A_TeloSpawnC; + TRNG B 3 Bright A_TeloSpawnB; + TRNG A 3 Bright A_TeloSpawnA; + TRNG B 3 Bright A_TeloSpawnB; + TRNG C 3 Bright A_TeloSpawnC; + TRNG D 3 Bright A_TeloSpawnD; + Goto Spawn+2; + Death: + TRNG E 3 Bright; + Stop; + } +} + + +class TelOtherFX2 : TelOtherFX1 +{ + Default + { + Speed 16; + } + States + { + Spawn: + TRNG BCDCB 4 Bright; + TRNG A 4 Bright A_CheckTeleRing; + Loop; + } +} + +class TelOtherFX3 : TelOtherFX1 +{ + Default + { + Speed 16; + } + States + { + Spawn: + TRNG CDCBA 4 Bright; + TRNG B 4 Bright A_CheckTeleRing; + Loop; + } +} + +class TelOtherFX4 : TelOtherFX1 +{ + Default + { + Speed 16; + } + States + { + Spawn: + TRNG DCBAB 4 Bright; + TRNG C 4 Bright A_CheckTeleRing; + Loop; + } + +} + +class TelOtherFX5 : TelOtherFX1 +{ + Default + { + Speed 16; + } + States + { + Spawn: + TRNG CBABC 4 Bright; + TRNG D 4 Bright A_CheckTeleRing; + Loop; + } +} + + diff --git a/wadsrc/static/zscript/hexen/wraith.txt b/wadsrc/static/zscript/hexen/wraith.txt new file mode 100644 index 000000000..a8b648a72 --- /dev/null +++ b/wadsrc/static/zscript/hexen/wraith.txt @@ -0,0 +1,236 @@ + +// Wraith ------------------------------------------------------------------- + +class Wraith : Actor +{ + Default + { + Health 150; + PainChance 25; + Speed 11; + Height 55; + Mass 75; + Damage 10; + Monster; + +NOGRAVITY +DROPOFF +FLOAT + +FLOORCLIP +TELESTOMP + SeeSound "WraithSight"; + AttackSound "WraithAttack"; + PainSound "WraithPain"; + DeathSound "WraithDeath"; + ActiveSound "WraithActive"; + HitObituary "$OB_WRAITHHIT"; + Obituary "$OB_WRAITH"; + } + + action native void A_WraithInit(); + action native void A_WraithChase(); + action native void A_WraithFX3(); + action native void A_WraithMelee(); + + States + { + Spawn: + WRTH A 10; + WRTH B 5 A_WraithInit; + Goto Look; + Look: + WRTH AB 15 A_Look; + Loop; + See: + WRTH ABCD 4 A_WraithChase; + Loop; + Pain: + WRTH A 2; + WRTH H 6 A_Pain; + Goto See; + Melee: + WRTH E 6 A_FaceTarget; + WRTH F 6 A_WraithFX3; + WRTH G 6 A_WraithMelee; + Goto See; + Missile: + WRTH E 6 A_FaceTarget; + WRTH F 6; + WRTH G 6 A_CustomMissile("WraithFX1", 32, 0); + Goto See; + Death: + WRTH I 4; + WRTH J 4 A_Scream; + WRTH KL 4; + WRTH M 4 A_NoBlocking; + WRTH N 4 A_QueueCorpse; + WRTH O 4; + WRTH PQ 5; + WRTH R -1; + Stop; + XDeath: + WRT2 A 5; + WRT2 B 5 A_Scream; + WRT2 CD 5; + WRT2 E 5 A_NoBlocking; + WRT2 F 5 A_QueueCorpse; + WRT2 G 5; + WRT2 H -1; + Stop; + Ice: + WRT2 I 5 A_FreezeDeath; + WRT2 I 1 A_FreezeDeathChunks; + Wait; + } +} + +// Buried wraith ------------------------------------------------------------ + +class WraithBuried : Wraith +{ + Default + { + Height 68; + -SHOOTABLE + -SOLID + +DONTMORPH + +DONTBLAST + +SPECIALFLOORCLIP + +STAYMORPHED + +INVISIBLE + PainChance 0; + } + + action native void A_WraithRaiseInit(); + action native void A_WraithRaise(); + + States + { + Spawn: + Goto Super::Look; + See: + WRTH A 2 A_WraithRaiseInit; + WRTH A 2 A_WraithRaise; + WRTH A 2 A_FaceTarget; + WRTH BB 2 A_WraithRaise; + Goto See + 1; + Chase: + Goto Super::See; + } +} + +// Wraith FX 1 -------------------------------------------------------------- + +class WraithFX1 : Actor +{ + Default + { + Speed 14; + Radius 10; + Height 6; + Mass 5; + Damage 5; + DamageType "Fire"; + Projectile; + +FLOORCLIP + SeeSound "WraithMissileFire"; + DeathSound "WraithMissileExplode"; + } + + action native void A_WraithFX2(); + + States + { + Spawn: + WRBL A 3 Bright; + WRBL B 3 Bright A_WraithFX2; + WRBL C 3 Bright; + Loop; + Death: + WRBL D 4 Bright; + WRBL E 4 Bright A_WraithFX2; + WRBL F 4 Bright; + WRBL GH 3 Bright A_WraithFX2; + WRBL I 3 Bright; + Stop; + } +} + +// Wraith FX 2 -------------------------------------------------------------- + +class WraithFX2 : Actor +{ + Default + { + Radius 2; + Height 5; + Mass 5; + +NOBLOCKMAP +DROPOFF + +FLOORCLIP +NOTELEPORT + } + States + { + Spawn: + WRBL JKLMNOP 4 Bright; + Stop; + } +} + +// Wraith FX 3 -------------------------------------------------------------- + +class WraithFX3 : Actor +{ + Default + { + Radius 2; + Height 5; + Mass 5; + +NOBLOCKMAP +DROPOFF +MISSILE + +FLOORCLIP +NOTELEPORT + DeathSound "Drip"; + } + States + { + Spawn: + WRBL QRS 4 Bright; + Loop; + Death: + WRBL S 4 Bright; + Stop; + } +} + +// Wraith FX 4 -------------------------------------------------------------- + +class WraithFX4 : Actor +{ + Default + { + Radius 2; + Height 5; + Mass 5; + +NOBLOCKMAP +DROPOFF +MISSILE + +NOTELEPORT + DeathSound "Drip"; + } + States + { + Spawn: + WRBL TUVW 4; + Loop; + Death: + WRBL W 10; + Stop; + } +} + +// Wraith FX 5 -------------------------------------------------------------- + +class WraithFX5 : WraithFX4 +{ + States + { + Spawn: + WRBL XYZ 7; + Loop; + Death: + WRBL Z 35; + Stop; + } +} From 5643831ccc320e530312909b163e322ccf4eb601 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 23:05:58 +0200 Subject: [PATCH 068/255] - converted all Strife actors. --- wadsrc/static/actors/strife/acolyte.txt | 185 -- wadsrc/static/actors/strife/alienspectres.txt | 202 -- wadsrc/static/actors/strife/beggars.txt | 87 - wadsrc/static/actors/strife/coin.txt | 84 - wadsrc/static/actors/strife/crusader.txt | 122 - wadsrc/static/actors/strife/entityboss.txt | 199 -- wadsrc/static/actors/strife/inquisitor.txt | 141 -- wadsrc/static/actors/strife/loremaster.txt | 114 - wadsrc/static/actors/strife/macil.txt | 89 - wadsrc/static/actors/strife/merchants.txt | 93 - wadsrc/static/actors/strife/oracle.txt | 35 - wadsrc/static/actors/strife/peasants.txt | 182 -- wadsrc/static/actors/strife/programmer.txt | 107 - wadsrc/static/actors/strife/ratbuddy.txt | 34 - wadsrc/static/actors/strife/reaver.txt | 64 - wadsrc/static/actors/strife/rebels.txt | 131 -- wadsrc/static/actors/strife/sentinel.txt | 95 - wadsrc/static/actors/strife/sigil.txt | 161 -- wadsrc/static/actors/strife/spectral.txt | 262 --- wadsrc/static/actors/strife/stalker.txt | 76 - wadsrc/static/actors/strife/strifeammo.txt | 202 -- wadsrc/static/actors/strife/strifearmor.txt | 43 - wadsrc/static/actors/strife/strifebishop.txt | 94 - .../static/actors/strife/strifehumanoid.txt | 53 - wadsrc/static/actors/strife/strifeitems.txt | 519 ----- wadsrc/static/actors/strife/strifekeys.txt | 460 ---- wadsrc/static/actors/strife/strifeplayer.txt | 102 - wadsrc/static/actors/strife/strifestuff.txt | 1723 -------------- wadsrc/static/actors/strife/strifeweapons.txt | 813 ------- wadsrc/static/actors/strife/templar.txt | 66 - .../static/actors/strife/thingstoblowup.txt | 141 -- wadsrc/static/actors/strife/zombie.txt | 58 - wadsrc/static/decorate.txt | 33 - wadsrc/static/zscript.txt | 34 + wadsrc/static/zscript/strife/acolyte.txt | 218 ++ .../static/zscript/strife/alienspectres.txt | 223 ++ wadsrc/static/zscript/strife/beggars.txt | 90 + wadsrc/static/zscript/strife/coin.txt | 99 + wadsrc/static/zscript/strife/crusader.txt | 131 ++ wadsrc/static/zscript/strife/entityboss.txt | 211 ++ wadsrc/static/zscript/strife/inquisitor.txt | 150 ++ wadsrc/static/zscript/strife/loremaster.txt | 123 + wadsrc/static/zscript/strife/macil.txt | 95 + wadsrc/static/zscript/strife/merchants.txt | 108 + wadsrc/static/zscript/strife/oracle.txt | 38 + wadsrc/static/zscript/strife/peasants.txt | 251 +++ wadsrc/static/zscript/strife/programmer.txt | 116 + .../{actors => zscript}/strife/questitems.txt | 93 +- wadsrc/static/zscript/strife/ratbuddy.txt | 37 + wadsrc/static/zscript/strife/reaver.txt | 67 + wadsrc/static/zscript/strife/rebels.txt | 140 ++ wadsrc/static/zscript/strife/sentinel.txt | 104 + wadsrc/static/zscript/strife/sigil.txt | 178 ++ wadsrc/static/zscript/strife/spectral.txt | 307 +++ wadsrc/static/zscript/strife/stalker.txt | 79 + wadsrc/static/zscript/strife/strifeammo.txt | 235 ++ wadsrc/static/zscript/strife/strifearmor.txt | 49 + wadsrc/static/zscript/strife/strifebishop.txt | 99 + .../static/zscript/strife/strifehumanoid.txt | 58 + wadsrc/static/zscript/strife/strifeitems.txt | 597 +++++ wadsrc/static/zscript/strife/strifekeys.txt | 547 +++++ wadsrc/static/zscript/strife/strifeplayer.txt | 105 + wadsrc/static/zscript/strife/strifestuff.txt | 2002 +++++++++++++++++ .../static/zscript/strife/strifeweapons.txt | 891 ++++++++ wadsrc/static/zscript/strife/templar.txt | 68 + .../static/zscript/strife/thingstoblowup.txt | 153 ++ wadsrc/static/zscript/strife/zombie.txt | 64 + 67 files changed, 7718 insertions(+), 6812 deletions(-) delete mode 100644 wadsrc/static/actors/strife/acolyte.txt delete mode 100644 wadsrc/static/actors/strife/alienspectres.txt delete mode 100644 wadsrc/static/actors/strife/beggars.txt delete mode 100644 wadsrc/static/actors/strife/coin.txt delete mode 100644 wadsrc/static/actors/strife/crusader.txt delete mode 100644 wadsrc/static/actors/strife/entityboss.txt delete mode 100644 wadsrc/static/actors/strife/inquisitor.txt delete mode 100644 wadsrc/static/actors/strife/loremaster.txt delete mode 100644 wadsrc/static/actors/strife/macil.txt delete mode 100644 wadsrc/static/actors/strife/merchants.txt delete mode 100644 wadsrc/static/actors/strife/oracle.txt delete mode 100644 wadsrc/static/actors/strife/peasants.txt delete mode 100644 wadsrc/static/actors/strife/programmer.txt delete mode 100644 wadsrc/static/actors/strife/ratbuddy.txt delete mode 100644 wadsrc/static/actors/strife/reaver.txt delete mode 100644 wadsrc/static/actors/strife/rebels.txt delete mode 100644 wadsrc/static/actors/strife/sentinel.txt delete mode 100644 wadsrc/static/actors/strife/sigil.txt delete mode 100644 wadsrc/static/actors/strife/spectral.txt delete mode 100644 wadsrc/static/actors/strife/stalker.txt delete mode 100644 wadsrc/static/actors/strife/strifeammo.txt delete mode 100644 wadsrc/static/actors/strife/strifearmor.txt delete mode 100644 wadsrc/static/actors/strife/strifebishop.txt delete mode 100644 wadsrc/static/actors/strife/strifehumanoid.txt delete mode 100644 wadsrc/static/actors/strife/strifeitems.txt delete mode 100644 wadsrc/static/actors/strife/strifekeys.txt delete mode 100644 wadsrc/static/actors/strife/strifeplayer.txt delete mode 100644 wadsrc/static/actors/strife/strifestuff.txt delete mode 100644 wadsrc/static/actors/strife/strifeweapons.txt delete mode 100644 wadsrc/static/actors/strife/templar.txt delete mode 100644 wadsrc/static/actors/strife/thingstoblowup.txt delete mode 100644 wadsrc/static/actors/strife/zombie.txt create mode 100644 wadsrc/static/zscript/strife/acolyte.txt create mode 100644 wadsrc/static/zscript/strife/alienspectres.txt create mode 100644 wadsrc/static/zscript/strife/beggars.txt create mode 100644 wadsrc/static/zscript/strife/coin.txt create mode 100644 wadsrc/static/zscript/strife/crusader.txt create mode 100644 wadsrc/static/zscript/strife/entityboss.txt create mode 100644 wadsrc/static/zscript/strife/inquisitor.txt create mode 100644 wadsrc/static/zscript/strife/loremaster.txt create mode 100644 wadsrc/static/zscript/strife/macil.txt create mode 100644 wadsrc/static/zscript/strife/merchants.txt create mode 100644 wadsrc/static/zscript/strife/oracle.txt create mode 100644 wadsrc/static/zscript/strife/peasants.txt create mode 100644 wadsrc/static/zscript/strife/programmer.txt rename wadsrc/static/{actors => zscript}/strife/questitems.txt (51%) create mode 100644 wadsrc/static/zscript/strife/ratbuddy.txt create mode 100644 wadsrc/static/zscript/strife/reaver.txt create mode 100644 wadsrc/static/zscript/strife/rebels.txt create mode 100644 wadsrc/static/zscript/strife/sentinel.txt create mode 100644 wadsrc/static/zscript/strife/sigil.txt create mode 100644 wadsrc/static/zscript/strife/spectral.txt create mode 100644 wadsrc/static/zscript/strife/stalker.txt create mode 100644 wadsrc/static/zscript/strife/strifeammo.txt create mode 100644 wadsrc/static/zscript/strife/strifearmor.txt create mode 100644 wadsrc/static/zscript/strife/strifebishop.txt create mode 100644 wadsrc/static/zscript/strife/strifehumanoid.txt create mode 100644 wadsrc/static/zscript/strife/strifeitems.txt create mode 100644 wadsrc/static/zscript/strife/strifekeys.txt create mode 100644 wadsrc/static/zscript/strife/strifeplayer.txt create mode 100644 wadsrc/static/zscript/strife/strifestuff.txt create mode 100644 wadsrc/static/zscript/strife/strifeweapons.txt create mode 100644 wadsrc/static/zscript/strife/templar.txt create mode 100644 wadsrc/static/zscript/strife/thingstoblowup.txt create mode 100644 wadsrc/static/zscript/strife/zombie.txt diff --git a/wadsrc/static/actors/strife/acolyte.txt b/wadsrc/static/actors/strife/acolyte.txt deleted file mode 100644 index f190fb928..000000000 --- a/wadsrc/static/actors/strife/acolyte.txt +++ /dev/null @@ -1,185 +0,0 @@ - -// Base class for the acolytes ---------------------------------------------- - -ACTOR Acolyte : StrifeHumanoid -{ - Health 70 - PainChance 150 - Speed 7 - Radius 24 - Height 64 - Mass 400 - Monster - +SEESDAGGERS - +NOSPLASHALERT - +FLOORCLIP - +NEVERRESPAWN - MinMissileChance 150 - Tag "$TAG_ACOLYTE" - SeeSound "acolyte/sight" - PainSound "acolyte/pain" - AttackSound "acolyte/rifle" - DeathSound "acolyte/death" - ActiveSound "acolyte/active" - Obituary "$OB_ACOLYTE" - - action native A_BeShadowyFoe (); - action native A_AcolyteBits (); - action native A_AcolyteDie (); - - States - { - Spawn: - AGRD A 5 A_Look2 - Wait - AGRD B 8 A_ClearShadow - Loop - AGRD D 8 - Loop - AGRD ABCDABCD 5 A_Wander - Loop - See: - AGRD A 6 Fast Slow A_AcolyteBits - AGRD BCD 6 Fast Slow A_Chase - Loop - Missile: - AGRD E 8 Fast Slow A_FaceTarget - AGRD FE 4 Fast Slow A_ShootGun - AGRD F 6 Fast Slow A_ShootGun - Goto See - Pain: - AGRD O 8 Fast Slow A_Pain - Goto See - Death: - AGRD G 4 - AGRD H 4 A_Scream - AGRD I 4 - AGRD J 3 - AGRD K 3 A_NoBlocking - AGRD L 3 - AGRD M 3 A_AcolyteDie - AGRD N -1 - Stop - XDeath: - GIBS A 5 A_NoBlocking - GIBS BC 5 A_TossGib - GIBS D 4 A_TossGib - GIBS E 4 A_XScream - GIBS F 4 A_TossGib - GIBS GH 4 - GIBS I 5 - GIBS J 5 A_AcolyteDie - GIBS K 5 - GIBS L 1400 - Stop - } -} - - -// Acolyte 1 ---------------------------------------------------------------- - -ACTOR AcolyteTan : Acolyte -{ - +MISSILEMORE +MISSILEEVENMORE - DropItem "ClipOfBullets" -} - -// Acolyte 2 ---------------------------------------------------------------- - -ACTOR AcolyteRed : Acolyte -{ - +MISSILEMORE +MISSILEEVENMORE - Translation 0 -} - -// Acolyte 3 ---------------------------------------------------------------- - -ACTOR AcolyteRust : Acolyte -{ - +MISSILEMORE +MISSILEEVENMORE - Translation 1 -} - -// Acolyte 4 ---------------------------------------------------------------- - -ACTOR AcolyteGray : Acolyte -{ - +MISSILEMORE +MISSILEEVENMORE - Translation 2 -} - -// Acolyte 5 ---------------------------------------------------------------- - -ACTOR AcolyteDGreen : Acolyte -{ - +MISSILEMORE +MISSILEEVENMORE - Translation 3 -} - -// Acolyte 6 ---------------------------------------------------------------- - -ACTOR AcolyteGold : Acolyte -{ - +MISSILEMORE +MISSILEEVENMORE - Translation 4 -} - -// Acolyte 7 ---------------------------------------------------------------- - -ACTOR AcolyteLGreen : Acolyte -{ - Health 60 - Translation 5 -} - -// Acolyte 8 ---------------------------------------------------------------- - -ACTOR AcolyteBlue : Acolyte -{ - Health 60 - Translation 6 -} - -// Shadow Acolyte ----------------------------------------------------------- - -ACTOR AcolyteShadow : Acolyte -{ - +MISSILEMORE - DropItem "ClipOfBullets" - States - { - See: - AGRD A 6 A_BeShadowyFoe - Goto Super::See+1 - Pain: - AGRD O 0 Fast Slow A_SetShadow - AGRD O 8 Fast Slow A_Pain - Goto See - } -} - -// Some guy turning into an acolyte ----------------------------------------- - -ACTOR AcolyteToBe : Acolyte -{ - Health 61 - Radius 20 - Height 56 - DeathSound "becoming/death" - -COUNTKILL - -ISMONSTER - - action native A_HideDecepticon (); - - States - { - Spawn: - ARMR A -1 - Stop - Pain: - ARMR A -1 A_HideDecepticon - Stop - Death: - Goto XDeath - } -} diff --git a/wadsrc/static/actors/strife/alienspectres.txt b/wadsrc/static/actors/strife/alienspectres.txt deleted file mode 100644 index 0476fdfdf..000000000 --- a/wadsrc/static/actors/strife/alienspectres.txt +++ /dev/null @@ -1,202 +0,0 @@ - -// Alien Spectre 1 ----------------------------------------------------------- - -ACTOR AlienSpectre1 : SpectralMonster -{ - Health 1000 - Painchance 250 - Speed 12 - Radius 64 - Height 64 - FloatSpeed 5 - Mass 1000 - MinMissileChance 150 - RenderStyle Translucent - Alpha 0.666 - SeeSound "alienspectre/sight" - AttackSound "alienspectre/blade" - PainSound "alienspectre/pain" - DeathSound "alienspectre/death" - ActiveSound "alienspectre/active" - Obituary "$OB_ALIENSPECTRE" - +NOGRAVITY - +FLOAT - +SHADOW - +NOTDMATCH - +DONTMORPH - +NOBLOCKMONST - +INCOMBAT - +LOOKALLAROUND - +NOICEDEATH - - action native A_AlienSpectreDeath (); - - states - { - Spawn: - ALN1 A 10 A_Look - ALN1 B 10 A_SentinelBob - Loop - See: - ALN1 AB 4 Bright A_Chase - ALN1 C 4 Bright A_SentinelBob - ALN1 DEF 4 Bright A_Chase - ALN1 G 4 Bright A_SentinelBob - ALN1 HIJ 4 Bright A_Chase - ALN1 K 4 Bright A_SentinelBob - Loop - Melee: - ALN1 J 4 Bright A_FaceTarget - ALN1 I 4 Bright A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5) - ALN1 H 4 Bright - Goto See - Missile: - ALN1 J 4 Bright A_FaceTarget - ALN1 I 4 Bright A_SpotLightning - ALN1 H 4 Bright - Goto See+10 - Pain: - ALN1 J 2 A_Pain - Goto See+6 - Death: - AL1P A 6 Bright A_SpectreChunkSmall - AL1P B 6 Bright A_Scream - AL1P C 6 Bright A_SpectreChunkSmall - AL1P DE 6 Bright - AL1P F 6 Bright A_SpectreChunkSmall - AL1P G 6 Bright - AL1P H 6 Bright A_SpectreChunkSmall - AL1P IJK 6 Bright - AL1P LM 5 Bright - AL1P N 5 Bright A_SpectreChunkLarge - AL1P OPQ 5 Bright - AL1P R 5 Bright A_AlienSpectreDeath - Stop - } -} - - -// Alien Spectre 2 ----------------------------------------------------------- - -ACTOR AlienSpectre2 : AlienSpectre1 -{ - Health 1200 - Painchance 50 - Radius 24 - DropItem "Sigil2" - States - { - Missile: - ALN1 F 4 A_FaceTarget - ALN1 I 4 A_CustomMissile("SpectralLightningH3", 32, 0) - ALN1 E 4 - Goto See+10 - } -} - -// Alien Spectre 3 ---------------------------------------------------------- -// This is the Oracle's personal spectre, so it's a little different. - -ACTOR AlienSpectre3 : AlienSpectre1 -{ - Health 1500 - Painchance 50 - Radius 24 - +SPAWNCEILING - DropItem "Sigil3" - DamageFactor "SpectralLow", 0 - states - { - Spawn: - ALN1 ABCDEFGHIJK 5 - Loop - See: - ALN1 AB 5 A_Chase - ALN1 C 5 A_SentinelBob - ALN1 DEF 5 A_Chase - ALN1 G 5 A_SentinelBob - ALN1 HIJ 5 A_Chase - ALN1 K 5 A_SentinelBob - Loop - Melee: - ALN1 J 4 A_FaceTarget - ALN1 I 4 A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5) - ALN1 C 4 - Goto See+2 - Missile: - ALN1 F 4 A_FaceTarget - ALN1 I 4 A_Spectre3Attack - ALN1 E 4 - Goto See+10 - Pain: - ALN1 J 2 A_Pain - Goto See+6 - } -} - - -// Alien Spectre 4 ----------------------------------------------------------- - -ACTOR AlienSpectre4 : AlienSpectre1 -{ - Health 1700 - Painchance 50 - Radius 24 - DropItem "Sigil4" - States - { - Missile: - ALN1 F 4 A_FaceTarget - ALN1 I 4 A_CustomMissile("SpectralLightningBigV2", 32, 0) - ALN1 E 4 - Goto See+10 - } -} - - -// Alien Spectre 5 ----------------------------------------------------------- - -ACTOR AlienSpectre5 : AlienSpectre1 -{ - Health 2000 - Painchance 50 - Radius 24 - DropItem "Sigil5" - States - { - Missile: - ALN1 F 4 A_FaceTarget - ALN1 I 4 A_CustomMissile("SpectralLightningBigBall2", 32, 0) - ALN1 E 4 - Goto See+10 - } -} - -// Small Alien Chunk -------------------------------------------------------- - -ACTOR AlienChunkSmall -{ - +NOBLOCKMAP - +NOCLIP - States - { - Spawn: - NODE ABCDEFG 6 Bright - Stop - } -} - -// Large Alien Chunk -------------------------------------------------------- - -ACTOR AlienChunkLarge -{ - +NOBLOCKMAP - +NOCLIP - States - { - Spawn: - MTHD ABCDEFGHIJK 5 Bright - Stop - } -} - diff --git a/wadsrc/static/actors/strife/beggars.txt b/wadsrc/static/actors/strife/beggars.txt deleted file mode 100644 index eca6e67f4..000000000 --- a/wadsrc/static/actors/strife/beggars.txt +++ /dev/null @@ -1,87 +0,0 @@ - -// Base class for the beggars --------------------------------------------- - -ACTOR Beggar : StrifeHumanoid -{ - Health 20 - PainChance 250 - Speed 3 - Radius 20 - Height 56 - Monster - +JUSTHIT - -COUNTKILL - +NOSPLASHALERT - MinMissileChance 150 - Tag "$TAG_BEGGAR" - MaxStepHeight 16 - MaxDropoffHeight 32 - HitObituary "$OB_BEGGAR" - - AttackSound "beggar/attack" - PainSound "beggar/pain" - DeathSound "beggar/death" - States - { - Spawn: - BEGR A 10 A_Look - Loop - See: - BEGR AABBCC 4 A_Wander - Loop - Melee: - BEGR D 8 - BEGR D 8 A_CustomMeleeAttack(2*random[PeasantAttack](1,5)+2) - BEGR E 1 A_Chase - BEGR D 8 A_SentinelRefire - Loop - Pain: - BEGR A 3 A_Pain - BEGR A 3 A_Chase - Goto Melee - Death: - BEGR F 4 - BEGR G 4 A_Scream - BEGR H 4 - BEGR I 4 A_NoBlocking - BEGR JKLM 4 - BEGR N -1 - Stop - XDeath: - BEGR F 5 A_TossGib - GIBS M 5 A_TossGib - GIBS N 5 A_XScream - GIBS O 5 A_NoBlocking - GIBS PQRST 4 A_TossGib - GIBS U 5 - GIBS V 1400 - Stop - } -} - - -// Beggars ----------------------------------------------------------------- - -ACTOR Beggar1 : Beggar -{ -} - - -ACTOR Beggar2 : Beggar -{ -} - - -ACTOR Beggar3 : Beggar -{ -} - - -ACTOR Beggar4 : Beggar -{ -} - - -ACTOR Beggar5 : Beggar -{ -} diff --git a/wadsrc/static/actors/strife/coin.txt b/wadsrc/static/actors/strife/coin.txt deleted file mode 100644 index b410d25a1..000000000 --- a/wadsrc/static/actors/strife/coin.txt +++ /dev/null @@ -1,84 +0,0 @@ - -// Coin --------------------------------------------------------------------- - -ACTOR Coin : Inventory native -{ - +DROPPED - +NOTDMATCH - +FLOORCLIP - Inventory.MaxAmount 0x7fffffff - +INVENTORY.INVBAR - Tag "$TAG_COIN" - Inventory.Icon "I_COIN" - Inventory.PickupMessage "$TXT_COIN" - States - { - Spawn: - COIN A -1 - Stop - } -} - - -// 10 Gold ------------------------------------------------------------------ - -ACTOR Gold10 : Coin -{ - Inventory.Amount 10 - Tag "$TAG_10GOLD" - Inventory.PickupMessage "$TXT_10GOLD" - States - { - Spawn: - CRED A -1 - Stop - } -} - -// 25 Gold ------------------------------------------------------------------ - -ACTOR Gold25 : Coin -{ - Inventory.Amount 25 - Tag "$TAG_25GOLD" - Inventory.PickupMessage "$TXT_25GOLD" - States - { - Spawn: - SACK A -1 - Stop - } -} - -// 50 Gold ------------------------------------------------------------------ - -ACTOR Gold50 : Coin -{ - Inventory.Amount 50 - Tag "$TAG_50GOLD" - Inventory.PickupMessage "$TXT_50GOLD" - States - { - Spawn: - CHST A -1 - Stop - } -} - -// 300 Gold ------------------------------------------------------------------ - -ACTOR Gold300 : Coin -{ - Inventory.Amount 300 - Tag "$TAG_300GOLD" - Inventory.PickupMessage "$TXT_300GOLD" - Inventory.GiveQuest 3 - +INVENTORY.ALWAYSPICKUP - States - { - Spawn: - TOKN A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/crusader.txt b/wadsrc/static/actors/strife/crusader.txt deleted file mode 100644 index c39747471..000000000 --- a/wadsrc/static/actors/strife/crusader.txt +++ /dev/null @@ -1,122 +0,0 @@ - -// Crusader ----------------------------------------------------------------- - -ACTOR Crusader -{ - Speed 8 - Radius 40 - Height 56 - Mass 400 - Health 400 - Painchance 128 - Monster - +FLOORCLIP - +DONTMORPH - +MISSILEMORE - +INCOMBAT - +NOICEDEATH - +NOBLOOD - MinMissileChance 120 - MaxDropoffHeight 32 - DropItem "EnergyPod", 256, 20 - SeeSound "crusader/sight" - PainSound "crusader/pain" - DeathSound "crusader/death" - ActiveSound "crusader/active" - Obituary "$OB_CRUSADER" - - action native A_CrusaderChoose (); - action native A_CrusaderSweepLeft (); - action native A_CrusaderSweepRight (); - action native A_CrusaderRefire (); - action native A_CrusaderDeath (); - - States - { - Spawn: - ROB2 Q 10 A_Look - Loop - See: - ROB2 AABBCCDD 3 A_Chase - Loop - Missile: - ROB2 E 3 Slow A_FaceTarget - ROB2 F 2 Slow Bright A_CrusaderChoose - ROB2 E 2 Slow Bright A_CrusaderSweepLeft - ROB2 F 3 Slow Bright A_CrusaderSweepLeft - ROB2 EF 2 Slow Bright A_CrusaderSweepLeft - ROB2 EFE 2 Slow Bright A_CrusaderSweepRight - ROB2 F 2 Slow A_CrusaderRefire - Loop - Pain: - ROB2 D 1 Slow A_Pain - Goto See - Death: - ROB2 G 3 A_Scream - ROB2 H 5 A_TossGib - ROB2 I 4 Bright A_TossGib - ROB2 J 4 Bright A_Explode(64,64,1,1) - ROB2 K 4 Bright A_Fall - ROB2 L 4 A_Explode(64,64,1,1) - ROB2 MN 4 A_TossGib - ROB2 O 4 A_Explode(64,64,1,1) - ROB2 P -1 A_CrusaderDeath - Stop - } -} - - -// Fast Flame Projectile (used by Crusader) --------------------------------- - -ACTOR FastFlameMissile : FlameMissile -{ - Mass 50 - Damage 1 - Speed 35 -} - -// Crusader Missile --------------------------------------------------------- -// This is just like the mini missile the player shoots, except it doesn't -// explode when it dies, and it does slightly less damage for a direct hit. - -ACTOR CrusaderMissile -{ - Speed 20 - Radius 10 - Height 14 - Damage 7 - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - SeeSound "crusader/misl" - DeathSound "crusader/mislx" - States - { - Spawn: - MICR A 6 Bright A_RocketInFlight - Loop - Death: - SMIS A 0 Bright A_SetTranslucent(1,1) - SMIS A 5 Bright - SMIS B 5 Bright - SMIS C 4 Bright - SMIS DEFG 2 Bright - Stop - } -} - - -// Dead Crusader ------------------------------------------------------------ - -ACTOR DeadCrusader -{ - States - { - Spawn: - ROB2 N 4 - ROB2 O 4 - ROB2 P -1 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/entityboss.txt b/wadsrc/static/actors/strife/entityboss.txt deleted file mode 100644 index ddd19d9ef..000000000 --- a/wadsrc/static/actors/strife/entityboss.txt +++ /dev/null @@ -1,199 +0,0 @@ - -// Entity Nest -------------------------------------------------------------- - -ACTOR EntityNest -{ - Radius 84 - Height 47 - +SOLID - +NOTDMATCH - +FLOORCLIP - States - { - Spawn: - NEST A -1 - Stop - } -} - -// Entity Pod --------------------------------------------------------------- - -ACTOR EntityPod -{ - Radius 25 - Height 91 - +SOLID - +NOTDMATCH - SeeSound "misc/gibbed" - - action native A_SpawnEntity (); - - States - { - Spawn: - PODD A 60 A_Look - Loop - See: - PODD A 360 - PODD B 9 A_NoBlocking - PODD C 9 - PODD D 9 A_SpawnEntity - PODD E -1 - Stop - } -} - - -// Entity Boss -------------------------------------------------------------- - -ACTOR EntityBoss : SpectralMonster -{ - Health 2500 - Painchance 255 - Speed 13 - Radius 130 - Height 200 - FloatSpeed 5 - Mass 1000 - Monster - +SPECIAL - +NOGRAVITY - +FLOAT - +SHADOW - +NOTDMATCH - +DONTMORPH - +NOTARGET - +NOBLOCKMONST - +INCOMBAT - +LOOKALLAROUND - +SPECTRAL - +NOICEDEATH - MinMissileChance 150 - RenderStyle Translucent - Alpha 0.5 - SeeSound "entity/sight" - AttackSound "entity/melee" - PainSound "entity/pain" - DeathSound "entity/death" - ActiveSound "entity/active" - Obituary "$OB_ENTITY" - - action native A_EntityAttack(); - action native A_EntityDeath(); - - States - { - Spawn: - MNAM A 100 - MNAM B 60 Bright - MNAM CDEFGHIJKL 4 Bright - MNAL A 4 Bright A_Look - MNAL B 4 Bright A_SentinelBob - Goto Spawn+12 - See: - MNAL AB 4 Bright A_Chase - MNAL C 4 Bright A_SentinelBob - MNAL DEF 4 Bright A_Chase - MNAL G 4 Bright A_SentinelBob - MNAL HIJ 4 Bright A_Chase - MNAL K 4 Bright A_SentinelBob - Loop - Melee: - MNAL J 4 Bright A_FaceTarget - MNAL I 4 Bright A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5) - MNAL C 4 Bright - Goto See+2 - Missile: - MNAL F 4 Bright A_FaceTarget - MNAL I 4 Bright A_EntityAttack - MNAL E 4 Bright - Goto See+10 - Pain: - MNAL J 2 Bright A_Pain - Goto See+6 - Death: - MNAL L 7 Bright A_SpectreChunkSmall - MNAL M 7 Bright A_Scream - MNAL NO 7 Bright A_SpectreChunkSmall - MNAL P 7 Bright A_SpectreChunkLarge - MNAL Q 64 Bright A_SpectreChunkSmall - MNAL Q 6 Bright A_EntityDeath - Stop - } -} - -// Second Entity Boss ------------------------------------------------------- - -ACTOR EntitySecond : SpectralMonster -{ - Health 990 - Painchance 255 - Speed 14 - Radius 130 - Height 200 - FloatSpeed 5 - Mass 1000 - Monster - +SPECIAL - +NOGRAVITY - +FLOAT - +SHADOW - +NOTDMATCH - +DONTMORPH - +NOBLOCKMONST - +INCOMBAT - +LOOKALLAROUND - +SPECTRAL - +NOICEDEATH - MinMissileChance 150 - RenderStyle Translucent - Alpha 0.25 - SeeSound "alienspectre/sight" - AttackSound "alienspectre/blade" - PainSound "alienspectre/pain" - DeathSound "alienspectre/death" - ActiveSound "alienspectre/active" - Obituary "$OB_ENTITY" - - action native A_SubEntityDeath (); - - States - { - Spawn: - MNAL R 10 Bright A_Look - Loop - See: - MNAL R 5 Bright A_SentinelBob - MNAL ST 5 Bright A_Chase - MNAL U 5 Bright A_SentinelBob - MNAL V 5 Bright A_Chase - MNAL W 5 Bright A_SentinelBob - Loop - Melee: - MNAL S 4 Bright A_FaceTarget - MNAL R 4 Bright A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5) - MNAL T 4 Bright A_SentinelBob - Goto See+1 - Missile: - MNAL W 4 Bright A_FaceTarget - MNAL U 4 Bright A_CustomMissile("SpectralLightningH3",32,0) - MNAL V 4 Bright A_SentinelBob - Goto See+4 - Pain: - MNAL R 2 Bright A_Pain - Goto See - Death: - MDTH A 3 Bright A_Scream - MDTH B 3 Bright A_TossGib - MDTH C 3 Bright A_NoBlocking - MDTH DEFGHIJKLMN 3 Bright A_TossGib - MDTH O 3 Bright A_SubEntityDeath - Stop - } -} - - - - - - diff --git a/wadsrc/static/actors/strife/inquisitor.txt b/wadsrc/static/actors/strife/inquisitor.txt deleted file mode 100644 index 5b9495d40..000000000 --- a/wadsrc/static/actors/strife/inquisitor.txt +++ /dev/null @@ -1,141 +0,0 @@ - -// Inquisitor --------------------------------------------------------------- - -ACTOR Inquisitor -{ - Health 1000 - Speed 12 - Radius 40 - Height 110 - Mass 0x7fffffff - Monster - +DROPOFF - +NOBLOOD - +BOSS - +FLOORCLIP - +DONTMORPH - +NORADIUSDMG - MaxDropOffHeight 32 - MinMissileChance 150 - SeeSound "inquisitor/sight" - DeathSound "inquisitor/death" - ActiveSound "inquisitor/active" - Obituary "$OB_INQUISITOR" - - action native A_InquisitorWalk (); - action native A_InquisitorDecide (); - action native A_InquisitorAttack (); - action native A_InquisitorJump (); - action native A_InquisitorCheckLand (); - action native A_TossArm (); - action native A_ReaverRanged (); - - states - { - Spawn: - ROB3 AB 10 A_Look - Loop - See: - ROB3 B 3 A_InquisitorWalk - ROB3 B 3 A_Chase - ROB3 CCDD 4 A_Chase - ROB3 E 3 A_InquisitorWalk - ROB3 E 3 A_InquisitorDecide - Loop - Missile: - ROB3 A 2 A_InquisitorDecide - ROB3 F 6 A_FaceTarget - ROB3 G 8 Bright A_ReaverRanged - ROB3 G 8 A_ReaverRanged - Goto See - Grenade: - ROB3 K 12 A_FaceTarget - ROB3 J 6 Bright A_InquisitorAttack - ROB3 K 12 - Goto See - Jump: - ROB3 H 8 Bright A_InquisitorJump - ROB3 I 4 Bright A_InquisitorCheckLand - ROB3 H 4 Bright A_InquisitorCheckLand - Goto Jump+1 - Death: - ROB3 L 0 A_StopSoundEx("Item") - ROB3 L 4 A_TossGib - ROB3 M 4 A_Scream - ROB3 N 4 A_TossGib - ROB3 O 4 Bright A_Explode(128,128,1,1) - ROB3 P 4 Bright A_TossGib - ROB3 Q 4 Bright A_NoBlocking - ROB3 RSTUV 4 A_TossGib - ROB3 W 4 Bright A_Explode(128,128,1,1) - ROB3 XY 4 Bright A_TossGib - ROB3 Z 4 A_TossGib - ROB3 "[" 4 A_TossGib - ROB3 "\" 3 A_TossGib - ROB3 "]" 3 Bright A_Explode(128,128,1,1) - RBB3 A 3 Bright A_TossArm - RBB3 B 3 Bright A_TossGib - RBB3 CD 3 A_TossGib - RBB3 E -1 - Stop - } -} - -// Inquisitor Shot ---------------------------------------------------------- - -ACTOR InquisitorShot -{ - ReactionTime 15 - Speed 25 - Radius 13 - Height 13 - Mass 15 - Projectile - -ACTIVATEIMPACT - -ACTIVATEPCROSS - -NOGRAVITY - +STRIFEDAMAGE - MaxStepHeight 4 - SeeSound "inquisitor/attack" - DeathSound "inquisitor/atkexplode" - States - { - Spawn: - UBAM AB 3 A_Countdown - Loop - Death: - BNG2 A 0 Bright A_SetTranslucent(1,1) - BNG2 A 4 Bright A_Explode(192, 192, 1, 1) - BNG2 B 4 Bright - BNG2 C 4 Bright - BNG2 D 4 Bright - BNG2 E 4 Bright - BNG2 F 4 Bright - BNG2 G 4 Bright - BNG2 H 4 Bright - BNG2 I 4 Bright - Stop - } - -} - - -// The Dead Inquisitor's Detached Arm --------------------------------------- - -ACTOR InquisitorArm -{ - Speed 25 - +NOBLOCKMAP - +NOCLIP - +NOBLOOD - States - { - Spawn: - RBB3 FG 5 Bright - RBB3 H -1 - Stop - } -} - - - diff --git a/wadsrc/static/actors/strife/loremaster.txt b/wadsrc/static/actors/strife/loremaster.txt deleted file mode 100644 index fd2b400cb..000000000 --- a/wadsrc/static/actors/strife/loremaster.txt +++ /dev/null @@ -1,114 +0,0 @@ - -// Loremaster (aka Priest) -------------------------------------------------- - -ACTOR Loremaster -{ - Health 800 - Speed 10 - Radius 15 - Height 56 - FloatSpeed 5 - Monster - +FLOAT - +NOBLOOD - +NOGRAVITY - +NOTDMATCH - +FLOORCLIP - +NOBLOCKMONST - +INCOMBAT - +LOOKALLAROUND - +NOICEDEATH - +NEVERRESPAWN - DamageFactor "Fire", 0.5 - MinMissileChance 150 - Tag "$TAG_PRIEST" - SeeSound "loremaster/sight" - AttackSound "loremaster/attack" - PainSound "loremaster/pain" - DeathSound "loremaster/death" - ActiveSound "loremaster/active" - Obituary "$OB_LOREMASTER" - DropItem "Junk" - states - { - Spawn: - PRST A 10 A_Look - PRST B 10 A_SentinelBob - Loop - See: - PRST A 4 A_Chase - PRST A 4 A_SentinelBob - PRST B 4 A_Chase - PRST B 4 A_SentinelBob - PRST C 4 A_Chase - PRST C 4 A_SentinelBob - PRST D 4 A_Chase - PRST D 4 A_SentinelBob - Loop - Melee: - PRST E 4 A_FaceTarget - PRST F 4 A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5) - PRST E 4 A_SentinelBob - Goto See - Missile: - PRST E 4 A_FaceTarget - PRST F 4 A_CustomMissile("LoreShot", 32, 0) - PRST E 4 A_SentinelBob - Goto See - Death: - PDED A 6 - PDED B 6 A_Scream - PDED C 6 - PDED D 6 A_Fall - PDED E 6 - PDED FGHIJIJIJKL 5 - PDED MNOP 4 - PDED Q 4 A_SpawnItemEx("AlienSpectre5", 0, 0, 0, 0, 0, random[spectrespawn](0,255)*0.0078125, 0, SXF_NOCHECKPOSITION) - PDED RS 4 - PDED T -1 - Stop - } -} - - -// Loremaster Projectile ---------------------------------------------------- - -ACTOR LoreShot native -{ - Speed 20 - Height 14 - Radius 10 - Projectile - +STRIFEDAMAGE - Damage 2 - MaxStepHeight 4 - SeeSound "loremaster/chain" - ActiveSound "loremaster/swish" - - action native A_LoremasterChain (); - - States - { - Spawn: - OCLW A 2 A_LoremasterChain - Loop - Death: - OCLW A 6 - Stop - } -} - -// Loremaster Subprojectile ------------------------------------------------- - -ACTOR LoreShot2 -{ - +NOBLOCKMAP - +NOGRAVITY - States - { - Spawn: - TEND A 20 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/macil.txt b/wadsrc/static/actors/strife/macil.txt deleted file mode 100644 index 7c03d1f24..000000000 --- a/wadsrc/static/actors/strife/macil.txt +++ /dev/null @@ -1,89 +0,0 @@ - -// Macil (version 1) --------------------------------------------------------- - -ACTOR Macil1 -{ - Health 95 - Radius 20 - Height 56 - Speed 8 - Painchance 250 - Monster - -COUNTKILL - +NOTDMATCH - +NOICEDEATH - +NOSPLASHALERT - +NODAMAGE - +NEVERRESPAWN - DamageFactor "Fire", 0.5 - MinMissileChance 150 - SeeSound "macil/sight" - PainSound "macil/pain" - ActiveSound "macil/active" - CrushPainSound "misc/pcrush" - Tag "$TAG_MACIL1" - Obituary "$OB_MACIL" - DropItem "BoxOfBullets" - MaxStepHeight 16 - MaxDropoffHeight 32 - States - { - Spawn: - LEDR C 5 A_Look2 - Loop - LEDR A 8 - Loop - LEDR B 8 - Loop - LEAD ABCD 6 A_Wander - Loop - See: - LEAD AABBCCDD 3 A_Chase - Loop - Missile: - Death: - LEAD E 2 A_FaceTarget - LEAD F 2 BRIGHT A_ShootGun - LEAD E 1 A_SentinelRefire - Loop - Pain: - LEAD Y 3 - LEAD Y 3 A_Pain - Goto See - } -} - - -// Macil (version 2) --------------------------------------------------------- - -ACTOR Macil2 : Macil1 -{ - Painchance 200 - +COUNTKILL - +SPECTRAL - -NODAMAGE - Tag "$TAG_MACIL2" - DeathSound "macil/slop" - DropItem "None" - DamageFactor "SpectralLow", 0 - States - { - Missile: - LEAD E 4 A_FaceTarget - LEAD F 4 BRIGHT A_ShootGun - LEAD E 2 A_SentinelRefire - Loop - Death: - LEAD G 5 - LEAD H 5 A_Scream - LEAD IJ 4 - LEAD K 3 - LEAD L 3 A_NoBlocking - LEAD MNOPQRSTUV 3 - LEAD W 3 A_SpawnItemEx("AlienSpectre4", 0, 0, 0, 0, 0, random[spectrespawn](0,255)*0.0078125, 0, SXF_NOCHECKPOSITION) - LEAD X -1 - Stop - } -} - - diff --git a/wadsrc/static/actors/strife/merchants.txt b/wadsrc/static/actors/strife/merchants.txt deleted file mode 100644 index 1a843f47a..000000000 --- a/wadsrc/static/actors/strife/merchants.txt +++ /dev/null @@ -1,93 +0,0 @@ -// Base class for the merchants --------------------------------------------- - -ACTOR Merchant -{ - Health 10000000 - PainChance 256 // a merchant should always enter the pain state when getting hurt - Radius 20 - Height 56 - Mass 5000 - CrushPainSound "misc/pcrush" - +SOLID - +SHOOTABLE - +NOTDMATCH - +NOSPLASHALERT - +NODAMAGE - States - { - Spawn: - MRST A 10 A_Look2 - Loop - MRLK A 30 A_ActiveSound - Loop - MRLK B 30 - Loop - MRBD ABCDEDCB 4 - MRBD A 5 - MRBD F 6 - Loop - See: - Pain: - MRPN A 1 - MRPN A 2 A_AlertMonsters - MRPN B 3 A_Pain - MRPN C 3 - MRPN D 9 Door_CloseWaitOpen(999, 64, 960) - MRPN C 4 - MRPN B 3 - MRPN A 3 A_ClearSoundTarget - Goto Spawn - Yes: - MRYS A 20 - // Fall through - Greetings: - MRGT ABCDEFGHI 5 - Goto Spawn - No: - MRNO AB 6 - MRNO C 10 - MRNO BA 6 - Goto Greetings - } -} - - -// Weapon Smith ------------------------------------------------------------- - -ACTOR WeaponSmith : Merchant -{ - PainSound "smith/pain" - Tag "$TAG_WEAPONSMITH" -} - - -// Bar Keep ----------------------------------------------------------------- - -ACTOR BarKeep : Merchant -{ - Translation 4 - PainSound "barkeep/pain" - ActiveSound "barkeep/active" - Tag "$TAG_BARKEEP" -} - - -// Armorer ------------------------------------------------------------------ - -ACTOR Armorer : Merchant -{ - Translation 5 - PainSound "armorer/pain" - Tag "$TAG_ARMORER" -} - - -// Medic -------------------------------------------------------------------- - -ACTOR Medic : Merchant -{ - Translation 6 - PainSound "medic/pain" - Tag "$TAG_MEDIC" -} - diff --git a/wadsrc/static/actors/strife/oracle.txt b/wadsrc/static/actors/strife/oracle.txt deleted file mode 100644 index 8502bae96..000000000 --- a/wadsrc/static/actors/strife/oracle.txt +++ /dev/null @@ -1,35 +0,0 @@ - -// Oracle ------------------------------------------------------------------- - -ACTOR Oracle -{ - Health 1 - Radius 15 - Height 56 - Monster - +NOTDMATCH - +NOBLOOD - +NEVERRESPAWN - DamageFactor "Fire", 0.5 - DamageFactor "SpectralLow", 0 - MaxDropoffHeight 32 - Tag "$TAG_ORACLE" - DropItem "Meat" - - action native A_WakeOracleSpectre (); - - States - { - Spawn: - ORCL A -1 - Stop - Death: - ORCL BCDEFGHIJK 5 - ORCL L 5 A_NoBlocking - ORCL M 5 - ORCL N 5 A_WakeOracleSpectre - ORCL OP 5 - ORCL Q -1 - Stop - } -} diff --git a/wadsrc/static/actors/strife/peasants.txt b/wadsrc/static/actors/strife/peasants.txt deleted file mode 100644 index b5ec89258..000000000 --- a/wadsrc/static/actors/strife/peasants.txt +++ /dev/null @@ -1,182 +0,0 @@ - -// Peasant Base Class ------------------------------------------------------- - -ACTOR Peasant : StrifeHumanoid -{ - Health 31 - PainChance 200 - Speed 8 - Radius 20 - Height 56 - Monster - +NEVERTARGET - -COUNTKILL - +NOSPLASHALERT - +FLOORCLIP - +JUSTHIT - MinMissileChance 150 - MaxStepHeight 16 - MaxDropoffHeight 32 - SeeSound "peasant/sight" - AttackSound "peasant/attack" - PainSound "peasant/pain" - DeathSound "peasant/death" - HitObituary "$OB_PEASANT" - States - { - Spawn: - PEAS A 10 A_Look2 - Loop - See: - PEAS AABBCCDD 5 A_Wander - Goto Spawn - Melee: - PEAS E 10 A_FaceTarget - PEAS F 8 A_CustomMeleeAttack(2*random[PeasantAttack](1,5)+2) - PEAS E 8 - Goto See - Pain: - PEAS O 3 - PEAS O 3 A_Pain - Goto Melee - Wound: - PEAS G 5 - PEAS H 10 A_GetHurt - PEAS I 6 - Goto Wound+1 - Death: - PEAS G 5 - PEAS H 5 A_Scream - PEAS I 6 - PEAS J 5 A_NoBlocking - PEAS K 5 - PEAS L 6 - PEAS M 8 - PEAS N 1400 - GIBS U 5 - GIBS V 1400 - Stop - XDeath: - GIBS M 5 A_TossGib - GIBS N 5 A_XScream - GIBS O 5 A_NoBlocking - GIBS PQRS 4 A_TossGib - Goto Death+8 - } -} - -// Peasant Variant 1 -------------------------------------------------------- - -ACTOR Peasant1 : Peasant -{ - Speed 4 -} - -ACTOR Peasant2 : Peasant -{ - Speed 5 -} - -ACTOR Peasant3 : Peasant -{ - Speed 5 -} - -ACTOR Peasant4 : Peasant -{ - Translation 0 - Speed 7 -} - -ACTOR Peasant5 : Peasant -{ - Translation 0 - Speed 7 -} - -ACTOR Peasant6 : Peasant -{ - Translation 0 - Speed 7 -} - -ACTOR Peasant7 : Peasant -{ - Translation 2 -} - -ACTOR Peasant8 : Peasant -{ - Translation 2 -} - -ACTOR Peasant9 : Peasant -{ - Translation 2 -} - -ACTOR Peasant10 : Peasant -{ - Translation 1 -} - -ACTOR Peasant11 : Peasant -{ - Translation 1 -} - -ACTOR Peasant12 : Peasant -{ - Translation 1 -} - -ACTOR Peasant13 : Peasant -{ - Translation 3 -} - -ACTOR Peasant14 : Peasant -{ - Translation 3 -} - -ACTOR Peasant15 : Peasant -{ - Translation 3 -} - -ACTOR Peasant16 : Peasant -{ - Translation 5 -} - -ACTOR Peasant17 : Peasant -{ - Translation 5 -} - -ACTOR Peasant18 : Peasant -{ - Translation 5 -} - -ACTOR Peasant19 : Peasant -{ - Translation 4 -} - -ACTOR Peasant20 : Peasant -{ - Translation 4 -} - -ACTOR Peasant21 : Peasant -{ - Translation 4 -} - -ACTOR Peasant22 : Peasant -{ - Translation 6 -} - diff --git a/wadsrc/static/actors/strife/programmer.txt b/wadsrc/static/actors/strife/programmer.txt deleted file mode 100644 index d9544af9c..000000000 --- a/wadsrc/static/actors/strife/programmer.txt +++ /dev/null @@ -1,107 +0,0 @@ - -// Programmer --------------------------------------------------------------- - -ACTOR Programmer -{ - Health 1100 - PainChance 50 - Speed 26 - FloatSpeed 5 - Radius 45 - Height 60 - Mass 800 - Damage 4 - Monster - +NOGRAVITY - +FLOAT - +NOBLOOD - +NOTDMATCH - +DONTMORPH - +NOBLOCKMONST - +LOOKALLAROUND - +NOICEDEATH - +NOTARGETSWITCH - DamageFactor "Fire", 0.5 - MinMissileChance 150 - AttackSound "programmer/attack" - PainSound "programmer/pain" - DeathSound "programmer/death" - ActiveSound "programmer/active" - Obituary "$OB_PROGRAMMER" - DropItem "Sigil1" - - action native A_ProgrammerMelee (); - action native A_SpawnProgrammerBase (); - action native A_ProgrammerDeath (); - action native A_SpotLightning(); - - States - { - Spawn: - PRGR A 5 A_Look - PRGR A 1 A_SentinelBob - Loop - See: - PRGR A 160 A_SentinelBob - PRGR BCD 5 A_SentinelBob - PRGR EF 2 A_SentinelBob - PRGR EF 3 A_Chase - Goto See+4 - Melee: - PRGR E 2 A_SentinelBob - PRGR F 3 A_SentinelBob - PRGR E 3 A_FaceTarget - PRGR F 4 A_ProgrammerMelee - Goto See+4 - Missile: - PRGR G 5 A_FaceTarget - PRGR H 5 A_SentinelBob - PRGR I 5 Bright A_FaceTarget - PRGR J 5 Bright A_SpotLightning - Goto See+4 - Pain: - PRGR K 5 A_Pain - PRGR L 5 A_SentinelBob - Goto See+4 - Death: - PRGR L 7 Bright A_TossGib - PRGR M 7 Bright A_Scream - PRGR N 7 Bright A_TossGib - PRGR O 7 Bright A_NoBlocking - PRGR P 7 Bright A_TossGib - PRGR Q 7 Bright A_SpawnProgrammerBase - PRGR R 7 Bright - PRGR S 6 Bright - PRGR TUVW 5 Bright - PRGR X 32 Bright - PRGR X -1 Bright A_ProgrammerDeath - Stop - } -} - - -// The Programmer's base for when he dies ----------------------------------- - -ACTOR ProgrammerBase -{ - +NOBLOCKMAP - +NOCLIP - +NOBLOOD - states - { - Spawn: - BASE A 5 Bright A_Explode(32,32,1,1) - BASE BCD 5 Bright - BASE EFG 5 - BASE H -1 - Stop - } -} - - -// The Programmer level ending thing ---------------------------------------- - -ACTOR ProgLevelEnder : Inventory native -{ - +INVENTORY.UNDROPPABLE -} diff --git a/wadsrc/static/actors/strife/ratbuddy.txt b/wadsrc/static/actors/strife/ratbuddy.txt deleted file mode 100644 index c6a1baf9c..000000000 --- a/wadsrc/static/actors/strife/ratbuddy.txt +++ /dev/null @@ -1,34 +0,0 @@ - -ACTOR RatBuddy -{ - Health 5 - Speed 13 - Radius 10 - Height 16 - +NOBLOOD +FLOORCLIP +CANPASS - +ISMONSTER +INCOMBAT - MinMissileChance 150 - MaxStepHeight 16 - MaxDropoffHeight 32 - Tag "$TAG_RATBUDDY" - SeeSound "rat/sight" - DeathSound "rat/death" - ActiveSound "rat/active" - States - { - Spawn: - RATT A 10 A_Look - Loop - See: - RATT AABB 4 A_Chase - Loop - Melee: - RATT A 8 A_Wander - RATT B 4 A_Wander - Goto See - Death: - MEAT Q 700 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/reaver.txt b/wadsrc/static/actors/strife/reaver.txt deleted file mode 100644 index 816070d47..000000000 --- a/wadsrc/static/actors/strife/reaver.txt +++ /dev/null @@ -1,64 +0,0 @@ - -ACTOR Reaver -{ - Health 150 - Painchance 128 - Speed 12 - Radius 20 - Height 60 - Monster - +NOBLOOD - +INCOMBAT - MinMissileChance 150 - MaxDropoffHeight 32 - Mass 500 - SeeSound "reaver/sight" - PainSound "reaver/pain" - DeathSound "reaver/death" - ActiveSound "reaver/active" - HitObituary "$OB_REAVERHIT" - Obituary "$OB_REAVER" - - action native A_ReaverRanged (); - - States - { - Spawn: - ROB1 A 10 A_Look - Loop - See: - ROB1 BBCCDDEE 3 A_Chase - Loop - Melee: - ROB1 H 6 Slow A_FaceTarget - ROB1 I 8 Slow A_CustomMeleeAttack(random[ReaverMelee](1,8)*3, "reaver/blade") - ROB1 H 6 Slow - Goto See - Missile: - ROB1 F 8 Slow A_FaceTarget - ROB1 G 11 Slow BRIGHT A_ReaverRanged - Goto See - Pain: - ROB1 A 2 Slow - ROB1 A 2 A_Pain - Goto See - Death: - ROB1 J 6 - ROB1 K 6 A_Scream - ROB1 L 5 - ROB1 M 5 A_NoBlocking - ROB1 NOP 5 - ROB1 Q 6 A_Explode(32,32,1,1) - ROB1 R -1 - Stop - XDeath: - ROB1 L 5 A_TossGib - ROB1 M 5 A_Scream - ROB1 N 5 A_TossGib - ROB1 O 5 A_NoBlocking - ROB1 P 5 A_TossGib - Goto Death+7 - } - -} - \ No newline at end of file diff --git a/wadsrc/static/actors/strife/rebels.txt b/wadsrc/static/actors/strife/rebels.txt deleted file mode 100644 index 2dcb5ac1a..000000000 --- a/wadsrc/static/actors/strife/rebels.txt +++ /dev/null @@ -1,131 +0,0 @@ - - -// Base class for the rebels ------------------------------------------------ - -ACTOR Rebel : StrifeHumanoid -{ - Health 60 - Painchance 250 - Speed 8 - Radius 20 - Height 56 - Monster - +FRIENDLY - -COUNTKILL - +NOSPLASHALERT - MinMissileChance 150 - Tag "$TAG_REBEL" - SeeSound "rebel/sight" - PainSound "rebel/pain" - DeathSound "rebel/death" - ActiveSound "rebel/active" - Obituary "$OB_REBEL" - States - { - Spawn: - HMN1 P 5 A_Look2 - Loop - HMN1 Q 8 - Loop - HMN1 R 8 - Loop - HMN1 ABCDABCD 6 A_Wander - Loop - See: - HMN1 AABBCCDD 3 A_Chase - Loop - Missile: - HMN1 E 10 A_FaceTarget - HMN1 F 10 BRIGHT A_ShootGun - HMN1 E 10 A_ShootGun - Goto See - Pain: - HMN1 O 3 - HMN1 O 3 A_Pain - Goto See - Death: - HMN1 G 5 - HMN1 H 5 A_Scream - HMN1 I 3 A_NoBlocking - HMN1 J 4 - HMN1 KLM 3 - HMN1 N -1 - Stop - XDeath: - RGIB A 4 A_TossGib - RGIB B 4 A_XScream - RGIB C 3 A_NoBlocking - RGIB DEF 3 A_TossGib - RGIB G 3 - RGIB H 1400 - Stop - } -} - -// Rebel 1 ------------------------------------------------------------------ - -ACTOR Rebel1 : Rebel -{ - DropItem "ClipOfBullets" -} - -// Rebel 2 ------------------------------------------------------------------ - -ACTOR Rebel2 : Rebel -{ -} - -// Rebel 3 ------------------------------------------------------------------ - -ACTOR Rebel3 : Rebel -{ -} - -// Rebel 4 ------------------------------------------------------------------ - -ACTOR Rebel4 : Rebel -{ -} - -// Rebel 5 ------------------------------------------------------------------ - -ACTOR Rebel5 : Rebel -{ -} - -// Rebel 6 ------------------------------------------------------------------ - -ACTOR Rebel6 : Rebel -{ -} - -// Teleporter Beacon -------------------------------------------------------- - -ACTOR TeleporterBeacon : Inventory native -{ - Health 5 - Radius 16 - Height 16 - Inventory.MaxAmount 3 - +DROPPED - +INVENTORY.INVBAR - Inventory.Icon "I_BEAC" - Tag "$TAG_TELEPORTERBEACON" - Inventory.PickupMessage "$TXT_BEACON" - - action native A_Beacon (); - - States - { - Spawn: - BEAC A -1 - Stop - Drop: - BEAC A 30 - BEAC A 160 A_Beacon - Wait - Death: - BEAC A 1 A_FadeOut(0.015) - Loop - } -} \ No newline at end of file diff --git a/wadsrc/static/actors/strife/sentinel.txt b/wadsrc/static/actors/strife/sentinel.txt deleted file mode 100644 index ca61f2bf8..000000000 --- a/wadsrc/static/actors/strife/sentinel.txt +++ /dev/null @@ -1,95 +0,0 @@ - -// Sentinel ----------------------------------------------------------------- - -ACTOR Sentinel -{ - Health 100 - Painchance 255 - Speed 7 - Radius 23 - Height 53 - Mass 300 - Monster - +SPAWNCEILING - +NOGRAVITY - +DROPOFF - +NOBLOOD - +NOBLOCKMONST - +INCOMBAT - +MISSILEMORE - +LOOKALLAROUND - +NEVERRESPAWN - MinMissileChance 150 - SeeSound "sentinel/sight" - DeathSound "sentinel/death" - ActiveSound "sentinel/active" - Obituary "$OB_SENTINEL" - - action native A_SentinelAttack (); - - States - { - Spawn: - SEWR A 10 A_Look - Loop - See: - SEWR A 6 A_SentinelBob - SEWR A 6 A_Chase - Loop - Missile: - SEWR B 4 A_FaceTarget - SEWR C 8 Bright A_SentinelAttack - SEWR C 4 Bright A_SentinelRefire - Goto Missile+1 - Pain: - SEWR D 5 A_Pain - Goto Missile+2 - Death: - SEWR D 7 A_Fall - SEWR E 8 Bright A_TossGib - SEWR F 5 Bright A_Scream - SEWR GH 4 Bright A_TossGib - SEWR I 4 - SEWR J 5 - Stop - } -} - -// Sentinel FX 1 ------------------------------------------------------------ - -ACTOR SentinelFX1 -{ - Speed 40 - Radius 10 - Height 8 - Damage 0 - DamageType Disintegrate - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - RenderStyle Add - States - { - Spawn: - SHT1 AB 4 - Loop - Death: - POW1 J 4 - Stop - } -} - -// Sentinel FX 2 ------------------------------------------------------------ - -ACTOR SentinelFX2 : SentinelFX1 -{ - SeeSound "sentinel/plasma" - Damage 1 - States - { - Death: - POW1 FGHI 4 - Goto Super::Death - } -} - diff --git a/wadsrc/static/actors/strife/sigil.txt b/wadsrc/static/actors/strife/sigil.txt deleted file mode 100644 index 4c5f552d5..000000000 --- a/wadsrc/static/actors/strife/sigil.txt +++ /dev/null @@ -1,161 +0,0 @@ - -// The Almighty Sigil! ------------------------------------------------------ - -ACTOR Sigil : Weapon native -{ - - Weapon.Kickback 100 - Weapon.SelectionOrder 4000 - Health 1 - +FLOORCLIP - +WEAPON.CHEATNOTWEAPON - Inventory.PickupSound "weapons/sigilcharge" - Tag "$TAG_SIGIL" - Inventory.Icon "I_SGL1" - Inventory.PickupMessage "$TXT_SIGIL" - - action native A_SelectPiece (); - action native A_SelectSigilView (); - action native A_SelectSigilDown (); - action native A_SelectSigilAttack (); - action native A_SigilCharge (); - action native A_FireSigil1 (); - action native A_FireSigil2 (); - action native A_FireSigil3 (); - action native A_FireSigil4 (); - action native A_FireSigil5 (); - - States - { - Spawn: - SIGL A 1 - SIGL A -1 A_SelectPiece - Stop - SIGL B -1 - Stop - SIGL C -1 - Stop - SIGL D -1 - Stop - SIGL E -1 - Stop - Ready: - SIGH A 0 Bright A_SelectSigilView - Wait - SIGH A 1 Bright A_WeaponReady - Wait - SIGH B 1 Bright A_WeaponReady - Wait - SIGH C 1 Bright A_WeaponReady - Wait - SIGH D 1 Bright A_WeaponReady - Wait - SIGH E 1 Bright A_WeaponReady - Wait - Deselect: - SIGH A 1 Bright A_SelectSigilDown - Wait - SIGH A 1 Bright A_Lower - Wait - SIGH B 1 Bright A_Lower - Wait - SIGH C 1 Bright A_Lower - Wait - SIGH D 1 Bright A_Lower - Wait - SIGH E 1 Bright A_Lower - Wait - Select: - SIGH A 1 Bright A_SelectSigilView - Wait - SIGH A 1 Bright A_Raise - Wait - SIGH B 1 Bright A_Raise - Wait - SIGH C 1 Bright A_Raise - Wait - SIGH D 1 Bright A_Raise - Wait - SIGH E 1 Bright A_Raise - Wait - - Fire: - SIGH A 0 Bright A_SelectSigilAttack - - SIGH A 18 Bright A_SigilCharge - SIGH A 3 Bright A_GunFlash - SIGH A 10 A_FireSigil1 - SIGH A 5 - Goto Ready - - SIGH B 18 Bright A_SigilCharge - SIGH B 3 Bright A_GunFlash - SIGH B 10 A_FireSigil2 - SIGH B 5 - Goto Ready - - SIGH C 18 Bright A_SigilCharge - SIGH C 3 Bright A_GunFlash - SIGH C 10 A_FireSigil3 - SIGH C 5 - Goto Ready - - SIGH D 18 Bright A_SigilCharge - SIGH D 3 Bright A_GunFlash - SIGH D 10 A_FireSigil4 - SIGH D 5 - Goto Ready - - SIGH E 18 Bright A_SigilCharge - SIGH E 3 Bright A_GunFlash - SIGH E 10 A_FireSigil5 - SIGH E 5 - Goto Ready - Flash: - SIGF A 4 Bright A_Light2 - SIGF B 6 Bright A_LightInverse - SIGF C 4 Bright A_Light1 - SIGF C 0 Bright A_Light0 - Stop - } -} - -// Sigil 1 ------------------------------------------------------------------ - -ACTOR Sigil1 : Sigil -{ - Inventory.Icon "I_SGL1" - Health 1 -} - -// Sigil 2 ------------------------------------------------------------------ - -ACTOR Sigil2 : Sigil -{ - Inventory.Icon "I_SGL2" - Health 2 -} - -// Sigil 3 ------------------------------------------------------------------ - -ACTOR Sigil3 : Sigil -{ - Inventory.Icon "I_SGL3" - Health 3 -} - -// Sigil 4 ------------------------------------------------------------------ - -ACTOR Sigil4 : Sigil -{ - Inventory.Icon "I_SGL4" - Health 4 -} - -// Sigil 5 ------------------------------------------------------------------ - -ACTOR Sigil5 : Sigil -{ - Inventory.Icon "I_SGL5" - Health 5 -} diff --git a/wadsrc/static/actors/strife/spectral.txt b/wadsrc/static/actors/strife/spectral.txt deleted file mode 100644 index 6f9c87c0c..000000000 --- a/wadsrc/static/actors/strife/spectral.txt +++ /dev/null @@ -1,262 +0,0 @@ - - -// base for all spectral monsters which hurt when being touched-------------- - -ACTOR SpectralMonster native -{ - Monster - +SPECIAL - +SPECTRAL - +NOICEDEATH - - action native A_SpectreChunkSmall (); - action native A_SpectreChunkLarge (); - action native A_Spectre3Attack (); - action native A_SpotLightning (); -} - - -// Container for all spectral lightning deaths ------------------------------ - -ACTOR SpectralLightningBase -{ - +NOTELEPORT - +ACTIVATEIMPACT - +ACTIVATEPCROSS - +STRIFEDAMAGE - MaxStepHeight 4 - RenderStyle Add - SeeSound "weapons/sigil" - DeathSound "weapons/sigilhit" - States - { - Death: - ZAP1 B 3 A_Explode(32,32) - ZAP1 A 3 A_AlertMonsters - ZAP1 BCDEFE 3 - ZAP1 DCB 2 - ZAP1 A 1 - Stop - } -} - -// Spectral Lightning death that does not explode --------------------------- - -ACTOR SpectralLightningDeath1 : SpectralLightningBase -{ - States - { - Death: - Goto Super::Death+1 - } -} - -// Spectral Lightning death that does not alert monsters -------------------- - -ACTOR SpectralLightningDeath2 : SpectralLightningBase -{ - States - { - Death: - Goto Super::Death+2 - } -} - -// Spectral Lightning death that is shorter than the rest ------------------- - -ACTOR SpectralLightningDeathShort : SpectralLightningBase -{ - States - { - Death: - Goto Super::Death+6 - } -} - -// Spectral Lightning (Ball Shaped #1) -------------------------------------- - -ACTOR SpectralLightningBall1 : SpectralLightningBase -{ - Speed 30 - Radius 8 - Height 16 - Damage 70 - Projectile - +SPECTRAL - States - { - Spawn: - ZOT3 ABCDE 4 Bright - Loop - } -} - -// Spectral Lightning (Ball Shaped #2) -------------------------------------- - -ACTOR SpectralLightningBall2 : SpectralLightningBall1 -{ - Damage 20 -} - -// Spectral Lightning (Horizontal #1) --------------------------------------- - -ACTOR SpectralLightningH1 : SpectralLightningBase -{ - Speed 30 - Radius 8 - Height 16 - Damage 70 - Projectile - +SPECTRAL - - action native A_SpectralLightningTail (); - - States - { - Spawn: - ZAP6 A 4 Bright - ZAP6 BC 4 Bright A_SpectralLightningTail - Loop - } -} - - -// Spectral Lightning (Horizontal #2) ------------------------------------- - -ACTOR SpectralLightningH2 : SpectralLightningH1 -{ - Damage 20 -} - -// Spectral Lightning (Horizontal #3) ------------------------------------- - -ACTOR SpectralLightningH3 : SpectralLightningH1 -{ - Damage 10 -} - -// ASpectralLightningHTail -------------------------------------------------- - -ACTOR SpectralLightningHTail -{ - +NOBLOCKMAP - +NOGRAVITY - +DROPOFF - RenderStyle Add - States - { - Spawn: - ZAP6 ABC 5 Bright - Stop - } -} - -// Spectral Lightning (Big Ball #1) ----------------------------------------- - -ACTOR SpectralLightningBigBall1 : SpectralLightningDeath2 -{ - Speed 18 - Radius 20 - Height 40 - Damage 130 - Projectile - +SPECTRAL - - action native A_SpectralBigBallLightning (); - - States - { - Spawn: - ZAP7 AB 4 Bright A_SpectralBigBallLightning - ZAP7 CDE 6 Bright A_SpectralBigBallLightning - Loop - } -} - - -// Spectral Lightning (Big Ball #2 - less damaging) ------------------------- - -ACTOR SpectralLightningBigBall2 : SpectralLightningBigBall1 -{ - Damage 30 -} - -// Sigil Lightning (Vertical #1) -------------------------------------------- - -ACTOR SpectralLightningV1 : SpectralLightningDeathShort -{ - Speed 22 - Radius 8 - Height 24 - Damage 100 - Projectile - DamageType "SpectralLow" - +SPECTRAL - States - { - Spawn: - ZOT1 AB 4 Bright - ZOT1 CDE 6 Bright - Loop - } -} - -// Sigil Lightning (Vertical #2 - less damaging) ---------------------------- - -ACTOR SpectralLightningV2 : SpectralLightningV1 -{ - Damage 50 -} - -// Sigil Lightning Spot (roams around dropping lightning from above) -------- - -ACTOR SpectralLightningSpot : SpectralLightningDeath1 -{ - Speed 18 - ReactionTime 70 - +NOBLOCKMAP - +NOBLOCKMONST - +NODROPOFF - RenderStyle Translucent - Alpha 0.6 - - action native A_SpectralLightning (); - - States - { - Spawn: - ZAP5 A 4 Bright A_Countdown - ZAP5 B 4 Bright A_SpectralLightning - ZAP5 CD 4 Bright A_Countdown - Loop - } -} - -// Sigil Lightning (Big Vertical #1) ---------------------------------------- - -ACTOR SpectralLightningBigV1 : SpectralLightningDeath1 -{ - Speed 28 - Radius 8 - Height 16 - Damage 120 - Projectile - +SPECTRAL - States - { - Spawn: - ZOT2 ABCDE 4 Bright A_Tracer2 - Loop - } -} - -// Actor 90 ----------------------------------------------------------------- - -ACTOR SpectralLightningBigV2 : SpectralLightningBigV1 -{ - Damage 60 -} - - - - diff --git a/wadsrc/static/actors/strife/stalker.txt b/wadsrc/static/actors/strife/stalker.txt deleted file mode 100644 index 7f469e610..000000000 --- a/wadsrc/static/actors/strife/stalker.txt +++ /dev/null @@ -1,76 +0,0 @@ - - -// Stalker ------------------------------------------------------------------ - -ACTOR Stalker -{ - Health 80 - Painchance 40 - Speed 16 - Radius 31 - Height 25 - Monster - +NOGRAVITY - +DROPOFF - +NOBLOOD - +SPAWNCEILING - +INCOMBAT - +NOVERTICALMELEERANGE - MaxDropOffHeight 32 - MinMissileChance 150 - SeeSound "stalker/sight" - AttackSound "stalker/attack" - PainSound "stalker/pain" - DeathSound "stalker/death" - ActiveSound "stalker/active" - HitObituary "$OB_STALKER" - - action native A_StalkerLookInit (); - action native A_StalkerChaseDecide (); - action native A_StalkerWalk (); - action native A_StalkerDrop (); - action native A_StalkerAttack (); - - states - { - Spawn: - STLK A 1 A_StalkerLookInit - Loop - LookCeiling: - STLK A 10 A_Look - Loop - LookFloor: - STLK J 10 A_Look - Loop - See: - STLK A 1 Slow A_StalkerChaseDecide - STLK ABB 3 Slow A_Chase - STLK C 3 Slow A_StalkerWalk - STLK C 3 Slow A_Chase - Loop - Melee: - STLK J 3 Slow A_FaceTarget - STLK K 3 Slow A_StalkerAttack - SeeFloor: - STLK J 3 A_StalkerWalk - STLK KK 3 A_Chase - STLK L 3 A_StalkerWalk - STLK L 3 A_Chase - Loop - Pain: - STLK L 1 A_Pain - Goto See - Drop: - STLK C 2 A_StalkerDrop - STLK IHGFED 3 - Goto SeeFloor - Death: - STLK O 4 - STLK P 4 A_Scream - STLK QRST 4 - STLK U 4 A_NoBlocking - STLK VW 4 - STLK "XYZ[" 4 Bright - Stop - } -} diff --git a/wadsrc/static/actors/strife/strifeammo.txt b/wadsrc/static/actors/strife/strifeammo.txt deleted file mode 100644 index e432a7144..000000000 --- a/wadsrc/static/actors/strife/strifeammo.txt +++ /dev/null @@ -1,202 +0,0 @@ -// HE-Grenade Rounds -------------------------------------------------------- - -ACTOR HEGrenadeRounds : Ammo -{ - +FLOORCLIP - Inventory.Amount 6 - Inventory.MaxAmount 30 - Ammo.BackpackAmount 6 - Ammo.BackpackMaxAmount 60 - Inventory.Icon "I_GRN1" - Tag "$TAG_HEGRENADES" - Inventory.PickupMessage "$TXT_HEGRENADES" - States - { - Spawn: - GRN1 A -1 - Stop - } -} - -// Phosphorus-Grenade Rounds ------------------------------------------------ - -ACTOR PhosphorusGrenadeRounds : Ammo -{ - +FLOORCLIP - Inventory.Amount 4 - Inventory.MaxAmount 16 - Ammo.BackpackAmount 4 - Ammo.BackpackMaxAmount 32 - Inventory.Icon "I_GRN2" - Tag "$TAG_PHGRENADES" - Inventory.PickupMessage "$TXT_PHGRENADES" - States - { - Spawn: - GRN2 A -1 - Stop - } -} - -// Clip of Bullets ---------------------------------------------------------- - -ACTOR ClipOfBullets : Ammo -{ - +FLOORCLIP - Inventory.Amount 10 - Inventory.MaxAmount 250 - Ammo.BackpackAmount 10 - Ammo.BackpackMaxAmount 500 - Inventory.Icon "I_BLIT" - Tag "$TAG_CLIPOFBULLETS" - Inventory.PickupMessage "$TXT_CLIPOFBULLETS" - States - { - Spawn: - BLIT A -1 - Stop - } -} - -// Box of Bullets ----------------------------------------------------------- - -ACTOR BoxOfBullets : ClipOfBullets -{ - Inventory.Amount 50 - Tag "$TAG_BOXOFBULLETS" - Inventory.PickupMessage "$TXT_BOXOFBULLETS" - States - { - Spawn: - BBOX A -1 - Stop - } -} - -// Mini Missiles ------------------------------------------------------------ - -ACTOR MiniMissiles : Ammo -{ - +FLOORCLIP - Inventory.Amount 4 - Inventory.MaxAmount 100 - Ammo.BackpackAmount 4 - Ammo.BackpackMaxAmount 200 - Inventory.Icon "I_ROKT" - Tag "$TAG_MINIMISSILES" - Inventory.PickupMessage "$TXT_MINIMISSILES" - States - { - Spawn: - MSSL A -1 - Stop - } -} - -// Crate of Missiles -------------------------------------------------------- - -ACTOR CrateOfMissiles : MiniMissiles -{ - Inventory.Amount 20 - Tag "$TAG_CRATEOFMISSILES" - Inventory.PickupMessage "$TXT_CRATEOFMISSILES" - States - { - Spawn: - ROKT A -1 - Stop - } -} - -// Energy Pod --------------------------------------------------------------- - -ACTOR EnergyPod : Ammo -{ - +FLOORCLIP - Inventory.Amount 20 - Inventory.MaxAmount 400 - Ammo.BackpackAmount 20 - Ammo.BackpackMaxAmount 800 - Ammo.DropAmount 20 - Inventory.Icon "I_BRY1" - Tag "$TAG_ENERGYPOD" - Inventory.PickupMessage "$TXT_ENERGYPOD" - States - { - Spawn: - BRY1 AB 6 - Loop - } -} - -// Energy pack --------------------------------------------------------------- - -ACTOR EnergyPack : EnergyPod -{ - Inventory.Amount 100 - Tag "$TAG_ENERGYPACK" - Inventory.PickupMessage "$TXT_ENERGYPACK" - States - { - Spawn: - CPAC AB 6 - Loop - } -} - -// Poison Bolt Quiver ------------------------------------------------------- - -ACTOR PoisonBolts : Ammo -{ - +FLOORCLIP - Inventory.Amount 10 - Inventory.MaxAmount 25 - Ammo.BackpackAmount 2 - Ammo.BackpackMaxAmount 50 - Inventory.Icon "I_PQRL" - Tag "$TAG_POISONBOLTS" - Inventory.PickupMessage "$TXT_POISONBOLTS" - States - { - Spawn: - PQRL A -1 - Stop - } -} - -// Electric Bolt Quiver ------------------------------------------------------- - -ACTOR ElectricBolts : Ammo -{ - +FLOORCLIP - Inventory.Amount 20 - Inventory.MaxAmount 50 - Ammo.BackpackAmount 4 - Ammo.BackpackMaxAmount 100 - Inventory.Icon "I_XQRL" - Tag "$TAG_ELECTRICBOLTS" - Inventory.PickupMessage "$TXT_ELECTRICBOLTS" - States - { - Spawn: - XQRL A -1 - Stop - } -} - -// Ammo Satchel ------------------------------------------------------------- - -ACTOR AmmoSatchel : BackpackItem -{ - +FLOORCLIP - Inventory.Icon "I_BKPK" - Tag "$TAG_AMMOSATCHEL" - Inventory.PickupMessage "$TXT_AMMOSATCHEL" - States - { - Spawn: - BKPK A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/strifearmor.txt b/wadsrc/static/actors/strife/strifearmor.txt deleted file mode 100644 index 3722d9338..000000000 --- a/wadsrc/static/actors/strife/strifearmor.txt +++ /dev/null @@ -1,43 +0,0 @@ - -ACTOR MetalArmor : BasicArmorPickup -{ - Radius 20 - Height 16 - +FLOORCLIP - +INVENTORY.AUTOACTIVATE - +INVENTORY.INVBAR - Inventory.MaxAmount 3 - Inventory.Icon "I_ARM1" - Inventory.PickupMessage "$TXT_METALARMOR" - Armor.SaveAmount 200 - Armor.SavePercent 50 - Tag "$TAG_METALARMOR" - States - { - Spawn: - ARM3 A -1 - Stop - } -} - -ACTOR LeatherArmor : BasicArmorPickup -{ - Radius 20 - Height 16 - +FLOORCLIP - +INVENTORY.AUTOACTIVATE - +INVENTORY.INVBAR - Inventory.MaxAmount 5 - Inventory.Icon "I_ARM2" - Inventory.PickupMessage "$TXT_LEATHERARMOR" - Armor.SaveAmount 100 - Armor.SavePercent 33.335 - Tag "$TAG_LEATHER" - States - { - Spawn: - ARM4 A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/strifebishop.txt b/wadsrc/static/actors/strife/strifebishop.txt deleted file mode 100644 index e64b247b1..000000000 --- a/wadsrc/static/actors/strife/strifebishop.txt +++ /dev/null @@ -1,94 +0,0 @@ - -// Bishop ------------------------------------------------------------------- - -ACTOR StrifeBishop -{ - Health 500 - Painchance 128 - Speed 8 - Radius 40 - Height 56 - Mass 500 - Monster - +NOBLOOD - +NOTDMATCH - +FLOORCLIP - +INCOMBAT - +NOICEDEATH - +NEVERRESPAWN - DamageFactor "Fire", 0.5 - MinMissileChance 150 - MaxDropoffHeight 32 - SeeSound "bishop/sight" - PainSound "bishop/pain" - DeathSound "bishop/death" - ActiveSound "bishop/active" - DropItem "CrateOfMissiles", 256, 20 - Obituary "$OB_STFBISHOP" - States - { - Spawn: - MLDR A 10 A_Look - Loop - See: - MLDR AABBCCDD 3 A_Chase - Loop - Missile: - MLDR E 3 A_FaceTarget - MLDR F 2 Bright A_CustomMissile("BishopMissile", 64, 0, 0, CMF_AIMOFFSET) - Goto See - Pain: - MLDR D 1 A_Pain - Goto See - Death: - MLDR G 3 Bright - MLDR H 5 Bright A_Scream - MLDR I 4 Bright A_TossGib - MLDR J 4 Bright A_Explode(64,64,1,1) - MLDR KL 3 Bright - MLDR M 4 Bright A_NoBlocking - MLDR N 4 Bright - MLDR O 4 Bright A_TossGib - MLDR P 4 Bright - MLDR Q 4 Bright A_TossGib - MLDR R 4 Bright - MLDR S 4 Bright A_TossGib - MLDR T 4 Bright - MLDR U 4 Bright A_TossGib - MLDR V 4 Bright A_SpawnItemEx("AlienSpectre2", 0, 0, 0, 0, 0, random[spectrespawn](0,255)*0.0078125, 0, SXF_NOCHECKPOSITION) - Stop - } -} - - -// The Bishop's missile ----------------------------------------------------- - -ACTOR BishopMissile -{ - Speed 20 - Radius 10 - Height 14 - Damage 10 - Projectile - +SEEKERMISSILE - +STRIFEDAMAGE - MaxStepHeight 4 - SeeSound "bishop/misl" - DeathSound "bishop/mislx" - States - { - Spawn: - MISS A 4 Bright A_RocketInFlight - MISS B 3 Bright A_Tracer2 - Loop - Death: - SMIS A 0 Bright A_SetTranslucent(1,1) - SMIS A 0 Bright // State left for savegame compatibility - SMIS A 5 Bright A_Explode(64,64,1,1) - SMIS B 5 Bright - SMIS C 4 Bright - SMIS DEFG 2 Bright - Stop - } -} - diff --git a/wadsrc/static/actors/strife/strifehumanoid.txt b/wadsrc/static/actors/strife/strifehumanoid.txt deleted file mode 100644 index 716806564..000000000 --- a/wadsrc/static/actors/strife/strifehumanoid.txt +++ /dev/null @@ -1,53 +0,0 @@ - -// Humanoid Base Class ------------------------------------------------------ - - -ACTOR StrifeHumanoid -{ - MaxStepHeight 16 - MaxDropoffHeight 32 - - CrushPainSound "misc/pcrush" - States - { - Burn: - BURN A 3 Bright A_PlaySoundEx("human/imonfire", "Voice") - BURN B 3 Bright A_DropFire - BURN C 3 Bright A_Wander - BURN D 3 Bright A_NoBlocking - BURN E 5 Bright A_DropFire - BURN FGH 5 Bright A_Wander - BURN I 5 Bright A_DropFire - BURN JKL 5 Bright A_Wander - BURN M 5 Bright A_DropFire - BURN N 5 Bright - BURN OPQPQ 5 Bright - BURN RSTU 7 Bright - BURN V -1 - Stop - Disintegrate: - DISR A 5 A_PlaySoundEx("misc/disruptordeath", "Voice") - DISR BC 5 - DISR D 5 A_NoBlocking - DISR EF 5 - DISR GHIJ 4 - MEAT D 700 - Stop - } -} - -// Fire Droplet ------------------------------------------------------------- - -ACTOR FireDroplet -{ - +NOBLOCKMAP - +NOCLIP - States - { - Spawn: - FFOT ABCD 9 Bright - Stop - } -} - - diff --git a/wadsrc/static/actors/strife/strifeitems.txt b/wadsrc/static/actors/strife/strifeitems.txt deleted file mode 100644 index 357d64ad5..000000000 --- a/wadsrc/static/actors/strife/strifeitems.txt +++ /dev/null @@ -1,519 +0,0 @@ -// Med patch ----------------------------------------------------------------- - -ACTOR MedPatch : HealthPickup -{ - Health 10 - +FLOORCLIP - +INVENTORY.INVBAR - Inventory.MaxAmount 20 - Tag "$TAG_MEDPATCH" - Inventory.Icon "I_STMP" - Inventory.PickupMessage "$TXT_MEDPATCH" - HealthPickup.Autouse 3 - States - { - Spawn: - STMP A -1 - Stop - } -} - - -// Medical Kit --------------------------------------------------------------- - -ACTOR MedicalKit : HealthPickup -{ - Health 25 - +FLOORCLIP - +INVENTORY.INVBAR - Inventory.MaxAmount 15 - Tag "$TAG_MEDICALKIT" - Inventory.Icon "I_MDKT" - Inventory.PickupMessage "$TXT_MEDICALKIT" - HealthPickup.Autouse 3 - States - { - Spawn: - MDKT A -1 - Stop - } -} - - -// Surgery Kit -------------------------------------------------------------- - -ACTOR SurgeryKit : HealthPickup -{ - +FLOORCLIP - +INVENTORY.INVBAR - Health -100 - Inventory.MaxAmount 5 - Tag "$TAG_SURGERYKIT" - Inventory.Icon "I_FULL" - Inventory.PickupMessage "$TXT_SURGERYKIT" - States - { - Spawn: - FULL AB 35 - Loop - } -} - - -// StrifeMap ---------------------------------------------------------------- - -ACTOR StrifeMap : MapRevealer -{ - +FLOORCLIP - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_STRIFEMAP" - States - { - Spawn: - SMAP AB 6 Bright - Loop - } -} - - -// Beldin's Ring ------------------------------------------------------------ - -ACTOR BeldinsRing : Inventory -{ - +NOTDMATCH - +FLOORCLIP - +INVENTORY.INVBAR - Tag "$TAG_BELDINSRING" - Inventory.Icon "I_RING" - Inventory.GiveQuest 1 - Inventory.PickupMessage "$TXT_BELDINSRING" - States - { - Spawn: - RING A -1 - Stop - } -} - - -// Offering Chalice --------------------------------------------------------- - -ACTOR OfferingChalice : Inventory -{ - +DROPPED - +FLOORCLIP - +INVENTORY.INVBAR - Radius 10 - Height 16 - Tag "$TAG_OFFERINGCHALICE" - Inventory.Icon "I_RELC" - Inventory.PickupMessage "$TXT_OFFERINGCHALICE" - Inventory.GiveQuest 2 - States - { - Spawn: - RELC A -1 - Stop - } -} - - -// Ear ---------------------------------------------------------------------- - -ACTOR Ear : Inventory -{ - +FLOORCLIP - +INVENTORY.INVBAR - Tag "$TAG_EAR" - Inventory.Icon "I_EARS" - Inventory.PickupMessage "$TXT_EAR" - Inventory.GiveQuest 9 - States - { - Spawn: - EARS A -1 - Stop - } -} - - -// Broken Power Coupling ---------------------------------------------------- - -ACTOR BrokenPowerCoupling : Inventory -{ - Health 40 - +DROPPED - +FLOORCLIP - +INVENTORY.INVBAR - Radius 16 - Height 16 - Tag "$TAG_BROKENCOUPLING" - Inventory.MaxAmount 1 - Inventory.Icon "I_COUP" - Inventory.PickupMessage "$TXT_BROKENCOUPLING" - Inventory.GiveQuest 8 - States - { - Spawn: - COUP C -1 - Stop - } -} - - -// Shadow Armor ------------------------------------------------------------- - -ACTOR ShadowArmor : PowerupGiver -{ - +FLOORCLIP - +VISIBILITYPULSE - +INVENTORY.INVBAR - -INVENTORY.FANCYPICKUPSOUND - RenderStyle Translucent - Tag "$TAG_SHADOWARMOR" - Inventory.MaxAmount 2 - Powerup.Type "Shadow" - Inventory.Icon "I_SHD1" - Inventory.PickupSound "misc/i_pkup" - Inventory.PickupMessage "$TXT_SHADOWARMOR" - States - { - Spawn: - SHD1 A -1 Bright - Stop - } -} - - -// Environmental suit ------------------------------------------------------- - -ACTOR EnvironmentalSuit : PowerupGiver -{ - +FLOORCLIP - +INVENTORY.INVBAR - -INVENTORY.FANCYPICKUPSOUND - Inventory.MaxAmount 5 - Powerup.Type "Mask" - Tag "$TAG_ENVSUIT" - Inventory.Icon "I_MASK" - Inventory.PickupSound "misc/i_pkup" - Inventory.PickupMessage "$TXT_ENVSUIT" - States - { - Spawn: - MASK A -1 - Stop - } -} - - -// Guard Uniform ------------------------------------------------------------ - -ACTOR GuardUniform : Inventory -{ - +FLOORCLIP - +INVENTORY.INVBAR - Tag "$TAG_GUARDUNIFORM" - Inventory.Icon "I_UNIF" - Inventory.PickupMessage "$TXT_GUARDUNIFORM" - Inventory.GiveQuest 15 - States - { - Spawn: - UNIF A -1 - Stop - } -} - - -// Officer's Uniform -------------------------------------------------------- - -ACTOR OfficersUniform : Inventory -{ - +FLOORCLIP - +INVENTORY.INVBAR - Tag "$TAG_OFFICERSUNIFORM" - Inventory.Icon "I_OFIC" - Inventory.PickupMessage "$TXT_OFFICERSUNIFORM" - States - { - Spawn: - OFIC A -1 - Stop - } -} - - -// Flame Thrower Parts ------------------------------------------------------ - -ACTOR FlameThrowerParts : Inventory -{ - +FLOORCLIP - +INVENTORY.INVBAR - Inventory.Icon "I_BFLM" - Tag "$TAG_FTHROWERPARTS" - Inventory.PickupMessage "$TXT_FTHROWERPARTS" - States - { - Spawn: - BFLM A -1 - Stop - } -} - -// InterrogatorReport ------------------------------------------------------- -// SCRIPT32 in strife0.wad has an Acolyte that drops this, but I couldn't -// find that Acolyte in the map. It seems to be totally unused in the -// final game. - -ACTOR InterrogatorReport : Inventory -{ - +FLOORCLIP - Tag "$TAG_REPORT" - Inventory.PickupMessage "$TXT_REPORT" - States - { - Spawn: - TOKN A -1 - Stop - } -} - - -// Info --------------------------------------------------------------------- - -ACTOR Info : Inventory -{ - +FLOORCLIP - +INVENTORY.INVBAR - Tag "$TAG_INFO" - Inventory.Icon "I_TOKN" - Inventory.PickupMessage "$TXT_INFO" - States - { - Spawn: - TOKN A -1 - Stop - } -} - - -// Targeter ----------------------------------------------------------------- - -ACTOR Targeter : PowerupGiver -{ - +FLOORCLIP - +INVENTORY.INVBAR - -INVENTORY.FANCYPICKUPSOUND - Tag "$TAG_TARGETER" - Powerup.Type "Targeter" - Inventory.MaxAmount 5 - Inventory.Icon "I_TARG" - Inventory.PickupSound "misc/i_pkup" - Inventory.PickupMessage "$TXT_TARGETER" - States - { - Spawn: - TARG A -1 - Stop - } -} - -// Communicator ----------------------------------------------------------------- - -ACTOR Communicator : Inventory -{ - +NOTDMATCH - Tag "$TAG_COMMUNICATOR" - Inventory.Icon "I_COMM" - Inventory.PickupSound "misc/p_pkup" - Inventory.PickupMessage "$TXT_COMMUNICATOR" - States - { - Spawn: - COMM A -1 - Stop - } -} - -// Degnin Ore --------------------------------------------------------------- - -ACTOR DegninOre : Inventory native -{ - Health 10 - Radius 16 - Height 16 - Inventory.MaxAmount 10 - +SOLID - +SHOOTABLE - +NOBLOOD - +FLOORCLIP - +INCOMBAT - +INVENTORY.INVBAR - Tag "$TAG_DEGNINORE" - DeathSound "ore/explode" - Inventory.Icon "I_XPRK" - Inventory.PickupMessage "$TXT_DEGNINORE" - States - { - Spawn: - XPRK A -1 - Stop - Death: - XPRK A 1 A_RemoveForceField - BNG3 A 0 A_SetTranslucent(1,1) - BNG3 A 0 A_Scream - BNG3 A 3 Bright A_Explode(192,192,1,1) - BNG3 BCDEFGH 3 Bright - Stop - } -} - -// Gun Training ------------------------------------------------------------- - -ACTOR GunTraining : Inventory -{ - +FLOORCLIP - +INVENTORY.INVBAR - +INVENTORY.UNDROPPABLE - Inventory.MaxAmount 100 - Tag "$TAG_GUNTRAINING" - Inventory.Icon "I_GUNT" - States - { - Spawn: - GUNT A -1 - Stop - } -} - -// Health Training ---------------------------------------------------------- - -ACTOR HealthTraining : Inventory native -{ - +FLOORCLIP - +INVENTORY.INVBAR - +INVENTORY.UNDROPPABLE - Inventory.MaxAmount 100 - Tag "$TAG_HEALTHTRAINING" - Inventory.Icon "I_HELT" - States - { - Spawn: - HELT A -1 - Stop - } -} - - - -// Scanner ------------------------------------------------------------------ - -ACTOR Scanner : PowerupGiver native -{ - +FLOORCLIP - +INVENTORY.FANCYPICKUPSOUND - Inventory.MaxAmount 1 - Tag "$TAG_SCANNER" - Inventory.Icon "I_PMUP" - Powerup.Type "Scanner" - Inventory.PickupSound "misc/i_pkup" - Inventory.PickupMessage "$TXT_SCANNER" - States - { - Spawn: - PMUP AB 6 - Loop - } -} - -// Prison Pass -------------------------------------------------------------- - -ACTOR PrisonPass : Key native -{ - Inventory.Icon "I_TOKN" - Tag "$TAG_PRISONPASS" - Inventory.PickupMessage "$TXT_PRISONPASS" - States - { - Spawn: - TOKN A -1 - Stop - } -} - -//--------------------------------------------------------------------------- -// Dummy items. They are just used by Strife to perform --------------------- -// actions and cannot be held. ---------------------------------------------- -//--------------------------------------------------------------------------- - -ACTOR DummyStrifeItem : Inventory native -{ - States - { - Spawn: - TOKN A -1 - Stop - } -} - -// Sound the alarm! --------------------------------------------------------- - -ACTOR RaiseAlarm : DummyStrifeItem native -{ - Tag "$TAG_ALARM" -} - -// Open door tag 222 -------------------------------------------------------- - -ACTOR OpenDoor222 : DummyStrifeItem native -{ -} - -// Close door tag 222 ------------------------------------------------------- - -ACTOR CloseDoor222 : DummyStrifeItem native -{ -} - -// Open door tag 224 -------------------------------------------------------- - -ACTOR OpenDoor224 : DummyStrifeItem native -{ -} - -// Ammo --------------------------------------------------------------------- - -ACTOR AmmoFillup : DummyStrifeItem native -{ - Tag "$TAG_AMMOFILLUP" -} - -// Health ------------------------------------------------------------------- - -ACTOR HealthFillup : DummyStrifeItem native -{ - Tag "$TAG_HEALTHFILLUP" -} - -// Upgrade Stamina ---------------------------------------------------------- - -ACTOR UpgradeStamina : DummyStrifeItem native -{ - Inventory.Amount 10 - Inventory.MaxAmount 100 -} - -// Upgrade Accuracy --------------------------------------------------------- - -ACTOR UpgradeAccuracy : DummyStrifeItem native -{ -} - -// Start a slideshow -------------------------------------------------------- - -ACTOR SlideshowStarter : DummyStrifeItem native -{ -} - - diff --git a/wadsrc/static/actors/strife/strifekeys.txt b/wadsrc/static/actors/strife/strifekeys.txt deleted file mode 100644 index 1a58505bb..000000000 --- a/wadsrc/static/actors/strife/strifekeys.txt +++ /dev/null @@ -1,460 +0,0 @@ -ACTOR StrifeKey : Key -{ - Radius 20 - Height 16 - +NOTDMATCH - +FLOORCLIP -} - -// Base Key ----------------------------------------------------------------- - -ACTOR BaseKey : StrifeKey -{ - Inventory.Icon "I_FUSL" - Tag "$TAG_BASEKEY" - Inventory.PickupMessage "$TXT_BASEKEY" - States - { - Spawn: - FUSL A -1 - Stop - } -} - - -// Govs Key ----------------------------------------------------------------- - -ACTOR GovsKey : StrifeKey -{ - Inventory.Icon "I_REBL" - Tag "$TAG_GOVSKEY" - Inventory.PickupMessage "$TXT_GOVSKEY" - States - { - Spawn: - REBL A -1 - Stop - } -} - - -// Passcard ----------------------------------------------------------------- - -ACTOR Passcard : StrifeKey -{ - Inventory.Icon "I_TPAS" - Tag "$TAG_PASSCARD" - Inventory.PickupMessage "$TXT_PASSCARD" - States - { - Spawn: - TPAS A -1 - Stop - } -} - - -// ID Badge ----------------------------------------------------------------- - -ACTOR IDBadge : StrifeKey -{ - Inventory.Icon "I_CRD1" - Tag "$TAG_IDBADGE" - Inventory.PickupMessage "$TXT_IDBADGE" - States - { - Spawn: - CRD1 A -1 - Stop - } -} - - -// Prison Key --------------------------------------------------------------- - -ACTOR PrisonKey : StrifeKey -{ - Inventory.Icon "I_PRIS" - Tag "$TAG_PRISONKEY" - Inventory.GiveQuest 11 - Inventory.PickupMessage "$TXT_PRISONKEY" - States - { - Spawn: - PRIS A -1 - Stop - } -} - - -// Severed Hand ------------------------------------------------------------- - -ACTOR SeveredHand : StrifeKey -{ - Inventory.Icon "I_HAND" - Tag "$TAG_SEVEREDHAND" - Inventory.GiveQuest 12 - Inventory.PickupMessage "$TXT_SEVEREDHAND" - States - { - Spawn: - HAND A -1 - Stop - } -} - - -// Power1 Key --------------------------------------------------------------- - -ACTOR Power1Key : StrifeKey -{ - Inventory.Icon "I_PWR1" - Tag "$TAG_POWER1KEY" - Inventory.PickupMessage "$TXT_POWER1KEY" - States - { - Spawn: - PWR1 A -1 - Stop - } -} - - -// Power2 Key --------------------------------------------------------------- - -ACTOR Power2Key : StrifeKey -{ - Inventory.Icon "I_PWR2" - Tag "$TAG_POWER2KEY" - Inventory.PickupMessage "$TXT_POWER2KEY" - States - { - Spawn: - PWR2 A -1 - Stop - } -} - - -// Power3 Key --------------------------------------------------------------- - -ACTOR Power3Key : StrifeKey -{ - Inventory.Icon "I_PWR3" - Tag "$TAG_POWER3KEY" - Inventory.PickupMessage "$TXT_POWER3KEY" - States - { - Spawn: - PWR3 A -1 - Stop - } -} - - -// Gold Key ----------------------------------------------------------------- - -ACTOR GoldKey : StrifeKey -{ - Inventory.Icon "I_KY1G" - Tag "$TAG_GOLDKEY" - Inventory.PickupMessage "$TXT_GOLDKEY" - States - { - Spawn: - KY1G A -1 - Stop - } -} - - -// ID Card ------------------------------------------------------------------ - -ACTOR IDCard : StrifeKey -{ - Inventory.Icon "I_CRD2" - Tag "$TAG_IDCARD" - Inventory.PickupMessage "$TXT_IDCARD" - States - { - Spawn: - CRD2 A -1 - Stop - } -} - - -// Silver Key --------------------------------------------------------------- - -ACTOR SilverKey : StrifeKey -{ - Inventory.Icon "I_KY2S" - Tag "$TAG_SILVERKEY" - Inventory.PickupMessage "$TXT_SILVERKEY" - States - { - Spawn: - KY2S A -1 - Stop - } -} - - -// Oracle Key --------------------------------------------------------------- - -ACTOR OracleKey : StrifeKey -{ - Inventory.Icon "I_ORAC" - Tag "$TAG_ORACLEKEY" - Inventory.PickupMessage "$TXT_ORACLEKEY" - States - { - Spawn: - ORAC A -1 - Stop - } -} - - -// Military ID -------------------------------------------------------------- - -ACTOR MilitaryID : StrifeKey -{ - Inventory.Icon "I_GYID" - Tag "$TAG_MILITARYID" - Inventory.PickupMessage "$TXT_MILITARYID" - States - { - Spawn: - GYID A -1 - Stop - } -} - - -// Order Key ---------------------------------------------------------------- - -ACTOR OrderKey : StrifeKey -{ - Inventory.Icon "I_FUBR" - Tag "$TAG_ORDERKEY" - Inventory.PickupMessage "$TXT_ORDERKEY" - States - { - Spawn: - FUBR A -1 - Stop - } -} - - -// Warehouse Key ------------------------------------------------------------ - -ACTOR WarehouseKey : StrifeKey -{ - Inventory.Icon "I_WARE" - Tag "$TAG_WAREHOUSEKEY" - Inventory.PickupMessage "$TXT_WAREHOUSEKEY" - States - { - Spawn: - WARE A -1 - Stop - } -} - - -// Brass Key ---------------------------------------------------------------- - -ACTOR BrassKey : StrifeKey -{ - Inventory.Icon "I_KY3B" - Tag "$TAG_BRASSKEY" - Inventory.PickupMessage "$TXT_BRASSKEY" - States - { - Spawn: - KY3B A -1 - Stop - } -} - - -// Red Crystal Key ---------------------------------------------------------- - -ACTOR RedCrystalKey : StrifeKey -{ - Inventory.Icon "I_RCRY" - Tag "$TAG_REDCRYSTALKEY" - Inventory.PickupMessage "$TXT_REDCRYSTAL" - States - { - Spawn: - RCRY A -1 Bright - Stop - } -} - - -// Blue Crystal Key --------------------------------------------------------- - -ACTOR BlueCrystalKey : StrifeKey -{ - Inventory.Icon "I_BCRY" - Tag "$TAG_BLUECRYSTALKEY" - Inventory.PickupMessage "$TXT_BLUECRYSTAL" - States - { - Spawn: - BCRY A -1 Bright - Stop - } -} - - -// Chapel Key --------------------------------------------------------------- - -ACTOR ChapelKey : StrifeKey -{ - Inventory.Icon "I_CHAP" - Tag "$TAG_CHAPELKEY" - Inventory.PickupMessage "$TXT_CHAPELKEY" - States - { - Spawn: - CHAP A -1 - Stop - } -} - - -// Catacomb Key ------------------------------------------------------------- - -ACTOR CatacombKey : StrifeKey -{ - Inventory.Icon "I_TUNL" - Tag "$TAG_CATACOMBKEY" - Inventory.GiveQuest 28 - Inventory.PickupMessage "$TXT_CATACOMBKEY" - States - { - Spawn: - TUNL A -1 - Stop - } -} - - -// Security Key ------------------------------------------------------------- - -ACTOR SecurityKey : StrifeKey -{ - Inventory.Icon "I_SECK" - Tag "$TAG_SECURITYKEY" - Inventory.PickupMessage "$TXT_SECURITYKEY" - States - { - Spawn: - SECK A -1 - Stop - } -} - - -// Core Key ----------------------------------------------------------------- - -ACTOR CoreKey : StrifeKey -{ - Inventory.Icon "I_GOID" - Tag "$TAG_COREKEY" - Inventory.PickupMessage "$TXT_COREKEY" - States - { - Spawn: - GOID A -1 - Stop - } -} - - -// Mauler Key --------------------------------------------------------------- - -ACTOR MaulerKey : StrifeKey -{ - Inventory.Icon "I_BLTK" - Tag "$TAG_MAULERKEY" - Inventory.PickupMessage "$TXT_MAULERKEY" - States - { - Spawn: - BLTK A -1 - Stop - } -} - - -// Factory Key -------------------------------------------------------------- - -ACTOR FactoryKey : StrifeKey -{ - Inventory.Icon "I_PROC" - Tag "$TAG_FACTORYKEY" - Inventory.PickupMessage "$TXT_FACTORYKEY" - States - { - Spawn: - PROC A -1 - Stop - } -} - - -// Mine Key ----------------------------------------------------------------- - -ACTOR MineKey : StrifeKey -{ - Inventory.Icon "I_MINE" - Tag "$TAG_MINEKEY" - Inventory.PickupMessage "$TXT_MINEKEY" - States - { - Spawn: - MINE A -1 - Stop - } -} - - -// New Key5 ----------------------------------------------------------------- - -ACTOR NewKey5 : StrifeKey -{ - Inventory.Icon "I_BLTK" - Tag "$TAG_NEWKEY5" - Inventory.PickupMessage "$TXT_NEWKEY5" - States - { - Spawn: - BLTK A -1 - Stop - } -} - - -// Oracle Pass -------------------------------------------------------------- - -ACTOR OraclePass : Inventory -{ - +INVENTORY.INVBAR - Inventory.Icon "I_OTOK" - Inventory.GiveQuest 18 - Inventory.PickupMessage "$TXT_ORACLEPASS" - Tag "$TAG_ORACLEPASS" - States - { - Spawn: - OTOK A -1 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/strifeplayer.txt b/wadsrc/static/actors/strife/strifeplayer.txt deleted file mode 100644 index 77135dcbf..000000000 --- a/wadsrc/static/actors/strife/strifeplayer.txt +++ /dev/null @@ -1,102 +0,0 @@ -// The player --------------------------------------------------------------- - -ACTOR StrifePlayer : PlayerPawn -{ - Health 100 - Radius 18 - Height 56 - Mass 100 - PainChance 255 - Speed 1 - MaxStepHeight 16 - CrushPainSound "misc/pcrush" - Player.DisplayName "Rebel" - Player.StartItem "PunchDagger" - Player.RunHealth 15 - Player.WeaponSlot 1, PunchDagger - Player.WeaponSlot 2, StrifeCrossbow2, StrifeCrossbow - Player.WeaponSlot 3, AssaultGun - Player.WeaponSlot 4, MiniMissileLauncher - Player.WeaponSlot 5, StrifeGrenadeLauncher2, StrifeGrenadeLauncher - Player.WeaponSlot 6, FlameThrower - Player.WeaponSlot 7, Mauler2, Mauler - Player.WeaponSlot 8, Sigil - - Player.ColorRange 128, 143 - Player.Colorset 0, "Brown", 0x80, 0x8F, 0x82 - Player.Colorset 1, "Red", 0x40, 0x4F, 0x42, 0x20, 0x3F, 0x00, 0x1F, 0xF1, 0xF6, 0xE0, 0xE5, 0xF7, 0xFB, 0xF1, 0xF5 - Player.Colorset 2, "Rust", 0xB0, 0xBF, 0xB2, 0x20, 0x3F, 0x00, 0x1F - Player.Colorset 3, "Gray", 0x10, 0x1F, 0x12, 0x20, 0x2F, 0xD0, 0xDF, 0x30, 0x3F, 0xD0, 0xDF - Player.Colorset 4, "Dark Green", 0x30, 0x3F, 0x32, 0x20, 0x2F, 0xD0, 0xDF, 0x30, 0x3F, 0xD0, 0xDF - - Player.Colorset 5, "Gold", 0x50, 0x5F, 0x52, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x80, 0x8F, 0xC0, 0xCF, 0xA0, 0xAF, 0xD0, 0xDF, 0xB0, 0xBF - Player.Colorset 6, "Bright Green", 0x60, 0x6F, 0x62, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x10, 0x1F, 0xC0, 0xCF, 0x20, 0x2F, 0xD0, 0xDF, 0x30, 0x3F - Player.Colorset 7, "Blue", 0x90, 0x9F, 0x92, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x40, 0x4F, 0xC1, 0xCF, 0x01, 0x0F, 0xC0,0xC0,1,1, 0xD0, 0xDF, 0x10, 0x1F - - action native A_ItBurnsItBurns(); - action native A_CrispyPlayer(); - action native A_HandLower(); - - States - { - Spawn: - PLAY A -1 - stop - See: - PLAY ABCD 4 - loop - Missile: - PLAY E 12 - goto Spawn - Melee: - PLAY F 6 - goto Missile - Pain: - PLAY Q 4 - PLAY Q 4 A_Pain - Goto Spawn - Death: - PLAY H 3 - PLAY I 3 A_PlayerScream - PLAY J 3 A_NoBlocking - PLAY KLMNO 4 - PLAY P -1 - Stop - XDeath: - RGIB A 5 A_TossGib - RGIB B 5 A_XScream - RGIB C 5 A_NoBlocking - RGIB DEFG 5 A_TossGib - RGIB H -1 A_TossGib - Burn: - BURN A 3 Bright A_ItBurnsItBurns - BURN B 3 Bright A_DropFire - BURN C 3 Bright A_Wander - BURN D 3 Bright A_NoBlocking - BURN E 5 Bright A_DropFire - BURN FGH 5 Bright A_Wander - BURN I 5 Bright A_DropFire - BURN JKL 5 Bright A_Wander - BURN M 5 Bright A_DropFire - BURN N 5 Bright A_CrispyPlayer - BURN OPQPQ 5 Bright - BURN RSTU 7 Bright - BURN V -1 - Stop - Disintegrate: - DISR A 5 A_PlaySoundEx("misc/disruptordeath", "Voice") - DISR BC 5 - DISR D 5 A_NoBlocking - DISR EF 5 - DISR GHIJ 4 - MEAT D -1 - Stop - Firehands: - WAVE ABCD 3 - Loop - Firehandslower: - WAVE ABCD 3 A_HandLower - Loop - } -} - diff --git a/wadsrc/static/actors/strife/strifestuff.txt b/wadsrc/static/actors/strife/strifestuff.txt deleted file mode 100644 index 3bbc1fb90..000000000 --- a/wadsrc/static/actors/strife/strifestuff.txt +++ /dev/null @@ -1,1723 +0,0 @@ -// Tank 1 Huge ------------------------------------------------------------ - -ACTOR Tank1 -{ - Radius 16 - Height 192 - +SOLID - States - { - Spawn: - TNK1 A 15 - TNK1 B 11 - TNK1 C 40 - Loop - } -} - -// Tank 2 Huge ------------------------------------------------------------ - -ACTOR Tank2 -{ - Radius 16 - Height 192 - +SOLID - States - { - Spawn: - TNK2 A 15 - TNK2 B 11 - TNK2 C 40 - Loop - } -} - -// Tank 3 Huge ------------------------------------------------------------ - -ACTOR Tank3 -{ - Radius 16 - Height 192 - +SOLID - States - { - Spawn: - TNK3 A 15 - TNK3 B 11 - TNK3 C 40 - Loop - } -} - -// Tank 4 ------------------------------------------------------------------- - -ACTOR Tank4 -{ - Radius 16 - Height 56 - +SOLID - States - { - Spawn: - TNK4 A 15 - TNK4 B 11 - TNK4 C 40 - Loop - } -} - -// Tank 5 ------------------------------------------------------------------- - -ACTOR Tank5 -{ - Radius 16 - Height 56 - +SOLID - States - { - Spawn: - TNK5 A 15 - TNK5 B 11 - TNK5 C 40 - Loop - } -} - -// Tank 6 ------------------------------------------------------------------- - -ACTOR Tank6 -{ - Radius 16 - Height 56 - +SOLID - States - { - Spawn: - TNK6 A 15 - TNK6 B 11 - TNK6 C 40 - Loop - } -} - -// Water Bottle ------------------------------------------------------------- - -ACTOR WaterBottle -{ - States - { - Spawn: - WATR A -1 - Stop - } -} - -// Mug ---------------------------------------------------------------------- - -ACTOR Mug -{ - States - { - Spawn: - MUGG A -1 - Stop - } -} - -// Wooden Barrel ------------------------------------------------------------ - -ACTOR WoodenBarrel -{ - Health 10 - Radius 10 - Height 32 - +SOLID +SHOOTABLE +NOBLOOD - +INCOMBAT - DeathSound "woodenbarrel/death" - States - { - Spawn: - BARW A -1 - Stop - Death: - BARW B 2 A_Scream - BARW C 2 - BARW D 2 A_NoBlocking - BARW EFG 2 - BARW H -1 - Stop - } -} - -// Strife's explosive barrel ------------------------------------------------ - -ACTOR ExplosiveBarrel2 -{ - Health 30 - Radius 10 - Height 32 - +SOLID +SHOOTABLE +NOBLOOD +OLDRADIUSDMG - DeathSound "world/barrelx" - +INCOMBAT - States - { - Spawn: - BART A -1 - Stop - Death: - BART B 2 Bright A_Scream - BART CD 2 Bright - BART E 2 Bright A_NoBlocking - BART F 2 Bright A_Explode(64, 64, 1, 1) - BART GHIJ 2 Bright - BART K 3 Bright - BART L -1 - Stop - } -} - -// Light Silver, Fluorescent ---------------------------------------------- - -ACTOR LightSilverFluorescent -{ - Radius 2.5 - Height 16 - +NOBLOCKMAP - +FIXMAPTHINGPOS - States - { - Spawn: - LITS A -1 Bright - Stop - } -} - -// Light Brown, Fluorescent ----------------------------------------------- - -ACTOR LightBrownFluorescent -{ - Radius 2.5 - Height 16 - +NOBLOCKMAP - +FIXMAPTHINGPOS - States - { - Spawn: - LITB A -1 Bright - Stop - } -} - -// Light Gold, Fluorescent ------------------------------------------------ - -ACTOR LightGoldFluorescent -{ - Radius 2.5 - Height 16 - +NOBLOCKMAP - +FIXMAPTHINGPOS - States - { - Spawn: - LITG A -1 Bright - Stop - } -} - -// Light Globe -------------------------------------------------------------- - -ACTOR LightGlobe -{ - Radius 16 - Height 16 - +SOLID - States - { - Spawn: - LITE A -1 Bright - Stop - } -} - -// Techno Pillar ------------------------------------------------------------ - -ACTOR PillarTechno -{ - Radius 20 - Height 128 - +SOLID - States - { - Spawn: - MONI A -1 - Stop - } -} - -// Aztec Pillar ------------------------------------------------------------- - -ACTOR PillarAztec -{ - Radius 16 - Height 128 - +SOLID - States - { - Spawn: - STEL A -1 - Stop - } -} - -// Damaged Aztec Pillar ----------------------------------------------------- - -ACTOR PillarAztecDamaged -{ - Radius 16 - Height 80 - +SOLID - States - { - Spawn: - STLA A -1 - Stop - } -} - -// Ruined Aztec Pillar ------------------------------------------------------ - -ACTOR PillarAztecRuined -{ - Radius 16 - Height 40 - +SOLID - States - { - Spawn: - STLE A -1 - Stop - } -} - -// Huge Tech Pillar --------------------------------------------------------- - -ACTOR PillarHugeTech -{ - Radius 24 - Height 192 - +SOLID - States - { - Spawn: - HUGE ABCD 4 - Loop - } -} - -// Alien Power Crystal in a Pillar ------------------------------------------ - -ACTOR PillarAlienPower -{ - Radius 24 - Height 192 - +SOLID - ActiveSound "ambient/alien2" - States - { - Spawn: - APOW A 4 A_LoopActiveSound - Loop - } -} - -// SStalactiteBig ----------------------------------------------------------- - -ACTOR SStalactiteBig -{ - Radius 16 - Height 54 - +SOLID +SPAWNCEILING +NOGRAVITY - States - { - Spawn: - STLG C -1 - Stop - } -} - -// SStalactiteSmall --------------------------------------------------------- - -ACTOR SStalactiteSmall -{ - Radius 16 - Height 40 - +SOLID +SPAWNCEILING +NOGRAVITY - States - { - Spawn: - STLG A -1 - Stop - } -} - -// SStalagmiteBig ----------------------------------------------------------- - -ACTOR SStalagmiteBig -{ - Radius 16 - Height 40 - +SOLID - States - { - Spawn: - STLG B -1 - Stop - } -} - -// Cave Pillar Top ---------------------------------------------------------- - -ACTOR CavePillarTop -{ - Radius 16 - Height 128 - +SOLID +SPAWNCEILING +NOGRAVITY - States - { - Spawn: - STLG D -1 - Stop - } -} - -// Cave Pillar Bottom ------------------------------------------------------- - -ACTOR CavePillarBottom -{ - Radius 16 - Height 128 - +SOLID - States - { - Spawn: - STLG E -1 - Stop - } -} - -// SStalagmiteSmall --------------------------------------------------------- - -ACTOR SStalagmiteSmall -{ - Radius 16 - Height 25 - +SOLID - States - { - Spawn: - STLG F -1 - Stop - } -} - -// Candle ------------------------------------------------------------------- - -ACTOR Candle -{ - States - { - Spawn: - KNDL A -1 Bright - Stop - } -} - -// StrifeCandelabra --------------------------------------------------------- - -ACTOR StrifeCandelabra -{ - Radius 16 - Height 40 - +SOLID - States - { - Spawn: - CLBR A -1 - Stop - } -} - -// Floor Water Drop --------------------------------------------------------- - -ACTOR WaterDropOnFloor -{ - +NOBLOCKMAP - ActiveSound "world/waterdrip" - States - { - Spawn: - DRIP A 6 A_FLoopActiveSound - DRIP BC 4 - DRIP D 4 A_FLoopActiveSound - DRIP EF 4 - DRIP G 4 A_FLoopActiveSound - DRIP H 4 - Loop - } -} - -// Waterfall Splash --------------------------------------------------------- - -ACTOR WaterfallSplash -{ - +NOBLOCKMAP - ActiveSound "world/waterfall" - States - { - Spawn: - SPLH ABCDEFG 4 - SPLH H 4 A_LoopActiveSound - Loop - } -} - -// Ceiling Water Drip ------------------------------------------------------- - -ACTOR WaterDrip -{ - Height 1 - +NOBLOCKMAP +SPAWNCEILING +NOGRAVITY - States - { - Spawn: - CDRP A 10 - CDRP BCD 8 - Loop - } -} - -// WaterFountain ------------------------------------------------------------ - -ACTOR WaterFountain -{ - +NOBLOCKMAP - ActiveSound "world/watersplash" - States - { - Spawn: - WTFT ABC 4 - WTFT D 4 A_LoopActiveSound - Loop - } -} - -// Hearts in Tank ----------------------------------------------------------- - -ACTOR HeartsInTank -{ - Radius 16 - Height 56 - +SOLID - States - { - Spawn: - HERT ABC 4 Bright - Loop - } -} - -// Teleport Swirl ----------------------------------------------------------- - -ACTOR TeleportSwirl -{ - +NOBLOCKMAP - RenderStyle Add - Alpha 0.25 - States - { - Spawn: - TELP ABCD 3 Bright - Loop - } -} - -// Dead Player -------------------------------------------------------------- -// Strife's disappeared. This one doesn't. - -ACTOR DeadStrifePlayer -{ - States - { - Spawn: - PLAY P 700 - RGIB H -1 - Stop - } -} - -// Dead Peasant ------------------------------------------------------------- -// Unlike Strife's, this one does not turn into gibs and disappear. - -ACTOR DeadPeasant -{ - States - { - Spawn: - PEAS N -1 - Stop - } -} - -// Dead Acolyte ------------------------------------------------------------- -// Unlike Strife's, this one does not turn into gibs and disappear. - -ACTOR DeadAcolyte -{ - States - { - Spawn: - AGRD N -1 - Stop - } -} - -// Dead Reaver -------------------------------------------------------------- - -ACTOR DeadReaver -{ - States - { - Spawn: - ROB1 R -1 - Stop - } -} - -// Dead Rebel --------------------------------------------------------------- - -ACTOR DeadRebel -{ - States - { - Spawn: - HMN1 N -1 - Stop - } -} - -// Sacrificed Guy ----------------------------------------------------------- - -ACTOR SacrificedGuy -{ - States - { - Spawn: - SACR A -1 - Stop - } -} - -// Pile of Guts ------------------------------------------------------------- - -ACTOR PileOfGuts -{ - // Strife used a doomednum, which is the same as the Aztec Pillar. Since - // the pillar came first in the mobjinfo list, you could not spawn this - // in a map. Pity. - States - { - Spawn: - DEAD A -1 - Stop - } -} - -// Burning Barrel ----------------------------------------------------------- - -ACTOR StrifeBurningBarrel -{ - Radius 16 - Height 48 - +SOLID - States - { - Spawn: - BBAR ABCD 4 Bright - Loop - } -} - -// Burning Bowl ----------------------------------------------------------- - -ACTOR BurningBowl -{ - Radius 16 - Height 16 - +SOLID - ActiveSound "world/smallfire" - States - { - Spawn: - BOWL ABCD 4 Bright - Loop - } -} - -// Burning Brazier ----------------------------------------------------------- - -ACTOR BurningBrazier -{ - Radius 10 - Height 32 - +SOLID - ActiveSound "world/smallfire" - States - { - Spawn: - BRAZ ABCD 4 Bright - Loop - } -} - -// Small Torch Lit -------------------------------------------------------- - -ACTOR SmallTorchLit -{ - Radius 2.5 - Height 16 - +NOBLOCKMAP - +FIXMAPTHINGPOS - - // It doesn't have any action functions, so how does it use this sound? - ActiveSound "world/smallfire" - States - { - Spawn: - TRHL ABCD 4 Bright - Loop - } -} - -// Small Torch Unlit -------------------------------------------------------- - -ACTOR SmallTorchUnlit -{ - Radius 2.5 - Height 16 - +NOBLOCKMAP - +FIXMAPTHINGPOS - States - { - Spawn: - TRHO A -1 - Stop - } -} - -// Ceiling Chain ------------------------------------------------------------ - -ACTOR CeilingChain -{ - Radius 20 - Height 93 - +NOBLOCKMAP +SPAWNCEILING +NOGRAVITY - States - { - Spawn: - CHAN A -1 - Stop - } -} - -// Cage Light --------------------------------------------------------------- - -ACTOR CageLight -{ - // No, it's not bright even though it's a light. - Height 3 - +NOBLOCKMAP +SPAWNCEILING +NOGRAVITY - States - { - Spawn: - CAGE A -1 - Stop - } -} - -// Statue ------------------------------------------------------------------- - -ACTOR Statue -{ - Radius 20 - Height 64 - +SOLID - States - { - Spawn: - STAT A -1 - Stop - } -} - -// Ruined Statue ------------------------------------------------------------ - -ACTOR StatueRuined -{ - Radius 20 - Height 56 - +SOLID - States - { - Spawn: - DSTA A -1 - Stop - } -} - -// Medium Torch ------------------------------------------------------------- - -ACTOR MediumTorch -{ - Radius 4 - Height 72 - +SOLID - States - { - Spawn: - LTRH ABCD 4 - Loop - } -} - -// Outside Lamp ------------------------------------------------------------- - -ACTOR OutsideLamp -{ - // No, it's not bright. - Radius 3 - Height 80 - +SOLID - States - { - Spawn: - LAMP A -1 - Stop - } -} - -// Pole Lantern ------------------------------------------------------------- - -ACTOR PoleLantern -{ - // No, it's not bright. - Radius 3 - Height 80 - +SOLID - States - { - Spawn: - LANT A -1 - Stop - } -} - -// Rock 1 ------------------------------------------------------------------- - -ACTOR SRock1 -{ - +NOBLOCKMAP - States - { - Spawn: - ROK1 A -1 - Stop - } -} - -// Rock 2 ------------------------------------------------------------------- - -ACTOR SRock2 -{ - +NOBLOCKMAP - States - { - Spawn: - ROK2 A -1 - Stop - } -} - -// Rock 3 ------------------------------------------------------------------- - -ACTOR SRock3 -{ - +NOBLOCKMAP - States - { - Spawn: - ROK3 A -1 - Stop - } -} - -// Rock 4 ------------------------------------------------------------------- - -ACTOR SRock4 -{ - +NOBLOCKMAP - States - { - Spawn: - ROK4 A -1 - Stop - } -} - -// Stick in Water ----------------------------------------------------------- - -ACTOR StickInWater -{ - +NOBLOCKMAP - +FLOORCLIP - ActiveSound "world/river" - States - { - Spawn: - LOGW ABCD 5 A_LoopActiveSound - Loop - } -} - -// Rubble 1 ----------------------------------------------------------------- - -ACTOR Rubble1 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB1 A -1 - Stop - } -} - -// Rubble 2 ----------------------------------------------------------------- - -ACTOR Rubble2 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB2 A -1 - Stop - } -} - -// Rubble 3 ----------------------------------------------------------------- - -ACTOR Rubble3 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB3 A -1 - Stop - } -} - -// Rubble 4 ----------------------------------------------------------------- - -ACTOR Rubble4 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB4 A -1 - Stop - } -} - -// Rubble 5 ----------------------------------------------------------------- - -ACTOR Rubble5 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB5 A -1 - Stop - } -} - -// Rubble 6 ----------------------------------------------------------------- - -ACTOR Rubble6 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB6 A -1 - Stop - } -} - -// Rubble 7 ----------------------------------------------------------------- - -ACTOR Rubble7 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB7 A -1 - Stop - } -} - -// Rubble 8 ----------------------------------------------------------------- - -ACTOR Rubble8 -{ - +NOBLOCKMAP +NOCLIP - States - { - Spawn: - RUB8 A -1 - Stop - } -} - -// Surgery Crab ------------------------------------------------------------- - -ACTOR SurgeryCrab -{ - +SOLID +SPAWNCEILING +NOGRAVITY - Radius 20 - Height 16 - States - { - Spawn: - CRAB A -1 - Stop - } -} - -// Large Torch -------------------------------------------------------------- - -ACTOR LargeTorch -{ - Radius 10 - Height 72 - +SOLID - ActiveSound "world/smallfire" - States - { - Spawn: - LMPC ABCD 4 Bright - Loop - } -} - -// Huge Torch -------------------------------------------------------------- - -ACTOR HugeTorch -{ - Radius 10 - Height 80 - +SOLID - ActiveSound "world/smallfire" - States - { - Spawn: - LOGS ABCD 4 - Loop - } -} - -// Palm Tree ---------------------------------------------------------------- - -ACTOR PalmTree -{ - Radius 15 - Height 109 - +SOLID - States - { - Spawn: - TREE A -1 - Stop - } -} - -// Big Tree ---------------------------------------------------------------- - -ACTOR BigTree2 -{ - Radius 15 - Height 109 - +SOLID - States - { - Spawn: - TREE B -1 - Stop - } -} - -// Potted Tree ---------------------------------------------------------------- - -ACTOR PottedTree -{ - Radius 15 - Height 64 - +SOLID - States - { - Spawn: - TREE C -1 - Stop - } -} - -// Tree Stub ---------------------------------------------------------------- - -ACTOR TreeStub -{ - Radius 15 - Height 80 - +SOLID - States - { - Spawn: - TRET A -1 - Stop - } -} - -// Short Bush --------------------------------------------------------------- - -ACTOR ShortBush -{ - Radius 15 - Height 40 - +SOLID - States - { - Spawn: - BUSH A -1 - Stop - } -} - -// Tall Bush --------------------------------------------------------------- - -ACTOR TallBush -{ - Radius 20 - Height 64 - +SOLID - States - { - Spawn: - SHRB A -1 - Stop - } -} - -// Chimney Stack ------------------------------------------------------------ - -ACTOR ChimneyStack -{ - Radius 20 - Height 64 // This height does not fit the sprite - +SOLID - States - { - Spawn: - STAK A -1 - Stop - } -} - -// Barricade Column --------------------------------------------------------- - -ACTOR BarricadeColumn -{ - Radius 16 - Height 128 - +SOLID - States - { - Spawn: - BARC A -1 - Stop - } -} - -// Pot ---------------------------------------------------------------------- - -ACTOR Pot -{ - Radius 12 - Height 24 - +SOLID - States - { - Spawn: - VAZE A -1 - Stop - } -} - -// Pitcher ------------------------------------------------------------------ - -ACTOR Pitcher -{ - Radius 12 - Height 32 - +SOLID - States - { - Spawn: - VAZE B -1 - Stop - } -} - -// Stool -------------------------------------------------------------------- - -ACTOR Stool -{ - Radius 6 - Height 24 - +SOLID - States - { - Spawn: - STOL A -1 - Stop - } -} - -// Metal Pot ---------------------------------------------------------------- - -ACTOR MetalPot -{ - +NOBLOCKMAP - States - { - Spawn: - MPOT A -1 - Stop - } -} - -// Tub ---------------------------------------------------------------------- - -ACTOR Tub -{ - +NOBLOCKMAP - States - { - Spawn: - TUB1 A -1 - Stop - } -} - -// Anvil -------------------------------------------------------------------- - -ACTOR Anvil -{ - Radius 16 - Height 32 - +SOLID - States - { - Spawn: - ANVL A -1 - Stop - } -} - -// Silver Tech Lamp ---------------------------------------------------------- - -ACTOR TechLampSilver -{ - Radius 11 - Height 64 - +SOLID - States - { - Spawn: - TECH A -1 - Stop - } -} - -// Brass Tech Lamp ---------------------------------------------------------- - -ACTOR TechLampBrass -{ - Radius 8 - Height 64 - +SOLID - States - { - Spawn: - TECH B -1 - Stop - } -} - -// Tray -------------------------------------------------------------------- - -ACTOR Tray -{ - Radius 24 - Height 40 - +SOLID - States - { - Spawn: - TRAY A -1 - Stop - } -} - -// AmmoFiller --------------------------------------------------------------- - -ACTOR AmmoFiller -{ - Radius 12 - Height 24 - +SOLID - States - { - Spawn: - AFED A -1 - Stop - } -} - -// Sigil Banner ------------------------------------------------------------- - -ACTOR SigilBanner -{ - Radius 24 - Height 96 - +NOBLOCKMAP // I take it this was once solid, yes? - States - { - Spawn: - SBAN A -1 - Stop - } -} - -// RebelBoots --------------------------------------------------------------- - -ACTOR RebelBoots -{ - +NOBLOCKMAP - States - { - Spawn: - BOTR A -1 - Stop - } -} - -// RebelHelmet -------------------------------------------------------------- - -ACTOR RebelHelmet -{ - +NOBLOCKMAP - States - { - Spawn: - HATR A -1 - Stop - } -} - -// RebelShirt --------------------------------------------------------------- - -ACTOR RebelShirt -{ - +NOBLOCKMAP - States - { - Spawn: - TOPR A -1 - Stop - } -} - -// Alien Bubble Column ------------------------------------------------------ - -ACTOR AlienBubbleColumn -{ - Radius 16 - Height 128 - +SOLID - ActiveSound "ambient/alien5" - States - { - Spawn: - BUBB A 4 A_LoopActiveSound - Loop - } -} - -// Alien Floor Bubble ------------------------------------------------------- - -ACTOR AlienFloorBubble -{ - Radius 16 - Height 72 - +SOLID - ActiveSound "ambient/alien6" - States - { - Spawn: - BUBF A 4 A_LoopActiveSound - Loop - } -} - -// Alien Ceiling Bubble ----------------------------------------------------- - -ACTOR AlienCeilingBubble -{ - Radius 16 - Height 72 - +SOLID +SPAWNCEILING +NOGRAVITY - ActiveSound "ambient/alien4" - States - { - Spawn: - BUBC A 4 A_LoopActiveSound - Loop - } -} - -// Alien Asp Climber -------------------------------------------------------- - -ACTOR AlienAspClimber -{ - Radius 16 - Height 128 - +SOLID - ActiveSound "ambient/alien3" - States - { - Spawn: - ASPR A 4 A_LoopActiveSound - Loop - } -} - -// Alien Spider Light ------------------------------------------------------- - -ACTOR AlienSpiderLight -{ - Radius 32 - Height 56 - +SOLID - ActiveSound "ambient/alien1" - States - { - Spawn: - SPDL ABC 5 A_LoopActiveSound - Loop - } -} - -// Target Practice ----------------------------------------------------------- - -ACTOR TargetPractice -{ - Health 99999999 - PainChance 255 - Radius 10 - Height 72 - Mass 9999999 - +SOLID +SHOOTABLE +NOBLOOD - +INCOMBAT +NODAMAGE - PainSound "misc/metalhit" - States - { - Spawn: - HOGN A 2 A_CheckTerrain - Loop - Pain: - HOGN B 1 A_CheckTerrain - HOGN C 1 A_Pain - Goto Spawn - } -} - -// Force Field Guard -------------------------------------------------------- - -ACTOR ForceFieldGuard native -{ - Health 10 - Radius 2 - Height 1 - Mass 10000 - +SHOOTABLE - +NOSECTOR - +NOBLOOD - +INCOMBAT - States - { - Spawn: - TNT1 A -1 - Stop - Death: - TNT1 A 1 A_RemoveForceField - Stop - } -} - -// Kneeling Guy ------------------------------------------------------------- - -ACTOR KneelingGuy -{ - Health 51 - Painchance 255 - Radius 6 - Height 17 - Mass 50000 - +SOLID - +SHOOTABLE - +NOBLOOD - +ISMONSTER - +INCOMBAT - PainSound "misc/static" - DeathSound "misc/static" - ActiveSound "misc/chant" - states - { - Spawn: - See: - NEAL A 15 A_LoopActiveSound - NEAL B 40 A_LoopActiveSound - Loop - Pain: - NEAL C 5 A_SetShadow - NEAL B 4 A_Pain - NEAL C 5 A_ClearShadow - Goto Spawn - Wound: - NEAL B 6 - NEAL C 13 A_GetHurt - Loop - Death: - NEAL D 5 - NEAL E 5 A_Scream - NEAL F 6 - NEAL G 5 A_NoBlocking - NEAL H 5 - NEAL I 6 - NEAL J -1 - Stop - } - - -} - -// Klaxon Warning Light ----------------------------------------------------- - -ACTOR KlaxonWarningLight -{ - ReactionTime 60 - Radius 5 - +NOBLOCKMAP +AMBUSH - +SPAWNCEILING +NOGRAVITY - +FIXMAPTHINGPOS +NOSPLASHALERT - +SYNCHRONIZED - States - { - Spawn: - KLAX A 5 A_TurretLook - Loop - See: - KLAX B 6 A_KlaxonBlare - KLAX C 60 - Loop - } - -} - -// CeilingTurret ------------------------------------------------------------ - -ACTOR CeilingTurret -{ - Health 125 - Speed 0 - Painchance 0 - Mass 10000000 - Monster - -SOLID - -CANPASS - +AMBUSH - +SPAWNCEILING - +NOGRAVITY - +NOBLOOD - +NOSPLASHALERT - +DONTFALL - MinMissileChance 150 - DeathSound "turret/death" - States - { - Spawn: - TURT A 5 A_TurretLook - Loop - See: - TURT A 2 A_Chase - Loop - Missile: - Pain: - TURT B 4 Slow A_ShootGun - TURT D 3 Slow A_SentinelRefire - TURT A 4 A_SentinelRefire - Loop - Death: - BALL A 6 Bright A_Scream - BALL BCDE 6 Bright - TURT C -1 - Stop - } -} - - -// Power Coupling ----------------------------------------------------------- - -ACTOR PowerCoupling native -{ - Health 40 - Radius 17 - Height 64 - Mass 999999 - +SOLID - +SHOOTABLE - +DROPPED - +NOBLOOD - +NOTDMATCH - +INCOMBAT - States - { - Spawn: - COUP AB 5 - Loop - } -} - -// Gibs for things that bleed ----------------------------------------------- - -ACTOR Meat native -{ - +NOCLIP - States - { - Spawn: - MEAT A 700 - Stop - MEAT B 700 - Stop - MEAT C 700 - Stop - MEAT D 700 - Stop - MEAT E 700 - Stop - MEAT F 700 - Stop - MEAT G 700 - Stop - MEAT H 700 - Stop - MEAT I 700 - Stop - MEAT J 700 - Stop - MEAT K 700 - Stop - MEAT L 700 - Stop - MEAT M 700 - Stop - MEAT N 700 - Stop - MEAT O 700 - Stop - MEAT P 700 - Stop - MEAT Q 700 - Stop - MEAT R 700 - Stop - MEAT S 700 - Stop - MEAT T 700 - Stop - } -} - -// Gibs for things that don't bleed ----------------------------------------- - -ACTOR Junk : Meat -{ - States - { - Spawn: - JUNK A 700 - Stop - JUNK B 700 - Stop - JUNK C 700 - Stop - JUNK D 700 - Stop - JUNK E 700 - Stop - JUNK F 700 - Stop - JUNK G 700 - Stop - JUNK H 700 - Stop - JUNK I 700 - Stop - JUNK J 700 - Stop - JUNK K 700 - Stop - JUNK L 700 - Stop - JUNK M 700 - Stop - JUNK N 700 - Stop - JUNK O 700 - Stop - JUNK P 700 - Stop - JUNK Q 700 - Stop - JUNK R 700 - Stop - JUNK S 700 - Stop - JUNK T 700 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/strifeweapons.txt b/wadsrc/static/actors/strife/strifeweapons.txt deleted file mode 100644 index b807f110a..000000000 --- a/wadsrc/static/actors/strife/strifeweapons.txt +++ /dev/null @@ -1,813 +0,0 @@ - -ACTOR StrifeWeapon : Weapon -{ - Weapon.Kickback 100 -} - -// Same as the bullet puff for Doom ----------------------------------------- - -ACTOR StrifePuff -{ - +NOBLOCKMAP - +NOGRAVITY - +ALLOWPARTICLES - RenderStyle Translucent - Alpha 0.25 - - states - { - Spawn: - POW3 ABCDEFGH 3 - Stop - Crash: - PUFY A 4 Bright - PUFY BCD 4 - Stop - } -} - - -// A spark when you hit something that doesn't bleed ------------------------ -// Only used by the dagger. - -ACTOR StrifeSpark : StrifePuff -{ - RenderStyle Add - States - { - Crash: - POW2 ABCD 4 - Stop - } -} - -// Punch Dagger ------------------------------------------------------------- - -ACTOR PunchDagger : StrifeWeapon -{ - Weapon.SelectionOrder 3900 - +WEAPON.NOALERT - Obituary "$OB_MPPUNCHDAGGER" - Tag "$TAG_PUNCHDAGGER" - - action native A_JabDagger (); - - States - { - Ready: - PNCH A 1 A_WeaponReady - Loop - Deselect: - PNCH A 1 A_Lower - Loop - Select: - PNCH A 1 A_Raise - Loop - Fire: - PNCH B 4 - PNCH C 4 A_JabDagger - PNCH D 5 - PNCH C 4 - PNCH B 5 A_ReFire - Goto Ready - } - -} - - -// The base for Strife projectiles that die with ZAP1 ----------------------- - -ACTOR StrifeZap1 -{ - +NOBLOCKMAP - +NOGRAVITY - +DROPOFF - States - { - Spawn: - Death: - ZAP1 A 3 A_AlertMonsters - ZAP1 BCDEFE 3 - ZAP1 DCB 2 - ZAP1 A 1 - Stop - } -} - - -// Electric Bolt ------------------------------------------------------------ - -ACTOR ElectricBolt : StrifeZap1 -{ - Speed 30 - Radius 10 - Height 10 - Damage 10 - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - SeeSound "misc/swish" - ActiveSound "misc/swish" - DeathSound "weapons/xbowhit" - Obituary "$OB_MPELECTRICBOLT" - States - { - Spawn: - AROW A 10 A_LoopActiveSound - Loop - } -} - - -// Poison Bolt -------------------------------------------------------------- - -ACTOR PoisonBolt native -{ - Speed 30 - Radius 10 - Height 10 - Damage 500 - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - SeeSound "misc/swish" - ActiveSound "misc/swish" - Obituary "$OB_MPPOISONBOLT" - States - { - Spawn: - ARWP A 10 A_LoopActiveSound - Loop - Death: - AROW A 1 - Stop - } -} - - -// Strife's Crossbow -------------------------------------------------------- - -ACTOR StrifeCrossbow : StrifeWeapon -{ - +FLOORCLIP - Weapon.SelectionOrder 1200 - +WEAPON.NOALERT - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 8 - Weapon.AmmoType1 "ElectricBolts" - Weapon.SisterWeapon "StrifeCrossbow2" - Inventory.PickupMessage "$TXT_STRIFECROSSBOW" - Tag "$TAG_STRIFECROSSBOW1" - Inventory.Icon "CBOWA0" - - action native A_ClearFlash (); - action native A_ShowElectricFlash (); - action native A_FireArrow (class proj); - - states - { - Spawn: - CBOW A -1 - Stop - Ready: - XBOW A 0 A_ShowElectricFlash - XBOW A 1 A_WeaponReady - Wait - Deselect: - XBOW A 1 A_Lower - Loop - Select: - XBOW A 1 A_Raise - Loop - Fire: - XBOW A 3 A_ClearFlash - XBOW B 6 A_FireArrow("ElectricBolt") - XBOW C 4 - XBOW D 6 - XBOW E 3 - XBOW F 5 - XBOW G 0 A_ShowElectricFlash - XBOW G 5 A_CheckReload - Goto Ready+1 - Flash: - XBOW KLM 5 - Loop - } -} - - -ACTOR StrifeCrossbow2 : StrifeCrossbow -{ - Weapon.SelectionOrder 2700 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 0 - Weapon.AmmoType1 "PoisonBolts" - Weapon.SisterWeapon "StrifeCrossbow" - Tag "$TAG_STRIFECROSSBOW2" - - States - { - Ready: - XBOW H 1 A_WeaponReady - Loop - Deselect: - XBOW H 1 A_Lower - Loop - Select: - XBOW H 1 A_Raise - Loop - Fire: - XBOW H 3 - XBOW B 6 A_FireArrow("PoisonBolt") - XBOW C 4 - XBOW D 6 - XBOW E 3 - XBOW I 5 - XBOW J 5 A_CheckReload - Goto Ready - Flash: - Stop - } -} - -// Assault Gun -------------------------------------------------------------- - -actor AssaultGun : StrifeWeapon -{ - +FLOORCLIP - Weapon.SelectionOrder 600 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 20 - Weapon.AmmoType1 "ClipOfBullets" - Inventory.Icon "RIFLA0" - Tag "$TAG_ASSAULTGUN" - Inventory.PickupMessage "$TXT_ASSAULTGUN" - Obituary "$OB_MPASSAULTGUN" - States - { - Spawn: - RIFL A -1 - Stop - Ready: - RIFG A 1 A_WeaponReady - Loop - Deselect: - RIFG B 1 A_Lower - Loop - Select: - RIFG A 1 A_Raise - Loop - Fire: - RIFF AB 3 A_FireAssaultGun - RIFG D 3 A_FireAssaultGun - RIFG C 0 A_ReFire - RIFG B 2 A_Light0 - Goto Ready - } -} - - -// Standing variant of the assault gun -------------------------------------- - -ACTOR AssaultGunStanding : WeaponGiver -{ - DropItem "AssaultGun" - Inventory.PickupMessage "$TXT_ASSAULTGUN" - States - { - Spawn: - RIFL B -1 - Stop - } -} - - -// Mini-Missile Launcher ---------------------------------------------------- - - -ACTOR MiniMissileLauncher : StrifeWeapon -{ - +FLOORCLIP - Weapon.SelectionOrder 1800 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 8 - Weapon.AmmoType1 "MiniMissiles" - Inventory.Icon "MMSLA0" - Tag "$TAG_MMLAUNCHER" - Inventory.PickupMessage "$TXT_MMLAUNCHER" - - action native A_FireMiniMissile (); - - States - { - Spawn: - MMSL A -1 - Stop - Ready: - MMIS A 1 A_WeaponReady - Loop - Deselect: - MMIS A 1 A_Lower - Loop - Select: - MMIS A 1 A_Raise - Loop - Fire: - MMIS A 4 A_FireMiniMissile - MMIS B 4 A_Light1 - MMIS C 5 Bright - MMIS D 2 Bright A_Light2 - MMIS E 2 Bright - MMIS F 2 Bright A_Light0 - MMIS F 0 A_ReFire - Goto Ready - } -} - - -// Rocket Trail ------------------------------------------------------------- - -ACTOR RocketTrail -{ - +NOBLOCKMAP - +NOGRAVITY - RenderStyle Translucent - Alpha 0.25 - SeeSound "misc/missileinflight" - States - { - Spawn: - PUFY BCBCD 4 - Stop - } -} - -// Rocket Puff -------------------------------------------------------------- - -ACTOR MiniMissilePuff : StrifePuff -{ - -ALLOWPARTICLES - States - { - Spawn: - Goto Crash - } -} - -// Mini Missile ------------------------------------------------------------- - -ACTOR MiniMissile -{ - Speed 20 - Radius 10 - Height 14 - Damage 10 - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - SeeSound "weapons/minimissile" - DeathSound "weapons/minimissilehit" - Obituary "$OB_MPMINIMISSILELAUNCHER" - States - { - Spawn: - MICR A 6 Bright A_RocketInFlight - Loop - Death: - SMIS A 0 Bright A_SetTranslucent(1,1) - SMIS A 0 Bright // State left for savegame compatibility - SMIS A 5 Bright A_Explode(64,64,1,1) - SMIS B 5 Bright - SMIS C 4 Bright - SMIS DEFG 2 Bright - Stop - } -} - -// Flame Thrower ------------------------------------------------------------ - -ACTOR FlameThrower : StrifeWeapon -{ - +FLOORCLIP - Weapon.SelectionOrder 2100 - Weapon.Kickback 0 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 100 - Weapon.UpSound "weapons/flameidle" - Weapon.ReadySound "weapons/flameidle" - Weapon.AmmoType1 "EnergyPod" - Inventory.Icon "FLAMA0" - Tag "$TAG_FLAMER" - Inventory.PickupMessage "$TXT_FLAMER" - - action native A_FireFlamer (); - - States - { - Spawn: - FLAM A -1 - Stop - Ready: - FLMT AB 3 A_WeaponReady - Loop - Deselect: - FLMT A 1 A_Lower - Loop - Select: - FLMT A 1 A_Raise - Loop - Fire: - FLMF A 2 A_FireFlamer - FLMF B 3 A_ReFire - Goto Ready - } -} - - -// Flame Thrower Projectile ------------------------------------------------- - -ACTOR FlameMissile -{ - Speed 15 - Height 11 - Radius 8 - Mass 10 - Damage 4 - DamageType Fire - ReactionTime 8 - Projectile - -NOGRAVITY - +STRIFEDAMAGE - MaxStepHeight 4 - RenderStyle Add - SeeSound "weapons/flamethrower" - Obituary "$OB_MPFLAMETHROWER" - - action native A_FlameDie (); - - States - { - Spawn: - FRBL AB 3 Bright - FRBL C 3 Bright A_Countdown - Loop - Death: - FRBL D 5 Bright A_FlameDie - FRBL EFGHI 5 Bright - Stop - } - -} - - -// Mauler ------------------------------------------------------------------- -// The scatter version - -ACTOR Mauler : StrifeWeapon -{ - +FLOORCLIP - Weapon.SelectionOrder 300 - Weapon.AmmoUse1 20 - Weapon.AmmoGive1 40 - Weapon.AmmoType1 "EnergyPod" - Weapon.SisterWeapon "Mauler2" - Inventory.Icon "TRPDA0" - Tag "$TAG_MAULER1" - Inventory.PickupMessage "$TXT_MAULER" - Obituary "$OB_MPMAULER1" - - action native A_FireMauler1 (); - - States - { - Ready: - MAUL FGHA 6 A_WeaponReady - Loop - Deselect: - MAUL A 1 A_Lower - Loop - Select: - MAUL A 1 A_Raise - Loop - Fire: - BLSF A 5 Bright A_FireMauler1 - MAUL B 3 Bright A_Light1 - MAUL C 2 A_Light2 - MAUL DE 2 - MAUL A 7 A_Light0 - MAUL H 7 - MAUL G 7 A_CheckReload - Goto Ready - Spawn: - TRPD A -1 - Stop - } -} - - -// Mauler Torpedo version --------------------------------------------------- - -ACTOR Mauler2 : Mauler -{ - Weapon.SelectionOrder 3300 - Weapon.AmmoUse1 30 - Weapon.AmmoGive1 0 - Weapon.AmmoType1 "EnergyPod" - Weapon.SisterWeapon "Mauler" - Tag "$TAG_MAULER2" - - action native A_FireMauler2Pre (); - action native A_FireMauler2 (); - - States - { - Ready: - MAUL IJKL 7 A_WeaponReady - Loop - Deselect: - MAUL I 1 A_Lower - Loop - Select: - MAUL I 1 A_Raise - Loop - Fire: - MAUL I 20 A_FireMauler2Pre - MAUL J 10 A_Light1 - BLSF A 10 Bright A_FireMauler2 - MAUL B 10 Bright A_Light2 - MAUL C 2 - MAUL D 2 A_Light0 - MAUL E 2 A_ReFire - Goto Ready - } -} - - -// Mauler "Bullet" Puff ----------------------------------------------------- - -ACTOR MaulerPuff -{ - +NOBLOCKMAP - +NOGRAVITY - +PUFFONACTORS - RenderStyle Add - DamageType Disintegrate - states - { - Spawn: - MPUF AB 5 - POW1 ABCDE 4 - Stop - } -} - -// The Mauler's Torpedo ----------------------------------------------------- - -ACTOR MaulerTorpedo -{ - Speed 20 - Height 8 - Radius 13 - Damage 1 - DamageType Disintegrate - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - RenderStyle Add - SeeSound "weapons/mauler2fire" - DeathSound "weapons/mauler2hit" - Obituary "$OB_MPMAULER" - - action native A_MaulerTorpedoWave (); - - States - { - Spawn: - TORP ABCD 4 Bright - Loop - Death: - THIT AB 8 Bright - THIT C 8 Bright A_MaulerTorpedoWave - THIT DE 8 Bright - Stop - } -} - - -// The mini torpedoes shot by the big torpedo -------------------------------- - -ACTOR MaulerTorpedoWave -{ - Speed 35 - Radius 13 - Height 13 - Damage 10 - DamageType Disintegrate - Projectile - +STRIFEDAMAGE - MaxStepHeight 4 - RenderStyle Add - Obituary "$OB_MPMAULER" - States - { - Spawn: - TWAV AB 9 Bright - Death: - TWAV C 9 Bright - Stop - } -} - - -// High-Explosive Grenade --------------------------------------------------- - -ACTOR HEGrenade -{ - Speed 15 - Radius 13 - Height 13 - Mass 20 - Damage 1 - Reactiontime 30 - Projectile - -NOGRAVITY - +STRIFEDAMAGE - +BOUNCEONACTORS - +EXPLODEONWATER - MaxStepHeight 4 - BounceType "Doom" - BounceFactor 0.5 - BounceCount 2 - SeeSound "weapons/hegrenadeshoot" - DeathSound "weapons/hegrenadebang" - Obituary "$OB_MPSTRIFEGRENADE" - States - { - Spawn: - GRAP AB 3 A_Countdown - Loop - Death: - BNG4 A 0 Bright A_NoGravity - BNG4 A 0 Bright A_SetTranslucent(1,1) - BNG4 A 2 Bright A_Explode(192,192,1,1) - BNG4 BCDEFGHIJKLMN 3 Bright - Stop - } -} - -// White Phosphorous Grenade ------------------------------------------------ - -ACTOR PhosphorousGrenade -{ - Speed 15 - Radius 13 - Height 13 - Mass 20 - Damage 1 - Reactiontime 40 - Projectile - -NOGRAVITY - +STRIFEDAMAGE - +BOUNCEONACTORS - +EXPLODEONWATER - BounceType "Doom" - MaxStepHeight 4 - BounceFactor 0.5 - BounceCount 2 - SeeSound "weapons/phgrenadeshoot" - DeathSound "weapons/phgrenadebang" - Obituary "$OB_MPPHOSPHOROUSGRENADE" - States - { - Spawn: - GRIN AB 3 A_Countdown - Loop - Death: - BNG3 A 2 A_SpawnItemEx("PhosphorousFire") - Stop - } -} - -// Fire from the Phoshorous Grenade ----------------------------------------- - -ACTOR PhosphorousFire native -{ - Reactiontime 120 - DamageType Fire - +NOBLOCKMAP - +FLOORCLIP - +NOTELEPORT - +NODAMAGETHRUST - +DONTSPLASH - RenderStyle Add - Obituary "$OB_MPPHOSPHOROUSGRENADE" - - action native A_Burnarea (); - action native A_Burnination (); - - states - { - Spawn: - BNG3 B 2 Bright A_Burnarea - BNG3 C 2 Bright A_Countdown - FLBE A 2 Bright A_Burnination - FLBE B 2 Bright A_Countdown - FLBE C 2 Bright A_Burnarea - FLBE D 3 Bright A_Countdown - FLBE E 3 Bright A_Burnarea - FLBE F 3 Bright A_Countdown - FLBE G 3 Bright A_Burnination - Goto Spawn+5 - Death: - FLBE H 2 Bright - FLBE I 2 Bright A_Burnination - FLBE JK 2 Bright - Stop - } -} - -// High-Explosive Grenade Launcher ------------------------------------------ - -ACTOR StrifeGrenadeLauncher : StrifeWeapon -{ - +FLOORCLIP - Weapon.SelectionOrder 2400 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 12 - Weapon.AmmoType1 "HEGrenadeRounds" - Weapon.SisterWeapon "StrifeGrenadeLauncher2" - Inventory.Icon "GRNDA0" - Tag "$TAG_GLAUNCHER1" - Inventory.PickupMessage "$TXT_GLAUNCHER" - - action native A_FireGrenade (class grenadetype, float angleofs, state flash); - - States - { - Spawn: - GRND A -1 - Stop - Ready: - GREN A 1 A_WeaponReady - Loop - Deselect: - GREN A 1 A_Lower - Loop - Select: - GREN A 1 A_Raise - Loop - Fire: - GREN A 5 A_FireGrenade("HEGrenade", -90, "Flash") - GREN B 10 - GREN A 5 A_FireGrenade("HEGrenade", 90, "Flash2") - GREN C 10 - GREN A 0 A_ReFire - Goto Ready - Flash: - GREF A 5 Bright A_Light1 - Goto LightDone - Flash2: - GREF B 5 Bright A_Light2 - Goto LightDone - } - -} - -// White Phosphorous Grenade Launcher --------------------------------------- - -ACTOR StrifeGrenadeLauncher2 : StrifeGrenadeLauncher -{ - Weapon.SelectionOrder 3200 - Weapon.AmmoUse1 1 - Weapon.AmmoGive1 0 - Weapon.AmmoType1 "PhosphorusGrenadeRounds" - Weapon.SisterWeapon "StrifeGrenadeLauncher" - Tag "$TAG_GLAUNCHER2" - - States - { - Ready: - GREN D 1 A_WeaponReady - Loop - Deselect: - GREN D 1 A_Lower - Loop - Select: - GREN D 1 A_Raise - Loop - Fire: - GREN D 5 A_FireGrenade("PhosphorousGrenade", -90, "Flash") - GREN E 10 - GREN D 5 A_FireGrenade("PhosphorousGrenade", 90, "Flash2") - GREN F 10 - GREN A 0 A_ReFire - Goto Ready - Flash: - GREF C 5 Bright A_Light1 - Goto LightDone - Flash2: - GREF D 5 Bright A_Light2 - Goto LightDone - } -} - diff --git a/wadsrc/static/actors/strife/templar.txt b/wadsrc/static/actors/strife/templar.txt deleted file mode 100644 index f15195c3d..000000000 --- a/wadsrc/static/actors/strife/templar.txt +++ /dev/null @@ -1,66 +0,0 @@ - -ACTOR Templar -{ - Health 300 - Painchance 100 - Speed 8 - Radius 20 - Height 60 - Mass 500 - Monster - +NOBLOOD - +SEESDAGGERS - +NOSPLASHALERT - MaxdropoffHeight 32 - MinMissileChance 200 - SeeSound "templar/sight" - PainSound "templar/pain" - DeathSound "templar/death" - ActiveSound "templar/active" - CrushPainSound "misc/pcrush" - Tag "$TAG_TEMPLAR" - HitObituary "$OB_TEMPLARHIT" - Obituary "$OB_TEMPLAR" - DropItem "EnergyPod" - - action native A_TemplarAttack(); - - States - { - Spawn: - PGRD A 5 A_Look2 - Loop - PGRD B 10 - Loop - PGRD C 10 - Loop - PGRD B 10 A_Wander - Loop - See: - PGRD AABBCCDD 3 A_Chase - Loop - Melee: - PGRD E 8 A_FaceTarget - PGRD F 8 A_CustomMeleeAttack(random[ReaverMelee](1,8)*3, "reaver/blade") - Goto See - Missile: - PGRD G 8 BRIGHT A_FaceTarget - PGRD H 8 BRIGHT A_TemplarAttack - Goto See - Pain: - PGRD A 2 - PGRD A 2 A_Pain - Goto See - Death: - PGRD I 4 A_TossGib - PGRD J 4 A_Scream - PGRD K 4 A_TossGib - PGRD L 4 A_NoBlocking - PGRD MN 4 - PGRD O 4 A_TossGib - PGRD "PQRSTUVWXYZ[" 4 - PGRD "\" -1 - Stop - } -} - diff --git a/wadsrc/static/actors/strife/thingstoblowup.txt b/wadsrc/static/actors/strife/thingstoblowup.txt deleted file mode 100644 index 8f8148809..000000000 --- a/wadsrc/static/actors/strife/thingstoblowup.txt +++ /dev/null @@ -1,141 +0,0 @@ - - -// A Cloud used for varius explosions --------------------------------------- -// This actor has no direct equivalent in strife. To create this, Strife -// spawned a spark and then changed its state to that of this explosion -// cloud. Weird. - -ACTOR Bang4Cloud -{ - +NOBLOCKMAP - +NOGRAVITY - RenderStyle Add - VSpeed 1 - States - { - Spawn: - BNG4 BCDEFGHIJKLMN 3 Bright - Stop - } -} - -// Piston ------------------------------------------------------------------- - -ACTOR Piston -{ - Health 100 - Speed 16 - Radius 20 - Height 76 - Mass 10000000 - +SOLID - +SHOOTABLE - +NOBLOOD - +FLOORCLIP - +INCOMBAT - DeathSound "misc/explosion" - states - { - Spawn: - PSTN AB 8 - Loop - Death: - PSTN A 4 Bright A_Scream - PSTN B 4 Bright A_NoBlocking - PSTN C 4 Bright A_GiveQuestItem(16) - PSTN D 4 Bright A_Bang4Cloud - PSTN E 4 Bright A_TossGib - PSTN F 4 Bright - PSTN G 4 Bright A_Bang4Cloud - PSTN H 4 - PSTN I -1 - Stop - } - -} - -// Computer ----------------------------------------------------------------- - -ACTOR Computer -{ - Health 80 - Speed 27 - Radius 26 - Height 128 - Mass 10000000 - +SOLID - +SHOOTABLE - +NOBLOOD - +FLOORCLIP - +INCOMBAT - DeathSound "misc/explosion" - states - { - Spawn: - SECR ABCD 4 Bright - Loop - Death: - SECR E 5 Bright A_Bang4Cloud - SECR F 5 Bright A_NoBlocking - SECR G 5 Bright A_GiveQuestItem(27) - SECR H 5 Bright A_TossGib - SECR I 5 Bright A_Bang4Cloud - SECR J 5 - SECR K 5 A_Bang4Cloud - SECR L 5 - SECR M 5 A_Bang4Cloud - SECR N 5 - SECR O 5 A_Bang4Cloud - SECR P -1 - Stop - } -} - - -// Power Crystal ------------------------------------------------------------ - -ACTOR PowerCrystal -{ - Health 50 - Speed 14 - Radius 20 - Height 16 - Mass 99999999 - +SOLID - +SHOOTABLE - +NOGRAVITY - +NOBLOOD - +FLOORCLIP - DeathSound "misc/explosion" - ActiveSound "misc/reactor" - - action native A_ExtraLightOff (); - action native A_Explode512 (); - action native A_LightGoesOut (); - - States - { - Spawn: - CRYS A 16 A_LoopActiveSound - CRYS B 5 A_LoopActiveSound - CRYS CDEF 4 A_LoopActiveSound - Loop - Death: - BOOM A 0 Bright A_Scream - BOOM A 1 Bright A_Explode512 - BOOM B 3 Bright A_GiveQuestItem(14) - BOOM C 2 Bright A_LightGoesOut - BOOM D 3 Bright A_Bang4Cloud - BOOM EF 3 Bright - BOOM G 3 Bright A_Bang4Cloud - BOOM H 1 Bright A_Explode512 - BOOM I 3 Bright - BOOM JKL 3 Bright A_Bang4Cloud - BOOM MN 3 Bright - BOOM O 3 Bright A_Bang4Cloud - BOOM PQRST 3 Bright - BOOM U 3 Bright A_ExtraLightOff - BOOM VWXY 3 Bright - Stop - } -} diff --git a/wadsrc/static/actors/strife/zombie.txt b/wadsrc/static/actors/strife/zombie.txt deleted file mode 100644 index 54683b824..000000000 --- a/wadsrc/static/actors/strife/zombie.txt +++ /dev/null @@ -1,58 +0,0 @@ - -// Zombie ------------------------------------------------------------------- - -ACTOR Zombie : StrifeHumanoid -{ - Health 31 - Radius 20 - Height 56 - PainChance 0 - +SOLID - +SHOOTABLE - +FLOORCLIP - +CANPASS - +CANPUSHWALLS - +ACTIVATEMCROSS - MinMissileChance 150 - MaxStepHeight 16 - MaxDropOffHeight 32 - Translation 0 - DeathSound "zombie/death" - CrushPainSound "misc/pcrush" - States - { - Spawn: - PEAS A 5 A_CheckTerrain - Loop - Pain: - AGRD A 5 A_CheckTerrain - Loop - Death: - GIBS M 5 A_TossGib - GIBS N 5 A_XScream - GIBS O 5 A_NoBlocking - GIBS PQRST 4 A_TossGib - GIBS U 5 - GIBS V -1 - Stop - } -} - - -// Zombie Spawner ----------------------------------------------------------- - -ACTOR ZombieSpawner -{ - Health 20 - +SHOOTABLE - +NOSECTOR - RenderStyle None - ActiveSound "zombie/spawner" // Does Strife use this somewhere else? - States - { - Spawn: - TNT1 A 175 A_SpawnItemEx("Zombie") - Loop - } -} - diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt index 6ecac49c6..2fc515af0 100644 --- a/wadsrc/static/decorate.txt +++ b/wadsrc/static/decorate.txt @@ -1,36 +1,3 @@ -#include "actors/strife/strifehumanoid.txt" -#include "actors/strife/strifeplayer.txt" -#include "actors/strife/strifeweapons.txt" -#include "actors/strife/spectral.txt" -#include "actors/strife/acolyte.txt" -#include "actors/strife/alienspectres.txt" -#include "actors/strife/beggars.txt" -#include "actors/strife/coin.txt" -#include "actors/strife/crusader.txt" -#include "actors/strife/entityboss.txt" -#include "actors/strife/inquisitor.txt" -#include "actors/strife/loremaster.txt" -#include "actors/strife/macil.txt" -#include "actors/strife/merchants.txt" -#include "actors/strife/peasants.txt" -#include "actors/strife/strifebishop.txt" -#include "actors/strife/oracle.txt" -#include "actors/strife/programmer.txt" -#include "actors/strife/questitems.txt" -#include "actors/strife/ratbuddy.txt" -#include "actors/strife/rebels.txt" -#include "actors/strife/reaver.txt" -#include "actors/strife/sentinel.txt" -#include "actors/strife/stalker.txt" -#include "actors/strife/strifeammo.txt" -#include "actors/strife/strifearmor.txt" -#include "actors/strife/strifeitems.txt" -#include "actors/strife/strifekeys.txt" -#include "actors/strife/strifestuff.txt" -#include "actors/strife/thingstoblowup.txt" -#include "actors/strife/templar.txt" -#include "actors/strife/zombie.txt" -#include "actors/strife/sigil.txt" #include "actors/chex/chexmonsters.txt" #include "actors/chex/chexkeys.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index c4dac2b95..f65ae5555 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -135,3 +135,37 @@ zscript/hexen/serpent.txt zscript/hexen/spike.txt zscript/hexen/wraith.txt zscript/hexen/heresiarch.txt + +zscript/strife/strifehumanoid.txt +zscript/strife/strifeplayer.txt +zscript/strife/strifeweapons.txt +zscript/strife/spectral.txt +zscript/strife/acolyte.txt +zscript/strife/alienspectres.txt +zscript/strife/beggars.txt +zscript/strife/coin.txt +zscript/strife/crusader.txt +zscript/strife/entityboss.txt +zscript/strife/inquisitor.txt +zscript/strife/loremaster.txt +zscript/strife/macil.txt +zscript/strife/merchants.txt +zscript/strife/peasants.txt +zscript/strife/strifebishop.txt +zscript/strife/oracle.txt +zscript/strife/programmer.txt +zscript/strife/questitems.txt +zscript/strife/ratbuddy.txt +zscript/strife/rebels.txt +zscript/strife/reaver.txt +zscript/strife/sentinel.txt +zscript/strife/stalker.txt +zscript/strife/strifeammo.txt +zscript/strife/strifearmor.txt +zscript/strife/strifeitems.txt +zscript/strife/strifekeys.txt +zscript/strife/strifestuff.txt +zscript/strife/thingstoblowup.txt +zscript/strife/templar.txt +zscript/strife/zombie.txt +zscript/strife/sigil.txt diff --git a/wadsrc/static/zscript/strife/acolyte.txt b/wadsrc/static/zscript/strife/acolyte.txt new file mode 100644 index 000000000..2f01cb836 --- /dev/null +++ b/wadsrc/static/zscript/strife/acolyte.txt @@ -0,0 +1,218 @@ + +// Base class for the acolytes ---------------------------------------------- + +class Acolyte : StrifeHumanoid +{ + Default + { + Health 70; + PainChance 150; + Speed 7; + Radius 24; + Height 64; + Mass 400; + Monster; + +SEESDAGGERS + +NOSPLASHALERT + +FLOORCLIP + +NEVERRESPAWN + MinMissileChance 150; + Tag "$TAG_ACOLYTE"; + SeeSound "acolyte/sight"; + PainSound "acolyte/pain"; + AttackSound "acolyte/rifle"; + DeathSound "acolyte/death"; + ActiveSound "acolyte/active"; + Obituary "$OB_ACOLYTE"; + } + + action native void A_BeShadowyFoe (); + action native void A_AcolyteBits (); + action native void A_AcolyteDie (); + + States + { + Spawn: + AGRD A 5 A_Look2; + Wait; + AGRD B 8 A_ClearShadow; + Loop; + AGRD D 8; + Loop; + AGRD ABCDABCD 5 A_Wander; + Loop; + See: + AGRD A 6 Fast Slow A_AcolyteBits; + AGRD BCD 6 Fast Slow A_Chase; + Loop; + Missile: + AGRD E 8 Fast Slow A_FaceTarget; + AGRD FE 4 Fast Slow A_ShootGun; + AGRD F 6 Fast Slow A_ShootGun; + Goto See; + Pain: + AGRD O 8 Fast Slow A_Pain; + Goto See; + Death: + AGRD G 4; + AGRD H 4 A_Scream; + AGRD I 4; + AGRD J 3; + AGRD K 3 A_NoBlocking; + AGRD L 3; + AGRD M 3 A_AcolyteDie; + AGRD N -1; + Stop; + XDeath: + GIBS A 5 A_NoBlocking; + GIBS BC 5 A_TossGib; + GIBS D 4 A_TossGib; + GIBS E 4 A_XScream; + GIBS F 4 A_TossGib; + GIBS GH 4; + GIBS I 5; + GIBS J 5 A_AcolyteDie; + GIBS K 5; + GIBS L 1400; + Stop; + } +} + + +// Acolyte 1 ---------------------------------------------------------------- + +class AcolyteTan : Acolyte +{ + Default + { + +MISSILEMORE +MISSILEEVENMORE + DropItem "ClipOfBullets"; + } +} + +// Acolyte 2 ---------------------------------------------------------------- + +class AcolyteRed : Acolyte +{ + Default + { + +MISSILEMORE +MISSILEEVENMORE + Translation 0; + } +} + +// Acolyte 3 ---------------------------------------------------------------- + +class AcolyteRust : Acolyte +{ + Default + { + +MISSILEMORE +MISSILEEVENMORE + Translation 1; + } +} + +// Acolyte 4 ---------------------------------------------------------------- + +class AcolyteGray : Acolyte +{ + Default + { + +MISSILEMORE +MISSILEEVENMORE + Translation 2; + } +} + +// Acolyte 5 ---------------------------------------------------------------- + +class AcolyteDGreen : Acolyte +{ + Default + { + +MISSILEMORE +MISSILEEVENMORE + Translation 3; + } +} + +// Acolyte 6 ---------------------------------------------------------------- + +class AcolyteGold : Acolyte +{ + Default + { + +MISSILEMORE +MISSILEEVENMORE + Translation 4; + } +} + +// Acolyte 7 ---------------------------------------------------------------- + +class AcolyteLGreen : Acolyte +{ + Default + { + Health 60; + Translation 5; + } +} + +// Acolyte 8 ---------------------------------------------------------------- + +class AcolyteBlue : Acolyte +{ + Default + { + Health 60; + Translation 6; + } +} + +// Shadow Acolyte ----------------------------------------------------------- + +class AcolyteShadow : Acolyte +{ + Default + { + +MISSILEMORE + DropItem "ClipOfBullets"; + } + States + { + See: + AGRD A 6 A_BeShadowyFoe; + Goto Super::See+1; + Pain: + AGRD O 0 Fast Slow A_SetShadow; + AGRD O 8 Fast Slow A_Pain; + Goto See; + } +} + +// Some guy turning into an acolyte ----------------------------------------- + +class AcolyteToBe : Acolyte +{ + Default + { + Health 61; + Radius 20; + Height 56; + DeathSound "becoming/death"; + -COUNTKILL + -ISMONSTER + } + + action native void A_HideDecepticon (); + + States + { + Spawn: + ARMR A -1; + Stop; + Pain: + ARMR A -1 A_HideDecepticon; + Stop; + Death: + Goto XDeath; + } +} diff --git a/wadsrc/static/zscript/strife/alienspectres.txt b/wadsrc/static/zscript/strife/alienspectres.txt new file mode 100644 index 000000000..42c8293d0 --- /dev/null +++ b/wadsrc/static/zscript/strife/alienspectres.txt @@ -0,0 +1,223 @@ + +// Alien Spectre 1 ----------------------------------------------------------- + +class AlienSpectre1 : SpectralMonster +{ + Default + { + Health 1000; + Painchance 250; + Speed 12; + Radius 64; + Height 64; + FloatSpeed 5; + Mass 1000; + MinMissileChance 150; + RenderStyle "Translucent"; + Alpha 0.666; + SeeSound "alienspectre/sight"; + AttackSound "alienspectre/blade"; + PainSound "alienspectre/pain"; + DeathSound "alienspectre/death"; + ActiveSound "alienspectre/active"; + Obituary "$OB_ALIENSPECTRE"; + +NOGRAVITY + +FLOAT + +SHADOW + +NOTDMATCH + +DONTMORPH + +NOBLOCKMONST + +INCOMBAT + +LOOKALLAROUND + +NOICEDEATH + } + + action native void A_AlienSpectreDeath (); + + States + { + Spawn: + ALN1 A 10 A_Look; + ALN1 B 10 A_SentinelBob; + Loop; + See: + ALN1 AB 4 Bright A_Chase; + ALN1 C 4 Bright A_SentinelBob; + ALN1 DEF 4 Bright A_Chase; + ALN1 G 4 Bright A_SentinelBob; + ALN1 HIJ 4 Bright A_Chase; + ALN1 K 4 Bright A_SentinelBob; + Loop; + Melee: + ALN1 J 4 Bright A_FaceTarget; + ALN1 I 4 Bright A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5); + ALN1 H 4 Bright; + Goto See; + Missile: + ALN1 J 4 Bright A_FaceTarget; + ALN1 I 4 Bright A_SpotLightning; + ALN1 H 4 Bright; + Goto See+10; + Pain: + ALN1 J 2 A_Pain; + Goto See+6; + Death: + AL1P A 6 Bright A_SpectreChunkSmall; + AL1P B 6 Bright A_Scream; + AL1P C 6 Bright A_SpectreChunkSmall; + AL1P DE 6 Bright; + AL1P F 6 Bright A_SpectreChunkSmall; + AL1P G 6 Bright; + AL1P H 6 Bright A_SpectreChunkSmall; + AL1P IJK 6 Bright; + AL1P LM 5 Bright; + AL1P N 5 Bright A_SpectreChunkLarge; + AL1P OPQ 5 Bright; + AL1P R 5 Bright A_AlienSpectreDeath; + Stop; + } +} + + +// Alien Spectre 2 ----------------------------------------------------------- + +class AlienSpectre2 : AlienSpectre1 +{ + Default + { + Health 1200; + Painchance 50; + Radius 24; + DropItem "Sigil2"; + } + States + { + Missile: + ALN1 F 4 A_FaceTarget; + ALN1 I 4 A_CustomMissile("SpectralLightningH3", 32, 0); + ALN1 E 4; + Goto See+10; + } +} + +// Alien Spectre 3 ---------------------------------------------------------- +// This is the Oracle's personal spectre, so it's a little different. + +class AlienSpectre3 : AlienSpectre1 +{ + Default + { + Health 1500; + Painchance 50; + Radius 24; + +SPAWNCEILING + DropItem "Sigil3"; + DamageFactor "SpectralLow", 0; + } + States + { + Spawn: + ALN1 ABCDEFGHIJK 5; + Loop; + See: + ALN1 AB 5 A_Chase; + ALN1 C 5 A_SentinelBob; + ALN1 DEF 5 A_Chase; + ALN1 G 5 A_SentinelBob; + ALN1 HIJ 5 A_Chase; + ALN1 K 5 A_SentinelBob; + Loop; + Melee: + ALN1 J 4 A_FaceTarget; + ALN1 I 4 A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5); + ALN1 C 4; + Goto See+2; + Missile: + ALN1 F 4 A_FaceTarget; + ALN1 I 4 A_Spectre3Attack; + ALN1 E 4; + Goto See+10; + Pain: + ALN1 J 2 A_Pain; + Goto See+6; + } +} + + +// Alien Spectre 4 ----------------------------------------------------------- + +class AlienSpectre4 : AlienSpectre1 +{ + Default + { + Health 1700; + Painchance 50; + Radius 24; + DropItem "Sigil4"; + } + States + { + Missile: + ALN1 F 4 A_FaceTarget; + ALN1 I 4 A_CustomMissile("SpectralLightningBigV2", 32, 0); + ALN1 E 4; + Goto See+10; + } +} + + +// Alien Spectre 5 ----------------------------------------------------------- + +class AlienSpectre5 : AlienSpectre1 +{ + Default + { + Health 2000; + Painchance 50; + Radius 24; + DropItem "Sigil5"; + } + States + { + Missile: + ALN1 F 4 A_FaceTarget; + ALN1 I 4 A_CustomMissile("SpectralLightningBigBall2", 32, 0); + ALN1 E 4; + Goto See+10; + } +} + +// Small Alien Chunk -------------------------------------------------------- + +class AlienChunkSmall : Actor +{ + Default + { + +NOBLOCKMAP + +NOCLIP + } + States + { + Spawn: + NODE ABCDEFG 6 Bright; + Stop; + } +} + +// Large Alien Chunk -------------------------------------------------------- + +class AlienChunkLarge : Actor +{ + Default + { + +NOBLOCKMAP + +NOCLIP + } + States + { + Spawn: + MTHD ABCDEFGHIJK 5 Bright; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/beggars.txt b/wadsrc/static/zscript/strife/beggars.txt new file mode 100644 index 000000000..e70a3a8e7 --- /dev/null +++ b/wadsrc/static/zscript/strife/beggars.txt @@ -0,0 +1,90 @@ + +// Base class for the beggars --------------------------------------------- + +class Beggar : StrifeHumanoid +{ + Default + { + Health 20; + PainChance 250; + Speed 3; + Radius 20; + Height 56; + Monster; + +JUSTHIT + -COUNTKILL + +NOSPLASHALERT + MinMissileChance 150; + Tag "$TAG_BEGGAR"; + MaxStepHeight 16; + MaxDropoffHeight 32; + HitObituary "$OB_BEGGAR"; + + AttackSound "beggar/attack"; + PainSound "beggar/pain"; + DeathSound "beggar/death"; + } + States + { + Spawn: + BEGR A 10 A_Look; + Loop; + See: + BEGR AABBCC 4 A_Wander; + Loop; + Melee: + BEGR D 8; + BEGR D 8 A_CustomMeleeAttack(2*random[PeasantAttack](1,5)+2); + BEGR E 1 A_Chase; + BEGR D 8 A_SentinelRefire; + Loop; + Pain: + BEGR A 3 A_Pain; + BEGR A 3 A_Chase; + Goto Melee; + Death: + BEGR F 4; + BEGR G 4 A_Scream; + BEGR H 4; + BEGR I 4 A_NoBlocking; + BEGR JKLM 4; + BEGR N -1; + Stop; + XDeath: + BEGR F 5 A_TossGib; + GIBS M 5 A_TossGib; + GIBS N 5 A_XScream; + GIBS O 5 A_NoBlocking; + GIBS PQRST 4 A_TossGib; + GIBS U 5; + GIBS V 1400; + Stop; + } +} + + +// Beggars ----------------------------------------------------------------- + +class Beggar1 : Beggar +{ +} + + +class Beggar2 : Beggar +{ +} + + +class Beggar3 : Beggar +{ +} + + +class Beggar4 : Beggar +{ +} + + +class Beggar5 : Beggar +{ +} diff --git a/wadsrc/static/zscript/strife/coin.txt b/wadsrc/static/zscript/strife/coin.txt new file mode 100644 index 000000000..a930cb0ba --- /dev/null +++ b/wadsrc/static/zscript/strife/coin.txt @@ -0,0 +1,99 @@ + +// Coin --------------------------------------------------------------------- + +class Coin : Inventory native +{ + Default + { + +DROPPED + +NOTDMATCH + +FLOORCLIP + Inventory.MaxAmount 0x7fffffff; + +INVENTORY.INVBAR + Tag "$TAG_COIN"; + Inventory.Icon "I_COIN"; + Inventory.PickupMessage "$TXT_COIN"; + } + States + { + Spawn: + COIN A -1; + Stop; + } +} + + +// 10 Gold ------------------------------------------------------------------ + +class Gold10 : Coin +{ + Default + { + Inventory.Amount 10; + Tag "$TAG_10GOLD"; + Inventory.PickupMessage "$TXT_10GOLD"; + } + States + { + Spawn: + CRED A -1; + Stop; + } +} + +// 25 Gold ------------------------------------------------------------------ + +class Gold25 : Coin +{ + Default + { + Inventory.Amount 25; + Tag "$TAG_25GOLD"; + Inventory.PickupMessage "$TXT_25GOLD"; + } + States + { + Spawn: + SACK A -1; + Stop; + } +} + +// 50 Gold ------------------------------------------------------------------ + +class Gold50 : Coin +{ + Default + { + Inventory.Amount 50; + Tag "$TAG_50GOLD"; + Inventory.PickupMessage "$TXT_50GOLD"; + } + States + { + Spawn: + CHST A -1; + Stop; + } +} + +// 300 Gold ------------------------------------------------------------------ + +class Gold300 : Coin +{ + Default + { + Inventory.Amount 300; + Tag "$TAG_300GOLD"; + Inventory.PickupMessage "$TXT_300GOLD"; + Inventory.GiveQuest 3; + +INVENTORY.ALWAYSPICKUP + } + States + { + Spawn: + TOKN A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/crusader.txt b/wadsrc/static/zscript/strife/crusader.txt new file mode 100644 index 000000000..334e9d803 --- /dev/null +++ b/wadsrc/static/zscript/strife/crusader.txt @@ -0,0 +1,131 @@ + +// Crusader ----------------------------------------------------------------- + +class Crusader : Actor +{ + Default + { + Speed 8; + Radius 40; + Height 56; + Mass 400; + Health 400; + Painchance 128; + Monster; + +FLOORCLIP + +DONTMORPH + +MISSILEMORE + +INCOMBAT + +NOICEDEATH + +NOBLOOD + MinMissileChance 120; + MaxDropoffHeight 32; + DropItem "EnergyPod", 256, 20; + SeeSound "crusader/sight"; + PainSound "crusader/pain"; + DeathSound "crusader/death"; + ActiveSound "crusader/active"; + Obituary "$OB_CRUSADER"; + } + + action native void A_CrusaderChoose (); + action native void A_CrusaderSweepLeft (); + action native void A_CrusaderSweepRight (); + action native void A_CrusaderRefire (); + action native void A_CrusaderDeath (); + + States + { + Spawn: + ROB2 Q 10 A_Look; + Loop; + See: + ROB2 AABBCCDD 3 A_Chase; + Loop; + Missile: + ROB2 E 3 Slow A_FaceTarget; + ROB2 F 2 Slow Bright A_CrusaderChoose; + ROB2 E 2 Slow Bright A_CrusaderSweepLeft; + ROB2 F 3 Slow Bright A_CrusaderSweepLeft; + ROB2 EF 2 Slow Bright A_CrusaderSweepLeft; + ROB2 EFE 2 Slow Bright A_CrusaderSweepRight; + ROB2 F 2 Slow A_CrusaderRefire; + Loop; + Pain: + ROB2 D 1 Slow A_Pain; + Goto See; + Death: + ROB2 G 3 A_Scream; + ROB2 H 5 A_TossGib; + ROB2 I 4 Bright A_TossGib; + ROB2 J 4 Bright A_Explode(64,64,1,1); + ROB2 K 4 Bright A_Fall; + ROB2 L 4 A_Explode(64,64,1,1); + ROB2 MN 4 A_TossGib; + ROB2 O 4 A_Explode(64,64,1,1); + ROB2 P -1 A_CrusaderDeath; + Stop; + } +} + + +// Fast Flame Projectile (used by Crusader) --------------------------------- + +class FastFlameMissile : FlameMissile +{ + Default + { + Mass 50; + Damage 1; + Speed 35; + } +} + +// Crusader Missile --------------------------------------------------------- +// This is just like the mini missile the player shoots, except it doesn't +// explode when it dies, and it does slightly less damage for a direct hit. + +class CrusaderMissile : Actor +{ + Default + { + Speed 20; + Radius 10; + Height 14; + Damage 7; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + SeeSound "crusader/misl"; + DeathSound "crusader/mislx"; + } + States + { + Spawn: + MICR A 6 Bright A_RocketInFlight; + Loop; + Death: + SMIS A 0 Bright A_SetTranslucent(1,1); + SMIS A 5 Bright; + SMIS B 5 Bright; + SMIS C 4 Bright; + SMIS DEFG 2 Bright; + Stop; + } +} + + +// Dead Crusader ------------------------------------------------------------ + +class DeadCrusader : Actor +{ + States + { + Spawn: + ROB2 N 4; + ROB2 O 4; + ROB2 P -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/entityboss.txt b/wadsrc/static/zscript/strife/entityboss.txt new file mode 100644 index 000000000..d54a95a76 --- /dev/null +++ b/wadsrc/static/zscript/strife/entityboss.txt @@ -0,0 +1,211 @@ + +// Entity Nest -------------------------------------------------------------- + +class EntityNest : Actor +{ + Default + { + Radius 84; + Height 47; + +SOLID + +NOTDMATCH + +FLOORCLIP + } + States + { + Spawn: + NEST A -1; + Stop; + } +} + +// Entity Pod --------------------------------------------------------------- + +class EntityPod : Actor +{ + Default + { + Radius 25; + Height 91; + +SOLID + +NOTDMATCH + SeeSound "misc/gibbed"; + } + + action native void A_SpawnEntity (); + + States + { + Spawn: + PODD A 60 A_Look; + Loop; + See: + PODD A 360; + PODD B 9 A_NoBlocking; + PODD C 9; + PODD D 9 A_SpawnEntity; + PODD E -1; + Stop; + } +} + + +// Entity Boss -------------------------------------------------------------- + +class EntityBoss : SpectralMonster +{ + Default + { + Health 2500; + Painchance 255; + Speed 13; + Radius 130; + Height 200; + FloatSpeed 5; + Mass 1000; + Monster; + +SPECIAL + +NOGRAVITY + +FLOAT + +SHADOW + +NOTDMATCH + +DONTMORPH + +NOTARGET + +NOBLOCKMONST + +INCOMBAT + +LOOKALLAROUND + +SPECTRAL + +NOICEDEATH + MinMissileChance 150; + RenderStyle "Translucent"; + Alpha 0.5; + SeeSound "entity/sight"; + AttackSound "entity/melee"; + PainSound "entity/pain"; + DeathSound "entity/death"; + ActiveSound "entity/active"; + Obituary "$OB_ENTITY"; + } + + action native void A_EntityAttack(); + action native void A_EntityDeath(); + + States + { + Spawn: + MNAM A 100; + MNAM B 60 Bright; + MNAM CDEFGHIJKL 4 Bright; + MNAL A 4 Bright A_Look; + MNAL B 4 Bright A_SentinelBob; + Goto Spawn+12; + See: + MNAL AB 4 Bright A_Chase; + MNAL C 4 Bright A_SentinelBob; + MNAL DEF 4 Bright A_Chase; + MNAL G 4 Bright A_SentinelBob; + MNAL HIJ 4 Bright A_Chase; + MNAL K 4 Bright A_SentinelBob; + Loop; + Melee: + MNAL J 4 Bright A_FaceTarget; + MNAL I 4 Bright A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5); + MNAL C 4 Bright; + Goto See+2; + Missile: + MNAL F 4 Bright A_FaceTarget; + MNAL I 4 Bright A_EntityAttack; + MNAL E 4 Bright; + Goto See+10; + Pain: + MNAL J 2 Bright A_Pain; + Goto See+6; + Death: + MNAL L 7 Bright A_SpectreChunkSmall; + MNAL M 7 Bright A_Scream; + MNAL NO 7 Bright A_SpectreChunkSmall; + MNAL P 7 Bright A_SpectreChunkLarge; + MNAL Q 64 Bright A_SpectreChunkSmall; + MNAL Q 6 Bright A_EntityDeath; + Stop; + } +} + +// Second Entity Boss ------------------------------------------------------- + +class EntitySecond : SpectralMonster +{ + Default + { + Health 990; + Painchance 255; + Speed 14; + Radius 130; + Height 200; + FloatSpeed 5; + Mass 1000; + Monster; + +SPECIAL + +NOGRAVITY + +FLOAT + +SHADOW + +NOTDMATCH + +DONTMORPH + +NOBLOCKMONST + +INCOMBAT + +LOOKALLAROUND + +SPECTRAL + +NOICEDEATH + MinMissileChance 150; + RenderStyle "Translucent"; + Alpha 0.25; + SeeSound "alienspectre/sight"; + AttackSound "alienspectre/blade"; + PainSound "alienspectre/pain"; + DeathSound "alienspectre/death"; + ActiveSound "alienspectre/active"; + Obituary "$OB_ENTITY"; + } + + action native void A_SubEntityDeath (); + + States + { + Spawn: + MNAL R 10 Bright A_Look; + Loop; + See: + MNAL R 5 Bright A_SentinelBob; + MNAL ST 5 Bright A_Chase; + MNAL U 5 Bright A_SentinelBob; + MNAL V 5 Bright A_Chase; + MNAL W 5 Bright A_SentinelBob; + Loop; + Melee: + MNAL S 4 Bright A_FaceTarget; + MNAL R 4 Bright A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5); + MNAL T 4 Bright A_SentinelBob; + Goto See+1; + Missile: + MNAL W 4 Bright A_FaceTarget; + MNAL U 4 Bright A_CustomMissile("SpectralLightningH3",32,0); + MNAL V 4 Bright A_SentinelBob; + Goto See+4; + Pain: + MNAL R 2 Bright A_Pain; + Goto See; + Death: + MDTH A 3 Bright A_Scream; + MDTH B 3 Bright A_TossGib; + MDTH C 3 Bright A_NoBlocking; + MDTH DEFGHIJKLMN 3 Bright A_TossGib; + MDTH O 3 Bright A_SubEntityDeath; + Stop; + } +} + + + + + + diff --git a/wadsrc/static/zscript/strife/inquisitor.txt b/wadsrc/static/zscript/strife/inquisitor.txt new file mode 100644 index 000000000..5a053c74f --- /dev/null +++ b/wadsrc/static/zscript/strife/inquisitor.txt @@ -0,0 +1,150 @@ + +// Inquisitor --------------------------------------------------------------- + +class Inquisitor : Actor +{ + Default + { + Health 1000; + Speed 12; + Radius 40; + Height 110; + Mass 0x7fffffff; + Monster; + +DROPOFF + +NOBLOOD + +BOSS + +FLOORCLIP + +DONTMORPH + +NORADIUSDMG + MaxDropOffHeight 32; + MinMissileChance 150; + SeeSound "inquisitor/sight"; + DeathSound "inquisitor/death"; + ActiveSound "inquisitor/active"; + Obituary "$OB_INQUISITOR"; + } + + action native void A_InquisitorWalk (); + action native void A_InquisitorDecide (); + action native void A_InquisitorAttack (); + action native void A_InquisitorJump (); + action native void A_InquisitorCheckLand (); + action native void A_TossArm (); + action native void A_ReaverRanged (); + + States + { + Spawn: + ROB3 AB 10 A_Look; + Loop; + See: + ROB3 B 3 A_InquisitorWalk; + ROB3 B 3 A_Chase; + ROB3 CCDD 4 A_Chase; + ROB3 E 3 A_InquisitorWalk; + ROB3 E 3 A_InquisitorDecide; + Loop; + Missile: + ROB3 A 2 A_InquisitorDecide; + ROB3 F 6 A_FaceTarget; + ROB3 G 8 Bright A_ReaverRanged; + ROB3 G 8 A_ReaverRanged; + Goto See; + Grenade: + ROB3 K 12 A_FaceTarget; + ROB3 J 6 Bright A_InquisitorAttack; + ROB3 K 12; + Goto See; + Jump: + ROB3 H 8 Bright A_InquisitorJump; + ROB3 I 4 Bright A_InquisitorCheckLand; + ROB3 H 4 Bright A_InquisitorCheckLand; + Goto Jump+1; + Death: + ROB3 L 0 A_StopSound(CHAN_ITEM); + ROB3 L 4 A_TossGib; + ROB3 M 4 A_Scream; + ROB3 N 4 A_TossGib; + ROB3 O 4 Bright A_Explode(128,128,1,1); + ROB3 P 4 Bright A_TossGib; + ROB3 Q 4 Bright A_NoBlocking; + ROB3 RSTUV 4 A_TossGib; + ROB3 W 4 Bright A_Explode(128,128,1,1); + ROB3 XY 4 Bright A_TossGib; + ROB3 Z 4 A_TossGib; + ROB3 [ 4 A_TossGib; + ROB3 \ 3 A_TossGib; + ROB3 ] 3 Bright A_Explode(128,128,1,1); + RBB3 A 3 Bright A_TossArm; + RBB3 B 3 Bright A_TossGib; + RBB3 CD 3 A_TossGib; + RBB3 E -1; + Stop; + } +} + +// Inquisitor Shot ---------------------------------------------------------- + +class InquisitorShot : Actor +{ + Default + { + ReactionTime 15; + Speed 25; + Radius 13; + Height 13; + Mass 15; + Projectile; + -ACTIVATEIMPACT + -ACTIVATEPCROSS + -NOGRAVITY + +STRIFEDAMAGE + MaxStepHeight 4; + SeeSound "inquisitor/attack"; + DeathSound "inquisitor/atkexplode"; + } + States + { + Spawn: + UBAM AB 3 A_Countdown; + Loop; + Death: + BNG2 A 0 Bright A_SetTranslucent(1,1); + BNG2 A 4 Bright A_Explode(192, 192, 1, 1); + BNG2 B 4 Bright; + BNG2 C 4 Bright; + BNG2 D 4 Bright; + BNG2 E 4 Bright; + BNG2 F 4 Bright; + BNG2 G 4 Bright; + BNG2 H 4 Bright; + BNG2 I 4 Bright; + Stop; + } + +} + + +// The Dead Inquisitor's Detached Arm --------------------------------------- + +class InquisitorArm : Actor +{ + Default + { + Speed 25; + +NOBLOCKMAP + +NOCLIP + +NOBLOOD + } + States + { + Spawn: + RBB3 FG 5 Bright; + RBB3 H -1; + Stop; + } +} + + + diff --git a/wadsrc/static/zscript/strife/loremaster.txt b/wadsrc/static/zscript/strife/loremaster.txt new file mode 100644 index 000000000..d3b437bbd --- /dev/null +++ b/wadsrc/static/zscript/strife/loremaster.txt @@ -0,0 +1,123 @@ + +// Loremaster (aka Priest) -------------------------------------------------- + +class Loremaster : Actor +{ + Default + { + Health 800; + Speed 10; + Radius 15; + Height 56; + FloatSpeed 5; + Monster; + +FLOAT + +NOBLOOD + +NOGRAVITY + +NOTDMATCH + +FLOORCLIP + +NOBLOCKMONST + +INCOMBAT + +LOOKALLAROUND + +NOICEDEATH + +NEVERRESPAWN + DamageFactor "Fire", 0.5; + MinMissileChance 150; + Tag "$TAG_PRIEST"; + SeeSound "loremaster/sight"; + AttackSound "loremaster/attack"; + PainSound "loremaster/pain"; + DeathSound "loremaster/death"; + ActiveSound "loremaster/active"; + Obituary "$OB_LOREMASTER"; + DropItem "Junk"; + } + States + { + Spawn: + PRST A 10 A_Look; + PRST B 10 A_SentinelBob; + Loop; + See: + PRST A 4 A_Chase; + PRST A 4 A_SentinelBob; + PRST B 4 A_Chase; + PRST B 4 A_SentinelBob; + PRST C 4 A_Chase; + PRST C 4 A_SentinelBob; + PRST D 4 A_Chase; + PRST D 4 A_SentinelBob; + Loop; + Melee: + PRST E 4 A_FaceTarget; + PRST F 4 A_CustomMeleeAttack((random[SpectreMelee](0,255)&9)*5); + PRST E 4 A_SentinelBob; + Goto See; + Missile: + PRST E 4 A_FaceTarget; + PRST F 4 A_CustomMissile("LoreShot", 32, 0); + PRST E 4 A_SentinelBob; + Goto See; + Death: + PDED A 6; + PDED B 6 A_Scream; + PDED C 6; + PDED D 6 A_Fall; + PDED E 6; + PDED FGHIJIJIJKL 5; + PDED MNOP 4; + PDED Q 4 A_SpawnItemEx("AlienSpectre5", 0, 0, 0, 0, 0, random[spectrespawn](0,255)*0.0078125, 0, SXF_NOCHECKPOSITION); + PDED RS 4; + PDED T -1; + Stop; + } +} + + +// Loremaster Projectile ---------------------------------------------------- + +class LoreShot : Actor native +{ + Default + { + Speed 20; + Height 14; + Radius 10; + Projectile; + +STRIFEDAMAGE + Damage 2; + MaxStepHeight 4; + SeeSound "loremaster/chain"; + ActiveSound "loremaster/swish"; + } + + action native void A_LoremasterChain (); + + States + { + Spawn: + OCLW A 2 A_LoremasterChain; + Loop; + Death: + OCLW A 6; + Stop; + } +} + +// Loremaster Subprojectile ------------------------------------------------- + +class LoreShot2 : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + } + States + { + Spawn: + TEND A 20; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/macil.txt b/wadsrc/static/zscript/strife/macil.txt new file mode 100644 index 000000000..870f0db35 --- /dev/null +++ b/wadsrc/static/zscript/strife/macil.txt @@ -0,0 +1,95 @@ + +// Macil (version 1) --------------------------------------------------------- + +class Macil1 : Actor +{ + Default + { + Health 95; + Radius 20; + Height 56; + Speed 8; + Painchance 250; + Monster; + -COUNTKILL + +NOTDMATCH + +NOICEDEATH + +NOSPLASHALERT + +NODAMAGE + +NEVERRESPAWN + DamageFactor "Fire", 0.5; + MinMissileChance 150; + SeeSound "macil/sight"; + PainSound "macil/pain"; + ActiveSound "macil/active"; + CrushPainSound "misc/pcrush"; + Tag "$TAG_MACIL1"; + Obituary "$OB_MACIL"; + DropItem "BoxOfBullets"; + MaxStepHeight 16; + MaxDropoffHeight 32; + } + States + { + Spawn: + LEDR C 5 A_Look2; + Loop; + LEDR A 8; + Loop; + LEDR B 8; + Loop; + LEAD ABCD 6 A_Wander; + Loop; + See: + LEAD AABBCCDD 3 A_Chase; + Loop; + Missile: + Death: + LEAD E 2 A_FaceTarget; + LEAD F 2 BRIGHT A_ShootGun; + LEAD E 1 A_SentinelRefire; + Loop; + Pain: + LEAD Y 3; + LEAD Y 3 A_Pain; + Goto See; + } +} + + +// Macil (version 2) --------------------------------------------------------- + +class Macil2 : Macil1 +{ + Default + { + Painchance 200; + +COUNTKILL + +SPECTRAL + -NODAMAGE + Tag "$TAG_MACIL2"; + DeathSound "macil/slop"; + DropItem "None"; + DamageFactor "SpectralLow", 0; + } + States + { + Missile: + LEAD E 4 A_FaceTarget; + LEAD F 4 BRIGHT A_ShootGun; + LEAD E 2 A_SentinelRefire; + Loop; + Death: + LEAD G 5; + LEAD H 5 A_Scream; + LEAD IJ 4; + LEAD K 3; + LEAD L 3 A_NoBlocking; + LEAD MNOPQRSTUV 3; + LEAD W 3 A_SpawnItemEx("AlienSpectre4", 0, 0, 0, 0, 0, random[spectrespawn](0,255)*0.0078125, 0, SXF_NOCHECKPOSITION); + LEAD X -1; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/strife/merchants.txt b/wadsrc/static/zscript/strife/merchants.txt new file mode 100644 index 000000000..71b797639 --- /dev/null +++ b/wadsrc/static/zscript/strife/merchants.txt @@ -0,0 +1,108 @@ +// Base class for the merchants --------------------------------------------- + +class Merchant : Actor +{ + Default + { + Health 10000000; + PainChance 256; // a merchant should always enter the pain state when getting hurt + Radius 20; + Height 56; + Mass 5000; + CrushPainSound "misc/pcrush"; + +SOLID + +SHOOTABLE + +NOTDMATCH + +NOSPLASHALERT + +NODAMAGE + } + States + { + Spawn: + MRST A 10 A_Look2; + Loop; + MRLK A 30 A_ActiveSound; + Loop; + MRLK B 30; + Loop; + MRBD ABCDEDCB 4; + MRBD A 5; + MRBD F 6; + Loop; + See: + Pain: + MRPN A 1; + MRPN A 2 A_AlertMonsters; + MRPN B 3 A_Pain; + MRPN C 3; + MRPN D 9 Door_CloseWaitOpen(999, 64, 960); + MRPN C 4; + MRPN B 3; + MRPN A 3 A_ClearSoundTarget; + Goto Spawn; + Yes: + MRYS A 20; + // Fall through + Greetings: + MRGT ABCDEFGHI 5; + Goto Spawn; + No: + MRNO AB 6; + MRNO C 10; + MRNO BA 6; + Goto Greetings; + } +} + + +// Weapon Smith ------------------------------------------------------------- + +class WeaponSmith : Merchant +{ + Default + { + PainSound "smith/pain"; + Tag "$TAG_WEAPONSMITH"; + } +} + + +// Bar Keep ----------------------------------------------------------------- + +class BarKeep : Merchant +{ + Default + { + Translation 4; + PainSound "barkeep/pain"; + ActiveSound "barkeep/active"; + Tag "$TAG_BARKEEP"; + } +} + + +// Armorer ------------------------------------------------------------------ + +class Armorer : Merchant +{ + Default + { + Translation 5; + PainSound "armorer/pain"; + Tag "$TAG_ARMORER"; + } +} + + +// Medic -------------------------------------------------------------------- + +class Medic : Merchant +{ + Default + { + Translation 6; + PainSound "medic/pain"; + Tag "$TAG_MEDIC"; + } +} + diff --git a/wadsrc/static/zscript/strife/oracle.txt b/wadsrc/static/zscript/strife/oracle.txt new file mode 100644 index 000000000..206dee164 --- /dev/null +++ b/wadsrc/static/zscript/strife/oracle.txt @@ -0,0 +1,38 @@ + +// Oracle ------------------------------------------------------------------- + +class Oracle : Actor +{ + Default + { + Health 1; + Radius 15; + Height 56; + Monster; + +NOTDMATCH + +NOBLOOD + +NEVERRESPAWN + DamageFactor "Fire", 0.5; + DamageFactor "SpectralLow", 0; + MaxDropoffHeight 32; + Tag "$TAG_ORACLE"; + DropItem "Meat"; + } + + action native void A_WakeOracleSpectre (); + + States + { + Spawn: + ORCL A -1; + Stop; + Death: + ORCL BCDEFGHIJK 5; + ORCL L 5 A_NoBlocking; + ORCL M 5; + ORCL N 5 A_WakeOracleSpectre; + ORCL OP 5; + ORCL Q -1; + Stop; + } +} diff --git a/wadsrc/static/zscript/strife/peasants.txt b/wadsrc/static/zscript/strife/peasants.txt new file mode 100644 index 000000000..6645c69fa --- /dev/null +++ b/wadsrc/static/zscript/strife/peasants.txt @@ -0,0 +1,251 @@ + +// Peasant Base Class ------------------------------------------------------- + +class Peasant : StrifeHumanoid +{ + Default + { + Health 31; + PainChance 200; + Speed 8; + Radius 20; + Height 56; + Monster; + +NEVERTARGET + -COUNTKILL + +NOSPLASHALERT + +FLOORCLIP + +JUSTHIT + MinMissileChance 150; + MaxStepHeight 16; + MaxDropoffHeight 32; + SeeSound "peasant/sight"; + AttackSound "peasant/attack"; + PainSound "peasant/pain"; + DeathSound "peasant/death"; + HitObituary "$OB_PEASANT"; + } + States + { + Spawn: + PEAS A 10 A_Look2; + Loop; + See: + PEAS AABBCCDD 5 A_Wander; + Goto Spawn; + Melee: + PEAS E 10 A_FaceTarget; + PEAS F 8 A_CustomMeleeAttack(2*random[PeasantAttack](1,5)+2); + PEAS E 8; + Goto See; + Pain: + PEAS O 3; + PEAS O 3 A_Pain; + Goto Melee; + Wound: + PEAS G 5; + PEAS H 10 A_GetHurt; + PEAS I 6; + Goto Wound+1; + Death: + PEAS G 5; + PEAS H 5 A_Scream; + PEAS I 6; + PEAS J 5 A_NoBlocking; + PEAS K 5; + PEAS L 6; + PEAS M 8; + PEAS N 1400; + GIBS U 5; + GIBS V 1400; + Stop; + XDeath: + GIBS M 5 A_TossGib; + GIBS N 5 A_XScream; + GIBS O 5 A_NoBlocking; + GIBS PQRS 4 A_TossGib; + Goto Death+8; + } +} + +// Peasant Variant 1 -------------------------------------------------------- + +class Peasant1 : Peasant +{ + Default + { + Speed 4; + } +} + +class Peasant2 : Peasant +{ + Default + { + Speed 5; + } +} + +class Peasant3 : Peasant +{ + Default + { + Speed 5; + } +} + +class Peasant4 : Peasant +{ + Default + { + Translation 0; + Speed 7; + } +} + +class Peasant5 : Peasant +{ + Default + { + Translation 0; + Speed 7; + } +} + +class Peasant6 : Peasant +{ + Default + { + Translation 0; + Speed 7; + } +} + +class Peasant7 : Peasant +{ + Default + { + Translation 2; + } +} + +class Peasant8 : Peasant +{ + Default + { + Translation 2; + } +} + +class Peasant9 : Peasant +{ + Default + { + Translation 2; + } +} + +class Peasant10 : Peasant +{ + Default + { + Translation 1; + } +} + +class Peasant11 : Peasant +{ + Default + { + Translation 1; + } +} + +class Peasant12 : Peasant +{ + Default + { + Translation 1; + } +} + +class Peasant13 : Peasant +{ + Default + { + Translation 3; + } +} + +class Peasant14 : Peasant +{ + Default + { + Translation 3; + } +} + +class Peasant15 : Peasant +{ + Default + { + Translation 3; + } +} + +class Peasant16 : Peasant +{ + Default + { + Translation 5; + } +} + +class Peasant17 : Peasant +{ + Default + { + Translation 5; + } +} + +class Peasant18 : Peasant +{ + Default + { + Translation 5; + } +} + +class Peasant19 : Peasant +{ + Default + { + Translation 4; + } +} + +class Peasant20 : Peasant +{ + Default + { + Translation 4; + } +} + +class Peasant21 : Peasant +{ + Default + { + Translation 4; + } +} + +class Peasant22 : Peasant +{ + Default + { + Translation 6; + } +} + diff --git a/wadsrc/static/zscript/strife/programmer.txt b/wadsrc/static/zscript/strife/programmer.txt new file mode 100644 index 000000000..cd577ff13 --- /dev/null +++ b/wadsrc/static/zscript/strife/programmer.txt @@ -0,0 +1,116 @@ + +// Programmer --------------------------------------------------------------- + +class Programmer : Actor +{ + Default + { + Health 1100; + PainChance 50; + Speed 26; + FloatSpeed 5; + Radius 45; + Height 60; + Mass 800; + Damage 4; + Monster; + +NOGRAVITY + +FLOAT + +NOBLOOD + +NOTDMATCH + +DONTMORPH + +NOBLOCKMONST + +LOOKALLAROUND + +NOICEDEATH + +NOTARGETSWITCH + DamageFactor "Fire", 0.5; + MinMissileChance 150; + AttackSound "programmer/attack"; + PainSound "programmer/pain"; + DeathSound "programmer/death"; + ActiveSound "programmer/active"; + Obituary "$OB_PROGRAMMER"; + DropItem "Sigil1"; + } + + action native void A_ProgrammerMelee (); + action native void A_SpawnProgrammerBase (); + action native void A_ProgrammerDeath (); + action native void A_SpotLightning(); + + States + { + Spawn: + PRGR A 5 A_Look; + PRGR A 1 A_SentinelBob; + Loop; + See: + PRGR A 160 A_SentinelBob; + PRGR BCD 5 A_SentinelBob; + PRGR EF 2 A_SentinelBob; + PRGR EF 3 A_Chase; + Goto See+4; + Melee: + PRGR E 2 A_SentinelBob; + PRGR F 3 A_SentinelBob; + PRGR E 3 A_FaceTarget; + PRGR F 4 A_ProgrammerMelee; + Goto See+4; + Missile: + PRGR G 5 A_FaceTarget; + PRGR H 5 A_SentinelBob; + PRGR I 5 Bright A_FaceTarget; + PRGR J 5 Bright A_SpotLightning; + Goto See+4; + Pain: + PRGR K 5 A_Pain; + PRGR L 5 A_SentinelBob; + Goto See+4; + Death: + PRGR L 7 Bright A_TossGib; + PRGR M 7 Bright A_Scream; + PRGR N 7 Bright A_TossGib; + PRGR O 7 Bright A_NoBlocking; + PRGR P 7 Bright A_TossGib; + PRGR Q 7 Bright A_SpawnProgrammerBase; + PRGR R 7 Bright; + PRGR S 6 Bright; + PRGR TUVW 5 Bright; + PRGR X 32 Bright; + PRGR X -1 Bright A_ProgrammerDeath; + Stop; + } +} + + +// The Programmer's base for when he dies ----------------------------------- + +class ProgrammerBase : Actor +{ + Default + { + +NOBLOCKMAP + +NOCLIP + +NOBLOOD + } + States + { + Spawn: + BASE A 5 Bright A_Explode(32,32,1,1); + BASE BCD 5 Bright; + BASE EFG 5; + BASE H -1; + Stop; + } +} + + +// The Programmer level ending thing ---------------------------------------- + +class ProgLevelEnder : Inventory native +{ + Default + { + +INVENTORY.UNDROPPABLE + } +} diff --git a/wadsrc/static/actors/strife/questitems.txt b/wadsrc/static/zscript/strife/questitems.txt similarity index 51% rename from wadsrc/static/actors/strife/questitems.txt rename to wadsrc/static/zscript/strife/questitems.txt index 11da7c90f..4946f0414 100644 --- a/wadsrc/static/actors/strife/questitems.txt +++ b/wadsrc/static/zscript/strife/questitems.txt @@ -16,11 +16,11 @@ * 13 You've freed the prisoners! * 14 You've Blown Up the Crystal * 15 You got the guard uniform - * 16 You've Blown Up the Gates (/Piston) - * 17 You watched the Sigil slideshow on map10 + * 16 You've Blown Up the Gates (/Piston); + * 17 You watched the Sigil slideshow on map10; * 18 You got the Oracle pass * 19 You met Quincy and talked to him about the Bishop - * 20 + * 20; * 21 You Killed the Bishop! * 22 The Oracle has told you to kill Macil * 23 You've Killed The Oracle! @@ -30,146 +30,155 @@ * 27 You've Blown Up the Computer * 28 You got the catacomb key * 29 You destroyed the mind control device in the mines - * 30 - * 31 + * 30; + * 31; */ -ACTOR QuestItem : Inventory +class QuestItem : Inventory { States { Spawn: - TOKN A -1 - Stop + TOKN A -1; + Stop; } } // Quest Items ------------------------------------------------------------- -ACTOR QuestItem1 : QuestItem +class QuestItem1 : QuestItem { } -ACTOR QuestItem2 : QuestItem +class QuestItem2 : QuestItem { } -ACTOR QuestItem3 : QuestItem +class QuestItem3 : QuestItem { } -ACTOR QuestItem4 : QuestItem +class QuestItem4 : QuestItem { - Tag "$TAG_QUEST4" + Default + { + Tag "$TAG_QUEST4"; + } } -ACTOR QuestItem5 : QuestItem +class QuestItem5 : QuestItem { - Tag "$TAG_QUEST5" + Default + { + Tag "$TAG_QUEST5"; + } } -ACTOR QuestItem6 : QuestItem +class QuestItem6 : QuestItem { - Tag "TAG_QUEST6" + Default + { + Tag "TAG_QUEST6"; + } } -ACTOR QuestItem7 : QuestItem +class QuestItem7 : QuestItem { } -ACTOR QuestItem8 : QuestItem +class QuestItem8 : QuestItem { } -ACTOR QuestItem9 : QuestItem +class QuestItem9 : QuestItem { } -ACTOR QuestItem10 : QuestItem +class QuestItem10 : QuestItem { } -ACTOR QuestItem11 : QuestItem +class QuestItem11 : QuestItem { } -ACTOR QuestItem12 : QuestItem +class QuestItem12 : QuestItem { } -ACTOR QuestItem13 : QuestItem +class QuestItem13 : QuestItem { } -ACTOR QuestItem14 : QuestItem +class QuestItem14 : QuestItem { } -ACTOR QuestItem15 : QuestItem +class QuestItem15 : QuestItem { } -ACTOR QuestItem16 : QuestItem +class QuestItem16 : QuestItem { } -ACTOR QuestItem17 : QuestItem +class QuestItem17 : QuestItem { } -ACTOR QuestItem18 : QuestItem +class QuestItem18 : QuestItem { } -ACTOR QuestItem19 : QuestItem +class QuestItem19 : QuestItem { } -ACTOR QuestItem20 : QuestItem +class QuestItem20 : QuestItem { } -ACTOR QuestItem21 : QuestItem +class QuestItem21 : QuestItem { } -ACTOR QuestItem22 : QuestItem +class QuestItem22 : QuestItem { } -ACTOR QuestItem23 : QuestItem +class QuestItem23 : QuestItem { } -ACTOR QuestItem24 : QuestItem +class QuestItem24 : QuestItem { } -ACTOR QuestItem25 : QuestItem +class QuestItem25 : QuestItem { } -ACTOR QuestItem26 : QuestItem +class QuestItem26 : QuestItem { } -ACTOR QuestItem27 : QuestItem +class QuestItem27 : QuestItem { } -ACTOR QuestItem28 : QuestItem +class QuestItem28 : QuestItem { } -ACTOR QuestItem29 : QuestItem +class QuestItem29 : QuestItem { } -ACTOR QuestItem30 : QuestItem +class QuestItem30 : QuestItem { } -ACTOR QuestItem31 : QuestItem +class QuestItem31 : QuestItem { } diff --git a/wadsrc/static/zscript/strife/ratbuddy.txt b/wadsrc/static/zscript/strife/ratbuddy.txt new file mode 100644 index 000000000..fc0c9c63e --- /dev/null +++ b/wadsrc/static/zscript/strife/ratbuddy.txt @@ -0,0 +1,37 @@ + +class RatBuddy : Actor +{ + Default + { + Health 5; + Speed 13; + Radius 10; + Height 16; + +NOBLOOD +FLOORCLIP +CANPASS + +ISMONSTER +INCOMBAT + MinMissileChance 150; + MaxStepHeight 16; + MaxDropoffHeight 32; + Tag "$TAG_RATBUDDY"; + SeeSound "rat/sight"; + DeathSound "rat/death"; + ActiveSound "rat/active"; + } + States + { + Spawn: + RATT A 10 A_Look; + Loop; + See: + RATT AABB 4 A_Chase; + Loop; + Melee: + RATT A 8 A_Wander; + RATT B 4 A_Wander; + Goto See; + Death: + MEAT Q 700; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/reaver.txt b/wadsrc/static/zscript/strife/reaver.txt new file mode 100644 index 000000000..0ce15fab8 --- /dev/null +++ b/wadsrc/static/zscript/strife/reaver.txt @@ -0,0 +1,67 @@ + +class Reaver : Actor +{ + Default + { + Health 150; + Painchance 128; + Speed 12; + Radius 20; + Height 60; + Monster; + +NOBLOOD + +INCOMBAT + MinMissileChance 150; + MaxDropoffHeight 32; + Mass 500; + SeeSound "reaver/sight"; + PainSound "reaver/pain"; + DeathSound "reaver/death"; + ActiveSound "reaver/active"; + HitObituary "$OB_REAVERHIT"; + Obituary "$OB_REAVER"; + } + + action native void A_ReaverRanged (); + + States + { + Spawn: + ROB1 A 10 A_Look; + Loop; + See: + ROB1 BBCCDDEE 3 A_Chase; + Loop; + Melee: + ROB1 H 6 Slow A_FaceTarget; + ROB1 I 8 Slow A_CustomMeleeAttack(random[ReaverMelee](1,8)*3, "reaver/blade"); + ROB1 H 6 Slow; + Goto See; + Missile: + ROB1 F 8 Slow A_FaceTarget; + ROB1 G 11 Slow BRIGHT A_ReaverRanged; + Goto See; + Pain: + ROB1 A 2 Slow; + ROB1 A 2 A_Pain; + Goto See; + Death: + ROB1 J 6; + ROB1 K 6 A_Scream; + ROB1 L 5; + ROB1 M 5 A_NoBlocking; + ROB1 NOP 5; + ROB1 Q 6 A_Explode(32,32,1,1); + ROB1 R -1; + Stop; + XDeath: + ROB1 L 5 A_TossGib; + ROB1 M 5 A_Scream; + ROB1 N 5 A_TossGib; + ROB1 O 5 A_NoBlocking; + ROB1 P 5 A_TossGib; + Goto Death+7; + } + +} + \ No newline at end of file diff --git a/wadsrc/static/zscript/strife/rebels.txt b/wadsrc/static/zscript/strife/rebels.txt new file mode 100644 index 000000000..3ee0200dc --- /dev/null +++ b/wadsrc/static/zscript/strife/rebels.txt @@ -0,0 +1,140 @@ + + +// Base class for the rebels ------------------------------------------------ + +class Rebel : StrifeHumanoid +{ + Default + { + Health 60; + Painchance 250; + Speed 8; + Radius 20; + Height 56; + Monster; + +FRIENDLY + -COUNTKILL + +NOSPLASHALERT + MinMissileChance 150; + Tag "$TAG_REBEL"; + SeeSound "rebel/sight"; + PainSound "rebel/pain"; + DeathSound "rebel/death"; + ActiveSound "rebel/active"; + Obituary "$OB_REBEL"; + } + States + { + Spawn: + HMN1 P 5 A_Look2; + Loop; + HMN1 Q 8; + Loop; + HMN1 R 8; + Loop; + HMN1 ABCDABCD 6 A_Wander; + Loop; + See: + HMN1 AABBCCDD 3 A_Chase; + Loop; + Missile: + HMN1 E 10 A_FaceTarget; + HMN1 F 10 BRIGHT A_ShootGun; + HMN1 E 10 A_ShootGun; + Goto See; + Pain: + HMN1 O 3; + HMN1 O 3 A_Pain; + Goto See; + Death: + HMN1 G 5; + HMN1 H 5 A_Scream; + HMN1 I 3 A_NoBlocking; + HMN1 J 4; + HMN1 KLM 3; + HMN1 N -1; + Stop; + XDeath: + RGIB A 4 A_TossGib; + RGIB B 4 A_XScream; + RGIB C 3 A_NoBlocking; + RGIB DEF 3 A_TossGib; + RGIB G 3; + RGIB H 1400; + Stop; + } +} + +// Rebel 1 ------------------------------------------------------------------ + +class Rebel1 : Rebel +{ + Default + { + DropItem "ClipOfBullets"; + } +} + +// Rebel 2 ------------------------------------------------------------------ + +class Rebel2 : Rebel +{ +} + +// Rebel 3 ------------------------------------------------------------------ + +class Rebel3 : Rebel +{ +} + +// Rebel 4 ------------------------------------------------------------------ + +class Rebel4 : Rebel +{ +} + +// Rebel 5 ------------------------------------------------------------------ + +class Rebel5 : Rebel +{ +} + +// Rebel 6 ------------------------------------------------------------------ + +class Rebel6 : Rebel +{ +} + +// Teleporter Beacon -------------------------------------------------------- + +class TeleporterBeacon : Inventory native +{ + Default + { + Health 5; + Radius 16; + Height 16; + Inventory.MaxAmount 3; + +DROPPED + +INVENTORY.INVBAR + Inventory.Icon "I_BEAC"; + Tag "$TAG_TELEPORTERBEACON"; + Inventory.PickupMessage "$TXT_BEACON"; + } + + action native void A_Beacon (); + + States + { + Spawn: + BEAC A -1; + Stop; + Drop: + BEAC A 30; + BEAC A 160 A_Beacon; + Wait; + Death: + BEAC A 1 A_FadeOut(0.015); + Loop; + } +} \ No newline at end of file diff --git a/wadsrc/static/zscript/strife/sentinel.txt b/wadsrc/static/zscript/strife/sentinel.txt new file mode 100644 index 000000000..8108265cb --- /dev/null +++ b/wadsrc/static/zscript/strife/sentinel.txt @@ -0,0 +1,104 @@ + +// Sentinel ----------------------------------------------------------------- + +class Sentinel : Actor +{ + Default + { + Health 100; + Painchance 255; + Speed 7; + Radius 23; + Height 53; + Mass 300; + Monster; + +SPAWNCEILING + +NOGRAVITY + +DROPOFF + +NOBLOOD + +NOBLOCKMONST + +INCOMBAT + +MISSILEMORE + +LOOKALLAROUND + +NEVERRESPAWN + MinMissileChance 150; + SeeSound "sentinel/sight"; + DeathSound "sentinel/death"; + ActiveSound "sentinel/active"; + Obituary "$OB_SENTINEL"; + } + + action native void A_SentinelAttack (); + + States + { + Spawn: + SEWR A 10 A_Look; + Loop; + See: + SEWR A 6 A_SentinelBob; + SEWR A 6 A_Chase; + Loop; + Missile: + SEWR B 4 A_FaceTarget; + SEWR C 8 Bright A_SentinelAttack; + SEWR C 4 Bright A_SentinelRefire; + Goto Missile+1; + Pain: + SEWR D 5 A_Pain; + Goto Missile+2; + Death: + SEWR D 7 A_Fall; + SEWR E 8 Bright A_TossGib; + SEWR F 5 Bright A_Scream; + SEWR GH 4 Bright A_TossGib; + SEWR I 4; + SEWR J 5; + Stop; + } +} + +// Sentinel FX 1 ------------------------------------------------------------ + +class SentinelFX1 : Actor +{ + Default + { + Speed 40; + Radius 10; + Height 8; + Damage 0; + DamageType "Disintegrate"; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + RenderStyle "Add"; + } + States + { + Spawn: + SHT1 AB 4; + Loop; + Death: + POW1 J 4; + Stop; + } +} + +// Sentinel FX 2 ------------------------------------------------------------ + +class SentinelFX2 : SentinelFX1 +{ + Default + { + SeeSound "sentinel/plasma"; + Damage 1; + } + States + { + Death: + POW1 FGHI 4; + Goto Super::Death; + } +} + diff --git a/wadsrc/static/zscript/strife/sigil.txt b/wadsrc/static/zscript/strife/sigil.txt new file mode 100644 index 000000000..d8b1f80f8 --- /dev/null +++ b/wadsrc/static/zscript/strife/sigil.txt @@ -0,0 +1,178 @@ + +// The Almighty Sigil! ------------------------------------------------------ + +class Sigil : Weapon native +{ + Default + { + Weapon.Kickback 100; + Weapon.SelectionOrder 4000; + Health 1; + +FLOORCLIP + +WEAPON.CHEATNOTWEAPON + Inventory.PickupSound "weapons/sigilcharge"; + Tag "$TAG_SIGIL"; + Inventory.Icon "I_SGL1"; + Inventory.PickupMessage "$TXT_SIGIL"; + } + + action native void A_SelectPiece (); + action native void A_SelectSigilView (); + action native void A_SelectSigilDown (); + action native void A_SelectSigilAttack (); + action native void A_SigilCharge (); + action native void A_FireSigil1 (); + action native void A_FireSigil2 (); + action native void A_FireSigil3 (); + action native void A_FireSigil4 (); + action native void A_FireSigil5 (); + + States + { + Spawn: + SIGL A 1; + SIGL A -1 A_SelectPiece; + Stop; + SIGL B -1; + Stop; + SIGL C -1; + Stop; + SIGL D -1; + Stop; + SIGL E -1; + Stop; + Ready: + SIGH A 0 Bright A_SelectSigilView; + Wait; + SIGH A 1 Bright A_WeaponReady; + Wait; + SIGH B 1 Bright A_WeaponReady; + Wait; + SIGH C 1 Bright A_WeaponReady; + Wait; + SIGH D 1 Bright A_WeaponReady; + Wait; + SIGH E 1 Bright A_WeaponReady; + Wait; + Deselect: + SIGH A 1 Bright A_SelectSigilDown; + Wait; + SIGH A 1 Bright A_Lower; + Wait; + SIGH B 1 Bright A_Lower; + Wait; + SIGH C 1 Bright A_Lower; + Wait; + SIGH D 1 Bright A_Lower; + Wait; + SIGH E 1 Bright A_Lower; + Wait; + Select: + SIGH A 1 Bright A_SelectSigilView; + Wait; + SIGH A 1 Bright A_Raise; + Wait; + SIGH B 1 Bright A_Raise; + Wait; + SIGH C 1 Bright A_Raise; + Wait; + SIGH D 1 Bright A_Raise; + Wait; + SIGH E 1 Bright A_Raise; + Wait; + + Fire: + SIGH A 0 Bright A_SelectSigilAttack; + + SIGH A 18 Bright A_SigilCharge; + SIGH A 3 Bright A_GunFlash; + SIGH A 10 A_FireSigil1; + SIGH A 5; + Goto Ready; + + SIGH B 18 Bright A_SigilCharge; + SIGH B 3 Bright A_GunFlash; + SIGH B 10 A_FireSigil2; + SIGH B 5; + Goto Ready; + + SIGH C 18 Bright A_SigilCharge; + SIGH C 3 Bright A_GunFlash; + SIGH C 10 A_FireSigil3; + SIGH C 5; + Goto Ready; + + SIGH D 18 Bright A_SigilCharge; + SIGH D 3 Bright A_GunFlash; + SIGH D 10 A_FireSigil4; + SIGH D 5; + Goto Ready; + + SIGH E 18 Bright A_SigilCharge; + SIGH E 3 Bright A_GunFlash; + SIGH E 10 A_FireSigil5; + SIGH E 5; + Goto Ready; + Flash: + SIGF A 4 Bright A_Light2; + SIGF B 6 Bright A_LightInverse; + SIGF C 4 Bright A_Light1; + SIGF C 0 Bright A_Light0; + Stop; + } +} + +// Sigil 1 ------------------------------------------------------------------ + +class Sigil1 : Sigil +{ + Default + { + Inventory.Icon "I_SGL1"; + Health 1; + } +} + +// Sigil 2 ------------------------------------------------------------------ + +class Sigil2 : Sigil +{ + Default + { + Inventory.Icon "I_SGL2"; + Health 2; + } +} + +// Sigil 3 ------------------------------------------------------------------ + +class Sigil3 : Sigil +{ + Default + { + Inventory.Icon "I_SGL3"; + Health 3; + } +} + +// Sigil 4 ------------------------------------------------------------------ + +class Sigil4 : Sigil +{ + Default + { + Inventory.Icon "I_SGL4"; + Health 4; + } +} + +// Sigil 5 ------------------------------------------------------------------ + +class Sigil5 : Sigil +{ + Default + { + Inventory.Icon "I_SGL5"; + Health 5; + } +} diff --git a/wadsrc/static/zscript/strife/spectral.txt b/wadsrc/static/zscript/strife/spectral.txt new file mode 100644 index 000000000..df23f3663 --- /dev/null +++ b/wadsrc/static/zscript/strife/spectral.txt @@ -0,0 +1,307 @@ + + +// base for all spectral monsters which hurt when being touched-------------- + +class SpectralMonster : Actor native +{ + Default + { + Monster; + +SPECIAL + +SPECTRAL + +NOICEDEATH + } + + action native void A_SpectreChunkSmall (); + action native void A_SpectreChunkLarge (); + action native void A_Spectre3Attack (); + action native void A_SpotLightning (); +} + + +// Container for all spectral lightning deaths ------------------------------ + +class SpectralLightningBase : Actor +{ + Default + { + +NOTELEPORT + +ACTIVATEIMPACT + +ACTIVATEPCROSS + +STRIFEDAMAGE + MaxStepHeight 4; + RenderStyle "Add"; + SeeSound "weapons/sigil"; + DeathSound "weapons/sigilhit"; + } + States + { + Death: + ZAP1 B 3 A_Explode(32,32); + ZAP1 A 3 A_AlertMonsters; + ZAP1 BCDEFE 3; + ZAP1 DCB 2; + ZAP1 A 1; + Stop; + } +} + +// Spectral Lightning death that does not explode --------------------------- + +class SpectralLightningDeath1 : SpectralLightningBase +{ + States + { + Death: + Goto Super::Death+1; + } +} + +// Spectral Lightning death that does not alert monsters -------------------- + +class SpectralLightningDeath2 : SpectralLightningBase +{ + States + { + Death: + Goto Super::Death+2; + } +} + +// Spectral Lightning death that is shorter than the rest ------------------- + +class SpectralLightningDeathShort : SpectralLightningBase +{ + States + { + Death: + Goto Super::Death+6; + } +} + +// Spectral Lightning (Ball Shaped #1) -------------------------------------- + +class SpectralLightningBall1 : SpectralLightningBase +{ + Default + { + Speed 30; + Radius 8; + Height 16; + Damage 70; + Projectile; + +SPECTRAL + } + States + { + Spawn: + ZOT3 ABCDE 4 Bright; + Loop; + } +} + +// Spectral Lightning (Ball Shaped #2) -------------------------------------- + +class SpectralLightningBall2 : SpectralLightningBall1 +{ + Default + { + Damage 20; + } +} + +// Spectral Lightning (Horizontal #1) --------------------------------------- + +class SpectralLightningH1 : SpectralLightningBase +{ + Default + { + Speed 30; + Radius 8; + Height 16; + Damage 70; + Projectile; + +SPECTRAL + } + + action native void A_SpectralLightningTail (); + + States + { + Spawn: + ZAP6 A 4 Bright; + ZAP6 BC 4 Bright A_SpectralLightningTail; + Loop; + } +} + + +// Spectral Lightning (Horizontal #2) ------------------------------------- + +class SpectralLightningH2 : SpectralLightningH1 +{ + Default + { + Damage 20; + } +} + +// Spectral Lightning (Horizontal #3) ------------------------------------- + +class SpectralLightningH3 : SpectralLightningH1 +{ + Default + { + Damage 10; + } +} + +// ASpectralLightningHTail -------------------------------------------------- + +class SpectralLightningHTail : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +DROPOFF + RenderStyle "Add"; + } + States + { + Spawn: + ZAP6 ABC 5 Bright; + Stop; + } +} + +// Spectral Lightning (Big Ball #1) ----------------------------------------- + +class SpectralLightningBigBall1 : SpectralLightningDeath2 +{ + Default + { + Speed 18; + Radius 20; + Height 40; + Damage 130; + Projectile; + +SPECTRAL + } + + action native void A_SpectralBigBallLightning (); + + States + { + Spawn: + ZAP7 AB 4 Bright A_SpectralBigBallLightning; + ZAP7 CDE 6 Bright A_SpectralBigBallLightning; + Loop; + } +} + + +// Spectral Lightning (Big Ball #2 - less damaging) ------------------------- + +class SpectralLightningBigBall2 : SpectralLightningBigBall1 +{ + Default + { + Damage 30; + } +} + +// Sigil Lightning (Vertical #1) -------------------------------------------- + +class SpectralLightningV1 : SpectralLightningDeathShort +{ + Default + { + Speed 22; + Radius 8; + Height 24; + Damage 100; + Projectile; + DamageType "SpectralLow"; + +SPECTRAL + } + States + { + Spawn: + ZOT1 AB 4 Bright; + ZOT1 CDE 6 Bright; + Loop; + } +} + +// Sigil Lightning (Vertical #2 - less damaging) ---------------------------- + +class SpectralLightningV2 : SpectralLightningV1 +{ + Default + { + Damage 50; + } +} + +// Sigil Lightning Spot (roams around dropping lightning from above) -------- + +class SpectralLightningSpot : SpectralLightningDeath1 +{ + Default + { + Speed 18; + ReactionTime 70; + +NOBLOCKMAP + +NOBLOCKMONST + +NODROPOFF + RenderStyle "Translucent"; + Alpha 0.6; + } + + action native void A_SpectralLightning (); + + States + { + Spawn: + ZAP5 A 4 Bright A_Countdown; + ZAP5 B 4 Bright A_SpectralLightning; + ZAP5 CD 4 Bright A_Countdown; + Loop; + } +} + +// Sigil Lightning (Big Vertical #1) ---------------------------------------- + +class SpectralLightningBigV1 : SpectralLightningDeath1 +{ + Default + { + Speed 28; + Radius 8; + Height 16; + Damage 120; + Projectile; + +SPECTRAL + } + States + { + Spawn: + ZOT2 ABCDE 4 Bright A_Tracer2; + Loop; + } +} + +// Actor 90 ----------------------------------------------------------------- + +class SpectralLightningBigV2 : SpectralLightningBigV1 +{ + Default + { + Damage 60; + } +} + + + + diff --git a/wadsrc/static/zscript/strife/stalker.txt b/wadsrc/static/zscript/strife/stalker.txt new file mode 100644 index 000000000..b22e432c6 --- /dev/null +++ b/wadsrc/static/zscript/strife/stalker.txt @@ -0,0 +1,79 @@ + + +// Stalker ------------------------------------------------------------------ + +class Stalker : Actor +{ + Default + { + Health 80; + Painchance 40; + Speed 16; + Radius 31; + Height 25; + Monster; + +NOGRAVITY + +DROPOFF + +NOBLOOD + +SPAWNCEILING + +INCOMBAT + +NOVERTICALMELEERANGE + MaxDropOffHeight 32; + MinMissileChance 150; + SeeSound "stalker/sight"; + AttackSound "stalker/attack"; + PainSound "stalker/pain"; + DeathSound "stalker/death"; + ActiveSound "stalker/active"; + HitObituary "$OB_STALKER"; + } + + action native void A_StalkerLookInit (); + action native void A_StalkerChaseDecide (); + action native void A_StalkerWalk (); + action native void A_StalkerDrop (); + action native void A_StalkerAttack (); + + States + { + Spawn: + STLK A 1 A_StalkerLookInit; + Loop; + LookCeiling: + STLK A 10 A_Look; + Loop; + LookFloor: + STLK J 10 A_Look; + Loop; + See: + STLK A 1 Slow A_StalkerChaseDecide; + STLK ABB 3 Slow A_Chase; + STLK C 3 Slow A_StalkerWalk; + STLK C 3 Slow A_Chase; + Loop; + Melee: + STLK J 3 Slow A_FaceTarget; + STLK K 3 Slow A_StalkerAttack; + SeeFloor: + STLK J 3 A_StalkerWalk; + STLK KK 3 A_Chase; + STLK L 3 A_StalkerWalk; + STLK L 3 A_Chase; + Loop; + Pain: + STLK L 1 A_Pain; + Goto See; + Drop: + STLK C 2 A_StalkerDrop; + STLK IHGFED 3; + Goto SeeFloor; + Death: + STLK O 4; + STLK P 4 A_Scream; + STLK QRST 4; + STLK U 4 A_NoBlocking; + STLK VW 4; + STLK "XYZ[" 4 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/strife/strifeammo.txt b/wadsrc/static/zscript/strife/strifeammo.txt new file mode 100644 index 000000000..dcc31b2c7 --- /dev/null +++ b/wadsrc/static/zscript/strife/strifeammo.txt @@ -0,0 +1,235 @@ +// HE-Grenade Rounds -------------------------------------------------------- + +class HEGrenadeRounds : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 6; + Inventory.MaxAmount 30; + Ammo.BackpackAmount 6; + Ammo.BackpackMaxAmount 60; + Inventory.Icon "I_GRN1"; + Tag "$TAG_HEGRENADES"; + Inventory.PickupMessage "$TXT_HEGRENADES"; + } + States + { + Spawn: + GRN1 A -1; + Stop; + } +} + +// Phosphorus-Grenade Rounds ------------------------------------------------ + +class PhosphorusGrenadeRounds : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 4; + Inventory.MaxAmount 16; + Ammo.BackpackAmount 4; + Ammo.BackpackMaxAmount 32; + Inventory.Icon "I_GRN2"; + Tag "$TAG_PHGRENADES"; + Inventory.PickupMessage "$TXT_PHGRENADES"; + } + States + { + Spawn: + GRN2 A -1; + Stop; + } +} + +// Clip of Bullets ---------------------------------------------------------- + +class ClipOfBullets : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 10; + Inventory.MaxAmount 250; + Ammo.BackpackAmount 10; + Ammo.BackpackMaxAmount 500; + Inventory.Icon "I_BLIT"; + Tag "$TAG_CLIPOFBULLETS"; + Inventory.PickupMessage "$TXT_CLIPOFBULLETS"; + } + States + { + Spawn: + BLIT A -1; + Stop; + } +} + +// Box of Bullets ----------------------------------------------------------- + +class BoxOfBullets : ClipOfBullets +{ + Default + { + Inventory.Amount 50; + Tag "$TAG_BOXOFBULLETS"; + Inventory.PickupMessage "$TXT_BOXOFBULLETS"; + } + States + { + Spawn: + BBOX A -1; + Stop; + } +} + +// Mini Missiles ------------------------------------------------------------ + +class MiniMissiles : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 4; + Inventory.MaxAmount 100; + Ammo.BackpackAmount 4; + Ammo.BackpackMaxAmount 200; + Inventory.Icon "I_ROKT"; + Tag "$TAG_MINIMISSILES"; + Inventory.PickupMessage "$TXT_MINIMISSILES"; + } + States + { + Spawn: + MSSL A -1; + Stop; + } +} + +// Crate of Missiles -------------------------------------------------------- + +class CrateOfMissiles : MiniMissiles +{ + Default + { + Inventory.Amount 20; + Tag "$TAG_CRATEOFMISSILES"; + Inventory.PickupMessage "$TXT_CRATEOFMISSILES"; + } + States + { + Spawn: + ROKT A -1; + Stop; + } +} + +// Energy Pod --------------------------------------------------------------- + +class EnergyPod : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 20; + Inventory.MaxAmount 400; + Ammo.BackpackAmount 20; + Ammo.BackpackMaxAmount 800; + Ammo.DropAmount 20; + Inventory.Icon "I_BRY1"; + Tag "$TAG_ENERGYPOD"; + Inventory.PickupMessage "$TXT_ENERGYPOD"; + } + States + { + Spawn: + BRY1 AB 6; + Loop; + } +} + +// Energy pack --------------------------------------------------------------- + +class EnergyPack : EnergyPod +{ + Default + { + Inventory.Amount 100; + Tag "$TAG_ENERGYPACK"; + Inventory.PickupMessage "$TXT_ENERGYPACK"; + } + States + { + Spawn: + CPAC AB 6; + Loop; + } +} + +// Poison Bolt Quiver ------------------------------------------------------- + +class PoisonBolts : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 10; + Inventory.MaxAmount 25; + Ammo.BackpackAmount 2; + Ammo.BackpackMaxAmount 50; + Inventory.Icon "I_PQRL"; + Tag "$TAG_POISONBOLTS"; + Inventory.PickupMessage "$TXT_POISONBOLTS"; + } + States + { + Spawn: + PQRL A -1; + Stop; + } +} + +// Electric Bolt Quiver ------------------------------------------------------- + +class ElectricBolts : Ammo +{ + Default + { + +FLOORCLIP + Inventory.Amount 20; + Inventory.MaxAmount 50; + Ammo.BackpackAmount 4; + Ammo.BackpackMaxAmount 100; + Inventory.Icon "I_XQRL"; + Tag "$TAG_ELECTRICBOLTS"; + Inventory.PickupMessage "$TXT_ELECTRICBOLTS"; + } + States + { + Spawn: + XQRL A -1; + Stop; + } +} + +// Ammo Satchel ------------------------------------------------------------- + +class AmmoSatchel : BackpackItem +{ + Default + { + +FLOORCLIP + Inventory.Icon "I_BKPK"; + Tag "$TAG_AMMOSATCHEL"; + Inventory.PickupMessage "$TXT_AMMOSATCHEL"; + } + States + { + Spawn: + BKPK A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/strifearmor.txt b/wadsrc/static/zscript/strife/strifearmor.txt new file mode 100644 index 000000000..8d2c7fad5 --- /dev/null +++ b/wadsrc/static/zscript/strife/strifearmor.txt @@ -0,0 +1,49 @@ + +class MetalArmor : BasicArmorPickup +{ + Default + { + Radius 20; + Height 16; + +FLOORCLIP + +INVENTORY.AUTOACTIVATE + +INVENTORY.INVBAR + Inventory.MaxAmount 3; + Inventory.Icon "I_ARM1"; + Inventory.PickupMessage "$TXT_METALARMOR"; + Armor.SaveAmount 200; + Armor.SavePercent 50; + Tag "$TAG_METALARMOR"; + } + States + { + Spawn: + ARM3 A -1; + Stop; + } +} + +class LeatherArmor : BasicArmorPickup +{ + Default + { + Radius 20; + Height 16; + +FLOORCLIP + +INVENTORY.AUTOACTIVATE + +INVENTORY.INVBAR + Inventory.MaxAmount 5; + Inventory.Icon "I_ARM2"; + Inventory.PickupMessage "$TXT_LEATHERARMOR"; + Armor.SaveAmount 100; + Armor.SavePercent 33.335; + Tag "$TAG_LEATHER"; + } + States + { + Spawn: + ARM4 A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/strifebishop.txt b/wadsrc/static/zscript/strife/strifebishop.txt new file mode 100644 index 000000000..98b09ecee --- /dev/null +++ b/wadsrc/static/zscript/strife/strifebishop.txt @@ -0,0 +1,99 @@ + +// Bishop ------------------------------------------------------------------- + +class StrifeBishop : Actor +{ + Default + { + Health 500; + Painchance 128; + Speed 8; + Radius 40; + Height 56; + Mass 500; + Monster; + +NOBLOOD + +NOTDMATCH + +FLOORCLIP + +INCOMBAT + +NOICEDEATH + +NEVERRESPAWN + DamageFactor "Fire", 0.5; + MinMissileChance 150; + MaxDropoffHeight 32; + SeeSound "bishop/sight"; + PainSound "bishop/pain"; + DeathSound "bishop/death"; + ActiveSound "bishop/active"; + DropItem "CrateOfMissiles", 256, 20; + Obituary "$OB_STFBISHOP"; + } + States + { + Spawn: + MLDR A 10 A_Look; + Loop; + See: + MLDR AABBCCDD 3 A_Chase; + Loop; + Missile: + MLDR E 3 A_FaceTarget; + MLDR F 2 Bright A_CustomMissile("BishopMissile", 64, 0, 0, CMF_AIMOFFSET); + Goto See; + Pain: + MLDR D 1 A_Pain; + Goto See; + Death: + MLDR G 3 Bright; + MLDR H 5 Bright A_Scream; + MLDR I 4 Bright A_TossGib; + MLDR J 4 Bright A_Explode(64,64,1,1); + MLDR KL 3 Bright; + MLDR M 4 Bright A_NoBlocking; + MLDR N 4 Bright; + MLDR O 4 Bright A_TossGib; + MLDR P 4 Bright; + MLDR Q 4 Bright A_TossGib; + MLDR R 4 Bright; + MLDR S 4 Bright A_TossGib; + MLDR T 4 Bright; + MLDR U 4 Bright A_TossGib; + MLDR V 4 Bright A_SpawnItemEx("AlienSpectre2", 0, 0, 0, 0, 0, random[spectrespawn](0,255)*0.0078125, 0, SXF_NOCHECKPOSITION); + Stop; + } +} + + +// The Bishop's missile ----------------------------------------------------- + +class BishopMissile : Actor +{ + Default + { + Speed 20; + Radius 10; + Height 14; + Damage 10; + Projectile; + +SEEKERMISSILE + +STRIFEDAMAGE + MaxStepHeight 4; + SeeSound "bishop/misl"; + DeathSound "bishop/mislx"; + } + States + { + Spawn: + MISS A 4 Bright A_RocketInFlight; + MISS B 3 Bright A_Tracer2; + Loop; + Death: + SMIS A 0 Bright A_SetTranslucent(1,1); + SMIS A 5 Bright A_Explode(64,64,1,1); + SMIS B 5 Bright; + SMIS C 4 Bright; + SMIS DEFG 2 Bright; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/strifehumanoid.txt b/wadsrc/static/zscript/strife/strifehumanoid.txt new file mode 100644 index 000000000..7ac776026 --- /dev/null +++ b/wadsrc/static/zscript/strife/strifehumanoid.txt @@ -0,0 +1,58 @@ + +// Humanoid Base Class ------------------------------------------------------ + + +class StrifeHumanoid : Actor +{ + Default + { + MaxStepHeight 16; + MaxDropoffHeight 32; + CrushPainSound "misc/pcrush"; + } + States + { + Burn: + BURN A 3 Bright A_PlaySound("human/imonfire", CHAN_VOICE); + BURN B 3 Bright A_DropFire; + BURN C 3 Bright A_Wander; + BURN D 3 Bright A_NoBlocking; + BURN E 5 Bright A_DropFire; + BURN FGH 5 Bright A_Wander; + BURN I 5 Bright A_DropFire; + BURN JKL 5 Bright A_Wander; + BURN M 5 Bright A_DropFire; + BURN N 5 Bright; + BURN OPQPQ 5 Bright; + BURN RSTU 7 Bright; + BURN V -1; + Stop; + Disintegrate: + DISR A 5 A_PlaySound("misc/disruptordeath", CHAN_VOICE); + DISR BC 5; + DISR D 5 A_NoBlocking; + DISR EF 5; + DISR GHIJ 4; + MEAT D 700; + Stop; + } +} + +// Fire Droplet ------------------------------------------------------------- + +class FireDroplet : Actor +{ + Default + { + +NOBLOCKMAP + +NOCLIP + } + States + { + Spawn: + FFOT ABCD 9 Bright; + Stop; + } +} + + diff --git a/wadsrc/static/zscript/strife/strifeitems.txt b/wadsrc/static/zscript/strife/strifeitems.txt new file mode 100644 index 000000000..3d8b4af54 --- /dev/null +++ b/wadsrc/static/zscript/strife/strifeitems.txt @@ -0,0 +1,597 @@ +// Med patch ----------------------------------------------------------------- + +class MedPatch : HealthPickup +{ + Default + { + Health 10; + +FLOORCLIP + +INVENTORY.INVBAR + Inventory.MaxAmount 20; + Tag "$TAG_MEDPATCH"; + Inventory.Icon "I_STMP"; + Inventory.PickupMessage "$TXT_MEDPATCH"; + HealthPickup.Autouse 3; + } + States + { + Spawn: + STMP A -1; + Stop; + } +} + + +// Medical Kit --------------------------------------------------------------- + +class MedicalKit : HealthPickup +{ + Default + { + Health 25; + +FLOORCLIP + +INVENTORY.INVBAR + Inventory.MaxAmount 15; + Tag "$TAG_MEDICALKIT"; + Inventory.Icon "I_MDKT"; + Inventory.PickupMessage "$TXT_MEDICALKIT"; + HealthPickup.Autouse 3; + } + States + { + Spawn: + MDKT A -1; + Stop; + } +} + + +// Surgery Kit -------------------------------------------------------------- + +class SurgeryKit : HealthPickup +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + Health -100; + Inventory.MaxAmount 5; + Tag "$TAG_SURGERYKIT"; + Inventory.Icon "I_FULL"; + Inventory.PickupMessage "$TXT_SURGERYKIT"; + } + States + { + Spawn: + FULL AB 35; + Loop; + } +} + + +// StrifeMap ---------------------------------------------------------------- + +class StrifeMap : MapRevealer +{ + Default + { + +FLOORCLIP + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_STRIFEMAP"; + } + States + { + Spawn: + SMAP AB 6 Bright; + Loop; + } +} + + +// Beldin's Ring ------------------------------------------------------------ + +class BeldinsRing : Inventory +{ + Default + { + +NOTDMATCH + +FLOORCLIP + +INVENTORY.INVBAR + Tag "$TAG_BELDINSRING"; + Inventory.Icon "I_RING"; + Inventory.GiveQuest 1; + Inventory.PickupMessage "$TXT_BELDINSRING"; + } + States + { + Spawn: + RING A -1; + Stop; + } +} + + +// Offering Chalice --------------------------------------------------------- + +class OfferingChalice : Inventory +{ + Default + { + +DROPPED + +FLOORCLIP + +INVENTORY.INVBAR + Radius 10; + Height 16; + Tag "$TAG_OFFERINGCHALICE"; + Inventory.Icon "I_RELC"; + Inventory.PickupMessage "$TXT_OFFERINGCHALICE"; + Inventory.GiveQuest 2; + } + States + { + Spawn: + RELC A -1; + Stop; + } +} + + +// Ear ---------------------------------------------------------------------- + +class Ear : Inventory +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + Tag "$TAG_EAR"; + Inventory.Icon "I_EARS"; + Inventory.PickupMessage "$TXT_EAR"; + Inventory.GiveQuest 9; + } + States + { + Spawn: + EARS A -1; + Stop; + } +} + + +// Broken Power Coupling ---------------------------------------------------- + +class BrokenPowerCoupling : Inventory +{ + Default + { + Health 40; + +DROPPED + +FLOORCLIP + +INVENTORY.INVBAR + Radius 16; + Height 16; + Tag "$TAG_BROKENCOUPLING"; + Inventory.MaxAmount 1; + Inventory.Icon "I_COUP"; + Inventory.PickupMessage "$TXT_BROKENCOUPLING"; + Inventory.GiveQuest 8; + } + States + { + Spawn: + COUP C -1; + Stop; + } +} + + +// Shadow Armor ------------------------------------------------------------- + +class ShadowArmor : PowerupGiver +{ + Default + { + +FLOORCLIP + +VISIBILITYPULSE + +INVENTORY.INVBAR + -INVENTORY.FANCYPICKUPSOUND + RenderStyle "Translucent"; + Tag "$TAG_SHADOWARMOR"; + Inventory.MaxAmount 2; + Powerup.Type "Shadow"; + Inventory.Icon "I_SHD1"; + Inventory.PickupSound "misc/i_pkup"; + Inventory.PickupMessage "$TXT_SHADOWARMOR"; + } + States + { + Spawn: + SHD1 A -1 Bright; + Stop; + } +} + + +// Environmental suit ------------------------------------------------------- + +class EnvironmentalSuit : PowerupGiver +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + -INVENTORY.FANCYPICKUPSOUND + Inventory.MaxAmount 5; + Powerup.Type "Mask"; + Tag "$TAG_ENVSUIT"; + Inventory.Icon "I_MASK"; + Inventory.PickupSound "misc/i_pkup"; + Inventory.PickupMessage "$TXT_ENVSUIT"; + } + States + { + Spawn: + MASK A -1; + Stop; + } +} + + +// Guard Uniform ------------------------------------------------------------ + +class GuardUniform : Inventory +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + Tag "$TAG_GUARDUNIFORM"; + Inventory.Icon "I_UNIF"; + Inventory.PickupMessage "$TXT_GUARDUNIFORM"; + Inventory.GiveQuest 15; + } + States + { + Spawn: + UNIF A -1; + Stop; + } +} + + +// Officer's Uniform -------------------------------------------------------- + +class OfficersUniform : Inventory +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + Tag "$TAG_OFFICERSUNIFORM"; + Inventory.Icon "I_OFIC"; + Inventory.PickupMessage "$TXT_OFFICERSUNIFORM"; + } + States + { + Spawn: + OFIC A -1; + Stop; + } +} + + +// Flame Thrower Parts ------------------------------------------------------ + +class FlameThrowerParts : Inventory +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + Inventory.Icon "I_BFLM"; + Tag "$TAG_FTHROWERPARTS"; + Inventory.PickupMessage "$TXT_FTHROWERPARTS"; + } + States + { + Spawn: + BFLM A -1; + Stop; + } +} + +// InterrogatorReport ------------------------------------------------------- +// SCRIPT32 in strife0.wad has an Acolyte that drops this, but I couldn't +// find that Acolyte in the map. It seems to be totally unused in the +// final game. + +class InterrogatorReport : Inventory +{ + Default + { + +FLOORCLIP + Tag "$TAG_REPORT"; + Inventory.PickupMessage "$TXT_REPORT"; + } + States + { + Spawn: + TOKN A -1; + Stop; + } +} + + +// Info --------------------------------------------------------------------- + +class Info : Inventory +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + Tag "$TAG_INFO"; + Inventory.Icon "I_TOKN"; + Inventory.PickupMessage "$TXT_INFO"; + } + States + { + Spawn: + TOKN A -1; + Stop; + } +} + + +// Targeter ----------------------------------------------------------------- + +class Targeter : PowerupGiver +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + -INVENTORY.FANCYPICKUPSOUND + Tag "$TAG_TARGETER"; + Powerup.Type "Targeter"; + Inventory.MaxAmount 5; + Inventory.Icon "I_TARG"; + Inventory.PickupSound "misc/i_pkup"; + Inventory.PickupMessage "$TXT_TARGETER"; + } + States + { + Spawn: + TARG A -1; + Stop; + } +} + +// Communicator ----------------------------------------------------------------- + +class Communicator : Inventory +{ + Default + { + +NOTDMATCH + Tag "$TAG_COMMUNICATOR"; + Inventory.Icon "I_COMM"; + Inventory.PickupSound "misc/p_pkup"; + Inventory.PickupMessage "$TXT_COMMUNICATOR"; + } + States + { + Spawn: + COMM A -1; + Stop; + } +} + +// Degnin Ore --------------------------------------------------------------- + +class DegninOre : Inventory native +{ + Default + { + Health 10; + Radius 16; + Height 16; + Inventory.MaxAmount 10; + +SOLID + +SHOOTABLE + +NOBLOOD + +FLOORCLIP + +INCOMBAT + +INVENTORY.INVBAR + Tag "$TAG_DEGNINORE"; + DeathSound "ore/explode"; + Inventory.Icon "I_XPRK"; + Inventory.PickupMessage "$TXT_DEGNINORE"; + } + States + { + Spawn: + XPRK A -1; + Stop; + Death: + XPRK A 1 A_RemoveForceField; + BNG3 A 0 A_SetTranslucent(1,1); + BNG3 A 0 A_Scream; + BNG3 A 3 Bright A_Explode(192,192,1,1); + BNG3 BCDEFGH 3 Bright; + Stop; + } +} + +// Gun Training ------------------------------------------------------------- + +class GunTraining : Inventory +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + +INVENTORY.UNDROPPABLE + Inventory.MaxAmount 100; + Tag "$TAG_GUNTRAINING"; + Inventory.Icon "I_GUNT"; + } + States + { + Spawn: + GUNT A -1; + Stop; + } +} + +// Health Training ---------------------------------------------------------- + +class HealthTraining : Inventory native +{ + Default + { + +FLOORCLIP + +INVENTORY.INVBAR + +INVENTORY.UNDROPPABLE + Inventory.MaxAmount 100; + Tag "$TAG_HEALTHTRAINING"; + Inventory.Icon "I_HELT"; + } + States + { + Spawn: + HELT A -1; + Stop; + } +} + + + +// Scanner ------------------------------------------------------------------ + +class Scanner : PowerupGiver native +{ + Default + { + +FLOORCLIP + +INVENTORY.FANCYPICKUPSOUND + Inventory.MaxAmount 1; + Tag "$TAG_SCANNER"; + Inventory.Icon "I_PMUP"; + Powerup.Type "Scanner"; + Inventory.PickupSound "misc/i_pkup"; + Inventory.PickupMessage "$TXT_SCANNER"; + } + States + { + Spawn: + PMUP AB 6; + Loop; + } +} + +// Prison Pass -------------------------------------------------------------- + +class PrisonPass : Key native +{ + Default + { + Inventory.Icon "I_TOKN"; + Tag "$TAG_PRISONPASS"; + Inventory.PickupMessage "$TXT_PRISONPASS"; + } + States + { + Spawn: + TOKN A -1; + Stop; + } +} + +//--------------------------------------------------------------------------- +// Dummy items. They are just used by Strife to perform --------------------- +// actions and cannot be held. ---------------------------------------------- +//--------------------------------------------------------------------------- + +class DummyStrifeItem : Inventory native +{ + States + { + Spawn: + TOKN A -1; + Stop; + } +} + +// Sound the alarm! --------------------------------------------------------- + +class RaiseAlarm : DummyStrifeItem native +{ + Default + { + Tag "$TAG_ALARM"; + } +} + +// Open door tag 222 -------------------------------------------------------- + +class OpenDoor222 : DummyStrifeItem native +{ +} + +// Close door tag 222 ------------------------------------------------------- + +class CloseDoor222 : DummyStrifeItem native +{ +} + +// Open door tag 224 -------------------------------------------------------- + +class OpenDoor224 : DummyStrifeItem native +{ +} + +// Ammo --------------------------------------------------------------------- + +class AmmoFillup : DummyStrifeItem native +{ + Default + { + Tag "$TAG_AMMOFILLUP"; + } +} + +// Health ------------------------------------------------------------------- + +class HealthFillup : DummyStrifeItem native +{ + Default + { + Tag "$TAG_HEALTHFILLUP"; + } +} + +// Upgrade Stamina ---------------------------------------------------------- + +class UpgradeStamina : DummyStrifeItem native +{ + Default + { + Inventory.Amount 10; + Inventory.MaxAmount 100; + } +} + +// Upgrade Accuracy --------------------------------------------------------- + +class UpgradeAccuracy : DummyStrifeItem native +{ +} + +// Start a slideshow -------------------------------------------------------- + +class SlideshowStarter : DummyStrifeItem native +{ +} + + diff --git a/wadsrc/static/zscript/strife/strifekeys.txt b/wadsrc/static/zscript/strife/strifekeys.txt new file mode 100644 index 000000000..024144384 --- /dev/null +++ b/wadsrc/static/zscript/strife/strifekeys.txt @@ -0,0 +1,547 @@ +class StrifeKey : Key +{ + Default + { + Radius 20; + Height 16; + +NOTDMATCH + +FLOORCLIP + } +} + +// Base Key ----------------------------------------------------------------- + +class BaseKey : StrifeKey +{ + Default + { + Inventory.Icon "I_FUSL"; + Tag "$TAG_BASEKEY"; + Inventory.PickupMessage "$TXT_BASEKEY"; + } + States + { + Spawn: + FUSL A -1; + Stop; + } +} + + +// Govs Key ----------------------------------------------------------------- + +class GovsKey : StrifeKey +{ + Default + { + Inventory.Icon "I_REBL"; + Tag "$TAG_GOVSKEY"; + Inventory.PickupMessage "$TXT_GOVSKEY"; + } + States + { + Spawn: + REBL A -1; + Stop; + } +} + + +// Passcard ----------------------------------------------------------------- + +class Passcard : StrifeKey +{ + Default + { + Inventory.Icon "I_TPAS"; + Tag "$TAG_PASSCARD"; + Inventory.PickupMessage "$TXT_PASSCARD"; + } + States + { + Spawn: + TPAS A -1; + Stop; + } +} + + +// ID Badge ----------------------------------------------------------------- + +class IDBadge : StrifeKey +{ + Default + { + Inventory.Icon "I_CRD1"; + Tag "$TAG_IDBADGE"; + Inventory.PickupMessage "$TXT_IDBADGE"; + } + States + { + Spawn: + CRD1 A -1; + Stop; + } +} + + +// Prison Key --------------------------------------------------------------- + +class PrisonKey : StrifeKey +{ + Default + { + Inventory.Icon "I_PRIS"; + Tag "$TAG_PRISONKEY"; + Inventory.GiveQuest 11; + Inventory.PickupMessage "$TXT_PRISONKEY"; + } + States + { + Spawn: + PRIS A -1; + Stop; + } +} + + +// Severed Hand ------------------------------------------------------------- + +class SeveredHand : StrifeKey +{ + Default + { + Inventory.Icon "I_HAND"; + Tag "$TAG_SEVEREDHAND"; + Inventory.GiveQuest 12; + Inventory.PickupMessage "$TXT_SEVEREDHAND"; + } + States + { + Spawn: + HAND A -1; + Stop; + } +} + + +// Power1 Key --------------------------------------------------------------- + +class Power1Key : StrifeKey +{ + Default + { + Inventory.Icon "I_PWR1"; + Tag "$TAG_POWER1KEY"; + Inventory.PickupMessage "$TXT_POWER1KEY"; + } + States + { + Spawn: + PWR1 A -1; + Stop; + } +} + + +// Power2 Key --------------------------------------------------------------- + +class Power2Key : StrifeKey +{ + Default + { + Inventory.Icon "I_PWR2"; + Tag "$TAG_POWER2KEY"; + Inventory.PickupMessage "$TXT_POWER2KEY"; + } + States + { + Spawn: + PWR2 A -1; + Stop; + } +} + + +// Power3 Key --------------------------------------------------------------- + +class Power3Key : StrifeKey +{ + Default + { + Inventory.Icon "I_PWR3"; + Tag "$TAG_POWER3KEY"; + Inventory.PickupMessage "$TXT_POWER3KEY"; + } + States + { + Spawn: + PWR3 A -1; + Stop; + } +} + + +// Gold Key ----------------------------------------------------------------- + +class GoldKey : StrifeKey +{ + Default + { + Inventory.Icon "I_KY1G"; + Tag "$TAG_GOLDKEY"; + Inventory.PickupMessage "$TXT_GOLDKEY"; + } + States + { + Spawn: + KY1G A -1; + Stop; + } +} + + +// ID Card ------------------------------------------------------------------ + +class IDCard : StrifeKey +{ + Default + { + Inventory.Icon "I_CRD2"; + Tag "$TAG_IDCARD"; + Inventory.PickupMessage "$TXT_IDCARD"; + } + States + { + Spawn: + CRD2 A -1; + Stop; + } +} + + +// Silver Key --------------------------------------------------------------- + +class SilverKey : StrifeKey +{ + Default + { + Inventory.Icon "I_KY2S"; + Tag "$TAG_SILVERKEY"; + Inventory.PickupMessage "$TXT_SILVERKEY"; + } + States + { + Spawn: + KY2S A -1; + Stop; + } +} + + +// Oracle Key --------------------------------------------------------------- + +class OracleKey : StrifeKey +{ + Default + { + Inventory.Icon "I_ORAC"; + Tag "$TAG_ORACLEKEY"; + Inventory.PickupMessage "$TXT_ORACLEKEY"; + } + States + { + Spawn: + ORAC A -1; + Stop; + } +} + + +// Military ID -------------------------------------------------------------- + +class MilitaryID : StrifeKey +{ + Default + { + Inventory.Icon "I_GYID"; + Tag "$TAG_MILITARYID"; + Inventory.PickupMessage "$TXT_MILITARYID"; + } + States + { + Spawn: + GYID A -1; + Stop; + } +} + + +// Order Key ---------------------------------------------------------------- + +class OrderKey : StrifeKey +{ + Default + { + Inventory.Icon "I_FUBR"; + Tag "$TAG_ORDERKEY"; + Inventory.PickupMessage "$TXT_ORDERKEY"; + } + States + { + Spawn: + FUBR A -1; + Stop; + } +} + + +// Warehouse Key ------------------------------------------------------------ + +class WarehouseKey : StrifeKey +{ + Default + { + Inventory.Icon "I_WARE"; + Tag "$TAG_WAREHOUSEKEY"; + Inventory.PickupMessage "$TXT_WAREHOUSEKEY"; + } + States + { + Spawn: + WARE A -1; + Stop; + } +} + + +// Brass Key ---------------------------------------------------------------- + +class BrassKey : StrifeKey +{ + Default + { + Inventory.Icon "I_KY3B"; + Tag "$TAG_BRASSKEY"; + Inventory.PickupMessage "$TXT_BRASSKEY"; + } + States + { + Spawn: + KY3B A -1; + Stop; + } +} + + +// Red Crystal Key ---------------------------------------------------------- + +class RedCrystalKey : StrifeKey +{ + Default + { + Inventory.Icon "I_RCRY"; + Tag "$TAG_REDCRYSTALKEY"; + Inventory.PickupMessage "$TXT_REDCRYSTAL"; + } + States + { + Spawn: + RCRY A -1 Bright; + Stop; + } +} + + +// Blue Crystal Key --------------------------------------------------------- + +class BlueCrystalKey : StrifeKey +{ + Default + { + Inventory.Icon "I_BCRY"; + Tag "$TAG_BLUECRYSTALKEY"; + Inventory.PickupMessage "$TXT_BLUECRYSTAL"; + } + States + { + Spawn: + BCRY A -1 Bright; + Stop; + } +} + + +// Chapel Key --------------------------------------------------------------- + +class ChapelKey : StrifeKey +{ + Default + { + Inventory.Icon "I_CHAP"; + Tag "$TAG_CHAPELKEY"; + Inventory.PickupMessage "$TXT_CHAPELKEY"; + } + States + { + Spawn: + CHAP A -1; + Stop; + } +} + + +// Catacomb Key ------------------------------------------------------------- + +class CatacombKey : StrifeKey +{ + Default + { + Inventory.Icon "I_TUNL"; + Tag "$TAG_CATACOMBKEY"; + Inventory.GiveQuest 28; + Inventory.PickupMessage "$TXT_CATACOMBKEY"; + } + States + { + Spawn: + TUNL A -1; + Stop; + } +} + + +// Security Key ------------------------------------------------------------- + +class SecurityKey : StrifeKey +{ + Default + { + Inventory.Icon "I_SECK"; + Tag "$TAG_SECURITYKEY"; + Inventory.PickupMessage "$TXT_SECURITYKEY"; + } + States + { + Spawn: + SECK A -1; + Stop; + } +} + + +// Core Key ----------------------------------------------------------------- + +class CoreKey : StrifeKey +{ + Default + { + Inventory.Icon "I_GOID"; + Tag "$TAG_COREKEY"; + Inventory.PickupMessage "$TXT_COREKEY"; + } + States + { + Spawn: + GOID A -1; + Stop; + } +} + + +// Mauler Key --------------------------------------------------------------- + +class MaulerKey : StrifeKey +{ + Default + { + Inventory.Icon "I_BLTK"; + Tag "$TAG_MAULERKEY"; + Inventory.PickupMessage "$TXT_MAULERKEY"; + } + States + { + Spawn: + BLTK A -1; + Stop; + } +} + + +// Factory Key -------------------------------------------------------------- + +class FactoryKey : StrifeKey +{ + Default + { + Inventory.Icon "I_PROC"; + Tag "$TAG_FACTORYKEY"; + Inventory.PickupMessage "$TXT_FACTORYKEY"; + } + States + { + Spawn: + PROC A -1; + Stop; + } +} + + +// Mine Key ----------------------------------------------------------------- + +class MineKey : StrifeKey +{ + Default + { + Inventory.Icon "I_MINE"; + Tag "$TAG_MINEKEY"; + Inventory.PickupMessage "$TXT_MINEKEY"; + } + States + { + Spawn: + MINE A -1; + Stop; + } +} + + +// New Key5 ----------------------------------------------------------------- + +class NewKey5 : StrifeKey +{ + Default + { + Inventory.Icon "I_BLTK"; + Tag "$TAG_NEWKEY5"; + Inventory.PickupMessage "$TXT_NEWKEY5"; + } + States + { + Spawn: + BLTK A -1; + Stop; + } +} + + +// Oracle Pass -------------------------------------------------------------- + +class OraclePass : Inventory +{ + Default + { + +INVENTORY.INVBAR + Inventory.Icon "I_OTOK"; + Inventory.GiveQuest 18; + Inventory.PickupMessage "$TXT_ORACLEPASS"; + Tag "$TAG_ORACLEPASS"; + } + States + { + Spawn: + OTOK A -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/strifeplayer.txt b/wadsrc/static/zscript/strife/strifeplayer.txt new file mode 100644 index 000000000..311bf308a --- /dev/null +++ b/wadsrc/static/zscript/strife/strifeplayer.txt @@ -0,0 +1,105 @@ +// The player --------------------------------------------------------------- + +class StrifePlayer : PlayerPawn +{ + Default + { + Health 100; + Radius 18; + Height 56; + Mass 100; + PainChance 255; + Speed 1; + MaxStepHeight 16; + CrushPainSound "misc/pcrush"; + Player.DisplayName "Rebel"; + Player.StartItem "PunchDagger"; + Player.RunHealth 15; + Player.WeaponSlot 1, "PunchDagger"; + Player.WeaponSlot 2, "StrifeCrossbow2", "StrifeCrossbow"; + Player.WeaponSlot 3, "AssaultGun"; + Player.WeaponSlot 4, "MiniMissileLauncher"; + Player.WeaponSlot 5, "StrifeGrenadeLauncher2", "StrifeGrenadeLauncher"; + Player.WeaponSlot 6, "FlameThrower"; + Player.WeaponSlot 7, "Mauler2", "Mauler"; + Player.WeaponSlot 8, "Sigil"; + + Player.ColorRange 128, 143; + Player.Colorset 0, "Brown", 0x80, 0x8F, 0x82; + Player.Colorset 1, "Red", 0x40, 0x4F, 0x42, 0x20, 0x3F, 0x00, 0x1F, 0xF1, 0xF6, 0xE0, 0xE5, 0xF7, 0xFB, 0xF1, 0xF5; + Player.Colorset 2, "Rust", 0xB0, 0xBF, 0xB2, 0x20, 0x3F, 0x00, 0x1F; + Player.Colorset 3, "Gray", 0x10, 0x1F, 0x12, 0x20, 0x2F, 0xD0, 0xDF, 0x30, 0x3F, 0xD0, 0xDF; + Player.Colorset 4, "Dark Green", 0x30, 0x3F, 0x32, 0x20, 0x2F, 0xD0, 0xDF, 0x30, 0x3F, 0xD0, 0xDF; + + Player.Colorset 5, "Gold", 0x50, 0x5F, 0x52, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x80, 0x8F, 0xC0, 0xCF, 0xA0, 0xAF, 0xD0, 0xDF, 0xB0, 0xBF; + Player.Colorset 6, "Bright Green", 0x60, 0x6F, 0x62, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x10, 0x1F, 0xC0, 0xCF, 0x20, 0x2F, 0xD0, 0xDF, 0x30, 0x3F; + Player.Colorset 7, "Blue", 0x90, 0x9F, 0x92, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x40, 0x4F, 0xC1, 0xCF, 0x01, 0x0F, 0xC0,0xC0,1,1, 0xD0, 0xDF, 0x10, 0x1F; + } + + action native void A_ItBurnsItBurns(); + action native void A_CrispyPlayer(); + action native void A_HandLower(); + + States + { + Spawn: + PLAY A -1; + stop; + See: + PLAY ABCD 4; + loop; + Missile: + PLAY E 12; + goto Spawn; + Melee: + PLAY F 6; + goto Missile; + Pain: + PLAY Q 4; + PLAY Q 4 A_Pain; + Goto Spawn; + Death: + PLAY H 3; + PLAY I 3 A_PlayerScream; + PLAY J 3 A_NoBlocking; + PLAY KLMNO 4; + PLAY P -1; + Stop; + XDeath: + RGIB A 5 A_TossGib; + RGIB B 5 A_XScream; + RGIB C 5 A_NoBlocking; + RGIB DEFG 5 A_TossGib; + RGIB H -1 A_TossGib; + Burn: + BURN A 3 Bright A_ItBurnsItBurns; + BURN B 3 Bright A_DropFire; + BURN C 3 Bright A_Wander; + BURN D 3 Bright A_NoBlocking; + BURN E 5 Bright A_DropFire; + BURN FGH 5 Bright A_Wander; + BURN I 5 Bright A_DropFire; + BURN JKL 5 Bright A_Wander; + BURN M 5 Bright A_DropFire; + BURN N 5 Bright A_CrispyPlayer; + BURN OPQPQ 5 Bright; + BURN RSTU 7 Bright; + BURN V -1; + Stop; + Disintegrate: + DISR A 5 A_PlaySound("misc/disruptordeath", CHAN_VOICE); + DISR BC 5; + DISR D 5 A_NoBlocking; + DISR EF 5; + DISR GHIJ 4; + MEAT D -1; + Stop; + Firehands: + WAVE ABCD 3; + Loop; + Firehandslower: + WAVE ABCD 3 A_HandLower; + Loop; + } +} + diff --git a/wadsrc/static/zscript/strife/strifestuff.txt b/wadsrc/static/zscript/strife/strifestuff.txt new file mode 100644 index 000000000..e72e8d924 --- /dev/null +++ b/wadsrc/static/zscript/strife/strifestuff.txt @@ -0,0 +1,2002 @@ +// Tank 1 Huge ------------------------------------------------------------ + +class Tank1 : Actor +{ + Default + { + Radius 16; + Height 192; + +SOLID + } + States + { + Spawn: + TNK1 A 15; + TNK1 B 11; + TNK1 C 40; + Loop; + } +} + +// Tank 2 Huge ------------------------------------------------------------ + +class Tank2 : Actor +{ + Default + { + Radius 16; + Height 192; + +SOLID + } + States + { + Spawn: + TNK2 A 15; + TNK2 B 11; + TNK2 C 40; + Loop; + } +} + +// Tank 3 Huge ------------------------------------------------------------ + +class Tank3 : Actor +{ + Default + { + Radius 16; + Height 192; + +SOLID + } + States + { + Spawn: + TNK3 A 15; + TNK3 B 11; + TNK3 C 40; + Loop; + } +} + +// Tank 4 ------------------------------------------------------------------- + +class Tank4 : Actor +{ + Default + { + Radius 16; + Height 56; + +SOLID + } + States + { + Spawn: + TNK4 A 15; + TNK4 B 11; + TNK4 C 40; + Loop; + } +} + +// Tank 5 ------------------------------------------------------------------- + +class Tank5 : Actor +{ + Default + { + Radius 16; + Height 56; + +SOLID + } + States + { + Spawn: + TNK5 A 15; + TNK5 B 11; + TNK5 C 40; + Loop; + } +} + +// Tank 6 ------------------------------------------------------------------- + +class Tank6 : Actor +{ + Default + { + Radius 16; + Height 56; + +SOLID + } + States + { + Spawn: + TNK6 A 15; + TNK6 B 11; + TNK6 C 40; + Loop; + } +} + +// Water Bottle ------------------------------------------------------------- + +class WaterBottle : Actor +{ + States + { + Spawn: + WATR A -1; + Stop; + } +} + +// Mug ---------------------------------------------------------------------- + +class Mug : Actor +{ + States + { + Spawn: + MUGG A -1; + Stop; + } +} + +// Wooden Barrel ------------------------------------------------------------ + +class WoodenBarrel : Actor +{ + Default + { + Health 10; + Radius 10; + Height 32; + +SOLID +SHOOTABLE +NOBLOOD + +INCOMBAT + DeathSound "woodenbarrel/death"; + } + States + { + Spawn: + BARW A -1; + Stop; + Death: + BARW B 2 A_Scream; + BARW C 2; + BARW D 2 A_NoBlocking; + BARW EFG 2; + BARW H -1; + Stop; + } +} + +// Strife's explosive barrel ------------------------------------------------ + +class ExplosiveBarrel2 : Actor +{ + Default + { + Health 30; + Radius 10; + Height 32; + +SOLID +SHOOTABLE +NOBLOOD +OLDRADIUSDMG + DeathSound "world/barrelx"; + +INCOMBAT + } + States + { + Spawn: + BART A -1; + Stop; + Death: + BART B 2 Bright A_Scream; + BART CD 2 Bright; + BART E 2 Bright A_NoBlocking; + BART F 2 Bright A_Explode(64, 64, 1, 1); + BART GHIJ 2 Bright; + BART K 3 Bright; + BART L -1; + Stop; + } +} + +// Light Silver, Fluorescent ---------------------------------------------- + +class LightSilverFluorescent : Actor +{ + Default + { + Radius 2.5; + Height 16; + +NOBLOCKMAP + +FIXMAPTHINGPOS + } + States + { + Spawn: + LITS A -1 Bright; + Stop; + } +} + +// Light Brown, Fluorescent ----------------------------------------------- + +class LightBrownFluorescent : Actor +{ + Default + { + Radius 2.5; + Height 16; + +NOBLOCKMAP + +FIXMAPTHINGPOS + } + States + { + Spawn: + LITB A -1 Bright; + Stop; + } +} + +// Light Gold, Fluorescent ------------------------------------------------ + +class LightGoldFluorescent : Actor +{ + Default + { + Radius 2.5; + Height 16; + +NOBLOCKMAP + +FIXMAPTHINGPOS + } + States + { + Spawn: + LITG A -1 Bright; + Stop; + } +} + +// Light Globe -------------------------------------------------------------- + +class LightGlobe : Actor +{ + Default + { + Radius 16; + Height 16; + +SOLID + } + States + { + Spawn: + LITE A -1 Bright; + Stop; + } +} + +// Techno Pillar ------------------------------------------------------------ + +class PillarTechno : Actor +{ + Default + { + Radius 20; + Height 128; + +SOLID + } + States + { + Spawn: + MONI A -1; + Stop; + } +} + +// Aztec Pillar ------------------------------------------------------------- + +class PillarAztec : Actor +{ + Default + { + Radius 16; + Height 128; + +SOLID + } + States + { + Spawn: + STEL A -1; + Stop; + } +} + +// Damaged Aztec Pillar ----------------------------------------------------- + +class PillarAztecDamaged : Actor +{ + Default + { + Radius 16; + Height 80; + +SOLID + } + States + { + Spawn: + STLA A -1; + Stop; + } +} + +// Ruined Aztec Pillar ------------------------------------------------------ + +class PillarAztecRuined : Actor +{ + Default + { + Radius 16; + Height 40; + +SOLID + } + States + { + Spawn: + STLE A -1; + Stop; + } +} + +// Huge Tech Pillar --------------------------------------------------------- + +class PillarHugeTech : Actor +{ + Default + { + Radius 24; + Height 192; + +SOLID + } + States + { + Spawn: + HUGE ABCD 4; + Loop; + } +} + +// Alien Power Crystal in a Pillar ------------------------------------------ + +class PillarAlienPower : Actor +{ + Default + { + Radius 24; + Height 192; + +SOLID + ActiveSound "ambient/alien2"; + } + States + { + Spawn: + APOW A 4 A_LoopActiveSound; + Loop; + } +} + +// SStalactiteBig ----------------------------------------------------------- + +class SStalactiteBig : Actor +{ + Default + { + Radius 16; + Height 54; + +SOLID +SPAWNCEILING +NOGRAVITY + } + States + { + Spawn: + STLG C -1; + Stop; + } +} + +// SStalactiteSmall --------------------------------------------------------- + +class SStalactiteSmall : Actor +{ + Default + { + Radius 16; + Height 40; + +SOLID +SPAWNCEILING +NOGRAVITY + } + States + { + Spawn: + STLG A -1; + Stop; + } +} + +// SStalagmiteBig ----------------------------------------------------------- + +class SStalagmiteBig : Actor +{ + Default + { + Radius 16; + Height 40; + +SOLID + } + States + { + Spawn: + STLG B -1; + Stop; + } +} + +// Cave Pillar Top ---------------------------------------------------------- + +class CavePillarTop : Actor +{ + Default + { + Radius 16; + Height 128; + +SOLID +SPAWNCEILING +NOGRAVITY + } + States + { + Spawn: + STLG D -1; + Stop; + } +} + +// Cave Pillar Bottom ------------------------------------------------------- + +class CavePillarBottom : Actor +{ + Default + { + Radius 16; + Height 128; + +SOLID + } + States + { + Spawn: + STLG E -1; + Stop; + } +} + +// SStalagmiteSmall --------------------------------------------------------- + +class SStalagmiteSmall : Actor +{ + Default + { + Radius 16; + Height 25; + +SOLID + } + States + { + Spawn: + STLG F -1; + Stop; + } +} + +// Candle ------------------------------------------------------------------- + +class Candle : Actor +{ + States + { + Spawn: + KNDL A -1 Bright; + Stop; + } +} + +// StrifeCandelabra --------------------------------------------------------- + +class StrifeCandelabra : Actor +{ + Default + { + Radius 16; + Height 40; + +SOLID + } + States + { + Spawn: + CLBR A -1; + Stop; + } +} + +// Floor Water Drop --------------------------------------------------------- + +class WaterDropOnFloor : Actor +{ + Default + { + +NOBLOCKMAP + ActiveSound "world/waterdrip"; + } + States + { + Spawn: + DRIP A 6 A_FLoopActiveSound; + DRIP BC 4; + DRIP D 4 A_FLoopActiveSound; + DRIP EF 4; + DRIP G 4 A_FLoopActiveSound; + DRIP H 4; + Loop; + } +} + +// Waterfall Splash --------------------------------------------------------- + +class WaterfallSplash : Actor +{ + Default + { + +NOBLOCKMAP + ActiveSound "world/waterfall"; + } + States + { + Spawn: + SPLH ABCDEFG 4; + SPLH H 4 A_LoopActiveSound; + Loop; + } +} + +// Ceiling Water Drip ------------------------------------------------------- + +class WaterDrip : Actor +{ + Default + { + Height 1; + +NOBLOCKMAP +SPAWNCEILING +NOGRAVITY + } + States + { + Spawn: + CDRP A 10; + CDRP BCD 8; + Loop; + } +} + +// WaterFountain ------------------------------------------------------------ + +class WaterFountain : Actor +{ + Default + { + +NOBLOCKMAP + ActiveSound "world/watersplash"; + } + States + { + Spawn: + WTFT ABC 4; + WTFT D 4 A_LoopActiveSound; + Loop; + } +} + +// Hearts in Tank ----------------------------------------------------------- + +class HeartsInTank : Actor +{ + Default + { + Radius 16; + Height 56; + +SOLID + } + States + { + Spawn: + HERT ABC 4 Bright; + Loop; + } +} + +// Teleport Swirl ----------------------------------------------------------- + +class TeleportSwirl : Actor +{ + Default + { + +NOBLOCKMAP + RenderStyle "Add"; + Alpha 0.25; + } + States + { + Spawn: + TELP ABCD 3 Bright; + Loop; + } +} + +// Dead Player -------------------------------------------------------------- +// Strife's disappeared. This one doesn't. + +class DeadStrifePlayer : Actor +{ + States + { + Spawn: + PLAY P 700; + RGIB H -1; + Stop; + } +} + +// Dead Peasant ------------------------------------------------------------- +// Unlike Strife's, this one does not turn into gibs and disappear. + +class DeadPeasant : Actor +{ + States + { + Spawn: + PEAS N -1; + Stop; + } +} + +// Dead Acolyte ------------------------------------------------------------- +// Unlike Strife's, this one does not turn into gibs and disappear. + +class DeadAcolyte : Actor +{ + States + { + Spawn: + AGRD N -1; + Stop; + } +} + +// Dead Reaver -------------------------------------------------------------- + +class DeadReaver : Actor +{ + States + { + Spawn: + ROB1 R -1; + Stop; + } +} + +// Dead Rebel --------------------------------------------------------------- + +class DeadRebel : Actor +{ + States + { + Spawn: + HMN1 N -1; + Stop; + } +} + +// Sacrificed Guy ----------------------------------------------------------- + +class SacrificedGuy : Actor +{ + States + { + Spawn: + SACR A -1; + Stop; + } +} + +// Pile of Guts ------------------------------------------------------------- + +class PileOfGuts : Actor +{ + // Strife used a doomednum, which is the same as the Aztec Pillar. Since + // the pillar came first in the mobjinfo list, you could not spawn this + // in a map. Pity. + States + { + Spawn: + DEAD A -1; + Stop; + } +} + +// Burning Barrel ----------------------------------------------------------- + +class StrifeBurningBarrel : Actor +{ + Default + { + Radius 16; + Height 48; + +SOLID + } + States + { + Spawn: + BBAR ABCD 4 Bright; + Loop; + } +} + +// Burning Bowl ----------------------------------------------------------- + +class BurningBowl : Actor +{ + Default + { + Radius 16; + Height 16; + +SOLID + ActiveSound "world/smallfire"; + } + States + { + Spawn: + BOWL ABCD 4 Bright; + Loop; + } +} + +// Burning Brazier ----------------------------------------------------------- + +class BurningBrazier : Actor +{ + Default + { + Radius 10; + Height 32; + +SOLID + ActiveSound "world/smallfire"; + } + States + { + Spawn: + BRAZ ABCD 4 Bright; + Loop; + } +} + +// Small Torch Lit -------------------------------------------------------- + +class SmallTorchLit : Actor +{ + Default + { + Radius 2.5; + Height 16; + +NOBLOCKMAP + +FIXMAPTHINGPOS + + // It doesn't have any action functions, so how does it use this sound? + ActiveSound "world/smallfire"; + } + States + { + Spawn: + TRHL ABCD 4 Bright; + Loop; + } +} + +// Small Torch Unlit -------------------------------------------------------- + +class SmallTorchUnlit : Actor +{ + Default + { + Radius 2.5; + Height 16; + +NOBLOCKMAP + +FIXMAPTHINGPOS + } + States + { + Spawn: + TRHO A -1; + Stop; + } +} + +// Ceiling Chain ------------------------------------------------------------ + +class CeilingChain : Actor +{ + Default + { + Radius 20; + Height 93; + +NOBLOCKMAP +SPAWNCEILING +NOGRAVITY + } + States + { + Spawn: + CHAN A -1; + Stop; + } +} + +// Cage Light --------------------------------------------------------------- + +class CageLight : Actor +{ + Default + { + // No, it's not bright even though it's a light. + Height 3; + +NOBLOCKMAP +SPAWNCEILING +NOGRAVITY + } + States + { + Spawn: + CAGE A -1; + Stop; + } +} + +// Statue ------------------------------------------------------------------- + +class Statue : Actor +{ + Default + { + Radius 20; + Height 64; + +SOLID + } + States + { + Spawn: + STAT A -1; + Stop; + } +} + +// Ruined Statue ------------------------------------------------------------ + +class StatueRuined : Actor +{ + Default + { + Radius 20; + Height 56; + +SOLID + } + States + { + Spawn: + DSTA A -1; + Stop; + } +} + +// Medium Torch ------------------------------------------------------------- + +class MediumTorch : Actor +{ + Default + { + Radius 4; + Height 72; + +SOLID + } + States + { + Spawn: + LTRH ABCD 4; + Loop; + } +} + +// Outside Lamp ------------------------------------------------------------- + +class OutsideLamp : Actor +{ + Default + { + // No, it's not bright. + Radius 3; + Height 80; + +SOLID + } + States + { + Spawn: + LAMP A -1; + Stop; + } +} + +// Pole Lantern ------------------------------------------------------------- + +class PoleLantern : Actor +{ + Default + { + // No, it's not bright. + Radius 3; + Height 80; + +SOLID + } + States + { + Spawn: + LANT A -1; + Stop; + } +} + +// Rock 1 ------------------------------------------------------------------- + +class SRock1 : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + ROK1 A -1; + Stop; + } +} + +// Rock 2 ------------------------------------------------------------------- + +class SRock2 : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + ROK2 A -1; + Stop; + } +} + +// Rock 3 ------------------------------------------------------------------- + +class SRock3 : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + ROK3 A -1; + Stop; + } +} + +// Rock 4 ------------------------------------------------------------------- + +class SRock4 : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + ROK4 A -1; + Stop; + } +} + +// Stick in Water ----------------------------------------------------------- + +class StickInWater : Actor +{ + Default + { + +NOBLOCKMAP + +FLOORCLIP + ActiveSound "world/river"; + } + States + { + Spawn: + LOGW ABCD 5 A_LoopActiveSound; + Loop; + } +} + +// Rubble 1 ----------------------------------------------------------------- + +class Rubble1 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB1 A -1; + Stop; + } +} + +// Rubble 2 ----------------------------------------------------------------- + +class Rubble2 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB2 A -1; + Stop; + } +} + +// Rubble 3 ----------------------------------------------------------------- + +class Rubble3 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB3 A -1; + Stop; + } +} + +// Rubble 4 ----------------------------------------------------------------- + +class Rubble4 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB4 A -1; + Stop; + } +} + +// Rubble 5 ----------------------------------------------------------------- + +class Rubble5 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB5 A -1; + Stop; + } +} + +// Rubble 6 ----------------------------------------------------------------- + +class Rubble6 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB6 A -1; + Stop; + } +} + +// Rubble 7 ----------------------------------------------------------------- + +class Rubble7 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB7 A -1; + Stop; + } +} + +// Rubble 8 ----------------------------------------------------------------- + +class Rubble8 : Actor +{ + Default + { + +NOBLOCKMAP +NOCLIP + } + States + { + Spawn: + RUB8 A -1; + Stop; + } +} + +// Surgery Crab ------------------------------------------------------------- + +class SurgeryCrab : Actor +{ + Default + { + +SOLID +SPAWNCEILING +NOGRAVITY + Radius 20; + Height 16; + } + States + { + Spawn: + CRAB A -1; + Stop; + } +} + +// Large Torch -------------------------------------------------------------- + +class LargeTorch : Actor +{ + Default + { + Radius 10; + Height 72; + +SOLID + ActiveSound "world/smallfire"; + } + States + { + Spawn: + LMPC ABCD 4 Bright; + Loop; + } +} + +// Huge Torch -------------------------------------------------------------- + +class HugeTorch : Actor +{ + Default + { + Radius 10; + Height 80; + +SOLID + ActiveSound "world/smallfire"; + } + States + { + Spawn: + LOGS ABCD 4; + Loop; + } +} + +// Palm Tree ---------------------------------------------------------------- + +class PalmTree : Actor +{ + Default + { + Radius 15; + Height 109; + +SOLID + } + States + { + Spawn: + TREE A -1; + Stop; + } +} + +// Big Tree ---------------------------------------------------------------- + +class BigTree2 : Actor +{ + Default + { + Radius 15; + Height 109; + +SOLID + } + States + { + Spawn: + TREE B -1; + Stop; + } +} + +// Potted Tree ---------------------------------------------------------------- + +class PottedTree : Actor +{ + Default + { + Radius 15; + Height 64; + +SOLID + } + States + { + Spawn: + TREE C -1; + Stop; + } +} + +// Tree Stub ---------------------------------------------------------------- + +class TreeStub : Actor +{ + Default + { + Radius 15; + Height 80; + +SOLID + } + States + { + Spawn: + TRET A -1; + Stop; + } +} + +// Short Bush --------------------------------------------------------------- + +class ShortBush : Actor +{ + Default + { + Radius 15; + Height 40; + +SOLID + } + States + { + Spawn: + BUSH A -1; + Stop; + } +} + +// Tall Bush --------------------------------------------------------------- + +class TallBush : Actor +{ + Default + { + Radius 20; + Height 64; + +SOLID + } + States + { + Spawn: + SHRB A -1; + Stop; + } +} + +// Chimney Stack ------------------------------------------------------------ + +class ChimneyStack : Actor +{ + Default + { + Radius 20; + Height 64; // This height does not fit the sprite + +SOLID + } + States + { + Spawn: + STAK A -1; + Stop; + } +} + +// Barricade Column --------------------------------------------------------- + +class BarricadeColumn : Actor +{ + Default + { + Radius 16; + Height 128; + +SOLID + } + States + { + Spawn: + BARC A -1; + Stop; + } +} + +// Pot ---------------------------------------------------------------------- + +class Pot : Actor +{ + Default + { + Radius 12; + Height 24; + +SOLID + } + States + { + Spawn: + VAZE A -1; + Stop; + } +} + +// Pitcher ------------------------------------------------------------------ + +class Pitcher : Actor +{ + Default + { + Radius 12; + Height 32; + +SOLID + } + States + { + Spawn: + VAZE B -1; + Stop; + } +} + +// Stool -------------------------------------------------------------------- + +class Stool : Actor +{ + Default + { + Radius 6; + Height 24; + +SOLID + } + States + { + Spawn: + STOL A -1; + Stop; + } +} + +// Metal Pot ---------------------------------------------------------------- + +class MetalPot : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + MPOT A -1; + Stop; + } +} + +// Tub ---------------------------------------------------------------------- + +class Tub : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + TUB1 A -1; + Stop; + } +} + +// Anvil -------------------------------------------------------------------- + +class Anvil : Actor +{ + Default + { + Radius 16; + Height 32; + +SOLID + } + States + { + Spawn: + ANVL A -1; + Stop; + } +} + +// Silver Tech Lamp ---------------------------------------------------------- + +class TechLampSilver : Actor +{ + Default + { + Radius 11; + Height 64; + +SOLID + } + States + { + Spawn: + TECH A -1; + Stop; + } +} + +// Brass Tech Lamp ---------------------------------------------------------- + +class TechLampBrass : Actor +{ + Default + { + Radius 8; + Height 64; + +SOLID + } + States + { + Spawn: + TECH B -1; + Stop; + } +} + +// Tray -------------------------------------------------------------------- + +class Tray : Actor +{ + Default + { + Radius 24; + Height 40; + +SOLID + } + States + { + Spawn: + TRAY A -1; + Stop; + } +} + +// AmmoFiller --------------------------------------------------------------- + +class AmmoFiller : Actor +{ + Default + { + Radius 12; + Height 24; + +SOLID + } + States + { + Spawn: + AFED A -1; + Stop; + } +} + +// Sigil Banner ------------------------------------------------------------- + +class SigilBanner : Actor +{ + Default + { + Radius 24; + Height 96; + +NOBLOCKMAP // I take it this was once solid, yes? + } + States + { + Spawn: + SBAN A -1; + Stop; + } +} + +// RebelBoots --------------------------------------------------------------- + +class RebelBoots : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + BOTR A -1; + Stop; + } +} + +// RebelHelmet -------------------------------------------------------------- + +class RebelHelmet : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + HATR A -1; + Stop; + } +} + +// RebelShirt --------------------------------------------------------------- + +class RebelShirt : Actor +{ + Default + { + +NOBLOCKMAP + } + States + { + Spawn: + TOPR A -1; + Stop; + } +} + +// Alien Bubble Column ------------------------------------------------------ + +class AlienBubbleColumn : Actor +{ + Default + { + Radius 16; + Height 128; + +SOLID + ActiveSound "ambient/alien5"; + } + States + { + Spawn: + BUBB A 4 A_LoopActiveSound; + Loop; + } +} + +// Alien Floor Bubble ------------------------------------------------------- + +class AlienFloorBubble : Actor +{ + Default + { + Radius 16; + Height 72; + +SOLID + ActiveSound "ambient/alien6"; + } + States + { + Spawn: + BUBF A 4 A_LoopActiveSound; + Loop; + } +} + +// Alien Ceiling Bubble ----------------------------------------------------- + +class AlienCeilingBubble : Actor +{ + Default + { + Radius 16; + Height 72; + +SOLID +SPAWNCEILING +NOGRAVITY + ActiveSound "ambient/alien4"; + } + States + { + Spawn: + BUBC A 4 A_LoopActiveSound; + Loop; + } +} + +// Alien Asp Climber -------------------------------------------------------- + +class AlienAspClimber : Actor +{ + Default + { + Radius 16; + Height 128; + +SOLID + ActiveSound "ambient/alien3"; + } + States + { + Spawn: + ASPR A 4 A_LoopActiveSound; + Loop; + } +} + +// Alien Spider Light ------------------------------------------------------- + +class AlienSpiderLight : Actor +{ + Default + { + Radius 32; + Height 56; + +SOLID + ActiveSound "ambient/alien1"; + } + States + { + Spawn: + SPDL ABC 5 A_LoopActiveSound; + Loop; + } +} + +// Target Practice ----------------------------------------------------------- + +class TargetPractice : Actor +{ + Default + { + Health 99999999; + PainChance 255; + Radius 10; + Height 72; + Mass 9999999; + +SOLID +SHOOTABLE +NOBLOOD + +INCOMBAT +NODAMAGE + PainSound "misc/metalhit"; + } + States + { + Spawn: + HOGN A 2 A_CheckTerrain; + Loop; + Pain: + HOGN B 1 A_CheckTerrain; + HOGN C 1 A_Pain; + Goto Spawn; + } +} + +// Force Field Guard -------------------------------------------------------- + +class ForceFieldGuard : Actor native +{ + Default + { + Health 10; + Radius 2; + Height 1; + Mass 10000; + +SHOOTABLE + +NOSECTOR + +NOBLOOD + +INCOMBAT + } + States + { + Spawn: + TNT1 A -1; + Stop; + Death: + TNT1 A 1 A_RemoveForceField; + Stop; + } +} + +// Kneeling Guy ------------------------------------------------------------- + +class KneelingGuy : Actor +{ + Default + { + Health 51; + Painchance 255; + Radius 6; + Height 17; + Mass 50000; + +SOLID + +SHOOTABLE + +NOBLOOD + +ISMONSTER + +INCOMBAT + PainSound "misc/static"; + DeathSound "misc/static"; + ActiveSound "misc/chant"; + } + States + { + Spawn: + See: + NEAL A 15 A_LoopActiveSound; + NEAL B 40 A_LoopActiveSound; + Loop; + Pain: + NEAL C 5 A_SetShadow; + NEAL B 4 A_Pain; + NEAL C 5 A_ClearShadow; + Goto Spawn; + Wound: + NEAL B 6; + NEAL C 13 A_GetHurt; + Loop; + Death: + NEAL D 5; + NEAL E 5 A_Scream; + NEAL F 6; + NEAL G 5 A_NoBlocking; + NEAL H 5; + NEAL I 6; + NEAL J -1; + Stop; + } + + +} + +// Klaxon Warning Light ----------------------------------------------------- + +class KlaxonWarningLight : Actor +{ + Default + { + ReactionTime 60; + Radius 5; + +NOBLOCKMAP +AMBUSH + +SPAWNCEILING +NOGRAVITY + +FIXMAPTHINGPOS +NOSPLASHALERT + +SYNCHRONIZED + } + States + { + Spawn: + KLAX A 5 A_TurretLook; + Loop; + See: + KLAX B 6 A_KlaxonBlare; + KLAX C 60; + Loop; + } + +} + +// CeilingTurret ------------------------------------------------------------ + +class CeilingTurret : Actor +{ + Default + { + Health 125; + Speed 0; + Painchance 0; + Mass 10000000; + Monster; + -SOLID + -CANPASS + +AMBUSH + +SPAWNCEILING + +NOGRAVITY + +NOBLOOD + +NOSPLASHALERT + +DONTFALL + MinMissileChance 150; + DeathSound "turret/death"; + } + States + { + Spawn: + TURT A 5 A_TurretLook; + Loop; + See: + TURT A 2 A_Chase; + Loop; + Missile: + Pain: + TURT B 4 Slow A_ShootGun; + TURT D 3 Slow A_SentinelRefire; + TURT A 4 A_SentinelRefire; + Loop; + Death: + BALL A 6 Bright A_Scream; + BALL BCDE 6 Bright; + TURT C -1; + Stop; + } +} + + +// Power Coupling ----------------------------------------------------------- + +class PowerCoupling : Actor native +{ + Default + { + Health 40; + Radius 17; + Height 64; + Mass 999999; + +SOLID + +SHOOTABLE + +DROPPED + +NOBLOOD + +NOTDMATCH + +INCOMBAT + } + States + { + Spawn: + COUP AB 5; + Loop; + } +} + +// Gibs for things that bleed ----------------------------------------------- + +class Meat : Actor native +{ + Default + { + +NOCLIP + } + States + { + Spawn: + MEAT A 700; + Stop; + MEAT B 700; + Stop; + MEAT C 700; + Stop; + MEAT D 700; + Stop; + MEAT E 700; + Stop; + MEAT F 700; + Stop; + MEAT G 700; + Stop; + MEAT H 700; + Stop; + MEAT I 700; + Stop; + MEAT J 700; + Stop; + MEAT K 700; + Stop; + MEAT L 700; + Stop; + MEAT M 700; + Stop; + MEAT N 700; + Stop; + MEAT O 700; + Stop; + MEAT P 700; + Stop; + MEAT Q 700; + Stop; + MEAT R 700; + Stop; + MEAT S 700; + Stop; + MEAT T 700; + Stop; + } +} + +// Gibs for things that don't bleed ----------------------------------------- + +class Junk : Meat +{ + States + { + Spawn: + JUNK A 700; + Stop; + JUNK B 700; + Stop; + JUNK C 700; + Stop; + JUNK D 700; + Stop; + JUNK E 700; + Stop; + JUNK F 700; + Stop; + JUNK G 700; + Stop; + JUNK H 700; + Stop; + JUNK I 700; + Stop; + JUNK J 700; + Stop; + JUNK K 700; + Stop; + JUNK L 700; + Stop; + JUNK M 700; + Stop; + JUNK N 700; + Stop; + JUNK O 700; + Stop; + JUNK P 700; + Stop; + JUNK Q 700; + Stop; + JUNK R 700; + Stop; + JUNK S 700; + Stop; + JUNK T 700; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/strifeweapons.txt b/wadsrc/static/zscript/strife/strifeweapons.txt new file mode 100644 index 000000000..4ae358bfa --- /dev/null +++ b/wadsrc/static/zscript/strife/strifeweapons.txt @@ -0,0 +1,891 @@ + +class StrifeWeapon : Weapon +{ + Default + { + Weapon.Kickback 100; + } +} + +// Same as the bullet puff for Doom ----------------------------------------- + +class StrifePuff : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +ALLOWPARTICLES + RenderStyle "Translucent"; + Alpha 0.25; + } + + States + { + Spawn: + POW3 ABCDEFGH 3; + Stop; + Crash: + PUFY A 4 Bright; + PUFY BCD 4; + Stop; + } +} + + +// A spark when you hit something that doesn't bleed ------------------------ +// Only used by the dagger. + +class StrifeSpark : StrifePuff +{ + Default + { + RenderStyle "Add"; + } + States + { + Crash: + POW2 ABCD 4; + Stop; + } +} + +// Punch Dagger ------------------------------------------------------------- + +class PunchDagger : StrifeWeapon +{ + Default + { + Weapon.SelectionOrder 3900; + +WEAPON.NOALERT + Obituary "$OB_MPPUNCHDAGGER"; + Tag "$TAG_PUNCHDAGGER"; + } + + action native void A_JabDagger (); + + States + { + Ready: + PNCH A 1 A_WeaponReady; + Loop; + Deselect: + PNCH A 1 A_Lower; + Loop; + Select: + PNCH A 1 A_Raise; + Loop; + Fire: + PNCH B 4; + PNCH C 4 A_JabDagger; + PNCH D 5; + PNCH C 4; + PNCH B 5 A_ReFire; + Goto Ready; + } + +} + + +// The base for Strife projectiles that die with ZAP1 ----------------------- + +class StrifeZap1 : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +DROPOFF + } + States + { + Spawn: + Death: + ZAP1 A 3 A_AlertMonsters; + ZAP1 BCDEFE 3; + ZAP1 DCB 2; + ZAP1 A 1; + Stop; + } +} + + +// Electric Bolt ------------------------------------------------------------ + +class ElectricBolt : StrifeZap1 +{ + Default + { + Speed 30; + Radius 10; + Height 10; + Damage 10; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + SeeSound "misc/swish"; + ActiveSound "misc/swish"; + DeathSound "weapons/xbowhit"; + Obituary "$OB_MPELECTRICBOLT"; + } + States + { + Spawn: + AROW A 10 A_LoopActiveSound; + Loop; + } +} + + +// Poison Bolt -------------------------------------------------------------- + +class PoisonBolt : Actor native +{ + Default + { + Speed 30; + Radius 10; + Height 10; + Damage 500; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + SeeSound "misc/swish"; + ActiveSound "misc/swish"; + Obituary "$OB_MPPOISONBOLT"; + } + States + { + Spawn: + ARWP A 10 A_LoopActiveSound; + Loop; + Death: + AROW A 1; + Stop; + } +} + + +// Strife's Crossbow -------------------------------------------------------- + +class StrifeCrossbow : StrifeWeapon +{ + Default + { + +FLOORCLIP + Weapon.SelectionOrder 1200; + +WEAPON.NOALERT + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 8; + Weapon.AmmoType1 "ElectricBolts"; + Weapon.SisterWeapon "StrifeCrossbow2"; + Inventory.PickupMessage "$TXT_STRIFECROSSBOW"; + Tag "$TAG_STRIFECROSSBOW1"; + Inventory.Icon "CBOWA0"; + } + + action native void A_ClearFlash (); + action native void A_ShowElectricFlash (); + action native void A_FireArrow (class proj); + + States + { + Spawn: + CBOW A -1; + Stop; + Ready: + XBOW A 0 A_ShowElectricFlash; + XBOW A 1 A_WeaponReady; + Wait; + Deselect: + XBOW A 1 A_Lower; + Loop; + Select: + XBOW A 1 A_Raise; + Loop; + Fire: + XBOW A 3 A_ClearFlash; + XBOW B 6 A_FireArrow("ElectricBolt"); + XBOW C 4; + XBOW D 6; + XBOW E 3; + XBOW F 5; + XBOW G 0 A_ShowElectricFlash; + XBOW G 5 A_CheckReload; + Goto Ready+1; + Flash: + XBOW KLM 5; + Loop; + } +} + + +class StrifeCrossbow2 : StrifeCrossbow +{ + Default + { + Weapon.SelectionOrder 2700; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 0; + Weapon.AmmoType1 "PoisonBolts"; + Weapon.SisterWeapon "StrifeCrossbow"; + Tag "$TAG_STRIFECROSSBOW2"; + } + States + { + Ready: + XBOW H 1 A_WeaponReady; + Loop; + Deselect: + XBOW H 1 A_Lower; + Loop; + Select: + XBOW H 1 A_Raise; + Loop; + Fire: + XBOW H 3; + XBOW B 6 A_FireArrow("PoisonBolt"); + XBOW C 4; + XBOW D 6; + XBOW E 3; + XBOW I 5; + XBOW J 5 A_CheckReload; + Goto Ready; + Flash: + Stop; + } +} + +// Assault Gun -------------------------------------------------------------- + +class AssaultGun : StrifeWeapon +{ + Default + { + +FLOORCLIP + Weapon.SelectionOrder 600; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 20; + Weapon.AmmoType1 "ClipOfBullets"; + Inventory.Icon "RIFLA0"; + Tag "$TAG_ASSAULTGUN"; + Inventory.PickupMessage "$TXT_ASSAULTGUN"; + Obituary "$OB_MPASSAULTGUN"; + } + States + { + Spawn: + RIFL A -1; + Stop; + Ready: + RIFG A 1 A_WeaponReady; + Loop; + Deselect: + RIFG B 1 A_Lower; + Loop; + Select: + RIFG A 1 A_Raise; + Loop; + Fire: + RIFF AB 3 A_FireAssaultGun; + RIFG D 3 A_FireAssaultGun; + RIFG C 0 A_ReFire; + RIFG B 2 A_Light0; + Goto Ready; + } +} + + +// Standing variant of the assault gun -------------------------------------- + +class AssaultGunStanding : WeaponGiver +{ + Default + { + DropItem "AssaultGun"; + Inventory.PickupMessage "$TXT_ASSAULTGUN"; + } + States + { + Spawn: + RIFL B -1; + Stop; + } +} + + +// Mini-Missile Launcher ---------------------------------------------------- + + +class MiniMissileLauncher : StrifeWeapon +{ + Default + { + +FLOORCLIP + Weapon.SelectionOrder 1800; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 8; + Weapon.AmmoType1 "MiniMissiles"; + Inventory.Icon "MMSLA0"; + Tag "$TAG_MMLAUNCHER"; + Inventory.PickupMessage "$TXT_MMLAUNCHER"; + } + + action native void A_FireMiniMissile (); + + States + { + Spawn: + MMSL A -1; + Stop; + Ready: + MMIS A 1 A_WeaponReady; + Loop; + Deselect: + MMIS A 1 A_Lower; + Loop; + Select: + MMIS A 1 A_Raise; + Loop; + Fire: + MMIS A 4 A_FireMiniMissile; + MMIS B 4 A_Light1; + MMIS C 5 Bright; + MMIS D 2 Bright A_Light2; + MMIS E 2 Bright; + MMIS F 2 Bright A_Light0; + MMIS F 0 A_ReFire; + Goto Ready; + } +} + + +// Rocket Trail ------------------------------------------------------------- + +class RocketTrail : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + RenderStyle "Translucent"; + Alpha 0.25; + SeeSound "misc/missileinflight"; + } + States + { + Spawn: + PUFY BCBCD 4; + Stop; + } +} + +// Rocket Puff -------------------------------------------------------------- + +class MiniMissilePuff : StrifePuff +{ + Default + { + -ALLOWPARTICLES + } + States + { + Spawn: + Goto Crash; + } +} + +// Mini Missile ------------------------------------------------------------- + +class MiniMissile : Actor +{ + Default + { + Speed 20; + Radius 10; + Height 14; + Damage 10; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + SeeSound "weapons/minimissile"; + DeathSound "weapons/minimissilehit"; + Obituary "$OB_MPMINIMISSILELAUNCHER"; + } + States + { + Spawn: + MICR A 6 Bright A_RocketInFlight; + Loop; + Death: + SMIS A 0 Bright A_SetTranslucent(1,1); + SMIS A 5 Bright A_Explode(64,64,1,1); + SMIS B 5 Bright; + SMIS C 4 Bright; + SMIS DEFG 2 Bright; + Stop; + } +} + +// Flame Thrower ------------------------------------------------------------ + +class FlameThrower : StrifeWeapon +{ + Default + { + +FLOORCLIP + Weapon.SelectionOrder 2100; + Weapon.Kickback 0; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 100; + Weapon.UpSound "weapons/flameidle"; + Weapon.ReadySound "weapons/flameidle"; + Weapon.AmmoType1 "EnergyPod"; + Inventory.Icon "FLAMA0"; + Tag "$TAG_FLAMER"; + Inventory.PickupMessage "$TXT_FLAMER"; + } + + action native void A_FireFlamer (); + + States + { + Spawn: + FLAM A -1; + Stop; + Ready: + FLMT AB 3 A_WeaponReady; + Loop; + Deselect: + FLMT A 1 A_Lower; + Loop; + Select: + FLMT A 1 A_Raise; + Loop; + Fire: + FLMF A 2 A_FireFlamer; + FLMF B 3 A_ReFire; + Goto Ready; + } +} + + +// Flame Thrower Projectile ------------------------------------------------- + +class FlameMissile : Actor +{ + Default + { + Speed 15; + Height 11; + Radius 8; + Mass 10; + Damage 4; + DamageType "Fire"; + ReactionTime 8; + Projectile; + -NOGRAVITY + +STRIFEDAMAGE + MaxStepHeight 4; + RenderStyle "Add"; + SeeSound "weapons/flamethrower"; + Obituary "$OB_MPFLAMETHROWER"; + } + + action native void A_FlameDie (); + + States + { + Spawn: + FRBL AB 3 Bright; + FRBL C 3 Bright A_Countdown; + Loop; + Death: + FRBL D 5 Bright A_FlameDie; + FRBL EFGHI 5 Bright; + Stop; + } + +} + + +// Mauler ------------------------------------------------------------------- +// The scatter version + +class Mauler : StrifeWeapon +{ + Default + { + +FLOORCLIP + Weapon.SelectionOrder 300; + Weapon.AmmoUse1 20; + Weapon.AmmoGive1 40; + Weapon.AmmoType1 "EnergyPod"; + Weapon.SisterWeapon "Mauler2"; + Inventory.Icon "TRPDA0"; + Tag "$TAG_MAULER1"; + Inventory.PickupMessage "$TXT_MAULER"; + Obituary "$OB_MPMAULER1"; + } + + action native void A_FireMauler1 (); + + States + { + Ready: + MAUL FGHA 6 A_WeaponReady; + Loop; + Deselect: + MAUL A 1 A_Lower; + Loop; + Select: + MAUL A 1 A_Raise; + Loop; + Fire: + BLSF A 5 Bright A_FireMauler1; + MAUL B 3 Bright A_Light1; + MAUL C 2 A_Light2; + MAUL DE 2; + MAUL A 7 A_Light0; + MAUL H 7; + MAUL G 7 A_CheckReload; + Goto Ready; + Spawn: + TRPD A -1; + Stop; + } +} + + +// Mauler Torpedo version --------------------------------------------------- + +class Mauler2 : Mauler +{ + Default + { + Weapon.SelectionOrder 3300; + Weapon.AmmoUse1 30; + Weapon.AmmoGive1 0; + Weapon.AmmoType1 "EnergyPod"; + Weapon.SisterWeapon "Mauler"; + Tag "$TAG_MAULER2"; + } + + action native void A_FireMauler2Pre (); + action native void A_FireMauler2 (); + + States + { + Ready: + MAUL IJKL 7 A_WeaponReady; + Loop; + Deselect: + MAUL I 1 A_Lower; + Loop; + Select: + MAUL I 1 A_Raise; + Loop; + Fire: + MAUL I 20 A_FireMauler2Pre; + MAUL J 10 A_Light1; + BLSF A 10 Bright A_FireMauler2; + MAUL B 10 Bright A_Light2; + MAUL C 2; + MAUL D 2 A_Light0; + MAUL E 2 A_ReFire; + Goto Ready; + } +} + + +// Mauler "Bullet" Puff ----------------------------------------------------- + +class MaulerPuff : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + +PUFFONACTORS + RenderStyle "Add"; + DamageType "Disintegrate"; + } + States + { + Spawn: + MPUF AB 5; + POW1 ABCDE 4; + Stop; + } +} + +// The Mauler's Torpedo ----------------------------------------------------- + +class MaulerTorpedo : Actor +{ + Default + { + Speed 20; + Height 8; + Radius 13; + Damage 1; + DamageType "Disintegrate"; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + RenderStyle "Add"; + SeeSound "weapons/mauler2fire"; + DeathSound "weapons/mauler2hit"; + Obituary "$OB_MPMAULER"; + } + + action native void A_MaulerTorpedoWave (); + + States + { + Spawn: + TORP ABCD 4 Bright; + Loop; + Death: + THIT AB 8 Bright; + THIT C 8 Bright A_MaulerTorpedoWave; + THIT DE 8 Bright; + Stop; + } +} + + +// The mini torpedoes shot by the big torpedo -------------------------------- + +class MaulerTorpedoWave : Actor +{ + Default + { + Speed 35; + Radius 13; + Height 13; + Damage 10; + DamageType "Disintegrate"; + Projectile; + +STRIFEDAMAGE + MaxStepHeight 4; + RenderStyle "Add"; + Obituary "$OB_MPMAULER"; + } + States + { + Spawn: + TWAV AB 9 Bright; + Death: + TWAV C 9 Bright; + Stop; + } +} + + +// High-Explosive Grenade --------------------------------------------------- + +class HEGrenade : Actor +{ + Default + { + Speed 15; + Radius 13; + Height 13; + Mass 20; + Damage 1; + Reactiontime 30; + Projectile; + -NOGRAVITY + +STRIFEDAMAGE + +BOUNCEONACTORS + +EXPLODEONWATER + MaxStepHeight 4; + BounceType "Doom"; + BounceFactor 0.5; + BounceCount 2; + SeeSound "weapons/hegrenadeshoot"; + DeathSound "weapons/hegrenadebang"; + Obituary "$OB_MPSTRIFEGRENADE"; + } + States + { + Spawn: + GRAP AB 3 A_Countdown; + Loop; + Death: + BNG4 A 0 Bright A_NoGravity; + BNG4 A 0 Bright A_SetTranslucent(1,1); + BNG4 A 2 Bright A_Explode(192,192,1,1); + BNG4 BCDEFGHIJKLMN 3 Bright; + Stop; + } +} + +// White Phosphorous Grenade ------------------------------------------------ + +class PhosphorousGrenade : Actor +{ + Default + { + Speed 15; + Radius 13; + Height 13; + Mass 20; + Damage 1; + Reactiontime 40; + Projectile; + -NOGRAVITY + +STRIFEDAMAGE + +BOUNCEONACTORS + +EXPLODEONWATER + BounceType "Doom"; + MaxStepHeight 4; + BounceFactor 0.5; + BounceCount 2; + SeeSound "weapons/phgrenadeshoot"; + DeathSound "weapons/phgrenadebang"; + Obituary "$OB_MPPHOSPHOROUSGRENADE"; + } + States + { + Spawn: + GRIN AB 3 A_Countdown; + Loop; + Death: + BNG3 A 2 A_SpawnItemEx("PhosphorousFire"); + Stop; + } +} + +// Fire from the Phoshorous Grenade ----------------------------------------- + +class PhosphorousFire : Actor native +{ + Default + { + Reactiontime 120; + DamageType "Fire"; + +NOBLOCKMAP + +FLOORCLIP + +NOTELEPORT + +NODAMAGETHRUST + +DONTSPLASH + RenderStyle "Add"; + Obituary "$OB_MPPHOSPHOROUSGRENADE"; + } + + action native void A_Burnarea (); + action native void A_Burnination (); + + States + { + Spawn: + BNG3 B 2 Bright A_Burnarea; + BNG3 C 2 Bright A_Countdown; + FLBE A 2 Bright A_Burnination; + FLBE B 2 Bright A_Countdown; + FLBE C 2 Bright A_Burnarea; + FLBE D 3 Bright A_Countdown; + FLBE E 3 Bright A_Burnarea; + FLBE F 3 Bright A_Countdown; + FLBE G 3 Bright A_Burnination; + Goto Spawn+5; + Death: + FLBE H 2 Bright; + FLBE I 2 Bright A_Burnination; + FLBE JK 2 Bright; + Stop; + } +} + +// High-Explosive Grenade Launcher ------------------------------------------ + +class StrifeGrenadeLauncher : StrifeWeapon +{ + Default + { + +FLOORCLIP + Weapon.SelectionOrder 2400; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 12; + Weapon.AmmoType1 "HEGrenadeRounds"; + Weapon.SisterWeapon "StrifeGrenadeLauncher2"; + Inventory.Icon "GRNDA0"; + Tag "$TAG_GLAUNCHER1"; + Inventory.PickupMessage "$TXT_GLAUNCHER"; + } + + action native void A_FireGrenade (class grenadetype, float angleofs, state flash); + + States + { + Spawn: + GRND A -1; + Stop; + Ready: + GREN A 1 A_WeaponReady; + Loop; + Deselect: + GREN A 1 A_Lower; + Loop; + Select: + GREN A 1 A_Raise; + Loop; + Fire: + GREN A 5 A_FireGrenade("HEGrenade", -90, "Flash"); + GREN B 10; + GREN A 5 A_FireGrenade("HEGrenade", 90, "Flash2"); + GREN C 10; + GREN A 0 A_ReFire; + Goto Ready; + Flash: + GREF A 5 Bright A_Light1; + Goto LightDone; + Flash2: + GREF B 5 Bright A_Light2; + Goto LightDone; + } + +} + +// White Phosphorous Grenade Launcher --------------------------------------- + +class StrifeGrenadeLauncher2 : StrifeGrenadeLauncher +{ + Default + { + Weapon.SelectionOrder 3200; + Weapon.AmmoUse1 1; + Weapon.AmmoGive1 0; + Weapon.AmmoType1 "PhosphorusGrenadeRounds"; + Weapon.SisterWeapon "StrifeGrenadeLauncher"; + Tag "$TAG_GLAUNCHER2"; + } + States + { + Ready: + GREN D 1 A_WeaponReady; + Loop; + Deselect: + GREN D 1 A_Lower; + Loop; + Select: + GREN D 1 A_Raise; + Loop; + Fire: + GREN D 5 A_FireGrenade("PhosphorousGrenade", -90, "Flash"); + GREN E 10; + GREN D 5 A_FireGrenade("PhosphorousGrenade", 90, "Flash2"); + GREN F 10; + GREN A 0 A_ReFire; + Goto Ready; + Flash: + GREF C 5 Bright A_Light1; + Goto LightDone; + Flash2: + GREF D 5 Bright A_Light2; + Goto LightDone; + } +} + diff --git a/wadsrc/static/zscript/strife/templar.txt b/wadsrc/static/zscript/strife/templar.txt new file mode 100644 index 000000000..4c640fd54 --- /dev/null +++ b/wadsrc/static/zscript/strife/templar.txt @@ -0,0 +1,68 @@ + +class Templar : Actor +{ + Default + { + Health 300; + Painchance 100; + Speed 8; + Radius 20; + Height 60; + Mass 500; + Monster; + +NOBLOOD + +SEESDAGGERS + +NOSPLASHALERT + MaxdropoffHeight 32; + MinMissileChance 200; + SeeSound "templar/sight"; + PainSound "templar/pain"; + DeathSound "templar/death"; + ActiveSound "templar/active"; + CrushPainSound "misc/pcrush"; + Tag "$TAG_TEMPLAR"; + HitObituary "$OB_TEMPLARHIT"; + Obituary "$OB_TEMPLAR"; + DropItem "EnergyPod"; + } + action native void A_TemplarAttack(); + + States + { + Spawn: + PGRD A 5 A_Look2; + Loop; + PGRD B 10; + Loop; + PGRD C 10; + Loop; + PGRD B 10 A_Wander; + Loop; + See: + PGRD AABBCCDD 3 A_Chase; + Loop; + Melee: + PGRD E 8 A_FaceTarget; + PGRD F 8 A_CustomMeleeAttack(random[ReaverMelee](1,8)*3, "reaver/blade"); + Goto See; + Missile: + PGRD G 8 BRIGHT A_FaceTarget; + PGRD H 8 BRIGHT A_TemplarAttack; + Goto See; + Pain: + PGRD A 2; + PGRD A 2 A_Pain; + Goto See; + Death: + PGRD I 4 A_TossGib; + PGRD J 4 A_Scream; + PGRD K 4 A_TossGib; + PGRD L 4 A_NoBlocking; + PGRD MN 4; + PGRD O 4 A_TossGib; + PGRD PQRSTUVWXYZ[ 4; + PGRD \ -1; + Stop; + } +} + diff --git a/wadsrc/static/zscript/strife/thingstoblowup.txt b/wadsrc/static/zscript/strife/thingstoblowup.txt new file mode 100644 index 000000000..659c13f56 --- /dev/null +++ b/wadsrc/static/zscript/strife/thingstoblowup.txt @@ -0,0 +1,153 @@ + + +// A Cloud used for varius explosions --------------------------------------- +// This actor has no direct equivalent in strife. To create this, Strife +// spawned a spark and then changed its state to that of this explosion +// cloud. Weird. + +class Bang4Cloud : Actor +{ + Default + { + +NOBLOCKMAP + +NOGRAVITY + RenderStyle "Add"; + VSpeed 1; + } + States + { + Spawn: + BNG4 BCDEFGHIJKLMN 3 Bright; + Stop; + } +} + +// Piston ------------------------------------------------------------------- + +class Piston : Actor +{ + Default + { + Health 100; + Speed 16; + Radius 20; + Height 76; + Mass 10000000; + +SOLID + +SHOOTABLE + +NOBLOOD + +FLOORCLIP + +INCOMBAT + DeathSound "misc/explosion"; + } + States + { + Spawn: + PSTN AB 8; + Loop; + Death: + PSTN A 4 Bright A_Scream; + PSTN B 4 Bright A_NoBlocking; + PSTN C 4 Bright A_GiveQuestItem(16); + PSTN D 4 Bright A_Bang4Cloud; + PSTN E 4 Bright A_TossGib; + PSTN F 4 Bright; + PSTN G 4 Bright A_Bang4Cloud; + PSTN H 4; + PSTN I -1; + Stop; + } + +} + +// Computer ----------------------------------------------------------------- + +class Computer : Actor +{ + Default + { + Health 80; + Speed 27; + Radius 26; + Height 128; + Mass 10000000; + +SOLID + +SHOOTABLE + +NOBLOOD + +FLOORCLIP + +INCOMBAT + DeathSound "misc/explosion"; + } + States + { + Spawn: + SECR ABCD 4 Bright; + Loop; + Death: + SECR E 5 Bright A_Bang4Cloud; + SECR F 5 Bright A_NoBlocking; + SECR G 5 Bright A_GiveQuestItem(27); + SECR H 5 Bright A_TossGib; + SECR I 5 Bright A_Bang4Cloud; + SECR J 5; + SECR K 5 A_Bang4Cloud; + SECR L 5; + SECR M 5 A_Bang4Cloud; + SECR N 5; + SECR O 5 A_Bang4Cloud; + SECR P -1; + Stop; + } +} + + +// Power Crystal ------------------------------------------------------------ + +class PowerCrystal : Actor +{ + Default + { + Health 50; + Speed 14; + Radius 20; + Height 16; + Mass 99999999; + +SOLID + +SHOOTABLE + +NOGRAVITY + +NOBLOOD + +FLOORCLIP + DeathSound "misc/explosion"; + ActiveSound "misc/reactor"; + } + + action native void A_ExtraLightOff (); + action native void A_Explode512 (); + action native void A_LightGoesOut (); + + States + { + Spawn: + CRYS A 16 A_LoopActiveSound; + CRYS B 5 A_LoopActiveSound; + CRYS CDEF 4 A_LoopActiveSound; + Loop; + Death: + BOOM A 0 Bright A_Scream; + BOOM A 1 Bright A_Explode512; + BOOM B 3 Bright A_GiveQuestItem(14); + BOOM C 2 Bright A_LightGoesOut; + BOOM D 3 Bright A_Bang4Cloud; + BOOM EF 3 Bright; + BOOM G 3 Bright A_Bang4Cloud; + BOOM H 1 Bright A_Explode512; + BOOM I 3 Bright; + BOOM JKL 3 Bright A_Bang4Cloud; + BOOM MN 3 Bright; + BOOM O 3 Bright A_Bang4Cloud; + BOOM PQRST 3 Bright; + BOOM U 3 Bright A_ExtraLightOff; + BOOM VWXY 3 Bright; + Stop; + } +} diff --git a/wadsrc/static/zscript/strife/zombie.txt b/wadsrc/static/zscript/strife/zombie.txt new file mode 100644 index 000000000..c7a7cea59 --- /dev/null +++ b/wadsrc/static/zscript/strife/zombie.txt @@ -0,0 +1,64 @@ + +// Zombie ------------------------------------------------------------------- + +class Zombie : StrifeHumanoid +{ + Default + { + Health 31; + Radius 20; + Height 56; + PainChance 0; + +SOLID + +SHOOTABLE + +FLOORCLIP + +CANPASS + +CANPUSHWALLS + +ACTIVATEMCROSS + MinMissileChance 150; + MaxStepHeight 16; + MaxDropOffHeight 32; + Translation 0; + DeathSound "zombie/death"; + CrushPainSound "misc/pcrush"; + } + States + { + Spawn: + PEAS A 5 A_CheckTerrain; + Loop; + Pain: + AGRD A 5 A_CheckTerrain; + Loop; + Death: + GIBS M 5 A_TossGib; + GIBS N 5 A_XScream; + GIBS O 5 A_NoBlocking; + GIBS PQRST 4 A_TossGib; + GIBS U 5; + GIBS V -1; + Stop; + } +} + + +// Zombie Spawner ----------------------------------------------------------- + +class ZombieSpawner : Actor +{ + Default + { + Health 20; + +SHOOTABLE + +NOSECTOR + RenderStyle "None"; + ActiveSound "zombie/spawner"; // Does Strife use this somewhere else? + } + States + { + Spawn: + TNT1 A 175 A_SpawnItemEx("Zombie"); + Loop; + } +} + From f6b3cdc23d6f40773baefa54b66892713ad7beb8 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 18 Oct 2016 23:22:41 +0200 Subject: [PATCH 069/255] - converted the Chex Quest actors, completing the DECORATE conversion. --- wadsrc/static/actors/chex/chexammo.txt | 77 -------- wadsrc/static/actors/chex/chexdecorations.txt | 120 ------------ wadsrc/static/actors/chex/chexitems.txt | 59 ------ wadsrc/static/actors/chex/chexkeys.txt | 16 -- wadsrc/static/actors/chex/chexplayer.txt | 29 --- wadsrc/static/actors/chex/chexweapons.txt | 124 ------------ wadsrc/static/decorate.txt | 8 - wadsrc/static/zscript.txt | 8 + wadsrc/static/zscript/chex/chexammo.txt | 101 ++++++++++ .../static/zscript/chex/chexdecorations.txt | 180 ++++++++++++++++++ wadsrc/static/zscript/chex/chexitems.txt | 89 +++++++++ wadsrc/static/zscript/chex/chexkeys.txt | 25 +++ .../{actors => zscript}/chex/chexmonsters.txt | 68 ++++--- wadsrc/static/zscript/chex/chexplayer.txt | 32 ++++ wadsrc/static/zscript/chex/chexweapons.txt | 160 ++++++++++++++++ 15 files changed, 638 insertions(+), 458 deletions(-) delete mode 100644 wadsrc/static/actors/chex/chexammo.txt delete mode 100644 wadsrc/static/actors/chex/chexdecorations.txt delete mode 100644 wadsrc/static/actors/chex/chexitems.txt delete mode 100644 wadsrc/static/actors/chex/chexkeys.txt delete mode 100644 wadsrc/static/actors/chex/chexplayer.txt delete mode 100644 wadsrc/static/actors/chex/chexweapons.txt delete mode 100644 wadsrc/static/decorate.txt create mode 100644 wadsrc/static/zscript/chex/chexammo.txt create mode 100644 wadsrc/static/zscript/chex/chexdecorations.txt create mode 100644 wadsrc/static/zscript/chex/chexitems.txt create mode 100644 wadsrc/static/zscript/chex/chexkeys.txt rename wadsrc/static/{actors => zscript}/chex/chexmonsters.txt (62%) create mode 100644 wadsrc/static/zscript/chex/chexplayer.txt create mode 100644 wadsrc/static/zscript/chex/chexweapons.txt diff --git a/wadsrc/static/actors/chex/chexammo.txt b/wadsrc/static/actors/chex/chexammo.txt deleted file mode 100644 index 27c5d419b..000000000 --- a/wadsrc/static/actors/chex/chexammo.txt +++ /dev/null @@ -1,77 +0,0 @@ -// Renaming and changing messages - -// Mini Zorch ----------------------------------------------------------------- - -actor MiniZorchRecharge : Clip -{ - inventory.pickupmessage "$GOTZORCHRECHARGE" -} - -actor MiniZorchPack : Clip -{ - Inventory.PickupMessage "$GOTMINIZORCHPACK" - Inventory.Amount 50 - States - { - Spawn: - AMMO A -1 - Stop - } -} - -// Large Zorch ---------------------------------------------------------------- - -actor LargeZorchRecharge : Shell -{ - inventory.pickupmessage "$GOTLARGEZORCHERRECHARGE" -} - -actor LargeZorchPack : Shell -{ - Inventory.PickupMessage "$GOTLARGEZORCHERPACK" - Inventory.Amount 20 - States - { - Spawn: - SBOX A -1 - Stop - } -} - -// Zorch Propulsor ------------------------------------------------------------ - -actor PropulsorZorch : RocketAmmo -{ - inventory.pickupmessage "$GOTPROPULSORRECHARGE" -} - -actor PropulsorZorchPack : RocketAmmo -{ - Inventory.PickupMessage "$GOTPROPULSORPACK" - Inventory.Amount 5 - States - { - Spawn: - BROK A -1 - Stop - } -} - -// Phasing Zorch -------------------------------------------------------------- - -actor PhasingZorch : Cell -{ - inventory.pickupmessage "$GOTPHASINGZORCHERRECHARGE" -} - -actor PhasingZorchPack : Cell -{ - Inventory.PickupMessage "$GOTPHASINGZORCHERPACK" - Inventory.Amount 100 - States - { - Spawn: - CELP A -1 - Stop - } -} diff --git a/wadsrc/static/actors/chex/chexdecorations.txt b/wadsrc/static/actors/chex/chexdecorations.txt deleted file mode 100644 index 6515061c5..000000000 --- a/wadsrc/static/actors/chex/chexdecorations.txt +++ /dev/null @@ -1,120 +0,0 @@ -// Doom items renamed with height changes - -// Civilians ------------------------------------------------------------------ - -actor ChexCivilian1 : GreenTorch -{ - height 54 -} - -actor ChexCivilian2 : ShortGreenTorch -{ - height 54 -} - -actor ChexCivilian3 : ShortRedTorch -{ - height 48 -} - -// Landing Zone --------------------------------------------------------------- - -actor ChexLandingLight : Column -{ - height 35 -} - -actor ChexSpaceship : TechPillar -{ - height 52 -} - -// Trees and Plants ----------------------------------------------------------- - -actor ChexAppleTree : Stalagtite -{ - height 92 -} - -actor ChexBananaTree : BigTree -{ - height 108 -} - -actor ChexOrangeTree : TorchTree -{ - height 92 -} - -actor ChexSubmergedPlant : ShortGreenColumn -{ - height 42 -} - -actor ChexTallFlower : HeadsOnAStick -{ - height 25 -} - -actor ChexTallFlower2 : DeadStick -{ - height 25 -} - -// Slime Fountain ------------------------------------------------------------- - -actor ChexSlimeFountain : BlueTorch -{ - height 48 - States - { - Spawn: - TBLU ABCD 4 - Loop - } -} - -// Cavern Decorations --------------------------------------------------------- - -actor ChexCavernColumn : TallRedColumn -{ - height 128 -} - -actor ChexCavernStalagmite : TallGreenColumn -{ - height 60 -} - -// Misc. Props ---------------------------------------------------------------- - -actor ChexChemicalBurner : EvilEye -{ - height 25 -} - -actor ChexChemicalFlask : Candlestick -{ - renderstyle translucent - alpha 0.75 -} - -actor ChexFlagOnPole : SkullColumn -{ - height 128 -} - -actor ChexGasTank : Candelabra -{ - height 36 -} - -actor ChexLightColumn : ShortBlueTorch -{ - height 86 -} - -actor ChexMineCart : ShortRedColumn -{ - height 30 -} diff --git a/wadsrc/static/actors/chex/chexitems.txt b/wadsrc/static/actors/chex/chexitems.txt deleted file mode 100644 index 431728e07..000000000 --- a/wadsrc/static/actors/chex/chexitems.txt +++ /dev/null @@ -1,59 +0,0 @@ - -// General Pickups ============================================================ - -// Health --------------------------------------------------------------------- - -actor GlassOfWater : HealthBonus -{ - inventory.pickupmessage "$GOTWATER" -} - -actor BowlOfFruit : Stimpack -{ - inventory.pickupmessage "$GOTFRUIT" -} - -actor BowlOfVegetables : Medikit -{ - inventory.pickupmessage "$GOTVEGETABLES" - health.lowmessage 25, "$GOTVEGETABLESNEED" -} - -actor SuperchargeBreakfast : Soulsphere -{ - inventory.pickupmessage "$GOTBREAKFAST" -} - -// Armor ---------------------------------------------------------------------- - -actor SlimeRepellent : ArmorBonus -{ - inventory.pickupmessage "$GOTREPELLENT" -} - -actor ChexArmor : GreenArmor -{ - inventory.pickupmessage "$GOTCHEXARMOR" -} - -actor SuperChexArmor : BlueArmor -{ - inventory.pickupmessage "$GOTSUPERCHEXARMOR" -} - -// Powerups =================================================================== - -actor ComputerAreaMap : Allmap -{ - inventory.pickupmessage "$GOTCHEXMAP" -} - -actor SlimeProofSuit : RadSuit -{ - inventory.pickupmessage "$GOTSLIMESUIT" -} - -actor Zorchpack : Backpack -{ - inventory.pickupmessage "$GOTZORCHPACK" -} diff --git a/wadsrc/static/actors/chex/chexkeys.txt b/wadsrc/static/actors/chex/chexkeys.txt deleted file mode 100644 index 0d5156392..000000000 --- a/wadsrc/static/actors/chex/chexkeys.txt +++ /dev/null @@ -1,16 +0,0 @@ -// These are merely renames of the Doom cards - -actor ChexBlueCard : BlueCard -{ - inventory.pickupmessage "$GOTCBLUEKEY" -} - -actor ChexYellowCard : YellowCard -{ - inventory.pickupmessage "$GOTCYELLOWKEY" -} - -actor ChexRedCard : RedCard -{ - inventory.pickupmessage "$GOTCREDKEY" -} diff --git a/wadsrc/static/actors/chex/chexplayer.txt b/wadsrc/static/actors/chex/chexplayer.txt deleted file mode 100644 index 210a68470..000000000 --- a/wadsrc/static/actors/chex/chexplayer.txt +++ /dev/null @@ -1,29 +0,0 @@ -// Chex Warrior - -actor ChexPlayer : DoomPlayer -{ - player.displayname "Chex Warrior" - player.crouchsprite "" - player.colorrange 192, 207 //Not perfect, but its better than everyone being blue. - player.startitem "MiniZorcher" - player.startitem "Bootspoon" - player.startitem "MiniZorchRecharge", 50 - player.damagescreencolor "60 b0 58" - player.WeaponSlot 1, Bootspoon, SuperBootspork - player.WeaponSlot 2, MiniZorcher - player.WeaponSlot 3, LargeZorcher, SuperLargeZorcher - player.WeaponSlot 4, RapidZorcher - player.WeaponSlot 5, ZorchPropulsor - player.WeaponSlot 6, PhasingZorcher - player.WeaponSlot 7, LAZDevice - - Player.Colorset 0, "Light Blue", 0xC0, 0xCF, 0xC2 - Player.Colorset 1, "Green", 0x70, 0x7F, 0x72 - Player.Colorset 2, "Gray", 0x60, 0x6F, 0x62 - Player.Colorset 3, "Brown", 0x40, 0x4F, 0x42 - Player.Colorset 4, "Red", 0x20, 0x2F, 0x22 - Player.Colorset 5, "Light Gray", 0x58, 0x67, 0x5A - Player.Colorset 6, "Light Brown", 0x38, 0x47, 0x3A - Player.Colorset 7, "Light Red", 0xB0, 0xBF, 0xB2 - -} diff --git a/wadsrc/static/actors/chex/chexweapons.txt b/wadsrc/static/actors/chex/chexweapons.txt deleted file mode 100644 index 0cdb96849..000000000 --- a/wadsrc/static/actors/chex/chexweapons.txt +++ /dev/null @@ -1,124 +0,0 @@ -// Same as Doom weapons, but the obituaries are removed. - -actor Bootspoon : Fist -{ - obituary "$OB_MPSPOON" - Tag "$TAG_SPOON" -} - -actor SuperBootspork : Chainsaw -{ - obituary "$OB_MPBOOTSPORK" - Inventory.PickupMessage "$GOTSUPERBOOTSPORK" - Tag "$TAG_SPORK" -} - -actor MiniZorcher : Pistol -{ - obituary "$OB_MPZORCH" - inventory.pickupmessage "$GOTMINIZORCHER" - Tag "$TAG_MINIZORCHER" - states - { - Spawn: - MINZ A -1 - stop - } -} - -actor LargeZorcher : Shotgun -{ - obituary "$OB_MPZORCH" - inventory.pickupmessage "$GOTLARGEZORCHER" - Tag "$TAG_LARGEZORCHER" -} - -actor SuperLargeZorcher : SuperShotgun -{ - obituary "$OB_MPMEGAZORCH" - inventory.pickupmessage "$GOTSUPERLARGEZORCHER" - Tag "$TAG_SUPERLARGEZORCHER" -} - -actor RapidZorcher : Chaingun -{ - obituary "$OB_MPRAPIDZORCH" - inventory.pickupmessage "$GOTRAPIDZORCHER" - Tag "$TAG_RAPIDZORCHER" -} - -actor ZorchPropulsor : RocketLauncher -{ - obituary "" - inventory.pickupmessage "$GOTZORCHPROPULSOR" - Tag "$TAG_ZORCHPROPULSOR" - States - { - Fire: - MISG B 8 A_GunFlash - MISG B 12 A_FireCustomMissile("PropulsorMissile") - MISG B 0 A_ReFire - Goto Ready - } -} - -actor PropulsorMissile : Rocket -{ - -ROCKETTRAIL - -DEHEXPLOSION - RenderStyle Translucent - Obituary "$OB_MPPROPULSOR" - Alpha 0.75 -} - -actor PhasingZorcher : PlasmaRifle -{ - obituary "" - inventory.pickupmessage "$GOTPHASINGZORCHER" - Tag "$TAG_PHASINGZORCHER" - states - { - Fire: - PLSG A 0 A_GunFlash - PLSG A 3 A_FireCustomMissile("PhaseZorchMissile") - PLSG B 20 A_ReFire - Goto Ready - Flash: - PLSF A 0 A_Jump(128, "Flash2") - PLSF A 3 Bright A_Light1 - Goto LightDone - Flash2: - PLSF B 3 Bright A_Light1 - Goto LightDone - } -} - -actor PhaseZorchMissile : PlasmaBall -{ - RenderStyle Translucent - Obituary "$OB_MPPHASEZORCH" - Alpha 0.75 -} - -actor LAZDevice : BFG9000 -{ - obituary "" - inventory.pickupmessage "$GOTLAZDEVICE" - Tag "$TAG_LAZDEVICE" - states - { - Fire: - BFGG A 20 A_BFGsound - BFGG B 10 A_GunFlash - BFGG B 10 A_FireCustomMissile("LAZBall") - BFGG B 20 A_ReFire - Goto Ready - } -} - -actor LAZBall : BFGBall -{ - RenderStyle Translucent - Obituary "$OB_MPLAZ_BOOM" - Alpha 0.75 -} diff --git a/wadsrc/static/decorate.txt b/wadsrc/static/decorate.txt deleted file mode 100644 index 2fc515af0..000000000 --- a/wadsrc/static/decorate.txt +++ /dev/null @@ -1,8 +0,0 @@ - -#include "actors/chex/chexmonsters.txt" -#include "actors/chex/chexkeys.txt" -#include "actors/chex/chexammo.txt" -#include "actors/chex/chexweapons.txt" -#include "actors/chex/chexitems.txt" -#include "actors/chex/chexdecorations.txt" -#include "actors/chex/chexplayer.txt" diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index f65ae5555..6de64d07e 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -169,3 +169,11 @@ zscript/strife/thingstoblowup.txt zscript/strife/templar.txt zscript/strife/zombie.txt zscript/strife/sigil.txt + +zscript/chex/chexmonsters.txt +zscript/chex/chexkeys.txt +zscript/chex/chexammo.txt +zscript/chex/chexweapons.txt +zscript/chex/chexitems.txt +zscript/chex/chexdecorations.txt +zscript/chex/chexplayer.txt diff --git a/wadsrc/static/zscript/chex/chexammo.txt b/wadsrc/static/zscript/chex/chexammo.txt new file mode 100644 index 000000000..23c3cccd5 --- /dev/null +++ b/wadsrc/static/zscript/chex/chexammo.txt @@ -0,0 +1,101 @@ +// Renaming and changing messages + +// Mini Zorch ----------------------------------------------------------------- + +class MiniZorchRecharge : Clip +{ + Default + { + inventory.pickupmessage "$GOTZORCHRECHARGE"; + } +} + +class MiniZorchPack : Clip +{ + Default + { + Inventory.PickupMessage "$GOTMINIZORCHPACK"; + Inventory.Amount 50; + } + States + { + Spawn: + AMMO A -1; + Stop; + } +} + +// Large Zorch ---------------------------------------------------------------- + +class LargeZorchRecharge : Shell +{ + Default + { + inventory.pickupmessage "$GOTLARGEZORCHERRECHARGE"; + } +} + +class LargeZorchPack : Shell +{ + Default + { + Inventory.PickupMessage "$GOTLARGEZORCHERPACK"; + Inventory.Amount 20; + } + States + { + Spawn: + SBOX A -1; + Stop; + } +} + +// Zorch Propulsor ------------------------------------------------------------ + +class PropulsorZorch : RocketAmmo +{ + Default + { + inventory.pickupmessage "$GOTPROPULSORRECHARGE"; + } +} + +class PropulsorZorchPack : RocketAmmo +{ + Default + { + Inventory.PickupMessage "$GOTPROPULSORPACK"; + Inventory.Amount 5; + } + States + { + Spawn: + BROK A -1; + Stop; + } +} + +// Phasing Zorch -------------------------------------------------------------- + +class PhasingZorch : Cell +{ + Default + { + inventory.pickupmessage "$GOTPHASINGZORCHERRECHARGE"; + } +} + +class PhasingZorchPack : Cell +{ + Default + { + Inventory.PickupMessage "$GOTPHASINGZORCHERPACK"; + Inventory.Amount 100; + } + States + { + Spawn: + CELP A -1; + Stop; + } +} diff --git a/wadsrc/static/zscript/chex/chexdecorations.txt b/wadsrc/static/zscript/chex/chexdecorations.txt new file mode 100644 index 000000000..2db19181d --- /dev/null +++ b/wadsrc/static/zscript/chex/chexdecorations.txt @@ -0,0 +1,180 @@ +// Doom items renamed with height changes + +// Civilians ------------------------------------------------------------------ + +class ChexCivilian1 : GreenTorch +{ + Default + { + height 54; + } +} + +class ChexCivilian2 : ShortGreenTorch +{ + Default + { + height 54; + } +} + +class ChexCivilian3 : ShortRedTorch +{ + Default + { + height 48; + } +} + +// Landing Zone --------------------------------------------------------------- + +class ChexLandingLight : Column +{ + Default + { + height 35; + } +} + +class ChexSpaceship : TechPillar +{ + Default + { + height 52; + } +} + +// Trees and Plants ----------------------------------------------------------- + +class ChexAppleTree : Stalagtite +{ + Default + { + height 92; + } +} + +class ChexBananaTree : BigTree +{ + Default + { + height 108; + } +} + +class ChexOrangeTree : TorchTree +{ + Default + { + height 92; + } +} + +class ChexSubmergedPlant : ShortGreenColumn +{ + Default + { + height 42; + } +} + +class ChexTallFlower : HeadsOnAStick +{ + Default + { + height 25; + } +} + +class ChexTallFlower2 : DeadStick +{ + Default + { + height 25; + } +} + +// Slime Fountain ------------------------------------------------------------- + +class ChexSlimeFountain : BlueTorch +{ + Default + { + height 48; + } + States + { + Spawn: + TBLU ABCD 4; + Loop; + } +} + +// Cavern Decorations --------------------------------------------------------- + +class ChexCavernColumn : TallRedColumn +{ + Default + { + height 128; + } +} + +class ChexCavernStalagmite : TallGreenColumn +{ + Default + { + height 60; + } +} + +// Misc. Props ---------------------------------------------------------------- + +class ChexChemicalBurner : EvilEye +{ + Default + { + height 25; + } +} + +class ChexChemicalFlask : Candlestick +{ + Default + { + RenderStyle "Translucent"; + alpha 0.75; + } +} + +class ChexFlagOnPole : SkullColumn +{ + Default + { + height 128; + } +} + +class ChexGasTank : Candelabra +{ + Default + { + height 36; + } +} + +class ChexLightColumn : ShortBlueTorch +{ + Default + { + height 86; + } +} + +class ChexMineCart : ShortRedColumn +{ + Default + { + height 30; + } +} diff --git a/wadsrc/static/zscript/chex/chexitems.txt b/wadsrc/static/zscript/chex/chexitems.txt new file mode 100644 index 000000000..fc5d4c817 --- /dev/null +++ b/wadsrc/static/zscript/chex/chexitems.txt @@ -0,0 +1,89 @@ + +// General Pickups ============================================================ + +// Health --------------------------------------------------------------------- + +class GlassOfWater : HealthBonus +{ + Default + { + inventory.pickupmessage "$GOTWATER"; + } +} + +class BowlOfFruit : Stimpack +{ + Default + { + inventory.pickupmessage "$GOTFRUIT"; + } +} + +class BowlOfVegetables : Medikit +{ + Default + { + inventory.pickupmessage "$GOTVEGETABLES"; + health.lowmessage 25, "$GOTVEGETABLESNEED"; + } +} + +class SuperchargeBreakfast : Soulsphere +{ + Default + { + inventory.pickupmessage "$GOTBREAKFAST"; + } +} + +// Armor ---------------------------------------------------------------------- + +class SlimeRepellent : ArmorBonus +{ + Default + { + inventory.pickupmessage "$GOTREPELLENT"; + } +} + +class ChexArmor : GreenArmor +{ + Default + { + inventory.pickupmessage "$GOTCHEXARMOR"; + } +} + +class SuperChexArmor : BlueArmor +{ + Default + { + inventory.pickupmessage "$GOTSUPERCHEXARMOR"; + } +} + +// Powerups =================================================================== + +class ComputerAreaMap : Allmap +{ + Default + { + inventory.pickupmessage "$GOTCHEXMAP"; + } +} + +class SlimeProofSuit : RadSuit +{ + Default + { + inventory.pickupmessage "$GOTSLIMESUIT"; + } +} + +class Zorchpack : Backpack +{ + Default + { + inventory.pickupmessage "$GOTZORCHPACK"; + } +} diff --git a/wadsrc/static/zscript/chex/chexkeys.txt b/wadsrc/static/zscript/chex/chexkeys.txt new file mode 100644 index 000000000..5ac28330e --- /dev/null +++ b/wadsrc/static/zscript/chex/chexkeys.txt @@ -0,0 +1,25 @@ +// These are merely renames of the Doom cards + +class ChexBlueCard : BlueCard +{ + Default + { + inventory.pickupmessage "$GOTCBLUEKEY"; + } +} + +class ChexYellowCard : YellowCard +{ + Default + { + inventory.pickupmessage "$GOTCYELLOWKEY"; + } +} + +class ChexRedCard : RedCard +{ + Default + { + inventory.pickupmessage "$GOTCREDKEY"; + } +} diff --git a/wadsrc/static/actors/chex/chexmonsters.txt b/wadsrc/static/zscript/chex/chexmonsters.txt similarity index 62% rename from wadsrc/static/actors/chex/chexmonsters.txt rename to wadsrc/static/zscript/chex/chexmonsters.txt index 0ee3c34c5..22e397702 100644 --- a/wadsrc/static/actors/chex/chexmonsters.txt +++ b/wadsrc/static/zscript/chex/chexmonsters.txt @@ -5,16 +5,19 @@ // //=========================================================================== -actor FlemoidusCommonus : ZombieMan +class FlemoidusCommonus : ZombieMan { - DropItem "" - Obituary "$OB_COMMONUS" + Default + { + DropItem ""; + Obituary "$OB_COMMONUS"; + } States { Missile: - stop + Stop; Melee: - goto Super::Missile + goto Super::Missile; } } @@ -24,16 +27,19 @@ actor FlemoidusCommonus : ZombieMan // //=========================================================================== -actor FlemoidusBipedicus : ShotgunGuy +class FlemoidusBipedicus : ShotgunGuy { - DropItem "" - Obituary "$OB_BIPEDICUS" + Default + { + DropItem ""; + Obituary "$OB_BIPEDICUS"; + } States { Missile: - stop + Stop; Melee: - goto Super::Missile + goto Super::Missile; } } @@ -43,10 +49,13 @@ actor FlemoidusBipedicus : ShotgunGuy // //=========================================================================== -actor ArmoredFlemoidusBipedicus : DoomImp +class ArmoredFlemoidusBipedicus : DoomImp { - Obituary "$OB_BIPEDICUS2" - HitObituary "$OB_BIPEDICUS2" + Default + { + Obituary "$OB_BIPEDICUS2"; + HitObituary "$OB_BIPEDICUS2"; + } } //=========================================================================== @@ -55,9 +64,12 @@ actor ArmoredFlemoidusBipedicus : DoomImp // //=========================================================================== -actor FlemoidusCycloptisCommonus : Demon +class FlemoidusCycloptisCommonus : Demon { - Obituary "$OB_CYCLOPTIS" + Default + { + Obituary "$OB_CYCLOPTIS"; + } } //=========================================================================== @@ -66,24 +78,30 @@ actor FlemoidusCycloptisCommonus : Demon // //=========================================================================== -actor Flembrane : BaronOfHell +class Flembrane : BaronOfHell { - radius 44 - height 100 - speed 0 - Obituary "$OB_FLEMBRANE" + Default + { + radius 44; + height 100; + speed 0; + Obituary "$OB_FLEMBRANE"; + } States { Missile: - BOSS EF 3 A_FaceTarget - BOSS G 0 A_BruisAttack - goto See + BOSS EF 3 A_FaceTarget; + BOSS G 0 A_BruisAttack; + goto See; } } //=========================================================================== -actor ChexSoul : LostSoul +class ChexSoul : LostSoul { - height 0 + Default + { + height 0; + } } diff --git a/wadsrc/static/zscript/chex/chexplayer.txt b/wadsrc/static/zscript/chex/chexplayer.txt new file mode 100644 index 000000000..43f7fc1ee --- /dev/null +++ b/wadsrc/static/zscript/chex/chexplayer.txt @@ -0,0 +1,32 @@ +// Chex Warrior + +class ChexPlayer : DoomPlayer +{ + Default + { + player.displayname "Chex Warrior"; + player.crouchsprite ""; + player.colorrange 192, 207; //Not perfect, but its better than everyone being blue. + player.startitem "MiniZorcher"; + player.startitem "Bootspoon"; + player.startitem "MiniZorchRecharge", 50; + player.damagescreencolor "60 b0 58"; + player.WeaponSlot 1, "Bootspoon", "SuperBootspork"; + player.WeaponSlot 2, "MiniZorcher"; + player.WeaponSlot 3, "LargeZorcher", "SuperLargeZorcher"; + player.WeaponSlot 4, "RapidZorcher"; + player.WeaponSlot 5, "ZorchPropulsor"; + player.WeaponSlot 6, "PhasingZorcher"; + player.WeaponSlot 7, "LAZDevice"; + + Player.Colorset 0, "Light Blue", 0xC0, 0xCF, 0xC2; + Player.Colorset 1, "Green", 0x70, 0x7F, 0x72; + Player.Colorset 2, "Gray", 0x60, 0x6F, 0x62; + Player.Colorset 3, "Brown", 0x40, 0x4F, 0x42; + Player.Colorset 4, "Red", 0x20, 0x2F, 0x22; + Player.Colorset 5, "Light Gray", 0x58, 0x67, 0x5A; + Player.Colorset 6, "Light Brown", 0x38, 0x47, 0x3A; + Player.Colorset 7, "Light Red", 0xB0, 0xBF, 0xB2; + } + +} diff --git a/wadsrc/static/zscript/chex/chexweapons.txt b/wadsrc/static/zscript/chex/chexweapons.txt new file mode 100644 index 000000000..a4c862d64 --- /dev/null +++ b/wadsrc/static/zscript/chex/chexweapons.txt @@ -0,0 +1,160 @@ +// Same as Doom weapons, but the obituaries are removed. + +class Bootspoon : Fist +{ + Default + { + obituary "$OB_MPSPOON"; + Tag "$TAG_SPOON"; + } +} + +class SuperBootspork : Chainsaw +{ + Default + { + obituary "$OB_MPBOOTSPORK"; + Inventory.PickupMessage "$GOTSUPERBOOTSPORK"; + Tag "$TAG_SPORK"; + } +} + +class MiniZorcher : Pistol +{ + Default + { + obituary "$OB_MPZORCH"; + inventory.pickupmessage "$GOTMINIZORCHER"; + Tag "$TAG_MINIZORCHER"; + } + States + { + Spawn: + MINZ A -1; + Stop; + } +} + +class LargeZorcher : Shotgun +{ + Default + { + obituary "$OB_MPZORCH"; + inventory.pickupmessage "$GOTLARGEZORCHER"; + Tag "$TAG_LARGEZORCHER"; + } +} + +class SuperLargeZorcher : SuperShotgun +{ + Default + { + obituary "$OB_MPMEGAZORCH"; + inventory.pickupmessage "$GOTSUPERLARGEZORCHER"; + Tag "$TAG_SUPERLARGEZORCHER"; + } +} + +class RapidZorcher : Chaingun +{ + Default + { + obituary "$OB_MPRAPIDZORCH"; + inventory.pickupmessage "$GOTRAPIDZORCHER"; + Tag "$TAG_RAPIDZORCHER"; + } +} + +class ZorchPropulsor : RocketLauncher +{ + Default + { + obituary ""; + inventory.pickupmessage "$GOTZORCHPROPULSOR"; + Tag "$TAG_ZORCHPROPULSOR"; + } + States + { + Fire: + MISG B 8 A_GunFlash; + MISG B 12 A_FireCustomMissile("PropulsorMissile"); + MISG B 0 A_ReFire; + Goto Ready; + } +} + +class PropulsorMissile : Rocket +{ + Default + { + -ROCKETTRAIL + -DEHEXPLOSION + RenderStyle "Translucent"; + Obituary "$OB_MPPROPULSOR"; + Alpha 0.75; + } +} + +class PhasingZorcher : PlasmaRifle +{ + Default + { + obituary ""; + inventory.pickupmessage "$GOTPHASINGZORCHER"; + Tag "$TAG_PHASINGZORCHER"; + } + States + { + Fire: + PLSG A 0 A_GunFlash; + PLSG A 3 A_FireCustomMissile("PhaseZorchMissile"); + PLSG B 20 A_ReFire; + Goto Ready; + Flash: + PLSF A 0 A_Jump(128, "Flash2"); + PLSF A 3 Bright A_Light1; + Goto LightDone; + Flash2: + PLSF B 3 Bright A_Light1; + Goto LightDone; + } +} + +class PhaseZorchMissile : PlasmaBall +{ + Default + { + RenderStyle "Translucent"; + Obituary "$OB_MPPHASEZORCH"; + Alpha 0.75; + } +} + +class LAZDevice : BFG9000 +{ + Default + { + obituary ""; + inventory.pickupmessage "$GOTLAZDEVICE"; + Tag "$TAG_LAZDEVICE"; + } + States + { + Fire: + BFGG A 20 A_BFGsound; + BFGG B 10 A_GunFlash; + BFGG B 10 A_FireCustomMissile("LAZBall"); + BFGG B 20 A_ReFire; + Goto Ready; + } +} + +class LAZBall : BFGBall +{ + Default + { + RenderStyle "Translucent"; + Obituary "$OB_MPLAZ_BOOM"; + Alpha 0.75; + } +} From 665d7526867f52b12d62d861643c0042e797e165 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 19 Oct 2016 00:35:34 +0200 Subject: [PATCH 070/255] - added 'null' token to the ZScript parser which is needed for null pointers. - removed function declaration parser from DECORATE because it is not needed anymore. - fixed: comparison operators could not handle names. --- src/sc_man_scanner.re | 1 + src/sc_man_tokens.h | 1 + src/scripting/codegeneration/codegen.cpp | 20 +- src/scripting/decorate/thingdef_parse.cpp | 264 ---------------------- src/scripting/zscript/zcc-parse.lemon | 7 + src/scripting/zscript/zcc_exprlist.h | 1 + src/scripting/zscript/zcc_parser.cpp | 1 + 7 files changed, 23 insertions(+), 272 deletions(-) diff --git a/src/sc_man_scanner.re b/src/sc_man_scanner.re index ba0e9a8e5..caeb18f8c 100644 --- a/src/sc_man_scanner.re +++ b/src/sc_man_scanner.re @@ -171,6 +171,7 @@ std2: 'global' { RET(TK_Global); } 'self' { RET(TK_Self); } 'stop' { RET(TK_Stop); } + 'null' { RET(TK_Null); } 'is' { RET(TK_Is); } 'replaces' { RET(TK_Replaces); } diff --git a/src/sc_man_tokens.h b/src/sc_man_tokens.h index 934558d54..69927883c 100644 --- a/src/sc_man_tokens.h +++ b/src/sc_man_tokens.h @@ -106,6 +106,7 @@ xx(TK_Optional, "'optional'") xx(TK_Export, "'expert'") xx(TK_Virtual, "'virtual'") xx(TK_Super, "'super'") +xx(TK_Null, "'null'") xx(TK_Global, "'global'") xx(TK_Self, "'self'") xx(TK_Stop, "'stop'") diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index bc503d832..7687be371 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1888,16 +1888,20 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) { ValueType = TypeBool; } + else if (left->ValueType == TypeName && right->ValueType == TypeName) + { + ValueType = TypeName; + } else if (left->IsNumeric() && right->IsNumeric()) { - if (left->ValueType->GetRegType() == REGT_INT && right->ValueType->GetRegType() == REGT_INT) - { - ValueType = TypeSInt32; - } + if (left->ValueType->GetRegType() == REGT_INT && right->ValueType->GetRegType() == REGT_INT) + { + ValueType = TypeSInt32; + } else - { - ValueType = TypeFloat64; - } + { + ValueType = TypeFloat64; + } } else if (left->ValueType->GetRegType() == REGT_POINTER && left->ValueType == right->ValueType) { @@ -2395,7 +2399,7 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) return NULL; } - if (!IsNumeric() && !IsPointer()) + if (!IsNumeric() && !IsPointer() && ValueType != TypeName) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index f416d6103..bd4885c87 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -334,213 +334,6 @@ static void ParseEnum (FScanner &sc, PSymbolTable *symt, PClassActor *cls) sc.MustGetToken(';'); } -//========================================================================== -// -// ParseArgListDef -// -// Parses the argument list from a function declaration. -// -//========================================================================== - -static void ParseArgListDef(FScanner &sc, PClassActor *cls, - TArray &args, TArray &argflags) -{ - if (!sc.CheckToken(')')) - { - while (sc.TokenType != ')') - { - int flags = 0; - PType *type = NULL; - PClass *restrict = NULL; - - // Retrieve flags before type name - for (;;) - { - if (sc.CheckToken(TK_Coerce) || sc.CheckToken(TK_Native)) - { - } - else - { - break; - } - } - // Read the variable type - sc.MustGetAnyToken(); - switch (sc.TokenType) - { - case TK_Bool: - type = TypeBool; - break; - - case TK_Int: - type = TypeSInt32; - break; - - case TK_Float: - type = TypeFloat64; - break; - - case TK_Sound: type = TypeSound; break; - case TK_String: type = TypeString; break; - case TK_Name: type = TypeName; break; - case TK_State: type = TypeState; break; - case TK_Color: type = TypeColor; break; - case TK_Class: - sc.MustGetToken('<'); - sc.MustGetToken(TK_Identifier); // Get class name - restrict = PClass::FindClass(sc.String); - if (restrict == NULL) - { - sc.ScriptMessage("Unknown class type %s", sc.String); - FScriptPosition::ErrorCounter++; - } - else - { - type = NewClassPointer(restrict); - } - sc.MustGetToken('>'); - break; - case TK_Ellipsis: - // Making the final type NULL signals a varargs function. - type = NULL; - sc.MustGetToken(')'); - sc.UnGet(); - break; - default: - sc.ScriptMessage ("Unknown variable type %s", sc.TokenName(sc.TokenType, sc.String).GetChars()); - type = TypeSInt32; - FScriptPosition::ErrorCounter++; - break; - } - // Read the optional variable name - if (!sc.CheckToken(',') && !sc.CheckToken(')')) - { - sc.MustGetToken(TK_Identifier); - } - else - { - sc.UnGet(); - } - - if (sc.CheckToken('=')) - { - flags |= VARF_Optional; - FxExpression *def = ParseParameter(sc, cls, type, true); - delete def; - } - - args.Push(type); - argflags.Push(flags); - sc.MustGetAnyToken(); - if (sc.TokenType != ',' && sc.TokenType != ')') - { - sc.ScriptError ("Expected ',' or ')' but got %s instead", sc.TokenName(sc.TokenType, sc.String).GetChars()); - } - } - } - sc.MustGetToken(';'); -} - -//========================================================================== -// -// ParseFunctionDef -// -// Parses a native function's parameters and adds it to the class, -// if possible. -// -//========================================================================== - -void ParseFunctionDef(FScanner &sc, PClassActor *cls, FName funcname, - TArray &rets, DWORD funcflags) -{ - assert(cls != NULL); - - const AFuncDesc *afd; - TArray args; - TArray argflags; - TArray argnames; - - afd = FindFunction(funcname); - if (afd == NULL) - { - sc.ScriptMessage ("The function '%s' has not been exported from the executable.", funcname.GetChars()); - FScriptPosition::ErrorCounter++; - } - sc.MustGetToken('('); - - SetImplicitArgs(&args, &argflags, &argnames, cls, funcflags); - // This function will be removed once all internal classes have been ported so don't bother filling in the function's argument names, because for anything going through here they'll never be used. - ParseArgListDef(sc, cls, args, argflags); - - if (afd != NULL) - { - PFunction *sym = new PFunction(cls, funcname); - sym->AddVariant(NewPrototype(rets, args), argflags, argnames, *(afd->VMPointer), funcflags); - if (cls->Symbols.AddSymbol(sym) == NULL) - { - delete sym; - sc.ScriptMessage ("'%s' is already defined in class '%s'.", - funcname.GetChars(), cls->TypeName.GetChars()); - FScriptPosition::ErrorCounter++; - } - } -} - -//========================================================================== -// -// ParseNativeFunction -// -// Parses a non-action function declaration. -// -//========================================================================== - -static void ParseNativeFunction(FScanner &sc, PClassActor *cls) -{ - TArray rets(1); - - if (sc.LumpNum == -1 || Wads.GetLumpFile(sc.LumpNum) > 0) - { - sc.ScriptMessage ("functions can only be declared by native actors!"); - FScriptPosition::ErrorCounter++; - } - - // Read the type and make sure it's acceptable. - sc.MustGetAnyToken(); - switch (sc.TokenType) - { - case TK_Bool: - rets.Push(TypeBool); - break; - - case TK_Int: - rets.Push(TypeSInt32); - break; - - case TK_Float: - rets.Push(TypeFloat64); - break; - - case TK_State: - rets.Push(TypeState); - break; - - case TK_Void: - break; - - case TK_Identifier: - rets.Push(NewPointer(RUNTIME_CLASS(DObject))); - // Todo: Object type - sc.ScriptError("Object type variables not implemented yet!"); - break; - - default: - sc.ScriptError("Invalid return type %s", sc.String); - return; - } - sc.MustGetToken(TK_Identifier); - ParseFunctionDef(sc, cls, sc.String, rets, VARF_Method); -} - //========================================================================== // // ParseUserVariable @@ -1081,55 +874,6 @@ static void ParseActorProperty(FScanner &sc, Baggage &bag) } } -//========================================================================== -// -// ActorActionDef -// -// Parses an action function definition. A lot of this is essentially -// documentation in the declaration for when I have a proper language -// ready. -// -//========================================================================== - -static void ParseActionDef (FScanner &sc, PClassActor *cls) -{ - unsigned int error = 0; - FName funcname; - TArray rets; - - if (sc.LumpNum == -1 || Wads.GetLumpFile(sc.LumpNum) > 0) - { - sc.ScriptMessage ("Action functions can only be imported by internal class and actor definitions!"); - FScriptPosition::ErrorCounter++; - } - - sc.MustGetToken(TK_Native); - // check for a return value - do - { - if (sc.CheckToken(TK_Bool)) - { - rets.Push(TypeBool); - } - else if (sc.CheckToken(TK_Int)) - { - rets.Push(TypeSInt32); - } - else if (sc.CheckToken(TK_State)) - { - rets.Push(TypeState); - } - else if (sc.CheckToken(TK_Float)) - { - rets.Push(TypeFloat64); - } - } - while (sc.CheckToken(',')); - sc.MustGetToken(TK_Identifier); - funcname = sc.String; - ParseFunctionDef(sc, cls, funcname, rets, VARF_Method | VARF_Action); -} - //========================================================================== // // Starts a new actor definition @@ -1330,10 +1074,6 @@ static void ParseActor(FScanner &sc) { switch (sc.TokenType) { - case TK_Action: - ParseActionDef (sc, info); - break; - case TK_Const: ParseConstant (sc, &info->Symbols, info); break; @@ -1342,10 +1082,6 @@ static void ParseActor(FScanner &sc) ParseEnum (sc, &info->Symbols, info); break; - case TK_Native: - ParseNativeFunction (sc, info); - break; - case TK_Var: ParseUserVariable (sc, &info->Symbols, info); break; diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 1e10103a0..595f2a318 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -956,6 +956,13 @@ primary(X) ::= IDENTIFIER(A). expr->Type = NULL; X = expr; } +primary(X) ::= NULL(T). +{ + NEW_AST_NODE(Expression, expr, T); + expr->Operation = PEX_Null; + expr->Type = NULL; + X = expr; +} primary(X) ::= SUPER(T). { NEW_AST_NODE(Expression, expr, T); diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index 46a1b9c69..eeabb10e5 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -3,6 +3,7 @@ xx(Nil, ) xx(ID, ) xx(Super, ) +xx(Null, ) xx(Self, ) xx(ConstValue, ) xx(FuncCall, ) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 9fefa537d..48fd28f45 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -153,6 +153,7 @@ static void InitTokenMap() TOKENDEF (TK_Out, ZCC_OUT); TOKENDEF (TK_Optional, ZCC_OPTIONAL); TOKENDEF (TK_Super, ZCC_SUPER); + TOKENDEF (TK_Null, ZCC_NULL); TOKENDEF (TK_Self, ZCC_SELF); TOKENDEF ('~', ZCC_TILDE); TOKENDEF ('!', ZCC_BANG); From 33567741f5c3b0bc80dd7d208db5857989ac0e5d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 19 Oct 2016 10:38:25 +0200 Subject: [PATCH 071/255] - fixed: The parser was not generating a compound statement node for anonymous action functions. --- src/scripting/zscript/zcc-parse.lemon | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 595f2a318..45b7a99ff 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -522,7 +522,12 @@ light_list(X) ::= light_list(A) COMMA STRCONST(B). } /* A state action can be either a compound statement or a single action function call. */ -state_action(X) ::= LBRACE statement_list(A) scanner_mode RBRACE. { X = A; /*X-overwrites-A*/ } +state_action(X) ::= LBRACE(T) statement_list(A) scanner_mode RBRACE. +{ + NEW_AST_NODE(CompoundStmt,stmt,T); + stmt->Content = A; + X = stmt; +} state_action(X) ::= LBRACE error scanner_mode RBRACE. { X = NULL; } state_action(X) ::= state_call(A) scanner_mode SEMICOLON. { X = A; /*X-overwrites-A*/ } From cfbcfc440d134f6ed6642b45456bce449b6c0864 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 19 Oct 2016 13:07:44 +0200 Subject: [PATCH 072/255] - 'fixed' local variable declrations to work like C, not like some Lua-inspired nightmare. Also added proper initialization syntax for arrays. --- src/scripting/zscript/ast.cpp | 13 ++++- src/scripting/zscript/zcc-parse.lemon | 70 +++++++++++++++++++++++++-- src/scripting/zscript/zcc_parser.h | 10 +++- 3 files changed, 85 insertions(+), 8 deletions(-) diff --git a/src/scripting/zscript/ast.cpp b/src/scripting/zscript/ast.cpp index 45b8053ba..2f15c019e 100644 --- a/src/scripting/zscript/ast.cpp +++ b/src/scripting/zscript/ast.cpp @@ -437,6 +437,17 @@ static void PrintVarName(FLispString &out, ZCC_TreeNode *node) out.Close(); } +static void PrintVarInit(FLispString &out, ZCC_TreeNode *node) +{ + ZCC_VarInit *vnode = (ZCC_VarInit *)node; + out.Open("var-init"); + PrintNodes(out, vnode->ArraySize); + PrintNodes(out, vnode->Init); + if (vnode->InitIsArray) out.Add("array", 5); + out.AddName(vnode->Name); + out.Close(); +} + static void PrintType(FLispString &out, ZCC_TreeNode *node) { ZCC_Type *tnode = (ZCC_Type *)node; @@ -762,7 +773,6 @@ static void PrintLocalVarStmt(FLispString &out, ZCC_TreeNode *node) out.Open("local-var-stmt"); PrintNodes(out, snode->Type); PrintNodes(out, snode->Vars); - PrintNodes(out, snode->Inits); out.Close(); } @@ -859,6 +869,7 @@ void (* const TreeNodePrinter[NUM_AST_NODE_TYPES])(FLispString &, ZCC_TreeNode * PrintStateGoto, PrintStateLine, PrintVarName, + PrintVarInit, PrintType, PrintBasicType, PrintMapType, diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 45b7a99ff..43d7d02ab 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -1637,15 +1637,75 @@ assign_op(X) ::= XOREQ(T). { X.Int = ZCC_XOREQ; X.SourceLoc = T.SourceLoc; } %type local_var{ZCC_LocalVarStmt *} -local_var(X) ::= type(A) variable_list(B) var_init(C). +local_var(X) ::= type(A) variable_list_with_init(B). { NEW_AST_NODE(LocalVarStmt,vardef,A); vardef->Type = A; vardef->Vars = B; - vardef->Inits = C; X = vardef; } -%type var_init{ZCC_Expression *} -var_init(X) ::= . { X = NULL; } -var_init(X) ::= EQ expr_list(A). { X = A; /*X-overwrites-A*/ } +%type var_init{ZCC_VarInit *} +var_init(X) ::= IDENTIFIER(A). +{ + NEW_AST_NODE(VarInit,var,A); + var->Name = ENamedName(A.Int); + var->ArraySize = NULL; + var->Init = NULL; + var->InitIsArray = false; + X = var; +} + +var_init(X) ::= IDENTIFIER(A) array_size(B). +{ + NEW_AST_NODE(VarInit,var,A); + var->Name = ENamedName(A.Int); + var->ArraySize = B; + var->Init = NULL; + var->InitIsArray = false; + X = var; +} + +var_init(X) ::= IDENTIFIER(A) EQ expr(B). +{ + NEW_AST_NODE(VarInit,var,A); + var->Name = ENamedName(A.Int); + var->ArraySize = NULL; + var->Init = B; + var->InitIsArray = false; + X = var; +} + +var_init(X) ::= IDENTIFIER(A) EQ LBRACE expr_list(C) RBRACE. // this is for arrays which declare the size with the type +{ + NEW_AST_NODE(VarInit,var,A); + var->Name = ENamedName(A.Int); + var->ArraySize = NULL; + var->Init = C; + var->InitIsArray = true; + X = var; +} + +var_init(X) ::= IDENTIFIER(A) array_size(B) EQ LBRACE expr_list(C) RBRACE. +{ + NEW_AST_NODE(VarInit,var,A); + var->Name = ENamedName(A.Int); + var->ArraySize = B; + var->Init = C; + var->InitIsArray = true; + X = var; +} + +var_init(X) ::= IDENTIFIER EQ LBRACE error RBRACE. +{ + X = NULL; +} + +%type variable_list_with_init{ZCC_VarInit *} + +variable_list_with_init(X) ::= var_init(X). +variable_list_with_init(X) ::= variable_list_with_init(A) COMMA var_init(B). +{ + A->AppendSibling(B); + X = A; /*X-overwrites-A*/ +} diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 5dae72ee0..503ef7e9e 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -62,6 +62,7 @@ enum EZCCTreeNodeType AST_StateGoto, AST_StateLine, AST_VarName, + AST_VarInit, AST_Type, AST_BasicType, AST_MapType, @@ -294,6 +295,12 @@ struct ZCC_VarName : ZCC_TreeNode ZCC_Expression *ArraySize; // NULL if not an array }; +struct ZCC_VarInit : ZCC_VarName +{ + ZCC_Expression *Init; + bool InitIsArray; // this is needed to distinguish one-element arrays from raw elements. +}; + struct ZCC_Type : ZCC_TreeNode { ZCC_Expression *ArraySize; // NULL if not an array @@ -446,8 +453,7 @@ struct ZCC_AssignStmt : ZCC_Statement struct ZCC_LocalVarStmt : ZCC_Statement { ZCC_Type *Type; - ZCC_VarName *Vars; - ZCC_Expression *Inits; + ZCC_VarInit *Vars; }; struct ZCC_FuncParamDecl : ZCC_TreeNode From 458c68775f4adee9df0f57081296c6d1c0d4e67e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 19 Oct 2016 14:36:54 +0200 Subject: [PATCH 073/255] - fixed handling of loop statements. All break and continue statements were collected in one list, and each loop statement taking hold of that entire list, including the breaks and continues from previous outer loops. Changed it so that loop statements contain the jump addresses themselves and set a pointer in FCompileContext, so that the jump point can be set directly in the loop statement - and an error printed if there is none in the resolving stage, not the emitting one. Consolidated the identical backpatching code of the three loop statement nodes into a subfunction. --- src/scripting/codegeneration/codegen.cpp | 112 +++++++++-------------- src/scripting/codegeneration/codegen.h | 17 ++-- 2 files changed, 52 insertions(+), 77 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 7687be371..d5c70f493 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5185,23 +5185,36 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) return ExpEmit(); } - //========================================================================== // -// FxLoopStatement +// FxLoopStatement :: Resolve +// +// saves the loop pointer in the context and sets this object as the current loop +// so that continues and breaks always resolve to the innermost loop. // //========================================================================== -void FxLoopStatement::HandleJumps(int token, FCompileContext &ctx) +FxExpression *FxLoopStatement::Resolve(FCompileContext &ctx) { - for (unsigned int i = 0; i < ctx.Jumps.Size(); i++) + auto outer = ctx.Loop; + ctx.Loop = this; + auto x = DoResolve(ctx); + ctx.Loop = outer; + return x; +} + +void FxLoopStatement::Backpatch(VMFunctionBuilder *build, size_t loopstart, size_t loopend) +{ + // Give a proper address to any break/continue statement within this loop. + for (unsigned int i = 0; i < Jumps.Size(); i++) { - if (ctx.Jumps[i]->Token == token) + if (Jumps[i]->Token == TK_Break) { - ctx.Jumps[i]->AddressResolver = this; - JumpAddresses.Push(ctx.Jumps[i]); - ctx.Jumps.Delete(i); - i--; + build->Backpatch(Jumps[i]->Address, loopend); + } + else + { // Continue statement. + build->Backpatch(Jumps[i]->Address, loopstart); } } } @@ -5224,15 +5237,12 @@ FxWhileLoop::~FxWhileLoop() SAFE_DELETE(Code); } -FxExpression *FxWhileLoop::Resolve(FCompileContext &ctx) +FxExpression *FxWhileLoop::DoResolve(FCompileContext &ctx) { CHECKRESOLVED(); SAFE_RESOLVE(Condition, ctx); SAFE_RESOLVE_OPT(Code, ctx); - HandleJumps(TK_Break, ctx); - HandleJumps(TK_Continue, ctx); - if (Condition->ValueType != TypeBool) { Condition = new FxBoolCast(Condition); @@ -5291,19 +5301,7 @@ ExpEmit FxWhileLoop::Emit(VMFunctionBuilder *build) build->Backpatch(jumpspot, loopend); } - // Give a proper address to any break/continue statement within this loop. - for (unsigned int i = 0; i < JumpAddresses.Size(); i++) - { - if (JumpAddresses[i]->Token == TK_Break) - { - build->Backpatch(JumpAddresses[i]->Address, loopend); - } - else - { // Continue statement. - build->Backpatch(JumpAddresses[i]->Address, loopstart); - } - } - + Backpatch(build, loopstart, loopend); return ExpEmit(); } @@ -5325,15 +5323,12 @@ FxDoWhileLoop::~FxDoWhileLoop() SAFE_DELETE(Code); } -FxExpression *FxDoWhileLoop::Resolve(FCompileContext &ctx) +FxExpression *FxDoWhileLoop::DoResolve(FCompileContext &ctx) { CHECKRESOLVED(); SAFE_RESOLVE(Condition, ctx); SAFE_RESOLVE_OPT(Code, ctx); - HandleJumps(TK_Break, ctx); - HandleJumps(TK_Continue, ctx); - if (Condition->ValueType != TypeBool) { Condition = new FxBoolCast(Condition); @@ -5344,7 +5339,7 @@ FxExpression *FxDoWhileLoop::Resolve(FCompileContext &ctx) { if (static_cast(Condition)->GetValue().GetBool() == false) { // The code executes once, if any. - if (JumpAddresses.Size() == 0) + if (Jumps.Size() == 0) { // We would still have to handle the jumps however. FxExpression *e = Code; if (e == nullptr) e = new FxNop(ScriptPosition); @@ -5393,18 +5388,7 @@ ExpEmit FxDoWhileLoop::Emit(VMFunctionBuilder *build) } loopend = build->GetAddress(); - // Give a proper address to any break/continue statement within this loop. - for (unsigned int i = 0; i < JumpAddresses.Size(); i++) - { - if (JumpAddresses[i]->Token == TK_Break) - { - build->Backpatch(JumpAddresses[i]->Address, loopend); - } - else - { // Continue statement. - build->Backpatch(JumpAddresses[i]->Address, loopstart); - } - } + Backpatch(build, loopstart, loopend); return ExpEmit(); } @@ -5429,7 +5413,7 @@ FxForLoop::~FxForLoop() SAFE_DELETE(Code); } -FxExpression *FxForLoop::Resolve(FCompileContext &ctx) +FxExpression *FxForLoop::DoResolve(FCompileContext &ctx) { CHECKRESOLVED(); SAFE_RESOLVE_OPT(Init, ctx); @@ -5437,9 +5421,6 @@ FxExpression *FxForLoop::Resolve(FCompileContext &ctx) SAFE_RESOLVE_OPT(Iteration, ctx); SAFE_RESOLVE_OPT(Code, ctx); - HandleJumps(TK_Break, ctx); - HandleJumps(TK_Continue, ctx); - if (Condition != nullptr) { if (Condition->ValueType != TypeBool) @@ -5480,7 +5461,7 @@ ExpEmit FxForLoop::Emit(VMFunctionBuilder *build) size_t codestart; size_t jumpspot; - // Init statement. + // Init statement (only used by DECORATE. ZScript is pulling it before the loop statement and enclosing the entire loop in a compound statement so that Init can have local variables.) if (Init != nullptr) { ExpEmit init = Init->Emit(build); @@ -5520,19 +5501,7 @@ ExpEmit FxForLoop::Emit(VMFunctionBuilder *build) build->Backpatch(jumpspot, loopend); } - // Give a proper address to any break/continue statement within this loop. - for (unsigned int i = 0; i < JumpAddresses.Size(); i++) - { - if (JumpAddresses[i]->Token == TK_Break) - { - build->Backpatch(JumpAddresses[i]->Address, loopend); - } - else - { // Continue statement. - build->Backpatch(JumpAddresses[i]->Address, loopstart); - } - } - + Backpatch(build, loopstart, loopend); return ExpEmit(); } @@ -5543,7 +5512,7 @@ ExpEmit FxForLoop::Emit(VMFunctionBuilder *build) //========================================================================== FxJumpStatement::FxJumpStatement(int token, const FScriptPosition &pos) -: FxExpression(pos), Token(token), AddressResolver(nullptr) +: FxExpression(pos), Token(token) { ValueType = TypeVoid; } @@ -5552,18 +5521,21 @@ FxExpression *FxJumpStatement::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); - ctx.Jumps.Push(this); - - return this; + if (ctx.Loop != nullptr) + { + ctx.Loop->Jumps.Push(this); + return this; + } + else + { + ScriptPosition.Message(MSG_ERROR, "'%s' outside of a loop", Token == TK_Break ? "break" : "continue"); + delete this; + return nullptr; + } } ExpEmit FxJumpStatement::Emit(VMFunctionBuilder *build) { - if (AddressResolver == nullptr) - { - ScriptPosition.Message(MSG_ERROR, "Jump statement %s has nowhere to go!", FScanner::TokenName(Token).GetChars()); - } - Address = build->Emit(OP_JMP, 0); return ExpEmit(); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 1a2d2045d..c4e1753bd 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -62,10 +62,11 @@ class FxJumpStatement; // //========================================================================== struct FScriptPosition; +class FxLoopStatement; struct FCompileContext { - TArray Jumps; + FxLoopStatement *Loop; PPrototype *ReturnProto; PFunction *Function; // The function that is currently being compiled (or nullptr for constant evaluation.) PClass *Class; // The type of the owning class. @@ -1127,9 +1128,12 @@ protected: { } - void HandleJumps(int token, FCompileContext &ctx); + void Backpatch(VMFunctionBuilder *build, size_t loopstart, size_t loopend); + FxExpression *Resolve(FCompileContext&) final; + virtual FxExpression *DoResolve(FCompileContext&) = 0; - TArray JumpAddresses; +public: + TArray Jumps; }; //========================================================================== @@ -1146,7 +1150,7 @@ class FxWhileLoop : public FxLoopStatement public: FxWhileLoop(FxExpression *condition, FxExpression *code, const FScriptPosition &pos); ~FxWhileLoop(); - FxExpression *Resolve(FCompileContext&); + FxExpression *DoResolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1164,7 +1168,7 @@ class FxDoWhileLoop : public FxLoopStatement public: FxDoWhileLoop(FxExpression *condition, FxExpression *code, const FScriptPosition &pos); ~FxDoWhileLoop(); - FxExpression *Resolve(FCompileContext&); + FxExpression *DoResolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1184,7 +1188,7 @@ class FxForLoop : public FxLoopStatement public: FxForLoop(FxExpression *init, FxExpression *condition, FxExpression *iteration, FxExpression *code, const FScriptPosition &pos); ~FxForLoop(); - FxExpression *Resolve(FCompileContext&); + FxExpression *DoResolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1203,7 +1207,6 @@ public: int Token; size_t Address; - FxExpression *AddressResolver; }; //========================================================================== From 8a6230d64a23a8c51e5dc519322ceddc0ca51032 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 19 Oct 2016 16:15:02 +0200 Subject: [PATCH 074/255] - Renamed FxSequence to FxCompoundStatement. - fixed: The state parser was unable to accept empty anonymous functions, which should be treated as if there is none at all. --- src/scripting/codegeneration/codegen.cpp | 12 ++++++------ src/scripting/codegeneration/codegen.h | 6 +++--- src/scripting/decorate/thingdef_states.cpp | 6 +++--- src/scripting/zscript/zcc-parse.lemon | 4 ++++ src/scripting/zscript/zcc_compile.cpp | 2 +- 5 files changed, 17 insertions(+), 13 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d5c70f493..7a7ff7f13 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5016,11 +5016,11 @@ ExpEmit FxFlopFunctionCall::Emit(VMFunctionBuilder *build) //========================================================================== // -// FxSequence :: Resolve +// FxCompoundStatement :: Resolve // //========================================================================== -FxExpression *FxSequence::Resolve(FCompileContext &ctx) +FxExpression *FxCompoundStatement::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); for (unsigned i = 0; i < Expressions.Size(); ++i) @@ -5036,11 +5036,11 @@ FxExpression *FxSequence::Resolve(FCompileContext &ctx) //========================================================================== // -// FxSequence :: Emit +// FxCompoundStatement :: Emit // //========================================================================== -ExpEmit FxSequence::Emit(VMFunctionBuilder *build) +ExpEmit FxCompoundStatement::Emit(VMFunctionBuilder *build) { for (unsigned i = 0; i < Expressions.Size(); ++i) { @@ -5053,11 +5053,11 @@ ExpEmit FxSequence::Emit(VMFunctionBuilder *build) //========================================================================== // -// FxSequence :: GetDirectFunction +// FxCompoundStatement :: GetDirectFunction // //========================================================================== -VMFunction *FxSequence::GetDirectFunction() +VMFunction *FxCompoundStatement::GetDirectFunction() { if (Expressions.Size() == 1) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index c4e1753bd..57a6d4257 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -1079,16 +1079,16 @@ public: //========================================================================== // -// FxSequence +// FxCompoundStatement // //========================================================================== -class FxSequence : public FxExpression +class FxCompoundStatement : public FxExpression { TDeletingArray Expressions; public: - FxSequence(const FScriptPosition &pos) : FxExpression(pos) {} + FxCompoundStatement(const FScriptPosition &pos) : FxExpression(pos) {} FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); } diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 59ec3e39d..11db1504d 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -314,7 +314,7 @@ do_stop: ScriptCode = ParseActions(sc, state, statestring, bag, hasfinalret); if (!hasfinalret && ScriptCode != nullptr) { - static_cast(ScriptCode)->Add(new FxReturnStatement(nullptr, sc)); + static_cast(ScriptCode)->Add(new FxReturnStatement(nullptr, sc)); } goto endofstate; } @@ -474,7 +474,7 @@ FxExpression *ParseActions(FScanner &sc, FState state, FString statestring, Bagg const FScriptPosition pos(sc); - FxSequence *seq = NULL; + FxCompoundStatement *seq = NULL; bool lastwasret = false; sc.MustGetString(); @@ -536,7 +536,7 @@ FxExpression *ParseActions(FScanner &sc, FState state, FString statestring, Bagg { if (seq == NULL) { - seq = new FxSequence(pos); + seq = new FxCompoundStatement(pos); } seq->Add(add); } diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 43d7d02ab..0c493d54a 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -528,6 +528,10 @@ state_action(X) ::= LBRACE(T) statement_list(A) scanner_mode RBRACE. stmt->Content = A; X = stmt; } +state_action(X) ::= LBRACE scanner_mode RBRACE. +{ + X = NULL; +} state_action(X) ::= LBRACE error scanner_mode RBRACE. { X = NULL; } state_action(X) ::= state_call(A) scanner_mode SEMICOLON. { X = A; /*X-overwrites-A*/ } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 43219acb1..e86a7c959 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2087,7 +2087,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a tcall->Code = ParseActions(sc, state, statestring, bag, hasfinalret); if (!hasfinalret && tcall->Code != nullptr) { - static_cast(tcall->Code)->Add(new FxReturnStatement(nullptr, sc)); + static_cast(tcall->Code)->Add(new FxReturnStatement(nullptr, sc)); } */ From 2d85efce2ad0ae4150223979e26997f8d11e3f87 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 19 Oct 2016 19:05:48 +0200 Subject: [PATCH 075/255] - added processing of compound statements to the compiler. This means that anonymous functions without control statements are generating code now. - added local variable declarations to the code generator. This is not tested yet, that will come with the next commit. --- src/scripting/codegeneration/codegen.cpp | 141 ++++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 38 +++++- src/scripting/thingdef.h | 1 + src/scripting/zscript/zcc_compile.cpp | 57 ++++++++- 4 files changed, 232 insertions(+), 5 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 7a7ff7f13..d115cbbd8 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5023,14 +5023,18 @@ ExpEmit FxFlopFunctionCall::Emit(VMFunctionBuilder *build) FxExpression *FxCompoundStatement::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); + Outer = ctx.Block; + ctx.Block = this; for (unsigned i = 0; i < Expressions.Size(); ++i) { if (NULL == (Expressions[i] = Expressions[i]->Resolve(ctx))) { + ctx.Block = Outer; delete this; - return NULL; + return nullptr; } } + ctx.Block = Outer; return this; } @@ -5048,6 +5052,11 @@ ExpEmit FxCompoundStatement::Emit(VMFunctionBuilder *build) // Throw away any result. We don't care about it. v.Free(build); } + // Release all local variables in this block. + for (auto l : LocalVars) + { + l->Release(build); + } return ExpEmit(); } @@ -5066,6 +5075,52 @@ VMFunction *FxCompoundStatement::GetDirectFunction() return NULL; } +//========================================================================== +// +// FxCompoundStatement :: FindLocalVariable +// +// Looks for a variable name in any of the containing compound statements +// +//========================================================================== + +FxLocalVariableDeclaration *FxCompoundStatement::FindLocalVariable(FName name) +{ + auto block = this; + while (block != nullptr) + { + for (auto l : block->LocalVars) + { + if (l->Name == name) + { + return l; + } + } + block = block->Outer; + } + return nullptr; +} + +//========================================================================== +// +// FxCompoundStatement :: CheckLocalVariable +// +// Checks if the current block already contains a local variable +// of the given name. +// +//========================================================================== + +bool FxCompoundStatement::CheckLocalVariable(FName name) +{ + for (auto l : LocalVars) + { + if (l->Name == name) + { + return true; + } + } + return false; +} + //========================================================================== // // FxIfStatement @@ -6142,3 +6197,87 @@ ExpEmit FxDamageValue::Emit(VMFunctionBuilder *build) return ExpEmit(); } + +//========================================================================== +// +// declares a single local variable (no arrays) +// +//========================================================================== + +FxLocalVariableDeclaration::FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, const FScriptPosition &p) + :FxExpression(p) +{ + ValueType = type; + Name = name; + Init = initval == nullptr? nullptr : new FxTypeCast(initval, type, false); +} + +FxExpression *FxLocalVariableDeclaration::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE_OPT(Init, ctx); + if (ctx.Block == nullptr) + { + ScriptPosition.Message(MSG_ERROR, "Variable declaration outside compound statement"); + delete this; + return nullptr; + } + ctx.Block->LocalVars.Push(this); + return this; +} + +ExpEmit FxLocalVariableDeclaration::Emit(VMFunctionBuilder *build) +{ + if (Init == nullptr) + { + RegNum = build->Registers[ValueType->GetRegType()].Get(1); + } + else + { + ExpEmit emitval = Init->Emit(build); + + int regtype = emitval.RegType; + if (regtype < REGT_INT || regtype > REGT_TYPE) + { + ScriptPosition.Message(MSG_ERROR, "Attempted to assign a non-value"); + return ExpEmit(); + } + if (emitval.Konst) + { + auto constval = static_cast(Init); + RegNum = build->Registers[regtype].Get(1); + switch (regtype) + { + default: + case REGT_INT: + build->Emit(OP_LK, build->GetConstantInt(constval->GetValue().GetInt()), RegNum); + break; + + case REGT_FLOAT: + build->Emit(OP_LKF, build->GetConstantFloat(constval->GetValue().GetFloat()), RegNum); + break; + + case REGT_POINTER: + build->Emit(OP_LKP, build->GetConstantAddress(constval->GetValue().GetPointer(), ATAG_GENERIC), RegNum); + break; + + case REGT_STRING: + build->Emit(OP_LKS, build->GetConstantString(constval->GetValue().GetString()), RegNum); + } + emitval.Free(build); + } + else + { + // take over the register that got allocated while emitting the Init expression. + RegNum = emitval.RegNum; + } + } + return ExpEmit(); +} + +void FxLocalVariableDeclaration::Release(VMFunctionBuilder *build) +{ + // Release the register after the containing block gets closed + assert(RegNum != -1); + build->Registers[ValueType->GetRegType()].Return(RegNum, 1); +} diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 57a6d4257..75cdadf8d 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -63,10 +63,12 @@ class FxJumpStatement; //========================================================================== struct FScriptPosition; class FxLoopStatement; +class FxCompoundStatement; struct FCompileContext { - FxLoopStatement *Loop; + FxLoopStatement *Loop = nullptr; + FxCompoundStatement *Block = nullptr; PPrototype *ReturnProto; PFunction *Function; // The function that is currently being compiled (or nullptr for constant evaluation.) PClass *Class; // The type of the owning class. @@ -162,6 +164,12 @@ struct ExpVal return regtype == REGT_INT ? double(Int) : regtype == REGT_FLOAT ? Float : 0; } + void *GetPointer() const + { + int regtype = Type->GetRegType(); + return regtype == REGT_POINTER ? pointer : nullptr; + } + const FString GetString() const { return Type == TypeString ? *(FString *)&pointer : Type == TypeName ? FString(FName(ENamedName(Int)).GetChars()) : ""; @@ -1082,10 +1090,15 @@ public: // FxCompoundStatement // //========================================================================== +class FxLocalVariableDeclaration; class FxCompoundStatement : public FxExpression { + TArray LocalVars; TDeletingArray Expressions; + FxCompoundStatement *Outer = nullptr; + + friend class FxLocalVariableDeclaration; public: FxCompoundStatement(const FScriptPosition &pos) : FxExpression(pos) {} @@ -1093,6 +1106,8 @@ public: ExpEmit Emit(VMFunctionBuilder *build); void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); } VMFunction *GetDirectFunction(); + FxLocalVariableDeclaration *FindLocalVariable(FName name); + bool CheckLocalVariable(FName name); }; //========================================================================== @@ -1341,7 +1356,26 @@ public: } }; -FxExpression *ParseExpression (FScanner &sc, PClassActor *cls, bool mustresolve = false); +//========================================================================== +// +// +// +//========================================================================== +class FxLocalVariableDeclaration : public FxExpression +{ + friend class FxCompoundStatement; + + FName Name; + FxExpression *Init; + int RegNum = -1; + +public: + FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, const FScriptPosition &p); + FxExpression *Resolve(FCompileContext&); + ExpEmit Emit(VMFunctionBuilder *build); + void Release(VMFunctionBuilder *build); + +}; #endif diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 7c2b90e50..bdee476ee 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -144,6 +144,7 @@ inline void ResetBaggage (Baggage *bag, PClassActor *stateclass) AFuncDesc *FindFunction(const char * string); +FxExpression *ParseExpression(FScanner &sc, PClassActor *cls, bool mustresolve = false); void ParseStates(FScanner &sc, PClassActor *actor, AActor *defaults, Baggage &bag); void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArray &out_params, PFunction *afd, FString statestring, FStateDefinitions *statedef); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e86a7c959..e641524af 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2313,8 +2313,27 @@ void ZCCCompiler::CompileStates() FxExpression *ZCCCompiler::ConvertAST(ZCC_TreeNode *ast) { - // FxReturnStatement will have to be done more intelligently, of course. - return new FxReturnStatement(ConvertNode(ast), *ast); + // there are two possibilities here: either a single function call or a compound statement. For a compound statement we also need to check if the last thing added was a return. + if (ast->NodeType == AST_ExprFuncCall) + { + return new FxReturnStatement(ConvertNode(ast), *ast); + } + else + { + // This must be done here so that we can check for a trailing return statement. + auto x = new FxCompoundStatement(*ast); + auto compound = static_cast(ast); + bool isreturn = false; + auto node = compound->Content; + if (node != nullptr) do + { + x->Add(ConvertNode(node)); + isreturn = node->NodeType == AST_ReturnStmt; + node = static_cast(node->SiblingNext); + } while (node != compound->Content); + if (!isreturn) x->Add(new FxReturnStatement(nullptr, *ast)); + return x; + } } FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) @@ -2514,8 +2533,42 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return new FxConditional(condition, left, right); } + + case AST_ExpressionStmt: + return ConvertNode(static_cast(ast)->Expression); + + case AST_ReturnStmt: + { + auto ret = static_cast(ast); + FArgumentList *args = ConvertNodeList(ret->Values); + if (args->Size() == 0) + { + return new FxReturnStatement(nullptr, *ast); + } + else if (args->Size() == 1) + { + return new FxReturnStatement((*args)[0], *ast); + } + else + { + Error(ast, "Return with multiple values not implemented yet."); + return new FxReturnStatement(nullptr, *ast); + } } + case AST_CompoundStmt: + { + auto x = new FxCompoundStatement(*ast); + auto compound = static_cast(ast); + auto node = compound->Content; + if (node != nullptr) do + { + x->Add(ConvertNode(node)); + node = static_cast(node->SiblingNext); + } while (node != compound->Content); + return x; + } + } // only for development. I_Error is more convenient here than a normal error. I_Error("ConvertNode encountered unsupported node of type %d", ast->NodeType); return nullptr; From ffc38d422ea1ee7f8bbebc7238a6672288bc0c47 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 20 Oct 2016 01:09:35 +0200 Subject: [PATCH 076/255] - split up FxCompoundStatement into the old FxSequence and a new subclass. FxSequence is just a sequence of expressions, while FxCompoundStatement is the one that actually implements handling of local variables. The split was done so that ZCCCompiler::ConvertNode can return multiple statements as one object and for that FxCompoundStatement is not suitable. - added conversion of local variable declarations. This is still untested --- src/scripting/codegeneration/codegen.cpp | 89 +++++++++++++++--------- src/scripting/codegeneration/codegen.h | 28 ++++++-- src/scripting/zscript/zcc_compile.cpp | 33 +++++++++ 3 files changed, 112 insertions(+), 38 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d115cbbd8..4554a830b 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5014,6 +5014,58 @@ ExpEmit FxFlopFunctionCall::Emit(VMFunctionBuilder *build) return v; } +//========================================================================== +// +// FxSequence :: Resolve +// +//========================================================================== + +FxExpression *FxSequence::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + for (unsigned i = 0; i < Expressions.Size(); ++i) + { + if (NULL == (Expressions[i] = Expressions[i]->Resolve(ctx))) + { + delete this; + return nullptr; + } + } + return this; +} + +//========================================================================== +// +// FxSequence :: Emit +// +//========================================================================== + +ExpEmit FxSequence::Emit(VMFunctionBuilder *build) +{ + for (unsigned i = 0; i < Expressions.Size(); ++i) + { + ExpEmit v = Expressions[i]->Emit(build); + // Throw away any result. We don't care about it. + v.Free(build); + } + return ExpEmit(); +} + +//========================================================================== +// +// FxSequence :: GetDirectFunction +// +//========================================================================== + +VMFunction *FxSequence::GetDirectFunction() +{ + if (Expressions.Size() == 1) + { + return Expressions[0]->GetDirectFunction(); + } + return NULL; +} + //========================================================================== // // FxCompoundStatement :: Resolve @@ -5023,18 +5075,11 @@ ExpEmit FxFlopFunctionCall::Emit(VMFunctionBuilder *build) FxExpression *FxCompoundStatement::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); + auto outer = ctx.Block; Outer = ctx.Block; ctx.Block = this; - for (unsigned i = 0; i < Expressions.Size(); ++i) - { - if (NULL == (Expressions[i] = Expressions[i]->Resolve(ctx))) - { - ctx.Block = Outer; - delete this; - return nullptr; - } - } - ctx.Block = Outer; + auto x = FxSequence::Resolve(ctx); + ctx.Block = outer; return this; } @@ -5046,33 +5091,13 @@ FxExpression *FxCompoundStatement::Resolve(FCompileContext &ctx) ExpEmit FxCompoundStatement::Emit(VMFunctionBuilder *build) { - for (unsigned i = 0; i < Expressions.Size(); ++i) - { - ExpEmit v = Expressions[i]->Emit(build); - // Throw away any result. We don't care about it. - v.Free(build); - } + auto e = FxSequence::Emit(build); // Release all local variables in this block. for (auto l : LocalVars) { l->Release(build); } - return ExpEmit(); -} - -//========================================================================== -// -// FxCompoundStatement :: GetDirectFunction -// -//========================================================================== - -VMFunction *FxCompoundStatement::GetDirectFunction() -{ - if (Expressions.Size() == 1) - { - return Expressions[0]->GetDirectFunction(); - } - return NULL; + return e; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 75cdadf8d..eeabf891e 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -1087,25 +1087,41 @@ public: //========================================================================== // -// FxCompoundStatement +// FxSequence (a list of statements with no semantics attached - used to return multiple nodes as one) // //========================================================================== class FxLocalVariableDeclaration; -class FxCompoundStatement : public FxExpression +class FxSequence : public FxExpression +{ + TDeletingArray Expressions; + +public: + FxSequence(const FScriptPosition &pos) : FxExpression(pos) {} + FxExpression *Resolve(FCompileContext&); + ExpEmit Emit(VMFunctionBuilder *build); + void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); } + VMFunction *GetDirectFunction(); +}; + +//========================================================================== +// +// FxCompoundStatement (like a list but implements maintenance of local variables) +// +//========================================================================== +class FxLocalVariableDeclaration; + +class FxCompoundStatement : public FxSequence { TArray LocalVars; - TDeletingArray Expressions; FxCompoundStatement *Outer = nullptr; friend class FxLocalVariableDeclaration; public: - FxCompoundStatement(const FScriptPosition &pos) : FxExpression(pos) {} + FxCompoundStatement(const FScriptPosition &pos) : FxSequence(pos) {} FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); - void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); } - VMFunction *GetDirectFunction(); FxLocalVariableDeclaration *FindLocalVariable(FName name); bool CheckLocalVariable(FName name); }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e641524af..33830d135 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2534,6 +2534,39 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return new FxConditional(condition, left, right); } + case AST_LocalVarStmt: + { + auto loc = static_cast(ast); + auto node = loc->Vars; + FxSequence *list = new FxSequence(*ast); + do + { + // Type determination must be done for each field to properly handle array definitions. + PType *type = DetermineType(ConvertClass, node, node->Name, loc->Type, true, false); + if (type->IsKindOf(RUNTIME_CLASS(PArray))) + { + Error(loc, "Local array variables not implemented yet."); + } + else + { + FxExpression *val; + if (node->InitIsArray) + { + Error(node, "Tried to initialize %s with an array", FName(node->Name).GetChars()); + val = nullptr; + } + else + { + val = node->Init ? ConvertNode(node->Init) : nullptr; + } + list->Add(new FxLocalVariableDeclaration(type, node->Name, val, *node)); + } + + node = static_cast(node->SiblingNext); + } while (node != loc->Vars); + return list; + } + case AST_ExpressionStmt: return ConvertNode(static_cast(ast)->Expression); From 24394dfc924b17abc0581e2d6c022be42d1a6c0d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 20 Oct 2016 16:55:12 +0200 Subject: [PATCH 077/255] - tested and fixed FxLocalVariableDeclaration. - create proper variable data from the function prototype instead of assuming that there's just 3 pointers. - added a printable name to VMScriptFunction for error output during gameplay in case something goes wrong. --- src/dobjtype.cpp | 3 ++- src/scripting/codegeneration/codegen.cpp | 13 +++++++-- src/scripting/codegeneration/codegen.h | 9 ++++--- src/scripting/vm/vm.h | 1 + src/scripting/vm/vmbuilder.cpp | 34 ++++++++++++++---------- src/scripting/vm/vmbuilder.h | 2 +- src/scripting/zscript/zcc_compile.cpp | 13 --------- 7 files changed, 40 insertions(+), 35 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 317694e20..f25e592f2 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2545,7 +2545,8 @@ unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArra variant.Flags = flags; variant.Proto = proto; - variant.ArgFlags = argflags; + variant.ArgFlags = std::move(argflags); + variant.ArgNames = std::move(argnames); variant.Implementation = impl; if (impl != nullptr) impl->Proto = proto; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4554a830b..9b6248c88 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5074,7 +5074,6 @@ VMFunction *FxSequence::GetDirectFunction() FxExpression *FxCompoundStatement::Resolve(FCompileContext &ctx) { - CHECKRESOLVED(); auto outer = ctx.Block; Outer = ctx.Block; ctx.Block = this; @@ -5105,10 +5104,12 @@ ExpEmit FxCompoundStatement::Emit(VMFunctionBuilder *build) // FxCompoundStatement :: FindLocalVariable // // Looks for a variable name in any of the containing compound statements +// This does a simple linear search on each block's variables. +// The lists here normally don't get large enough to justify something more complex. // //========================================================================== -FxLocalVariableDeclaration *FxCompoundStatement::FindLocalVariable(FName name) +FxLocalVariableDeclaration *FxCompoundStatement::FindLocalVariable(FName name, FCompileContext &ctx) { auto block = this; while (block != nullptr) @@ -5122,6 +5123,14 @@ FxLocalVariableDeclaration *FxCompoundStatement::FindLocalVariable(FName name) } block = block->Outer; } + // finally check the context for function arguments + for (auto arg : ctx.FunctionArgs) + { + if (arg->Name == name) + { + return arg; + } + } return nullptr; } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index eeabf891e..c16c45f42 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -64,6 +64,7 @@ class FxJumpStatement; struct FScriptPosition; class FxLoopStatement; class FxCompoundStatement; +class FxLocalVariableDeclaration; struct FCompileContext { @@ -73,6 +74,7 @@ struct FCompileContext PFunction *Function; // The function that is currently being compiled (or nullptr for constant evaluation.) PClass *Class; // The type of the owning class. bool FromDecorate; + TDeletingArray FunctionArgs; FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate); FCompileContext(PClass *cls); // only to be used to resolve constants! @@ -191,8 +193,7 @@ struct ExpVal struct ExpEmit { ExpEmit() : RegNum(0), RegType(REGT_NIL), Konst(false), Fixed(false), Final(false) {} - ExpEmit(int reg, int type) : RegNum(reg), RegType(type), Konst(false), Fixed(false), Final(false) {} - ExpEmit(int reg, int type, bool konst) : RegNum(reg), RegType(type), Konst(konst), Fixed(false), Final(false) {} + ExpEmit(int reg, int type, bool konst = false, bool fixed = false) : RegNum(reg), RegType(type), Konst(konst), Fixed(fixed), Final(false) {} ExpEmit(VMFunctionBuilder *build, int type); void Free(VMFunctionBuilder *build); void Reuse(VMFunctionBuilder *build); @@ -1122,7 +1123,7 @@ public: FxCompoundStatement(const FScriptPosition &pos) : FxSequence(pos) {} FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); - FxLocalVariableDeclaration *FindLocalVariable(FName name); + FxLocalVariableDeclaration *FindLocalVariable(FName name, FCompileContext &ctx); bool CheckLocalVariable(FName name); }; @@ -1384,9 +1385,9 @@ class FxLocalVariableDeclaration : public FxExpression FName Name; FxExpression *Init; +public: int RegNum = -1; -public: FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, const FScriptPosition &p); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 425eba531..8cd63f3e5 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -789,6 +789,7 @@ public: VM_UBYTE NumKonstA; VM_UHALF MaxParam; // Maximum number of parameters this function has on the stack at once VM_UBYTE NumArgs; // Number of arguments this function takes + FString PrintableName; // so that the VM can print meaningful info if something in this function goes wrong. }; class VMFrameStack diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 7e946a17c..5e5ce85db 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -663,7 +663,7 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c Item it; it.Func = functype; it.Code = code; - it.DumpName = name; + it.PrintableName = name; it.Function = new VMScriptFunction; it.Proto = nullptr; it.FromDecorate = fromdecorate; @@ -684,39 +684,45 @@ void FFunctionBuildList::Build() { assert(item.Code != NULL); - // This needs to be fixed, so that the compile context receives the entire function symbol, including the containing class, the prototype and argument names, which will be needed to run the code generator - // As a first step this just needs to get working so fetch the class type from the prototype's argument list. // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(item.Func, nullptr, item.FromDecorate); + FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate); + + // Allocate registers for the function's arguments and create local variable nodes before starting to resolve it. + VMFunctionBuilder buildit(true); + for(unsigned i=0;iVariants[0].Proto->ArgumentTypes.Size();i++) + { + auto type = item.Func->Variants[0].Proto->ArgumentTypes[i]; + auto name = item.Func->Variants[0].ArgNames[i]; + // this won't get resolved and won't get emitted. This is only needed so that the code generator can retrieve the necessary info to do its work. + auto local = new FxLocalVariableDeclaration(type, name, nullptr, FScriptPosition()); + local->RegNum = buildit.Registers[type->GetRegType()].Get(1); + ctx.FunctionArgs.Push(local); + } + item.Code = item.Code->Resolve(ctx); item.Proto = ctx.ReturnProto; // Make sure resolving it didn't obliterate it. if (item.Code != nullptr) { - VMFunctionBuilder buildit(true); - assert(item.Proto != nullptr); - auto numargs = item.Func->Variants[0].Proto->ArgumentTypes.Size(); // Generate prototype for this anonymous function - // Fixme: This later needs to do proper allocation for the function's entire argument list, once non-anonymous functions can be done. - buildit.Registers[REGT_POINTER].Get(numargs); - VMScriptFunction *sfunc = item.Function; // create a new prototype from the now known return type and the argument list of the function's template prototype. - item.Function->Proto = NewPrototype(item.Proto->ReturnTypes, item.Func->Variants[0].Proto->ArgumentTypes); + sfunc->Proto = NewPrototype(item.Proto->ReturnTypes, item.Func->Variants[0].Proto->ArgumentTypes); // Emit code item.Code->Emit(&buildit); - buildit.MakeFunction(item.Function); - item.Function->NumArgs = numargs; + buildit.MakeFunction(sfunc); + sfunc->NumArgs = item.Func->Variants[0].Proto->ArgumentTypes.Size(); if (dump != nullptr) { - DumpFunction(dump, sfunc, item.DumpName.GetChars(), (int)item.DumpName.Len()); + DumpFunction(dump, sfunc, item.PrintableName.GetChars(), (int)item.PrintableName.Len()); codesize += sfunc->CodeSize; } + sfunc->PrintableName = item.PrintableName; } delete item.Code; } diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index c5ca868e0..dcaae7251 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -105,7 +105,7 @@ class FFunctionBuildList FxExpression *Code = nullptr; PPrototype *Proto = nullptr; VMScriptFunction *Function = nullptr; - FString DumpName; + FString PrintableName; bool FromDecorate; }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 33830d135..88486d9c3 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2078,19 +2078,6 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a } ConvertClass = cls; return ConvertAST(af); - - //Error(af, "Complex action functions not supported yet."); - //return nullptr; - - /* - bool hasfinalret; - tcall->Code = ParseActions(sc, state, statestring, bag, hasfinalret); - if (!hasfinalret && tcall->Code != nullptr) - { - static_cast(tcall->Code)->Add(new FxReturnStatement(nullptr, sc)); - } - */ - } //========================================================================== From 9f99ca478890b1b50698233a84888b8dcdb5de27 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 01:12:54 +0200 Subject: [PATCH 078/255] - process most of the remaining statement types. - extend assignment operations to handle local variables (untested.) - make the implicit function arguments read only. --- src/dobjtype.cpp | 56 ++++++++++ src/dobjtype.h | 9 +- src/scripting/codegeneration/codegen.cpp | 135 +++++++++++++++++++---- src/scripting/codegeneration/codegen.h | 25 ++++- src/scripting/thingdef.cpp | 6 +- src/scripting/vm/vmbuilder.cpp | 5 +- src/scripting/vm/vmexec.h | 20 ++-- src/scripting/zscript/zcc_compile.cpp | 63 ++++++++++- 8 files changed, 277 insertions(+), 42 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index f25e592f2..ded832f2d 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -500,6 +500,18 @@ int PType::GetLoadOp() const return OP_NOP; } +//========================================================================== +// +// PType :: GetMoveOp +// +//========================================================================== + +int PType::GetMoveOp() const +{ + assert(0 && "Cannot move this type"); + return OP_NOP; +} + //========================================================================== // // PType :: GetRegType @@ -974,6 +986,17 @@ int PInt::GetLoadOp() const } } +//========================================================================== +// +// PInt :: GetLoadOp +// +//========================================================================== + +int PInt::GetMoveOp() const +{ + return OP_MOVE; +} + //========================================================================== // // PInt :: GetRegType @@ -1271,6 +1294,17 @@ int PFloat::GetLoadOp() const return OP_NOP; } +//========================================================================== +// +// PFloat :: GetMoveOp +// +//========================================================================== + +int PFloat::GetMoveOp() const +{ + return OP_MOVEF; +} + //========================================================================== // // PFloat :: GetRegType @@ -1540,6 +1574,17 @@ int PStatePointer::GetLoadOp() const return OP_LP; } +//========================================================================== +// +// PStatePointer :: GetMoveOp +// +//========================================================================== + +int PStatePointer::GetMoveOp() const +{ + return OP_MOVEA; +} + //========================================================================== // // PStatePointer :: GetRegType @@ -1627,6 +1672,17 @@ int PPointer::GetLoadOp() const return PointedType->IsKindOf(RUNTIME_CLASS(PClass)) ? OP_LO : OP_LP; } +//========================================================================== +// +// PPointer :: GetMoveOp +// +//========================================================================== + +int PPointer::GetMoveOp() const +{ + return OP_MOVEA; +} + //========================================================================== // // PPointer :: GetRegType diff --git a/src/dobjtype.h b/src/dobjtype.h index fd6e078ea..4a15078fd 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -28,7 +28,7 @@ enum VARF_Final = (1<<9), // Function may not be overridden in subclasses VARF_In = (1<<10), VARF_Out = (1<<11), - VARF_Implicit = (1<<12), // implicitly created parameters (i.e. do not compare when checking function signatures) + VARF_Implicit = (1<<12), // implicitly created parameters (i.e. do not compare types when checking function signatures) VARF_Static = (1<<13), // static class data (by necessity read only.) }; @@ -272,6 +272,9 @@ public: // Gets the opcode to load from memory to a register virtual int GetLoadOp() const; + // Gets the opcode to move from register to another register + virtual int GetMoveOp() const; + // Gets the register type for this type virtual int GetRegType() const; @@ -409,6 +412,7 @@ public: virtual double GetValueFloat(void *addr) const; virtual int GetStoreOp() const; virtual int GetLoadOp() const; + virtual int GetMoveOp() const; virtual int GetRegType() const; bool Unsigned; @@ -438,6 +442,7 @@ public: virtual double GetValueFloat(void *addr) const; virtual int GetStoreOp() const; virtual int GetLoadOp() const; + virtual int GetMoveOp() const; virtual int GetRegType() const; protected: PFloat(); @@ -516,6 +521,7 @@ public: virtual int GetStoreOp() const; virtual int GetLoadOp() const; + virtual int GetMoveOp() const; virtual int GetRegType() const; }; @@ -530,6 +536,7 @@ public: virtual int GetStoreOp() const; virtual int GetLoadOp() const; + virtual int GetMoveOp() const; virtual int GetRegType() const; virtual bool IsMatch(intptr_t id1, intptr_t id2) const; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9b6248c88..d3e7ef029 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -160,6 +160,18 @@ void FCompileContext::CheckReturn(PPrototype *proto, FScriptPosition &pos) } } +FxLocalVariableDeclaration *FCompileContext::FindLocalVariable(FName name) +{ + if (Block == nullptr) + { + return nullptr; + } + else + { + return Block->FindLocalVariable(name, *this); + } +} + //========================================================================== // // ExpEmit @@ -1611,9 +1623,13 @@ ExpEmit FxPreIncrDecr::Emit(VMFunctionBuilder *build) int zero = build->GetConstantInt(0); int regtype = ValueType->GetRegType(); ExpEmit pointer = Base->Emit(build); + ExpEmit value = pointer; - ExpEmit value(build, regtype); - build->Emit(ValueType->GetLoadOp(), value.RegNum, pointer.RegNum, zero); + if (!pointer.Target) + { + value = ExpEmit(build, regtype); + build->Emit(ValueType->GetLoadOp(), value.RegNum, pointer.RegNum, zero); + } if (regtype == REGT_INT) { @@ -1624,7 +1640,10 @@ ExpEmit FxPreIncrDecr::Emit(VMFunctionBuilder *build) build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, value.RegNum, value.RegNum, build->GetConstantFloat(1.)); } - build->Emit(ValueType->GetStoreOp(), pointer.RegNum, value.RegNum, zero); + if (!pointer.Target) + { + build->Emit(ValueType->GetStoreOp(), pointer.RegNum, value.RegNum, zero); + } if (AddressRequested) { @@ -1690,9 +1709,13 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) int zero = build->GetConstantInt(0); int regtype = ValueType->GetRegType(); ExpEmit pointer = Base->Emit(build); + ExpEmit out = pointer; - ExpEmit out(build, regtype); - build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, zero); + if (!pointer.Target) + { + out = ExpEmit(build, regtype); + build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, zero); + } ExpEmit assign(build, regtype); if (regtype == REGT_INT) @@ -1704,7 +1727,10 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, assign.RegNum, out.RegNum, build->GetConstantFloat(1.)); } - build->Emit(ValueType->GetStoreOp(), pointer.RegNum, assign.RegNum, zero); + if (!pointer.Target) + { + build->Emit(ValueType->GetStoreOp(), pointer.RegNum, assign.RegNum, zero); + } pointer.Free(build); assign.Free(build); @@ -1781,6 +1807,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) ExpEmit FxAssign::Emit(VMFunctionBuilder *build) { + static const BYTE loadops[] = { OP_NOP, OP_LK, OP_LKF, OP_LKS, OP_LKP }; assert(ValueType == Base->ValueType && IsNumeric()); assert(ValueType->GetRegType() == Right->ValueType->GetRegType()); @@ -1788,16 +1815,31 @@ ExpEmit FxAssign::Emit(VMFunctionBuilder *build) Address = pointer; ExpEmit result = Right->Emit(build); - - if (result.Konst) - { - ExpEmit temp(build, result.RegType); - build->Emit(result.RegType == REGT_FLOAT ? OP_LKF : OP_LK, temp.RegNum, result.RegNum); - result.Free(build); - result = temp; - } + assert(result.RegType <= REGT_TYPE); - build->Emit(ValueType->GetStoreOp(), pointer.RegNum, result.RegNum, build->GetConstantInt(0)); + if (pointer.Target) + { + if (result.Konst) + { + build->Emit(loadops[result.RegType], pointer.RegNum, result.RegNum); + } + else + { + build->Emit(Right->ValueType->GetMoveOp(), pointer.RegNum, result.RegNum); + } + } + else + { + if (result.Konst) + { + ExpEmit temp(build, result.RegType); + build->Emit(loadops[result.RegType], temp.RegNum, result.RegNum); + result.Free(build); + result = temp; + } + + build->Emit(ValueType->GetStoreOp(), pointer.RegNum, result.RegNum, build->GetConstantInt(0)); + } if (AddressRequested) { @@ -1837,9 +1879,16 @@ ExpEmit FxAssignSelf::Emit(VMFunctionBuilder *build) { assert(ValueType = Assignment->ValueType); ExpEmit pointer = Assignment->Address; // FxAssign should have already emitted it - ExpEmit out(build, ValueType->GetRegType()); - build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, build->GetConstantInt(0)); - return out; + if (!pointer.Target) + { + ExpEmit out(build, ValueType->GetRegType()); + build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, build->GetConstantInt(0)); + return out; + } + else + { + return pointer; + } } //========================================================================== @@ -3858,8 +3907,15 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) CHECKRESOLVED(); + // Local variables have highest priority. + FxLocalVariableDeclaration *local = ctx.FindLocalVariable(Identifier); + if (local != nullptr) + { + auto x = new FxLocalVariable(local, ScriptPosition); + delete this; + return x->Resolve(ctx); + } // Ugh, the horror. Constants need to be taken from the owning class, but members from the self class to catch invalid accesses here... - // see if the current class (if valid) defines something with this name. PSymbolTable *symtbl; if ((sym = ctx.FindInClass(Identifier, symtbl)) != nullptr) @@ -3959,6 +4015,40 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } +//========================================================================== +// +// +// +//========================================================================== + +FxLocalVariable::FxLocalVariable(FxLocalVariableDeclaration *var, const FScriptPosition &sc) + : FxExpression(sc) +{ + Variable = var; + AddressRequested = false; +} + +FxExpression *FxLocalVariable::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + return this; +} + +bool FxLocalVariable::RequestAddress(bool *writable) +{ + AddressRequested = true; + if (writable != nullptr) *writable = !(Variable->VarFlags & VARF_ReadOnly); + return true; +} + +ExpEmit FxLocalVariable::Emit(VMFunctionBuilder *build) +{ + ExpEmit ret(Variable->RegNum, Variable->ValueType->GetRegType(), false, true); + if (AddressRequested) ret.Target = true; + return ret; +} + + //========================================================================== // // @@ -3998,9 +4088,7 @@ FxExpression *FxSelf::Resolve(FCompileContext& ctx) ExpEmit FxSelf::Emit(VMFunctionBuilder *build) { // self is always the first pointer passed to the function - ExpEmit me(0, REGT_POINTER); - me.Fixed = true; - return me; + return ExpEmit(0, REGT_POINTER, false, true); } @@ -6238,10 +6326,11 @@ ExpEmit FxDamageValue::Emit(VMFunctionBuilder *build) // //========================================================================== -FxLocalVariableDeclaration::FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, const FScriptPosition &p) +FxLocalVariableDeclaration::FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, int varflags, const FScriptPosition &p) :FxExpression(p) { ValueType = type; + VarFlags = varflags; Name = name; Init = initval == nullptr? nullptr : new FxTypeCast(initval, type, false); } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index c16c45f42..7a69f3989 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -85,6 +85,7 @@ struct FCompileContext void HandleJumps(int token, FxExpression *handler); void CheckReturn(PPrototype *proto, FScriptPosition &pos); + FxLocalVariableDeclaration *FindLocalVariable(FName name); }; //========================================================================== @@ -198,7 +199,7 @@ struct ExpEmit void Free(VMFunctionBuilder *build); void Reuse(VMFunctionBuilder *build); - BYTE RegNum, RegType, Konst:1, Fixed:1, Final:1; + BYTE RegNum, RegType, Konst:1, Fixed:1, Final:1, Target:1; }; //========================================================================== @@ -964,6 +965,24 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxLocalVariable +// +//========================================================================== + +class FxLocalVariable : public FxExpression +{ +public: + FxLocalVariableDeclaration *Variable; + bool AddressRequested; + + FxLocalVariable(FxLocalVariableDeclaration*, const FScriptPosition&); + FxExpression *Resolve(FCompileContext&); + bool RequestAddress(bool *writable); + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxSelf @@ -1382,13 +1401,15 @@ public: class FxLocalVariableDeclaration : public FxExpression { friend class FxCompoundStatement; + friend class FxLocalVariable; FName Name; FxExpression *Init; + int VarFlags; public: int RegNum = -1; - FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, const FScriptPosition &p); + FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, int varflags, const FScriptPosition &p); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); void Release(VMFunctionBuilder *build); diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index fc281e8e8..7fcb0ce39 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -90,7 +90,7 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArrayPush(NewPointer(cls)); - if (argflags != nullptr) argflags->Push(VARF_Implicit); + if (argflags != nullptr) argflags->Push(VARF_Implicit | VARF_ReadOnly); if (argnames != nullptr) argnames->Push(NAME_self); } if (funcflags & VARF_Action) @@ -111,8 +111,8 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArrayPush(VARF_Implicit); - argflags->Push(VARF_Implicit); + argflags->Push(VARF_Implicit | VARF_ReadOnly); + argflags->Push(VARF_Implicit | VARF_ReadOnly); } if (argnames != nullptr) { diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 5e5ce85db..0ba697495 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -693,8 +693,9 @@ void FFunctionBuildList::Build() { auto type = item.Func->Variants[0].Proto->ArgumentTypes[i]; auto name = item.Func->Variants[0].ArgNames[i]; - // this won't get resolved and won't get emitted. This is only needed so that the code generator can retrieve the necessary info to do its work. - auto local = new FxLocalVariableDeclaration(type, name, nullptr, FScriptPosition()); + auto flags = item.Func->Variants[0].ArgFlags[i]; + // this won't get resolved and won't get emitted. It is only needed so that the code generator can retrieve the necessary info about this argument to do its work. + auto local = new FxLocalVariableDeclaration(type, name, nullptr, flags, FScriptPosition()); local->RegNum = buildit.Registers[type->GetRegType()].Get(1); ctx.FunctionArgs.Push(local); } diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 9dbea7c51..db4afa05a 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -194,7 +194,7 @@ begin: ASSERTF(a+2); ASSERTA(B); ASSERTKD(C); GETADDR(PB,KC,X_READ_NIL); { - float *v = (float *)ptr; + auto v = (double *)ptr; reg.f[a] = v[0]; reg.f[a+1] = v[1]; reg.f[a+2] = v[2]; @@ -204,7 +204,7 @@ begin: ASSERTF(a+2); ASSERTA(B); ASSERTD(C); GETADDR(PB,RC,X_READ_NIL); { - float *v = (float *)ptr; + auto v = (double *)ptr; reg.f[a] = v[0]; reg.f[a+1] = v[1]; reg.f[a+2] = v[2]; @@ -290,20 +290,20 @@ begin: ASSERTA(a); ASSERTF(B+2); ASSERTKD(C); GETADDR(PA,KC,X_WRITE_NIL); { - float *v = (float *)ptr; - v[0] = (float)reg.f[B]; - v[1] = (float)reg.f[B+1]; - v[2] = (float)reg.f[B+2]; + auto v = (double *)ptr; + v[0] = reg.f[B]; + v[1] = reg.f[B+1]; + v[2] = reg.f[B+2]; } NEXTOP; OP(SV_R): ASSERTA(a); ASSERTF(B+2); ASSERTD(C); GETADDR(PA,RC,X_WRITE_NIL); { - float *v = (float *)ptr; - v[0] = (float)reg.f[B]; - v[1] = (float)reg.f[B+1]; - v[2] = (float)reg.f[B+2]; + auto v = (double *)ptr; + v[0] = reg.f[B]; + v[1] = reg.f[B+1]; + v[2] = reg.f[B+2]; } NEXTOP; OP(SBIT): diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 88486d9c3..d5b3a2705 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -42,6 +42,7 @@ #include "cmdlib.h" #include "m_alloc.h" #include "zcc_parser.h" +#include "zcc-parse.h" #include "zcc_compile.h" #include "v_text.h" #include "p_lnspec.h" @@ -2344,11 +2345,42 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // The function name is a simple identifier. return new FxFunctionCall(static_cast(fcall->Function)->Identifier, NAME_None, ConvertNodeList(fcall->Parameters), *ast); + // not yet done + case AST_ExprTypeRef: + case AST_SwitchStmt: + case AST_CaseStmt: case AST_ExprMemberAccess: // calling a class member through its pointer // todo. break; + case AST_AssignStmt: + { + auto assign = static_cast(ast); + switch (assign->AssignOp) + { + case ZCC_EQ: + // this ignores multi-assign statements (these should probably be disabled in the grammar.) + return new FxAssign(ConvertNode(assign->Dests), ConvertNode(assign->Sources)); + + case ZCC_MULEQ: + case ZCC_DIVEQ: + case ZCC_MODEQ: + case ZCC_ADDEQ: + case ZCC_SUBEQ: + case ZCC_LSHEQ: + case ZCC_RSHEQ: + case ZCC_ANDEQ: + case ZCC_OREQ: + case ZCC_XOREQ: + //break; + default: + Error(ast, "Invalid assign statement"); + + } + break; + } + case AST_ExprBinary: // Array syntax for randoms. They are internally stored as ExprBinary with both an identifier on the left and right side. if (fcall->Function->Operation == PEX_ArrayAccess) @@ -2546,7 +2578,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { val = node->Init ? ConvertNode(node->Init) : nullptr; } - list->Add(new FxLocalVariableDeclaration(type, node->Name, val, *node)); + list->Add(new FxLocalVariableDeclaration(type, node->Name, val, 0, *node)); // todo: Handle flags in the grammar. } node = static_cast(node->SiblingNext); @@ -2576,6 +2608,35 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } } + case AST_BreakStmt: + case AST_ContinueStmt: + return new FxJumpStatement(ast->NodeType == AST_BreakStmt ? TK_Break : TK_Continue, *ast); + + case AST_IfStmt: + { + auto iff = static_cast(ast); + return new FxIfStatement(ConvertNode(iff->Condition), ConvertNode(iff->TruePath), ConvertNode(iff->FalsePath), *ast); + } + + case AST_IterationStmt: + { + auto iter = static_cast(ast); + if (iter->CheckAt == ZCC_IterationStmt::End) + { + assert(iter->LoopBumper == nullptr); + return new FxDoWhileLoop(ConvertNode(iter->LoopCondition), ConvertNode(iter->LoopStatement), *ast); + } + else if (iter->LoopBumper != nullptr) + { + return new FxForLoop(nullptr, ConvertNode(iter->LoopCondition), ConvertNode(iter->LoopBumper), ConvertNode(iter->LoopStatement), *ast); + } + else + { + return new FxWhileLoop(ConvertNode(iter->LoopCondition), ConvertNode(iter->LoopStatement), *ast); + } + } + + case AST_CompoundStmt: { auto x = new FxCompoundStatement(*ast); From 1450c3dffb1e432cf4baccbe9218c310c9ba0bc9 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 10:09:01 +0200 Subject: [PATCH 079/255] - tested and fixed the regular assignment statement for both local and member variables. The generated object code can definitely use an optimization pass but that's something left for later when more things are working. Right now it creates one opcode more than necessary for all member accesses (instead of using the offset in the store command it calculates an actual address of the variable in another address register) and can create one too many for non-constant expressions being assigned to local variables (a move between two registers because the emitted expression on the right hand side does not know that it can emit to the actual variable's register.) --- src/scripting/codegeneration/codegen.cpp | 13 +++--- src/scripting/codegeneration/codegen.h | 4 +- src/scripting/vm/vmbuilder.cpp | 4 ++ src/scripting/zscript/zcc_compile.cpp | 54 ++++++++++++------------ 4 files changed, 40 insertions(+), 35 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d3e7ef029..1b169411f 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -179,7 +179,7 @@ FxLocalVariableDeclaration *FCompileContext::FindLocalVariable(FName name) //========================================================================== ExpEmit::ExpEmit(VMFunctionBuilder *build, int type) -: RegNum(build->Registers[type].Get(1)), RegType(type), Konst(false), Fixed(false), Final(false) +: RegNum(build->Registers[type].Get(1)), RegType(type), Konst(false), Fixed(false), Final(false), Target(false) { } @@ -1807,16 +1807,16 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) ExpEmit FxAssign::Emit(VMFunctionBuilder *build) { - static const BYTE loadops[] = { OP_NOP, OP_LK, OP_LKF, OP_LKS, OP_LKP }; + static const BYTE loadops[] = { OP_LK, OP_LKF, OP_LKS, OP_LKP }; assert(ValueType == Base->ValueType && IsNumeric()); assert(ValueType->GetRegType() == Right->ValueType->GetRegType()); - ExpEmit pointer = Base->Emit(build); - Address = pointer; - ExpEmit result = Right->Emit(build); assert(result.RegType <= REGT_TYPE); + ExpEmit pointer = Base->Emit(build); + Address = pointer; + if (pointer.Target) { if (result.Konst) @@ -4025,6 +4025,7 @@ FxLocalVariable::FxLocalVariable(FxLocalVariableDeclaration *var, const FScriptP : FxExpression(sc) { Variable = var; + ValueType = var->ValueType; AddressRequested = false; } @@ -5167,7 +5168,7 @@ FxExpression *FxCompoundStatement::Resolve(FCompileContext &ctx) ctx.Block = this; auto x = FxSequence::Resolve(ctx); ctx.Block = outer; - return this; + return x; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 7a69f3989..525325276 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -193,8 +193,8 @@ struct ExpVal struct ExpEmit { - ExpEmit() : RegNum(0), RegType(REGT_NIL), Konst(false), Fixed(false), Final(false) {} - ExpEmit(int reg, int type, bool konst = false, bool fixed = false) : RegNum(reg), RegType(type), Konst(konst), Fixed(fixed), Final(false) {} + ExpEmit() : RegNum(0), RegType(REGT_NIL), Konst(false), Fixed(false), Final(false), Target(false) {} + ExpEmit(int reg, int type, bool konst = false, bool fixed = false) : RegNum(reg), RegType(type), Konst(konst), Fixed(fixed), Final(false), Target(false) {} ExpEmit(VMFunctionBuilder *build, int type); void Free(VMFunctionBuilder *build); void Reuse(VMFunctionBuilder *build); diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 0ba697495..a5f15b262 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -682,6 +682,10 @@ void FFunctionBuildList::Build() for (auto &item : mItems) { + if (item.PrintableName.CompareNoCase("Middle.StateFunction.3") == 0) + { + int a = 0; + } assert(item.Code != NULL); // We don't know the return type in advance for anonymous functions. diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index d5b3a2705..eb039f996 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2354,33 +2354,6 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // todo. break; - case AST_AssignStmt: - { - auto assign = static_cast(ast); - switch (assign->AssignOp) - { - case ZCC_EQ: - // this ignores multi-assign statements (these should probably be disabled in the grammar.) - return new FxAssign(ConvertNode(assign->Dests), ConvertNode(assign->Sources)); - - case ZCC_MULEQ: - case ZCC_DIVEQ: - case ZCC_MODEQ: - case ZCC_ADDEQ: - case ZCC_SUBEQ: - case ZCC_LSHEQ: - case ZCC_RSHEQ: - case ZCC_ANDEQ: - case ZCC_OREQ: - case ZCC_XOREQ: - //break; - default: - Error(ast, "Invalid assign statement"); - - } - break; - } - case AST_ExprBinary: // Array syntax for randoms. They are internally stored as ExprBinary with both an identifier on the left and right side. if (fcall->Function->Operation == PEX_ArrayAccess) @@ -2400,6 +2373,33 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) break; } + case AST_AssignStmt: + { + auto assign = static_cast(ast); + switch (assign->AssignOp) + { + case ZCC_EQ: + // this ignores multi-assign statements (these should probably be disabled in the grammar.) + return new FxAssign(ConvertNode(assign->Dests), ConvertNode(assign->Sources)); + + case ZCC_MULEQ: + case ZCC_DIVEQ: + case ZCC_MODEQ: + case ZCC_ADDEQ: + case ZCC_SUBEQ: + case ZCC_LSHEQ: + case ZCC_RSHEQ: + case ZCC_ANDEQ: + case ZCC_OREQ: + case ZCC_XOREQ: + //break; + default: + Error(ast, "Invalid assign statement"); + + } + break; + } + case AST_FuncParm: { auto fparm = static_cast(ast); From 3e995d7aac7620848e7058e3a03748e145162cce Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 12:22:42 +0200 Subject: [PATCH 080/255] - changed assignment operators to be expressions, like they are in C and DECORATE. This also means that for now Lua-style multi-assignments are disabled, those should be easy to enable by making some changes to the assignment_statement grammar so that it doesn't recognize single assignments, but for now this is low priority because it adds a significant amount of complexity to do this right with functions that have multiple return values. --- src/scripting/zscript/ast.cpp | 15 ----- src/scripting/zscript/zcc-parse.lemon | 87 +++++++++++++++++++++------ src/scripting/zscript/zcc_compile.cpp | 46 ++++++-------- src/scripting/zscript/zcc_exprlist.h | 13 ++++ src/scripting/zscript/zcc_parser.cpp | 1 + 5 files changed, 102 insertions(+), 60 deletions(-) diff --git a/src/scripting/zscript/ast.cpp b/src/scripting/zscript/ast.cpp index 2f15c019e..e23fc5a87 100644 --- a/src/scripting/zscript/ast.cpp +++ b/src/scripting/zscript/ast.cpp @@ -747,21 +747,6 @@ static void PrintAssignStmt(FLispString &out, ZCC_TreeNode *node) { ZCC_AssignStmt *snode = (ZCC_AssignStmt *)node; out.Open("assign-stmt"); - switch (snode->AssignOp) - { - case ZCC_EQ: out.AddChar('='); break; - case ZCC_MULEQ: out.Add("*=", 2); break; - case ZCC_DIVEQ: out.Add("/=", 2); break; - case ZCC_MODEQ: out.Add("%=", 2); break; - case ZCC_ADDEQ: out.Add("+=", 2); break; - case ZCC_SUBEQ: out.Add("-=", 2); break; - case ZCC_LSHEQ: out.Add("<<=", 2); break; - case ZCC_RSHEQ: out.Add(">>=", 2); break; - case ZCC_ANDEQ: out.Add("&=", 2); break; - case ZCC_OREQ: out.Add("|=", 2); break; - case ZCC_XOREQ: out.Add("^=", 2); break; - default: BadAssignOp(out, snode->AssignOp); break; - } PrintNodes(out, snode->Dests); PrintNodes(out, snode->Sources); out.Close(); diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 0c493d54a..42c3014c1 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -104,7 +104,7 @@ static void SetNodeLine(ZCC_TreeNode *name, int line) %parse_accept { DPrintf(DMSG_SPAMMY, "Input accepted\n"); } %parse_failure { /**failed = true;*/ } -%nonassoc EQ MULEQ DIVEQ MODEQ ADDEQ SUBEQ LSHEQ RSHEQ ANDEQ OREQ XOREQ. +%right EQ MULEQ DIVEQ MODEQ ADDEQ SUBEQ LSHEQ RSHEQ ANDEQ OREQ XOREQ URSHEQ. %right QUESTION COLON. %left OROR. %left ANDAND. @@ -1247,6 +1247,67 @@ expr(X) ::= expr(A) OROR expr(B). /* a || b */ BINARY_EXPR(A,B,PEX_BoolOr); X = expr2; } +expr(X) ::= expr(A) EQ expr(B). /* a = b */ +{ + BINARY_EXPR(A,B,PEX_Assign); + X = expr2; +} +expr(X) ::= expr(A) ADDEQ expr(B). /* a += b */ +{ + BINARY_EXPR(A,B,PEX_AddAssign); + X = expr2; +} +expr(X) ::= expr(A) SUBEQ expr(B). /* a -= b */ +{ + BINARY_EXPR(A,B,PEX_SubAssign); + X = expr2; +} +expr(X) ::= expr(A) MULEQ expr(B). /* a *= b */ +{ + BINARY_EXPR(A,B,PEX_MulAssign); + X = expr2; +} +expr(X) ::= expr(A) DIVEQ expr(B). /* a /= b */ +{ + BINARY_EXPR(A,B,PEX_DivAssign); + X = expr2; +} +expr(X) ::= expr(A) MODEQ expr(B). /* a %= b */ +{ + BINARY_EXPR(A,B,PEX_ModAssign); + X = expr2; +} +expr(X) ::= expr(A) LSHEQ expr(B). /* a <<= b */ +{ + BINARY_EXPR(A,B,PEX_LshAssign); + X = expr2; +} +expr(X) ::= expr(A) RSHEQ expr(B). /* a >>= b */ +{ + BINARY_EXPR(A,B,PEX_RshAssign); + X = expr2; +} +expr(X) ::= expr(A) URSHEQ expr(B). /* a >>>= b */ +{ + BINARY_EXPR(A,B,PEX_URshAssign); + X = expr2; +} +expr(X) ::= expr(A) ANDEQ expr(B). /* a &= b */ +{ + BINARY_EXPR(A,B,PEX_AndAssign); + X = expr2; +} +expr(X) ::= expr(A) OREQ expr(B). /* a |= b */ +{ + BINARY_EXPR(A,B,PEX_OrAssign); + X = expr2; +} +expr(X) ::= expr(A) XOREQ expr(B). /* a ^= b */ +{ + BINARY_EXPR(A,B,PEX_XorAssign); + X = expr2; +} + expr(X) ::= expr(A) SCOPE expr(B). { @@ -1402,7 +1463,7 @@ statement(X) ::= expression_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ statement(X) ::= selection_statement(X). statement(X) ::= iteration_statement(X). statement(X) ::= jump_statement(X). -statement(X) ::= assign_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } +//statement(X) ::= assign_statement(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } statement(X) ::= local_var(A) SEMICOLON. { X = A; /*X-overwrites-A*/ } statement(X) ::= error SEMICOLON. { X = NULL; } @@ -1553,7 +1614,6 @@ for_init(X) ::= for_bump(A). { X = A /*X-overwrites-A*/; } %type for_bump{ZCC_Statement *} for_bump(X) ::= . { X = NULL; } for_bump(X) ::= expression_statement(A). { X = A; /*X-overwrites-A*/ } -for_bump(X) ::= assign_statement(A). { X = A; /*X-overwrites-A*/ } /*----- If Statements -----*/ @@ -1614,28 +1674,19 @@ labeled_statement(X) ::= DEFAULT(T) COLON. /*----- Assignment Statements -----*/ +/* This is no longer being used, in favor of handling assignments as expressions, just like C and C++ do. + Keep this here in case some other parts require assignment syntax or Lua-style multi-assignments become a thing. %type assign_statement{ZCC_AssignStmt *} -assign_statement(X) ::= expr_list(A) assign_op(OP) expr_list(B). [EQ] +assign_statement(X) ::= expr_list(A) EQ expr_list(B). [EQ] { - NEW_AST_NODE(AssignStmt,stmt,OP); - stmt->AssignOp = OP.Int; + NEW_AST_NODE(AssignStmt,stmt,A); + stmt->AssignOp = ZCC_EQ; stmt->Dests = A; stmt->Sources = B; X = stmt; } - -assign_op(X) ::= EQ(T). { X.Int = ZCC_EQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= MULEQ(T). { X.Int = ZCC_MULEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= DIVEQ(T). { X.Int = ZCC_DIVEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= MODEQ(T). { X.Int = ZCC_MODEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= ADDEQ(T). { X.Int = ZCC_ADDEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= SUBEQ(T). { X.Int = ZCC_SUBEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= LSHEQ(T). { X.Int = ZCC_LSHEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= RSHEQ(T). { X.Int = ZCC_RSHEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= ANDEQ(T). { X.Int = ZCC_ANDEQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= OREQ(T). { X.Int = ZCC_OREQ; X.SourceLoc = T.SourceLoc; } -assign_op(X) ::= XOREQ(T). { X.Int = ZCC_XOREQ; X.SourceLoc = T.SourceLoc; } +*/ /*----- Local Variable Definition "Statements" -----*/ diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index eb039f996..b2c58c124 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2373,33 +2373,6 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) break; } - case AST_AssignStmt: - { - auto assign = static_cast(ast); - switch (assign->AssignOp) - { - case ZCC_EQ: - // this ignores multi-assign statements (these should probably be disabled in the grammar.) - return new FxAssign(ConvertNode(assign->Dests), ConvertNode(assign->Sources)); - - case ZCC_MULEQ: - case ZCC_DIVEQ: - case ZCC_MODEQ: - case ZCC_ADDEQ: - case ZCC_SUBEQ: - case ZCC_LSHEQ: - case ZCC_RSHEQ: - case ZCC_ANDEQ: - case ZCC_OREQ: - case ZCC_XOREQ: - //break; - default: - Error(ast, "Invalid assign statement"); - - } - break; - } - case AST_FuncParm: { auto fparm = static_cast(ast); @@ -2526,6 +2499,23 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_NEQ: return new FxCompareEq(op == PEX_NEQ ? TK_Neq : TK_Eq, left, right); + case PEX_Assign: + return new FxAssign(left, right); +/* + case ZCC_MULEQ: + case ZCC_DIVEQ: + case ZCC_MODEQ: + case ZCC_ADDEQ: + case ZCC_SUBEQ: + case ZCC_LSHEQ: + case ZCC_RSHEQ: + case ZCC_ANDEQ: + case ZCC_OREQ: + case ZCC_XOREQ: + //break; + default: + Error(ast, "Invalid assign statement"); +*/ // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_LTGTEQ: @@ -2537,6 +2527,8 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // vector operations will be done later. case PEX_CrossProduct: case PEX_DotProduct: + + default: I_Error("Binary operator %d not implemented yet", op); } diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index eeabb10e5..5c9936988 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -53,6 +53,19 @@ xx(BitXor, ) xx(BoolAnd, ) xx(BoolOr, ) +xx(Assign, ) +xx(AddAssign, ) +xx(SubAssign, ) +xx(MulAssign, ) +xx(DivAssign, ) +xx(ModAssign, ) +xx(LshAssign, ) +xx(RshAssign, ) +xx(URshAssign, ) +xx(AndAssign, ) +xx(OrAssign, ) +xx(XorAssign, ) + xx(Scope, ) xx(Trinary, ) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 48fd28f45..222e8e6c5 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -73,6 +73,7 @@ static void InitTokenMap() TOKENDEF (TK_SubEq, ZCC_SUBEQ); TOKENDEF (TK_LShiftEq, ZCC_LSHEQ); TOKENDEF (TK_RShiftEq, ZCC_RSHEQ); + TOKENDEF (TK_URShiftEq, ZCC_URSHEQ); TOKENDEF (TK_AndEq, ZCC_ANDEQ); TOKENDEF (TK_OrEq, ZCC_OREQ); TOKENDEF (TK_XorEq, ZCC_XOREQ); From 9f260983c752586b5a1eb71923f6573a1eb2493d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 14:18:31 +0200 Subject: [PATCH 081/255] - implemented all assign/modify operators. - use a table to translate from PEX to tokens to make the code easier to read. --- src/scripting/codegeneration/codegen.cpp | 8 +- src/scripting/zscript/zcc_compile.cpp | 78 +++++++++----- src/scripting/zscript/zcc_exprlist.h | 124 +++++++++++------------ 3 files changed, 120 insertions(+), 90 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 1b169411f..9deeeaed2 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1550,7 +1550,7 @@ FxExpression *FxSizeAlign::Resolve(FCompileContext& ctx) } else { - FxExpression *x = new FxConstant(Which == 'a' ? int(type->Align) : int(type->Size), Operand->ScriptPosition); + FxExpression *x = new FxConstant(Which == TK_AlignOf ? int(type->Align) : int(type->Size), Operand->ScriptPosition); delete this; return x->Resolve(ctx); } @@ -1811,12 +1811,12 @@ ExpEmit FxAssign::Emit(VMFunctionBuilder *build) assert(ValueType == Base->ValueType && IsNumeric()); assert(ValueType->GetRegType() == Right->ValueType->GetRegType()); - ExpEmit result = Right->Emit(build); - assert(result.RegType <= REGT_TYPE); - ExpEmit pointer = Base->Emit(build); Address = pointer; + ExpEmit result = Right->Emit(build); + assert(result.RegType <= REGT_TYPE); + if (pointer.Target) { if (result.Konst) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index b2c58c124..297ac2ef0 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2324,6 +2324,33 @@ FxExpression *ZCCCompiler::ConvertAST(ZCC_TreeNode *ast) } } + +#define xx(a,z) z, +static int Pex2Tok[] = { +#include "zcc_exprlist.h" +}; + +//========================================================================== +// +// Helper for modify/assign operators +// +//========================================================================== + +static FxExpression *ModifyAssign(FxBinary *operation, FxExpression *left) +{ + auto assignself = static_cast(operation->left); + auto assignment = new FxAssign(left, operation); + assignself->Assignment = assignment; + return assignment; +} + + +//========================================================================== +// +// Convert an AST node and its children +// +//========================================================================== + FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { // Note: Do not call 'Simplify' here because that function tends to destroy identifiers due to lack of context in which to resolve them. @@ -2426,11 +2453,11 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { case PEX_PostDec: case PEX_PostInc: - return new FxPostIncrDecr(operand, op == PEX_PostDec ? TK_Decr : TK_Incr); + return new FxPostIncrDecr(operand, Pex2Tok[op]); case PEX_PreDec: case PEX_PreInc: - return new FxPreIncrDecr(operand, op == PEX_PostDec ? TK_Decr : TK_Incr); + return new FxPreIncrDecr(operand, Pex2Tok[op]); case PEX_Negate: return new FxMinusSign(operand); @@ -2446,7 +2473,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_SizeOf: case PEX_AlignOf: - return new FxSizeAlign(operand, op == PEX_AlignOf ? 'a' : 's'); + return new FxSizeAlign(operand, Pex2Tok[op]); default: assert(0 && "Unknown unary operator."); // should never happen @@ -2463,16 +2490,17 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) auto left = ConvertNode(binary->Left); auto right = ConvertNode(binary->Right); auto op = binary->Operation; + auto tok = Pex2Tok[op]; switch (op) { case PEX_Add: case PEX_Sub: - return new FxAddSub(op == PEX_Add ? '+' : '-', left, right); + return new FxAddSub(tok, left, right); case PEX_Mul: case PEX_Div: case PEX_Mod: - return new FxMulDiv(op == PEX_Mul ? '*' : op == PEX_Div ? '/' : '%', left, right); + return new FxMulDiv(tok, left, right); case PEX_Pow: return new FxPow(left, right); @@ -2483,39 +2511,41 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_BitAnd: case PEX_BitOr: case PEX_BitXor: - return new FxBinaryInt(op == PEX_LeftShift ? TK_LShift : op == PEX_RightShift ? TK_RShift : op == PEX_URightShift ? TK_URShift : op == PEX_BitAnd ? '&' : op == PEX_BitOr ? '|' : '^', left, right); + return new FxBinaryInt(tok, left, right); case PEX_BoolOr: case PEX_BoolAnd: - return new FxBinaryLogical(op == PEX_BoolAnd ? TK_AndAnd : TK_OrOr, left, right); + return new FxBinaryLogical(tok, left, right); case PEX_LT: case PEX_LTEQ: case PEX_GT: case PEX_GTEQ: - return new FxCompareRel(op == PEX_LT ? '<' : op == PEX_RightShift ? '>' : op == PEX_LTEQ ? TK_Leq : TK_Geq, left, right); + return new FxCompareRel(tok, left, right); case PEX_EQEQ: case PEX_NEQ: - return new FxCompareEq(op == PEX_NEQ ? TK_Neq : TK_Eq, left, right); + return new FxCompareEq(tok, left, right); case PEX_Assign: return new FxAssign(left, right); -/* - case ZCC_MULEQ: - case ZCC_DIVEQ: - case ZCC_MODEQ: - case ZCC_ADDEQ: - case ZCC_SUBEQ: - case ZCC_LSHEQ: - case ZCC_RSHEQ: - case ZCC_ANDEQ: - case ZCC_OREQ: - case ZCC_XOREQ: - //break; - default: - Error(ast, "Invalid assign statement"); -*/ + + case PEX_AddAssign: + case PEX_SubAssign: + return ModifyAssign(new FxAddSub(tok, new FxAssignSelf(*ast), right), left); + + case PEX_MulAssign: + case PEX_DivAssign: + case PEX_ModAssign: + return ModifyAssign(new FxMulDiv(tok, new FxAssignSelf(*ast), right), left); + + case PEX_LshAssign: + case PEX_RshAssign: + case PEX_URshAssign: + case PEX_AndAssign: + case PEX_OrAssign: + case PEX_XorAssign: + return ModifyAssign(new FxBinaryInt(tok, new FxAssignSelf(*ast), right), left); // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_LTGTEQ: diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index 5c9936988..4770a08a4 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -1,75 +1,75 @@ -// Name n-ary -xx(Nil, ) +// Name Token used in the code generator +xx(Nil, TK_None) -xx(ID, ) -xx(Super, ) -xx(Null, ) -xx(Self, ) -xx(ConstValue, ) -xx(FuncCall, ) -xx(ArrayAccess, ) -xx(MemberAccess, ) -xx(TypeRef, ) +xx(ID, TK_Identifier) +xx(Super, TK_Super) +xx(Null, TK_Null) +xx(Self, TK_Self) +xx(ConstValue, TK_Const) +xx(FuncCall, '(') +xx(ArrayAccess, TK_Array) +xx(MemberAccess, '.') +xx(TypeRef, TK_Class) -xx(PostInc, ) -xx(PostDec, ) +xx(PostInc, TK_Incr) +xx(PostDec, TK_Decr) -xx(PreInc, ) -xx(PreDec, ) -xx(Negate, ) -xx(AntiNegate, ) -xx(BitNot, ) -xx(BoolNot, ) -xx(SizeOf, ) -xx(AlignOf, ) +xx(PreInc, TK_Incr) +xx(PreDec, TK_Decr) +xx(Negate, '-') +xx(AntiNegate, '+') +xx(BitNot, '~') +xx(BoolNot, '!') +xx(SizeOf, TK_SizeOf) +xx(AlignOf, TK_AlignOf) -xx(Add, ) -xx(Sub, ) -xx(Mul, ) -xx(Div, ) -xx(Mod, ) -xx(Pow, ) -xx(CrossProduct, ) -xx(DotProduct, ) -xx(LeftShift, ) -xx(RightShift, ) -xx(URightShift, ) -xx(Concat, ) +xx(Add, '+') +xx(Sub, '-') +xx(Mul, '*') +xx(Div, '/') +xx(Mod, '%') +xx(Pow, TK_MulMul) +xx(CrossProduct, TK_Cross) +xx(DotProduct, TK_Dot) +xx(LeftShift, TK_LShift) +xx(RightShift, TK_RShift) +xx(URightShift, TK_URShift) +xx(Concat, TK_DotDot) -xx(LT, ) -xx(LTEQ, ) -xx(GT, ) -xx(GTEQ, ) -xx(LTGTEQ, ) -xx(Is, ) +xx(LT, '<') +xx(LTEQ, TK_Leq) +xx(GT, '>') +xx(GTEQ, TK_Geq) +xx(LTGTEQ, TK_LtGtEq) +xx(Is, TK_Is) -xx(EQEQ, ) -xx(NEQ, ) -xx(APREQ, ) +xx(EQEQ, TK_Eq) +xx(NEQ, TK_Neq) +xx(APREQ, TK_ApproxEq) -xx(BitAnd, ) -xx(BitOr, ) -xx(BitXor, ) -xx(BoolAnd, ) -xx(BoolOr, ) +xx(BitAnd, '&') +xx(BitOr, '|') +xx(BitXor, '^') +xx(BoolAnd, TK_AndAnd) +xx(BoolOr, TK_OrOr) -xx(Assign, ) -xx(AddAssign, ) -xx(SubAssign, ) -xx(MulAssign, ) -xx(DivAssign, ) -xx(ModAssign, ) -xx(LshAssign, ) -xx(RshAssign, ) -xx(URshAssign, ) -xx(AndAssign, ) -xx(OrAssign, ) -xx(XorAssign, ) +xx(Assign, '=') +xx(AddAssign, '+') // these are what the code generator needs, not what they represent. +xx(SubAssign, '-') +xx(MulAssign, '*') +xx(DivAssign, '/') +xx(ModAssign, '%') +xx(LshAssign, TK_LShift) +xx(RshAssign, TK_RShift) +xx(URshAssign, TK_URShift) +xx(AndAssign, '&') +xx(OrAssign, '|') +xx(XorAssign, '^') -xx(Scope, ) +xx(Scope, TK_ColonColon) -xx(Trinary, ) +xx(Trinary, '?') -xx(Cast, ) +xx(Cast, TK_Coerce) #undef xx From f5e4c4b1096aa8d9e8b2e880a49016409fd4465e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 16:35:07 +0200 Subject: [PATCH 082/255] - implemented the '<>=' operator - more as a VM coding exercise than for its usefulness, though. --- src/scripting/codegeneration/codegen.cpp | 92 ++++++++++++++++++++++++ src/scripting/codegeneration/codegen.h | 15 ++++ src/scripting/zscript/zcc_compile.cpp | 4 +- 3 files changed, 110 insertions(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9deeeaed2..4bde29ac6 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -2678,6 +2678,98 @@ ExpEmit FxBinaryInt::Emit(VMFunctionBuilder *build) // //========================================================================== +FxLtGtEq::FxLtGtEq(FxExpression *l, FxExpression *r) + : FxBinary(TK_LtGtEq, l, r) +{ + ValueType = TypeSInt32; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxLtGtEq::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + if (!ResolveLR(ctx, false)) return NULL; + + if (!left->IsNumeric() || !right->IsNumeric()) + { + ScriptPosition.Message(MSG_ERROR, "<>= expects two numeric operands"); + delete this; + return nullptr; + } + if (left->ValueType->GetRegType() != right->ValueType->GetRegType()) + { + if (left->ValueType->GetRegType() == REGT_INT) + { + left = new FxFloatCast(left); + SAFE_RESOLVE(left, ctx); + } + if (right->ValueType->GetRegType() == REGT_INT) + { + right = new FxFloatCast(left); + SAFE_RESOLVE(left, ctx); + } + } + + else if (left->isConstant() && right->isConstant()) + { + // let's cut this short and always compare doubles. For integers the result will be exactly the same as with an integer comparison, either signed or unsigned. + auto v1 = static_cast(left)->GetValue().GetFloat(); + auto v2 = static_cast(right)->GetValue().GetFloat(); + auto e = new FxConstant(v1 < v2 ? -1 : v1 > v2 ? 1 : 0, ScriptPosition); + delete this; + return e; + } + return this; +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxLtGtEq::Emit(VMFunctionBuilder *build) +{ + ExpEmit op1 = left->Emit(build); + ExpEmit op2 = right->Emit(build); + + assert(op1.RegType == op2.RegType); + assert(op1.RegType == REGT_INT || op1.RegType == REGT_FLOAT); + assert(!op1.Konst || !op2.Konst); + + ExpEmit to(build, REGT_INT); + + int instr = op1.RegType == REGT_INT ? (left->ValueType == TypeUInt32? OP_LTU_RR : OP_LT_RR) : OP_LTF_RR; + if (op1.Konst) instr += 2; + if (op2.Konst) instr++; + + + build->Emit(OP_LI, to.RegNum, 1); // default to 1 + build->Emit(instr, 0, op1.RegNum, op2.RegNum); // if (left < right) + auto j1 = build->Emit(OP_JMP, 1); + build->Emit(OP_LI, to.RegNum, -1); // result is -1 + auto j2 = build->Emit(OP_JMP, 1); // jump to end + build->BackpatchToHere(j1); + build->Emit(instr + OP_LE_RR - OP_LT_RR, 0, op1.RegNum, op2.RegNum); // if (left == right) + auto j3 = build->Emit(OP_JMP, 1); + build->Emit(OP_LI, to.RegNum, 0); // result is 0 + build->BackpatchToHere(j2); + build->BackpatchToHere(j3); + + return to; +} + +//========================================================================== +// +// +// +//========================================================================== + FxBinaryLogical::FxBinaryLogical(int o, FxExpression *l, FxExpression *r) : FxExpression(l->ScriptPosition) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 525325276..6bcc32830 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -769,6 +769,21 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// +// +//========================================================================== + +class FxLtGtEq : public FxBinary +{ +public: + FxLtGtEq(FxExpression*, FxExpression*); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxBinaryLogical diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 297ac2ef0..52d21784e 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2547,8 +2547,10 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_XorAssign: return ModifyAssign(new FxBinaryInt(tok, new FxAssignSelf(*ast), right), left); - // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_LTGTEQ: + return new FxLtGtEq(left, right); + + // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_Concat: case PEX_Is: // more esoteric operators From 5bed0a2b3973a69ba9dd6f8bf2ac98d308050ae1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 17:41:39 +0200 Subject: [PATCH 083/255] - implemented class member access for variables. (Struct members and functions not done yet.) --- src/namedef.h | 1 + src/scripting/codegeneration/codegen.cpp | 152 ++++++++++++++++++----- src/scripting/codegeneration/codegen.h | 17 +++ src/scripting/thingdef_data.cpp | 2 + src/scripting/zscript/zcc_compile.cpp | 17 ++- 5 files changed, 153 insertions(+), 36 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index 43856aad1..d512a7948 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -436,6 +436,7 @@ xx(Scale) xx(ScaleX) xx(ScaleY) xx(Floatbobphase) +xx(Target) xx(Blocking) xx(Blockmonsters) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4bde29ac6..a271d240a 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4019,7 +4019,12 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } else if (sym->IsKindOf(RUNTIME_CLASS(PField))) { - ABORT(ctx.Function); // only valid when resolving a function. + if (!ctx.Function) + { + ScriptPosition.Message(MSG_ERROR, "Cannot resolve class member outside a function", sym->SymbolName.GetChars()); + delete this; + return nullptr; + } PField *vsym = static_cast(sym); // We have 4 cases to consider here: @@ -4029,11 +4034,11 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) // 4. This is a normal member or unrestricted action function. if (vsym->Flags & VARF_Deprecated) { - ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", sym->SymbolName.GetChars()); } if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) { - ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); + ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", sym->SymbolName.GetChars()); delete this; return nullptr; } @@ -4041,6 +4046,7 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) if (vsym->Flags & VARF_Static) { // todo. For now these cannot be defined so let's just exit. + ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); delete this; return nullptr; } @@ -4051,29 +4057,29 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) delete this; return nullptr; } - else + + if (ctx.Function->Variants[0].SelfClass != ctx.Class) { - if (ctx.Function->Variants[0].SelfClass != ctx.Class) + // Check if the restricted class can access it. + PSymbol *sym2; + if ((sym2 = ctx.FindInSelfClass(Identifier, symtbl)) != nullptr) { - // Check if the restricted class can access it. - PSymbol *sym2; - if ((sym2 = ctx.FindInSelfClass(Identifier, symtbl)) != nullptr) + if (sym != sym2) { - if (sym != sym2) - { - ScriptPosition.Message(MSG_ERROR, "Member variable of %s not accessible through restricted self pointer", ctx.Class->TypeName.GetChars()); - delete this; - return nullptr; - } + ScriptPosition.Message(MSG_ERROR, "Member variable of %s not accessible through restricted self pointer", ctx.Class->TypeName.GetChars()); + delete this; + return nullptr; } } + } ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as member variable, index %d\n", Identifier.GetChars(), vsym->Offset); newex = new FxClassMember((new FxSelf(ScriptPosition))->Resolve(ctx), vsym, ScriptPosition); } - } else { ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); + delete this; + return nullptr; } } @@ -4100,10 +4106,109 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) else { ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); - newex = new FxConstant(0, ScriptPosition); + delete this; + return nullptr; } delete this; - return newex? newex->Resolve(ctx) : NULL; + return newex? newex->Resolve(ctx) : nullptr; +} + + +//========================================================================== +// +// +// +//========================================================================== + +FxMemberIdentifier::FxMemberIdentifier(FxExpression *left, FName name, const FScriptPosition &pos) + : FxIdentifier(name, pos) +{ + Object = left; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) +{ + PSymbol * sym; + FxExpression *newex = nullptr; + + CHECKRESOLVED(); + + SAFE_RESOLVE(Object, ctx); + + if (Object->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) + { + PSymbolTable *symtbl; + PClass *cls = static_cast(Object->ValueType)->ClassRestriction; + if ((sym = cls->Symbols.FindSymbolInTable(Identifier, symtbl)) != nullptr) + { + if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) + { + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as class constant\n", Identifier.GetChars()); + newex = FxConstant::MakeConstant(sym, ScriptPosition); + } + else if (sym->IsKindOf(RUNTIME_CLASS(PField))) + { + PField *vsym = static_cast(sym); + + // We have 4 cases to consider here: + // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. + // 2. This is a static function + // 3. This is an action function with a restricted self pointer + // 4. This is a normal member or unrestricted action function. + if (vsym->Flags & VARF_Deprecated) + { + ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + } + if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) + { + ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); + delete this; + return nullptr; + } + + if (vsym->Flags & VARF_Static) + { + // todo. For now these cannot be defined so let's just exit. + ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); + delete this; + return nullptr; + } + auto x = new FxClassMember(Object, vsym, ScriptPosition); + delete this; + return x->Resolve(ctx); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); + delete this; + return nullptr; + } + } + else + { + ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); + delete this; + return nullptr; + } + } + else if (Object->ValueType->IsA(RUNTIME_CLASS(PStruct))) + { + // todo + } + else if (Object->ValueType->IsA(RUNTIME_CLASS(PPointer))) + { + // todo + } + + ScriptPosition.Message(MSG_ERROR, "Left side of %s is not a struct or class", Identifier.GetChars()); + delete this; + return nullptr; } @@ -4248,19 +4353,6 @@ FxExpression *FxClassMember::Resolve(FCompileContext &ctx) ExpEmit FxClassMember::Emit(VMFunctionBuilder *build) { - if (build->IsActionFunc && ~membervar->Flags & VARF_Native) - { // Check if this is a user-defined variable. - // As of right now, FxClassMember is only ever used with FxSelf. - // This very user variable was defined in stateowner so if - // self (a0) != stateowner (a1) then the offset is most likely - // going to end up being totally wrong even if the variable was - // redefined in self which means we have to abort to avoid reading - // or writing to a random address and possibly crash. - build->Emit(OP_EQA_R, 1, 0, 1); - build->Emit(OP_JMP, 1); - build->Emit(OP_THROW, 2, X_BAD_SELF); - } - ExpEmit obj = classx->Emit(build); assert(obj.RegType == REGT_POINTER); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 6bcc32830..333075961 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -245,6 +245,7 @@ public: class FxIdentifier : public FxExpression { +protected: FName Identifier; public: @@ -253,6 +254,22 @@ public: }; +//========================================================================== +// +// FxIdentifier +// +//========================================================================== + +class FxMemberIdentifier : public FxIdentifier +{ + FxExpression *Object; + +public: + FxMemberIdentifier(FxExpression *obj, FName i, const FScriptPosition &p); + FxExpression *Resolve(FCompileContext&); +}; + + //========================================================================== // // FxDotIdentifier diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index bdb992fba..470594897 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -636,6 +636,7 @@ void InitThingdef() // Define some member variables we feel like exposing to the user PSymbolTable &symt = RUNTIME_CLASS(AActor)->Symbols; PType *array5 = NewArray(TypeSInt32, 5); + PType *TypeActor = NewClassPointer(RUNTIME_CLASS(AActor)); symt.AddSymbol(new PField(NAME_Alpha, TypeFloat64, VARF_Native, myoffsetof(AActor, Alpha))); symt.AddSymbol(new PField(NAME_Angle, TypeFloat64, VARF_Native, myoffsetof(AActor, Angles.Yaw))); symt.AddSymbol(new PField(NAME_Args, array5, VARF_Native, myoffsetof(AActor, args))); @@ -675,4 +676,5 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_VisibleStartPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartPitch))); symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); + symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 52d21784e..a91d27a4e 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2372,13 +2372,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // The function name is a simple identifier. return new FxFunctionCall(static_cast(fcall->Function)->Identifier, NAME_None, ConvertNodeList(fcall->Parameters), *ast); - // not yet done - case AST_ExprTypeRef: - case AST_SwitchStmt: - case AST_CaseStmt: case AST_ExprMemberAccess: - // calling a class member through its pointer - // todo. break; case AST_ExprBinary: @@ -2400,6 +2394,12 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) break; } + case AST_ExprMemberAccess: + { + auto memaccess = static_cast(ast); + return new FxMemberIdentifier(ConvertNode(memaccess->Left), memaccess->Right, *ast); + } + case AST_FuncParm: { auto fparm = static_cast(ast); @@ -2660,6 +2660,11 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } } + // not yet done + case AST_SwitchStmt: + case AST_CaseStmt: + break; + case AST_CompoundStmt: { From 89416835a8426c79cf36a55c297e20a55810dcf8 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 21 Oct 2016 19:18:39 +0200 Subject: [PATCH 084/255] - preparations for null pointer support. - add pointer support to FxAssign. --- src/dobjtype.cpp | 4 +- src/dobjtype.h | 3 +- src/scripting/codegeneration/codegen.cpp | 98 +++++++++++++++++++----- src/scripting/codegeneration/codegen.h | 7 ++ 4 files changed, 90 insertions(+), 22 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index ded832f2d..0cd1a8d31 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -84,6 +84,7 @@ PColor *TypeColor; PStatePointer *TypeState; PStruct *TypeVector2; PStruct *TypeVector3; +PPointer *TypeNullPtr; // PRIVATE DATA DEFINITIONS ------------------------------------------------ @@ -616,6 +617,7 @@ void PType::StaticInit() TypeTable.AddType(TypeSound = new PSound); TypeTable.AddType(TypeColor = new PColor); TypeTable.AddType(TypeState = new PStatePointer); + TypeTable.AddType(TypeNullPtr = new PPointer); TypeVector2 = new PStruct(NAME_Vector2, nullptr); TypeVector2->AddField(NAME_X, TypeFloat64); @@ -1635,7 +1637,7 @@ END_POINTERS PPointer::PPointer() : PBasicType(sizeof(void *), __alignof(void *)), PointedType(NULL) { - mDescriptiveName = "Pointer"; + mDescriptiveName = "NullPointer"; } //========================================================================== diff --git a/src/dobjtype.h b/src/dobjtype.h index 4a15078fd..e6f2a491b 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -530,6 +530,7 @@ class PPointer : public PBasicType DECLARE_CLASS(PPointer, PBasicType); HAS_OBJECT_POINTERS; public: + PPointer(); PPointer(PType *pointsat); PType *PointedType; @@ -546,7 +547,6 @@ public: bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; protected: - PPointer(); }; class PClassPointer : public PPointer @@ -890,6 +890,7 @@ extern PColor *TypeColor; extern PStruct *TypeVector2; extern PStruct *TypeVector3; extern PStatePointer *TypeState; +extern PPointer *TypeNullPtr; // A constant value --------------------------------------------------------- diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index a271d240a..f3cf4867e 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1078,6 +1078,10 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) // don't go through the entire list if the types are the same. goto basereturn; } + else if (basex->ValueType == TypeNullPtr && (ValueType == TypeState || ValueType->IsKindOf(RUNTIME_CLASS(PPointer)))) + { + goto basereturn; + } else if (ValueType->GetRegType() == REGT_FLOAT) { FxExpression *x = new FxFloatCast(basex); @@ -1199,6 +1203,7 @@ basereturn: auto x = basex; basex = nullptr; delete this; + x->ValueType = ValueType; return x; } @@ -1772,9 +1777,64 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) SAFE_RESOLVE(Right, ctx); - if (!Base->IsNumeric() || !Right->IsNumeric()) + if (Base->IsNumeric() && Right->IsNumeric()) { - ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); + if (Right->ValueType != ValueType) + { + if (ValueType == TypeBool) + { + Right = new FxBoolCast(Right); + } + else if (ValueType->GetRegType() == REGT_INT) + { + Right = new FxIntCast(Right, ctx.FromDecorate); + } + else + { + Right = new FxFloatCast(Right); + } + SAFE_RESOLVE(Right, ctx); + } + } + else if (Base->ValueType == Right->ValueType) + { + if (Base->ValueType->IsKindOf(RUNTIME_CLASS(PArray))) + { + ScriptPosition.Message(MSG_ERROR, "Cannot assign arrays"); + delete this; + return nullptr; + } + if (Base->ValueType->IsKindOf(RUNTIME_CLASS(PStruct))) + { + ScriptPosition.Message(MSG_ERROR, "Struct assignment not implemented yet"); + delete this; + return nullptr; + } + // Both types are the same so this is ok. + } + else if ((Base->ValueType == TypeState || Base->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) && Right->ValueType == TypeNullPtr) + { + // null pointers can be assigned to any other pointer + } + else if (Base->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) + { + // class pointers may be assignable so add a cast which performs a check. + Right = new FxClassTypeCast(static_cast(ValueType), Right); + SAFE_RESOLVE(Right, ctx); + } + else if (Base->ValueType == TypeString && (Right->ValueType == TypeName || Right->ValueType == TypeSound)) + { + Right = new FxStringCast(Right); + SAFE_RESOLVE(Right, ctx); + } + else if (Base->ValueType == TypeName && Right->ValueType == TypeString) + { + Right = new FxNameCast(Right); + SAFE_RESOLVE(Right, ctx); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Assignment between incompatible types."); delete this; return nullptr; } @@ -1785,22 +1845,6 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) return nullptr; } - if (Right->ValueType != ValueType) - { - if (ValueType == TypeBool) - { - Right = new FxBoolCast(Right); - } - else if (ValueType->GetRegType() == REGT_INT) - { - Right = new FxIntCast(Right, ctx.FromDecorate); - } - else - { - Right = new FxFloatCast(Right); - } - SAFE_RESOLVE(Right, ctx); - } return this; } @@ -1808,7 +1852,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) ExpEmit FxAssign::Emit(VMFunctionBuilder *build) { static const BYTE loadops[] = { OP_LK, OP_LKF, OP_LKS, OP_LKP }; - assert(ValueType == Base->ValueType && IsNumeric()); + assert(ValueType == Base->ValueType); assert(ValueType->GetRegType() == Right->ValueType->GetRegType()); ExpEmit pointer = Base->Emit(build); @@ -2272,8 +2316,14 @@ FxExpression *FxPow::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return NULL; + if (!ResolveLR(ctx, true)) return nullptr; + if (!IsNumeric()) + { + ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); + delete this; + return nullptr; + } if (left->isConstant() && right->isConstant()) { double v1 = static_cast(left)->GetValue().GetFloat(); @@ -6015,6 +6065,14 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) CHECKRESOLVED(); SAFE_RESOLVE(basex, ctx); + if (basex->ValueType == TypeNullPtr) + { + basex->ValueType = ValueType; + auto x = basex; + basex = nullptr; + delete this; + return x; + } if (basex->ValueType->GetClass() == RUNTIME_CLASS(PClassPointer)) { auto to = static_cast(ValueType); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 333075961..0348468a9 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -379,6 +379,13 @@ public: ValueType = value.Type = TypeState; isresolved = true; } + + FxConstant(nullptr_t *nullp, const FScriptPosition &pos) : FxExpression(pos) + { + value.pointer = nullptr; + ValueType = value.Type = TypeNullPtr; + isresolved = true; + } static FxExpression *MakeConstant(PSymbol *sym, const FScriptPosition &pos); From 4b41e735f1cf0514279583a92d4623c42bdd7007 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 00:50:04 +0200 Subject: [PATCH 085/255] - added null pointer. - fixed: FxMemberIdentifier checked for ClassPointers instead of object pointers to resolve the left hand side of the expression. - allow comparison of pointers. --- src/dobjtype.cpp | 2 +- src/scripting/codegeneration/codegen.cpp | 139 +++++++++++++---------- src/scripting/codegeneration/codegen.h | 2 +- src/scripting/thingdef_data.cpp | 2 +- src/scripting/zscript/zcc-parse.lemon | 8 ++ src/scripting/zscript/zcc_compile.cpp | 10 ++ src/scripting/zscript/zcc_parser.cpp | 2 +- 7 files changed, 104 insertions(+), 61 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 0cd1a8d31..9191c60c0 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -1671,7 +1671,7 @@ int PPointer::GetStoreOp() const int PPointer::GetLoadOp() const { - return PointedType->IsKindOf(RUNTIME_CLASS(PClass)) ? OP_LO : OP_LP; + return (PointedType && PointedType->IsKindOf(RUNTIME_CLASS(PClass))) ? OP_LO : OP_LP; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f3cf4867e..f78dcdff6 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -229,6 +229,31 @@ static PSymbol *FindDecorateBuiltinFunction(FName funcname, VMNativeFunction::Na // //========================================================================== +static bool AreCompatiblePointerTypes(PType *dest, PType *source) +{ + if (dest->IsKindOf(RUNTIME_CLASS(PPointer)) && source->IsKindOf(RUNTIME_CLASS(PPointer))) + { + // Pointers to different types are only compatible if both point to an object and the source type is a child of the destination type. + auto fromtype = static_cast(source); + auto totype = static_cast(dest); + if (fromtype == nullptr) return true; + if (fromtype == totype) return true; + if (fromtype->PointedType->IsKindOf(RUNTIME_CLASS(PClass)) && totype->PointedType->IsKindOf(RUNTIME_CLASS(PClass))) + { + auto fromcls = static_cast(fromtype->PointedType); + auto tocls = static_cast(totype->PointedType); + return (fromcls->IsDescendantOf(tocls)); + } + } + return false; +} + +//========================================================================== +// +// +// +//========================================================================== + ExpEmit FxExpression::Emit (VMFunctionBuilder *build) { ScriptPosition.Message(MSG_ERROR, "Unemitted expression found"); @@ -1174,21 +1199,9 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) if (fromtype->IsDescendantOf(totype)) goto basereturn; } } - else if (ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) + else if (AreCompatiblePointerTypes(ValueType, basex->ValueType)) { - // Pointers to different types are only compatible if both point to an object and the source type is a child of the destination type. - if (basex->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) - { - auto fromtype = static_cast(basex->ValueType); - auto totype = static_cast(ValueType); - if (fromtype->PointedType->IsKindOf(RUNTIME_CLASS(PClass)) && totype->PointedType->IsKindOf(RUNTIME_CLASS(PClass))) - { - - auto fromcls = static_cast(fromtype->PointedType); - auto tocls = static_cast(totype->PointedType); - if (fromcls->IsDescendantOf(tocls)) goto basereturn; - } - } + goto basereturn; } // todo: pointers to class objects. // All other types are only compatible to themselves and have already been handled above by the equality check. @@ -1201,9 +1214,9 @@ errormsg: basereturn: auto x = basex; + x->ValueType = ValueType; basex = nullptr; delete this; - x->ValueType = ValueType; return x; } @@ -1996,14 +2009,21 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) ValueType = TypeFloat64; } } - else if (left->ValueType->GetRegType() == REGT_POINTER && left->ValueType == right->ValueType) + else if (left->ValueType->GetRegType() == REGT_POINTER) { - ValueType = left->ValueType; + if (left->ValueType == right->ValueType || right->ValueType == TypeNullPtr || left->ValueType == TypeNullPtr || + AreCompatiblePointerTypes(left->ValueType, right->ValueType)) + { + // pointers can only be compared for equality. + assert(Operator == TK_Eq || Operator == TK_Neq); + ValueType = TypeBool; + } } else { ValueType = TypeVoid; } + assert(ValueType > nullptr && ValueType < (PType*)0xfffffffffffffff); if (castnumeric) { @@ -4191,70 +4211,75 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) SAFE_RESOLVE(Object, ctx); - if (Object->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) + if (Object->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) { PSymbolTable *symtbl; - PClass *cls = static_cast(Object->ValueType)->ClassRestriction; - if ((sym = cls->Symbols.FindSymbolInTable(Identifier, symtbl)) != nullptr) + auto ptype = static_cast(Object->ValueType)->PointedType; + + if (ptype->IsKindOf(RUNTIME_CLASS(PClass))) { - if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) + PClass *cls = static_cast(ptype); + if ((sym = cls->Symbols.FindSymbolInTable(Identifier, symtbl)) != nullptr) { - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as class constant\n", Identifier.GetChars()); - newex = FxConstant::MakeConstant(sym, ScriptPosition); - } - else if (sym->IsKindOf(RUNTIME_CLASS(PField))) - { - PField *vsym = static_cast(sym); - - // We have 4 cases to consider here: - // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. - // 2. This is a static function - // 3. This is an action function with a restricted self pointer - // 4. This is a normal member or unrestricted action function. - if (vsym->Flags & VARF_Deprecated) + if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) { - ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as class constant\n", Identifier.GetChars()); + newex = FxConstant::MakeConstant(sym, ScriptPosition); } - if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) + else if (sym->IsKindOf(RUNTIME_CLASS(PField))) { - ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); + PField *vsym = static_cast(sym); + + // We have 4 cases to consider here: + // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. + // 2. This is a static function + // 3. This is an action function with a restricted self pointer + // 4. This is a normal member or unrestricted action function. + if (vsym->Flags & VARF_Deprecated) + { + ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + } + if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) + { + ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); + delete this; + return nullptr; + } + + if (vsym->Flags & VARF_Static) + { + // todo. For now these cannot be defined so let's just exit. + ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); + delete this; + return nullptr; + } + auto x = new FxClassMember(Object, vsym, ScriptPosition); + delete this; + return x->Resolve(ctx); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); delete this; return nullptr; } - - if (vsym->Flags & VARF_Static) - { - // todo. For now these cannot be defined so let's just exit. - ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); - delete this; - return nullptr; - } - auto x = new FxClassMember(Object, vsym, ScriptPosition); - delete this; - return x->Resolve(ctx); } else { - ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); + ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); delete this; return nullptr; } } - else + else if (ptype->IsA(RUNTIME_CLASS(PStruct))) { - ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); - delete this; - return nullptr; + // todo } } else if (Object->ValueType->IsA(RUNTIME_CLASS(PStruct))) { // todo } - else if (Object->ValueType->IsA(RUNTIME_CLASS(PPointer))) - { - // todo - } ScriptPosition.Message(MSG_ERROR, "Left side of %s is not a struct or class", Identifier.GetChars()); delete this; diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 0348468a9..32dc4bfbf 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -380,7 +380,7 @@ public: isresolved = true; } - FxConstant(nullptr_t *nullp, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(const FScriptPosition &pos) : FxExpression(pos) { value.pointer = nullptr; ValueType = value.Type = TypeNullPtr; diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 470594897..260cc6408 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -636,7 +636,7 @@ void InitThingdef() // Define some member variables we feel like exposing to the user PSymbolTable &symt = RUNTIME_CLASS(AActor)->Symbols; PType *array5 = NewArray(TypeSInt32, 5); - PType *TypeActor = NewClassPointer(RUNTIME_CLASS(AActor)); + PType *TypeActor = NewPointer(RUNTIME_CLASS(AActor)); symt.AddSymbol(new PField(NAME_Alpha, TypeFloat64, VARF_Native, myoffsetof(AActor, Alpha))); symt.AddSymbol(new PField(NAME_Angle, TypeFloat64, VARF_Native, myoffsetof(AActor, Angles.Yaw))); symt.AddSymbol(new PField(NAME_Args, array5, VARF_Native, myoffsetof(AActor, args))); diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 42c3014c1..eeeba6295 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -1450,6 +1450,14 @@ constant(X) ::= TRUE(A). NEW_INTCONST_NODE(boolconst, TypeBool, true, A); X = boolconst; } +constant(X) ::= NULLPTR(A). +{ + NEW_AST_NODE(ExprConstant, nullptrconst, A); + nullptrconst->Operation = PEX_ConstValue; + nullptrconst->Type = TypeNullPtr; + nullptrconst->StringVal = nullptr; + X = nullptrconst; +} /************ Statements ************/ diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index a91d27a4e..06c08f681 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1462,6 +1462,10 @@ PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt) { return TypeSInt32; // hack this to an integer until we can resolve the enum mess. } + if (type->IsKindOf(RUNTIME_CLASS(PClass))) + { + return NewPointer(type); + } return type; } return TypeError; @@ -2353,6 +2357,8 @@ static FxExpression *ModifyAssign(FxBinary *operation, FxExpression *left) FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { + if (ast == nullptr) return nullptr; + // Note: Do not call 'Simplify' here because that function tends to destroy identifiers due to lack of context in which to resolve them. // The Fx nodes created here will be better suited for that. switch (ast->NodeType) @@ -2436,6 +2442,10 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { return new FxConstant(*cnst->StringVal, *ast); } + else if (cnst->Type == TypeNullPtr) + { + return new FxConstant(*ast); + } else { // can there be other types? diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 222e8e6c5..7d4edf78a 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -154,7 +154,7 @@ static void InitTokenMap() TOKENDEF (TK_Out, ZCC_OUT); TOKENDEF (TK_Optional, ZCC_OPTIONAL); TOKENDEF (TK_Super, ZCC_SUPER); - TOKENDEF (TK_Null, ZCC_NULL); + TOKENDEF (TK_Null, ZCC_NULLPTR); TOKENDEF (TK_Self, ZCC_SELF); TOKENDEF ('~', ZCC_TILDE); TOKENDEF ('!', ZCC_BANG); From 1e11042de099442363eee88c1660dc6e3f8c253d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 02:52:28 +0200 Subject: [PATCH 086/255] - changed VM_EPSILON from 1/1024 to 1/65536 so that the ~== operator can actually be used. 1/1024 is far too coarse for ZDoom's purposes, this needs to be at least fixed point precision. --- src/scripting/vm/vm.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 8cd63f3e5..b9dafde0c 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -17,7 +17,7 @@ typedef unsigned int VM_UWORD; typedef signed int VM_SWORD; typedef VM_UBYTE VM_ATAG; -#define VM_EPSILON (1/1024.0) +#define VM_EPSILON (1/65536.0) union VMOP { From 43aec685590f32a5f228a212e495a543da800ed1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 09:31:37 +0200 Subject: [PATCH 087/255] - implemented ~== operator. Turned out this was really simple because the functionality was already there. --- src/scripting/codegeneration/codegen.cpp | 5 +++-- src/scripting/zscript/zcc_compile.cpp | 3 +-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f78dcdff6..a9c5d40e7 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -2525,6 +2525,7 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) return NULL; } + if (Operator == TK_ApproxEq && ValueType->GetRegType() != REGT_FLOAT) Operator = TK_Eq; if (left->isConstant() && right->isConstant()) { int v; @@ -2533,7 +2534,7 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) { double v1 = static_cast(left)->GetValue().GetFloat(); double v2 = static_cast(right)->GetValue().GetFloat(); - v = Operator == TK_Eq? v1 == v2 : v1 != v2; + v = Operator == TK_Eq? v1 == v2 : Operator == TK_Neq? v1 != v2 : fabs(v1-v2) < VM_EPSILON; } else { @@ -2588,7 +2589,7 @@ ExpEmit FxCompareEq::Emit(VMFunctionBuilder *build) // See FxUnaryNotBoolean for comments, since it's the same thing. build->Emit(OP_LI, to.RegNum, 0, 0); - build->Emit(instr, Operator != TK_Eq, op1.RegNum, op2.RegNum); + build->Emit(instr, Operator == TK_ApproxEq? CMP_APPROX : Operator != TK_Eq, op1.RegNum, op2.RegNum); build->Emit(OP_JMP, 1); build->Emit(OP_LI, to.RegNum, 1); return to; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 06c08f681..bf3d14d06 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2535,6 +2535,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_EQEQ: case PEX_NEQ: + case PEX_APREQ: return new FxCompareEq(tok, left, right); case PEX_Assign: @@ -2563,8 +2564,6 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_Concat: case PEX_Is: - // more esoteric operators - case PEX_APREQ: // vector operations will be done later. case PEX_CrossProduct: From d6047ae651ac9166ac713f7eca018e0977abaf0c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 12:10:19 +0200 Subject: [PATCH 088/255] - added the required code genration nodes for member function calls. This is not testable right now because finally the action function mess has come full circle. The current setup makes it impossible to call action functions from non-action functions because the needed info is local to the functions. Long avoided, this needs to be refactored now so that the different semantics for action functions are no longer needed. --- src/scripting/codegeneration/codegen.cpp | 181 +++++++++++++++++---- src/scripting/codegeneration/codegen.h | 25 ++- src/scripting/decorate/thingdef_exp.cpp | 2 +- src/scripting/decorate/thingdef_states.cpp | 4 +- src/scripting/thingdef.cpp | 2 +- src/scripting/thingdef.h | 2 +- src/scripting/zscript/zcc_compile.cpp | 2 +- 7 files changed, 180 insertions(+), 38 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index a9c5d40e7..dce724a32 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4717,12 +4717,26 @@ static bool CheckArgSize(FName fname, FArgumentList *args, int min, int max, FSc FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { ABORT(ctx.Class); + bool error = false; - PFunction *afd = FindClassMemberFunction(ctx.Class, ctx.Class, MethodName, ScriptPosition); + PFunction *afd = FindClassMemberFunction(ctx.Class, ctx.Class, MethodName, ScriptPosition, &error); + + if (error) + { + delete this; + return nullptr; + } if (afd != nullptr) { - auto x = new FxVMFunctionCall(afd, ArgList, ScriptPosition, false); + if (ctx.Function->Variants[0].Flags & VARF_Static && !(afd->Variants[0].Flags & VARF_Static)) + { + ScriptPosition.Message(MSG_ERROR, "Call to non-static function %s from a static context", MethodName.GetChars()); + delete this; + return nullptr; + } + auto self = !(afd->Variants[0].Flags & VARF_Static)? new FxSelf(ScriptPosition) : nullptr; + auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, false); ArgList = nullptr; delete this; return x->Resolve(ctx); @@ -4867,6 +4881,105 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) } +//========================================================================== +// +// +// +//========================================================================== + +FxMemberFunctionCall::FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos) + : FxExpression(pos) +{ + Self = self; + MethodName = methodname; + ArgList = args; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxMemberFunctionCall::~FxMemberFunctionCall() +{ + SAFE_DELETE(Self); + SAFE_DELETE(ArgList); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) +{ + ABORT(ctx.Class); + SAFE_RESOLVE(Self, ctx); + + PClass *cls; + bool staticonly = false; + if (Self->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) + { + cls = static_cast(Self->ValueType)->ClassRestriction; + staticonly = true; + } + else if (Self->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) + { + auto ptype = static_cast(Self->ValueType)->PointedType; + if (ptype->IsKindOf(RUNTIME_CLASS(PClass))) + { + cls = static_cast(ptype); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Left hand side of %s must point to a class object\n", MethodName.GetChars()); + delete this; + return nullptr; + } + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid expression on left hand side of %s\n", MethodName.GetChars()); + delete this; + return nullptr; + } + + bool error = false; + PFunction *afd = FindClassMemberFunction(cls, cls, MethodName, ScriptPosition, &error); + if (error) + { + delete this; + return nullptr; + } + + if (afd == nullptr) + { + ScriptPosition.Message(MSG_ERROR, "Unknown function %s\n", MethodName.GetChars()); + delete this; + return nullptr; + } + if (staticonly && !(afd->Variants[0].Flags & VARF_Static)) + { + if (!ctx.Class->IsDescendantOf(cls)) + { + ScriptPosition.Message(MSG_ERROR, "Cannot call non-static function %s::%s from here\n", cls->TypeName.GetChars(), MethodName.GetChars()); + delete this; + return nullptr; + } + // If this is a qualified call to a parent class function, let it through (but this needs to disable virtual calls later.) + } + + // do not pass the self pointer to static functions. + auto self = !(afd->Variants[0].Flags & VARF_Static) ? Self : nullptr; + auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, staticonly); + ArgList = nullptr; + delete this; + return x->Resolve(ctx); +} + + //========================================================================== // // FxActionSpecialCall @@ -5042,13 +5155,14 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) // //========================================================================== -FxVMFunctionCall::FxVMFunctionCall(PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool ownerisself) +FxVMFunctionCall::FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool novirtual) : FxExpression(pos) { + Self = self; Function = func; ArgList = args; EmitTail = false; - OwnerIsSelf = ownerisself; + NoVirtual = novirtual; } //========================================================================== @@ -5103,6 +5217,7 @@ VMFunction *FxVMFunctionCall::GetDirectFunction() FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); + SAFE_RESOLVE_OPT(Self, ctx); bool failed = false; auto proto = Function->Variants[0].Proto; auto argtypes = proto->ArgumentTypes; @@ -5112,6 +5227,14 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) else if (Function->Variants[0].Flags & VARF_Method) implicit = 1; else implicit = 0; + // This should never happen. + if (Self == nullptr && !(Function->Variants[0].Flags & VARF_Static)) + { + ScriptPosition.Message(MSG_ERROR, "Call to non-static function without a self pointer"); + delete this; + return nullptr; + } + if (ArgList != NULL) { for (unsigned i = 0; i < ArgList->Size(); i++) @@ -5142,16 +5265,14 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) //========================================================================== // -// Assumption: This call is being generated inside a function whose a0 -// register is a self pointer. For action functions, a1 maps to stateowner -// and a2 maps to callingstate. (self, stateowner, callingstate) +// // //========================================================================== ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) { assert((build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= NAP) || - (!build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= 1)); + (!build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= 1)); int count = (ArgList ? ArgList->Size() : 0); if (count == 1) @@ -5163,35 +5284,34 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } } - // Passing the caller as 'self' is a serious design mistake in DECORATE because it mixes up the types of the two actors involved. - // For ZSCRIPT 'self' is properly used for the state's owning actor, meaning we have to pass the second argument here. - // If both functions are non-action or both are action, there is no need for special treatment. - if (!OwnerIsSelf || (!!(Function->Variants[0].Flags & VARF_Action) == build->IsActionFunc)) + //if (elf || (!!(Function->Variants[0].Flags & VARF_Action) == build->IsActionFunc)) { - // Emit code to pass implied parameters + // Emit code to pass implied parameters if (Function->Variants[0].Flags & VARF_Method) - { - build->Emit(OP_PARAM, 0, REGT_POINTER, 0); - count += 1; - } + { + assert(Self != nullptr); + Self->Emit(build); + count += 1; + } if (Function->Variants[0].Flags & VARF_Action) - { - static_assert(NAP == 3, "This code needs to be updated if NAP changes"); - if (build->IsActionFunc) { - build->Emit(OP_PARAM, 0, REGT_POINTER, 1); - build->Emit(OP_PARAM, 0, REGT_POINTER, 2); + static_assert(NAP == 3, "This code needs to be updated if NAP changes"); + if (build->IsActionFunc) + { + build->Emit(OP_PARAM, 0, REGT_POINTER, 1); + build->Emit(OP_PARAM, 0, REGT_POINTER, 2); + } + else + { + int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); + } + count += 2; } - else - { - int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - } - count += 2; - } } + /* else { if (build->IsActionFunc && (Function->Variants[0].Flags & VARF_Method)) @@ -5207,6 +5327,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) I_Error("Cannot call action function from non-action functions."); } } + */ // Emit code to pass explicit parameters if (ArgList != NULL) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 32dc4bfbf..4f3b57c13 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -1080,6 +1080,26 @@ public: }; +//========================================================================== +// +// FxFunctionCall +// +//========================================================================== + +class FxMemberFunctionCall : public FxExpression +{ + FxExpression *Self; + FName MethodName; + FArgumentList *ArgList; + +public: + + FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos); + ~FxMemberFunctionCall(); + FxExpression *Resolve(FCompileContext&); +}; + + //========================================================================== // // FxActionSpecialCall @@ -1130,12 +1150,13 @@ public: class FxVMFunctionCall : public FxExpression { bool EmitTail; - bool OwnerIsSelf; // ZSCRIPT makes the state's owner the self pointer to ensure proper type handling + bool NoVirtual; + FxExpression *Self; PFunction *Function; FArgumentList *ArgList; public: - FxVMFunctionCall(PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool ownerisself); + FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool novirtual); ~FxVMFunctionCall(); FxExpression *Resolve(FCompileContext&); PPrototype *ReturnProto(); diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 5be69390e..2d1d189b4 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -515,7 +515,7 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) args = nullptr; } - return new FxVMFunctionCall(func, args, sc, false); + return new FxVMFunctionCall(new FxSelf(sc), func, args, sc, false); } } diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 11db1504d..8b75b935f 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -99,7 +99,7 @@ FxVMFunctionCall *DoActionSpecials(FScanner &sc, FState & state, Baggage &bag) { sc.ScriptError ("Too many arguments to %s", specname.GetChars()); } - return new FxVMFunctionCall(FindGlobalActionFunction("A_CallSpecial"), args, sc, false); + return new FxVMFunctionCall(new FxSelf(sc), FindGlobalActionFunction("A_CallSpecial"), args, sc, false); } return NULL; } @@ -571,7 +571,7 @@ FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestring, B { FArgumentList *args = new FArgumentList; ParseFunctionParameters(sc, bag.Info, *args, afd, statestring, &bag.statedef); - call = new FxVMFunctionCall(afd, args->Size() > 0 ? args : NULL, sc, false); + call = new FxVMFunctionCall(new FxSelf(sc), afd, args->Size() > 0 ? args : NULL, sc, false); if (args->Size() == 0) { delete args; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 7fcb0ce39..45e77b3ad 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -155,7 +155,7 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i // //========================================================================== -PFunction *FindClassMemberFunction(PClass *selfcls, PClass *funccls, FName name, FScriptPosition &sc) +PFunction *FindClassMemberFunction(PClass *selfcls, PClass *funccls, FName name, FScriptPosition &sc, bool *error) { // Skip ACS_NamedExecuteWithResult. Anything calling this should use the builtin instead. if (name == NAME_ACS_NamedExecuteWithResult) return nullptr; diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index bdee476ee..51df4821e 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -153,7 +153,7 @@ class FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestr FName CheckCastKludges(FName in); void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); -PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc); +PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc, bool *error); //========================================================================== // diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index bf3d14d06..ba038a716 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2066,7 +2066,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a if (fc->Parameters == nullptr && (afd->Variants[0].Flags & VARF_Action)) { // We can use this function directly without wrapping it in a caller. - return new FxVMFunctionCall(afd, nullptr, *af, true); + return new FxVMFunctionCall(new FxSelf(*af), afd, nullptr, *af, false); } } else From d714670acc85712ddecf0da39e03c051184cde67 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 16:35:48 +0200 Subject: [PATCH 089/255] - allow calling non-action functions directly from a state. Ironically this only requires a very minor change in the calling code and an added member for the VMFunction to tell that code how many parameters to pass. This change will allow to turn the vast majority of action functions into regular members, the only ones that still need to be an action function are the few that actually use the pointers. --- src/d_dehacked.cpp | 2 ++ src/dobjtype.h | 6 ++++++ src/info.cpp | 4 ++-- src/p_actionfunctions.cpp | 2 +- src/scripting/codegeneration/codegen.cpp | 9 +++------ src/scripting/vm/vm.h | 4 ++-- src/scripting/vm/vmbuilder.cpp | 1 + src/scripting/zscript/zcc_compile.cpp | 8 +++++--- 8 files changed, 22 insertions(+), 14 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 81ee907f4..66bdc652c 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -823,7 +823,9 @@ void SetDehParams(FState *state, int codepointer) VMScriptFunction *sfunc = new VMScriptFunction; buildit.MakeFunction(sfunc); sfunc->NumArgs = NAP; + sfunc->ImplicitArgs = NAP; state->SetAction(sfunc); + sfunc->PrintableName.Format("Dehacked.%s.%d.%d", MBFCodePointers[codepointer].name.GetChars(), value1, value2); } } diff --git a/src/dobjtype.h b/src/dobjtype.h index e6f2a491b..c5d96972b 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -719,6 +719,12 @@ public: PClass *OwningClass = nullptr; unsigned AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl, int flags); + int GetImplicitArgs() + { + if (Variants[0].Flags & VARF_Action) return 3; + else if (Variants[0].Flags & VARF_Method) return 1; + return 0; + } size_t PropagateMark(); diff --git a/src/info.cpp b/src/info.cpp index 44f485e6c..5e267b39c 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -94,13 +94,13 @@ bool FState::CallAction(AActor *self, AActor *stateowner, FStateParamInfo *info, } if (stateret == NULL) { - stack.Call(ActionFunc, params, countof(params), NULL, 0, NULL); + stack.Call(ActionFunc, params, ActionFunc->ImplicitArgs, NULL, 0, NULL); } else { VMReturn ret; ret.PointerAt((void **)stateret); - stack.Call(ActionFunc, params, countof(params), &ret, 1, NULL); + stack.Call(ActionFunc, params, ActionFunc->ImplicitArgs, &ret, 1, NULL); } ActionCycles.Unclock(); return true; diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index c8e110a68..bbeeca374 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -168,7 +168,7 @@ bool ACustomInventory::CallStateChain (AActor *actor, FState *state) numret = 2; } } - stack.Call(state->ActionFunc, params, countof(params), wantret, numret); + stack.Call(state->ActionFunc, params, state->ActionFunc->ImplicitArgs, wantret, numret); // As long as even one state succeeds, the whole chain succeeds unless aborted below. // A state that wants to jump does not count as "succeeded". if (nextstate == NULL) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index dce724a32..1de5c13c2 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5196,11 +5196,11 @@ PPrototype *FxVMFunctionCall::ReturnProto() VMFunction *FxVMFunctionCall::GetDirectFunction() { - // If this return statement calls a function with no arguments, + // If this return statement calls a non-virtual function with no arguments, // then it can be a "direct" function. That is, the DECORATE // definition can call that function directly without wrapping // it inside VM code. - if ((ArgList ? ArgList->Size() : 0) == 0 && (Function->Variants[0].Flags & VARF_Action)) + if ((ArgList ? ArgList->Size() : 0) == 0 && !(Function->Variants[0].Flags & VARF_Virtual)) { return Function->Variants[0].Implementation; } @@ -5222,10 +5222,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) auto proto = Function->Variants[0].Proto; auto argtypes = proto->ArgumentTypes; - int implicit; - if (Function->Variants[0].Flags & VARF_Action) implicit = 3; - else if (Function->Variants[0].Flags & VARF_Method) implicit = 1; - else implicit = 0; + int implicit = Function->GetImplicitArgs(); // This should never happen. if (Self == nullptr && !(Function->Variants[0].Flags & VARF_Static)) diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index b9dafde0c..a37b7449b 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -179,12 +179,12 @@ class VMFunction : public DObject HAS_OBJECT_POINTERS; public: bool Native; + BYTE ImplicitArgs = 0; // either 0 for static, 1 for method or 3 for action FName Name; class PPrototype *Proto; - VMFunction() : Native(false), Name(NAME_None), Proto(NULL) {} - VMFunction(FName name) : Native(false), Name(name), Proto(NULL) {} + VMFunction(FName name = NAME_None) : Native(false), ImplicitArgs(0), Name(name), Proto(NULL) {} }; enum EVMOpMode diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index a5f15b262..b58de0ea4 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -665,6 +665,7 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c it.Code = code; it.PrintableName = name; it.Function = new VMScriptFunction; + it.Function->ImplicitArgs = functype->GetImplicitArgs(); it.Proto = nullptr; it.FromDecorate = fromdecorate; mItems.Push(it); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index ba038a716..9b4212820 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1951,14 +1951,15 @@ void ZCCCompiler::InitFunctions() f->Flags &= notallowed; } uint32_t varflags = VARF_Method; + int implicitargs = 1; AFuncDesc *afd = nullptr; // map to implementation flags. if (f->Flags & ZCC_Private) varflags |= VARF_Private; if (f->Flags & ZCC_Protected) varflags |= VARF_Protected; if (f->Flags & ZCC_Deprecated) varflags |= VARF_Deprecated; - if (f->Flags & ZCC_Action) varflags |= VARF_Action|VARF_Final; // Action implies Final. - if (f->Flags & ZCC_Static) varflags = (varflags & ~VARF_Method) | VARF_Final; // Static implies Final. + if (f->Flags & ZCC_Action) varflags |= VARF_Action|VARF_Final, implicitargs = 3; // Action implies Final. + if (f->Flags & ZCC_Static) varflags = (varflags & ~VARF_Method) | VARF_Final, implicitargs = 0; // Static implies Final. if ((f->Flags & (ZCC_Action | ZCC_Static)) == (ZCC_Action | ZCC_Static)) { Error(f, "%s: Action and Static on the same function is not allowed.", FName(f->Name).GetChars()); @@ -1973,6 +1974,7 @@ void ZCCCompiler::InitFunctions() { Error(f, "The function '%s' has not been exported from the executable.", FName(f->Name).GetChars()); } + (*afd->VMPointer)->ImplicitArgs = BYTE(implicitargs); } SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags); auto p = f->Params; @@ -2063,7 +2065,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a PFunction *afd = dyn_cast(cls->Symbols.FindSymbol(id->Identifier, true)); if (afd != nullptr) { - if (fc->Parameters == nullptr && (afd->Variants[0].Flags & VARF_Action)) + if (fc->Parameters == nullptr && !(afd->Variants[0].Flags & VARF_Virtual)) { // We can use this function directly without wrapping it in a caller. return new FxVMFunctionCall(new FxSelf(*af), afd, nullptr, *af, false); From 32ac1a8ad7613baf369bb0e5d3780c72ee4b2d69 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 16:46:47 +0200 Subject: [PATCH 090/255] - moved the special weapon functions from Inventory to StateProvider. This will restrict them to the only classes that may use them: Weapon and CustomInventory. Note: Should a mod surface which uses them improperly the better solution would be a warning message and NULLing the bogus code pointer instead of leaving them in Inventory. --- src/d_dehacked.cpp | 8 +-- wadsrc/static/zscript/shared/inventory.txt | 63 +++++++++++----------- 2 files changed, 35 insertions(+), 36 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 66bdc652c..71deb0169 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -797,7 +797,7 @@ void SetDehParams(FState *state, int codepointer) // Let's identify the codepointer we're dealing with. PFunction *sym; - sym = dyn_cast(RUNTIME_CLASS(AInventory)->Symbols.FindSymbol(FName(MBFCodePointers[codepointer].name), true)); + sym = dyn_cast(RUNTIME_CLASS(AStateProvider)->Symbols.FindSymbol(FName(MBFCodePointers[codepointer].name), true)); if (sym == NULL) return; if (codepointer < 0 || (unsigned)codepointer >= countof(MBFCodePointerFactories)) @@ -2113,7 +2113,7 @@ static int PatchCodePtrs (int dummy) // This skips the action table and goes directly to the internal symbol table // DEH compatible functions are easy to recognize. - PFunction *sym = dyn_cast(RUNTIME_CLASS(AInventory)->Symbols.FindSymbol(symname, true)); + PFunction *sym = dyn_cast(RUNTIME_CLASS(AStateProvider)->Symbols.FindSymbol(symname, true)); if (sym == NULL) { Printf("Frame %d: Unknown code pointer '%s'\n", frame, Line2); @@ -2721,11 +2721,11 @@ static bool LoadDehSupp () } else { - // all relevant code pointers are either defined in AInventory + // all relevant code pointers are either defined in AStateProvider // or AActor so this will find all of them. FString name = "A_"; name << sc.String; - PFunction *sym = dyn_cast(RUNTIME_CLASS(AInventory)->Symbols.FindSymbol(name, true)); + PFunction *sym = dyn_cast(RUNTIME_CLASS(AStateProvider)->Symbols.FindSymbol(name, true)); if (sym == NULL) { sc.ScriptError("Unknown code pointer '%s'", sc.String); diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index bf2f7e188..80771e1a1 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -10,6 +10,37 @@ class Inventory : Actor native Inventory.PickupMessage "$TXT_DEFAULTPICKUPMSG"; } + // These are regular functions for the item itself. + private action native void A_RestoreSpecialPosition(); + private action native void A_RestoreSpecialDoomThing(); + private action native void A_RestoreSpecialThing1(); + private action native void A_RestoreSpecialThing2(); + + States + { + HideDoomish: + TNT1 A 1050; + TNT1 A 0 A_RestoreSpecialPosition; + TNT1 A 1 A_RestoreSpecialDoomThing; + Stop; + HideSpecial: + ACLO E 1400; + ACLO A 0 A_RestoreSpecialPosition; + ACLO A 4 A_RestoreSpecialThing1; + ACLO BABCBCDC 4; + ACLO D 4 A_RestoreSpecialThing2; + Stop; + Held: + TNT1 A -1; + Stop; + HoldAndDestroy: + TNT1 A 1; + Stop; + } +} + +class StateProvider : Inventory native +{ action native state A_JumpIfNoAmmo(state label); action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = "", sound MissSound = ""); action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); @@ -47,38 +78,6 @@ class Inventory : Actor native action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); action native state A_CheckForReload(int counter, state label, bool dontincrement = false); action native void A_ResetReloadCounter(); - - // These are regular functions for the item itself. - private action native void A_RestoreSpecialPosition(); - private action native void A_RestoreSpecialDoomThing(); - private action native void A_RestoreSpecialThing1(); - private action native void A_RestoreSpecialThing2(); - - States - { - HideDoomish: - TNT1 A 1050; - TNT1 A 0 A_RestoreSpecialPosition; - TNT1 A 1 A_RestoreSpecialDoomThing; - Stop; - HideSpecial: - ACLO E 1400; - ACLO A 0 A_RestoreSpecialPosition; - ACLO A 4 A_RestoreSpecialThing1; - ACLO BABCBCDC 4; - ACLO D 4 A_RestoreSpecialThing2; - Stop; - Held: - TNT1 A -1; - Stop; - HoldAndDestroy: - TNT1 A 1; - Stop; - } -} - -class StateProvider : Inventory native -{ } class ScoreItem : Inventory native From 371712c53a92cdce5bc2ac0e7b41306d884a4836 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 17:49:08 +0200 Subject: [PATCH 091/255] - turned everything I could into non-action functions. - fixed emission of the self pointer in FxVMFunctionCall. I did not realize that the self expression only sets up a register for the value, not pushing it onto the stack. --- src/g_doom/a_arachnotron.cpp | 4 +- src/g_doom/a_archvile.cpp | 12 +- src/g_doom/a_bossbrain.cpp | 16 +- src/g_doom/a_bruiser.cpp | 2 +- src/g_doom/a_cacodemon.cpp | 2 +- src/g_doom/a_cyberdemon.cpp | 4 +- src/g_doom/a_demon.cpp | 2 +- src/g_doom/a_doomimp.cpp | 2 +- src/g_doom/a_doommisc.cpp | 2 +- src/g_doom/a_doomweaps.cpp | 38 +- src/g_doom/a_fatso.cpp | 10 +- src/g_doom/a_keen.cpp | 2 +- src/g_doom/a_lostsoul.cpp | 4 +- src/g_doom/a_painelemental.cpp | 6 +- src/g_doom/a_possessed.cpp | 10 +- src/g_doom/a_revenant.cpp | 8 +- src/g_doom/a_scriptedmarine.cpp | 34 +- src/g_doom/a_spidermaster.cpp | 4 +- src/g_heretic/a_chicken.cpp | 10 +- src/g_heretic/a_dsparil.cpp | 20 +- src/g_heretic/a_hereticartifacts.cpp | 2 +- src/g_heretic/a_hereticimp.cpp | 8 +- src/g_heretic/a_hereticmisc.cpp | 14 +- src/g_heretic/a_hereticweaps.cpp | 54 +-- src/g_heretic/a_ironlich.cpp | 8 +- src/g_heretic/a_knight.cpp | 4 +- src/g_heretic/a_wizard.cpp | 8 +- src/g_hexen/a_bats.cpp | 6 +- src/g_hexen/a_bishop.cpp | 18 +- src/g_hexen/a_blastradius.cpp | 2 +- src/g_hexen/a_centaur.cpp | 2 +- src/g_hexen/a_clericflame.cpp | 8 +- src/g_hexen/a_clericholy.cpp | 14 +- src/g_hexen/a_clericmace.cpp | 2 +- src/g_hexen/a_clericstaff.cpp | 10 +- src/g_hexen/a_dragon.cpp | 14 +- src/g_hexen/a_fighteraxe.cpp | 12 +- src/g_hexen/a_fighterhammer.cpp | 4 +- src/g_hexen/a_fighterplayer.cpp | 2 +- src/g_hexen/a_fighterquietus.cpp | 6 +- src/g_hexen/a_firedemon.cpp | 10 +- src/g_hexen/a_flechette.cpp | 10 +- src/g_hexen/a_flies.cpp | 4 +- src/g_hexen/a_fog.cpp | 4 +- src/g_hexen/a_heresiarch.cpp | 26 +- src/g_hexen/a_hexenspecialdecs.cpp | 24 +- src/g_hexen/a_iceguy.cpp | 10 +- src/g_hexen/a_korax.cpp | 16 +- src/g_hexen/a_magecone.cpp | 4 +- src/g_hexen/a_magelightning.cpp | 14 +- src/g_hexen/a_magestaff.cpp | 8 +- src/g_hexen/a_pig.cpp | 4 +- src/g_hexen/a_serpent.cpp | 26 +- src/g_hexen/a_spike.cpp | 10 +- src/g_hexen/a_summon.cpp | 2 +- src/g_hexen/a_teleportother.cpp | 10 +- src/g_hexen/a_wraith.cpp | 14 +- src/g_raven/a_minotaur.cpp | 20 +- src/g_shared/a_action.cpp | 46 +-- src/g_shared/a_bridge.cpp | 4 +- src/g_shared/a_pickups.cpp | 8 +- src/g_shared/a_specialspot.cpp | 2 +- src/g_shared/a_weapons.cpp | 4 +- src/g_strife/a_acolyte.cpp | 8 +- src/g_strife/a_alienspectres.cpp | 8 +- src/g_strife/a_crusader.cpp | 10 +- src/g_strife/a_entityboss.cpp | 8 +- src/g_strife/a_inquisitor.cpp | 12 +- src/g_strife/a_loremaster.cpp | 2 +- src/g_strife/a_oracle.cpp | 2 +- src/g_strife/a_programmer.cpp | 8 +- src/g_strife/a_reaver.cpp | 2 +- src/g_strife/a_rebels.cpp | 4 +- src/g_strife/a_sentinel.cpp | 6 +- src/g_strife/a_spectral.cpp | 8 +- src/g_strife/a_stalker.cpp | 10 +- src/g_strife/a_strifeitems.cpp | 2 +- src/g_strife/a_strifestuff.cpp | 30 +- src/g_strife/a_strifeweapons.cpp | 56 +-- src/g_strife/a_templar.cpp | 2 +- src/g_strife/a_thingstoblowup.cpp | 8 +- src/info.h | 4 +- src/p_actionfunctions.cpp | 116 +++--- src/p_enemy.cpp | 44 +-- src/p_pspr.cpp | 38 +- src/p_user.cpp | 6 +- src/scripting/codegeneration/codegen.cpp | 53 +-- wadsrc/static/zscript/actor.txt | 342 +++++++++--------- wadsrc/static/zscript/doom/scriptedmarine.txt | 32 +- wadsrc/static/zscript/heretic/chicken.txt | 6 +- wadsrc/static/zscript/heretic/dsparil.txt | 20 +- .../zscript/heretic/hereticartifacts.txt | 2 +- wadsrc/static/zscript/heretic/hereticimp.txt | 8 +- wadsrc/static/zscript/heretic/hereticmisc.txt | 14 +- .../static/zscript/heretic/hereticweaps.txt | 54 +-- wadsrc/static/zscript/heretic/ironlich.txt | 8 +- wadsrc/static/zscript/heretic/knight.txt | 4 +- wadsrc/static/zscript/heretic/wizard.txt | 8 +- wadsrc/static/zscript/hexen/bats.txt | 6 +- wadsrc/static/zscript/hexen/bishop.txt | 14 +- wadsrc/static/zscript/hexen/clericboss.txt | 2 +- wadsrc/static/zscript/hexen/clericflame.txt | 8 +- wadsrc/static/zscript/hexen/clericholy.txt | 12 +- wadsrc/static/zscript/hexen/clericmace.txt | 2 +- wadsrc/static/zscript/hexen/clericstaff.txt | 8 +- wadsrc/static/zscript/hexen/dragon.txt | 14 +- wadsrc/static/zscript/hexen/fighteraxe.txt | 12 +- wadsrc/static/zscript/hexen/fighterboss.txt | 2 +- wadsrc/static/zscript/hexen/fighterfist.txt | 2 +- wadsrc/static/zscript/hexen/fighterhammer.txt | 4 +- .../static/zscript/hexen/fighterquietus.txt | 4 +- wadsrc/static/zscript/hexen/firedemon.txt | 10 +- wadsrc/static/zscript/hexen/flechette.txt | 14 +- wadsrc/static/zscript/hexen/flies.txt | 4 +- wadsrc/static/zscript/hexen/fog.txt | 4 +- wadsrc/static/zscript/hexen/heresiarch.txt | 26 +- .../static/zscript/hexen/hexenspecialdecs.txt | 22 +- wadsrc/static/zscript/hexen/iceguy.txt | 8 +- wadsrc/static/zscript/hexen/korax.txt | 16 +- wadsrc/static/zscript/hexen/mageboss.txt | 2 +- wadsrc/static/zscript/hexen/magecone.txt | 4 +- wadsrc/static/zscript/hexen/magelightning.txt | 14 +- wadsrc/static/zscript/hexen/magestaff.txt | 6 +- wadsrc/static/zscript/hexen/pig.txt | 2 +- wadsrc/static/zscript/hexen/serpent.txt | 26 +- wadsrc/static/zscript/hexen/spike.txt | 10 +- wadsrc/static/zscript/hexen/summon.txt | 2 +- wadsrc/static/zscript/hexen/teleportother.txt | 10 +- wadsrc/static/zscript/hexen/wraith.txt | 14 +- wadsrc/static/zscript/raven/minotaur.txt | 20 +- wadsrc/static/zscript/shared/bridge.txt | 4 +- wadsrc/static/zscript/shared/ice.txt | 2 +- wadsrc/static/zscript/shared/inventory.txt | 50 +-- wadsrc/static/zscript/shared/specialspot.txt | 2 +- wadsrc/static/zscript/strife/acolyte.txt | 8 +- .../static/zscript/strife/alienspectres.txt | 2 +- wadsrc/static/zscript/strife/crusader.txt | 10 +- wadsrc/static/zscript/strife/entityboss.txt | 8 +- wadsrc/static/zscript/strife/inquisitor.txt | 14 +- wadsrc/static/zscript/strife/loremaster.txt | 2 +- wadsrc/static/zscript/strife/oracle.txt | 2 +- wadsrc/static/zscript/strife/programmer.txt | 8 +- wadsrc/static/zscript/strife/reaver.txt | 2 +- wadsrc/static/zscript/strife/rebels.txt | 2 +- wadsrc/static/zscript/strife/sentinel.txt | 2 +- wadsrc/static/zscript/strife/sigil.txt | 20 +- wadsrc/static/zscript/strife/spectral.txt | 14 +- wadsrc/static/zscript/strife/stalker.txt | 10 +- wadsrc/static/zscript/strife/strifeplayer.txt | 6 +- .../static/zscript/strife/strifeweapons.txt | 28 +- wadsrc/static/zscript/strife/templar.txt | 2 +- .../static/zscript/strife/thingstoblowup.txt | 6 +- 152 files changed, 1051 insertions(+), 1072 deletions(-) diff --git a/src/g_doom/a_arachnotron.cpp b/src/g_doom/a_arachnotron.cpp index e558b05b2..22223d24b 100644 --- a/src/g_doom/a_arachnotron.cpp +++ b/src/g_doom/a_arachnotron.cpp @@ -9,7 +9,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BspiAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -23,7 +23,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BspiAttack) DEFINE_ACTION_FUNCTION(AActor, A_BabyMetal) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "baby/walk", 1, ATTN_IDLE); A_Chase (stack, self); return 0; diff --git a/src/g_doom/a_archvile.cpp b/src/g_doom/a_archvile.cpp index 06be5cc0c..b63564654 100644 --- a/src/g_doom/a_archvile.cpp +++ b/src/g_doom/a_archvile.cpp @@ -21,7 +21,7 @@ void A_Fire(AActor *self, double height); // DEFINE_ACTION_FUNCTION(AActor, A_VileStart) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_VOICE, "vile/start", 1, ATTN_NORM); return 0; } @@ -33,7 +33,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_VileStart) // DEFINE_ACTION_FUNCTION(AActor, A_StartFire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "vile/firestrt", 1, ATTN_NORM); A_Fire (self, 0); return 0; @@ -41,7 +41,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_StartFire) DEFINE_ACTION_FUNCTION(AActor, A_FireCrackle) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "vile/firecrkl", 1, ATTN_NORM); A_Fire (self, 0); return 0; @@ -49,7 +49,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrackle) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Fire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(height) { height = 0; } A_Fire(self, height); @@ -80,7 +80,7 @@ void A_Fire(AActor *self, double height) // DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileTarget) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(fire, AActor) { fire = PClass::FindActor("ArchvileFire"); } AActor *fog; @@ -111,7 +111,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileTarget) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_SOUND_OPT (snd) { snd = "vile/stop"; } PARAM_INT_OPT (dmg) { dmg = 20; } PARAM_INT_OPT (blastdmg) { blastdmg = 70; } diff --git a/src/g_doom/a_bossbrain.cpp b/src/g_doom/a_bossbrain.cpp index 8d4163c09..84cd9040c 100644 --- a/src/g_doom/a_bossbrain.cpp +++ b/src/g_doom/a_bossbrain.cpp @@ -18,7 +18,7 @@ static FRandom pr_spawnfly ("SpawnFly"); DEFINE_ACTION_FUNCTION(AActor, A_BrainAwake) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // killough 3/26/98: only generates sound now S_Sound (self, CHAN_VOICE, "brain/sight", 1, ATTN_NONE); return 0; @@ -26,7 +26,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainAwake) DEFINE_ACTION_FUNCTION(AActor, A_BrainPain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_VOICE, "brain/pain", 1, ATTN_NONE); return 0; } @@ -56,7 +56,7 @@ static void BrainishExplosion (const DVector3 &pos) DEFINE_ACTION_FUNCTION(AActor, A_BrainScream) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); for (double x = -196; x < +320; x += 8) { @@ -69,7 +69,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainScream) DEFINE_ACTION_FUNCTION(AActor, A_BrainExplode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double x = pr_brainexplode.Random2() / 32.; DVector3 pos = self->Vec2OffsetZ(x, 0, 1 / 512. + pr_brainexplode() * 2); BrainishExplosion(pos); @@ -78,7 +78,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainExplode) DEFINE_ACTION_FUNCTION(AActor, A_BrainDie) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // [RH] If noexit, then don't end the level. if ((deathmatch || alwaysapplydmflags) && (dmflags & DF_NO_EXIT)) @@ -111,7 +111,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainDie) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BrainSpit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } DSpotState *state = DSpotState::GetSpotState(); @@ -297,7 +297,7 @@ static void SpawnFly(AActor *self, PClassActor *spawntype, FSoundID sound) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnFly) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; } FSoundID sound; @@ -318,7 +318,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnFly) // travelling cube sound DEFINE_ACTION_FUNCTION(AActor, A_SpawnSound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "brain/cube", 1, ATTN_IDLE); SpawnFly(self, PClass::FindActor("SpawnFire"), "brain/spawn"); return 0; diff --git a/src/g_doom/a_bruiser.cpp b/src/g_doom/a_bruiser.cpp index 0d2f83aee..1d2be64f0 100644 --- a/src/g_doom/a_bruiser.cpp +++ b/src/g_doom/a_bruiser.cpp @@ -3,7 +3,7 @@ static FRandom pr_bruisattack ("BruisAttack"); DEFINE_ACTION_FUNCTION(AActor, A_BruisAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_doom/a_cacodemon.cpp b/src/g_doom/a_cacodemon.cpp index 775580c29..354443bd6 100644 --- a/src/g_doom/a_cacodemon.cpp +++ b/src/g_doom/a_cacodemon.cpp @@ -14,7 +14,7 @@ static FRandom pr_headattack ("HeadAttack"); DEFINE_ACTION_FUNCTION(AActor, A_HeadAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_doom/a_cyberdemon.cpp b/src/g_doom/a_cyberdemon.cpp index 55d9181bf..6e78759c3 100644 --- a/src/g_doom/a_cyberdemon.cpp +++ b/src/g_doom/a_cyberdemon.cpp @@ -9,7 +9,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CyberAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -21,7 +21,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CyberAttack) DEFINE_ACTION_FUNCTION(AActor, A_Hoof) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "cyber/hoof", 1, ATTN_IDLE); A_Chase (stack, self); diff --git a/src/g_doom/a_demon.cpp b/src/g_doom/a_demon.cpp index 330b02b30..5ac3e9e74 100644 --- a/src/g_doom/a_demon.cpp +++ b/src/g_doom/a_demon.cpp @@ -13,7 +13,7 @@ static FRandom pr_sargattack ("SargAttack"); DEFINE_ACTION_FUNCTION(AActor, A_SargAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_doom/a_doomimp.cpp b/src/g_doom/a_doomimp.cpp index 6130d39ca..1b9dd9485 100644 --- a/src/g_doom/a_doomimp.cpp +++ b/src/g_doom/a_doomimp.cpp @@ -17,7 +17,7 @@ static FRandom pr_troopattack ("TroopAttack"); // DEFINE_ACTION_FUNCTION(AActor, A_TroopAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index b68ded59d..a4eca67b7 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -44,7 +44,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BarrelDestroy) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (dmflags2 & DF2_BARRELS_RESPAWN) { diff --git a/src/g_doom/a_doomweaps.cpp b/src/g_doom/a_doomweaps.cpp index fd60e85d8..f7511b2be 100644 --- a/src/g_doom/a_doomweaps.cpp +++ b/src/g_doom/a_doomweaps.cpp @@ -28,7 +28,7 @@ static FRandom pr_oldbfg ("OldBFG"); // DEFINE_ACTION_FUNCTION(AActor, A_Punch) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; @@ -69,7 +69,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Punch) // DEFINE_ACTION_FUNCTION(AActor, A_FirePistol) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); bool accurate; @@ -115,7 +115,7 @@ enum SAW_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_SOUND_OPT (fullsound) { fullsound = "weapons/sawfull"; } PARAM_SOUND_OPT (hitsound) { hitsound = "weapons/sawhit"; } PARAM_INT_OPT (damage) { damage = 2; } @@ -257,7 +257,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw) // DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); int i; player_t *player; @@ -291,7 +291,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun) // DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun2) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); int i; DAngle angle; @@ -338,21 +338,21 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun2) DEFINE_ACTION_FUNCTION(AActor, A_OpenShotgun2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/sshoto", 1, ATTN_NORM); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_LoadShotgun2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/sshotl", 1, ATTN_NORM); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_CloseShotgun2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/sshotc", 1, ATTN_NORM); A_ReFire (self); return 0; @@ -411,7 +411,7 @@ void P_SetSafeFlash(AWeapon *weapon, player_t *player, FState *flashstate, int i // DEFINE_ACTION_FUNCTION(AActor, A_FireCGun) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -456,7 +456,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCGun) // DEFINE_ACTION_FUNCTION(AActor, A_FireMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -479,7 +479,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMissile) // DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireSTGrenade) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS_OPT(grenade, AActor) { grenade = PClass::FindActor("Grenade"); } player_t *player; @@ -511,7 +511,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireSTGrenade) // DEFINE_ACTION_FUNCTION(AActor, A_FirePlasma) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -574,21 +574,21 @@ static void FireRailgun(AActor *self, int offset_xy, bool fromweapon) DEFINE_ACTION_FUNCTION(AActor, A_FireRailgun) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); FireRailgun(self, 0, ACTION_CALL_FROM_PSPRITE()); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_FireRailgunRight) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); FireRailgun(self, 10, ACTION_CALL_FROM_PSPRITE()); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_FireRailgunLeft) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); FireRailgun(self, -10, ACTION_CALL_FROM_PSPRITE()); return 0; } @@ -605,7 +605,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RailWait) DEFINE_ACTION_FUNCTION(AActor, A_FireBFG) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -638,7 +638,7 @@ enum BFG_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT (spraytype, AActor) { spraytype = NULL; } PARAM_INT_OPT (numrays) { numrays = 0; } PARAM_INT_OPT (damagecnt) { damagecnt = 0; } @@ -722,7 +722,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray) // DEFINE_ACTION_FUNCTION(AActor, A_BFGsound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/bfgf", 1, ATTN_NORM); return 0; } @@ -738,7 +738,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BFGsound) DEFINE_ACTION_FUNCTION(AActor, A_FireOldBFG) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PClassActor *plasma[] = { PClass::FindActor("PlasmaBall1"), PClass::FindActor("PlasmaBall2") }; AActor * mo = NULL; diff --git a/src/g_doom/a_fatso.cpp b/src/g_doom/a_fatso.cpp index eeef39984..d84046104 100644 --- a/src/g_doom/a_fatso.cpp +++ b/src/g_doom/a_fatso.cpp @@ -19,7 +19,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FatRaise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_FaceTarget (self); S_Sound (self, CHAN_WEAPON, "fatso/raiseguns", 1, ATTN_NORM); @@ -28,7 +28,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FatRaise) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } AActor *missile; @@ -54,7 +54,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack1) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } AActor *missile; @@ -80,7 +80,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack2) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack3) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } AActor *missile; @@ -122,7 +122,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Mushroom) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; } PARAM_INT_OPT (n) { n = 0; } PARAM_INT_OPT (flags) { flags = 0; } diff --git a/src/g_doom/a_keen.cpp b/src/g_doom/a_keen.cpp index 5c57128a3..3040e0545 100644 --- a/src/g_doom/a_keen.cpp +++ b/src/g_doom/a_keen.cpp @@ -16,7 +16,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KeenDie) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(doortag) { doortag = 666; } A_Unblock(self, false); diff --git a/src/g_doom/a_lostsoul.cpp b/src/g_doom/a_lostsoul.cpp index 35468ac08..18b8251e9 100644 --- a/src/g_doom/a_lostsoul.cpp +++ b/src/g_doom/a_lostsoul.cpp @@ -36,7 +36,7 @@ void A_SkullAttack(AActor *self, double speed) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(speed) { speed = SKULLSPEED; } if (speed <= 0) @@ -47,7 +47,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullAttack) DEFINE_ACTION_FUNCTION(AActor, A_BetaSkullAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int damage; if (!self || !self->target || self->target->GetSpecies() == self->GetSpecies()) diff --git a/src/g_doom/a_painelemental.cpp b/src/g_doom/a_painelemental.cpp index 8a0aa41bf..30136f9f7 100644 --- a/src/g_doom/a_painelemental.cpp +++ b/src/g_doom/a_painelemental.cpp @@ -147,7 +147,7 @@ void A_PainShootSkull (AActor *self, DAngle Angle, PClassActor *spawntype, int f // DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -165,7 +165,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DualPainAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } if (!self->target) @@ -179,7 +179,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DualPainAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainDie) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } if (self->target != NULL && self->IsFriend(self->target)) diff --git a/src/g_doom/a_possessed.cpp b/src/g_doom/a_possessed.cpp index e665e8f11..0b9a9ecfd 100644 --- a/src/g_doom/a_possessed.cpp +++ b/src/g_doom/a_possessed.cpp @@ -20,7 +20,7 @@ static FRandom pr_cposrefire ("CPosRefire"); // DEFINE_ACTION_FUNCTION(AActor, A_PosAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int damage; DAngle angle; @@ -60,7 +60,7 @@ static void A_SPosAttack2 (AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_SPosAttackUseAtkSound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -74,7 +74,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SPosAttackUseAtkSound) // meant for Dehacked only. DEFINE_ACTION_FUNCTION(AActor, A_SPosAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -86,7 +86,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SPosAttack) DEFINE_ACTION_FUNCTION(AActor, A_CPosAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; DAngle bangle; @@ -115,7 +115,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CPosAttack) DEFINE_ACTION_FUNCTION(AActor, A_CPosRefire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // keep firing unless target got out of sight A_FaceTarget (self); diff --git a/src/g_doom/a_revenant.cpp b/src/g_doom/a_revenant.cpp index adb0ea100..0ffaed753 100644 --- a/src/g_doom/a_revenant.cpp +++ b/src/g_doom/a_revenant.cpp @@ -20,7 +20,7 @@ static FRandom pr_skelfist ("SkelFist"); // DEFINE_ACTION_FUNCTION(AActor, A_SkelMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *missile; @@ -44,7 +44,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SkelMissile) DEFINE_ACTION_FUNCTION(AActor, A_Tracer) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double dist; double slope; @@ -123,7 +123,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Tracer) DEFINE_ACTION_FUNCTION(AActor, A_SkelWhoosh) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -134,7 +134,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SkelWhoosh) DEFINE_ACTION_FUNCTION(AActor, A_SkelFist) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_doom/a_scriptedmarine.cpp b/src/g_doom/a_scriptedmarine.cpp index 76f3e4577..61c7c8ac4 100644 --- a/src/g_doom/a_scriptedmarine.cpp +++ b/src/g_doom/a_scriptedmarine.cpp @@ -150,7 +150,7 @@ void AScriptedMarine::Tick () DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Refire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL_OPT(ignoremissile) { ignoremissile = false; } if (self->target == NULL || self->target->health <= 0) @@ -182,7 +182,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Refire) DEFINE_ACTION_FUNCTION(AActor, A_M_SawRefire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL || self->target->health <= 0) { @@ -204,7 +204,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_SawRefire) DEFINE_ACTION_FUNCTION(AActor, A_MarineNoise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (static_cast(self)->CurrentWeapon == AScriptedMarine::WEAPON_Chainsaw) { @@ -221,7 +221,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MarineNoise) DEFINE_ACTION_FUNCTION(AActor, A_MarineChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_MarineNoise, self); A_Chase (stack, self); return 0; @@ -235,7 +235,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MarineChase) DEFINE_ACTION_FUNCTION(AActor, A_MarineLook) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_MarineNoise, self); CALL_ACTION(A_Look, self); return 0; @@ -249,7 +249,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MarineLook) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Saw) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_SOUND_OPT (fullsound) { fullsound = "weapons/sawfull"; } PARAM_SOUND_OPT (hitsound) { hitsound = "weapons/sawhit"; } PARAM_INT_OPT (damage) { damage = 2; } @@ -347,7 +347,7 @@ static void MarinePunch(AActor *self, int damagemul) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Punch) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT(mult); MarinePunch(self, mult); @@ -384,7 +384,7 @@ void P_GunShot2 (AActor *mo, bool accurate, DAngle pitch, PClassActor *pufftype) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_FirePistol) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL(accurate); if (self->target == NULL) @@ -405,7 +405,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_FirePistol) DEFINE_ACTION_FUNCTION(AActor, A_M_FireShotgun) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle pitch; @@ -431,7 +431,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FireShotgun) DEFINE_ACTION_FUNCTION(AActor, A_M_CheckAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->special1 != 0 || self->target == NULL) { @@ -452,7 +452,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_CheckAttack) DEFINE_ACTION_FUNCTION(AActor, A_M_FireShotgun2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle pitch; @@ -483,7 +483,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FireShotgun2) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_FireCGun) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL(accurate); if (self->target == NULL) @@ -508,7 +508,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_FireCGun) DEFINE_ACTION_FUNCTION(AActor, A_M_FireMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -533,7 +533,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FireMissile) DEFINE_ACTION_FUNCTION(AActor, A_M_FireRailgun) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -551,7 +551,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FireRailgun) DEFINE_ACTION_FUNCTION(AActor, A_M_FirePlasma) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -570,7 +570,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FirePlasma) DEFINE_ACTION_FUNCTION(AActor, A_M_BFGsound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -597,7 +597,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_BFGsound) DEFINE_ACTION_FUNCTION(AActor, A_M_FireBFG) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; diff --git a/src/g_doom/a_spidermaster.cpp b/src/g_doom/a_spidermaster.cpp index ab12db4f0..37d0deb18 100644 --- a/src/g_doom/a_spidermaster.cpp +++ b/src/g_doom/a_spidermaster.cpp @@ -13,7 +13,7 @@ static FRandom pr_spidrefire ("SpidRefire"); DEFINE_ACTION_FUNCTION(AActor, A_SpidRefire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // keep firing unless target got out of sight A_FaceTarget (self); @@ -33,7 +33,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpidRefire) DEFINE_ACTION_FUNCTION(AActor, A_Metal) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "spider/walk", 1, ATTN_IDLE); A_Chase (stack, self); diff --git a/src/g_heretic/a_chicken.cpp b/src/g_heretic/a_chicken.cpp index 78eb7ca8d..883eac353 100644 --- a/src/g_heretic/a_chicken.cpp +++ b/src/g_heretic/a_chicken.cpp @@ -66,7 +66,7 @@ void AChickenPlayer::MorphPlayerThink () DEFINE_ACTION_FUNCTION(AActor, A_ChicAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) { @@ -89,7 +89,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ChicAttack) DEFINE_ACTION_FUNCTION(AActor, A_Feathers) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; int count; @@ -138,7 +138,7 @@ void P_UpdateBeak (AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_BeakRaise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -170,7 +170,7 @@ void P_PlayPeck (AActor *chicken) DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -205,7 +205,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL1) DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; diff --git a/src/g_heretic/a_dsparil.cpp b/src/g_heretic/a_dsparil.cpp index 632260648..5ab4067d3 100644 --- a/src/g_heretic/a_dsparil.cpp +++ b/src/g_heretic/a_dsparil.cpp @@ -28,7 +28,7 @@ static FRandom pr_bluespark ("BlueSpark"); DEFINE_ACTION_FUNCTION(AActor, A_Sor1Pain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special1 = 20; // Number of steps to walk fast CALL_ACTION(A_Pain, self); @@ -43,7 +43,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Sor1Pain) DEFINE_ACTION_FUNCTION(AActor, A_Sor1Chase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->special1) { @@ -64,7 +64,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Sor1Chase) DEFINE_ACTION_FUNCTION(AActor, A_Srcr1Attack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; DAngle angle; @@ -120,7 +120,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Srcr1Attack) DEFINE_ACTION_FUNCTION(AActor, A_SorcererRise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -173,7 +173,7 @@ void P_DSparilTeleport (AActor *actor) DEFINE_ACTION_FUNCTION(AActor, A_Srcr2Decide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); static const int chance[] = { @@ -201,7 +201,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Srcr2Decide) DEFINE_ACTION_FUNCTION(AActor, A_Srcr2Attack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int chance; @@ -243,7 +243,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Srcr2Attack) DEFINE_ACTION_FUNCTION(AActor, A_BlueSpark) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; AActor *mo; @@ -266,7 +266,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BlueSpark) DEFINE_ACTION_FUNCTION(AActor, A_GenWizard) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -301,7 +301,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_GenWizard) DEFINE_ACTION_FUNCTION(AActor, A_Sor2DthInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special1 = 7; // Animation loop counter P_Massacre (); // Kill monsters early @@ -316,7 +316,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Sor2DthInit) DEFINE_ACTION_FUNCTION(AActor, A_Sor2DthLoop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (--self->special1) { // Need to loop diff --git a/src/g_heretic/a_hereticartifacts.cpp b/src/g_heretic/a_hereticartifacts.cpp index 1c4677cb6..eceb2cfe1 100644 --- a/src/g_heretic/a_hereticartifacts.cpp +++ b/src/g_heretic/a_hereticartifacts.cpp @@ -47,7 +47,7 @@ bool AArtiTomeOfPower::Use (bool pickup) DEFINE_ACTION_FUNCTION(AActor, A_TimeBomb) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->AddZ(32, false); self->RenderStyle = STYLE_Add; diff --git a/src/g_heretic/a_hereticimp.cpp b/src/g_heretic/a_hereticimp.cpp index 41e207ef1..39dfb049e 100644 --- a/src/g_heretic/a_hereticimp.cpp +++ b/src/g_heretic/a_hereticimp.cpp @@ -21,7 +21,7 @@ static FRandom pr_imp ("ImpExplode"); DEFINE_ACTION_FUNCTION(AActor, A_ImpMsAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target || pr_impmsatk() > 64) { @@ -40,7 +40,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ImpMsAttack) DEFINE_ACTION_FUNCTION(AActor, A_ImpExplode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *chunk; @@ -70,7 +70,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ImpExplode) DEFINE_ACTION_FUNCTION(AActor, A_ImpDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~MF_SOLID; self->flags2 |= MF2_FLOORCLIP; @@ -85,7 +85,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ImpDeath) DEFINE_ACTION_FUNCTION(AActor, A_ImpXDeath1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~MF_SOLID; self->flags |= MF_NOGRAVITY; diff --git a/src/g_heretic/a_hereticmisc.cpp b/src/g_heretic/a_hereticmisc.cpp index d3ffbac23..02c1393dd 100644 --- a/src/g_heretic/a_hereticmisc.cpp +++ b/src/g_heretic/a_hereticmisc.cpp @@ -47,7 +47,7 @@ static FRandom pr_volcimpact ("VolcBallImpact"); DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PodPain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT (gootype, AActor) { gootype = PClass::FindActor("PodGoo"); } int count; @@ -78,7 +78,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PodPain) DEFINE_ACTION_FUNCTION(AActor, A_RemovePod) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -102,7 +102,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RemovePod) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MakePod) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(podtype, AActor) { podtype = PClass::FindActor("Pod"); } AActor *mo; @@ -133,7 +133,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MakePod) DEFINE_ACTION_FUNCTION(AActor, A_AccTeleGlitter) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (++self->health > 35) { @@ -151,7 +151,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_AccTeleGlitter) DEFINE_ACTION_FUNCTION(AActor, A_VolcanoSet) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->tics = 105 + (pr_volcano() & 127); return 0; @@ -165,7 +165,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_VolcanoSet) DEFINE_ACTION_FUNCTION(AActor, A_VolcanoBlast) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; int count; @@ -193,7 +193,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_VolcanoBlast) DEFINE_ACTION_FUNCTION(AActor, A_VolcBallImpact) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); unsigned int i; AActor *tiny; diff --git a/src/g_heretic/a_hereticweaps.cpp b/src/g_heretic/a_hereticweaps.cpp index c86cafce7..51d759640 100644 --- a/src/g_heretic/a_hereticweaps.cpp +++ b/src/g_heretic/a_hereticweaps.cpp @@ -61,7 +61,7 @@ extern bool P_AutoUseChaosDevice (player_t *player); DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StaffAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; DAngle slope; @@ -107,7 +107,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StaffAttack) DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -144,7 +144,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL1) DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; DAngle angle; @@ -187,7 +187,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL2) DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -216,7 +216,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL1) DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -247,7 +247,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL2) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GauntletAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle Angle; int damage; @@ -421,7 +421,7 @@ void FireMacePL1B (AActor *actor) DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *ball; player_t *player; @@ -461,7 +461,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL1) DEFINE_ACTION_FUNCTION(AActor, A_MacePL1Check) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->special1 == 0) { @@ -498,7 +498,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MacePL1Check) DEFINE_ACTION_FUNCTION(AActor, A_MaceBallImpact) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if ((self->health != MAGIC_JUNK) && (self->flags & MF_INBOUNCE)) { // Bounce @@ -526,7 +526,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MaceBallImpact) DEFINE_ACTION_FUNCTION(AActor, A_MaceBallImpact2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *tiny; @@ -579,7 +579,7 @@ boom: DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -618,7 +618,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL2) DEFINE_ACTION_FUNCTION(AActor, A_DeathBallImpact) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; AActor *target; @@ -761,7 +761,7 @@ int ARipper::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_FireBlasterPL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -798,7 +798,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireBlasterPL1) DEFINE_ACTION_FUNCTION(AActor, A_SpawnRippers) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); unsigned int i; DAngle angle; @@ -888,7 +888,7 @@ void ARainTracker::Serialize(FSerializer &arc) DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -924,7 +924,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL1) DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; AActor *MissileActor; @@ -964,7 +964,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL2) DEFINE_ACTION_FUNCTION(AActor, A_AddPlayerRain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); ARainTracker *tracker; @@ -1024,7 +1024,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_AddPlayerRain) DEFINE_ACTION_FUNCTION(AActor, A_SkullRodStorm) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; ARainTracker *tracker; @@ -1095,7 +1095,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SkullRodStorm) DEFINE_ACTION_FUNCTION(AActor, A_RainImpact) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->Z() > self->floorz) { self->SetState (self->FindState("NotFloor")); @@ -1115,7 +1115,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RainImpact) DEFINE_ACTION_FUNCTION(AActor, A_HideInCeiling) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // We use bouncecount to store the 3D floor index double foo; @@ -1218,7 +1218,7 @@ int APhoenixFX2::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -1246,7 +1246,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL1) DEFINE_ACTION_FUNCTION(AActor, A_PhoenixPuff) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *puff; DAngle angle; @@ -1271,7 +1271,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PhoenixPuff) DEFINE_ACTION_FUNCTION(AActor, A_InitPhoenixPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -1294,7 +1294,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_InitPhoenixPL2) DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -1347,7 +1347,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL2) DEFINE_ACTION_FUNCTION(AActor, A_ShutdownPhoenixPL2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -1373,7 +1373,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ShutdownPhoenixPL2) DEFINE_ACTION_FUNCTION(AActor, A_FlameEnd) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Vel.Z += 1.5; return 0; @@ -1387,7 +1387,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlameEnd) DEFINE_ACTION_FUNCTION(AActor, A_FloatPuff) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Vel.Z += 1.8; return 0; diff --git a/src/g_heretic/a_ironlich.cpp b/src/g_heretic/a_ironlich.cpp index c80a7bbed..e2e1cb021 100644 --- a/src/g_heretic/a_ironlich.cpp +++ b/src/g_heretic/a_ironlich.cpp @@ -63,7 +63,7 @@ int AWhirlwind::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_LichAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; AActor *fire; @@ -143,7 +143,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichAttack) DEFINE_ACTION_FUNCTION(AActor, A_WhirlwindSeek) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->health -= 3; if (self->health < 0) @@ -174,7 +174,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WhirlwindSeek) DEFINE_ACTION_FUNCTION(AActor, A_LichIceImpact) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); unsigned int i; AActor *shard; @@ -199,7 +199,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichIceImpact) DEFINE_ACTION_FUNCTION(AActor, A_LichFireGrow) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->health--; self->AddZ(9.); diff --git a/src/g_heretic/a_knight.cpp b/src/g_heretic/a_knight.cpp index 9c4ae2473..a3125f77d 100644 --- a/src/g_heretic/a_knight.cpp +++ b/src/g_heretic/a_knight.cpp @@ -21,7 +21,7 @@ static FRandom pr_knightatk ("KnightAttack"); DEFINE_ACTION_FUNCTION(AActor, A_DripBlood) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -42,7 +42,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DripBlood) DEFINE_ACTION_FUNCTION(AActor, A_KnightAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) { diff --git a/src/g_heretic/a_wizard.cpp b/src/g_heretic/a_wizard.cpp index e66bc5531..271fd5592 100644 --- a/src/g_heretic/a_wizard.cpp +++ b/src/g_heretic/a_wizard.cpp @@ -20,7 +20,7 @@ static FRandom pr_wizatk3 ("WizAtk3"); DEFINE_ACTION_FUNCTION(AActor, A_GhostOff) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->RenderStyle = STYLE_Normal; self->flags3 &= ~MF3_GHOST; @@ -35,7 +35,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_GhostOff) DEFINE_ACTION_FUNCTION(AActor, A_WizAtk1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_FaceTarget (self); CALL_ACTION(A_GhostOff, self); @@ -50,7 +50,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WizAtk1) DEFINE_ACTION_FUNCTION(AActor, A_WizAtk2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_FaceTarget (self); self->Alpha = HR_SHADOW; @@ -67,7 +67,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WizAtk2) DEFINE_ACTION_FUNCTION(AActor, A_WizAtk3) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; diff --git a/src/g_hexen/a_bats.cpp b/src/g_hexen/a_bats.cpp index 875910059..5be91b69b 100644 --- a/src/g_hexen/a_bats.cpp +++ b/src/g_hexen/a_bats.cpp @@ -27,7 +27,7 @@ static FRandom pr_batmove ("BatMove"); DEFINE_ACTION_FUNCTION(AActor, A_BatSpawnInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special1 = 0; // Frequency count return 0; @@ -35,7 +35,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatSpawnInit) DEFINE_ACTION_FUNCTION(AActor, A_BatSpawn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int delta; @@ -64,7 +64,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatSpawn) DEFINE_ACTION_FUNCTION(AActor, A_BatMove) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle newangle; diff --git a/src/g_hexen/a_bishop.cpp b/src/g_hexen/a_bishop.cpp index a88daa23b..bd9f24061 100644 --- a/src/g_hexen/a_bishop.cpp +++ b/src/g_hexen/a_bishop.cpp @@ -24,7 +24,7 @@ static FRandom pr_pain ("BishopPainBlur"); DEFINE_ACTION_FUNCTION(AActor, A_BishopAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) { @@ -51,7 +51,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopAttack) DEFINE_ACTION_FUNCTION(AActor, A_BishopAttack2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -78,7 +78,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopAttack2) DEFINE_ACTION_FUNCTION(AActor, A_BishopMissileWeave) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_Weave(self, 2, 2, 2., 1.); return 0; @@ -92,7 +92,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopMissileWeave) DEFINE_ACTION_FUNCTION(AActor, A_BishopDecide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (pr_decide() < 220) { @@ -113,7 +113,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopDecide) DEFINE_ACTION_FUNCTION(AActor, A_BishopDoBlur) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special1 = (pr_doblur() & 3) + 3; // Random number of blurs if (pr_doblur() < 120) @@ -140,7 +140,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopDoBlur) DEFINE_ACTION_FUNCTION(AActor, A_BishopSpawnBlur) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -172,7 +172,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopSpawnBlur) DEFINE_ACTION_FUNCTION(AActor, A_BishopChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double newz = self->Z() - BobSin(self->special2) / 2.; self->special2 = (self->special2 + 4) & 63; @@ -189,7 +189,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopChase) DEFINE_ACTION_FUNCTION(AActor, A_BishopPuff) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -209,7 +209,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopPuff) DEFINE_ACTION_FUNCTION(AActor, A_BishopPainBlur) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; diff --git a/src/g_hexen/a_blastradius.cpp b/src/g_hexen/a_blastradius.cpp index f906d247c..0b0ab5d10 100644 --- a/src/g_hexen/a_blastradius.cpp +++ b/src/g_hexen/a_blastradius.cpp @@ -95,7 +95,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS (AActor, A_Blast) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT_OPT (blastflags) { blastflags = 0; } PARAM_FLOAT_OPT (strength) { strength = 255; } PARAM_FLOAT_OPT (radius) { radius = 255; } diff --git a/src/g_hexen/a_centaur.cpp b/src/g_hexen/a_centaur.cpp index 75049650d..9bf5e6046 100644 --- a/src/g_hexen/a_centaur.cpp +++ b/src/g_hexen/a_centaur.cpp @@ -16,7 +16,7 @@ static FRandom pr_centaurdefend ("CentaurDefend"); DEFINE_ACTION_FUNCTION(AActor, A_CentaurDefend) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_FaceTarget (self); if (self->CheckMeleeRange() && pr_centaurdefend() < 32) diff --git a/src/g_hexen/a_clericflame.cpp b/src/g_hexen/a_clericflame.cpp index a9c8b6378..b03b9b6b9 100644 --- a/src/g_hexen/a_clericflame.cpp +++ b/src/g_hexen/a_clericflame.cpp @@ -66,7 +66,7 @@ void ACFlameMissile::Effect () DEFINE_ACTION_FUNCTION(AActor, A_CFlameAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -93,7 +93,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlameAttack) DEFINE_ACTION_FUNCTION(AActor, A_CFlamePuff) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags &= ~RF_INVISIBLE; self->Vel.Zero(); @@ -109,7 +109,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlamePuff) DEFINE_ACTION_FUNCTION(AActor, A_CFlameMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; DAngle an; @@ -159,7 +159,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlameMissile) DEFINE_ACTION_FUNCTION(AActor, A_CFlameRotate) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle an = self->Angles.Yaw + 90.; self->VelFromAngle(an, FLAMEROTSPEED); diff --git a/src/g_hexen/a_clericholy.cpp b/src/g_hexen/a_clericholy.cpp index f660b1e7d..b87bd3986 100644 --- a/src/g_hexen/a_clericholy.cpp +++ b/src/g_hexen/a_clericholy.cpp @@ -131,7 +131,7 @@ bool AHolySpirit::SpecialBlastHandling (AActor *source, double strength) DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int j; AActor *mo; @@ -211,7 +211,7 @@ void SpawnSpiritTail (AActor *spirit) DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; FTranslatedLineTarget t; @@ -245,7 +245,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack) DEFINE_ACTION_FUNCTION(AActor, A_CHolyPalette) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -328,7 +328,7 @@ static void CHolyTailRemove (AActor *actor) DEFINE_ACTION_FUNCTION(AActor, A_CHolyTail) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *parent; @@ -446,7 +446,7 @@ static void CHolySeekerMissile (AActor *actor, DAngle thresh, DAngle turnMax) DEFINE_ACTION_FUNCTION(AActor, A_CHolySeek) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->health--; if (self->health <= 0) @@ -481,7 +481,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolySeek) DEFINE_ACTION_FUNCTION(AActor, A_CHolyCheckScream) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_CHolySeek, self); if (pr_checkscream() < 20) @@ -504,7 +504,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyCheckScream) DEFINE_ACTION_FUNCTION(AActor, A_ClericAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_hexen/a_clericmace.cpp b/src/g_hexen/a_clericmace.cpp index fce979af1..9b8148930 100644 --- a/src/g_hexen/a_clericmace.cpp +++ b/src/g_hexen/a_clericmace.cpp @@ -15,7 +15,7 @@ static FRandom pr_maceatk ("CMaceAttack"); DEFINE_ACTION_FUNCTION(AActor, A_CMaceAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; diff --git a/src/g_hexen/a_clericstaff.cpp b/src/g_hexen/a_clericstaff.cpp index 6b54d4de3..a0e6b94c6 100644 --- a/src/g_hexen/a_clericstaff.cpp +++ b/src/g_hexen/a_clericstaff.cpp @@ -46,7 +46,7 @@ int ACStaffMissile::DoSpecialDamage (AActor *target, int damage, FName damagetyp DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheck) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); APlayerPawn *pmo; int damage; @@ -115,7 +115,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheck) DEFINE_ACTION_FUNCTION(AActor, A_CStaffAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -153,7 +153,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffAttack) DEFINE_ACTION_FUNCTION(AActor, A_CStaffMissileSlither) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_Weave(self, 3, 0, 1., 0.); return 0; @@ -167,7 +167,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffMissileSlither) DEFINE_ACTION_FUNCTION(AActor, A_CStaffInitBlink) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->weaponspecial = (pr_blink()>>1)+20; return 0; @@ -181,7 +181,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffInitBlink) DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheckBlink) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player && self->player->ReadyWeapon) { diff --git a/src/g_hexen/a_dragon.cpp b/src/g_hexen/a_dragon.cpp index ca56525a9..b79d92b36 100644 --- a/src/g_hexen/a_dragon.cpp +++ b/src/g_hexen/a_dragon.cpp @@ -150,7 +150,7 @@ static void DragonSeek (AActor *actor, DAngle thresh, DAngle turnMax) DEFINE_ACTION_FUNCTION(AActor, A_DragonInitFlight) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); FActorIterator iterator (self->tid); @@ -175,7 +175,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonInitFlight) DEFINE_ACTION_FUNCTION(AActor, A_DragonFlight) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; @@ -216,7 +216,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonFlight) DEFINE_ACTION_FUNCTION(AActor, A_DragonFlap) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_DragonFlight, self); if (pr_dragonflap() < 240) @@ -238,7 +238,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonFlap) DEFINE_ACTION_FUNCTION(AActor, A_DragonAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); P_SpawnMissile (self, self->target, PClass::FindActor("DragonFireball")); return 0; @@ -252,7 +252,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonAttack) DEFINE_ACTION_FUNCTION(AActor, A_DragonFX2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int i; @@ -283,7 +283,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonFX2) DEFINE_ACTION_FUNCTION(AActor, A_DragonPain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_Pain, self); if (!self->tracer) @@ -301,7 +301,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonPain) DEFINE_ACTION_FUNCTION(AActor, A_DragonCheckCrash) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->Z() <= self->floorz) { diff --git a/src/g_hexen/a_fighteraxe.cpp b/src/g_hexen/a_fighteraxe.cpp index a194869f3..696dda019 100644 --- a/src/g_hexen/a_fighteraxe.cpp +++ b/src/g_hexen/a_fighteraxe.cpp @@ -68,7 +68,7 @@ FState *AFWeapAxe::GetAtkState (bool hold) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReady) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -95,7 +95,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReady) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReadyG) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -122,7 +122,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReadyG) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUp) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -149,7 +149,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUp) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUpG) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -176,7 +176,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUpG) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckAtk) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -199,7 +199,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckAtk) DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int power; diff --git a/src/g_hexen/a_fighterhammer.cpp b/src/g_hexen/a_fighterhammer.cpp index f8fbe33e3..faa15d8af 100644 --- a/src/g_hexen/a_fighterhammer.cpp +++ b/src/g_hexen/a_fighterhammer.cpp @@ -25,7 +25,7 @@ static FRandom pr_hammeratk ("FHammerAtk"); DEFINE_ACTION_FUNCTION(AActor, A_FHammerAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -95,7 +95,7 @@ hammerdone: DEFINE_ACTION_FUNCTION(AActor, A_FHammerThrow) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; player_t *player; diff --git a/src/g_hexen/a_fighterplayer.cpp b/src/g_hexen/a_fighterplayer.cpp index d946c689c..020cec78e 100644 --- a/src/g_hexen/a_fighterplayer.cpp +++ b/src/g_hexen/a_fighterplayer.cpp @@ -99,7 +99,7 @@ static bool TryPunch(APlayerPawn *pmo, DAngle angle, int damage, int power) DEFINE_ACTION_FUNCTION(AActor, A_FPunchAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int damage; int i; diff --git a/src/g_hexen/a_fighterquietus.cpp b/src/g_hexen/a_fighterquietus.cpp index a86d4911a..6a4daabb2 100644 --- a/src/g_hexen/a_fighterquietus.cpp +++ b/src/g_hexen/a_fighterquietus.cpp @@ -78,7 +78,7 @@ int AFSwordMissile::DoSpecialDamage(AActor *victim, int damage, FName damagetype DEFINE_ACTION_FUNCTION(AActor, A_FSwordAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -109,7 +109,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FSwordAttack) DEFINE_ACTION_FUNCTION(AActor, A_FSwordFlames) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; @@ -131,7 +131,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FSwordFlames) DEFINE_ACTION_FUNCTION(AActor, A_FighterAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; diff --git a/src/g_hexen/a_firedemon.cpp b/src/g_hexen/a_firedemon.cpp index b60c904e3..cc9beaaeb 100644 --- a/src/g_hexen/a_firedemon.cpp +++ b/src/g_hexen/a_firedemon.cpp @@ -80,7 +80,7 @@ void A_FiredSpawnRock (AActor *actor) DEFINE_ACTION_FUNCTION(AActor, A_FiredRocks) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_FiredSpawnRock (self); A_FiredSpawnRock (self); @@ -98,7 +98,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FiredRocks) DEFINE_ACTION_FUNCTION(AActor, A_SmBounce) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // give some more velocity (x,y,&z) self->SetZ(self->floorz + 1); @@ -116,7 +116,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SmBounce) DEFINE_ACTION_FUNCTION(AActor, A_FiredAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -133,7 +133,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FiredAttack) DEFINE_ACTION_FUNCTION(AActor, A_FiredChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int weaveindex = self->special1; AActor *target = self->target; @@ -226,7 +226,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FiredChase) DEFINE_ACTION_FUNCTION(AActor, A_FiredSplotch) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; diff --git a/src/g_hexen/a_flechette.cpp b/src/g_hexen/a_flechette.cpp index 3d9555843..bc13d5cf7 100644 --- a/src/g_hexen/a_flechette.cpp +++ b/src/g_hexen/a_flechette.cpp @@ -362,7 +362,7 @@ int APoisonCloud::DoSpecialDamage (AActor *victim, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -382,7 +382,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagInit) DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagCheck) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (--self->special1 <= 0) { @@ -403,7 +403,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagCheck) DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagDamage) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int bobIndex; @@ -422,7 +422,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagDamage) DEFINE_ACTION_FUNCTION(AActor, A_CheckThrowBomb) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (--self->health <= 0) { @@ -439,7 +439,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CheckThrowBomb) DEFINE_ACTION_FUNCTION(AActor, A_CheckThrowBomb2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // [RH] Check using actual velocity, although the vel.z < 2 check still stands if (self->Vel.Z < 2 && self->Vel.LengthSquared() < (9./4.)) diff --git a/src/g_hexen/a_flies.cpp b/src/g_hexen/a_flies.cpp index 1023c12ae..7281dd8f2 100644 --- a/src/g_hexen/a_flies.cpp +++ b/src/g_hexen/a_flies.cpp @@ -60,7 +60,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlySearch) // So search the sectors instead. We can't potentially find something all // the way on the other side of the map and we can't find invisible corpses, // but at least we aren't crippled on maps with lots of stuff going on. - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); validcount++; AActor *other = FindCorpse(self, self->Sector, 5); @@ -74,7 +74,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlySearch) DEFINE_ACTION_FUNCTION(AActor, A_FlyBuzz) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *targ = self->target; diff --git a/src/g_hexen/a_fog.cpp b/src/g_hexen/a_fog.cpp index 98dbf62b7..6b2bc9706 100644 --- a/src/g_hexen/a_fog.cpp +++ b/src/g_hexen/a_fog.cpp @@ -27,7 +27,7 @@ static FRandom pr_fogspawn ("FogSpawn"); DEFINE_ACTION_FUNCTION(AActor, A_FogSpawn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); static const char *fogs[3] = { @@ -70,7 +70,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FogSpawn) DEFINE_ACTION_FUNCTION(AActor, A_FogMove) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double speed = self->args[0]; int weaveindex; diff --git a/src/g_hexen/a_heresiarch.cpp b/src/g_hexen/a_heresiarch.cpp index 267320029..03ffcc5d6 100644 --- a/src/g_hexen/a_heresiarch.cpp +++ b/src/g_hexen/a_heresiarch.cpp @@ -218,7 +218,7 @@ void ASorcBall1::DoFireSpell () DEFINE_ACTION_FUNCTION(AActor, A_SorcSpinBalls) { - PARAM_ACTION_PROLOGUE_TYPE(AHeresiarch); + PARAM_SELF_PROLOGUE(AHeresiarch); AActor *mo; @@ -254,7 +254,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcSpinBalls) DEFINE_ACTION_FUNCTION(AActor, A_SorcBallOrbit) { - PARAM_ACTION_PROLOGUE_TYPE(ASorcBall); + PARAM_SELF_PROLOGUE(ASorcBall); // [RH] If no parent, then die instead of crashing if (self->target == NULL) @@ -380,7 +380,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBallOrbit) DEFINE_ACTION_FUNCTION(AActor, A_SpeedBalls) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->args[3] = SORC_ACCELERATE; // speed mode self->args[2] = SORCBALL_TERMINAL_SPEED; // target speed @@ -676,7 +676,7 @@ void A_SorcOffense2(AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_SorcBossAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->args[3] = SORC_ACCELERATE; self->args[2] = SORCBALL_INITIAL_SPEED; @@ -693,7 +693,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBossAttack) DEFINE_ACTION_FUNCTION(AActor, A_SpawnFizzle) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int speed = (int)self->Speed; DAngle rangle; AActor *mo; @@ -725,7 +725,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpawnFizzle) DEFINE_ACTION_FUNCTION(AActor, A_SorcFX1Seek) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_DoBounceCheck (self, "SorcererHeadScream"); P_SeekerMissile(self, 2, 6); @@ -751,7 +751,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX1Seek) // Split ball in two DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Split) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -785,7 +785,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Split) DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Orbit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; DVector3 pos; @@ -852,7 +852,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Orbit) DEFINE_ACTION_FUNCTION(AActor, A_SpawnBishop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; mo = Spawn("Bishop", self->Pos(), ALLOW_REPLACE); @@ -881,7 +881,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpawnBishop) DEFINE_ACTION_FUNCTION(AActor, A_SorcererBishopEntry) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); Spawn("SorcFX3Explosion", self->Pos(), ALLOW_REPLACE); S_Sound (self, CHAN_VOICE, self->SeeSound, 1, ATTN_NORM); @@ -898,7 +898,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcererBishopEntry) DEFINE_ACTION_FUNCTION(AActor, A_SorcFX4Check) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->special2-- <= 0) { @@ -917,7 +917,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX4Check) DEFINE_ACTION_FUNCTION(AActor, A_SorcBallPop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "SorcererBallPop", 1, ATTN_NONE); self->flags &= ~MF_NOGRAVITY; @@ -961,7 +961,7 @@ void A_DoBounceCheck (AActor *self, const char *sound) DEFINE_ACTION_FUNCTION(AActor, A_BounceCheck) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_DoBounceCheck (self, "SorcererBigBallExplode"); return 0; diff --git a/src/g_hexen/a_hexenspecialdecs.cpp b/src/g_hexen/a_hexenspecialdecs.cpp index 61d5780d1..866fc8372 100644 --- a/src/g_hexen/a_hexenspecialdecs.cpp +++ b/src/g_hexen/a_hexenspecialdecs.cpp @@ -55,7 +55,7 @@ void APottery1::HitFloor () DEFINE_ACTION_FUNCTION(AActor, A_PotteryExplode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo = NULL; int i; @@ -93,7 +93,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PotteryExplode) DEFINE_ACTION_FUNCTION(AActor, A_PotteryChooseBit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->SetState (self->FindState(NAME_Death) + 1 + 2*(pr_bit()%5)); self->tics = 256+(pr_bit()<<1); @@ -108,7 +108,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PotteryChooseBit) DEFINE_ACTION_FUNCTION(AActor, A_PotteryCheck) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; @@ -152,7 +152,7 @@ void AZCorpseLynchedNoHeart::PostBeginPlay () DEFINE_ACTION_FUNCTION(AActor, A_CorpseBloodDrip) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (pr_drip() <= 128) { @@ -169,7 +169,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CorpseBloodDrip) DEFINE_ACTION_FUNCTION(AActor, A_CorpseExplode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int i; @@ -207,7 +207,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CorpseExplode) DEFINE_ACTION_FUNCTION(AActor, A_LeafSpawn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int i; @@ -238,7 +238,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LeafSpawn) DEFINE_ACTION_FUNCTION(AActor, A_LeafThrust) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (pr_leafthrust() <= 96) { @@ -255,7 +255,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LeafThrust) DEFINE_ACTION_FUNCTION(AActor, A_LeafCheck) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special1++; if (self->special1 >= 20) @@ -287,7 +287,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LeafCheck) DEFINE_ACTION_FUNCTION(AActor, A_PoisonShroom) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->tics = 128 + (pr_shroom() << 1); return 0; @@ -301,7 +301,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonShroom) DEFINE_ACTION_FUNCTION(AActor, A_SoAExplode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int i; @@ -362,7 +362,7 @@ void AZBell::Activate (AActor *activator) DEFINE_ACTION_FUNCTION(AActor, A_BellReset1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_NOGRAVITY; self->Height *= 4; @@ -383,7 +383,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BellReset1) DEFINE_ACTION_FUNCTION(AActor, A_BellReset2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_SHOOTABLE; self->flags &= ~MF_CORPSE; diff --git a/src/g_hexen/a_iceguy.cpp b/src/g_hexen/a_iceguy.cpp index d518c7db7..1163a117a 100644 --- a/src/g_hexen/a_iceguy.cpp +++ b/src/g_hexen/a_iceguy.cpp @@ -26,7 +26,7 @@ static const char *WispTypes[2] = DEFINE_ACTION_FUNCTION(AActor, A_IceGuyLook) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double dist; DAngle an; @@ -49,7 +49,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyLook) DEFINE_ACTION_FUNCTION(AActor, A_IceGuyChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double dist; DAngle an; @@ -78,7 +78,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyChase) DEFINE_ACTION_FUNCTION(AActor, A_IceGuyAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if(!self->target) { @@ -98,7 +98,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyAttack) DEFINE_ACTION_FUNCTION(AActor, A_IceGuyDie) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Vel.Zero(); self->Height = self->GetDefault()->Height; @@ -114,7 +114,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyDie) DEFINE_ACTION_FUNCTION(AActor, A_IceGuyMissileExplode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; unsigned int i; diff --git a/src/g_hexen/a_korax.cpp b/src/g_hexen/a_korax.cpp index 01457b91c..2824d8c0a 100644 --- a/src/g_hexen/a_korax.cpp +++ b/src/g_hexen/a_korax.cpp @@ -88,7 +88,7 @@ extern void SpawnSpiritTail (AActor *spirit); DEFINE_ACTION_FUNCTION(AActor, A_KoraxChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *spot; @@ -155,7 +155,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxChase) DEFINE_ACTION_FUNCTION(AActor, A_KoraxBonePop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int i; @@ -201,7 +201,7 @@ void KSpiritInit (AActor *spirit, AActor *korax) DEFINE_ACTION_FUNCTION(AActor, A_KoraxDecide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (pr_koraxdecide()<220) { @@ -222,7 +222,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxDecide) DEFINE_ACTION_FUNCTION(AActor, A_KoraxMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); static const struct { const char *type, *sound; } choices[6] = { @@ -265,7 +265,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxMissile) DEFINE_ACTION_FUNCTION(AActor, A_KoraxCommand) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle ang; int numcommands; @@ -399,7 +399,7 @@ static void A_KSpiritSeeker (AActor *actor, DAngle thresh, DAngle turnMax) DEFINE_ACTION_FUNCTION(AActor, A_KSpiritRoam) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->health-- <= 0) { @@ -432,7 +432,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KSpiritRoam) DEFINE_ACTION_FUNCTION(AActor, A_KBolt) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // Countdown lifetime if (self->special1-- <= 0) @@ -450,7 +450,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KBolt) DEFINE_ACTION_FUNCTION(AActor, A_KBoltRaise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; diff --git a/src/g_hexen/a_magecone.cpp b/src/g_hexen/a_magecone.cpp index b33f93787..57e68c16f 100644 --- a/src/g_hexen/a_magecone.cpp +++ b/src/g_hexen/a_magecone.cpp @@ -51,7 +51,7 @@ int AFrostMissile::DoSpecialDamage (AActor *victim, int damage, FName damagetype DEFINE_ACTION_FUNCTION(AActor, A_FireConePL1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -112,7 +112,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireConePL1) DEFINE_ACTION_FUNCTION(AActor, A_ShedShard) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int spawndir = self->special1; diff --git a/src/g_hexen/a_magelightning.cpp b/src/g_hexen/a_magelightning.cpp index f322d88a6..e4390131a 100644 --- a/src/g_hexen/a_magelightning.cpp +++ b/src/g_hexen/a_magelightning.cpp @@ -126,7 +126,7 @@ int ALightningZap::SpecialMissileHit (AActor *thing) DEFINE_ACTION_FUNCTION(AActor, A_LightningReady) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DoReadyWeapon(self); if (pr_lightningready() < 160) @@ -144,7 +144,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningReady) DEFINE_ACTION_FUNCTION(AActor, A_LightningClip) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *cMo; AActor *target = NULL; @@ -211,7 +211,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningClip) DEFINE_ACTION_FUNCTION(AActor, A_LightningZap) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PClassActor *lightning = PClass::FindActor(self->GetClass()->MissileName); AActor *mo; @@ -257,7 +257,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningZap) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MLightningAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(floor, AActor) { floor = PClass::FindActor("LightningFloor"); } PARAM_CLASS_OPT(ceiling, AActor) { ceiling = PClass::FindActor("LightningCeiling"); } @@ -298,7 +298,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MLightningAttack) DEFINE_ACTION_FUNCTION(AActor, A_ZapMimic) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -326,7 +326,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ZapMimic) DEFINE_ACTION_FUNCTION(AActor, A_LastZap) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PClassActor *lightning = PClass::FindActor(self->GetClass()->MissileName); AActor *mo; @@ -353,7 +353,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LastZap) DEFINE_ACTION_FUNCTION(AActor, A_LightningRemove) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; diff --git a/src/g_hexen/a_magestaff.cpp b/src/g_hexen/a_magestaff.cpp index ca846d794..710af8198 100644 --- a/src/g_hexen/a_magestaff.cpp +++ b/src/g_hexen/a_magestaff.cpp @@ -122,7 +122,7 @@ void MStaffSpawn (AActor *pmo, DAngle angle, AActor *alttarget) DEFINE_ACTION_FUNCTION(AActor, A_MStaffAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; player_t *player; @@ -167,7 +167,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MStaffAttack) DEFINE_ACTION_FUNCTION(AActor, A_MStaffPalette) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -188,7 +188,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MStaffPalette) DEFINE_ACTION_FUNCTION(AActor, A_MStaffTrack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if ((self->tracer == 0) && (pr_mstafftrack()<50)) { @@ -250,7 +250,7 @@ void MStaffSpawn2 (AActor *actor, DAngle angle) DEFINE_ACTION_FUNCTION(AActor, A_MageAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) { diff --git a/src/g_hexen/a_pig.cpp b/src/g_hexen/a_pig.cpp index 11bfe3ce8..cafcbcda3 100644 --- a/src/g_hexen/a_pig.cpp +++ b/src/g_hexen/a_pig.cpp @@ -58,7 +58,7 @@ void APigPlayer::MorphPlayerThink () DEFINE_ACTION_FUNCTION(AActor, A_SnoutAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -96,7 +96,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SnoutAttack) DEFINE_ACTION_FUNCTION(AActor, A_PigPain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_Pain, self); if (self->Z() <= self->floorz) diff --git a/src/g_hexen/a_serpent.cpp b/src/g_hexen/a_serpent.cpp index 1f6d1dd2b..6f435747e 100644 --- a/src/g_hexen/a_serpent.cpp +++ b/src/g_hexen/a_serpent.cpp @@ -25,7 +25,7 @@ static FRandom pr_delaygib ("DelayGib"); DEFINE_ACTION_FUNCTION(AActor, A_SerpentUnHide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags &= ~RF_INVISIBLE; self->Floorclip = 24; @@ -40,7 +40,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentUnHide) DEFINE_ACTION_FUNCTION(AActor, A_SerpentHide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags |= RF_INVISIBLE; self->Floorclip = 0; @@ -56,7 +56,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentHide) DEFINE_ACTION_FUNCTION(AActor, A_SerpentRaiseHump) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Floorclip -= 4; return 0; @@ -70,7 +70,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentRaiseHump) DEFINE_ACTION_FUNCTION(AActor, A_SerpentLowerHump) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Floorclip += 4; return 0; @@ -86,7 +86,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentLowerHump) DEFINE_ACTION_FUNCTION(AActor, A_SerpentHumpDecide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->MissileState != NULL) { @@ -127,7 +127,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentHumpDecide) DEFINE_ACTION_FUNCTION(AActor, A_SerpentCheckForAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) { @@ -167,7 +167,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentCheckForAttack) DEFINE_ACTION_FUNCTION(AActor, A_SerpentChooseAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target || self->CheckMeleeRange()) { @@ -188,7 +188,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentChooseAttack) DEFINE_ACTION_FUNCTION(AActor, A_SerpentMeleeAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) { @@ -216,7 +216,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentMeleeAttack) DEFINE_ACTION_FUNCTION(AActor, A_SerpentSpawnGibs) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; static const char *GibTypes[] = @@ -250,7 +250,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentSpawnGibs) DEFINE_ACTION_FUNCTION(AActor, A_FloatGib) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Floorclip -= 1; return 0; @@ -264,7 +264,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FloatGib) DEFINE_ACTION_FUNCTION(AActor, A_SinkGib) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Floorclip += 1;; return 0; @@ -278,7 +278,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SinkGib) DEFINE_ACTION_FUNCTION(AActor, A_DelayGib) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->tics -= pr_delaygib()>>2; return 0; @@ -292,7 +292,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DelayGib) DEFINE_ACTION_FUNCTION(AActor, A_SerpentHeadCheck) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->Z() <= self->floorz) { diff --git a/src/g_hexen/a_spike.cpp b/src/g_hexen/a_spike.cpp index 1e81f568f..3f5f4d2e8 100644 --- a/src/g_hexen/a_spike.cpp +++ b/src/g_hexen/a_spike.cpp @@ -79,7 +79,7 @@ void AThrustFloor::Deactivate (AActor *activator) DEFINE_ACTION_FUNCTION(AActor, A_ThrustInitUp) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special2 = 5; // Raise speed self->args[0] = 1; // Mark as up @@ -92,7 +92,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustInitUp) DEFINE_ACTION_FUNCTION(AActor, A_ThrustInitDn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->special2 = 5; // Raise speed self->args[0] = 0; // Mark as down @@ -108,7 +108,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustInitDn) DEFINE_ACTION_FUNCTION(AActor, A_ThrustRaise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AThrustFloor *actor = static_cast(self); @@ -137,7 +137,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustRaise) DEFINE_ACTION_FUNCTION(AActor, A_ThrustLower) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (A_SinkMobj (self, 6)) { @@ -152,7 +152,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustLower) DEFINE_ACTION_FUNCTION(AActor, A_ThrustImpale) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // This doesn't need to iterate through portals. diff --git a/src/g_hexen/a_summon.cpp b/src/g_hexen/a_summon.cpp index c9daad6ec..e1b2bae09 100644 --- a/src/g_hexen/a_summon.cpp +++ b/src/g_hexen/a_summon.cpp @@ -49,7 +49,7 @@ bool AArtiDarkServant::Use (bool pickup) DEFINE_ACTION_FUNCTION(AActor, A_Summon) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AMinotaurFriend *mo; diff --git a/src/g_hexen/a_teleportother.cpp b/src/g_hexen/a_teleportother.cpp index a89e62b4b..99d6876a5 100644 --- a/src/g_hexen/a_teleportother.cpp +++ b/src/g_hexen/a_teleportother.cpp @@ -63,35 +63,35 @@ static void TeloSpawn (AActor *source, const char *type) DEFINE_ACTION_FUNCTION(AActor, A_TeloSpawnA) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); TeloSpawn (self, "TelOtherFX2"); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_TeloSpawnB) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); TeloSpawn (self, "TelOtherFX3"); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_TeloSpawnC) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); TeloSpawn (self, "TelOtherFX4"); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_TeloSpawnD) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); TeloSpawn (self, "TelOtherFX5"); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_CheckTeleRing) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->special1-- <= 0) { diff --git a/src/g_hexen/a_wraith.cpp b/src/g_hexen/a_wraith.cpp index f5c1f44f4..fcd0d75f3 100644 --- a/src/g_hexen/a_wraith.cpp +++ b/src/g_hexen/a_wraith.cpp @@ -23,7 +23,7 @@ static FRandom pr_wraithfx4 ("WraithFX4"); DEFINE_ACTION_FUNCTION(AActor, A_WraithInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->AddZ(48); @@ -45,7 +45,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithInit) DEFINE_ACTION_FUNCTION(AActor, A_WraithRaiseInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags &= ~RF_INVISIBLE; self->flags2 &= ~MF2_NONSHOOTABLE; @@ -63,7 +63,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithRaiseInit) DEFINE_ACTION_FUNCTION(AActor, A_WraithRaise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (A_RaiseMobj (self, 2)) { @@ -88,7 +88,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithRaise) DEFINE_ACTION_FUNCTION(AActor, A_WraithMelee) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int amount; @@ -110,7 +110,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithMelee) DEFINE_ACTION_FUNCTION(AActor, A_WraithFX2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; DAngle angle; @@ -147,7 +147,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithFX2) DEFINE_ACTION_FUNCTION(AActor, A_WraithFX3) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; int numdropped = pr_wraithfx3() % 15; @@ -242,7 +242,7 @@ void A_WraithFX4 (AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_WraithChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int weaveindex = self->WeaveIndexZ; self->AddZ(BobSin(weaveindex)); diff --git a/src/g_raven/a_minotaur.cpp b/src/g_raven/a_minotaur.cpp index e3636fe1b..8bdbe122b 100644 --- a/src/g_raven/a_minotaur.cpp +++ b/src/g_raven/a_minotaur.cpp @@ -135,7 +135,7 @@ bool AMinotaurFriend::OkayToSwitchTarget (AActor *other) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (Wads.CheckNumForName ("MNTRF1", ns_sprites) < 0 && Wads.CheckNumForName ("MNTRF0", ns_sprites) < 0) @@ -145,7 +145,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDeath) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player; @@ -180,7 +180,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk1) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDecide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); bool friendly = !!(self->flags5 & MF5_SUMMONEDMONSTER); AActor *target; @@ -237,7 +237,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDecide) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurCharge) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *puff; @@ -280,7 +280,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurCharge) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; DAngle angle; @@ -330,7 +330,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk2) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk3) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -386,7 +386,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk3) DEFINE_ACTION_FUNCTION(AActor, A_MntrFloorFire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *mo; @@ -443,7 +443,7 @@ void P_MinotaurSlam (AActor *source, AActor *target) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurRoam) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // In case pain caused him to skip his fade in. self->RenderStyle = STYLE_Normal; @@ -491,7 +491,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurRoam) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurLook) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->IsKindOf(RUNTIME_CLASS(AMinotaurFriend))) { @@ -562,7 +562,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurLook) DEFINE_ACTION_FUNCTION(AActor, A_MinotaurChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->IsKindOf(RUNTIME_CLASS(AMinotaurFriend))) { diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index 3b1191131..abd58dec1 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -104,14 +104,14 @@ void A_Unblock(AActor *self, bool drop) DEFINE_ACTION_FUNCTION(AActor, A_NoBlocking) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_Unblock(self, true); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_Fall) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_Unblock(self, true); return 0; } @@ -124,7 +124,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Fall) DEFINE_ACTION_FUNCTION(AActor, A_SetFloorClip) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 |= MF2_FLOORCLIP; self->AdjustFloorClip (); @@ -139,7 +139,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SetFloorClip) DEFINE_ACTION_FUNCTION(AActor, A_UnSetFloorClip) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 &= ~MF2_FLOORCLIP; self->Floorclip = 0; @@ -154,7 +154,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnSetFloorClip) DEFINE_ACTION_FUNCTION(AActor, A_HideThing) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags |= RF_INVISIBLE; return 0; @@ -168,7 +168,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_HideThing) DEFINE_ACTION_FUNCTION(AActor, A_UnHideThing) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags &= ~RF_INVISIBLE; return 0; @@ -182,7 +182,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnHideThing) DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int t = pr_freezedeath(); self->tics = 75+t+pr_freezedeath(); @@ -228,7 +228,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeath) DEFINE_ACTION_FUNCTION(AActor, A_GenericFreezeDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Translation = TRANSLATION(TRANSLATION_Standard, 7); CALL_ACTION(A_FreezeDeath, self); @@ -243,7 +243,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_GenericFreezeDeath) DEFINE_ACTION_FUNCTION(AActor, A_IceSetTics) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int floor; @@ -268,7 +268,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceSetTics) DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeathChunks) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; int numChunks; @@ -446,7 +446,7 @@ void DCorpsePointer::Serialize(FSerializer &arc) // throw another corpse on the queue DEFINE_ACTION_FUNCTION(AActor, A_QueueCorpse) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (sv_corpsequeuesize > 0) { @@ -458,7 +458,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_QueueCorpse) // Remove an self from the queue (for resurrection) DEFINE_ACTION_FUNCTION(AActor, A_DeQueueCorpse) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); TThinkerIterator iterator (STAT_CORPSEPOINTER); DCorpsePointer *corpsePtr; @@ -483,7 +483,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeQueueCorpse) DEFINE_ACTION_FUNCTION(AActor, A_SetInvulnerable) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 |= MF2_INVULNERABLE; return 0; @@ -497,7 +497,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SetInvulnerable) DEFINE_ACTION_FUNCTION(AActor, A_UnSetInvulnerable) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 &= ~MF2_INVULNERABLE; return 0; @@ -511,7 +511,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnSetInvulnerable) DEFINE_ACTION_FUNCTION(AActor, A_SetReflective) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 |= MF2_REFLECTIVE; return 0; @@ -525,7 +525,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SetReflective) DEFINE_ACTION_FUNCTION(AActor, A_UnSetReflective) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 &= ~MF2_REFLECTIVE; return 0; @@ -539,7 +539,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnSetReflective) DEFINE_ACTION_FUNCTION(AActor, A_SetReflectiveInvulnerable) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 |= MF2_REFLECTIVE|MF2_INVULNERABLE; return 0; @@ -553,7 +553,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SetReflectiveInvulnerable) DEFINE_ACTION_FUNCTION(AActor, A_UnSetReflectiveInvulnerable) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 &= ~(MF2_REFLECTIVE|MF2_INVULNERABLE); return 0; @@ -567,7 +567,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnSetReflectiveInvulnerable) DEFINE_ACTION_FUNCTION(AActor, A_SetShootable) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 &= ~MF2_NONSHOOTABLE; self->flags |= MF_SHOOTABLE; @@ -582,7 +582,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SetShootable) DEFINE_ACTION_FUNCTION(AActor, A_UnSetShootable) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags2 |= MF2_NONSHOOTABLE; self->flags &= ~MF_SHOOTABLE; @@ -597,7 +597,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnSetShootable) DEFINE_ACTION_FUNCTION(AActor, A_NoGravity) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_NOGRAVITY; return 0; @@ -611,7 +611,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_NoGravity) DEFINE_ACTION_FUNCTION(AActor, A_Gravity) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~MF_NOGRAVITY; self->Gravity = 1; @@ -626,7 +626,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Gravity) DEFINE_ACTION_FUNCTION(AActor, A_LowGravity) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~MF_NOGRAVITY; self->Gravity = 1. / 8;; diff --git a/src/g_shared/a_bridge.cpp b/src/g_shared/a_bridge.cpp index 3161c2a45..f3b12a1d1 100644 --- a/src/g_shared/a_bridge.cpp +++ b/src/g_shared/a_bridge.cpp @@ -92,7 +92,7 @@ void ACustomBridge::Destroy() DEFINE_ACTION_FUNCTION(AActor, A_BridgeOrbit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) { // Don't crash if somebody spawned this into the world @@ -121,7 +121,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BridgeOrbit) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BridgeInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(balltype, AActor) { balltype = NULL; } AActor *ball; diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index 38f0a5130..ae7516d17 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -355,7 +355,7 @@ bool P_GiveBody (AActor *actor, int num, int max) DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialThing1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags &= ~RF_INVISIBLE; if (static_cast(self)->DoRespawn ()) @@ -373,7 +373,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialThing1) DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialThing2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_SPECIAL; if (!(self->GetDefault()->flags & MF_NOGRAVITY)) @@ -393,7 +393,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialThing2) DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialDoomThing) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->renderflags &= ~RF_INVISIBLE; self->flags |= MF_SPECIAL; @@ -418,7 +418,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialDoomThing) DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialPosition) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // Move item back to its original location DVector2 sp = self->SpawnPoint; diff --git a/src/g_shared/a_specialspot.cpp b/src/g_shared/a_specialspot.cpp index 48a8ce1a1..1af9f6db7 100644 --- a/src/g_shared/a_specialspot.cpp +++ b/src/g_shared/a_specialspot.cpp @@ -380,7 +380,7 @@ void ASpecialSpot::Destroy() DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnSingleItem) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (cls, AActor); PARAM_INT_OPT (fail_sp) { fail_sp = 0; } PARAM_INT_OPT (fail_co) { fail_co = 0; } diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index 84305b9cd..d7f432a7a 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -1922,7 +1922,7 @@ PClassWeapon *Net_ReadWeapon(BYTE **stream) DEFINE_ACTION_FUNCTION_PARAMS(AWeapon, A_ZoomFactor) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT (zoom) { zoom = 1; } PARAM_INT_OPT (flags) { flags = 0; } @@ -1950,7 +1950,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AWeapon, A_ZoomFactor) DEFINE_ACTION_FUNCTION_PARAMS(AWeapon, A_SetCrosshair) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT(xhair); if (self->player != NULL && self->player->ReadyWeapon != NULL) diff --git a/src/g_strife/a_acolyte.cpp b/src/g_strife/a_acolyte.cpp index 6f08a84c8..a21c06619 100644 --- a/src/g_strife/a_acolyte.cpp +++ b/src/g_strife/a_acolyte.cpp @@ -27,7 +27,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_HideDecepticon) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); EV_DoDoor (DDoor::doorClose, NULL, self, 999, 8., 0, 0, 0); if (self->target != NULL && self->target->player != NULL) @@ -45,7 +45,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_HideDecepticon) DEFINE_ACTION_FUNCTION(AActor, A_AcolyteDie) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; @@ -92,7 +92,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_AcolyteDie) DEFINE_ACTION_FUNCTION(AActor, A_BeShadowyFoe) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->RenderStyle = STYLE_Translucent; self->Alpha = HR_SHADOW; @@ -108,7 +108,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeShadowyFoe) DEFINE_ACTION_FUNCTION(AActor, A_AcolyteBits) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->SpawnFlags & MTF_SHADOW) { diff --git a/src/g_strife/a_alienspectres.cpp b/src/g_strife/a_alienspectres.cpp index d4103015c..a1c20355f 100644 --- a/src/g_strife/a_alienspectres.cpp +++ b/src/g_strife/a_alienspectres.cpp @@ -20,7 +20,7 @@ static FRandom pr_spectrechunk ("212e4"); DEFINE_ACTION_FUNCTION(AActor, A_SpectreChunkSmall) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *foo = Spawn("AlienChunkSmall", self->PosPlusZ(10.), ALLOW_REPLACE); @@ -41,7 +41,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpectreChunkSmall) DEFINE_ACTION_FUNCTION(AActor, A_SpectreChunkLarge) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *foo = Spawn("AlienChunkLarge", self->PosPlusZ(10.), ALLOW_REPLACE); @@ -62,7 +62,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpectreChunkLarge) DEFINE_ACTION_FUNCTION(AActor, A_Spectre3Attack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -86,7 +86,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Spectre3Attack) DEFINE_ACTION_FUNCTION(AActor, A_AlienSpectreDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *player; char voc[32]; diff --git a/src/g_strife/a_crusader.cpp b/src/g_strife/a_crusader.cpp index 8e340b820..05835a5f9 100644 --- a/src/g_strife/a_crusader.cpp +++ b/src/g_strife/a_crusader.cpp @@ -20,7 +20,7 @@ static bool CrusaderCheckRange (AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_CrusaderChoose) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -51,7 +51,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CrusaderChoose) DEFINE_ACTION_FUNCTION(AActor, A_CrusaderSweepLeft) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Angles.Yaw += 90./16; AActor *misl = P_SpawnMissileZAimed (self, self->Z() + 48, self->target, PClass::FindActor("FastFlameMissile")); @@ -64,7 +64,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CrusaderSweepLeft) DEFINE_ACTION_FUNCTION(AActor, A_CrusaderSweepRight) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Angles.Yaw -= 90./16; AActor *misl = P_SpawnMissileZAimed (self, self->Z() + 48, self->target, PClass::FindActor("FastFlameMissile")); @@ -77,7 +77,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CrusaderSweepRight) DEFINE_ACTION_FUNCTION(AActor, A_CrusaderRefire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL || self->target->health <= 0 || @@ -90,7 +90,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CrusaderRefire) DEFINE_ACTION_FUNCTION(AActor, A_CrusaderDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (CheckBossDeath (self)) { diff --git a/src/g_strife/a_entityboss.cpp b/src/g_strife/a_entityboss.cpp index b7f60e26f..84a4b3fa3 100644 --- a/src/g_strife/a_entityboss.cpp +++ b/src/g_strife/a_entityboss.cpp @@ -14,7 +14,7 @@ static FRandom pr_entity ("Entity"); DEFINE_ACTION_FUNCTION(AActor, A_SubEntityDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (CheckBossDeath (self)) { @@ -42,7 +42,7 @@ DECLARE_ACTION(A_Spectre3Attack) DEFINE_ACTION_FUNCTION(AActor, A_EntityAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // Apparent Strife bug: Case 5 was unreachable because they used % 5 instead of % 6. // I've fixed that by making case 1 duplicate it, since case 1 did nothing. @@ -75,7 +75,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_EntityAttack) DEFINE_ACTION_FUNCTION(AActor, A_SpawnEntity) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *entity = Spawn("EntityBoss", self->PosPlusZ(70.), ALLOW_REPLACE); if (entity != NULL) @@ -90,7 +90,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpawnEntity) DEFINE_ACTION_FUNCTION(AActor, A_EntityDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *second; double secondRadius = GetDefaultByName("EntitySecond")->radius * 2; diff --git a/src/g_strife/a_inquisitor.cpp b/src/g_strife/a_inquisitor.cpp index 16871300a..a4c2d72f4 100644 --- a/src/g_strife/a_inquisitor.cpp +++ b/src/g_strife/a_inquisitor.cpp @@ -12,7 +12,7 @@ static FRandom pr_inq ("Inquisitor"); DEFINE_ACTION_FUNCTION(AActor, A_InquisitorWalk) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "inquisitor/walk", 1, ATTN_NORM); A_Chase (stack, self); @@ -30,7 +30,7 @@ bool InquisitorCheckDistance (AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_InquisitorDecide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target == NULL) return 0; @@ -52,7 +52,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_InquisitorDecide) DEFINE_ACTION_FUNCTION(AActor, A_InquisitorAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *proj; @@ -80,7 +80,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_InquisitorAttack) DEFINE_ACTION_FUNCTION(AActor, A_InquisitorJump) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double dist; double speed; @@ -102,7 +102,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_InquisitorJump) DEFINE_ACTION_FUNCTION(AActor, A_InquisitorCheckLand) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->reactiontime--; if (self->reactiontime < 0 || @@ -125,7 +125,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_InquisitorCheckLand) DEFINE_ACTION_FUNCTION(AActor, A_TossArm) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *foo = Spawn("InquisitorArm", self->PosPlusZ(24.), ALLOW_REPLACE); foo->Angles.Yaw = self->Angles.Yaw - 90. + pr_inq.Random2() * (360./1024.); diff --git a/src/g_strife/a_loremaster.cpp b/src/g_strife/a_loremaster.cpp index 2d695ac8d..504324590 100644 --- a/src/g_strife/a_loremaster.cpp +++ b/src/g_strife/a_loremaster.cpp @@ -33,7 +33,7 @@ int ALoreShot::DoSpecialDamage (AActor *victim, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_LoremasterChain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "loremaster/active", 1, ATTN_NORM); Spawn("LoreShot2", self->Pos(), ALLOW_REPLACE); diff --git a/src/g_strife/a_oracle.cpp b/src/g_strife/a_oracle.cpp index 139786d89..f49849922 100644 --- a/src/g_strife/a_oracle.cpp +++ b/src/g_strife/a_oracle.cpp @@ -10,7 +10,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WakeOracleSpectre) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); TThinkerIterator it(NAME_AlienSpectre3); AActor *spectre = it.Next(); diff --git a/src/g_strife/a_programmer.cpp b/src/g_strife/a_programmer.cpp index 9c8cb6be3..b46b47e70 100644 --- a/src/g_strife/a_programmer.cpp +++ b/src/g_strife/a_programmer.cpp @@ -74,7 +74,7 @@ PalEntry AProgLevelEnder::GetBlend () DEFINE_ACTION_FUNCTION(AActor, A_ProgrammerMelee) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int damage; @@ -102,7 +102,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ProgrammerMelee) DEFINE_ACTION_FUNCTION(AActor, A_SpotLightning) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *spot; @@ -128,7 +128,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpotLightning) DEFINE_ACTION_FUNCTION(AActor, A_SpawnProgrammerBase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *foo = Spawn("ProgrammerBase", self->PosPlusZ(24.), ALLOW_REPLACE); if (foo != NULL) @@ -148,7 +148,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpawnProgrammerBase) DEFINE_ACTION_FUNCTION(AActor, A_ProgrammerDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!CheckBossDeath (self)) return 0; diff --git a/src/g_strife/a_reaver.cpp b/src/g_strife/a_reaver.cpp index 09d771a19..9c6e9f6b9 100644 --- a/src/g_strife/a_reaver.cpp +++ b/src/g_strife/a_reaver.cpp @@ -13,7 +13,7 @@ static FRandom pr_reaverattack ("ReaverAttack"); DEFINE_ACTION_FUNCTION(AActor, A_ReaverRanged) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target != NULL) { diff --git a/src/g_strife/a_rebels.cpp b/src/g_strife/a_rebels.cpp index c4df1cba1..e460dd91a 100644 --- a/src/g_strife/a_rebels.cpp +++ b/src/g_strife/a_rebels.cpp @@ -22,7 +22,7 @@ static FRandom pr_shootgun ("ShootGun"); DEFINE_ACTION_FUNCTION(AActor, A_ShootGun) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle pitch; @@ -74,7 +74,7 @@ bool ATeleporterBeacon::Use (bool pickup) DEFINE_ACTION_FUNCTION(AActor, A_Beacon) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *owner = self->target; AActor *rebel; diff --git a/src/g_strife/a_sentinel.cpp b/src/g_strife/a_sentinel.cpp index 42a7aeb47..44946c84a 100644 --- a/src/g_strife/a_sentinel.cpp +++ b/src/g_strife/a_sentinel.cpp @@ -11,7 +11,7 @@ static FRandom pr_sentinelrefire ("SentinelRefire"); DEFINE_ACTION_FUNCTION(AActor, A_SentinelBob) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double minz, maxz; @@ -43,7 +43,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SentinelBob) DEFINE_ACTION_FUNCTION(AActor, A_SentinelAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *missile, *trail; @@ -75,7 +75,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SentinelAttack) DEFINE_ACTION_FUNCTION(AActor, A_SentinelRefire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_FaceTarget (self); diff --git a/src/g_strife/a_spectral.cpp b/src/g_strife/a_spectral.cpp index 1b1f13b1a..b348e54dc 100644 --- a/src/g_strife/a_spectral.cpp +++ b/src/g_strife/a_spectral.cpp @@ -26,7 +26,7 @@ void ASpectralMonster::Touch (AActor *toucher) DEFINE_ACTION_FUNCTION(AActor, A_SpectralLightningTail) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *foo = Spawn("SpectralLightningHTail", self->Vec3Offset(-self->Vel.X, -self->Vel.Y, 0.), ALLOW_REPLACE); @@ -37,7 +37,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpectralLightningTail) DEFINE_ACTION_FUNCTION(AActor, A_SpectralBigBallLightning) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PClassActor *cls = PClass::FindActor("SpectralLightningH3"); if (cls) @@ -56,7 +56,7 @@ static FRandom pr_zap5 ("Zap5"); DEFINE_ACTION_FUNCTION(AActor, A_SpectralLightning) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *flash; @@ -90,7 +90,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpectralLightning) DEFINE_ACTION_FUNCTION(AActor, A_Tracer2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *dest; double dist; diff --git a/src/g_strife/a_stalker.cpp b/src/g_strife/a_stalker.cpp index 210bd8c22..9189ef8de 100644 --- a/src/g_strife/a_stalker.cpp +++ b/src/g_strife/a_stalker.cpp @@ -13,7 +13,7 @@ static FRandom pr_stalker ("Stalker"); DEFINE_ACTION_FUNCTION(AActor, A_StalkerChaseDecide) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!(self->flags & MF_NOGRAVITY)) { @@ -28,7 +28,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_StalkerChaseDecide) DEFINE_ACTION_FUNCTION(AActor, A_StalkerLookInit) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); FState *state; if (self->flags & MF_NOGRAVITY) @@ -48,7 +48,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_StalkerLookInit) DEFINE_ACTION_FUNCTION(AActor, A_StalkerDrop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags5 &= ~MF5_NOVERTICALMELEERANGE; self->flags &= ~MF_NOGRAVITY; @@ -57,7 +57,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_StalkerDrop) DEFINE_ACTION_FUNCTION(AActor, A_StalkerAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->flags & MF_NOGRAVITY) { @@ -79,7 +79,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_StalkerAttack) DEFINE_ACTION_FUNCTION(AActor, A_StalkerWalk) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_BODY, "stalker/walk", 1, ATTN_NORM); A_Chase (stack, self); diff --git a/src/g_strife/a_strifeitems.cpp b/src/g_strife/a_strifeitems.cpp index 20de58d4f..6cda8a0fc 100644 --- a/src/g_strife/a_strifeitems.cpp +++ b/src/g_strife/a_strifeitems.cpp @@ -23,7 +23,7 @@ IMPLEMENT_CLASS(ADegninOre) DEFINE_ACTION_FUNCTION(AActor, A_RemoveForceField) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~MF_SPECIAL; diff --git a/src/g_strife/a_strifestuff.cpp b/src/g_strife/a_strifestuff.cpp index 32ce0e395..ef60b77e7 100644 --- a/src/g_strife/a_strifestuff.cpp +++ b/src/g_strife/a_strifestuff.cpp @@ -87,7 +87,7 @@ int AForceFieldGuard::TakeSpecialDamage (AActor *inflictor, AActor *source, int DEFINE_ACTION_FUNCTION(AActor, A_SetShadow) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_STRIFEx8000000|MF_SHADOW; self->RenderStyle = STYLE_Translucent; @@ -97,7 +97,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SetShadow) DEFINE_ACTION_FUNCTION(AActor, A_ClearShadow) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~(MF_STRIFEx8000000|MF_SHADOW); self->RenderStyle = STYLE_Normal; @@ -109,7 +109,7 @@ static FRandom pr_gethurt ("HurtMe!"); DEFINE_ACTION_FUNCTION(AActor, A_GetHurt) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags4 |= MF4_INCOMBAT; if ((pr_gethurt() % 5) == 0) @@ -128,7 +128,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_GetHurt) DEFINE_ACTION_FUNCTION(AActor, A_TurretLook) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *target; @@ -160,7 +160,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_TurretLook) DEFINE_ACTION_FUNCTION(AActor, A_KlaxonBlare) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (--self->reactiontime < 0) { @@ -249,7 +249,7 @@ IMPLEMENT_CLASS (AMeat) DEFINE_ACTION_FUNCTION(AActor, A_TossGib) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); const char *gibtype = (self->flags & MF_NOBLOOD) ? "Junk" : "Meat"; AActor *gib = Spawn (gibtype, self->PosPlusZ(24.), ALLOW_REPLACE); @@ -269,7 +269,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_TossGib) DEFINE_ACTION_FUNCTION(AActor, A_FLoopActiveSound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->ActiveSound != 0 && !(level.time & 7)) { @@ -280,7 +280,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FLoopActiveSound) DEFINE_ACTION_FUNCTION(AActor, A_Countdown) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (--self->reactiontime <= 0) { @@ -292,7 +292,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Countdown) DEFINE_ACTION_FUNCTION(AActor, A_LoopActiveSound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->ActiveSound != 0 && !S_IsActorPlayingSomething (self, CHAN_VOICE, -1)) { @@ -303,7 +303,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LoopActiveSound) DEFINE_ACTION_FUNCTION(AActor, A_CheckTerrain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); sector_t *sec = self->Sector; @@ -332,7 +332,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CheckTerrain) DEFINE_ACTION_FUNCTION(AActor, A_ClearSoundTarget) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *actor; @@ -347,7 +347,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ClearSoundTarget) DEFINE_ACTION_FUNCTION(AActor, A_ItBurnsItBurns) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_VOICE, "human/imonfire", 1, ATTN_NORM); @@ -365,7 +365,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ItBurnsItBurns) DEFINE_ACTION_FUNCTION(AActor, A_DropFire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *drop = Spawn("FireDroplet", self->PosPlusZ(24.), ALLOW_REPLACE); drop->Vel.Z = -1.; @@ -375,7 +375,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DropFire) DEFINE_ACTION_FUNCTION(AActor, A_CrispyPlayer) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != nullptr && self->player->mo == self) { @@ -401,7 +401,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CrispyPlayer) DEFINE_ACTION_FUNCTION(AActor, A_HandLower) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != nullptr) { diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index 66d635aa5..91f4ac75e 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -94,7 +94,7 @@ void P_DaggerAlert (AActor *target, AActor *emitter) DEFINE_ACTION_FUNCTION(AActor, A_JabDagger) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DAngle angle; int damage; @@ -146,7 +146,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_AlertMonsters) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(maxdist) { maxdist = 0; } PARAM_INT_OPT(Flags) { Flags = 0; } @@ -212,7 +212,7 @@ int APoisonBolt::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_ClearFlash) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; @@ -231,7 +231,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ClearFlash) DEFINE_ACTION_FUNCTION(AActor, A_ShowElectricFlash) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != nullptr) { @@ -248,7 +248,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ShowElectricFlash) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireArrow) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(ti, AActor); DAngle savedangle; @@ -307,7 +307,7 @@ void P_StrifeGunShot (AActor *mo, bool accurate, DAngle pitch) DEFINE_ACTION_FUNCTION(AActor, A_FireAssaultGun) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); bool accurate; @@ -343,7 +343,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireAssaultGun) DEFINE_ACTION_FUNCTION(AActor, A_FireMiniMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; DAngle savedangle; @@ -374,7 +374,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMiniMissile) DEFINE_ACTION_FUNCTION(AActor, A_RocketInFlight) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *trail; @@ -398,7 +398,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RocketInFlight) DEFINE_ACTION_FUNCTION(AActor, A_FlameDie) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_NOGRAVITY; self->Vel.Z = pr_flamedie() & 3; @@ -413,7 +413,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlameDie) DEFINE_ACTION_FUNCTION(AActor, A_FireFlamer) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; @@ -450,7 +450,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireFlamer) DEFINE_ACTION_FUNCTION(AActor, A_FireMauler1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -494,7 +494,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMauler1) DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2Pre) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/mauler2charge", 1, ATTN_NORM); @@ -516,7 +516,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2Pre) DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -544,7 +544,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2) DEFINE_ACTION_FUNCTION(AActor, A_MaulerTorpedoWave) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *wavedef = GetDefaultByName("MaulerTorpedoWave"); double savedz; @@ -620,7 +620,7 @@ int APhosphorousFire::DoSpecialDamage (AActor *target, int damage, FName damaget DEFINE_ACTION_FUNCTION(AActor, A_BurnArea) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); P_RadiusAttack (self, self->target, 128, 128, self->DamageType, RADF_HURTSOURCE); return 0; @@ -628,7 +628,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BurnArea) DEFINE_ACTION_FUNCTION(AActor, A_Burnination) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Vel.Z -= 8; self->Vel.X += (pr_phburn.Random2 (3)); @@ -688,7 +688,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Burnination) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireGrenade) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(grenadetype, AActor); PARAM_ANGLE(angleofs); PARAM_STATE(flash) @@ -821,7 +821,7 @@ AInventory *ASigil::CreateCopy (AActor *other) DEFINE_ACTION_FUNCTION(AActor, A_SelectPiece) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int pieces = MIN (static_cast(self)->NumPieces, 5); @@ -847,7 +847,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectPiece) DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilView) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DPSprite *pspr; int pieces; @@ -874,7 +874,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilView) DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilDown) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DPSprite *pspr; int pieces; @@ -904,7 +904,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilDown) DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); DPSprite *pspr; int pieces; @@ -927,7 +927,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilAttack) DEFINE_ACTION_FUNCTION(AActor, A_SigilCharge) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/sigilcharge", 1, ATTN_NORM); if (self->player != NULL) @@ -945,7 +945,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SigilCharge) DEFINE_ACTION_FUNCTION(AActor, A_LightInverse) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -962,7 +962,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightInverse) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *spot; player_t *player = self->player; @@ -1007,7 +1007,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil1) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; @@ -1029,7 +1029,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil2) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil3) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *spot; player_t *player = self->player; @@ -1063,7 +1063,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil3) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil4) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *spot; player_t *player = self->player; @@ -1103,7 +1103,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil4) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil5) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; diff --git a/src/g_strife/a_templar.cpp b/src/g_strife/a_templar.cpp index 5ca2ef862..0bfa00b24 100644 --- a/src/g_strife/a_templar.cpp +++ b/src/g_strife/a_templar.cpp @@ -13,7 +13,7 @@ static FRandom pr_templar ("Templar"); DEFINE_ACTION_FUNCTION(AActor, A_TemplarAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int damage; DAngle angle; diff --git a/src/g_strife/a_thingstoblowup.cpp b/src/g_strife/a_thingstoblowup.cpp index 6d1294b53..5e1bc42d2 100644 --- a/src/g_strife/a_thingstoblowup.cpp +++ b/src/g_strife/a_thingstoblowup.cpp @@ -16,7 +16,7 @@ static FRandom pr_lightout ("LightOut"); DEFINE_ACTION_FUNCTION(AActor, A_Bang4Cloud) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); double xo = (pr_bang4cloud.Random2() & 3) * (10. / 64); double yo = (pr_bang4cloud.Random2() & 3) * (10. / 64); @@ -63,7 +63,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GiveQuestItem) DEFINE_ACTION_FUNCTION(AActor, A_ExtraLightOff) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->target != NULL && self->target->player != NULL) { @@ -74,7 +74,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ExtraLightOff) DEFINE_ACTION_FUNCTION(AActor, A_Explode512) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); P_RadiusAttack (self, self->target, 512, 512, NAME_None, RADF_HURTSOURCE); if (self->target != NULL && self->target->player != NULL) @@ -90,7 +90,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Explode512) DEFINE_ACTION_FUNCTION(AActor, A_LightGoesOut) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *foo; sector_t *sec = self->Sector; diff --git a/src/info.h b/src/info.h index 0fe479d20..5e1d045f2 100644 --- a/src/info.h +++ b/src/info.h @@ -360,14 +360,12 @@ void AddStateLight(FState *state, const char *lname); // self - Actor this action is to operate on (player if a weapon) // stateowner - Actor this action really belongs to (may be an item) // callingstate - State this action was called from -#define PARAM_ACTION_PROLOGUE_TYPE(type) \ +#define PARAM_ACTION_PROLOGUE(type) \ PARAM_PROLOGUE; \ PARAM_OBJECT (self, type); \ PARAM_OBJECT_OPT (stateowner, AActor) { stateowner = self; } \ PARAM_STATEINFO_OPT (stateinfo) { stateinfo = nullptr; } \ -#define PARAM_ACTION_PROLOGUE PARAM_ACTION_PROLOGUE_TYPE(AActor) - // Number of action paramaters #define NAP 3 diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index bbeeca374..f389cd1ee 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -891,7 +891,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_TransferPointer) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopyFriendliness) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (ptr_source) { ptr_source = AAPTR_MASTER; } if (self->player != NULL) @@ -914,28 +914,28 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopyFriendliness) //========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_SetSolid) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_SOLID; return 0; } DEFINE_ACTION_FUNCTION(AActor, A_UnsetSolid) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~MF_SOLID; return 0; } DEFINE_ACTION_FUNCTION(AActor, A_SetFloat) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags |= MF_FLOAT; return 0; } DEFINE_ACTION_FUNCTION(AActor, A_UnsetFloat) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->flags &= ~(MF_FLOAT|MF_INFLOAT); return 0; } @@ -980,7 +980,7 @@ static void DoAttack (AActor *self, bool domelee, bool domissile, DEFINE_ACTION_FUNCTION(AActor, A_MeleeAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int MeleeDamage = self->GetClass()->MeleeDamage; FSoundID MeleeSound = self->GetClass()->MeleeSound; DoAttack(self, true, false, MeleeDamage, MeleeSound, NULL, 0); @@ -989,7 +989,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MeleeAttack) DEFINE_ACTION_FUNCTION(AActor, A_MissileAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PClassActor *MissileType = PClass::FindActor(self->GetClass()->MissileName); DoAttack(self, false, true, 0, 0, MissileType, self->GetClass()->MissileHeight); return 0; @@ -997,7 +997,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MissileAttack) DEFINE_ACTION_FUNCTION(AActor, A_ComboAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int MeleeDamage = self->GetClass()->MeleeDamage; FSoundID MeleeSound = self->GetClass()->MeleeSound; PClassActor *MissileType = PClass::FindActor(self->GetClass()->MissileName); @@ -1028,7 +1028,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BasicAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlaySound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_SOUND_OPT (soundid) { soundid = "weapons/pistol"; } PARAM_INT_OPT (channel) { channel = CHAN_BODY; } PARAM_FLOAT_OPT (volume) { volume = 1; } @@ -1051,7 +1051,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlaySound) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StopSound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(slot) { slot = CHAN_VOICE; } S_StopSound(self, slot); @@ -1167,7 +1167,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SeekerMissile) //========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_BulletAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int i; @@ -1415,7 +1415,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Explode) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (damage) { damage = -1; } PARAM_INT_OPT (distance) { distance = -1; } PARAM_INT_OPT (flags) { flags = XF_HURTSOURCE; } @@ -1484,7 +1484,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RadiusThrust) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (force) { force = 128; } PARAM_INT_OPT (distance) { distance = -1; } PARAM_INT_OPT (flags) { flags = RTF_AFFECTSOURCE; } @@ -1524,7 +1524,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RadiusDamageSelf) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(damage) { damage = 128; } PARAM_FLOAT_OPT(distance) { distance = 128; } PARAM_INT_OPT(flags) { flags = 0; } @@ -1859,7 +1859,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomBulletAttack) //========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomMeleeAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (damage) { damage = 0; } PARAM_SOUND_OPT (meleesound) { meleesound = 0; } PARAM_SOUND_OPT (misssound) { misssound = 0; } @@ -1946,7 +1946,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomComboAttack) //========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfNoAmmo) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_STATE(jump); if (!ACTION_CALL_FROM_PSPRITE() || self->player->ReadyWeapon == nullptr) @@ -2017,7 +2017,7 @@ static void AimBulletMissile(AActor *proj, AActor *puff, int flags, bool temp, b DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireBullets) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_ANGLE (spread_xy); PARAM_ANGLE (spread_z); PARAM_INT (numbullets); @@ -2147,7 +2147,7 @@ enum FP_Flags }; DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireCustomMissile) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS (ti, AActor); PARAM_ANGLE_OPT (angle) { angle = 0.; } PARAM_BOOL_OPT (useammo) { useammo = true; } @@ -2224,7 +2224,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomPunch) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (damage); PARAM_BOOL_OPT (norandom) { norandom = false; } PARAM_INT_OPT (flags) { flags = CPF_USEAMMO; } @@ -2328,7 +2328,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomPunch) //========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RailAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (damage); PARAM_INT_OPT (spawnofs_xy) { spawnofs_xy = 0; } PARAM_BOOL_OPT (useammo) { useammo = true; } @@ -2632,7 +2632,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GiveToSiblings) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetInventory) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(itemtype, AInventory); PARAM_INT(amount); PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } @@ -3012,7 +3012,7 @@ static bool InitSpawnedItem(AActor *self, AActor *mo, int flags) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnItem) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS_OPT (missile, AActor) { missile = PClass::FindActor("Unknown"); } PARAM_FLOAT_OPT (distance) { distance = 0; } PARAM_FLOAT_OPT (zheight) { zheight = 0; } @@ -3144,7 +3144,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnItemEx) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ThrowGrenade) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS (missile, AActor); PARAM_FLOAT_OPT (zheight) { zheight = 0; } PARAM_FLOAT_OPT (xyvel) { xyvel = 0; } @@ -3442,7 +3442,7 @@ enum FadeFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeIn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(reduce) { reduce = 0.1; } PARAM_INT_OPT(flags) { flags = 0; } @@ -3476,7 +3476,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeIn) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeOut) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(reduce) { reduce = 0.1; } PARAM_INT_OPT(flags) { flags = FTF_REMOVE; } @@ -4036,7 +4036,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckCeiling) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_Stop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->Vel.Zero(); if (self->player && self->player->mo == self && !(self->player->cheats & CF_PREDICTING)) { @@ -4074,7 +4074,7 @@ enum RS_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Respawn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(flags) { flags = RSF_FOG; } bool oktorespawn = false; @@ -4189,7 +4189,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetGravity) DEFINE_ACTION_FUNCTION(AActor, A_ClearTarget) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->target = NULL; self->LastHeard = NULL; self->lastenemy = NULL; @@ -4747,7 +4747,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckForReload) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if ( self->player == NULL || self->player->ReadyWeapon == NULL ) { @@ -4800,7 +4800,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckForReload) DEFINE_ACTION_FUNCTION(AActor, A_ResetReloadCounter) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player == NULL || self->player->ReadyWeapon == NULL) return 0; @@ -4859,7 +4859,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFlag) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RaiseMaster) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL_OPT(copy) { copy = false; } if (self->master != NULL) @@ -4876,7 +4876,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RaiseMaster) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RaiseChildren) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL_OPT(copy) { copy = false; } TThinkerIterator it; @@ -4899,7 +4899,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RaiseChildren) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_RaiseSiblings) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL_OPT(copy) { copy = false; } TThinkerIterator it; @@ -4975,7 +4975,7 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetAngle) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(angle) { angle = 0; } PARAM_INT_OPT(flags) { flags = 0; } PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } @@ -5077,7 +5077,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ScaleVelocity) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeVelocity) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT (x) { x = 0; } PARAM_FLOAT_OPT (y) { y = 0; } PARAM_FLOAT_OPT (z) { z = 0; } @@ -5302,7 +5302,7 @@ enum T_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Teleport) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_STATE_OPT (teleport_state) { teleport_state = NULL; } PARAM_CLASS_OPT (target_type, ASpecialSpot) { target_type = PClass::FindActor("BossSpot"); } PARAM_CLASS_OPT (fog_type, AActor) { fog_type = PClass::FindActor("TeleportFog"); } @@ -5478,7 +5478,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Teleport) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Turn) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(angle) { angle = 0; } self->Angles.Yaw += angle; return 0; @@ -5606,7 +5606,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Weave) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_LineEffect) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(special) { special = 0; } PARAM_INT_OPT(tag) { tag = 0; } @@ -5641,7 +5641,7 @@ enum WolfAttackFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_WolfAttack) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (flags) { flags = 0; } PARAM_SOUND_OPT (sound) { sound = "weapons/pistol"; } PARAM_FLOAT_OPT (snipe) { snipe = 1.; } @@ -5746,7 +5746,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_WolfAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Warp) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT(destination_selector); PARAM_FLOAT_OPT(xofs) { xofs = 0; } PARAM_FLOAT_OPT(yofs) { yofs = 0; } @@ -6170,7 +6170,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSpecies) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetTics) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT(tics_to_set); if (ACTION_CALL_FROM_PSPRITE()) @@ -6567,7 +6567,7 @@ static void DoKill(AActor *killtarget, AActor *inflictor, AActor *source, FName //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6590,7 +6590,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6613,7 +6613,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6636,7 +6636,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6667,7 +6667,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6743,7 +6743,7 @@ static void DoRemove(AActor *removetarget, int flags, PClassActor *filter, FName //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } PARAM_NAME_OPT (species) { species = NAME_None; } @@ -6762,7 +6762,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } PARAM_NAME_OPT (species) { species = NAME_None; } @@ -6781,7 +6781,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } PARAM_NAME_OPT (species) { species = NAME_None; } @@ -6800,7 +6800,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL_OPT (removeall) { removeall = false; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6826,7 +6826,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL_OPT (removeall) { removeall = false; } PARAM_INT_OPT (flags) { flags = 0; } PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } @@ -6897,7 +6897,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetTeleFog) DEFINE_ACTION_FUNCTION(AActor, A_SwapTeleFog) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if ((self->TeleFogSourceType != self->TeleFogDestType)) //Does nothing if they're the same. { PClassActor *temp = self->TeleFogSourceType; @@ -6974,7 +6974,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetHealth) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ResetHealth) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } AActor *mobj = COPY_AAPTR(self, ptr); @@ -7291,7 +7291,7 @@ enum FMDFlags }; DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceMovementDirection) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE_OPT(offset) { offset = 0.; } PARAM_ANGLE_OPT(anglelimit) { anglelimit = 0.; } PARAM_ANGLE_OPT(pitchlimit) { pitchlimit = 0.; } @@ -7385,7 +7385,7 @@ enum CPSFFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopySpriteFrame) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT(from); PARAM_INT(to); PARAM_INT_OPT(flags) { flags = 0; } @@ -7412,7 +7412,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopySpriteFrame) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpriteAngle) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(angle) { angle = 0.; } PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } @@ -7435,7 +7435,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpriteAngle) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpriteRotation) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE_OPT(angle) { angle = 0.; } PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } @@ -7466,7 +7466,7 @@ enum VRFFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetVisibleRotation) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE_OPT(anglestart) { anglestart = 0.; } PARAM_ANGLE_OPT(angleend) { angleend = 0.; } PARAM_ANGLE_OPT(pitchstart) { pitchstart = 0.; } diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 5f63ff1e5..1a2bddda4 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -1789,7 +1789,7 @@ bool P_LookForPlayers (AActor *actor, INTBOOL allaround, FLookExParams *params) // DEFINE_ACTION_FUNCTION(AActor, A_Look) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *targ; @@ -1909,7 +1909,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Look) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_LookEx) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT (flags) { flags = 0; } PARAM_FLOAT_OPT (minseedist) { minseedist = 0; } PARAM_FLOAT_OPT (maxseedist) { maxseedist = 0; } @@ -2101,7 +2101,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_LookEx) DEFINE_ACTION_FUNCTION(AActor, A_ClearLastHeard) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); self->LastHeard = NULL; return 0; } @@ -2126,7 +2126,7 @@ enum ChaseFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Wander) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(flags) { flags = 0; } A_Wander(self, flags); return 0; @@ -2186,7 +2186,7 @@ void A_Wander(AActor *self, int flags) //========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_Look2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); AActor *targ; @@ -2768,7 +2768,7 @@ static bool P_CheckForResurrection(AActor *self, bool usevilestates) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Chase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_STATE_OPT (melee) { melee = NULL; } PARAM_STATE_OPT (missile) { missile = NULL; } PARAM_INT_OPT (flags) { flags = 0; } @@ -2790,14 +2790,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Chase) DEFINE_ACTION_FUNCTION(AActor, A_FastChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_DoChase(stack, self, true, self->MeleeState, self->MissileState, true, true, false, 0); return 0; } DEFINE_ACTION_FUNCTION(AActor, A_VileChase) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!P_CheckForResurrection(self, true)) { A_DoChase(stack, self, false, self->MeleeState, self->MissileState, true, gameinfo.nightmarefast, false, 0); @@ -2947,7 +2947,7 @@ void A_FaceTarget(AActor *self) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceTarget) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE_OPT(max_turn) { max_turn = 0.; } PARAM_ANGLE_OPT(max_pitch) { max_pitch = 270.; } PARAM_ANGLE_OPT(ang_offset) { ang_offset = 0.; } @@ -2961,7 +2961,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceTarget) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceMaster) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE_OPT(max_turn) { max_turn = 0.; } PARAM_ANGLE_OPT(max_pitch) { max_pitch = 270.; } PARAM_ANGLE_OPT(ang_offset) { ang_offset = 0.; } @@ -2975,7 +2975,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceMaster) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceTracer) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE_OPT(max_turn) { max_turn = 0.; } PARAM_ANGLE_OPT(max_pitch) { max_pitch = 270.; } PARAM_ANGLE_OPT(ang_offset) { ang_offset = 0.; } @@ -2996,7 +2996,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceTracer) //=========================================================================== DEFINE_ACTION_FUNCTION(AActor, A_MonsterRail) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (!self->target) return 0; @@ -3042,7 +3042,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MonsterRail) DEFINE_ACTION_FUNCTION(AActor, A_Scream) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->DeathSound) { // Check for bosses. @@ -3061,7 +3061,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Scream) DEFINE_ACTION_FUNCTION(AActor, A_XScream) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player) S_Sound (self, CHAN_VOICE, "*gibbed", 1, ATTN_NORM); else @@ -3077,7 +3077,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_XScream) DEFINE_ACTION_FUNCTION(AActor, A_ScreamAndUnblock) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_Scream, self); A_Unblock(self, true); return 0; @@ -3091,7 +3091,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ScreamAndUnblock) DEFINE_ACTION_FUNCTION(AActor, A_ActiveSound) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->ActiveSound) { S_Sound (self, CHAN_VOICE, self->ActiveSound, 1, ATTN_NORM); @@ -3107,7 +3107,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ActiveSound) DEFINE_ACTION_FUNCTION(AActor, A_ActiveAndUnblock) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); CALL_ACTION(A_ActiveSound, self); A_Unblock(self, true); return 0; @@ -3257,7 +3257,7 @@ void P_TossItem (AActor *item) DEFINE_ACTION_FUNCTION(AActor, A_Pain) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); // [RH] Vary player pain sounds depending on health (ala Quake2) if (self->player && self->player->morphTics == 0) @@ -3306,7 +3306,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Pain) // killough 11/98: kill an object DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Die) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } P_DamageMobj(self, NULL, NULL, self->health, damagetype, DMG_FORCED); @@ -3320,7 +3320,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Die) DEFINE_ACTION_FUNCTION(AActor, A_Detonate) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int damage = self->GetMissileDamage(0, 1); P_RadiusAttack (self, self->target, damage, damage, self->DamageType, RADF_HURTSOURCE); P_CheckSplash(self, damage); @@ -3463,7 +3463,7 @@ void A_BossDeath(AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_BossDeath) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); A_BossDeath(self); return 0; } @@ -3541,7 +3541,7 @@ bool A_RaiseMobj (AActor *actor, double speed) DEFINE_ACTION_FUNCTION(AActor, A_ClassBossHealth) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (multiplayer && !deathmatch) // co-op only { if (!self->special1) diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index e2e0778ab..055649466 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -743,7 +743,7 @@ void DoReadyWeapon(AActor *self) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_WeaponReady) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(flags) { flags = 0; } DoReadyWeaponToSwitch(self, !(flags & WRF_NoSwitch)); @@ -875,7 +875,7 @@ static void P_CheckWeaponButtons (player_t *player) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_ReFire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_STATE_OPT(state) { state = NULL; } A_ReFire(self, state); return 0; @@ -913,7 +913,7 @@ void A_ReFire(AActor *self, FState *state) DEFINE_ACTION_FUNCTION(AInventory, A_ClearReFire) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; if (NULL != player) @@ -935,7 +935,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_ClearReFire) DEFINE_ACTION_FUNCTION(AInventory, A_CheckReload) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -1002,7 +1002,7 @@ void A_OverlayOffset(AActor *self, int layer, double wx, double wy, int flags) DEFINE_ACTION_FUNCTION(AActor, A_OverlayOffset) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT_OPT(layer) { layer = PSP_WEAPON; } PARAM_FLOAT_OPT(wx) { wx = 0.; } PARAM_FLOAT_OPT(wy) { wy = 32.; } @@ -1013,7 +1013,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_OverlayOffset) DEFINE_ACTION_FUNCTION(AActor, A_WeaponOffset) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_OPT(wx) { wx = 0.; } PARAM_FLOAT_OPT(wy) { wy = 32.; } PARAM_INT_OPT(flags) { flags = 0; } @@ -1029,7 +1029,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WeaponOffset) DEFINE_ACTION_FUNCTION(AActor, A_OverlayFlags) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT(layer); PARAM_INT(flags); PARAM_BOOL(set); @@ -1072,7 +1072,7 @@ static double GetOverlayPosition(AActor *self, int layer, bool gety) DEFINE_ACTION_FUNCTION(AActor, OverlayX) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT_OPT(layer) { layer = 0; } if (ACTION_CALL_FROM_PSPRITE()) @@ -1085,7 +1085,7 @@ DEFINE_ACTION_FUNCTION(AActor, OverlayX) DEFINE_ACTION_FUNCTION(AActor, OverlayY) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT_OPT(layer) { layer = 0; } if (ACTION_CALL_FROM_PSPRITE()) @@ -1104,7 +1104,7 @@ DEFINE_ACTION_FUNCTION(AActor, OverlayY) DEFINE_ACTION_FUNCTION(AActor, OverlayID) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); if (ACTION_CALL_FROM_PSPRITE()) { @@ -1123,7 +1123,7 @@ DEFINE_ACTION_FUNCTION(AActor, OverlayID) DEFINE_ACTION_FUNCTION(AInventory, A_Lower) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); player_t *player = self->player; DPSprite *psp; @@ -1171,7 +1171,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_Lower) DEFINE_ACTION_FUNCTION(AInventory, A_Raise) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self == nullptr) { @@ -1212,7 +1212,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_Raise) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Overlay) { - PARAM_ACTION_PROLOGUE; + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (layer); PARAM_STATE_OPT (state) { state = nullptr; } PARAM_BOOL_OPT (dontoverride) { dontoverride = false; } @@ -1232,7 +1232,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Overlay) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ClearOverlays) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT_OPT(start) { start = 0; } PARAM_INT_OPT(stop) { stop = 0; } PARAM_BOOL_OPT(safety) { safety = true; } @@ -1283,7 +1283,7 @@ enum GF_Flags DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_GunFlash) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_STATE_OPT(flash) { flash = nullptr; } PARAM_INT_OPT (flags) { flags = 0; } @@ -1373,7 +1373,7 @@ void P_GunShot (AActor *mo, bool accurate, PClassActor *pufftype, DAngle pitch) DEFINE_ACTION_FUNCTION(AInventory, A_Light0) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -1384,7 +1384,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_Light0) DEFINE_ACTION_FUNCTION(AInventory, A_Light1) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -1395,7 +1395,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_Light1) DEFINE_ACTION_FUNCTION(AInventory, A_Light2) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player != NULL) { @@ -1406,7 +1406,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_Light2) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_Light) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_INT(light); if (self->player != NULL) diff --git a/src/p_user.cpp b/src/p_user.cpp index 7cea484de..00d22a9ba 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -1546,7 +1546,7 @@ void APlayerPawn::TweakSpeeds (double &forward, double &side) DEFINE_ACTION_FUNCTION(AActor, A_PlayerScream) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); int sound = 0; int chan = CHAN_VOICE; @@ -1622,7 +1622,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PlayerScream) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullPop) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS_OPT(spawntype, APlayerChunk) { spawntype = NULL; } APlayerPawn *mo; @@ -1672,7 +1672,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullPop) DEFINE_ACTION_FUNCTION(AActor, A_CheckPlayerDone) { - PARAM_ACTION_PROLOGUE; + PARAM_SELF_PROLOGUE(AActor); if (self->player == NULL) { diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 1de5c13c2..c4a466873 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5281,50 +5281,31 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } } - // If both functions are non-action or both are action, there is no need for special treatment. - //if (elf || (!!(Function->Variants[0].Flags & VARF_Action) == build->IsActionFunc)) + // Emit code to pass implied parameters + if (Function->Variants[0].Flags & VARF_Method) { - // Emit code to pass implied parameters - if (Function->Variants[0].Flags & VARF_Method) - { - assert(Self != nullptr); - Self->Emit(build); - count += 1; - } - if (Function->Variants[0].Flags & VARF_Action) - { - static_assert(NAP == 3, "This code needs to be updated if NAP changes"); - if (build->IsActionFunc) - { - build->Emit(OP_PARAM, 0, REGT_POINTER, 1); - build->Emit(OP_PARAM, 0, REGT_POINTER, 2); - } - else - { - int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - } - count += 2; - } + assert(Self != nullptr); + ExpEmit selfemit = Self->Emit(build); + assert(selfemit.RegType == REGT_POINTER); + build->Emit(OP_PARAM, 0, selfemit.RegType, selfemit.RegNum); + count += 1; } - /* - else + if (Function->Variants[0].Flags & VARF_Action) { - if (build->IsActionFunc && (Function->Variants[0].Flags & VARF_Method)) + static_assert(NAP == 3, "This code needs to be updated if NAP changes"); + if (build->IsActionFunc) { - build->Emit(OP_PARAM, 0, REGT_POINTER, 0); - count += 1; + build->Emit(OP_PARAM, 0, REGT_POINTER, 1); + build->Emit(OP_PARAM, 0, REGT_POINTER, 2); } - // and calling an action function from a non-action function. - // This must be blocked because it lacks crucial information. - if (!build->IsActionFunc && (Function->Variants[0].Flags & VARF_Action)) + else { - // This case should be eliminated in the analyzing stage. - I_Error("Cannot call action function from non-action functions."); + int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); } + count += 2; } - */ // Emit code to pass explicit parameters if (ArgList != NULL) diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 4c09e8664..5144a1bd0 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -68,139 +68,139 @@ class Actor : Thinker native // Action functions // Meh, MBF redundant functions. Only for DeHackEd support. - action native void A_Turn(float angle = 0); - action native bool A_LineEffect(int boomspecial = 0, int tag = 0); + native void A_Turn(float angle = 0); + native bool A_LineEffect(int boomspecial = 0, int tag = 0); // End of MBF redundant functions. - action native void A_MonsterRail(); - action native void A_BFGSpray(class spraytype = "BFGExtra", int numrays = 40, int damagecount = 15, float angle = 90, float distance = 16*64, float vrange = 32, int damage = 0, int flags = 0); - action native void A_Pain(); - action native void A_NoBlocking(); - action native void A_XScream(); - action native void A_Look(); - action native void A_Chase(state melee = "*", state missile = "none", int flags = 0); - action native void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - action native void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - action native void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - action native void A_PosAttack(); - action native void A_Scream(); - action native void A_SPosAttack(); - action native void A_SPosAttackUseAtkSound(); - action native void A_VileChase(); - action native void A_VileStart(); - action native void A_VileTarget(class fire = "ArchvileFire"); - action native void A_VileAttack(sound snd = "vile/stop", int initialdmg = 20, int blastdmg = 70, int blastradius = 70, float thrustfac = 1.0, name damagetype = "Fire", int flags = 0); - action native void A_StartFire(); - action native void A_Fire(float spawnheight = 0); - action native void A_FireCrackle(); - action native void A_Tracer(); - action native void A_SkelWhoosh(); - action native void A_SkelFist(); - action native void A_SkelMissile(); - action native void A_FatRaise(); - action native void A_FatAttack1(class spawntype = "FatShot"); - action native void A_FatAttack2(class spawntype = "FatShot"); - action native void A_FatAttack3(class spawntype = "FatShot"); - action native void A_BossDeath(); - action native void A_CPosAttack(); - action native void A_CPosRefire(); - action native void A_TroopAttack(); - action native void A_SargAttack(); - action native void A_HeadAttack(); - action native void A_BruisAttack(); - action native void A_SkullAttack(float speed = 20); - action native void A_BetaSkullAttack(); - action native void A_Metal(); - action native void A_SpidRefire(); - action native void A_BabyMetal(); - action native void A_BspiAttack(); - action native void A_Hoof(); - action native void A_CyberAttack(); - action native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); - action native void A_DualPainAttack(class spawntype = "LostSoul"); - action native void A_PainDie(class spawntype = "LostSoul"); - action native void A_KeenDie(int doortag = 666); - action native void A_BrainPain(); - action native void A_BrainScream(); - action native void A_BrainDie(); - action native void A_BrainAwake(); - action native void A_BrainSpit(class spawntype = "none"); // needs special treatment for default - action native void A_SpawnSound(); - action native void A_SpawnFly(class spawntype = "none"); // needs special treatment for default - action native void A_BrainExplode(); - action native void A_Die(name damagetype = "none"); - action native void A_Detonate(); - action native void A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5); + native void A_MonsterRail(); + native void A_BFGSpray(class spraytype = "BFGExtra", int numrays = 40, int damagecount = 15, float angle = 90, float distance = 16*64, float vrange = 32, int damage = 0, int flags = 0); + native void A_Pain(); + native void A_NoBlocking(); + native void A_XScream(); + native void A_Look(); + native void A_Chase(state melee = "*", state missile = "none", int flags = 0); + native void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + native void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + native void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + native void A_PosAttack(); + native void A_Scream(); + native void A_SPosAttack(); + native void A_SPosAttackUseAtkSound(); + native void A_VileChase(); + native void A_VileStart(); + native void A_VileTarget(class fire = "ArchvileFire"); + native void A_VileAttack(sound snd = "vile/stop", int initialdmg = 20, int blastdmg = 70, int blastradius = 70, float thrustfac = 1.0, name damagetype = "Fire", int flags = 0); + native void A_StartFire(); + native void A_Fire(float spawnheight = 0); + native void A_FireCrackle(); + native void A_Tracer(); + native void A_SkelWhoosh(); + native void A_SkelFist(); + native void A_SkelMissile(); + native void A_FatRaise(); + native void A_FatAttack1(class spawntype = "FatShot"); + native void A_FatAttack2(class spawntype = "FatShot"); + native void A_FatAttack3(class spawntype = "FatShot"); + native void A_BossDeath(); + native void A_CPosAttack(); + native void A_CPosRefire(); + native void A_TroopAttack(); + native void A_SargAttack(); + native void A_HeadAttack(); + native void A_BruisAttack(); + native void A_SkullAttack(float speed = 20); + native void A_BetaSkullAttack(); + native void A_Metal(); + native void A_SpidRefire(); + native void A_BabyMetal(); + native void A_BspiAttack(); + native void A_Hoof(); + native void A_CyberAttack(); + native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); + native void A_DualPainAttack(class spawntype = "LostSoul"); + native void A_PainDie(class spawntype = "LostSoul"); + native void A_KeenDie(int doortag = 666); + native void A_BrainPain(); + native void A_BrainScream(); + native void A_BrainDie(); + native void A_BrainAwake(); + native void A_BrainSpit(class spawntype = "none"); // needs special treatment for default + native void A_SpawnSound(); + native void A_SpawnFly(class spawntype = "none"); // needs special treatment for default + native void A_BrainExplode(); + native void A_Die(name damagetype = "none"); + native void A_Detonate(); + native void A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); - action native void A_SetFloorClip(); - action native void A_UnSetFloorClip(); - action native void A_HideThing(); - action native void A_UnHideThing(); - action native void A_SetInvulnerable(); - action native void A_UnSetInvulnerable(); - action native void A_SetReflective(); - action native void A_UnSetReflective(); - action native void A_SetReflectiveInvulnerable(); - action native void A_UnSetReflectiveInvulnerable(); - action native void A_SetShootable(); - action native void A_UnSetShootable(); - action native void A_NoGravity(); - action native void A_Gravity(); - action native void A_LowGravity(); + native void A_SetFloorClip(); + native void A_UnSetFloorClip(); + native void A_HideThing(); + native void A_UnHideThing(); + native void A_SetInvulnerable(); + native void A_UnSetInvulnerable(); + native void A_SetReflective(); + native void A_UnSetReflective(); + native void A_SetReflectiveInvulnerable(); + native void A_UnSetReflectiveInvulnerable(); + native void A_SetShootable(); + native void A_UnSetShootable(); + native void A_NoGravity(); + native void A_Gravity(); + native void A_LowGravity(); native void A_SetGravity(float gravity); - action native void A_Fall(); - action native void A_SetSolid(); - action native void A_UnsetSolid(); - action native void A_SetFloat(); - action native void A_UnsetFloat(); + native void A_Fall(); + native void A_SetSolid(); + native void A_UnsetSolid(); + native void A_SetFloat(); + native void A_UnsetFloat(); - action native void A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); + native void A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); - action native void A_ScreamAndUnblock(); - action native void A_ActiveAndUnblock(); - action native void A_ActiveSound(); + native void A_ScreamAndUnblock(); + native void A_ActiveAndUnblock(); + native void A_ActiveSound(); - action native void A_FastChase(); - action native void A_FreezeDeath(); - action native void A_FreezeDeathChunks(); - action native void A_GenericFreezeDeath(); - action native void A_IceGuyDie(); - action native void A_CentaurDefend(); - action native void A_BishopMissileWeave(); - action native void A_CStaffMissileSlither(); - action native void A_PlayerScream(); - action native void A_SkullPop(class skulltype = "BloodySkull"); - action native void A_CheckPlayerDone(); + native void A_FastChase(); + native void A_FreezeDeath(); + native void A_FreezeDeathChunks(); + native void A_GenericFreezeDeath(); + native void A_IceGuyDie(); + native void A_CentaurDefend(); + native void A_BishopMissileWeave(); + native void A_CStaffMissileSlither(); + native void A_PlayerScream(); + native void A_SkullPop(class skulltype = "BloodySkull"); + native void A_CheckPlayerDone(); - action native void A_Wander(int flags = 0); - action native void A_Look2(); - action native void A_TossGib(); - action native void A_SentinelBob(); - action native void A_SentinelRefire(); - action native void A_Tracer2(); - action native void A_SetShadow(); - action native void A_ClearShadow(); - action native void A_GetHurt(); - action native void A_TurretLook(); - action native void A_KlaxonBlare(); - action native void A_Countdown(); - action native void A_AlertMonsters(float maxdist = 0, int flags = 0); - action native void A_ClearSoundTarget(); - action native void A_FireAssaultGun(); - action native void A_CheckTerrain(); - action native void A_FaceConsolePlayer(float MaxTurnAngle = 0); // [TP] no-op + native void A_Wander(int flags = 0); + native void A_Look2(); + native void A_TossGib(); + native void A_SentinelBob(); + native void A_SentinelRefire(); + native void A_Tracer2(); + native void A_SetShadow(); + native void A_ClearShadow(); + native void A_GetHurt(); + native void A_TurretLook(); + native void A_KlaxonBlare(); + native void A_Countdown(); + native void A_AlertMonsters(float maxdist = 0, int flags = 0); + native void A_ClearSoundTarget(); + native void A_FireAssaultGun(); + native void A_CheckTerrain(); + native void A_FaceConsolePlayer(float MaxTurnAngle = 0); // [TP] no-op - deprecated action native void A_MissileAttack(); - deprecated action native void A_MeleeAttack(); - deprecated action native void A_ComboAttack(); - deprecated action native void A_BulletAttack(); - action native void A_WolfAttack(int flags = 0, sound whattoplay = "weapons/pistol", float snipe = 1.0, int maxdamage = 64, int blocksize = 128, int pointblank = 2, int longrange = 4, float runspeed = 160.0, class pufftype = "BulletPuff"); - action native void A_PlaySound(sound whattoplay = "weapons/pistol", int slot = CHAN_BODY, float volume = 1.0, bool looping = false, float attenuation = ATTN_NORM); + deprecated native void A_MissileAttack(); + deprecated native void A_MeleeAttack(); + deprecated native void A_ComboAttack(); + deprecated native void A_BulletAttack(); + native void A_WolfAttack(int flags = 0, sound whattoplay = "weapons/pistol", float snipe = 1.0, int maxdamage = 64, int blocksize = 128, int pointblank = 2, int longrange = 4, float runspeed = 160.0, class pufftype = "BulletPuff"); + native void A_PlaySound(sound whattoplay = "weapons/pistol", int slot = CHAN_BODY, float volume = 1.0, bool looping = false, float attenuation = ATTN_NORM); native void A_PlayWeaponSound(sound whattoplay); - action native void A_FLoopActiveSound(); - action native void A_LoopActiveSound(); - action native void A_StopSound(int slot = CHAN_VOICE); // Bad default but that's what is originally was... + native void A_FLoopActiveSound(); + native void A_LoopActiveSound(); + native void A_StopSound(int slot = CHAN_VOICE); // Bad default but that's what is originally was... deprecated native void A_PlaySoundEx(sound whattoplay, name slot, bool looping = false, int attenuation = 0); deprecated native void A_StopSoundEx(name slot); native void A_SeekerMissile(int threshold, int turnmax, int flags = 0, int chance = 50, int distance = 10); @@ -227,8 +227,8 @@ class Actor : Thinker native native void A_LogFloat(float whattoprint); native void A_SetTranslucent(float alpha, int style = 0); native void A_SetRenderStyle(float alpha, int style); - action native void A_FadeIn(float reduce = 0.1, int flags = 0); - action native void A_FadeOut(float reduce = 0.1, int flags = 1); //bool remove == true + native void A_FadeIn(float reduce = 0.1, int flags = 0); + native void A_FadeOut(float reduce = 0.1, int flags = 1); //bool remove == true native void A_FadeTo(float target, float amount = 0.1, int flags = 0); native void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false); native void A_SetMass(int mass); @@ -241,15 +241,15 @@ class Actor : Thinker native native void A_ChangeFlag(string flagname, bool value); native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); native state A_JumpIf(bool expression, state label); - action native void A_RaiseMaster(bool copy = 0); - action native void A_RaiseChildren(bool copy = 0); - action native void A_RaiseSiblings(bool copy = 0); + native void A_RaiseMaster(bool copy = 0); + native void A_RaiseChildren(bool copy = 0); + native void A_RaiseSiblings(bool copy = 0); native state A_CheckFloor(state label); native state A_CheckCeiling(state label); native state A_PlayerSkinCheck(state label); deprecated native void A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); - action native state, bool A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); - action native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = "", float heightoffset = 0, float radiusoffset = 0, float pitch = 0); + native state, bool A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); + native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = "", float heightoffset = 0, float radiusoffset = 0, float pitch = 0); action native bool A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); @@ -260,42 +260,42 @@ class Actor : Thinker native native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = "None", name species = "None", float mindist = 0, int limit = 0); native state A_CheckSpecies(state jump, name species = "", int ptr = AAPTR_DEFAULT); native void A_CountdownArg(int argnum, state targstate = ""); - action native void A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); + native void A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); native void A_CustomComboAttack(class missiletype, float spawnheight, int damage, sound meleesound = "", name damagetype = "none", bool bleed = true); native void A_Burst(class chunktype); action native void A_Blast(int flags = 0, float strength = 255, float radius = 255, float speed = 20, class blasteffect = "BlastEffect", sound blastsound = "BlastRadius"); - action native void A_RadiusThrust(int force = 128, int distance = -1, int flags = RTF_AFFECTSOURCE, int fullthrustdistance = 0); - action native void A_RadiusDamageSelf(int damage = 128, float distance = 128, int flags = 0, class flashtype = "None"); - action native int A_Explode(int damage = -1, int distance = -1, int flags = XF_HURTSOURCE, bool alert = false, int fulldamagedistance = 0, int nails = 0, int naildamage = 10, class pufftype = "BulletPuff", name damagetype = "none"); - action native void A_Stop(); - action native void A_Respawn(int flags = 1); - action native void A_BarrelDestroy(); - action native void A_QueueCorpse(); - action native void A_DeQueueCorpse(); - action native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = ""); - action native void A_ClearLastHeard(); - action native void A_ClearTarget(); + native void A_RadiusThrust(int force = 128, int distance = -1, int flags = RTF_AFFECTSOURCE, int fullthrustdistance = 0); + native void A_RadiusDamageSelf(int damage = 128, float distance = 128, int flags = 0, class flashtype = "None"); + native int A_Explode(int damage = -1, int distance = -1, int flags = XF_HURTSOURCE, bool alert = false, int fulldamagedistance = 0, int nails = 0, int naildamage = 10, class pufftype = "BulletPuff", name damagetype = "none"); + native void A_Stop(); + native void A_Respawn(int flags = 1); + native void A_BarrelDestroy(); + native void A_QueueCorpse(); + native void A_DeQueueCorpse(); + native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = ""); + native void A_ClearLastHeard(); + native void A_ClearTarget(); native state A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); native state A_JumpIfTargetInLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); native state A_JumpIfInTargetLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); native bool A_SelectWeapon(class whichweapon, int flags = 0); action native void A_Punch(); - action native void A_Feathers(); - action native void A_ClassBossHealth(); - action native void A_ShootGun(); - action native void A_RocketInFlight(); - action native void A_Bang4Cloud(); - action native void A_DropFire(); + native void A_Feathers(); + native void A_ClassBossHealth(); + native void A_ShootGun(); + native void A_RocketInFlight(); + native void A_Bang4Cloud(); + native void A_DropFire(); native void A_GiveQuestItem(int itemno); - action native void A_RemoveForcefield(); + native void A_RemoveForcefield(); native void A_DropWeaponPieces(class p1, class p2, class p3); - action native void A_PigPain (); + native void A_PigPain (); native state A_MonsterRefire(int chance, state label); - action native void A_SetAngle(float angle = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_SetAngle(float angle = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetPitch(float pitch, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetRoll(float roll, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_ScaleVelocity(float scale, int ptr = AAPTR_DEFAULT); - action native void A_ChangeVelocity(float x = 0, float y = 0, float z = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native void A_ChangeVelocity(float x = 0, float y = 0, float z = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetArg(int pos, int value); deprecated native void A_SetUserVar(name varname, int value); deprecated native void A_SetUserArray(name varname, int index, int value); @@ -316,26 +316,26 @@ class Actor : Thinker native native void A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); native void A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); native void A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native void A_KillTarget(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native void A_KillMaster(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native void A_KillTracer(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native void A_KillChildren(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native void A_KillSiblings(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - action native void A_RemoveTarget(int flags = 0, class filter = "None", name species = "None"); - action native void A_RemoveMaster(int flags = 0, class filter = "None", name species = "None"); - action native void A_RemoveTracer(int flags = 0, class filter = "None", name species = "None"); - action native void A_RemoveChildren(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); - action native void A_RemoveSiblings(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); + native void A_KillTarget(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillMaster(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillTracer(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillChildren(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillSiblings(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_RemoveTarget(int flags = 0, class filter = "None", name species = "None"); + native void A_RemoveMaster(int flags = 0, class filter = "None", name species = "None"); + native void A_RemoveTracer(int flags = 0, class filter = "None", name species = "None"); + native void A_RemoveChildren(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); + native void A_RemoveSiblings(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); native void A_Remove(int removee, int flags = 0, class filter = "None", name species = "None"); native int A_GiveToChildren(class itemtype, int amount = 0); native int A_GiveToSiblings(class itemtype, int amount = 0); native int A_TakeFromChildren(class itemtype, int amount = 0); native int A_TakeFromSiblings(class itemtype, int amount = 0); native void A_SetTeleFog(class oldpos, class newpos); - action native void A_SwapTeleFog(); + native void A_SwapTeleFog(); native void A_SetFloatBobPhase(int bob); native void A_SetHealth(int health, int ptr = AAPTR_DEFAULT); - action native void A_ResetHealth(int ptr = AAPTR_DEFAULT); + native void A_ResetHealth(int ptr = AAPTR_DEFAULT); native state A_JumpIfHigherOrLower(state high, state low, float offsethigh = 0, float offsetlow = 0, bool includeHeight = true, int ptr = AAPTR_TARGET); native void A_SetSpecies(name species, int ptr = AAPTR_DEFAULT); native void A_SetRipperLevel(int level); @@ -346,20 +346,20 @@ class Actor : Thinker native native state A_CheckBlock(state block, int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0); native state A_CheckSightOrRange(float distance, state label, bool two_dimension = false); native state A_CheckRange(float distance, state label, bool two_dimension = false); - action native bool A_FaceMovementDirection(float offset = 0, float anglelimit = 0, float pitchlimit = 0, int flags = 0, int ptr = AAPTR_DEFAULT); - action native int A_ClearOverlays(int sstart = 0, int sstop = 0, bool safety = true); - action native bool A_CopySpriteFrame(int from, int to, int flags = 0); - action native bool A_SetSpriteAngle(float angle = 0, int ptr = AAPTR_DEFAULT); - action native bool A_SetSpriteRotation(float angle = 0, int ptr = AAPTR_DEFAULT); - action native bool A_SetVisibleRotation(float anglestart = 0, float angleend = 0, float pitchstart = 0, float pitchend = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native bool A_FaceMovementDirection(float offset = 0, float anglelimit = 0, float pitchlimit = 0, int flags = 0, int ptr = AAPTR_DEFAULT); + native int A_ClearOverlays(int sstart = 0, int sstop = 0, bool safety = true); + native bool A_CopySpriteFrame(int from, int to, int flags = 0); + native bool A_SetSpriteAngle(float angle = 0, int ptr = AAPTR_DEFAULT); + native bool A_SetSpriteRotation(float angle = 0, int ptr = AAPTR_DEFAULT); + native bool A_SetVisibleRotation(float anglestart = 0, float angleend = 0, float pitchstart = 0, float pitchend = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetTranslation(string transname); native void A_RearrangePointers(int newtarget, int newmaster = AAPTR_DEFAULT, int newtracer = AAPTR_DEFAULT, int flags=0); native void A_TransferPointer(int ptr_source, int ptr_recepient, int sourcefield, int recepientfield=AAPTR_DEFAULT, int flags=0); - action native void A_CopyFriendliness(int ptr_source = AAPTR_MASTER); + native void A_CopyFriendliness(int ptr_source = AAPTR_MASTER); action native bool A_Overlay(int layer, state start = "", bool nooverride = false); - action native void A_WeaponOffset(float wx = 0, float wy = 32, int flags = 0); + native void A_WeaponOffset(float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayOffset(int layer = PSP_WEAPON, float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayFlags(int layer, int flags, bool set); diff --git a/wadsrc/static/zscript/doom/scriptedmarine.txt b/wadsrc/static/zscript/doom/scriptedmarine.txt index 358bf4ea4..7a82513cb 100644 --- a/wadsrc/static/zscript/doom/scriptedmarine.txt +++ b/wadsrc/static/zscript/doom/scriptedmarine.txt @@ -19,22 +19,22 @@ class ScriptedMarine : Actor native PainSound "*pain50"; } - action native void A_M_Refire (bool ignoremissile=false); - action native void A_M_CheckAttack (); - action native void A_MarineChase (); - action native void A_MarineLook (); - action native void A_MarineNoise (); - action native void A_M_Punch (int force); - action native void A_M_SawRefire (); - action native void A_M_FirePistol (bool accurate); - action native void A_M_FireShotgun (); - action native void A_M_FireShotgun2 (); - action native void A_M_FireCGun(bool accurate); - action native void A_M_FireMissile (); - action native void A_M_FirePlasma (); - action native void A_M_FireRailgun (); - action native void A_M_BFGsound (); - action native void A_M_FireBFG (); + native void A_M_Refire (bool ignoremissile=false); + native void A_M_CheckAttack (); + native void A_MarineChase (); + native void A_MarineLook (); + native void A_MarineNoise (); + native void A_M_Punch (int force); + native void A_M_SawRefire (); + native void A_M_FirePistol (bool accurate); + native void A_M_FireShotgun (); + native void A_M_FireShotgun2 (); + native void A_M_FireCGun(bool accurate); + native void A_M_FireMissile (); + native void A_M_FirePlasma (); + native void A_M_FireRailgun (); + native void A_M_BFGsound (); + native void A_M_FireBFG (); States { diff --git a/wadsrc/static/zscript/heretic/chicken.txt b/wadsrc/static/zscript/heretic/chicken.txt index 2e5ada81c..77e2b0a92 100644 --- a/wadsrc/static/zscript/heretic/chicken.txt +++ b/wadsrc/static/zscript/heretic/chicken.txt @@ -26,8 +26,8 @@ class Beak : Weapon Weapon.SisterWeapon "BeakPowered"; } - action native void A_BeakRaise (); - action native void A_BeakAttackPL1(); + native void A_BeakRaise (); + native void A_BeakAttackPL1(); States { @@ -55,7 +55,7 @@ class BeakPowered : Beak Weapon.SisterWeapon "Beak"; } - action native void A_BeakAttackPL2(); + native void A_BeakAttackPL2(); States { diff --git a/wadsrc/static/zscript/heretic/dsparil.txt b/wadsrc/static/zscript/heretic/dsparil.txt index ebf60eb47..8cd60c8bb 100644 --- a/wadsrc/static/zscript/heretic/dsparil.txt +++ b/wadsrc/static/zscript/heretic/dsparil.txt @@ -38,10 +38,10 @@ class Sorcerer1 : Actor HitObituary "$OB_DSPARIL1HIT"; } - action native void A_Sor1Pain (); - action native void A_Sor1Chase (); - action native void A_Srcr1Attack (); - action native void A_SorcererRise (); + native void A_Sor1Pain (); + native void A_Sor1Chase (); + native void A_Srcr1Attack (); + native void A_SorcererRise (); States { @@ -142,10 +142,10 @@ class Sorcerer2 : Actor HitObituary "$OB_DSPARIL2HIT"; } - action native void A_Srcr2Decide (); - action native void A_Srcr2Attack (); - action native void A_Sor2DthInit (); - action native void A_Sor2DthLoop (); + native void A_Srcr2Decide (); + native void A_Srcr2Attack (); + native void A_Sor2DthInit (); + native void A_Sor2DthLoop (); States { @@ -210,7 +210,7 @@ class Sorcerer2FX1 : Actor RenderStyle "Add"; } - action native void A_BlueSpark (); + native void A_BlueSpark (); States { @@ -263,7 +263,7 @@ class Sorcerer2FX2 : Actor RenderStyle "Add"; } - action native void A_GenWizard (); + native void A_GenWizard (); States { diff --git a/wadsrc/static/zscript/heretic/hereticartifacts.txt b/wadsrc/static/zscript/heretic/hereticartifacts.txt index 154f48ad3..94271c8cd 100644 --- a/wadsrc/static/zscript/heretic/hereticartifacts.txt +++ b/wadsrc/static/zscript/heretic/hereticartifacts.txt @@ -80,7 +80,7 @@ Class ActivatedTimeBomb : Actor DeathSound "misc/timebomb"; } - action native void A_Timebomb(); + native void A_Timebomb(); States { diff --git a/wadsrc/static/zscript/heretic/hereticimp.txt b/wadsrc/static/zscript/heretic/hereticimp.txt index 9f5c0a23e..5764094de 100644 --- a/wadsrc/static/zscript/heretic/hereticimp.txt +++ b/wadsrc/static/zscript/heretic/hereticimp.txt @@ -26,10 +26,10 @@ class HereticImp : Actor HitObituary "$OB_HERETICIMPHIT"; } - action native void A_ImpMsAttack(); - action native void A_ImpDeath(); - action native void A_ImpXDeath1(); - action native void A_ImpExplode(); + native void A_ImpMsAttack(); + native void A_ImpDeath(); + native void A_ImpXDeath1(); + native void A_ImpExplode(); States diff --git a/wadsrc/static/zscript/heretic/hereticmisc.txt b/wadsrc/static/zscript/heretic/hereticmisc.txt index 0b90208b9..f858a6fa2 100644 --- a/wadsrc/static/zscript/heretic/hereticmisc.txt +++ b/wadsrc/static/zscript/heretic/hereticmisc.txt @@ -16,8 +16,8 @@ class Pod : Actor DeathSound "world/podexplode"; PushFactor 0.5; } - action native void A_PodPain (class podtype = "PodGoo"); - action native void A_RemovePod (); + native void A_PodPain (class podtype = "PodGoo"); + native void A_RemovePod (); States { @@ -75,7 +75,7 @@ class PodGenerator : Actor AttackSound "world/podgrow"; } - action native void A_MakePod (class podtype = "Pod"); + native void A_MakePod (class podtype = "Pod"); States { @@ -136,7 +136,7 @@ class TeleGlitter1 : Actor Damage 0; } - action native void A_AccTeleGlitter (); + native void A_AccTeleGlitter (); States { @@ -178,8 +178,8 @@ class Volcano : Actor +SOLID } - action native void A_VolcanoSet (); - action native void A_VolcanoBlast (); + native void A_VolcanoSet (); + native void A_VolcanoBlast (); States { @@ -210,7 +210,7 @@ class VolcanoBlast : Actor DeathSound "world/volcano/blast"; } - action native void A_VolcBallImpact (); + native void A_VolcBallImpact (); States { diff --git a/wadsrc/static/zscript/heretic/hereticweaps.txt b/wadsrc/static/zscript/heretic/hereticweaps.txt index eabecd9d8..0c3123c7c 100644 --- a/wadsrc/static/zscript/heretic/hereticweaps.txt +++ b/wadsrc/static/zscript/heretic/hereticweaps.txt @@ -23,7 +23,7 @@ class Staff : HereticWeapon Tag "$TAG_STAFF"; } - action native void A_StaffAttack (int damage, class puff); + native void A_StaffAttack (int damage, class puff); States { @@ -142,7 +142,7 @@ class GoldWand : HereticWeapon Tag "$TAG_GOLDWAND"; } - action native void A_FireGoldWandPL1 (); + native void A_FireGoldWandPL1 (); States { @@ -178,7 +178,7 @@ class GoldWandPowered : GoldWand Tag "$TAG_GOLDWANDP"; } - action native void A_FireGoldWandPL2 (); + native void A_FireGoldWandPL2 (); States { @@ -294,7 +294,7 @@ class Crossbow : HereticWeapon Tag "$TAG_CROSSBOW"; } - action native void A_FireCrossbowPL1 (); + native void A_FireCrossbowPL1 (); States { @@ -330,7 +330,7 @@ class CrossbowPowered : Crossbow Tag "$TAG_CROSSBOWP"; } - action native void A_FireCrossbowPL2(); + native void A_FireCrossbowPL2(); States { @@ -462,7 +462,7 @@ class Gauntlets : Weapon Obituary "$OB_MPGAUNTLETS"; } - action native void A_GauntletAttack (int power); + native void A_GauntletAttack (int power); States { @@ -574,7 +574,7 @@ class Mace : HereticWeapon Tag "$TAG_MACE"; } - action native void A_FireMacePL1(); + native void A_FireMacePL1(); States { @@ -611,7 +611,7 @@ class MacePowered : Mace Tag "$TAG_MACEP"; } - action native void A_FireMacePL2(); + native void A_FireMacePL2(); States { @@ -642,8 +642,8 @@ class MaceFX1 : Actor Obituary "$OB_MPMACE"; } - action native void A_MacePL1Check(); - action native void A_MaceBallImpact(); + native void A_MacePL1Check(); + native void A_MaceBallImpact(); States { @@ -670,7 +670,7 @@ class MaceFX2 : MaceFX1 SeeSound ""; } - action native void A_MaceBallImpact2(); + native void A_MaceBallImpact2(); States { @@ -725,7 +725,7 @@ class MaceFX4 : Actor native Obituary "$OB_MPPMACE"; } - action native void A_DeathBallImpact(); + native void A_DeathBallImpact(); States { @@ -778,7 +778,7 @@ class Blaster : HereticWeapon Obituary "$OB_MPBLASTER"; } - action native void A_FireBlasterPL1(); + native void A_FireBlasterPL1(); States { @@ -843,7 +843,7 @@ class BlasterFX1 : FastProjectile native Obituary "$OB_MPPBLASTER"; } - action native void A_SpawnRippers(); + native void A_SpawnRippers(); States { @@ -950,7 +950,7 @@ class SkullRod : HereticWeapon Tag "$TAG_SKULLROD"; } - action native void A_FireSkullRodPL1(); + native void A_FireSkullRodPL1(); States { @@ -984,7 +984,7 @@ class SkullRodPowered : SkullRod Tag "$TAG_SKULLRODP"; } - action native void A_FireSkullRodPL2(); + native void A_FireSkullRodPL2(); States { @@ -1053,9 +1053,9 @@ class HornRodFX2 : Actor native Obituary "$OB_MPPSKULLROD"; } - action native void A_AddPlayerRain(); - action native void A_HideInCeiling(); - action native void A_SkullRodStorm(); + native void A_AddPlayerRain(); + native void A_HideInCeiling(); + native void A_SkullRodStorm(); States { @@ -1094,7 +1094,7 @@ class RainPillar : Actor native Obituary "$OB_MPPSKULLROD"; } - action native void A_RainImpact(); + native void A_RainImpact(); States { @@ -1140,7 +1140,7 @@ class PhoenixRod : Weapon native Tag "$TAG_PHOENIXROD"; } - action native void A_FirePhoenixPL1(); + native void A_FirePhoenixPL1(); States { @@ -1176,9 +1176,9 @@ class PhoenixRodPowered : PhoenixRod native Tag "$TAG_PHOENIXRODP"; } - action native void A_InitPhoenixPL2(); - action native void A_FirePhoenixPL2(); - action native void A_ShutdownPhoenixPL2(); + native void A_InitPhoenixPL2(); + native void A_FirePhoenixPL2(); + native void A_ShutdownPhoenixPL2(); States { @@ -1212,7 +1212,7 @@ class PhoenixFX1 : Actor native Obituary "$OB_MPPHOENIXROD"; } - action native void A_PhoenixPuff(); + native void A_PhoenixPuff(); States { @@ -1265,8 +1265,8 @@ class PhoenixFX2 : Actor native Obituary "$OB_MPPPHOENIXROD"; } - action native void A_FlameEnd(); - action native void A_FloatPuff(); + native void A_FlameEnd(); + native void A_FloatPuff(); States { diff --git a/wadsrc/static/zscript/heretic/ironlich.txt b/wadsrc/static/zscript/heretic/ironlich.txt index 9b66bcb0d..e6ba05e05 100644 --- a/wadsrc/static/zscript/heretic/ironlich.txt +++ b/wadsrc/static/zscript/heretic/ironlich.txt @@ -27,7 +27,7 @@ class Ironlich : Actor DropItem "ArtiEgg", 51, 0; } - action native void A_LichAttack (); + native void A_LichAttack (); States { @@ -74,7 +74,7 @@ class HeadFX1 : Actor RenderStyle "Add"; } - action native void A_LichIceImpact(); + native void A_LichIceImpact(); States { @@ -135,7 +135,7 @@ class HeadFX3 : Actor RenderStyle "Add"; } - action native void A_LichFireGrow (); + native void A_LichFireGrow (); States { @@ -174,7 +174,7 @@ class Whirlwind : Actor native Alpha 0.4; } - action native void A_WhirlwindSeek(); + native void A_WhirlwindSeek(); States { diff --git a/wadsrc/static/zscript/heretic/knight.txt b/wadsrc/static/zscript/heretic/knight.txt index f8b84b9aa..1eb341859 100644 --- a/wadsrc/static/zscript/heretic/knight.txt +++ b/wadsrc/static/zscript/heretic/knight.txt @@ -23,7 +23,7 @@ class Knight : Actor DropItem "CrossbowAmmo", 84, 5; } - action native void A_KnightAttack (); + native void A_KnightAttack (); States { @@ -116,7 +116,7 @@ class RedAxe : KnightAxe Damage 7; } - action native void A_DripBlood (); + native void A_DripBlood (); States { diff --git a/wadsrc/static/zscript/heretic/wizard.txt b/wadsrc/static/zscript/heretic/wizard.txt index 3599354ad..d33e2dd8a 100644 --- a/wadsrc/static/zscript/heretic/wizard.txt +++ b/wadsrc/static/zscript/heretic/wizard.txt @@ -26,10 +26,10 @@ class Wizard : Actor DropItem "ArtiTomeOfPower", 4, 0; } - action native void A_GhostOff (); - action native void A_WizAtk1 (); - action native void A_WizAtk2 (); - action native void A_WizAtk3 (); + native void A_GhostOff (); + native void A_WizAtk1 (); + native void A_WizAtk2 (); + native void A_WizAtk3 (); States { diff --git a/wadsrc/static/zscript/hexen/bats.txt b/wadsrc/static/zscript/hexen/bats.txt index f96f93272..1e6ee459f 100644 --- a/wadsrc/static/zscript/hexen/bats.txt +++ b/wadsrc/static/zscript/hexen/bats.txt @@ -9,8 +9,8 @@ class BatSpawner : SwitchableDecoration RenderStyle "None"; } - action native void A_BatSpawnInit(); - action native void A_BatSpawn(); + native void A_BatSpawnInit(); + native void A_BatSpawn(); States { @@ -39,7 +39,7 @@ class Bat : Actor +NOTELEPORT +CANPASS } - action native void A_BatMove(); + native void A_BatMove(); States { diff --git a/wadsrc/static/zscript/hexen/bishop.txt b/wadsrc/static/zscript/hexen/bishop.txt index 4dbb0d226..d116ee932 100644 --- a/wadsrc/static/zscript/hexen/bishop.txt +++ b/wadsrc/static/zscript/hexen/bishop.txt @@ -23,13 +23,13 @@ class Bishop : Actor Obituary"$OB_BISHOP"; } - action native void A_BishopChase(); - action native void A_BishopDecide(); - action native void A_BishopDoBlur(); - action native void A_BishopSpawnBlur(); - action native void A_BishopPainBlur(); - action native void A_BishopAttack(); - action native void A_BishopAttack2(); + native void A_BishopChase(); + native void A_BishopDecide(); + native void A_BishopDoBlur(); + native void A_BishopSpawnBlur(); + native void A_BishopPainBlur(); + native void A_BishopAttack(); + native void A_BishopAttack2(); States { diff --git a/wadsrc/static/zscript/hexen/clericboss.txt b/wadsrc/static/zscript/hexen/clericboss.txt index 6493cde89..a2019bae5 100644 --- a/wadsrc/static/zscript/hexen/clericboss.txt +++ b/wadsrc/static/zscript/hexen/clericboss.txt @@ -18,7 +18,7 @@ class ClericBoss : Actor Obituary "$OBCBOSS"; } - action native void A_ClericAttack(); + native void A_ClericAttack(); States { diff --git a/wadsrc/static/zscript/hexen/clericflame.txt b/wadsrc/static/zscript/hexen/clericflame.txt index ae5ecaac3..e72496530 100644 --- a/wadsrc/static/zscript/hexen/clericflame.txt +++ b/wadsrc/static/zscript/hexen/clericflame.txt @@ -16,7 +16,7 @@ class CWeapFlame : ClericWeapon Tag "$TAG_CWEAPFLAME"; } - action native void A_CFlameAttack(); + native void A_CFlameAttack(); States { @@ -140,7 +140,7 @@ class CircleFlame : Actor Obituary "$OB_MPCWEAPFLAME"; } - action native void A_CFlameRotate(); + native void A_CFlameRotate(); States { @@ -184,8 +184,8 @@ class CFlameMissile : FastProjectile native Obituary "$OB_MPCWEAPFLAME"; } - action native void A_CFlamePuff(); - action native void A_CFlameMissile(); + native void A_CFlamePuff(); + native void A_CFlameMissile(); States { diff --git a/wadsrc/static/zscript/hexen/clericholy.txt b/wadsrc/static/zscript/hexen/clericholy.txt index b238ce09b..6fc9cf43d 100644 --- a/wadsrc/static/zscript/hexen/clericholy.txt +++ b/wadsrc/static/zscript/hexen/clericholy.txt @@ -96,8 +96,8 @@ class CWeapWraithverge : ClericWeapon native Inventory.PickupSound "WeaponBuild"; } - action native void A_CHolyAttack(); - action native void A_CHolyPalette(); + native void A_CHolyAttack(); + native void A_CHolyPalette(); States { @@ -139,7 +139,7 @@ class HolyMissile : Actor +EXTREMEDEATH } - action native void A_CHolyAttack2(); + native void A_CHolyAttack2(); States { @@ -211,8 +211,8 @@ class HolySpirit : Actor native Obituary "$OB_MPCWEAPWRAITHVERGE"; } - action native void A_CHolySeek(); - action native void A_CHolyCheckScream(); + native void A_CHolySeek(); + native void A_CHolyCheckScream(); States { @@ -242,7 +242,7 @@ class HolyTail : Actor Alpha 0.6; } - action native void A_CHolyTail(); + native void A_CHolyTail(); States { diff --git a/wadsrc/static/zscript/hexen/clericmace.txt b/wadsrc/static/zscript/hexen/clericmace.txt index 5e00b9c3b..b47974d4b 100644 --- a/wadsrc/static/zscript/hexen/clericmace.txt +++ b/wadsrc/static/zscript/hexen/clericmace.txt @@ -13,7 +13,7 @@ class CWeapMace : ClericWeapon Tag "$TAG_CWEAPMACE"; } - action native void A_CMaceAttack(); + native void A_CMaceAttack(); States { diff --git a/wadsrc/static/zscript/hexen/clericstaff.txt b/wadsrc/static/zscript/hexen/clericstaff.txt index 7ae0e9da3..c33f14a80 100644 --- a/wadsrc/static/zscript/hexen/clericstaff.txt +++ b/wadsrc/static/zscript/hexen/clericstaff.txt @@ -16,10 +16,10 @@ class CWeapStaff : ClericWeapon Tag "$TAG_CWEAPSTAFF"; } - action native void A_CStaffInitBlink(); - action native void A_CStaffCheckBlink(); - action native void A_CStaffCheck(); - action native void A_CStaffAttack(); + native void A_CStaffInitBlink(); + native void A_CStaffCheckBlink(); + native void A_CStaffCheck(); + native void A_CStaffAttack(); States { diff --git a/wadsrc/static/zscript/hexen/dragon.txt b/wadsrc/static/zscript/hexen/dragon.txt index bfc037e71..6df3da943 100644 --- a/wadsrc/static/zscript/hexen/dragon.txt +++ b/wadsrc/static/zscript/hexen/dragon.txt @@ -23,12 +23,12 @@ class Dragon : Actor Obituary "$OB_DRAGON"; } - action native void A_DragonInitFlight(); - action native void A_DragonFlap(); - action native void A_DragonFlight(); - action native void A_DragonPain(); - action native void A_DragonAttack(); - action native void A_DragonCheckCrash(); + native void A_DragonInitFlight(); + native void A_DragonFlap(); + native void A_DragonFlight(); + native void A_DragonPain(); + native void A_DragonAttack(); + native void A_DragonCheckCrash(); States { @@ -77,7 +77,7 @@ class DragonFireball : Actor DeathSound "DragonFireballExplode"; } - action native void A_DragonFX2(); + native void A_DragonFX2(); States { diff --git a/wadsrc/static/zscript/hexen/fighteraxe.txt b/wadsrc/static/zscript/hexen/fighteraxe.txt index 30b235192..436172bef 100644 --- a/wadsrc/static/zscript/hexen/fighteraxe.txt +++ b/wadsrc/static/zscript/hexen/fighteraxe.txt @@ -17,12 +17,12 @@ class FWeapAxe : FighterWeapon native Tag "$TAG_FWEAPAXE"; } - action native void A_FAxeCheckUp(); - action native void A_FAxeCheckReady(); - action native void A_FAxeCheckAtk(); - action native void A_FAxeAttack(); - action native void A_FAxeCheckUpG(); - action native void A_FAxeCheckReadyG(); + native void A_FAxeCheckUp(); + native void A_FAxeCheckReady(); + native void A_FAxeCheckAtk(); + native void A_FAxeAttack(); + native void A_FAxeCheckUpG(); + native void A_FAxeCheckReadyG(); States { diff --git a/wadsrc/static/zscript/hexen/fighterboss.txt b/wadsrc/static/zscript/hexen/fighterboss.txt index aa3e28ce7..8e862de30 100644 --- a/wadsrc/static/zscript/hexen/fighterboss.txt +++ b/wadsrc/static/zscript/hexen/fighterboss.txt @@ -19,7 +19,7 @@ class FighterBoss : Actor Obituary "$OB_FBOSS"; } - action native void A_FighterAttack(); + native void A_FighterAttack(); States { diff --git a/wadsrc/static/zscript/hexen/fighterfist.txt b/wadsrc/static/zscript/hexen/fighterfist.txt index 8428ebe7d..e556ebd87 100644 --- a/wadsrc/static/zscript/hexen/fighterfist.txt +++ b/wadsrc/static/zscript/hexen/fighterfist.txt @@ -13,7 +13,7 @@ class FWeapFist : FighterWeapon Tag "$TAG_FWEAPFIST"; } - action native void A_FPunchAttack(); + native void A_FPunchAttack(); States { diff --git a/wadsrc/static/zscript/hexen/fighterhammer.txt b/wadsrc/static/zscript/hexen/fighterhammer.txt index f415cbb72..0104c7670 100644 --- a/wadsrc/static/zscript/hexen/fighterhammer.txt +++ b/wadsrc/static/zscript/hexen/fighterhammer.txt @@ -18,8 +18,8 @@ class FWeapHammer : FighterWeapon Tag "$TAG_FWEAPHAMMER"; } - action native void A_FHammerAttack(); - action native void A_FHammerThrow(); + native void A_FHammerAttack(); + native void A_FHammerThrow(); States { diff --git a/wadsrc/static/zscript/hexen/fighterquietus.txt b/wadsrc/static/zscript/hexen/fighterquietus.txt index 5fe132237..2430cd70c 100644 --- a/wadsrc/static/zscript/hexen/fighterquietus.txt +++ b/wadsrc/static/zscript/hexen/fighterquietus.txt @@ -97,7 +97,7 @@ class FWeapQuietus : FighterWeapon Tag "$TAG_FWEAPQUIETUS"; } - action native void A_FSwordAttack(); + native void A_FSwordAttack(); States { @@ -146,7 +146,7 @@ class FSwordMissile : Actor native Obituary "$OB_MPFWEAPQUIETUS"; } - action native void A_FSwordFlames(); + native void A_FSwordFlames(); States { diff --git a/wadsrc/static/zscript/hexen/firedemon.txt b/wadsrc/static/zscript/hexen/firedemon.txt index f79303400..001e1629f 100644 --- a/wadsrc/static/zscript/hexen/firedemon.txt +++ b/wadsrc/static/zscript/hexen/firedemon.txt @@ -23,10 +23,10 @@ class FireDemon : Actor Obituary "$OB_FIREDEMON"; } - action native void A_FiredRocks(); - action native void A_FiredChase(); - action native void A_FiredAttack(); - action native void A_FiredSplotch(); + native void A_FiredRocks(); + native void A_FiredChase(); + native void A_FiredAttack(); + native void A_FiredSplotch(); States { @@ -124,7 +124,7 @@ class FireDemonRock1 : Actor +NOTELEPORT } - action native void A_SmBounce(); + native void A_SmBounce(); States { diff --git a/wadsrc/static/zscript/hexen/flechette.txt b/wadsrc/static/zscript/hexen/flechette.txt index 4b3cd914c..6f7b3a818 100644 --- a/wadsrc/static/zscript/hexen/flechette.txt +++ b/wadsrc/static/zscript/hexen/flechette.txt @@ -10,7 +10,7 @@ class PoisonBag : Actor +NOBLOCKMAP +NOGRAVITY } - action native void A_PoisonBagInit(); + native void A_PoisonBagInit(); States { @@ -37,7 +37,7 @@ class FireBomb : Actor DeathSound "FlechetteExplode"; } - action native void A_TimeBomb(); + native void A_TimeBomb(); States { @@ -69,8 +69,8 @@ class ThrowingBomb : Actor DeathSound "FlechetteExplode"; } - action native void A_CheckThrowBomb(); - action native void A_CheckThrowBomb2(); + native void A_CheckThrowBomb(); + native void A_CheckThrowBomb2(); States { @@ -193,8 +193,8 @@ class PoisonCloud : Actor native DamageType "PoisonCloud"; } - action native void A_PoisonBagDamage(); - action native void A_PoisonBagCheck(); + native void A_PoisonBagDamage(); + native void A_PoisonBagCheck(); States { @@ -233,7 +233,7 @@ class ZPoisonShroom : PoisonBag DeathSound "PoisonShroomDeath"; } - action native void A_PoisonShroom(); + native void A_PoisonShroom(); States { diff --git a/wadsrc/static/zscript/hexen/flies.txt b/wadsrc/static/zscript/hexen/flies.txt index 35c52a124..464e6e9d9 100644 --- a/wadsrc/static/zscript/hexen/flies.txt +++ b/wadsrc/static/zscript/hexen/flies.txt @@ -15,8 +15,8 @@ class LittleFly : Actor ActiveSound "FlyBuzz"; } - action native void A_FlySearch(); - action native void A_FlyBuzz(); + native void A_FlySearch(); + native void A_FlyBuzz(); States { diff --git a/wadsrc/static/zscript/hexen/fog.txt b/wadsrc/static/zscript/hexen/fog.txt index 84cc6c03e..93b5e9593 100644 --- a/wadsrc/static/zscript/hexen/fog.txt +++ b/wadsrc/static/zscript/hexen/fog.txt @@ -11,7 +11,7 @@ class FogSpawner : Actor +INVISIBLE } - action native void A_FogSpawn(); + native void A_FogSpawn(); States { @@ -34,7 +34,7 @@ class FogPatchSmall : Actor Alpha 0.6; } - action native void A_FogMove(); + native void A_FogMove(); States { diff --git a/wadsrc/static/zscript/hexen/heresiarch.txt b/wadsrc/static/zscript/hexen/heresiarch.txt index 076bc01ca..6ffc11b3b 100644 --- a/wadsrc/static/zscript/hexen/heresiarch.txt +++ b/wadsrc/static/zscript/hexen/heresiarch.txt @@ -27,10 +27,10 @@ class Heresiarch native Obituary "$OB_HERESIARCH"; } - action native void A_SorcSpinBalls(); - action native void A_SpeedBalls(); - action native void A_SorcBossAttack(); - action native void A_SpawnFizzle(); + native void A_SorcSpinBalls(); + native void A_SpeedBalls(); + native void A_SorcBossAttack(); + native void A_SpawnFizzle(); States { @@ -93,9 +93,9 @@ class SorcBall native DeathSound "SorcererBigBallExplode"; } - action native void A_SorcBallOrbit(); - action native void A_SorcBallPop(); - action native void A_BounceCheck (); + native void A_SorcBallOrbit(); + native void A_SorcBallPop(); + native void A_BounceCheck (); } // First ball (purple) - fires projectiles ---------------------------------- @@ -188,7 +188,7 @@ class SorcFX1 : Actor DeathSound "SorcererHeadScream"; } - action native void A_SorcFX1Seek(); + native void A_SorcFX1Seek(); States { @@ -218,8 +218,8 @@ class SorcFX2 : Actor +NOTELEPORT } - action native void A_SorcFX2Split(); - action native void A_SorcFX2Orbit (); + native void A_SorcFX2Split(); + native void A_SorcFX2Orbit (); states { @@ -268,8 +268,8 @@ class SorcFX3 : Actor SeeSound "SorcererBishopSpawn"; } - action native void A_SpawnBishop(); - action native void A_SorcererBishopEntry(); + native void A_SpawnBishop(); + native void A_SorcererBishopEntry(); States { @@ -323,7 +323,7 @@ class SorcFX4 : Actor DeathSound "SorcererBallExplode"; } - action native void A_SorcFX4Check(); + native void A_SorcFX4Check(); States { diff --git a/wadsrc/static/zscript/hexen/hexenspecialdecs.txt b/wadsrc/static/zscript/hexen/hexenspecialdecs.txt index 97c6ea41e..30ae0fff1 100644 --- a/wadsrc/static/zscript/hexen/hexenspecialdecs.txt +++ b/wadsrc/static/zscript/hexen/hexenspecialdecs.txt @@ -95,7 +95,7 @@ class Pottery1 : Actor native +NOICEDEATH } - action native void A_PotteryExplode(); + native void A_PotteryExplode(); States { @@ -153,8 +153,8 @@ class PotteryBit : Actor +NOICEDEATH } - action native void A_PotteryChooseBit(); - action native void A_PotteryCheck(); + native void A_PotteryChooseBit(); + native void A_PotteryCheck(); States { @@ -212,7 +212,7 @@ class ZCorpseLynchedNoHeart : Actor native +SOLID +SPAWNCEILING +NOGRAVITY } - action native void A_CorpseBloodDrip(); + native void A_CorpseBloodDrip(); States { @@ -289,7 +289,7 @@ class ZCorpseSitting : Actor DeathSound "FireDemonDeath"; } - action native void A_CorpseExplode(); + native void A_CorpseExplode(); States { @@ -313,7 +313,7 @@ class LeafSpawner : Actor +INVISIBLE } - action native void A_LeafSpawn(); + native void A_LeafSpawn(); States { @@ -338,8 +338,8 @@ class Leaf1 : Actor +NOICEDEATH } - action native void A_LeafThrust(); - action native void A_LeafCheck(); + native void A_LeafThrust(); + native void A_LeafCheck(); States { @@ -556,7 +556,7 @@ class ZSuitOfArmor : Actor DeathSound "SuitofArmorBreak"; } - action native void A_SoAExplode(); + native void A_SoAExplode(); States { @@ -621,8 +621,8 @@ class ZBell : Actor native DeathSound "BellRing"; } - action native void A_BellReset1(); - action native void A_BellReset2(); + native void A_BellReset1(); + native void A_BellReset2(); States { diff --git a/wadsrc/static/zscript/hexen/iceguy.txt b/wadsrc/static/zscript/hexen/iceguy.txt index 635aea07f..8081d5a61 100644 --- a/wadsrc/static/zscript/hexen/iceguy.txt +++ b/wadsrc/static/zscript/hexen/iceguy.txt @@ -22,9 +22,9 @@ class IceGuy : Actor Obituary "$OB_ICEGUY"; } - action native void A_IceGuyLook(); - action native void A_IceGuyChase(); - action native void A_IceGuyAttack(); + native void A_IceGuyLook(); + native void A_IceGuyChase(); + native void A_IceGuyAttack(); States { @@ -69,7 +69,7 @@ class IceGuyFX : Actor DeathSound "IceGuyMissileExplode"; } - action native void A_IceGuyMissileExplode(); + native void A_IceGuyMissileExplode(); States { diff --git a/wadsrc/static/zscript/hexen/korax.txt b/wadsrc/static/zscript/hexen/korax.txt index 3928de884..16bf172a4 100644 --- a/wadsrc/static/zscript/hexen/korax.txt +++ b/wadsrc/static/zscript/hexen/korax.txt @@ -24,11 +24,11 @@ class Korax : Actor Obituary "$OB_KORAX"; } - action native void A_KoraxChase(); - action native void A_KoraxDecide(); - action native void A_KoraxBonePop(); - action native void A_KoraxMissile(); - action native void A_KoraxCommand(); + native void A_KoraxChase(); + native void A_KoraxDecide(); + native void A_KoraxBonePop(); + native void A_KoraxMissile(); + native void A_KoraxCommand(); States { @@ -94,7 +94,7 @@ class KoraxSpirit : Actor Alpha 0.4; } - action native void A_KSpiritRoam(); + native void A_KSpiritRoam(); States { @@ -119,8 +119,8 @@ class KoraxBolt : Actor RenderStyle "Add"; } - action native void A_KBolt(); - action native void A_KBoltRaise(); + native void A_KBolt(); + native void A_KBoltRaise(); States { diff --git a/wadsrc/static/zscript/hexen/mageboss.txt b/wadsrc/static/zscript/hexen/mageboss.txt index 083d21016..f9637f8d1 100644 --- a/wadsrc/static/zscript/hexen/mageboss.txt +++ b/wadsrc/static/zscript/hexen/mageboss.txt @@ -18,7 +18,7 @@ class MageBoss : Actor Obituary "$OB_MBOSS"; } - action native void A_MageAttack(); + native void A_MageAttack(); States { diff --git a/wadsrc/static/zscript/hexen/magecone.txt b/wadsrc/static/zscript/hexen/magecone.txt index 94452985c..471b5b0b7 100644 --- a/wadsrc/static/zscript/hexen/magecone.txt +++ b/wadsrc/static/zscript/hexen/magecone.txt @@ -17,7 +17,7 @@ class MWeapFrost : MageWeapon Tag "$TAG_MWEAPFROST"; } - action native void A_FireConePL1(); + native void A_FireConePL1(); States { @@ -63,7 +63,7 @@ class FrostMissile : Actor native Obituary "$OB_MPMWEAPFROST"; } - action native void A_ShedShard(); + native void A_ShedShard(); States { diff --git a/wadsrc/static/zscript/hexen/magelightning.txt b/wadsrc/static/zscript/hexen/magelightning.txt index 2c35a41e5..46687e813 100644 --- a/wadsrc/static/zscript/hexen/magelightning.txt +++ b/wadsrc/static/zscript/hexen/magelightning.txt @@ -16,8 +16,8 @@ class MWeapLightning : MageWeapon Tag "$TAG_MWEAPLIGHTNING"; } - action native void A_LightningReady(); - action native void A_MLightningAttack(class floor = "LightningFloor", class ceiling = "LightningCeiling"); + native void A_LightningReady(); + native void A_MLightningAttack(class floor = "LightningFloor", class ceiling = "LightningCeiling"); States { @@ -79,9 +79,9 @@ class LightningCeiling : Lightning RenderStyle "Add"; } - action native void A_LightningZap(); - action native void A_LightningClip(); - action native void A_LightningRemove(); + native void A_LightningZap(); + native void A_LightningClip(); + native void A_LightningRemove(); States { @@ -117,7 +117,7 @@ class LightningFloor : LightningCeiling RenderStyle "Add"; } - action native void A_LastZap(); + native void A_LastZap(); States { @@ -155,7 +155,7 @@ class LightningZap : Actor native Obituary "$OB_MPMWEAPLIGHTNING"; } - action native void A_ZapMimic(); + native void A_ZapMimic(); States { diff --git a/wadsrc/static/zscript/hexen/magestaff.txt b/wadsrc/static/zscript/hexen/magestaff.txt index b71c1e3dc..9338febe6 100644 --- a/wadsrc/static/zscript/hexen/magestaff.txt +++ b/wadsrc/static/zscript/hexen/magestaff.txt @@ -97,8 +97,8 @@ class MWeapBloodscourge : MageWeapon native Tag "$TAG_MWEAPBLOODSCOURGE"; } - action native void A_MStaffAttack(); - action native void A_MStaffPalette(); + native void A_MStaffAttack(); + native void A_MStaffPalette(); States { @@ -143,7 +143,7 @@ class MageStaffFX2 : Actor native Obituary "$OB_MPMWEAPBLOODSCOURGE"; } - action native void A_MStaffTrack(); + native void A_MStaffTrack(); States { diff --git a/wadsrc/static/zscript/hexen/pig.txt b/wadsrc/static/zscript/hexen/pig.txt index 8fa446882..6362ff36e 100644 --- a/wadsrc/static/zscript/hexen/pig.txt +++ b/wadsrc/static/zscript/hexen/pig.txt @@ -34,7 +34,7 @@ class Snout : Weapon Weapon.YAdjust 10; } - action native void A_SnoutAttack (); + native void A_SnoutAttack (); States { diff --git a/wadsrc/static/zscript/hexen/serpent.txt b/wadsrc/static/zscript/hexen/serpent.txt index 516d0c703..d8886ccb2 100644 --- a/wadsrc/static/zscript/hexen/serpent.txt +++ b/wadsrc/static/zscript/hexen/serpent.txt @@ -24,15 +24,15 @@ class Serpent : Actor HitObituary "$OB_SERPENTHIT"; } - action native void A_SerpentHumpDecide(); - action native void A_SerpentHide(); - action native void A_SerpentCheckForAttack(); - action native void A_SerpentSpawnGibs(); - action native void A_SerpentUnHide(); - action native void A_SerpentRaiseHump(); - action native void A_SerpentLowerHump(); - action native void A_SerpentChooseAttack(); - action native void A_SerpentMeleeAttack(); + native void A_SerpentHumpDecide(); + native void A_SerpentHide(); + native void A_SerpentCheckForAttack(); + native void A_SerpentSpawnGibs(); + native void A_SerpentUnHide(); + native void A_SerpentRaiseHump(); + native void A_SerpentLowerHump(); + native void A_SerpentChooseAttack(); + native void A_SerpentMeleeAttack(); States { @@ -159,7 +159,7 @@ class SerpentHead : Actor +NOBLOCKMAP } - action native void A_SerpentHeadCheck(); + native void A_SerpentHeadCheck(); States { @@ -183,9 +183,9 @@ class SerpentGib1 : Actor +NOBLOCKMAP +NOGRAVITY } - action native void A_FloatGib(); - action native void A_DelayGib(); - action native void A_SinkGib(); + native void A_FloatGib(); + native void A_DelayGib(); + native void A_SinkGib(); States { diff --git a/wadsrc/static/zscript/hexen/spike.txt b/wadsrc/static/zscript/hexen/spike.txt index 2c8b4e80a..58f763ccc 100644 --- a/wadsrc/static/zscript/hexen/spike.txt +++ b/wadsrc/static/zscript/hexen/spike.txt @@ -26,11 +26,11 @@ class ThrustFloor : Actor native Height 128; } - action native void A_ThrustRaise(); - action native void A_ThrustImpale(); - action native void A_ThrustLower(); - action native void A_ThrustInitDn(); - action native void A_ThrustInitUp(); + native void A_ThrustRaise(); + native void A_ThrustImpale(); + native void A_ThrustLower(); + native void A_ThrustInitDn(); + native void A_ThrustInitUp(); States { diff --git a/wadsrc/static/zscript/hexen/summon.txt b/wadsrc/static/zscript/hexen/summon.txt index 395d4760d..06ceb7e17 100644 --- a/wadsrc/static/zscript/hexen/summon.txt +++ b/wadsrc/static/zscript/hexen/summon.txt @@ -36,7 +36,7 @@ class SummoningDoll : Actor +NOTELEPORT } - action native void A_Summon(); + native void A_Summon(); States { diff --git a/wadsrc/static/zscript/hexen/teleportother.txt b/wadsrc/static/zscript/hexen/teleportother.txt index 90015b207..2de144d5f 100644 --- a/wadsrc/static/zscript/hexen/teleportother.txt +++ b/wadsrc/static/zscript/hexen/teleportother.txt @@ -41,11 +41,11 @@ class TelOtherFX1 : Actor native Speed 20; } - action native void A_TeloSpawnA(); - action native void A_TeloSpawnB(); - action native void A_TeloSpawnC(); - action native void A_TeloSpawnD(); - action native void A_CheckTeleRing (); + native void A_TeloSpawnA(); + native void A_TeloSpawnB(); + native void A_TeloSpawnC(); + native void A_TeloSpawnD(); + native void A_CheckTeleRing (); States { diff --git a/wadsrc/static/zscript/hexen/wraith.txt b/wadsrc/static/zscript/hexen/wraith.txt index a8b648a72..9d811ec5c 100644 --- a/wadsrc/static/zscript/hexen/wraith.txt +++ b/wadsrc/static/zscript/hexen/wraith.txt @@ -23,10 +23,10 @@ class Wraith : Actor Obituary "$OB_WRAITH"; } - action native void A_WraithInit(); - action native void A_WraithChase(); - action native void A_WraithFX3(); - action native void A_WraithMelee(); + native void A_WraithInit(); + native void A_WraithChase(); + native void A_WraithFX3(); + native void A_WraithMelee(); States { @@ -97,8 +97,8 @@ class WraithBuried : Wraith PainChance 0; } - action native void A_WraithRaiseInit(); - action native void A_WraithRaise(); + native void A_WraithRaiseInit(); + native void A_WraithRaise(); States { @@ -133,7 +133,7 @@ class WraithFX1 : Actor DeathSound "WraithMissileExplode"; } - action native void A_WraithFX2(); + native void A_WraithFX2(); States { diff --git a/wadsrc/static/zscript/raven/minotaur.txt b/wadsrc/static/zscript/raven/minotaur.txt index 9bc02fced..9bbbe81a0 100644 --- a/wadsrc/static/zscript/raven/minotaur.txt +++ b/wadsrc/static/zscript/raven/minotaur.txt @@ -26,15 +26,15 @@ class Minotaur : Actor native DropItem "PhoenixRodAmmo", 84, 10; } - action native void A_MinotaurDecide(); - action native void A_MinotaurAtk1(); - action native void A_MinotaurAtk2(); - action native void A_MinotaurAtk3(); - action native void A_MinotaurCharge(); - action native void A_MinotaurLook(); - action native void A_MinotaurRoam(); - action native void A_MinotaurChase(); - action native void A_MinotaurDeath(); + native void A_MinotaurDecide(); + native void A_MinotaurAtk1(); + native void A_MinotaurAtk2(); + native void A_MinotaurAtk3(); + native void A_MinotaurCharge(); + native void A_MinotaurLook(); + native void A_MinotaurRoam(); + native void A_MinotaurChase(); + native void A_MinotaurDeath(); States { @@ -179,7 +179,7 @@ class MinotaurFX2 : MinotaurFX1 DeathSound "minotaur/fx2hit"; } - action native void A_MntrFloorFire(); + native void A_MntrFloorFire(); states { diff --git a/wadsrc/static/zscript/shared/bridge.txt b/wadsrc/static/zscript/shared/bridge.txt index 08c788f8e..ea38796a7 100644 --- a/wadsrc/static/zscript/shared/bridge.txt +++ b/wadsrc/static/zscript/shared/bridge.txt @@ -9,7 +9,7 @@ class BridgeBall : Actor +NOGRAVITY } - action native void A_BridgeOrbit(); + native void A_BridgeOrbit(); States { @@ -36,7 +36,7 @@ class CustomBridge : Actor native RenderStyle "None"; } - action native void A_BridgeInit(class balltype = "BridgeBall"); + native void A_BridgeInit(class balltype = "BridgeBall"); states { diff --git a/wadsrc/static/zscript/shared/ice.txt b/wadsrc/static/zscript/shared/ice.txt index 9668466cb..534113785 100644 --- a/wadsrc/static/zscript/shared/ice.txt +++ b/wadsrc/static/zscript/shared/ice.txt @@ -21,7 +21,7 @@ class IceChunk : Actor +NOBLOCKMAP +MOVEWITHSECTOR } - action native void A_IceSetTics (); + native void A_IceSetTics (); States { diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index 80771e1a1..2fde3b3cd 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -11,10 +11,10 @@ class Inventory : Actor native } // These are regular functions for the item itself. - private action native void A_RestoreSpecialPosition(); - private action native void A_RestoreSpecialDoomThing(); - private action native void A_RestoreSpecialThing1(); - private action native void A_RestoreSpecialThing2(); + private native void A_RestoreSpecialPosition(); + private native void A_RestoreSpecialDoomThing(); + private native void A_RestoreSpecialThing1(); + private native void A_RestoreSpecialThing2(); States { @@ -46,20 +46,20 @@ class StateProvider : Inventory native action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = "", color color2 = "", int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); - action native void A_Light(int extralight); - action native void A_Light0(); - action native void A_Light1(); - action native void A_Light2(); - action native void A_LightInverse(); - action native void A_WeaponReady(int flags = 0); - action native void A_Lower(); - action native void A_Raise(); + native void A_Light(int extralight); + native void A_Light0(); + native void A_Light1(); + native void A_Light2(); + native void A_LightInverse(); + native void A_WeaponReady(int flags = 0); + native void A_Lower(); + native void A_Raise(); action native void A_FirePistol(); action native void A_FireShotgun(); action native void A_FireShotgun2(); - action native void A_OpenShotgun2(); - action native void A_LoadShotgun2(); - action native void A_CloseShotgun2(); + native void A_OpenShotgun2(); + native void A_LoadShotgun2(); + native void A_CloseShotgun2(); action native void A_FireCGun(); action native void A_FireSTGrenade(class grenadetype = "Grenade"); action native void A_FireMissile(); @@ -67,17 +67,17 @@ class StateProvider : Inventory native action native void A_FireRailgun(); action native void A_FireRailgunLeft(); action native void A_FireRailgunRight(); - action native void A_RailWait(); - action native void A_BFGsound(); + native void A_RailWait(); + native void A_BFGsound(); action native void A_FireBFG(); action native void A_FireOldBFG(); - action native void A_ReFire(state flash = ""); - action native void A_ClearReFire(); - action native void A_CheckReload(); - action native void A_GunFlash(state flash = "", int flags = 0); + native void A_ReFire(state flash = ""); + native void A_ClearReFire(); + native void A_CheckReload(); + native void A_GunFlash(state flash = "", int flags = 0); action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); - action native state A_CheckForReload(int counter, state label, bool dontincrement = false); - action native void A_ResetReloadCounter(); + native state A_CheckForReload(int counter, state label, bool dontincrement = false); + native void A_ResetReloadCounter(); } class ScoreItem : Inventory native @@ -468,11 +468,11 @@ class Weapon : StateProvider native Stop; } - action native void A_ZoomFactor(float scale = 1, int flags = 0); + native void A_ZoomFactor(float scale = 1, int flags = 0); const ZOOM_INSTANT = 1; const ZOOM_NOSCALETURNING = 2; - action native void A_SetCrosshair(int xhair); + native void A_SetCrosshair(int xhair); } class WeaponGiver : Weapon native diff --git a/wadsrc/static/zscript/shared/specialspot.txt b/wadsrc/static/zscript/shared/specialspot.txt index a06d41c27..c0bf84de5 100644 --- a/wadsrc/static/zscript/shared/specialspot.txt +++ b/wadsrc/static/zscript/shared/specialspot.txt @@ -1,5 +1,5 @@ class SpecialSpot : Actor native { - action native void A_SpawnSingleItem(class type, int fail_sp = 0, int fail_co = 0, int fail_dm = 0); + native void A_SpawnSingleItem(class type, int fail_sp = 0, int fail_co = 0, int fail_dm = 0); } diff --git a/wadsrc/static/zscript/strife/acolyte.txt b/wadsrc/static/zscript/strife/acolyte.txt index 2f01cb836..0c1305b57 100644 --- a/wadsrc/static/zscript/strife/acolyte.txt +++ b/wadsrc/static/zscript/strife/acolyte.txt @@ -26,9 +26,9 @@ class Acolyte : StrifeHumanoid Obituary "$OB_ACOLYTE"; } - action native void A_BeShadowyFoe (); - action native void A_AcolyteBits (); - action native void A_AcolyteDie (); + native void A_BeShadowyFoe (); + native void A_AcolyteBits (); + native void A_AcolyteDie (); States { @@ -202,7 +202,7 @@ class AcolyteToBe : Acolyte -ISMONSTER } - action native void A_HideDecepticon (); + native void A_HideDecepticon (); States { diff --git a/wadsrc/static/zscript/strife/alienspectres.txt b/wadsrc/static/zscript/strife/alienspectres.txt index 42c8293d0..0fe9826f0 100644 --- a/wadsrc/static/zscript/strife/alienspectres.txt +++ b/wadsrc/static/zscript/strife/alienspectres.txt @@ -32,7 +32,7 @@ class AlienSpectre1 : SpectralMonster +NOICEDEATH } - action native void A_AlienSpectreDeath (); + native void A_AlienSpectreDeath (); States { diff --git a/wadsrc/static/zscript/strife/crusader.txt b/wadsrc/static/zscript/strife/crusader.txt index 334e9d803..02b08fc93 100644 --- a/wadsrc/static/zscript/strife/crusader.txt +++ b/wadsrc/static/zscript/strife/crusader.txt @@ -28,11 +28,11 @@ class Crusader : Actor Obituary "$OB_CRUSADER"; } - action native void A_CrusaderChoose (); - action native void A_CrusaderSweepLeft (); - action native void A_CrusaderSweepRight (); - action native void A_CrusaderRefire (); - action native void A_CrusaderDeath (); + native void A_CrusaderChoose (); + native void A_CrusaderSweepLeft (); + native void A_CrusaderSweepRight (); + native void A_CrusaderRefire (); + native void A_CrusaderDeath (); States { diff --git a/wadsrc/static/zscript/strife/entityboss.txt b/wadsrc/static/zscript/strife/entityboss.txt index d54a95a76..8ccdbbd02 100644 --- a/wadsrc/static/zscript/strife/entityboss.txt +++ b/wadsrc/static/zscript/strife/entityboss.txt @@ -32,7 +32,7 @@ class EntityPod : Actor SeeSound "misc/gibbed"; } - action native void A_SpawnEntity (); + native void A_SpawnEntity (); States { @@ -87,8 +87,8 @@ class EntityBoss : SpectralMonster Obituary "$OB_ENTITY"; } - action native void A_EntityAttack(); - action native void A_EntityDeath(); + native void A_EntityAttack(); + native void A_EntityDeath(); States { @@ -167,7 +167,7 @@ class EntitySecond : SpectralMonster Obituary "$OB_ENTITY"; } - action native void A_SubEntityDeath (); + native void A_SubEntityDeath (); States { diff --git a/wadsrc/static/zscript/strife/inquisitor.txt b/wadsrc/static/zscript/strife/inquisitor.txt index 5a053c74f..b27818a61 100644 --- a/wadsrc/static/zscript/strife/inquisitor.txt +++ b/wadsrc/static/zscript/strife/inquisitor.txt @@ -25,13 +25,13 @@ class Inquisitor : Actor Obituary "$OB_INQUISITOR"; } - action native void A_InquisitorWalk (); - action native void A_InquisitorDecide (); - action native void A_InquisitorAttack (); - action native void A_InquisitorJump (); - action native void A_InquisitorCheckLand (); - action native void A_TossArm (); - action native void A_ReaverRanged (); + native void A_InquisitorWalk (); + native void A_InquisitorDecide (); + native void A_InquisitorAttack (); + native void A_InquisitorJump (); + native void A_InquisitorCheckLand (); + native void A_TossArm (); + native void A_ReaverRanged (); States { diff --git a/wadsrc/static/zscript/strife/loremaster.txt b/wadsrc/static/zscript/strife/loremaster.txt index d3b437bbd..4a48cf4d3 100644 --- a/wadsrc/static/zscript/strife/loremaster.txt +++ b/wadsrc/static/zscript/strife/loremaster.txt @@ -91,7 +91,7 @@ class LoreShot : Actor native ActiveSound "loremaster/swish"; } - action native void A_LoremasterChain (); + native void A_LoremasterChain (); States { diff --git a/wadsrc/static/zscript/strife/oracle.txt b/wadsrc/static/zscript/strife/oracle.txt index 206dee164..6023629c2 100644 --- a/wadsrc/static/zscript/strife/oracle.txt +++ b/wadsrc/static/zscript/strife/oracle.txt @@ -19,7 +19,7 @@ class Oracle : Actor DropItem "Meat"; } - action native void A_WakeOracleSpectre (); + native void A_WakeOracleSpectre (); States { diff --git a/wadsrc/static/zscript/strife/programmer.txt b/wadsrc/static/zscript/strife/programmer.txt index cd577ff13..dc88a790f 100644 --- a/wadsrc/static/zscript/strife/programmer.txt +++ b/wadsrc/static/zscript/strife/programmer.txt @@ -33,10 +33,10 @@ class Programmer : Actor DropItem "Sigil1"; } - action native void A_ProgrammerMelee (); - action native void A_SpawnProgrammerBase (); - action native void A_ProgrammerDeath (); - action native void A_SpotLightning(); + native void A_ProgrammerMelee (); + native void A_SpawnProgrammerBase (); + native void A_ProgrammerDeath (); + native void A_SpotLightning(); States { diff --git a/wadsrc/static/zscript/strife/reaver.txt b/wadsrc/static/zscript/strife/reaver.txt index 0ce15fab8..7656a37a9 100644 --- a/wadsrc/static/zscript/strife/reaver.txt +++ b/wadsrc/static/zscript/strife/reaver.txt @@ -22,7 +22,7 @@ class Reaver : Actor Obituary "$OB_REAVER"; } - action native void A_ReaverRanged (); + native void A_ReaverRanged (); States { diff --git a/wadsrc/static/zscript/strife/rebels.txt b/wadsrc/static/zscript/strife/rebels.txt index 3ee0200dc..d9e65560f 100644 --- a/wadsrc/static/zscript/strife/rebels.txt +++ b/wadsrc/static/zscript/strife/rebels.txt @@ -122,7 +122,7 @@ class TeleporterBeacon : Inventory native Inventory.PickupMessage "$TXT_BEACON"; } - action native void A_Beacon (); + native void A_Beacon (); States { diff --git a/wadsrc/static/zscript/strife/sentinel.txt b/wadsrc/static/zscript/strife/sentinel.txt index 8108265cb..946a99ea2 100644 --- a/wadsrc/static/zscript/strife/sentinel.txt +++ b/wadsrc/static/zscript/strife/sentinel.txt @@ -28,7 +28,7 @@ class Sentinel : Actor Obituary "$OB_SENTINEL"; } - action native void A_SentinelAttack (); + native void A_SentinelAttack (); States { diff --git a/wadsrc/static/zscript/strife/sigil.txt b/wadsrc/static/zscript/strife/sigil.txt index d8b1f80f8..dab1db2f5 100644 --- a/wadsrc/static/zscript/strife/sigil.txt +++ b/wadsrc/static/zscript/strife/sigil.txt @@ -16,16 +16,16 @@ class Sigil : Weapon native Inventory.PickupMessage "$TXT_SIGIL"; } - action native void A_SelectPiece (); - action native void A_SelectSigilView (); - action native void A_SelectSigilDown (); - action native void A_SelectSigilAttack (); - action native void A_SigilCharge (); - action native void A_FireSigil1 (); - action native void A_FireSigil2 (); - action native void A_FireSigil3 (); - action native void A_FireSigil4 (); - action native void A_FireSigil5 (); + native void A_SelectPiece (); + native void A_SelectSigilView (); + native void A_SelectSigilDown (); + native void A_SelectSigilAttack (); + native void A_SigilCharge (); + native void A_FireSigil1 (); + native void A_FireSigil2 (); + native void A_FireSigil3 (); + native void A_FireSigil4 (); + native void A_FireSigil5 (); States { diff --git a/wadsrc/static/zscript/strife/spectral.txt b/wadsrc/static/zscript/strife/spectral.txt index df23f3663..d6a234904 100644 --- a/wadsrc/static/zscript/strife/spectral.txt +++ b/wadsrc/static/zscript/strife/spectral.txt @@ -12,10 +12,10 @@ class SpectralMonster : Actor native +NOICEDEATH } - action native void A_SpectreChunkSmall (); - action native void A_SpectreChunkLarge (); - action native void A_Spectre3Attack (); - action native void A_SpotLightning (); + native void A_SpectreChunkSmall (); + native void A_SpectreChunkLarge (); + native void A_Spectre3Attack (); + native void A_SpotLightning (); } @@ -124,7 +124,7 @@ class SpectralLightningH1 : SpectralLightningBase +SPECTRAL } - action native void A_SpectralLightningTail (); + native void A_SpectralLightningTail (); States { @@ -189,7 +189,7 @@ class SpectralLightningBigBall1 : SpectralLightningDeath2 +SPECTRAL } - action native void A_SpectralBigBallLightning (); + native void A_SpectralBigBallLightning (); States { @@ -259,7 +259,7 @@ class SpectralLightningSpot : SpectralLightningDeath1 Alpha 0.6; } - action native void A_SpectralLightning (); + native void A_SpectralLightning (); States { diff --git a/wadsrc/static/zscript/strife/stalker.txt b/wadsrc/static/zscript/strife/stalker.txt index b22e432c6..51a919041 100644 --- a/wadsrc/static/zscript/strife/stalker.txt +++ b/wadsrc/static/zscript/strife/stalker.txt @@ -28,11 +28,11 @@ class Stalker : Actor HitObituary "$OB_STALKER"; } - action native void A_StalkerLookInit (); - action native void A_StalkerChaseDecide (); - action native void A_StalkerWalk (); - action native void A_StalkerDrop (); - action native void A_StalkerAttack (); + native void A_StalkerLookInit (); + native void A_StalkerChaseDecide (); + native void A_StalkerWalk (); + native void A_StalkerDrop (); + native void A_StalkerAttack (); States { diff --git a/wadsrc/static/zscript/strife/strifeplayer.txt b/wadsrc/static/zscript/strife/strifeplayer.txt index 311bf308a..0b61e3122 100644 --- a/wadsrc/static/zscript/strife/strifeplayer.txt +++ b/wadsrc/static/zscript/strife/strifeplayer.txt @@ -36,9 +36,9 @@ class StrifePlayer : PlayerPawn Player.Colorset 7, "Blue", 0x90, 0x9F, 0x92, 0x20, 0x3F, 0x00, 0x1F, 0x50, 0x5F, 0x40, 0x4F, 0xC1, 0xCF, 0x01, 0x0F, 0xC0,0xC0,1,1, 0xD0, 0xDF, 0x10, 0x1F; } - action native void A_ItBurnsItBurns(); - action native void A_CrispyPlayer(); - action native void A_HandLower(); + native void A_ItBurnsItBurns(); + native void A_CrispyPlayer(); + native void A_HandLower(); States { diff --git a/wadsrc/static/zscript/strife/strifeweapons.txt b/wadsrc/static/zscript/strife/strifeweapons.txt index 4ae358bfa..bf94706c9 100644 --- a/wadsrc/static/zscript/strife/strifeweapons.txt +++ b/wadsrc/static/zscript/strife/strifeweapons.txt @@ -62,7 +62,7 @@ class PunchDagger : StrifeWeapon Tag "$TAG_PUNCHDAGGER"; } - action native void A_JabDagger (); + native void A_JabDagger (); States { @@ -184,9 +184,9 @@ class StrifeCrossbow : StrifeWeapon Inventory.Icon "CBOWA0"; } - action native void A_ClearFlash (); - action native void A_ShowElectricFlash (); - action native void A_FireArrow (class proj); + native void A_ClearFlash (); + native void A_ShowElectricFlash (); + native void A_FireArrow (class proj); States { @@ -331,7 +331,7 @@ class MiniMissileLauncher : StrifeWeapon Inventory.PickupMessage "$TXT_MMLAUNCHER"; } - action native void A_FireMiniMissile (); + native void A_FireMiniMissile (); States { @@ -446,7 +446,7 @@ class FlameThrower : StrifeWeapon Inventory.PickupMessage "$TXT_FLAMER"; } - action native void A_FireFlamer (); + native void A_FireFlamer (); States { @@ -492,7 +492,7 @@ class FlameMissile : Actor Obituary "$OB_MPFLAMETHROWER"; } - action native void A_FlameDie (); + native void A_FlameDie (); States { @@ -528,7 +528,7 @@ class Mauler : StrifeWeapon Obituary "$OB_MPMAULER1"; } - action native void A_FireMauler1 (); + native void A_FireMauler1 (); States { @@ -571,8 +571,8 @@ class Mauler2 : Mauler Tag "$TAG_MAULER2"; } - action native void A_FireMauler2Pre (); - action native void A_FireMauler2 (); + native void A_FireMauler2Pre (); + native void A_FireMauler2 (); States { @@ -639,7 +639,7 @@ class MaulerTorpedo : Actor Obituary "$OB_MPMAULER"; } - action native void A_MaulerTorpedoWave (); + native void A_MaulerTorpedoWave (); States { @@ -775,8 +775,8 @@ class PhosphorousFire : Actor native Obituary "$OB_MPPHOSPHOROUSGRENADE"; } - action native void A_Burnarea (); - action native void A_Burnination (); + native void A_Burnarea (); + native void A_Burnination (); States { @@ -816,7 +816,7 @@ class StrifeGrenadeLauncher : StrifeWeapon Inventory.PickupMessage "$TXT_GLAUNCHER"; } - action native void A_FireGrenade (class grenadetype, float angleofs, state flash); + native void A_FireGrenade (class grenadetype, float angleofs, state flash); States { diff --git a/wadsrc/static/zscript/strife/templar.txt b/wadsrc/static/zscript/strife/templar.txt index 4c640fd54..5b1605cf4 100644 --- a/wadsrc/static/zscript/strife/templar.txt +++ b/wadsrc/static/zscript/strife/templar.txt @@ -25,7 +25,7 @@ class Templar : Actor Obituary "$OB_TEMPLAR"; DropItem "EnergyPod"; } - action native void A_TemplarAttack(); + native void A_TemplarAttack(); States { diff --git a/wadsrc/static/zscript/strife/thingstoblowup.txt b/wadsrc/static/zscript/strife/thingstoblowup.txt index 659c13f56..dbbad8ed6 100644 --- a/wadsrc/static/zscript/strife/thingstoblowup.txt +++ b/wadsrc/static/zscript/strife/thingstoblowup.txt @@ -121,9 +121,9 @@ class PowerCrystal : Actor ActiveSound "misc/reactor"; } - action native void A_ExtraLightOff (); - action native void A_Explode512 (); - action native void A_LightGoesOut (); + native void A_ExtraLightOff (); + native void A_Explode512 (); + native void A_LightGoesOut (); States { From 37914223f0bcae69a3f8095e66c504715a9f42ec Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 18:13:54 +0200 Subject: [PATCH 092/255] - reviewed all places where VARF_Action and NAP were used and fixed what was still wrong. --- src/d_dehacked.cpp | 17 ++++++++++------- src/p_enemy.cpp | 2 +- src/scripting/decorate/thingdef_states.cpp | 14 +++++++------- src/scripting/thingdef.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 2 +- 5 files changed, 20 insertions(+), 17 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 71deb0169..97d15e4d0 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -808,22 +808,23 @@ void SetDehParams(FState *state, int codepointer) else { VMFunctionBuilder buildit(true); + int numargs = sym->GetImplicitArgs(); // Allocate registers used to pass parameters in. // self, stateowner, state (all are pointers) - buildit.Registers[REGT_POINTER].Get(NAP); + buildit.Registers[REGT_POINTER].Get(numargs); // Emit code to pass the standard action function parameters. - for (int i = 0; i < NAP; i++) + for (int i = 0; i < numargs; i++) { buildit.Emit(OP_PARAM, 0, REGT_POINTER, i); } // Emit code for action parameters. int argcount = MBFCodePointerFactories[codepointer](buildit, value1, value2); - buildit.Emit(OP_TAIL_K, buildit.GetConstantAddress(sym->Variants[0].Implementation, ATAG_OBJECT), NAP + argcount, 0); + buildit.Emit(OP_TAIL_K, buildit.GetConstantAddress(sym->Variants[0].Implementation, ATAG_OBJECT), numargs + argcount, 0); // Attach it to the state. VMScriptFunction *sfunc = new VMScriptFunction; buildit.MakeFunction(sfunc); - sfunc->NumArgs = NAP; - sfunc->ImplicitArgs = NAP; + sfunc->NumArgs = numargs; + sfunc->ImplicitArgs = numargs; state->SetAction(sfunc); sfunc->PrintableName.Format("Dehacked.%s.%d.%d", MBFCodePointers[codepointer].name.GetChars(), value1, value2); } @@ -2121,7 +2122,8 @@ static int PatchCodePtrs (int dummy) else { TArray &args = sym->Variants[0].ArgFlags; - if ((sym->Variants[0].Flags & (VARF_Method | VARF_Action)) != (VARF_Method | VARF_Action) || (args.Size() > NAP && !(args[NAP] & VARF_Optional))) + unsigned numargs = sym->GetImplicitArgs(); + if ((sym->Variants[0].Flags & VARF_Virtual || (args.Size() > numargs && !(args[numargs] & VARF_Optional)))) { Printf("Frame %d: Incompatible code pointer '%s'\n", frame, Line2); sym = NULL; @@ -2733,7 +2735,8 @@ static bool LoadDehSupp () else { TArray &args = sym->Variants[0].ArgFlags; - if ((sym->Variants[0].Flags & (VARF_Method|VARF_Action)) != (VARF_Method | VARF_Action) || (args.Size() > NAP && !(args[NAP] & VARF_Optional))) + unsigned numargs = sym->GetImplicitArgs(); + if ((sym->Variants[0].Flags & VARF_Virtual || (args.Size() > numargs && !(args[numargs] & VARF_Optional)))) { sc.ScriptMessage("Incompatible code pointer '%s'", sc.String); } diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 1a2bddda4..14ea2b7c1 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -2773,7 +2773,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Chase) PARAM_STATE_OPT (missile) { missile = NULL; } PARAM_INT_OPT (flags) { flags = 0; } - if (numparam >= NAP + 1) + if (numparam > 1) { if ((flags & CHF_RESURRECT) && P_CheckForResurrection(self, false)) return 0; diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 8b75b935f..dda25f926 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -38,7 +38,7 @@ ** */ -#include "actor.h" +#include "a_pickups.h" #include "info.h" #include "sc_man.h" #include "tarray.h" @@ -602,16 +602,16 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArrayVariants[0].Flags & VARF_Method) + if (afd->Variants[0].Flags & VARF_Action) + { + numparams -= NAP; + pnum += NAP; + } + else if (afd->Variants[0].Flags & VARF_Method) { numparams--; pnum++; } - if (afd->Variants[0].Flags & VARF_Action) - { - numparams -= 2; - pnum += 2; - } assert(numparams >= 0); zeroparm = numparams == 0; if (numparams > 0 && !(paramflags[pnum] & VARF_Optional)) diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 45e77b3ad..2798ab633 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -143,7 +143,7 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i SetImplicitArgs(&args, &argflags, &argnames, containingclass, flags); PFunction *sym = new PFunction(containingclass, NAME_None); // anonymous functions do not have names. - sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, VARF_Action|VARF_Method); + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, flags); return sym; } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 9b4212820..e702f7d2a 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -32,7 +32,7 @@ ** */ -#include "actor.h" +#include "a_pickups.h" #include "thingdef.h" #include "sc_man.h" #include "c_console.h" From c2b37aeeea85a3774a5c19c3411f466fa62773c1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 19:43:53 +0200 Subject: [PATCH 093/255] - fixed a conversion warning with the pointer-type AActor fields. - added master and tracer to the list of exported variables. - fixed: 'none' as class type must map to the real null pointer so that it won't get rejected by the stricter type checks. - added handling for member function calls to zcc_compile.cpp. - fixed: FxMemberFunctionCall may not delete the self expression if it gets passed on to the actual function call. --- src/dobjtype.h | 2 +- src/namedef.h | 2 ++ src/scripting/codegeneration/codegen.cpp | 8 +++++++- src/scripting/thingdef_data.cpp | 2 ++ src/scripting/zscript/zcc_compile.cpp | 6 +++++- 5 files changed, 17 insertions(+), 3 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index c5d96972b..f3e043bd9 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -574,7 +574,7 @@ class PField : public PSymbol public: PField(FName name, PType *type) : PSymbol(name), Offset(0), Type(type), Flags(0) {} PField(FName name, PType *type, DWORD flags) : PSymbol(name), Offset(0), Type(type), Flags(flags) {} - PField(FName name, PType *type, DWORD flags, unsigned offset) : PSymbol(name), Offset(offset), Type(type), Flags(flags) {} + PField(FName name, PType *type, DWORD flags, size_t offset) : PSymbol(name), Offset(unsigned(offset)), Type(type), Flags(flags) {} unsigned int Offset; PType *Type; diff --git a/src/namedef.h b/src/namedef.h index d512a7948..973557874 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -437,6 +437,8 @@ xx(ScaleX) xx(ScaleY) xx(Floatbobphase) xx(Target) +xx(Master) +xx(Tracer) xx(Blocking) xx(Blockmonsters) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index c4a466873..c7cd6e524 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4975,6 +4975,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) auto self = !(afd->Variants[0].Flags & VARF_Static) ? Self : nullptr; auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, staticonly); ArgList = nullptr; + if (Self == self) Self = nullptr; delete this; return x->Resolve(ctx); } @@ -6226,6 +6227,7 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) { FName clsname = static_cast(basex)->GetValue().GetName(); PClass *cls = NULL; + FxExpression *x; if (clsname != NAME_None) { @@ -6248,8 +6250,12 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) } ScriptPosition.Message(MSG_DEBUG, "resolving '%s' as class name", clsname.GetChars()); } + x = new FxConstant(cls, ScriptPosition); + } + else + { + x = new FxConstant(ScriptPosition); // create a genuine null pointer to get past the type checks. } - FxExpression *x = new FxConstant(cls, ScriptPosition); delete this; return x; } diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 260cc6408..7e0668a0f 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -677,4 +677,6 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); + symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); + symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e702f7d2a..5d309bedc 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2381,7 +2381,11 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return new FxFunctionCall(static_cast(fcall->Function)->Identifier, NAME_None, ConvertNodeList(fcall->Parameters), *ast); case AST_ExprMemberAccess: - break; + { + auto ema = static_cast(fcall->Function); + Printf("Member call to %s\n", FName(ema->Right).GetChars()); + return new FxMemberFunctionCall(ConvertNode(ema->Left), ema->Right, ConvertNodeList(fcall->Parameters), *ast); + } case AST_ExprBinary: // Array syntax for randoms. They are internally stored as ExprBinary with both an identifier on the left and right side. From 32d33618eab1933aba8decea604263aa0464f46a Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 22 Oct 2016 19:51:24 +0200 Subject: [PATCH 094/255] - better fix for the class type problem: We already know the wanted type so let's use that instead of trying to determine it from the actual name. --- src/scripting/codegeneration/codegen.cpp | 9 ++------- src/scripting/codegeneration/codegen.h | 6 ++---- 2 files changed, 4 insertions(+), 11 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index c7cd6e524..87f2e1f73 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6199,9 +6199,9 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) delete this; return x; } + auto to = static_cast(ValueType); if (basex->ValueType->GetClass() == RUNTIME_CLASS(PClassPointer)) { - auto to = static_cast(ValueType); auto from = static_cast(basex->ValueType); if (from->ClassRestriction->IsDescendantOf(to->ClassRestriction)) { @@ -6227,7 +6227,6 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) { FName clsname = static_cast(basex)->GetValue().GetName(); PClass *cls = NULL; - FxExpression *x; if (clsname != NAME_None) { @@ -6250,12 +6249,8 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) } ScriptPosition.Message(MSG_DEBUG, "resolving '%s' as class name", clsname.GetChars()); } - x = new FxConstant(cls, ScriptPosition); - } - else - { - x = new FxConstant(ScriptPosition); // create a genuine null pointer to get past the type checks. } + FxExpression *x = new FxConstant(cls, to, ScriptPosition); delete this; return x; } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 4f3b57c13..15ba2a933 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -364,12 +364,10 @@ public: isresolved = true; } - FxConstant(PClass *val, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(PClass *val, PClassPointer *valtype, const FScriptPosition &pos) : FxExpression(pos) { value.pointer = (void*)val; - if (val != nullptr) ValueType = NewClassPointer(val); - else ValueType = NewClassPointer(RUNTIME_CLASS(DObject)); - value.Type = NewClassPointer(RUNTIME_CLASS(DObject)); + value.Type = ValueType = valtype; isresolved = true; } From ccabb6f9bdc1e9ddf7549fe4b6f4eb98cdfc8e0d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 01:14:49 +0200 Subject: [PATCH 095/255] - Gave FxExpression a type identifier field so that certain combinations that are easy to optimize can be detected. --- src/scripting/codegeneration/codegen.cpp | 96 +++++++++---------- src/scripting/codegeneration/codegen.h | 114 ++++++++++++++++------- 2 files changed, 129 insertions(+), 81 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 87f2e1f73..d0713c50b 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -435,7 +435,7 @@ ExpEmit FxConstant::Emit(VMFunctionBuilder *build) //========================================================================== FxBoolCast::FxBoolCast(FxExpression *x) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_BoolCast, x->ScriptPosition) { basex = x; ValueType = TypeBool; @@ -533,7 +533,7 @@ ExpEmit FxBoolCast::Emit(VMFunctionBuilder *build) //========================================================================== FxIntCast::FxIntCast(FxExpression *x, bool nowarn) -: FxExpression(x->ScriptPosition) +: FxExpression(EFX_IntCast, x->ScriptPosition) { basex=x; ValueType = TypeSInt32; @@ -632,7 +632,7 @@ ExpEmit FxIntCast::Emit(VMFunctionBuilder *build) //========================================================================== FxFloatCast::FxFloatCast(FxExpression *x) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_FloatCast, x->ScriptPosition) { basex = x; ValueType = TypeFloat64; @@ -723,7 +723,7 @@ ExpEmit FxFloatCast::Emit(VMFunctionBuilder *build) //========================================================================== FxNameCast::FxNameCast(FxExpression *x) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_NameCast, x->ScriptPosition) { basex = x; ValueType = TypeName; @@ -801,7 +801,7 @@ ExpEmit FxNameCast::Emit(VMFunctionBuilder *build) //========================================================================== FxStringCast::FxStringCast(FxExpression *x) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_StringCast, x->ScriptPosition) { basex = x; ValueType = TypeString; @@ -898,7 +898,7 @@ ExpEmit FxStringCast::Emit(VMFunctionBuilder *build) //========================================================================== FxColorCast::FxColorCast(FxExpression *x) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_ColorCast, x->ScriptPosition) { basex = x; ValueType = TypeColor; @@ -977,7 +977,7 @@ ExpEmit FxColorCast::Emit(VMFunctionBuilder *build) //========================================================================== FxSoundCast::FxSoundCast(FxExpression *x) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_SoundCast, x->ScriptPosition) { basex = x; ValueType = TypeSound; @@ -1056,7 +1056,7 @@ ExpEmit FxSoundCast::Emit(VMFunctionBuilder *build) //========================================================================== FxTypeCast::FxTypeCast(FxExpression *x, PType *type, bool nowarn) - : FxExpression(x->ScriptPosition) + : FxExpression(EFX_TypeCast, x->ScriptPosition) { basex = x; ValueType = type; @@ -1241,7 +1241,7 @@ ExpEmit FxTypeCast::Emit(VMFunctionBuilder *build) //========================================================================== FxPlusSign::FxPlusSign(FxExpression *operand) -: FxExpression(operand->ScriptPosition) +: FxExpression(EFX_PlusSign, operand->ScriptPosition) { Operand=operand; } @@ -1295,7 +1295,7 @@ ExpEmit FxPlusSign::Emit(VMFunctionBuilder *build) //========================================================================== FxMinusSign::FxMinusSign(FxExpression *operand) -: FxExpression(operand->ScriptPosition) +: FxExpression(EFX_MinusSign, operand->ScriptPosition) { Operand=operand; } @@ -1375,7 +1375,7 @@ ExpEmit FxMinusSign::Emit(VMFunctionBuilder *build) //========================================================================== FxUnaryNotBitwise::FxUnaryNotBitwise(FxExpression *operand) -: FxExpression(operand->ScriptPosition) +: FxExpression(EFX_UnaryNotBitwise, operand->ScriptPosition) { Operand=operand; } @@ -1455,7 +1455,7 @@ ExpEmit FxUnaryNotBitwise::Emit(VMFunctionBuilder *build) //========================================================================== FxUnaryNotBoolean::FxUnaryNotBoolean(FxExpression *operand) -: FxExpression(operand->ScriptPosition) +: FxExpression(EFX_UnaryNotBoolean, operand->ScriptPosition) { Operand=operand; } @@ -1525,7 +1525,7 @@ ExpEmit FxUnaryNotBoolean::Emit(VMFunctionBuilder *build) //========================================================================== FxSizeAlign::FxSizeAlign(FxExpression *operand, int which) - : FxExpression(operand->ScriptPosition) + : FxExpression(EFX_SizeAlign, operand->ScriptPosition) { Operand = operand; Which = which; @@ -1586,7 +1586,7 @@ ExpEmit FxSizeAlign::Emit(VMFunctionBuilder *build) //========================================================================== FxPreIncrDecr::FxPreIncrDecr(FxExpression *base, int token) -: FxExpression(base->ScriptPosition), Token(token), Base(base) +: FxExpression(EFX_PreIncrDecr, base->ScriptPosition), Token(token), Base(base) { AddressRequested = false; AddressWritable = false; @@ -1680,7 +1680,7 @@ ExpEmit FxPreIncrDecr::Emit(VMFunctionBuilder *build) //========================================================================== FxPostIncrDecr::FxPostIncrDecr(FxExpression *base, int token) -: FxExpression(base->ScriptPosition), Token(token), Base(base) +: FxExpression(EFX_PostIncrDecr, base->ScriptPosition), Token(token), Base(base) { } @@ -1762,7 +1762,7 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) //========================================================================== FxAssign::FxAssign(FxExpression *base, FxExpression *right) -: FxExpression(base->ScriptPosition), Base(base), Right(right) +: FxExpression(EFX_Assign, base->ScriptPosition), Base(base), Right(right) { AddressRequested = false; AddressWritable = false; @@ -1915,7 +1915,7 @@ ExpEmit FxAssign::Emit(VMFunctionBuilder *build) //========================================================================== FxAssignSelf::FxAssignSelf(const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_AssignSelf, pos) { Assignment = nullptr; } @@ -1955,7 +1955,7 @@ ExpEmit FxAssignSelf::Emit(VMFunctionBuilder *build) //========================================================================== FxBinary::FxBinary(int o, FxExpression *l, FxExpression *r) -: FxExpression(l->ScriptPosition) +: FxExpression(EFX_Binary, l->ScriptPosition) { Operator=o; left=l; @@ -2842,7 +2842,7 @@ ExpEmit FxLtGtEq::Emit(VMFunctionBuilder *build) //========================================================================== FxBinaryLogical::FxBinaryLogical(int o, FxExpression *l, FxExpression *r) -: FxExpression(l->ScriptPosition) +: FxExpression(EFX_BinaryLogical, l->ScriptPosition) { Operator=o; left=l; @@ -3020,7 +3020,7 @@ ExpEmit FxBinaryLogical::Emit(VMFunctionBuilder *build) //========================================================================== FxConditional::FxConditional(FxExpression *c, FxExpression *t, FxExpression *f) -: FxExpression(c->ScriptPosition) +: FxExpression(EFX_Conditional, c->ScriptPosition) { condition = c; truex=t; @@ -3185,7 +3185,7 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) // //========================================================================== FxAbs::FxAbs(FxExpression *v) -: FxExpression(v->ScriptPosition) +: FxExpression(EFX_Abs, v->ScriptPosition) { val = v; ValueType = v->ValueType; @@ -3275,7 +3275,7 @@ ExpEmit FxAbs::Emit(VMFunctionBuilder *build) // //========================================================================== FxATan2::FxATan2(FxExpression *y, FxExpression *x, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_ATan2, pos) { yval = y; xval = x; @@ -3368,7 +3368,7 @@ ExpEmit FxATan2::ToReg(VMFunctionBuilder *build, FxExpression *val) // //========================================================================== FxMinMax::FxMinMax(TArray &expr, FName type, const FScriptPosition &pos) -: FxExpression(pos), Type(type) +: FxExpression(EFX_MinMax, pos), Type(type) { assert(expr.Size() > 0); assert(type == NAME_Min || type == NAME_Max); @@ -3586,7 +3586,7 @@ ExpEmit FxMinMax::Emit(VMFunctionBuilder *build) // //========================================================================== FxRandom::FxRandom(FRandom * r, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos, bool nowarn) -: FxExpression(pos) +: FxExpression(EFX_Random, pos) { EmitTail = false; if (mi != NULL && ma != NULL) @@ -3719,7 +3719,7 @@ ExpEmit FxRandom::Emit(VMFunctionBuilder *build) // //========================================================================== FxRandomPick::FxRandomPick(FRandom *r, TArray &expr, bool floaty, const FScriptPosition &pos, bool nowarn) -: FxExpression(pos) +: FxExpression(EFX_RandomPick, pos) { assert(expr.Size() > 0); choices.Resize(expr.Size()); @@ -3891,6 +3891,7 @@ FxFRandom::FxFRandom(FRandom *r, FxExpression *mi, FxExpression *ma, const FScri max = new FxFloatCast(ma); } ValueType = TypeFloat64; + ExprType = EFX_FRandom; } //========================================================================== @@ -3965,7 +3966,7 @@ ExpEmit FxFRandom::Emit(VMFunctionBuilder *build) //========================================================================== FxRandom2::FxRandom2(FRandom *r, FxExpression *m, const FScriptPosition &pos, bool nowarn) -: FxExpression(pos) +: FxExpression(EFX_Random2, pos) { EmitTail = false; rng = r; @@ -4051,7 +4052,7 @@ ExpEmit FxRandom2::Emit(VMFunctionBuilder *build) //========================================================================== FxIdentifier::FxIdentifier(FName name, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_Identifier, pos) { Identifier = name; } @@ -4195,6 +4196,7 @@ FxMemberIdentifier::FxMemberIdentifier(FxExpression *left, FName name, const FSc : FxIdentifier(name, pos) { Object = left; + ExprType = EFX_MemberIdentifier; } //========================================================================== @@ -4295,7 +4297,7 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) //========================================================================== FxLocalVariable::FxLocalVariable(FxLocalVariableDeclaration *var, const FScriptPosition &sc) - : FxExpression(sc) + : FxExpression(EFX_LocalVariable, sc) { Variable = var; ValueType = var->ValueType; @@ -4330,7 +4332,7 @@ ExpEmit FxLocalVariable::Emit(VMFunctionBuilder *build) //========================================================================== FxSelf::FxSelf(const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_Self, pos) { } @@ -4373,7 +4375,7 @@ ExpEmit FxSelf::Emit(VMFunctionBuilder *build) //========================================================================== FxClassMember::FxClassMember(FxExpression *x, PField* mem, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_ClassMember, pos) { classx = x; membervar = mem; @@ -4471,7 +4473,7 @@ ExpEmit FxClassMember::Emit(VMFunctionBuilder *build) //========================================================================== FxArrayElement::FxArrayElement(FxExpression *base, FxExpression *_index) -:FxExpression(base->ScriptPosition) +:FxExpression(EFX_ArrayElement, base->ScriptPosition) { Array=base; index = _index; @@ -4650,7 +4652,7 @@ ExpEmit FxArrayElement::Emit(VMFunctionBuilder *build) //========================================================================== FxFunctionCall::FxFunctionCall(FName methodname, FName rngname, FArgumentList *args, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_FunctionCall, pos) { MethodName = methodname; RNG = nullptr; @@ -4888,7 +4890,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) //========================================================================== FxMemberFunctionCall::FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos) - : FxExpression(pos) + : FxExpression(EFX_MemberFunctionCall, pos) { Self = self; MethodName = methodname; @@ -4991,7 +4993,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) //========================================================================== FxActionSpecialCall::FxActionSpecialCall(FxExpression *self, int special, FArgumentList *args, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_ActionSpecialCall, pos) { Self = self; Special = special; @@ -5157,7 +5159,7 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) //========================================================================== FxVMFunctionCall::FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool novirtual) -: FxExpression(pos) +: FxExpression(EFX_VMFunctionCall, pos) { Self = self; Function = func; @@ -5391,7 +5393,7 @@ bool FxVMFunctionCall::CheckEmitCast(VMFunctionBuilder *build, bool returnit, Ex //========================================================================== FxFlopFunctionCall::FxFlopFunctionCall(size_t index, FArgumentList *args, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_FlopFunctionCall, pos) { assert(index < countof(FxFlops) && "FLOP index out of range"); Index = (int)index; @@ -5612,7 +5614,7 @@ bool FxCompoundStatement::CheckLocalVariable(FName name) FxIfStatement::FxIfStatement(FxExpression *cond, FxExpression *true_part, FxExpression *false_part, const FScriptPosition &pos) -: FxExpression(pos) +: FxExpression(EFX_IfStatement, pos) { Condition = cond; WhenTrue = true_part; @@ -5764,7 +5766,7 @@ void FxLoopStatement::Backpatch(VMFunctionBuilder *build, size_t loopstart, size //========================================================================== FxWhileLoop::FxWhileLoop(FxExpression *condition, FxExpression *code, const FScriptPosition &pos) -: FxLoopStatement(pos), Condition(condition), Code(code) +: FxLoopStatement(EFX_WhileLoop, pos), Condition(condition), Code(code) { ValueType = TypeVoid; } @@ -5850,7 +5852,7 @@ ExpEmit FxWhileLoop::Emit(VMFunctionBuilder *build) //========================================================================== FxDoWhileLoop::FxDoWhileLoop(FxExpression *condition, FxExpression *code, const FScriptPosition &pos) -: FxLoopStatement(pos), Condition(condition), Code(code) +: FxLoopStatement(EFX_DoWhileLoop, pos), Condition(condition), Code(code) { ValueType = TypeVoid; } @@ -5938,7 +5940,7 @@ ExpEmit FxDoWhileLoop::Emit(VMFunctionBuilder *build) //========================================================================== FxForLoop::FxForLoop(FxExpression *init, FxExpression *condition, FxExpression *iteration, FxExpression *code, const FScriptPosition &pos) -: FxLoopStatement(pos), Init(init), Condition(condition), Iteration(iteration), Code(code) +: FxLoopStatement(EFX_ForLoop, pos), Init(init), Condition(condition), Iteration(iteration), Code(code) { ValueType = TypeVoid; } @@ -6050,7 +6052,7 @@ ExpEmit FxForLoop::Emit(VMFunctionBuilder *build) //========================================================================== FxJumpStatement::FxJumpStatement(int token, const FScriptPosition &pos) -: FxExpression(pos), Token(token) +: FxExpression(EFX_JumpStatement, pos), Token(token) { ValueType = TypeVoid; } @@ -6084,7 +6086,7 @@ ExpEmit FxJumpStatement::Emit(VMFunctionBuilder *build) //========================================================================== FxReturnStatement::FxReturnStatement(FxExpression *value, const FScriptPosition &pos) -: FxExpression(pos), Value(value) +: FxExpression(EFX_ReturnStatement, pos), Value(value) { ValueType = TypeVoid; } @@ -6162,7 +6164,7 @@ VMFunction *FxReturnStatement::GetDirectFunction() //========================================================================== FxClassTypeCast::FxClassTypeCast(PClassPointer *dtype, FxExpression *x) -: FxExpression(x->ScriptPosition) +: FxExpression(EFX_ClassTypeCast, x->ScriptPosition) { ValueType = dtype; desttype = dtype->ClassRestriction; @@ -6348,7 +6350,7 @@ FxExpression *FxStateByIndex::Resolve(FCompileContext &ctx) //========================================================================== FxRuntimeStateIndex::FxRuntimeStateIndex(FxExpression *index) -: FxExpression(index->ScriptPosition), Index(index) +: FxExpression(EFX_RuntimeStateIndex, index->ScriptPosition), Index(index) { EmitTail = false; ValueType = TypeState; @@ -6468,7 +6470,7 @@ ExpEmit FxRuntimeStateIndex::Emit(VMFunctionBuilder *build) //========================================================================== FxMultiNameState::FxMultiNameState(const char *_statestring, const FScriptPosition &pos) - :FxExpression(pos) + :FxExpression(EFX_MultiNameState, pos) { FName scopename; FString statestring = _statestring; @@ -6645,7 +6647,7 @@ ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) //========================================================================== FxDamageValue::FxDamageValue(FxExpression *v) -: FxExpression(v->ScriptPosition) +: FxExpression(EFX_DamageValue, v->ScriptPosition) { val = v; ValueType = TypeVoid; @@ -6696,7 +6698,7 @@ ExpEmit FxDamageValue::Emit(VMFunctionBuilder *build) //========================================================================== FxLocalVariableDeclaration::FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, int varflags, const FScriptPosition &p) - :FxExpression(p) + :FxExpression(EFX_LocalVariableDeclaration, p) { ValueType = type; VarFlags = varflags; diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 15ba2a933..8cce34a15 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -202,6 +202,68 @@ struct ExpEmit BYTE RegNum, RegType, Konst:1, Fixed:1, Final:1, Target:1; }; +enum EFxType +{ + EFX_Expression, + EFX_Identifier, + EFX_MemberIdentifier, + EFX_ClassDefaults, + EFX_Constant, + EFX_BoolCast, + EFX_IntCast, + EFX_FloatCast, + EFX_NameCast, + EFX_StringCast, + EFX_ColorCast, + EFX_SoundCast, + EFX_TypeCast, + EFX_PlusSign, + EFX_MinusSign, + EFX_UnaryNotBitwise, + EFX_UnaryNotBoolean, + EFX_SizeAlign, + EFX_PreIncrDecr, + EFX_PostIncrDecr, + EFX_Assign, + EFX_AssignSelf, + EFX_Binary, // one token fits all, the operator is enough to distinguish them. + EFX_BinaryLogical, + EFX_Conditional, + EFX_Abs, + EFX_ATan2, + EFX_MinMax, + EFX_Random, + EFX_RandomPick, + EFX_FRandom, + EFX_Random2, + EFX_ClassMember, + EFX_LocalVariable, + EFX_Self, + EFX_ArrayElement, + EFX_FunctionCall, + EFX_MemberFunctionCall, + EFX_ActionSpecialCall, + EFX_FlopFunctionCall, + EFX_VMFunctionCall, + EFX_Sequence, + EFX_CompoundStatement, + EFX_IfStatement, + EFX_LoopStatement, + EFX_WhileLoop, + EFX_DoWhileLoop, + EFX_ForLoop, + EFX_JumpStatement, + EFX_ReturnStatement, + EFX_ClassTypeCast, + EFX_StateByIndex, + EFX_RuntimeStateIndex, + EFX_MultiNameState, + EFX_DamageValue, + EFX_Nop, + EFX_LocalVariableDeclaration, + EFX_COUNT +}; + //========================================================================== // // @@ -211,8 +273,8 @@ struct ExpEmit class FxExpression { protected: - FxExpression(const FScriptPosition &pos) - : ScriptPosition(pos) + FxExpression(EFxType type, const FScriptPosition &pos) + : ScriptPosition(pos), ExprType(type) { } @@ -235,6 +297,7 @@ public: PType *ValueType = nullptr; bool isresolved = false; + EFxType ExprType; }; //========================================================================== @@ -270,23 +333,6 @@ public: }; -//========================================================================== -// -// FxDotIdentifier -// -//========================================================================== - -class FxDotIdentifier : public FxExpression -{ - FxExpression *container; - FName Identifier; - -public: - FxDotIdentifier(FxExpression*, FName, const FScriptPosition &); - ~FxDotIdentifier(); - FxExpression *Resolve(FCompileContext&); -}; - //========================================================================== // // FxClassDefaults @@ -315,70 +361,70 @@ class FxConstant : public FxExpression ExpVal value; public: - FxConstant(bool val, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(bool val, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { ValueType = value.Type = TypeBool; value.Int = val; isresolved = true; } - FxConstant(int val, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(int val, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { ValueType = value.Type = TypeSInt32; value.Int = val; isresolved = true; } - FxConstant(double val, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(double val, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { ValueType = value.Type = TypeFloat64; value.Float = val; isresolved = true; } - FxConstant(FSoundID val, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(FSoundID val, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { ValueType = value.Type = TypeSound; value.Int = val; isresolved = true; } - FxConstant(FName val, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(FName val, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { ValueType = value.Type = TypeName; value.Int = val; isresolved = true; } - FxConstant(const FString &str, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(const FString &str, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { ValueType = TypeString; value = ExpVal(str); isresolved = true; } - FxConstant(ExpVal cv, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(ExpVal cv, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { value = cv; ValueType = cv.Type; isresolved = true; } - FxConstant(PClass *val, PClassPointer *valtype, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(PClass *val, PClassPointer *valtype, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { value.pointer = (void*)val; value.Type = ValueType = valtype; isresolved = true; } - FxConstant(FState *state, const FScriptPosition &pos) : FxExpression(pos) + FxConstant(FState *state, const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { value.pointer = state; ValueType = value.Type = TypeState; isresolved = true; } - FxConstant(const FScriptPosition &pos) : FxExpression(pos) + FxConstant(const FScriptPosition &pos) : FxExpression(EFX_Constant, pos) { value.pointer = nullptr; ValueType = value.Type = TypeNullPtr; @@ -1175,7 +1221,7 @@ class FxSequence : public FxExpression TDeletingArray Expressions; public: - FxSequence(const FScriptPosition &pos) : FxExpression(pos) {} + FxSequence(const FScriptPosition &pos) : FxExpression(EFX_Sequence, pos) {} FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); } @@ -1232,8 +1278,8 @@ public: class FxLoopStatement : public FxExpression { protected: - FxLoopStatement(const FScriptPosition &pos) - : FxExpression(pos) + FxLoopStatement(EFxType etype, const FScriptPosition &pos) + : FxExpression(etype, pos) { } @@ -1367,7 +1413,7 @@ class FxStateByIndex : public FxExpression public: - FxStateByIndex(int i, const FScriptPosition &pos) : FxExpression(pos) + FxStateByIndex(int i, const FScriptPosition &pos) : FxExpression(EFX_StateByIndex, pos) { index = i; } @@ -1440,7 +1486,7 @@ class FxNop : public FxExpression { public: FxNop(const FScriptPosition &p) - : FxExpression(p) + : FxExpression(EFX_Nop, p) { isresolved = true; } From f9cd2c9af7fa4dce1edfb32097ed813ff4f38527 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 12:00:25 +0200 Subject: [PATCH 096/255] - added switch/case processing. Right now it is just a sequence of test/jmp instructions. It may make sense to add a special opcode that can perform the comparisons natively but that's an option for later. - added a TESTN instruction. This is like TEST but negates the operand. This was added to avoid flooding the constant table with too many case labels. With TEST and TESTN combined, all numbers between -65535 and 65535 can be kept entirely inside the instruction. Numbers outside this range still use a BEQ instruction. --- src/scripting/codegeneration/codegen.cpp | 228 +++++++++++++++++++++++ src/scripting/codegeneration/codegen.h | 47 +++++ src/scripting/vm/vmexec.h | 7 + src/scripting/vm/vmops.h | 1 + src/scripting/zscript/zcc_compile.cpp | 21 ++- wadsrc/static/zscript.txt | 2 + 6 files changed, 304 insertions(+), 2 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d0713c50b..9568c34a5 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5606,6 +5606,234 @@ bool FxCompoundStatement::CheckLocalVariable(FName name) return false; } +//========================================================================== +// +// FxSwitchStatement +// +//========================================================================== + +FxSwitchStatement::FxSwitchStatement(FxExpression *cond, FArgumentList *content, const FScriptPosition &pos) + : FxExpression(EFX_SwitchStatement, pos) +{ + Condition = new FxIntCast(cond, false); + Content = content; +} + +FxSwitchStatement::~FxSwitchStatement() +{ + SAFE_DELETE(Condition); + SAFE_DELETE(Content); +} + +FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(Condition, ctx); + + if (Content == nullptr || Content->Size() == 0) + { + ScriptPosition.Message(MSG_WARNING, "Empty switch statement"); + if (Condition->isConstant()) + { + return new FxNop(ScriptPosition); + } + else + { + // The condition may have a side effect so it should be processed (possible to-do: Analyze all nodes in there and delete if not.) + auto x = Condition; + Condition = nullptr; + delete this; + return Condition; + } + } + + for (auto &line : *Content) + { + // Do not resolve breaks, they need special treatment inside switch blocks. + if (line->ExprType != EFX_JumpStatement || static_cast(line)->Token != TK_Break) + { + SAFE_RESOLVE(line, ctx); + } + } + + if (Condition->isConstant()) + { + ScriptPosition.Message(MSG_WARNING, "Case expression is constant"); + auto &content = *Content; + unsigned defaultindex = -1; + unsigned defaultbreak = -1; + unsigned caseindex = -1; + unsigned casebreak = -1; + // look for a case label with a matching value + for (unsigned i = 0; i < content.Size(); i++) + { + if (content[i] != nullptr) + { + if (content[i]->ExprType == EFX_CaseStatement) + { + auto casestmt = static_cast(content[i]); + if (casestmt->Condition == nullptr) defaultindex = i; + else if (casestmt->CaseValue == static_cast(Condition)->GetValue().GetInt()) caseindex = i; + } + if (content[i]->ExprType == EFX_JumpStatement && static_cast(content[i])->Token == TK_Break) + { + if (defaultindex >= 0 && defaultbreak < 0) defaultbreak = i; + if (caseindex >= 0 && casebreak < 0) + { + casebreak = i; + break; // when we find this we do not need to look any further. + } + } + } + } + if (caseindex < 0) + { + caseindex = defaultindex; + casebreak = defaultbreak; + } + if (caseindex > 0 && casebreak - caseindex > 1) + { + auto seq = new FxSequence(ScriptPosition); + for (unsigned i = caseindex + 1; i < casebreak; i++) + { + if (content[i] != nullptr && content[i]->ExprType != EFX_CaseStatement) + { + seq->Add(content[i]); + content[i] = nullptr; + } + } + delete this; + return seq->Resolve(ctx); + } + delete this; + return new FxNop(ScriptPosition); + } + + int mincase = INT_MAX; + int maxcase = INT_MIN; + for (auto line : *Content) + { + if (line->ExprType == EFX_CaseStatement) + { + auto casestmt = static_cast(line); + if (casestmt->Condition != nullptr) + { + CaseAddr ca = { casestmt->CaseValue, 0 }; + CaseAddresses.Push(ca); + if (ca.casevalue < mincase) mincase = ca.casevalue; + if (ca.casevalue > maxcase) maxcase = ca.casevalue; + } + } + } + return this; +} + +ExpEmit FxSwitchStatement::Emit(VMFunctionBuilder *build) +{ + assert(Condition != nullptr); + ExpEmit emit = Condition->Emit(build); + assert(emit.RegType == REGT_INT); + // todo: + // - sort jump table by value. + // - optimize the switch dispatcher to run in native code instead of executing each single branch instruction on its own. + // e.g.: build->Emit(OP_SWITCH, emit.RegNum, build->GetConstantInt(CaseAddresses.Size()); + for (auto &ca : CaseAddresses) + { + if (ca.casevalue >= 0 && ca.casevalue <= 0xffff) + { + build->Emit(OP_TEST, emit.RegNum, (VM_SHALF)ca.casevalue); + } + else if (ca.casevalue < 0 && ca.casevalue >= -0xffff) + { + build->Emit(OP_TESTN, emit.RegNum, (VM_SHALF)-ca.casevalue); + } + else + { + build->Emit(OP_EQ_K, 1, emit.RegNum, build->GetConstantInt(ca.casevalue)); + } + ca.jumpaddress = build->Emit(OP_JMP, 0); + } + size_t DefaultAddress = build->Emit(OP_JMP, 0); + TArray BreakAddresses; + + for (auto line : *Content) + { + switch (line->ExprType) + { + case EFX_CaseStatement: + if (static_cast(line)->Condition != nullptr) + { + for (auto &ca : CaseAddresses) + { + if (ca.casevalue == static_cast(line)->CaseValue) + { + build->BackpatchToHere(ca.jumpaddress); + break; + } + } + } + else + { + build->BackpatchToHere(DefaultAddress); + } + break; + + case EFX_JumpStatement: + if (static_cast(line)->Token == TK_Break) + { + BreakAddresses.Push(build->Emit(OP_JMP, 0)); + break; + } + // fall through for continue. + + default: + line->Emit(build); + break; + } + } + for (auto addr : BreakAddresses) + { + build->BackpatchToHere(addr); + } + return ExpEmit(); +} + + +//========================================================================== +// +// FxCaseStatement +// +//========================================================================== + +FxCaseStatement::FxCaseStatement(FxExpression *cond, const FScriptPosition &pos) + : FxExpression(EFX_CaseStatement, pos) +{ + Condition = cond? new FxIntCast(cond, false) : nullptr; +} + +FxCaseStatement::~FxCaseStatement() +{ + SAFE_DELETE(Condition); +} + +FxExpression *FxCaseStatement::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE_OPT(Condition, ctx); + + if (Condition != nullptr) + { + if (!Condition->isConstant()) + { + ScriptPosition.Message(MSG_ERROR, "Case label must be a constant value"); + delete this; + return nullptr; + } + CaseValue = static_cast(Condition)->GetValue().GetInt(); + } + return this; +} + //========================================================================== // // FxIfStatement diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 8cce34a15..3ea97ba66 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -261,6 +261,8 @@ enum EFxType EFX_DamageValue, EFX_Nop, EFX_LocalVariableDeclaration, + EFX_SwitchStatement, + EFX_CaseStatement, EFX_COUNT }; @@ -1250,6 +1252,51 @@ public: bool CheckLocalVariable(FName name); }; +//========================================================================== +// +// FxSwitchStatement +// +//========================================================================== + +class FxSwitchStatement : public FxExpression +{ + FxExpression *Condition; + FArgumentList *Content; + + struct CaseAddr + { + int casevalue; + size_t jumpaddress; + }; + + TArray CaseAddresses; + +public: + FxSwitchStatement(FxExpression *cond, FArgumentList *content, const FScriptPosition &pos); + ~FxSwitchStatement(); + FxExpression *Resolve(FCompileContext&); + ExpEmit Emit(VMFunctionBuilder *build); +}; + +//========================================================================== +// +// FxSwitchStatement +// +//========================================================================== + +class FxCaseStatement : public FxExpression +{ + FxExpression *Condition; + int CaseValue; // copy the value to here for easier access. + + friend class FxSwitchStatement; + +public: + FxCaseStatement(FxExpression *cond, const FScriptPosition &pos); + ~FxCaseStatement(); + FxExpression *Resolve(FCompileContext&); +}; + //========================================================================== // // FxIfStatement diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index d3c1632b8..2ddc50599 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -372,6 +372,13 @@ begin: pc++; } NEXTOP; + OP(TESTN): + ASSERTD(a); + if (-reg.d[a] != BC) + { + pc++; + } + NEXTOP; OP(JMP): pc += JMPOFS(pc); NEXTOP; diff --git a/src/scripting/vm/vmops.h b/src/scripting/vm/vmops.h index 1b34dcc0f..9ffe2d847 100644 --- a/src/scripting/vm/vmops.h +++ b/src/scripting/vm/vmops.h @@ -69,6 +69,7 @@ xx(DYNCAST_K, dyncast,RPRPKP), // Control flow. xx(TEST, test, RII16), // if (dA != BC) then pc++ +xx(TESTN, testn, RII16), // if (dA != -BC) then pc++ xx(JMP, jmp, I24), // pc += ABC -- The ABC fields contain a signed 24-bit offset. xx(IJMP, ijmp, RII16), // pc += dA + BC -- BC is a signed offset. The target instruction must be a JMP. xx(PARAM, param, __BCP), // push parameter encoded in BC for function call (B=regtype, C=regnum) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 5d309bedc..ed85ab6b3 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2677,9 +2677,26 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // not yet done case AST_SwitchStmt: - case AST_CaseStmt: - break; + { + auto swtch = static_cast(ast); + if (swtch->Content->NodeType != AST_CompoundStmt) + { + Error(ast, "Expecting { after 'switch'"); + return new FxNop(*ast); // allow compiler to continue looking for errors. + } + else + { + // The switch content is wrapped into a compound statement which needs to be unraveled here. + auto cmpnd = static_cast(swtch->Content); + return new FxSwitchStatement(ConvertNode(swtch->Condition), ConvertNodeList(cmpnd->Content), *ast); + } + } + case AST_CaseStmt: + { + auto cases = static_cast(ast); + return new FxCaseStatement(ConvertNode(cases->Condition), *ast); + } case AST_CompoundStmt: { diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 6de64d07e..3ab33bfd9 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -177,3 +177,5 @@ zscript/chex/chexweapons.txt zscript/chex/chexitems.txt zscript/chex/chexdecorations.txt zscript/chex/chexplayer.txt + +zscript/test2.txt From a2116fc7bf682cb67d3c9c675930743fd83072ff Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 12:57:21 +0200 Subject: [PATCH 097/255] - created an export for P_SpawnMissile so that I can do some tests with functions. - allow class extensions. These are separate blocks in different files that get concatenated to one class body for processing. The reason is to allow spreading the many functions in Actor over multiple files, so that they remain manageable. For example, all the Doom action functions should be in their respective files, but their symbols need to be in Actor. To extend a class, both files need to be in the same translation unit, so it won't allow user-side extension of internal classes. --- src/p_mobj.cpp | 9 ++++++++ src/sc_man_scanner.re | 2 +- src/sc_man_tokens.h | 2 +- src/scripting/vm/vm.h | 1 + src/scripting/zscript/zcc-parse.lemon | 12 +++++++++++ src/scripting/zscript/zcc_compile.cpp | 31 +++++++++++++++++++++++++-- src/scripting/zscript/zcc_parser.cpp | 1 + src/scripting/zscript/zcc_parser.h | 1 + wadsrc/static/zscript/actor.txt | 7 ++++-- 9 files changed, 60 insertions(+), 6 deletions(-) diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index f61ad34bb..d89a89576 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -5824,6 +5824,15 @@ AActor *P_SpawnMissile (AActor *source, AActor *dest, PClassActor *type, AActor return P_SpawnMissileXYZ (source->PosPlusZ(32 + source->GetBobOffset()), source, dest, type, true, owner); } +DEFINE_ACTION_FUNCTION(AActor, P_SpawnMissile) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(dest, AActor); + PARAM_CLASS(type, AActor); + PARAM_OBJECT_OPT(owner, AActor) { owner = self; } + ACTION_RETURN_OBJECT(P_SpawnMissile(self, dest, type, owner)); +} + AActor *P_SpawnMissileZ (AActor *source, double z, AActor *dest, PClassActor *type) { if (source == NULL) diff --git a/src/sc_man_scanner.re b/src/sc_man_scanner.re index caeb18f8c..cc9968ae3 100644 --- a/src/sc_man_scanner.re +++ b/src/sc_man_scanner.re @@ -151,7 +151,7 @@ std2: 'transient' { RET(TK_Transient); } 'final' { RET(TK_Final); } 'throws' { RET(TK_Throws); } - 'extends' { RET(TK_Extends); } + 'extend' { RET(TK_Extend); } 'public' { RET(TK_Public); } 'protected' { RET(TK_Protected); } 'private' { RET(TK_Private); } diff --git a/src/sc_man_tokens.h b/src/sc_man_tokens.h index 69927883c..19d331301 100644 --- a/src/sc_man_tokens.h +++ b/src/sc_man_tokens.h @@ -89,7 +89,7 @@ xx(TK_Transient, "'transient'") xx(TK_Volatile, "'volatile'") xx(TK_Final, "'final'") xx(TK_Throws, "'throws'") -xx(TK_Extends, "'extends'") +xx(TK_Extend, "'extend'") xx(TK_Public, "'public'") xx(TK_Protected, "'protected'") xx(TK_Private, "'private'") diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index a37b7449b..12ce01273 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -1013,6 +1013,7 @@ struct AFuncDesc #define ACTION_RETURN_STATE(v) do { FState *state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_STATE); return 1; } return 0; } while(0) +#define ACTION_RETURN_OBJECT(v) do { auto state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_OBJECT); return 1; } return 0; } while(0) #define ACTION_RETURN_FLOAT(v) do { double u = v; if (numret > 0) { assert(ret != nullptr); ret->SetFloat(u); return 1; } return 0; } while(0) #define ACTION_RETURN_INT(v) do { int u = v; if (numret > 0) { assert(ret != NULL); ret->SetInt(u); return 1; } return 0; } while(0) #define ACTION_RETURN_BOOL(v) ACTION_RETURN_INT(v) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index eeeba6295..fc34fd2d7 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -171,6 +171,18 @@ class_definition(X) ::= class_head(A) class_body(B). X = A; /*X-overwrites-A*/ } +class_head(X) ::= EXTEND CLASS(T) IDENTIFIER(A). +{ + NEW_AST_NODE(Class,head,T); + head->NodeName = A.Name(); + head->ParentName = nullptr; + head->Flags = ZCC_Extension; + head->Replaces = nullptr; + head->Type = nullptr; + head->Symbol = nullptr; + X = head; +} + class_head(X) ::= CLASS(T) IDENTIFIER(A) class_ancestry(B) class_flags(C). { NEW_AST_NODE(Class,head,T); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index ed85ab6b3..8389975ef 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -61,8 +61,29 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) { - Classes.Push(new ZCC_ClassWork(static_cast(cnode), treenode)); - auto cls = Classes.Last(); + ZCC_ClassWork *cls = nullptr; + // If this is a class extension, put the new node directly into the existing class. + if (cnode->Flags == ZCC_Extension) + { + for (auto clss : Classes) + { + if (clss->NodeName() == cnode->NodeName) + { + cls = clss; + break; + } + } + if (cls == nullptr) + { + Error(cnode, "Class %s cannot be found in the current translation unit."); + return; + } + } + else + { + Classes.Push(new ZCC_ClassWork(static_cast(cnode), treenode)); + cls = Classes.Last(); + } auto node = cnode->Body; PSymbolTreeNode *childnode; @@ -220,6 +241,12 @@ ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, switch (node->NodeType) { case AST_Class: + // a class extension should not check the tree node symbols. + if (static_cast(node)->Flags == ZCC_Extension) + { + ProcessClass(static_cast(node), tnode); + break; + } case AST_Struct: case AST_ConstantDef: case AST_Enum: diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 7d4edf78a..bc7857630 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -198,6 +198,7 @@ static void InitTokenMap() TOKENDEF (TK_Offset, ZCC_OFFSET); TOKENDEF (TK_CanRaise, ZCC_CANRAISE); TOKENDEF (TK_Light, ZCC_LIGHT); + TOKENDEF (TK_Extend, ZCC_EXTEND); ZCC_InitOperators(); ZCC_InitConversions(); diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 503ef7e9e..ca8c3f3cb 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -32,6 +32,7 @@ enum ZCC_ReadOnly = 1 << 9, ZCC_FuncConst = 1 << 10, ZCC_Abstract = 1 << 11, + ZCC_Extension = 1 << 12, }; // Function parameter modifiers diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 5144a1bd0..502b8d0cf 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -47,6 +47,9 @@ class Actor : Thinker native } // Functions + native Actor P_SpawnMissile(Actor dest, class type, Actor owner = null); + + // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); native bool IsPointerEqual(int ptr_select1, int ptr_select2); native int CountInv(class itemtype, int ptr_select = AAPTR_DEFAULT); @@ -112,8 +115,8 @@ class Actor : Thinker native native void A_BetaSkullAttack(); native void A_Metal(); native void A_SpidRefire(); - native void A_BabyMetal(); - native void A_BspiAttack(); + //native void A_BabyMetal(); + //native void A_BspiAttack(); native void A_Hoof(); native void A_CyberAttack(); native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); From 46c7f1151fe074b75e8b4d3cf663b5ff625a6376 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 12:58:03 +0200 Subject: [PATCH 098/255] - restored zscript.txt. --- wadsrc/static/zscript.txt | 2 -- 1 file changed, 2 deletions(-) diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 3ab33bfd9..6de64d07e 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -177,5 +177,3 @@ zscript/chex/chexweapons.txt zscript/chex/chexitems.txt zscript/chex/chexdecorations.txt zscript/chex/chexplayer.txt - -zscript/test2.txt From 5b952b116aa9d1563b432a5f2cf2f6d048792264 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 14:26:33 +0200 Subject: [PATCH 099/255] - named class functions are working. Yay!! - converted A_BspiAttack and A_BabyMetal to script functions to test the implementation. --- src/CMakeLists.txt | 1 - src/g_doom/a_arachnotron.cpp | 30 ---------------------- src/g_doom/a_doommisc.cpp | 1 - src/scripting/vm/vmbuilder.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 9 +++++++ wadsrc/static/zscript/doom/arachnotron.txt | 23 +++++++++++++++++ 6 files changed, 33 insertions(+), 33 deletions(-) delete mode 100644 src/g_doom/a_arachnotron.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ddd027c80..2720f026d 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -835,7 +835,6 @@ set( NOT_COMPILED_SOURCE_FILES ${OTHER_SYSTEM_SOURCES} sc_man_scanner.h sc_man_scanner.re - g_doom/a_arachnotron.cpp g_doom/a_archvile.cpp g_doom/a_bossbrain.cpp g_doom/a_bruiser.cpp diff --git a/src/g_doom/a_arachnotron.cpp b/src/g_doom/a_arachnotron.cpp deleted file mode 100644 index 22223d24b..000000000 --- a/src/g_doom/a_arachnotron.cpp +++ /dev/null @@ -1,30 +0,0 @@ -/* -#include "actor.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "a_action.h" -#include "vm.h" -*/ - -DEFINE_ACTION_FUNCTION(AActor, A_BspiAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - A_FaceTarget (self); - - // launch a missile - P_SpawnMissile (self, self->target, PClass::FindActor("ArachnotronPlasma")); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_BabyMetal) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_BODY, "baby/walk", 1, ATTN_IDLE); - A_Chase (stack, self); - return 0; -} diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index a4eca67b7..81e5a253a 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -22,7 +22,6 @@ #include "vm.h" // Include all the other Doom stuff here to reduce compile time -#include "a_arachnotron.cpp" #include "a_archvile.cpp" #include "a_bossbrain.cpp" #include "a_bruiser.cpp" diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index b58de0ea4..1b7c4ce70 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -693,7 +693,7 @@ void FFunctionBuildList::Build() FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate); // Allocate registers for the function's arguments and create local variable nodes before starting to resolve it. - VMFunctionBuilder buildit(true); + VMFunctionBuilder buildit(!!(item.Func->Variants[0].Flags & VARF_Action)); for(unsigned i=0;iVariants[0].Proto->ArgumentTypes.Size();i++) { auto type = item.Func->Variants[0].Proto->ArgumentTypes[i]; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 8389975ef..723e82c8d 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2042,6 +2042,15 @@ void ZCCCompiler::InitFunctions() sym->AddVariant(NewPrototype(rets, args), argflags, argnames, afd == nullptr? nullptr : *(afd->VMPointer), varflags); c->Type()->Symbols.ReplaceSymbol(sym); + if (!(f->Flags & ZCC_Native)) + { + auto code = ConvertAST(f->Body); + if (code != nullptr) + { + sym->Variants[0].Implementation = FunctionBuildList.AddFunction(sym, code, FStringf("%s.%s", c->Type()->TypeName.GetChars(), FName(f->Name).GetChars()), false); + } + } + // todo: Check inheritance. // todo: Process function bodies. } diff --git a/wadsrc/static/zscript/doom/arachnotron.txt b/wadsrc/static/zscript/doom/arachnotron.txt index e3aa17d48..0e093323b 100644 --- a/wadsrc/static/zscript/doom/arachnotron.txt +++ b/wadsrc/static/zscript/doom/arachnotron.txt @@ -88,4 +88,27 @@ class ArachnotronPlasma : Actor } } +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_BspiAttack() + { + if (target) + { + A_FaceTarget(); + P_SpawnMissile(target, "ArachnotronPlasma"); + } + } + + void A_BabyMetal() + { + A_PlaySound("baby/walk", CHAN_BODY, 1, false, ATTN_IDLE); + A_Chase(); + } +} From da56e5908d9f2e2ac3c94ecc56d07f2daad91dd8 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 15:30:58 +0200 Subject: [PATCH 100/255] - added an optimization to FxBoolCast that it doesn't force the source value to a 0/1 integer if not explicitly needed. When doing comparisons we do not care about actual values, we only want to know if it is 0 or not. - added the above for the 'if' condition. It works for integers, floats and pointers and will save 3 instructions if the condition is a non-boolean that can be implicitly casted to bool. --- src/scripting/codegeneration/codegen.cpp | 72 ++++++++++++++++-------- src/scripting/codegeneration/codegen.h | 3 +- 2 files changed, 49 insertions(+), 26 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9568c34a5..f882b8b2b 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -434,11 +434,12 @@ ExpEmit FxConstant::Emit(VMFunctionBuilder *build) // //========================================================================== -FxBoolCast::FxBoolCast(FxExpression *x) +FxBoolCast::FxBoolCast(FxExpression *x, bool needvalue) : FxExpression(EFX_BoolCast, x->ScriptPosition) { basex = x; ValueType = TypeBool; + NeedValue = needvalue; } //========================================================================== @@ -499,31 +500,37 @@ ExpEmit FxBoolCast::Emit(VMFunctionBuilder *build) ExpEmit from = basex->Emit(build); assert(!from.Konst); assert(basex->ValueType->GetRegType() == REGT_INT || basex->ValueType->GetRegType() == REGT_FLOAT || basex->ValueType->GetRegType() == REGT_POINTER); - ExpEmit to(build, REGT_INT); - from.Free(build); - // Preload result with 0. - build->Emit(OP_LI, to.RegNum, 0); - - // Check source against 0. - if (from.RegType == REGT_INT) + if (NeedValue) { - build->Emit(OP_EQ_R, 1, from.RegNum, to.RegNum); - } - else if (from.RegType == REGT_FLOAT) - { - build->Emit(OP_EQF_K, 1, from.RegNum, build->GetConstantFloat(0.)); - } - else if (from.RegType == REGT_POINTER) - { - build->Emit(OP_EQA_K, 1, from.RegNum, build->GetConstantAddress(nullptr, ATAG_GENERIC)); - } - build->Emit(OP_JMP, 1); + ExpEmit to(build, REGT_INT); + from.Free(build); + // Preload result with 0. + build->Emit(OP_LI, to.RegNum, 0); - // Reload result with 1 if the comparison fell through. - build->Emit(OP_LI, to.RegNum, 1); + // Check source against 0. + if (from.RegType == REGT_INT) + { + build->Emit(OP_EQ_R, 1, from.RegNum, to.RegNum); + } + else if (from.RegType == REGT_FLOAT) + { + build->Emit(OP_EQF_K, 1, from.RegNum, build->GetConstantFloat(0.)); + } + else if (from.RegType == REGT_POINTER) + { + build->Emit(OP_EQA_K, 1, from.RegNum, build->GetConstantAddress(nullptr, ATAG_GENERIC)); + } + build->Emit(OP_JMP, 1); - return to; + // Reload result with 1 if the comparison fell through. + build->Emit(OP_LI, to.RegNum, 1); + return to; + } + else + { + return from; + } } //========================================================================== @@ -5871,7 +5878,7 @@ FxExpression *FxIfStatement::Resolve(FCompileContext &ctx) if (Condition->ValueType != TypeBool) { - Condition = new FxBoolCast(Condition); + Condition = new FxBoolCast(Condition, false); SAFE_RESOLVE(Condition, ctx); } @@ -5914,7 +5921,7 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) // This is pretty much copied from FxConditional, except we don't // keep any results. ExpEmit cond = Condition->Emit(build); - assert(cond.RegType == REGT_INT && !cond.Konst); + assert(cond.RegType != REGT_STRING && !cond.Konst); if (WhenTrue != NULL) { @@ -5933,7 +5940,22 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) } // Test condition. - build->Emit(OP_EQ_K, condcheck, cond.RegNum, build->GetConstantInt(0)); + + switch (cond.RegType) + { + default: + case REGT_INT: + build->Emit(OP_EQ_K, condcheck, cond.RegNum, build->GetConstantInt(0)); + break; + + case REGT_FLOAT: + build->Emit(OP_EQF_K, condcheck, cond.RegNum, build->GetConstantFloat(0)); + break; + + case REGT_POINTER: + build->Emit(OP_EQA_K, condcheck, cond.RegNum, build->GetConstantAddress(nullptr, ATAG_GENERIC)); + break; + } jumpspot = build->Emit(OP_JMP, 0); cond.Free(build); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 3ea97ba66..9125d5d8c 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -457,10 +457,11 @@ public: class FxBoolCast : public FxExpression { FxExpression *basex; + bool NeedValue; public: - FxBoolCast(FxExpression *x); + FxBoolCast(FxExpression *x, bool needvalue = true); ~FxBoolCast(); FxExpression *Resolve(FCompileContext&); From 9f8a5dae214b03e73aa51c80c59760c202c293be Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 23 Oct 2016 17:15:24 +0200 Subject: [PATCH 101/255] - scriptified A_BruisAttack. - removed 'self' as a dedicated token. Internally this gets handled as a normal but implicitly named variable so the token just gets in the way of proper processing. - removed P_ prefix from SpawnMissile export. - fixed a crash with misnamed function exports. --- src/g_doom/a_bruiser.cpp | 23 ------------------ src/g_doom/a_doommisc.cpp | 1 - src/p_enemy.cpp | 6 +++++ src/p_interaction.cpp | 12 ++++++++++ src/p_map.cpp | 10 ++++++++ src/p_mobj.cpp | 2 +- src/sc_man_scanner.re | 1 - src/sc_man_tokens.h | 1 - src/scripting/zscript/zcc-parse.lemon | 15 +----------- src/scripting/zscript/zcc_compile.cpp | 5 +++- src/scripting/zscript/zcc_exprlist.h | 1 - src/scripting/zscript/zcc_parser.cpp | 1 - src/scripting/zscript/zcc_parser.h | 1 - wadsrc/static/zscript/actor.txt | 8 +++---- wadsrc/static/zscript/doom/arachnotron.txt | 2 +- wadsrc/static/zscript/doom/bruiser.txt | 27 ++++++++++++++++++++++ 16 files changed, 66 insertions(+), 50 deletions(-) delete mode 100644 src/g_doom/a_bruiser.cpp diff --git a/src/g_doom/a_bruiser.cpp b/src/g_doom/a_bruiser.cpp deleted file mode 100644 index 1d2be64f0..000000000 --- a/src/g_doom/a_bruiser.cpp +++ /dev/null @@ -1,23 +0,0 @@ -static FRandom pr_bruisattack ("BruisAttack"); - - -DEFINE_ACTION_FUNCTION(AActor, A_BruisAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - if (self->CheckMeleeRange ()) - { - int damage = (pr_bruisattack()%8+1)*10; - S_Sound (self, CHAN_WEAPON, "baron/melee", 1, ATTN_NORM); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - return 0; - } - - // launch a missile - P_SpawnMissile (self, self->target, PClass::FindActor("BaronBall")); - return 0; -} diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 81e5a253a..2115e70e1 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -24,7 +24,6 @@ // Include all the other Doom stuff here to reduce compile time #include "a_archvile.cpp" #include "a_bossbrain.cpp" -#include "a_bruiser.cpp" #include "a_cacodemon.cpp" #include "a_cyberdemon.cpp" #include "a_demon.cpp" diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 14ea2b7c1..0c2cb8e28 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -310,6 +310,12 @@ bool AActor::CheckMeleeRange () return true; } +DEFINE_ACTION_FUNCTION(AActor, CheckMeleeRange) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_INT(self->CheckMeleeRange()); +} + //---------------------------------------------------------------------------- // // FUNC P_CheckMeleeRange2 diff --git a/src/p_interaction.cpp b/src/p_interaction.cpp index 261cfb8f3..f3d02428d 100644 --- a/src/p_interaction.cpp +++ b/src/p_interaction.cpp @@ -1555,6 +1555,18 @@ dopain: return damage; } +DEFINE_ACTION_FUNCTION(AActor, DamageMobj) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(inflictor, AActor); + PARAM_OBJECT(source, AActor); + PARAM_INT(damage); + PARAM_NAME(mod); + PARAM_INT_OPT(flags) { flags = 0; } + PARAM_FLOAT_OPT(angle) { angle = 0; } + ACTION_RETURN_INT(P_DamageMobj(self, inflictor, source, damage, mod, flags, angle)); +} + void P_PoisonMobj (AActor *target, AActor *inflictor, AActor *source, int damage, int duration, int period, FName type) { // Check for invulnerability. diff --git a/src/p_map.cpp b/src/p_map.cpp index 5cc9bdf72..849f8dd24 100644 --- a/src/p_map.cpp +++ b/src/p_map.cpp @@ -4574,6 +4574,16 @@ void P_TraceBleed(int damage, AActor *target, AActor *missile) P_TraceBleed(damage, target->PosPlusZ(target->Height/2), target, missile->AngleTo(target), pitch); } +DEFINE_ACTION_FUNCTION(AActor, TraceBleed) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_INT(damage); + PARAM_OBJECT(missile, AActor); + + P_TraceBleed(damage, self, missile); + return 0; +} + //========================================================================== // // diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index d89a89576..8e630b77a 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -5824,7 +5824,7 @@ AActor *P_SpawnMissile (AActor *source, AActor *dest, PClassActor *type, AActor return P_SpawnMissileXYZ (source->PosPlusZ(32 + source->GetBobOffset()), source, dest, type, true, owner); } -DEFINE_ACTION_FUNCTION(AActor, P_SpawnMissile) +DEFINE_ACTION_FUNCTION(AActor, SpawnMissile) { PARAM_SELF_PROLOGUE(AActor); PARAM_OBJECT(dest, AActor); diff --git a/src/sc_man_scanner.re b/src/sc_man_scanner.re index cc9968ae3..8fbb28ef5 100644 --- a/src/sc_man_scanner.re +++ b/src/sc_man_scanner.re @@ -169,7 +169,6 @@ std2: 'virtual' { RET(TK_Virtual); } 'super' { RET(TK_Super); } 'global' { RET(TK_Global); } - 'self' { RET(TK_Self); } 'stop' { RET(TK_Stop); } 'null' { RET(TK_Null); } diff --git a/src/sc_man_tokens.h b/src/sc_man_tokens.h index 19d331301..7d9f81e9b 100644 --- a/src/sc_man_tokens.h +++ b/src/sc_man_tokens.h @@ -108,7 +108,6 @@ xx(TK_Virtual, "'virtual'") xx(TK_Super, "'super'") xx(TK_Null, "'null'") xx(TK_Global, "'global'") -xx(TK_Self, "'self'") xx(TK_Stop, "'stop'") xx(TK_Include, "'include'") diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index fc34fd2d7..0cf061bef 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -977,13 +977,6 @@ primary(X) ::= IDENTIFIER(A). expr->Type = NULL; X = expr; } -primary(X) ::= NULL(T). -{ - NEW_AST_NODE(Expression, expr, T); - expr->Operation = PEX_Null; - expr->Type = NULL; - X = expr; -} primary(X) ::= SUPER(T). { NEW_AST_NODE(Expression, expr, T); @@ -992,13 +985,7 @@ primary(X) ::= SUPER(T). X = expr; } primary(X) ::= constant(A). { X = A; /*X-overwrites-A*/ } -primary(X) ::= SELF(T). -{ - NEW_AST_NODE(Expression, expr, T); - expr->Operation = PEX_Self; - expr->Type = NULL; - X = expr; -} + primary(X) ::= LPAREN expr(A) RPAREN. { X = A; /*X-overwrites-A*/ diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 723e82c8d..274778dfe 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2001,7 +2001,10 @@ void ZCCCompiler::InitFunctions() { Error(f, "The function '%s' has not been exported from the executable.", FName(f->Name).GetChars()); } - (*afd->VMPointer)->ImplicitArgs = BYTE(implicitargs); + else + { + (*afd->VMPointer)->ImplicitArgs = BYTE(implicitargs); + } } SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags); auto p = f->Params; diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index 4770a08a4..bbf99189c 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -4,7 +4,6 @@ xx(Nil, TK_None) xx(ID, TK_Identifier) xx(Super, TK_Super) xx(Null, TK_Null) -xx(Self, TK_Self) xx(ConstValue, TK_Const) xx(FuncCall, '(') xx(ArrayAccess, TK_Array) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index bc7857630..18d683c4c 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -155,7 +155,6 @@ static void InitTokenMap() TOKENDEF (TK_Optional, ZCC_OPTIONAL); TOKENDEF (TK_Super, ZCC_SUPER); TOKENDEF (TK_Null, ZCC_NULLPTR); - TOKENDEF (TK_Self, ZCC_SELF); TOKENDEF ('~', ZCC_TILDE); TOKENDEF ('!', ZCC_BANG); TOKENDEF (TK_SizeOf, ZCC_SIZEOF); diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index ca8c3f3cb..7ba48d711 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -44,7 +44,6 @@ enum }; - // Syntax tree structures. enum EZCCTreeNodeType { diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 502b8d0cf..caea22aae 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -47,7 +47,10 @@ class Actor : Thinker native } // Functions - native Actor P_SpawnMissile(Actor dest, class type, Actor owner = null); + native Actor SpawnMissile(Actor dest, class type, Actor owner = null); + native void TraceBleed(int damage, Actor missile); + native bool CheckMeleeRange(); + native int DamageMobj(Actor inflictor, Actor source, int damage, Name mod, int flags = 0, double angle = 0); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); @@ -110,13 +113,10 @@ class Actor : Thinker native native void A_TroopAttack(); native void A_SargAttack(); native void A_HeadAttack(); - native void A_BruisAttack(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); native void A_Metal(); native void A_SpidRefire(); - //native void A_BabyMetal(); - //native void A_BspiAttack(); native void A_Hoof(); native void A_CyberAttack(); native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); diff --git a/wadsrc/static/zscript/doom/arachnotron.txt b/wadsrc/static/zscript/doom/arachnotron.txt index 0e093323b..c7e11ab14 100644 --- a/wadsrc/static/zscript/doom/arachnotron.txt +++ b/wadsrc/static/zscript/doom/arachnotron.txt @@ -101,7 +101,7 @@ extend class Actor if (target) { A_FaceTarget(); - P_SpawnMissile(target, "ArachnotronPlasma"); + SpawnMissile(target, "ArachnotronPlasma"); } } diff --git a/wadsrc/static/zscript/doom/bruiser.txt b/wadsrc/static/zscript/doom/bruiser.txt index bbeb319f6..c1faa23c1 100644 --- a/wadsrc/static/zscript/doom/bruiser.txt +++ b/wadsrc/static/zscript/doom/bruiser.txt @@ -138,3 +138,30 @@ class BaronBall : Actor } } +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_BruisAttack() + { + if (target) + { + if (CheckMeleeRange()) + { + int damage = random[pr_bruisattack](1, 8) * 10; + A_PlaySound ("baron/melee", CHAN_WEAPON); + int newdam = target.DamageMobj (self, self, damage, "Melee"); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + } + else + { + // launch a missile + SpawnMissile (target, "BaronBall"); + } + } + } +} From 3f1673f34ffdfb468c5680ca0328b1f05041ccf7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 24 Oct 2016 00:50:28 +0200 Subject: [PATCH 102/255] - scriptified A_HeadAttack, A_CyberAttack and A_Hoof. --- src/g_doom/a_cacodemon.cpp | 35 ----------------------- src/g_doom/a_cyberdemon.cpp | 29 ------------------- src/g_doom/a_doommisc.cpp | 2 -- src/scripting/thingdef_data.cpp | 1 + wadsrc/static/zscript/actor.txt | 3 -- wadsrc/static/zscript/doom/cacodemon.txt | 29 +++++++++++++++++++ wadsrc/static/zscript/doom/cyberdemon.txt | 25 ++++++++++++++++ 7 files changed, 55 insertions(+), 69 deletions(-) delete mode 100644 src/g_doom/a_cacodemon.cpp delete mode 100644 src/g_doom/a_cyberdemon.cpp diff --git a/src/g_doom/a_cacodemon.cpp b/src/g_doom/a_cacodemon.cpp deleted file mode 100644 index 354443bd6..000000000 --- a/src/g_doom/a_cacodemon.cpp +++ /dev/null @@ -1,35 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "s_sound.h" -#include "vm.h" -*/ - -static FRandom pr_headattack ("HeadAttack"); - -DEFINE_ACTION_FUNCTION(AActor, A_HeadAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - A_FaceTarget (self); - if (self->CheckMeleeRange ()) - { - int damage = (pr_headattack()%6+1)*10; - S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - return 0; - } - - // launch a missile - P_SpawnMissile (self, self->target, PClass::FindActor("CacodemonBall")); - return 0; -} diff --git a/src/g_doom/a_cyberdemon.cpp b/src/g_doom/a_cyberdemon.cpp deleted file mode 100644 index 6e78759c3..000000000 --- a/src/g_doom/a_cyberdemon.cpp +++ /dev/null @@ -1,29 +0,0 @@ -/* -#include "actor.h" -#include "p_local.h" -#include "s_sound.h" -#include "p_enemy.h" -#include "a_action.h" -#include "vm.h" -*/ - -DEFINE_ACTION_FUNCTION(AActor, A_CyberAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - A_FaceTarget (self); - P_SpawnMissile (self, self->target, PClass::FindActor("Rocket")); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_Hoof) -{ - PARAM_SELF_PROLOGUE(AActor); - - S_Sound (self, CHAN_BODY, "cyber/hoof", 1, ATTN_IDLE); - A_Chase (stack, self); - return 0; -} diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 2115e70e1..fb5ae3b28 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -24,8 +24,6 @@ // Include all the other Doom stuff here to reduce compile time #include "a_archvile.cpp" #include "a_bossbrain.cpp" -#include "a_cacodemon.cpp" -#include "a_cyberdemon.cpp" #include "a_demon.cpp" #include "a_doomimp.cpp" #include "a_doomweaps.cpp" diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 7e0668a0f..e11e249ce 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -676,6 +676,7 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_VisibleStartPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartPitch))); symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); + symt.AddSymbol(new PField("AttackSound", TypeSound, VARF_Native, myoffsetof(AActor, AttackSound))); symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index caea22aae..b6d65a29e 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -112,13 +112,10 @@ class Actor : Thinker native native void A_CPosRefire(); native void A_TroopAttack(); native void A_SargAttack(); - native void A_HeadAttack(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); native void A_Metal(); native void A_SpidRefire(); - native void A_Hoof(); - native void A_CyberAttack(); native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); native void A_DualPainAttack(class spawntype = "LostSoul"); native void A_PainDie(class spawntype = "LostSoul"); diff --git a/wadsrc/static/zscript/doom/cacodemon.txt b/wadsrc/static/zscript/doom/cacodemon.txt index 6a07feb70..b21acacd2 100644 --- a/wadsrc/static/zscript/doom/cacodemon.txt +++ b/wadsrc/static/zscript/doom/cacodemon.txt @@ -86,3 +86,32 @@ class CacodemonBall : Actor Stop; } } + + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_HeadAttack() + { + if (target) + { + if (CheckMeleeRange()) + { + int damage = random[pr_headattack](1, 6) * 10; + A_PlaySound (AttackSound, CHAN_WEAPON); + int newdam = target.DamageMobj (self, self, damage, "Melee"); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + } + else + { + // launch a missile + SpawnMissile (target, "CacodemonBall"); + } + } + } +} diff --git a/wadsrc/static/zscript/doom/cyberdemon.txt b/wadsrc/static/zscript/doom/cyberdemon.txt index 75f4fd211..1a2890f9a 100644 --- a/wadsrc/static/zscript/doom/cyberdemon.txt +++ b/wadsrc/static/zscript/doom/cyberdemon.txt @@ -62,3 +62,28 @@ class Cyberdemon : Actor } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_CyberAttack() + { + if (target) + { + A_FaceTarget(); + SpawnMissile (target, "Rocket"); + } + } + + void A_Hoof() + { + A_PlaySound("cyber/hoof", CHAN_BODY, 1, false, ATTN_IDLE); + A_Chase(); + } + +} From 808188ff184cb935126cd2a0a37ad135ea2adacf Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 24 Oct 2016 13:18:13 +0200 Subject: [PATCH 103/255] - added handling for structs. When defined inside classes or other structs the double member access will be merged, so there is no performance hit by using structs to group data. --- src/scripting/codegeneration/codegen.cpp | 134 +++++++++++++++++++---- src/scripting/codegeneration/codegen.h | 22 +++- src/scripting/thingdef_data.cpp | 25 +++-- 3 files changed, 145 insertions(+), 36 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f882b8b2b..bcea7e9fa 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4226,14 +4226,15 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) PSymbolTable *symtbl; auto ptype = static_cast(Object->ValueType)->PointedType; - if (ptype->IsKindOf(RUNTIME_CLASS(PClass))) + if (ptype->IsKindOf(RUNTIME_CLASS(PStruct))) // PClass is a child class of PStruct so this covers both. { - PClass *cls = static_cast(ptype); + PStruct *cls = static_cast(ptype); + bool isclass = cls->IsKindOf(RUNTIME_CLASS(PClass)); if ((sym = cls->Symbols.FindSymbolInTable(Identifier, symtbl)) != nullptr) { if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) { - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as class constant\n", Identifier.GetChars()); + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as %s constant\n", Identifier.GetChars(), isclass? "class" : "struct"); newex = FxConstant::MakeConstant(sym, ScriptPosition); } else if (sym->IsKindOf(RUNTIME_CLASS(PField))) @@ -4263,7 +4264,7 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) delete this; return nullptr; } - auto x = new FxClassMember(Object, vsym, ScriptPosition); + auto x = isclass? new FxClassMember(Object, vsym, ScriptPosition) : new FxStructMember(Object, vsym, ScriptPosition); delete this; return x->Resolve(ctx); } @@ -4281,14 +4282,41 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) return nullptr; } } - else if (ptype->IsA(RUNTIME_CLASS(PStruct))) - { - // todo - } } else if (Object->ValueType->IsA(RUNTIME_CLASS(PStruct))) { - // todo + if ((sym = Object->ValueType->Symbols.FindSymbol(Identifier, false)) != nullptr) + { + if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) + { + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as struct constant\n", Identifier.GetChars()); + newex = FxConstant::MakeConstant(sym, ScriptPosition); + } + else if (sym->IsKindOf(RUNTIME_CLASS(PField))) + { + PField *vsym = static_cast(sym); + + if (vsym->Flags & VARF_Deprecated) + { + ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + } + auto x = new FxStructMember(Object, vsym, ScriptPosition); + delete this; + return x->Resolve(ctx); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); + delete this; + return nullptr; + } + } + else + { + ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); + delete this; + return nullptr; + } } ScriptPosition.Message(MSG_ERROR, "Left side of %s is not a struct or class", Identifier.GetChars()); @@ -4381,13 +4409,13 @@ ExpEmit FxSelf::Emit(VMFunctionBuilder *build) // //========================================================================== -FxClassMember::FxClassMember(FxExpression *x, PField* mem, const FScriptPosition &pos) -: FxExpression(EFX_ClassMember, pos) +FxStructMember::FxStructMember(FxExpression *x, PField* mem, const FScriptPosition &pos) + : FxExpression(EFX_StructMember, pos) { classx = x; membervar = mem; AddressRequested = false; - //if (classx->IsDefaultObject()) Readonly=true; + AddressWritable = true; // must be true unless classx tells us otherwise if requested. } //========================================================================== @@ -4396,7 +4424,7 @@ FxClassMember::FxClassMember(FxExpression *x, PField* mem, const FScriptPosition // //========================================================================== -FxClassMember::~FxClassMember() +FxStructMember::~FxStructMember() { SAFE_DELETE(classx); } @@ -4407,10 +4435,10 @@ FxClassMember::~FxClassMember() // //========================================================================== -bool FxClassMember::RequestAddress(bool *writable) +bool FxStructMember::RequestAddress(bool *writable) { AddressRequested = true; - if (writable != nullptr) *writable = !(membervar->Flags & VARF_ReadOnly); + if (writable != nullptr) *writable = AddressWritable && !(membervar->Flags & VARF_ReadOnly); return true; } @@ -4420,23 +4448,50 @@ bool FxClassMember::RequestAddress(bool *writable) // //========================================================================== -FxExpression *FxClassMember::Resolve(FCompileContext &ctx) +FxExpression *FxStructMember::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); SAFE_RESOLVE(classx, ctx); - PPointer *ptrtype = dyn_cast(classx->ValueType); - if (ptrtype == NULL || !ptrtype->IsKindOf(RUNTIME_CLASS(DObject))) + if (classx->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) { - ScriptPosition.Message(MSG_ERROR, "Member variable requires a class or object"); - delete this; - return NULL; + PPointer *ptrtype = dyn_cast(classx->ValueType); + if (ptrtype == nullptr || !ptrtype->PointedType->IsA(RUNTIME_CLASS(PStruct))) + { + ScriptPosition.Message(MSG_ERROR, "Member variable requires a struct"); + delete this; + return nullptr; + } + } + else if (classx->ValueType->IsA(RUNTIME_CLASS(PStruct))) + { + // if this is a struct within a class or another struct we can simplify the expression by creating a new PField with a cumulative offset. + if (classx->ExprType == EFX_ClassMember || classx->ExprType == EFX_StructMember) + { + auto parentfield = static_cast(classx)->membervar; + // PFields are garbage collected so this will be automatically taken care of later. + auto newfield = new PField(membervar->SymbolName, membervar->Type, membervar->Flags | parentfield->Flags, membervar->Offset + parentfield->Offset); + static_cast(classx)->membervar = newfield; + classx->isresolved = false; // re-resolve the parent so it can also check if it can be optimized away. + auto x = classx->Resolve(ctx); + classx = nullptr; + return x; + } + else + { + if (!(classx->RequestAddress(&AddressWritable))) + { + ScriptPosition.Message(MSG_ERROR, "unable to dereference left side of %s", membervar->SymbolName.GetChars()); + delete this; + return nullptr; + } + } } ValueType = membervar->Type; return this; } -ExpEmit FxClassMember::Emit(VMFunctionBuilder *build) +ExpEmit FxStructMember::Emit(VMFunctionBuilder *build) { ExpEmit obj = classx->Emit(build); assert(obj.RegType == REGT_POINTER); @@ -4473,6 +4528,41 @@ ExpEmit FxClassMember::Emit(VMFunctionBuilder *build) } +//========================================================================== +// +// +// +//========================================================================== + +FxClassMember::FxClassMember(FxExpression *x, PField* mem, const FScriptPosition &pos) +: FxStructMember(x, mem, pos) +{ + ExprType = EFX_ClassMember; + //if (classx->IsDefaultObject()) Readonly=true; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxClassMember::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(classx, ctx); + + PPointer *ptrtype = dyn_cast(classx->ValueType); + if (ptrtype == NULL || !ptrtype->PointedType->IsKindOf(RUNTIME_CLASS(PClass))) + { + ScriptPosition.Message(MSG_ERROR, "Member variable requires a class or object"); + delete this; + return NULL; + } + ValueType = membervar->Type; + return this; +} + //========================================================================== // // diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 9125d5d8c..771faa2c8 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -237,6 +237,7 @@ enum EFxType EFX_FRandom, EFX_Random2, EFX_ClassMember, + EFX_StructMember, EFX_LocalVariable, EFX_Self, EFX_ArrayElement, @@ -1037,20 +1038,35 @@ public: // //========================================================================== -class FxClassMember : public FxExpression +class FxStructMember : public FxExpression { public: FxExpression *classx; PField *membervar; bool AddressRequested; + bool AddressWritable; - FxClassMember(FxExpression*, PField*, const FScriptPosition&); - ~FxClassMember(); + FxStructMember(FxExpression*, PField*, const FScriptPosition&); + ~FxStructMember(); FxExpression *Resolve(FCompileContext&); bool RequestAddress(bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxClassMember +// +//========================================================================== + +class FxClassMember : public FxStructMember +{ +public: + + FxClassMember(FxExpression*, PField*, const FScriptPosition&); + FxExpression *Resolve(FCompileContext&); +}; + //========================================================================== // // FxLocalVariable diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index e11e249ce..03e88b149 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -650,17 +650,17 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_TID, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, tid))); symt.AddSymbol(new PField(NAME_TIDtoHate, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, TIDtoHate))); symt.AddSymbol(new PField(NAME_WaterLevel, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, waterlevel))); - symt.AddSymbol(new PField(NAME_X, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos.X))); // must remain read-only! - symt.AddSymbol(new PField(NAME_Y, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos.Y))); // must remain read-only! - symt.AddSymbol(new PField(NAME_Z, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos.Z))); // must remain read-only! - symt.AddSymbol(new PField(NAME_VelX, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Vel.X))); - symt.AddSymbol(new PField(NAME_VelY, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Vel.Y))); - symt.AddSymbol(new PField(NAME_VelZ, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Vel.Z))); - symt.AddSymbol(new PField(NAME_MomX, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Vel.X))); - symt.AddSymbol(new PField(NAME_MomY, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Vel.Y))); - symt.AddSymbol(new PField(NAME_MomZ, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Vel.Z))); - symt.AddSymbol(new PField(NAME_ScaleX, TypeFloat64, VARF_Native, myoffsetof(AActor, Scale.X))); - symt.AddSymbol(new PField(NAME_ScaleY, TypeFloat64, VARF_Native, myoffsetof(AActor, Scale.Y))); + symt.AddSymbol(new PField(NAME_X, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, __Pos.X))); // must remain read-only! + symt.AddSymbol(new PField(NAME_Y, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, __Pos.Y))); // must remain read-only! + symt.AddSymbol(new PField(NAME_Z, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, __Pos.Z))); // must remain read-only! + symt.AddSymbol(new PField(NAME_VelX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.X))); + symt.AddSymbol(new PField(NAME_VelY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Y))); + symt.AddSymbol(new PField(NAME_VelZ, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Z))); + symt.AddSymbol(new PField(NAME_MomX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.X))); + symt.AddSymbol(new PField(NAME_MomY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Y))); + symt.AddSymbol(new PField(NAME_MomZ, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Z))); + symt.AddSymbol(new PField(NAME_ScaleX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Scale.X))); + symt.AddSymbol(new PField(NAME_ScaleY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Scale.Y))); symt.AddSymbol(new PField(NAME_Score, TypeSInt32, VARF_Native, myoffsetof(AActor, Score))); symt.AddSymbol(new PField(NAME_Accuracy, TypeSInt32, VARF_Native, myoffsetof(AActor, accuracy))); symt.AddSymbol(new PField(NAME_Stamina, TypeSInt32, VARF_Native, myoffsetof(AActor, stamina))); @@ -677,6 +677,9 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); symt.AddSymbol(new PField("AttackSound", TypeSound, VARF_Native, myoffsetof(AActor, AttackSound))); + symt.AddSymbol(new PField("Pos", TypeVector3, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos))); + symt.AddSymbol(new PField("Vel", TypeVector3, VARF_Native, myoffsetof(AActor, Vel))); + symt.AddSymbol(new PField("Scale", TypeVector2, VARF_Native, myoffsetof(AActor, Scale))); symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); From f810b981672a082ef3543fd2df0b0d70bde484f3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 24 Oct 2016 17:18:20 +0200 Subject: [PATCH 104/255] - implement flag variables with the VM's sbit and lbit instructions. - synthesize PField entries from the flag list for AActor. This intentionally excludes the bounce flags for now. - allow deprecated flags that do not call the deprecated flag handler. - disallow constructs like (a = b) = c by not allowing an address request on an assignment operation. - restrict modify/assign on boolean variables to the bit operators. Everything else needs to promote the result to an integer to make sense so it should be disallowed. --- src/dobjtype.cpp | 25 +++++ src/dobjtype.h | 5 +- src/scripting/codegeneration/codegen.cpp | 135 ++++++++++++++++------- src/scripting/codegeneration/codegen.h | 9 +- src/scripting/decorate/thingdef_exp.cpp | 2 +- src/scripting/thingdef.h | 1 + src/scripting/thingdef_data.cpp | 46 +++++--- src/scripting/zscript/zcc_compile.cpp | 7 +- 8 files changed, 166 insertions(+), 64 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 9191c60c0..3bce521c8 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2479,6 +2479,31 @@ PField::PField() { } +PField::PField(FName name, PType *type, DWORD flags, size_t offset, int bitvalue) + : PSymbol(name), Offset(unsigned(offset)), Type(type), Flags(flags) +{ + BitValue = bitvalue; + if (bitvalue > -1) + { + if (type->IsA(RUNTIME_CLASS(PInt)) && unsigned(bitvalue) < 8 * type->Size) + { + // map to the single bytes in the actual variable. The internal bit instructions operate on 8 bit values. +#ifndef __BIG_ENDIAN__ + Offset += BitValue / 8; +#else + Offset += type->Size - 1 - BitValue / 8; +#endif + BitValue &= 7; + Type = TypeBool; + } + else + { + // Just abort. Bit fields should only be defined internally. + I_FatalError("Trying to create an invalid bit field element: %s", name.GetChars()); + } + } +} + /* PPrototype *************************************************************/ IMPLEMENT_CLASS(PPrototype) diff --git a/src/dobjtype.h b/src/dobjtype.h index f3e043bd9..0c26f3a35 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -572,13 +572,12 @@ class PField : public PSymbol DECLARE_CLASS(PField, PSymbol); HAS_OBJECT_POINTERS public: - PField(FName name, PType *type) : PSymbol(name), Offset(0), Type(type), Flags(0) {} - PField(FName name, PType *type, DWORD flags) : PSymbol(name), Offset(0), Type(type), Flags(flags) {} - PField(FName name, PType *type, DWORD flags, size_t offset) : PSymbol(name), Offset(unsigned(offset)), Type(type), Flags(flags) {} + PField(FName name, PType *type, DWORD flags = 0, size_t offset = 0, int bitvalue = -1); unsigned int Offset; PType *Type; DWORD Flags; + int BitValue; protected: PField(); }; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index bcea7e9fa..c8a682189 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1768,8 +1768,8 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) // //========================================================================== -FxAssign::FxAssign(FxExpression *base, FxExpression *right) -: FxExpression(EFX_Assign, base->ScriptPosition), Base(base), Right(right) +FxAssign::FxAssign(FxExpression *base, FxExpression *right, bool ismodify) +: FxExpression(EFX_Assign, base->ScriptPosition), Base(base), Right(right), IsModifyAssign(ismodify), IsBitWrite(-1) { AddressRequested = false; AddressWritable = false; @@ -1781,12 +1781,14 @@ FxAssign::~FxAssign() SAFE_DELETE(Right); } +/* I don't think we should allow constructs like (a = b) = c;... bool FxAssign::RequestAddress(bool *writable) { AddressRequested = true; if (writable != nullptr) *writable = AddressWritable; return true; } +*/ FxExpression *FxAssign::Resolve(FCompileContext &ctx) { @@ -1797,6 +1799,15 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) SAFE_RESOLVE(Right, ctx); + if (IsModifyAssign && Base->ValueType == TypeBool && Right->ValueType != TypeBool) + { + // If the modify operation resulted in a type promotion from bool to int, this must be blocked. + // (this means, for bool, only &=, ^= and |= are allowed, although DECORATE is more lax.) + ScriptPosition.Message(MSG_ERROR, "Invalid modify/assign operation with a boolean operand"); + delete this; + return nullptr; + } + if (Base->IsNumeric() && Right->IsNumeric()) { if (Right->ValueType != ValueType) @@ -1865,6 +1876,16 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) return nullptr; } + // Special case: Assignment to a bitfield. + if (Base->ExprType == EFX_StructMember || Base->ExprType == EFX_ClassMember) + { + auto f = static_cast(Base)->membervar; + if (f->BitValue != -1 && !(f->Flags & VARF_ReadOnly)) + { + IsBitWrite = f->BitValue; + return this; + } + } return this; } @@ -1902,7 +1923,15 @@ ExpEmit FxAssign::Emit(VMFunctionBuilder *build) result = temp; } - build->Emit(ValueType->GetStoreOp(), pointer.RegNum, result.RegNum, build->GetConstantInt(0)); + if (IsBitWrite == -1) + { + build->Emit(ValueType->GetStoreOp(), pointer.RegNum, result.RegNum, build->GetConstantInt(0)); + } + else + { + build->Emit(OP_SBIT, pointer.RegNum, result.RegNum, 1 << IsBitWrite); + } + } if (AddressRequested) @@ -1941,12 +1970,19 @@ FxExpression *FxAssignSelf::Resolve(FCompileContext &ctx) ExpEmit FxAssignSelf::Emit(VMFunctionBuilder *build) { - assert(ValueType = Assignment->ValueType); + assert(ValueType == Assignment->ValueType); ExpEmit pointer = Assignment->Address; // FxAssign should have already emitted it if (!pointer.Target) { ExpEmit out(build, ValueType->GetRegType()); - build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, build->GetConstantInt(0)); + if (Assignment->IsBitWrite != -1) + { + build->Emit(OP_LBIT, out.RegNum, pointer.RegNum, 1 << Assignment->IsBitWrite); + } + else + { + build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, build->GetConstantInt(0)); + } return out; } else @@ -1999,11 +2035,29 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) if (left->ValueType == TypeBool && right->ValueType == TypeBool) { - ValueType = TypeBool; + if (Operator == '&' || Operator == '|' || Operator == '^' || ctx.FromDecorate) + { + ValueType = TypeBool; + } + else + { + ValueType = TypeSInt32; // math operations on bools result in integers. + } } else if (left->ValueType == TypeName && right->ValueType == TypeName) { - ValueType = TypeName; + // pointers can only be compared for equality. + if (Operator == TK_Eq || Operator == TK_Neq) + { + ValueType = TypeBool; + return true; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid operation for names"); + delete this; + return false; + } } else if (left->IsNumeric() && right->IsNumeric()) { @@ -2022,13 +2076,25 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) AreCompatiblePointerTypes(left->ValueType, right->ValueType)) { // pointers can only be compared for equality. - assert(Operator == TK_Eq || Operator == TK_Neq); - ValueType = TypeBool; + if (Operator == TK_Eq || Operator == TK_Neq) + { + ValueType = TypeBool; + return true; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid operation for pointers"); + delete this; + return false; + } } } else { - ValueType = TypeVoid; + // To check: It may be that this could pass in DECORATE, although setting TypeVoid here would pretty much prevent that. + ScriptPosition.Message(MSG_ERROR, "Incompatible operator"); + delete this; + return false; } assert(ValueType > nullptr && ValueType < (PType*)0xfffffffffffffff); @@ -2077,7 +2143,7 @@ FxExpression *FxAddSub::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } else if (left->isConstant() && right->isConstant()) { @@ -2771,7 +2837,7 @@ FxLtGtEq::FxLtGtEq(FxExpression *l, FxExpression *r) FxExpression *FxLtGtEq::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, false)) return NULL; + if (!ResolveLR(ctx, true)) return NULL; if (!left->IsNumeric() || !right->IsNumeric()) { @@ -4456,21 +4522,21 @@ FxExpression *FxStructMember::Resolve(FCompileContext &ctx) if (classx->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) { PPointer *ptrtype = dyn_cast(classx->ValueType); - if (ptrtype == nullptr || !ptrtype->PointedType->IsA(RUNTIME_CLASS(PStruct))) + if (ptrtype == nullptr || !ptrtype->PointedType->IsKindOf(RUNTIME_CLASS(PStruct))) { - ScriptPosition.Message(MSG_ERROR, "Member variable requires a struct"); + ScriptPosition.Message(MSG_ERROR, "Member variable requires a struct or class object."); delete this; return nullptr; } } - else if (classx->ValueType->IsA(RUNTIME_CLASS(PStruct))) + else if (classx->ValueType->IsA(RUNTIME_CLASS(PStruct))) // Classes can never be used as value types so we do not have to consider that case. { // if this is a struct within a class or another struct we can simplify the expression by creating a new PField with a cumulative offset. if (classx->ExprType == EFX_ClassMember || classx->ExprType == EFX_StructMember) { auto parentfield = static_cast(classx)->membervar; // PFields are garbage collected so this will be automatically taken care of later. - auto newfield = new PField(membervar->SymbolName, membervar->Type, membervar->Flags | parentfield->Flags, membervar->Offset + parentfield->Offset); + auto newfield = new PField(membervar->SymbolName, membervar->Type, membervar->Flags | parentfield->Flags, membervar->Offset + parentfield->Offset, membervar->BitValue); static_cast(classx)->membervar = newfield; classx->isresolved = false; // re-resolve the parent so it can also check if it can be optimized away. auto x = classx->Resolve(ctx); @@ -4522,7 +4588,17 @@ ExpEmit FxStructMember::Emit(VMFunctionBuilder *build) int offsetreg = build->GetConstantInt((int)membervar->Offset); ExpEmit loc(build, membervar->Type->GetRegType()); - build->Emit(membervar->Type->GetLoadOp(), loc.RegNum, obj.RegNum, offsetreg); + if (membervar->BitValue == -1) + { + build->Emit(membervar->Type->GetLoadOp(), loc.RegNum, obj.RegNum, offsetreg); + } + else + { + ExpEmit out(build, REGT_POINTER); + build->Emit(OP_ADDA_RK, out.RegNum, obj.RegNum, offsetreg); + build->Emit(OP_LBIT, loc.RegNum, out.RegNum, 1 << membervar->BitValue); + out.Free(build); + } obj.Free(build); return loc; } @@ -4530,7 +4606,8 @@ ExpEmit FxStructMember::Emit(VMFunctionBuilder *build) //========================================================================== // -// +// not really needed at the moment but may become useful with meta properties +// and some other class-specific extensions. // //========================================================================== @@ -4547,28 +4624,6 @@ FxClassMember::FxClassMember(FxExpression *x, PField* mem, const FScriptPosition // //========================================================================== -FxExpression *FxClassMember::Resolve(FCompileContext &ctx) -{ - CHECKRESOLVED(); - SAFE_RESOLVE(classx, ctx); - - PPointer *ptrtype = dyn_cast(classx->ValueType); - if (ptrtype == NULL || !ptrtype->PointedType->IsKindOf(RUNTIME_CLASS(PClass))) - { - ScriptPosition.Message(MSG_ERROR, "Member variable requires a class or object"); - delete this; - return NULL; - } - ValueType = membervar->Type; - return this; -} - -//========================================================================== -// -// -// -//========================================================================== - FxArrayElement::FxArrayElement(FxExpression *base, FxExpression *_index) :FxExpression(EFX_ArrayElement, base->ScriptPosition) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 771faa2c8..3fb1b1576 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -703,14 +703,18 @@ class FxAssign : public FxExpression { FxExpression *Base; FxExpression *Right; + int IsBitWrite; bool AddressRequested; bool AddressWritable; + bool IsModifyAssign; + + friend class FxAssignSelf; public: - FxAssign(FxExpression *base, FxExpression *right); + FxAssign(FxExpression *base, FxExpression *right, bool ismodify = false); ~FxAssign(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(bool *writable); + //bool RequestAddress(bool *writable); ExpEmit Emit(VMFunctionBuilder *build); ExpEmit Address; @@ -1064,7 +1068,6 @@ class FxClassMember : public FxStructMember public: FxClassMember(FxExpression*, PField*, const FScriptPosition&); - FxExpression *Resolve(FCompileContext&); }; //========================================================================== diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 2d1d189b4..84e1200e9 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -170,7 +170,7 @@ static FxExpression *ParseExpressionM (FScanner &sc, PClassActor *cls) exp->right = ParseExpressionM(sc, cls); - FxAssign *ret = new FxAssign(base, exp); + FxAssign *ret = new FxAssign(base, exp, true); left->Assignment = ret; return ret; } diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 51df4821e..a8c9b0b9b 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -24,6 +24,7 @@ struct FFlagDef const char *name; int structoffset; int fieldsize; + bool deprecated; }; FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bool strict = false); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 03e88b149..063b6e204 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -54,10 +54,11 @@ static TArray AFTable; //========================================================================== // [RH] Keep GCC quiet by not using offsetof on Actor types. -#define DEFINE_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable) } -#define DEFINE_FLAG2(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable) } -#define DEFINE_DEPRECATED_FLAG(name) { DEPF_##name, #name, -1, 0 } -#define DEFINE_DUMMY_FLAG(name) { DEPF_UNUSED, #name, -1, 0 } +#define DEFINE_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), false } +#define DEFINE_FLAG2(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), false } +#define DEFINE_FLAG2_DEPRECATED(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), true } +#define DEFINE_DEPRECATED_FLAG(name) { DEPF_##name, #name, -1, 0, true } +#define DEFINE_DUMMY_FLAG(name, deprec) { DEPF_UNUSED, #name, -1, 0, deprec } static FFlagDef ActorFlagDefs[]= { @@ -171,7 +172,6 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF4, SYNCHRONIZED, AActor, flags4), DEFINE_FLAG(MF4, NOTARGETSWITCH, AActor, flags4), DEFINE_FLAG(MF4, DONTHARMCLASS, AActor, flags4), - DEFINE_FLAG2(MF4_DONTHARMCLASS, DONTHURTSPECIES, AActor, flags4), // Deprecated name as an alias DEFINE_FLAG(MF4, SHIELDREFLECT, AActor, flags4), DEFINE_FLAG(MF4, DEFLECT, AActor, flags4), DEFINE_FLAG(MF4, ALLOWPARTICLES, AActor, flags4), @@ -278,7 +278,11 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(RF, MASKROTATION, AActor, renderflags), DEFINE_FLAG(RF, ABSMASKANGLE, AActor, renderflags), DEFINE_FLAG(RF, ABSMASKPITCH, AActor, renderflags), +}; +// These won't be accessible through bitfield variables +static FFlagDef MoreFlagDefs[] = +{ // Bounce flags DEFINE_FLAG2(BOUNCE_Walls, BOUNCEONWALLS, AActor, BounceFlags), DEFINE_FLAG2(BOUNCE_Floors, BOUNCEONFLOORS, AActor, BounceFlags), @@ -308,15 +312,16 @@ static FFlagDef ActorFlagDefs[]= DEFINE_DEPRECATED_FLAG(DOOMBOUNCE), // Deprecated flags with no more existing functionality. - DEFINE_DUMMY_FLAG(FASTER), // obsolete, replaced by 'Fast' state flag - DEFINE_DUMMY_FLAG(FASTMELEE), // obsolete, replaced by 'Fast' state flag + DEFINE_DUMMY_FLAG(FASTER, true), // obsolete, replaced by 'Fast' state flag + DEFINE_DUMMY_FLAG(FASTMELEE, true), // obsolete, replaced by 'Fast' state flag // Various Skulltag flags that are quite irrelevant to ZDoom - DEFINE_DUMMY_FLAG(NONETID), // netcode-based - DEFINE_DUMMY_FLAG(ALLOWCLIENTSPAWN), // netcode-based - DEFINE_DUMMY_FLAG(CLIENTSIDEONLY), // netcode-based - DEFINE_DUMMY_FLAG(SERVERSIDEONLY), // netcode-based - DEFINE_DUMMY_FLAG(EXPLODEONDEATH), // seems useless + DEFINE_DUMMY_FLAG(NONETID, false), // netcode-based + DEFINE_DUMMY_FLAG(ALLOWCLIENTSPAWN, false), // netcode-based + DEFINE_DUMMY_FLAG(CLIENTSIDEONLY, false), // netcode-based + DEFINE_DUMMY_FLAG(SERVERSIDEONLY, false), // netcode-based + DEFINE_DUMMY_FLAG(EXPLODEONDEATH, true), // seems useless + DEFINE_FLAG2_DEPRECATED(MF4_DONTHARMCLASS, DONTHURTSPECIES, AActor, flags4), // Deprecated name as an alias }; static FFlagDef InventoryFlagDefs[] = @@ -372,9 +377,9 @@ static FFlagDef WeaponFlagDefs[] = DEFINE_FLAG(WIF, NODEATHDESELECT, AWeapon, WeaponFlags), DEFINE_FLAG(WIF, NODEATHINPUT, AWeapon, WeaponFlags), - DEFINE_DUMMY_FLAG(NOLMS), + DEFINE_DUMMY_FLAG(NOLMS, false), DEFINE_FLAG(WIF, ALT_USES_BOTH, AWeapon, WeaponFlags), - DEFINE_DUMMY_FLAG(ALLOW_WITH_RESPAWN_INVUL), + DEFINE_DUMMY_FLAG(ALLOW_WITH_RESPAWN_INVUL, false), }; static FFlagDef PlayerPawnFlagDefs[] = @@ -394,6 +399,7 @@ static FFlagDef PowerSpeedFlagDefs[] = static const struct FFlagList { const PClass * const *Type; FFlagDef *Defs; int NumDefs; } FlagLists[] = { { &RUNTIME_CLASS_CASTLESS(AActor), ActorFlagDefs, countof(ActorFlagDefs) }, + { &RUNTIME_CLASS_CASTLESS(AActor), MoreFlagDefs, countof(MoreFlagDefs) }, { &RUNTIME_CLASS_CASTLESS(AInventory), InventoryFlagDefs, countof(InventoryFlagDefs) }, { &RUNTIME_CLASS_CASTLESS(AWeapon), WeaponFlagDefs, countof(WeaponFlagDefs) }, { &RUNTIME_CLASS_CASTLESS(APlayerPawn), PlayerPawnFlagDefs, countof(PlayerPawnFlagDefs) }, @@ -443,7 +449,7 @@ FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bo if (part2 == NULL) { // Search all lists - int max = strict ? 1 : NUM_FLAG_LISTS; + int max = strict ? 2 : NUM_FLAG_LISTS; for (i = 0; i < max; ++i) { if (type->IsDescendantOf (*FlagLists[i].Type)) @@ -683,4 +689,14 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); + + // synthesize a symbol for each flag. The bounce flags are excluded on purpose. + for (size_t i = 0; i < countof(ActorFlagDefs); i++) + { + int bit = 0; + unsigned val = ActorFlagDefs[i].flagbit; + while ((val >>= 1)) bit++; + symt.AddSymbol(new PField(FStringf("b%s", ActorFlagDefs[i].name), (ActorFlagDefs[i].fieldsize == 4? TypeSInt32 : TypeSInt16), VARF_Native, ActorFlagDefs[i].structoffset, bit)); + } + } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 274778dfe..49ba68f0a 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1836,9 +1836,12 @@ void ZCCCompiler::ProcessDefaultFlag(PClassActor *cls, ZCC_FlagStmt *flg) auto fd = FindFlag(cls, n1, n2, true); if (fd != nullptr) { - if (fd->structoffset == -1) + if (fd->deprecated) { Warn(flg, "Deprecated flag '%s%s%s' used", n1, n2 ? "." : "", n2 ? n2 : ""); + } + if (fd->structoffset == -1) + { HandleDeprecatedFlags((AActor*)cls->Defaults, cls, flg->set, fd->flagbit); } else @@ -2384,7 +2387,7 @@ static int Pex2Tok[] = { static FxExpression *ModifyAssign(FxBinary *operation, FxExpression *left) { auto assignself = static_cast(operation->left); - auto assignment = new FxAssign(left, operation); + auto assignment = new FxAssign(left, operation, true); assignself->Assignment = assignment; return assignment; } From ae728cc61a1e4777bcdab90d4ba7d316431b2a45 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 09:55:13 +0200 Subject: [PATCH 105/255] - made the count flags and NOBLOCKMAP and NOSECTOR read-only. These require special treatment to work which can only be done by a setter function. --- src/CMakeLists.txt | 3 --- src/scripting/thingdef.h | 2 +- src/scripting/thingdef_data.cpp | 21 +++++++++++---------- src/scripting/zscript/zcc_compile.cpp | 2 +- 4 files changed, 13 insertions(+), 15 deletions(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 2720f026d..9e64f1d29 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -837,9 +837,6 @@ set( NOT_COMPILED_SOURCE_FILES sc_man_scanner.re g_doom/a_archvile.cpp g_doom/a_bossbrain.cpp - g_doom/a_bruiser.cpp - g_doom/a_cacodemon.cpp - g_doom/a_cyberdemon.cpp g_doom/a_demon.cpp g_doom/a_doomimp.cpp g_doom/a_doomweaps.cpp diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index a8c9b0b9b..44a441bee 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -24,7 +24,7 @@ struct FFlagDef const char *name; int structoffset; int fieldsize; - bool deprecated; + int varflags; }; FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bool strict = false); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 063b6e204..4622e764c 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -54,11 +54,12 @@ static TArray AFTable; //========================================================================== // [RH] Keep GCC quiet by not using offsetof on Actor types. -#define DEFINE_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), false } -#define DEFINE_FLAG2(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), false } -#define DEFINE_FLAG2_DEPRECATED(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), true } +#define DEFINE_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native } +#define DEFINE_READONLY_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native|VARF_ReadOnly } +#define DEFINE_FLAG2(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native } +#define DEFINE_FLAG2_DEPRECATED(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native|VARF_Deprecated } #define DEFINE_DEPRECATED_FLAG(name) { DEPF_##name, #name, -1, 0, true } -#define DEFINE_DUMMY_FLAG(name, deprec) { DEPF_UNUSED, #name, -1, 0, deprec } +#define DEFINE_DUMMY_FLAG(name, deprec) { DEPF_UNUSED, #name, -1, 0, deprec? VARF_Deprecated:0 } static FFlagDef ActorFlagDefs[]= { @@ -66,8 +67,8 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF, SPECIAL, APlayerPawn, flags), DEFINE_FLAG(MF, SOLID, AActor, flags), DEFINE_FLAG(MF, SHOOTABLE, AActor, flags), - DEFINE_FLAG(MF, NOSECTOR, AActor, flags), - DEFINE_FLAG(MF, NOBLOCKMAP, AActor, flags), + DEFINE_READONLY_FLAG(MF, NOSECTOR, AActor, flags), + DEFINE_READONLY_FLAG(MF, NOBLOCKMAP, AActor, flags), DEFINE_FLAG(MF, AMBUSH, AActor, flags), DEFINE_FLAG(MF, JUSTHIT, AActor, flags), DEFINE_FLAG(MF, JUSTATTACKED, AActor, flags), @@ -83,8 +84,8 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF, NOBLOOD, AActor, flags), DEFINE_FLAG(MF, CORPSE, AActor, flags), DEFINE_FLAG(MF, INFLOAT, AActor, flags), - DEFINE_FLAG(MF, COUNTKILL, AActor, flags), - DEFINE_FLAG(MF, COUNTITEM, AActor, flags), + DEFINE_READONLY_FLAG(MF, COUNTKILL, AActor, flags), + DEFINE_READONLY_FLAG(MF, COUNTITEM, AActor, flags), DEFINE_FLAG(MF, SKULLFLY, AActor, flags), DEFINE_FLAG(MF, NOTDMATCH, AActor, flags), DEFINE_FLAG(MF, SPAWNSOUNDSOURCE, AActor, flags), @@ -185,7 +186,7 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF5, GETOWNER, AActor, flags5), DEFINE_FLAG(MF5, NODROPOFF, AActor, flags5), DEFINE_FLAG(MF5, NOFORWARDFALL, AActor, flags5), - DEFINE_FLAG(MF5, COUNTSECRET, AActor, flags5), + DEFINE_READONLY_FLAG(MF5, COUNTSECRET, AActor, flags5), DEFINE_FLAG(MF5, NODAMAGE, AActor, flags5), DEFINE_FLAG(MF5, BLOODSPLATTER, AActor, flags5), DEFINE_FLAG(MF5, OLDRADIUSDMG, AActor, flags5), @@ -696,7 +697,7 @@ void InitThingdef() int bit = 0; unsigned val = ActorFlagDefs[i].flagbit; while ((val >>= 1)) bit++; - symt.AddSymbol(new PField(FStringf("b%s", ActorFlagDefs[i].name), (ActorFlagDefs[i].fieldsize == 4? TypeSInt32 : TypeSInt16), VARF_Native, ActorFlagDefs[i].structoffset, bit)); + symt.AddSymbol(new PField(FStringf("b%s", ActorFlagDefs[i].name), (ActorFlagDefs[i].fieldsize == 4? TypeSInt32 : TypeSInt16), ActorFlagDefs[i].varflags, ActorFlagDefs[i].structoffset, bit)); } } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 49ba68f0a..22107796f 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1836,7 +1836,7 @@ void ZCCCompiler::ProcessDefaultFlag(PClassActor *cls, ZCC_FlagStmt *flg) auto fd = FindFlag(cls, n1, n2, true); if (fd != nullptr) { - if (fd->deprecated) + if (fd->varflags & VARF_Deprecated) { Warn(flg, "Deprecated flag '%s%s%s' used", n1, n2 ? "." : "", n2 ? n2 : ""); } From 656b8cb16e0baec82589f124b689397f5271e2f2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 10:15:24 +0200 Subject: [PATCH 106/255] - added explicit setter functions for the count and link flags so that A_ChangeFlag and A_SetFlag can be deprecated. --- src/p_actionfunctions.cpp | 68 +++++++++++++++++++++++++++++ wadsrc/static/zscript.txt | 2 + wadsrc/static/zscript/actor.txt | 6 ++- wadsrc/static/zscript/constants.txt | 5 +++ 4 files changed, 79 insertions(+), 2 deletions(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index f389cd1ee..3d9ccb326 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -4852,6 +4852,74 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFlag) } +//=========================================================================== +// +// A_ChangeCountFlags (needed, because these flags affect global counters) +// +//=========================================================================== +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeLinkFlags) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_INT_OPT(blockmap) { blockmap = -1; } + PARAM_INT_OPT(sector) { sector = -1; } + + self->UnlinkFromWorld(); + + if (blockmap != -1) + { + if (blockmap == 0) self->flags &= MF_NOBLOCKMAP; + else self->flags |= MF_NOBLOCKMAP; + } + + if (sector != -1) + { + if (sector == 0) self->flags &= MF_NOSECTOR; + else self->flags |= MF_NOSECTOR; + } + + self->LinkToWorld(); + return 0; +} + +//=========================================================================== +// +// A_ChangeCountFlags (needed, because these flags affect global counters) +// +//=========================================================================== +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeCountFlags) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_INT_OPT(kill) { kill = -1; } + PARAM_INT_OPT(item) { item = -1; } + PARAM_INT_OPT(secret) { secret = -1; } + + if (self->CountsAsKill() && self->health > 0) --level.total_monsters; + if (self->flags & MF_COUNTITEM) --level.total_items; + if (self->flags5 & MF5_COUNTSECRET) --level.total_secrets; + + if (kill != -1) + { + if (kill == 0) self->flags &= MF_COUNTKILL; + else self->flags |= MF_COUNTKILL; + } + + if (item != -1) + { + if (item == 0) self->flags &= MF_COUNTITEM; + else self->flags |= MF_COUNTITEM; + } + + if (secret != -1) + { + if (secret == 0) self->flags5 &= MF5_COUNTSECRET; + else self->flags5 |= MF5_COUNTSECRET; + } + if (self->CountsAsKill() && self->health > 0) ++level.total_monsters; + if (self->flags & MF_COUNTITEM) ++level.total_items; + if (self->flags5 & MF5_COUNTSECRET) ++level.total_secrets; + return 0; +} + //=========================================================================== // // A_RaiseMaster diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 6de64d07e..3ab33bfd9 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -177,3 +177,5 @@ zscript/chex/chexweapons.txt zscript/chex/chexitems.txt zscript/chex/chexdecorations.txt zscript/chex/chexplayer.txt + +zscript/test2.txt diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index b6d65a29e..fa45eb0e6 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -238,8 +238,10 @@ class Actor : Thinker native native void A_ExtChase(bool usemelee, bool usemissile, bool playactive = true, bool nightmarefast = false); native void A_DropInventory(class itemtype); native void A_SetBlend(color color1, float alpha, int tics, color color2 = ""); - native void A_ChangeFlag(string flagname, bool value); - native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); + deprecated native void A_ChangeFlag(string flagname, bool value); + deprecated native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); + native void A_ChangeCountFlags(int kill = FLAG_NO_CHANGE, int item = FLAG_NO_CHANGE, int secret = FLAG_NO_CHANGE); + native void A_ChangeLinkFlags(int blockmap = FLAG_NO_CHANGE, int sector = FLAG_NO_CHANGE); native state A_JumpIf(bool expression, state label); native void A_RaiseMaster(bool copy = 0); native void A_RaiseChildren(bool copy = 0); diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index b98846d8b..9792ec230 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -1,3 +1,6 @@ +// for flag changer functions. +const int FLAG_NO_CHANGE = -1; + // Flags for A_PainAttack enum EPainAttackFlags { @@ -820,3 +823,5 @@ struct FStateParamInfo EStateType mStateType; int mPSPIndex; } + + From e39bf9eaeb7544762d65be41c1571a612c5595e3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 11:38:02 +0200 Subject: [PATCH 107/255] - made the bounce flags accessible after verifying that the code works for 16 bit variables. - fixed a deprecation warning with the Heresiarch by replacing A_ChangeFlag. --- wadsrc/static/zscript/constants.txt | 2 +- wadsrc/static/zscript/hexen/heresiarch.txt | 15 +++++++++------ 2 files changed, 10 insertions(+), 7 deletions(-) diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 9792ec230..41c4bfec9 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -1,5 +1,5 @@ // for flag changer functions. -const int FLAG_NO_CHANGE = -1; +const FLAG_NO_CHANGE = -1; // Flags for A_PainAttack enum EPainAttackFlags diff --git a/wadsrc/static/zscript/hexen/heresiarch.txt b/wadsrc/static/zscript/hexen/heresiarch.txt index 6ffc11b3b..7d3ba63a5 100644 --- a/wadsrc/static/zscript/hexen/heresiarch.txt +++ b/wadsrc/static/zscript/hexen/heresiarch.txt @@ -96,6 +96,12 @@ class SorcBall native native void A_SorcBallOrbit(); native void A_SorcBallPop(); native void A_BounceCheck (); + + void A_SorcBallExplode() + { + bNOBOUNCESOUND = true; + A_Explode(255, 255); + } } // First ball (purple) - fires projectiles ---------------------------------- @@ -112,8 +118,7 @@ class SorcBall1 : SorcBall native SBMP B 2 A_BounceCheck; Wait; Death: - SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1); - SBS4 D 5 A_Explode(255,255); + SBS4 D 5 A_SorcBallExplode; SBS4 E 5; SBS4 FGH 6; Stop; @@ -135,8 +140,7 @@ class SorcBall2 : SorcBall native SBMB B 2 A_BounceCheck; Wait; Death: - SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1); - SBS3 D 5 A_Explode(255,255); + SBS3 D 5 A_SorcBallExplode; SBS3 E 5; SBS3 FGH 6; Stop; @@ -157,8 +161,7 @@ class SorcBall3 : SorcBall native SBMG B 2 A_BounceCheck; Wait; Death: - SBS4 D 0 A_ChangeFlag("NOBOUNCESOUND", 1); - SBS3 D 5 A_Explode(255,255); + SBS3 D 5 A_SorcBallExplode; SBS3 E 5; SBS3 FGH 6; Stop; From 142278a8186725f65d4ac2fe8add1ad965f365ee Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 13:29:58 +0200 Subject: [PATCH 108/255] - fixed incomplete commit for bounce flags - fixed flag clearing in new function. --- src/p_actionfunctions.cpp | 10 +++++----- src/scripting/thingdef_data.cpp | 9 +++++---- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 3d9ccb326..f5d7251c3 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -4867,13 +4867,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeLinkFlags) if (blockmap != -1) { - if (blockmap == 0) self->flags &= MF_NOBLOCKMAP; + if (blockmap == 0) self->flags &= *MF_NOBLOCKMAP; else self->flags |= MF_NOBLOCKMAP; } if (sector != -1) { - if (sector == 0) self->flags &= MF_NOSECTOR; + if (sector == 0) self->flags &= *MF_NOSECTOR; else self->flags |= MF_NOSECTOR; } @@ -4899,19 +4899,19 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeCountFlags) if (kill != -1) { - if (kill == 0) self->flags &= MF_COUNTKILL; + if (kill == 0) self->flags &= ~MF_COUNTKILL; else self->flags |= MF_COUNTKILL; } if (item != -1) { - if (item == 0) self->flags &= MF_COUNTITEM; + if (item == 0) self->flags &= ~MF_COUNTITEM; else self->flags |= MF_COUNTITEM; } if (secret != -1) { - if (secret == 0) self->flags5 &= MF5_COUNTSECRET; + if (secret == 0) self->flags5 &= ~MF5_COUNTSECRET; else self->flags5 |= MF5_COUNTSECRET; } if (self->CountsAsKill() && self->health > 0) ++level.total_monsters; diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 4622e764c..a4815cb33 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -279,11 +279,7 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(RF, MASKROTATION, AActor, renderflags), DEFINE_FLAG(RF, ABSMASKANGLE, AActor, renderflags), DEFINE_FLAG(RF, ABSMASKPITCH, AActor, renderflags), -}; -// These won't be accessible through bitfield variables -static FFlagDef MoreFlagDefs[] = -{ // Bounce flags DEFINE_FLAG2(BOUNCE_Walls, BOUNCEONWALLS, AActor, BounceFlags), DEFINE_FLAG2(BOUNCE_Floors, BOUNCEONFLOORS, AActor, BounceFlags), @@ -299,6 +295,11 @@ static FFlagDef MoreFlagDefs[] = DEFINE_FLAG2(BOUNCE_MBF, MBFBOUNCER, AActor, BounceFlags), DEFINE_FLAG2(BOUNCE_AutoOffFloorOnly, BOUNCEAUTOOFFFLOORONLY, AActor, BounceFlags), DEFINE_FLAG2(BOUNCE_UseBounceState, USEBOUNCESTATE, AActor, BounceFlags), +}; + +// These won't be accessible through bitfield variables +static FFlagDef MoreFlagDefs[] = +{ // Deprecated flags. Handling must be performed in HandleDeprecatedFlags DEFINE_DEPRECATED_FLAG(FIREDAMAGE), From 449dfc3cdccc9bc50587e908ff2cee517bf6a3b0 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 13:30:22 +0200 Subject: [PATCH 109/255] - removed test file from zscript.txt. --- wadsrc/static/zscript.txt | 2 -- 1 file changed, 2 deletions(-) diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 3ab33bfd9..6de64d07e 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -177,5 +177,3 @@ zscript/chex/chexweapons.txt zscript/chex/chexitems.txt zscript/chex/chexdecorations.txt zscript/chex/chexplayer.txt - -zscript/test2.txt From 576fc0c237fe31bd30b618100d7dd183184b7a2d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 14:27:49 +0200 Subject: [PATCH 110/255] - how did this happen. --- src/p_actionfunctions.cpp | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index f5d7251c3..57c676801 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -4867,13 +4867,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeLinkFlags) if (blockmap != -1) { - if (blockmap == 0) self->flags &= *MF_NOBLOCKMAP; + if (blockmap == 0) self->flags &= ~MF_NOBLOCKMAP; else self->flags |= MF_NOBLOCKMAP; } if (sector != -1) { - if (sector == 0) self->flags &= *MF_NOSECTOR; + if (sector == 0) self->flags &= ~MF_NOSECTOR; else self->flags |= MF_NOSECTOR; } From 6d0dad3b38d9f9e89c492a5af51f35fcadeaf753 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 14:41:58 +0200 Subject: [PATCH 111/255] - scriptified the code for the Demon and DoomImp. --- src/CMakeLists.txt | 2 -- src/g_doom/a_demon.cpp | 29 -------------------- src/g_doom/a_doomimp.cpp | 38 -------------------------- src/g_doom/a_doommisc.cpp | 2 -- wadsrc/static/zscript/actor.txt | 2 -- wadsrc/static/zscript/doom/demon.txt | 18 ++++++++++++ wadsrc/static/zscript/doom/doomimp.txt | 28 +++++++++++++++++++ 7 files changed, 46 insertions(+), 73 deletions(-) delete mode 100644 src/g_doom/a_demon.cpp delete mode 100644 src/g_doom/a_doomimp.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 9e64f1d29..5a3351880 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -837,8 +837,6 @@ set( NOT_COMPILED_SOURCE_FILES sc_man_scanner.re g_doom/a_archvile.cpp g_doom/a_bossbrain.cpp - g_doom/a_demon.cpp - g_doom/a_doomimp.cpp g_doom/a_doomweaps.cpp g_doom/a_fatso.cpp g_doom/a_keen.cpp diff --git a/src/g_doom/a_demon.cpp b/src/g_doom/a_demon.cpp deleted file mode 100644 index 5ac3e9e74..000000000 --- a/src/g_doom/a_demon.cpp +++ /dev/null @@ -1,29 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -*/ - -static FRandom pr_sargattack ("SargAttack"); - -DEFINE_ACTION_FUNCTION(AActor, A_SargAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - A_FaceTarget (self); - if (self->CheckMeleeRange ()) - { - int damage = ((pr_sargattack()%10)+1)*4; - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - } - return 0; -} diff --git a/src/g_doom/a_doomimp.cpp b/src/g_doom/a_doomimp.cpp deleted file mode 100644 index 1b9dd9485..000000000 --- a/src/g_doom/a_doomimp.cpp +++ /dev/null @@ -1,38 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -*/ - -static FRandom pr_troopattack ("TroopAttack"); - -// -// A_TroopAttack -// -DEFINE_ACTION_FUNCTION(AActor, A_TroopAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - A_FaceTarget (self); - if (self->CheckMeleeRange ()) - { - int damage = (pr_troopattack()%8+1)*3; - S_Sound (self, CHAN_WEAPON, "imp/melee", 1, ATTN_NORM); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - return 0; - } - - // launch a missile - P_SpawnMissile (self, self->target, PClass::FindActor("DoomImpBall")); - return 0; -} diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index fb5ae3b28..de53dc3af 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -24,8 +24,6 @@ // Include all the other Doom stuff here to reduce compile time #include "a_archvile.cpp" #include "a_bossbrain.cpp" -#include "a_demon.cpp" -#include "a_doomimp.cpp" #include "a_doomweaps.cpp" #include "a_fatso.cpp" #include "a_keen.cpp" diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index fa45eb0e6..872a3ef98 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -110,8 +110,6 @@ class Actor : Thinker native native void A_BossDeath(); native void A_CPosAttack(); native void A_CPosRefire(); - native void A_TroopAttack(); - native void A_SargAttack(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); native void A_Metal(); diff --git a/wadsrc/static/zscript/doom/demon.txt b/wadsrc/static/zscript/doom/demon.txt index 398888e45..d4cd9002c 100644 --- a/wadsrc/static/zscript/doom/demon.txt +++ b/wadsrc/static/zscript/doom/demon.txt @@ -75,3 +75,21 @@ class Spectre : Demon } +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_SargAttack() + { + if (target && CheckMeleeRange()) + { + int damage = random[pr_sargattack](1, 10) * 4; + int newdam = target.DamageMobj (self, self, damage, "Melee"); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + } + } +} diff --git a/wadsrc/static/zscript/doom/doomimp.txt b/wadsrc/static/zscript/doom/doomimp.txt index 318e81471..d2b93acdd 100644 --- a/wadsrc/static/zscript/doom/doomimp.txt +++ b/wadsrc/static/zscript/doom/doomimp.txt @@ -92,3 +92,31 @@ class DoomImpBall : Actor Stop; } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_TroopAttack() + { + if (target) + { + if (CheckMeleeRange()) + { + int damage = random[pr_troopattack](1, 8) * 3; + A_PlaySound ("imp/melee", CHAN_WEAPON); + int newdam = target.DamageMobj (self, self, damage, "Melee"); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + } + else + { + // launch a missile + SpawnMissile (target, "DoomImpBall"); + } + } + } +} From be4ce05aeebcbad43f1eaf865677e20b766860b4 Mon Sep 17 00:00:00 2001 From: Edoardo Prezioso Date: Tue, 25 Oct 2016 16:53:14 +0200 Subject: [PATCH 112/255] - Fixed Clang compiler errors and some warnings. --- src/scripting/codegeneration/codegen.cpp | 2 +- src/scripting/thingdef_properties.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 6 +++--- src/scripting/zscript/zcc_parser.cpp | 6 +++--- 4 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index c8a682189..7bb18178c 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1769,7 +1769,7 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) //========================================================================== FxAssign::FxAssign(FxExpression *base, FxExpression *right, bool ismodify) -: FxExpression(EFX_Assign, base->ScriptPosition), Base(base), Right(right), IsModifyAssign(ismodify), IsBitWrite(-1) +: FxExpression(EFX_Assign, base->ScriptPosition), Base(base), Right(right), IsBitWrite(-1), IsModifyAssign(ismodify) { AddressRequested = false; AddressWritable = false; diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index cb8688610..d3fb452cb 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -2432,7 +2432,7 @@ DEFINE_CLASS_PROPERTY_PREFIX(powerup, type, S, PowerupGiver) // Yuck! What was I thinking when I decided to prepend "Power" to the name? // Now it's too late to change it... PClassActor *cls = PClass::FindActor(str); - if (cls == NULL || !cls->IsDescendantOf(RUNTIME_CLASS(APowerup)) && !bag.fromZScript) + if (cls == NULL || (!cls->IsDescendantOf(RUNTIME_CLASS(APowerup)) && !bag.fromZScript)) { FString st; st.Format("%s%s", strnicmp(str, "power", 5)? "Power" : "", str); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 22107796f..340a77703 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1240,7 +1240,7 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel if (field->Flags & notallowed) { - Error(field, "Invalid qualifiers for %s (%s not allowed)", FName(field->Names->Name).GetChars(), FlagsToString(field->Flags & notallowed)); + Error(field, "Invalid qualifiers for %s (%s not allowed)", FName(field->Names->Name).GetChars(), FlagsToString(field->Flags & notallowed).GetChars()); field->Flags &= notallowed; } uint32_t varflags = 0; @@ -1977,7 +1977,7 @@ void ZCCCompiler::InitFunctions() if (f->Flags & notallowed) { - Error(f, "Invalid qualifiers for %s (%s not allowed)", FName(f->Name).GetChars(), FlagsToString(f->Flags & notallowed)); + Error(f, "Invalid qualifiers for %s (%s not allowed)", FName(f->Name).GetChars(), FlagsToString(f->Flags & notallowed).GetChars()); f->Flags &= notallowed; } uint32_t varflags = VARF_Method; @@ -2018,7 +2018,7 @@ void ZCCCompiler::InitFunctions() if (p->Type != nullptr) { auto type = DetermineType(c->Type(), p, f->Name, p->Type, false, false); - int flags; + int flags = 0; if (p->Flags & ZCC_In) flags |= VARF_In; if (p->Flags & ZCC_Out) flags |= VARF_Out; if (p->Default != nullptr) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 18d683c4c..8ebc86167 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -331,7 +331,7 @@ static void DoParse(int lumpnum) // If the parser fails, there is no point starting the compiler, because it'd only flood the output with endless errors. if (FScriptPosition::ErrorCounter > 0) { - I_Error("%d errors while parsing %s", FScriptPosition::ErrorCounter, Wads.GetLumpFullPath(lumpnum)); + I_Error("%d errors while parsing %s", FScriptPosition::ErrorCounter, Wads.GetLumpFullPath(lumpnum).GetChars()); } #if 0 @@ -364,12 +364,12 @@ static void DoParse(int lumpnum) if (FScriptPosition::ErrorCounter > 0) { // Abort if the compiler produced any errors. Also do not compile further lumps, because they very likely miss some stuff. - I_Error("%d errors, %d warnings while compiling %s", FScriptPosition::ErrorCounter, FScriptPosition::WarnCounter, Wads.GetLumpFullPath(lumpnum)); + I_Error("%d errors, %d warnings while compiling %s", FScriptPosition::ErrorCounter, FScriptPosition::WarnCounter, Wads.GetLumpFullPath(lumpnum).GetChars()); } else if (FScriptPosition::WarnCounter > 0) { // If we got warnings, but no errors, print the information but continue. - Printf(TEXTCOLOR_ORANGE, "%d warnings while compiling %s", FScriptPosition::WarnCounter, Wads.GetLumpFullPath(lumpnum)); + Printf(TEXTCOLOR_ORANGE "%d warnings while compiling %s", FScriptPosition::WarnCounter, Wads.GetLumpFullPath(lumpnum).GetChars()); } } From 33d00070b5e6ebb415fa04d477e85558b627b855 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 25 Oct 2016 17:07:19 +0200 Subject: [PATCH 113/255] - made some variables signed that should not be unsigned. --- src/scripting/codegeneration/codegen.cpp | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 7bb18178c..de7048d88 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5812,10 +5812,10 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_WARNING, "Case expression is constant"); auto &content = *Content; - unsigned defaultindex = -1; - unsigned defaultbreak = -1; - unsigned caseindex = -1; - unsigned casebreak = -1; + int defaultindex = -1; + int defaultbreak = -1; + int caseindex = -1; + int casebreak = -1; // look for a case label with a matching value for (unsigned i = 0; i < content.Size(); i++) { @@ -5846,7 +5846,7 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) if (caseindex > 0 && casebreak - caseindex > 1) { auto seq = new FxSequence(ScriptPosition); - for (unsigned i = caseindex + 1; i < casebreak; i++) + for (int i = caseindex + 1; i < casebreak; i++) { if (content[i] != nullptr && content[i]->ExprType != EFX_CaseStatement) { From 823c52aeb2d0c92c7a298709da44534528c6da7f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 26 Oct 2016 11:30:30 +0200 Subject: [PATCH 114/255] - scriptified the functions in a_possessed.cpp and added the needed exports and constants. - fixed: Script functions did not receive the function name when being created. - relaxed the asserts for PARAM_STATE, because the VM knows nothing about ATAG_STATE. Any state variable's content (e.g. Actor.SeeState) will receive ATAG_GENERIC, rather than ATAG_STATE. - added a 'NeedResult' flag so that certain operations can create shorter code if the result of the expression is not needed. So far only used for postdecrement/increment statements on local variables (which is the most frequent case where this matters.) - fixed postincrement and decrement for local variables. Due to the result preservation semantics it created faulty code. --- src/CMakeLists.txt | 1 - src/g_doom/a_doommisc.cpp | 1 - src/g_doom/a_possessed.cpp | 134 ----------------------- src/info.cpp | 2 +- src/p_enemy.cpp | 6 + src/p_map.cpp | 31 ++++++ src/p_mobj.cpp | 8 ++ src/p_sight.cpp | 8 ++ src/scripting/codegeneration/codegen.cpp | 75 +++++++++---- src/scripting/codegeneration/codegen.h | 3 +- src/scripting/thingdef_data.cpp | 2 + src/scripting/vm/vm.h | 6 +- src/scripting/vm/vmbuilder.cpp | 1 + wadsrc/static/zscript/actor.txt | 11 +- wadsrc/static/zscript/constants.txt | 37 +++++++ wadsrc/static/zscript/doom/possessed.txt | 90 +++++++++++++++ 16 files changed, 246 insertions(+), 170 deletions(-) delete mode 100644 src/g_doom/a_possessed.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 5a3351880..a5164e84b 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -842,7 +842,6 @@ set( NOT_COMPILED_SOURCE_FILES g_doom/a_keen.cpp g_doom/a_lostsoul.cpp g_doom/a_painelemental.cpp - g_doom/a_possessed.cpp g_doom/a_revenant.cpp g_doom/a_scriptedmarine.cpp g_doom/a_spidermaster.cpp diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index de53dc3af..4c8be07f1 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -29,7 +29,6 @@ #include "a_keen.cpp" #include "a_lostsoul.cpp" #include "a_painelemental.cpp" -#include "a_possessed.cpp" #include "a_revenant.cpp" #include "a_spidermaster.cpp" #include "a_scriptedmarine.cpp" diff --git a/src/g_doom/a_possessed.cpp b/src/g_doom/a_possessed.cpp deleted file mode 100644 index 0b9a9ecfd..000000000 --- a/src/g_doom/a_possessed.cpp +++ /dev/null @@ -1,134 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -*/ - -static FRandom pr_posattack ("PosAttack"); -static FRandom pr_sposattack ("SPosAttack"); -static FRandom pr_cposattack ("CPosAttack"); -static FRandom pr_cposrefire ("CPosRefire"); - -// -// A_PosAttack -// -DEFINE_ACTION_FUNCTION(AActor, A_PosAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - int damage; - DAngle angle; - DAngle slope; - - if (!self->target) - return 0; - - A_FaceTarget (self); - angle = self->Angles.Yaw; - slope = P_AimLineAttack (self, angle, MISSILERANGE); - - S_Sound (self, CHAN_WEAPON, "grunt/attack", 1, ATTN_NORM); - angle += pr_posattack.Random2() * (22.5 / 256); - damage = ((pr_posattack()%5)+1)*3; - P_LineAttack (self, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff); - return 0; -} - -static void A_SPosAttack2 (AActor *self) -{ - int i; - DAngle bangle; - DAngle slope; - - A_FaceTarget (self); - bangle = self->Angles.Yaw; - slope = P_AimLineAttack (self, bangle, MISSILERANGE); - - for (i=0 ; i<3 ; i++) - { - DAngle angle = bangle + pr_sposattack.Random2() * (22.5 / 256); - int damage = ((pr_sposattack()%5)+1)*3; - P_LineAttack(self, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff); - } -} - -DEFINE_ACTION_FUNCTION(AActor, A_SPosAttackUseAtkSound) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM); - A_SPosAttack2 (self); - return 0; -} - -// This version of the function, which uses a hard-coded sound, is -// meant for Dehacked only. -DEFINE_ACTION_FUNCTION(AActor, A_SPosAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - S_Sound (self, CHAN_WEAPON, "shotguy/attack", 1, ATTN_NORM); - A_SPosAttack2 (self); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_CPosAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - DAngle angle; - DAngle bangle; - int damage; - DAngle slope; - - if (!self->target) - return 0; - - // [RH] Andy Baker's stealth monsters - if (self->flags & MF_STEALTH) - { - self->visdir = 1; - } - - S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM); - A_FaceTarget (self); - bangle = self->Angles.Yaw; - slope = P_AimLineAttack (self, bangle, MISSILERANGE); - - angle = bangle + pr_cposattack.Random2() * (22.5 / 256); - damage = ((pr_cposattack()%5)+1)*3; - P_LineAttack (self, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_CPosRefire) -{ - PARAM_SELF_PROLOGUE(AActor); - - // keep firing unless target got out of sight - A_FaceTarget (self); - - if (pr_cposrefire() < 40) - return 0; - - if (!self->target - || P_HitFriend (self) - || self->target->health <= 0 - || !P_CheckSight (self, self->target, SF_SEEPASTBLOCKEVERYTHING|SF_SEEPASTSHOOTABLELINES)) - { - self->SetState (self->SeeState); - } - return 0; -} diff --git a/src/info.cpp b/src/info.cpp index 5e267b39c..268d4f91c 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -77,7 +77,7 @@ bool FState::CallAction(AActor *self, AActor *stateowner, FStateParamInfo *info, { ActionCycles.Clock(); - static VMFrameStack stack; + VMFrameStack stack; VMValue params[3] = { self, stateowner, VMValue(info, ATAG_STATEINFO) }; // If the function returns a state, store it at *stateret. // If it doesn't return a state but stateret is non-NULL, we need diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 0c2cb8e28..fbdc1a212 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -461,6 +461,12 @@ bool P_HitFriend(AActor * self) return false; } +DEFINE_ACTION_FUNCTION(AActor, HitFriend) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_BOOL(P_HitFriend(self)); +} + // // P_Move // Move in the current direction, diff --git a/src/p_map.cpp b/src/p_map.cpp index 849f8dd24..ef46f6566 100644 --- a/src/p_map.cpp +++ b/src/p_map.cpp @@ -4043,6 +4043,18 @@ DAngle P_AimLineAttack(AActor *t1, DAngle angle, double distance, FTranslatedLin return result->linetarget ? result->pitch : t1->Angles.Pitch; } +DEFINE_ACTION_FUNCTION(AActor, AimLineAttack) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_ANGLE(angle); + PARAM_FLOAT(distance); + PARAM_POINTER_OPT(pLineTarget, FTranslatedLineTarget) { pLineTarget = nullptr; } + PARAM_ANGLE_OPT(vrange) { vrange = 0.; } + PARAM_INT_OPT(flags) { flags = 0; } + PARAM_OBJECT_OPT(target, AActor) { target = nullptr; } + PARAM_OBJECT_OPT(friender, AActor) { friender = nullptr; } + ACTION_RETURN_FLOAT(P_AimLineAttack(self, angle, distance, pLineTarget, vrange, flags, target, friender).Degrees); +} //========================================================================== // @@ -4410,6 +4422,25 @@ AActor *P_LineAttack(AActor *t1, DAngle angle, double distance, } } +DEFINE_ACTION_FUNCTION(AActor, LineAttack) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_ANGLE(angle); + PARAM_FLOAT(distance); + PARAM_ANGLE(pitch); + PARAM_INT(damage); + PARAM_NAME(damageType); + PARAM_CLASS(puffType, AActor); + PARAM_INT_OPT(flags) { flags = 0; } + PARAM_POINTER_OPT(victim, FTranslatedLineTarget) { victim = nullptr; } + + int acdmg; + auto puff = P_LineAttack(self, angle, distance, pitch, damage, damageType, puffType, flags, victim, &acdmg); + if (numret > 0) ret[0].SetPointer(puff, ATAG_OBJECT); + if (numret > 1) ret[1].SetInt(acdmg), numret = 2; + return numret; +} + //========================================================================== // // P_LinePickActor diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 5d40d1ed3..7398fa29f 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -510,6 +510,14 @@ bool AActor::SetState (FState *newstate, bool nofunction) return true; } +DEFINE_ACTION_FUNCTION(AActor, SetState) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_STATE(state); + PARAM_BOOL_OPT(nofunction) { nofunction = false; } + ACTION_RETURN_BOOL(self->SetState(state, nofunction)); +}; + //============================================================================ // // AActor :: AddInventory diff --git a/src/p_sight.cpp b/src/p_sight.cpp index c10365eea..fefe9eb27 100644 --- a/src/p_sight.cpp +++ b/src/p_sight.cpp @@ -905,6 +905,14 @@ done: return res; } +DEFINE_ACTION_FUNCTION(AActor, CheckSight) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(target, AActor); + PARAM_INT_OPT(flags) { flags = 0; } + ACTION_RETURN_BOOL(P_CheckSight(self, target, flags)); +} + ADD_STAT (sight) { FString out; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index de7048d88..8fec40113 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1519,9 +1519,8 @@ ExpEmit FxUnaryNotBoolean::Emit(VMFunctionBuilder *build) assert(ValueType == TypeBool); ExpEmit from = Operand->Emit(build); assert(!from.Konst); - // ~x & 1 - build->Emit(OP_NOT, from.RegNum, from.RegNum, 0); - build->Emit(OP_AND_RK, from.RegNum, from.RegNum, build->GetConstantInt(1)); + // boolean not is the same as XOR-ing the lowest bit + build->Emit(OP_XOR_RK, from.RegNum, from.RegNum, build->GetConstantInt(1)); return from; } @@ -1734,32 +1733,54 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) int zero = build->GetConstantInt(0); int regtype = ValueType->GetRegType(); ExpEmit pointer = Base->Emit(build); - ExpEmit out = pointer; if (!pointer.Target) { - out = ExpEmit(build, regtype); + ExpEmit out(build, regtype); build->Emit(ValueType->GetLoadOp(), out.RegNum, pointer.RegNum, zero); + ExpEmit assign(build, regtype); + if (regtype == REGT_INT) + { + build->Emit((Token == TK_Incr) ? OP_ADD_RK : OP_SUB_RK, assign.RegNum, out.RegNum, build->GetConstantInt(1)); + } + else + { + build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, assign.RegNum, out.RegNum, build->GetConstantFloat(1.)); + } + build->Emit(ValueType->GetStoreOp(), pointer.RegNum, out.RegNum, zero); + pointer.Free(build); + assign.Free(build); + return out; } - - ExpEmit assign(build, regtype); - if (regtype == REGT_INT) + else if (NeedResult) { - build->Emit((Token == TK_Incr) ? OP_ADD_RK : OP_SUB_RK, assign.RegNum, out.RegNum, build->GetConstantInt(1)); + ExpEmit out(build, regtype); + if (regtype == REGT_INT) + { + build->Emit(OP_MOVE, out.RegNum, pointer.RegNum); + build->Emit((Token == TK_Incr) ? OP_ADD_RK : OP_SUB_RK, pointer.RegNum, pointer.RegNum, build->GetConstantInt(1)); + } + else + { + build->Emit(OP_MOVEF, out.RegNum, pointer.RegNum); + build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, pointer.RegNum, pointer.RegNum, build->GetConstantFloat(1.)); + } + pointer.Free(build); + return out; } else { - build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, assign.RegNum, out.RegNum, build->GetConstantFloat(1.)); + if (regtype == REGT_INT) + { + build->Emit((Token == TK_Incr) ? OP_ADD_RK : OP_SUB_RK, pointer.RegNum, pointer.RegNum, build->GetConstantInt(1)); + } + else + { + build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, pointer.RegNum, pointer.RegNum, build->GetConstantFloat(1.)); + } + pointer.Free(build); + return ExpEmit(); } - - if (!pointer.Target) - { - build->Emit(ValueType->GetStoreOp(), pointer.RegNum, assign.RegNum, zero); - } - - pointer.Free(build); - assign.Free(build); - return out; } //========================================================================== @@ -5795,7 +5816,8 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) auto x = Condition; Condition = nullptr; delete this; - return Condition; + x->NeedResult = false; + return x; } } @@ -5805,6 +5827,7 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) if (line->ExprType != EFX_JumpStatement || static_cast(line)->Token != TK_Break) { SAFE_RESOLVE(line, ctx); + line->NeedResult = false; } } @@ -5999,6 +6022,8 @@ FxIfStatement::FxIfStatement(FxExpression *cond, FxExpression *true_part, Condition = cond; WhenTrue = true_part; WhenFalse = false_part; + if (WhenTrue != nullptr) WhenTrue->NeedResult = false; + if (WhenFalse != nullptr) WhenFalse->NeedResult = false; assert(cond != NULL); } @@ -6338,6 +6363,8 @@ FxForLoop::FxForLoop(FxExpression *init, FxExpression *condition, FxExpression * : FxLoopStatement(EFX_ForLoop, pos), Init(init), Condition(condition), Iteration(iteration), Code(code) { ValueType = TypeVoid; + if (Iteration != nullptr) Iteration->NeedResult = false; + if (Code != nullptr) Code->NeedResult = false; } FxForLoop::~FxForLoop() @@ -7139,19 +7166,19 @@ ExpEmit FxLocalVariableDeclaration::Emit(VMFunctionBuilder *build) { default: case REGT_INT: - build->Emit(OP_LK, build->GetConstantInt(constval->GetValue().GetInt()), RegNum); + build->Emit(OP_LK, RegNum, build->GetConstantInt(constval->GetValue().GetInt())); break; case REGT_FLOAT: - build->Emit(OP_LKF, build->GetConstantFloat(constval->GetValue().GetFloat()), RegNum); + build->Emit(OP_LKF, RegNum, build->GetConstantFloat(constval->GetValue().GetFloat())); break; case REGT_POINTER: - build->Emit(OP_LKP, build->GetConstantAddress(constval->GetValue().GetPointer(), ATAG_GENERIC), RegNum); + build->Emit(OP_LKP, RegNum, build->GetConstantAddress(constval->GetValue().GetPointer(), ATAG_GENERIC)); break; case REGT_STRING: - build->Emit(OP_LKS, build->GetConstantString(constval->GetValue().GetString()), RegNum); + build->Emit(OP_LKS, RegNum, build->GetConstantString(constval->GetValue().GetString())); } emitval.Free(build); } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 3fb1b1576..d099daa22 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -300,6 +300,7 @@ public: PType *ValueType = nullptr; bool isresolved = false; + bool NeedResult = true; // should be set to false if not needed and properly handled by all nodes for their subnodes to eliminate redundant code EFxType ExprType; }; @@ -1246,7 +1247,7 @@ public: FxSequence(const FScriptPosition &pos) : FxExpression(EFX_Sequence, pos) {} FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); - void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); } + void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); expr->NeedResult = false; } VMFunction *GetDirectFunction(); }; diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index a4815cb33..601fb5e9a 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -680,6 +680,7 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_Threshold, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, threshold))); symt.AddSymbol(new PField(NAME_DefThreshold, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DefThreshold))); symt.AddSymbol(new PField(NAME_Damage, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DamageVal))); + symt.AddSymbol(new PField("visdir", TypeSInt32, VARF_Native, myoffsetof(AActor, visdir))); symt.AddSymbol(new PField(NAME_VisibleStartAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartAngle))); symt.AddSymbol(new PField(NAME_VisibleStartPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartPitch))); symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); @@ -688,6 +689,7 @@ void InitThingdef() symt.AddSymbol(new PField("Pos", TypeVector3, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos))); symt.AddSymbol(new PField("Vel", TypeVector3, VARF_Native, myoffsetof(AActor, Vel))); symt.AddSymbol(new PField("Scale", TypeVector2, VARF_Native, myoffsetof(AActor, Scale))); + symt.AddSymbol(new PField("SeeState", TypeState, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, SeeState))); symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 12ce01273..747d53c3b 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -915,7 +915,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_FLOAT_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); double x = param[p].f; #define PARAM_ANGLE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); DAngle x = param[p].f; #define PARAM_STRING_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_STRING); FString x = param[p].s(); -#define PARAM_STATE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].a == NULL)); FState *x = (FState *)param[p].a; +#define PARAM_STATE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); FState *x = (FState *)param[p].a; #define PARAM_POINTER_AT(p,x,type) assert((p) < numparam); assert(param[p].Type == REGT_POINTER); type *x = (type *)param[p].a; #define PARAM_OBJECT_AT(p,x,type) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); type *x = (type *)param[p].a; assert(x == NULL || x->IsKindOf(RUNTIME_CLASS(type))); #define PARAM_CLASS_AT(p,x,base) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); base::MetaClass *x = (base::MetaClass *)param[p].a; assert(x == NULL || x->IsDescendantOf(RUNTIME_CLASS(base))); @@ -932,8 +932,8 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_FLOAT_OPT_AT(p,x) double x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_FLOAT); x = param[p].f; } else #define PARAM_ANGLE_OPT_AT(p,x) DAngle x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_FLOAT); x = param[p].f; } else #define PARAM_STRING_OPT_AT(p,x) FString x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_STRING); x = param[p].s(); } else -#define PARAM_STATE_OPT_AT(p,x) FState *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].a == NULL)); x = (FState *)param[p].a; } else -#define PARAM_STATEINFO_OPT_AT(p,x) FStateParamInfo *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATEINFO || param[p].a == NULL)); x = (FStateParamInfo *)param[p].a; } else +#define PARAM_STATE_OPT_AT(p,x) FState *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); x = (FState *)param[p].a; } else +#define PARAM_STATEINFO_OPT_AT(p,x) FStateParamInfo *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATEINFO || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); x = (FStateParamInfo *)param[p].a; } else #define PARAM_POINTER_OPT_AT(p,x,type) type *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER); x = (type *)param[p].a; } else #define PARAM_OBJECT_OPT_AT(p,x,type) type *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); x = (type *)param[p].a; assert(x == NULL || x->IsKindOf(RUNTIME_CLASS(type))); } else #define PARAM_CLASS_OPT_AT(p,x,base) base::MetaClass *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); x = (base::MetaClass *)param[p].a; assert(x == NULL || x->IsDescendantOf(RUNTIME_CLASS(base))); } else diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 1b7c4ce70..c72c2b567 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -665,6 +665,7 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c it.Code = code; it.PrintableName = name; it.Function = new VMScriptFunction; + it.Function->Name = functype->SymbolName; it.Function->ImplicitArgs = functype->GetImplicitArgs(); it.Proto = nullptr; it.FromDecorate = fromdecorate; diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 872a3ef98..027aaf7dc 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -51,6 +51,12 @@ class Actor : Thinker native native void TraceBleed(int damage, Actor missile); native bool CheckMeleeRange(); native int DamageMobj(Actor inflictor, Actor source, int damage, Name mod, int flags = 0, double angle = 0); + native double AimLineAttack(double angle, double distance, out FTranslatedLineTarget pLineTarget = null, double vrange = 0., int flags = 0, Actor target = null, Actor friender = null); + native Actor, int LineAttack(double angle, double distance, double pitch, int damage, Name damageType, class pufftype, int flags = 0, out FTranslatedLineTarget victim = null); + native bool CheckSight(Actor target, int flags = 0); + native bool HitFriend(); + native bool SetState(state st, bool nofunction = false); + // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); @@ -88,10 +94,7 @@ class Actor : Thinker native native void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); native void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); native void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - native void A_PosAttack(); native void A_Scream(); - native void A_SPosAttack(); - native void A_SPosAttackUseAtkSound(); native void A_VileChase(); native void A_VileStart(); native void A_VileTarget(class fire = "ArchvileFire"); @@ -108,8 +111,6 @@ class Actor : Thinker native native void A_FatAttack2(class spawntype = "FatShot"); native void A_FatAttack3(class spawntype = "FatShot"); native void A_BossDeath(); - native void A_CPosAttack(); - native void A_CPosRefire(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); native void A_Metal(); diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 41c4bfec9..f49264062 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -824,4 +824,41 @@ struct FStateParamInfo int mPSPIndex; } +// returned by AimLineAttack. +struct FTranslatedLineTarget +{ + Actor linetarget; + double angleFromSource; + bool unlinked; // found by a trace that went through an unlinked portal. +} +enum EAimFlags +{ + ALF_FORCENOSMART = 1, + ALF_CHECK3D = 2, + ALF_CHECKNONSHOOTABLE = 4, + ALF_CHECKCONVERSATION = 8, + ALF_NOFRIENDS = 16, + ALF_PORTALRESTRICT = 32, // only work through portals with a global offset (to be used for stuff that cannot remember the calculated FTranslatedLineTarget info) +} + +enum ELineAttackFlags +{ + LAF_ISMELEEATTACK = 1, + LAF_NORANDOMPUFFZ = 2, + LAF_NOIMPACTDECAL = 4, + LAF_NOINTERACT = 8, +} + +const MELEERANGE = 64; +const SAWRANGE = (64.+(1./65536.)); // use meleerange + 1 so the puff doesn't skip the flash (i.e. plays all states) +const MISSILERANGE = (32*64); +const PLAYERMISSILERANGE = 8192; // [RH] New MISSILERANGE for players + +enum ESightFlags +{ + SF_IGNOREVISIBILITY=1, + SF_SEEPASTSHOOTABLELINES=2, + SF_SEEPASTBLOCKEVERYTHING=4, + SF_IGNOREWATERBOUNDARY=8 +} diff --git a/wadsrc/static/zscript/doom/possessed.txt b/wadsrc/static/zscript/doom/possessed.txt index de1e50ff2..8b6612076 100644 --- a/wadsrc/static/zscript/doom/possessed.txt +++ b/wadsrc/static/zscript/doom/possessed.txt @@ -251,3 +251,93 @@ class WolfensteinSS : Actor Goto See ; } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_PosAttack() + { + if (target) + { + A_FaceTarget(); + double ang = angle; + double slope = AimLineAttack(ang, MISSILERANGE); + A_PlaySound("grunt/attack", CHAN_WEAPON); + ang += Random2[PosAttack]() * (22.5/256); + int damage = Random[PosAttack](1, 5) * 3; + LineAttack(ang, MISSILERANGE, slope, damage, "Hitscan", "Bulletpuff"); + } + } + + + private void A_SPosAttackInternal() + { + if (target) + { + A_FaceTarget(); + double bangle = angle; + double slope = AimLineAttack(bangle, MISSILERANGE); + + for (int i=0 ; i<3 ; i++) + { + double ang = bangle + Random2[SPosAttack]() * (22.5/256); + int damage = Random[SPosAttack](1, 5) * 3; + LineAttack(ang, MISSILERANGE, slope, damage, "Hitscan", "Bulletpuff"); + } + } + } + + void A_SPosAttackUseAtkSound() + { + if (target) + { + A_PlaySound(AttackSound, CHAN_WEAPON); + A_SPosAttackInternal(); + } + } + + // This version of the function, which uses a hard-coded sound, is meant for Dehacked only. + void A_SPosAttack() + { + if (target) + { + A_PlaySound("shotguy/attack", CHAN_WEAPON); + A_SPosAttackInternal(); + } + } + + void A_CPosAttack() + { + if (target) + { + if (bStealth) visdir = 1; + A_PlaySound(AttackSound, CHAN_WEAPON); + A_FaceTarget(); + double slope = AimLineAttack(angle, MISSILERANGE); + double ang = angle + Random2[SPosAttack]() * (22.5/256); + int damage = Random[CPosAttack](1, 5) * 3; + LineAttack(ang, MISSILERANGE, slope, damage, "Hitscan", "Bulletpuff"); + } + } + + void A_CPosRefire() + { + // keep firing unless target got out of sight + A_FaceTarget(); + if (Random[CPosRefire](0, 255) >= 40) + { + if (!target + || HitFriend() + || target.health <= 0 + || !CheckSight(target, SF_SEEPASTBLOCKEVERYTHING|SF_SEEPASTSHOOTABLELINES)) + { + SetState(SeeState); + } + } + } +} From e50315bd31bde9ed3f1040ed453b7bbce2bbd943 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 26 Oct 2016 13:22:36 +0200 Subject: [PATCH 115/255] - fixed: Deprecation messages should never appear in DECORATE. - removed some console message spam. --- src/d_dehacked.cpp | 7 ++++--- src/scripting/codegeneration/codegen.cpp | 2 +- src/scripting/thingdef.cpp | 2 ++ src/scripting/zscript/zcc_compile.cpp | 2 -- 4 files changed, 7 insertions(+), 6 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 97d15e4d0..064f37c02 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -73,6 +73,7 @@ #include "vm.h" #include "thingdef.h" #include "info.h" +#include "v_text.h" #include "vmbuilder.h" // [SO] Just the way Randy said to do it :) @@ -2108,7 +2109,7 @@ static int PatchCodePtrs (int dummy) if (!symname.CompareNoCase(MBFCodePointers[i].alias)) { symname = MBFCodePointers[i].name; - Printf("%s --> %s\n", MBFCodePointers[i].alias, MBFCodePointers[i].name.GetChars()); + DPrintf(DMSG_SPAMMY, "%s --> %s\n", MBFCodePointers[i].alias, MBFCodePointers[i].name.GetChars()); } } @@ -2117,7 +2118,7 @@ static int PatchCodePtrs (int dummy) PFunction *sym = dyn_cast(RUNTIME_CLASS(AStateProvider)->Symbols.FindSymbol(symname, true)); if (sym == NULL) { - Printf("Frame %d: Unknown code pointer '%s'\n", frame, Line2); + Printf(TEXTCOLOR_RED "Frame %d: Unknown code pointer '%s'\n", frame, Line2); } else { @@ -2125,7 +2126,7 @@ static int PatchCodePtrs (int dummy) unsigned numargs = sym->GetImplicitArgs(); if ((sym->Variants[0].Flags & VARF_Virtual || (args.Size() > numargs && !(args[numargs] & VARF_Optional)))) { - Printf("Frame %d: Incompatible code pointer '%s'\n", frame, Line2); + Printf(TEXTCOLOR_RED "Frame %d: Incompatible code pointer '%s'\n", frame, Line2); sym = NULL; } } diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 8fec40113..aaa6888e6 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4198,7 +4198,7 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) // 2. This is a static function // 3. This is an action function with a restricted self pointer // 4. This is a normal member or unrestricted action function. - if (vsym->Flags & VARF_Deprecated) + if ((vsym->Flags & VARF_Deprecated) && !ctx.FromDecorate) { ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", sym->SymbolName.GetChars()); } diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 2798ab633..183c3f69e 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -202,8 +202,10 @@ void LoadActors () FScriptPosition::ResetErrorCounter(); InitThingdef(); + FScriptPosition::StrictErrors = true; ParseScripts(); + FScriptPosition::StrictErrors = false; ParseAllDecorate(); FunctionBuildList.Build(); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 340a77703..afc74e75e 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1901,7 +1901,6 @@ void ZCCCompiler::InitDefaults() bag.CurrentState = 0; bag.Lumpnum = c->cls->SourceLump; bag.DropItemList = nullptr; - bag.ScriptPosition.StrictErrors = true; // The actual script position needs to be set per property. for (auto d : c->Defaults) @@ -2425,7 +2424,6 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case AST_ExprMemberAccess: { auto ema = static_cast(fcall->Function); - Printf("Member call to %s\n", FName(ema->Right).GetChars()); return new FxMemberFunctionCall(ConvertNode(ema->Left), ema->Right, ConvertNodeList(fcall->Parameters), *ast); } From 7c759f9fcfb1116c716abf4a76dc337684c11c38 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 26 Oct 2016 14:04:49 +0200 Subject: [PATCH 116/255] - removed the FxDamageValue hack and implemented it properly using FxReturnStatement. - added handling of damage functions for ZScript. --- src/namedef.h | 2 ++ src/scripting/codegeneration/codegen.h | 19 ------------------- src/scripting/decorate/thingdef_parse.cpp | 2 +- src/scripting/thingdef.cpp | 22 ++++++++++++++++++++++ src/scripting/thingdef.h | 1 + src/scripting/thingdef_properties.cpp | 14 ++------------ src/scripting/vm/vmbuilder.cpp | 4 ---- src/scripting/zscript/zcc_compile.cpp | 9 +++++++++ 8 files changed, 37 insertions(+), 36 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index 973557874..3587643e8 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -727,3 +727,5 @@ xx(__decorate_internal_int__) xx(__decorate_internal_bool__) xx(__decorate_internal_state__) xx(__decorate_internal_float__) + +xx(DamageFunction) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index d099daa22..f6468e61f 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -1531,25 +1531,6 @@ public: // //========================================================================== -class FxDamageValue : public FxExpression -{ - FxExpression *val; - -public: - - FxDamageValue(FxExpression *v); - ~FxDamageValue(); - FxExpression *Resolve(FCompileContext&); - - ExpEmit Emit(VMFunctionBuilder *build); -}; - -//========================================================================== -// -// -// -//========================================================================== - class FxNop : public FxExpression { public: diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index bd4885c87..b344a1228 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -664,7 +664,7 @@ static bool ParsePropertyParams(FScanner &sc, FPropertyInfo *prop, AActor *defau { conv.i = -1; params.Push(conv); - x = new FxDamageValue(new FxIntCast(ParseExpression(sc, bag.Info), true)); + x = ParseExpression(sc, bag.Info); sc.MustGetStringName(")"); conv.exp = x; params.Push(conv); diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 183c3f69e..8c42e8987 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -184,6 +184,28 @@ PFunction *FindClassMemberFunction(PClass *selfcls, PClass *funccls, FName name, return funcsym; } +//========================================================================== +// +// CreateDamageFunction +// +// creates a damage function from the given expression +// +//========================================================================== + +void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, bool fromDecorate) +{ + if (id == nullptr) + { + defaults->DamageFunc = nullptr; + } + else + { + auto dmg = new FxReturnStatement(new FxIntCast(id, true), id->ScriptPosition); + auto funcsym = CreateAnonymousFunction(info, TypeSInt32, VARF_Method); + defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, dmg, FStringf("%s.DamageFunction", info->TypeName.GetChars()), fromDecorate); + } +} + //========================================================================== // // LoadActors diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 44a441bee..b2d34231d 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -155,6 +155,7 @@ FName CheckCastKludges(FName in); void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc, bool *error); +void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, bool fromDecorate); //========================================================================== // diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index d3fb452cb..6f1455e43 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -647,19 +647,9 @@ DEFINE_PROPERTY(damage, X, Actor) // compatibility reasons, expressions must be enclosed within // parentheses. - // Store this expression here for now. It will be converted to a function - // later once all actors have been processed. defaults->DamageVal = dmgval; - - if (id == nullptr) - { - defaults->DamageFunc = nullptr; - } - else - { - auto funcsym = CreateAnonymousFunction(bag.Info, TypeSInt32, VARF_Method); - defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, id, FStringf("%s.DamageFunction", bag.Info->TypeName.GetChars()), !bag.fromZScript); - } + // Only DECORATE can get here with a valid expression. + CreateDamageFunction(bag.Info, defaults, id, true); } //========================================================================== diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index c72c2b567..7f8a643c6 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -684,10 +684,6 @@ void FFunctionBuildList::Build() for (auto &item : mItems) { - if (item.PrintableName.CompareNoCase("Middle.StateFunction.3") == 0) - { - int a = 0; - } assert(item.Code != NULL); // We don't know the return type in advance for anonymous functions. diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index afc74e75e..f0f884f68 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1773,8 +1773,16 @@ void ZCCCompiler::ProcessDefaultProperty(PClassActor *cls, ZCC_PropertyStmt *pro if (namenode->SiblingNext == namenode) { + if (namenode->Id == NAME_DamageFunction) + { + auto x = ConvertNode(prop->Values); + CreateDamageFunction(cls, (AActor *)bag.Info->Defaults, x, false); + return; + } + // a one-name property propname = FName(namenode->Id); + } else if (namenode->SiblingNext->SiblingNext == namenode) { @@ -1787,6 +1795,7 @@ void ZCCCompiler::ProcessDefaultProperty(PClassActor *cls, ZCC_PropertyStmt *pro return; } + FPropertyInfo *property = FindProperty(propname); if (property != nullptr && property->category != CAT_INFO) From a166183ab49b07d6e0d9284761df918df74b4453 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 26 Oct 2016 14:15:11 +0200 Subject: [PATCH 117/255] -fixed type handling for varargs (i.e. A_Jump.) --- src/scripting/codegeneration/codegen.cpp | 64 +++++------------------- 1 file changed, 12 insertions(+), 52 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index aaa6888e6..2bf1fedc8 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1067,6 +1067,7 @@ FxTypeCast::FxTypeCast(FxExpression *x, PType *type, bool nowarn) { basex = x; ValueType = type; + assert(ValueType != nullptr); } //========================================================================== @@ -5410,9 +5411,19 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) if (ArgList != NULL) { + bool foundvarargs = false; + PType * type = nullptr; for (unsigned i = 0; i < ArgList->Size(); i++) { - FxExpression *x = new FxTypeCast((*ArgList)[i], argtypes[i + implicit], false); + // Varargs must all have the same type as the last typed argument. A_Jump is the only function using it. + if (!foundvarargs) + { + if (argtypes[i + implicit] == nullptr) foundvarargs = true; + else type = argtypes[i + implicit]; + } + assert(type != nullptr); + + FxExpression *x = new FxTypeCast((*ArgList)[i], type, false); x = x->Resolve(ctx); failed |= (x == nullptr); (*ArgList)[i] = x; @@ -7062,57 +7073,6 @@ ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) return dest; } -//========================================================================== -// -// -// -//========================================================================== - -FxDamageValue::FxDamageValue(FxExpression *v) -: FxExpression(EFX_DamageValue, v->ScriptPosition) -{ - val = v; - ValueType = TypeVoid; -} - -FxDamageValue::~FxDamageValue() -{ - SAFE_DELETE(val); - -} - -FxExpression *FxDamageValue::Resolve(FCompileContext &ctx) -{ - CHECKRESOLVED(); - SAFE_RESOLVE(val, ctx) - - if (!val->IsNumeric()) - { - ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); - delete this; - return NULL; - } - return this; -} - -// This is a highly-specialized "expression" type that emits a complete function. -ExpEmit FxDamageValue::Emit(VMFunctionBuilder *build) -{ - if (val->isConstant()) - { - build->EmitRetInt(0, false, static_cast(val)->GetValue().Int); - } - else - { - ExpEmit emitval = val->Emit(build); - assert(emitval.RegType == REGT_INT); - build->Emit(OP_RET, 0, REGT_INT | (emitval.Konst ? REGT_KONST : 0), emitval.RegNum); - } - build->Emit(OP_RETI, 1 | RET_FINAL, true); - - return ExpEmit(); -} - //========================================================================== // // declares a single local variable (no arrays) From d32d52c0b9e55f375c2b52a3d8da7bca617be2d2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 26 Oct 2016 17:21:25 +0200 Subject: [PATCH 118/255] - scriptified a_spidermaster.cpp. - fixed bad assert in XOR_RK instruction. --- src/CMakeLists.txt | 1 - src/g_doom/a_doommisc.cpp | 1 - src/g_doom/a_spidermaster.cpp | 41 --------------------- src/scripting/vm/vmexec.h | 2 +- wadsrc/static/zscript/actor.txt | 2 - wadsrc/static/zscript/doom/spidermaster.txt | 31 ++++++++++++++++ 6 files changed, 32 insertions(+), 46 deletions(-) delete mode 100644 src/g_doom/a_spidermaster.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index a5164e84b..395e72e2c 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -844,7 +844,6 @@ set( NOT_COMPILED_SOURCE_FILES g_doom/a_painelemental.cpp g_doom/a_revenant.cpp g_doom/a_scriptedmarine.cpp - g_doom/a_spidermaster.cpp g_heretic/a_chicken.cpp g_heretic/a_dsparil.cpp g_heretic/a_hereticartifacts.cpp diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 4c8be07f1..df42bfa7b 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -30,7 +30,6 @@ #include "a_lostsoul.cpp" #include "a_painelemental.cpp" #include "a_revenant.cpp" -#include "a_spidermaster.cpp" #include "a_scriptedmarine.cpp" // The barrel of green goop ------------------------------------------------ diff --git a/src/g_doom/a_spidermaster.cpp b/src/g_doom/a_spidermaster.cpp deleted file mode 100644 index 37d0deb18..000000000 --- a/src/g_doom/a_spidermaster.cpp +++ /dev/null @@ -1,41 +0,0 @@ -/* -#include "templates.h" -#include "actor.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "a_action.h" -#include "vm.h" -*/ - -static FRandom pr_spidrefire ("SpidRefire"); - -DEFINE_ACTION_FUNCTION(AActor, A_SpidRefire) -{ - PARAM_SELF_PROLOGUE(AActor); - - // keep firing unless target got out of sight - A_FaceTarget (self); - - if (pr_spidrefire() < 10) - return 0; - - if (!self->target - || P_HitFriend (self) - || self->target->health <= 0 - || !P_CheckSight (self, self->target, SF_SEEPASTBLOCKEVERYTHING|SF_SEEPASTSHOOTABLELINES)) - { - self->SetState (self->SeeState); - } - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_Metal) -{ - PARAM_SELF_PROLOGUE(AActor); - - S_Sound (self, CHAN_BODY, "spider/walk", 1, ATTN_IDLE); - A_Chase (stack, self); - return 0; -} diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 2ddc50599..65891493e 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -924,7 +924,7 @@ begin: reg.d[a] = reg.d[B] ^ reg.d[C]; NEXTOP; OP(XOR_RK): - ASSERTD(a); ASSERTD(B); ASSERTD(C); + ASSERTD(a); ASSERTD(B); ASSERTKD(C); reg.d[a] = reg.d[B] ^ konstd[C]; NEXTOP; diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 027aaf7dc..02cb4f3cf 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -113,8 +113,6 @@ class Actor : Thinker native native void A_BossDeath(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); - native void A_Metal(); - native void A_SpidRefire(); native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); native void A_DualPainAttack(class spawntype = "LostSoul"); native void A_PainDie(class spawntype = "LostSoul"); diff --git a/wadsrc/static/zscript/doom/spidermaster.txt b/wadsrc/static/zscript/doom/spidermaster.txt index b9f060068..9a72a2bbe 100644 --- a/wadsrc/static/zscript/doom/spidermaster.txt +++ b/wadsrc/static/zscript/doom/spidermaster.txt @@ -60,3 +60,34 @@ class SpiderMastermind : Actor Stop; } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + void A_SpidRefire() + { + // keep firing unless target got out of sight + A_FaceTarget(); + if (Random[CPosRefire](0, 255) >= 10) + { + if (!target + || HitFriend() + || target.health <= 0 + || !CheckSight(target, SF_SEEPASTBLOCKEVERYTHING|SF_SEEPASTSHOOTABLELINES)) + { + SetState(SeeState); + } + } + } + + void A_Metal() + { + A_PlaySound("spider/walk", CHAN_BODY, 1, false, ATTN_IDLE); + A_Chase(); + } +} From 66b1f36e563233b80cae90fa9845cb6fb24a4e59 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 27 Oct 2016 01:30:34 +0200 Subject: [PATCH 119/255] - actually evaluate the default parameters and store them in the VMFunction. - disabled the assert in PType::GetRegType. This assert blocks any use to check for types that are incompatible with function parameters. - pass the default parameter constants to the native functions. At the moment this is not used yet. - use the function defaults to complete argument lists to script functions. - fixed all default values that got flagged by the expression evaluator as non-constant. Most were state labels and colors which were defaulted to "". The proper value is null for states and 0 for colors. - also replaced all "" defaults for names with "none". --- src/dobjtype.cpp | 2 +- src/scripting/codegeneration/codegen.cpp | 16 ++--- src/scripting/codegeneration/codegen.h | 2 +- src/scripting/decorate/thingdef_exp.cpp | 2 +- src/scripting/thingdef_data.cpp | 4 +- src/scripting/vm/vm.h | 61 ++++++++++++----- src/scripting/vm/vmexec.cpp | 7 +- src/scripting/vm/vmexec.h | 4 +- src/scripting/vm/vmframe.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 80 +++++++++++++++++++--- wadsrc/static/zscript/actor.txt | 24 +++---- wadsrc/static/zscript/shared/inventory.txt | 10 +-- 12 files changed, 152 insertions(+), 62 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 3bce521c8..3f5b734c4 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -521,7 +521,7 @@ int PType::GetMoveOp() const int PType::GetRegType() const { - assert(0 && "No register for this type"); + //assert(0 && "No register for this type"); // wrong place for this assert, it makes it impossible to use this function to check for bad types. return REGT_NIL; } diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 2bf1fedc8..d4ee11383 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -96,7 +96,7 @@ FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret, bool fromdecor if (fnc != nullptr) Class = fnc->OwningClass; } -FCompileContext::FCompileContext(PClass *cls) : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(true) // only used by DECORATE constants. +FCompileContext::FCompileContext(PClass *cls, bool fromdecorate) : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(fromdecorate) { } @@ -3745,7 +3745,7 @@ FxExpression *FxRandom::Resolve(FCompileContext &ctx) // //========================================================================== -int DecoRandom(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int DecoRandom(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam >= 1 && numparam <= 3); FRandom *rng = reinterpret_cast(param[0].a); @@ -3995,7 +3995,7 @@ FxFRandom::FxFRandom(FRandom *r, FxExpression *mi, FxExpression *ma, const FScri // //========================================================================== -int DecoFRandom(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int DecoFRandom(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam == 1 || numparam == 3); FRandom *rng = reinterpret_cast(param[0].a); @@ -5255,7 +5255,7 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) // //========================================================================== -int DecoCallLineSpecial(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int DecoCallLineSpecial(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam > 2 && numparam < 8); assert(param[0].Type == REGT_INT); @@ -6702,7 +6702,7 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) // //========================================================================== -int DecoNameToClass(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int DecoNameToClass(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam == 2); assert(numret == 1); @@ -6842,7 +6842,7 @@ static bool VerifyJumpTarget(AActor *stateowner, FStateParamInfo *stateinfo, int return false; } -static int DecoHandleRuntimeState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +static int DecoHandleRuntimeState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { PARAM_PROLOGUE; PARAM_OBJECT(stateowner, AActor); @@ -7008,7 +7008,7 @@ static int DoFindState(VMFrameStack *stack, VMValue *param, int numparam, VMRetu } // Find a state with any number of dots in its name. -int BuiltinFindMultiNameState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int BuiltinFindMultiNameState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam > 1); assert(numret == 1); @@ -7024,7 +7024,7 @@ int BuiltinFindMultiNameState(VMFrameStack *stack, VMValue *param, int numparam, } // Find a state without any dots in its name. -int BuiltinFindSingleNameState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret) +int BuiltinFindSingleNameState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam == 2); assert(numret == 1); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index f6468e61f..a55491a0b 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -77,7 +77,7 @@ struct FCompileContext TDeletingArray FunctionArgs; FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate); - FCompileContext(PClass *cls); // only to be used to resolve constants! + FCompileContext(PClass *cls, bool fromdecorate); // only to be used to resolve constants! PSymbol *FindInClass(FName identifier, PSymbolTable *&symt); PSymbol *FindInSelfClass(FName identifier, PSymbolTable *&symt); diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 84e1200e9..c63677e0c 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -87,7 +87,7 @@ FxExpression *ParseExpression (FScanner &sc, PClassActor *cls, bool mustresolve) if (mustresolve) { - FCompileContext ctx(cls); + FCompileContext ctx(cls, true); data = data->Resolve(ctx); } diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 601fb5e9a..e04935f58 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -667,8 +667,8 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_MomX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.X))); symt.AddSymbol(new PField(NAME_MomY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Y))); symt.AddSymbol(new PField(NAME_MomZ, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Z))); - symt.AddSymbol(new PField(NAME_ScaleX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Scale.X))); - symt.AddSymbol(new PField(NAME_ScaleY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Scale.Y))); + symt.AddSymbol(new PField(NAME_ScaleX, TypeFloat64, VARF_Native|VARF_Deprecated, myoffsetof(AActor, Scale.X))); + symt.AddSymbol(new PField(NAME_ScaleY, TypeFloat64, VARF_Native|VARF_Deprecated, myoffsetof(AActor, Scale.Y))); symt.AddSymbol(new PField(NAME_Score, TypeSInt32, VARF_Native, myoffsetof(AActor, Score))); symt.AddSymbol(new PField(NAME_Accuracy, TypeSInt32, VARF_Native, myoffsetof(AActor, accuracy))); symt.AddSymbol(new PField(NAME_Stamina, TypeSInt32, VARF_Native, myoffsetof(AActor, stamina))); diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 747d53c3b..c6ff99d48 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -173,20 +173,6 @@ enum EVMAbortException X_BAD_SELF, }; -class VMFunction : public DObject -{ - DECLARE_ABSTRACT_CLASS(VMFunction, DObject); - HAS_OBJECT_POINTERS; -public: - bool Native; - BYTE ImplicitArgs = 0; // either 0 for static, 1 for method or 3 for action - FName Name; - - class PPrototype *Proto; - - VMFunction(FName name = NAME_None) : Native(false), ImplicitArgs(0), Name(name), Proto(NULL) {} -}; - enum EVMOpMode { MODE_ASHIFT = 0, @@ -642,6 +628,21 @@ do_double: if (inexact) } }; +class VMFunction : public DObject +{ + DECLARE_ABSTRACT_CLASS(VMFunction, DObject); + HAS_OBJECT_POINTERS; +public: + bool Native; + BYTE ImplicitArgs = 0; // either 0 for static, 1 for method or 3 for action + FName Name; + TArray Defaults; + + class PPrototype *Proto; + + VMFunction(FName name = NAME_None) : Native(false), ImplicitArgs(0), Name(name), Proto(NULL) {} +}; + // VM frame layout: // VMFrame header // parameter stack - 16 byte boundary, 16 bytes each @@ -829,7 +830,7 @@ class VMNativeFunction : public VMFunction { DECLARE_CLASS(VMNativeFunction, VMFunction); public: - typedef int (*NativeCallType)(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret); + typedef int (*NativeCallType)(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret); VMNativeFunction() : NativeCall(NULL) { Native = true; } VMNativeFunction(NativeCallType call) : NativeCall(call) { Native = true; } @@ -900,8 +901,8 @@ void VMDumpConstants(FILE *out, const VMScriptFunction *func); void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction *func); // Use this in the prototype for a native function. -#define VM_ARGS VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret -#define VM_ARGS_NAMES stack, param, numparam, ret, numret +#define VM_ARGS VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret +#define VM_ARGS_NAMES stack, param, defaultparam, numparam, ret, numret // Use these to collect the parameters in a native function. // variable name at position

@@ -924,6 +925,16 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction // PARAM_INT_OPT(0,myint) { myint = 55; } // Just make sure to fill it in when using these macros, because the compiler isn't likely // to give useful error messages if you don't. +#define PARAM_EXISTS ((p) < numparam && param[p].Type != REGT_NIL) +#define ASSERTINT(p) assert((p).Type == REGT_INT) +#define ASSERTFLOAT(p) assert((p).Type == REGT_FLOAT) +#define ASSERTSTRING(p) assert((p).Type == REGT_STRING) +#define ASSERTOBJECT(p) assert((p).Type == REGT_POINTER && (p).atag == ATAG_OBJECT) +#define ASSERTPOINTER(p) assert((p).Type == REGT_POINTER && (p).atag == ATAG_GENERIC) +#define ASSERTSTATE(p) assert((p).Type == REGT_POINTER && ((p).atag == ATAG_GENERIC || (p).atag == ATAG_STATE)) + +#define PARAM_INT_DEF_AT(p,x) int x; if (PARAM_EXISTS) { ASSERTINT(param[p]); x = param[p].i; } else { ASSERTINT(defaultparam[p]); x = defaultparam[p].i; } + #define PARAM_INT_OPT_AT(p,x) int x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = param[p].i; } else #define PARAM_BOOL_OPT_AT(p,x) bool x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = !!param[p].i; } else #define PARAM_NAME_OPT_AT(p,x) FName x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = ENamedName(param[p].i); } else @@ -954,6 +965,20 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_OBJECT(x,type) ++paramnum; PARAM_OBJECT_AT(paramnum,x,type) #define PARAM_CLASS(x,base) ++paramnum; PARAM_CLASS_AT(paramnum,x,base) +#define PARAM_INT_DEF(x) ++paramnum; PARAM_INT_DEF_AT(paramnum,x) +#define PARAM_BOOL_DEF(x) ++paramnum; PARAM_BOOL_DEF_AT(paramnum,x) +#define PARAM_NAME_DEF(x) ++paramnum; PARAM_NAME_DEF_AT(paramnum,x) +#define PARAM_SOUND_DEF(x) ++paramnum; PARAM_SOUND_DEF_AT(paramnum,x) +#define PARAM_COLOR_DEF(x) ++paramnum; PARAM_COLOR_DEF_AT(paramnum,x) +#define PARAM_FLOAT_DEF(x) ++paramnum; PARAM_FLOAT_DEF_AT(paramnum,x) +#define PARAM_ANGLE_DEF(x) ++paramnum; PARAM_ANGLE_DEF_AT(paramnum,x) +#define PARAM_STRING_DEF(x) ++paramnum; PARAM_STRING_DEF_AT(paramnum,x) +#define PARAM_STATE_DEF(x) ++paramnum; PARAM_STATE_DEF_AT(paramnum,x) +#define PARAM_STATEINFO_DEF(x) ++paramnum; PARAM_STATEINFO_DEF_AT(paramnum,x) +#define PARAM_POINTER_DEF(x,type) ++paramnum; PARAM_POINTER_DEF_AT(paramnum,x,type) +#define PARAM_OBJECT_DEF(x,type) ++paramnum; PARAM_OBJECT_DEF_AT(paramnum,x,type) +#define PARAM_CLASS_DEF(x,base) ++paramnum; PARAM_CLASS_DEF_AT(paramnum,x,base) + #define PARAM_INT_OPT(x) ++paramnum; PARAM_INT_OPT_AT(paramnum,x) #define PARAM_BOOL_OPT(x) ++paramnum; PARAM_BOOL_OPT_AT(paramnum,x) #define PARAM_NAME_OPT(x) ++paramnum; PARAM_NAME_OPT_AT(paramnum,x) @@ -968,7 +993,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_OBJECT_OPT(x,type) ++paramnum; PARAM_OBJECT_OPT_AT(paramnum,x,type) #define PARAM_CLASS_OPT(x,base) ++paramnum; PARAM_CLASS_OPT_AT(paramnum,x,base) -typedef int(*actionf_p)(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, int numret);/*(VM_ARGS)*/ +typedef int(*actionf_p)(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret);/*(VM_ARGS)*/ struct AFuncDesc { diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index fb428f781..b8078f071 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -188,13 +188,14 @@ void VMFillParams(VMValue *params, VMFrame *callee, int numparam) const VMRegisters calleereg(callee); assert(calleefunc != NULL && !calleefunc->Native); - assert(numparam == calleefunc->NumArgs); + assert(numparam == calleefunc->NumArgs || ((int)calleefunc->Defaults.Size() == numparam)); assert(REGT_INT == 0 && REGT_FLOAT == 1 && REGT_STRING == 2 && REGT_POINTER == 3); regd = regf = regs = rega = 0; - for (int i = 0; i < numparam; ++i) + for (int i = 0; i < calleefunc->NumArgs; ++i) { - VMValue &p = params[i]; + // get all actual parameters and fill the rest from the defaults. + VMValue &p = i < numparam? params[i] : calleefunc->Defaults[i]; if (p.Type < REGT_STRING) { if (p.Type == REGT_INT) diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 65891493e..a5ad3ac00 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -506,7 +506,7 @@ begin: FillReturns(reg, f, returns, pc+1, C); if (call->Native) { - numret = static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, B, returns, C); + numret = static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, call->Defaults, B, returns, C); } else { @@ -550,7 +550,7 @@ begin: if (call->Native) { - return static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, B, ret, numret); + return static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, call->Defaults, B, ret, numret); } else { // FIXME: Not a true tail call diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index e5e58aa47..bf2159fa1 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -415,7 +415,7 @@ int VMFrameStack::Call(VMFunction *func, VMValue *params, int numparams, VMRetur { if (func->Native) { - return static_cast(func)->NativeCall(this, params, numparams, results, numresults); + return static_cast(func)->NativeCall(this, params, func->Defaults, numparams, results, numresults); } else { diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f0f884f68..3a1e734a4 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1952,6 +1952,7 @@ void ZCCCompiler::InitFunctions() TArray rets(1); TArray args; TArray argflags; + TArray argdefaults; TArray argnames; for (auto c : Classes) @@ -1961,6 +1962,7 @@ void ZCCCompiler::InitFunctions() rets.Clear(); args.Clear(); argflags.Clear(); + bool hasdefault = false; // For the time being, let's not allow overloading. This may be reconsidered later but really just adds an unnecessary amount of complexity here. if (AddTreeNode(f->Name, f, &c->TreeNodes, false)) { @@ -2018,36 +2020,96 @@ void ZCCCompiler::InitFunctions() } } SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags); + argdefaults.Resize(argnames.Size()); auto p = f->Params; if (p != nullptr) { do { + VMValue vmval; // default is REGT_NIL which means 'no default value' here. if (p->Type != nullptr) { auto type = DetermineType(c->Type(), p, f->Name, p->Type, false, false); int flags = 0; if (p->Flags & ZCC_In) flags |= VARF_In; if (p->Flags & ZCC_Out) flags |= VARF_Out; - if (p->Default != nullptr) + if ((type->IsA(RUNTIME_CLASS(PStruct))) || (flags & VARF_Out)) { - auto val = Simplify(p->Default, &c->Type()->Symbols, true); - flags |= VARF_Optional; - if (val->Operation != PEX_ConstValue) + // 'out' parameters and all structs except vectors are passed by reference + if ((flags & VARF_Out) || (type != TypeVector2 && type != TypeVector3)) { - Error(c->cls, "Default parameter %s is not constant in %s", FName(p->Name).GetChars(), FName(f->Name).GetChars()); + type = NewPointer(type); } - // Todo: Store and handle the default value (native functions will discard it anyway but for scripted ones this should be done decently.) + } + if (type->GetRegType() == REGT_NIL && type != TypeVector2 && type != TypeVector3) + { + Error(p, "Invalid type %s for function parameter", type->DescriptiveName()); + } + else if (p->Default != nullptr) + { + flags |= VARF_Optional; + // The simplifier is not suited to convert the constant into something usable. + // All it does is reduce the expression to a constant but we still got to do proper type checking and conversion. + // It will also lose important type info about enums, once these get implemented + // The code generator can do this properly for us. + FxExpression *x = new FxTypeCast(ConvertNode(p->Default), type, false); + FCompileContext ctx(c->Type(), false); + x = x->Resolve(ctx); + + if (x != nullptr) + { + if (!x->isConstant()) + { + Error(p, "Default parameter %s is not constant in %s", FName(p->Name).GetChars(), FName(f->Name).GetChars()); + } + else if (x->ValueType != type) + { + Error(p, "Default parameter %s could not be converted to target type %s", FName(p->Name).GetChars(), c->Type()->TypeName.GetChars()); + } + else + { + auto cnst = static_cast(x); + hasdefault = true; + switch (type->GetRegType()) + { + case REGT_INT: + vmval = cnst->GetValue().GetInt(); + break; + + case REGT_FLOAT: + vmval = cnst->GetValue().GetFloat(); + break; + + case REGT_POINTER: + if (type->IsKindOf(RUNTIME_CLASS(PClassPointer))) + vmval = (DObject*)cnst->GetValue().GetPointer(); + else + vmval = cnst->GetValue().GetPointer(); + break; + + case REGT_STRING: + vmval = cnst->GetValue().GetString(); + break; + + default: + assert(0 && "no valid type for constant"); + break; + } + } + } + if (x != nullptr) delete x; } // TBD: disallow certain types? For now, let everything pass that isn't an array. args.Push(type); argflags.Push(flags); + } else { args.Push(nullptr); argflags.Push(0); } + argdefaults.Push(vmval); p = static_cast(p->SiblingNext); } while (p != f->Params); } @@ -2064,9 +2126,11 @@ void ZCCCompiler::InitFunctions() sym->Variants[0].Implementation = FunctionBuildList.AddFunction(sym, code, FStringf("%s.%s", c->Type()->TypeName.GetChars(), FName(f->Name).GetChars()), false); } } - + if (sym->Variants[0].Implementation != nullptr && hasdefault) // do not copy empty default lists, they only waste space and processing time. + { + sym->Variants[0].Implementation->Defaults = std::move(argdefaults); + } // todo: Check inheritance. - // todo: Process function bodies. } } } diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 02cb4f3cf..706acaee7 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -90,7 +90,7 @@ class Actor : Thinker native native void A_NoBlocking(); native void A_XScream(); native void A_Look(); - native void A_Chase(state melee = "*", state missile = "none", int flags = 0); + native void A_Chase(state melee = null, state missile = null, int flags = 0); native void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); native void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); native void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); @@ -203,8 +203,8 @@ class Actor : Thinker native native void A_SeekerMissile(int threshold, int turnmax, int flags = 0, int chance = 50, int distance = 10); native state A_Jump(int chance = 256, state label, ...); native void A_CustomMissile(class missiletype, float spawnheight = 32, float spawnofs_xy = 0, float angle = 0, int flags = 0, float pitch = 0, int ptr = AAPTR_TARGET); - native void A_CustomBulletAttack(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); - native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = "", color color2 = "", int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); + native void A_CustomBulletAttack(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); + native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = 0, color color2 = 0, int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); native state A_JumpIfHealthLower(int health, state label, int ptr_selector = AAPTR_DEFAULT); native state A_JumpIfCloser(float distance, state label, bool noz = false); native state A_JumpIfTracerCloser(float distance, state label, bool noz = false); @@ -217,8 +217,8 @@ class Actor : Thinker native native bool A_TakeInventory(class itemtype, int amount = 0, int flags = 0, int giveto = AAPTR_DEFAULT); action native bool A_SpawnItem(class itemtype = "Unknown", float distance = 0, float zheight = 0, bool useammo = true, bool transfer_translation = false); native bool A_SpawnItemEx(class itemtype, float xofs = 0, float yofs = 0, float zofs = 0, float xvel = 0, float yvel = 0, float zvel = 0, float angle = 0, int flags = 0, int failchance = 0, int tid=0); - native void A_Print(string whattoprint, float time = 0, name fontname = ""); - native void A_PrintBold(string whattoprint, float time = 0, name fontname = ""); + native void A_Print(string whattoprint, float time = 0, name fontname = "none"); + native void A_PrintBold(string whattoprint, float time = 0, name fontname = "none"); native void A_Log(string whattoprint); native void A_LogInt(int whattoprint); native void A_LogFloat(float whattoprint); @@ -234,7 +234,7 @@ class Actor : Thinker native native state A_CheckSight(state label); native void A_ExtChase(bool usemelee, bool usemissile, bool playactive = true, bool nightmarefast = false); native void A_DropInventory(class itemtype); - native void A_SetBlend(color color1, float alpha, int tics, color color2 = ""); + native void A_SetBlend(color color1, float alpha, int tics, color color2 = 0); deprecated native void A_ChangeFlag(string flagname, bool value); deprecated native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); native void A_ChangeCountFlags(int kill = FLAG_NO_CHANGE, int item = FLAG_NO_CHANGE, int secret = FLAG_NO_CHANGE); @@ -247,8 +247,8 @@ class Actor : Thinker native native state A_CheckCeiling(state label); native state A_PlayerSkinCheck(state label); deprecated native void A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); - native state, bool A_Teleport(state teleportstate = "", class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); - native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = "", float heightoffset = 0, float radiusoffset = 0, float pitch = 0); + native state, bool A_Teleport(state teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); + native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = null, float heightoffset = 0, float radiusoffset = 0, float pitch = 0); action native bool A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); @@ -257,8 +257,8 @@ class Actor : Thinker native native bool A_GiveToTarget(class itemtype, int amount = 0, int forward_ptr = AAPTR_DEFAULT); native bool A_TakeFromTarget(class itemtype, int amount = 0, int flags = 0, int forward_ptr = AAPTR_DEFAULT); native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = "None", name species = "None", float mindist = 0, int limit = 0); - native state A_CheckSpecies(state jump, name species = "", int ptr = AAPTR_DEFAULT); - native void A_CountdownArg(int argnum, state targstate = ""); + native state A_CheckSpecies(state jump, name species = 'none', int ptr = AAPTR_DEFAULT); + native void A_CountdownArg(int argnum, state targstate = null); native void A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); native void A_CustomComboAttack(class missiletype, float spawnheight, int damage, sound meleesound = "", name damagetype = "none", bool bleed = true); native void A_Burst(class chunktype); @@ -271,7 +271,7 @@ class Actor : Thinker native native void A_BarrelDestroy(); native void A_QueueCorpse(); native void A_DeQueueCorpse(); - native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = ""); + native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = null); native void A_ClearLastHeard(); native void A_ClearTarget(); native state A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); @@ -357,7 +357,7 @@ class Actor : Thinker native native void A_TransferPointer(int ptr_source, int ptr_recepient, int sourcefield, int recepientfield=AAPTR_DEFAULT, int flags=0); native void A_CopyFriendliness(int ptr_source = AAPTR_MASTER); - action native bool A_Overlay(int layer, state start = "", bool nooverride = false); + action native bool A_Overlay(int layer, state start = null, bool nooverride = false); native void A_WeaponOffset(float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayOffset(int layer = PSP_WEAPON, float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayFlags(int layer, int flags, bool set); diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index 2fde3b3cd..4a9cde740 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -42,10 +42,10 @@ class Inventory : Actor native class StateProvider : Inventory native { action native state A_JumpIfNoAmmo(state label); - action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = "", sound MissSound = ""); - action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = "", float Spawnheight = 32, float Spawnofs_xy = 0); + action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = 0, sound MissSound = ""); + action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); - action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = "", color color2 = "", int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); + action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = 0, color color2 = 0, int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); native void A_Light(int extralight); native void A_Light0(); native void A_Light1(); @@ -71,10 +71,10 @@ class StateProvider : Inventory native native void A_BFGsound(); action native void A_FireBFG(); action native void A_FireOldBFG(); - native void A_ReFire(state flash = ""); + native void A_ReFire(state flash = null); native void A_ClearReFire(); native void A_CheckReload(); - native void A_GunFlash(state flash = "", int flags = 0); + native void A_GunFlash(state flash = null, int flags = 0); action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); native state A_CheckForReload(int counter, state label, bool dontincrement = false); native void A_ResetReloadCounter(); From 948ef62fcdbf8740e7e1a83fd43057095679a0b1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 27 Oct 2016 15:53:53 +0200 Subject: [PATCH 120/255] - use the function defaults from the script instead of explicitly setting them again in the code. This is a needless cause of potential errors and since the values are readily available now it's better to use them in the functions. - fixed: ZCCCompiler did not process array access nodes. - fixed: Function argument names were not placed in the destination list by the compiler. - scriptified several trivial functions from p_actionfunctions.cpp. --- src/info.h | 17 - src/p_actionfunctions.cpp | 1298 ++++++----------- src/p_maputl.cpp | 15 + src/scripting/codegeneration/codegen.cpp | 81 +- src/scripting/codegeneration/codegen.h | 6 +- src/scripting/thingdef_data.cpp | 24 +- src/scripting/vm/vm.h | 33 +- src/scripting/vm/vmexec.h | 4 +- src/scripting/zscript/zcc_compile.cpp | 15 +- src/scripting/zscript/zcc_compile.h | 4 +- wadsrc/static/zscript/actor.txt | 200 ++- .../static/zscript/heretic/hereticweaps.txt | 4 +- wadsrc/static/zscript/hexen/wraith.txt | 2 +- 13 files changed, 707 insertions(+), 996 deletions(-) diff --git a/src/info.h b/src/info.h index 5e1d045f2..2155734ad 100644 --- a/src/info.h +++ b/src/info.h @@ -356,21 +356,4 @@ int GetSpriteIndex(const char * spritename, bool add = true); TArray &MakeStateNameList(const char * fname); void AddStateLight(FState *state, const char *lname); -// Standard parameters for all action functons -// self - Actor this action is to operate on (player if a weapon) -// stateowner - Actor this action really belongs to (may be an item) -// callingstate - State this action was called from -#define PARAM_ACTION_PROLOGUE(type) \ - PARAM_PROLOGUE; \ - PARAM_OBJECT (self, type); \ - PARAM_OBJECT_OPT (stateowner, AActor) { stateowner = self; } \ - PARAM_STATEINFO_OPT (stateinfo) { stateinfo = nullptr; } \ - -// Number of action paramaters -#define NAP 3 - -#define PARAM_SELF_PROLOGUE(type) \ - PARAM_PROLOGUE; \ - PARAM_OBJECT(self, type); - #endif // __INFO_H__ diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 57c676801..a4f49607f 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -197,6 +197,22 @@ bool ACustomInventory::CallStateChain (AActor *actor, FState *state) return !!result; } + +//========================================================================== +// +// GetPointer +// +// resolve AAPTR_* +// +//========================================================================== + +DEFINE_ACTION_FUNCTION(AActor, GetPointer) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_INT(ptr); + ACTION_RETURN_OBJECT(COPY_AAPTR(self, ptr)); +} + //========================================================================== // // CheckClass @@ -212,8 +228,8 @@ DEFINE_ACTION_FUNCTION(AActor, CheckClass) assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (checktype, AActor); - PARAM_INT_OPT (pick_pointer) { pick_pointer = AAPTR_DEFAULT; } - PARAM_BOOL_OPT (match_superclass) { match_superclass = false; } + PARAM_INT_DEF (pick_pointer); + PARAM_BOOL_DEF (match_superclass); self = COPY_AAPTR(self, pick_pointer); if (self == NULL) @@ -248,8 +264,8 @@ DEFINE_ACTION_FUNCTION(AActor, GetMissileDamage) assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); PARAM_INT(mask); - PARAM_INT(add) - PARAM_INT_OPT(pick_pointer) { pick_pointer = AAPTR_DEFAULT; } + PARAM_INT(add); + PARAM_INT_DEF(pick_pointer); self = COPY_AAPTR(self, pick_pointer); if (self == NULL) @@ -265,29 +281,6 @@ DEFINE_ACTION_FUNCTION(AActor, GetMissileDamage) return 0; } -//========================================================================== -// -// IsPointerEqual -// -// NON-ACTION function to check if two pointers are equal. -// -//========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, IsPointerEqual) -{ - if (numret > 0) - { - assert(ret != NULL); - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT (ptr_select1); - PARAM_INT (ptr_select2); - - ret->SetInt(COPY_AAPTR(self, ptr_select1) == COPY_AAPTR(self, ptr_select2)); - return 1; - } - return 0; -} - //========================================================================== // // CountInv @@ -303,7 +296,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, CountInv) assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(itemtype, AInventory); - PARAM_INT_OPT(pick_pointer) { pick_pointer = AAPTR_DEFAULT; } + PARAM_INT_DEF(pick_pointer); self = COPY_AAPTR(self, pick_pointer); if (self == NULL || itemtype == NULL) @@ -334,7 +327,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetDistance) assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL(checkz); - PARAM_INT_OPT(ptr) { ptr = AAPTR_TARGET; } + PARAM_INT_DEF(ptr); AActor *target = COPY_AAPTR(self, ptr); @@ -377,7 +370,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetAngle) assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); PARAM_INT(flags); - PARAM_INT_OPT(ptr) { ptr = AAPTR_TARGET; } + PARAM_INT_DEF(ptr) AActor *target = COPY_AAPTR(self, ptr); @@ -442,7 +435,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetSpriteAngle) { assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(ptr); AActor *target = COPY_AAPTR(self, ptr); if (target == nullptr) @@ -471,7 +464,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetSpriteRotation) { assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(ptr); AActor *target = COPY_AAPTR(self, ptr); if (target == nullptr) @@ -511,11 +504,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetZAt) { assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(px) { px = 0.; } - PARAM_FLOAT_OPT(py) { py = 0.; } - PARAM_ANGLE_OPT(angle) { angle = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(pick_pointer) { pick_pointer = AAPTR_DEFAULT; } + PARAM_FLOAT_DEF(px); + PARAM_FLOAT_DEF(py); + PARAM_ANGLE_DEF(angle); + PARAM_INT_DEF(flags); + PARAM_INT_DEF(pick_pointer); AActor *mobj = COPY_AAPTR(self, pick_pointer); if (mobj == nullptr) @@ -599,7 +592,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetCrouchFactor) { assert(ret != NULL); PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(ptr) { ptr = AAPTR_PLAYER1; } + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); if (!mobj || !mobj->player) @@ -660,7 +653,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, GetPlayerInput) assert(ret != nullptr); PARAM_SELF_PROLOGUE(AActor); PARAM_INT (inputnum); - PARAM_INT_OPT (ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -693,8 +686,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, CountProximity) PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(classname, AActor); PARAM_FLOAT(distance); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(flags); + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); if (mobj == nullptr) @@ -770,9 +763,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RearrangePointers) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (ptr_target); - PARAM_INT_OPT (ptr_master) { ptr_master = AAPTR_DEFAULT; } - PARAM_INT_OPT (ptr_tracer) { ptr_tracer = AAPTR_TRACER; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_INT_DEF (ptr_master); + PARAM_INT_DEF (ptr_tracer); + PARAM_INT_DEF (flags); // Rearrange pointers internally @@ -852,8 +845,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_TransferPointer) PARAM_INT (ptr_source); PARAM_INT (ptr_recipient); PARAM_INT (ptr_sourcefield); - PARAM_INT_OPT (ptr_recipientfield) { ptr_recipientfield = AAPTR_DEFAULT; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_INT_DEF (ptr_recipientfield); + PARAM_INT_DEF (flags); AActor *source, *recipient; @@ -892,7 +885,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_TransferPointer) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopyFriendliness) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (ptr_source) { ptr_source = AAPTR_MASTER; } + PARAM_INT_DEF (ptr_source); if (self->player != NULL) { @@ -907,39 +900,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopyFriendliness) return 0; } -//========================================================================== -// -// Simple flag changers -// -//========================================================================== -DEFINE_ACTION_FUNCTION(AActor, A_SetSolid) -{ - PARAM_SELF_PROLOGUE(AActor); - self->flags |= MF_SOLID; - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_UnsetSolid) -{ - PARAM_SELF_PROLOGUE(AActor); - self->flags &= ~MF_SOLID; - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_SetFloat) -{ - PARAM_SELF_PROLOGUE(AActor); - self->flags |= MF_FLOAT; - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_UnsetFloat) -{ - PARAM_SELF_PROLOGUE(AActor); - self->flags &= ~(MF_FLOAT|MF_INFLOAT); - return 0; -} - //========================================================================== // // Customizable attack functions which use actor parameters. @@ -1029,11 +989,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BasicAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlaySound) { PARAM_SELF_PROLOGUE(AActor); - PARAM_SOUND_OPT (soundid) { soundid = "weapons/pistol"; } - PARAM_INT_OPT (channel) { channel = CHAN_BODY; } - PARAM_FLOAT_OPT (volume) { volume = 1; } - PARAM_BOOL_OPT (looping) { looping = false; } - PARAM_FLOAT_OPT (attenuation) { attenuation = ATTN_NORM; } + PARAM_SOUND_DEF (soundid); + PARAM_INT_DEF (channel); + PARAM_FLOAT_DEF (volume); + PARAM_BOOL_DEF (looping); + PARAM_FLOAT_DEF (attenuation); if (!looping) { @@ -1052,7 +1012,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlaySound) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StopSound) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(slot) { slot = CHAN_VOICE; } + PARAM_INT_DEF(slot); S_StopSound(self, slot); return 0; @@ -1067,22 +1027,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StopSound) // //========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlayWeaponSound) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_SOUND(soundid); - - S_Sound(self, CHAN_WEAPON, soundid, 1, ATTN_NORM); - return 0; -} - DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlaySoundEx) { PARAM_SELF_PROLOGUE(AActor); PARAM_SOUND (soundid); PARAM_NAME (channel); - PARAM_BOOL_OPT (looping) { looping = false; } - PARAM_INT_OPT (attenuation_raw) { attenuation_raw = 0; } + PARAM_BOOL_DEF (looping); + PARAM_INT_DEF (attenuation_raw); float attenuation; switch (attenuation_raw) @@ -1142,9 +1093,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SeekerMissile) PARAM_SELF_PROLOGUE(AActor); PARAM_INT(ang1); PARAM_INT(ang2); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(chance) { chance = 50; } - PARAM_INT_OPT(distance) { distance = 10; } + PARAM_INT_DEF(flags); + PARAM_INT_DEF(chance); + PARAM_INT_DEF(distance); if ((flags & SMF_LOOK) && (self->tracer == 0) && (pr_seekermissile()target, self, param, numparam, ret, numret); + return DoJumpIfInventory(self->target, VM_ARGS_NAMES); } //========================================================================== @@ -1389,7 +1340,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfArmorType) PARAM_SELF_PROLOGUE(AActor); PARAM_NAME (type); PARAM_STATE (label); - PARAM_INT_OPT(amount) { amount = 1; } + PARAM_INT_DEF(amount); ABasicArmor *armor = (ABasicArmor *)self->FindInventory(NAME_BasicArmor); @@ -1416,15 +1367,15 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Explode) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (damage) { damage = -1; } - PARAM_INT_OPT (distance) { distance = -1; } - PARAM_INT_OPT (flags) { flags = XF_HURTSOURCE; } - PARAM_BOOL_OPT (alert) { alert = false; } - PARAM_INT_OPT (fulldmgdistance) { fulldmgdistance = 0; } - PARAM_INT_OPT (nails) { nails = 0; } - PARAM_INT_OPT (naildamage) { naildamage = 10; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = PClass::FindActor(NAME_BulletPuff); } - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } + PARAM_INT_DEF (damage); + PARAM_INT_DEF (distance); + PARAM_INT_DEF (flags); + PARAM_BOOL_DEF (alert); + PARAM_INT_DEF (fulldmgdistance); + PARAM_INT_DEF (nails); + PARAM_INT_DEF (naildamage); + PARAM_CLASS_DEF (pufftype, AActor); + PARAM_NAME_DEF (damagetype); if (damage < 0) // get parameters from metadata { @@ -1485,10 +1436,10 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RadiusThrust) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (force) { force = 128; } - PARAM_INT_OPT (distance) { distance = -1; } - PARAM_INT_OPT (flags) { flags = RTF_AFFECTSOURCE; } - PARAM_INT_OPT (fullthrustdistance) { fullthrustdistance = 0; } + PARAM_INT_DEF (force); + PARAM_INT_DEF (distance); + PARAM_INT_DEF (flags); + PARAM_INT_DEF (fullthrustdistance); bool sourcenothrust = false; @@ -1525,10 +1476,10 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RadiusDamageSelf) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(damage) { damage = 128; } - PARAM_FLOAT_OPT(distance) { distance = 128; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_CLASS_OPT(flashtype, AActor) { flashtype = NULL; } + PARAM_INT_DEF(damage); + PARAM_FLOAT_DEF(distance); + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(flashtype, AActor); int i; int damageSteps; @@ -1587,11 +1538,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CallSpecial) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (special); - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (arg3) { arg3 = 0; } - PARAM_INT_OPT (arg4) { arg4 = 0; } - PARAM_INT_OPT (arg5) { arg5 = 0; } + PARAM_INT_DEF (arg1); + PARAM_INT_DEF (arg2); + PARAM_INT_DEF (arg3); + PARAM_INT_DEF (arg4); + PARAM_INT_DEF (arg5); bool res = !!P_ExecuteSpecial(special, NULL, self, false, arg1, arg2, arg3, arg4, arg5); @@ -1620,12 +1571,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomMissile) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (ti, AActor); - PARAM_FLOAT_OPT (Spawnheight) { Spawnheight = 32; } - PARAM_FLOAT_OPT (Spawnofs_xy) { Spawnofs_xy = 0; } - PARAM_ANGLE_OPT (Angle) { Angle = 0.; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_ANGLE_OPT (Pitch) { Pitch = 0.; } - PARAM_INT_OPT (ptr) { ptr = AAPTR_TARGET; } + PARAM_FLOAT_DEF (Spawnheight); + PARAM_FLOAT_DEF (Spawnofs_xy); + PARAM_ANGLE_DEF (Angle); + PARAM_INT_DEF (flags); + PARAM_ANGLE_DEF (Pitch); + PARAM_INT_DEF (ptr); AActor *ref = COPY_AAPTR(self, ptr); @@ -1772,13 +1723,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomBulletAttack) PARAM_ANGLE (spread_z); PARAM_INT (numbullets); PARAM_INT (damageperbullet); - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = nullptr; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (ptr) { ptr = AAPTR_TARGET; } - PARAM_CLASS_OPT (missile, AActor) { missile = nullptr; } - PARAM_FLOAT_OPT (Spawnheight) { Spawnheight = 32; } - PARAM_FLOAT_OPT (Spawnofs_xy) { Spawnofs_xy = 0; } + PARAM_CLASS_DEF (pufftype, AActor); + PARAM_FLOAT_DEF (range); + PARAM_INT_DEF (flags); + PARAM_INT_DEF (ptr); + PARAM_CLASS_DEF (missile, AActor); + PARAM_FLOAT_DEF (Spawnheight); + PARAM_FLOAT_DEF (Spawnofs_xy); AActor *ref = COPY_AAPTR(self, ptr); @@ -1860,11 +1811,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomBulletAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomMeleeAttack) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (damage) { damage = 0; } - PARAM_SOUND_OPT (meleesound) { meleesound = 0; } - PARAM_SOUND_OPT (misssound) { misssound = 0; } - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_BOOL_OPT (bleed) { bleed = true; } + PARAM_INT_DEF (damage); + PARAM_SOUND_DEF (meleesound); + PARAM_SOUND_DEF (misssound); + PARAM_NAME_DEF (damagetype); + PARAM_BOOL_DEF (bleed); if (damagetype == NAME_None) damagetype = NAME_Melee; // Melee is the default type @@ -1900,9 +1851,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomComboAttack) PARAM_CLASS (ti, AActor); PARAM_FLOAT (spawnheight); PARAM_INT (damage); - PARAM_SOUND_OPT (meleesound) { meleesound = 0; } - PARAM_NAME_OPT (damagetype) { damagetype = NAME_Melee; } - PARAM_BOOL_OPT (bleed) { bleed = true; } + PARAM_SOUND_DEF (meleesound); + PARAM_NAME_DEF (damagetype); + PARAM_BOOL_DEF (bleed); if (!self->target) return 0; @@ -2022,12 +1973,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireBullets) PARAM_ANGLE (spread_z); PARAM_INT (numbullets); PARAM_INT (damageperbullet); - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = nullptr; } - PARAM_INT_OPT (flags) { flags = FBF_USEAMMO; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_CLASS_OPT (missile, AActor) { missile = nullptr; } - PARAM_FLOAT_OPT (Spawnheight) { Spawnheight = 0; } - PARAM_FLOAT_OPT (Spawnofs_xy) { Spawnofs_xy = 0; } + PARAM_CLASS_DEF (pufftype, AActor); + PARAM_INT_DEF (flags); + PARAM_FLOAT_DEF (range); + PARAM_CLASS_DEF (missile, AActor); + PARAM_FLOAT_DEF (Spawnheight); + PARAM_FLOAT_DEF (Spawnofs_xy); if (!self->player) return 0; @@ -2149,12 +2100,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireCustomMissile) { PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS (ti, AActor); - PARAM_ANGLE_OPT (angle) { angle = 0.; } - PARAM_BOOL_OPT (useammo) { useammo = true; } - PARAM_FLOAT_OPT (spawnofs_xy) { spawnofs_xy = 0; } - PARAM_FLOAT_OPT (spawnheight) { spawnheight = 0; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_ANGLE_OPT (pitch) { pitch = 0.; } + PARAM_ANGLE_DEF (angle); + PARAM_BOOL_DEF (useammo); + PARAM_FLOAT_DEF (spawnofs_xy); + PARAM_FLOAT_DEF (spawnheight); + PARAM_INT_DEF (flags); + PARAM_ANGLE_DEF (pitch); if (!self->player) return 0; @@ -2226,15 +2177,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomPunch) { PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (damage); - PARAM_BOOL_OPT (norandom) { norandom = false; } - PARAM_INT_OPT (flags) { flags = CPF_USEAMMO; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = NULL; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_FLOAT_OPT (lifesteal) { lifesteal = 0; } - PARAM_INT_OPT (lifestealmax) { lifestealmax = 0; } - PARAM_CLASS_OPT (armorbonustype, ABasicArmorBonus) { armorbonustype = NULL; } - PARAM_SOUND_OPT (MeleeSound) { MeleeSound = ""; } - PARAM_SOUND_OPT (MissSound) { MissSound = ""; } + PARAM_BOOL_DEF (norandom); + PARAM_INT_DEF (flags); + PARAM_CLASS_DEF (pufftype, AActor); + PARAM_FLOAT_DEF (range); + PARAM_FLOAT_DEF (lifesteal); + PARAM_INT_DEF (lifestealmax); + PARAM_CLASS_DEF (armorbonustype, ABasicArmorBonus); + PARAM_SOUND_DEF (MeleeSound); + PARAM_SOUND_DEF (MissSound); if (!self->player) return 0; @@ -2330,23 +2281,23 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RailAttack) { PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (damage); - PARAM_INT_OPT (spawnofs_xy) { spawnofs_xy = 0; } - PARAM_BOOL_OPT (useammo) { useammo = true; } - PARAM_COLOR_OPT (color1) { color1 = 0; } - PARAM_COLOR_OPT (color2) { color2 = 0; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (maxdiff) { maxdiff = 0; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = PClass::FindActor(NAME_BulletPuff); } - PARAM_ANGLE_OPT (spread_xy) { spread_xy = 0.; } - PARAM_ANGLE_OPT (spread_z) { spread_z = 0.; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_INT_OPT (duration) { duration = 0; } - PARAM_FLOAT_OPT (sparsity) { sparsity = 1; } - PARAM_FLOAT_OPT (driftspeed) { driftspeed = 1; } - PARAM_CLASS_OPT (spawnclass, AActor){ spawnclass = NULL; } - PARAM_FLOAT_OPT (spawnofs_z) { spawnofs_z = 0; } - PARAM_INT_OPT (SpiralOffset) { SpiralOffset = 270; } - PARAM_INT_OPT (limit) { limit = 0; } + PARAM_INT_DEF (spawnofs_xy); + PARAM_BOOL_DEF (useammo); + PARAM_COLOR_DEF (color1); + PARAM_COLOR_DEF (color2); + PARAM_INT_DEF (flags); + PARAM_FLOAT_DEF (maxdiff); + PARAM_CLASS_DEF (pufftype, AActor); + PARAM_ANGLE_DEF (spread_xy); + PARAM_ANGLE_DEF (spread_z); + PARAM_FLOAT_DEF (range) ; + PARAM_INT_DEF (duration); + PARAM_FLOAT_DEF (sparsity); + PARAM_FLOAT_DEF (driftspeed); + PARAM_CLASS_DEF (spawnclass, AActor); + PARAM_FLOAT_DEF (spawnofs_z); + PARAM_INT_DEF (SpiralOffset); + PARAM_INT_DEF (limit); if (range == 0) range = 8192; if (sparsity == 0) sparsity=1.0; @@ -2409,23 +2360,23 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomRailgun) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (damage); - PARAM_INT_OPT (spawnofs_xy) { spawnofs_xy = 0; } - PARAM_COLOR_OPT (color1) { color1 = 0; } - PARAM_COLOR_OPT (color2) { color2 = 0; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (aim) { aim = CRF_DONTAIM; } - PARAM_FLOAT_OPT (maxdiff) { maxdiff = 0; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = PClass::FindActor(NAME_BulletPuff); } - PARAM_ANGLE_OPT (spread_xy) { spread_xy = 0.; } - PARAM_ANGLE_OPT (spread_z) { spread_z = 0.; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_INT_OPT (duration) { duration = 0; } - PARAM_FLOAT_OPT (sparsity) { sparsity = 1; } - PARAM_FLOAT_OPT (driftspeed) { driftspeed = 1; } - PARAM_CLASS_OPT (spawnclass, AActor){ spawnclass = NULL; } - PARAM_FLOAT_OPT (spawnofs_z) { spawnofs_z = 0; } - PARAM_INT_OPT (SpiralOffset) { SpiralOffset = 270; } - PARAM_INT_OPT (limit) { limit = 0; } + PARAM_INT_DEF (spawnofs_xy) + PARAM_COLOR_DEF (color1) + PARAM_COLOR_DEF (color2) + PARAM_INT_DEF (flags) + PARAM_INT_DEF (aim) + PARAM_FLOAT_DEF (maxdiff) + PARAM_CLASS_DEF (pufftype, AActor) + PARAM_ANGLE_DEF (spread_xy) + PARAM_ANGLE_DEF (spread_z) + PARAM_FLOAT_DEF (range) + PARAM_INT_DEF (duration) + PARAM_FLOAT_DEF (sparsity) + PARAM_FLOAT_DEF (driftspeed) + PARAM_CLASS_DEF (spawnclass, AActor) + PARAM_FLOAT_DEF (spawnofs_z) + PARAM_INT_DEF (SpiralOffset) + PARAM_INT_DEF (limit) if (range == 0) range = 8192.; if (sparsity == 0) sparsity = 1; @@ -2527,11 +2478,11 @@ static bool DoGiveInventory(AActor *receiver, bool orresult, VM_ARGS) { int paramnum = 0; PARAM_CLASS (mi, AInventory); - PARAM_INT_OPT (amount) { amount = 1; } + PARAM_INT_DEF (amount) if (!orresult) { - PARAM_INT_OPT(setreceiver) { setreceiver = AAPTR_DEFAULT; } + PARAM_INT_DEF(setreceiver) receiver = COPY_AAPTR(receiver, setreceiver); } if (receiver == NULL) @@ -2635,8 +2586,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetInventory) PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(itemtype, AInventory); PARAM_INT(amount); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } - PARAM_BOOL_OPT(beyondMax) { beyondMax = false; } + PARAM_INT_DEF(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_BOOL_DEF(beyondMax) { beyondMax = false; } bool res = false; @@ -2725,8 +2676,8 @@ bool DoTakeInventory(AActor *receiver, bool orresult, VM_ARGS) { int paramnum = 0; PARAM_CLASS (itemtype, AInventory); - PARAM_INT_OPT (amount) { amount = 0; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_INT_DEF (amount); + PARAM_INT_DEF (flags); if (itemtype == NULL) { @@ -3013,11 +2964,11 @@ static bool InitSpawnedItem(AActor *self, AActor *mo, int flags) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnItem) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_CLASS_OPT (missile, AActor) { missile = PClass::FindActor("Unknown"); } - PARAM_FLOAT_OPT (distance) { distance = 0; } - PARAM_FLOAT_OPT (zheight) { zheight = 0; } - PARAM_BOOL_OPT (useammo) { useammo = true; } - PARAM_BOOL_OPT (transfer_translation) { transfer_translation = false; } + PARAM_CLASS_DEF (missile, AActor) + PARAM_FLOAT_DEF (distance) + PARAM_FLOAT_DEF (zheight) + PARAM_BOOL_DEF (useammo) + PARAM_BOOL_DEF (transfer_translation) if (missile == NULL) { @@ -3062,16 +3013,16 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnItemEx) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (missile, AActor); - PARAM_FLOAT_OPT (xofs) { xofs = 0; } - PARAM_FLOAT_OPT (yofs) { yofs = 0; } - PARAM_FLOAT_OPT (zofs) { zofs = 0; } - PARAM_FLOAT_OPT (xvel) { xvel = 0; } - PARAM_FLOAT_OPT (yvel) { yvel = 0; } - PARAM_FLOAT_OPT (zvel) { zvel = 0; } - PARAM_ANGLE_OPT (angle) { angle = 0.; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (chance) { chance = 0; } - PARAM_INT_OPT (tid) { tid = 0; } + PARAM_FLOAT_DEF (xofs) + PARAM_FLOAT_DEF (yofs) + PARAM_FLOAT_DEF (zofs) + PARAM_FLOAT_DEF (xvel) + PARAM_FLOAT_DEF (yvel) + PARAM_FLOAT_DEF (zvel) + PARAM_ANGLE_DEF (angle) + PARAM_INT_DEF (flags) + PARAM_INT_DEF (chance) + PARAM_INT_DEF (tid) if (missile == NULL) { @@ -3144,15 +3095,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnItemEx) //=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ThrowGrenade) { - PARAM_ACTION_PROLOGUE(AActor); - PARAM_CLASS (missile, AActor); - PARAM_FLOAT_OPT (zheight) { zheight = 0; } - PARAM_FLOAT_OPT (xyvel) { xyvel = 0; } - PARAM_FLOAT_OPT (zvel) { zvel = 0; } - PARAM_BOOL_OPT (useammo) { useammo = true; } + PARAM_ACTION_PROLOGUE(AActor); + PARAM_CLASS (missile, AActor); + PARAM_FLOAT_DEF (zheight) + PARAM_FLOAT_DEF (xyvel) + PARAM_FLOAT_DEF (zvel) + PARAM_BOOL_DEF (useammo) - if (missile == NULL) - { + if (missile == NULL) + { ACTION_RETURN_BOOL(true); } if (ACTION_CALL_FROM_PSPRITE()) @@ -3243,7 +3194,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SelectWeapon) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(cls, AWeapon); - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_INT_DEF(flags); bool selectPriority = !!(flags & SWF_SELECTPRIORITY); @@ -3288,8 +3239,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Print) { PARAM_SELF_PROLOGUE(AActor); PARAM_STRING (text); - PARAM_FLOAT_OPT (time) { time = 0; } - PARAM_NAME_OPT (fontname) { fontname = NAME_None; } + PARAM_FLOAT_DEF (time); + PARAM_NAME_DEF (fontname); if (text[0] == '$') text = GStrings(&text[1]); if (self->CheckLocalView (consoleplayer) || @@ -3323,8 +3274,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PrintBold) { PARAM_SELF_PROLOGUE(AActor); PARAM_STRING (text); - PARAM_FLOAT_OPT (time) { time = 0; } - PARAM_NAME_OPT (fontname) { fontname = NAME_None; } + PARAM_FLOAT_DEF (time); + PARAM_NAME_DEF (fontname); float saved = con_midtime; FFont *font = NULL; @@ -3400,7 +3351,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetTranslucent) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT (alpha); - PARAM_INT_OPT (mode) { mode = 0; } + PARAM_INT_DEF (mode); mode = mode == 0 ? STYLE_Translucent : mode == 2 ? STYLE_Fuzzy : STYLE_Add; @@ -3419,7 +3370,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetRenderStyle) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(alpha); - PARAM_INT_OPT(mode) { mode = 0; } + PARAM_INT_DEF(mode); self->Alpha = clamp(alpha, 0., 1.); self->RenderStyle = ERenderStyle(mode); @@ -3443,8 +3394,10 @@ enum FadeFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeIn) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(reduce) { reduce = 0.1; } - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_FLOAT_DEF(reduce); + PARAM_INT_DEF(flags); + PARAM_NAME_DEF(fontname); + if (reduce == 0) { @@ -3477,8 +3430,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeIn) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeOut) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(reduce) { reduce = 0.1; } - PARAM_INT_OPT(flags) { flags = FTF_REMOVE; } + PARAM_FLOAT_DEF(reduce); + PARAM_INT_DEF(flags); if (reduce == 0) { @@ -3512,8 +3465,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeTo) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT (target); - PARAM_FLOAT_OPT (amount) { amount = 0.1; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_FLOAT_DEF (amount); + PARAM_INT_DEF (flags); self->RenderStyle.Flags &= ~STYLEF_Alpha1; @@ -3546,50 +3499,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeTo) return 0; } -//=========================================================================== -// -// A_Scale(float scalex, optional float scaley) -// -// Scales the actor's graphics. If scaley is 0, use scalex. -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetScale) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT (scalex); - PARAM_FLOAT_OPT (scaley) { scaley = scalex; } - PARAM_INT_OPT (ptr) { ptr = AAPTR_DEFAULT; } - PARAM_BOOL_OPT (usezero) { usezero = false; } - - AActor *ref = COPY_AAPTR(self, ptr); - - if (ref != NULL) - { - if (scaley == 0 && !usezero) - { - scaley = scalex; - } - ref->Scale = { scalex, scaley }; - } - return 0; -} - -//=========================================================================== -// -// A_SetMass(int mass) -// -// Sets the actor's mass. -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetMass) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT (mass); - - self->Mass = mass; - return 0; -} - //=========================================================================== // // A_SpawnDebris @@ -3599,9 +3508,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnDebris) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (debris, AActor); - PARAM_BOOL_OPT (transfer_translation) { transfer_translation = false; } - PARAM_FLOAT_OPT (mult_h) { mult_h = 1; } - PARAM_FLOAT_OPT (mult_v) { mult_v = 1; } + PARAM_BOOL_DEF (transfer_translation) + PARAM_FLOAT_DEF (mult_h) + PARAM_FLOAT_DEF (mult_v) int i; AActor *mo; @@ -3655,22 +3564,22 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnParticle) { PARAM_SELF_PROLOGUE(AActor); PARAM_COLOR (color); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (lifetime) { lifetime = 35; } - PARAM_FLOAT_OPT (size) { size = 1.; } - PARAM_ANGLE_OPT (angle) { angle = 0.; } - PARAM_FLOAT_OPT (xoff) { xoff = 0; } - PARAM_FLOAT_OPT (yoff) { yoff = 0; } - PARAM_FLOAT_OPT (zoff) { zoff = 0; } - PARAM_FLOAT_OPT (xvel) { xvel = 0; } - PARAM_FLOAT_OPT (yvel) { yvel = 0; } - PARAM_FLOAT_OPT (zvel) { zvel = 0; } - PARAM_FLOAT_OPT (accelx) { accelx = 0; } - PARAM_FLOAT_OPT (accely) { accely = 0; } - PARAM_FLOAT_OPT (accelz) { accelz = 0; } - PARAM_FLOAT_OPT (startalpha) { startalpha = 1.; } - PARAM_FLOAT_OPT (fadestep) { fadestep = -1.; } - PARAM_FLOAT_OPT (sizestep) { sizestep = 0.; } + PARAM_INT_DEF (flags) + PARAM_INT_DEF (lifetime) + PARAM_FLOAT_DEF (size) + PARAM_ANGLE_DEF (angle) + PARAM_FLOAT_DEF (xoff) + PARAM_FLOAT_DEF (yoff) + PARAM_FLOAT_DEF (zoff) + PARAM_FLOAT_DEF (xvel) + PARAM_FLOAT_DEF (yvel) + PARAM_FLOAT_DEF (zvel) + PARAM_FLOAT_DEF (accelx) + PARAM_FLOAT_DEF (accely) + PARAM_FLOAT_DEF (accelz) + PARAM_FLOAT_DEF (startalpha) + PARAM_FLOAT_DEF (fadestep) + PARAM_FLOAT_DEF (sizestep) startalpha = clamp(startalpha, 0., 1.); if (fadestep > 0) fadestep = clamp(fadestep, 0., 1.); @@ -3786,7 +3695,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSightOrRange) PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(range); PARAM_STATE(jump); - PARAM_BOOL_OPT(twodi) { twodi = false; } + PARAM_BOOL_DEF(twodi); range *= range; for (int i = 0; i < MAXPLAYERS; ++i) @@ -3815,7 +3724,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckRange) PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(range); PARAM_STATE(jump); - PARAM_BOOL_OPT(twodi) { twodi = false; } + PARAM_BOOL_DEF(twodi); range *= range; for (int i = 0; i < MAXPLAYERS; ++i) @@ -3872,7 +3781,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetBlend) PARAM_COLOR (color); PARAM_FLOAT (alpha); PARAM_INT (tics); - PARAM_COLOR_OPT (color2) { color2 = 0; } + PARAM_COLOR_DEF (color2); if (color == MAKEARGB(255,255,255,255)) color = 0; @@ -3912,7 +3821,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CountdownArg) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT(cnt); - PARAM_STATE_OPT(state) { state = self->FindState(NAME_Death); } + PARAM_STATE_DEF(state) if (cnt<0 || cnt >= 5) return 0; if (!self->args[cnt]--) @@ -3927,6 +3836,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CountdownArg) } else { + if (state == nullptr) state = self->FindState(NAME_Death); self->SetState(state); } } @@ -4075,7 +3985,7 @@ enum RS_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Respawn) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(flags) { flags = RSF_FOG; } + PARAM_INT_DEF(flags); bool oktorespawn = false; DVector3 pos = self->Pos(); @@ -4164,38 +4074,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlayerSkinCheck) ACTION_RETURN_STATE(NULL); } -//=========================================================================== -// -// A_SetGravity -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetGravity) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT(gravity); - - self->Gravity = clamp(gravity, 0., 10.); - return 0; -} - - // [KS] *** Start of my modifications *** -//=========================================================================== -// -// A_ClearTarget -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_ClearTarget) -{ - PARAM_SELF_PROLOGUE(AActor); - self->target = NULL; - self->LastHeard = NULL; - self->lastenemy = NULL; - return 0; -} - //========================================================================== // // A_CheckLOF (state jump, int flags = CRF_AIM_VERT|CRF_AIM_HOR, @@ -4530,10 +4410,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) { PARAM_SELF_PROLOGUE(AActor); PARAM_STATE (jump); - PARAM_ANGLE_OPT (fov) { fov = 0.; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (dist_max) { dist_max = 0; } - PARAM_FLOAT_OPT (dist_close) { dist_close = 0; } + PARAM_ANGLE_DEF (fov) + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (dist_max) + PARAM_FLOAT_DEF (dist_close) AActor *target, *viewport; FTranslatedLineTarget t; @@ -4668,10 +4548,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) { PARAM_SELF_PROLOGUE(AActor); PARAM_STATE (jump); - PARAM_ANGLE_OPT (fov) { fov = 0.; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (dist_max) { dist_max = 0; } - PARAM_FLOAT_OPT (dist_close) { dist_close = 0; } + PARAM_ANGLE_DEF (fov) + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (dist_max) + PARAM_FLOAT_DEF (dist_close) AActor *target; @@ -4755,7 +4635,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckForReload) } PARAM_INT (count); PARAM_STATE (jump); - PARAM_BOOL_OPT (dontincrement) { dontincrement = false; } + PARAM_BOOL_DEF (dontincrement); if (numret > 0) { @@ -4836,7 +4716,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFlag) PARAM_SELF_PROLOGUE(AActor); PARAM_STRING (flagname); PARAM_STATE (jumpto); - PARAM_INT_OPT (checkpointer) { checkpointer = AAPTR_DEFAULT; } + PARAM_INT_DEF (checkpointer); AActor *owner = COPY_AAPTR(self, checkpointer); if (owner == NULL) @@ -4852,46 +4732,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFlag) } -//=========================================================================== -// -// A_ChangeCountFlags (needed, because these flags affect global counters) -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeLinkFlags) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(blockmap) { blockmap = -1; } - PARAM_INT_OPT(sector) { sector = -1; } - - self->UnlinkFromWorld(); - - if (blockmap != -1) - { - if (blockmap == 0) self->flags &= ~MF_NOBLOCKMAP; - else self->flags |= MF_NOBLOCKMAP; - } - - if (sector != -1) - { - if (sector == 0) self->flags &= ~MF_NOSECTOR; - else self->flags |= MF_NOSECTOR; - } - - self->LinkToWorld(); - return 0; -} - -//=========================================================================== -// -// A_ChangeCountFlags (needed, because these flags affect global counters) -// -//=========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeCountFlags) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(kill) { kill = -1; } - PARAM_INT_OPT(item) { item = -1; } - PARAM_INT_OPT(secret) { secret = -1; } + PARAM_INT_DEF(kill); + PARAM_INT_DEF(item); + PARAM_INT_DEF(secret); if (self->CountsAsKill() && self->health > 0) --level.total_monsters; if (self->flags & MF_COUNTITEM) --level.total_items; @@ -4928,7 +4774,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeCountFlags) DEFINE_ACTION_FUNCTION(AActor, A_RaiseMaster) { PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL_OPT(copy) { copy = false; } + PARAM_BOOL_DEF(copy); if (self->master != NULL) { @@ -4945,7 +4791,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RaiseMaster) DEFINE_ACTION_FUNCTION(AActor, A_RaiseChildren) { PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL_OPT(copy) { copy = false; } + PARAM_BOOL_DEF(copy); TThinkerIterator it; AActor *mo; @@ -4968,7 +4814,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RaiseChildren) DEFINE_ACTION_FUNCTION(AActor, A_RaiseSiblings) { PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL_OPT(copy) { copy = false; } + PARAM_BOOL_DEF(copy); TThinkerIterator it; AActor *mo; @@ -4986,18 +4832,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_RaiseSiblings) return 0; } - //=========================================================================== - // -// [TP] A_FaceConsolePlayer -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS (AActor, A_FaceConsolePlayer) -{ - // NOTE: It does nothing for ZDoom, since in a multiplayer game, each - // node has its own console player. - return 0; -} - //=========================================================================== // // A_MonsterRefire @@ -5044,9 +4878,9 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetAngle) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(angle) { angle = 0; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_FLOAT_DEF(angle); + PARAM_INT_DEF(flags); + PARAM_INT_DEF(ptr); AActor *ref = COPY_AAPTR(self, ptr); if (ref != NULL) @@ -5068,8 +4902,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetPitch) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(pitch); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(flags); + PARAM_INT_DEF(ptr); AActor *ref = COPY_AAPTR(self, ptr); @@ -5092,8 +4926,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetRoll) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT (roll); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF (flags); + PARAM_INT_DEF (ptr) ; AActor *ref = COPY_AAPTR(self, ptr); if (ref != NULL) @@ -5115,7 +4949,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ScaleVelocity) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(scale); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(ptr); AActor *ref = COPY_AAPTR(self, ptr); @@ -5146,11 +4980,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ScaleVelocity) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeVelocity) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT (x) { x = 0; } - PARAM_FLOAT_OPT (y) { y = 0; } - PARAM_FLOAT_OPT (z) { z = 0; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (ptr) { ptr = AAPTR_DEFAULT; } + PARAM_FLOAT_DEF (x) + PARAM_FLOAT_DEF (y) + PARAM_FLOAT_DEF (z) + PARAM_INT_DEF (flags) + PARAM_INT_DEF (ptr) AActor *ref = COPY_AAPTR(self, ptr); @@ -5186,51 +5020,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeVelocity) return 0; } -//=========================================================================== -// -// A_SetArg -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetArg) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT(pos); - PARAM_INT(value); - - // Set the value of the specified arg - if ((size_t)pos < countof(self->args)) - { - self->args[pos] = value; - } - return 0; -} - -//=========================================================================== -// -// A_SetSpecial -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpecial) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT (spec); - PARAM_INT_OPT (arg0) { arg0 = 0; } - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (arg3) { arg3 = 0; } - PARAM_INT_OPT (arg4) { arg4 = 0; } - - self->special = spec; - self->args[0] = arg0; - self->args[1] = arg1; - self->args[2] = arg2; - self->args[3] = arg3; - self->args[4] = arg4; - return 0; -} - //=========================================================================== // // A_SetUserVar @@ -5371,13 +5160,13 @@ enum T_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Teleport) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE_OPT (teleport_state) { teleport_state = NULL; } - PARAM_CLASS_OPT (target_type, ASpecialSpot) { target_type = PClass::FindActor("BossSpot"); } - PARAM_CLASS_OPT (fog_type, AActor) { fog_type = PClass::FindActor("TeleportFog"); } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (mindist) { mindist = 128; } - PARAM_FLOAT_OPT (maxdist) { maxdist = 0; } - PARAM_INT_OPT (ptr) { ptr = AAPTR_DEFAULT; } + PARAM_STATE_DEF (teleport_state) + PARAM_CLASS_DEF (target_type, ASpecialSpot) + PARAM_CLASS_DEF (fog_type, AActor) + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (mindist) + PARAM_FLOAT_DEF (maxdist) + PARAM_INT_DEF (ptr) AActor *ref = COPY_AAPTR(self, ptr); @@ -5538,20 +5327,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Teleport) return numret; } -//=========================================================================== -// -// A_Turn -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Turn) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(angle) { angle = 0; } - self->Angles.Yaw += angle; - return 0; -} - //=========================================================================== // // A_Quake @@ -5565,7 +5340,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Quake) PARAM_INT (duration); PARAM_INT (damrad); PARAM_INT (tremrad); - PARAM_SOUND_OPT (sound) { sound = "world/quake"; } + PARAM_SOUND_DEF (sound); P_StartQuake(self, 0, intensity, duration, damrad, tremrad, sound); return 0; @@ -5588,15 +5363,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_QuakeEx) PARAM_INT(duration); PARAM_INT(damrad); PARAM_INT(tremrad); - PARAM_SOUND_OPT (sound) { sound = "world/quake"; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_FLOAT_OPT(mulWaveX) { mulWaveX = 1.; } - PARAM_FLOAT_OPT(mulWaveY) { mulWaveY = 1.; } - PARAM_FLOAT_OPT(mulWaveZ) { mulWaveZ = 1.; } - PARAM_INT_OPT(falloff) { falloff = 0; } - PARAM_INT_OPT(highpoint) { highpoint = 0; } - PARAM_FLOAT_OPT(rollIntensity) { rollIntensity = 0.; } - PARAM_FLOAT_OPT(rollWave) { rollWave = 0.; } + PARAM_SOUND_DEF(sound); + PARAM_INT_DEF(flags); + PARAM_FLOAT_DEF(mulWaveX); + PARAM_FLOAT_DEF(mulWaveY); + PARAM_FLOAT_DEF(mulWaveZ); + PARAM_INT_DEF(falloff); + PARAM_INT_DEF(highpoint); + PARAM_FLOAT_DEF(rollIntensity); + PARAM_FLOAT_DEF(rollWave); P_StartQuakeXYZ(self, 0, intensityX, intensityY, intensityZ, duration, damrad, tremrad, sound, flags, mulWaveX, mulWaveY, mulWaveZ, falloff, highpoint, rollIntensity, rollWave); return 0; @@ -5675,8 +5450,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Weave) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_LineEffect) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(special) { special = 0; } - PARAM_INT_OPT(tag) { tag = 0; } + PARAM_INT_DEF(special); + PARAM_INT_DEF(tag); line_t junk; maplinedef_t oldjunk; @@ -5710,15 +5485,15 @@ enum WolfAttackFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_WolfAttack) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_SOUND_OPT (sound) { sound = "weapons/pistol"; } - PARAM_FLOAT_OPT (snipe) { snipe = 1.; } - PARAM_INT_OPT (maxdamage) { maxdamage = 64; } - PARAM_INT_OPT (blocksize) { blocksize = 128; } - PARAM_INT_OPT (pointblank) { pointblank = 2; } - PARAM_INT_OPT (longrange) { longrange = 4; } - PARAM_FLOAT_OPT (runspeed) { runspeed = 160; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = PClass::FindActor(NAME_BulletPuff); } + PARAM_INT_DEF (flags) + PARAM_SOUND_DEF (sound) + PARAM_FLOAT_DEF (snipe) + PARAM_INT_DEF (maxdamage) + PARAM_INT_DEF (blocksize) + PARAM_INT_DEF (pointblank) + PARAM_INT_DEF (longrange) + PARAM_FLOAT_DEF (runspeed) + PARAM_CLASS_DEF (pufftype, AActor) if (!self->target) return 0; @@ -5816,15 +5591,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Warp) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT(destination_selector); - PARAM_FLOAT_OPT(xofs) { xofs = 0; } - PARAM_FLOAT_OPT(yofs) { yofs = 0; } - PARAM_FLOAT_OPT(zofs) { zofs = 0; } - PARAM_ANGLE_OPT(angle) { angle = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_STATE_OPT(success_state) { success_state = NULL; } - PARAM_FLOAT_OPT(heightoffset) { heightoffset = 0; } - PARAM_FLOAT_OPT(radiusoffset) { radiusoffset = 0; } - PARAM_ANGLE_OPT(pitch) { pitch = 0.; } + PARAM_FLOAT_DEF(xofs) + PARAM_FLOAT_DEF(yofs) + PARAM_FLOAT_DEF(zofs) + PARAM_ANGLE_DEF(angle) + PARAM_INT_DEF(flags) + PARAM_STATE_DEF(success_state) + PARAM_FLOAT_DEF(heightoffset) + PARAM_FLOAT_DEF(radiusoffset) + PARAM_ANGLE_DEF(pitch) AActor *reference; @@ -5874,104 +5649,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Warp) return numret; } -//========================================================================== -// -// ACS_Named* stuff - -// -// These are exactly like their un-named line special equivalents, except -// they take strings instead of integers to indicate which script to run. -// Some of these probably aren't very useful, but they are included for -// the sake of completeness. -// -//========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedExecuteWithResult) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (arg3) { arg3 = 0; } - PARAM_INT_OPT (arg4) { arg4 = 0; } - - int res = P_ExecuteSpecial(ACS_ExecuteWithResult, NULL, self, false, -scriptname, arg1, arg2, arg3, arg4); - ACTION_RETURN_INT(res); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedExecute) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (mapnum) { mapnum = 0; } - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (arg3) { arg3 = 0; } - - int res = P_ExecuteSpecial(ACS_Execute, NULL, self, false, -scriptname, mapnum, arg1, arg2, arg3); - ACTION_RETURN_INT(res); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedExecuteAlways) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (mapnum) { mapnum = 0; } - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (arg3) { arg3 = 0; } - - int res = P_ExecuteSpecial(ACS_ExecuteAlways, NULL, self, false, -scriptname, mapnum, arg1, arg2, arg3); - ACTION_RETURN_INT(res); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedLockedExecute) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (mapnum) { mapnum = 0; } - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (lock) { lock = 0; } - - int res = P_ExecuteSpecial(ACS_LockedExecute, NULL, self, false, -scriptname, mapnum, arg1, arg2, lock); - ACTION_RETURN_INT(res); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedLockedExecuteDoor) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (mapnum) { mapnum = 0; } - PARAM_INT_OPT (arg1) { arg1 = 0; } - PARAM_INT_OPT (arg2) { arg2 = 0; } - PARAM_INT_OPT (lock) { lock = 0; } - - int res = P_ExecuteSpecial(ACS_LockedExecuteDoor, NULL, self, false, -scriptname, mapnum, arg1, arg2, lock); - ACTION_RETURN_INT(res); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedSuspend) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (mapnum) { mapnum = 0; } - - int res = P_ExecuteSpecial(ACS_Suspend, NULL, self, false, -scriptname, mapnum, 0, 0, 0); - ACTION_RETURN_INT(res); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, ACS_NamedTerminate) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME (scriptname); - PARAM_INT_OPT (mapnum) { mapnum = 0; } - - int res = P_ExecuteSpecial(ACS_Terminate, NULL, self, false, -scriptname, mapnum, 0, 0, 0); - ACTION_RETURN_INT(res); -} - - static bool DoCheckSpecies(AActor *mo, FName filterSpecies, bool exclude) { FName actorSpecies = mo->GetSpecies(); @@ -6168,11 +5845,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RadiusGive) PARAM_CLASS (item, AInventory); PARAM_FLOAT (distance); PARAM_INT (flags); - PARAM_INT_OPT (amount) { amount = 0; } - PARAM_CLASS_OPT (filter, AActor) { filter = nullptr; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_FLOAT_OPT (mindist) { mindist = 0; } - PARAM_INT_OPT (limit) { limit = 0; } + PARAM_INT_DEF (amount); + PARAM_CLASS_DEF (filter, AActor); + PARAM_NAME_DEF (species); + PARAM_FLOAT_DEF (mindist); + PARAM_INT_DEF (limit); // We need a valid item, valid targets, and a valid range if (item == nullptr || (flags & RGF_MASK) == 0 || !flags || distance <= 0 || mindist >= distance) @@ -6218,8 +5895,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSpecies) { PARAM_SELF_PROLOGUE(AActor); PARAM_STATE(jump); - PARAM_NAME_OPT(species) { species = NAME_None; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_NAME_DEF(species); + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -6259,21 +5936,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetTics) return 0; } -//========================================================================== -// -// A_SetDamageType -// -//========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetDamageType) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME(damagetype); - - self->DamageType = damagetype; - return 0; -} - //========================================================================== // // A_DropItem @@ -6284,77 +5946,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DropItem) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (spawntype, AActor); - PARAM_INT_OPT (amount) { amount = -1; } - PARAM_INT_OPT (chance) { chance = 256; } + PARAM_INT_DEF(amount); + PARAM_INT_DEF(chance); P_DropItem(self, spawntype, amount, chance); return 0; } -//========================================================================== -// -// A_SetSpeed -// -//========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpeed) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT(speed); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } - - AActor *ref = COPY_AAPTR(self, ptr); - - if (ref != NULL) - { - ref->Speed = speed; - } - return 0; -} - -//========================================================================== -// -// A_SetFloatSpeed -// -//========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetFloatSpeed) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT(speed); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } - - AActor *ref = COPY_AAPTR(self, ptr); - - if (!ref) - { - return 0; - } - - ref->FloatSpeed = speed; - return 0; -} - -//========================================================================== -// -// A_SetPainThreshold -// -//========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetPainThreshold) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT(threshold); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } - - AActor *ref = COPY_AAPTR(self, ptr); - - if (!ref) - { - return 0; - } - - ref->PainThreshold = threshold; - return 0; -} - //=========================================================================== // // Common A_Damage handler @@ -6429,12 +6027,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSelf) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (amount); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6452,12 +6050,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTarget) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (amount); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6476,12 +6074,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageTracer) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (amount); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6500,12 +6098,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageMaster) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (amount); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6524,12 +6122,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageChildren) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (amount); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6554,12 +6152,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DamageSiblings) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (amount); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6636,12 +6234,12 @@ static void DoKill(AActor *killtarget, AActor *inflictor, AActor *source, FName DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) { PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6659,12 +6257,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTarget) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) { PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6682,14 +6280,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillTracer) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) { PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) - AActor *source = COPY_AAPTR(self, src); + AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); if (self->master != NULL) @@ -6705,12 +6303,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillMaster) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) { PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6736,12 +6334,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillChildren) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KillSiblings) { PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } - PARAM_INT_OPT (src) { src = AAPTR_DEFAULT; } - PARAM_INT_OPT (inflict) { inflict = AAPTR_DEFAULT; } + PARAM_NAME_DEF (damagetype) + PARAM_INT_DEF (flags) + PARAM_CLASS_DEF (filter, AActor) + PARAM_NAME_DEF (species) + PARAM_INT_DEF (src) + PARAM_INT_DEF (inflict) AActor *source = COPY_AAPTR(self, src); AActor *inflictor = COPY_AAPTR(self, inflict); @@ -6812,9 +6410,9 @@ static void DoRemove(AActor *removetarget, int flags, PClassActor *filter, FName DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(filter, AActor); + PARAM_NAME_DEF(species); if (self->target != NULL) { @@ -6831,9 +6429,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTarget) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(filter, AActor); + PARAM_NAME_DEF(species); if (self->tracer != NULL) { @@ -6850,9 +6448,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveTracer) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(filter, AActor); + PARAM_NAME_DEF(species); if (self->master != NULL) { @@ -6869,10 +6467,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveMaster) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) { PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL_OPT (removeall) { removeall = false; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } + PARAM_BOOL_DEF(removeall); + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(filter, AActor); + PARAM_NAME_DEF(species); TThinkerIterator it; AActor *mo; @@ -6895,10 +6493,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveChildren) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) { PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL_OPT (removeall) { removeall = false; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } + PARAM_BOOL_DEF(removeall); + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(filter, AActor); + PARAM_NAME_DEF(species); TThinkerIterator it; AActor *mo; @@ -6924,10 +6522,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RemoveSiblings) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Remove) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT (removee); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_CLASS_OPT (filter, AActor){ filter = NULL; } - PARAM_NAME_OPT (species) { species = NAME_None; } + PARAM_INT(removee); + PARAM_INT_DEF(flags); + PARAM_CLASS_DEF(filter, AActor); + PARAM_NAME_DEF(species); AActor *reference = COPY_AAPTR(self, removee); if (reference != NULL) @@ -6982,18 +6580,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_SwapTeleFog) // Changes the FloatBobPhase of the actor. //=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetFloatBobPhase) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT(bob); - - //Respect float bob phase limits. - if (self && (bob >= 0 && bob <= 63)) - { - self->FloatBobPhase = bob; - } - return 0; -} //=========================================================================== // A_SetHealth @@ -7006,7 +6592,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetHealth) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT (health); - PARAM_INT_OPT (ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF (ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -7043,7 +6629,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetHealth) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ResetHealth) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -7080,10 +6666,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfHigherOrLower) PARAM_SELF_PROLOGUE(AActor); PARAM_STATE(high); PARAM_STATE(low); - PARAM_FLOAT_OPT(offsethigh) { offsethigh = 0; } - PARAM_FLOAT_OPT(offsetlow) { offsetlow = 0; } - PARAM_BOOL_OPT(includeHeight) { includeHeight = true; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_TARGET; } + PARAM_FLOAT_DEF(offsethigh); + PARAM_FLOAT_DEF(offsetlow); + PARAM_BOOL_DEF(includeHeight); + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -7111,7 +6697,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpecies) { PARAM_SELF_PROLOGUE(AActor); PARAM_NAME(species); - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); if (!mobj) @@ -7123,48 +6709,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpecies) return 0; } -//=========================================================================== -// -// A_SetRipperLevel(int level) -// -// Sets the ripper level of the calling actor. -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetRipperLevel) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT(level); - self->RipperLevel = level; - return 0; -} - -//=========================================================================== -// -// A_SetRipMin(int min) -// -// Sets the minimum level a ripper must be in order to rip through this actor. -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetRipMin) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT(min); - self->RipLevelMin = min; - return 0; -} - -//=========================================================================== -// -// A_SetRipMax(int max) -// -// Sets the minimum level a ripper must be in order to rip through this actor. -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetRipMax) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT(max); - self->RipLevelMax = max; - return 0; -} - //=========================================================================== // // A_SetChaseThreshold(int threshold, bool def, int ptr) @@ -7177,8 +6721,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetChaseThreshold) { PARAM_SELF_PROLOGUE(AActor); PARAM_INT(threshold); - PARAM_BOOL_OPT(def) { def = false; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_BOOL_DEF(def); + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -7206,9 +6750,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckProximity) PARAM_STATE(jump); PARAM_CLASS(classname, AActor); PARAM_FLOAT(distance); - PARAM_INT_OPT(count) { count = 1; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_INT_DEF(count); + PARAM_INT_DEF(flags); + PARAM_INT_DEF(ptr); if (!jump) { @@ -7250,12 +6794,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckBlock) { PARAM_SELF_PROLOGUE(AActor); PARAM_STATE(block) - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } - PARAM_FLOAT_OPT(xofs) { xofs = 0; } - PARAM_FLOAT_OPT(yofs) { yofs = 0; } - PARAM_FLOAT_OPT(zofs) { zofs = 0; } - PARAM_ANGLE_OPT(angle) { angle = 0.; } + PARAM_INT_DEF(flags) + PARAM_INT_DEF(ptr) + PARAM_FLOAT_DEF(xofs) + PARAM_FLOAT_DEF(yofs) + PARAM_FLOAT_DEF(zofs) + PARAM_ANGLE_DEF(angle) AActor *mobj = COPY_AAPTR(self, ptr); @@ -7360,11 +6904,11 @@ enum FMDFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceMovementDirection) { PARAM_SELF_PROLOGUE(AActor); - PARAM_ANGLE_OPT(offset) { offset = 0.; } - PARAM_ANGLE_OPT(anglelimit) { anglelimit = 0.; } - PARAM_ANGLE_OPT(pitchlimit) { pitchlimit = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_ANGLE_DEF(offset) + PARAM_ANGLE_DEF(anglelimit) + PARAM_ANGLE_DEF(pitchlimit) + PARAM_INT_DEF(flags) + PARAM_INT_DEF(ptr) AActor *mobj = COPY_AAPTR(self, ptr); @@ -7456,7 +7000,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopySpriteFrame) PARAM_SELF_PROLOGUE(AActor); PARAM_INT(from); PARAM_INT(to); - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_INT_DEF(flags); AActor *copyfrom = COPY_AAPTR(self, from); AActor *copyto = COPY_AAPTR(self, to); @@ -7481,8 +7025,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopySpriteFrame) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpriteAngle) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(angle) { angle = 0.; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_FLOAT_DEF(angle); + PARAM_INT_DEF(ptr); AActor *mobj = COPY_AAPTR(self, ptr); @@ -7535,12 +7079,12 @@ enum VRFFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetVisibleRotation) { PARAM_SELF_PROLOGUE(AActor); - PARAM_ANGLE_OPT(anglestart) { anglestart = 0.; } - PARAM_ANGLE_OPT(angleend) { angleend = 0.; } - PARAM_ANGLE_OPT(pitchstart) { pitchstart = 0.; } - PARAM_ANGLE_OPT(pitchend) { pitchend = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } + PARAM_ANGLE_DEF(anglestart) + PARAM_ANGLE_DEF(angleend) + PARAM_ANGLE_DEF(pitchstart) + PARAM_ANGLE_DEF(pitchend) + PARAM_INT_DEF(flags) + PARAM_INT_DEF(ptr) AActor *mobj = COPY_AAPTR(self, ptr); diff --git a/src/p_maputl.cpp b/src/p_maputl.cpp index a3d4d0e9e..04372f0ed 100644 --- a/src/p_maputl.cpp +++ b/src/p_maputl.cpp @@ -386,6 +386,14 @@ bool AActor::FixMapthingPos() return success; } +DEFINE_ACTION_FUNCTION(AActor, UnlinkFromWorld) +{ + PARAM_SELF_PROLOGUE(AActor); + self->UnlinkFromWorld(); + return 0; +} + + //========================================================================== // // P_SetThingPosition @@ -508,6 +516,13 @@ void AActor::LinkToWorld(bool spawningmapthing, sector_t *sector) if (!spawningmapthing) UpdateRenderSectorList(); } +DEFINE_ACTION_FUNCTION(AActor, LinkToWorld) +{ + PARAM_SELF_PROLOGUE(AActor); + self->LinkToWorld(); + return 0; +} + void AActor::SetOrigin(double x, double y, double z, bool moving) { UnlinkFromWorld (); diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d4ee11383..5148952a7 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -539,12 +539,13 @@ ExpEmit FxBoolCast::Emit(VMFunctionBuilder *build) // //========================================================================== -FxIntCast::FxIntCast(FxExpression *x, bool nowarn) +FxIntCast::FxIntCast(FxExpression *x, bool nowarn, bool explicitly) : FxExpression(EFX_IntCast, x->ScriptPosition) { basex=x; ValueType = TypeSInt32; NoWarn = nowarn; + Explicit = explicitly; } //========================================================================== @@ -571,9 +572,10 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) if (basex->ValueType->GetRegType() == REGT_INT) { - if (basex->ValueType != TypeName) + if (basex->ValueType != TypeName || Explicit) // names can be converted to int, but only with an explicit type cast. { FxExpression *x = basex; + x->ValueType = ValueType; basex = NULL; delete this; return x; @@ -582,7 +584,8 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) { // Ugh. This should abort, but too many mods fell into this logic hole somewhere, so this seroious error needs to be reduced to a warning. :( // At least in ZScript, MSG_OPTERROR always means to report an error, not a warning so the problem only exists in DECORATE. - if (!basex->isConstant()) ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got a name"); + if (!basex->isConstant()) + ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got a name"); else ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got \"%s\"", static_cast(basex)->GetValue().GetName().GetChars()); FxExpression * x = new FxConstant(0, ScriptPosition); delete this; @@ -1062,11 +1065,13 @@ ExpEmit FxSoundCast::Emit(VMFunctionBuilder *build) // //========================================================================== -FxTypeCast::FxTypeCast(FxExpression *x, PType *type, bool nowarn) +FxTypeCast::FxTypeCast(FxExpression *x, PType *type, bool nowarn, bool explicitly) : FxExpression(EFX_TypeCast, x->ScriptPosition) { basex = x; ValueType = type; + NoWarn = nowarn; + Explicit = explicitly; assert(ValueType != nullptr); } @@ -1126,7 +1131,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) else if (ValueType->IsA(RUNTIME_CLASS(PInt))) { // This is only for casting to actual ints. Subtypes representing an int will be handled elsewhere. - FxExpression *x = new FxIntCast(basex, NoWarn); + FxExpression *x = new FxIntCast(basex, NoWarn, Explicit); x = x->Resolve(ctx); basex = nullptr; delete this; @@ -4964,12 +4969,31 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) return x->Resolve(ctx); } - // Last but not least: Check builtins. The random functions can take a named RNG if specified. + // Last but not least: Check builtins and type casts. The random functions can take a named RNG if specified. // Note that for all builtins the used arguments have to be nulled in the ArgList so that they won't get deleted before they get used. FxExpression *func = nullptr; switch (MethodName) { + case NAME_Int: + case NAME_uInt: + case NAME_Double: + case NAME_Name: + case NAME_Color: + case NAME_Sound: + if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) + { + PType *type = MethodName == NAME_Int ? TypeSInt32 : + MethodName == NAME_uInt ? TypeUInt32 : + MethodName == NAME_Double ? TypeFloat64 : + MethodName == NAME_Name ? TypeName : + MethodName == NAME_Color ? TypeColor : (PType*)TypeSound; + + func = new FxTypeCast((*ArgList)[0], type, true, true); + (*ArgList)[0] = nullptr; + } + break; + case NAME_Random: if (CheckArgSize(NAME_Random, ArgList, 2, 2, ScriptPosition)) { @@ -5044,6 +5068,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) break; default: + // todo: Check for class type casts break; } if (func != nullptr) @@ -5216,8 +5241,11 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) for (unsigned i = 0; i < ArgList->Size(); i++) { (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); - if ((*ArgList)[i] == NULL) failed = true; - if (Special < 0 && i == 0) + if ((*ArgList)[i] == NULL) + { + failed = true; + } + else if (Special < 0 && i == 0) { if ((*ArgList)[i]->ValueType != TypeName) { @@ -5409,10 +5437,16 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) return nullptr; } - if (ArgList != NULL) + if (ArgList != nullptr) { bool foundvarargs = false; PType * type = nullptr; + if (ArgList->Size() + implicit > proto->ArgumentTypes.Size()) + { + ScriptPosition.Message(MSG_ERROR, "Too many arguments in call to %s", Function->SymbolName.GetChars()); + delete this; + return nullptr; + } for (unsigned i = 0; i < ArgList->Size(); i++) { // Varargs must all have the same type as the last typed argument. A_Jump is the only function using it. @@ -5476,24 +5510,23 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) assert(selfemit.RegType == REGT_POINTER); build->Emit(OP_PARAM, 0, selfemit.RegType, selfemit.RegNum); count += 1; - } - if (Function->Variants[0].Flags & VARF_Action) - { - static_assert(NAP == 3, "This code needs to be updated if NAP changes"); - if (build->IsActionFunc) + if (Function->Variants[0].Flags & VARF_Action) { - build->Emit(OP_PARAM, 0, REGT_POINTER, 1); - build->Emit(OP_PARAM, 0, REGT_POINTER, 2); + static_assert(NAP == 3, "This code needs to be updated if NAP changes"); + if (build->IsActionFunc && selfemit.RegNum == 0) // only pass this function's stateowner and stateinfo if the subfunction is run in self's context. + { + build->Emit(OP_PARAM, 0, REGT_POINTER, 1); + build->Emit(OP_PARAM, 0, REGT_POINTER, 2); + } + else + { + // pass self as stateowner, otherwise all attempts of the subfunction to retrieve a state from a name would fail. + build->Emit(OP_PARAM, 0, selfemit.RegType, selfemit.RegNum); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, build->GetConstantAddress(nullptr, ATAG_GENERIC)); + } + count += 2; } - else - { - int null = build->GetConstantAddress(nullptr, ATAG_GENERIC); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, null); - } - count += 2; } - // Emit code to pass explicit parameters if (ArgList != NULL) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index a55491a0b..cd93b8894 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -474,10 +474,11 @@ class FxIntCast : public FxExpression { FxExpression *basex; bool NoWarn; + bool Explicit; public: - FxIntCast(FxExpression *x, bool nowarn); + FxIntCast(FxExpression *x, bool nowarn, bool explicitly = false); ~FxIntCast(); FxExpression *Resolve(FCompileContext&); @@ -559,10 +560,11 @@ class FxTypeCast : public FxExpression { FxExpression *basex; bool NoWarn; + bool Explicit; public: - FxTypeCast(FxExpression *x, PType *type, bool nowarn); + FxTypeCast(FxExpression *x, PType *type, bool nowarn, bool explicitly = false); ~FxTypeCast(); FxExpression *Resolve(FCompileContext&); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index e04935f58..55cc03c0c 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -67,8 +67,8 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF, SPECIAL, APlayerPawn, flags), DEFINE_FLAG(MF, SOLID, AActor, flags), DEFINE_FLAG(MF, SHOOTABLE, AActor, flags), - DEFINE_READONLY_FLAG(MF, NOSECTOR, AActor, flags), - DEFINE_READONLY_FLAG(MF, NOBLOCKMAP, AActor, flags), + DEFINE_FLAG(MF, NOSECTOR, AActor, flags), + DEFINE_FLAG(MF, NOBLOCKMAP, AActor, flags), DEFINE_FLAG(MF, AMBUSH, AActor, flags), DEFINE_FLAG(MF, JUSTHIT, AActor, flags), DEFINE_FLAG(MF, JUSTATTACKED, AActor, flags), @@ -84,8 +84,8 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF, NOBLOOD, AActor, flags), DEFINE_FLAG(MF, CORPSE, AActor, flags), DEFINE_FLAG(MF, INFLOAT, AActor, flags), - DEFINE_READONLY_FLAG(MF, COUNTKILL, AActor, flags), - DEFINE_READONLY_FLAG(MF, COUNTITEM, AActor, flags), + DEFINE_FLAG(MF, COUNTKILL, AActor, flags), + DEFINE_FLAG(MF, COUNTITEM, AActor, flags), DEFINE_FLAG(MF, SKULLFLY, AActor, flags), DEFINE_FLAG(MF, NOTDMATCH, AActor, flags), DEFINE_FLAG(MF, SPAWNSOUNDSOURCE, AActor, flags), @@ -186,7 +186,7 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF5, GETOWNER, AActor, flags5), DEFINE_FLAG(MF5, NODROPOFF, AActor, flags5), DEFINE_FLAG(MF5, NOFORWARDFALL, AActor, flags5), - DEFINE_READONLY_FLAG(MF5, COUNTSECRET, AActor, flags5), + DEFINE_FLAG(MF5, COUNTSECRET, AActor, flags5), DEFINE_FLAG(MF5, NODAMAGE, AActor, flags5), DEFINE_FLAG(MF5, BLOODSPLATTER, AActor, flags5), DEFINE_FLAG(MF5, OLDRADIUSDMG, AActor, flags5), @@ -677,10 +677,20 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_ReactionTime, TypeSInt32, VARF_Native, myoffsetof(AActor, reactiontime))); symt.AddSymbol(new PField(NAME_MeleeRange, TypeFloat64, VARF_Native, myoffsetof(AActor, meleerange))); symt.AddSymbol(new PField(NAME_Speed, TypeFloat64, VARF_Native, myoffsetof(AActor, Speed))); - symt.AddSymbol(new PField(NAME_Threshold, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, threshold))); + symt.AddSymbol(new PField("FloatSpeed", TypeFloat64, VARF_Native, myoffsetof(AActor, FloatSpeed))); + symt.AddSymbol(new PField("PainThreshold", TypeSInt32, VARF_Native, myoffsetof(AActor, PainThreshold))); + symt.AddSymbol(new PField("spriteAngle", TypeFloat64, VARF_Native, myoffsetof(AActor, SpriteAngle))); + symt.AddSymbol(new PField("spriteRotation", TypeFloat64, VARF_Native, myoffsetof(AActor, SpriteRotation))); + symt.AddSymbol(new PField(NAME_Threshold, TypeSInt32, VARF_Native, myoffsetof(AActor, threshold))); symt.AddSymbol(new PField(NAME_DefThreshold, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DefThreshold))); symt.AddSymbol(new PField(NAME_Damage, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DamageVal))); symt.AddSymbol(new PField("visdir", TypeSInt32, VARF_Native, myoffsetof(AActor, visdir))); + symt.AddSymbol(new PField("Gravity", TypeFloat64, VARF_Native, myoffsetof(AActor, Gravity))); + symt.AddSymbol(new PField("DamageType", TypeName, VARF_Native, myoffsetof(AActor, DamageType))); + symt.AddSymbol(new PField("FloatBobPhase", TypeUInt8, VARF_Native, myoffsetof(AActor, FloatBobPhase))); + symt.AddSymbol(new PField("RipperLevel", TypeSInt32, VARF_Native, myoffsetof(AActor, RipperLevel))); + symt.AddSymbol(new PField("RipLevelMin", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMin))); + symt.AddSymbol(new PField("RipLevelMax", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMax))); symt.AddSymbol(new PField(NAME_VisibleStartAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartAngle))); symt.AddSymbol(new PField(NAME_VisibleStartPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartPitch))); symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); @@ -693,6 +703,8 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); + symt.AddSymbol(new PField("LastHeard", TypeActor, VARF_Native, myoffsetof(AActor, LastHeard))); + symt.AddSymbol(new PField("LastEnemy", TypeActor, VARF_Native, myoffsetof(AActor, lastenemy))); // synthesize a symbol for each flag. The bounce flags are excluded on purpose. for (size_t i = 0; i < countof(ActorFlagDefs); i++) diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index c6ff99d48..ae936b844 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -925,7 +925,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction // PARAM_INT_OPT(0,myint) { myint = 55; } // Just make sure to fill it in when using these macros, because the compiler isn't likely // to give useful error messages if you don't. -#define PARAM_EXISTS ((p) < numparam && param[p].Type != REGT_NIL) +#define PARAM_EXISTS(p) ((p) < numparam && param[p].Type != REGT_NIL) #define ASSERTINT(p) assert((p).Type == REGT_INT) #define ASSERTFLOAT(p) assert((p).Type == REGT_FLOAT) #define ASSERTSTRING(p) assert((p).Type == REGT_STRING) @@ -933,7 +933,18 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define ASSERTPOINTER(p) assert((p).Type == REGT_POINTER && (p).atag == ATAG_GENERIC) #define ASSERTSTATE(p) assert((p).Type == REGT_POINTER && ((p).atag == ATAG_GENERIC || (p).atag == ATAG_STATE)) -#define PARAM_INT_DEF_AT(p,x) int x; if (PARAM_EXISTS) { ASSERTINT(param[p]); x = param[p].i; } else { ASSERTINT(defaultparam[p]); x = defaultparam[p].i; } +#define PARAM_INT_DEF_AT(p,x) int x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = param[p].i; } else { ASSERTINT(defaultparam[p]); x = defaultparam[p].i; } +#define PARAM_BOOL_DEF_AT(p,x) bool x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = !!param[p].i; } else { ASSERTINT(defaultparam[p]); x = !!defaultparam[p].i; } +#define PARAM_NAME_DEF_AT(p,x) FName x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = ENamedName(param[p].i); } else { ASSERTINT(defaultparam[p]); x = ENamedName(defaultparam[p].i); } +#define PARAM_SOUND_DEF_AT(p,x) FSoundID x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = FSoundID(param[p].i); } else { ASSERTINT(defaultparam[p]); x = FSoundID(defaultparam[p].i); } +#define PARAM_COLOR_DEF_AT(p,x) PalEntry x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = param[p].i; } else { ASSERTINT(defaultparam[p]); x = defaultparam[p].i; } +#define PARAM_FLOAT_DEF_AT(p,x) double x; if (PARAM_EXISTS(p)) { ASSERTFLOAT(param[p]); x = param[p].f; } else { ASSERTFLOAT(defaultparam[p]); x = defaultparam[p].f; } +#define PARAM_ANGLE_DEF_AT(p,x) DAngle x; if (PARAM_EXISTS(p)) { ASSERTFLOAT(param[p]); x = param[p].f; } else { ASSERTFLOAT(defaultparam[p]); x = defaultparam[p].f; } +#define PARAM_STRING_DEF_AT(p,x) FString x; if (PARAM_EXISTS(p)) { ASSERTSTRING(param[p]); x = param[p].s; } else { ASSERTSTRING(defaultparam[p]); x = defaultparam[p].s; } +#define PARAM_STATE_DEF_AT(p,x) FState *x; if (PARAM_EXISTS(p)) { ASSERTSTATE(param[p]); x = (FState*)param[p].a; } else { ASSERTSTATE(defaultparam[p]); x = (FState*)defaultparam[p].a; } +#define PARAM_POINTER_DEF_AT(p,x,t) t *x; if (PARAM_EXISTS(p)) { ASSERTPOINTER(param[p]); x = (t*)param[p].a; } else { ASSERTPOINTER(defaultparam[p]); x = (t*)defaultparam[p].a; } +#define PARAM_OBJECT_DEF_AT(p,x,t) t *x; if (PARAM_EXISTS(p)) { ASSERTOBJECT(param[p]); x = (t*)param[p].a; } else { ASSERTOBJECT(defaultparam[p]); x = (t*)defaultparam[p].a; } +#define PARAM_CLASS_DEF_AT(p,x,t) t::MetaClass *x; if (PARAM_EXISTS(p)) { ASSERTOBJECT(param[p]); x = (t::MetaClass*)param[p].a; } else { ASSERTOBJECT(defaultparam[p]); x = (t::MetaClass*)defaultparam[p].a; } #define PARAM_INT_OPT_AT(p,x) int x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = param[p].i; } else #define PARAM_BOOL_OPT_AT(p,x) bool x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = !!param[p].i; } else @@ -1048,6 +1059,24 @@ struct AFuncDesc #define ACTION_CALL_FROM_PSPRITE() (self->player && stateinfo != nullptr && stateinfo->mStateType == STATE_Psprite) #define ACTION_CALL_FROM_INVENTORY() (stateinfo != nullptr && stateinfo->mStateType == STATE_StateChain) +// Standard parameters for all action functons +// self - Actor this action is to operate on (player if a weapon) +// stateowner - Actor this action really belongs to (may be an item) +// callingstate - State this action was called from +#define PARAM_ACTION_PROLOGUE(type) \ + PARAM_PROLOGUE; \ + PARAM_OBJECT (self, type); \ + PARAM_OBJECT_OPT (stateowner, AActor) { stateowner = self; } \ + PARAM_STATEINFO_OPT (stateinfo) { stateinfo = nullptr; } \ + +// Number of action paramaters +#define NAP 3 + +#define PARAM_SELF_PROLOGUE(type) \ + PARAM_PROLOGUE; \ + PARAM_OBJECT(self, type); + + class PFunction; PFunction *FindGlobalActionFunction(const char *name); diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index a5ad3ac00..4fbe29257 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -175,13 +175,13 @@ begin: OP(LO): ASSERTA(a); ASSERTA(B); ASSERTKD(C); GETADDR(PB,KC,X_READ_NIL); - reg.a[a] = *(void **)ptr; + reg.a[a] = GC::ReadBarrier(*(DObject **)ptr); reg.atag[a] = ATAG_OBJECT; NEXTOP; OP(LO_R): ASSERTA(a); ASSERTA(B); ASSERTD(C); GETADDR(PB,RC,X_READ_NIL); - reg.a[a] = *(void **)ptr; + reg.a[a] = GC::ReadBarrier(*(DObject **)ptr); reg.atag[a] = ATAG_OBJECT; NEXTOP; OP(LP): diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 3a1e734a4..370e65919 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2102,12 +2102,14 @@ void ZCCCompiler::InitFunctions() // TBD: disallow certain types? For now, let everything pass that isn't an array. args.Push(type); argflags.Push(flags); + argnames.Push(p->Name); } else { args.Push(nullptr); argflags.Push(0); + argnames.Push(NAME_None); } argdefaults.Push(vmval); p = static_cast(p->SiblingNext); @@ -2120,7 +2122,7 @@ void ZCCCompiler::InitFunctions() if (!(f->Flags & ZCC_Native)) { - auto code = ConvertAST(f->Body); + auto code = ConvertAST(c->Type(), f->Body); if (code != nullptr) { sym->Variants[0].Implementation = FunctionBuildList.AddFunction(sym, code, FStringf("%s.%s", c->Type()->TypeName.GetChars(), FName(f->Name).GetChars()), false); @@ -2157,7 +2159,7 @@ static bool CheckRandom(ZCC_Expression *duration) // Sets up the action function call // //========================================================================== -FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *af) +FxExpression *ZCCCompiler::SetupActionFunction(PClass *cls, ZCC_TreeNode *af) { // We have 3 cases to consider here: // 1. An action function without parameters. This can be called directly @@ -2197,8 +2199,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClassActor *cls, ZCC_TreeNode *a } } } - ConvertClass = cls; - return ConvertAST(af); + return ConvertAST(cls, af); } //========================================================================== @@ -2419,8 +2420,9 @@ void ZCCCompiler::CompileStates() // //========================================================================== -FxExpression *ZCCCompiler::ConvertAST(ZCC_TreeNode *ast) +FxExpression *ZCCCompiler::ConvertAST(PClass *cls, ZCC_TreeNode *ast) { + ConvertClass = cls; // there are two possibilities here: either a single function call or a compound statement. For a compound statement we also need to check if the last thing added was a return. if (ast->NodeType == AST_ExprFuncCall) { @@ -2680,6 +2682,9 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_LTGTEQ: return new FxLtGtEq(left, right); + case PEX_ArrayAccess: + return new FxArrayElement(left, right); + // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_Concat: case PEX_Is: diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index cf2775834..4ad72769a 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -109,7 +109,7 @@ private: void InitFunctions(); void CompileStates(); - FxExpression *SetupActionFunction(PClassActor *cls, ZCC_TreeNode *sl); + FxExpression *SetupActionFunction(PClass *cls, ZCC_TreeNode *sl); bool SimplifyingConstant; TArray Constants; @@ -140,7 +140,7 @@ private: void Error(ZCC_TreeNode *node, const char *msg, ...); void MessageV(ZCC_TreeNode *node, const char *txtcolor, const char *msg, va_list argptr); - FxExpression *ConvertAST(ZCC_TreeNode *ast); + FxExpression *ConvertAST(PClass *cclass, ZCC_TreeNode *ast); FxExpression *ConvertNode(ZCC_TreeNode *node); FArgumentList *ConvertNodeList(ZCC_TreeNode *head); diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 706acaee7..4f859d3b0 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -47,6 +47,13 @@ class Actor : Thinker native } // Functions + + bool IsPointerEqual(int ptr_select1, int ptr_select2) + { + return GetPointer(ptr_select1) == GetPointer(ptr_select2); + } + + native Actor GetPointer(int aaptr); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); native void TraceBleed(int damage, Actor missile); native bool CheckMeleeRange(); @@ -56,11 +63,11 @@ class Actor : Thinker native native bool CheckSight(Actor target, int flags = 0); native bool HitFriend(); native bool SetState(state st, bool nofunction = false); + native void LinkToWorld(); + native void UnlinkFromWorld(); - // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); - native bool IsPointerEqual(int ptr_select1, int ptr_select2); native int CountInv(class itemtype, int ptr_select = AAPTR_DEFAULT); native float GetDistance(bool checkz, int ptr = AAPTR_DEFAULT); native float GetAngle(int flags, int ptr = AAPTR_DEFAULT); @@ -78,9 +85,89 @@ class Actor : Thinker native action native float OverlayX(int layer = 0); action native float OverlayY(int layer = 0); + // DECORATE setters - it probably makes more sense to set these values directly now... + void A_SetMass(int newmass) { mass = newmass; } + void A_SetGravity(float newgravity) { gravity = clamp(newgravity, 0., 10.); } + void A_SetArg(int arg, int val) { if (arg >= 0 && arg < 5) args[arg] = val; } + void A_Turn(float turn = 0) { angle += turn; } + void A_SetDamageType(name newdamagetype) { damagetype = newdamagetype; } + void A_SetSolid() { bSolid = true; } + void A_UnsetSolid() { bSolid = false; } + void A_SetFloat() { bFloat = true; } + void A_UnsetFloat() { bFloat = false; } + void A_SetFloatBobPhase(int bob) { if (bob >= 0 && bob <= 63) FloatBobPhase = bob; } + void A_SetRipperLevel(int level) { RipperLevel = level; } + void A_SetRipMin(int minimum) { RipLevelMin = minimum; } + void A_SetRipMax(int maximum) { RipLevelMax = maximum; } + + void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false) + { + Actor aptr = GetPointer(ptr); + if (aptr) + { + aptr.Scale.X = scalex; + aptr.Scale.Y = scaley != 0 || usezero? scaley : scalex; // use scalex here, too, if only one parameter. + } + } + void A_SetSpeed(float speed, int ptr = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr); + if (aptr) aptr.Speed = speed; + } + void A_SetFloatSpeed(float speed, int ptr = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr); + if (aptr) aptr.FloatSpeed = speed; + } + void A_SetPainThreshold(int threshold, int ptr = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr); + if (aptr) aptr.PainThreshold = threshold; + } + bool A_SetSpriteAngle(float angle = 0, int ptr = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr); + if (!aptr) return false; + aptr.SpriteAngle = angle; + return true; + } + bool A_SetSpriteRotation(float angle = 0, int ptr = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr); + if (!aptr) return false; + aptr.SpriteRotation = angle; + return true; + } + + deprecated void A_FaceConsolePlayer(float MaxTurnAngle = 0) {} + + void A_SetSpecial(int spec, int arg0 = 0, int arg1 = 0, int arg2 = 0, int arg3 = 0, int arg4 = 0) + { + special = spec; + args[0] = arg0; + args[1] = arg1; + args[2] = arg2; + args[3] = arg3; + args[4] = arg4; + } + + void A_ClearTarget() + { + target = null; + lastheard = null; + lastenemy = null; + } + + void A_ChangeLinkFlags(int blockmap = FLAG_NO_CHANGE, int sector = FLAG_NO_CHANGE) + { + UnlinkFromWorld(); + if (blockmap != FLAG_NO_CHANGE) bNoBlockmap = blockmap; + if (sector != FLAG_NO_CHANGE) bNoSector = sector; + LinkToWorld(); + } + // Action functions // Meh, MBF redundant functions. Only for DeHackEd support. - native void A_Turn(float angle = 0); native bool A_LineEffect(int boomspecial = 0, int tag = 0); // End of MBF redundant functions. @@ -121,9 +208,9 @@ class Actor : Thinker native native void A_BrainScream(); native void A_BrainDie(); native void A_BrainAwake(); - native void A_BrainSpit(class spawntype = "none"); // needs special treatment for default + native void A_BrainSpit(class spawntype = null); // needs special treatment for default native void A_SpawnSound(); - native void A_SpawnFly(class spawntype = "none"); // needs special treatment for default + native void A_SpawnFly(class spawntype = null); // needs special treatment for default native void A_BrainExplode(); native void A_Die(name damagetype = "none"); native void A_Detonate(); @@ -145,12 +232,8 @@ class Actor : Thinker native native void A_NoGravity(); native void A_Gravity(); native void A_LowGravity(); - native void A_SetGravity(float gravity); + native void A_Fall(); - native void A_SetSolid(); - native void A_UnsetSolid(); - native void A_SetFloat(); - native void A_UnsetFloat(); native void A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); @@ -186,7 +269,6 @@ class Actor : Thinker native native void A_ClearSoundTarget(); native void A_FireAssaultGun(); native void A_CheckTerrain(); - native void A_FaceConsolePlayer(float MaxTurnAngle = 0); // [TP] no-op deprecated native void A_MissileAttack(); deprecated native void A_MeleeAttack(); @@ -194,7 +276,7 @@ class Actor : Thinker native deprecated native void A_BulletAttack(); native void A_WolfAttack(int flags = 0, sound whattoplay = "weapons/pistol", float snipe = 1.0, int maxdamage = 64, int blocksize = 128, int pointblank = 2, int longrange = 4, float runspeed = 160.0, class pufftype = "BulletPuff"); native void A_PlaySound(sound whattoplay = "weapons/pistol", int slot = CHAN_BODY, float volume = 1.0, bool looping = false, float attenuation = ATTN_NORM); - native void A_PlayWeaponSound(sound whattoplay); + deprecated void A_PlayWeaponSound(sound whattoplay) { A_PlaySound(whattoplay, CHAN_WEAPON); } native void A_FLoopActiveSound(); native void A_LoopActiveSound(); native void A_StopSound(int slot = CHAN_VOICE); // Bad default but that's what is originally was... @@ -204,7 +286,7 @@ class Actor : Thinker native native state A_Jump(int chance = 256, state label, ...); native void A_CustomMissile(class missiletype, float spawnheight = 32, float spawnofs_xy = 0, float angle = 0, int flags = 0, float pitch = 0, int ptr = AAPTR_TARGET); native void A_CustomBulletAttack(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); - native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = 0, color color2 = 0, int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); + native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = 0, color color2 = 0, int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = null, float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); native state A_JumpIfHealthLower(int health, state label, int ptr_selector = AAPTR_DEFAULT); native state A_JumpIfCloser(float distance, state label, bool noz = false); native state A_JumpIfTracerCloser(float distance, state label, bool noz = false); @@ -213,6 +295,7 @@ class Actor : Thinker native native state A_JumpIfTargetInsideMeleeRange(state label); native state A_JumpIfInventory(class itemtype, int itemamount, state label, int owner = AAPTR_DEFAULT); native state A_JumpIfArmorType(name Type, state label, int amount = 1); + native bool A_SetInventory(class itemtype, int amount, int ptr = AAPTR_DEFAULT, bool beyondMax = false); native bool A_GiveInventory(class itemtype, int amount = 0, int giveto = AAPTR_DEFAULT); native bool A_TakeInventory(class itemtype, int amount = 0, int flags = 0, int giveto = AAPTR_DEFAULT); action native bool A_SpawnItem(class itemtype = "Unknown", float distance = 0, float zheight = 0, bool useammo = true, bool transfer_translation = false); @@ -227,8 +310,6 @@ class Actor : Thinker native native void A_FadeIn(float reduce = 0.1, int flags = 0); native void A_FadeOut(float reduce = 0.1, int flags = 1); //bool remove == true native void A_FadeTo(float target, float amount = 0.1, int flags = 0); - native void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false); - native void A_SetMass(int mass); native void A_SpawnDebris(class spawntype, bool transfer_translation = false, float mult_h = 1, float mult_v = 1); native void A_SpawnParticle(color color1, int flags = 0, int lifetime = 35, float size = 1, float angle = 0, float xoff = 0, float yoff = 0, float zoff = 0, float velx = 0, float vely = 0, float velz = 0, float accelx = 0, float accely = 0, float accelz = 0, float startalphaf = 1, float fadestepf = -1, float sizestep = 0); native state A_CheckSight(state label); @@ -238,7 +319,6 @@ class Actor : Thinker native deprecated native void A_ChangeFlag(string flagname, bool value); deprecated native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); native void A_ChangeCountFlags(int kill = FLAG_NO_CHANGE, int item = FLAG_NO_CHANGE, int secret = FLAG_NO_CHANGE); - native void A_ChangeLinkFlags(int blockmap = FLAG_NO_CHANGE, int sector = FLAG_NO_CHANGE); native state A_JumpIf(bool expression, state label); native void A_RaiseMaster(bool copy = 0); native void A_RaiseChildren(bool copy = 0); @@ -247,7 +327,7 @@ class Actor : Thinker native native state A_CheckCeiling(state label); native state A_PlayerSkinCheck(state label); deprecated native void A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); - native state, bool A_Teleport(state teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 0, int ptr = AAPTR_DEFAULT); + native state, bool A_Teleport(state teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 128, int ptr = AAPTR_DEFAULT); native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = null, float heightoffset = 0, float radiusoffset = 0, float pitch = 0); action native bool A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); @@ -256,7 +336,7 @@ class Actor : Thinker native native state A_JumpIfInTargetInventory(class itemtype, int amount, state label, int forward_ptr = AAPTR_DEFAULT); native bool A_GiveToTarget(class itemtype, int amount = 0, int forward_ptr = AAPTR_DEFAULT); native bool A_TakeFromTarget(class itemtype, int amount = 0, int flags = 0, int forward_ptr = AAPTR_DEFAULT); - native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = "None", name species = "None", float mindist = 0, int limit = 0); + native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = null, name species = "None", float mindist = 0, int limit = 0); native state A_CheckSpecies(state jump, name species = 'none', int ptr = AAPTR_DEFAULT); native void A_CountdownArg(int argnum, state targstate = null); native void A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); @@ -264,7 +344,7 @@ class Actor : Thinker native native void A_Burst(class chunktype); action native void A_Blast(int flags = 0, float strength = 255, float radius = 255, float speed = 20, class blasteffect = "BlastEffect", sound blastsound = "BlastRadius"); native void A_RadiusThrust(int force = 128, int distance = -1, int flags = RTF_AFFECTSOURCE, int fullthrustdistance = 0); - native void A_RadiusDamageSelf(int damage = 128, float distance = 128, int flags = 0, class flashtype = "None"); + native void A_RadiusDamageSelf(int damage = 128, float distance = 128, int flags = 0, class flashtype = null); native int A_Explode(int damage = -1, int distance = -1, int flags = XF_HURTSOURCE, bool alert = false, int fulldamagedistance = 0, int nails = 0, int naildamage = 10, class pufftype = "BulletPuff", name damagetype = "none"); native void A_Stop(); native void A_Respawn(int flags = 1); @@ -273,7 +353,6 @@ class Actor : Thinker native native void A_DeQueueCorpse(); native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = null); native void A_ClearLastHeard(); - native void A_ClearTarget(); native state A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); native state A_JumpIfTargetInLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); native state A_JumpIfInTargetLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); @@ -295,51 +374,41 @@ class Actor : Thinker native native void A_SetRoll(float roll, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_ScaleVelocity(float scale, int ptr = AAPTR_DEFAULT); native void A_ChangeVelocity(float x = 0, float y = 0, float z = 0, int flags = 0, int ptr = AAPTR_DEFAULT); - native void A_SetArg(int pos, int value); deprecated native void A_SetUserVar(name varname, int value); deprecated native void A_SetUserArray(name varname, int index, int value); deprecated native void A_SetUserVarFloat(name varname, float value); deprecated native void A_SetUserArrayFloat(name varname, int index, float value); - native void A_SetSpecial(int spec, int arg0 = 0, int arg1 = 0, int arg2 = 0, int arg3 = 0, int arg4 = 0); native void A_Quake(int intensity, int duration, int damrad, int tremrad, sound sfx = "world/quake"); native void A_QuakeEx(int intensityX, int intensityY, int intensityZ, int duration, int damrad, int tremrad, sound sfx = "world/quake", int flags = 0, float mulWaveX = 1, float mulWaveY = 1, float mulWaveZ = 1, int falloff = 0, int highpoint = 0, float rollIntensity = 0, float rollWave = 0); action native void A_SetTics(int tics); - native void A_SetDamageType(name damagetype); native void A_DropItem(class item, int dropamount = -1, int chance = 256); - native void A_SetSpeed(float speed, int ptr = AAPTR_DEFAULT); - native void A_SetFloatSpeed(float speed, int ptr = AAPTR_DEFAULT); - native void A_SetPainThreshold(int threshold, int ptr = AAPTR_DEFAULT); - native void A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_KillTarget(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_KillMaster(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_KillTracer(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_KillChildren(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_KillSiblings(name damagetype = "none", int flags = 0, class filter = "None", name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); - native void A_RemoveTarget(int flags = 0, class filter = "None", name species = "None"); - native void A_RemoveMaster(int flags = 0, class filter = "None", name species = "None"); - native void A_RemoveTracer(int flags = 0, class filter = "None", name species = "None"); - native void A_RemoveChildren(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); - native void A_RemoveSiblings(bool removeall = false, int flags = 0, class filter = "None", name species = "None"); - native void A_Remove(int removee, int flags = 0, class filter = "None", name species = "None"); + native void A_DamageSelf(int amount, name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageTarget(int amount, name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageMaster(int amount, name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageTracer(int amount, name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageChildren(int amount, name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_DamageSiblings(int amount, name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillTarget(name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillMaster(name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillTracer(name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillChildren(name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_KillSiblings(name damagetype = "none", int flags = 0, class filter = null, name species = "None", int src = AAPTR_DEFAULT, int inflict = AAPTR_DEFAULT); + native void A_RemoveTarget(int flags = 0, class filter = null, name species = "None"); + native void A_RemoveMaster(int flags = 0, class filter = null, name species = "None"); + native void A_RemoveTracer(int flags = 0, class filter = null, name species = "None"); + native void A_RemoveChildren(bool removeall = false, int flags = 0, class filter = null, name species = "None"); + native void A_RemoveSiblings(bool removeall = false, int flags = 0, class filter = null, name species = "None"); + native void A_Remove(int removee, int flags = 0, class filter = null, name species = "None"); native int A_GiveToChildren(class itemtype, int amount = 0); native int A_GiveToSiblings(class itemtype, int amount = 0); native int A_TakeFromChildren(class itemtype, int amount = 0); native int A_TakeFromSiblings(class itemtype, int amount = 0); native void A_SetTeleFog(class oldpos, class newpos); native void A_SwapTeleFog(); - native void A_SetFloatBobPhase(int bob); native void A_SetHealth(int health, int ptr = AAPTR_DEFAULT); native void A_ResetHealth(int ptr = AAPTR_DEFAULT); native state A_JumpIfHigherOrLower(state high, state low, float offsethigh = 0, float offsetlow = 0, bool includeHeight = true, int ptr = AAPTR_TARGET); native void A_SetSpecies(name species, int ptr = AAPTR_DEFAULT); - native void A_SetRipperLevel(int level); - native void A_SetRipMin(int mininum); - native void A_SetRipMax(int maximum); native void A_SetChaseThreshold(int threshold, bool def = false, int ptr = AAPTR_DEFAULT); native state A_CheckProximity(state jump, class classname, float distance, int count = 1, int flags = 0, int ptr = AAPTR_DEFAULT); native state A_CheckBlock(state block, int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0); @@ -348,8 +417,6 @@ class Actor : Thinker native native bool A_FaceMovementDirection(float offset = 0, float anglelimit = 0, float pitchlimit = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native int A_ClearOverlays(int sstart = 0, int sstop = 0, bool safety = true); native bool A_CopySpriteFrame(int from, int to, int flags = 0); - native bool A_SetSpriteAngle(float angle = 0, int ptr = AAPTR_DEFAULT); - native bool A_SetSpriteRotation(float angle = 0, int ptr = AAPTR_DEFAULT); native bool A_SetVisibleRotation(float anglestart = 0, float angleend = 0, float pitchstart = 0, float pitchend = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetTranslation(string transname); @@ -362,13 +429,34 @@ class Actor : Thinker native action native void A_OverlayOffset(int layer = PSP_WEAPON, float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayFlags(int layer, int flags, bool set); - native int ACS_NamedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); - native int ACS_NamedSuspend(name script, int mapnum=0); - native int ACS_NamedTerminate(name script, int mapnum=0); - native int ACS_NamedLockedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0); - native int ACS_NamedLockedExecuteDoor(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0); - native int ACS_NamedExecuteWithResult(name script, int arg1=0, int arg2=0, int arg3=0, int arg4=0); - native void ACS_NamedExecuteAlways(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0); + int ACS_NamedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0) + { + return ACS_Execute(-int(script), mapnum, arg1, arg2, arg3); + } + int ACS_NamedSuspend(name script, int mapnum=0) + { + return ACS_Suspend(-int(script), mapnum); + } + int ACS_NamedTerminate(name script, int mapnum=0) + { + return ACS_Terminate(-int(script), mapnum); + } + int ACS_NamedLockedExecute(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0) + { + return ACS_LockedExecute(-int(script), mapnum, arg1, arg2, lock); + } + int ACS_NamedLockedExecuteDoor(name script, int mapnum=0, int arg1=0, int arg2=0, int lock=0) + { + return ACS_LockedExecuteDoor(-int(script), mapnum, arg1, arg2, lock); + } + int ACS_NamedExecuteWithResult(name script, int arg1=0, int arg2=0, int arg3=0, int arg4=0) + { + return ACS_ExecuteWithResult(-int(script), arg1, arg2, arg3, arg4); + } + int ACS_NamedExecuteAlways(name script, int mapnum=0, int arg1=0, int arg2=0, int arg3=0) + { + return ACS_ExecuteAlways(-int(script), mapnum, arg1, arg2, arg3); + } States { diff --git a/wadsrc/static/zscript/heretic/hereticweaps.txt b/wadsrc/static/zscript/heretic/hereticweaps.txt index 0c3123c7c..ae5e97179 100644 --- a/wadsrc/static/zscript/heretic/hereticweaps.txt +++ b/wadsrc/static/zscript/heretic/hereticweaps.txt @@ -479,7 +479,7 @@ class Gauntlets : Weapon GAUN A 1 A_Raise; Loop; Fire: - GAUN B 4 A_PlayWeaponSound("weapons/gauntletsuse"); + GAUN B 4 A_PlaySound("weapons/gauntletsuse", CHAN_WEAPON); GAUN C 4; Hold: GAUN DEF 4 BRIGHT A_GauntletAttack(0); @@ -512,7 +512,7 @@ class GauntletsPowered : Gauntlets GAUN G 1 A_Raise; Loop; Fire: - GAUN J 4 A_PlayWeaponSound("weapons/gauntletsuse"); + GAUN J 4 A_PlaySound("weapons/gauntletsuse", CHAN_WEAPON); GAUN K 4; Hold: GAUN LMN 4 BRIGHT A_GauntletAttack(1); diff --git a/wadsrc/static/zscript/hexen/wraith.txt b/wadsrc/static/zscript/hexen/wraith.txt index 9d811ec5c..86df72d94 100644 --- a/wadsrc/static/zscript/hexen/wraith.txt +++ b/wadsrc/static/zscript/hexen/wraith.txt @@ -52,7 +52,7 @@ class Wraith : Actor Missile: WRTH E 6 A_FaceTarget; WRTH F 6; - WRTH G 6 A_CustomMissile("WraithFX1", 32, 0); + WRTH G 6 A_CustomMissile("WraithFX1"); Goto See; Death: WRTH I 4; From c7347608a4db5f05c46686dba6494d6f442a8496 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 27 Oct 2016 17:47:46 +0200 Subject: [PATCH 121/255] - scriptified A_FatAttack*. - swapped parameters of two-parameter VelToAngle method, so that internal and script version are in line. - fixed parameter asserts to handle NULL pointers properly. --- src/actor.h | 2 +- src/g_doom/a_fatso.cpp | 93 ---------------------------- src/g_hexen/a_bats.cpp | 2 +- src/g_hexen/a_clericflame.cpp | 2 +- src/g_raven/a_minotaur.cpp | 2 +- src/g_strife/a_entityboss.cpp | 2 +- src/g_strife/a_strifeweapons.cpp | 4 +- src/info.cpp | 2 +- src/p_actionfunctions.cpp | 20 +++--- src/p_enemy.cpp | 12 +--- src/p_interaction.cpp | 4 +- src/p_map.cpp | 14 ++--- src/p_mobj.cpp | 27 +++++++- src/scripting/vm/vm.h | 20 ++---- src/scripting/vm/vmexec.cpp | 2 +- wadsrc/static/zscript/actor.txt | 12 ++-- wadsrc/static/zscript/constants.txt | 14 +++++ wadsrc/static/zscript/doom/fatso.txt | 72 +++++++++++++++++++++ 18 files changed, 152 insertions(+), 154 deletions(-) diff --git a/src/actor.h b/src/actor.h index 3f7c1178e..df5ef3c17 100644 --- a/src/actor.h +++ b/src/actor.h @@ -1366,7 +1366,7 @@ public: Vel.Y = speed * Angles.Yaw.Sin(); } - void VelFromAngle(DAngle angle, double speed) + void VelFromAngle(double speed, DAngle angle) { Vel.X = speed * angle.Cos(); Vel.Y = speed * angle.Sin(); diff --git a/src/g_doom/a_fatso.cpp b/src/g_doom/a_fatso.cpp index d84046104..d373a7a08 100644 --- a/src/g_doom/a_fatso.cpp +++ b/src/g_doom/a_fatso.cpp @@ -15,99 +15,6 @@ // firing three missiles in three different directions? // Doesn't look like it. // -#define FATSPREAD (90./8) - -DEFINE_ACTION_FUNCTION(AActor, A_FatRaise) -{ - PARAM_SELF_PROLOGUE(AActor); - - A_FaceTarget (self); - S_Sound (self, CHAN_WEAPON, "fatso/raiseguns", 1, ATTN_NORM); - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack1) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } - - AActor *missile; - - if (!self->target) - return 0; - - if (spawntype == NULL) spawntype = PClass::FindActor("FatShot"); - - A_FaceTarget (self); - // Change direction to ... - self->Angles.Yaw += FATSPREAD; - P_SpawnMissile (self, self->target, spawntype); - - missile = P_SpawnMissile (self, self->target, spawntype); - if (missile != NULL) - { - missile->Angles.Yaw += FATSPREAD; - missile->VelFromAngle(); - } - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack2) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } - - AActor *missile; - - if (!self->target) - return 0; - - if (spawntype == NULL) spawntype = PClass::FindActor("FatShot"); - - A_FaceTarget (self); - // Now here choose opposite deviation. - self->Angles.Yaw -= FATSPREAD; - P_SpawnMissile (self, self->target, spawntype); - - missile = P_SpawnMissile (self, self->target, spawntype); - if (missile != NULL) - { - missile->Angles.Yaw -= FATSPREAD*2; - missile->VelFromAngle(); - } - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack3) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } - - AActor *missile; - - if (!self->target) - return 0; - - if (spawntype == NULL) spawntype = PClass::FindActor("FatShot"); - - A_FaceTarget (self); - - missile = P_SpawnMissile (self, self->target, spawntype); - if (missile != NULL) - { - missile->Angles.Yaw -= FATSPREAD/2; - missile->VelFromAngle(); - } - - missile = P_SpawnMissile (self, self->target, spawntype); - if (missile != NULL) - { - missile->Angles.Yaw += FATSPREAD/2; - missile->VelFromAngle(); - } - return 0; -} - // // killough 9/98: a mushroom explosion effect, sorta :) // Original idea: Linguica diff --git a/src/g_hexen/a_bats.cpp b/src/g_hexen/a_bats.cpp index 5be91b69b..02fc6111e 100644 --- a/src/g_hexen/a_bats.cpp +++ b/src/g_hexen/a_bats.cpp @@ -84,7 +84,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatMove) } // Adjust velocity vector to new direction - self->VelFromAngle(newangle, self->Speed); + self->VelFromAngle(self->Speed, newangle); if (pr_batmove()<15) { diff --git a/src/g_hexen/a_clericflame.cpp b/src/g_hexen/a_clericflame.cpp index b03b9b6b9..56267b8e6 100644 --- a/src/g_hexen/a_clericflame.cpp +++ b/src/g_hexen/a_clericflame.cpp @@ -162,7 +162,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlameRotate) PARAM_SELF_PROLOGUE(AActor); DAngle an = self->Angles.Yaw + 90.; - self->VelFromAngle(an, FLAMEROTSPEED); + self->VelFromAngle(FLAMEROTSPEED, an); self->Vel += DVector2(self->specialf1, self->specialf2); self->Angles.Yaw += 6.; diff --git a/src/g_raven/a_minotaur.cpp b/src/g_raven/a_minotaur.cpp index 8bdbe122b..209afc9f4 100644 --- a/src/g_raven/a_minotaur.cpp +++ b/src/g_raven/a_minotaur.cpp @@ -415,7 +415,7 @@ void P_MinotaurSlam (AActor *source, AActor *target) angle = source->AngleTo(target); thrust = 16 + pr_minotaurslam() / 64.; - target->VelFromAngle(angle, thrust); + target->VelFromAngle(thrust, angle); damage = pr_minotaurslam.HitDice (static_cast(source) ? 4 : 6); int newdam = P_DamageMobj (target, NULL, NULL, damage, NAME_Melee); P_TraceBleed (newdam > 0 ? newdam : damage, target, angle, 0.); diff --git a/src/g_strife/a_entityboss.cpp b/src/g_strife/a_entityboss.cpp index 84a4b3fa3..535022901 100644 --- a/src/g_strife/a_entityboss.cpp +++ b/src/g_strife/a_entityboss.cpp @@ -109,7 +109,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_EntityDeath) second = Spawn("EntitySecond", pos, ALLOW_REPLACE); second->CopyFriendliness(self, true); A_FaceTarget(second); - second->VelFromAngle(an, velmul[i]); + second->VelFromAngle(velmul[i], an); } return 0; } diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index 91f4ac75e..f80f3e863 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -988,7 +988,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil1) spot = Spawn("SpectralLightningSpot", self->Pos(), ALLOW_REPLACE); if (spot != NULL) { - spot->VelFromAngle(self->Angles.Yaw, 28.); + spot->VelFromAngle(28., self->Angles.Yaw); } } if (spot != NULL) @@ -1089,7 +1089,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil4) spot = P_SpawnPlayerMissile (self, PClass::FindActor("SpectralLightningBigV1")); if (spot != NULL) { - spot->VelFromAngle(self->Angles.Yaw, spot->Speed); + spot->VelFromAngle(spot->Speed, self->Angles.Yaw); } } return 0; diff --git a/src/info.cpp b/src/info.cpp index 268d4f91c..26bd306fa 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -78,7 +78,7 @@ bool FState::CallAction(AActor *self, AActor *stateowner, FStateParamInfo *info, ActionCycles.Clock(); VMFrameStack stack; - VMValue params[3] = { self, stateowner, VMValue(info, ATAG_STATEINFO) }; + VMValue params[3] = { self, stateowner, VMValue(info, ATAG_GENERIC) }; // If the function returns a state, store it at *stateret. // If it doesn't return a state but stateret is non-NULL, we need // to set *stateret to NULL. diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index a4f49607f..fd67e0a64 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -137,7 +137,7 @@ bool ACustomInventory::CallStateChain (AActor *actor, FState *state) VMReturn *wantret; FStateParamInfo stp = { state, STATE_StateChain, PSP_WEAPON }; - params[2] = VMValue(&stp, ATAG_STATEINFO); + params[2] = VMValue(&stp, ATAG_GENERIC); retval = true; // assume success wantret = NULL; // assume no return value wanted numret = 0; @@ -4218,15 +4218,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) PARAM_SELF_PROLOGUE(AActor); PARAM_STATE (jump); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_FLOAT_OPT (minrange) { minrange = 0; } - PARAM_ANGLE_OPT (angle) { angle = 0.; } - PARAM_ANGLE_OPT (pitch) { pitch = 0.; } - PARAM_FLOAT_OPT (offsetheight) { offsetheight = 0; } - PARAM_FLOAT_OPT (offsetwidth) { offsetwidth = 0; } - PARAM_INT_OPT (ptr_target) { ptr_target = AAPTR_DEFAULT; } - PARAM_FLOAT_OPT (offsetforward) { offsetforward = 0; } + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (range) + PARAM_FLOAT_DEF (minrange) + PARAM_ANGLE_DEF (angle) + PARAM_ANGLE_DEF (pitch) + PARAM_FLOAT_DEF (offsetheight) + PARAM_FLOAT_DEF (offsetwidth) + PARAM_INT_DEF (ptr_target) + PARAM_FLOAT_DEF (offsetforward) DAngle ang; diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index fbdc1a212..3f5570681 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -2500,7 +2500,7 @@ void A_DoChase (VMFrameStack *stack, AActor *actor, bool fastchase, FState *mele DAngle ang = actor->AngleTo(actor->target); if (pr_chase() < 128) ang += 90.; else ang -= 90.; - actor->VelFromAngle(ang, 13.); + actor->VelFromAngle(13., ang); actor->FastChaseStrafeCount = 3; // strafe time } } @@ -3315,16 +3315,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_Pain) return 0; } -// killough 11/98: kill an object -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Die) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_NAME_OPT (damagetype) { damagetype = NAME_None; } - - P_DamageMobj(self, NULL, NULL, self->health, damagetype, DMG_FORCED); - return 0; -} - // // A_Detonate // killough 8/9/98: same as A_Explode, except that the damage is variable diff --git a/src/p_interaction.cpp b/src/p_interaction.cpp index f3d02428d..b4ecc827e 100644 --- a/src/p_interaction.cpp +++ b/src/p_interaction.cpp @@ -1562,8 +1562,8 @@ DEFINE_ACTION_FUNCTION(AActor, DamageMobj) PARAM_OBJECT(source, AActor); PARAM_INT(damage); PARAM_NAME(mod); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_FLOAT_OPT(angle) { angle = 0; } + PARAM_INT_DEF(flags); + PARAM_FLOAT_DEF(angle); ACTION_RETURN_INT(P_DamageMobj(self, inflictor, source, damage, mod, flags, angle)); } diff --git a/src/p_map.cpp b/src/p_map.cpp index ef46f6566..a2e83b73f 100644 --- a/src/p_map.cpp +++ b/src/p_map.cpp @@ -4048,11 +4048,11 @@ DEFINE_ACTION_FUNCTION(AActor, AimLineAttack) PARAM_SELF_PROLOGUE(AActor); PARAM_ANGLE(angle); PARAM_FLOAT(distance); - PARAM_POINTER_OPT(pLineTarget, FTranslatedLineTarget) { pLineTarget = nullptr; } - PARAM_ANGLE_OPT(vrange) { vrange = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_OBJECT_OPT(target, AActor) { target = nullptr; } - PARAM_OBJECT_OPT(friender, AActor) { friender = nullptr; } + PARAM_POINTER_DEF(pLineTarget, FTranslatedLineTarget); + PARAM_ANGLE_DEF(vrange); + PARAM_INT_DEF(flags); + PARAM_OBJECT_DEF(target, AActor); + PARAM_OBJECT_DEF(friender, AActor); ACTION_RETURN_FLOAT(P_AimLineAttack(self, angle, distance, pLineTarget, vrange, flags, target, friender).Degrees); } @@ -4431,8 +4431,8 @@ DEFINE_ACTION_FUNCTION(AActor, LineAttack) PARAM_INT(damage); PARAM_NAME(damageType); PARAM_CLASS(puffType, AActor); - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_POINTER_OPT(victim, FTranslatedLineTarget) { victim = nullptr; } + PARAM_INT_DEF(flags); + PARAM_POINTER_DEF(victim, FTranslatedLineTarget); int acdmg; auto puff = P_LineAttack(self, angle, distance, pitch, damage, damageType, puffType, flags, victim, &acdmg); diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 7398fa29f..7d37e3546 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -5838,7 +5838,7 @@ DEFINE_ACTION_FUNCTION(AActor, SpawnMissile) PARAM_SELF_PROLOGUE(AActor); PARAM_OBJECT(dest, AActor); PARAM_CLASS(type, AActor); - PARAM_OBJECT_OPT(owner, AActor) { owner = self; } + PARAM_OBJECT_DEF(owner, AActor); ACTION_RETURN_OBJECT(P_SpawnMissile(self, dest, type, owner)); } @@ -6584,6 +6584,31 @@ void AActor::SetTranslation(const char *trname) // silently ignore if the name does not exist, this would create some insane message spam otherwise. } + +// This combines all 3 variations of the internal function +DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) +{ + PARAM_SELF_PROLOGUE(AActor); + if (numparam == 1) + { + self->VelFromAngle(); + } + else + { + PARAM_FLOAT(speed); + if (numparam == 2) + { + self->VelFromAngle(speed); + } + else + { + PARAM_ANGLE(angle); + self->VelFromAngle(speed, angle); + } + } + return 0; +} + //---------------------------------------------------------------------------- // // DropItem handling diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index ae936b844..3d0dc166d 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -159,7 +159,6 @@ enum ATAG_AREGISTER, // pointer to an address register ATAG_STATE, // pointer to FState - ATAG_STATEINFO, // FState plus some info. ATAG_RNG, // pointer to FRandom }; @@ -929,7 +928,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define ASSERTINT(p) assert((p).Type == REGT_INT) #define ASSERTFLOAT(p) assert((p).Type == REGT_FLOAT) #define ASSERTSTRING(p) assert((p).Type == REGT_STRING) -#define ASSERTOBJECT(p) assert((p).Type == REGT_POINTER && (p).atag == ATAG_OBJECT) +#define ASSERTOBJECT(p) assert((p).Type == REGT_POINTER && ((p).atag == ATAG_OBJECT || (p).a == nullptr)) #define ASSERTPOINTER(p) assert((p).Type == REGT_POINTER && (p).atag == ATAG_GENERIC) #define ASSERTSTATE(p) assert((p).Type == REGT_POINTER && ((p).atag == ATAG_GENERIC || (p).atag == ATAG_STATE)) @@ -950,14 +949,9 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_BOOL_OPT_AT(p,x) bool x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = !!param[p].i; } else #define PARAM_NAME_OPT_AT(p,x) FName x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = ENamedName(param[p].i); } else #define PARAM_SOUND_OPT_AT(p,x) FSoundID x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = FSoundID(param[p].i); } else -#define PARAM_COLOR_OPT_AT(p,x) PalEntry x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x.d = param[p].i; } else #define PARAM_FLOAT_OPT_AT(p,x) double x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_FLOAT); x = param[p].f; } else #define PARAM_ANGLE_OPT_AT(p,x) DAngle x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_FLOAT); x = param[p].f; } else -#define PARAM_STRING_OPT_AT(p,x) FString x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_STRING); x = param[p].s(); } else #define PARAM_STATE_OPT_AT(p,x) FState *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); x = (FState *)param[p].a; } else -#define PARAM_STATEINFO_OPT_AT(p,x) FStateParamInfo *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATEINFO || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); x = (FStateParamInfo *)param[p].a; } else -#define PARAM_POINTER_OPT_AT(p,x,type) type *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER); x = (type *)param[p].a; } else -#define PARAM_OBJECT_OPT_AT(p,x,type) type *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); x = (type *)param[p].a; assert(x == NULL || x->IsKindOf(RUNTIME_CLASS(type))); } else #define PARAM_CLASS_OPT_AT(p,x,base) base::MetaClass *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); x = (base::MetaClass *)param[p].a; assert(x == NULL || x->IsDescendantOf(RUNTIME_CLASS(base))); } else // The above, but with an automatically increasing position index. @@ -985,7 +979,6 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_ANGLE_DEF(x) ++paramnum; PARAM_ANGLE_DEF_AT(paramnum,x) #define PARAM_STRING_DEF(x) ++paramnum; PARAM_STRING_DEF_AT(paramnum,x) #define PARAM_STATE_DEF(x) ++paramnum; PARAM_STATE_DEF_AT(paramnum,x) -#define PARAM_STATEINFO_DEF(x) ++paramnum; PARAM_STATEINFO_DEF_AT(paramnum,x) #define PARAM_POINTER_DEF(x,type) ++paramnum; PARAM_POINTER_DEF_AT(paramnum,x,type) #define PARAM_OBJECT_DEF(x,type) ++paramnum; PARAM_OBJECT_DEF_AT(paramnum,x,type) #define PARAM_CLASS_DEF(x,base) ++paramnum; PARAM_CLASS_DEF_AT(paramnum,x,base) @@ -994,14 +987,9 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_BOOL_OPT(x) ++paramnum; PARAM_BOOL_OPT_AT(paramnum,x) #define PARAM_NAME_OPT(x) ++paramnum; PARAM_NAME_OPT_AT(paramnum,x) #define PARAM_SOUND_OPT(x) ++paramnum; PARAM_SOUND_OPT_AT(paramnum,x) -#define PARAM_COLOR_OPT(x) ++paramnum; PARAM_COLOR_OPT_AT(paramnum,x) #define PARAM_FLOAT_OPT(x) ++paramnum; PARAM_FLOAT_OPT_AT(paramnum,x) #define PARAM_ANGLE_OPT(x) ++paramnum; PARAM_ANGLE_OPT_AT(paramnum,x) -#define PARAM_STRING_OPT(x) ++paramnum; PARAM_STRING_OPT_AT(paramnum,x) #define PARAM_STATE_OPT(x) ++paramnum; PARAM_STATE_OPT_AT(paramnum,x) -#define PARAM_STATEINFO_OPT(x) ++paramnum; PARAM_STATEINFO_OPT_AT(paramnum,x) -#define PARAM_POINTER_OPT(x,type) ++paramnum; PARAM_POINTER_OPT_AT(paramnum,x,type) -#define PARAM_OBJECT_OPT(x,type) ++paramnum; PARAM_OBJECT_OPT_AT(paramnum,x,type) #define PARAM_CLASS_OPT(x,base) ++paramnum; PARAM_CLASS_OPT_AT(paramnum,x,base) typedef int(*actionf_p)(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret);/*(VM_ARGS)*/ @@ -1043,7 +1031,7 @@ struct AFuncDesc //#define PUSH_PARAMINFO self, stateowner, CallingState, ParameterIndex, statecall #define CALL_ACTION(name,self) { /*AF_##name(self, self, NULL, 0, NULL)*/ \ - VMValue params[3] = { self, self, VMValue(NULL, ATAG_STATEINFO) }; \ + VMValue params[3] = { self, self, VMValue(NULL, ATAG_GENERIC) }; \ stack->Call(name##_VMPtr, params, countof(params), NULL, 0, NULL); \ } @@ -1066,8 +1054,8 @@ struct AFuncDesc #define PARAM_ACTION_PROLOGUE(type) \ PARAM_PROLOGUE; \ PARAM_OBJECT (self, type); \ - PARAM_OBJECT_OPT (stateowner, AActor) { stateowner = self; } \ - PARAM_STATEINFO_OPT (stateinfo) { stateinfo = nullptr; } \ + PARAM_OBJECT (stateowner, AActor) \ + PARAM_POINTER (stateinfo, FStateParamInfo) \ // Number of action paramaters #define NAP 3 diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index b8078f071..e2691470e 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -188,7 +188,7 @@ void VMFillParams(VMValue *params, VMFrame *callee, int numparam) const VMRegisters calleereg(callee); assert(calleefunc != NULL && !calleefunc->Native); - assert(numparam == calleefunc->NumArgs || ((int)calleefunc->Defaults.Size() == numparam)); + assert(numparam == calleefunc->NumArgs || ((int)calleefunc->Defaults.Size() == calleefunc->NumArgs)); assert(REGT_INT == 0 && REGT_FLOAT == 1 && REGT_STRING == 2 && REGT_POINTER == 3); regd = regf = regs = rega = 0; diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 4f859d3b0..12a8ebb3b 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -65,6 +65,7 @@ class Actor : Thinker native native bool SetState(state st, bool nofunction = false); native void LinkToWorld(); native void UnlinkFromWorld(); + native void VelFromAngle(float speed = 0, float angle = 0); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); @@ -166,6 +167,12 @@ class Actor : Thinker native LinkToWorld(); } + // killough 11/98: kill an object + void A_Die(name damagetype = "none") + { + DamageMobj(null, null, health, damagetype, DMG_FORCED); + } + // Action functions // Meh, MBF redundant functions. Only for DeHackEd support. native bool A_LineEffect(int boomspecial = 0, int tag = 0); @@ -193,10 +200,6 @@ class Actor : Thinker native native void A_SkelWhoosh(); native void A_SkelFist(); native void A_SkelMissile(); - native void A_FatRaise(); - native void A_FatAttack1(class spawntype = "FatShot"); - native void A_FatAttack2(class spawntype = "FatShot"); - native void A_FatAttack3(class spawntype = "FatShot"); native void A_BossDeath(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); @@ -212,7 +215,6 @@ class Actor : Thinker native native void A_SpawnSound(); native void A_SpawnFly(class spawntype = null); // needs special treatment for default native void A_BrainExplode(); - native void A_Die(name damagetype = "none"); native void A_Detonate(); native void A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index f49264062..b14634e0d 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -862,3 +862,17 @@ enum ESightFlags SF_SEEPASTBLOCKEVERYTHING=4, SF_IGNOREWATERBOUNDARY=8 } + +enum EDmgFlags +{ + DMG_NO_ARMOR = 1, + DMG_INFLICTOR_IS_PUFF = 2, + DMG_THRUSTLESS = 4, + DMG_FORCED = 8, + DMG_NO_FACTOR = 16, + DMG_PLAYERATTACK = 32, + DMG_FOILINVUL = 64, + DMG_FOILBUDDHA = 128, + DMG_NO_PROTECT = 256, + DMG_USEANGLE = 512, +} diff --git a/wadsrc/static/zscript/doom/fatso.txt b/wadsrc/static/zscript/doom/fatso.txt index 46d013d7f..c477cbb44 100644 --- a/wadsrc/static/zscript/doom/fatso.txt +++ b/wadsrc/static/zscript/doom/fatso.txt @@ -93,3 +93,75 @@ class FatShot : Actor } +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + const FATSPREAD = 90./8; + + + void A_FatRaise() + { + A_FaceTarget(); + A_PlaySound("fatso/raiseguns", CHAN_WEAPON); + } + + void A_FatAttack1(class spawntype = "FatShot") + { + if (target) + { + A_FaceTarget (); + // Change direction to ... + Angle += FATSPREAD; + SpawnMissile (target, spawntype); + Actor missile = SpawnMissile (target, spawntype); + if (missile) + { + missile.Angle += FATSPREAD; + missile.VelFromAngle(); + } + } + } + + void A_FatAttack2(class spawntype = "FatShot") + { + if (target) + { + A_FaceTarget (); + // Now here choose opposite deviation. + Angle -= FATSPREAD; + SpawnMissile (target, spawntype); + Actor missile = SpawnMissile (target, spawntype); + if (missile) + { + missile.Angle -= FATSPREAD; + missile.VelFromAngle(); + } + } + } + + void A_FatAttack3(class spawntype = "FatShot") + { + if (target) + { + A_FaceTarget (); + Actor missile = SpawnMissile (target, spawntype); + if (missile) + { + missile.Angle -= FATSPREAD/2; + missile.VelFromAngle(); + } + missile = SpawnMissile (target, spawntype); + if (missile) + { + missile.Angle += FATSPREAD/2; + missile.VelFromAngle(); + } + } + } +} + From 03efb63e93e38efc15869714f761127596ae86de Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 27 Oct 2016 19:14:16 +0200 Subject: [PATCH 122/255] - fixed bad register use in postincrement operator. --- src/scripting/codegeneration/codegen.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 5148952a7..3eaaa7170 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1753,7 +1753,7 @@ ExpEmit FxPostIncrDecr::Emit(VMFunctionBuilder *build) { build->Emit((Token == TK_Incr) ? OP_ADDF_RK : OP_SUBF_RK, assign.RegNum, out.RegNum, build->GetConstantFloat(1.)); } - build->Emit(ValueType->GetStoreOp(), pointer.RegNum, out.RegNum, zero); + build->Emit(ValueType->GetStoreOp(), pointer.RegNum, assign.RegNum, zero); pointer.Free(build); assign.Free(build); return out; From 286f9510d42f9df0a866479a5f5a6b25aea9ab5a Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 00:32:52 +0200 Subject: [PATCH 123/255] - got rid of all default parameter redundancies. - scriptified a few more functions. --- src/g_doom/a_archvile.cpp | 18 ++--- src/g_doom/a_bossbrain.cpp | 4 +- src/g_doom/a_doomweaps.cpp | 40 ++++++------ src/g_doom/a_fatso.cpp | 10 +-- src/g_doom/a_keen.cpp | 2 +- src/g_doom/a_lostsoul.cpp | 2 +- src/g_doom/a_painelemental.cpp | 52 ++------------- src/g_doom/a_scriptedmarine.cpp | 10 +-- src/g_heretic/a_hereticmisc.cpp | 4 +- src/g_hexen/a_blastradius.cpp | 12 ++-- src/g_hexen/a_magelightning.cpp | 4 +- src/g_shared/a_bridge.cpp | 2 +- src/g_shared/a_specialspot.cpp | 6 +- src/g_shared/a_weapons.cpp | 4 +- src/g_strife/a_strifeweapons.cpp | 4 +- src/p_actionfunctions.cpp | 50 +------------- src/p_enemy.cpp | 69 ++++++-------------- src/p_mobj.cpp | 9 ++- src/p_pspr.cpp | 36 +++++----- src/p_sight.cpp | 2 +- src/p_user.cpp | 2 +- src/scripting/thingdef_data.cpp | 5 +- src/scripting/vm/vm.h | 18 ----- src/scripting/vm/vmbuilder.cpp | 4 ++ wadsrc/static/zscript/actor.txt | 23 +++++-- wadsrc/static/zscript/doom/painelemental.txt | 42 ++++++++++++ 26 files changed, 183 insertions(+), 251 deletions(-) diff --git a/src/g_doom/a_archvile.cpp b/src/g_doom/a_archvile.cpp index b63564654..959c5763d 100644 --- a/src/g_doom/a_archvile.cpp +++ b/src/g_doom/a_archvile.cpp @@ -50,7 +50,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrackle) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Fire) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(height) { height = 0; } + PARAM_FLOAT_DEF(height); A_Fire(self, height); return 0; @@ -81,7 +81,7 @@ void A_Fire(AActor *self, double height) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileTarget) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(fire, AActor) { fire = PClass::FindActor("ArchvileFire"); } + PARAM_CLASS_DEF(fire, AActor); AActor *fog; @@ -112,13 +112,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileTarget) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileAttack) { PARAM_SELF_PROLOGUE(AActor); - PARAM_SOUND_OPT (snd) { snd = "vile/stop"; } - PARAM_INT_OPT (dmg) { dmg = 20; } - PARAM_INT_OPT (blastdmg) { blastdmg = 70; } - PARAM_INT_OPT (blastrad) { blastrad = 70; } - PARAM_FLOAT_OPT (thrust) { thrust = 1; } - PARAM_NAME_OPT (dmgtype) { dmgtype = NAME_Fire; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_SOUND_DEF (snd) + PARAM_INT_DEF (dmg) + PARAM_INT_DEF (blastdmg) + PARAM_INT_DEF (blastrad) + PARAM_FLOAT_DEF (thrust) + PARAM_NAME_DEF (dmgtype) + PARAM_INT_DEF (flags) AActor *fire, *target; diff --git a/src/g_doom/a_bossbrain.cpp b/src/g_doom/a_bossbrain.cpp index 84cd9040c..1b50cb3cc 100644 --- a/src/g_doom/a_bossbrain.cpp +++ b/src/g_doom/a_bossbrain.cpp @@ -112,7 +112,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainDie) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BrainSpit) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } + PARAM_CLASS_DEF(spawntype, AActor); DSpotState *state = DSpotState::GetSpotState(); AActor *targ; @@ -298,7 +298,7 @@ static void SpawnFly(AActor *self, PClassActor *spawntype, FSoundID sound) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnFly) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; } + PARAM_CLASS_DEF(spawntype, AActor); FSoundID sound; diff --git a/src/g_doom/a_doomweaps.cpp b/src/g_doom/a_doomweaps.cpp index f7511b2be..37ff05c70 100644 --- a/src/g_doom/a_doomweaps.cpp +++ b/src/g_doom/a_doomweaps.cpp @@ -116,17 +116,17 @@ enum SAW_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_SOUND_OPT (fullsound) { fullsound = "weapons/sawfull"; } - PARAM_SOUND_OPT (hitsound) { hitsound = "weapons/sawhit"; } - PARAM_INT_OPT (damage) { damage = 2; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = NULL; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (range) { range = 0; } - PARAM_ANGLE_OPT (spread_xy) { spread_xy = 2.8125; } - PARAM_ANGLE_OPT (spread_z) { spread_z = 0.; } - PARAM_FLOAT_OPT (lifesteal) { lifesteal = 0; } - PARAM_INT_OPT (lifestealmax) { lifestealmax = 0; } - PARAM_CLASS_OPT (armorbonustype, ABasicArmorBonus) { armorbonustype = NULL; } + PARAM_SOUND_DEF (fullsound) + PARAM_SOUND_DEF (hitsound) + PARAM_INT_DEF (damage) + PARAM_CLASS_DEF (pufftype, AActor) + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (range) + PARAM_ANGLE_DEF (spread_xy) + PARAM_ANGLE_DEF (spread_z) + PARAM_FLOAT_DEF (lifesteal) + PARAM_INT_DEF (lifestealmax) + PARAM_CLASS_DEF (armorbonustype, ABasicArmorBonus) DAngle angle; DAngle slope; @@ -480,7 +480,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMissile) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireSTGrenade) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_CLASS_OPT(grenade, AActor) { grenade = PClass::FindActor("Grenade"); } + PARAM_CLASS_DEF(grenade, AActor); player_t *player; @@ -639,14 +639,14 @@ enum BFG_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT (spraytype, AActor) { spraytype = NULL; } - PARAM_INT_OPT (numrays) { numrays = 0; } - PARAM_INT_OPT (damagecnt) { damagecnt = 0; } - PARAM_ANGLE_OPT (angle) { angle = 0.; } - PARAM_FLOAT_OPT (distance) { distance = 0; } - PARAM_ANGLE_OPT (vrange) { vrange = 0.; } - PARAM_INT_OPT (defdamage) { defdamage = 0; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_CLASS_DEF (spraytype, AActor) + PARAM_INT_DEF (numrays) + PARAM_INT_DEF (damagecnt) + PARAM_ANGLE_DEF (angle) + PARAM_FLOAT_DEF (distance) + PARAM_ANGLE_DEF (vrange) + PARAM_INT_DEF (defdamage) + PARAM_INT_DEF (flags) int i; int j; diff --git a/src/g_doom/a_fatso.cpp b/src/g_doom/a_fatso.cpp index d373a7a08..ea2d8f397 100644 --- a/src/g_doom/a_fatso.cpp +++ b/src/g_doom/a_fatso.cpp @@ -30,11 +30,11 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Mushroom) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; } - PARAM_INT_OPT (n) { n = 0; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (vrange) { vrange = 4; } - PARAM_FLOAT_OPT (hrange) { hrange = 0.5; } + PARAM_CLASS_DEF (spawntype, AActor) + PARAM_INT_DEF (n) + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (vrange) + PARAM_FLOAT_DEF (hrange) int i, j; diff --git a/src/g_doom/a_keen.cpp b/src/g_doom/a_keen.cpp index 3040e0545..b22f141b4 100644 --- a/src/g_doom/a_keen.cpp +++ b/src/g_doom/a_keen.cpp @@ -17,7 +17,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KeenDie) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(doortag) { doortag = 666; } + PARAM_INT_DEF(doortag); A_Unblock(self, false); diff --git a/src/g_doom/a_lostsoul.cpp b/src/g_doom/a_lostsoul.cpp index 18b8251e9..1c33f47a7 100644 --- a/src/g_doom/a_lostsoul.cpp +++ b/src/g_doom/a_lostsoul.cpp @@ -37,7 +37,7 @@ void A_SkullAttack(AActor *self, double speed) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullAttack) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(speed) { speed = SKULLSPEED; } + PARAM_FLOAT_DEF(speed); if (speed <= 0) speed = SKULLSPEED; diff --git a/src/g_doom/a_painelemental.cpp b/src/g_doom/a_painelemental.cpp index 30136f9f7..09160ddeb 100644 --- a/src/g_doom/a_painelemental.cpp +++ b/src/g_doom/a_painelemental.cpp @@ -141,54 +141,14 @@ void A_PainShootSkull (AActor *self, DAngle Angle, PClassActor *spawntype, int f } -// -// A_PainAttack -// Spawn a lost soul and launch it at the target -// -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainAttack) +DEFINE_ACTION_FUNCTION(AActor, A_PainShootSkull) { PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; } - PARAM_ANGLE_OPT (angle) { angle = 0.; } - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_INT_OPT (limit) { limit = -1; } - - if (!(flags & PAF_AIMFACING)) - A_FaceTarget (self); - A_PainShootSkull (self, self->Angles.Yaw + angle, spawntype, flags, limit); + PARAM_CLASS(spawntype, AActor); + PARAM_FLOAT(angle); + PARAM_INT_DEF(flags); + PARAM_INT_DEF(limit); + A_PainShootSkull(self, angle, spawntype, flags, limit); return 0; } -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DualPainAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } - - if (!self->target) - return 0; - - A_FaceTarget (self); - A_PainShootSkull (self, self->Angles.Yaw + 45., spawntype); - A_PainShootSkull (self, self->Angles.Yaw - 45., spawntype); - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainDie) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; } - - if (self->target != NULL && self->IsFriend(self->target)) - { // And I thought you were my friend! - self->flags &= ~MF_FRIENDLY; - } - A_Unblock(self, true); - A_PainShootSkull (self, self->Angles.Yaw + 90, spawntype); - A_PainShootSkull (self, self->Angles.Yaw + 180, spawntype); - A_PainShootSkull (self, self->Angles.Yaw + 270, spawntype); - return 0; -} diff --git a/src/g_doom/a_scriptedmarine.cpp b/src/g_doom/a_scriptedmarine.cpp index 61c7c8ac4..4bf828342 100644 --- a/src/g_doom/a_scriptedmarine.cpp +++ b/src/g_doom/a_scriptedmarine.cpp @@ -151,7 +151,7 @@ void AScriptedMarine::Tick () DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Refire) { PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL_OPT(ignoremissile) { ignoremissile = false; } + PARAM_BOOL_DEF(ignoremissile); if (self->target == NULL || self->target->health <= 0) { @@ -250,10 +250,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_MarineLook) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Saw) { PARAM_SELF_PROLOGUE(AActor); - PARAM_SOUND_OPT (fullsound) { fullsound = "weapons/sawfull"; } - PARAM_SOUND_OPT (hitsound) { hitsound = "weapons/sawhit"; } - PARAM_INT_OPT (damage) { damage = 2; } - PARAM_CLASS_OPT (pufftype, AActor) { pufftype = NULL; } + PARAM_SOUND_DEF (fullsound) + PARAM_SOUND_DEF (hitsound) + PARAM_INT_DEF (damage) + PARAM_CLASS_DEF (pufftype, AActor) if (self->target == NULL) return 0; diff --git a/src/g_heretic/a_hereticmisc.cpp b/src/g_heretic/a_hereticmisc.cpp index 02c1393dd..2d4f3497c 100644 --- a/src/g_heretic/a_hereticmisc.cpp +++ b/src/g_heretic/a_hereticmisc.cpp @@ -48,7 +48,7 @@ static FRandom pr_volcimpact ("VolcBallImpact"); DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PodPain) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT (gootype, AActor) { gootype = PClass::FindActor("PodGoo"); } + PARAM_CLASS_DEF (gootype, AActor) int count; int chance; @@ -103,7 +103,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RemovePod) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MakePod) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(podtype, AActor) { podtype = PClass::FindActor("Pod"); } + PARAM_CLASS_DEF(podtype, AActor) AActor *mo; diff --git a/src/g_hexen/a_blastradius.cpp b/src/g_hexen/a_blastradius.cpp index 0b0ab5d10..f8bc60a7f 100644 --- a/src/g_hexen/a_blastradius.cpp +++ b/src/g_hexen/a_blastradius.cpp @@ -96,12 +96,12 @@ enum DEFINE_ACTION_FUNCTION_PARAMS (AActor, A_Blast) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_INT_OPT (blastflags) { blastflags = 0; } - PARAM_FLOAT_OPT (strength) { strength = 255; } - PARAM_FLOAT_OPT (radius) { radius = 255; } - PARAM_FLOAT_OPT (speed) { speed = 20; } - PARAM_CLASS_OPT (blasteffect, AActor) { blasteffect = PClass::FindActor("BlastEffect"); } - PARAM_SOUND_OPT (blastsound) { blastsound = "BlastRadius"; } + PARAM_INT_DEF (blastflags) + PARAM_FLOAT_DEF (strength) + PARAM_FLOAT_DEF (radius) + PARAM_FLOAT_DEF (speed) + PARAM_CLASS_DEF (blasteffect, AActor) + PARAM_SOUND_DEF (blastsound) AActor *mo; TThinkerIterator iterator; diff --git a/src/g_hexen/a_magelightning.cpp b/src/g_hexen/a_magelightning.cpp index e4390131a..192fd03e0 100644 --- a/src/g_hexen/a_magelightning.cpp +++ b/src/g_hexen/a_magelightning.cpp @@ -258,8 +258,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningZap) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MLightningAttack) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(floor, AActor) { floor = PClass::FindActor("LightningFloor"); } - PARAM_CLASS_OPT(ceiling, AActor) { ceiling = PClass::FindActor("LightningCeiling"); } + PARAM_CLASS_DEF(floor, AActor); + PARAM_CLASS_DEF(ceiling, AActor); AActor *fmo, *cmo; diff --git a/src/g_shared/a_bridge.cpp b/src/g_shared/a_bridge.cpp index f3b12a1d1..3cd7ee172 100644 --- a/src/g_shared/a_bridge.cpp +++ b/src/g_shared/a_bridge.cpp @@ -122,7 +122,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BridgeOrbit) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BridgeInit) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(balltype, AActor) { balltype = NULL; } + PARAM_CLASS_DEF(balltype, AActor); AActor *ball; diff --git a/src/g_shared/a_specialspot.cpp b/src/g_shared/a_specialspot.cpp index 1af9f6db7..c47116f79 100644 --- a/src/g_shared/a_specialspot.cpp +++ b/src/g_shared/a_specialspot.cpp @@ -382,9 +382,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnSingleItem) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (cls, AActor); - PARAM_INT_OPT (fail_sp) { fail_sp = 0; } - PARAM_INT_OPT (fail_co) { fail_co = 0; } - PARAM_INT_OPT (fail_dm) { fail_dm = 0; } + PARAM_INT_DEF (fail_sp) + PARAM_INT_DEF (fail_co) + PARAM_INT_DEF (fail_dm) AActor *spot = NULL; DSpotState *state = DSpotState::GetSpotState(); diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index d7f432a7a..774d8d5e5 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -1923,8 +1923,8 @@ PClassWeapon *Net_ReadWeapon(BYTE **stream) DEFINE_ACTION_FUNCTION_PARAMS(AWeapon, A_ZoomFactor) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT (zoom) { zoom = 1; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_FLOAT_DEF(zoom); + PARAM_INT_DEF(flags); if (self->player != NULL && self->player->ReadyWeapon != NULL) { diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index f80f3e863..41ceff087 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -147,8 +147,8 @@ enum DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_AlertMonsters) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(maxdist) { maxdist = 0; } - PARAM_INT_OPT(Flags) { Flags = 0; } + PARAM_FLOAT_DEF(maxdist); + PARAM_INT_DEF(Flags); AActor * target = NULL; AActor * emitter = self; diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index fd67e0a64..0e9620564 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -1148,7 +1148,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BulletAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Jump) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(maxchance) { maxchance = 256; } + PARAM_INT_DEF(maxchance); paramnum++; // Increment paramnum to point at the first jump target int count = numparam - paramnum; @@ -2685,7 +2685,7 @@ bool DoTakeInventory(AActor *receiver, bool orresult, VM_ARGS) } if (!orresult) { - PARAM_INT_OPT(setreceiver) { setreceiver = AAPTR_DEFAULT; } + PARAM_INT_DEF(setreceiver); receiver = COPY_AAPTR(receiver, setreceiver); } if (receiver == NULL) @@ -7015,52 +7015,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CopySpriteFrame) ACTION_RETURN_BOOL(true); } -//========================================================================== -// -// A_SetSpriteAngle(angle, ptr) -// -// Specifies which angle the actor must always draw its sprite from. -//========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpriteAngle) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_DEF(angle); - PARAM_INT_DEF(ptr); - - AActor *mobj = COPY_AAPTR(self, ptr); - - if (mobj == nullptr) - { - ACTION_RETURN_BOOL(false); - } - mobj->SpriteAngle = angle; - ACTION_RETURN_BOOL(true); -} - -//========================================================================== -// -// A_SetSpriteRotation(angle, ptr) -// -// Specifies how much to fake a sprite rotation. -//========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetSpriteRotation) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_ANGLE_OPT(angle) { angle = 0.; } - PARAM_INT_OPT(ptr) { ptr = AAPTR_DEFAULT; } - - AActor *mobj = COPY_AAPTR(self, ptr); - - if (mobj == nullptr) - { - ACTION_RETURN_BOOL(false); - } - mobj->SpriteRotation = angle; - ACTION_RETURN_BOOL(true); -} - //========================================================================== // // A_SetMaskRotation(anglestart, angleend, pitchstart, pitchend, flags, ptr) diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 3f5570681..77082f3a4 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -1922,12 +1922,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_Look) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_LookEx) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT (flags) { flags = 0; } - PARAM_FLOAT_OPT (minseedist) { minseedist = 0; } - PARAM_FLOAT_OPT (maxseedist) { maxseedist = 0; } - PARAM_FLOAT_OPT (maxheardist) { maxheardist = 0; } - PARAM_ANGLE_OPT (fov) { fov = 0.; } - PARAM_STATE_OPT (seestate) { seestate = NULL; } + PARAM_INT_DEF (flags) + PARAM_FLOAT_DEF (minseedist) + PARAM_FLOAT_DEF (maxseedist) + PARAM_FLOAT_DEF (maxheardist) + PARAM_ANGLE_DEF (fov) + PARAM_STATE_DEF (seestate) AActor *targ = NULL; // Shuts up gcc double dist; @@ -2139,7 +2139,7 @@ enum ChaseFlags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Wander) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_INT_DEF(flags); A_Wander(self, flags); return 0; } @@ -2781,9 +2781,9 @@ static bool P_CheckForResurrection(AActor *self, bool usevilestates) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Chase) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE_OPT (melee) { melee = NULL; } - PARAM_STATE_OPT (missile) { missile = NULL; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_STATE_DEF (melee) + PARAM_STATE_DEF (missile) + PARAM_INT_DEF (flags) if (numparam > 1) { @@ -2822,8 +2822,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ExtChase) PARAM_SELF_PROLOGUE(AActor); PARAM_BOOL (domelee); PARAM_BOOL (domissile); - PARAM_BOOL_OPT (playactive) { playactive = true; } - PARAM_BOOL_OPT (nightmarefast) { nightmarefast = false; } + PARAM_BOOL_DEF (playactive); + PARAM_BOOL_DEF (nightmarefast); // Now that A_Chase can handle state label parameters, this function has become rather useless... A_DoChase(stack, self, false, @@ -2957,45 +2957,18 @@ void A_FaceTarget(AActor *self) A_Face(self, self->target); } -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceTarget) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Face) { PARAM_SELF_PROLOGUE(AActor); - PARAM_ANGLE_OPT(max_turn) { max_turn = 0.; } - PARAM_ANGLE_OPT(max_pitch) { max_pitch = 270.; } - PARAM_ANGLE_OPT(ang_offset) { ang_offset = 0.; } - PARAM_ANGLE_OPT(pitch_offset) { pitch_offset = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_FLOAT_OPT(z_add) { z_add = 0; } + PARAM_OBJECT(faceto, AActor) + PARAM_ANGLE_DEF(max_turn) + PARAM_ANGLE_DEF(max_pitch) + PARAM_ANGLE_DEF(ang_offset) + PARAM_ANGLE_DEF(pitch_offset) + PARAM_INT_DEF(flags) + PARAM_FLOAT_DEF(z_add) - A_Face(self, self->target, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_add); - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceMaster) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_ANGLE_OPT(max_turn) { max_turn = 0.; } - PARAM_ANGLE_OPT(max_pitch) { max_pitch = 270.; } - PARAM_ANGLE_OPT(ang_offset) { ang_offset = 0.; } - PARAM_ANGLE_OPT(pitch_offset) { pitch_offset = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_FLOAT_OPT(z_add) { z_add = 0; } - - A_Face(self, self->master, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_add); - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FaceTracer) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_ANGLE_OPT(max_turn) { max_turn = 0.; } - PARAM_ANGLE_OPT(max_pitch) { max_pitch = 270.; } - PARAM_ANGLE_OPT(ang_offset) { ang_offset = 0.; } - PARAM_ANGLE_OPT(pitch_offset) { pitch_offset = 0.; } - PARAM_INT_OPT(flags) { flags = 0; } - PARAM_FLOAT_OPT(z_add) { z_add = 0; } - - A_Face(self, self->tracer, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_add); + A_Face(self, faceto, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_add); return 0; } diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 7d37e3546..754ec516a 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -514,7 +514,7 @@ DEFINE_ACTION_FUNCTION(AActor, SetState) { PARAM_SELF_PROLOGUE(AActor); PARAM_STATE(state); - PARAM_BOOL_OPT(nofunction) { nofunction = false; } + PARAM_BOOL_DEF(nofunction); ACTION_RETURN_BOOL(self->SetState(state, nofunction)); }; @@ -6257,6 +6257,13 @@ bool AActor::IsFriend (AActor *other) return false; } +DEFINE_ACTION_FUNCTION(AActor, isFriend) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(other, AActor); + ACTION_RETURN_BOOL(self->IsFriend(other)); +} + //========================================================================== // // AActor :: IsHostile diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index 055649466..e8be2e865 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -744,7 +744,7 @@ void DoReadyWeapon(AActor *self) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_WeaponReady) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_INT_DEF(flags); DoReadyWeaponToSwitch(self, !(flags & WRF_NoSwitch)); if ((flags & WRF_NoFire) != WRF_NoFire) DoReadyWeaponToFire(self, !(flags & WRF_NoPrimary), !(flags & WRF_NoSecondary)); @@ -876,7 +876,7 @@ static void P_CheckWeaponButtons (player_t *player) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_ReFire) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE_OPT(state) { state = NULL; } + PARAM_STATE_DEF(state); A_ReFire(self, state); return 0; } @@ -1003,10 +1003,10 @@ void A_OverlayOffset(AActor *self, int layer, double wx, double wy, int flags) DEFINE_ACTION_FUNCTION(AActor, A_OverlayOffset) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_INT_OPT(layer) { layer = PSP_WEAPON; } - PARAM_FLOAT_OPT(wx) { wx = 0.; } - PARAM_FLOAT_OPT(wy) { wy = 32.; } - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_INT_DEF(layer) + PARAM_FLOAT_DEF(wx) + PARAM_FLOAT_DEF(wy) + PARAM_INT_DEF(flags) A_OverlayOffset(self, ((layer != 0) ? layer : stateinfo->mPSPIndex), wx, wy, flags); return 0; } @@ -1014,9 +1014,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_OverlayOffset) DEFINE_ACTION_FUNCTION(AActor, A_WeaponOffset) { PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_OPT(wx) { wx = 0.; } - PARAM_FLOAT_OPT(wy) { wy = 32.; } - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_FLOAT_DEF(wx) + PARAM_FLOAT_DEF(wy) + PARAM_INT_DEF(flags) A_OverlayOffset(self, PSP_WEAPON, wx, wy, flags); return 0; } @@ -1073,7 +1073,7 @@ static double GetOverlayPosition(AActor *self, int layer, bool gety) DEFINE_ACTION_FUNCTION(AActor, OverlayX) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_INT_OPT(layer) { layer = 0; } + PARAM_INT_DEF(layer); if (ACTION_CALL_FROM_PSPRITE()) { @@ -1086,7 +1086,7 @@ DEFINE_ACTION_FUNCTION(AActor, OverlayX) DEFINE_ACTION_FUNCTION(AActor, OverlayY) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_INT_OPT(layer) { layer = 0; } + PARAM_INT_DEF(layer); if (ACTION_CALL_FROM_PSPRITE()) { @@ -1214,8 +1214,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Overlay) { PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (layer); - PARAM_STATE_OPT (state) { state = nullptr; } - PARAM_BOOL_OPT (dontoverride) { dontoverride = false; } + PARAM_STATE_DEF(state); + PARAM_BOOL_DEF(dontoverride); player_t *player = self->player; @@ -1233,9 +1233,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Overlay) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ClearOverlays) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_OPT(start) { start = 0; } - PARAM_INT_OPT(stop) { stop = 0; } - PARAM_BOOL_OPT(safety) { safety = true; } + PARAM_INT_DEF(start); + PARAM_INT_DEF(stop); + PARAM_BOOL_DEF(safety) if (self->player == nullptr) ACTION_RETURN_INT(0); @@ -1284,8 +1284,8 @@ enum GF_Flags DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_GunFlash) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE_OPT(flash) { flash = nullptr; } - PARAM_INT_OPT (flags) { flags = 0; } + PARAM_STATE_DEF(flash); + PARAM_INT_DEF(flags); player_t *player = self->player; diff --git a/src/p_sight.cpp b/src/p_sight.cpp index fefe9eb27..319d5b3ec 100644 --- a/src/p_sight.cpp +++ b/src/p_sight.cpp @@ -909,7 +909,7 @@ DEFINE_ACTION_FUNCTION(AActor, CheckSight) { PARAM_SELF_PROLOGUE(AActor); PARAM_OBJECT(target, AActor); - PARAM_INT_OPT(flags) { flags = 0; } + PARAM_INT_DEF(flags); ACTION_RETURN_BOOL(P_CheckSight(self, target, flags)); } diff --git a/src/p_user.cpp b/src/p_user.cpp index 70c864c2a..4092c85c2 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -1626,7 +1626,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PlayerScream) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullPop) { PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_OPT(spawntype, APlayerChunk) { spawntype = NULL; } + PARAM_CLASS_DEF(spawntype, APlayerChunk); APlayerPawn *mo; player_t *player; diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 55cc03c0c..f071614a8 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -447,12 +447,11 @@ static FFlagDef *FindFlag (FFlagDef *flags, int numflags, const char *flag) FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bool strict) { FFlagDef *def; - size_t i; if (part2 == NULL) { // Search all lists int max = strict ? 2 : NUM_FLAG_LISTS; - for (i = 0; i < max; ++i) + for (int i = 0; i < max; ++i) { if (type->IsDescendantOf (*FlagLists[i].Type)) { @@ -466,7 +465,7 @@ FFlagDef *FindFlag (const PClass *type, const char *part1, const char *part2, bo } else { // Search just the named list - for (i = 0; i < NUM_FLAG_LISTS; ++i) + for (size_t i = 0; i < NUM_FLAG_LISTS; ++i) { if (stricmp ((*FlagLists[i].Type)->TypeName.GetChars(), part1) == 0) { diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 3d0dc166d..5684d5775 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -945,15 +945,6 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_OBJECT_DEF_AT(p,x,t) t *x; if (PARAM_EXISTS(p)) { ASSERTOBJECT(param[p]); x = (t*)param[p].a; } else { ASSERTOBJECT(defaultparam[p]); x = (t*)defaultparam[p].a; } #define PARAM_CLASS_DEF_AT(p,x,t) t::MetaClass *x; if (PARAM_EXISTS(p)) { ASSERTOBJECT(param[p]); x = (t::MetaClass*)param[p].a; } else { ASSERTOBJECT(defaultparam[p]); x = (t::MetaClass*)defaultparam[p].a; } -#define PARAM_INT_OPT_AT(p,x) int x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = param[p].i; } else -#define PARAM_BOOL_OPT_AT(p,x) bool x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = !!param[p].i; } else -#define PARAM_NAME_OPT_AT(p,x) FName x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = ENamedName(param[p].i); } else -#define PARAM_SOUND_OPT_AT(p,x) FSoundID x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_INT); x = FSoundID(param[p].i); } else -#define PARAM_FLOAT_OPT_AT(p,x) double x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_FLOAT); x = param[p].f; } else -#define PARAM_ANGLE_OPT_AT(p,x) DAngle x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_FLOAT); x = param[p].f; } else -#define PARAM_STATE_OPT_AT(p,x) FState *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); x = (FState *)param[p].a; } else -#define PARAM_CLASS_OPT_AT(p,x,base) base::MetaClass *x; if ((p) < numparam && param[p].Type != REGT_NIL) { assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); x = (base::MetaClass *)param[p].a; assert(x == NULL || x->IsDescendantOf(RUNTIME_CLASS(base))); } else - // The above, but with an automatically increasing position index. #define PARAM_PROLOGUE int paramnum = -1; @@ -983,15 +974,6 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_OBJECT_DEF(x,type) ++paramnum; PARAM_OBJECT_DEF_AT(paramnum,x,type) #define PARAM_CLASS_DEF(x,base) ++paramnum; PARAM_CLASS_DEF_AT(paramnum,x,base) -#define PARAM_INT_OPT(x) ++paramnum; PARAM_INT_OPT_AT(paramnum,x) -#define PARAM_BOOL_OPT(x) ++paramnum; PARAM_BOOL_OPT_AT(paramnum,x) -#define PARAM_NAME_OPT(x) ++paramnum; PARAM_NAME_OPT_AT(paramnum,x) -#define PARAM_SOUND_OPT(x) ++paramnum; PARAM_SOUND_OPT_AT(paramnum,x) -#define PARAM_FLOAT_OPT(x) ++paramnum; PARAM_FLOAT_OPT_AT(paramnum,x) -#define PARAM_ANGLE_OPT(x) ++paramnum; PARAM_ANGLE_OPT_AT(paramnum,x) -#define PARAM_STATE_OPT(x) ++paramnum; PARAM_STATE_OPT_AT(paramnum,x) -#define PARAM_CLASS_OPT(x,base) ++paramnum; PARAM_CLASS_OPT_AT(paramnum,x,base) - typedef int(*actionf_p)(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret);/*(VM_ARGS)*/ struct AFuncDesc diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 7f8a643c6..dd07d0100 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -728,6 +728,10 @@ void FFunctionBuildList::Build() sfunc->PrintableName = item.PrintableName; } delete item.Code; + if (dump != nullptr) + { + fflush(dump); + } } if (dump != nullptr) { diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 12a8ebb3b..363036507 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -66,6 +66,7 @@ class Actor : Thinker native native void LinkToWorld(); native void UnlinkFromWorld(); native void VelFromAngle(float speed = 0, float angle = 0); + native bool isFriend(Actor other); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); @@ -173,6 +174,22 @@ class Actor : Thinker native DamageMobj(null, null, health, damagetype, DMG_FORCED); } + + native void A_Face(Actor faceto, float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); + + void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0) + { + A_Face(target, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_ofs); + } + void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0) + { + A_Face(tracer, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_ofs); + } + void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0) + { + A_Face(master, max_turn, max_pitch, ang_offset, pitch_offset, flags, z_ofs); + } + // Action functions // Meh, MBF redundant functions. Only for DeHackEd support. native bool A_LineEffect(int boomspecial = 0, int tag = 0); @@ -185,9 +202,6 @@ class Actor : Thinker native native void A_XScream(); native void A_Look(); native void A_Chase(state melee = null, state missile = null, int flags = 0); - native void A_FaceTarget(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - native void A_FaceTracer(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); - native void A_FaceMaster(float max_turn = 0, float max_pitch = 270, float ang_offset = 0, float pitch_offset = 0, int flags = 0, float z_ofs = 0); native void A_Scream(); native void A_VileChase(); native void A_VileStart(); @@ -203,9 +217,6 @@ class Actor : Thinker native native void A_BossDeath(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); - native void A_PainAttack(class spawntype = "LostSoul", float angle = 0, int flags = 0, int limit = -1); - native void A_DualPainAttack(class spawntype = "LostSoul"); - native void A_PainDie(class spawntype = "LostSoul"); native void A_KeenDie(int doortag = 666); native void A_BrainPain(); native void A_BrainScream(); diff --git a/wadsrc/static/zscript/doom/painelemental.txt b/wadsrc/static/zscript/doom/painelemental.txt index ce30bbfd3..fde690b39 100644 --- a/wadsrc/static/zscript/doom/painelemental.txt +++ b/wadsrc/static/zscript/doom/painelemental.txt @@ -51,3 +51,45 @@ class PainElemental : Actor Goto See; } } + + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + native void A_PainShootSkull(Class spawntype, float angle, int flags = 0, int limit = -1); + + void A_PainAttack(class spawntype = "LostSoul", float addangle = 0, int flags = 0, int limit = -1) + { + if (target) + { + A_FaceTarget(); + A_PainShootSkull(spawntype, angle + addangle, flags, limit); + } + } + void A_DualPainAttack(class spawntype = "LostSoul") + { + if (target) + { + A_FaceTarget(); + A_PainShootSkull(spawntype, angle + 45); + A_PainShootSkull(spawntype, angle - 45); + } + } + + void A_PainDie(class spawntype = "LostSoul") + { + if (target && IsFriend(target)) + { // And I thought you were my friend! + bFriendly = false; + } + A_NoBlocking(); + A_PainShootSkull(spawntype, angle + 90); + A_PainShootSkull(spawntype, angle + 180); + A_PainShootSkull(spawntype, angle + 270); + } +} From 3fa315aaeac2217cda39b166d16edebcc0498398 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 01:14:21 +0200 Subject: [PATCH 124/255] - replaced 'vector<2>' and 'vector<3>' with 'vector2' and 'vector3'. - added initializer syntax for vectors. A vector can be set with vectorvar = (x,y,z); for a 3-dimensional vector and vectorvar = (x, y); for a 2-dimensional one. --- src/dobjtype.cpp | 2 ++ src/namedef.h | 1 + src/sc_man_scanner.re | 3 +- src/sc_man_tokens.h | 3 +- src/scripting/zscript/zcc-parse.lemon | 48 +++++++++++++++------------ src/scripting/zscript/zcc_exprlist.h | 1 + src/scripting/zscript/zcc_parser.cpp | 3 +- src/scripting/zscript/zcc_parser.h | 6 ++++ 8 files changed, 42 insertions(+), 25 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 3f5b734c4..603cb85d7 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -628,6 +628,8 @@ void PType::StaticInit() TypeVector3->AddField(NAME_X, TypeFloat64); TypeVector3->AddField(NAME_Y, TypeFloat64); TypeVector3->AddField(NAME_Z, TypeFloat64); + // allow accessing xy as a vector2. This is marked native because it's not supposed to be serialized. + TypeVector3->Symbols.AddSymbol(new PField(NAME_XY, TypeVector2, VARF_Native, 0)); TypeTable.AddType(TypeVector3); diff --git a/src/namedef.h b/src/namedef.h index 3587643e8..ea4a7b890 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -313,6 +313,7 @@ xx(WaterLevel) xx(X) xx(Y) xx(Z) +xx(XY) xx(MomX) xx(MomY) xx(MomZ) diff --git a/src/sc_man_scanner.re b/src/sc_man_scanner.re index 8fbb28ef5..bc0a4b2e2 100644 --- a/src/sc_man_scanner.re +++ b/src/sc_man_scanner.re @@ -124,7 +124,8 @@ std2: 'sound' { RET(TK_Sound); } 'state' { RET(TK_State); } 'color' { RET(TK_Color); } - 'vector' { RET(TK_Vector); } + 'vector2' { RET(TK_Vector2); } + 'vector3' { RET(TK_Vector3); } 'map' { RET(TK_Map); } 'array' { RET(TK_Array); } 'in' { RET(TK_In); } diff --git a/src/sc_man_tokens.h b/src/sc_man_tokens.h index 7d9f81e9b..2b93c9ac2 100644 --- a/src/sc_man_tokens.h +++ b/src/sc_man_tokens.h @@ -113,7 +113,8 @@ xx(TK_Include, "'include'") xx(TK_Is, "'is'") xx(TK_Replaces, "'replaces'") -xx(TK_Vector, "'vector'") +xx(TK_Vector2, "'vector2'") +xx(TK_Vector3, "'vector3'") xx(TK_Map, "'map'") xx(TK_Array, "'array'") xx(TK_In, "'in'") diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 0cf061bef..3f70799ec 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -656,7 +656,8 @@ type_name1(X) ::= int_type(X). type_name1(X) ::= FLOAT(T). { X.Int = ZCC_FloatAuto; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= DOUBLE(T). { X.Int = ZCC_Float64; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= STRING(T). { X.Int = ZCC_String; X.SourceLoc = T.SourceLoc; } -type_name1(X) ::= VECTOR(T) vector_size(A). { X.Int = A.Int; X.SourceLoc = T.SourceLoc; } +type_name1(X) ::= VECTOR2(T). { X.Int = ZCC_Vector2; X.SourceLoc = T.SourceLoc; } +type_name1(X) ::= VECTOR3(T). { X.Int = ZCC_Vector3; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= NAME(T). { X.Int = ZCC_Name; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= SOUND(T). { X.Int = ZCC_Sound; X.SourceLoc = T.SourceLoc; } type_name1(X) ::= STATE(T). { X.Int = ZCC_State; X.SourceLoc = T.SourceLoc; } @@ -686,30 +687,10 @@ type_name(X) ::= DOT dottable_id(A). X = type; } -/* Vectors can be 2, 3, or 4 entries long. Default is a 3D vector. - * (Well, actually, I'm not sure if 4D ones are going to happen - * straight away.) - */ -%token_class intconst INTCONST|UINTCONST. -vector_size(X) ::= . { X.Int = ZCC_Vector3; X.SourceLoc = stat->sc->GetMessageLine(); } -vector_size(X) ::= LT intconst(A) GT. -{ - if (A.Int >= 2 && A.Int <= 4) - { - X.Int = ZCC_Vector2 + A.Int - 2; - } - else - { - X.Int = ZCC_Vector3; - stat->sc->ScriptMessage("Invalid vector size %d\n", A.Int); - } - X.SourceLoc = A.SourceLoc; -} - /* Type names can also be used as identifiers in contexts where type names * are not normally allowed. */ %fallback IDENTIFIER - SBYTE BYTE SHORT USHORT INT UINT BOOL FLOAT DOUBLE STRING VECTOR NAME MAP ARRAY VOID. + SBYTE BYTE SHORT USHORT INT UINT BOOL FLOAT DOUBLE STRING VECTOR2 VECTOR3 NAME MAP ARRAY VOID. /* Aggregate types */ %type aggregate_type {ZCC_Type *} @@ -986,6 +967,29 @@ primary(X) ::= SUPER(T). } primary(X) ::= constant(A). { X = A; /*X-overwrites-A*/ } +primary(XX) ::= LPAREN expr(A) COMMA expr(B) COMMA expr(C) RPAREN. +{ + NEW_AST_NODE(VectorInitializer, expr, A); + expr->Operation = PEX_Vector; + expr->Type = TypeVector3; + expr->X = A; + expr->Y = B; + expr->Z = C; + XX = expr; +} + + +primary(X) ::= LPAREN expr(A) COMMA expr(B) RPAREN. +{ + NEW_AST_NODE(VectorInitializer, expr, A); + expr->Operation = PEX_Vector; + expr->Type = TypeVector2; + expr->X = A; + expr->Y = B; + expr->Z = nullptr; + X = expr; +} + primary(X) ::= LPAREN expr(A) RPAREN. { X = A; /*X-overwrites-A*/ diff --git a/src/scripting/zscript/zcc_exprlist.h b/src/scripting/zscript/zcc_exprlist.h index bbf99189c..b565c00fb 100644 --- a/src/scripting/zscript/zcc_exprlist.h +++ b/src/scripting/zscript/zcc_exprlist.h @@ -9,6 +9,7 @@ xx(FuncCall, '(') xx(ArrayAccess, TK_Array) xx(MemberAccess, '.') xx(TypeRef, TK_Class) +xx(Vector, TK_Vector2) xx(PostInc, TK_Incr) xx(PostDec, TK_Decr) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 8ebc86167..ef4a2ac41 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -141,7 +141,8 @@ static void InitTokenMap() TOKENDEF2(TK_Float, ZCC_FLOAT, NAME_Float); TOKENDEF2(TK_Double, ZCC_DOUBLE, NAME_Double); TOKENDEF2(TK_String, ZCC_STRING, NAME_String); - TOKENDEF2(TK_Vector, ZCC_VECTOR, NAME_Vector); + TOKENDEF2(TK_Vector2, ZCC_VECTOR2, NAME_Vector2); + TOKENDEF2(TK_Vector3, ZCC_VECTOR3, NAME_Vector3); TOKENDEF2(TK_Name, ZCC_NAME, NAME_Name); TOKENDEF2(TK_Map, ZCC_MAP, NAME_Map); TOKENDEF2(TK_Array, ZCC_ARRAY, NAME_Array); diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 7ba48d711..dafdb93e5 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -98,6 +98,7 @@ enum EZCCTreeNodeType AST_Default, AST_FlagStmt, AST_PropertyStmt, + AST_VectorInitializer, NUM_AST_NODE_TYPES }; @@ -385,6 +386,11 @@ struct ZCC_ExprTrinary : ZCC_Expression ZCC_Expression *Right; }; +struct ZCC_VectorInitializer : ZCC_Expression +{ + ZCC_Expression *X, *Y, *Z; +}; + struct ZCC_Statement : ZCC_TreeNode { }; From 35cd48b86b5cf2dcaec06215f7b0330b11ff2ba0 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 09:47:22 +0200 Subject: [PATCH 125/255] - fixed grammar rule for two-dimensional vectors. --- src/scripting/zscript/zcc-parse.lemon | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 3f70799ec..bbed008dd 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -979,7 +979,7 @@ primary(XX) ::= LPAREN expr(A) COMMA expr(B) COMMA expr(C) RPAREN. } -primary(X) ::= LPAREN expr(A) COMMA expr(B) RPAREN. +primary(XX) ::= LPAREN expr(A) COMMA expr(B) RPAREN. { NEW_AST_NODE(VectorInitializer, expr, A); expr->Operation = PEX_Vector; @@ -987,7 +987,7 @@ primary(X) ::= LPAREN expr(A) COMMA expr(B) RPAREN. expr->X = A; expr->Y = B; expr->Z = nullptr; - X = expr; + XX = expr; } primary(X) ::= LPAREN expr(A) RPAREN. From 3b1f411dce70fd3d11e9021840a791b3b57f947f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 10:13:07 +0200 Subject: [PATCH 126/255] - added a full set of 2D vector instructions to the VM. The existing one was 3D only but there's also need to handle two-dimensional vectors. - added the missing divv* instructions. --- src/scripting/vm/vmexec.h | 231 +++++++++++++++++++++++++++++++++----- src/scripting/vm/vmops.h | 66 +++++++---- 2 files changed, 250 insertions(+), 47 deletions(-) diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 4fbe29257..e3401eb38 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -196,7 +196,25 @@ begin: reg.a[a] = *(void **)ptr; reg.atag[a] = ATAG_GENERIC; NEXTOP; - OP(LV): + OP(LV2): + ASSERTF(a+2); ASSERTA(B); ASSERTKD(C); + GETADDR(PB,KC,X_READ_NIL); + { + auto v = (double *)ptr; + reg.f[a] = v[0]; + reg.f[a+1] = v[1]; + } + NEXTOP; + OP(LV2_R): + ASSERTF(a+2); ASSERTA(B); ASSERTD(C); + GETADDR(PB,RC,X_READ_NIL); + { + auto v = (double *)ptr; + reg.f[a] = v[0]; + reg.f[a+1] = v[1]; + } + NEXTOP; + OP(LV3): ASSERTF(a+2); ASSERTA(B); ASSERTKD(C); GETADDR(PB,KC,X_READ_NIL); { @@ -206,7 +224,7 @@ begin: reg.f[a+2] = v[2]; } NEXTOP; - OP(LV_R): + OP(LV3_R): ASSERTF(a+2); ASSERTA(B); ASSERTD(C); GETADDR(PB,RC,X_READ_NIL); { @@ -292,7 +310,25 @@ begin: GETADDR(PA,RC,X_WRITE_NIL); *(void **)ptr = reg.a[B]; NEXTOP; - OP(SV): + OP(SV2): + ASSERTA(a); ASSERTF(B+2); ASSERTKD(C); + GETADDR(PA,KC,X_WRITE_NIL); + { + auto v = (double *)ptr; + v[0] = reg.f[B]; + v[1] = reg.f[B+1]; + } + NEXTOP; + OP(SV2_R): + ASSERTA(a); ASSERTF(B+2); ASSERTD(C); + GETADDR(PA,RC,X_WRITE_NIL); + { + auto v = (double *)ptr; + v[0] = reg.f[B]; + v[1] = reg.f[B+1]; + } + NEXTOP; + OP(SV3): ASSERTA(a); ASSERTF(B+2); ASSERTKD(C); GETADDR(PA,KC,X_WRITE_NIL); { @@ -302,7 +338,7 @@ begin: v[2] = reg.f[B+2]; } NEXTOP; - OP(SV_R): + OP(SV3_R): ASSERTA(a); ASSERTF(B+2); ASSERTD(C); GETADDR(PA,RC,X_WRITE_NIL); { @@ -342,6 +378,17 @@ begin: reg.a[a] = reg.a[B]; reg.atag[a] = reg.atag[B]; NEXTOP; + OP(MOVEV2): + ASSERTF(a); ASSERTF(B); + reg.f[a] = reg.f[B]; + reg.f[a+1] = reg.f[B+1]; + NEXTOP; + OP(MOVEV3): + ASSERTF(a); ASSERTF(B); + reg.f[a] = reg.f[B]; + reg.f[a+1] = reg.f[B+1]; + reg.f[a+2] = reg.f[B+2]; + NEXTOP; OP(CAST): if (C == CAST_I2F) { @@ -1246,51 +1293,159 @@ begin: } NEXTOP; - OP(NEGV): + OP(NEGV2): + ASSERTF(a+1); ASSERTF(B+1); + reg.f[a] = -reg.f[B]; + reg.f[a+1] = -reg.f[B+1]; + NEXTOP; + + OP(ADDV2_RR): + ASSERTF(a+1); ASSERTF(B+1); ASSERTF(C+1); + fcp = ®.f[C]; + Do_ADDV2: + fbp = ®.f[B]; + reg.f[a] = fbp[0] + fcp[0]; + reg.f[a+1] = fbp[1] + fcp[1]; + NEXTOP; + OP(ADDV2_RK): + fcp = &konstf[C]; + goto Do_ADDV2; + + OP(SUBV2_RR): + ASSERTF(a+1); ASSERTF(B+1); ASSERTF(C+1); + fbp = ®.f[B]; + fcp = ®.f[C]; + Do_SUBV2: + reg.f[a] = fbp[0] - fcp[0]; + reg.f[a+1] = fbp[1] - fcp[1]; + NEXTOP; + OP(SUBV2_RK): + ASSERTF(a+1); ASSERTF(B+1); ASSERTKF(C+1); + fbp = ®.f[B]; + fcp = &konstf[C]; + goto Do_SUBV2; + OP(SUBV2_KR): + ASSERTF(A+1); ASSERTKF(B+1); ASSERTF(C+1); + fbp = &konstf[B]; + fcp = ®.f[C]; + goto Do_SUBV2; + + OP(DOTV2_RR): + ASSERTF(a); ASSERTF(B+1); ASSERTF(C+1); + reg.f[a] = reg.f[B] * reg.f[C] + reg.f[B+1] * reg.f[C+1]; + NEXTOP; + OP(DOTV2_RK): + ASSERTF(a); ASSERTF(B+1); ASSERTKF(C+1); + reg.f[a] = reg.f[B] * konstf[C] + reg.f[B+1] * konstf[C+1]; + NEXTOP; + + OP(MULVF2_RR): + ASSERTF(a+1); ASSERTF(B+1); ASSERTF(C); + fc = reg.f[C]; + fbp = ®.f[B]; + Do_MULV2: + reg.f[a] = fbp[0] * fc; + reg.f[a+1] = fbp[1] * fc; + NEXTOP; + OP(MULVF2_RK): + ASSERTF(a+1); ASSERTF(B+1); ASSERTKF(C); + fc = konstf[C]; + fbp = ®.f[B]; + goto Do_MULV2; + OP(MULVF2_KR): + ASSERTF(a+1); ASSERTKF(B+1); ASSERTF(C); + fc = reg.f[C]; + fbp = &konstf[B]; + goto Do_MULV2; + + OP(DIVVF2_RR): + ASSERTF(a+1); ASSERTF(B+1); ASSERTF(C); + fc = reg.f[C]; + fbp = ®.f[B]; + Do_DIVV2: + reg.f[a] = fbp[0] / fc; + reg.f[a+1] = fbp[1] / fc; + NEXTOP; + OP(DIVVF2_RK): + ASSERTF(a+1); ASSERTF(B+1); ASSERTKF(C); + fc = konstf[C]; + fbp = ®.f[B]; + goto Do_DIVV2; + OP(DIVVF2_KR): + ASSERTF(a+1); ASSERTKF(B+1); ASSERTF(C); + fc = reg.f[C]; + fbp = &konstf[B]; + goto Do_DIVV2; + + OP(LENV2): + ASSERTF(a); ASSERTF(B+1); + reg.f[a] = g_sqrt(reg.f[B] * reg.f[B] + reg.f[B+1] * reg.f[B+1]); + NEXTOP; + + OP(EQV2_R): + ASSERTF(B+1); ASSERTF(C+1); + fcp = ®.f[C]; + Do_EQV2: + if (a & CMP_APPROX) + { + CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); + } + else + { + CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); + } + NEXTOP; + OP(EQV2_K): + ASSERTF(B+1); ASSERTKF(C+1); + fcp = &konstf[C]; + goto Do_EQV2; + + OP(NEGV3): ASSERTF(a+2); ASSERTF(B+2); reg.f[a] = -reg.f[B]; reg.f[a+1] = -reg.f[B+1]; reg.f[a+2] = -reg.f[B+2]; NEXTOP; - OP(ADDV_RR): + OP(ADDV3_RR): ASSERTF(a+2); ASSERTF(B+2); ASSERTF(C+2); fcp = ®.f[C]; - Do_ADDV: + Do_ADDV3: fbp = ®.f[B]; reg.f[a] = fbp[0] + fcp[0]; reg.f[a+1] = fbp[1] + fcp[1]; reg.f[a+2] = fbp[2] + fcp[2]; NEXTOP; - OP(ADDV_RK): + OP(ADDV3_RK): fcp = &konstf[C]; - goto Do_ADDV; + goto Do_ADDV3; - OP(SUBV_RR): + OP(SUBV3_RR): ASSERTF(a+2); ASSERTF(B+2); ASSERTF(C+2); fbp = ®.f[B]; fcp = ®.f[C]; - Do_SUBV: + Do_SUBV3: reg.f[a] = fbp[0] - fcp[0]; reg.f[a+1] = fbp[1] - fcp[1]; reg.f[a+2] = fbp[2] - fcp[2]; NEXTOP; - OP(SUBV_RK): + OP(SUBV3_RK): ASSERTF(a+2); ASSERTF(B+2); ASSERTKF(C+2); fbp = ®.f[B]; fcp = &konstf[C]; - goto Do_SUBV; - OP(SUBV_KR): + goto Do_SUBV3; + OP(SUBV3_KR): ASSERTF(A+2); ASSERTKF(B+2); ASSERTF(C+2); fbp = &konstf[B]; fcp = ®.f[C]; - goto Do_SUBV; + goto Do_SUBV3; - OP(DOTV_RR): + OP(DOTV3_RR): ASSERTF(a); ASSERTF(B+2); ASSERTF(C+2); reg.f[a] = reg.f[B] * reg.f[C] + reg.f[B+1] * reg.f[C+1] + reg.f[B+2] * reg.f[C+2]; NEXTOP; - OP(DOTV_RK): + OP(DOTV3_RK): ASSERTF(a); ASSERTF(B+2); ASSERTKF(C+2); reg.f[a] = reg.f[B] * konstf[C] + reg.f[B+1] * konstf[C+1] + reg.f[B+2] * konstf[C+2]; NEXTOP; @@ -1319,35 +1474,55 @@ begin: fcp = &konstf[C]; goto Do_CROSSV; - OP(MULVF_RR): + OP(MULVF3_RR): ASSERTF(a+2); ASSERTF(B+2); ASSERTF(C); fc = reg.f[C]; fbp = ®.f[B]; - Do_MULV: + Do_MULV3: reg.f[a] = fbp[0] * fc; reg.f[a+1] = fbp[1] * fc; reg.f[a+2] = fbp[2] * fc; NEXTOP; - OP(MULVF_RK): + OP(MULVF3_RK): ASSERTF(a+2); ASSERTF(B+2); ASSERTKF(C); fc = konstf[C]; fbp = ®.f[B]; - goto Do_MULV; - OP(MULVF_KR): + goto Do_MULV3; + OP(MULVF3_KR): ASSERTF(a+2); ASSERTKF(B+2); ASSERTF(C); fc = reg.f[C]; fbp = &konstf[B]; - goto Do_MULV; + goto Do_MULV3; - OP(LENV): + OP(DIVVF3_RR): + ASSERTF(a+2); ASSERTF(B+2); ASSERTF(C); + fc = reg.f[C]; + fbp = ®.f[B]; + Do_DIVV3: + reg.f[a] = fbp[0] / fc; + reg.f[a+1] = fbp[1] / fc; + reg.f[a+2] = fbp[2] / fc; + NEXTOP; + OP(DIVVF3_RK): + ASSERTF(a+2); ASSERTF(B+2); ASSERTKF(C); + fc = konstf[C]; + fbp = ®.f[B]; + goto Do_DIVV3; + OP(DIVVF3_KR): + ASSERTF(a+2); ASSERTKF(B+2); ASSERTF(C); + fc = reg.f[C]; + fbp = &konstf[B]; + goto Do_DIVV3; + + OP(LENV3): ASSERTF(a); ASSERTF(B+2); reg.f[a] = g_sqrt(reg.f[B] * reg.f[B] + reg.f[B+1] * reg.f[B+1] + reg.f[B+2] * reg.f[B+2]); NEXTOP; - OP(EQV_R): + OP(EQV3_R): ASSERTF(B+2); ASSERTF(C+2); fcp = ®.f[C]; - Do_EQV: + Do_EQV3: if (a & CMP_APPROX) { CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && @@ -1359,10 +1534,10 @@ begin: CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); } NEXTOP; - OP(EQV_K): + OP(EQV3_K): ASSERTF(B+2); ASSERTKF(C+2); fcp = &konstf[C]; - goto Do_EQV; + goto Do_EQV3; OP(ADDA_RR): ASSERTA(a); ASSERTA(B); ASSERTD(C); diff --git a/src/scripting/vm/vmops.h b/src/scripting/vm/vmops.h index 9ffe2d847..ba86e2231 100644 --- a/src/scripting/vm/vmops.h +++ b/src/scripting/vm/vmops.h @@ -33,8 +33,10 @@ xx(LO, lo, RPRPKI), // load object xx(LO_R, lo, RPRPRI), xx(LP, lp, RPRPKI), // load pointer xx(LP_R, lp, RPRPRI), -xx(LV, lv, RVRPKI), // load vector -xx(LV_R, lv, RVRPRI), +xx(LV2, lv2, RVRPKI), // load vector2 +xx(LV2_R, lv2, RVRPRI), +xx(LV3, lv3, RVRPKI), // load vector3 +xx(LV3_R, lv3, RVRPRI), xx(LBIT, lbit, RIRPI8), // rA = !!(*rB & C) -- *rB is a byte @@ -53,8 +55,10 @@ xx(SS, ss, RPRSKI), // store string xx(SS_R, ss, RPRSRI), xx(SP, sp, RPRPKI), // store pointer xx(SP_R, sp, RPRPRI), -xx(SV, sv, RPRVKI), // store vector -xx(SV_R, sv, RPRVRI), +xx(SV2, sv2, RPRVKI), // store vector2 +xx(SV2_R, sv2, RPRVRI), +xx(SV3, sv3, RPRVKI), // store vector3 +xx(SV3_R, sv3, RPRVRI), xx(SBIT, sbit, RPRII8), // *rA |= C if rB is true, *rA &= ~C otherwise @@ -63,6 +67,8 @@ xx(MOVE, mov, RIRI), // dA = dB xx(MOVEF, mov, RFRF), // fA = fB xx(MOVES, mov, RSRS), // sA = sB xx(MOVEA, mov, RPRP), // aA = aB +xx(MOVEV2, mov2, RFRF), // fA = fB (2 elements) +xx(MOVEV3, mov3, RFRF), // fA = fB (3 elements) xx(CAST, cast, CAST), // xA = xB, conversion specified by C xx(DYNCAST_R, dyncast,RPRPRP), // aA = aB after casting to rkC (specifying a class) xx(DYNCAST_K, dyncast,RPRPKP), @@ -193,24 +199,46 @@ xx(LEF_RR, ble, CFRR), // if ((fkb <= fkC) != (A & 1)) then pc++ xx(LEF_RK, ble, CFRK), xx(LEF_KR, ble, CFKR), -// Vector math. -xx(NEGV, negv, RVRV), // vA = -vB -xx(ADDV_RR, addv, RVRVRV), // vA = vB + vkC -xx(ADDV_RK, addv, RVRVKV), -xx(SUBV_RR, subv, RVRVRV), // vA = vkB - vkC -xx(SUBV_RK, subv, RVRVKV), -xx(SUBV_KR, subv, RVKVRV), -xx(DOTV_RR, dotv, RVRVRV), // va = vB dot vkC -xx(DOTV_RK, dotv, RVRVKV), +// Vector math. (2D) +xx(NEGV2, negv2, RVRV), // vA = -vB +xx(ADDV2_RR, addv2, RVRVRV), // vA = vB + vkC +xx(ADDV2_RK, addv2, RVRVKV), +xx(SUBV2_RR, subv2, RVRVRV), // vA = vkB - vkC +xx(SUBV2_RK, subv2, RVRVKV), +xx(SUBV2_KR, subv2, RVKVRV), +xx(DOTV2_RR, dotv2, RVRVRV), // va = vB dot vkC +xx(DOTV2_RK, dotv2, RVRVKV), +xx(MULVF2_RR, mulv2, RVRVRV), // vA = vkB * fkC +xx(MULVF2_RK, mulv2, RVRVKV), +xx(MULVF2_KR, mulv2, RVKVRV), +xx(DIVVF2_RR, divv2, RVRVRV), // vA = vkB / fkC +xx(DIVVF2_RK, divv2, RVRVKV), +xx(DIVVF2_KR, divv2, RVKVRV), +xx(LENV2, lenv2, RFRV), // fA = vB.Length +xx(EQV2_R, beqv2, CVRR), // if ((vB == vkC) != A) then pc++ (inexact if A & 32) +xx(EQV2_K, beqv2, CVRK), + +// Vector math (3D) +xx(NEGV3, negv3, RVRV), // vA = -vB +xx(ADDV3_RR, addv3, RVRVRV), // vA = vB + vkC +xx(ADDV3_RK, addv3, RVRVKV), +xx(SUBV3_RR, subv3, RVRVRV), // vA = vkB - vkC +xx(SUBV3_RK, subv3, RVRVKV), +xx(SUBV3_KR, subv3, RVKVRV), +xx(DOTV3_RR, dotv3, RVRVRV), // va = vB dot vkC +xx(DOTV3_RK, dotv3, RVRVKV), xx(CROSSV_RR, crossv, RVRVRV), // vA = vkB cross vkC xx(CROSSV_RK, crossv, RVRVKV), xx(CROSSV_KR, crossv, RVKVRV), -xx(MULVF_RR, mulv, RVRVRV), // vA = vkB * fkC -xx(MULVF_RK, mulv, RVRVKV), -xx(MULVF_KR, mulv, RVKVRV), -xx(LENV, lenv, RFRV), // fA = vB.Length -xx(EQV_R, beqv, CVRR), // if ((vB == vkC) != A) then pc++ (inexact if A & 32) -xx(EQV_K, beqv, CVRK), +xx(MULVF3_RR, mulv3, RVRVRV), // vA = vkB * fkC +xx(MULVF3_RK, mulv3, RVRVKV), +xx(MULVF3_KR, mulv3, RVKVRV), +xx(DIVVF3_RR, divv3, RVRVRV), // vA = vkB / fkC +xx(DIVVF3_RK, divv3, RVRVKV), +xx(DIVVF3_KR, divv3, RVKVRV), +xx(LENV3, lenv3, RFRV), // fA = vB.Length +xx(EQV3_R, beqv3, CVRR), // if ((vB == vkC) != A) then pc++ (inexact if A & 33) +xx(EQV3_K, beqv3, CVRK), // Pointer math. xx(ADDA_RR, add, RPRPRI), // pA = pB + dkC From f511a9398ec07039ceaa27aa847740f73bf3ec57 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 10:44:01 +0200 Subject: [PATCH 127/255] - changed GetStore/LoadMoveOp and GetRegType to be based on a set of member variables instead of using virtual functions to return such trivial values. This not only creates significantly better code but also allows overriding these settings without having to create a new class just for changing them (as is needed for vectors.) --- src/dobjtype.cpp | 307 +++++--------------------- src/dobjtype.h | 46 ++-- src/scripting/zscript/zcc_compile.cpp | 2 +- 3 files changed, 75 insertions(+), 280 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 603cb85d7..bec28c7ec 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -191,18 +191,6 @@ IMPLEMENT_ABSTRACT_POINTY_CLASS(PType) DECLARE_POINTER(HashNext) END_POINTERS -//========================================================================== -// -// PType Default Constructor -// -//========================================================================== - -PType::PType() -: Size(0), Align(1), HashNext(NULL) -{ - mDescriptiveName = "Type"; -} - //========================================================================== // // PType Parameterized Constructor @@ -213,6 +201,10 @@ PType::PType(unsigned int size, unsigned int align) : Size(size), Align(align), HashNext(NULL) { mDescriptiveName = "Type"; + loadOp = OP_NOP; + storeOp = OP_NOP; + moveOp = OP_NOP; + RegType = REGT_NIL; } //========================================================================== @@ -477,54 +469,6 @@ double PType::GetValueFloat(void *addr) const return 0; } -//========================================================================== -// -// PType :: GetStoreOp -// -//========================================================================== - -int PType::GetStoreOp() const -{ - assert(0 && "Cannot store this type"); - return OP_NOP; -} - -//========================================================================== -// -// PType :: GetLoadOp -// -//========================================================================== - -int PType::GetLoadOp() const -{ - assert(0 && "Cannot load this type"); - return OP_NOP; -} - -//========================================================================== -// -// PType :: GetMoveOp -// -//========================================================================== - -int PType::GetMoveOp() const -{ - assert(0 && "Cannot move this type"); - return OP_NOP; -} - -//========================================================================== -// -// PType :: GetRegType -// -//========================================================================== - -int PType::GetRegType() const -{ - //assert(0 && "No register for this type"); // wrong place for this assert, it makes it impossible to use this function to check for bad types. - return REGT_NIL; -} - //========================================================================== // // PType :: IsMatch @@ -747,6 +691,7 @@ PInt::PInt() mDescriptiveName = "SInt32"; Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Min, this, -0x7FFFFFFF - 1)); Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Max, this, 0x7FFFFFFF)); + SetOps; } //========================================================================== @@ -773,6 +718,33 @@ PInt::PInt(unsigned int size, bool unsign) Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Min, this, 0u)); Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Max, this, (1u << (8 * size)) - 1)); } + SetOps(); +} + +void PInt::SetOps() +{ + moveOp = OP_MOVE; + RegType = REGT_INT; + if (Size == 4) + { + storeOp = OP_SW; + loadOp = OP_LW; + } + else if (Size == 1) + { + storeOp = OP_SB; + loadOp = Unsigned ? OP_LBU : OP_LB; + } + else if (Size == 2) + { + storeOp = OP_SH; + loadOp = Unsigned ? OP_LHU : OP_LH; + } + else + { + assert(0 && "Unhandled integer size"); + storeOp = OP_NOP; + } } //========================================================================== @@ -942,76 +914,6 @@ double PInt::GetValueFloat(void *addr) const // //========================================================================== -int PInt::GetStoreOp() const -{ - if (Size == 4) - { - return OP_SW; - } - else if (Size == 1) - { - return OP_SB; - } - else if (Size == 2) - { - return OP_SH; - } - else - { - assert(0 && "Unhandled integer size"); - return OP_NOP; - } -} - -//========================================================================== -// -// PInt :: GetLoadOp -// -//========================================================================== - -int PInt::GetLoadOp() const -{ - if (Size == 4) - { - return OP_LW; - } - else if (Size == 1) - { - return Unsigned ? OP_LBU : OP_LB; - } - else if (Size == 2) - { - return Unsigned ? OP_LHU : OP_LH; - } - else - { - assert(0 && "Unhandled integer size"); - return OP_NOP; - } -} - -//========================================================================== -// -// PInt :: GetLoadOp -// -//========================================================================== - -int PInt::GetMoveOp() const -{ - return OP_MOVE; -} - -//========================================================================== -// -// PInt :: GetRegType -// -//========================================================================== - -int PInt::GetRegType() const -{ - return REGT_INT; -} - /* PBool ******************************************************************/ IMPLEMENT_CLASS(PBool) @@ -1048,6 +950,7 @@ PFloat::PFloat() { mDescriptiveName = "Float"; SetDoubleSymbols(); + SetOps(); } //========================================================================== @@ -1070,6 +973,7 @@ PFloat::PFloat(unsigned int size) MemberOnly = true; SetSingleSymbols(); } + SetOps(); } //========================================================================== @@ -1264,60 +1168,21 @@ double PFloat::GetValueFloat(void *addr) const // //========================================================================== -int PFloat::GetStoreOp() const +void PFloat::SetOps() { if (Size == 4) { - return OP_SSP; + storeOp = OP_SSP; + loadOp = OP_LSP; } else { assert(Size == 8); - return OP_SDP; + storeOp = OP_SDP; + loadOp = OP_LDP; } -} - -//========================================================================== -// -// PFloat :: GetLoadOp -// -//========================================================================== - -int PFloat::GetLoadOp() const -{ - if (Size == 4) - { - return OP_LSP; - } - else - { - assert(Size == 8); - return OP_LDP; - } - assert(0 && "Cannot load this type"); - return OP_NOP; -} - -//========================================================================== -// -// PFloat :: GetMoveOp -// -//========================================================================== - -int PFloat::GetMoveOp() const -{ - return OP_MOVEF; -} - -//========================================================================== -// -// PFloat :: GetRegType -// -//========================================================================== - -int PFloat::GetRegType() const -{ - return REGT_FLOAT; + moveOp = OP_MOVEF; + RegType = REGT_FLOAT; } /* PString ****************************************************************/ @@ -1554,50 +1419,10 @@ PStatePointer::PStatePointer() : PBasicType(sizeof(FState *), __alignof(FState *)) { mDescriptiveName = "State"; -} - -//========================================================================== -// -// PStatePointer :: GetStoreOp -// -//========================================================================== - -int PStatePointer::GetStoreOp() const -{ - return OP_SP; -} - -//========================================================================== -// -// PStatePointer :: GetLoadOp -// -//========================================================================== - -int PStatePointer::GetLoadOp() const -{ - return OP_LP; -} - -//========================================================================== -// -// PStatePointer :: GetMoveOp -// -//========================================================================== - -int PStatePointer::GetMoveOp() const -{ - return OP_MOVEA; -} - -//========================================================================== -// -// PStatePointer :: GetRegType -// -//========================================================================== - -int PStatePointer::GetRegType() const -{ - return REGT_POINTER; + storeOp = OP_SP; + loadOp = OP_LP; + moveOp = OP_MOVEA; + RegType = REGT_POINTER; } //========================================================================== @@ -1640,6 +1465,7 @@ PPointer::PPointer() : PBasicType(sizeof(void *), __alignof(void *)), PointedType(NULL) { mDescriptiveName = "NullPointer"; + SetOps(); } //========================================================================== @@ -1652,6 +1478,7 @@ PPointer::PPointer(PType *pointsat) : PBasicType(sizeof(void *), __alignof(void *)), PointedType(pointsat) { mDescriptiveName.Format("Pointer<%s>", pointsat->DescriptiveName()); + SetOps(); } //========================================================================== @@ -1660,42 +1487,12 @@ PPointer::PPointer(PType *pointsat) // //========================================================================== -int PPointer::GetStoreOp() const +void PPointer::SetOps() { - return OP_SP; -} - -//========================================================================== -// -// PPointer :: GetLoadOp -// -//========================================================================== - -int PPointer::GetLoadOp() const -{ - return (PointedType && PointedType->IsKindOf(RUNTIME_CLASS(PClass))) ? OP_LO : OP_LP; -} - -//========================================================================== -// -// PPointer :: GetMoveOp -// -//========================================================================== - -int PPointer::GetMoveOp() const -{ - return OP_MOVEA; -} - -//========================================================================== -// -// PPointer :: GetRegType -// -//========================================================================== - -int PPointer::GetRegType() const -{ - return REGT_POINTER; + storeOp = OP_SP; + loadOp = (PointedType && PointedType->IsKindOf(RUNTIME_CLASS(PClass))) ? OP_LO : OP_LP; + moveOp = OP_MOVEA; + RegType = REGT_POINTER; } //========================================================================== diff --git a/src/dobjtype.h b/src/dobjtype.h index 0c26f3a35..984f5a379 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -204,6 +204,7 @@ class PType : public PTypeBase HAS_OBJECT_POINTERS; protected: enum { MetaClassNum = CLASSREG_PClassType }; + public: typedef PClassType MetaClass; MetaClass *GetClass() const; @@ -223,9 +224,9 @@ public: PSymbolTable Symbols; bool MemberOnly = false; // type may only be used as a struct/class member but not as a local variable or function argument. FString mDescriptiveName; + BYTE loadOp, storeOp, moveOp, RegType; - PType(); - PType(unsigned int size, unsigned int align); + PType(unsigned int size = 1, unsigned int align = 1); virtual ~PType(); bool AddConversion(PType *target, void (*convertconst)(ZCC_ExprConstant *, class FSharedStringArena &)); @@ -267,16 +268,28 @@ public: virtual double GetValueFloat(void *addr) const; // Gets the opcode to store from a register to memory - virtual int GetStoreOp() const; + int GetStoreOp() const + { + return storeOp; + } // Gets the opcode to load from memory to a register - virtual int GetLoadOp() const; + int GetLoadOp() const + { + return loadOp; + } // Gets the opcode to move from register to another register - virtual int GetMoveOp() const; + int GetMoveOp() const + { + return moveOp; + } // Gets the register type for this type - virtual int GetRegType() const; + int GetRegType() const + { + return RegType; + } // Returns true if this type matches the two identifiers. Referring to the // above table, any type is identified by at most two characteristics. Each @@ -410,14 +423,11 @@ public: virtual void SetValue(void *addr, double val); virtual int GetValueInt(void *addr) const; virtual double GetValueFloat(void *addr) const; - virtual int GetStoreOp() const; - virtual int GetLoadOp() const; - virtual int GetMoveOp() const; - virtual int GetRegType() const; bool Unsigned; protected: PInt(); + void SetOps(); }; class PBool : public PInt @@ -440,12 +450,9 @@ public: virtual void SetValue(void *addr, double val); virtual int GetValueInt(void *addr) const; virtual double GetValueFloat(void *addr) const; - virtual int GetStoreOp() const; - virtual int GetLoadOp() const; - virtual int GetMoveOp() const; - virtual int GetRegType() const; protected: PFloat(); + void SetOps(); private: struct SymbolInitF { @@ -518,11 +525,6 @@ public: void WriteValue(FSerializer &ar, const char *key,const void *addr) const override; bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; - - virtual int GetStoreOp() const; - virtual int GetLoadOp() const; - virtual int GetMoveOp() const; - virtual int GetRegType() const; }; class PPointer : public PBasicType @@ -535,11 +537,6 @@ public: PType *PointedType; - virtual int GetStoreOp() const; - virtual int GetLoadOp() const; - virtual int GetMoveOp() const; - virtual int GetRegType() const; - virtual bool IsMatch(intptr_t id1, intptr_t id2) const; virtual void GetTypeIDs(intptr_t &id1, intptr_t &id2) const; @@ -547,6 +544,7 @@ public: bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; protected: + void SetOps(); }; class PClassPointer : public PPointer diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 370e65919..dc638de0f 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1461,7 +1461,7 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n } if (retval != TypeError && retval->MemberOnly && !formember) { - Error(field, "Invalid type %s", retval->DescriptiveName()); // fixme: Types need a descriptive name that can be output here. + Error(field, "Invalid type %s", retval->DescriptiveName()); return TypeError; } return retval; From ed5a94d18733f5f70230d537dede7e04364b70c7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 13:30:19 +0200 Subject: [PATCH 128/255] - fixed GetOps() call and added info for vectors. --- src/dobjtype.cpp | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index bec28c7ec..fd454896e 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -567,6 +567,10 @@ void PType::StaticInit() TypeVector2->AddField(NAME_X, TypeFloat64); TypeVector2->AddField(NAME_Y, TypeFloat64); TypeTable.AddType(TypeVector2); + TypeVector2->loadOp = OP_LV2; + TypeVector2->storeOp = OP_SV2; + TypeVector2->moveOp = OP_MOVEV2; + TypeVector2->RegType = REGT_FLOAT|REGT_MULTIREG; TypeVector3 = new PStruct(NAME_Vector3, nullptr); TypeVector3->AddField(NAME_X, TypeFloat64); @@ -575,6 +579,10 @@ void PType::StaticInit() // allow accessing xy as a vector2. This is marked native because it's not supposed to be serialized. TypeVector3->Symbols.AddSymbol(new PField(NAME_XY, TypeVector2, VARF_Native, 0)); TypeTable.AddType(TypeVector3); + TypeVector2->loadOp = OP_LV3; + TypeVector2->storeOp = OP_SV3; + TypeVector2->moveOp = OP_MOVEV3; + TypeVector2->RegType = REGT_FLOAT | REGT_MULTIREG; @@ -691,7 +699,7 @@ PInt::PInt() mDescriptiveName = "SInt32"; Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Min, this, -0x7FFFFFFF - 1)); Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Max, this, 0x7FFFFFFF)); - SetOps; + SetOps(); } //========================================================================== From f2f365bfef4bc8ecfc1ee306a994af8766d03f60 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 14:43:29 +0200 Subject: [PATCH 129/255] - fixed setup for PString which was missing the load/store/move instructions which caused me to overlook its register type. - properly set up the vector types. - fixed: a struct must start with a size of 0, not 1. This caused the layout of the vectors to be broken. --- src/dobjtype.cpp | 29 ++++++++++++++--------------- src/dobjtype.h | 8 +++++--- 2 files changed, 19 insertions(+), 18 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index fd454896e..7eb152ebd 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -205,6 +205,7 @@ PType::PType(unsigned int size, unsigned int align) storeOp = OP_NOP; moveOp = OP_NOP; RegType = REGT_NIL; + RegCount = 1; } //========================================================================== @@ -570,7 +571,8 @@ void PType::StaticInit() TypeVector2->loadOp = OP_LV2; TypeVector2->storeOp = OP_SV2; TypeVector2->moveOp = OP_MOVEV2; - TypeVector2->RegType = REGT_FLOAT|REGT_MULTIREG; + TypeVector2->RegType = REGT_FLOAT; + TypeVector2->RegCount = 2; TypeVector3 = new PStruct(NAME_Vector3, nullptr); TypeVector3->AddField(NAME_X, TypeFloat64); @@ -579,10 +581,11 @@ void PType::StaticInit() // allow accessing xy as a vector2. This is marked native because it's not supposed to be serialized. TypeVector3->Symbols.AddSymbol(new PField(NAME_XY, TypeVector2, VARF_Native, 0)); TypeTable.AddType(TypeVector3); - TypeVector2->loadOp = OP_LV3; - TypeVector2->storeOp = OP_SV3; - TypeVector2->moveOp = OP_MOVEV3; - TypeVector2->RegType = REGT_FLOAT | REGT_MULTIREG; + TypeVector3->loadOp = OP_LV3; + TypeVector3->storeOp = OP_SV3; + TypeVector3->moveOp = OP_MOVEV3; + TypeVector3->RegType = REGT_FLOAT; + TypeVector3->RegCount = 3; @@ -1207,17 +1210,11 @@ PString::PString() : PBasicType(sizeof(FString), __alignof(FString)) { mDescriptiveName = "String"; -} + storeOp = OP_SS; + loadOp = OP_LS; + moveOp = OP_MOVES; + RegType = REGT_STRING; -//========================================================================== -// -// PString :: GetRegType -// -//========================================================================== - -int PString::GetRegType() const -{ - return REGT_STRING; } //========================================================================== @@ -2089,6 +2086,7 @@ IMPLEMENT_CLASS(PStruct) PStruct::PStruct() { mDescriptiveName = "Struct"; + Size = 0; } //========================================================================== @@ -2101,6 +2099,7 @@ PStruct::PStruct(FName name, PTypeBase *outer) : PNamedType(name, outer) { mDescriptiveName.Format("Struct<%s>", name.GetChars()); + Size = 0; } //========================================================================== diff --git a/src/dobjtype.h b/src/dobjtype.h index 984f5a379..302352b21 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -224,7 +224,7 @@ public: PSymbolTable Symbols; bool MemberOnly = false; // type may only be used as a struct/class member but not as a local variable or function argument. FString mDescriptiveName; - BYTE loadOp, storeOp, moveOp, RegType; + BYTE loadOp, storeOp, moveOp, RegType, RegCount; PType(unsigned int size = 1, unsigned int align = 1); virtual ~PType(); @@ -291,6 +291,10 @@ public: return RegType; } + int GetRegCount() const + { + return RegCount; + } // Returns true if this type matches the two identifiers. Referring to the // above table, any type is identified by at most two characteristics. Each // type that implements this function will cast these to the appropriate type. @@ -477,8 +481,6 @@ class PString : public PBasicType public: PString(); - virtual int GetRegType() const; - void WriteValue(FSerializer &ar, const char *key,const void *addr) const override; bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; void SetDefaultValue(void *base, unsigned offset, TArray *special=NULL) const override; From 9400f97189543987bec49fccdf2ceed1069bab6c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 28 Oct 2016 15:15:30 +0200 Subject: [PATCH 130/255] - implemented local vector variables. Currently only the definition plus initial assignment works. - removed all vector4 handling that had already been added, now that this type can no longer be defined. --- src/scripting/codegeneration/codegen.cpp | 208 ++++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 29 +++- src/scripting/vm/vm.h | 2 +- src/scripting/zscript/ast.cpp | 14 +- src/scripting/zscript/zcc-parse.lemon | 49 +++--- src/scripting/zscript/zcc_compile.cpp | 14 +- src/scripting/zscript/zcc_parser.cpp | 5 +- src/scripting/zscript/zcc_parser.h | 1 - 8 files changed, 278 insertions(+), 44 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 3eaaa7170..773fc4b1a 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -178,8 +178,8 @@ FxLocalVariableDeclaration *FCompileContext::FindLocalVariable(FName name) // //========================================================================== -ExpEmit::ExpEmit(VMFunctionBuilder *build, int type) -: RegNum(build->Registers[type].Get(1)), RegType(type), Konst(false), Fixed(false), Final(false), Target(false) +ExpEmit::ExpEmit(VMFunctionBuilder *build, int type, int count) +: RegNum(build->Registers[type].Get(count)), RegType(type), RegCount(count), Konst(false), Fixed(false), Final(false), Target(false) { } @@ -187,7 +187,7 @@ void ExpEmit::Free(VMFunctionBuilder *build) { if (!Fixed && !Konst && RegType <= REGT_TYPE) { - build->Registers[RegType].Return(RegNum, 1); + build->Registers[RegType].Return(RegNum, RegCount); } } @@ -195,6 +195,7 @@ void ExpEmit::Reuse(VMFunctionBuilder *build) { if (!Fixed && !Konst) { + assert(RegCount == 1); bool success = build->Registers[RegType].Reuse(RegNum); assert(success && "Attempt to reuse a register that is already in use"); } @@ -434,6 +435,200 @@ ExpEmit FxConstant::Emit(VMFunctionBuilder *build) // //========================================================================== +FxVectorInitializer::FxVectorInitializer(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc) + :FxExpression(EFX_VectorInitializer, sc) +{ + xyz[0] = x; + xyz[1] = y; + xyz[2] = z; + isConst = false; + ValueType = TypeVoid; // we do not know yet +} + +FxVectorInitializer::~FxVectorInitializer() +{ + for (auto &a : xyz) + SAFE_DELETE(a); +} + +FxExpression *FxVectorInitializer::Resolve(FCompileContext&ctx) +{ + bool fails = false; + + for (auto &a : xyz) + { + if (a != nullptr) + { + a = a->Resolve(ctx); + if (a == nullptr) fails = true; + else + { + if (a->ValueType != TypeVector2) // a vec3 may be initialized with (vec2, z) + { + a = new FxFloatCast(a); + a = a->Resolve(ctx); + fails |= (a == nullptr); + } + } + } + } + if (fails) + { + delete this; + return nullptr; + } + // at this point there are three legal cases: + // * two floats = vector2 + // * three floats = vector3 + // * vector2 + float = vector3 + if (xyz[0]->ValueType == TypeVector2) + { + if (xyz[1]->ValueType != TypeFloat64 || xyz[2] != nullptr) + { + ScriptPosition.Message(MSG_ERROR, "Not a valid vector"); + delete this; + return nullptr; + } + ValueType = TypeVector3; + if (xyz[0]->ExprType == EFX_VectorInitializer) + { + // If two vector initializers are nested, unnest them now. + auto vi = static_cast(xyz[0]); + xyz[2] = xyz[1]; + xyz[1] = vi->xyz[1]; + xyz[0] = vi->xyz[0]; + delete vi; + } + } + else if (xyz[0]->ValueType == TypeFloat64 && xyz[1]->ValueType == TypeFloat64) + { + ValueType = xyz[2] == nullptr ? TypeVector2 : TypeVector3; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Not a valid vector"); + delete this; + return nullptr; + } + + // check if all elements are constant. If so this can be emitted as a constant vector. + isConst = true; + for (auto &a : xyz) + { + if (a != nullptr && !a->isConstant()) isConst = false; + } + return this; +} + +static ExpEmit EmitKonst(VMFunctionBuilder *build, ExpEmit &emit) +{ + if (emit.Konst) + { + ExpEmit out(build, REGT_FLOAT); + build->Emit(OP_LKF, out.RegNum, emit.RegNum); + return out; + } + return emit; +} + +ExpEmit FxVectorInitializer::Emit(VMFunctionBuilder *build) +{ + // no const handling here. Ultimstely it's too rarely used (i.e. the only fully constant vector ever allocated in ZDoom is the 0-vector in a very few places) + // and the negatives (excessive allocation of float constants) outweigh the positives (saved a few instructions) + assert(xyz[0] != nullptr); + assert(xyz[1] != nullptr); + if (ValueType == TypeVector2) + { + ExpEmit xval = EmitKonst(build, xyz[0]->Emit(build)); + ExpEmit yval = EmitKonst(build, xyz[1]->Emit(build)); + assert(xval.RegType == REGT_FLOAT && yval.RegType == REGT_FLOAT); + if (yval.RegNum == xval.RegNum + 1) + { + // The results are already in two continuous registers so just return them as-is. + xval.RegCount++; + return xval; + } + else + { + // The values are not in continuous registers so they need to be copied together now. + ExpEmit out(build, REGT_FLOAT, 2); + build->Emit(OP_MOVEF, out.RegNum, xval.RegNum); + build->Emit(OP_MOVEF, out.RegNum + 1, yval.RegNum); + xval.Free(build); + yval.Free(build); + return out; + } + } + else if (xyz[0]->ValueType == TypeVector2) // vec2+float + { + ExpEmit xyval = xyz[0]->Emit(build); + ExpEmit zval = EmitKonst(build, xyz[1]->Emit(build)); + assert(xyval.RegType == REGT_FLOAT && xyval.RegCount == 2 && zval.RegType == REGT_FLOAT); + if (zval.RegNum == xyval.RegNum + 2) + { + // The results are already in three continuous registers so just return them as-is. + xyval.RegCount++; + return xyval; + } + else + { + // The values are not in continuous registers so they need to be copied together now. + ExpEmit out(build, REGT_FLOAT, 3); + build->Emit(OP_MOVEV2, out.RegNum, xyval.RegNum); + build->Emit(OP_MOVEF, out.RegNum + 2, zval.RegNum); + xyval.Free(build); + zval.Free(build); + return out; + } + } + else // 3*float + { + assert(xyz[2] != nullptr); + ExpEmit xval = EmitKonst(build, xyz[0]->Emit(build)); + ExpEmit yval = EmitKonst(build, xyz[1]->Emit(build)); + ExpEmit zval = EmitKonst(build, xyz[2]->Emit(build)); + assert(xval.RegType == REGT_FLOAT && yval.RegType == REGT_FLOAT && zval.RegType == REGT_FLOAT); + if (yval.RegNum == xval.RegNum + 1 && zval.RegNum == xval.RegNum + 2) + { + // The results are already in three continuous registers so just return them as-is. + xval.RegCount += 2; + return xval; + } + else + { + // The values are not in continuous registers so they need to be copied together now. + ExpEmit out(build, REGT_FLOAT, 3); + //Try to optimize a bit... + if (yval.RegNum == xval.RegNum + 1) + { + build->Emit(OP_MOVEV2, out.RegNum, xval.RegNum); + build->Emit(OP_MOVEF, out.RegNum + 2, zval.RegNum); + } + else if (zval.RegNum == yval.RegNum + 1) + { + build->Emit(OP_MOVEF, out.RegNum, xval.RegNum); + build->Emit(OP_MOVEV2, out.RegNum+1, yval.RegNum); + } + else + { + build->Emit(OP_MOVEF, out.RegNum, xval.RegNum); + build->Emit(OP_MOVEF, out.RegNum + 1, yval.RegNum); + build->Emit(OP_MOVEF, out.RegNum + 2, zval.RegNum); + } + xval.Free(build); + yval.Free(build); + zval.Free(build); + return out; + } + } +} + +//========================================================================== +// +// +// +//========================================================================== + FxBoolCast::FxBoolCast(FxExpression *x, bool needvalue) : FxExpression(EFX_BoolCast, x->ScriptPosition) { @@ -4613,7 +4808,7 @@ ExpEmit FxStructMember::Emit(VMFunctionBuilder *build) } int offsetreg = build->GetConstantInt((int)membervar->Offset); - ExpEmit loc(build, membervar->Type->GetRegType()); + ExpEmit loc(build, membervar->Type->GetRegType(), membervar->Type->GetRegCount()); if (membervar->BitValue == -1) { @@ -7118,6 +7313,7 @@ FxLocalVariableDeclaration::FxLocalVariableDeclaration(PType *type, FName name, ValueType = type; VarFlags = varflags; Name = name; + RegCount = type == TypeVector2 ? 2 : type == TypeVector3 ? 3 : 1; Init = initval == nullptr? nullptr : new FxTypeCast(initval, type, false); } @@ -7139,7 +7335,7 @@ ExpEmit FxLocalVariableDeclaration::Emit(VMFunctionBuilder *build) { if (Init == nullptr) { - RegNum = build->Registers[ValueType->GetRegType()].Get(1); + RegNum = build->Registers[ValueType->GetRegType()].Get(RegCount); } else { @@ -7188,5 +7384,5 @@ void FxLocalVariableDeclaration::Release(VMFunctionBuilder *build) { // Release the register after the containing block gets closed assert(RegNum != -1); - build->Registers[ValueType->GetRegType()].Return(RegNum, 1); + build->Registers[ValueType->GetRegType()].Return(RegNum, RegCount); } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index cd93b8894..30401f907 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -193,13 +193,13 @@ struct ExpVal struct ExpEmit { - ExpEmit() : RegNum(0), RegType(REGT_NIL), Konst(false), Fixed(false), Final(false), Target(false) {} - ExpEmit(int reg, int type, bool konst = false, bool fixed = false) : RegNum(reg), RegType(type), Konst(konst), Fixed(fixed), Final(false), Target(false) {} - ExpEmit(VMFunctionBuilder *build, int type); + ExpEmit() : RegNum(0), RegType(REGT_NIL), RegCount(1), Konst(false), Fixed(false), Final(false), Target(false) {} + ExpEmit(int reg, int type, bool konst = false, bool fixed = false) : RegNum(reg), RegType(type), RegCount(1), Konst(konst), Fixed(fixed), Final(false), Target(false) {} + ExpEmit(VMFunctionBuilder *build, int type, int count = 1); void Free(VMFunctionBuilder *build); void Reuse(VMFunctionBuilder *build); - BYTE RegNum, RegType, Konst:1, Fixed:1, Final:1, Target:1; + BYTE RegNum, RegType, RegCount, Konst:1, Fixed:1, Final:1, Target:1; }; enum EFxType @@ -264,6 +264,7 @@ enum EFxType EFX_LocalVariableDeclaration, EFX_SwitchStatement, EFX_CaseStatement, + EFX_VectorInitializer, EFX_COUNT }; @@ -449,6 +450,25 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// +// +//========================================================================== + +class FxVectorInitializer : public FxExpression +{ + FxExpression *xyz[3]; + bool isConst; // gets set to true if all element are const + +public: + FxVectorInitializer(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc); + ~FxVectorInitializer(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // @@ -1561,6 +1581,7 @@ class FxLocalVariableDeclaration : public FxExpression FName Name; FxExpression *Init; int VarFlags; + int RegCount; public: int RegNum = -1; diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 5684d5775..c14a8a6e5 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -137,7 +137,7 @@ enum REGT_MULTIREG = 8, // (e.g. a vector) REGT_ADDROF = 32, // used with PARAM: pass address of this register - REGT_NIL = 255 // parameter was omitted + REGT_NIL = 128 // parameter was omitted }; #define RET_FINAL (0x80) // Used with RET and RETI in the destination slot: this is the final return value diff --git a/src/scripting/zscript/ast.cpp b/src/scripting/zscript/ast.cpp index e23fc5a87..e77c631e1 100644 --- a/src/scripting/zscript/ast.cpp +++ b/src/scripting/zscript/ast.cpp @@ -52,7 +52,6 @@ static const char *BuiltInTypeNames[] = "string", "vector2", "vector3", - "vector4", "name", "color", "state", @@ -622,6 +621,16 @@ static void PrintExprTrinary(FLispString &out, ZCC_TreeNode *node) out.Close(); } +static void PrintVectorInitializer(FLispString &out, ZCC_TreeNode *node) +{ + ZCC_VectorInitializer *enode = (ZCC_VectorInitializer *)node; + OpenExprType(out, enode->Operation); + PrintNodes(out, enode->X); + PrintNodes(out, enode->Y); + PrintNodes(out, enode->Z); + out.Close(); +} + static void PrintFuncParam(FLispString &out, ZCC_TreeNode *node) { ZCC_FuncParm *pnode = (ZCC_FuncParm *)node; @@ -889,7 +898,8 @@ void (* const TreeNodePrinter[NUM_AST_NODE_TYPES])(FLispString &, ZCC_TreeNode * PrintFuncDeclarator, PrintDefault, PrintFlagStmt, - PrintPropertyStmt + PrintPropertyStmt, + PrintVectorInitializer, }; FString ZCC_PrintAST(ZCC_TreeNode *root) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index bbed008dd..173ec27fc 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -945,6 +945,7 @@ func_param_flags(X) ::= func_param_flags(A) OPTIONAL(T). { X.Int = A.Int | ZCC_O %type expr{ZCC_Expression *} %type primary{ZCC_Expression *} +%type vectorinit{ZCC_VectorInitializer*} %type unary_expr{ZCC_Expression *} %type constant{ZCC_ExprConstant *} @@ -966,29 +967,7 @@ primary(X) ::= SUPER(T). X = expr; } primary(X) ::= constant(A). { X = A; /*X-overwrites-A*/ } - -primary(XX) ::= LPAREN expr(A) COMMA expr(B) COMMA expr(C) RPAREN. -{ - NEW_AST_NODE(VectorInitializer, expr, A); - expr->Operation = PEX_Vector; - expr->Type = TypeVector3; - expr->X = A; - expr->Y = B; - expr->Z = C; - XX = expr; -} - - -primary(XX) ::= LPAREN expr(A) COMMA expr(B) RPAREN. -{ - NEW_AST_NODE(VectorInitializer, expr, A); - expr->Operation = PEX_Vector; - expr->Type = TypeVector2; - expr->X = A; - expr->Y = B; - expr->Z = nullptr; - XX = expr; -} +primary(X) ::= vectorinit(A). { X = A; /*X-overwrites-A*/ } primary(X) ::= LPAREN expr(A) RPAREN. { @@ -1039,6 +1018,30 @@ primary(X) ::= SCOPE primary(B). X = expr2; } */ + +vectorinit(XX) ::= LPAREN expr(A) COMMA expr(B) COMMA expr(C) RPAREN. [DOT] +{ + NEW_AST_NODE(VectorInitializer, expr, A); + expr->Operation = PEX_Vector; + expr->Type = TypeVector3; + expr->X = A; + expr->Y = B; + expr->Z = C; + XX = expr; +} + + +vectorinit(XX) ::= LPAREN expr(A) COMMA expr(B) RPAREN. [DOT] +{ + NEW_AST_NODE(VectorInitializer, expr, A); + expr->Operation = PEX_Vector; + expr->Type = TypeVector2; + expr->X = A; + expr->Y = B; + expr->Z = nullptr; + XX = expr; +} + /*----- Unary Expressions -----*/ unary_expr(X) ::= primary(X). diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index dc638de0f..f1a06d584 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1387,11 +1387,6 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n retval = TypeVector3; break; - case ZCC_Vector4: - // This has almost no use, so we really shouldn't bother. - Error(field, "vector<4> not implemented for %s", name.GetChars()); - return TypeError; - case ZCC_State: retval = TypeState; break; @@ -2710,6 +2705,15 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return new FxConditional(condition, left, right); } + case AST_VectorInitializer: + { + auto vecini = static_cast(ast); + auto xx = ConvertNode(vecini->X); + auto yy = ConvertNode(vecini->Y); + auto zz = ConvertNode(vecini->Z); + return new FxVectorInitializer(xx, yy, zz, *ast); + } + case AST_LocalVarStmt: { auto loc = static_cast(ast); diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index ef4a2ac41..84bebff40 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -301,7 +301,8 @@ static void DoParse(int lumpnum) parser = ZCCParseAlloc(malloc); ZCCParseState state; -#if 0 // this costs a lot of time and should only be activated when it's really needed. +//#define TRACE +#ifdef TRACE // this costs a lot of time and should only be activated when it's really needed. FILE *f = fopen("trace.txt", "w"); char prompt = '\0'; ZCCParseTrace(f, &prompt); @@ -335,7 +336,7 @@ static void DoParse(int lumpnum) I_Error("%d errors while parsing %s", FScriptPosition::ErrorCounter, Wads.GetLumpFullPath(lumpnum).GetChars()); } -#if 0 +#ifdef TRACE if (f != NULL) { fclose(f); diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index dafdb93e5..0889d1d37 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -120,7 +120,6 @@ enum EZCCBuiltinType ZCC_String, ZCC_Vector2, ZCC_Vector3, - ZCC_Vector4, ZCC_Name, ZCC_Color, // special types for ZDoom. From e5878f0cb289d3a23bd106891e25e7fd6a78cbc1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 01:39:25 +0200 Subject: [PATCH 131/255] - implemented vector operations. Vectors are now fully working as local variables. - removed mulv_kr and divv_kr instructions. The first are redundant and the second are useless. Maybe remove all other vector/const operations as well? They won't get used by the code generator. - fixed disassembly of vector multiplication and division instructions. --- src/scripting/codegeneration/codegen.cpp | 207 +++++++++++++++++++---- src/scripting/codegeneration/codegen.h | 5 +- src/scripting/vm/vmdisasm.cpp | 3 + src/scripting/vm/vmexec.h | 20 --- src/scripting/vm/vmops.h | 20 +-- 5 files changed, 193 insertions(+), 62 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 773fc4b1a..903a0fe13 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1476,7 +1476,7 @@ FxExpression *FxPlusSign::Resolve(FCompileContext& ctx) CHECKRESOLVED(); SAFE_RESOLVE(Operand, ctx); - if (Operand->IsNumeric()) + if (Operand->IsNumeric() || Operand->IsVector()) { FxExpression *e = Operand; Operand = NULL; @@ -1530,7 +1530,7 @@ FxExpression *FxMinusSign::Resolve(FCompileContext& ctx) CHECKRESOLVED(); SAFE_RESOLVE(Operand, ctx); - if (Operand->IsNumeric()) + if (Operand->IsNumeric() || Operand->IsVector()) { if (Operand->isConstant()) { @@ -1563,6 +1563,7 @@ ExpEmit FxMinusSign::Emit(VMFunctionBuilder *build) assert(ValueType == Operand->ValueType); ExpEmit from = Operand->Emit(build); assert(from.Konst == 0); + assert(ValueType->GetRegCount() == from.RegCount); // Do it in-place. if (ValueType->GetRegType() == REGT_INT) { @@ -1571,7 +1572,21 @@ ExpEmit FxMinusSign::Emit(VMFunctionBuilder *build) else { assert(ValueType->GetRegType() == REGT_FLOAT); - build->Emit(OP_FLOP, from.RegNum, from.RegNum, FLOP_NEG); + switch (from.RegCount) + { + case 1: + build->Emit(OP_FLOP, from.RegNum, from.RegNum, FLOP_NEG); + break; + + case 2: + build->Emit(OP_NEGV2, from.RegNum, from.RegNum); + break; + + case 3: + build->Emit(OP_NEGV3, from.RegNum, from.RegNum); + break; + + } } return from; } @@ -1610,10 +1625,10 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) CHECKRESOLVED(); SAFE_RESOLVE(Operand, ctx); - if (Operand->ValueType->GetRegType() == REGT_FLOAT /* lax */) + if (ctx.FromDecorate && Operand->IsNumeric() && Operand->ValueType->GetRegType() == REGT_FLOAT /* lax */) { // DECORATE allows floats here so cast them to int. - Operand = new FxIntCast(Operand, ctx.FromDecorate); + Operand = new FxIntCast(Operand, true); Operand = Operand->Resolve(ctx); if (Operand == NULL) { @@ -1622,7 +1637,8 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) } } - if (Operand->ValueType->GetRegType() != REGT_INT) + // Names were not blocked in DECORATE here after the scripting branch merge. Now they are again. + if (Operand->ValueType->GetRegType() != REGT_INT || Operand->ValueType == TypeName) { ScriptPosition.Message(MSG_ERROR, "Integer type expected"); delete this; @@ -1763,13 +1779,13 @@ FxExpression *FxSizeAlign::Resolve(FCompileContext& ctx) auto type = Operand->ValueType; if (Operand->isConstant()) { - ScriptPosition.Message(MSG_ERROR, "cannot determine %s of a constant", Which == 'a'? "alignment" : "size"); + ScriptPosition.Message(MSG_ERROR, "cannot determine %s of a constant", Which == TK_AlignOf? "alignment" : "size"); delete this; return NULL; } else if (!Operand->RequestAddress(nullptr)) { - ScriptPosition.Message(MSG_ERROR, "Operand must be addressable to determine %s", Which == 'a' ? "alignment" : "size"); + ScriptPosition.Message(MSG_ERROR, "Operand must be addressable to determine %s", Which == TK_AlignOf ? "alignment" : "size"); delete this; return NULL; } @@ -2057,7 +2073,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (Base->ValueType->IsKindOf(RUNTIME_CLASS(PStruct))) + if (!Base->IsVector() && Base->ValueType->IsKindOf(RUNTIME_CLASS(PStruct))) { ScriptPosition.Message(MSG_ERROR, "Struct assignment not implemented yet"); delete this; @@ -2255,7 +2271,78 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) return false; } - if (left->ValueType == TypeBool && right->ValueType == TypeBool) + if (left->IsVector() || right->IsVector()) + { + switch (Operator) + { + case '+': + case '-': + // a vector2 can be added to or subtracted from a vector 3 but it needs to be the right operand. + if (left->ValueType == right->ValueType || (left->ValueType == TypeVector3 && right->ValueType == TypeVector2)) + { + ValueType = left->ValueType; + return true; + } + else + { + ScriptPosition.Message(MSG_ERROR, "Incompatible operands for operator %c", Operator); + delete this; + return false; + } + break; + + case '/': + if (right->IsVector()) + { + // For division, the vector must be the first operand. + ScriptPosition.Message(MSG_ERROR, "Incompatible operands for division"); + delete this; + return false; + } + case '*': + if (left->IsVector()) + { + right = new FxFloatCast(right); + right = right->Resolve(ctx); + if (right == nullptr) + { + delete this; + return false; + } + ValueType = left->ValueType; + } + else + { + left = new FxFloatCast(left); + left = left->Resolve(ctx); + if (left == nullptr) + { + delete this; + return false; + } + ValueType = right->ValueType; + } + break; + + case TK_Eq: + case TK_Neq: + if (left->ValueType != right->ValueType) + { + ScriptPosition.Message(MSG_ERROR, "Incompatible operands for comparison"); + delete this; + return false; + } + ValueType = TypeBool; + break; + + default: + ScriptPosition.Message(MSG_ERROR, "Incompatible operation for vector type"); + delete this; + return false; + + } + } + else if (left->ValueType == TypeBool && right->ValueType == TypeBool) { if (Operator == '&' || Operator == '|' || Operator == '^' || ctx.FromDecorate) { @@ -2361,7 +2448,7 @@ FxExpression *FxAddSub::Resolve(FCompileContext& ctx) CHECKRESOLVED(); if (!ResolveLR(ctx, true)) return NULL; - if (!IsNumeric()) + if (!IsNumeric() && !IsVector()) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; @@ -2410,6 +2497,8 @@ FxExpression *FxAddSub::Resolve(FCompileContext& ctx) ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) { assert(Operator == '+' || Operator == '-'); + // allocate the result first so that the operation does not leave gaps in the register set. + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); if (Operator == '+') @@ -2422,10 +2511,20 @@ ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) assert(!op1.Konst); op1.Free(build); op2.Free(build); - if (ValueType->GetRegType() == REGT_FLOAT) + if (IsVector()) + { + assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); + build->Emit(right->ValueType == TypeVector2? OP_ADDV2_RR : OP_ADDV3_RR, to.RegNum, op1.RegNum, op2.RegNum); + if (left->ValueType == TypeVector3 && right->ValueType == TypeVector2 && to.RegNum != op1.RegNum) + { + // must move the z-coordinate + build->Emit(OP_MOVEF, to.RegNum + 2, op1.RegNum + 2); + } + return to; + } + else if (ValueType->GetRegType() == REGT_FLOAT) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); - ExpEmit to(build, REGT_FLOAT); build->Emit(op2.Konst ? OP_ADDF_RK : OP_ADDF_RR, to.RegNum, op1.RegNum, op2.RegNum); return to; } @@ -2433,7 +2532,6 @@ ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) { assert(ValueType->GetRegType() == REGT_INT); assert(op1.RegType == REGT_INT && op2.RegType == REGT_INT); - ExpEmit to(build, REGT_INT); build->Emit(op2.Konst ? OP_ADD_RK : OP_ADD_RR, to.RegNum, op1.RegNum, op2.RegNum); return to; } @@ -2444,21 +2542,23 @@ ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) assert(!op1.Konst || !op2.Konst); op1.Free(build); op2.Free(build); - if (ValueType->GetRegType() == REGT_FLOAT) + if (IsVector()) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); - ExpEmit to(build, REGT_FLOAT); - build->Emit(op1.Konst ? OP_SUBF_KR : op2.Konst ? OP_SUBF_RK : OP_SUBF_RR, - to.RegNum, op1.RegNum, op2.RegNum); + build->Emit(right->ValueType == TypeVector2 ? OP_SUBV2_RR : OP_SUBV3_RR, to.RegNum, op1.RegNum, op2.RegNum); + return to; + } + else if (ValueType->GetRegType() == REGT_FLOAT) + { + assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); + build->Emit(op1.Konst ? OP_SUBF_KR : op2.Konst ? OP_SUBF_RK : OP_SUBF_RR, to.RegNum, op1.RegNum, op2.RegNum); return to; } else { assert(ValueType->GetRegType() == REGT_INT); assert(op1.RegType == REGT_INT && op2.RegType == REGT_INT); - ExpEmit to(build, REGT_INT); - build->Emit(op1.Konst ? OP_SUB_KR : op2.Konst ? OP_SUB_RK : OP_SUB_RR, - to.RegNum, op1.RegNum, op2.RegNum); + build->Emit(op1.Konst ? OP_SUB_KR : op2.Konst ? OP_SUB_RK : OP_SUB_RR, to.RegNum, op1.RegNum, op2.RegNum); return to; } } @@ -2487,7 +2587,7 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) if (!ResolveLR(ctx, true)) return NULL; - if (!IsNumeric()) + if (!IsNumeric() && !IsVector()) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; @@ -2552,9 +2652,33 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) { + // allocate the result first so that the operation does not leave gaps in the register set. + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); + if (IsVector()) + { + assert(Operator != '%'); + if (right->IsVector()) + { + swapvalues(op1, op2); + } + int op; + if (op2.Konst) + { + op = Operator == '*' ? (ValueType == TypeVector2 ? OP_MULVF2_RK : OP_MULVF3_RK) : (ValueType == TypeVector2 ? OP_DIVVF2_RK : OP_DIVVF3_RK); + } + else + { + op = Operator == '*' ? (ValueType == TypeVector2 ? OP_MULVF2_RR : OP_MULVF3_RR) : (ValueType == TypeVector2 ? OP_DIVVF2_RR : OP_DIVVF3_RR); + } + build->Emit(op, to.RegNum, op1.RegNum, op2.RegNum); + op1.Free(build); + op2.Free(build); + return to; + } + if (Operator == '*') { // Multiplication is commutative, so only the second operand may be constant. @@ -2568,7 +2692,6 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) if (ValueType->GetRegType() == REGT_FLOAT) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); - ExpEmit to(build, REGT_FLOAT); build->Emit(op2.Konst ? OP_MULF_RK : OP_MULF_RR, to.RegNum, op1.RegNum, op2.RegNum); return to; } @@ -2576,7 +2699,6 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) { assert(ValueType->GetRegType() == REGT_INT); assert(op1.RegType == REGT_INT && op2.RegType == REGT_INT); - ExpEmit to(build, REGT_INT); build->Emit(op2.Konst ? OP_MUL_RK : OP_MUL_RR, to.RegNum, op1.RegNum, op2.RegNum); return to; } @@ -2813,7 +2935,7 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) return NULL; } - if (!IsNumeric() && !IsPointer() && ValueType != TypeName) + if (!IsNumeric() && !IsPointer() && !IsVector() && ValueType != TypeName) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; @@ -2866,11 +2988,13 @@ ExpEmit FxCompareEq::Emit(VMFunctionBuilder *build) swapvalues(op1, op2); } assert(!op1.Konst); + assert(op1.RegCount >= 1 && op1.RegCount <= 3); ExpEmit to(build, REGT_INT); + static int flops[] = { OP_EQF_R, OP_EQV2_R, OP_EQV3_R }; instr = op1.RegType == REGT_INT ? OP_EQ_R : - op1.RegType == REGT_FLOAT ? OP_EQF_R : + op1.RegType == REGT_FLOAT ? flops[op1.RegCount-1] : OP_EQA_R; op1.Free(build); if (!op2.Konst) @@ -3349,14 +3473,25 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) RESOLVE(falsex, ctx); ABORT(condition && truex && falsex); - if (truex->ValueType == TypeBool && falsex->ValueType == TypeBool) + if (truex->ValueType == falsex->ValueType) + ValueType = truex->ValueType; + else if (truex->ValueType == TypeBool && falsex->ValueType == TypeBool) ValueType = TypeBool; else if (truex->ValueType->GetRegType() == REGT_INT && falsex->ValueType->GetRegType() == REGT_INT) ValueType = TypeSInt32; else if (truex->IsNumeric() && falsex->IsNumeric()) ValueType = TypeFloat64; + else + ValueType = TypeVoid; //else if (truex->ValueType != falsex->ValueType) + if (!IsNumeric() && !IsPointer() && !IsVector()) + { + ScriptPosition.Message(MSG_ERROR, "Incompatible types for ?: operator"); + delete this; + return false; + } + if (condition->ValueType != TypeBool) { condition = new FxBoolCast(condition); @@ -3465,7 +3600,9 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) else { assert(falseop.RegType == REGT_FLOAT); - build->Emit(OP_MOVEF, out.RegNum, falseop.RegNum, 0); + assert(falseop.RegCount == out.RegCount); + static int flops[] = { OP_MOVEF, OP_MOVEV2, OP_MOVEV3 }; + build->Emit(flops[falseop.RegNum], out.RegNum, falseop.RegNum, 0); } } } @@ -4625,6 +4762,7 @@ FxLocalVariable::FxLocalVariable(FxLocalVariableDeclaration *var, const FScriptP Variable = var; ValueType = var->ValueType; AddressRequested = false; + RegOffset = 0; } FxExpression *FxLocalVariable::Resolve(FCompileContext &ctx) @@ -4642,7 +4780,8 @@ bool FxLocalVariable::RequestAddress(bool *writable) ExpEmit FxLocalVariable::Emit(VMFunctionBuilder *build) { - ExpEmit ret(Variable->RegNum, Variable->ValueType->GetRegType(), false, true); + ExpEmit ret(Variable->RegNum + RegOffset, Variable->ValueType->GetRegType(), false, true); + ret.RegCount = ValueType->GetRegCount(); if (AddressRequested) ret.Target = true; return ret; } @@ -4765,6 +4904,16 @@ FxExpression *FxStructMember::Resolve(FCompileContext &ctx) classx = nullptr; return x; } + else if (classx->ExprType == EFX_LocalVariable && classx->IsVector()) // vectors are a special case because they are held in registers + { + // since this is a vector, all potential things that may get here are single float or an xy-vector. + auto locvar = static_cast(classx); + locvar->RegOffset = membervar->Offset / 8; + locvar->ValueType = membervar->Type; + classx = nullptr; + delete this; + return locvar; + } else { if (!(classx->RequestAddress(&AddressWritable))) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 30401f907..01d63eaf8 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -292,8 +292,10 @@ public: virtual bool RequestAddress(bool *writable); virtual PPrototype *ReturnProto(); virtual VMFunction *GetDirectFunction(); - bool IsNumeric() const { return ValueType != TypeName && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT); } + bool IsNumeric() const { return ValueType != TypeName && ValueType->GetRegCount() == 1 && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT); } + bool IsInteger() const { return ValueType != TypeName && (ValueType->GetRegType() == REGT_INT); } bool IsPointer() const { return ValueType->GetRegType() == REGT_POINTER; } + bool IsVector() const { return ValueType == TypeVector2 || ValueType == TypeVector3; }; virtual ExpEmit Emit(VMFunctionBuilder *build); @@ -1104,6 +1106,7 @@ class FxLocalVariable : public FxExpression public: FxLocalVariableDeclaration *Variable; bool AddressRequested; + int RegOffset; FxLocalVariable(FxLocalVariableDeclaration*, const FScriptPosition&); FxExpression *Resolve(FCompileContext&); diff --git a/src/scripting/vm/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp index 563f89f28..c20083dcd 100644 --- a/src/scripting/vm/vmdisasm.cpp +++ b/src/scripting/vm/vmdisasm.cpp @@ -117,6 +117,9 @@ #define RVRVRV MODE_AV | MODE_BV | MODE_CV #define RVRVKV MODE_AV | MODE_BV | MODE_CKV #define RVKVRV MODE_AV | MODE_BKV | MODE_CV +#define RVRVRF MODE_AV | MODE_BV | MODE_CF +#define RVRVKF MODE_AV | MODE_BV | MODE_CKF +#define RVKVRF MODE_AV | MODE_BKV | MODE_CF #define RFRV MODE_AF | MODE_BV | MODE_CUNUSED #define I8RVRV MODE_AIMMZ | MODE_BV | MODE_CV #define I8RVKV MODE_AIMMZ | MODE_BV | MODE_CKV diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index e3401eb38..824cd6366 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1352,11 +1352,6 @@ begin: fc = konstf[C]; fbp = ®.f[B]; goto Do_MULV2; - OP(MULVF2_KR): - ASSERTF(a+1); ASSERTKF(B+1); ASSERTF(C); - fc = reg.f[C]; - fbp = &konstf[B]; - goto Do_MULV2; OP(DIVVF2_RR): ASSERTF(a+1); ASSERTF(B+1); ASSERTF(C); @@ -1371,11 +1366,6 @@ begin: fc = konstf[C]; fbp = ®.f[B]; goto Do_DIVV2; - OP(DIVVF2_KR): - ASSERTF(a+1); ASSERTKF(B+1); ASSERTF(C); - fc = reg.f[C]; - fbp = &konstf[B]; - goto Do_DIVV2; OP(LENV2): ASSERTF(a); ASSERTF(B+1); @@ -1488,11 +1478,6 @@ begin: fc = konstf[C]; fbp = ®.f[B]; goto Do_MULV3; - OP(MULVF3_KR): - ASSERTF(a+2); ASSERTKF(B+2); ASSERTF(C); - fc = reg.f[C]; - fbp = &konstf[B]; - goto Do_MULV3; OP(DIVVF3_RR): ASSERTF(a+2); ASSERTF(B+2); ASSERTF(C); @@ -1508,11 +1493,6 @@ begin: fc = konstf[C]; fbp = ®.f[B]; goto Do_DIVV3; - OP(DIVVF3_KR): - ASSERTF(a+2); ASSERTKF(B+2); ASSERTF(C); - fc = reg.f[C]; - fbp = &konstf[B]; - goto Do_DIVV3; OP(LENV3): ASSERTF(a); ASSERTF(B+2); diff --git a/src/scripting/vm/vmops.h b/src/scripting/vm/vmops.h index ba86e2231..e7ff19c22 100644 --- a/src/scripting/vm/vmops.h +++ b/src/scripting/vm/vmops.h @@ -208,12 +208,10 @@ xx(SUBV2_RK, subv2, RVRVKV), xx(SUBV2_KR, subv2, RVKVRV), xx(DOTV2_RR, dotv2, RVRVRV), // va = vB dot vkC xx(DOTV2_RK, dotv2, RVRVKV), -xx(MULVF2_RR, mulv2, RVRVRV), // vA = vkB * fkC -xx(MULVF2_RK, mulv2, RVRVKV), -xx(MULVF2_KR, mulv2, RVKVRV), -xx(DIVVF2_RR, divv2, RVRVRV), // vA = vkB / fkC -xx(DIVVF2_RK, divv2, RVRVKV), -xx(DIVVF2_KR, divv2, RVKVRV), +xx(MULVF2_RR, mulv2, RVRVRF), // vA = vkB * fkC +xx(MULVF2_RK, mulv2, RVRVKF), +xx(DIVVF2_RR, divv2, RVRVRF), // vA = vkB / fkC +xx(DIVVF2_RK, divv2, RVRVKF), xx(LENV2, lenv2, RFRV), // fA = vB.Length xx(EQV2_R, beqv2, CVRR), // if ((vB == vkC) != A) then pc++ (inexact if A & 32) xx(EQV2_K, beqv2, CVRK), @@ -230,12 +228,10 @@ xx(DOTV3_RK, dotv3, RVRVKV), xx(CROSSV_RR, crossv, RVRVRV), // vA = vkB cross vkC xx(CROSSV_RK, crossv, RVRVKV), xx(CROSSV_KR, crossv, RVKVRV), -xx(MULVF3_RR, mulv3, RVRVRV), // vA = vkB * fkC -xx(MULVF3_RK, mulv3, RVRVKV), -xx(MULVF3_KR, mulv3, RVKVRV), -xx(DIVVF3_RR, divv3, RVRVRV), // vA = vkB / fkC -xx(DIVVF3_RK, divv3, RVRVKV), -xx(DIVVF3_KR, divv3, RVKVRV), +xx(MULVF3_RR, mulv3, RVRVRF), // vA = vkB * fkC +xx(MULVF3_RK, mulv3, RVRVKF), +xx(DIVVF3_RR, divv3, RVRVRF), // vA = vkB / fkC +xx(DIVVF3_RK, divv3, RVRVKF), xx(LENV3, lenv3, RFRV), // fA = vB.Length xx(EQV3_R, beqv3, CVRR), // if ((vB == vkC) != A) then pc++ (inexact if A & 33) xx(EQV3_K, beqv3, CVRK), From 594a0c2008fa999a167f00883e59cf8797b92da1 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sat, 29 Oct 2016 01:30:05 +0200 Subject: [PATCH 132/255] Fixed: FxVMFunctionCall didn't check for varargs while checking argument count --- src/scripting/codegeneration/codegen.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 903a0fe13..4c048c452 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5785,7 +5785,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) { bool foundvarargs = false; PType * type = nullptr; - if (ArgList->Size() + implicit > proto->ArgumentTypes.Size()) + if (argtypes.Last() != nullptr && ArgList->Size() + implicit > argtypes.Size()) { ScriptPosition.Message(MSG_ERROR, "Too many arguments in call to %s", Function->SymbolName.GetChars()); delete this; From b5222f08e8ad25064750f033150552948a494988 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 10:16:00 +0200 Subject: [PATCH 133/255] - implemented dot and cross products (not that I'd ever expect these to become useful in a game like Doom...) --- src/scripting/codegeneration/codegen.cpp | 70 ++++++++++++++++++++++++ src/scripting/codegeneration/codegen.h | 21 +++++++ src/scripting/zscript/zcc_compile.cpp | 9 ++- 3 files changed, 95 insertions(+), 5 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4c048c452..039e428ff 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3438,6 +3438,76 @@ ExpEmit FxBinaryLogical::Emit(VMFunctionBuilder *build) // //========================================================================== +FxDotCross::FxDotCross(int o, FxExpression *l, FxExpression *r) + : FxExpression(EFX_DotCross, l->ScriptPosition) +{ + Operator = o; + left = l; + right = r; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxDotCross::~FxDotCross() +{ + SAFE_DELETE(left); + SAFE_DELETE(right); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxDotCross::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + RESOLVE(left, ctx); + RESOLVE(right, ctx); + ABORT(right && left); + + if (!left->IsVector() || left->ValueType != right->ValueType || (Operator == TK_Cross && left->ValueType != TypeVector3)) + { + ScriptPosition.Message(MSG_ERROR, "Incompatible operants for %sproduct", Operator == TK_Cross ? "cross-" : "dot-"); + delete this; + return nullptr; + } + ValueType = Operator == TK_Cross ? (PType*)TypeVector3 : TypeFloat64; + return this; +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxDotCross::Emit(VMFunctionBuilder *build) +{ + // This is not the "right" way to do these, but it works for now. + // (Problem: No information sharing is done between nodes to reduce the + // code size if you have something like a1 && a2 && a3 && ... && an.) + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); + ExpEmit op1 = left->Emit(build); + ExpEmit op2 = right->Emit(build); + int op = Operator == TK_Cross ? OP_CROSSV_RR : left->ValueType == TypeVector3 ? OP_DOTV3_RR : OP_DOTV2_RR; + build->Emit(op, to.RegNum, op1.RegNum, op2.RegNum); + op1.Free(build); + op2.Free(build); + return to; +} + +//========================================================================== +// +// +// +//========================================================================== + FxConditional::FxConditional(FxExpression *c, FxExpression *t, FxExpression *f) : FxExpression(EFX_Conditional, c->ScriptPosition) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 01d63eaf8..570575bb9 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -228,6 +228,7 @@ enum EFxType EFX_AssignSelf, EFX_Binary, // one token fits all, the operator is enough to distinguish them. EFX_BinaryLogical, + EFX_DotCross, EFX_Conditional, EFX_Abs, EFX_ATan2, @@ -905,6 +906,26 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxBinaryLogical +// +//========================================================================== + +class FxDotCross : public FxExpression +{ +public: + int Operator; + FxExpression *left; + FxExpression *right; + + FxDotCross(int, FxExpression*, FxExpression*); + ~FxDotCross(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxConditional diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f1a06d584..294763f9b 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2680,14 +2680,13 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_ArrayAccess: return new FxArrayElement(left, right); - // todo: These do not have representations in DECORATE and no implementation exists yet. - case PEX_Concat: - case PEX_Is: - - // vector operations will be done later. case PEX_CrossProduct: case PEX_DotProduct: + return new FxDotCross(tok, left, right); + // todo: These do not have representations in DECORATE and no implementation exists yet. + case PEX_Concat: + case PEX_Is: default: I_Error("Binary operator %d not implemented yet", op); From f5d1b1a491eb5065fb78f3b7c6c99c901d8ce19e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 10:43:22 +0200 Subject: [PATCH 134/255] - added vector builtins Length() and Unit(). This should complete the vector type except for use as function parameter. --- src/namedef.h | 2 + src/scripting/codegeneration/codegen.cpp | 57 ++++++++++++++++++++++++ src/scripting/codegeneration/codegen.h | 20 +++++++++ wadsrc/static/zscript.txt | 2 + 4 files changed, 81 insertions(+) diff --git a/src/namedef.h b/src/namedef.h index ea4a7b890..a5abfa5a1 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -730,3 +730,5 @@ xx(__decorate_internal_state__) xx(__decorate_internal_float__) xx(DamageFunction) +xx(Length) +xx(Unit) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 039e428ff..f8fd03946 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5535,6 +5535,18 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) PClass *cls; bool staticonly = false; + if (Self->IsVector()) + { + // handle builtins: Vectors got 2: Length and Unit. + if (MethodName == NAME_Length || MethodName == NAME_Unit) + { + auto x = new FxVectorBuiltin(Self, MethodName); + Self = nullptr; + delete this; + return x->Resolve(ctx); + } + } + if (Self->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) { cls = static_cast(Self->ValueType)->ClassRestriction; @@ -6096,6 +6108,51 @@ ExpEmit FxFlopFunctionCall::Emit(VMFunctionBuilder *build) return v; } + +//========================================================================== +// +// +//========================================================================== + +FxVectorBuiltin::FxVectorBuiltin(FxExpression *self, FName name) + :FxExpression(EFX_VectorBuiltin, self->ScriptPosition) +{ + Self = self; + Function = name; +} + +FxVectorBuiltin::~FxVectorBuiltin() +{ + SAFE_DELETE(Self); +} + +FxExpression *FxVectorBuiltin::Resolve(FCompileContext &ctx) +{ + SAFE_RESOLVE(Self, ctx); + assert(Self->IsVector()); // should never be created for anything else. + ValueType = Function == NAME_Length ? TypeFloat64 : Self->ValueType; + return this; +} + +ExpEmit FxVectorBuiltin::Emit(VMFunctionBuilder *build) +{ + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); + ExpEmit op = Self->Emit(build); + if (Function == NAME_Length) + { + build->Emit(Self->ValueType == TypeVector2 ? OP_LENV2 : OP_LENV3, to.RegNum, op.RegNum); + } + else + { + ExpEmit len(build, REGT_FLOAT); + build->Emit(Self->ValueType == TypeVector2 ? OP_LENV2 : OP_LENV3, len.RegNum, op.RegNum); + build->Emit(Self->ValueType == TypeVector2 ? OP_DIVVF2_RR : OP_DIVVF3_RR, to.RegNum, op.RegNum, len.RegNum); + len.Free(build); + } + op.Free(build); + return to; +} + //========================================================================== // // FxSequence :: Resolve diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 570575bb9..6c7dec487 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -266,6 +266,7 @@ enum EFxType EFX_SwitchStatement, EFX_CaseStatement, EFX_VectorInitializer, + EFX_VectorBuiltin, EFX_COUNT }; @@ -1254,6 +1255,25 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxFlopFunctionCall +// +//========================================================================== + +class FxVectorBuiltin : public FxExpression +{ + FName Function; + FxExpression *Self; + +public: + + FxVectorBuiltin(FxExpression *self, FName name); + ~FxVectorBuiltin(); + FxExpression *Resolve(FCompileContext&); + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxVMFunctionCall diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 6de64d07e..3ab33bfd9 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -177,3 +177,5 @@ zscript/chex/chexweapons.txt zscript/chex/chexitems.txt zscript/chex/chexdecorations.txt zscript/chex/chexplayer.txt + +zscript/test2.txt From 7209f9edd6b13d108b9123d01f018c5cfea9f381 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 13:10:27 +0200 Subject: [PATCH 135/255] - implemented passing vectors as parameters. So far working for native functions. - removed the bogus optional value from the first A_Jump argument. A quick test with an older ZDoom revealed that this was never working - and implementing it would make things a lot more complicated, especially error checking in the code generator. - fixed: The check for insufficient parameters to a function call was missing. --- src/namedef.h | 1 + src/p_actionfunctions.cpp | 2 +- src/p_maputl.cpp | 11 ++++++ src/scripting/codegeneration/codegen.cpp | 30 +++++++++++++-- src/scripting/vm/vm.h | 4 +- src/scripting/vm/vmbuilder.cpp | 6 ++- src/scripting/vm/vmdisasm.cpp | 6 ++- src/scripting/vm/vmexec.h | 49 ++++++++++-------------- src/scripting/zscript/zcc_compile.cpp | 6 +++ 9 files changed, 78 insertions(+), 37 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index a5abfa5a1..3966c95e7 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -732,3 +732,4 @@ xx(__decorate_internal_float__) xx(DamageFunction) xx(Length) xx(Unit) +xx(A_Jump) \ No newline at end of file diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 0e9620564..9f3a088d6 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -1148,7 +1148,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BulletAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Jump) { PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_DEF(maxchance); + PARAM_INT(maxchance); paramnum++; // Increment paramnum to point at the first jump target int count = numparam - paramnum; diff --git a/src/p_maputl.cpp b/src/p_maputl.cpp index 04372f0ed..0a1d831d8 100644 --- a/src/p_maputl.cpp +++ b/src/p_maputl.cpp @@ -532,6 +532,17 @@ void AActor::SetOrigin(double x, double y, double z, bool moving) if (!moving) ClearInterpolation(); } +DEFINE_ACTION_FUNCTION(AActor, SetOrigin) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(x); + PARAM_FLOAT(y); + PARAM_FLOAT(z); + PARAM_BOOL(moving); + self->SetOrigin(x, y, z, moving); + return 0; +} + //=========================================================================== // // FBlockNode - allows to link actors into multiple blocks in the blockmap diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f8fd03946..d87e601ff 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -334,7 +334,7 @@ PPrototype *FxExpression::ReturnProto() // //========================================================================== -static void EmitParameter(VMFunctionBuilder *build, FxExpression *operand, const FScriptPosition &pos) +static int EmitParameter(VMFunctionBuilder *build, FxExpression *operand, const FScriptPosition &pos) { ExpEmit where = operand->Emit(build); @@ -342,6 +342,7 @@ static void EmitParameter(VMFunctionBuilder *build, FxExpression *operand, const { pos.Message(MSG_ERROR, "Attempted to pass a non-value"); build->Emit(OP_PARAM, 0, where.RegType, where.RegNum); + return 1; } else { @@ -350,8 +351,17 @@ static void EmitParameter(VMFunctionBuilder *build, FxExpression *operand, const { regtype |= REGT_KONST; } + else if (where.RegCount == 2) + { + regtype |= REGT_MULTIREG2; + } + else if (where.RegCount == 3) + { + regtype |= REGT_MULTIREG3; + } build->Emit(OP_PARAM, 0, regtype, where.RegNum); where.Free(build); + return where.RegCount; } } @@ -5873,6 +5883,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) delete this; return nullptr; } + for (unsigned i = 0; i < ArgList->Size(); i++) { // Varargs must all have the same type as the last typed argument. A_Jump is the only function using it. @@ -5888,6 +5899,18 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) failed |= (x == nullptr); (*ArgList)[i] = x; } + int numargs = ArgList->Size() + implicit; + if ((unsigned)numargs < argtypes.Size() && argtypes[numargs] != nullptr) + { + auto flags = Function->Variants[0].ArgFlags[numargs]; + if (!(flags & VARF_Optional)) + { + ScriptPosition.Message(MSG_ERROR, "Insufficient arguments in call to %s", Function->SymbolName.GetChars()); + delete this; + return nullptr; + } + } + } if (failed) { @@ -5917,7 +5940,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) { assert((build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= NAP) || (!build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= 1)); - int count = (ArgList ? ArgList->Size() : 0); + int count = 0; (ArgList ? ArgList->Size() : 0); if (count == 1) { @@ -5928,6 +5951,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } } + count = 0; // Emit code to pass implied parameters if (Function->Variants[0].Flags & VARF_Method) { @@ -5958,7 +5982,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) { for (unsigned i = 0; i < ArgList->Size(); ++i) { - EmitParameter(build, (*ArgList)[i], ScriptPosition); + count += EmitParameter(build, (*ArgList)[i], ScriptPosition); } } // Get a constant register for this function diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index c14a8a6e5..4eb055e6e 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -134,7 +134,9 @@ enum REGT_TYPE = 3, REGT_KONST = 4, - REGT_MULTIREG = 8, // (e.g. a vector) + REGT_MULTIREG2 = 8, + REGT_MULTIREG3 = 16, // (e.g. a vector) + REGT_MULTIREG = 24, REGT_ADDROF = 32, // used with PARAM: pass address of this register REGT_NIL = 128 // parameter was omitted diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index dd07d0100..912b95861 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -498,7 +498,11 @@ size_t VMFunctionBuilder::Emit(int opcode, int opa, int opb, int opc) assert(opc >= 0 && opc <= 255); if (opcode == OP_PARAM) { - ParamChange(1); + int chg; + if (opb & REGT_MULTIREG2) chg = 2; + else if (opb®T_MULTIREG3) chg = 3; + else chg = 1; + ParamChange(chg); } else if (opcode == OP_CALL || opcode == OP_CALL_K || opcode == OP_TAIL || opcode == OP_TAIL_K) { diff --git a/src/scripting/vm/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp index c20083dcd..ea199612c 100644 --- a/src/scripting/vm/vmdisasm.cpp +++ b/src/scripting/vm/vmdisasm.cpp @@ -578,8 +578,10 @@ static int print_reg(FILE *out, int col, int arg, int mode, int immshift, const return col+printf_wrapper(out, "s%d", regnum); case REGT_POINTER: return col+printf_wrapper(out, "a%d", regnum); - case REGT_FLOAT | REGT_MULTIREG: - return col+printf_wrapper(out, "v%d", regnum); + case REGT_FLOAT | REGT_MULTIREG2: + return col+printf_wrapper(out, "v%d.2", regnum); + case REGT_FLOAT | REGT_MULTIREG3: + return col+printf_wrapper(out, "v%d.3", regnum); case REGT_INT | REGT_KONST: return col+print_reg(out, 0, regnum, MODE_KI, 0, func); case REGT_FLOAT | REGT_KONST: diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 824cd6366..9162ca996 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -453,7 +453,7 @@ begin: } else { - switch(b & (REGT_TYPE | REGT_KONST | REGT_ADDROF)) + switch(b) { case REGT_INT: assert(C < f->NumRegD); @@ -492,40 +492,31 @@ begin: ::new(param) VMValue(konsta[C].v, konstatag[C]); break; case REGT_FLOAT: - if (b & REGT_MULTIREG) - { - assert(C < f->NumRegF - 2); - assert(f->NumParam < sfunc->MaxParam - 1); - ::new(param) VMValue(reg.f[C]); - ::new(param+1) VMValue(reg.f[C+1]); - ::new(param+2) VMValue(reg.f[C+2]); - f->NumParam += 2; - } - else - { - assert(C < f->NumRegF); - ::new(param) VMValue(reg.f[C]); - } + assert(C < f->NumRegF); + ::new(param) VMValue(reg.f[C]); + break; + case REGT_FLOAT | REGT_MULTIREG2: + assert(C < f->NumRegF - 1); + assert(f->NumParam < sfunc->MaxParam); + ::new(param) VMValue(reg.f[C]); + ::new(param + 1) VMValue(reg.f[C + 1]); + f->NumParam++; + break; + case REGT_FLOAT | REGT_MULTIREG3: + assert(C < f->NumRegF - 2); + assert(f->NumParam < sfunc->MaxParam - 1); + ::new(param) VMValue(reg.f[C]); + ::new(param + 1) VMValue(reg.f[C + 1]); + ::new(param + 2) VMValue(reg.f[C + 2]); + f->NumParam += 2; break; case REGT_FLOAT | REGT_ADDROF: assert(C < f->NumRegF); ::new(param) VMValue(®.f[C], ATAG_FREGISTER); break; case REGT_FLOAT | REGT_KONST: - if (b & REGT_MULTIREG) - { - assert(C < sfunc->NumKonstF - 2); - assert(f->NumParam < sfunc->MaxParam - 1); - ::new(param) VMValue(konstf[C]); - ::new(param+1) VMValue(konstf[C+1]); - ::new(param+2) VMValue(konstf[C+2]); - f->NumParam += 2; - } - else - { - assert(C < sfunc->NumKonstF); - ::new(param) VMValue(konstf[C]); - } + assert(C < sfunc->NumKonstF); + ::new(param) VMValue(konstf[C]); break; default: assert(0); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 294763f9b..f2644b240 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2017,6 +2017,7 @@ void ZCCCompiler::InitFunctions() SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags); argdefaults.Resize(argnames.Size()); auto p = f->Params; + bool hasoptionals = false; if (p != nullptr) { do @@ -2043,6 +2044,7 @@ void ZCCCompiler::InitFunctions() else if (p->Default != nullptr) { flags |= VARF_Optional; + hasoptionals = true; // The simplifier is not suited to convert the constant into something usable. // All it does is reduce the expression to a constant but we still got to do proper type checking and conversion. // It will also lose important type info about enums, once these get implemented @@ -2094,6 +2096,10 @@ void ZCCCompiler::InitFunctions() } if (x != nullptr) delete x; } + else if (hasoptionals) + { + Error(p, "All arguments after the first optional one need also be optional."); + } // TBD: disallow certain types? For now, let everything pass that isn't an array. args.Push(type); argflags.Push(flags); From 4dc97a6ed02f2c24fe073186a0f14b2544f1c5ac Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 13:42:37 +0200 Subject: [PATCH 136/255] - fixed register allocation for vector arguments to script functions. - handle 2D and 3D vectors in SetReturn. --- src/scripting/vm/vm.h | 6 ++++++ src/scripting/vm/vmbuilder.cpp | 2 +- src/scripting/vm/vmexec.h | 6 +++++- 3 files changed, 12 insertions(+), 2 deletions(-) diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 4eb055e6e..5e8a4c2a4 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -296,6 +296,12 @@ struct VMReturn ((double *)Location)[1] = val[1]; ((double *)Location)[2] = val[2]; } + void SetVector2(const double val[2]) + { + //assert(RegType == REGT_FLOAT); + ((double *)Location)[0] = val[0]; + ((double *)Location)[1] = val[1]; + } void SetString(const FString &val) { assert(RegType == REGT_STRING); diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 912b95861..3f6d1cbd3 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -702,7 +702,7 @@ void FFunctionBuildList::Build() auto flags = item.Func->Variants[0].ArgFlags[i]; // this won't get resolved and won't get emitted. It is only needed so that the code generator can retrieve the necessary info about this argument to do its work. auto local = new FxLocalVariableDeclaration(type, name, nullptr, flags, FScriptPosition()); - local->RegNum = buildit.Registers[type->GetRegType()].Get(1); + local->RegNum = buildit.Registers[type->GetRegType()].Get(type->GetRegCount()); ctx.FunctionArgs.Push(local); } diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 9162ca996..4b43ed815 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1808,10 +1808,14 @@ static void SetReturn(const VMRegisters ®, VMFrame *frame, VMReturn *ret, VM_ assert(regnum + ((regtype & REGT_KONST) ? 2u : 0u) < frame->NumRegF); src = ®.f[regnum]; } - if (regtype & REGT_MULTIREG) + if (regtype & REGT_MULTIREG3) { ret->SetVector((double *)src); } + else if (regtype & REGT_MULTIREG2) + { + ret->SetVector2((double *)src); + } else { ret->SetFloat(*(double *)src); From 853c6f668410087ea72e78873d64be5d7a5e071f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 16:49:21 +0200 Subject: [PATCH 137/255] - fixed initialization of local variables with other local variables. - fixed several occurenced where vectors were treated as floats. NOTE: The entire codegen.cpp file needs to be carefully reviewed for bad use of the REGT_ constants, there's probably more places where using them has broken some type checks. - fixed: committed test version of zscript.txt instead of changed actor.txt by accident. Initialization and assignment for strings is working with this commit. --- src/scripting/codegeneration/codegen.cpp | 21 ++++++++++++++------- wadsrc/static/zscript.txt | 2 -- wadsrc/static/zscript/actor.txt | 3 ++- 3 files changed, 16 insertions(+), 10 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d87e601ff..37ff715dd 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -676,7 +676,7 @@ FxExpression *FxBoolCast::Resolve(FCompileContext &ctx) delete this; return x; } - else if (basex->ValueType->GetRegType() == REGT_INT || basex->ValueType->GetRegType() == REGT_FLOAT || basex->ValueType->GetRegType() == REGT_POINTER) + else if ((basex->ValueType->GetRegType() == REGT_INT || basex->ValueType->GetRegType() == REGT_FLOAT || basex->ValueType->GetRegType() == REGT_POINTER) && !basex->IsVector()) { if (basex->isConstant()) { @@ -797,7 +797,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) return x; } } - else if (basex->ValueType->GetRegType() == REGT_FLOAT) + else if (basex->ValueType->GetRegType() == REGT_FLOAT && !basex->IsVector()) { if (basex->isConstant()) { @@ -875,7 +875,7 @@ FxExpression *FxFloatCast::Resolve(FCompileContext &ctx) CHECKRESOLVED(); SAFE_RESOLVE(basex, ctx); - if (basex->ValueType->GetRegType() == REGT_FLOAT) + if (basex->ValueType->GetRegType() == REGT_FLOAT && !basex->IsVector()) { FxExpression *x = basex; basex = NULL; @@ -1095,11 +1095,11 @@ ExpEmit FxStringCast::Emit(VMFunctionBuilder *build) from.Free(build); ExpEmit to(build, REGT_STRING); - if (ValueType == TypeName) + if (basex->ValueType == TypeName) { build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_N2S); } - else if (ValueType == TypeSound) + else if (basex->ValueType == TypeSound) { build->Emit(OP_CAST, to.RegNum, from.RegNum, CAST_So2S); } @@ -1325,7 +1325,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) { goto basereturn; } - else if (ValueType->GetRegType() == REGT_FLOAT) + else if (ValueType->GetRegType() == REGT_FLOAT && !IsVector()) { FxExpression *x = new FxFloatCast(basex); x = x->Resolve(ctx); @@ -4867,6 +4867,7 @@ ExpEmit FxLocalVariable::Emit(VMFunctionBuilder *build) } + //========================================================================== // // @@ -7671,11 +7672,17 @@ ExpEmit FxLocalVariableDeclaration::Emit(VMFunctionBuilder *build) } emitval.Free(build); } - else + else if (Init->ExprType != EFX_LocalVariable) { // take over the register that got allocated while emitting the Init expression. RegNum = emitval.RegNum; } + else + { + ExpEmit out(build, emitval.RegType, emitval.RegCount); + build->Emit(ValueType->GetMoveOp(), out.RegNum, emitval.RegNum); + RegNum = out.RegNum; + } } return ExpEmit(); } diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 3ab33bfd9..6de64d07e 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -177,5 +177,3 @@ zscript/chex/chexweapons.txt zscript/chex/chexitems.txt zscript/chex/chexdecorations.txt zscript/chex/chexplayer.txt - -zscript/test2.txt diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 363036507..18f0facd0 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -53,6 +53,7 @@ class Actor : Thinker native return GetPointer(ptr_select1) == GetPointer(ptr_select2); } + native void SetOrigin(vector3 newpos, bool moving); native Actor GetPointer(int aaptr); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); native void TraceBleed(int damage, Actor missile); @@ -296,7 +297,7 @@ class Actor : Thinker native deprecated native void A_PlaySoundEx(sound whattoplay, name slot, bool looping = false, int attenuation = 0); deprecated native void A_StopSoundEx(name slot); native void A_SeekerMissile(int threshold, int turnmax, int flags = 0, int chance = 50, int distance = 10); - native state A_Jump(int chance = 256, state label, ...); + native state A_Jump(int chance, state label, ...); native void A_CustomMissile(class missiletype, float spawnheight = 32, float spawnofs_xy = 0, float angle = 0, int flags = 0, float pitch = 0, int ptr = AAPTR_TARGET); native void A_CustomBulletAttack(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = 0, color color2 = 0, int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = null, float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); From 78a18acf46567a1b8e22ab309f601f435cceaab4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 29 Oct 2016 18:57:56 +0200 Subject: [PATCH 138/255] - added string handling to comparison operators. --- src/scripting/codegeneration/codegen.cpp | 276 ++++++++++++++++------- src/scripting/codegeneration/codegen.h | 2 + src/scripting/vm/vm.h | 2 +- 3 files changed, 199 insertions(+), 81 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 37ff715dd..6b6d83068 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -676,7 +676,7 @@ FxExpression *FxBoolCast::Resolve(FCompileContext &ctx) delete this; return x; } - else if ((basex->ValueType->GetRegType() == REGT_INT || basex->ValueType->GetRegType() == REGT_FLOAT || basex->ValueType->GetRegType() == REGT_POINTER) && !basex->IsVector()) + else if (basex->IsBoolCompat()) { if (basex->isConstant()) { @@ -797,7 +797,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) return x; } } - else if (basex->ValueType->GetRegType() == REGT_FLOAT && !basex->IsVector()) + else if (basex->IsFloat()) { if (basex->isConstant()) { @@ -875,7 +875,7 @@ FxExpression *FxFloatCast::Resolve(FCompileContext &ctx) CHECKRESOLVED(); SAFE_RESOLVE(basex, ctx); - if (basex->ValueType->GetRegType() == REGT_FLOAT && !basex->IsVector()) + if (basex->IsFloat()) { FxExpression *x = basex; basex = NULL; @@ -1325,7 +1325,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) { goto basereturn; } - else if (ValueType->GetRegType() == REGT_FLOAT && !IsVector()) + else if (IsFloat()) { FxExpression *x = new FxFloatCast(basex); x = x->Resolve(ctx); @@ -1635,7 +1635,7 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) CHECKRESOLVED(); SAFE_RESOLVE(Operand, ctx); - if (ctx.FromDecorate && Operand->IsNumeric() && Operand->ValueType->GetRegType() == REGT_FLOAT /* lax */) + if (ctx.FromDecorate && Operand->IsFloat() /* lax */) { // DECORATE allows floats here so cast them to int. Operand = new FxIntCast(Operand, true); @@ -1648,7 +1648,7 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) } // Names were not blocked in DECORATE here after the scripting branch merge. Now they are again. - if (Operand->ValueType->GetRegType() != REGT_INT || Operand->ValueType == TypeName) + if (!Operand->IsInteger()) { ScriptPosition.Message(MSG_ERROR, "Integer type expected"); delete this; @@ -2281,7 +2281,51 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) return false; } - if (left->IsVector() || right->IsVector()) + if (left->ValueType == TypeString || right->ValueType == TypeString) + { + switch (Operator) + { + case '+': + // later + break; + + case '<': + case '>': + case TK_Geq: + case TK_Leq: + case TK_Eq: + case TK_Neq: + case TK_ApproxEq: + if (left->ValueType != TypeString) + { + left = new FxStringCast(left); + left = left->Resolve(ctx); + if (left == nullptr) + { + delete this; + return nullptr; + } + } + if (right->ValueType != TypeString) + { + right = new FxStringCast(right); + right = right->Resolve(ctx); + if (right == nullptr) + { + delete this; + return nullptr; + } + } + ValueType = TypeBool; + break; + + default: + ScriptPosition.Message(MSG_ERROR, "Incompatible operands for comparison"); + delete this; + return false; + } + } + else if (left->IsVector() || right->IsVector()) { switch (Operator) { @@ -2466,7 +2510,7 @@ FxExpression *FxAddSub::Resolve(FCompileContext& ctx) } else if (left->isConstant() && right->isConstant()) { - if (ValueType->GetRegType() == REGT_FLOAT) + if (IsFloat()) { double v; double v1 = static_cast(left)->GetValue().GetFloat(); @@ -2605,7 +2649,7 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) } else if (left->isConstant() && right->isConstant()) { - if (ValueType->GetRegType() == REGT_FLOAT) + if (IsFloat()) { double v; double v1 = static_cast(left)->GetValue().GetFloat(); @@ -2834,7 +2878,17 @@ FxExpression *FxCompareRel::Resolve(FCompileContext& ctx) { int v; - if (ValueType->GetRegType() == REGT_FLOAT) + if (ValueType == TypeString) + { + FString v1 = static_cast(left)->GetValue().GetString(); + FString v2 = static_cast(right)->GetValue().GetString(); + int res = v1.Compare(v2); + v = Operator == '<' ? res < 0 : + Operator == '>' ? res > 0 : + Operator == TK_Geq ? res >= 0 : + Operator == TK_Leq ? res <= 0 : 0; + } + else if (IsFloat()) { double v1 = static_cast(left)->GetValue().GetFloat(); double v2 = static_cast(right)->GetValue().GetFloat(); @@ -2873,47 +2927,81 @@ ExpEmit FxCompareRel::Emit(VMFunctionBuilder *build) ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); assert(op1.RegType == op2.RegType); - assert(op1.RegType == REGT_INT || op1.RegType == REGT_FLOAT); assert(!op1.Konst || !op2.Konst); - assert(Operator == '<' || Operator == '>' || Operator == TK_Geq || Operator == TK_Leq); - static const VM_UBYTE InstrMap[][4] = - { - { OP_LT_RR, OP_LTF_RR, 0 }, // < - { OP_LE_RR, OP_LEF_RR, 1 }, // > - { OP_LT_RR, OP_LTF_RR, 1 }, // >= - { OP_LE_RR, OP_LEF_RR, 0 } // <= - }; - int instr, check, index; - ExpEmit to(build, REGT_INT); - index = Operator == '<' ? 0 : + if (op1.RegType == REGT_STRING) + { + ExpEmit to(build, REGT_INT); + int a = Operator == '<' ? CMP_LT : + Operator == '>' ? CMP_LE | CMP_CHECK : + Operator == TK_Geq ? CMP_LT | CMP_CHECK : CMP_LE; + + if (op1.Konst) + { + a |= CMP_BK; + } + else + { + op1.Free(build); + } + if (op2.Konst) + { + a |= CMP_CK; + } + else + { + op2.Free(build); + } + + build->Emit(OP_LI, to.RegNum, 0, 0); + build->Emit(OP_CMPS, a, op1.RegNum, op2.RegNum); + build->Emit(OP_JMP, 1); + build->Emit(OP_LI, to.RegNum, 1); + return to; + } + else + { + assert(op1.RegType == REGT_INT || op1.RegType == REGT_FLOAT); + assert(Operator == '<' || Operator == '>' || Operator == TK_Geq || Operator == TK_Leq); + static const VM_UBYTE InstrMap[][4] = + { + { OP_LT_RR, OP_LTF_RR, 0 }, // < + { OP_LE_RR, OP_LEF_RR, 1 }, // > + { OP_LT_RR, OP_LTF_RR, 1 }, // >= + { OP_LE_RR, OP_LEF_RR, 0 } // <= + }; + int instr, check; + ExpEmit to(build, REGT_INT); + int index = Operator == '<' ? 0 : Operator == '>' ? 1 : Operator == TK_Geq ? 2 : 3; - instr = InstrMap[index][op1.RegType == REGT_INT ? 0 : 1]; - check = InstrMap[index][2]; - if (op2.Konst) - { - instr += 1; - } - else - { - op2.Free(build); - } - if (op1.Konst) - { - instr += 2; - } - else - { - op1.Free(build); - } - // See FxBoolCast for comments, since it's the same thing. - build->Emit(OP_LI, to.RegNum, 0, 0); - build->Emit(instr, check, op1.RegNum, op2.RegNum); - build->Emit(OP_JMP, 1); - build->Emit(OP_LI, to.RegNum, 1); - return to; + instr = InstrMap[index][op1.RegType == REGT_INT ? 0 : 1]; + check = InstrMap[index][2]; + if (op2.Konst) + { + instr += 1; + } + else + { + op2.Free(build); + } + if (op1.Konst) + { + instr += 2; + } + else + { + op1.Free(build); + } + + // See FxBoolCast for comments, since it's the same thing. + build->Emit(OP_LI, to.RegNum, 0, 0); + build->Emit(instr, check, op1.RegNum, op2.RegNum); + build->Emit(OP_JMP, 1); + build->Emit(OP_LI, to.RegNum, 1); + return to; + } } //========================================================================== @@ -2952,12 +3040,24 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) return NULL; } - if (Operator == TK_ApproxEq && ValueType->GetRegType() != REGT_FLOAT) Operator = TK_Eq; + if (Operator == TK_ApproxEq && left->ValueType->GetRegType() != REGT_FLOAT && left->ValueType->GetRegType() != REGT_STRING) + Operator = TK_Eq; if (left->isConstant() && right->isConstant()) { int v; - if (ValueType->GetRegType() == REGT_FLOAT) + if (ValueType == TypeString) + { + FString v1 = static_cast(left)->GetValue().GetString(); + FString v2 = static_cast(right)->GetValue().GetString(); + if (Operator == TK_ApproxEq) v = !v1.CompareNoCase(v2); + else + { + v = !!v1.Compare(v2); + if (Operator == TK_Eq) v = !v; + } + } + else if (ValueType->GetRegType() == REGT_FLOAT) { double v1 = static_cast(left)->GetValue().GetFloat(); double v2 = static_cast(right)->GetValue().GetFloat(); @@ -2989,39 +3089,55 @@ ExpEmit FxCompareEq::Emit(VMFunctionBuilder *build) ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); assert(op1.RegType == op2.RegType); - assert(op1.RegType == REGT_INT || op1.RegType == REGT_FLOAT || op1.RegType == REGT_POINTER); int instr; - // Only the second operand may be constant. - if (op1.Konst) + if (op1.RegType == REGT_STRING) { - swapvalues(op1, op2); - } - assert(!op1.Konst); - assert(op1.RegCount >= 1 && op1.RegCount <= 3); + ExpEmit to(build, REGT_INT); + assert(Operator == TK_Eq || Operator == TK_Neq || Operator == TK_ApproxEq); + int a = Operator == TK_Eq ? CMP_EQ : + Operator == TK_Neq ? CMP_EQ | CMP_CHECK : CMP_EQ | CMP_APPROX; - ExpEmit to(build, REGT_INT); - - static int flops[] = { OP_EQF_R, OP_EQV2_R, OP_EQV3_R }; - instr = op1.RegType == REGT_INT ? OP_EQ_R : - op1.RegType == REGT_FLOAT ? flops[op1.RegCount-1] : - OP_EQA_R; - op1.Free(build); - if (!op2.Konst) - { - op2.Free(build); + build->Emit(OP_LI, to.RegNum, 0, 0); + build->Emit(OP_CMPS, a, op1.RegNum, op2.RegNum); + build->Emit(OP_JMP, 1); + build->Emit(OP_LI, to.RegNum, 1); + return to; } else { - instr += 1; - } - // See FxUnaryNotBoolean for comments, since it's the same thing. - build->Emit(OP_LI, to.RegNum, 0, 0); - build->Emit(instr, Operator == TK_ApproxEq? CMP_APPROX : Operator != TK_Eq, op1.RegNum, op2.RegNum); - build->Emit(OP_JMP, 1); - build->Emit(OP_LI, to.RegNum, 1); - return to; + // Only the second operand may be constant. + if (op1.Konst) + { + swapvalues(op1, op2); + } + assert(!op1.Konst); + assert(op1.RegCount >= 1 && op1.RegCount <= 3); + + ExpEmit to(build, REGT_INT); + + static int flops[] = { OP_EQF_R, OP_EQV2_R, OP_EQV3_R }; + instr = op1.RegType == REGT_INT ? OP_EQ_R : + op1.RegType == REGT_FLOAT ? flops[op1.RegCount - 1] : + OP_EQA_R; + op1.Free(build); + if (!op2.Konst) + { + op2.Free(build); + } + else + { + instr += 1; + } + + // See FxUnaryNotBoolean for comments, since it's the same thing. + build->Emit(OP_LI, to.RegNum, 0, 0); + build->Emit(instr, Operator == TK_ApproxEq ? CMP_APPROX : Operator != TK_Eq, op1.RegNum, op2.RegNum); + build->Emit(OP_JMP, 1); + build->Emit(OP_LI, to.RegNum, 1); + return to; + } } //========================================================================== @@ -3047,7 +3163,7 @@ FxExpression *FxBinaryInt::Resolve(FCompileContext& ctx) CHECKRESOLVED(); if (!ResolveLR(ctx, false)) return NULL; - if (ValueType->GetRegType() == REGT_FLOAT && ctx.FromDecorate) + if (IsFloat() && ctx.FromDecorate) { // For DECORATE which allows floats here. ZScript does not. if (left->ValueType->GetRegType() != REGT_INT) @@ -3557,7 +3673,7 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) ValueType = truex->ValueType; else if (truex->ValueType == TypeBool && falsex->ValueType == TypeBool) ValueType = TypeBool; - else if (truex->ValueType->GetRegType() == REGT_INT && falsex->ValueType->GetRegType() == REGT_INT) + else if (truex->IsInteger() && falsex->IsInteger()) ValueType = TypeSInt32; else if (truex->IsNumeric() && falsex->IsNumeric()) ValueType = TypeFloat64; @@ -3565,7 +3681,7 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) ValueType = TypeVoid; //else if (truex->ValueType != falsex->ValueType) - if (!IsNumeric() && !IsPointer() && !IsVector()) + if ((!IsNumeric() && !IsPointer() && !IsVector()) || ValueType == TypeVoid) { ScriptPosition.Message(MSG_ERROR, "Incompatible types for ?: operator"); delete this; @@ -3590,7 +3706,7 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) return e; } - if (ValueType->GetRegType() == REGT_FLOAT) + if (IsFloat()) { if (truex->ValueType->GetRegType() != REGT_FLOAT) { @@ -3911,11 +4027,11 @@ FxExpression *FxMinMax::Resolve(FCompileContext &ctx) RESOLVE(choices[i], ctx); ABORT(choices[i]); - if (choices[i]->ValueType->GetRegType() == REGT_FLOAT) + if (choices[i]->IsFloat()) { floatcount++; } - else if (choices[i]->ValueType->GetRegType() == REGT_INT && choices[i]->ValueType != TypeName) + else if (choices[i]->IsInteger()) { intcount++; } @@ -5690,7 +5806,7 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) failed = true; } } - else if ((*ArgList)[i]->ValueType->GetRegType() != REGT_INT) + else if (!(*ArgList)[i]->IsInteger()) { if ((*ArgList)[i]->ValueType->GetRegType() == REGT_FLOAT /* lax */) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 6c7dec487..565da558d 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -295,9 +295,11 @@ public: virtual PPrototype *ReturnProto(); virtual VMFunction *GetDirectFunction(); bool IsNumeric() const { return ValueType != TypeName && ValueType->GetRegCount() == 1 && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT); } + bool IsFloat() const { return ValueType->GetRegType() == REGT_FLOAT && ValueType->GetRegCount() == 1; } bool IsInteger() const { return ValueType != TypeName && (ValueType->GetRegType() == REGT_INT); } bool IsPointer() const { return ValueType->GetRegType() == REGT_POINTER; } bool IsVector() const { return ValueType == TypeVector2 || ValueType == TypeVector3; }; + bool IsBoolCompat() const { return ValueType->GetRegCount() == 1 && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT || ValueType->GetRegType() == REGT_POINTER); } virtual ExpEmit Emit(VMFunctionBuilder *build); diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 5e8a4c2a4..d020b8e88 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -921,7 +921,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_SOUND_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_INT); FSoundID x = param[p].i; #define PARAM_COLOR_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_INT); PalEntry x; x.d = param[p].i; #define PARAM_FLOAT_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); double x = param[p].f; -#define PARAM_ANGLE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); DAngle x = param[p].f; +#define PARAM_ANGLE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); DAngle x = param[p].f; #define PARAM_STRING_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_STRING); FString x = param[p].s(); #define PARAM_STATE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); FState *x = (FState *)param[p].a; #define PARAM_POINTER_AT(p,x,type) assert((p) < numparam); assert(param[p].Type == REGT_POINTER); type *x = (type *)param[p].a; From ac1c022911662ac7f988111f3c1f0ed65cc13add Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 30 Oct 2016 01:05:56 +0200 Subject: [PATCH 139/255] - implemented the 'is' operator (i.e. class type check.) --- src/namedef.h | 11 +- src/scripting/codegeneration/codegen.cpp | 154 +++++++++++++++++++---- src/scripting/codegeneration/codegen.h | 22 ++++ src/scripting/zscript/zcc_compile.cpp | 4 +- 4 files changed, 158 insertions(+), 33 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index 3966c95e7..2d1c3c7a7 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -673,13 +673,14 @@ xx(PlayerClass) xx(Wi_NoAutostartMap) // Decorate compatibility functions -xx(DecoRandom) -xx(DecoFRandom) -xx(DecoCallLineSpecial) -xx(DecoNameToClass) +xx(BuiltinTypeCheck) +xx(BuiltinRandom) +xx(BuiltinFRandom) +xx(BuiltinCallLineSpecial) +xx(BuiltinNameToClass) xx(BuiltinFindMultiNameState) xx(BuiltinFindSingleNameState) -xx(DecoHandleRuntimeState) +xx(BuiltinHandleRuntimeState) xx(Damage) // basic type names diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 6b6d83068..d2ca17db5 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -203,23 +203,24 @@ void ExpEmit::Reuse(VMFunctionBuilder *build) //========================================================================== // -// FindDecorateBuiltinFunction +// FindBuiltinFunction // // Returns the symbol for a decorate utility function. If not found, create -// it and install it in Actor. +// it and install it a local symbol table. // //========================================================================== +static PSymbolTable Builtins; -static PSymbol *FindDecorateBuiltinFunction(FName funcname, VMNativeFunction::NativeCallType func) +static PSymbol *FindBuiltinFunction(FName funcname, VMNativeFunction::NativeCallType func) { - PSymbol *sym = RUNTIME_CLASS(AActor)->Symbols.FindSymbol(funcname, false); + PSymbol *sym = Builtins.FindSymbol(funcname, false); if (sym == NULL) { PSymbolVMFunction *symfunc = new PSymbolVMFunction(funcname); VMNativeFunction *calldec = new VMNativeFunction(func, funcname); symfunc->Function = calldec; sym = symfunc; - RUNTIME_CLASS(AActor)->Symbols.AddSymbol(sym); + Builtins.AddSymbol(sym); } return sym; } @@ -3615,9 +3616,6 @@ FxExpression *FxDotCross::Resolve(FCompileContext& ctx) ExpEmit FxDotCross::Emit(VMFunctionBuilder *build) { - // This is not the "right" way to do these, but it works for now. - // (Problem: No information sharing is done between nodes to reduce the - // code size if you have something like a1 && a2 && a3 && ... && an.) ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); @@ -3634,6 +3632,108 @@ ExpEmit FxDotCross::Emit(VMFunctionBuilder *build) // //========================================================================== +FxTypeCheck::FxTypeCheck(FxExpression *l, FxExpression *r) + : FxExpression(EFX_TypeCheck, l->ScriptPosition) +{ + left = new FxTypeCast(l, NewPointer(RUNTIME_CLASS(DObject)), false); + right = new FxClassTypeCast(NewClassPointer(RUNTIME_CLASS(DObject)), r); + EmitTail = false; + ValueType = TypeBool; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxTypeCheck::~FxTypeCheck() +{ + SAFE_DELETE(left); + SAFE_DELETE(right); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxTypeCheck::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + RESOLVE(left, ctx); + RESOLVE(right, ctx); + ABORT(right && left); + return this; +} + +//========================================================================== +// +// +// +//========================================================================== + +PPrototype *FxTypeCheck::ReturnProto() +{ + EmitTail = true; + return FxExpression::ReturnProto(); +} + + +//========================================================================== +// +// +// +//========================================================================== + +int BuiltinTypeCheck(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +{ + assert(numparam == 2); + PARAM_POINTER_AT(0, obj, DObject); + PARAM_CLASS_AT(1, cls, DObject); + ACTION_RETURN_BOOL(obj->IsKindOf(cls)); +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxTypeCheck::Emit(VMFunctionBuilder *build) +{ + ExpEmit out(build, REGT_INT); + EmitParameter(build, left, ScriptPosition); + EmitParameter(build, right, ScriptPosition); + + + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinTypeCheck, BuiltinTypeCheck); + + assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); + assert(((PSymbolVMFunction *)sym)->Function != NULL); + auto callfunc = ((PSymbolVMFunction *)sym)->Function; + + int opcode = (EmitTail ? OP_TAIL_K : OP_CALL_K); + build->Emit(opcode, build->GetConstantAddress(callfunc, ATAG_OBJECT), 2, 1); + + if (EmitTail) + { + ExpEmit call; + call.Final = true; + return call; + } + + build->Emit(OP_RESULT, 0, REGT_INT, out.RegNum); + return out; +} + +//========================================================================== +// +// +// +//========================================================================== + FxConditional::FxConditional(FxExpression *c, FxExpression *t, FxExpression *f) : FxExpression(EFX_Conditional, c->ScriptPosition) { @@ -4278,7 +4378,7 @@ FxExpression *FxRandom::Resolve(FCompileContext &ctx) // //========================================================================== -int DecoRandom(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +int BuiltinRandom(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam >= 1 && numparam <= 3); FRandom *rng = reinterpret_cast(param[0].a); @@ -4309,7 +4409,7 @@ ExpEmit FxRandom::Emit(VMFunctionBuilder *build) { // Call DecoRandom to generate a random number. VMFunction *callfunc; - PSymbol *sym = FindDecorateBuiltinFunction(NAME_DecoRandom, DecoRandom); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinRandom, BuiltinRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != NULL); @@ -4428,9 +4528,9 @@ ExpEmit FxRandomPick::Emit(VMFunctionBuilder *build) assert(choices.Size() > 0); - // Call DecoRandom to generate a random number. + // Call BuiltinRandom to generate a random number. VMFunction *callfunc; - PSymbol *sym = FindDecorateBuiltinFunction(NAME_DecoRandom, DecoRandom); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinRandom, BuiltinRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != NULL); @@ -4528,7 +4628,7 @@ FxFRandom::FxFRandom(FRandom *r, FxExpression *mi, FxExpression *ma, const FScri // //========================================================================== -int DecoFRandom(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +int BuiltinFRandom(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam == 1 || numparam == 3); FRandom *rng = reinterpret_cast(param[0].a); @@ -4553,9 +4653,9 @@ int DecoFRandom(VMFrameStack *stack, VMValue *param, TArray &defaultpar ExpEmit FxFRandom::Emit(VMFunctionBuilder *build) { - // Call the DecoFRandom function to generate a floating point random number.. + // Call the BuiltinFRandom function to generate a floating point random number.. VMFunction *callfunc; - PSymbol *sym = FindDecorateBuiltinFunction(NAME_DecoFRandom, DecoFRandom); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinFRandom, BuiltinFRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != NULL); @@ -4647,9 +4747,9 @@ FxExpression *FxRandom2::Resolve(FCompileContext &ctx) ExpEmit FxRandom2::Emit(VMFunctionBuilder *build) { - // Call the DecoRandom function to generate the random number. + // Call the BuiltinRandom function to generate the random number. VMFunction *callfunc; - PSymbol *sym = FindDecorateBuiltinFunction(NAME_DecoRandom, DecoRandom); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinRandom, BuiltinRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != NULL); @@ -5836,7 +5936,7 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) // //========================================================================== -int DecoCallLineSpecial(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +int BuiltinCallLineSpecial(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam > 2 && numparam < 8); assert(param[0].Type == REGT_INT); @@ -5885,9 +5985,9 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) } } } - // Call the DecoCallLineSpecial function to perform the desired special. + // Call the BuiltinCallLineSpecial function to perform the desired special. VMFunction *callfunc; - PSymbol *sym = FindDecorateBuiltinFunction(NAME_DecoCallLineSpecial, DecoCallLineSpecial); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinCallLineSpecial, BuiltinCallLineSpecial); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != NULL); @@ -7347,7 +7447,7 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) // //========================================================================== -int DecoNameToClass(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +int BuiltinNameToClass(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { assert(numparam == 2); assert(numret == 1); @@ -7380,9 +7480,9 @@ ExpEmit FxClassTypeCast::Emit(VMFunctionBuilder *build) build->Emit(OP_PARAM, 0, clsname.RegType, clsname.RegNum); build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, build->GetConstantAddress(const_cast(desttype), ATAG_OBJECT)); - // Call the DecoNameToClass function to convert from 'name' to class. + // Call the BuiltinNameToClass function to convert from 'name' to class. VMFunction *callfunc; - PSymbol *sym = FindDecorateBuiltinFunction(NAME_DecoNameToClass, DecoNameToClass); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinNameToClass, BuiltinNameToClass); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != NULL); @@ -7487,7 +7587,7 @@ static bool VerifyJumpTarget(AActor *stateowner, FStateParamInfo *stateinfo, int return false; } -static int DecoHandleRuntimeState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +static int BuiltinHandleRuntimeState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) { PARAM_PROLOGUE; PARAM_OBJECT(stateowner, AActor); @@ -7522,7 +7622,7 @@ ExpEmit FxRuntimeStateIndex::Emit(VMFunctionBuilder *build) VMFunction *callfunc; PSymbol *sym; - sym = FindDecorateBuiltinFunction(NAME_DecoHandleRuntimeState, DecoHandleRuntimeState); + sym = FindBuiltinFunction(NAME_BuiltinHandleRuntimeState, BuiltinHandleRuntimeState); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; @@ -7702,11 +7802,11 @@ ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) if (names.Size() == 1) { - sym = FindDecorateBuiltinFunction(NAME_BuiltinFindSingleNameState, BuiltinFindSingleNameState); + sym = FindBuiltinFunction(NAME_BuiltinFindSingleNameState, BuiltinFindSingleNameState); } else { - sym = FindDecorateBuiltinFunction(NAME_BuiltinFindMultiNameState, BuiltinFindMultiNameState); + sym = FindBuiltinFunction(NAME_BuiltinFindMultiNameState, BuiltinFindMultiNameState); } assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 565da558d..9e13d3806 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -267,6 +267,7 @@ enum EFxType EFX_CaseStatement, EFX_VectorInitializer, EFX_VectorBuiltin, + EFX_TypeCheck, EFX_COUNT }; @@ -929,6 +930,27 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxBinaryLogical +// +//========================================================================== + +class FxTypeCheck : public FxExpression +{ +public: + FxExpression *left; + FxExpression *right; + bool EmitTail; + + FxTypeCheck(FxExpression*, FxExpression*); + ~FxTypeCheck(); + FxExpression *Resolve(FCompileContext&); + PPrototype *ReturnProto(); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxConditional diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f2644b240..e545bd508 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2690,9 +2690,11 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case PEX_DotProduct: return new FxDotCross(tok, left, right); + case PEX_Is: + return new FxTypeCheck(left, right); + // todo: These do not have representations in DECORATE and no implementation exists yet. case PEX_Concat: - case PEX_Is: default: I_Error("Binary operator %d not implemented yet", op); From 94410accf41dd752861f002b33502db64cbcd74d Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 30 Oct 2016 04:35:01 +0100 Subject: [PATCH 140/255] Renamed "VectorInitializer" to "VectorValue" This was really confusing for me as this is an actual vector "value" rather than an "initializer" --- src/scripting/codegeneration/codegen.cpp | 14 ++++---- src/scripting/codegeneration/codegen.h | 8 ++--- src/scripting/zscript/ast.cpp | 2 +- src/scripting/zscript/zcc-parse.lemon | 46 +++++++++++------------- src/scripting/zscript/zcc_compile.cpp | 6 ++-- src/scripting/zscript/zcc_parser.h | 4 +-- 6 files changed, 37 insertions(+), 43 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d2ca17db5..093039902 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -446,8 +446,8 @@ ExpEmit FxConstant::Emit(VMFunctionBuilder *build) // //========================================================================== -FxVectorInitializer::FxVectorInitializer(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc) - :FxExpression(EFX_VectorInitializer, sc) +FxVectorValue::FxVectorValue(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc) + :FxExpression(EFX_VectorValue, sc) { xyz[0] = x; xyz[1] = y; @@ -456,13 +456,13 @@ FxVectorInitializer::FxVectorInitializer(FxExpression *x, FxExpression *y, FxExp ValueType = TypeVoid; // we do not know yet } -FxVectorInitializer::~FxVectorInitializer() +FxVectorValue::~FxVectorValue() { for (auto &a : xyz) SAFE_DELETE(a); } -FxExpression *FxVectorInitializer::Resolve(FCompileContext&ctx) +FxExpression *FxVectorValue::Resolve(FCompileContext&ctx) { bool fails = false; @@ -501,10 +501,10 @@ FxExpression *FxVectorInitializer::Resolve(FCompileContext&ctx) return nullptr; } ValueType = TypeVector3; - if (xyz[0]->ExprType == EFX_VectorInitializer) + if (xyz[0]->ExprType == EFX_VectorValue) { // If two vector initializers are nested, unnest them now. - auto vi = static_cast(xyz[0]); + auto vi = static_cast(xyz[0]); xyz[2] = xyz[1]; xyz[1] = vi->xyz[1]; xyz[0] = vi->xyz[0]; @@ -542,7 +542,7 @@ static ExpEmit EmitKonst(VMFunctionBuilder *build, ExpEmit &emit) return emit; } -ExpEmit FxVectorInitializer::Emit(VMFunctionBuilder *build) +ExpEmit FxVectorValue::Emit(VMFunctionBuilder *build) { // no const handling here. Ultimstely it's too rarely used (i.e. the only fully constant vector ever allocated in ZDoom is the 0-vector in a very few places) // and the negatives (excessive allocation of float constants) outweigh the positives (saved a few instructions) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 9e13d3806..f9393d11f 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -265,7 +265,7 @@ enum EFxType EFX_LocalVariableDeclaration, EFX_SwitchStatement, EFX_CaseStatement, - EFX_VectorInitializer, + EFX_VectorValue, EFX_VectorBuiltin, EFX_TypeCheck, EFX_COUNT @@ -463,14 +463,14 @@ public: // //========================================================================== -class FxVectorInitializer : public FxExpression +class FxVectorValue : public FxExpression { FxExpression *xyz[3]; bool isConst; // gets set to true if all element are const public: - FxVectorInitializer(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc); - ~FxVectorInitializer(); + FxVectorValue(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc); + ~FxVectorValue(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); diff --git a/src/scripting/zscript/ast.cpp b/src/scripting/zscript/ast.cpp index e77c631e1..cb0240dea 100644 --- a/src/scripting/zscript/ast.cpp +++ b/src/scripting/zscript/ast.cpp @@ -623,7 +623,7 @@ static void PrintExprTrinary(FLispString &out, ZCC_TreeNode *node) static void PrintVectorInitializer(FLispString &out, ZCC_TreeNode *node) { - ZCC_VectorInitializer *enode = (ZCC_VectorInitializer *)node; + ZCC_VectorValue *enode = (ZCC_VectorValue *)node; OpenExprType(out, enode->Operation); PrintNodes(out, enode->X); PrintNodes(out, enode->Y); diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 173ec27fc..b1065281c 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -945,7 +945,6 @@ func_param_flags(X) ::= func_param_flags(A) OPTIONAL(T). { X.Int = A.Int | ZCC_O %type expr{ZCC_Expression *} %type primary{ZCC_Expression *} -%type vectorinit{ZCC_VectorInitializer*} %type unary_expr{ZCC_Expression *} %type constant{ZCC_ExprConstant *} @@ -967,8 +966,26 @@ primary(X) ::= SUPER(T). X = expr; } primary(X) ::= constant(A). { X = A; /*X-overwrites-A*/ } -primary(X) ::= vectorinit(A). { X = A; /*X-overwrites-A*/ } - +primary(XX) ::= LPAREN expr(A) COMMA expr(B) COMMA expr(C) RPAREN. [DOT] +{ + NEW_AST_NODE(VectorValue, expr, A); + expr->Operation = PEX_Vector; + expr->Type = TypeVector3; + expr->X = A; + expr->Y = B; + expr->Z = C; + XX = expr; +} +primary(XX) ::= LPAREN expr(A) COMMA expr(B) RPAREN. [DOT] +{ + NEW_AST_NODE(VectorValue, expr, A); + expr->Operation = PEX_Vector; + expr->Type = TypeVector2; + expr->X = A; + expr->Y = B; + expr->Z = nullptr; + XX = expr; +} primary(X) ::= LPAREN expr(A) RPAREN. { X = A; /*X-overwrites-A*/ @@ -1019,29 +1036,6 @@ primary(X) ::= SCOPE primary(B). } */ -vectorinit(XX) ::= LPAREN expr(A) COMMA expr(B) COMMA expr(C) RPAREN. [DOT] -{ - NEW_AST_NODE(VectorInitializer, expr, A); - expr->Operation = PEX_Vector; - expr->Type = TypeVector3; - expr->X = A; - expr->Y = B; - expr->Z = C; - XX = expr; -} - - -vectorinit(XX) ::= LPAREN expr(A) COMMA expr(B) RPAREN. [DOT] -{ - NEW_AST_NODE(VectorInitializer, expr, A); - expr->Operation = PEX_Vector; - expr->Type = TypeVector2; - expr->X = A; - expr->Y = B; - expr->Z = nullptr; - XX = expr; -} - /*----- Unary Expressions -----*/ unary_expr(X) ::= primary(X). diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index e545bd508..38754bdce 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2712,13 +2712,13 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return new FxConditional(condition, left, right); } - case AST_VectorInitializer: + case AST_VectorValue: { - auto vecini = static_cast(ast); + auto vecini = static_cast(ast); auto xx = ConvertNode(vecini->X); auto yy = ConvertNode(vecini->Y); auto zz = ConvertNode(vecini->Z); - return new FxVectorInitializer(xx, yy, zz, *ast); + return new FxVectorValue(xx, yy, zz, *ast); } case AST_LocalVarStmt: diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 0889d1d37..715fa0be6 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -98,7 +98,7 @@ enum EZCCTreeNodeType AST_Default, AST_FlagStmt, AST_PropertyStmt, - AST_VectorInitializer, + AST_VectorValue, NUM_AST_NODE_TYPES }; @@ -385,7 +385,7 @@ struct ZCC_ExprTrinary : ZCC_Expression ZCC_Expression *Right; }; -struct ZCC_VectorInitializer : ZCC_Expression +struct ZCC_VectorValue : ZCC_Expression { ZCC_Expression *X, *Y, *Z; }; From 8be7af41a979cbd132e559da660fde38b77242ea Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 30 Oct 2016 04:35:48 +0100 Subject: [PATCH 141/255] Don't use a struct reference for vectors as return type just like for parameters --- src/scripting/zscript/zcc_compile.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 38754bdce..6c83b5a99 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1967,7 +1967,7 @@ void ZCCCompiler::InitFunctions() do { auto type = DetermineType(c->Type(), f, f->Name, t, false, false); - if (type->IsKindOf(RUNTIME_CLASS(PStruct))) + if (type->IsKindOf(RUNTIME_CLASS(PStruct)) && type != TypeVector2 && type != TypeVector3) { // structs and classes only get passed by pointer. type = NewPointer(type); From 5643d6c6928297888e6febd87d8ba3efe719f910 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 30 Oct 2016 06:17:37 +0100 Subject: [PATCH 142/255] Make sure to use the REGT_MULTIREG flags for opcodes that need it --- src/scripting/codegeneration/codegen.cpp | 47 +++++++++++++++--------- src/scripting/vm/vm.h | 4 +- 2 files changed, 31 insertions(+), 20 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 093039902..75058511d 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -335,6 +335,30 @@ PPrototype *FxExpression::ReturnProto() // //========================================================================== +static int EncodeRegType(ExpEmit reg) +{ + int regtype = reg.RegType; + if (reg.Konst) + { + regtype |= REGT_KONST; + } + else if (reg.RegCount == 2) + { + regtype |= REGT_MULTIREG2; + } + else if (reg.RegCount == 3) + { + regtype |= REGT_MULTIREG3; + } + return regtype; +} + +//========================================================================== +// +// +// +//========================================================================== + static int EmitParameter(VMFunctionBuilder *build, FxExpression *operand, const FScriptPosition &pos) { ExpEmit where = operand->Emit(build); @@ -347,20 +371,7 @@ static int EmitParameter(VMFunctionBuilder *build, FxExpression *operand, const } else { - int regtype = where.RegType; - if (where.Konst) - { - regtype |= REGT_KONST; - } - else if (where.RegCount == 2) - { - regtype |= REGT_MULTIREG2; - } - else if (where.RegCount == 3) - { - regtype |= REGT_MULTIREG3; - } - build->Emit(OP_PARAM, 0, regtype, where.RegNum); + build->Emit(OP_PARAM, 0, EncodeRegType(where), where.RegNum); where.Free(build); return where.RegCount; } @@ -6215,9 +6226,9 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } else if (vmfunc->Proto->ReturnTypes.Size() > 0) { // Call, expecting one result - ExpEmit reg(build, vmfunc->Proto->ReturnTypes[0]->GetRegType()); + ExpEmit reg(build, vmfunc->Proto->ReturnTypes[0]->GetRegType(), vmfunc->Proto->ReturnTypes[0]->GetRegCount()); build->Emit(OP_CALL_K, funcaddr, count, 1); - build->Emit(OP_RESULT, 0, reg.RegType, reg.RegNum); + build->Emit(OP_RESULT, 0, EncodeRegType(reg), reg.RegNum); return reg; } else @@ -6255,7 +6266,7 @@ bool FxVMFunctionCall::CheckEmitCast(VMFunctionBuilder *build, bool returnit, Ex else { ExpEmit where = arg->Emit(build); - build->Emit(OP_RET, RET_FINAL, where.RegType | (where.Konst ? REGT_KONST : 0), where.RegNum); + build->Emit(OP_RET, RET_FINAL, EncodeRegType(where), where.RegNum); where.Free(build); } reg = ExpEmit(); @@ -7319,7 +7330,7 @@ ExpEmit FxReturnStatement::Emit(VMFunctionBuilder *build) } else { - build->Emit(OP_RET, RET_FINAL, out.RegType | (out.Konst ? REGT_KONST : 0), out.RegNum); + build->Emit(OP_RET, RET_FINAL, EncodeRegType(out), out.RegNum); } } } diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index d020b8e88..92615461e 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -291,14 +291,14 @@ struct VMReturn } void SetVector(const double val[3]) { - //assert(RegType == REGT_FLOAT); + assert(RegType == (REGT_FLOAT|REGT_MULTIREG3)); ((double *)Location)[0] = val[0]; ((double *)Location)[1] = val[1]; ((double *)Location)[2] = val[2]; } void SetVector2(const double val[2]) { - //assert(RegType == REGT_FLOAT); + assert(RegType == (REGT_FLOAT|REGT_MULTIREG2)); ((double *)Location)[0] = val[0]; ((double *)Location)[1] = val[1]; } From 06ec6318a9dbcea64a5a487908d0c95d80856fb8 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 30 Oct 2016 06:55:16 +0100 Subject: [PATCH 143/255] Fixed: A vector value could point to garbage data after being 'unnested' --- src/scripting/codegeneration/codegen.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 75058511d..a0ccbb2c8 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -519,6 +519,7 @@ FxExpression *FxVectorValue::Resolve(FCompileContext&ctx) xyz[2] = xyz[1]; xyz[1] = vi->xyz[1]; xyz[0] = vi->xyz[0]; + vi->xyz[0] = vi->xyz[1] = nullptr; // Don't delete our own expressions. delete vi; } } From 9eeb56212b4c9736593df40d91e02c4b77b43fa8 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 30 Oct 2016 09:05:42 +0100 Subject: [PATCH 144/255] - fixed: A VM function's NumArgs value needs to count stack arguments, not logical ones, meaning that for vectors each element needs to count separately. - renamed VMFunction::Defaults to DefaultArgs to make searching easier. - let ZCCCompiler process vector defaults for function parameters. --- src/scripting/codegeneration/codegen.h | 10 ++++++- src/scripting/vm/vm.h | 2 +- src/scripting/vm/vmbuilder.cpp | 8 ++++- src/scripting/vm/vmexec.cpp | 4 +-- src/scripting/vm/vmexec.h | 4 +-- src/scripting/vm/vmframe.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 41 ++++++++++++++++++++------ 7 files changed, 54 insertions(+), 17 deletions(-) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index f9393d11f..b3a5e4297 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -466,12 +466,20 @@ public: class FxVectorValue : public FxExpression { FxExpression *xyz[3]; - bool isConst; // gets set to true if all element are const + bool isConst; // gets set to true if all element are const (used by function defaults parser) public: + + friend class ZCCCompiler; + FxVectorValue(FxExpression *x, FxExpression *y, FxExpression *z, const FScriptPosition &sc); ~FxVectorValue(); FxExpression *Resolve(FCompileContext&); + bool isConstVector(int dim) + { + if (!isConst) return false; + return dim == 2 ? xyz[2] == nullptr : xyz[2] != nullptr; + } ExpEmit Emit(VMFunctionBuilder *build); }; diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 92615461e..4109d4e79 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -643,7 +643,7 @@ public: bool Native; BYTE ImplicitArgs = 0; // either 0 for static, 1 for method or 3 for action FName Name; - TArray Defaults; + TArray DefaultArgs; class PPrototype *Proto; diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 3f6d1cbd3..e9ac38a78 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -722,7 +722,13 @@ void FFunctionBuildList::Build() // Emit code item.Code->Emit(&buildit); buildit.MakeFunction(sfunc); - sfunc->NumArgs = item.Func->Variants[0].Proto->ArgumentTypes.Size(); + sfunc->NumArgs = 0; + // NumArgs for the VMFunction must be the amount of stack elements, which can differ from the amount of logical function arguments if vectors are in the list. + // For the VM a vector is 2 or 3 args, depending on size. + for (auto s : item.Func->Variants[0].Proto->ArgumentTypes) + { + sfunc->NumArgs += s->GetRegCount(); + } if (dump != nullptr) { diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index e2691470e..57ce48a95 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -188,14 +188,14 @@ void VMFillParams(VMValue *params, VMFrame *callee, int numparam) const VMRegisters calleereg(callee); assert(calleefunc != NULL && !calleefunc->Native); - assert(numparam == calleefunc->NumArgs || ((int)calleefunc->Defaults.Size() == calleefunc->NumArgs)); + assert(numparam == calleefunc->NumArgs || ((int)calleefunc->DefaultArgs.Size() == calleefunc->NumArgs)); assert(REGT_INT == 0 && REGT_FLOAT == 1 && REGT_STRING == 2 && REGT_POINTER == 3); regd = regf = regs = rega = 0; for (int i = 0; i < calleefunc->NumArgs; ++i) { // get all actual parameters and fill the rest from the defaults. - VMValue &p = i < numparam? params[i] : calleefunc->Defaults[i]; + VMValue &p = i < numparam? params[i] : calleefunc->DefaultArgs[i]; if (p.Type < REGT_STRING) { if (p.Type == REGT_INT) diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 4b43ed815..4b16a99d1 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -544,7 +544,7 @@ begin: FillReturns(reg, f, returns, pc+1, C); if (call->Native) { - numret = static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, call->Defaults, B, returns, C); + numret = static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, call->DefaultArgs, B, returns, C); } else { @@ -588,7 +588,7 @@ begin: if (call->Native) { - return static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, call->Defaults, B, ret, numret); + return static_cast(call)->NativeCall(stack, reg.param + f->NumParam - B, call->DefaultArgs, B, ret, numret); } else { // FIXME: Not a true tail call diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index bf2159fa1..c54b585e9 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -415,7 +415,7 @@ int VMFrameStack::Call(VMFunction *func, VMValue *params, int numparams, VMRetur { if (func->Native) { - return static_cast(func)->NativeCall(this, params, func->Defaults, numparams, results, numresults); + return static_cast(func)->NativeCall(this, params, func->DefaultArgs, numparams, results, numresults); } else { diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 6c83b5a99..78a448f7c 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2022,7 +2022,8 @@ void ZCCCompiler::InitFunctions() { do { - VMValue vmval; // default is REGT_NIL which means 'no default value' here. + int elementcount = 1; + VMValue vmval[3]; // default is REGT_NIL which means 'no default value' here. if (p->Type != nullptr) { auto type = DetermineType(c->Type(), p, f->Name, p->Type, false, false); @@ -2036,6 +2037,14 @@ void ZCCCompiler::InitFunctions() { type = NewPointer(type); } + else if (type == TypeVector2) + { + elementcount = 2; + } + else if (type == TypeVector3) + { + elementcount = 3; + } } if (type->GetRegType() == REGT_NIL && type != TypeVector2 && type != TypeVector3) { @@ -2055,7 +2064,21 @@ void ZCCCompiler::InitFunctions() if (x != nullptr) { - if (!x->isConstant()) + // Vectors need special treatment because they use more than one entry in the Defaults and do not report as actual constants + if (type == TypeVector2 && x->ExprType == EFX_VectorValue && static_cast(x)->isConstVector(2)) + { + auto vx = static_cast(x); + vmval[0] = static_cast(vx->xyz[0])->GetValue().GetFloat(); + vmval[1] = static_cast(vx->xyz[1])->GetValue().GetFloat(); + } + else if (type == TypeVector3 && x->ExprType == EFX_VectorValue && static_cast(x)->isConstVector(3)) + { + auto vx = static_cast(x); + vmval[0] = static_cast(vx->xyz[0])->GetValue().GetFloat(); + vmval[1] = static_cast(vx->xyz[1])->GetValue().GetFloat(); + vmval[2] = static_cast(vx->xyz[2])->GetValue().GetFloat(); + } + else if (!x->isConstant()) { Error(p, "Default parameter %s is not constant in %s", FName(p->Name).GetChars(), FName(f->Name).GetChars()); } @@ -2070,22 +2093,22 @@ void ZCCCompiler::InitFunctions() switch (type->GetRegType()) { case REGT_INT: - vmval = cnst->GetValue().GetInt(); + vmval[0] = cnst->GetValue().GetInt(); break; case REGT_FLOAT: - vmval = cnst->GetValue().GetFloat(); + vmval[0] = cnst->GetValue().GetFloat(); break; case REGT_POINTER: if (type->IsKindOf(RUNTIME_CLASS(PClassPointer))) - vmval = (DObject*)cnst->GetValue().GetPointer(); + vmval[0] = (DObject*)cnst->GetValue().GetPointer(); else - vmval = cnst->GetValue().GetPointer(); + vmval[0] = cnst->GetValue().GetPointer(); break; case REGT_STRING: - vmval = cnst->GetValue().GetString(); + vmval[0] = cnst->GetValue().GetString(); break; default: @@ -2112,7 +2135,7 @@ void ZCCCompiler::InitFunctions() argflags.Push(0); argnames.Push(NAME_None); } - argdefaults.Push(vmval); + for(int i=0;i(p->SiblingNext); } while (p != f->Params); } @@ -2131,7 +2154,7 @@ void ZCCCompiler::InitFunctions() } if (sym->Variants[0].Implementation != nullptr && hasdefault) // do not copy empty default lists, they only waste space and processing time. { - sym->Variants[0].Implementation->Defaults = std::move(argdefaults); + sym->Variants[0].Implementation->DefaultArgs = std::move(argdefaults); } // todo: Check inheritance. } From f8ccda2dc84265d5e9ed48f34cd5583f4e65ec3e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 30 Oct 2016 14:00:11 +0100 Subject: [PATCH 145/255] - scriptified A_Mushroom to test something a bit more complex. - fixed: FxMinusSign trashed local variables that were used with negation. - fixed: FxConditional only handled ints and floats, but not pointers and strings. - fixed: A 'no states in non-actors' error was triggered, even for classes without any states. --- src/CMakeLists.txt | 1 - src/d_dehacked.cpp | 8 + src/dobject.cpp | 7 + src/g_doom/a_doommisc.cpp | 1 - src/g_doom/a_fatso.cpp | 84 ------- src/info.h | 2 +- src/p_mobj.cpp | 31 +++ src/scripting/codegeneration/codegen.cpp | 292 +++++++++++++---------- src/scripting/thingdef_data.cpp | 3 +- src/scripting/zscript/zcc_compile.cpp | 8 +- wadsrc/static/zscript.txt | 1 + wadsrc/static/zscript/actor.txt | 5 +- wadsrc/static/zscript/base.txt | 8 + wadsrc/static/zscript/constants.txt | 6 + wadsrc/static/zscript/doom/fatso.txt | 55 +++++ 15 files changed, 290 insertions(+), 222 deletions(-) delete mode 100644 src/g_doom/a_fatso.cpp create mode 100644 wadsrc/static/zscript/base.txt diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index a5c5fd3e3..f96bf7d36 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -838,7 +838,6 @@ set( NOT_COMPILED_SOURCE_FILES g_doom/a_archvile.cpp g_doom/a_bossbrain.cpp g_doom/a_doomweaps.cpp - g_doom/a_fatso.cpp g_doom/a_keen.cpp g_doom/a_lostsoul.cpp g_doom/a_painelemental.cpp diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 064f37c02..cc699ac47 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -1488,6 +1488,14 @@ static int PatchFrame (int frameNum) return result; } +// there is exactly one place where this is needed and we do not want to expose the state internals to ZSCRIPT. +DEFINE_ACTION_FUNCTION(AActor, isDEHState) +{ + PARAM_PROLOGUE; + PARAM_STATE(state); + ACTION_RETURN_BOOL(state != nullptr && (state->DefineFlags & SDF_DEHACKED)); +} + static int PatchSprite (int sprNum) { int result; diff --git a/src/dobject.cpp b/src/dobject.cpp index 4acb86ce4..beef73c89 100644 --- a/src/dobject.cpp +++ b/src/dobject.cpp @@ -349,6 +349,13 @@ void DObject::Destroy () ObjectFlags = (ObjectFlags & ~OF_Fixed) | OF_EuthanizeMe; } +DEFINE_ACTION_FUNCTION(DObject, Destroy) +{ + PARAM_SELF_PROLOGUE(DObject); + self->Destroy(); + return 0; +} + //========================================================================== // // diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index df42bfa7b..29e2fc8ee 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -25,7 +25,6 @@ #include "a_archvile.cpp" #include "a_bossbrain.cpp" #include "a_doomweaps.cpp" -#include "a_fatso.cpp" #include "a_keen.cpp" #include "a_lostsoul.cpp" #include "a_painelemental.cpp" diff --git a/src/g_doom/a_fatso.cpp b/src/g_doom/a_fatso.cpp deleted file mode 100644 index ea2d8f397..000000000 --- a/src/g_doom/a_fatso.cpp +++ /dev/null @@ -1,84 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -*/ - -// -// Mancubus attack, -// firing three missiles in three different directions? -// Doesn't look like it. -// -// -// killough 9/98: a mushroom explosion effect, sorta :) -// Original idea: Linguica -// - -enum -{ - MSF_Standard = 0, - MSF_Classic = 1, - MSF_DontHurt = 2, -}; - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Mushroom) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_DEF (spawntype, AActor) - PARAM_INT_DEF (n) - PARAM_INT_DEF (flags) - PARAM_FLOAT_DEF (vrange) - PARAM_FLOAT_DEF (hrange) - - int i, j; - - if (n == 0) - { - n = self->GetMissileDamage(0, 1); - } - if (spawntype == NULL) - { - spawntype = PClass::FindActor("FatShot"); - } - - P_RadiusAttack (self, self->target, 128, 128, self->DamageType, (flags & MSF_DontHurt) ? 0 : RADF_HURTSOURCE); - P_CheckSplash(self, 128.); - - // Now launch mushroom cloud - AActor *target = Spawn("Mapspot", self->Pos(), NO_REPLACE); // We need something to aim at. - AActor *master = (flags & MSF_DontHurt) ? (AActor*)(self->target) : self; - target->Height = self->Height; - for (i = -n; i <= n; i += 8) - { - for (j = -n; j <= n; j += 8) - { - AActor *mo; - target->SetXYZ( - self->X() + i, // Aim in many directions from source - self->Y() + j, - self->Z() + (P_AproxDistance(i,j) * vrange)); // Aim up fairly high - if ((flags & MSF_Classic) || // Flag explicitely set, or no flags and compat options - (flags == 0 && (self->state->DefineFlags & SDF_DEHACKED) && (i_compatflags & COMPATF_MUSHROOM))) - { // Use old function for MBF compatibility - mo = P_OldSpawnMissile (self, master, target, spawntype); - } - else // Use normal function - { - mo = P_SpawnMissile(self, target, spawntype, master); - } - if (mo != NULL) - { // Slow it down a bit - mo->Vel *= hrange; - mo->flags &= ~MF_NOGRAVITY; // Make debris fall under gravity - } - } - } - target->Destroy(); - return 0; -} diff --git a/src/info.h b/src/info.h index 2155734ad..ad25bdcaf 100644 --- a/src/info.h +++ b/src/info.h @@ -67,7 +67,7 @@ enum EStateDefineFlags SDF_DEHACKED = 8, // Identify a state as having been modified by a dehacked lump }; -enum EStateType +enum EStateType : int // this must ensure proper alignment. { STATE_Actor, STATE_Psprite, diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 754ec516a..3fd1be9a1 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -4258,6 +4258,17 @@ AActor *AActor::StaticSpawn (PClassActor *type, const DVector3 &pos, replace_t a return actor; } +DEFINE_ACTION_FUNCTION(AActor, Spawn) +{ + PARAM_PROLOGUE; + PARAM_CLASS(type, AActor); + PARAM_FLOAT_DEF(x); + PARAM_FLOAT_DEF(y); + PARAM_FLOAT_DEF(z); + PARAM_INT_DEF(flags); + ACTION_RETURN_OBJECT(AActor::StaticSpawn(type, DVector3(x, y, z), replace_t(flags))); +} + PClassActor *ClassForSpawn(FName classname) { PClass *cls = PClass::FindClass(classname); @@ -5951,6 +5962,16 @@ AActor *P_OldSpawnMissile(AActor *source, AActor *owner, AActor *dest, PClassAct return th; } +DEFINE_ACTION_FUNCTION(AActor, OldSpawnMissile) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(dest, AActor); + PARAM_CLASS(type, AActor); + PARAM_OBJECT_DEF(owner, AActor); + ACTION_RETURN_OBJECT(P_OldSpawnMissile(self, owner, dest, type)); +} + + //--------------------------------------------------------------------------- // // FUNC P_SpawnMissileAngle @@ -6616,6 +6637,16 @@ DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) return 0; } +DEFINE_ACTION_FUNCTION(AActor, SetXYZ) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(x); + PARAM_FLOAT(y); + PARAM_FLOAT(z); + self->SetXYZ(x, y, z); + return 0; +} + //---------------------------------------------------------------------------- // // DropItem handling diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index a0ccbb2c8..4fa6da73e 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -156,7 +156,7 @@ void FCompileContext::CheckReturn(PPrototype *proto, FScriptPosition &pos) if (fail) { - pos.Message(MSG_ERROR, "All return expressions must deduce to the same type"); + pos.Message(MSG_ERROR, "Return type mismatch"); } } @@ -214,7 +214,7 @@ static PSymbolTable Builtins; static PSymbol *FindBuiltinFunction(FName funcname, VMNativeFunction::NativeCallType func) { PSymbol *sym = Builtins.FindSymbol(funcname, false); - if (sym == NULL) + if (sym == nullptr) { PSymbolVMFunction *symfunc = new PSymbolVMFunction(funcname); VMNativeFunction *calldec = new VMNativeFunction(func, funcname); @@ -282,7 +282,7 @@ bool FxExpression::isConstant() const VMFunction *FxExpression::GetDirectFunction() { - return NULL; + return nullptr; } //========================================================================== @@ -387,7 +387,7 @@ FxExpression *FxConstant::MakeConstant(PSymbol *sym, const FScriptPosition &pos) { FxExpression *x; PSymbolConstNumeric *csym = dyn_cast(sym); - if (csym != NULL) + if (csym != nullptr) { if (csym->ValueType->IsA(RUNTIME_CLASS(PInt))) { @@ -400,13 +400,13 @@ FxExpression *FxConstant::MakeConstant(PSymbol *sym, const FScriptPosition &pos) else { pos.Message(MSG_ERROR, "Invalid constant '%s'\n", csym->SymbolName.GetChars()); - return NULL; + return nullptr; } } else { pos.Message(MSG_ERROR, "'%s' is not a constant\n", sym->SymbolName.GetChars()); - x = NULL; + x = nullptr; } return x; } @@ -794,7 +794,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) { FxExpression *x = basex; x->ValueType = ValueType; - basex = NULL; + basex = nullptr; delete this; return x; } @@ -833,7 +833,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) } ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } //========================================================================== @@ -891,7 +891,7 @@ FxExpression *FxFloatCast::Resolve(FCompileContext &ctx) if (basex->IsFloat()) { FxExpression *x = basex; - basex = NULL; + basex = nullptr; delete this; return x; } @@ -923,7 +923,7 @@ FxExpression *FxFloatCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } } @@ -982,7 +982,7 @@ FxExpression *FxNameCast::Resolve(FCompileContext &ctx) if (basex->ValueType == TypeName) { FxExpression *x = basex; - basex = NULL; + basex = nullptr; delete this; return x; } @@ -1001,7 +1001,7 @@ FxExpression *FxNameCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Cannot convert to name"); delete this; - return NULL; + return nullptr; } } @@ -1060,7 +1060,7 @@ FxExpression *FxStringCast::Resolve(FCompileContext &ctx) if (basex->ValueType == TypeString) { FxExpression *x = basex; - basex = NULL; + basex = nullptr; delete this; return x; } @@ -1091,7 +1091,7 @@ FxExpression *FxStringCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Cannot convert to string"); delete this; - return NULL; + return nullptr; } } @@ -1158,7 +1158,7 @@ FxExpression *FxColorCast::Resolve(FCompileContext &ctx) { FxExpression *x = basex; x->ValueType = TypeColor; - basex = NULL; + basex = nullptr; delete this; return x; } @@ -1177,7 +1177,7 @@ FxExpression *FxColorCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Cannot convert to color"); delete this; - return NULL; + return nullptr; } } @@ -1237,7 +1237,7 @@ FxExpression *FxSoundCast::Resolve(FCompileContext &ctx) { FxExpression *x = basex; x->ValueType = TypeSound; - basex = NULL; + basex = nullptr; delete this; return x; } @@ -1256,7 +1256,7 @@ FxExpression *FxSoundCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Cannot convert to sound"); delete this; - return NULL; + return nullptr; } } @@ -1318,6 +1318,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) // first deal with the simple types if (ValueType == TypeError || basex->ValueType == TypeError) { + ScriptPosition.Message(MSG_ERROR, "Trying to cast to invalid type. This error message means that somewhere in the script compiler an error check is missing."); delete this; return nullptr; } @@ -1502,7 +1503,7 @@ FxExpression *FxPlusSign::Resolve(FCompileContext& ctx) if (Operand->IsNumeric() || Operand->IsVector()) { FxExpression *e = Operand; - Operand = NULL; + Operand = nullptr; delete this; return e; } @@ -1510,7 +1511,7 @@ FxExpression *FxPlusSign::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } } @@ -1571,7 +1572,7 @@ FxExpression *FxMinusSign::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } } @@ -1587,7 +1588,14 @@ ExpEmit FxMinusSign::Emit(VMFunctionBuilder *build) ExpEmit from = Operand->Emit(build); assert(from.Konst == 0); assert(ValueType->GetRegCount() == from.RegCount); - // Do it in-place. + // Do it in-place, unless a local variable + if (from.Fixed) + { + ExpEmit to = ExpEmit(build, from.RegType, from.RegCount); + build->Emit(Operand->ValueType->GetMoveOp(), to.RegNum, from.RegNum); + from = to; + } + if (ValueType->GetRegType() == REGT_INT) { build->Emit(OP_NEG, from.RegNum, from.RegNum, 0); @@ -1653,10 +1661,10 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) // DECORATE allows floats here so cast them to int. Operand = new FxIntCast(Operand, true); Operand = Operand->Resolve(ctx); - if (Operand == NULL) + if (Operand == nullptr) { delete this; - return NULL; + return nullptr; } } @@ -1665,7 +1673,7 @@ FxExpression *FxUnaryNotBitwise::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Integer type expected"); delete this; - return NULL; + return nullptr; } if (Operand->isConstant()) @@ -1804,13 +1812,13 @@ FxExpression *FxSizeAlign::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "cannot determine %s of a constant", Which == TK_AlignOf? "alignment" : "size"); delete this; - return NULL; + return nullptr; } else if (!Operand->RequestAddress(nullptr)) { ScriptPosition.Message(MSG_ERROR, "Operand must be addressable to determine %s", Which == TK_AlignOf ? "alignment" : "size"); delete this; - return NULL; + return nullptr; } else { @@ -2513,7 +2521,8 @@ FxAddSub::FxAddSub(int o, FxExpression *l, FxExpression *r) FxExpression *FxAddSub::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return NULL; + if (!ResolveLR(ctx, true)) + return nullptr; if (!IsNumeric() && !IsVector()) { @@ -2652,13 +2661,14 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return NULL; + if (!ResolveLR(ctx, true)) + return nullptr; if (!IsNumeric() && !IsVector()) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } else if (left->isConstant() && right->isConstant()) { @@ -2672,7 +2682,7 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Division by 0"); delete this; - return NULL; + return nullptr; } v = Operator == '*'? v1 * v2 : @@ -2693,7 +2703,7 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Division by 0"); delete this; - return NULL; + return nullptr; } v = Operator == '*'? v1 * v2 : @@ -2820,7 +2830,8 @@ FxExpression *FxPow::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return nullptr; + if (!ResolveLR(ctx, true)) + return nullptr; if (!IsNumeric()) { @@ -2879,13 +2890,14 @@ FxCompareRel::FxCompareRel(int o, FxExpression *l, FxExpression *r) FxExpression *FxCompareRel::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return NULL; + if (!ResolveLR(ctx, true)) + return nullptr; if (!IsNumeric()) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } else if (left->isConstant() && right->isConstant()) { @@ -3038,19 +3050,20 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return NULL; + if (!ResolveLR(ctx, true)) + return nullptr; if (!left || !right) { delete this; - return NULL; + return nullptr; } if (!IsNumeric() && !IsPointer() && !IsVector() && ValueType != TypeName) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } if (Operator == TK_ApproxEq && left->ValueType->GetRegType() != REGT_FLOAT && left->ValueType->GetRegType() != REGT_STRING) @@ -3174,7 +3187,8 @@ FxBinaryInt::FxBinaryInt(int o, FxExpression *l, FxExpression *r) FxExpression *FxBinaryInt::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, false)) return NULL; + if (!ResolveLR(ctx, false)) + return nullptr; if (IsFloat() && ctx.FromDecorate) { @@ -3189,10 +3203,10 @@ FxExpression *FxBinaryInt::Resolve(FCompileContext& ctx) right = new FxIntCast(right, ctx.FromDecorate); right = right->Resolve(ctx); } - if (left == NULL || right == NULL) + if (left == nullptr || right == nullptr) { delete this; - return NULL; + return nullptr; } ValueType = TypeSInt32; } @@ -3201,7 +3215,7 @@ FxExpression *FxBinaryInt::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Integer type expected"); delete this; - return NULL; + return nullptr; } else if (left->isConstant() && right->isConstant()) { @@ -3322,7 +3336,8 @@ FxLtGtEq::FxLtGtEq(FxExpression *l, FxExpression *r) FxExpression *FxLtGtEq::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (!ResolveLR(ctx, true)) return NULL; + if (!ResolveLR(ctx, true)) + return nullptr; if (!left->IsNumeric() || !right->IsNumeric()) { @@ -3467,14 +3482,14 @@ FxExpression *FxBinaryLogical::Resolve(FCompileContext& ctx) else if (b_left==1) { FxExpression *x = right; - right=NULL; + right=nullptr; delete this; return x; } else if (b_right==1) { FxExpression *x = left; - left=NULL; + left=nullptr; delete this; return x; } @@ -3496,14 +3511,14 @@ FxExpression *FxBinaryLogical::Resolve(FCompileContext& ctx) else if (b_left==0) { FxExpression *x = right; - right=NULL; + right=nullptr; delete this; return x; } else if (b_right==0) { FxExpression *x = left; - left=NULL; + left=nullptr; delete this; return x; } @@ -3723,7 +3738,7 @@ ExpEmit FxTypeCheck::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinTypeCheck, BuiltinTypeCheck); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); auto callfunc = ((PSymbolVMFunction *)sym)->Function; int opcode = (EmitTail ? OP_TAIL_K : OP_CALL_K); @@ -3813,7 +3828,7 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) FxExpression *e = result? truex:falsex; delete (result? falsex:truex); - falsex = truex = NULL; + falsex = truex = nullptr; delete this; return e; } @@ -3867,9 +3882,22 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) ExpEmit trueop = truex->Emit(build); if (trueop.Konst) { - assert(trueop.RegType == REGT_FLOAT); - out = ExpEmit(build, REGT_FLOAT); - build->Emit(OP_LKF, out.RegNum, trueop.RegNum); + if (trueop.RegType == REGT_FLOAT) + { + out = ExpEmit(build, REGT_FLOAT); + build->Emit(OP_LKF, out.RegNum, trueop.RegNum); + } + else if (trueop.RegType == REGT_POINTER) + { + out = ExpEmit(build, REGT_POINTER); + build->Emit(OP_LKP, out.RegNum, trueop.RegNum); + } + else + { + assert(trueop.RegType == REGT_STRING); + out = ExpEmit(build, REGT_STRING); + build->Emit(OP_LKS, out.RegNum, trueop.RegNum); + } } else { @@ -3892,8 +3920,22 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) ExpEmit falseop = falsex->Emit(build); if (falseop.Konst) { - assert(falseop.RegType == REGT_FLOAT); - build->Emit(OP_LKF, out.RegNum, falseop.RegNum); + if (falseop.RegType == REGT_FLOAT) + { + out = ExpEmit(build, REGT_FLOAT); + build->Emit(OP_LKF, out.RegNum, falseop.RegNum); + } + else if (falseop.RegType == REGT_POINTER) + { + out = ExpEmit(build, REGT_POINTER); + build->Emit(OP_LKP, out.RegNum, falseop.RegNum); + } + else + { + assert(falseop.RegType == REGT_STRING); + out = ExpEmit(build, REGT_STRING); + build->Emit(OP_LKS, out.RegNum, falseop.RegNum); + } } else { @@ -3901,17 +3943,7 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) // returned by "true" so that only one register is returned by // this tree. falseop.Free(build); - if (falseop.RegType == REGT_INT) - { - build->Emit(OP_MOVE, out.RegNum, falseop.RegNum, 0); - } - else - { - assert(falseop.RegType == REGT_FLOAT); - assert(falseop.RegCount == out.RegCount); - static int flops[] = { OP_MOVEF, OP_MOVEV2, OP_MOVEV3 }; - build->Emit(flops[falseop.RegNum], out.RegNum, falseop.RegNum, 0); - } + build->Emit(falsex->ValueType->GetMoveOp(), out.RegNum, falseop.RegNum, 0); } } build->BackpatchToHere(truejump); @@ -3958,7 +3990,7 @@ FxExpression *FxAbs::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Numeric type expected"); delete this; - return NULL; + return nullptr; } else if (val->isConstant()) { @@ -3976,7 +4008,7 @@ FxExpression *FxAbs::Resolve(FCompileContext &ctx) default: // shouldn't happen delete this; - return NULL; + return nullptr; } FxExpression *x = new FxConstant(value, ScriptPosition); delete this; @@ -4047,7 +4079,7 @@ FxExpression *FxATan2::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "numeric value expected for parameter"); delete this; - return NULL; + return nullptr; } if (yval->isConstant() && xval->isConstant()) { @@ -4151,7 +4183,7 @@ FxExpression *FxMinMax::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Arguments must be of type int or float"); delete this; - return NULL; + return nullptr; } } if (floatcount != 0) @@ -4230,7 +4262,7 @@ FxExpression *FxMinMax::Resolve(FCompileContext &ctx) } } delete choices[j]; - choices[j] = NULL; + choices[j] = nullptr; choices.Delete(j); } } @@ -4329,12 +4361,12 @@ FxRandom::FxRandom(FRandom * r, FxExpression *mi, FxExpression *ma, const FScrip : FxExpression(EFX_Random, pos) { EmitTail = false; - if (mi != NULL && ma != NULL) + if (mi != nullptr && ma != nullptr) { min = new FxIntCast(mi, nowarn); max = new FxIntCast(ma, nowarn); } - else min = max = NULL; + else min = max = nullptr; rng = r; ValueType = TypeSInt32; } @@ -4424,13 +4456,13 @@ ExpEmit FxRandom::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinRandom, BuiltinRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; int opcode = (EmitTail ? OP_TAIL_K : OP_CALL_K); build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, build->GetConstantAddress(rng, ATAG_RNG)); - if (min != NULL && max != NULL) + if (min != nullptr && max != nullptr) { EmitParameter(build, min, ScriptPosition); EmitParameter(build, max, ScriptPosition); @@ -4545,7 +4577,7 @@ ExpEmit FxRandomPick::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinRandom, BuiltinRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, build->GetConstantAddress(rng, ATAG_RNG)); @@ -4623,9 +4655,9 @@ ExpEmit FxRandomPick::Emit(VMFunctionBuilder *build) // //========================================================================== FxFRandom::FxFRandom(FRandom *r, FxExpression *mi, FxExpression *ma, const FScriptPosition &pos) -: FxRandom(r, NULL, NULL, pos, true) +: FxRandom(r, nullptr, nullptr, pos, true) { - if (mi != NULL && ma != NULL) + if (mi != nullptr && ma != nullptr) { min = new FxFloatCast(mi); max = new FxFloatCast(ma); @@ -4670,13 +4702,13 @@ ExpEmit FxFRandom::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinFRandom, BuiltinFRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; int opcode = (EmitTail ? OP_TAIL_K : OP_CALL_K); build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, build->GetConstantAddress(rng, ATAG_RNG)); - if (min != NULL && max != NULL) + if (min != nullptr && max != nullptr) { EmitParameter(build, min, ScriptPosition); EmitParameter(build, max, ScriptPosition); @@ -4764,7 +4796,7 @@ ExpEmit FxRandom2::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinRandom, BuiltinRandom); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; int opcode = (EmitTail ? OP_TAIL_K : OP_CALL_K); @@ -4896,7 +4928,7 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } // now check the global identifiers. - else if ((sym = ctx.FindGlobal(Identifier)) != NULL) + else if ((sym = ctx.FindGlobal(Identifier)) != nullptr) { if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) { @@ -4910,7 +4942,7 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } // and line specials - else if ((num = P_FindLineSpecial(Identifier, NULL, NULL))) + else if ((num = P_FindLineSpecial(Identifier, nullptr, nullptr))) { ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as line special %d\n", Identifier.GetChars(), num); newex = new FxConstant(num, ScriptPosition); @@ -5355,25 +5387,25 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) // DECORATE allows floats here so cast them to int. index = new FxIntCast(index, ctx.FromDecorate); index = index->Resolve(ctx); - if (index == NULL) + if (index == nullptr) { delete this; - return NULL; + return nullptr; } } if (index->ValueType->GetRegType() != REGT_INT && index->ValueType != TypeName) { ScriptPosition.Message(MSG_ERROR, "Array index must be integer"); delete this; - return NULL; + return nullptr; } PArray *arraytype = dyn_cast(Array->ValueType); - if (arraytype == NULL) + if (arraytype == nullptr) { ScriptPosition.Message(MSG_ERROR, "'[]' can only be used with arrays."); delete this; - return NULL; + return nullptr; } if (index->isConstant()) { @@ -5382,7 +5414,7 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Array index out of bounds"); delete this; - return NULL; + return nullptr; } } @@ -5392,13 +5424,13 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) // int arrays only for now ScriptPosition.Message(MSG_ERROR, "Only numeric arrays are supported."); delete this; - return NULL; + return nullptr; } if (!Array->RequestAddress(&AddressWritable)) { ScriptPosition.Message(MSG_ERROR, "Unable to dereference array."); delete this; - return NULL; + return nullptr; } return this; } @@ -5901,12 +5933,12 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) bool failed = false; SAFE_RESOLVE_OPT(Self, ctx); - if (ArgList != NULL) + if (ArgList != nullptr) { for (unsigned i = 0; i < ArgList->Size(); i++) { (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); - if ((*ArgList)[i] == NULL) + if ((*ArgList)[i] == nullptr) { failed = true; } @@ -5934,7 +5966,7 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) if (failed) { delete this; - return NULL; + return nullptr; } } ValueType = TypeSInt32; @@ -5959,7 +5991,7 @@ int BuiltinCallLineSpecial(VMFrameStack *stack, VMValue *param, TArray { v[i - 2] = param[i].i; } - ACTION_RETURN_INT(P_ExecuteSpecial(param[0].i, NULL, reinterpret_cast(param[1].a), false, v[0], v[1], v[2], v[3], v[4])); + ACTION_RETURN_INT(P_ExecuteSpecial(param[0].i, nullptr, reinterpret_cast(param[1].a), false, v[0], v[1], v[2], v[3], v[4])); } ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) @@ -5970,7 +6002,7 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) // fixme: This really should use the Self pointer that got passed to this class instead of just using the first argument from the function. // Once static functions are possible, or specials can be called through a member access operator this won't work anymore. build->Emit(OP_PARAM, 0, REGT_POINTER, 0); // pass self - if (ArgList != NULL) + if (ArgList != nullptr) { for (; i < ArgList->Size(); ++i) { @@ -6002,7 +6034,7 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinCallLineSpecial, BuiltinCallLineSpecial); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; if (EmitTail) @@ -6144,7 +6176,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) if (failed) { delete this; - return NULL; + return nullptr; } TArray &rets = proto->ReturnTypes; if (rets.Size() > 0) @@ -6207,7 +6239,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } } // Emit code to pass explicit parameters - if (ArgList != NULL) + if (ArgList != nullptr) { for (unsigned i = 0; i < ArgList->Size(); ++i) { @@ -6311,25 +6343,25 @@ FxExpression *FxFlopFunctionCall::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (ArgList == NULL || ArgList->Size() != 1) + if (ArgList == nullptr || ArgList->Size() != 1) { ScriptPosition.Message(MSG_ERROR, "%s only has one parameter", FName(FxFlops[Index].Name).GetChars()); delete this; - return NULL; + return nullptr; } (*ArgList)[0] = (*ArgList)[0]->Resolve(ctx); - if ((*ArgList)[0] == NULL) + if ((*ArgList)[0] == nullptr) { delete this; - return NULL; + return nullptr; } if (!(*ArgList)[0]->IsNumeric()) { ScriptPosition.Message(MSG_ERROR, "numeric value expected for parameter"); delete this; - return NULL; + return nullptr; } if ((*ArgList)[0]->isConstant()) { @@ -6417,7 +6449,7 @@ FxExpression *FxSequence::Resolve(FCompileContext &ctx) CHECKRESOLVED(); for (unsigned i = 0; i < Expressions.Size(); ++i) { - if (NULL == (Expressions[i] = Expressions[i]->Resolve(ctx))) + if (nullptr == (Expressions[i] = Expressions[i]->Resolve(ctx))) { delete this; return nullptr; @@ -6455,7 +6487,7 @@ VMFunction *FxSequence::GetDirectFunction() { return Expressions[0]->GetDirectFunction(); } - return NULL; + return nullptr; } //========================================================================== @@ -6792,7 +6824,7 @@ FxIfStatement::FxIfStatement(FxExpression *cond, FxExpression *true_part, WhenFalse = false_part; if (WhenTrue != nullptr) WhenTrue->NeedResult = false; if (WhenFalse != nullptr) WhenFalse->NeedResult = false; - assert(cond != NULL); + assert(cond != nullptr); } FxIfStatement::~FxIfStatement() @@ -6840,8 +6872,8 @@ FxExpression *FxIfStatement::Resolve(FCompileContext &ctx) FxExpression *e = result ? WhenTrue : WhenFalse; delete (result ? WhenFalse : WhenTrue); - WhenTrue = WhenFalse = NULL; - if (e == NULL) e = new FxNop(ScriptPosition); // create a dummy if this statement gets completely removed by optimizing out the constant parts. + WhenTrue = WhenFalse = nullptr; + if (e == nullptr) e = new FxNop(ScriptPosition); // create a dummy if this statement gets completely removed by optimizing out the constant parts. delete this; return e; } @@ -6861,7 +6893,7 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) ExpEmit cond = Condition->Emit(build); assert(cond.RegType != REGT_STRING && !cond.Konst); - if (WhenTrue != NULL) + if (WhenTrue != nullptr) { path1 = WhenTrue; path2 = WhenFalse; @@ -6871,9 +6903,9 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) { // When there is only a false path, reverse the condition so we can // treat it as a true path. - assert(WhenFalse != NULL); + assert(WhenFalse != nullptr); path1 = WhenFalse; - path2 = NULL; + path2 = nullptr; condcheck = 0; } @@ -6900,7 +6932,7 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) // Evaluate first path v = path1->Emit(build); v.Free(build); - if (path2 != NULL) + if (path2 != nullptr) { size_t path1jump = build->Emit(OP_JMP, 0); // Evaluate second path @@ -7412,18 +7444,18 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "Cannot convert %s to class type", basex->ValueType->DescriptiveName()); delete this; - return NULL; + return nullptr; } if (basex->isConstant()) { FName clsname = static_cast(basex)->GetValue().GetName(); - PClass *cls = NULL; + PClass *cls = nullptr; if (clsname != NAME_None) { cls = PClass::FindClass(clsname); - if (cls == NULL) + if (cls == nullptr) { /* lax */ // Since this happens in released WADs it must pass without a terminal error... :( @@ -7437,7 +7469,7 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) { ScriptPosition.Message(MSG_ERROR, "class '%s' is not compatible with '%s'", clsname.GetChars(), desttype->TypeName.GetChars()); delete this; - return NULL; + return nullptr; } ScriptPosition.Message(MSG_DEBUG, "resolving '%s' as class name", clsname.GetChars()); } @@ -7474,7 +7506,7 @@ int BuiltinNameToClass(VMFrameStack *stack, VMValue *param, TArray &def if (!cls->IsDescendantOf(desttype)) { Printf("class '%s' is not compatible with '%s'", clsname.GetChars(), desttype->TypeName.GetChars()); - cls = NULL; + cls = nullptr; } ret->SetPointer(const_cast(cls), ATAG_OBJECT); return 1; @@ -7484,7 +7516,7 @@ ExpEmit FxClassTypeCast::Emit(VMFunctionBuilder *build) { if (basex->ValueType != TypeName) { - return ExpEmit(build->GetConstantAddress(NULL, ATAG_OBJECT), REGT_POINTER, true); + return ExpEmit(build->GetConstantAddress(nullptr, ATAG_OBJECT), REGT_POINTER, true); } ExpEmit clsname = basex->Emit(build); assert(!clsname.Konst); @@ -7497,7 +7529,7 @@ ExpEmit FxClassTypeCast::Emit(VMFunctionBuilder *build) PSymbol *sym = FindBuiltinFunction(NAME_BuiltinNameToClass, BuiltinNameToClass); assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), 2, 1); @@ -7526,7 +7558,7 @@ FxExpression *FxStateByIndex::Resolve(FCompileContext &ctx) ScriptPosition.Message(MSG_ERROR, "%s: Attempt to jump to non existing state index %d", ctx.Class->TypeName.GetChars(), index); delete this; - return NULL; + return nullptr; } FxExpression *x = new FxConstant(aclass->OwnedStates + index, ScriptPosition); delete this; @@ -7677,7 +7709,7 @@ FxMultiNameState::FxMultiNameState(const char *_statestring, const FScriptPositi } names = MakeStateNameList(statestring); names.Insert(0, scopename); - scope = NULL; + scope = nullptr; } //========================================================================== @@ -7693,7 +7725,7 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) if (names[0] == NAME_None) { - scope = NULL; + scope = nullptr; } else if (names[0] == NAME_Super) { @@ -7702,27 +7734,27 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) else { scope = PClass::FindActor(names[0]); - if (scope == NULL) + if (scope == nullptr) { ScriptPosition.Message(MSG_ERROR, "Unknown class '%s' in state label", names[0].GetChars()); delete this; - return NULL; + return nullptr; } else if (!scope->IsAncestorOf(ctx.Class)) { ScriptPosition.Message(MSG_ERROR, "'%s' is not an ancestor of '%s'", names[0].GetChars(), ctx.Class->TypeName.GetChars()); delete this; - return NULL; + return nullptr; } } - if (scope != NULL) + if (scope != nullptr) { - FState *destination = NULL; + FState *destination = nullptr; // If the label is class specific we can resolve it right here if (names[1] != NAME_None) { destination = scope->FindState(names.Size()-1, &names[1], false); - if (destination == NULL) + if (destination == nullptr) { ScriptPosition.Message(MSG_OPTERROR, "Unknown state jump destination"); /* lax */ @@ -7749,7 +7781,7 @@ static int DoFindState(VMFrameStack *stack, VMValue *param, int numparam, VMRetu { PARAM_OBJECT_AT(0, self, AActor); FState *state = self->GetClass()->FindState(numparam - 1, names); - if (state == NULL) + if (state == nullptr) { const char *dot = ""; Printf("Jump target '"); @@ -7822,7 +7854,7 @@ ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) } assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != NULL); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), names.Size() + 1, 1); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index f071614a8..6c47fabe0 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -671,7 +671,7 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_Score, TypeSInt32, VARF_Native, myoffsetof(AActor, Score))); symt.AddSymbol(new PField(NAME_Accuracy, TypeSInt32, VARF_Native, myoffsetof(AActor, accuracy))); symt.AddSymbol(new PField(NAME_Stamina, TypeSInt32, VARF_Native, myoffsetof(AActor, stamina))); - symt.AddSymbol(new PField(NAME_Height, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, Height))); + symt.AddSymbol(new PField(NAME_Height, TypeFloat64, VARF_Native, myoffsetof(AActor, Height))); symt.AddSymbol(new PField(NAME_Radius, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, radius))); symt.AddSymbol(new PField(NAME_ReactionTime, TypeSInt32, VARF_Native, myoffsetof(AActor, reactiontime))); symt.AddSymbol(new PField(NAME_MeleeRange, TypeFloat64, VARF_Native, myoffsetof(AActor, meleerange))); @@ -698,6 +698,7 @@ void InitThingdef() symt.AddSymbol(new PField("Pos", TypeVector3, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos))); symt.AddSymbol(new PField("Vel", TypeVector3, VARF_Native, myoffsetof(AActor, Vel))); symt.AddSymbol(new PField("Scale", TypeVector2, VARF_Native, myoffsetof(AActor, Scale))); + symt.AddSymbol(new PField("CurState", TypeState, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, state))); // has to be renamed on the script side because it clashes with the same named type. symt.AddSymbol(new PField("SeeState", TypeState, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, SeeState))); symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 78a448f7c..9e8b84163 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1490,6 +1490,7 @@ PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt) } return type; } + Error(type, "Unable to resolve %s as type.", FName(type->UserType->Id).GetChars()); return TypeError; } @@ -2186,8 +2187,8 @@ static bool CheckRandom(ZCC_Expression *duration) FxExpression *ZCCCompiler::SetupActionFunction(PClass *cls, ZCC_TreeNode *af) { // We have 3 cases to consider here: - // 1. An action function without parameters. This can be called directly - // 2. An action functon with parameters or a non-action function. This needs to be wrapped into a helper function to set everything up. + // 1. A function without parameters. This can be called directly + // 2. A functon with parameters. This needs to be wrapped into a helper function to set everything up. // 3. An anonymous function. // 1. and 2. are exposed through AST_ExprFunctionCall @@ -2236,9 +2237,10 @@ void ZCCCompiler::CompileStates() { for (auto c : Classes) { + if (!c->Type()->IsDescendantOf(RUNTIME_CLASS(AActor))) { - Error(c->cls, "%s: States can only be defined for actors.", c->Type()->TypeName.GetChars()); + if (c->States.Size()) Error(c->cls, "%s: States can only be defined for actors.", c->Type()->TypeName.GetChars()); continue; } FString statename; // The state builder wants the label as one complete string, not separated into tokens. diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 6de64d07e..8ea4bb114 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -1,3 +1,4 @@ +zscript/base.txt zscript/constants.txt zscript/actor.txt diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 18f0facd0..4fc18d75d 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -53,9 +53,13 @@ class Actor : Thinker native return GetPointer(ptr_select1) == GetPointer(ptr_select2); } + native static bool isDehState(state st); native void SetOrigin(vector3 newpos, bool moving); + native void SetXYZ(vector3 newpos); native Actor GetPointer(int aaptr); + native static Actor Spawn(class type, vector3 pos = (0,0,0), int replace = NO_REPLACE); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); + native Actor OldSpawnMissile(Actor dest, class type, Actor owner = null); native void TraceBleed(int damage, Actor missile); native bool CheckMeleeRange(); native int DamageMobj(Actor inflictor, Actor source, int damage, Name mod, int flags = 0, double angle = 0); @@ -228,7 +232,6 @@ class Actor : Thinker native native void A_SpawnFly(class spawntype = null); // needs special treatment for default native void A_BrainExplode(); native void A_Detonate(); - native void A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); native void A_SetFloorClip(); diff --git a/wadsrc/static/zscript/base.txt b/wadsrc/static/zscript/base.txt new file mode 100644 index 000000000..bda63f059 --- /dev/null +++ b/wadsrc/static/zscript/base.txt @@ -0,0 +1,8 @@ +class Object native +{ + /*virtual*/ native void Destroy(); +} + +class Thinker : Object native +{ +} \ No newline at end of file diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index b14634e0d..5cbbbaf9e 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -876,3 +876,9 @@ enum EDmgFlags DMG_NO_PROTECT = 256, DMG_USEANGLE = 512, } + +enum EReplace +{ + NO_REPLACE = 0, + ALLOW_REPLACE = 1 +} diff --git a/wadsrc/static/zscript/doom/fatso.txt b/wadsrc/static/zscript/doom/fatso.txt index c477cbb44..d1a456d16 100644 --- a/wadsrc/static/zscript/doom/fatso.txt +++ b/wadsrc/static/zscript/doom/fatso.txt @@ -110,6 +110,12 @@ extend class Actor A_PlaySound("fatso/raiseguns", CHAN_WEAPON); } + // + // Mancubus attack, + // firing three missiles in three different directions? + // Doesn't look like it. + // + void A_FatAttack1(class spawntype = "FatShot") { if (target) @@ -163,5 +169,54 @@ extend class Actor } } } + + // + // killough 9/98: a mushroom explosion effect, sorta :) + // Original idea: Linguica + // + + void A_Mushroom(class spawntype = "FatShot", int numspawns = 0, int flags = 0, float vrange = 4.0, float hrange = 0.5) + { + int i, j; + + if (numspawns == 0) + { + numspawns = GetMissileDamage(0, 1); + } + + A_Explode(128, 128, (flags & MSF_DontHurt) ? 0 : XF_HURTSOURCE); + + // Now launch mushroom cloud + Actor aimtarget = Spawn("Mapspot", pos, NO_REPLACE); // We need something to aim at. + Actor owner = (flags & MSF_DontHurt) ? target : self; + aimtarget.Height = Height; + + bool shootmode = ((flags & MSF_Classic) || // Flag explicitely set, or no flags and compat options + (flags == 0 && isDehState(CurState) && GetCVar("compat_mushroom"))); + + for (i = -numspawns; i <= numspawns; i += 8) + { + for (j = -numspawns; j <= numspawns; j += 8) + { + Actor mo; + aimtarget.SetXYZ(pos + (i, j, (i, j).Length() * vrange)); // Aim up fairly high + if (shootmode) + { // Use old function for MBF compatibility + mo = OldSpawnMissile(aimtarget, spawntype, owner); + } + else // Use normal function + { + mo = SpawnMissile(aimtarget, spawntype, owner); + } + if (mo) + { // Slow it down a bit + mo.Vel *= hrange; + mo.bNoGravity = false; // Make debris fall under gravity + } + } + } + aimtarget.Destroy(); + } + } From a652c5f259426bbc09c08f50657029a4f91fb9ae Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 30 Oct 2016 16:21:44 +0100 Subject: [PATCH 146/255] - fixed: For named functions the prototype needs to be set before the code generator starts resolving. Otherwise it will crash on incompletely set up forward declarations. --- src/scripting/vm/vmbuilder.cpp | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-) diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index e9ac38a78..afadaaa1e 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -673,6 +673,13 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c it.Function->ImplicitArgs = functype->GetImplicitArgs(); it.Proto = nullptr; it.FromDecorate = fromdecorate; + + // set prototype for named functions. + if (it.Func->SymbolName != NAME_None) + { + it.Function->Proto = it.Func->Variants[0].Proto; + } + mItems.Push(it); return it.Function; } @@ -714,10 +721,13 @@ void FFunctionBuildList::Build() { assert(item.Proto != nullptr); - // Generate prototype for this anonymous function + // Generate prototype for anonymous functions. VMScriptFunction *sfunc = item.Function; // create a new prototype from the now known return type and the argument list of the function's template prototype. - sfunc->Proto = NewPrototype(item.Proto->ReturnTypes, item.Func->Variants[0].Proto->ArgumentTypes); + if (sfunc->Proto == nullptr) + { + sfunc->Proto = NewPrototype(item.Proto->ReturnTypes, item.Func->Variants[0].Proto->ArgumentTypes); + } // Emit code item.Code->Emit(&buildit); From 2857fac3386194d45959faabdbe66dd194cd621a Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 30 Oct 2016 18:41:39 +0100 Subject: [PATCH 147/255] - scriptified a_archvile.cpp. - fixed the type checks for the conditional operator. --- src/CMakeLists.txt | 1 - src/g_doom/a_archvile.cpp | 160 ----------------------- src/g_doom/a_doommisc.cpp | 1 - src/p_actionfunctions.cpp | 3 +- src/p_mobj.cpp | 10 ++ src/scripting/codegeneration/codegen.cpp | 3 +- src/scripting/vm/vm.h | 15 +++ wadsrc/static/zscript/actor.txt | 7 +- wadsrc/static/zscript/constants.txt | 3 +- wadsrc/static/zscript/doom/archvile.txt | 88 +++++++++++++ 10 files changed, 120 insertions(+), 171 deletions(-) delete mode 100644 src/g_doom/a_archvile.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index f96bf7d36..12df2e61c 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -835,7 +835,6 @@ set( NOT_COMPILED_SOURCE_FILES ${OTHER_SYSTEM_SOURCES} sc_man_scanner.h sc_man_scanner.re - g_doom/a_archvile.cpp g_doom/a_bossbrain.cpp g_doom/a_doomweaps.cpp g_doom/a_keen.cpp diff --git a/src/g_doom/a_archvile.cpp b/src/g_doom/a_archvile.cpp deleted file mode 100644 index 959c5763d..000000000 --- a/src/g_doom/a_archvile.cpp +++ /dev/null @@ -1,160 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "p_local.h" -#include "s_sound.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -*/ - -// -// PIT_VileCheck -// Detect a corpse that could be raised. -// -void A_Fire(AActor *self, double height); - - -// -// A_VileStart -// -DEFINE_ACTION_FUNCTION(AActor, A_VileStart) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_VOICE, "vile/start", 1, ATTN_NORM); - return 0; -} - - -// -// A_Fire -// Keep fire in front of player unless out of sight -// -DEFINE_ACTION_FUNCTION(AActor, A_StartFire) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_BODY, "vile/firestrt", 1, ATTN_NORM); - A_Fire (self, 0); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_FireCrackle) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_BODY, "vile/firecrkl", 1, ATTN_NORM); - A_Fire (self, 0); - return 0; -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Fire) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_DEF(height); - - A_Fire(self, height); - return 0; -} - -void A_Fire(AActor *self, double height) -{ - AActor *dest; - - dest = self->tracer; - if (dest == NULL || self->target == NULL) - return; - - // don't move it if the vile lost sight - if (!P_CheckSight (self->target, dest, 0) ) - return; - - DVector3 newpos = dest->Vec3Angle(24., dest->Angles.Yaw, height); - self->SetOrigin(newpos, true); -} - - - -// -// A_VileTarget -// Spawn the hellfire -// -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileTarget) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_DEF(fire, AActor); - - AActor *fog; - - if (!self->target) - return 0; - - A_FaceTarget (self); - - fog = Spawn (fire, self->target->Pos(), ALLOW_REPLACE); - - self->tracer = fog; - fog->target = self; - fog->tracer = self->target; - A_Fire(fog, 0); - return 0; -} - - - - -// -// A_VileAttack -// - -// A_VileAttack flags -#define VAF_DMGTYPEAPPLYTODIRECT 1 - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_SOUND_DEF (snd) - PARAM_INT_DEF (dmg) - PARAM_INT_DEF (blastdmg) - PARAM_INT_DEF (blastrad) - PARAM_FLOAT_DEF (thrust) - PARAM_NAME_DEF (dmgtype) - PARAM_INT_DEF (flags) - - AActor *fire, *target; - - if (NULL == (target = self->target)) - return 0; - - A_FaceTarget (self); - - if (!P_CheckSight (self, target, 0) ) - return 0; - - S_Sound (self, CHAN_WEAPON, snd, 1, ATTN_NORM); - - int newdam; - - if (flags & VAF_DMGTYPEAPPLYTODIRECT) - newdam = P_DamageMobj (target, self, self, dmg, dmgtype); - - else - newdam = P_DamageMobj (target, self, self, dmg, NAME_None); - - P_TraceBleed (newdam > 0 ? newdam : dmg, target); - - fire = self->tracer; - - if (fire != NULL) - { - // move the fire between the vile and the player - DVector3 pos = target->Vec3Angle(-24., self->Angles.Yaw, 0); - fire->SetOrigin (pos, true); - - P_RadiusAttack (fire, self, blastdmg, blastrad, dmgtype, 0); - } - if (!(target->flags7 & MF7_DONTTHRUST)) - { - target->Vel.Z = thrust * 1000 / MAX(1, target->Mass); - } - return 0; -} diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 29e2fc8ee..31ee228f8 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -22,7 +22,6 @@ #include "vm.h" // Include all the other Doom stuff here to reduce compile time -#include "a_archvile.cpp" #include "a_bossbrain.cpp" #include "a_doomweaps.cpp" #include "a_keen.cpp" diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 9f3a088d6..4748b1708 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -1362,6 +1362,7 @@ enum XF_HURTSOURCE = 1, XF_NOTMISSILE = 4, XF_NOACTORTYPE = 1 << 3, + XF_NOSPLASH = 16, }; DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Explode) @@ -1412,7 +1413,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Explode) if (flags & XF_NOTMISSILE) pflags |= RADF_SOURCEISSPOT; int count = P_RadiusAttack (self, self->target, damage, distance, damagetype, pflags, fulldmgdistance); - P_CheckSplash(self, distance); + if (!(flags & XF_NOSPLASH)) P_CheckSplash(self, distance); if (alert && self->target != NULL && self->target->player != NULL) { P_NoiseAlert(self->target, self); diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 3fd1be9a1..26987e622 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6647,6 +6647,16 @@ DEFINE_ACTION_FUNCTION(AActor, SetXYZ) return 0; } +DEFINE_ACTION_FUNCTION(AActor, Vec3Angle) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(length) + PARAM_ANGLE(angle); + PARAM_FLOAT(z); + PARAM_BOOL_DEF(absolute); + ACTION_RETURN_VEC3(self->Vec3Angle(length, angle, z, absolute)); +} + //---------------------------------------------------------------------------- // // DropItem handling diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4fa6da73e..66a7d8b41 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -345,6 +345,7 @@ static int EncodeRegType(ExpEmit reg) else if (reg.RegCount == 2) { regtype |= REGT_MULTIREG2; + } else if (reg.RegCount == 3) { @@ -3808,7 +3809,7 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) ValueType = TypeVoid; //else if (truex->ValueType != falsex->ValueType) - if ((!IsNumeric() && !IsPointer() && !IsVector()) || ValueType == TypeVoid) + if (ValueType->GetRegType() == REGT_NIL) { ScriptPosition.Message(MSG_ERROR, "Incompatible types for ?: operator"); delete this; diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 4109d4e79..ca7aa6d54 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -4,6 +4,7 @@ #include "zstring.h" #include "dobject.h" #include "autosegs.h" +#include "vectors.h" #define MAX_RETURNS 8 // Maximum number of results a function called by script code can return #define MAX_TRY_DEPTH 8 // Maximum number of nested TRYs in a single function @@ -296,12 +297,25 @@ struct VMReturn ((double *)Location)[1] = val[1]; ((double *)Location)[2] = val[2]; } + void SetVector(const DVector3 &val) + { + assert(RegType == (REGT_FLOAT | REGT_MULTIREG3)); + ((double *)Location)[0] = val[0]; + ((double *)Location)[1] = val[1]; + ((double *)Location)[2] = val[2]; + } void SetVector2(const double val[2]) { assert(RegType == (REGT_FLOAT|REGT_MULTIREG2)); ((double *)Location)[0] = val[0]; ((double *)Location)[1] = val[1]; } + void SetVector2(const DVector2 &val) + { + assert(RegType == (REGT_FLOAT | REGT_MULTIREG2)); + ((double *)Location)[0] = val[0]; + ((double *)Location)[1] = val[1]; + } void SetString(const FString &val) { assert(RegType == REGT_STRING); @@ -1029,6 +1043,7 @@ struct AFuncDesc #define ACTION_RETURN_STATE(v) do { FState *state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_STATE); return 1; } return 0; } while(0) #define ACTION_RETURN_OBJECT(v) do { auto state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_OBJECT); return 1; } return 0; } while(0) #define ACTION_RETURN_FLOAT(v) do { double u = v; if (numret > 0) { assert(ret != nullptr); ret->SetFloat(u); return 1; } return 0; } while(0) +#define ACTION_RETURN_VEC3(v) do { DVector3 u = v; if (numret > 0) { assert(ret != nullptr); ret[0].SetVector(u); return 1; } return 0; } while(0) #define ACTION_RETURN_INT(v) do { int u = v; if (numret > 0) { assert(ret != NULL); ret->SetInt(u); return 1; } return 0; } while(0) #define ACTION_RETURN_BOOL(v) ACTION_RETURN_INT(v) diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 4fc18d75d..83ea76cb7 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -70,6 +70,7 @@ class Actor : Thinker native native bool SetState(state st, bool nofunction = false); native void LinkToWorld(); native void UnlinkFromWorld(); + native vector3 Vec3Angle(float length, float angle, float z = 0, bool absolute = false); native void VelFromAngle(float speed = 0, float angle = 0); native bool isFriend(Actor other); @@ -209,12 +210,6 @@ class Actor : Thinker native native void A_Chase(state melee = null, state missile = null, int flags = 0); native void A_Scream(); native void A_VileChase(); - native void A_VileStart(); - native void A_VileTarget(class fire = "ArchvileFire"); - native void A_VileAttack(sound snd = "vile/stop", int initialdmg = 20, int blastdmg = 70, int blastradius = 70, float thrustfac = 1.0, name damagetype = "Fire", int flags = 0); - native void A_StartFire(); - native void A_Fire(float spawnheight = 0); - native void A_FireCrackle(); native void A_Tracer(); native void A_SkelWhoosh(); native void A_SkelFist(); diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 5cbbbaf9e..9562e3f40 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -243,7 +243,8 @@ enum EExplodeFlags { XF_HURTSOURCE = 1, XF_NOTMISSILE = 4, - XF_EXPLICITDAMAGETYPE = 1 << 3, + XF_EXPLICITDAMAGETYPE = 8, + XF_NOSPLASH = 16, }; // Flags for A_RadiusThrust diff --git a/wadsrc/static/zscript/doom/archvile.txt b/wadsrc/static/zscript/doom/archvile.txt index bdca2b05f..0e9008570 100644 --- a/wadsrc/static/zscript/doom/archvile.txt +++ b/wadsrc/static/zscript/doom/archvile.txt @@ -87,3 +87,91 @@ class ArchvileFire : Actor } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +// A_VileAttack flags +//#define VAF_DMGTYPEAPPLYTODIRECT 1 + +extend class Actor +{ + + void A_VileStart() + { + A_PlaySound ("vile/start", CHAN_VOICE); + } + + // + // A_VileTarget + // Spawn the hellfire + // + void A_VileTarget(class fire = "ArchvileFire") + { + if (target) + { + A_FaceTarget (); + + Actor fog = Spawn (fire, target.Pos, ALLOW_REPLACE); + tracer = fog; + fog.target = self; + fog.tracer = self.target; + fog.A_Fire(0); + } + } + + void A_VileAttack(sound snd = "vile/stop", int initialdmg = 20, int blastdmg = 70, int blastradius = 70, float thrust = 1.0, name damagetype = "Fire", int flags = 0) + { + if (target) + { + A_FaceTarget(); + if (!CheckSight(target, 0)) return; + A_PlaySound(snd, CHAN_WEAPON); + int newdam = target.DamageMobj (self, self, initialdmg, (flags & VAF_DMGTYPEAPPLYTODIRECT)? damagetype : 'none'); + + TraceBleed (newdam > 0 ? newdam : initialdmg, target); + + Actor fire = tracer; + if (fire) + { + // move the fire between the vile and the player + fire.SetOrigin(target.Vec3Angle(-24., angle, 0), true); + fire.A_Explode(blastdmg, blastradius, XF_NOSPLASH, false, 0, 0, 0, "BulletPuff", damagetype); + } + if (!target.bDontThrust) + { + target.Vel.z = thrust * 1000 / max(1, target.Mass); + } + } + } + + void A_StartFire() + { + A_PlaySound ("vile/firestrt", CHAN_BODY); + A_Fire(); + } + + // + // A_Fire + // Keep fire in front of player unless out of sight + // + void A_Fire(float spawnheight = 0) + { + Actor dest = tracer; + if (!dest || !target) return; + + // don't move it if the vile lost sight + if (!target.CheckSight (dest, 0) ) return; + + SetOrigin(dest.Vec3Angle(24, dest.angle, height), true); + } + + void A_FireCrackle() + { + A_PlaySound ("vile/firecrkl", CHAN_BODY); + A_Fire(); + } +} From 6ff973a06bd97dfd1c2c5191b508fdbd98f62063 Mon Sep 17 00:00:00 2001 From: Marisa Heit Date: Sun, 30 Oct 2016 22:15:40 -0500 Subject: [PATCH 148/255] Modify CMPJMP to produce more compact code (as far as VC++ is concerned, anyway) --- src/scripting/vm/vmexec.cpp | 14 +++++++---- src/scripting/vm/vmexec.h | 46 ++++++++++++++++++------------------- 2 files changed, 33 insertions(+), 27 deletions(-) diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index 57ce48a95..af25030a9 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -82,11 +82,17 @@ #define THROW(x) throw(EVMAbortException(x)) #define CMPJMP(test) \ - if ((test) == (a & CMP_CHECK)) { \ + pc++; \ + if (VM_UBYTE(test) == VM_UBYTE(a)) { \ assert(pc[1].op == OP_JMP); \ - pc += 1 + JMPOFS(pc+1); \ - } else { \ - pc += 1; \ + pc += JMPOFS(pc); \ + } + +#define CMPJMP_MASK(test) \ + pc++; \ + if (VM_UBYTE(test) == (VM_UBYTE(a) & CMP_CHECK)) { \ + assert(pc[1].op == OP_JMP); \ + pc += JMPOFS(pc); \ } #define GETADDR(a,o,x) \ diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 4b16a99d1..10b85ef86 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1199,88 +1199,88 @@ begin: ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP(fabs(reg.f[C] - reg.f[B]) < VM_EPSILON); + CMPJMP_MASK(fabs(reg.f[C] - reg.f[B]) < VM_EPSILON); } else { - CMPJMP(reg.f[C] == reg.f[B]); + CMPJMP_MASK(reg.f[C] == reg.f[B]); } NEXTOP; OP(EQF_K): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP(fabs(konstf[C] - reg.f[B]) < VM_EPSILON); + CMPJMP_MASK(fabs(konstf[C] - reg.f[B]) < VM_EPSILON); } else { - CMPJMP(konstf[C] == reg.f[B]); + CMPJMP_MASK(konstf[C] == reg.f[B]); } NEXTOP; OP(LTF_RR): ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP((reg.f[B] - reg.f[C]) < -VM_EPSILON); + CMPJMP_MASK((reg.f[B] - reg.f[C]) < -VM_EPSILON); } else { - CMPJMP(reg.f[B] < reg.f[C]); + CMPJMP_MASK(reg.f[B] < reg.f[C]); } NEXTOP; OP(LTF_RK): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP((reg.f[B] - konstf[C]) < -VM_EPSILON); + CMPJMP_MASK((reg.f[B] - konstf[C]) < -VM_EPSILON); } else { - CMPJMP(reg.f[B] < konstf[C]); + CMPJMP_MASK(reg.f[B] < konstf[C]); } NEXTOP; OP(LTF_KR): ASSERTKF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP((konstf[B] - reg.f[C]) < -VM_EPSILON); + CMPJMP_MASK((konstf[B] - reg.f[C]) < -VM_EPSILON); } else { - CMPJMP(konstf[B] < reg.f[C]); + CMPJMP_MASK(konstf[B] < reg.f[C]); } NEXTOP; OP(LEF_RR): ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP((reg.f[B] - reg.f[C]) <= -VM_EPSILON); + CMPJMP_MASK((reg.f[B] - reg.f[C]) <= -VM_EPSILON); } else { - CMPJMP(reg.f[B] <= reg.f[C]); + CMPJMP_MASK(reg.f[B] <= reg.f[C]); } NEXTOP; OP(LEF_RK): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP((reg.f[B] - konstf[C]) <= -VM_EPSILON); + CMPJMP_MASK((reg.f[B] - konstf[C]) <= -VM_EPSILON); } else { - CMPJMP(reg.f[B] <= konstf[C]); + CMPJMP_MASK(reg.f[B] <= konstf[C]); } NEXTOP; OP(LEF_KR): ASSERTKF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP((konstf[B] - reg.f[C]) <= -VM_EPSILON); + CMPJMP_MASK((konstf[B] - reg.f[C]) <= -VM_EPSILON); } else { - CMPJMP(konstf[B] <= reg.f[C]); + CMPJMP_MASK(konstf[B] <= reg.f[C]); } NEXTOP; @@ -1369,12 +1369,12 @@ begin: Do_EQV2: if (a & CMP_APPROX) { - CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && - fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); + CMPJMP_MASK(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); } else { - CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); + CMPJMP_MASK(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); } NEXTOP; OP(EQV2_K): @@ -1496,13 +1496,13 @@ begin: Do_EQV3: if (a & CMP_APPROX) { - CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && - fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON && - fabs(reg.f[B+2] - fcp[2]) < VM_EPSILON); + CMPJMP_MASK(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON && + fabs(reg.f[B+2] - fcp[2]) < VM_EPSILON); } else { - CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); + CMPJMP_MASK(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); } NEXTOP; OP(EQV3_K): From e620c9bd7dc777fa733b4fbf0662506b17474807 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 31 Oct 2016 17:02:47 +0100 Subject: [PATCH 149/255] - scriptified parts of a_bossbrain.cpp. Some things cannot be done yet, the script code is there but commented out. - exported thinker iterator and drop item chain to scripting. Unlike its native counterpart the script-side iterator is wrapped into a DObject to allow proper handling for memory management. - fixed: The VMFunctionBuilder only distinguished between member and action functions but failed on static ones. - fixed: FxAssign did not add all needed type casts. Except for purely numeric types it will now wrap the expression in an FxTypeCast. Numeric handling remains unchanged for both performance reasons and not altering semantics for DECORATE. - exported all internal flags as variables to scripting. They still cannot be used in an actor definition. - make ATAG_STATE the same as ATAG_GENERIC. Since state pointers exist as actual variables they can take both values which on occasion can trigger some asserts. - gave PClass a bExported flag, so that scripts cannot see purely internal classes. Especially the types like PInt can cause problems. Todo: we need readonly references to safely expose the actor defaults. Right now some badly behaving code could overwrite them. --- src/d_dehacked.cpp | 2 +- src/dobjtype.cpp | 1 + src/dobjtype.h | 1 + src/dthinker.cpp | 38 +++ src/g_doom/a_bossbrain.cpp | 95 ------- src/p_mobj.cpp | 23 ++ src/scripting/codegeneration/codegen.cpp | 240 ++++++++++++++---- src/scripting/codegeneration/codegen.h | 25 +- src/scripting/thingdef_data.cpp | 51 +++- src/scripting/vm/vm.h | 2 +- src/scripting/vm/vmbuilder.cpp | 4 +- src/scripting/vm/vmbuilder.h | 6 +- src/scripting/vm/vmexec.h | 2 +- src/scripting/zscript/zcc_compile.cpp | 1 + wadsrc/static/zscript/actor.txt | 11 +- wadsrc/static/zscript/base.txt | 25 +- wadsrc/static/zscript/doom/bossbrain.txt | 302 +++++++++++++++++++++++ 17 files changed, 668 insertions(+), 161 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index cc699ac47..896e174d6 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -808,8 +808,8 @@ void SetDehParams(FState *state, int codepointer) } else { - VMFunctionBuilder buildit(true); int numargs = sym->GetImplicitArgs(); + VMFunctionBuilder buildit(numargs); // Allocate registers used to pass parameters in. // self, stateowner, state (all are pointers) buildit.Registers[REGT_POINTER].Get(numargs); diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 7eb152ebd..57a67384a 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2737,6 +2737,7 @@ PClass::PClass() HashNext = NULL; Defaults = NULL; bRuntimeClass = false; + bExported = false; ConstructNative = NULL; mDescriptiveName = "Class"; diff --git a/src/dobjtype.h b/src/dobjtype.h index 302352b21..5aeefac50 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -769,6 +769,7 @@ public: const size_t *FlatPointers; // object pointers defined by this class and all its superclasses; not initialized by default BYTE *Defaults; bool bRuntimeClass; // class was defined at run-time, not compile-time + bool bExported; // This type has been declared in a script void (*ConstructNative)(void *); diff --git a/src/dthinker.cpp b/src/dthinker.cpp index 114d260df..022e147da 100644 --- a/src/dthinker.cpp +++ b/src/dthinker.cpp @@ -521,6 +521,44 @@ DThinker *FThinkerIterator::Next () return NULL; } +// This is for scripting, which needs the iterator wrapped into an object with the needed functions exported. +// Unfortunately we cannot have templated type conversions in scripts. +class DThinkerIterator : public DObject, public FThinkerIterator +{ + DECLARE_CLASS(DThinkerIterator, DObject) + +public: + DThinkerIterator(PClass *cls = nullptr, int statnum = MAX_STATNUM + 1) + : FThinkerIterator(cls, statnum) + { + } +}; + +IMPLEMENT_CLASS(DThinkerIterator); +DEFINE_ACTION_FUNCTION(DThinkerIterator, Create) +{ + PARAM_PROLOGUE; + PARAM_CLASS_DEF(type, DThinker); + PARAM_INT_DEF(statnum); + ACTION_RETURN_OBJECT(new DThinkerIterator(type, statnum)); +} + +DEFINE_ACTION_FUNCTION(DThinkerIterator, Next) +{ + PARAM_SELF_PROLOGUE(DThinkerIterator); + ACTION_RETURN_OBJECT(self->Next()); +} + +DEFINE_ACTION_FUNCTION(DThinkerIterator, Reinit) +{ + PARAM_SELF_PROLOGUE(DThinkerIterator); + self->Reinit(); + return 0; +} + + + + ADD_STAT (think) { FString out; diff --git a/src/g_doom/a_bossbrain.cpp b/src/g_doom/a_bossbrain.cpp index 1b50cb3cc..f58e75375 100644 --- a/src/g_doom/a_bossbrain.cpp +++ b/src/g_doom/a_bossbrain.cpp @@ -12,103 +12,8 @@ #include "g_level.h" */ -static FRandom pr_brainscream ("BrainScream"); -static FRandom pr_brainexplode ("BrainExplode"); static FRandom pr_spawnfly ("SpawnFly"); -DEFINE_ACTION_FUNCTION(AActor, A_BrainAwake) -{ - PARAM_SELF_PROLOGUE(AActor); - // killough 3/26/98: only generates sound now - S_Sound (self, CHAN_VOICE, "brain/sight", 1, ATTN_NONE); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_BrainPain) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_VOICE, "brain/pain", 1, ATTN_NONE); - return 0; -} - -static void BrainishExplosion (const DVector3 &pos) -{ - AActor *boom = Spawn("Rocket", pos, NO_REPLACE); - if (boom != NULL) - { - boom->DeathSound = "misc/brainexplode"; - boom->Vel.Z = pr_brainscream() /128.; - - PClassActor *cls = PClass::FindActor("BossBrain"); - if (cls != NULL) - { - FState *state = cls->FindState(NAME_Brainexplode); - if (state != NULL) - boom->SetState (state); - } - boom->effects = 0; - boom->SetDamage(0); // disables collision detection which is not wanted here - boom->tics -= pr_brainscream() & 7; - if (boom->tics < 1) - boom->tics = 1; - } -} - -DEFINE_ACTION_FUNCTION(AActor, A_BrainScream) -{ - PARAM_SELF_PROLOGUE(AActor); - - for (double x = -196; x < +320; x += 8) - { - // (1 / 512.) is actually what the original value of 128 did, even though it probably meant 128 map units. - BrainishExplosion(self->Vec2OffsetZ(x, -320, (1 / 512.) + pr_brainexplode() * 2)); - } - S_Sound (self, CHAN_VOICE, "brain/death", 1, ATTN_NONE); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_BrainExplode) -{ - PARAM_SELF_PROLOGUE(AActor); - double x = pr_brainexplode.Random2() / 32.; - DVector3 pos = self->Vec2OffsetZ(x, 0, 1 / 512. + pr_brainexplode() * 2); - BrainishExplosion(pos); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_BrainDie) -{ - PARAM_SELF_PROLOGUE(AActor); - - // [RH] If noexit, then don't end the level. - if ((deathmatch || alwaysapplydmflags) && (dmflags & DF_NO_EXIT)) - return 0; - - // New dmflag: Kill all boss spawned monsters before ending the level. - if (dmflags2 & DF2_KILLBOSSMONST) - { - int count; // Repeat until we have no more boss-spawned monsters. - do // (e.g. Pain Elementals can spawn more to kill upon death.) - { - TThinkerIterator it; - AActor *mo; - count = 0; - while ((mo = it.Next())) - { - if (mo->health > 0 && mo->flags4 & MF4_BOSSSPAWNED) - { - P_DamageMobj(mo, self, self, mo->health, NAME_None, - DMG_NO_ARMOR|DMG_FORCED|DMG_THRUSTLESS|DMG_NO_FACTOR); - count++; - } - } - } while (count != 0); - } - - G_ExitLevel (0, false); - return 0; -} - DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BrainSpit) { PARAM_SELF_PROLOGUE(AActor); diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 26987e622..f597b89c2 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6612,6 +6612,20 @@ void AActor::SetTranslation(const char *trname) // silently ignore if the name does not exist, this would create some insane message spam otherwise. } +DEFINE_ACTION_FUNCTION(AActor, SetDamage) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_INT(dmg); + self->SetDamage(dmg); + return 0; +} + +DEFINE_ACTION_FUNCTION(AActor, GetDefaultByType) +{ + PARAM_PROLOGUE; + PARAM_CLASS(cls, AActor); + ACTION_RETURN_OBJECT(GetDefaultByType(cls)); +} // This combines all 3 variations of the internal function DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) @@ -6657,6 +6671,15 @@ DEFINE_ACTION_FUNCTION(AActor, Vec3Angle) ACTION_RETURN_VEC3(self->Vec3Angle(length, angle, z, absolute)); } +DEFINE_ACTION_FUNCTION(AActor, Vec2OffsetZ) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(x); + PARAM_FLOAT(y); + PARAM_FLOAT(z); + PARAM_BOOL_DEF(absolute); + ACTION_RETURN_VEC3(self->Vec2OffsetZ(x, y, z, absolute)); +} //---------------------------------------------------------------------------- // // DropItem handling diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 66a7d8b41..fa5405c60 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -2078,6 +2078,8 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) return nullptr; } + // keep the redundant handling for numeric types here to avoid problems with DECORATE. + // for non-numerics FxTypeCast can be used without issues. if (Base->IsNumeric() && Right->IsNumeric()) { if (Right->ValueType != ValueType) @@ -2113,32 +2115,13 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) } // Both types are the same so this is ok. } - else if ((Base->ValueType == TypeState || Base->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) && Right->ValueType == TypeNullPtr) - { - // null pointers can be assigned to any other pointer - } - else if (Base->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) - { - // class pointers may be assignable so add a cast which performs a check. - Right = new FxClassTypeCast(static_cast(ValueType), Right); - SAFE_RESOLVE(Right, ctx); - } - else if (Base->ValueType == TypeString && (Right->ValueType == TypeName || Right->ValueType == TypeSound)) - { - Right = new FxStringCast(Right); - SAFE_RESOLVE(Right, ctx); - } - else if (Base->ValueType == TypeName && Right->ValueType == TypeString) - { - Right = new FxNameCast(Right); - SAFE_RESOLVE(Right, ctx); - } else { - ScriptPosition.Message(MSG_ERROR, "Assignment between incompatible types."); - delete this; - return nullptr; + // pass it to FxTypeCast for complete handling. + Right = new FxTypeCast(Right, Base->ValueType, false); + SAFE_RESOLVE(Right, ctx); } + if (!Base->RequestAddress(&AddressWritable) || !AddressWritable) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); @@ -3100,6 +3083,69 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) delete this; return e; } + else + { + // also simplify comparisons against zero. For these a bool cast on the other value will do just as well and create better code. + if (left->isConstant()) + { + bool leftisnull; + switch (left->ValueType->GetRegType()) + { + case REGT_INT: + leftisnull = static_cast(left)->GetValue().GetInt() == 0; + break; + + case REGT_FLOAT: + assert(left->ValueType->GetRegCount() == 1); // vectors should not be able to get here. + leftisnull = static_cast(left)->GetValue().GetFloat() == 0; + break; + + case REGT_POINTER: + leftisnull = static_cast(left)->GetValue().GetPointer() == nullptr; + break; + + default: + leftisnull = false; + } + if (leftisnull) + { + FxExpression *x = new FxBoolCast(right); + right = nullptr; + delete this; + return x->Resolve(ctx); + } + + } + if (right->isConstant()) + { + bool rightisnull; + switch (right->ValueType->GetRegType()) + { + case REGT_INT: + rightisnull = static_cast(right)->GetValue().GetInt() == 0; + break; + + case REGT_FLOAT: + assert(right->ValueType->GetRegCount() == 1); // vectors should not be able to get here. + rightisnull = static_cast(right)->GetValue().GetFloat() == 0; + break; + + case REGT_POINTER: + rightisnull = static_cast(right)->GetValue().GetPointer() == nullptr; + break; + + default: + rightisnull = false; + } + if (rightisnull) + { + FxExpression *x = new FxBoolCast(left); + left = nullptr; + delete this; + return x->Resolve(ctx); + } + } + } Promote(ctx); ValueType = TypeBool; return this; @@ -3720,7 +3766,7 @@ int BuiltinTypeCheck(VMFrameStack *stack, VMValue *param, TArray &defau assert(numparam == 2); PARAM_POINTER_AT(0, obj, DObject); PARAM_CLASS_AT(1, cls, DObject); - ACTION_RETURN_BOOL(obj->IsKindOf(cls)); + ACTION_RETURN_BOOL(obj && obj->IsKindOf(cls)); } //========================================================================== @@ -3762,6 +3808,72 @@ ExpEmit FxTypeCheck::Emit(VMFunctionBuilder *build) // //========================================================================== +FxDynamicCast::FxDynamicCast(PClass * cls, FxExpression *r) + : FxExpression(EFX_DynamicCast, r->ScriptPosition) +{ + expr = new FxTypeCast(r, NewPointer(RUNTIME_CLASS(DObject)), true, true); + ValueType = NewPointer(cls); + CastType = cls; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxDynamicCast::~FxDynamicCast() +{ + SAFE_DELETE(expr); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxDynamicCast::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(expr, ctx); + return this; +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxDynamicCast::Emit(VMFunctionBuilder *build) +{ + ExpEmit out = expr->Emit(build); + ExpEmit check(build, REGT_INT); + assert(out.RegType == REGT_POINTER); + + build->Emit(OP_PARAM, 0, REGT_POINTER, out.RegNum); + build->Emit(OP_PARAM, 0, REGT_POINTER | REGT_KONST, build->GetConstantAddress(CastType, ATAG_OBJECT)); + + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinTypeCheck, BuiltinTypeCheck); + assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); + auto callfunc = ((PSymbolVMFunction *)sym)->Function; + + build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), 2, 1); + build->Emit(OP_RESULT, 0, REGT_INT, check.RegNum); + auto patch = build->Emit(OP_EQ_K, 0, check.RegNum, build->GetConstantInt(0)); + build->Emit(OP_LKP, out.RegNum, build->GetConstantAddress(nullptr, ATAG_OBJECT)); + build->BackpatchToHere(patch); + return out; +} + +//========================================================================== +// +// +// +//========================================================================== + FxConditional::FxConditional(FxExpression *c, FxExpression *t, FxExpression *f) : FxExpression(EFX_Conditional, c->ScriptPosition) { @@ -5655,6 +5767,24 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) return x->Resolve(ctx); } + PClass *cls = PClass::FindClass(MethodName); + if (cls != nullptr && cls->bExported) + { + if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) + { + FxExpression *x = new FxDynamicCast(cls, (*ArgList)[0]); + (*ArgList)[0] = nullptr; + delete this; + return x->Resolve(ctx); + } + else + { + delete this; + return nullptr; + } + } + + // Last but not least: Check builtins and type casts. The random functions can take a named RNG if specified. // Note that for all builtins the used arguments have to be nulled in the ArgList so that they won't get deleted before they get used. FxExpression *func = nullptr; @@ -5681,7 +5811,12 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) break; case NAME_Random: - if (CheckArgSize(NAME_Random, ArgList, 2, 2, ScriptPosition)) + // allow calling Random without arguments to default to (0, 255) + if (ArgList->Size() == 0) + { + func = new FxRandom(RNG, new FxConstant(0, ScriptPosition), new FxConstant(255, ScriptPosition), ScriptPosition, ctx.FromDecorate); + } + else if (CheckArgSize(NAME_Random, ArgList, 2, 2, ScriptPosition)) { func = new FxRandom(RNG, (*ArgList)[0], (*ArgList)[1], ScriptPosition, ctx.FromDecorate); (*ArgList)[0] = (*ArgList)[1] = nullptr; @@ -5754,7 +5889,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) break; default: - // todo: Check for class type casts + ScriptPosition.Message(MSG_ERROR, "Call to unknown function '%s'", MethodName.GetChars()); break; } if (func != nullptr) @@ -5762,7 +5897,6 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) delete this; return func->Resolve(ctx); } - ScriptPosition.Message(MSG_ERROR, "Call to unknown function '%s'", MethodName.GetChars()); delete this; return nullptr; } @@ -5803,10 +5937,22 @@ FxMemberFunctionCall::~FxMemberFunctionCall() FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) { ABORT(ctx.Class); - SAFE_RESOLVE(Self, ctx); - PClass *cls; bool staticonly = false; + + if (Self->ExprType == EFX_Identifier) + { + // If the left side is a class name for a static member function call it needs to be resolved manually + // because the resulting value type would cause problems in nearly every other place where identifiers are being used. + cls = PClass::FindClass(static_cast(Self)->Identifier); + if (cls != nullptr && cls->bExported) + { + staticonly = true; + goto isresolved; + } + } + SAFE_RESOLVE(Self, ctx); + if (Self->IsVector()) { // handle builtins: Vectors got 2: Length and Unit. @@ -5819,12 +5965,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) } } - if (Self->ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) - { - cls = static_cast(Self->ValueType)->ClassRestriction; - staticonly = true; - } - else if (Self->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) + if (Self->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) { auto ptype = static_cast(Self->ValueType)->PointedType; if (ptype->IsKindOf(RUNTIME_CLASS(PClass))) @@ -5845,6 +5986,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) return nullptr; } +isresolved: bool error = false; PFunction *afd = FindClassMemberFunction(cls, cls, MethodName, ScriptPosition, &error); if (error) @@ -5859,7 +6001,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) delete this; return nullptr; } - if (staticonly && !(afd->Variants[0].Flags & VARF_Static)) + if (staticonly && (afd->Variants[0].Flags & VARF_Method)) { if (!ctx.Class->IsDescendantOf(cls)) { @@ -5867,11 +6009,17 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) delete this; return nullptr; } - // If this is a qualified call to a parent class function, let it through (but this needs to disable virtual calls later.) + else + { + // Todo: If this is a qualified call to a parent class function, let it through (but this needs to disable virtual calls later.) + ScriptPosition.Message(MSG_ERROR, "Qualified member call to parent class not yet implemented\n", cls->TypeName.GetChars(), MethodName.GetChars()); + delete this; + return nullptr; + } } // do not pass the self pointer to static functions. - auto self = !(afd->Variants[0].Flags & VARF_Static) ? Self : nullptr; + auto self = (afd->Variants[0].Flags & VARF_Method) ? Self : nullptr; auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, staticonly); ArgList = nullptr; if (Self == self) Self = nullptr; @@ -6128,7 +6276,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) int implicit = Function->GetImplicitArgs(); // This should never happen. - if (Self == nullptr && !(Function->Variants[0].Flags & VARF_Static)) + if (Self == nullptr && (Function->Variants[0].Flags & VARF_Method)) { ScriptPosition.Message(MSG_ERROR, "Call to non-static function without a self pointer"); delete this; @@ -6200,8 +6348,7 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) { - assert((build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= NAP) || - (!build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= 1)); + assert(build->Registers[REGT_POINTER].GetMostUsed() >= build->NumImplicits); int count = 0; (ArgList ? ArgList->Size() : 0); if (count == 1) @@ -6225,7 +6372,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) if (Function->Variants[0].Flags & VARF_Action) { static_assert(NAP == 3, "This code needs to be updated if NAP changes"); - if (build->IsActionFunc && selfemit.RegNum == 0) // only pass this function's stateowner and stateinfo if the subfunction is run in self's context. + if (build->NumImplicits == NAP && selfemit.RegNum == 0) // only pass this function's stateowner and stateinfo if the subfunction is run in self's context. { build->Emit(OP_PARAM, 0, REGT_POINTER, 1); build->Emit(OP_PARAM, 0, REGT_POINTER, 2); @@ -6238,6 +6385,7 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } count += 2; } + selfemit.Free(build); } // Emit code to pass explicit parameters if (ArgList != nullptr) @@ -7654,7 +7802,9 @@ static int BuiltinHandleRuntimeState(VMFrameStack *stack, VMValue *param, TArray ExpEmit FxRuntimeStateIndex::Emit(VMFunctionBuilder *build) { - assert(build->IsActionFunc && build->Registers[REGT_POINTER].GetMostUsed() >= 3 && + // This code can only be called from DECORATE, not ZSCRIPT so any function going through here + // is an anoynmous one which are always marked as 'action'. + assert(build->NumImplicits >= NAP && build->Registers[REGT_POINTER].GetMostUsed() >= build->NumImplicits && "FxRuntimeStateIndex is only valid inside action functions"); ExpEmit out(build, REGT_POINTER); @@ -7741,7 +7891,7 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) delete this; return nullptr; } - else if (!scope->IsAncestorOf(ctx.Class)) + else if (!scope->IsAncestorOf(ctx.Class) && ctx.Class != RUNTIME_CLASS(AActor)) // AActor needs access to subclasses in a few places. TBD: Relax this for non-action functions? { ScriptPosition.Message(MSG_ERROR, "'%s' is not an ancestor of '%s'", names[0].GetChars(), ctx.Class->TypeName.GetChars()); delete this; @@ -7827,7 +7977,7 @@ int BuiltinFindSingleNameState(VMFrameStack *stack, VMValue *param, TArrayIsActionFunc) + if (build->NumImplicits == NAP) { build->Emit(OP_PARAM, 0, REGT_POINTER, 1); // pass stateowner } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index b3a5e4297..cfe261b39 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -268,6 +268,7 @@ enum EFxType EFX_VectorValue, EFX_VectorBuiltin, EFX_TypeCheck, + EFX_DynamicCast, EFX_COUNT }; @@ -320,10 +321,9 @@ public: class FxIdentifier : public FxExpression { -protected: +public: FName Identifier; -public: FxIdentifier(FName i, const FScriptPosition &p); FxExpression *Resolve(FCompileContext&); }; @@ -940,7 +940,7 @@ public: //========================================================================== // -// FxBinaryLogical +// // //========================================================================== @@ -959,6 +959,25 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// +// +//========================================================================== + +class FxDynamicCast : public FxExpression +{ + PClass *CastType; +public: + FxExpression *expr; + + FxDynamicCast(PClass*, FxExpression*); + ~FxDynamicCast(); + FxExpression *Resolve(FCompileContext&); + + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxConditional diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 6c47fabe0..c623290da 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -61,6 +61,39 @@ static TArray AFTable; #define DEFINE_DEPRECATED_FLAG(name) { DEPF_##name, #name, -1, 0, true } #define DEFINE_DUMMY_FLAG(name, deprec) { DEPF_UNUSED, #name, -1, 0, deprec? VARF_Deprecated:0 } +// internal flags. These do not get exposed to actor definitions but scripts need to be able to access them as variables. +static FFlagDef InternalActorFlagDefs[]= +{ + DEFINE_FLAG(MF, INCHASE, AActor, flags), + DEFINE_FLAG(MF, UNMORPHED, AActor, flags), + DEFINE_FLAG(MF2, FLY, AActor, flags2), + DEFINE_FLAG(MF2, ONMOBJ, AActor, flags2), + DEFINE_FLAG(MF2, DONTTRANSLATE, AActor, flags2), + DEFINE_FLAG(MF2, ARGSDEFINED, AActor, flags2), + DEFINE_FLAG(MF3, NOSIGHTCHECK, AActor, flags3), + DEFINE_FLAG(MF3, CRASHED, AActor, flags3), + DEFINE_FLAG(MF3, WARNBOT, AActor, flags3), + DEFINE_FLAG(MF3, HUNTPLAYERS, AActor, flags3), + DEFINE_FLAG(MF4, NOHATEPLAYERS, AActor, flags4), + DEFINE_FLAG(MF4, NOSKIN, AActor, flags4), + DEFINE_FLAG(MF4, SCROLLMOVE, AActor, flags4), + DEFINE_FLAG(MF4, VFRICTION, AActor, flags4), + DEFINE_FLAG(MF4, BOSSSPAWNED, AActor, flags4), + DEFINE_FLAG(MF5, AVOIDINGDROPOFF, AActor, flags5), + DEFINE_FLAG(MF5, CHASEGOAL, AActor, flags5), + DEFINE_FLAG(MF5, INCONVERSATION, AActor, flags5), + DEFINE_FLAG(MF6, ARMED, AActor, flags6), + DEFINE_FLAG(MF6, FALLING, AActor, flags6), + DEFINE_FLAG(MF6, LINEDONE, AActor, flags6), + DEFINE_FLAG(MF6, SHATTERING, AActor, flags6), + DEFINE_FLAG(MF6, KILLED, AActor, flags6), + DEFINE_FLAG(MF6, BOSSCUBE, AActor, flags6), + DEFINE_FLAG(MF6, INTRYMOVE, AActor, flags6), + DEFINE_FLAG(MF7, HANDLENODELAY, AActor, flags7), + DEFINE_FLAG(MF7, FLYCHEAT, AActor, flags7), +}; + + static FFlagDef ActorFlagDefs[]= { DEFINE_FLAG(MF, PICKUP, APlayerPawn, flags), @@ -687,6 +720,7 @@ void InitThingdef() symt.AddSymbol(new PField("Gravity", TypeFloat64, VARF_Native, myoffsetof(AActor, Gravity))); symt.AddSymbol(new PField("DamageType", TypeName, VARF_Native, myoffsetof(AActor, DamageType))); symt.AddSymbol(new PField("FloatBobPhase", TypeUInt8, VARF_Native, myoffsetof(AActor, FloatBobPhase))); + symt.AddSymbol(new PField("tics", TypeSInt32, VARF_Native, myoffsetof(AActor, tics))); symt.AddSymbol(new PField("RipperLevel", TypeSInt32, VARF_Native, myoffsetof(AActor, RipperLevel))); symt.AddSymbol(new PField("RipLevelMin", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMin))); symt.AddSymbol(new PField("RipLevelMax", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMax))); @@ -695,6 +729,7 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); symt.AddSymbol(new PField("AttackSound", TypeSound, VARF_Native, myoffsetof(AActor, AttackSound))); + symt.AddSymbol(new PField("DeathSound", TypeSound, VARF_Native, myoffsetof(AActor, DeathSound))); symt.AddSymbol(new PField("Pos", TypeVector3, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos))); symt.AddSymbol(new PField("Vel", TypeVector3, VARF_Native, myoffsetof(AActor, Vel))); symt.AddSymbol(new PField("Scale", TypeVector2, VARF_Native, myoffsetof(AActor, Scale))); @@ -706,7 +741,7 @@ void InitThingdef() symt.AddSymbol(new PField("LastHeard", TypeActor, VARF_Native, myoffsetof(AActor, LastHeard))); symt.AddSymbol(new PField("LastEnemy", TypeActor, VARF_Native, myoffsetof(AActor, lastenemy))); - // synthesize a symbol for each flag. The bounce flags are excluded on purpose. + // synthesize a symbol for each flag. for (size_t i = 0; i < countof(ActorFlagDefs); i++) { int bit = 0; @@ -714,5 +749,19 @@ void InitThingdef() while ((val >>= 1)) bit++; symt.AddSymbol(new PField(FStringf("b%s", ActorFlagDefs[i].name), (ActorFlagDefs[i].fieldsize == 4? TypeSInt32 : TypeSInt16), ActorFlagDefs[i].varflags, ActorFlagDefs[i].structoffset, bit)); } + for (size_t i = 0; i < countof(InternalActorFlagDefs); i++) + { + int bit = 0; + unsigned val = InternalActorFlagDefs[i].flagbit; + while ((val >>= 1)) bit++; + symt.AddSymbol(new PField(FStringf("b%s", InternalActorFlagDefs[i].name), (InternalActorFlagDefs[i].fieldsize == 4 ? TypeSInt32 : TypeSInt16), InternalActorFlagDefs[i].varflags, InternalActorFlagDefs[i].structoffset, bit)); + } + + PSymbolTable &symt2 = RUNTIME_CLASS(DDropItem)->Symbols; + PType *TypeDropItem = NewPointer(RUNTIME_CLASS(DDropItem)); + symt2.AddSymbol(new PField("Next", TypeDropItem, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Next))); + symt2.AddSymbol(new PField("ItemName", TypeName, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Name))); + symt2.AddSymbol(new PField("Probability", TypeSInt32, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Probability))); + symt2.AddSymbol(new PField("Amount", TypeSInt32, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Amount))); } diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index ca7aa6d54..811fb82e0 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -161,8 +161,8 @@ enum ATAG_SREGISTER, // pointer to a string register ATAG_AREGISTER, // pointer to an address register - ATAG_STATE, // pointer to FState ATAG_RNG, // pointer to FRandom + ATAG_STATE = ATAG_GENERIC, // pointer to FState (cannot have its own type because there's no means to track inside the VM.) }; enum EVMAbortException diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index afadaaa1e..d2d9e7140 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -43,7 +43,7 @@ // //========================================================================== -VMFunctionBuilder::VMFunctionBuilder(bool selfcheck) +VMFunctionBuilder::VMFunctionBuilder(int numimplicits) { NumIntConstants = 0; NumFloatConstants = 0; @@ -51,7 +51,7 @@ VMFunctionBuilder::VMFunctionBuilder(bool selfcheck) NumStringConstants = 0; MaxParam = 0; ActiveParam = 0; - IsActionFunc = selfcheck; + NumImplicits = numimplicits; } //========================================================================== diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index dcaae7251..9a97c216d 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -23,7 +23,7 @@ public: friend class VMFunctionBuilder; }; - VMFunctionBuilder(bool checkself = false); + VMFunctionBuilder(int numimplicits); ~VMFunctionBuilder(); void MakeFunction(VMScriptFunction *func); @@ -60,8 +60,8 @@ public: // Track available registers. RegAvailability Registers[4]; - // For use by DECORATE's self/stateowner sanitizer. - bool IsActionFunc; + // amount of implicit parameters so that proper code can be emitted for method calls + int NumImplicits; private: struct AddrKonst diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 10b85ef86..500c30c66 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -175,7 +175,7 @@ begin: OP(LO): ASSERTA(a); ASSERTA(B); ASSERTKD(C); GETADDR(PB,KC,X_READ_NIL); - reg.a[a] = GC::ReadBarrier(*(DObject **)ptr); + reg.a[a] = *(DObject **)ptr; reg.atag[a] = ATAG_OBJECT; NEXTOP; OP(LO_R): diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 9e8b84163..98d847ebe 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -508,6 +508,7 @@ void ZCCCompiler::CreateClassTypes() // We will never get here if the name is a duplicate, so we can just do the assignment. c->cls->Type = parent->FindClassTentative(c->NodeName()); } + c->Type()->bExported = true; // this class is accessible to script side type casts. (The reason for this flag is that types like PInt need to be skipped.) c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); GlobalSymbols.AddSymbol(c->cls->Symbol); c->Type()->Symbols.SetName(c->NodeName()); diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 83ea76cb7..213ca8b25 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -53,6 +53,8 @@ class Actor : Thinker native return GetPointer(ptr_select1) == GetPointer(ptr_select2); } + native static /*readonly*/ Actor GetDefaultByType(class cls); + native void SetDamage(int dmg); native static bool isDehState(state st); native void SetOrigin(vector3 newpos, bool moving); native void SetXYZ(vector3 newpos); @@ -71,6 +73,7 @@ class Actor : Thinker native native void LinkToWorld(); native void UnlinkFromWorld(); native vector3 Vec3Angle(float length, float angle, float z = 0, bool absolute = false); + native vector3 Vec2OffsetZ(float x, float y, float atz, bool absolute = false); native void VelFromAngle(float speed = 0, float angle = 0); native bool isFriend(Actor other); @@ -218,14 +221,6 @@ class Actor : Thinker native native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); native void A_KeenDie(int doortag = 666); - native void A_BrainPain(); - native void A_BrainScream(); - native void A_BrainDie(); - native void A_BrainAwake(); - native void A_BrainSpit(class spawntype = null); // needs special treatment for default - native void A_SpawnSound(); - native void A_SpawnFly(class spawntype = null); // needs special treatment for default - native void A_BrainExplode(); native void A_Detonate(); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); diff --git a/wadsrc/static/zscript/base.txt b/wadsrc/static/zscript/base.txt index bda63f059..cca39f1e2 100644 --- a/wadsrc/static/zscript/base.txt +++ b/wadsrc/static/zscript/base.txt @@ -5,4 +5,27 @@ class Object native class Thinker : Object native { -} \ No newline at end of file +} + +class ThinkerIterator : Object native +{ + enum EStatnums + { + MAX_STATNUM = 127 + } + + native static ThinkerIterator Create(class type = "Actor", int statnum=MAX_STATNUM+1); + native Thinker Next(); + native void Reinit(); +} + +class DropItem : Object native +{ + /* native fields listed for reference only for now + native readonly DropItem Next; + native readonly name ItemName; // internally called 'name' which clashes with the type. + native readonly int Probability; + native readonly int Amount; + */ +} + diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt index 533d0fa01..2193be954 100644 --- a/wadsrc/static/zscript/doom/bossbrain.txt +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -133,3 +133,305 @@ class SpawnFire : Actor Stop; } } + + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + + void A_BrainAwake() + { + A_PlaySound("brain/sight", CHAN_VOICE, 1, false, ATTN_NONE); + } + + void A_BrainPain() + { + A_PlaySound("brain/pain", CHAN_VOICE, 1, false, ATTN_NONE); + } + + private static void BrainishExplosion(vector3 pos) + { + Actor boom = Actor.Spawn("Rocket", pos, NO_REPLACE); + if (boom) + { + boom.DeathSound = "misc/brainexplode"; + boom.Vel.z = random[BrainScream](0, 255)/128.; + + State stt = "BossBrain::Brainexplode"; + if (stt) boom.SetState (stt); + } + boom.bRocketTrail = false; + boom.SetDamage(0); // disables collision detection which is not wanted here + boom.tics -= random[BrainScream](0, 7); + if (boom.tics < 1) boom.tics = 1; + } + + void A_BrainScream() + { + for (double x = -196; x < +320; x += 8) + { + // (1 / 512.) is actually what the original value of 128 did, even though it probably meant 128 map units. + BrainishExplosion(Vec2OffsetZ(x, -320, (1 / 512.) + random[BrainExplode](0, 255) * 2)); + } + A_PlaySound("brain/death", CHAN_VOICE, 1, false, ATTN_NONE); + } + + void A_BrainExplode() + { + double x = random2[BrainExplode]() / 32.; + Vector3 pos = Vec2OffsetZ(x, 0, 1 / 512. + random[BrainExplode]() * 2); + BrainishExplosion(pos); + } + + void A_BrainDie() + { + A_Log("A_BrainDie"); + // [RH] If noexit, then don't end the level. + if ((GetCVar("deathmatch") || GetCVar("alwaysapplydmflags")) && GetCVar("sv_noexit")) + return; + + // New dmflag: Kill all boss spawned monsters before ending the level. + if (GetCVar("sv_killbossmonst")) + { + int count; // Repeat until we have no more boss-spawned monsters. + ThinkerIterator it = ThinkerIterator.Create(); + do // (e.g. Pain Elementals can spawn more to kill upon death.) + { + Actor mo; + it.Reinit(); + count = 0; + while (mo = Actor(it.Next())) + { + if (mo.health > 0 && mo.bBossSpawned) + { + mo.DamageMobj(self, self, mo.health, "None", DMG_NO_ARMOR|DMG_FORCED|DMG_THRUSTLESS|DMG_NO_FACTOR); + count++; + } + } + } while (count != 0); + } + Exit_Normal(0); + } + + native + void A_BrainSpit(class spawntype = null) // needs special treatment for default + ;/* + { + SpotState spstate = SpotState.GetSpotState(); + Actor targ; + Actor spit; + bool isdefault = false; + + // shoot a cube at current target + targ = spstate.GetNextInList("BossTarget", G_SkillProperty(SKILLP_EasyBossBrain)); + + if (targ) + { + if (spawntype == null) + { + spawntype = "SpawnShot"; + isdefault = true; + } + + // spawn brain missile + spit = SpawnMissile (targ, spawntype); + + if (spit) + { + // Boss cubes should move freely to their destination so it's + // probably best to disable all collision detection for them. + spit.bNoInteraction = spit.bNoClip; + + spit.target = targ; + spit.master = self; + // [RH] Do this correctly for any trajectory. Doom would divide by 0 + // if the target had the same y coordinate as the spitter. + if (spit.Vel.xy == (0, 0)) + { + spit.special2 = 0; + } + else if (abs(spit.Vel.y) > fabs(spit.Vel.x)) + { + spit.special2 = int((targ.pos.y - pos.y) / spit.Vel.y); + } + else + { + spit.special2 = int((targ.pos.x - pos.x) / spit.Vel.y); + } + // [GZ] Calculates when the projectile will have reached destination + spit.special2 += level.maptime; + spit.bBossCube = true; + } + + if (!isdefault) + { + A_PlaySound(self.AttackSound, CHAN_WEAPON); + } + else + { + // compatibility fallback + A_PlaySound("brain/spit", CHAN_WEAPON); + } + } + } + */ + + /* + private void SpawnFly(class spawntype, sound snd) + { + AActor newmobj; + AActor fog; + AActor eye = master; // The eye is the spawnshot's master, not the target! + AActor targ = target; // Unlike other projectiles, the target is the intended destination. + int r; + + // [GZ] Should be more viable than a countdown... + if (special2 != 0) + { + if (special2 > level.maptime) + return; // still flying + } + else + { + if (reactiontime == 0 || --reactiontime != 0) + return; // still flying + } + + if (spawntype) + { + fog = Spawn (spawntype, targ.pos, ALLOW_REPLACE); + if (fog) A_PlaySound(snd, CHAN_BODY); + } + + class SpawnName; + + DropItem di; // di will be our drop item list iterator + DropItem drop; // while drop stays as the reference point. + int n = 0; + + // First see if this cube has its own actor list + drop = GetDropItems(); + + // If not, then default back to its master's list + if (drop == null && eye != null) + drop = eye.GetDropItems(); + + if (drop != null) + { + for (di = drop; di != null; di = di.Next) + { + if (di.Name != 'None') + { + if (di.Amount < 0) + { + di.Amount = 1; // default value is -1, we need a positive value. + } + n += di.Amount; // this is how we can weight the list. + } + } + di = drop; + n = randon[pr_spawnfly](0, n); + while (n >= 0) + { + if (di.Name != 'none') + { + n -= di.Amount; // logically, none of the -1 values have survived by now. + } + if ((di.Next != null) && (n >= 0)) + { + di = di.Next; + } + else + { + n = -1; + } + } + SpawnName = di.Name; + } + if (SpawnName == null) + { + // Randomly select monster to spawn. + r = random[pr_spawnfly](0, 255); + + // Probability distribution (kind of :), + // decreasing likelihood. + if (r < 50) SpawnName = "DoomImp"; + else if (r < 90) SpawnName = "Demon"; + else if (r < 120) SpawnName = "Spectre"; + else if (r < 130) SpawnName = "PainElemental"; + else if (r < 160) SpawnName = "Cacodemon"; + else if (r < 162) SpawnName = "Archvile"; + else if (r < 172) SpawnName = "Revenant"; + else if (r < 192) SpawnName = "Arachnotron"; + else if (r < 222) SpawnName = "Fatso"; + else if (r < 246) SpawnName = "HellKnight"; + else SpawnName = "BaronOfHell"; + } + if (spawnname != null) + { + newmobj = Spawn (spawnname, targ.pos, ALLOW_REPLACE); + if (newmobj != null) + { + // Make the new monster hate what the boss eye hates + if (eye != null) + { + newmobj.CopyFriendliness (eye, false); + } + // Make it act as if it was around when the player first made noise + // (if the player has made noise). + newmobj.LastHeard = newmobj.Sector.SoundTarget; + + if (newmobj.SeeState != null && newmobj.LookForPlayers (true, null)) + { + newmobj.SetState (newmobj.SeeState); + } + if (!(newmobj.ObjectFlags & OF_EuthanizeMe)) + { + // telefrag anything in this spot + newmobj.TeleportMove (newmobj.pos, true); + } + newmobj.bBossSpawned = true; + } + } + + // remove self (i.e., cube). + Destroy (); + } + */ + + + native + void A_SpawnFly(class spawntype = null) // needs special treatment for default + ; + /* + { + sound snd; + if (spawntype != null) + { + snd = GetDefaultByType(spawntype).SeeSound; + } + else + { + spawntype = "SpawnFire"; + snd = "brain/spawn"; + } + SpawnFly(self, spawntype, snd); + } + */ + + native + void A_SpawnSound() + ; + /* + { + // travelling cube sound + A_PlaySound("brain/cube", CHAN_BODY); + SpawnFly("SpawnFire", "brain/spawn"); + } + */ +} From 7137e87b4b709fcc2675b7fef3d0c36b96e3b47f Mon Sep 17 00:00:00 2001 From: Edoardo Prezioso Date: Sun, 30 Oct 2016 13:43:20 +0100 Subject: [PATCH 150/255] - Fixed GCC/Clang errors from recent commits. --- src/scripting/codegeneration/codegen.cpp | 28 ++++++++++++++---------- 1 file changed, 17 insertions(+), 11 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index fa5405c60..f1dfab523 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -563,8 +563,10 @@ ExpEmit FxVectorValue::Emit(VMFunctionBuilder *build) assert(xyz[1] != nullptr); if (ValueType == TypeVector2) { - ExpEmit xval = EmitKonst(build, xyz[0]->Emit(build)); - ExpEmit yval = EmitKonst(build, xyz[1]->Emit(build)); + ExpEmit tempxval = xyz[0]->Emit(build); + ExpEmit tempyval = xyz[1]->Emit(build); + ExpEmit xval = EmitKonst(build, tempxval); + ExpEmit yval = EmitKonst(build, tempyval); assert(xval.RegType == REGT_FLOAT && yval.RegType == REGT_FLOAT); if (yval.RegNum == xval.RegNum + 1) { @@ -586,7 +588,8 @@ ExpEmit FxVectorValue::Emit(VMFunctionBuilder *build) else if (xyz[0]->ValueType == TypeVector2) // vec2+float { ExpEmit xyval = xyz[0]->Emit(build); - ExpEmit zval = EmitKonst(build, xyz[1]->Emit(build)); + ExpEmit tempzval = xyz[1]->Emit(build); + ExpEmit zval = EmitKonst(build, tempzval); assert(xyval.RegType == REGT_FLOAT && xyval.RegCount == 2 && zval.RegType == REGT_FLOAT); if (zval.RegNum == xyval.RegNum + 2) { @@ -608,9 +611,12 @@ ExpEmit FxVectorValue::Emit(VMFunctionBuilder *build) else // 3*float { assert(xyz[2] != nullptr); - ExpEmit xval = EmitKonst(build, xyz[0]->Emit(build)); - ExpEmit yval = EmitKonst(build, xyz[1]->Emit(build)); - ExpEmit zval = EmitKonst(build, xyz[2]->Emit(build)); + ExpEmit tempxval = xyz[0]->Emit(build); + ExpEmit tempyval = xyz[1]->Emit(build); + ExpEmit tempzval = xyz[2]->Emit(build); + ExpEmit xval = EmitKonst(build, tempxval); + ExpEmit yval = EmitKonst(build, tempyval); + ExpEmit zval = EmitKonst(build, tempzval); assert(xval.RegType == REGT_FLOAT && yval.RegType == REGT_FLOAT && zval.RegType == REGT_FLOAT); if (yval.RegNum == xval.RegNum + 1 && zval.RegNum == xval.RegNum + 2) { @@ -2308,7 +2314,7 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) if (left == nullptr) { delete this; - return nullptr; + return false; } } if (right->ValueType != TypeString) @@ -2318,7 +2324,7 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) if (right == nullptr) { delete this; - return nullptr; + return false; } } ValueType = TypeBool; @@ -2464,7 +2470,7 @@ bool FxBinary::ResolveLR(FCompileContext& ctx, bool castnumeric) delete this; return false; } - assert(ValueType > nullptr && ValueType < (PType*)0xfffffffffffffff); + assert(ValueType != nullptr && ValueType < (PType*)0xfffffffffffffff); if (castnumeric) { @@ -3206,7 +3212,7 @@ ExpEmit FxCompareEq::Emit(VMFunctionBuilder *build) // See FxUnaryNotBoolean for comments, since it's the same thing. build->Emit(OP_LI, to.RegNum, 0, 0); - build->Emit(instr, Operator == TK_ApproxEq ? CMP_APPROX : Operator != TK_Eq, op1.RegNum, op2.RegNum); + build->Emit(instr, Operator == TK_ApproxEq ? CMP_APPROX : ((Operator != TK_Eq) ? CMP_CHECK : 0), op1.RegNum, op2.RegNum); build->Emit(OP_JMP, 1); build->Emit(OP_LI, to.RegNum, 1); return to; @@ -3925,7 +3931,7 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) { ScriptPosition.Message(MSG_ERROR, "Incompatible types for ?: operator"); delete this; - return false; + return nullptr; } if (condition->ValueType != TypeBool) From 88fd47247d41fc3a46f5f41f060591b3f773003a Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 1 Nov 2016 16:32:47 +0100 Subject: [PATCH 151/255] - scriptified several trivial functions from a_action.cpp. --- src/g_shared/a_action.cpp | 223 -------------------------------- src/p_mobj.cpp | 7 + src/scripting/thingdef_data.cpp | 1 + wadsrc/static/zscript/actor.txt | 35 +++-- 4 files changed, 25 insertions(+), 241 deletions(-) diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index abd58dec1..0ec388de8 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -109,71 +109,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_NoBlocking) return 0; } -DEFINE_ACTION_FUNCTION(AActor, A_Fall) -{ - PARAM_SELF_PROLOGUE(AActor); - A_Unblock(self, true); - return 0; -} - -//========================================================================== -// -// A_SetFloorClip -// -//========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_SetFloorClip) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 |= MF2_FLOORCLIP; - self->AdjustFloorClip (); - return 0; -} - -//========================================================================== -// -// A_UnSetFloorClip -// -//========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_UnSetFloorClip) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 &= ~MF2_FLOORCLIP; - self->Floorclip = 0; - return 0; -} - -//========================================================================== -// -// A_HideThing -// -//========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_HideThing) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->renderflags |= RF_INVISIBLE; - return 0; -} - -//========================================================================== -// -// A_UnHideThing -// -//========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_UnHideThing) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->renderflags &= ~RF_INVISIBLE; - return 0; -} - //============================================================================ // // A_FreezeDeath @@ -475,164 +410,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeQueueCorpse) return 0; } -//============================================================================ -// -// A_SetInvulnerable -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_SetInvulnerable) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 |= MF2_INVULNERABLE; - return 0; -} - -//============================================================================ -// -// A_UnSetInvulnerable -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_UnSetInvulnerable) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 &= ~MF2_INVULNERABLE; - return 0; -} - -//============================================================================ -// -// A_SetReflective -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_SetReflective) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 |= MF2_REFLECTIVE; - return 0; -} - -//============================================================================ -// -// A_UnSetReflective -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_UnSetReflective) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 &= ~MF2_REFLECTIVE; - return 0; -} - -//============================================================================ -// -// A_SetReflectiveInvulnerable -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_SetReflectiveInvulnerable) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 |= MF2_REFLECTIVE|MF2_INVULNERABLE; - return 0; -} - -//============================================================================ -// -// A_UnSetReflectiveInvulnerable -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_UnSetReflectiveInvulnerable) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 &= ~(MF2_REFLECTIVE|MF2_INVULNERABLE); - return 0; -} - -//========================================================================== -// -// A_SetShootable -// -//========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_SetShootable) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 &= ~MF2_NONSHOOTABLE; - self->flags |= MF_SHOOTABLE; - return 0; -} - -//========================================================================== -// -// A_UnSetShootable -// -//========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_UnSetShootable) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags2 |= MF2_NONSHOOTABLE; - self->flags &= ~MF_SHOOTABLE; - return 0; -} - -//=========================================================================== -// -// A_NoGravity -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_NoGravity) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags |= MF_NOGRAVITY; - return 0; -} - -//=========================================================================== -// -// A_Gravity -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_Gravity) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags &= ~MF_NOGRAVITY; - self->Gravity = 1; - return 0; -} - -//=========================================================================== -// -// A_LowGravity -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_LowGravity) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags &= ~MF_NOGRAVITY; - self->Gravity = 1. / 8;; - return 0; -} - //=========================================================================== // // FaceMovementDirection diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index f597b89c2..bd78fdcef 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -4509,6 +4509,13 @@ void AActor::AdjustFloorClip () } } +DEFINE_ACTION_FUNCTION(AActor, AdjustFloorClip) +{ + PARAM_SELF_PROLOGUE(AActor); + self->AdjustFloorClip(); + return 0; +} + // // P_SpawnPlayer // Called when a player is spawned on the level. diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index c623290da..b0edcb167 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -718,6 +718,7 @@ void InitThingdef() symt.AddSymbol(new PField(NAME_Damage, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DamageVal))); symt.AddSymbol(new PField("visdir", TypeSInt32, VARF_Native, myoffsetof(AActor, visdir))); symt.AddSymbol(new PField("Gravity", TypeFloat64, VARF_Native, myoffsetof(AActor, Gravity))); + symt.AddSymbol(new PField("FloorClip", TypeFloat64, VARF_Native, myoffsetof(AActor, Floorclip))); symt.AddSymbol(new PField("DamageType", TypeName, VARF_Native, myoffsetof(AActor, DamageType))); symt.AddSymbol(new PField("FloatBobPhase", TypeUInt8, VARF_Native, myoffsetof(AActor, FloatBobPhase))); symt.AddSymbol(new PField("tics", TypeSInt32, VARF_Native, myoffsetof(AActor, tics))); diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 213ca8b25..1e05d75a7 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -76,6 +76,7 @@ class Actor : Thinker native native vector3 Vec2OffsetZ(float x, float y, float atz, bool absolute = false); native void VelFromAngle(float speed = 0, float angle = 0); native bool isFriend(Actor other); + native void AdjustFloorClip(); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); @@ -98,7 +99,22 @@ class Actor : Thinker native // DECORATE setters - it probably makes more sense to set these values directly now... void A_SetMass(int newmass) { mass = newmass; } + void A_SetInvulnerable() { bInvulnerable = true; } + void A_UnSetInvulnerable() { bInvulnerable = false; } + void A_SetReflective() { bReflective = true; } + void A_UnSetReflective() { bReflective = false; } + void A_SetReflectiveInvulnerable() { bInvulnerable = true; bReflective = true; } + void A_UnSetReflectiveInvulnerable() { bInvulnerable = true; bReflective = false; } + void A_SetShootable() { bShootable = true; bNonShootable = false; } + void A_UnSetShootable() { bShootable = false; bNonShootable = true; } + void A_NoGravity() { bNoGravity = true; } + void A_Gravity() { bNoGravity = false; Gravity = 1; } + void A_LowGravity() { bNoGravity = false; Gravity = 0.125; } void A_SetGravity(float newgravity) { gravity = clamp(newgravity, 0., 10.); } + void A_SetFloorClip() { bFloorClip = true; AdjustFloorClip(); } + void A_UnSetFloorClip() { bFloorClip = false; FloorClip = 0; } + void A_HideThing() { bInvisible = true; } + void A_UnHideThing() { bInvisible = false; } void A_SetArg(int arg, int val) { if (arg >= 0 && arg < 5) args[arg] = val; } void A_Turn(float turn = 0) { angle += turn; } void A_SetDamageType(name newdamagetype) { damagetype = newdamagetype; } @@ -208,6 +224,7 @@ class Actor : Thinker native native void A_BFGSpray(class spraytype = "BFGExtra", int numrays = 40, int damagecount = 15, float angle = 90, float distance = 16*64, float vrange = 32, int damage = 0, int flags = 0); native void A_Pain(); native void A_NoBlocking(); + void A_Fall() { A_NoBlocking(); } native void A_XScream(); native void A_Look(); native void A_Chase(state melee = null, state missile = null, int flags = 0); @@ -224,24 +241,6 @@ class Actor : Thinker native native void A_Detonate(); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); - native void A_SetFloorClip(); - native void A_UnSetFloorClip(); - native void A_HideThing(); - native void A_UnHideThing(); - native void A_SetInvulnerable(); - native void A_UnSetInvulnerable(); - native void A_SetReflective(); - native void A_UnSetReflective(); - native void A_SetReflectiveInvulnerable(); - native void A_UnSetReflectiveInvulnerable(); - native void A_SetShootable(); - native void A_UnSetShootable(); - native void A_NoGravity(); - native void A_Gravity(); - native void A_LowGravity(); - - native void A_Fall(); - native void A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); native void A_ScreamAndUnblock(); From 5e76d3af186a9ba78955e22d402feb99d0fef6f7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 00:14:08 +0100 Subject: [PATCH 152/255] - fixed BrainishExplosion and removed some unnecessary checks, the state to be set is being defined in the same file, after all... --- wadsrc/static/zscript/doom/bossbrain.txt | 11 +++++------ 1 file changed, 5 insertions(+), 6 deletions(-) diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt index 2193be954..641263ecc 100644 --- a/wadsrc/static/zscript/doom/bossbrain.txt +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -162,13 +162,12 @@ extend class Actor boom.DeathSound = "misc/brainexplode"; boom.Vel.z = random[BrainScream](0, 255)/128.; - State stt = "BossBrain::Brainexplode"; - if (stt) boom.SetState (stt); + boom.SetState ("BossBrain::Brainexplode"); + boom.bRocketTrail = false; + boom.SetDamage(0); // disables collision detection which is not wanted here + boom.tics -= random[BrainScream](0, 7); + if (boom.tics < 1) boom.tics = 1; } - boom.bRocketTrail = false; - boom.SetDamage(0); // disables collision detection which is not wanted here - boom.tics -= random[BrainScream](0, 7); - if (boom.tics < 1) boom.tics = 1; } void A_BrainScream() From ff8b216167dedc041a422a3c382fef2599264aec Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 10:52:14 +0100 Subject: [PATCH 153/255] SHA-1: 8852bc7278d033bbed66c51bf23aee841ee977a9 * Revert "Modify CMPJMP to produce more compact code (as far as VC++ is concerned, anyway)" This reverts commit 6ff973a06bd97dfd1c2c5191b508fdbd98f62063. This modification did not work and broke the comparisons. Actually this had three problems: * the asserts checked the wrong instruction * the mask was not applied to regular comparisons. * incrementing PC before testing does not work because 'test' references the PC. --- src/scripting/vm/vmexec.cpp | 14 ++++------- src/scripting/vm/vmexec.h | 46 ++++++++++++++++++------------------- 2 files changed, 27 insertions(+), 33 deletions(-) diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index af25030a9..57ce48a95 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -82,17 +82,11 @@ #define THROW(x) throw(EVMAbortException(x)) #define CMPJMP(test) \ - pc++; \ - if (VM_UBYTE(test) == VM_UBYTE(a)) { \ + if ((test) == (a & CMP_CHECK)) { \ assert(pc[1].op == OP_JMP); \ - pc += JMPOFS(pc); \ - } - -#define CMPJMP_MASK(test) \ - pc++; \ - if (VM_UBYTE(test) == (VM_UBYTE(a) & CMP_CHECK)) { \ - assert(pc[1].op == OP_JMP); \ - pc += JMPOFS(pc); \ + pc += 1 + JMPOFS(pc+1); \ + } else { \ + pc += 1; \ } #define GETADDR(a,o,x) \ diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 500c30c66..69f406dd8 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1199,88 +1199,88 @@ begin: ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(reg.f[C] - reg.f[B]) < VM_EPSILON); + CMPJMP(fabs(reg.f[C] - reg.f[B]) < VM_EPSILON); } else { - CMPJMP_MASK(reg.f[C] == reg.f[B]); + CMPJMP(reg.f[C] == reg.f[B]); } NEXTOP; OP(EQF_K): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(konstf[C] - reg.f[B]) < VM_EPSILON); + CMPJMP(fabs(konstf[C] - reg.f[B]) < VM_EPSILON); } else { - CMPJMP_MASK(konstf[C] == reg.f[B]); + CMPJMP(konstf[C] == reg.f[B]); } NEXTOP; OP(LTF_RR): ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - reg.f[C]) < -VM_EPSILON); + CMPJMP((reg.f[B] - reg.f[C]) < -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] < reg.f[C]); + CMPJMP(reg.f[B] < reg.f[C]); } NEXTOP; OP(LTF_RK): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - konstf[C]) < -VM_EPSILON); + CMPJMP((reg.f[B] - konstf[C]) < -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] < konstf[C]); + CMPJMP(reg.f[B] < konstf[C]); } NEXTOP; OP(LTF_KR): ASSERTKF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((konstf[B] - reg.f[C]) < -VM_EPSILON); + CMPJMP((konstf[B] - reg.f[C]) < -VM_EPSILON); } else { - CMPJMP_MASK(konstf[B] < reg.f[C]); + CMPJMP(konstf[B] < reg.f[C]); } NEXTOP; OP(LEF_RR): ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - reg.f[C]) <= -VM_EPSILON); + CMPJMP((reg.f[B] - reg.f[C]) <= -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] <= reg.f[C]); + CMPJMP(reg.f[B] <= reg.f[C]); } NEXTOP; OP(LEF_RK): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - konstf[C]) <= -VM_EPSILON); + CMPJMP((reg.f[B] - konstf[C]) <= -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] <= konstf[C]); + CMPJMP(reg.f[B] <= konstf[C]); } NEXTOP; OP(LEF_KR): ASSERTKF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((konstf[B] - reg.f[C]) <= -VM_EPSILON); + CMPJMP((konstf[B] - reg.f[C]) <= -VM_EPSILON); } else { - CMPJMP_MASK(konstf[B] <= reg.f[C]); + CMPJMP(konstf[B] <= reg.f[C]); } NEXTOP; @@ -1369,12 +1369,12 @@ begin: Do_EQV2: if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && - fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); + CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); + CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); } NEXTOP; OP(EQV2_K): @@ -1496,13 +1496,13 @@ begin: Do_EQV3: if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && - fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON && - fabs(reg.f[B+2] - fcp[2]) < VM_EPSILON); + CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON && + fabs(reg.f[B+2] - fcp[2]) < VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); + CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); } NEXTOP; OP(EQV3_K): From 703aaa373e0127657cd88960c48bb330a99324fc Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 10:52:14 +0100 Subject: [PATCH 154/255] SHA-1: 8852bc7278d033bbed66c51bf23aee841ee977a9 * Revert "Modify CMPJMP to produce more compact code (as far as VC++ is concerned, anyway)" This reverts commit 6ff973a06bd97dfd1c2c5191b508fdbd98f62063. This modification did not work and broke the comparisons. Actually this had three problems: * the asserts checked the wrong instruction * the mask was not applied to regular comparisons. * incrementing PC before testing does not work because 'test' references the PC. --- src/scripting/vm/vmexec.cpp | 14 ++++------- src/scripting/vm/vmexec.h | 46 ++++++++++++++++++------------------- 2 files changed, 27 insertions(+), 33 deletions(-) diff --git a/src/scripting/vm/vmexec.cpp b/src/scripting/vm/vmexec.cpp index af25030a9..57ce48a95 100644 --- a/src/scripting/vm/vmexec.cpp +++ b/src/scripting/vm/vmexec.cpp @@ -82,17 +82,11 @@ #define THROW(x) throw(EVMAbortException(x)) #define CMPJMP(test) \ - pc++; \ - if (VM_UBYTE(test) == VM_UBYTE(a)) { \ + if ((test) == (a & CMP_CHECK)) { \ assert(pc[1].op == OP_JMP); \ - pc += JMPOFS(pc); \ - } - -#define CMPJMP_MASK(test) \ - pc++; \ - if (VM_UBYTE(test) == (VM_UBYTE(a) & CMP_CHECK)) { \ - assert(pc[1].op == OP_JMP); \ - pc += JMPOFS(pc); \ + pc += 1 + JMPOFS(pc+1); \ + } else { \ + pc += 1; \ } #define GETADDR(a,o,x) \ diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 500c30c66..69f406dd8 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1199,88 +1199,88 @@ begin: ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(reg.f[C] - reg.f[B]) < VM_EPSILON); + CMPJMP(fabs(reg.f[C] - reg.f[B]) < VM_EPSILON); } else { - CMPJMP_MASK(reg.f[C] == reg.f[B]); + CMPJMP(reg.f[C] == reg.f[B]); } NEXTOP; OP(EQF_K): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(konstf[C] - reg.f[B]) < VM_EPSILON); + CMPJMP(fabs(konstf[C] - reg.f[B]) < VM_EPSILON); } else { - CMPJMP_MASK(konstf[C] == reg.f[B]); + CMPJMP(konstf[C] == reg.f[B]); } NEXTOP; OP(LTF_RR): ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - reg.f[C]) < -VM_EPSILON); + CMPJMP((reg.f[B] - reg.f[C]) < -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] < reg.f[C]); + CMPJMP(reg.f[B] < reg.f[C]); } NEXTOP; OP(LTF_RK): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - konstf[C]) < -VM_EPSILON); + CMPJMP((reg.f[B] - konstf[C]) < -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] < konstf[C]); + CMPJMP(reg.f[B] < konstf[C]); } NEXTOP; OP(LTF_KR): ASSERTKF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((konstf[B] - reg.f[C]) < -VM_EPSILON); + CMPJMP((konstf[B] - reg.f[C]) < -VM_EPSILON); } else { - CMPJMP_MASK(konstf[B] < reg.f[C]); + CMPJMP(konstf[B] < reg.f[C]); } NEXTOP; OP(LEF_RR): ASSERTF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - reg.f[C]) <= -VM_EPSILON); + CMPJMP((reg.f[B] - reg.f[C]) <= -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] <= reg.f[C]); + CMPJMP(reg.f[B] <= reg.f[C]); } NEXTOP; OP(LEF_RK): ASSERTF(B); ASSERTKF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((reg.f[B] - konstf[C]) <= -VM_EPSILON); + CMPJMP((reg.f[B] - konstf[C]) <= -VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] <= konstf[C]); + CMPJMP(reg.f[B] <= konstf[C]); } NEXTOP; OP(LEF_KR): ASSERTKF(B); ASSERTF(C); if (a & CMP_APPROX) { - CMPJMP_MASK((konstf[B] - reg.f[C]) <= -VM_EPSILON); + CMPJMP((konstf[B] - reg.f[C]) <= -VM_EPSILON); } else { - CMPJMP_MASK(konstf[B] <= reg.f[C]); + CMPJMP(konstf[B] <= reg.f[C]); } NEXTOP; @@ -1369,12 +1369,12 @@ begin: Do_EQV2: if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && - fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); + CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); + CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1]); } NEXTOP; OP(EQV2_K): @@ -1496,13 +1496,13 @@ begin: Do_EQV3: if (a & CMP_APPROX) { - CMPJMP_MASK(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && - fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON && - fabs(reg.f[B+2] - fcp[2]) < VM_EPSILON); + CMPJMP(fabs(reg.f[B ] - fcp[0]) < VM_EPSILON && + fabs(reg.f[B+1] - fcp[1]) < VM_EPSILON && + fabs(reg.f[B+2] - fcp[2]) < VM_EPSILON); } else { - CMPJMP_MASK(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); + CMPJMP(reg.f[B] == fcp[0] && reg.f[B+1] == fcp[1] && reg.f[B+2] == fcp[2]); } NEXTOP; OP(EQV3_K): From 570572fcf2f6561c920279c98df53b79a79d86b7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 11:44:48 +0100 Subject: [PATCH 155/255] - scriptified a_hereticimp.cpp. - fixed the comparison against 0 simplification which did not negate the result for '=='. --- src/CMakeLists.txt | 1 - src/g_heretic/a_hereticimp.cpp | 96 ----------------- src/scripting/codegeneration/codegen.cpp | 103 ++++++++++--------- wadsrc/static/zscript/heretic/hereticimp.txt | 79 ++++++++++++-- 4 files changed, 128 insertions(+), 151 deletions(-) delete mode 100644 src/g_heretic/a_hereticimp.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 12df2e61c..adc90444d 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -845,7 +845,6 @@ set( NOT_COMPILED_SOURCE_FILES g_heretic/a_chicken.cpp g_heretic/a_dsparil.cpp g_heretic/a_hereticartifacts.cpp - g_heretic/a_hereticimp.cpp g_heretic/a_hereticweaps.cpp g_heretic/a_ironlich.cpp g_heretic/a_knight.cpp diff --git a/src/g_heretic/a_hereticimp.cpp b/src/g_heretic/a_hereticimp.cpp deleted file mode 100644 index 39dfb049e..000000000 --- a/src/g_heretic/a_hereticimp.cpp +++ /dev/null @@ -1,96 +0,0 @@ -/* -#include "templates.h" -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "gstrings.h" -#include "vm.h" -*/ - -static FRandom pr_impmsatk ("ImpMsAttack"); -static FRandom pr_imp ("ImpExplode"); - - -//---------------------------------------------------------------------------- -// -// PROC A_ImpMsAttack -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_ImpMsAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target || pr_impmsatk() > 64) - { - self->SetState (self->SeeState); - return 0; - } - A_SkullAttack(self, 12.); - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_ImpExplode -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_ImpExplode) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *chunk; - - self->flags &= ~MF_NOGRAVITY; - - chunk = Spawn("HereticImpChunk1", self->Pos(), ALLOW_REPLACE); - chunk->Vel.X = pr_imp.Random2() / 64.; - chunk->Vel.Y = pr_imp.Random2() / 64.; - chunk->Vel.Z = 9; - - chunk = Spawn("HereticImpChunk2", self->Pos(), ALLOW_REPLACE); - chunk->Vel.X = pr_imp.Random2() / 64.; - chunk->Vel.Y = pr_imp.Random2() / 64.; - chunk->Vel.Z = 9; - if (self->special1 == 666) - { // Extreme death crash - self->SetState (self->FindState("XCrash")); - } - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_ImpDeath -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_ImpDeath) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags &= ~MF_SOLID; - self->flags2 |= MF2_FLOORCLIP; - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_ImpXDeath1 -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_ImpXDeath1) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->flags &= ~MF_SOLID; - self->flags |= MF_NOGRAVITY; - self->flags2 |= MF2_FLOORCLIP; - self->special1 = 666; // Flag the crash routine - return 0; -} - diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f1dfab523..d3923b231 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3091,64 +3091,71 @@ FxExpression *FxCompareEq::Resolve(FCompileContext& ctx) } else { - // also simplify comparisons against zero. For these a bool cast on the other value will do just as well and create better code. - if (left->isConstant()) + // also simplify comparisons against zero. For these a bool cast/unary not on the other value will do just as well and create better code. + if (Operator != TK_ApproxEq) { - bool leftisnull; - switch (left->ValueType->GetRegType()) + if (left->isConstant()) { - case REGT_INT: - leftisnull = static_cast(left)->GetValue().GetInt() == 0; - break; + bool leftisnull; + switch (left->ValueType->GetRegType()) + { + case REGT_INT: + leftisnull = static_cast(left)->GetValue().GetInt() == 0; + break; - case REGT_FLOAT: - assert(left->ValueType->GetRegCount() == 1); // vectors should not be able to get here. - leftisnull = static_cast(left)->GetValue().GetFloat() == 0; - break; + case REGT_FLOAT: + assert(left->ValueType->GetRegCount() == 1); // vectors should not be able to get here. + leftisnull = static_cast(left)->GetValue().GetFloat() == 0; + break; - case REGT_POINTER: - leftisnull = static_cast(left)->GetValue().GetPointer() == nullptr; - break; + case REGT_POINTER: + leftisnull = static_cast(left)->GetValue().GetPointer() == nullptr; + break; + + default: + leftisnull = false; + } + if (leftisnull) + { + FxExpression *x; + if (Operator == TK_Eq) x = new FxUnaryNotBoolean(right); + else x = new FxBoolCast(right); + right = nullptr; + delete this; + return x->Resolve(ctx); + } - default: - leftisnull = false; } - if (leftisnull) + if (right->isConstant()) { - FxExpression *x = new FxBoolCast(right); - right = nullptr; - delete this; - return x->Resolve(ctx); - } - - } - if (right->isConstant()) - { - bool rightisnull; - switch (right->ValueType->GetRegType()) - { - case REGT_INT: - rightisnull = static_cast(right)->GetValue().GetInt() == 0; - break; + bool rightisnull; + switch (right->ValueType->GetRegType()) + { + case REGT_INT: + rightisnull = static_cast(right)->GetValue().GetInt() == 0; + break; - case REGT_FLOAT: - assert(right->ValueType->GetRegCount() == 1); // vectors should not be able to get here. - rightisnull = static_cast(right)->GetValue().GetFloat() == 0; - break; + case REGT_FLOAT: + assert(right->ValueType->GetRegCount() == 1); // vectors should not be able to get here. + rightisnull = static_cast(right)->GetValue().GetFloat() == 0; + break; - case REGT_POINTER: - rightisnull = static_cast(right)->GetValue().GetPointer() == nullptr; - break; + case REGT_POINTER: + rightisnull = static_cast(right)->GetValue().GetPointer() == nullptr; + break; - default: - rightisnull = false; - } - if (rightisnull) - { - FxExpression *x = new FxBoolCast(left); - left = nullptr; - delete this; - return x->Resolve(ctx); + default: + rightisnull = false; + } + if (rightisnull) + { + FxExpression *x; + if (Operator == TK_Eq) x = new FxUnaryNotBoolean(left); + else x = new FxBoolCast(left); + left = nullptr; + delete this; + return x->Resolve(ctx); + } } } } diff --git a/wadsrc/static/zscript/heretic/hereticimp.txt b/wadsrc/static/zscript/heretic/hereticimp.txt index 5764094de..34738ed56 100644 --- a/wadsrc/static/zscript/heretic/hereticimp.txt +++ b/wadsrc/static/zscript/heretic/hereticimp.txt @@ -3,6 +3,8 @@ class HereticImp : Actor { + bool extremecrash; + Default { Health 40; @@ -26,12 +28,6 @@ class HereticImp : Actor HitObituary "$OB_HERETICIMPHIT"; } - native void A_ImpMsAttack(); - native void A_ImpDeath(); - native void A_ImpXDeath1(); - native void A_ImpExplode(); - - States { Spawn: @@ -75,6 +71,77 @@ class HereticImp : Actor IMPX Z -1; Stop; } + + + //---------------------------------------------------------------------------- + // + // PROC A_ImpMsAttack + // + //---------------------------------------------------------------------------- + + void A_ImpMsAttack() + { + if (!target || random[ImpMSAtk]() > 64) + { + SetState (SeeState); + return; + } + A_SkullAttack(12); +} + + //---------------------------------------------------------------------------- + // + // PROC A_ImpExplode + // + //---------------------------------------------------------------------------- + + void A_ImpExplode() + { + Actor chunk; + + bNoGravity = false; + + chunk = Spawn("HereticImpChunk1", pos, ALLOW_REPLACE); + chunk.vel.x = random2[ImpExplode]() / 64.; + chunk.vel.y = random2[ImpExplode]() / 64.; + chunk.vel.z = 9; + + chunk = Spawn("HereticImpChunk2", pos, ALLOW_REPLACE); + chunk.vel.x = random2[ImpExplode]() / 64.; + chunk.vel.y = random2[ImpExplode]() / 64.; + chunk.vel.z = 9; + + if (extremecrash) + { + SetState ("XCrash"); + } + } + + //---------------------------------------------------------------------------- + // + // PROC A_ImpDeath + // + //---------------------------------------------------------------------------- + + void A_ImpDeath() + { + bSolid = false; + bFloorClip = true; + } + + //---------------------------------------------------------------------------- + // + // PROC A_ImpXDeath1 + // + //---------------------------------------------------------------------------- + + void A_ImpXDeath1() + { + bSolid = false; + bFloorClip = true; + bNoGravity = true; + extremecrash = true; + } } // Heretic imp leader ------------------------------------------------------- From 3a7f51db88e281970693c5d33ae057755620cd73 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 13:39:37 +0100 Subject: [PATCH 156/255] a_hereticimp.cpp does not exist anymore... --- src/g_heretic/a_hereticmisc.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/src/g_heretic/a_hereticmisc.cpp b/src/g_heretic/a_hereticmisc.cpp index 2d4f3497c..2ea39a4bc 100644 --- a/src/g_heretic/a_hereticmisc.cpp +++ b/src/g_heretic/a_hereticmisc.cpp @@ -24,7 +24,6 @@ #include "a_chicken.cpp" #include "a_dsparil.cpp" #include "a_hereticartifacts.cpp" -#include "a_hereticimp.cpp" #include "a_hereticweaps.cpp" #include "a_ironlich.cpp" #include "a_knight.cpp" From eca4fba0f638a40d27f7262bad14baf4b98a4a4e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 14:15:09 +0100 Subject: [PATCH 157/255] - fixed a merge conflict which wasn't flagged by TortoiseMerge. --- src/p_actionfunctions.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index c625bd927..7ec8bb874 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -994,7 +994,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlaySound) PARAM_FLOAT_DEF (volume); PARAM_BOOL_DEF (looping); PARAM_FLOAT_DEF (attenuation); - PARAM_BOOL_OPT (local) { local = false; } + PARAM_BOOL_DEF (local); if (!looping) { From ff66dc3189bb4fd5941d37affbca5a11587180af Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 15:46:15 +0100 Subject: [PATCH 158/255] - flatten FxBinaryLogical chains into a single node for more efficient processing. --- src/scripting/codegeneration/codegen.cpp | 100 ++++++++++++----------- src/scripting/codegeneration/codegen.h | 2 + 2 files changed, 55 insertions(+), 47 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d3923b231..620d9feed 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3583,9 +3583,47 @@ FxExpression *FxBinaryLogical::Resolve(FCompileContext& ctx) return x; } } + Flatten(); return this; } +//========================================================================== +// +// flatten a list of the same operator into a single node. +// +//========================================================================== + +void FxBinaryLogical::Flatten() +{ + if (left->ExprType == EFX_BinaryLogical && static_cast(left)->Operator == Operator) + { + list = std::move(static_cast(left)->list); + delete left; + } + else + { + list.Push(left); + } + + if (right->ExprType == EFX_BinaryLogical && static_cast(right)->Operator == Operator) + { + auto &rlist = static_cast(right)->list; + auto cnt = rlist.Size(); + auto v = list.Reserve(cnt); + for (unsigned i = 0; i < cnt; i++) + { + list[v + i] = rlist[i]; + rlist[i] = nullptr; + } + delete right; + } + else + { + list.Push(right); + } + left = right = nullptr; +} + //========================================================================== // // @@ -3594,56 +3632,24 @@ FxExpression *FxBinaryLogical::Resolve(FCompileContext& ctx) ExpEmit FxBinaryLogical::Emit(VMFunctionBuilder *build) { - // This is not the "right" way to do these, but it works for now. - // (Problem: No information sharing is done between nodes to reduce the - // code size if you have something like a1 && a2 && a3 && ... && an.) - assert(left->ValueType->GetRegType() == REGT_INT && right->ValueType->GetRegType() == REGT_INT); - ExpEmit op1 = left->Emit(build); - assert(!op1.Konst); + TArray patchspots; + int zero = build->GetConstantInt(0); - op1.Free(build); - - if (Operator == TK_AndAnd) + for (unsigned i = 0; i < list.Size(); i++) { - build->Emit(OP_EQ_K, 1, op1.RegNum, zero); - // If op1 is 0, skip evaluation of op2. - size_t patchspot = build->Emit(OP_JMP, 0, 0, 0); - - // Evaluate op2. - ExpEmit op2 = right->Emit(build); - assert(!op2.Konst); - op2.Free(build); - - ExpEmit to(build, REGT_INT); - build->Emit(OP_EQ_K, 1, op2.RegNum, zero); - build->Emit(OP_JMP, 2); - build->Emit(OP_LI, to.RegNum, 1); - build->Emit(OP_JMP, 1); - size_t target = build->Emit(OP_LI, to.RegNum, 0); - build->Backpatch(patchspot, target); - return to; - } - else - { - assert(Operator == TK_OrOr); - build->Emit(OP_EQ_K, 0, op1.RegNum, zero); - // If op1 is not 0, skip evaluation of op2. - size_t patchspot = build->Emit(OP_JMP, 0, 0, 0); - - // Evaluate op2. - ExpEmit op2 = right->Emit(build); - assert(!op2.Konst); - op2.Free(build); - - ExpEmit to(build, REGT_INT); - build->Emit(OP_EQ_K, 0, op2.RegNum, zero); - build->Emit(OP_JMP, 2); - build->Emit(OP_LI, to.RegNum, 0); - build->Emit(OP_JMP, 1); - size_t target = build->Emit(OP_LI, to.RegNum, 1); - build->Backpatch(patchspot, target); - return to; + assert(list[i]->ValueType->GetRegType() == REGT_INT); + ExpEmit op1 = list[i]->Emit(build); + assert(!op1.Konst); + op1.Free(build); + build->Emit(OP_EQ_K, (Operator == TK_AndAnd) ? 1 : 0, op1.RegNum, zero); + patchspots.Push(build->Emit(OP_JMP, 0, 0, 0)); } + ExpEmit to(build, REGT_INT); + build->Emit(OP_LI, to.RegNum, (Operator == TK_AndAnd) ? 1 : 0); + build->Emit(OP_JMP, 1); + auto ctarget = build->Emit(OP_LI, to.RegNum, (Operator == TK_AndAnd) ? 0 : 1); + for (auto addr : patchspots) build->Backpatch(addr, ctarget); + return to; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index cfe261b39..ee792e5bf 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -910,9 +910,11 @@ public: int Operator; FxExpression *left; FxExpression *right; + TDeletingArray list; FxBinaryLogical(int, FxExpression*, FxExpression*); ~FxBinaryLogical(); + void Flatten(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); From 6aecb29995914acb5c2768ebaaba10b465be82bc Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 2 Nov 2016 16:05:57 +0100 Subject: [PATCH 159/255] - fixed: The VM function builder was set up with the wrong number of implicit arguments. --- src/scripting/vm/vmbuilder.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index d2d9e7140..41ec4b920 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -701,7 +701,7 @@ void FFunctionBuildList::Build() FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate); // Allocate registers for the function's arguments and create local variable nodes before starting to resolve it. - VMFunctionBuilder buildit(!!(item.Func->Variants[0].Flags & VARF_Action)); + VMFunctionBuilder buildit(item.Func->GetImplicitArgs()); for(unsigned i=0;iVariants[0].Proto->ArgumentTypes.Size();i++) { auto type = item.Func->Variants[0].Proto->ArgumentTypes[i]; From a45523fb63239a4d9a35a596f0bcb7131c1a56a2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 3 Nov 2016 13:38:40 +0100 Subject: [PATCH 160/255] - scriptified A_SpawnFly. - added support for global variables to the code generator - not the compiler, though. For the handful of entries this is needed for it may just as well be done manually. So far FLevelLocals level is the only one being exported. - fixed: The VM disassembler truncated 64 bit pointers to 15 digits because the output buffer was too small. - resolve entire FxSequences instead of aborting on the first failed entry. This allows to output all errors at once. --- src/dobjtype.cpp | 34 +++++++-- src/dobjtype.h | 4 +- src/g_level.cpp | 59 ++++++++++++++ src/g_level.h | 2 +- src/p_enemy.cpp | 7 ++ src/p_map.cpp | 11 +++ src/p_mobj.cpp | 15 ++++ src/scripting/codegeneration/codegen.cpp | 97 +++++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 20 +++++ src/scripting/thingdef.cpp | 2 + src/scripting/thingdef_data.cpp | 17 ++++- src/scripting/vm/vmbuilder.h | 2 + src/scripting/vm/vmdisasm.cpp | 4 +- wadsrc/static/zscript/actor.txt | 4 + wadsrc/static/zscript/doom/bossbrain.txt | 35 +++------ 15 files changed, 274 insertions(+), 39 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 57a67384a..53eedc456 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2100,6 +2100,7 @@ PStruct::PStruct(FName name, PTypeBase *outer) { mDescriptiveName.Format("Struct<%s>", name.GetChars()); Size = 0; + HasNativeFields = false; } //========================================================================== @@ -2114,7 +2115,7 @@ void PStruct::SetDefaultValue(void *base, unsigned offset, TArrayFlags & VARF_Native)) { - field->Type->SetDefaultValue(base, offset + field->Offset, special); + field->Type->SetDefaultValue(base, unsigned(offset + field->Offset), special); } } } @@ -2216,13 +2217,13 @@ bool PStruct::ReadFields(FSerializer &ar, void *addr) const PField *PStruct::AddField(FName name, PType *type, DWORD flags) { - PField *field = new PField(name, type); + PField *field = new PField(name, type, flags); // The new field is added to the end of this struct, alignment permitting. field->Offset = (Size + (type->Align - 1)) & ~(type->Align - 1); // Enlarge this struct to enclose the new field. - Size = field->Offset + type->Size; + Size = unsigned(field->Offset + type->Size); // This struct's alignment is the same as the largest alignment of any of // its fields. @@ -2238,6 +2239,29 @@ PField *PStruct::AddField(FName name, PType *type, DWORD flags) return field; } +//========================================================================== +// +// PStruct :: AddField +// +// Appends a new native field to the struct. Returns either the new field +// or NULL if a symbol by that name already exists. +// +//========================================================================== + +PField *PStruct::AddNativeField(FName name, PType *type, size_t address, DWORD flags, int bitvalue) +{ + PField *field = new PField(name, type, flags|VARF_Native, address, bitvalue); + + if (Symbols.AddSymbol(field) == nullptr) + { // name is already in use + delete field; + return nullptr; + } + Fields.Push(field); + HasNativeFields = true; + return field; +} + //========================================================================== // // PStruct :: PropagateMark @@ -2286,7 +2310,7 @@ PField::PField() } PField::PField(FName name, PType *type, DWORD flags, size_t offset, int bitvalue) - : PSymbol(name), Offset(unsigned(offset)), Type(type), Flags(flags) + : PSymbol(name), Offset(offset), Type(type), Flags(flags) { BitValue = bitvalue; if (bitvalue > -1) @@ -3085,7 +3109,7 @@ PField *PClass::AddField(FName name, PType *type, DWORD flags) { Defaults = (BYTE *)M_Realloc(Defaults, Size); memset(Defaults + oldsize, 0, Size - oldsize); - type->SetDefaultValue(Defaults, field->Offset, &SpecialInits); + type->SetDefaultValue(Defaults, unsigned(field->Offset), &SpecialInits); } return field; } diff --git a/src/dobjtype.h b/src/dobjtype.h index 5aeefac50..db468870f 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -574,7 +574,7 @@ class PField : public PSymbol public: PField(FName name, PType *type, DWORD flags = 0, size_t offset = 0, int bitvalue = -1); - unsigned int Offset; + size_t Offset; PType *Type; DWORD Flags; int BitValue; @@ -669,8 +669,10 @@ public: PStruct(FName name, PTypeBase *outer); TArray Fields; + bool HasNativeFields; virtual PField *AddField(FName name, PType *type, DWORD flags=0); + virtual PField *AddNativeField(FName name, PType *type, size_t address, DWORD flags = 0, int bitvalue = -1); size_t PropagateMark(); diff --git a/src/g_level.cpp b/src/g_level.cpp index 9e8448879..5b0c46fa2 100644 --- a/src/g_level.cpp +++ b/src/g_level.cpp @@ -1848,6 +1848,65 @@ void FLevelLocals::AddScroller (int secnum) } } +//========================================================================== +// +// sets up the script-side version of FLevelLocals +// Since this is a global variable and the script compiler does +// not allow defining them, it will be fully set up here. +// +//========================================================================== + +inline int val2bit(int val) +{ + int bit = 0; + while ((val >>= 1)) bit++; + return bit; +} + +void G_InitLevelLocalsForScript() +{ + PStruct *lstruct = NewStruct("LevelLocals", nullptr); + PField *levelf = new PField("level", lstruct, VARF_Native | VARF_Static, (intptr_t)&level); + GlobalSymbols.AddSymbol(levelf); + + // This only exports a selection of fields. Not everything here is useful to the playsim. + lstruct->AddNativeField("time", TypeSInt32, myoffsetof(FLevelLocals, time), VARF_ReadOnly); + lstruct->AddNativeField("maptime", TypeSInt32, myoffsetof(FLevelLocals, maptime), VARF_ReadOnly); + lstruct->AddNativeField("totaltime", TypeSInt32, myoffsetof(FLevelLocals, totaltime), VARF_ReadOnly); + lstruct->AddNativeField("starttime", TypeSInt32, myoffsetof(FLevelLocals, starttime), VARF_ReadOnly); + lstruct->AddNativeField("partime", TypeSInt32, myoffsetof(FLevelLocals, partime), VARF_ReadOnly); + lstruct->AddNativeField("sucktime", TypeSInt32, myoffsetof(FLevelLocals, sucktime), VARF_ReadOnly); + lstruct->AddNativeField("cluster", TypeSInt32, myoffsetof(FLevelLocals, cluster), VARF_ReadOnly); + lstruct->AddNativeField("clusterflags", TypeSInt32, myoffsetof(FLevelLocals, clusterflags), VARF_ReadOnly); + lstruct->AddNativeField("levelnum", TypeSInt32, myoffsetof(FLevelLocals, levelnum), VARF_ReadOnly); + //lstruct->AddNativeField("levelname", TypeString, myoffsetof(FLevelLocals, LevelName), VARF_ReadOnly); // must use an access function to resolve string table references. + lstruct->AddNativeField("mapname", TypeString, myoffsetof(FLevelLocals, MapName), VARF_ReadOnly); + lstruct->AddNativeField("nextmap", TypeString, myoffsetof(FLevelLocals, NextMap)); + lstruct->AddNativeField("nextsecretmap", TypeString, myoffsetof(FLevelLocals, NextSecretMap)); + lstruct->AddNativeField("maptype", TypeSInt32, myoffsetof(FLevelLocals, maptype), VARF_ReadOnly); + lstruct->AddNativeField("monsterstelefrag", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, val2bit(LEVEL_MONSTERSTELEFRAG)); + lstruct->AddNativeField("actownspecial", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, val2bit(LEVEL_ACTOWNSPECIAL)); + lstruct->AddNativeField("sndseqtotalctrl", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, val2bit(LEVEL_SNDSEQTOTALCTRL)); + lstruct->AddNativeField("allmap", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_ALLMAP)); + lstruct->AddNativeField("missilesactivateimpact", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_MISSILESACTIVATEIMPACT)); + lstruct->AddNativeField("monsterfallingdamage", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_MONSTERFALLINGDAMAGE)); + lstruct->AddNativeField("checkswitchrange", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_CHECKSWITCHRANGE)); + lstruct->AddNativeField("polygrind", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_POLYGRIND)); + lstruct->AddNativeField("music", TypeString, myoffsetof(FLevelLocals, Music), VARF_ReadOnly); + lstruct->AddNativeField("musicorder", TypeSInt32, myoffsetof(FLevelLocals, musicorder), VARF_ReadOnly); + lstruct->AddNativeField("total_secrets", TypeSInt32, myoffsetof(FLevelLocals, total_secrets), VARF_ReadOnly); + lstruct->AddNativeField("found_secrets", TypeSInt32, myoffsetof(FLevelLocals, found_secrets)); + lstruct->AddNativeField("total_items", TypeSInt32, myoffsetof(FLevelLocals, total_items), VARF_ReadOnly); + lstruct->AddNativeField("found_items", TypeSInt32, myoffsetof(FLevelLocals, found_items)); + lstruct->AddNativeField("total_monsters", TypeSInt32, myoffsetof(FLevelLocals, total_monsters), VARF_ReadOnly); + lstruct->AddNativeField("killed_monsters", TypeSInt32, myoffsetof(FLevelLocals, killed_monsters)); + lstruct->AddNativeField("gravity", TypeFloat64, myoffsetof(FLevelLocals, gravity)); + lstruct->AddNativeField("aircontrol", TypeFloat64, myoffsetof(FLevelLocals, aircontrol)); + lstruct->AddNativeField("airfriction", TypeFloat64, myoffsetof(FLevelLocals, airfriction)); + lstruct->AddNativeField("airsupply", TypeSInt32, myoffsetof(FLevelLocals, airsupply)); + lstruct->AddNativeField("teamdamage", TypeFloat64, myoffsetof(FLevelLocals, teamdamage)); +} + //========================================================================== // // Lists all currently defined maps diff --git a/src/g_level.h b/src/g_level.h index 2b0de7b68..790eba344 100644 --- a/src/g_level.h +++ b/src/g_level.h @@ -260,7 +260,7 @@ struct FOptionalMapinfoDataPtr typedef TMap FOptData; typedef TMap FMusicMap; -enum EMapType +enum EMapType : int { MAPTYPE_UNKNOWN = 0, MAPTYPE_DOOM, diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 77082f3a4..833732008 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -1790,6 +1790,13 @@ bool P_LookForPlayers (AActor *actor, INTBOOL allaround, FLookExParams *params) } } +DEFINE_ACTION_FUNCTION(AActor, LookForPlayers) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_BOOL(allaround); + ACTION_RETURN_BOOL(P_LookForPlayers(self, allaround, nullptr)); +} + // // ACTION ROUTINES // diff --git a/src/p_map.cpp b/src/p_map.cpp index a2e83b73f..d7bffa589 100644 --- a/src/p_map.cpp +++ b/src/p_map.cpp @@ -444,6 +444,17 @@ bool P_TeleportMove(AActor* thing, const DVector3 &pos, bool telefrag, bool modi return true; } +DEFINE_ACTION_FUNCTION(AActor, TeleportMove) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(x); + PARAM_FLOAT(y); + PARAM_FLOAT(z); + PARAM_BOOL(telefrag); + PARAM_BOOL_DEF(modify); + ACTION_RETURN_BOOL(P_TeleportMove(self, DVector3(x, y, z), telefrag, modify)); +} + //========================================================================== // // [RH] P_PlayerStartStomp diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index bd78fdcef..08b662767 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -990,6 +990,15 @@ void AActor::CopyFriendliness (AActor *other, bool changeTarget, bool resetHealt level.total_monsters += CountsAsKill(); } +DEFINE_ACTION_FUNCTION(AActor, CopyFriendliness) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(other, AActor); + PARAM_BOOL_DEF(changetarget); + PARAM_BOOL_DEF(resethealth); + self->CopyFriendliness(other, changetarget, resethealth); + return 0; +} //============================================================================ // // AActor :: ObtainInventory @@ -6515,6 +6524,12 @@ DDropItem *AActor::GetDropItems() const return GetClass()->DropItems; } +DEFINE_ACTION_FUNCTION(AActor, GetDropItems) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_OBJECT(self->GetDropItems()); +} + double AActor::GetGravity() const { if (flags & MF_NOGRAVITY) return 0; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 620d9feed..50cd7699b 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5067,6 +5067,12 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as global constant\n", Identifier.GetChars()); newex = FxConstant::MakeConstant(sym, ScriptPosition); } + else if (sym->IsKindOf(RUNTIME_CLASS(PField))) + { + // internally defined global variable + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as global variable\n", Identifier.GetChars()); + newex = new FxGlobalVariable(static_cast(sym), ScriptPosition); + } else { ScriptPosition.Message(MSG_ERROR, "Invalid global identifier '%s'\n", Identifier.GetChars()); @@ -5303,6 +5309,72 @@ ExpEmit FxSelf::Emit(VMFunctionBuilder *build) } +//========================================================================== +// +// +// +//========================================================================== + +FxGlobalVariable::FxGlobalVariable(PField* mem, const FScriptPosition &pos) + : FxExpression(EFX_GlobalVariable, pos) +{ + membervar = mem; + AddressRequested = false; + AddressWritable = true; // must be true unless classx tells us otherwise if requested. +} + +//========================================================================== +// +// +// +//========================================================================== + +bool FxGlobalVariable::RequestAddress(bool *writable) +{ + AddressRequested = true; + if (writable != nullptr) *writable = AddressWritable && !(membervar->Flags & VARF_ReadOnly); + return true; +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxGlobalVariable::Resolve(FCompileContext &ctx) +{ + CHECKRESOLVED(); + ValueType = membervar->Type; + return this; +} + +ExpEmit FxGlobalVariable::Emit(VMFunctionBuilder *build) +{ + ExpEmit obj(build, REGT_POINTER); + + build->Emit(OP_LKP, obj.RegNum, build->GetConstantAddress((void*)(intptr_t)membervar->Offset, ATAG_GENERIC)); + if (AddressRequested) + { + return obj; + } + + ExpEmit loc(build, membervar->Type->GetRegType(), membervar->Type->GetRegCount()); + + if (membervar->BitValue == -1) + { + int offsetreg = build->GetConstantInt(0); + build->Emit(membervar->Type->GetLoadOp(), loc.RegNum, obj.RegNum, offsetreg); + } + else + { + build->Emit(OP_LBIT, loc.RegNum, obj.RegNum, 1 << membervar->BitValue); + } + obj.Free(build); + return loc; +} + + //========================================================================== // // @@ -5377,11 +5449,21 @@ FxExpression *FxStructMember::Resolve(FCompileContext &ctx) classx = nullptr; return x; } + else if (classx->ExprType == EFX_GlobalVariable) + { + auto parentfield = static_cast(classx)->membervar; + auto newfield = new PField(membervar->SymbolName, membervar->Type, membervar->Flags | parentfield->Flags, membervar->Offset + parentfield->Offset, membervar->BitValue); + static_cast(classx)->membervar = newfield; + classx->isresolved = false; // re-resolve the parent so it can also check if it can be optimized away. + auto x = classx->Resolve(ctx); + classx = nullptr; + return x; + } else if (classx->ExprType == EFX_LocalVariable && classx->IsVector()) // vectors are a special case because they are held in registers { // since this is a vector, all potential things that may get here are single float or an xy-vector. auto locvar = static_cast(classx); - locvar->RegOffset = membervar->Offset / 8; + locvar->RegOffset = int(membervar->Offset / 8); locvar->ValueType = membervar->Type; classx = nullptr; delete this; @@ -5816,13 +5898,15 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Name: case NAME_Color: case NAME_Sound: + case NAME_State: if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) { PType *type = MethodName == NAME_Int ? TypeSInt32 : MethodName == NAME_uInt ? TypeUInt32 : MethodName == NAME_Double ? TypeFloat64 : MethodName == NAME_Name ? TypeName : - MethodName == NAME_Color ? TypeColor : (PType*)TypeSound; + MethodName == NAME_Color ? TypeColor : + MethodName == NAME_State? TypeState :(PType*)TypeSound; func = new FxTypeCast((*ArgList)[0], type, true, true); (*ArgList)[0] = nullptr; @@ -6615,14 +6699,19 @@ ExpEmit FxVectorBuiltin::Emit(VMFunctionBuilder *build) FxExpression *FxSequence::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); + bool fail = false; for (unsigned i = 0; i < Expressions.Size(); ++i) { if (nullptr == (Expressions[i] = Expressions[i]->Resolve(ctx))) { - delete this; - return nullptr; + fail = true; } } + if (fail) + { + delete this; + return nullptr; + } return this; } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index ee792e5bf..b118b8d5d 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -269,6 +269,7 @@ enum EFxType EFX_VectorBuiltin, EFX_TypeCheck, EFX_DynamicCast, + EFX_GlobalVariable, EFX_COUNT }; @@ -1136,6 +1137,25 @@ public: }; +//========================================================================== +// +// FxGlobalVariaböe +// +//========================================================================== + +class FxGlobalVariable : public FxExpression +{ +public: + PField *membervar; + bool AddressRequested; + bool AddressWritable; + + FxGlobalVariable(PField*, const FScriptPosition&); + FxExpression *Resolve(FCompileContext&); + bool RequestAddress(bool *writable); + ExpEmit Emit(VMFunctionBuilder *build); +}; + //========================================================================== // // FxClassMember diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 8c42e8987..38bf2bcf6 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -215,6 +215,7 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, //========================================================================== void ParseScripts(); void ParseAllDecorate(); +void G_InitLevelLocalsForScript(); void LoadActors () { @@ -223,6 +224,7 @@ void LoadActors () timer.Reset(); timer.Clock(); FScriptPosition::ResetErrorCounter(); + G_InitLevelLocalsForScript(); InitThingdef(); FScriptPosition::StrictErrors = true; ParseScripts(); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index b0edcb167..4d18a083b 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -673,10 +673,16 @@ void InitThingdef() qsort(&AFTable[0], AFTable.Size(), sizeof(AFTable[0]), funccmp); } + PType *TypeActor = NewPointer(RUNTIME_CLASS(AActor)); + + PStruct *sstruct = NewStruct("Sector", nullptr); + auto sptr = NewPointer(sstruct); + sstruct->AddNativeField("soundtarget", TypeActor, myoffsetof(sector_t, SoundTarget)); + // Define some member variables we feel like exposing to the user PSymbolTable &symt = RUNTIME_CLASS(AActor)->Symbols; PType *array5 = NewArray(TypeSInt32, 5); - PType *TypeActor = NewPointer(RUNTIME_CLASS(AActor)); + symt.AddSymbol(new PField("sector", sptr, VARF_Native, myoffsetof(AActor, Sector))); symt.AddSymbol(new PField(NAME_Alpha, TypeFloat64, VARF_Native, myoffsetof(AActor, Alpha))); symt.AddSymbol(new PField(NAME_Angle, TypeFloat64, VARF_Native, myoffsetof(AActor, Angles.Yaw))); symt.AddSymbol(new PField(NAME_Args, array5, VARF_Native, myoffsetof(AActor, args))); @@ -725,12 +731,14 @@ void InitThingdef() symt.AddSymbol(new PField("RipperLevel", TypeSInt32, VARF_Native, myoffsetof(AActor, RipperLevel))); symt.AddSymbol(new PField("RipLevelMin", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMin))); symt.AddSymbol(new PField("RipLevelMax", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMax))); + symt.AddSymbol(new PField("special2", TypeSInt32, VARF_Native, myoffsetof(AActor, special2))); symt.AddSymbol(new PField(NAME_VisibleStartAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartAngle))); symt.AddSymbol(new PField(NAME_VisibleStartPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartPitch))); symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); symt.AddSymbol(new PField("AttackSound", TypeSound, VARF_Native, myoffsetof(AActor, AttackSound))); symt.AddSymbol(new PField("DeathSound", TypeSound, VARF_Native, myoffsetof(AActor, DeathSound))); + symt.AddSymbol(new PField("SeeSound", TypeSound, VARF_Native, myoffsetof(AActor, SeeSound))); symt.AddSymbol(new PField("Pos", TypeVector3, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos))); symt.AddSymbol(new PField("Vel", TypeVector3, VARF_Native, myoffsetof(AActor, Vel))); symt.AddSymbol(new PField("Scale", TypeVector2, VARF_Native, myoffsetof(AActor, Scale))); @@ -761,8 +769,11 @@ void InitThingdef() PSymbolTable &symt2 = RUNTIME_CLASS(DDropItem)->Symbols; PType *TypeDropItem = NewPointer(RUNTIME_CLASS(DDropItem)); symt2.AddSymbol(new PField("Next", TypeDropItem, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Next))); - symt2.AddSymbol(new PField("ItemName", TypeName, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Name))); + symt2.AddSymbol(new PField("Name", TypeName, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Name))); symt2.AddSymbol(new PField("Probability", TypeSInt32, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Probability))); - symt2.AddSymbol(new PField("Amount", TypeSInt32, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Amount))); + symt2.AddSymbol(new PField("Amount", TypeSInt32, VARF_Native, myoffsetof(DDropItem, Amount))); + + PSymbolTable &symt3 = RUNTIME_CLASS(DObject)->Symbols; + symt3.AddSymbol(new PField("bDestroyed", TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(DObject, ObjectFlags), 5/*OF_EuthanizeMe*/)); } diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index 9a97c216d..c94d85f3c 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -30,6 +30,8 @@ public: // Returns the constant register holding the value. int GetConstantInt(int val); + int GetConstantInt(size_t val) { return GetConstantInt(int(val)); } + int GetConstantInt(unsigned val) { return GetConstantInt(int(val)); } int GetConstantFloat(double val); int GetConstantAddress(void *ptr, VM_ATAG tag); int GetConstantString(FString str); diff --git a/src/scripting/vm/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp index ea199612c..239a0dc51 100644 --- a/src/scripting/vm/vmdisasm.cpp +++ b/src/scripting/vm/vmdisasm.cpp @@ -199,7 +199,7 @@ static int printf_wrapper(FILE *f, const char *fmt, ...) void VMDumpConstants(FILE *out, const VMScriptFunction *func) { - char tmp[21]; + char tmp[30]; int i, j, k, kk; if (func->KonstD != NULL && func->NumKonstD != 0) @@ -239,7 +239,7 @@ void VMDumpConstants(FILE *out, const VMScriptFunction *func) for (j = 0, k = i; j < 4 && k < func->NumKonstA; j++, k += kk) { mysnprintf(tmp, countof(tmp), "%3d. %p:%d", k, func->KonstA[k].v, func->KonstATags()[k]); - printf_wrapper(out, "%-20s", tmp); + printf_wrapper(out, "%-22s", tmp); } printf_wrapper(out, "\n"); } diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 0b3c4d40b..091fba4b5 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -77,6 +77,10 @@ class Actor : Thinker native native void VelFromAngle(float speed = 0, float angle = 0); native bool isFriend(Actor other); native void AdjustFloorClip(); + native DropItem GetDropItems(); + native void CopyFriendliness (Actor other, bool changeTarget, bool resetHealth = true); + native bool LookForPlayers(bool allaround); + native bool TeleportMove(Vector3 pos, bool telefrag, bool modifyactor = true); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt index 641263ecc..cb30e886b 100644 --- a/wadsrc/static/zscript/doom/bossbrain.txt +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -280,13 +280,12 @@ extend class Actor } */ - /* private void SpawnFly(class spawntype, sound snd) { - AActor newmobj; - AActor fog; - AActor eye = master; // The eye is the spawnshot's master, not the target! - AActor targ = target; // Unlike other projectiles, the target is the intended destination. + Actor newmobj; + Actor fog; + Actor eye = master; // The eye is the spawnshot's master, not the target! + Actor targ = target; // Unlike other projectiles, the target is the intended destination. int r; // [GZ] Should be more viable than a countdown... @@ -307,7 +306,7 @@ extend class Actor if (fog) A_PlaySound(snd, CHAN_BODY); } - class SpawnName; + class SpawnName = null; DropItem di; // di will be our drop item list iterator DropItem drop; // while drop stays as the reference point. @@ -334,7 +333,7 @@ extend class Actor } } di = drop; - n = randon[pr_spawnfly](0, n); + n = random[pr_spawnfly](0, n); while (n >= 0) { if (di.Name != 'none') @@ -385,11 +384,11 @@ extend class Actor // (if the player has made noise). newmobj.LastHeard = newmobj.Sector.SoundTarget; - if (newmobj.SeeState != null && newmobj.LookForPlayers (true, null)) + if (newmobj.SeeState != null && newmobj.LookForPlayers (true)) { newmobj.SetState (newmobj.SeeState); } - if (!(newmobj.ObjectFlags & OF_EuthanizeMe)) + if (!newmobj.bDestroyed) { // telefrag anything in this spot newmobj.TeleportMove (newmobj.pos, true); @@ -401,13 +400,8 @@ extend class Actor // remove self (i.e., cube). Destroy (); } - */ - - native - void A_SpawnFly(class spawntype = null) // needs special treatment for default - ; - /* + void A_SpawnFly(class spawntype = null) { sound snd; if (spawntype != null) @@ -419,18 +413,13 @@ extend class Actor spawntype = "SpawnFire"; snd = "brain/spawn"; } - SpawnFly(self, spawntype, snd); + SpawnFly(spawntype, snd); } - */ - - native - void A_SpawnSound() - ; - /* + + void A_SpawnSound() { // travelling cube sound A_PlaySound("brain/cube", CHAN_BODY); SpawnFly("SpawnFire", "brain/spawn"); } - */ } From 830500512516d363f5e3970864a47537c01d89b3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 3 Nov 2016 13:39:51 +0100 Subject: [PATCH 161/255] - remove debug message. --- wadsrc/static/zscript/doom/bossbrain.txt | 1 - 1 file changed, 1 deletion(-) diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt index cb30e886b..b1aa901a3 100644 --- a/wadsrc/static/zscript/doom/bossbrain.txt +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -189,7 +189,6 @@ extend class Actor void A_BrainDie() { - A_Log("A_BrainDie"); // [RH] If noexit, then don't end the level. if ((GetCVar("deathmatch") || GetCVar("alwaysapplydmflags")) && GetCVar("sv_noexit")) return; From 995f01f8aa3b8d7e5796f4ad6b875e98b8915419 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 3 Nov 2016 14:23:29 +0100 Subject: [PATCH 162/255] - removed obsolete code from a_bossbrain.cpp. - fixed: divisions wasted one register for each operation due to a double allocation. - changed math operations to use less registers. There was a well-intended change to allocate the destination first, but the better approach is to first allocate the operands and free then before allocating the destination register. --- src/g_doom/a_bossbrain.cpp | 150 ----------------------- src/scripting/codegeneration/codegen.cpp | 12 +- 2 files changed, 6 insertions(+), 156 deletions(-) diff --git a/src/g_doom/a_bossbrain.cpp b/src/g_doom/a_bossbrain.cpp index f58e75375..5807ce175 100644 --- a/src/g_doom/a_bossbrain.cpp +++ b/src/g_doom/a_bossbrain.cpp @@ -78,153 +78,3 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BrainSpit) return 0; } -static void SpawnFly(AActor *self, PClassActor *spawntype, FSoundID sound) -{ - AActor *newmobj; - AActor *fog; - AActor *eye = self->master; // The eye is the spawnshot's master, not the target! - AActor *targ = self->target; // Unlike other projectiles, the target is the intended destination. - int r; - - // [GZ] Should be more viable than a countdown... - if (self->special2 != 0) - { - if (self->special2 > level.maptime) - return; // still flying - } - else - { - if (self->reactiontime == 0 || --self->reactiontime != 0) - return; // still flying - } - - if (spawntype != NULL) - { - fog = Spawn (spawntype, targ->Pos(), ALLOW_REPLACE); - if (fog != NULL) S_Sound (fog, CHAN_BODY, sound, 1, ATTN_NORM); - } - - FName SpawnName; - - DDropItem *di; // di will be our drop item list iterator - DDropItem *drop; // while drop stays as the reference point. - int n = 0; - - // First see if this cube has its own actor list - drop = self->GetDropItems(); - - // If not, then default back to its master's list - if (drop == NULL && eye != NULL) - drop = eye->GetDropItems(); - - if (drop != NULL) - { - for (di = drop; di != NULL; di = di->Next) - { - if (di->Name != NAME_None) - { - if (di->Amount < 0) - { - di->Amount = 1; // default value is -1, we need a positive value. - } - n += di->Amount; // this is how we can weight the list. - } - } - di = drop; - n = pr_spawnfly(n); - while (n >= 0) - { - if (di->Name != NAME_None) - { - n -= di->Amount; // logically, none of the -1 values have survived by now. - } - if ((di->Next != NULL) && (n >= 0)) - { - di = di->Next; - } - else - { - n = -1; - } - } - SpawnName = di->Name; - } - if (SpawnName == NAME_None) - { - // Randomly select monster to spawn. - r = pr_spawnfly (); - - // Probability distribution (kind of :), - // decreasing likelihood. - if (r < 50) SpawnName = "DoomImp"; - else if (r < 90) SpawnName = "Demon"; - else if (r < 120) SpawnName = "Spectre"; - else if (r < 130) SpawnName = "PainElemental"; - else if (r < 160) SpawnName = "Cacodemon"; - else if (r < 162) SpawnName = "Archvile"; - else if (r < 172) SpawnName = "Revenant"; - else if (r < 192) SpawnName = "Arachnotron"; - else if (r < 222) SpawnName = "Fatso"; - else if (r < 246) SpawnName = "HellKnight"; - else SpawnName = "BaronOfHell"; - } - spawntype = PClass::FindActor(SpawnName); - if (spawntype != NULL) - { - newmobj = Spawn (spawntype, targ->Pos(), ALLOW_REPLACE); - if (newmobj != NULL) - { - // Make the new monster hate what the boss eye hates - if (eye != NULL) - { - newmobj->CopyFriendliness (eye, false); - } - // Make it act as if it was around when the player first made noise - // (if the player has made noise). - newmobj->LastHeard = newmobj->Sector->SoundTarget; - - if (newmobj->SeeState != NULL && P_LookForPlayers (newmobj, true, NULL)) - { - newmobj->SetState (newmobj->SeeState); - } - if (!(newmobj->ObjectFlags & OF_EuthanizeMe)) - { - // telefrag anything in this spot - P_TeleportMove (newmobj, newmobj->Pos(), true); - } - newmobj->flags4 |= MF4_BOSSSPAWNED; - } - } - - // remove self (i.e., cube). - self->Destroy (); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnFly) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_CLASS_DEF(spawntype, AActor); - - FSoundID sound; - - if (spawntype != NULL) - { - sound = GetDefaultByType(spawntype)->SeeSound; - } - else - { - spawntype = PClass::FindActor("SpawnFire"); - sound = "brain/spawn"; - } - SpawnFly(self, spawntype, sound); - return 0; -} - -// travelling cube sound -DEFINE_ACTION_FUNCTION(AActor, A_SpawnSound) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_BODY, "brain/cube", 1, ATTN_IDLE); - SpawnFly(self, PClass::FindActor("SpawnFire"), "brain/spawn"); - return 0; -} diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 50cd7699b..4c26da595 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -2563,8 +2563,6 @@ FxExpression *FxAddSub::Resolve(FCompileContext& ctx) ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) { assert(Operator == '+' || Operator == '-'); - // allocate the result first so that the operation does not leave gaps in the register set. - ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); if (Operator == '+') @@ -2577,6 +2575,7 @@ ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) assert(!op1.Konst); op1.Free(build); op2.Free(build); + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); if (IsVector()) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); @@ -2608,6 +2607,7 @@ ExpEmit FxAddSub::Emit(VMFunctionBuilder *build) assert(!op1.Konst || !op2.Konst); op1.Free(build); op2.Free(build); + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); if (IsVector()) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); @@ -2720,7 +2720,6 @@ FxExpression *FxMulDiv::Resolve(FCompileContext& ctx) ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) { // allocate the result first so that the operation does not leave gaps in the register set. - ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); ExpEmit op1 = left->Emit(build); ExpEmit op2 = right->Emit(build); @@ -2740,9 +2739,10 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) { op = Operator == '*' ? (ValueType == TypeVector2 ? OP_MULVF2_RR : OP_MULVF3_RR) : (ValueType == TypeVector2 ? OP_DIVVF2_RR : OP_DIVVF3_RR); } - build->Emit(op, to.RegNum, op1.RegNum, op2.RegNum); op1.Free(build); op2.Free(build); + ExpEmit to(build, ValueType->GetRegType(), ValueType->GetRegCount()); + build->Emit(op, to.RegNum, op1.RegNum, op2.RegNum); return to; } @@ -2756,6 +2756,7 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) assert(!op1.Konst); op1.Free(build); op2.Free(build); + ExpEmit to(build, ValueType->GetRegType()); if (ValueType->GetRegType() == REGT_FLOAT) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); @@ -2777,10 +2778,10 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) assert(Operator == '%' || Operator == '/'); op1.Free(build); op2.Free(build); + ExpEmit to(build, ValueType->GetRegType()); if (ValueType->GetRegType() == REGT_FLOAT) { assert(op1.RegType == REGT_FLOAT && op2.RegType == REGT_FLOAT); - ExpEmit to(build, REGT_FLOAT); build->Emit(Operator == '/' ? (op1.Konst ? OP_DIVF_KR : op2.Konst ? OP_DIVF_RK : OP_DIVF_RR) : (op1.Konst ? OP_MODF_KR : op2.Konst ? OP_MODF_RK : OP_MODF_RR), to.RegNum, op1.RegNum, op2.RegNum); @@ -2790,7 +2791,6 @@ ExpEmit FxMulDiv::Emit(VMFunctionBuilder *build) { assert(ValueType->GetRegType() == REGT_INT); assert(op1.RegType == REGT_INT && op2.RegType == REGT_INT); - ExpEmit to(build, REGT_INT); build->Emit(Operator == '/' ? (op1.Konst ? OP_DIV_KR : op2.Konst ? OP_DIV_RK : OP_DIV_RR) : (op1.Konst ? OP_MOD_KR : op2.Konst ? OP_MOD_RK : OP_MOD_RR), to.RegNum, op1.RegNum, op2.RegNum); From 9188dc07a7254cf3134508168cb3f7327af5bc50 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 3 Nov 2016 14:38:18 +0100 Subject: [PATCH 163/255] - removed excess parameter from A_FadeIn. --- src/p_actionfunctions.cpp | 1 - 1 file changed, 1 deletion(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 7ec8bb874..9ed20daf8 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -3398,7 +3398,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FadeIn) PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT_DEF(reduce); PARAM_INT_DEF(flags); - PARAM_NAME_DEF(fontname); if (reduce == 0) From c9dad704086ac9880ab207b90634107bddd7da52 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 3 Nov 2016 16:46:55 +0100 Subject: [PATCH 164/255] - removed the GetConstantInt overloads since it appears they are not needed. --- src/scripting/vm/vmbuilder.h | 2 -- 1 file changed, 2 deletions(-) diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index c94d85f3c..9a97c216d 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -30,8 +30,6 @@ public: // Returns the constant register holding the value. int GetConstantInt(int val); - int GetConstantInt(size_t val) { return GetConstantInt(int(val)); } - int GetConstantInt(unsigned val) { return GetConstantInt(int(val)); } int GetConstantFloat(double val); int GetConstantAddress(void *ptr, VM_ATAG tag); int GetConstantString(FString str); From 956304530501b82f8c96fad9c6b56bb3d2238498 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 00:19:36 +0100 Subject: [PATCH 165/255] - moved declaration of native fields into the respective class definitions. This bypasses a declaration in the script in favor of a simpler implementation. In order to work it is always necessary to have an offset table to map the variables to, but doing it fully on the native side only requires adding the type to the declaration. --- src/actor.h | 2 + src/dobject.cpp | 13 ++++ src/dobject.h | 25 ++++++-- src/dobjtype.cpp | 9 ++- src/g_level.cpp | 23 +++---- src/p_acs.cpp | 4 +- src/p_mobj.cpp | 108 +++++++++++++++++++++++++++++++- src/scripting/thingdef.cpp | 2 - src/scripting/thingdef_data.cpp | 108 ++++---------------------------- 9 files changed, 170 insertions(+), 124 deletions(-) diff --git a/src/actor.h b/src/actor.h index df5ef3c17..833cd2c0a 100644 --- a/src/actor.h +++ b/src/actor.h @@ -565,6 +565,7 @@ class DDropItem : public DObject { DECLARE_CLASS(DDropItem, DObject) HAS_OBJECT_POINTERS + HAS_FIELDS public: DDropItem *Next; FName Name; @@ -578,6 +579,7 @@ const double MinVel = EQUAL_EPSILON; class AActor : public DThinker { DECLARE_CLASS_WITH_META (AActor, DThinker, PClassActor) + HAS_FIELDS HAS_OBJECT_POINTERS public: AActor () throw(); diff --git a/src/dobject.cpp b/src/dobject.cpp index beef73c89..56d12787f 100644 --- a/src/dobject.cpp +++ b/src/dobject.cpp @@ -62,6 +62,7 @@ ClassReg DObject::RegistrationInfo = NULL, // ParentType NULL, // Pointers &DObject::InPlaceConstructor, // ConstructNative + &DObject::InitNativeFields, sizeof(DObject), // SizeOf CLASSREG_PClass, // MetaClassNum }; @@ -344,6 +345,18 @@ DObject::~DObject () // //========================================================================== +void DObject::InitNativeFields() +{ + auto meta = RUNTIME_CLASS(DObject); + meta->AddNativeField("bDestroyed", TypeSInt32, myoffsetof(DObject, ObjectFlags), VARF_ReadOnly, OF_EuthanizeMe); +} + +//========================================================================== +// +// +// +//========================================================================== + void DObject::Destroy () { ObjectFlags = (ObjectFlags & ~OF_Fixed) | OF_EuthanizeMe; diff --git a/src/dobject.h b/src/dobject.h index 91a80f9d0..ea0a44a85 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -111,6 +111,7 @@ struct ClassReg ClassReg *ParentType; const size_t *Pointers; void (*ConstructNative)(void *); + void(*InitNatives)(); unsigned int SizeOf:28; unsigned int MetaClassNum:4; @@ -147,6 +148,9 @@ protected: \ #define HAS_OBJECT_POINTERS \ static const size_t PointerOffsets[]; +#define HAS_FIELDS \ + static void InitNativeFields(); + // Taking the address of a field in an object at address 1 instead of // address 0 keeps GCC from complaining about possible misuse of offsetof. #define DECLARE_POINTER(field) (size_t)&((ThisClass*)1)->field - 1, @@ -159,13 +163,14 @@ protected: \ # define _DECLARE_TI(cls) ClassReg * const cls::RegistrationInfoPtr __attribute__((section(SECTION_CREG))) = &cls::RegistrationInfo; #endif -#define _IMP_PCLASS(cls,ptrs,create) \ +#define _IMP_PCLASS(cls,ptrs,create, initn) \ ClassReg cls::RegistrationInfo = {\ NULL, \ #cls, \ &cls::Super::RegistrationInfo, \ ptrs, \ create, \ + initn, \ sizeof(cls), \ cls::MetaClassNum }; \ _DECLARE_TI(cls) \ @@ -176,18 +181,27 @@ protected: \ #define IMPLEMENT_POINTY_CLASS(cls) \ _IMP_CREATE_OBJ(cls) \ - _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor) \ + _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor, nullptr) \ + const size_t cls::PointerOffsets[] = { + +#define IMPLEMENT_POINTY_CLASS_WITH_FIELDS(cls) \ + _IMP_CREATE_OBJ(cls) \ + _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor, cls::InitNativeFields) \ const size_t cls::PointerOffsets[] = { #define IMPLEMENT_CLASS(cls) \ _IMP_CREATE_OBJ(cls) \ - _IMP_PCLASS(cls,NULL,cls::InPlaceConstructor) + _IMP_PCLASS(cls,nullptr,cls::InPlaceConstructor, nullptr) + +#define IMPLEMENT_CLASS_WITH_FIELDS(cls) \ + _IMP_CREATE_OBJ(cls) \ + _IMP_PCLASS(cls,nullptr,cls::InPlaceConstructor, cls::InitNativeFields) #define IMPLEMENT_ABSTRACT_CLASS(cls) \ - _IMP_PCLASS(cls,NULL,NULL) + _IMP_PCLASS(cls,nullptr,nullptr,nullptr) #define IMPLEMENT_ABSTRACT_POINTY_CLASS(cls) \ - _IMP_PCLASS(cls,cls::PointerOffsets,NULL) \ + _IMP_PCLASS(cls,cls::PointerOffsets,nullptr,nullptr) \ const size_t cls::PointerOffsets[] = { enum EObjectFlags @@ -438,6 +452,7 @@ public: virtual PClass *StaticType() const { return RegistrationInfo.MyClass; } static ClassReg RegistrationInfo, * const RegistrationInfoPtr; static void InPlaceConstructor (void *mem); + static void InitNativeFields(); typedef PClass MetaClass; private: typedef DObject ThisClass; diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 53eedc456..631a7e6ee 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2309,13 +2309,18 @@ PField::PField() { } + PField::PField(FName name, PType *type, DWORD flags, size_t offset, int bitvalue) : PSymbol(name), Offset(offset), Type(type), Flags(flags) { BitValue = bitvalue; - if (bitvalue > -1) + if (bitvalue != -1) { - if (type->IsA(RUNTIME_CLASS(PInt)) && unsigned(bitvalue) < 8 * type->Size) + BitValue = 0; + unsigned val = bitvalue; + while ((val >>= 1)) BitValue++; + + if (type->IsA(RUNTIME_CLASS(PInt)) && unsigned(BitValue) < 8u * type->Size) { // map to the single bytes in the actual variable. The internal bit instructions operate on 8 bit values. #ifndef __BIG_ENDIAN__ diff --git a/src/g_level.cpp b/src/g_level.cpp index 5b0c46fa2..b13a39e20 100644 --- a/src/g_level.cpp +++ b/src/g_level.cpp @@ -1856,13 +1856,6 @@ void FLevelLocals::AddScroller (int secnum) // //========================================================================== -inline int val2bit(int val) -{ - int bit = 0; - while ((val >>= 1)) bit++; - return bit; -} - void G_InitLevelLocalsForScript() { PStruct *lstruct = NewStruct("LevelLocals", nullptr); @@ -1884,14 +1877,14 @@ void G_InitLevelLocalsForScript() lstruct->AddNativeField("nextmap", TypeString, myoffsetof(FLevelLocals, NextMap)); lstruct->AddNativeField("nextsecretmap", TypeString, myoffsetof(FLevelLocals, NextSecretMap)); lstruct->AddNativeField("maptype", TypeSInt32, myoffsetof(FLevelLocals, maptype), VARF_ReadOnly); - lstruct->AddNativeField("monsterstelefrag", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, val2bit(LEVEL_MONSTERSTELEFRAG)); - lstruct->AddNativeField("actownspecial", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, val2bit(LEVEL_ACTOWNSPECIAL)); - lstruct->AddNativeField("sndseqtotalctrl", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, val2bit(LEVEL_SNDSEQTOTALCTRL)); - lstruct->AddNativeField("allmap", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_ALLMAP)); - lstruct->AddNativeField("missilesactivateimpact", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_MISSILESACTIVATEIMPACT)); - lstruct->AddNativeField("monsterfallingdamage", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_MONSTERFALLINGDAMAGE)); - lstruct->AddNativeField("checkswitchrange", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_CHECKSWITCHRANGE)); - lstruct->AddNativeField("polygrind", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, val2bit(LEVEL2_POLYGRIND)); + lstruct->AddNativeField("monsterstelefrag", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, LEVEL_MONSTERSTELEFRAG); + lstruct->AddNativeField("actownspecial", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, LEVEL_ACTOWNSPECIAL); + lstruct->AddNativeField("sndseqtotalctrl", TypeSInt32, myoffsetof(FLevelLocals, flags), VARF_ReadOnly, LEVEL_SNDSEQTOTALCTRL); + lstruct->AddNativeField("allmap", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, (LEVEL2_ALLMAP)); + lstruct->AddNativeField("missilesactivateimpact", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, LEVEL2_MISSILESACTIVATEIMPACT); + lstruct->AddNativeField("monsterfallingdamage", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, LEVEL2_MONSTERFALLINGDAMAGE); + lstruct->AddNativeField("checkswitchrange", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, LEVEL2_CHECKSWITCHRANGE); + lstruct->AddNativeField("polygrind", TypeSInt32, myoffsetof(FLevelLocals, flags2), 0, LEVEL2_POLYGRIND); lstruct->AddNativeField("music", TypeString, myoffsetof(FLevelLocals, Music), VARF_ReadOnly); lstruct->AddNativeField("musicorder", TypeSInt32, myoffsetof(FLevelLocals, musicorder), VARF_ReadOnly); lstruct->AddNativeField("total_secrets", TypeSInt32, myoffsetof(FLevelLocals, total_secrets), VARF_ReadOnly); diff --git a/src/p_acs.cpp b/src/p_acs.cpp index a6197e9a6..4024bc9f9 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -5389,11 +5389,11 @@ doplaysound: if (funcIndex == ACSF_PlayActorSound) { if (!looping) { - S_PlaySound(spot, chan, sid, vol, atten, local); + S_PlaySound(spot, chan, sid, vol, atten, !!local); } else if (!S_IsActorPlayingSomething(spot, chan & 7, sid)) { - S_PlaySound(spot, chan | CHAN_LOOP, sid, vol, atten, local); + S_PlaySound(spot, chan | CHAN_LOOP, sid, vol, atten, !!local); } } } diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 08b662767..cf0a033b3 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -131,7 +131,7 @@ CVAR (Int, cl_bloodtype, 0, CVAR_ARCHIVE); // CODE -------------------------------------------------------------------- -IMPLEMENT_POINTY_CLASS (AActor) +IMPLEMENT_POINTY_CLASS_WITH_FIELDS (AActor) DECLARE_POINTER (target) DECLARE_POINTER (lastenemy) DECLARE_POINTER (tracer) @@ -151,6 +151,99 @@ AActor::~AActor () // Use Destroy() instead. } +extern FFlagDef InternalActorFlagDefs[]; +extern FFlagDef ActorFlagDefs[]; + +void AActor::InitNativeFields() +{ + PType *TypeActor = NewPointer(RUNTIME_CLASS(AActor)); + PType *TypeInventory = NewPointer(RUNTIME_CLASS(AInventory)); + PStruct *sstruct = NewStruct("Sector", nullptr); + auto TypeSector = NewPointer(sstruct); + PType *array5 = NewArray(TypeSInt32, 5); + + auto meta = RUNTIME_CLASS(AActor); + + // Define the member variables we feel like exposing to the user + meta->AddNativeField(NAME_Alpha, TypeFloat64, myoffsetof(AActor, Alpha)); + meta->AddNativeField(NAME_Angle, TypeFloat64, myoffsetof(AActor, Angles.Yaw)); + meta->AddNativeField(NAME_Args, array5, myoffsetof(AActor, args)); + meta->AddNativeField(NAME_CeilingZ, TypeFloat64, myoffsetof(AActor, ceilingz), VARF_ReadOnly); + meta->AddNativeField(NAME_FloorZ, TypeFloat64, myoffsetof(AActor, floorz), VARF_ReadOnly); + meta->AddNativeField(NAME_Health, TypeSInt32, myoffsetof(AActor, health), VARF_ReadOnly); + meta->AddNativeField(NAME_Mass, TypeSInt32, myoffsetof(AActor, Mass)); + meta->AddNativeField(NAME_Pitch, TypeFloat64, myoffsetof(AActor, Angles.Pitch)); + meta->AddNativeField(NAME_Roll, TypeFloat64, myoffsetof(AActor, Angles.Roll)); + meta->AddNativeField(NAME_Special, TypeSInt32, myoffsetof(AActor, special)); + meta->AddNativeField(NAME_TID, TypeSInt32, myoffsetof(AActor, tid), VARF_ReadOnly); + meta->AddNativeField(NAME_TIDtoHate, TypeSInt32, myoffsetof(AActor, TIDtoHate), VARF_ReadOnly); + meta->AddNativeField(NAME_WaterLevel, TypeSInt32, myoffsetof(AActor, waterlevel), VARF_ReadOnly); + meta->AddNativeField(NAME_X, TypeFloat64, myoffsetof(AActor, __Pos.X), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! + meta->AddNativeField(NAME_Y, TypeFloat64, myoffsetof(AActor, __Pos.Y), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! + meta->AddNativeField(NAME_Z, TypeFloat64, myoffsetof(AActor, __Pos.Z), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! + meta->AddNativeField(NAME_VelX, TypeFloat64, myoffsetof(AActor, Vel.X), VARF_ReadOnly | VARF_Deprecated); + meta->AddNativeField(NAME_VelY, TypeFloat64, myoffsetof(AActor, Vel.Y), VARF_ReadOnly | VARF_Deprecated); + meta->AddNativeField(NAME_VelZ, TypeFloat64, myoffsetof(AActor, Vel.Z), VARF_ReadOnly | VARF_Deprecated); + meta->AddNativeField(NAME_MomX, TypeFloat64, myoffsetof(AActor, Vel.X), VARF_ReadOnly | VARF_Deprecated); + meta->AddNativeField(NAME_MomY, TypeFloat64, myoffsetof(AActor, Vel.Y), VARF_ReadOnly | VARF_Deprecated); + meta->AddNativeField(NAME_MomZ, TypeFloat64, myoffsetof(AActor, Vel.Z), VARF_ReadOnly | VARF_Deprecated); + meta->AddNativeField(NAME_ScaleX, TypeFloat64, myoffsetof(AActor, Scale.X), VARF_Deprecated); + meta->AddNativeField(NAME_ScaleY, TypeFloat64, myoffsetof(AActor, Scale.Y), VARF_Deprecated); + meta->AddNativeField(NAME_Score, TypeSInt32, myoffsetof(AActor, Score)); + meta->AddNativeField(NAME_Accuracy, TypeSInt32, myoffsetof(AActor, accuracy)); + meta->AddNativeField(NAME_Stamina, TypeSInt32, myoffsetof(AActor, stamina)); + meta->AddNativeField(NAME_Height, TypeFloat64, myoffsetof(AActor, Height)); + meta->AddNativeField(NAME_Radius, TypeFloat64, myoffsetof(AActor, radius), VARF_ReadOnly); + meta->AddNativeField(NAME_ReactionTime, TypeSInt32, myoffsetof(AActor, reactiontime)); + meta->AddNativeField(NAME_MeleeRange, TypeFloat64, myoffsetof(AActor, meleerange)); + meta->AddNativeField(NAME_Speed, TypeFloat64, myoffsetof(AActor, Speed)); + meta->AddNativeField("FloatSpeed", TypeFloat64, myoffsetof(AActor, FloatSpeed)); + meta->AddNativeField("PainThreshold", TypeSInt32, myoffsetof(AActor, PainThreshold)); + meta->AddNativeField("spriteAngle", TypeFloat64, myoffsetof(AActor, SpriteAngle)); + meta->AddNativeField("spriteRotation", TypeFloat64, myoffsetof(AActor, SpriteRotation)); + meta->AddNativeField(NAME_Threshold, TypeSInt32, myoffsetof(AActor, threshold)); + meta->AddNativeField(NAME_DefThreshold, TypeSInt32, myoffsetof(AActor, DefThreshold), VARF_ReadOnly); + meta->AddNativeField(NAME_Damage, TypeSInt32, myoffsetof(AActor, DamageVal), VARF_ReadOnly); + meta->AddNativeField("visdir", TypeSInt32, myoffsetof(AActor, visdir)); + meta->AddNativeField("Gravity", TypeFloat64, myoffsetof(AActor, Gravity)); + meta->AddNativeField("FloorClip", TypeFloat64, myoffsetof(AActor, Floorclip)); + meta->AddNativeField("DamageType", TypeName, myoffsetof(AActor, DamageType)); + meta->AddNativeField("FloatBobPhase", TypeUInt8, myoffsetof(AActor, FloatBobPhase)); + meta->AddNativeField("tics", TypeSInt32, myoffsetof(AActor, tics)); + meta->AddNativeField("RipperLevel", TypeSInt32, myoffsetof(AActor, RipperLevel)); + meta->AddNativeField("RipLevelMin", TypeSInt32, myoffsetof(AActor, RipLevelMin)); + meta->AddNativeField("RipLevelMax", TypeSInt32, myoffsetof(AActor, RipLevelMax)); + meta->AddNativeField("special2", TypeSInt32, myoffsetof(AActor, special2)); + meta->AddNativeField(NAME_VisibleStartAngle, TypeFloat64, myoffsetof(AActor, VisibleStartAngle)); + meta->AddNativeField(NAME_VisibleStartPitch, TypeFloat64, myoffsetof(AActor, VisibleStartPitch)); + meta->AddNativeField(NAME_VisibleEndAngle, TypeFloat64, myoffsetof(AActor, VisibleEndAngle)); + meta->AddNativeField(NAME_VisibleEndPitch, TypeFloat64, myoffsetof(AActor, VisibleEndPitch)); + meta->AddNativeField("AttackSound", TypeSound, myoffsetof(AActor, AttackSound)); + meta->AddNativeField("DeathSound", TypeSound, myoffsetof(AActor, DeathSound)); + meta->AddNativeField("SeeSound", TypeSound, myoffsetof(AActor, SeeSound)); + meta->AddNativeField("Pos", TypeVector3, myoffsetof(AActor, __Pos), VARF_ReadOnly); + meta->AddNativeField("Vel", TypeVector3, myoffsetof(AActor, Vel)); + meta->AddNativeField("Scale", TypeVector2, myoffsetof(AActor, Scale)); + meta->AddNativeField("CurState", TypeState, myoffsetof(AActor, state), VARF_ReadOnly); // has to be renamed on the script side because it clashes with the same named type. + meta->AddNativeField("SeeState", TypeState, myoffsetof(AActor, SeeState), VARF_ReadOnly); + meta->AddNativeField(NAME_Target, TypeActor, myoffsetof(AActor, target)); + meta->AddNativeField(NAME_Master, TypeActor, myoffsetof(AActor, master)); + meta->AddNativeField(NAME_Tracer, TypeActor, myoffsetof(AActor, tracer)); + meta->AddNativeField("LastHeard", TypeActor, myoffsetof(AActor, LastHeard)); + meta->AddNativeField("LastEnemy", TypeActor, myoffsetof(AActor, lastenemy)); + meta->AddNativeField("Sector", TypeSector, myoffsetof(AActor, Sector)); + + // synthesize a symbol for each flag from the flag name tables to avoid redundant declaration of them. + for (size_t i = 0; ActorFlagDefs[i].flagbit != 0xffffffff; i++) + { + meta->AddNativeField(FStringf("b%s", ActorFlagDefs[i].name), (ActorFlagDefs[i].fieldsize == 4? TypeSInt32 : TypeSInt16), ActorFlagDefs[i].structoffset, ActorFlagDefs[i].varflags, ActorFlagDefs[i].flagbit); + } + for (size_t i = 0; InternalActorFlagDefs[i].flagbit != 0xffffffff; i++) + { + meta->AddNativeField(FStringf("b%s", InternalActorFlagDefs[i].name), (InternalActorFlagDefs[i].fieldsize == 4 ? TypeSInt32 : TypeSInt16), InternalActorFlagDefs[i].structoffset, InternalActorFlagDefs[i].varflags, InternalActorFlagDefs[i].flagbit); + } +} + //========================================================================== // // AActor :: Serialize @@ -6707,10 +6800,21 @@ DEFINE_ACTION_FUNCTION(AActor, Vec2OffsetZ) // DropItem handling // //---------------------------------------------------------------------------- -IMPLEMENT_POINTY_CLASS(DDropItem) +IMPLEMENT_POINTY_CLASS_WITH_FIELDS(DDropItem) DECLARE_POINTER(Next) END_POINTERS +void DDropItem::InitNativeFields() +{ + auto meta = RUNTIME_CLASS(DDropItem); + PType *TypeDropItem = NewPointer(RUNTIME_CLASS(DDropItem)); + meta->AddNativeField("Next", TypeDropItem, myoffsetof(DDropItem, Next), VARF_ReadOnly); + meta->AddNativeField("Name", TypeName, myoffsetof(DDropItem, Name), VARF_ReadOnly); + meta->AddNativeField("Probability", TypeSInt32, myoffsetof(DDropItem, Probability), VARF_ReadOnly); + meta->AddNativeField("Amount", TypeSInt32, myoffsetof(DDropItem, Amount)); +} + + void PrintMiscActorInfo(AActor *query) { if (query) diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 38bf2bcf6..8c42e8987 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -215,7 +215,6 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, //========================================================================== void ParseScripts(); void ParseAllDecorate(); -void G_InitLevelLocalsForScript(); void LoadActors () { @@ -224,7 +223,6 @@ void LoadActors () timer.Reset(); timer.Clock(); FScriptPosition::ResetErrorCounter(); - G_InitLevelLocalsForScript(); InitThingdef(); FScriptPosition::StrictErrors = true; ParseScripts(); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 4d18a083b..f628dec3c 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -62,7 +62,7 @@ static TArray AFTable; #define DEFINE_DUMMY_FLAG(name, deprec) { DEPF_UNUSED, #name, -1, 0, deprec? VARF_Deprecated:0 } // internal flags. These do not get exposed to actor definitions but scripts need to be able to access them as variables. -static FFlagDef InternalActorFlagDefs[]= +FFlagDef InternalActorFlagDefs[]= { DEFINE_FLAG(MF, INCHASE, AActor, flags), DEFINE_FLAG(MF, UNMORPHED, AActor, flags), @@ -91,10 +91,11 @@ static FFlagDef InternalActorFlagDefs[]= DEFINE_FLAG(MF6, INTRYMOVE, AActor, flags6), DEFINE_FLAG(MF7, HANDLENODELAY, AActor, flags7), DEFINE_FLAG(MF7, FLYCHEAT, AActor, flags7), + { 0xffffffff } }; -static FFlagDef ActorFlagDefs[]= +FFlagDef ActorFlagDefs[]= { DEFINE_FLAG(MF, PICKUP, APlayerPawn, flags), DEFINE_FLAG(MF, SPECIAL, APlayerPawn, flags), @@ -328,6 +329,7 @@ static FFlagDef ActorFlagDefs[]= DEFINE_FLAG2(BOUNCE_MBF, MBFBOUNCER, AActor, BounceFlags), DEFINE_FLAG2(BOUNCE_AutoOffFloorOnly, BOUNCEAUTOOFFFLOORONLY, AActor, BounceFlags), DEFINE_FLAG2(BOUNCE_UseBounceState, USEBOUNCESTATE, AActor, BounceFlags), + { 0xffffffff } }; // These won't be accessible through bitfield variables @@ -433,7 +435,7 @@ static FFlagDef PowerSpeedFlagDefs[] = static const struct FFlagList { const PClass * const *Type; FFlagDef *Defs; int NumDefs; } FlagLists[] = { - { &RUNTIME_CLASS_CASTLESS(AActor), ActorFlagDefs, countof(ActorFlagDefs) }, + { &RUNTIME_CLASS_CASTLESS(AActor), ActorFlagDefs, countof(ActorFlagDefs)-1 }, // -1 to account for the terminator { &RUNTIME_CLASS_CASTLESS(AActor), MoreFlagDefs, countof(MoreFlagDefs) }, { &RUNTIME_CLASS_CASTLESS(AInventory), InventoryFlagDefs, countof(InventoryFlagDefs) }, { &RUNTIME_CLASS_CASTLESS(AWeapon), WeaponFlagDefs, countof(WeaponFlagDefs) }, @@ -634,6 +636,7 @@ static int funccmp(const void * a, const void * b) // Initialization // //========================================================================== +void G_InitLevelLocalsForScript(); void InitThingdef() { @@ -679,101 +682,14 @@ void InitThingdef() auto sptr = NewPointer(sstruct); sstruct->AddNativeField("soundtarget", TypeActor, myoffsetof(sector_t, SoundTarget)); - // Define some member variables we feel like exposing to the user - PSymbolTable &symt = RUNTIME_CLASS(AActor)->Symbols; - PType *array5 = NewArray(TypeSInt32, 5); - symt.AddSymbol(new PField("sector", sptr, VARF_Native, myoffsetof(AActor, Sector))); - symt.AddSymbol(new PField(NAME_Alpha, TypeFloat64, VARF_Native, myoffsetof(AActor, Alpha))); - symt.AddSymbol(new PField(NAME_Angle, TypeFloat64, VARF_Native, myoffsetof(AActor, Angles.Yaw))); - symt.AddSymbol(new PField(NAME_Args, array5, VARF_Native, myoffsetof(AActor, args))); - symt.AddSymbol(new PField(NAME_CeilingZ, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, ceilingz))); - symt.AddSymbol(new PField(NAME_FloorZ, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, floorz))); - symt.AddSymbol(new PField(NAME_Health, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, health))); - symt.AddSymbol(new PField(NAME_Mass, TypeSInt32, VARF_Native, myoffsetof(AActor, Mass))); - symt.AddSymbol(new PField(NAME_Pitch, TypeFloat64, VARF_Native, myoffsetof(AActor, Angles.Pitch))); - symt.AddSymbol(new PField(NAME_Roll, TypeFloat64, VARF_Native, myoffsetof(AActor, Angles.Roll))); - symt.AddSymbol(new PField(NAME_Special, TypeSInt32, VARF_Native, myoffsetof(AActor, special))); - symt.AddSymbol(new PField(NAME_TID, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, tid))); - symt.AddSymbol(new PField(NAME_TIDtoHate, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, TIDtoHate))); - symt.AddSymbol(new PField(NAME_WaterLevel, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, waterlevel))); - symt.AddSymbol(new PField(NAME_X, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, __Pos.X))); // must remain read-only! - symt.AddSymbol(new PField(NAME_Y, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, __Pos.Y))); // must remain read-only! - symt.AddSymbol(new PField(NAME_Z, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, __Pos.Z))); // must remain read-only! - symt.AddSymbol(new PField(NAME_VelX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.X))); - symt.AddSymbol(new PField(NAME_VelY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Y))); - symt.AddSymbol(new PField(NAME_VelZ, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Z))); - symt.AddSymbol(new PField(NAME_MomX, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.X))); - symt.AddSymbol(new PField(NAME_MomY, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Y))); - symt.AddSymbol(new PField(NAME_MomZ, TypeFloat64, VARF_Native|VARF_ReadOnly|VARF_Deprecated, myoffsetof(AActor, Vel.Z))); - symt.AddSymbol(new PField(NAME_ScaleX, TypeFloat64, VARF_Native|VARF_Deprecated, myoffsetof(AActor, Scale.X))); - symt.AddSymbol(new PField(NAME_ScaleY, TypeFloat64, VARF_Native|VARF_Deprecated, myoffsetof(AActor, Scale.Y))); - symt.AddSymbol(new PField(NAME_Score, TypeSInt32, VARF_Native, myoffsetof(AActor, Score))); - symt.AddSymbol(new PField(NAME_Accuracy, TypeSInt32, VARF_Native, myoffsetof(AActor, accuracy))); - symt.AddSymbol(new PField(NAME_Stamina, TypeSInt32, VARF_Native, myoffsetof(AActor, stamina))); - symt.AddSymbol(new PField(NAME_Height, TypeFloat64, VARF_Native, myoffsetof(AActor, Height))); - symt.AddSymbol(new PField(NAME_Radius, TypeFloat64, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, radius))); - symt.AddSymbol(new PField(NAME_ReactionTime, TypeSInt32, VARF_Native, myoffsetof(AActor, reactiontime))); - symt.AddSymbol(new PField(NAME_MeleeRange, TypeFloat64, VARF_Native, myoffsetof(AActor, meleerange))); - symt.AddSymbol(new PField(NAME_Speed, TypeFloat64, VARF_Native, myoffsetof(AActor, Speed))); - symt.AddSymbol(new PField("FloatSpeed", TypeFloat64, VARF_Native, myoffsetof(AActor, FloatSpeed))); - symt.AddSymbol(new PField("PainThreshold", TypeSInt32, VARF_Native, myoffsetof(AActor, PainThreshold))); - symt.AddSymbol(new PField("spriteAngle", TypeFloat64, VARF_Native, myoffsetof(AActor, SpriteAngle))); - symt.AddSymbol(new PField("spriteRotation", TypeFloat64, VARF_Native, myoffsetof(AActor, SpriteRotation))); - symt.AddSymbol(new PField(NAME_Threshold, TypeSInt32, VARF_Native, myoffsetof(AActor, threshold))); - symt.AddSymbol(new PField(NAME_DefThreshold, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DefThreshold))); - symt.AddSymbol(new PField(NAME_Damage, TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, DamageVal))); - symt.AddSymbol(new PField("visdir", TypeSInt32, VARF_Native, myoffsetof(AActor, visdir))); - symt.AddSymbol(new PField("Gravity", TypeFloat64, VARF_Native, myoffsetof(AActor, Gravity))); - symt.AddSymbol(new PField("FloorClip", TypeFloat64, VARF_Native, myoffsetof(AActor, Floorclip))); - symt.AddSymbol(new PField("DamageType", TypeName, VARF_Native, myoffsetof(AActor, DamageType))); - symt.AddSymbol(new PField("FloatBobPhase", TypeUInt8, VARF_Native, myoffsetof(AActor, FloatBobPhase))); - symt.AddSymbol(new PField("tics", TypeSInt32, VARF_Native, myoffsetof(AActor, tics))); - symt.AddSymbol(new PField("RipperLevel", TypeSInt32, VARF_Native, myoffsetof(AActor, RipperLevel))); - symt.AddSymbol(new PField("RipLevelMin", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMin))); - symt.AddSymbol(new PField("RipLevelMax", TypeSInt32, VARF_Native, myoffsetof(AActor, RipLevelMax))); - symt.AddSymbol(new PField("special2", TypeSInt32, VARF_Native, myoffsetof(AActor, special2))); - symt.AddSymbol(new PField(NAME_VisibleStartAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartAngle))); - symt.AddSymbol(new PField(NAME_VisibleStartPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleStartPitch))); - symt.AddSymbol(new PField(NAME_VisibleEndAngle, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndAngle))); - symt.AddSymbol(new PField(NAME_VisibleEndPitch, TypeFloat64, VARF_Native, myoffsetof(AActor, VisibleEndPitch))); - symt.AddSymbol(new PField("AttackSound", TypeSound, VARF_Native, myoffsetof(AActor, AttackSound))); - symt.AddSymbol(new PField("DeathSound", TypeSound, VARF_Native, myoffsetof(AActor, DeathSound))); - symt.AddSymbol(new PField("SeeSound", TypeSound, VARF_Native, myoffsetof(AActor, SeeSound))); - symt.AddSymbol(new PField("Pos", TypeVector3, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, __Pos))); - symt.AddSymbol(new PField("Vel", TypeVector3, VARF_Native, myoffsetof(AActor, Vel))); - symt.AddSymbol(new PField("Scale", TypeVector2, VARF_Native, myoffsetof(AActor, Scale))); - symt.AddSymbol(new PField("CurState", TypeState, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, state))); // has to be renamed on the script side because it clashes with the same named type. - symt.AddSymbol(new PField("SeeState", TypeState, VARF_Native|VARF_ReadOnly, myoffsetof(AActor, SeeState))); - symt.AddSymbol(new PField(NAME_Target, TypeActor, VARF_Native, myoffsetof(AActor, target))); - symt.AddSymbol(new PField(NAME_Master, TypeActor, VARF_Native, myoffsetof(AActor, master))); - symt.AddSymbol(new PField(NAME_Tracer, TypeActor, VARF_Native, myoffsetof(AActor, tracer))); - symt.AddSymbol(new PField("LastHeard", TypeActor, VARF_Native, myoffsetof(AActor, LastHeard))); - symt.AddSymbol(new PField("LastEnemy", TypeActor, VARF_Native, myoffsetof(AActor, lastenemy))); + G_InitLevelLocalsForScript(); - // synthesize a symbol for each flag. - for (size_t i = 0; i < countof(ActorFlagDefs); i++) + FAutoSegIterator probe(CRegHead, CRegTail); + + while (*++probe != NULL) { - int bit = 0; - unsigned val = ActorFlagDefs[i].flagbit; - while ((val >>= 1)) bit++; - symt.AddSymbol(new PField(FStringf("b%s", ActorFlagDefs[i].name), (ActorFlagDefs[i].fieldsize == 4? TypeSInt32 : TypeSInt16), ActorFlagDefs[i].varflags, ActorFlagDefs[i].structoffset, bit)); + if (((ClassReg *)*probe)->InitNatives) + ((ClassReg *)*probe)->InitNatives(); } - for (size_t i = 0; i < countof(InternalActorFlagDefs); i++) - { - int bit = 0; - unsigned val = InternalActorFlagDefs[i].flagbit; - while ((val >>= 1)) bit++; - symt.AddSymbol(new PField(FStringf("b%s", InternalActorFlagDefs[i].name), (InternalActorFlagDefs[i].fieldsize == 4 ? TypeSInt32 : TypeSInt16), InternalActorFlagDefs[i].varflags, InternalActorFlagDefs[i].structoffset, bit)); - } - - PSymbolTable &symt2 = RUNTIME_CLASS(DDropItem)->Symbols; - PType *TypeDropItem = NewPointer(RUNTIME_CLASS(DDropItem)); - symt2.AddSymbol(new PField("Next", TypeDropItem, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Next))); - symt2.AddSymbol(new PField("Name", TypeName, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Name))); - symt2.AddSymbol(new PField("Probability", TypeSInt32, VARF_Native | VARF_ReadOnly, myoffsetof(DDropItem, Probability))); - symt2.AddSymbol(new PField("Amount", TypeSInt32, VARF_Native, myoffsetof(DDropItem, Amount))); - - PSymbolTable &symt3 = RUNTIME_CLASS(DObject)->Symbols; - symt3.AddSymbol(new PField("bDestroyed", TypeSInt32, VARF_Native|VARF_ReadOnly, myoffsetof(DObject, ObjectFlags), 5/*OF_EuthanizeMe*/)); } From d433fb76c999bb8fabc5ab5a3d3e014b0b1d553e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 08:57:10 +0100 Subject: [PATCH 166/255] - completed the list of AActor exported member variables, with the exception of a few things that cannot be done yet. Note that AActor::Inventory needed to be renamed because defining this symbol within AActor would hide the global type of the same name! --- src/p_mobj.cpp | 185 ++++++++++++++++++++++++++++++++++++------------- 1 file changed, 135 insertions(+), 50 deletions(-) diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index cf0a033b3..a567f5486 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -157,6 +157,7 @@ extern FFlagDef ActorFlagDefs[]; void AActor::InitNativeFields() { PType *TypeActor = NewPointer(RUNTIME_CLASS(AActor)); + PType *TypeActorClass = NewClassPointer(RUNTIME_CLASS(AActor)); PType *TypeInventory = NewPointer(RUNTIME_CLASS(AInventory)); PStruct *sstruct = NewStruct("Sector", nullptr); auto TypeSector = NewPointer(sstruct); @@ -164,74 +165,158 @@ void AActor::InitNativeFields() auto meta = RUNTIME_CLASS(AActor); - // Define the member variables we feel like exposing to the user - meta->AddNativeField(NAME_Alpha, TypeFloat64, myoffsetof(AActor, Alpha)); - meta->AddNativeField(NAME_Angle, TypeFloat64, myoffsetof(AActor, Angles.Yaw)); - meta->AddNativeField(NAME_Args, array5, myoffsetof(AActor, args)); - meta->AddNativeField(NAME_CeilingZ, TypeFloat64, myoffsetof(AActor, ceilingz), VARF_ReadOnly); - meta->AddNativeField(NAME_FloorZ, TypeFloat64, myoffsetof(AActor, floorz), VARF_ReadOnly); - meta->AddNativeField(NAME_Health, TypeSInt32, myoffsetof(AActor, health), VARF_ReadOnly); - meta->AddNativeField(NAME_Mass, TypeSInt32, myoffsetof(AActor, Mass)); - meta->AddNativeField(NAME_Pitch, TypeFloat64, myoffsetof(AActor, Angles.Pitch)); - meta->AddNativeField(NAME_Roll, TypeFloat64, myoffsetof(AActor, Angles.Roll)); - meta->AddNativeField(NAME_Special, TypeSInt32, myoffsetof(AActor, special)); - meta->AddNativeField(NAME_TID, TypeSInt32, myoffsetof(AActor, tid), VARF_ReadOnly); - meta->AddNativeField(NAME_TIDtoHate, TypeSInt32, myoffsetof(AActor, TIDtoHate), VARF_ReadOnly); - meta->AddNativeField(NAME_WaterLevel, TypeSInt32, myoffsetof(AActor, waterlevel), VARF_ReadOnly); + meta->AddNativeField("Pos", TypeVector3, myoffsetof(AActor, __Pos), VARF_ReadOnly); meta->AddNativeField(NAME_X, TypeFloat64, myoffsetof(AActor, __Pos.X), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! meta->AddNativeField(NAME_Y, TypeFloat64, myoffsetof(AActor, __Pos.Y), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! meta->AddNativeField(NAME_Z, TypeFloat64, myoffsetof(AActor, __Pos.Z), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! + meta->AddNativeField("Prev", TypeVector3, myoffsetof(AActor, Prev)); + meta->AddNativeField("spriteAngle", TypeFloat64, myoffsetof(AActor, SpriteAngle)); + meta->AddNativeField("spriteRotation", TypeFloat64, myoffsetof(AActor, SpriteRotation)); + meta->AddNativeField(NAME_VisibleStartAngle, TypeFloat64, myoffsetof(AActor, VisibleStartAngle)); + meta->AddNativeField(NAME_VisibleStartPitch, TypeFloat64, myoffsetof(AActor, VisibleStartPitch)); + meta->AddNativeField(NAME_VisibleEndAngle, TypeFloat64, myoffsetof(AActor, VisibleEndAngle)); + meta->AddNativeField(NAME_VisibleEndPitch, TypeFloat64, myoffsetof(AActor, VisibleEndPitch)); + meta->AddNativeField(NAME_Angle, TypeFloat64, myoffsetof(AActor, Angles.Yaw)); + meta->AddNativeField(NAME_Pitch, TypeFloat64, myoffsetof(AActor, Angles.Pitch)); + meta->AddNativeField(NAME_Roll, TypeFloat64, myoffsetof(AActor, Angles.Roll)); + meta->AddNativeField("Vel", TypeVector3, myoffsetof(AActor, Vel)); meta->AddNativeField(NAME_VelX, TypeFloat64, myoffsetof(AActor, Vel.X), VARF_ReadOnly | VARF_Deprecated); meta->AddNativeField(NAME_VelY, TypeFloat64, myoffsetof(AActor, Vel.Y), VARF_ReadOnly | VARF_Deprecated); meta->AddNativeField(NAME_VelZ, TypeFloat64, myoffsetof(AActor, Vel.Z), VARF_ReadOnly | VARF_Deprecated); meta->AddNativeField(NAME_MomX, TypeFloat64, myoffsetof(AActor, Vel.X), VARF_ReadOnly | VARF_Deprecated); meta->AddNativeField(NAME_MomY, TypeFloat64, myoffsetof(AActor, Vel.Y), VARF_ReadOnly | VARF_Deprecated); meta->AddNativeField(NAME_MomZ, TypeFloat64, myoffsetof(AActor, Vel.Z), VARF_ReadOnly | VARF_Deprecated); - meta->AddNativeField(NAME_ScaleX, TypeFloat64, myoffsetof(AActor, Scale.X), VARF_Deprecated); - meta->AddNativeField(NAME_ScaleY, TypeFloat64, myoffsetof(AActor, Scale.Y), VARF_Deprecated); - meta->AddNativeField(NAME_Score, TypeSInt32, myoffsetof(AActor, Score)); - meta->AddNativeField(NAME_Accuracy, TypeSInt32, myoffsetof(AActor, accuracy)); - meta->AddNativeField(NAME_Stamina, TypeSInt32, myoffsetof(AActor, stamina)); - meta->AddNativeField(NAME_Height, TypeFloat64, myoffsetof(AActor, Height)); - meta->AddNativeField(NAME_Radius, TypeFloat64, myoffsetof(AActor, radius), VARF_ReadOnly); - meta->AddNativeField(NAME_ReactionTime, TypeSInt32, myoffsetof(AActor, reactiontime)); - meta->AddNativeField(NAME_MeleeRange, TypeFloat64, myoffsetof(AActor, meleerange)); meta->AddNativeField(NAME_Speed, TypeFloat64, myoffsetof(AActor, Speed)); meta->AddNativeField("FloatSpeed", TypeFloat64, myoffsetof(AActor, FloatSpeed)); - meta->AddNativeField("PainThreshold", TypeSInt32, myoffsetof(AActor, PainThreshold)); - meta->AddNativeField("spriteAngle", TypeFloat64, myoffsetof(AActor, SpriteAngle)); - meta->AddNativeField("spriteRotation", TypeFloat64, myoffsetof(AActor, SpriteRotation)); - meta->AddNativeField(NAME_Threshold, TypeSInt32, myoffsetof(AActor, threshold)); - meta->AddNativeField(NAME_DefThreshold, TypeSInt32, myoffsetof(AActor, DefThreshold), VARF_ReadOnly); - meta->AddNativeField(NAME_Damage, TypeSInt32, myoffsetof(AActor, DamageVal), VARF_ReadOnly); - meta->AddNativeField("visdir", TypeSInt32, myoffsetof(AActor, visdir)); - meta->AddNativeField("Gravity", TypeFloat64, myoffsetof(AActor, Gravity)); - meta->AddNativeField("FloorClip", TypeFloat64, myoffsetof(AActor, Floorclip)); - meta->AddNativeField("DamageType", TypeName, myoffsetof(AActor, DamageType)); - meta->AddNativeField("FloatBobPhase", TypeUInt8, myoffsetof(AActor, FloatBobPhase)); - meta->AddNativeField("tics", TypeSInt32, myoffsetof(AActor, tics)); - meta->AddNativeField("RipperLevel", TypeSInt32, myoffsetof(AActor, RipperLevel)); - meta->AddNativeField("RipLevelMin", TypeSInt32, myoffsetof(AActor, RipLevelMin)); - meta->AddNativeField("RipLevelMax", TypeSInt32, myoffsetof(AActor, RipLevelMax)); - meta->AddNativeField("special2", TypeSInt32, myoffsetof(AActor, special2)); - meta->AddNativeField(NAME_VisibleStartAngle, TypeFloat64, myoffsetof(AActor, VisibleStartAngle)); - meta->AddNativeField(NAME_VisibleStartPitch, TypeFloat64, myoffsetof(AActor, VisibleStartPitch)); - meta->AddNativeField(NAME_VisibleEndAngle, TypeFloat64, myoffsetof(AActor, VisibleEndAngle)); - meta->AddNativeField(NAME_VisibleEndPitch, TypeFloat64, myoffsetof(AActor, VisibleEndPitch)); - meta->AddNativeField("AttackSound", TypeSound, myoffsetof(AActor, AttackSound)); - meta->AddNativeField("DeathSound", TypeSound, myoffsetof(AActor, DeathSound)); - meta->AddNativeField("SeeSound", TypeSound, myoffsetof(AActor, SeeSound)); - meta->AddNativeField("Pos", TypeVector3, myoffsetof(AActor, __Pos), VARF_ReadOnly); - meta->AddNativeField("Vel", TypeVector3, myoffsetof(AActor, Vel)); + meta->AddNativeField("sprite", TypeSInt32, myoffsetof(AActor, sprite)); // this is an index, not a name! + meta->AddNativeField("frame", TypeUInt8, myoffsetof(AActor, frame)); meta->AddNativeField("Scale", TypeVector2, myoffsetof(AActor, Scale)); + meta->AddNativeField(NAME_ScaleX, TypeFloat64, myoffsetof(AActor, Scale.X), VARF_Deprecated); + meta->AddNativeField(NAME_ScaleY, TypeFloat64, myoffsetof(AActor, Scale.Y), VARF_Deprecated); + //FRenderStyle RenderStyle; // how do we expose this? + meta->AddNativeField("picnum", TypeSInt32, myoffsetof(AActor, picnum)); // Do we need a variable type 'texture' to do this? + meta->AddNativeField(NAME_Alpha, TypeFloat64, myoffsetof(AActor, Alpha)); + meta->AddNativeField("fillcolor", TypeColor, myoffsetof(AActor, fillcolor)); + meta->AddNativeField("Sector", TypeSector, myoffsetof(AActor, Sector)); + //meta->AddNativeField("Subsector", TypeSubsector, myoffsetof(AActor, subsector)); + meta->AddNativeField(NAME_CeilingZ, TypeFloat64, myoffsetof(AActor, ceilingz), VARF_ReadOnly); + meta->AddNativeField(NAME_FloorZ, TypeFloat64, myoffsetof(AActor, floorz), VARF_ReadOnly); + meta->AddNativeField("DropoffZ", TypeFloat64, myoffsetof(AActor, dropoffz), VARF_ReadOnly); + meta->AddNativeField("floorsector", TypeSector, myoffsetof(AActor, floorsector)); + meta->AddNativeField("floorpic", TypeSInt32, myoffsetof(AActor, floorpic)); // Do we need a variable type 'texture' to do this? + meta->AddNativeField("floorterrain", TypeSInt32, myoffsetof(AActor, floorterrain)); + meta->AddNativeField("ceilingsector", TypeSector, myoffsetof(AActor, ceilingsector)); + meta->AddNativeField("ceilingpic", TypeSInt32, myoffsetof(AActor, ceilingpic)); // Do we need a variable type 'texture' to do this? + meta->AddNativeField(NAME_Height, TypeFloat64, myoffsetof(AActor, Height)); + meta->AddNativeField(NAME_Radius, TypeFloat64, myoffsetof(AActor, radius), VARF_ReadOnly); + meta->AddNativeField("projectilepassheight",TypeFloat64, myoffsetof(AActor, projectilepassheight)); + meta->AddNativeField("tics", TypeSInt32, myoffsetof(AActor, tics)); meta->AddNativeField("CurState", TypeState, myoffsetof(AActor, state), VARF_ReadOnly); // has to be renamed on the script side because it clashes with the same named type. - meta->AddNativeField("SeeState", TypeState, myoffsetof(AActor, SeeState), VARF_ReadOnly); + meta->AddNativeField(NAME_Damage, TypeSInt32, myoffsetof(AActor, DamageVal), VARF_ReadOnly); + meta->AddNativeField("projectilekickback", TypeSInt32, myoffsetof(AActor, projectileKickback)); + //DWORD VisibleToTeam; + meta->AddNativeField("special1", TypeSInt32, myoffsetof(AActor, special1)); + meta->AddNativeField("special2", TypeSInt32, myoffsetof(AActor, special2)); + meta->AddNativeField("specialf1", TypeFloat64, myoffsetof(AActor, specialf1)); + meta->AddNativeField("specialf2", TypeFloat64, myoffsetof(AActor, specialf2)); + meta->AddNativeField("weaponspecial", TypeSInt32, myoffsetof(AActor, weaponspecial)); + meta->AddNativeField(NAME_Health, TypeSInt32, myoffsetof(AActor, health), VARF_ReadOnly); + meta->AddNativeField("movedir", TypeUInt8, myoffsetof(AActor, movedir)); + meta->AddNativeField("visdir", TypeSInt8, myoffsetof(AActor, visdir)); + meta->AddNativeField("movecount", TypeSInt16, myoffsetof(AActor, movecount)); + meta->AddNativeField("strafecount", TypeSInt16, myoffsetof(AActor, strafecount)); meta->AddNativeField(NAME_Target, TypeActor, myoffsetof(AActor, target)); meta->AddNativeField(NAME_Master, TypeActor, myoffsetof(AActor, master)); meta->AddNativeField(NAME_Tracer, TypeActor, myoffsetof(AActor, tracer)); meta->AddNativeField("LastHeard", TypeActor, myoffsetof(AActor, LastHeard)); meta->AddNativeField("LastEnemy", TypeActor, myoffsetof(AActor, lastenemy)); - meta->AddNativeField("Sector", TypeSector, myoffsetof(AActor, Sector)); + meta->AddNativeField("LastLookActor", TypeActor, myoffsetof(AActor, LastLookActor)); + meta->AddNativeField(NAME_ReactionTime, TypeSInt32, myoffsetof(AActor, reactiontime)); + meta->AddNativeField(NAME_Threshold, TypeSInt32, myoffsetof(AActor, threshold)); + meta->AddNativeField(NAME_DefThreshold, TypeSInt32, myoffsetof(AActor, DefThreshold), VARF_ReadOnly); + meta->AddNativeField("SpawnPoint", TypeVector3, myoffsetof(AActor, SpawnPoint), VARF_ReadOnly); + meta->AddNativeField("SpawnAngle", TypeUInt16, myoffsetof(AActor, SpawnAngle), VARF_ReadOnly); + meta->AddNativeField("StartHealth", TypeSInt32, myoffsetof(AActor, StartHealth)); + meta->AddNativeField("WeaveIndexXY", TypeUInt16, myoffsetof(AActor, WeaveIndexXY)); + meta->AddNativeField("WeaveIndexZ", TypeUInt16, myoffsetof(AActor, WeaveIndexZ)); + meta->AddNativeField("skillrespawncount", TypeSInt32, myoffsetof(AActor, skillrespawncount)); + meta->AddNativeField(NAME_Args, array5, myoffsetof(AActor, args)); + meta->AddNativeField(NAME_Mass, TypeSInt32, myoffsetof(AActor, Mass)); + meta->AddNativeField(NAME_Special, TypeSInt32, myoffsetof(AActor, special)); + meta->AddNativeField(NAME_TID, TypeSInt32, myoffsetof(AActor, tid), VARF_ReadOnly); + meta->AddNativeField(NAME_TIDtoHate, TypeSInt32, myoffsetof(AActor, TIDtoHate), VARF_ReadOnly); + meta->AddNativeField(NAME_WaterLevel, TypeSInt32, myoffsetof(AActor, waterlevel), VARF_ReadOnly); + meta->AddNativeField(NAME_Score, TypeSInt32, myoffsetof(AActor, Score)); + meta->AddNativeField(NAME_Accuracy, TypeSInt32, myoffsetof(AActor, accuracy)); + meta->AddNativeField(NAME_Stamina, TypeSInt32, myoffsetof(AActor, stamina)); + meta->AddNativeField(NAME_MeleeRange, TypeFloat64, myoffsetof(AActor, meleerange)); + meta->AddNativeField("PainThreshold", TypeSInt32, myoffsetof(AActor, PainThreshold)); + meta->AddNativeField("Gravity", TypeFloat64, myoffsetof(AActor, Gravity)); + meta->AddNativeField("FloorClip", TypeFloat64, myoffsetof(AActor, Floorclip)); + meta->AddNativeField("DamageType", TypeName, myoffsetof(AActor, DamageType)); + meta->AddNativeField("DamageTypeReceived", TypeName, myoffsetof(AActor, DamageTypeReceived)); + meta->AddNativeField("FloatBobPhase", TypeUInt8, myoffsetof(AActor, FloatBobPhase)); + meta->AddNativeField("RipperLevel", TypeSInt32, myoffsetof(AActor, RipperLevel)); + meta->AddNativeField("RipLevelMin", TypeSInt32, myoffsetof(AActor, RipLevelMin)); + meta->AddNativeField("RipLevelMax", TypeSInt32, myoffsetof(AActor, RipLevelMax)); + meta->AddNativeField("Species", TypeName, myoffsetof(AActor, Species)); + meta->AddNativeField("Alternative", TypeActor, myoffsetof(AActor, alternative)); + meta->AddNativeField("goal", TypeActor, myoffsetof(AActor, goal)); + meta->AddNativeField("MinMissileChance", TypeUInt8, myoffsetof(AActor, MinMissileChance)); + meta->AddNativeField("LastLookPlayerNumber",TypeSInt8, myoffsetof(AActor, LastLookPlayerNumber)); + meta->AddNativeField("SpawnFlags", TypeUInt32, myoffsetof(AActor, SpawnFlags)); + meta->AddNativeField("meleethreshold", TypeFloat64, myoffsetof(AActor, meleethreshold)); + meta->AddNativeField("maxtargetrange", TypeFloat64, myoffsetof(AActor, maxtargetrange)); + meta->AddNativeField("bouncefactor", TypeFloat64, myoffsetof(AActor, bouncefactor)); + meta->AddNativeField("wallbouncefactor", TypeFloat64, myoffsetof(AActor, wallbouncefactor)); + meta->AddNativeField("bouncecount", TypeSInt32, myoffsetof(AActor, bouncecount)); + meta->AddNativeField("friction", TypeFloat64, myoffsetof(AActor, Friction)); + meta->AddNativeField("FastChaseStrafeCount",TypeSInt32, myoffsetof(AActor, FastChaseStrafeCount)); + meta->AddNativeField("pushfactor", TypeFloat64, myoffsetof(AActor, pushfactor)); + meta->AddNativeField("lastpush", TypeSInt32, myoffsetof(AActor, lastpush)); + meta->AddNativeField("activationtype", TypeSInt32, myoffsetof(AActor, activationtype)); + meta->AddNativeField("lastbump", TypeSInt32, myoffsetof(AActor, lastbump)); + meta->AddNativeField("DesignatedTeam", TypeSInt32, myoffsetof(AActor, DesignatedTeam)); + meta->AddNativeField("BlockingMobj", TypeActor, myoffsetof(AActor, BlockingMobj)); + //line_t *BlockingLine; // Line that blocked the last move + meta->AddNativeField("PoisonDamage", TypeSInt32, myoffsetof(AActor, PoisonDamage)); + meta->AddNativeField("PoisonDamageType", TypeName, myoffsetof(AActor, PoisonDamageType)); + meta->AddNativeField("PoisonDuration", TypeSInt32, myoffsetof(AActor, PoisonDuration)); + meta->AddNativeField("PoisonPeriod", TypeSInt32, myoffsetof(AActor, PoisonPeriod)); + meta->AddNativeField("PoisonDamageReceived",TypeSInt32, myoffsetof(AActor, PoisonDamageReceived)); + meta->AddNativeField("PoisonDamageTypeReceived", TypeName, myoffsetof(AActor, PoisonDamageTypeReceived)); + meta->AddNativeField("PoisonDurationReceived", TypeSInt32, myoffsetof(AActor, PoisonDurationReceived)); + meta->AddNativeField("PoisonPeriodReceived", TypeSInt32, myoffsetof(AActor, PoisonPeriodReceived)); + meta->AddNativeField("Poisoner", TypeActor, myoffsetof(AActor, Poisoner)); + meta->AddNativeField("Inv", TypeInventory, myoffsetof(AActor, Inventory)); // Needs to be renamed because it hides the actual type. + meta->AddNativeField("smokecounter", TypeUInt8, myoffsetof(AActor, smokecounter)); + meta->AddNativeField("FriendPlayer", TypeUInt8, myoffsetof(AActor, FriendPlayer)); + meta->AddNativeField("Translation", TypeUInt32, myoffsetof(AActor, Translation)); + meta->AddNativeField("AttackSound", TypeSound, myoffsetof(AActor, AttackSound)); + meta->AddNativeField("DeathSound", TypeSound, myoffsetof(AActor, DeathSound)); + meta->AddNativeField("SeeSound", TypeSound, myoffsetof(AActor, SeeSound)); + meta->AddNativeField("PainSound", TypeSound, myoffsetof(AActor, PainSound)); + meta->AddNativeField("ActiveSound", TypeSound, myoffsetof(AActor, ActiveSound)); + meta->AddNativeField("UseSound", TypeSound, myoffsetof(AActor, UseSound)); + meta->AddNativeField("BounceSound", TypeSound, myoffsetof(AActor, BounceSound)); + meta->AddNativeField("WallBounceSound", TypeSound, myoffsetof(AActor, WallBounceSound)); + meta->AddNativeField("CrushPainSound", TypeSound, myoffsetof(AActor, CrushPainSound)); + meta->AddNativeField("MaxDropoffHeight", TypeFloat64, myoffsetof(AActor, MaxDropOffHeight)); + meta->AddNativeField("MaxStepHeight", TypeFloat64, myoffsetof(AActor, MaxStepHeight)); + meta->AddNativeField("PainChance", TypeSInt16, myoffsetof(AActor, PainChance)); + meta->AddNativeField("PainType", TypeName, myoffsetof(AActor, PainType)); + meta->AddNativeField("DeathType", TypeName, myoffsetof(AActor, DeathType)); + meta->AddNativeField("DamageFactor", TypeFloat64, myoffsetof(AActor, DamageFactor)); + meta->AddNativeField("DamageMultiply", TypeFloat64, myoffsetof(AActor, DamageMultiply)); + meta->AddNativeField("TelefogSpurceType", TypeActorClass, myoffsetof(AActor, TeleFogSourceType)); + meta->AddNativeField("TelefogDestType", TypeActorClass, myoffsetof(AActor, TeleFogDestType)); + meta->AddNativeField("SpawnState", TypeState, myoffsetof(AActor, SpawnState), VARF_ReadOnly); + meta->AddNativeField("SeeState", TypeState, myoffsetof(AActor, SeeState), VARF_ReadOnly); + meta->AddNativeField("MeleeState", TypeState, myoffsetof(AActor, MeleeState), VARF_ReadOnly); + meta->AddNativeField("MissileState", TypeState, myoffsetof(AActor, MissileState), VARF_ReadOnly); + //int ConversationRoot; // THe root of the current dialogue + //FStrifeDialogueNode *Conversation; // [RH] The dialogue to show when this actor is "used." + //FDecalBase *DecalGenerator; // synthesize a symbol for each flag from the flag name tables to avoid redundant declaration of them. for (size_t i = 0; ActorFlagDefs[i].flagbit != 0xffffffff; i++) From 157cfe3ab37e7b94fe98a19fb53e45804e62a62f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 09:23:29 +0100 Subject: [PATCH 167/255] - fixed: The RNG was not initialized for script calls that did not explicitly specify an RNG by name. --- src/scripting/codegeneration/codegen.cpp | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4c26da595..9cbc1c2b1 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -55,6 +55,8 @@ #include "v_text.h" #include "math/cmath.h" +extern FRandom pr_exrandom; + struct FLOP { ENamedName Name; @@ -5733,7 +5735,7 @@ FxFunctionCall::FxFunctionCall(FName methodname, FName rngname, FArgumentList *a : FxExpression(EFX_FunctionCall, pos) { MethodName = methodname; - RNG = nullptr; + RNG = &pr_exrandom; ArgList = args; if (rngname != NAME_None) { From 7068070c0da0c4f28bf7b480477dca79e7ab8e94 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 09:56:03 +0100 Subject: [PATCH 168/255] - fixed: The identifier fallback which existed for all other basic types was missing for 'state'. - added the option to put code right into the ZSCRIPT lump for smaller definitions where a file list would be too cumbersome. --- src/scripting/zscript/zcc-parse.lemon | 2 +- src/scripting/zscript/zcc_parser.cpp | 64 ++++++++++++++++++--------- 2 files changed, 44 insertions(+), 22 deletions(-) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index b1065281c..9d22765fc 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -690,7 +690,7 @@ type_name(X) ::= DOT dottable_id(A). /* Type names can also be used as identifiers in contexts where type names * are not normally allowed. */ %fallback IDENTIFIER - SBYTE BYTE SHORT USHORT INT UINT BOOL FLOAT DOUBLE STRING VECTOR2 VECTOR3 NAME MAP ARRAY VOID. + SBYTE BYTE SHORT USHORT INT UINT BOOL FLOAT DOUBLE STRING VECTOR2 VECTOR3 NAME MAP ARRAY VOID STATE. /* Aggregate types */ %type aggregate_type {ZCC_Type *} diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 84bebff40..fe6341bb3 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -179,9 +179,9 @@ static void InitTokenMap() TOKENDEF (TK_Loop, ZCC_LOOP); TOKENDEF (TK_Goto, ZCC_GOTO); TOKENDEF (TK_States, ZCC_STATES); - TOKENDEF (TK_State, ZCC_STATE); - TOKENDEF (TK_Color, ZCC_COLOR); - TOKENDEF (TK_Sound, ZCC_SOUND); + TOKENDEF2(TK_State, ZCC_STATE, NAME_State); + TOKENDEF2(TK_Color, ZCC_COLOR, NAME_Color); + TOKENDEF2(TK_Sound, ZCC_SOUND, NAME_Sound); TOKENDEF (TK_Identifier, ZCC_IDENTIFIER); TOKENDEF (TK_StringConst, ZCC_STRCONST); @@ -206,24 +206,27 @@ static void InitTokenMap() #undef TOKENDEF #undef TOKENDEF2 -static void ParseSingleFile(const char *filename, void *parser, ZCCParseState &state) +static void ParseSingleFile(const char *filename, int lump, void *parser, ZCCParseState &state) { int tokentype; - int lump; //bool failed; ZCCToken value; FScanner sc; - lump = Wads.CheckNumForFullName(filename, true); - if (lump >= 0) + if (filename != nullptr) { - sc.OpenLumpNum(lump); - } - else - { - Printf("Could not find script lump '%s'\n", filename); - return; + lump = Wads.CheckNumForFullName(filename, true); + if (lump >= 0) + { + sc.OpenLumpNum(lump); + } + else + { + Printf("Could not find script lump '%s'\n", filename); + return; + } } + else sc.OpenLumpNum(lump); state.sc = ≻ while (sc.GetToken()) @@ -309,20 +312,39 @@ static void DoParse(int lumpnum) #endif sc.OpenLumpNum(lumpnum); - // parse all files from this list in one go. - while (sc.GetString()) + auto saved = sc.SavePos(); + bool parsed = false; + if (sc.GetToken()) { - if (Wads.GetLumpFile(sc.LumpNum) == 0) + if (sc.TokenType == TK_Class || sc.TokenType == TK_Enum || sc.TokenType == TK_Struct || sc.TokenType == TK_Const || sc.TokenType == TK_Native) { - int includefile = Wads.GetLumpFile(Wads.CheckNumForFullName(sc.String, true)); - if (includefile != 0) + if (sc.CheckToken(TK_Identifier)) { - I_FatalError("File %s is overriding core lump %s.", - Wads.GetWadFullName(includefile), sc.String); + // This looks like an actual definition file and not a file list. + ParseSingleFile(nullptr, lumpnum, parser, state); + parsed = true; } } + } + if (!parsed) + { + sc.RestorePos(saved); + // parse all files from this list in one go. + while (sc.GetString()) + { + FixPathSeperator(sc.String); + if (Wads.GetLumpFile(sc.LumpNum) == 0) + { + int includefile = Wads.GetLumpFile(Wads.CheckNumForFullName(sc.String, true)); + if (includefile != 0) + { + I_FatalError("File %s is overriding core lump %s.", + Wads.GetWadFullName(includefile), sc.String); + } + } - ParseSingleFile(sc.String, parser, state); + ParseSingleFile(sc.String, 0, parser, state); + } } value.Int = -1; From 07c24c7e27a65d22642df3e0bcaa0b72225fbca4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 10:35:14 +0100 Subject: [PATCH 169/255] - use different names for different AST dumps. --- src/scripting/zscript/zcc_parser.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index fe6341bb3..26fdeec43 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -369,10 +369,10 @@ static void DoParse(int lumpnum) if (Args->CheckParm("-dumpast")) { FString ast = ZCC_PrintAST(state.TopNode); - FString filename = Wads.GetLumpFullName(lumpnum); - FString astfile = ExtractFileBase(filename, false); - astfile << ".ast"; - FILE *ff = fopen(astfile, "w"); + FString filename = Wads.GetLumpFullPath(lumpnum); + filename.ReplaceChars(":\\/?|", '.'); + filename << ".ast"; + FILE *ff = fopen(filename, "w"); if (ff != NULL) { fputs(ast.GetChars(), ff); From 407345668a5f8166c340cc4f5425abc64b4255b6 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 15:16:56 +0100 Subject: [PATCH 170/255] - fixed: ZCCCompiler tried to process replacements too early, it can only be done after all classes have been created. --- src/scripting/zscript/zcc_compile.cpp | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 98d847ebe..8555432c0 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -93,11 +93,6 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) name << "nodes - " << FName(cnode->NodeName); cls->TreeNodes.SetName(name); - if (cnode->Replaces != nullptr && !static_cast(cnode->Type)->SetReplacement(cnode->Replaces->Id)) - { - Warn(cnode, "Replaced type '%s' not found for %s", FName(cnode->Replaces->Id).GetChars(), cnode->Type->TypeName.GetChars()); - } - // Need to check if the class actually has a body. if (node != nullptr) do { @@ -557,7 +552,7 @@ void ZCCCompiler::CreateClassTypes() Classes.Push(c); } - // Last but not least: Now that all classes have been created, we can create the symbols for the internal enums and link the treenode symbol tables + // Last but not least: Now that all classes have been created, we can create the symbols for the internal enums and link the treenode symbol tables and set up replacements for (auto cd : Classes) { for (auto e : cd->Enums) @@ -574,6 +569,12 @@ void ZCCCompiler::CreateClassTypes() break; } } + + if (cd->cls->Replaces != nullptr && !static_cast(cd->Type())->SetReplacement(cd->cls->Replaces->Id)) + { + Warn(cd->cls, "Replaced type '%s' not found for %s", FName(cd->cls->Replaces->Id).GetChars(), cd->Type()->TypeName.GetChars()); + } + } } From 8ae7aae14ae88396d1806a7243da60f3b5553005 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 4 Nov 2016 15:21:45 +0100 Subject: [PATCH 171/255] - do not delete duplicate PFields - they are better be destroyed and left to the GC. - removed two duplicate entries to the flag table. --- src/dobjtype.cpp | 2 +- src/scripting/thingdef_data.cpp | 2 -- 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 631a7e6ee..f1726adbf 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2254,7 +2254,7 @@ PField *PStruct::AddNativeField(FName name, PType *type, size_t address, DWORD f if (Symbols.AddSymbol(field) == nullptr) { // name is already in use - delete field; + field->Destroy(); return nullptr; } Fields.Push(field); diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index f628dec3c..74c685ea8 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -68,14 +68,12 @@ FFlagDef InternalActorFlagDefs[]= DEFINE_FLAG(MF, UNMORPHED, AActor, flags), DEFINE_FLAG(MF2, FLY, AActor, flags2), DEFINE_FLAG(MF2, ONMOBJ, AActor, flags2), - DEFINE_FLAG(MF2, DONTTRANSLATE, AActor, flags2), DEFINE_FLAG(MF2, ARGSDEFINED, AActor, flags2), DEFINE_FLAG(MF3, NOSIGHTCHECK, AActor, flags3), DEFINE_FLAG(MF3, CRASHED, AActor, flags3), DEFINE_FLAG(MF3, WARNBOT, AActor, flags3), DEFINE_FLAG(MF3, HUNTPLAYERS, AActor, flags3), DEFINE_FLAG(MF4, NOHATEPLAYERS, AActor, flags4), - DEFINE_FLAG(MF4, NOSKIN, AActor, flags4), DEFINE_FLAG(MF4, SCROLLMOVE, AActor, flags4), DEFINE_FLAG(MF4, VFRICTION, AActor, flags4), DEFINE_FLAG(MF4, BOSSSPAWNED, AActor, flags4), From b6633bc489481d514dd50e8c5bf830fe75bb43bf Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 00:39:00 +0100 Subject: [PATCH 172/255] - fixed: The states parser tried to simplify the head node for random duration but it has to simplify the two value nodes separately. - added jump by index to ZScript. --- src/dobjtype.h | 1 + src/scripting/codegeneration/codegen.cpp | 29 ++++++++++++++++++++-- src/scripting/decorate/thingdef_states.cpp | 2 +- src/scripting/thingdef.cpp | 5 ++-- src/scripting/thingdef.h | 2 +- src/scripting/zscript/zcc_compile.cpp | 11 +++++--- 6 files changed, 40 insertions(+), 10 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index db468870f..30e22e868 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -718,6 +718,7 @@ public: }; TArray Variants; PClass *OwningClass = nullptr; + int StateCount = 0; // needed to process state indices later. unsigned AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl, int flags); int GetImplicitArgs() diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9cbc1c2b1..9e86fff8f 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1416,6 +1416,26 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) delete this; return x; } + else if (basex->IsNumeric() && basex->ValueType != TypeSound && basex->ValueType != TypeColor) + { + if (ctx.Function->SymbolName != NAME_None || !(ctx.Function->Variants[0].Flags & VARF_Action)) + { + ScriptPosition.Message(MSG_ERROR, "State jumps with index can only be used in anonymous state functions."); + delete this; + return nullptr; + } + if (ctx.Function->StateCount != 1) + { + ScriptPosition.Message(MSG_ERROR, "State jumps with index cannot be used on multistate definitions"); + delete this; + return nullptr; + } + FxExpression *x = new FxRuntimeStateIndex(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } } else if (ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) { @@ -7859,6 +7879,12 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) delete this; return nullptr; } + else if (Index->isConstant() && static_cast(Index) < 0) + { + ScriptPosition.Message(MSG_ERROR, "State index must be positive"); + delete this; + return nullptr; + } else if (Index->ValueType->GetRegType() != REGT_INT) { // Float. Index = new FxIntCast(Index, ctx.FromDecorate); @@ -7912,8 +7938,7 @@ static int BuiltinHandleRuntimeState(VMFrameStack *stack, VMValue *param, TArray ExpEmit FxRuntimeStateIndex::Emit(VMFunctionBuilder *build) { - // This code can only be called from DECORATE, not ZSCRIPT so any function going through here - // is an anoynmous one which are always marked as 'action'. + // This can only be called from inline state functions which must be VARF_Action. assert(build->NumImplicits >= NAP && build->Registers[REGT_POINTER].GetMostUsed() >= build->NumImplicits && "FxRuntimeStateIndex is only valid inside action functions"); diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index dda25f926..59cf30938 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -322,7 +322,7 @@ do_stop: endofstate: if (ScriptCode != nullptr) { - auto funcsym = CreateAnonymousFunction(actor, nullptr, VARF_Method | VARF_Action); + auto funcsym = CreateAnonymousFunction(actor, nullptr, VARF_Method | VARF_Action, (int)statestring.Len()); state.ActionFunc = FunctionBuildList.AddFunction(funcsym, ScriptCode, FStringf("%s.StateFunction.%d", actor->TypeName.GetChars(), bag.statedef.GetStateCount()), true); } int count = bag.statedef.AddStates(&state, statestring); diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 8c42e8987..6f30f8add 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -132,7 +132,7 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArray rets(1); TArray args; @@ -143,6 +143,7 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i SetImplicitArgs(&args, &argflags, &argnames, containingclass, flags); PFunction *sym = new PFunction(containingclass, NAME_None); // anonymous functions do not have names. + sym->StateCount = statecount; sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, flags); return sym; } @@ -201,7 +202,7 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, else { auto dmg = new FxReturnStatement(new FxIntCast(id, true), id->ScriptPosition); - auto funcsym = CreateAnonymousFunction(info, TypeSInt32, VARF_Method); + auto funcsym = CreateAnonymousFunction(info, TypeSInt32, VARF_Method, 0); defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, dmg, FStringf("%s.DamageFunction", info->TypeName.GetChars()), fromDecorate); } } diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index b2d34231d..3511d1ee1 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -153,7 +153,7 @@ FxExpression *ParseActions(FScanner &sc, FState state, FString statestring, Bagg class FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestring, Baggage &bag); FName CheckCastKludges(FName in); void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); -PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); +PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags, int statecount); PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc, bool *error); void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, bool fromDecorate); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 8555432c0..f296a91b6 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2248,6 +2248,7 @@ void ZCCCompiler::CompileStates() FString statename; // The state builder wants the label as one complete string, not separated into tokens. FStateDefinitions statedef; statedef.MakeStateDefines(dyn_cast(c->Type()->ParentClass)); + int numframes = 0; for (auto s : c->States) { @@ -2279,13 +2280,15 @@ void ZCCCompiler::CompileStates() // It is important to call CheckRandom before Simplify, because Simplify will resolve the function's name to nonsense if (CheckRandom(sl->Duration)) { - auto func = static_cast(Simplify(sl->Duration, &c->Type()->Symbols, true)); + auto func = static_cast(sl->Duration); if (func->Parameters == func->Parameters->SiblingNext || func->Parameters != func->Parameters->SiblingNext->SiblingNext) { Error(sl, "Random duration requires exactly 2 parameters"); } - int v1 = GetInt(func->Parameters->Value); - int v2 = GetInt(static_cast(func->Parameters->SiblingNext)->Value); + auto p1 = Simplify(func->Parameters->Value, &c->Type()->Symbols, true); + auto p2 = Simplify(static_cast(func->Parameters->SiblingNext)->Value, &c->Type()->Symbols, true); + int v1 = GetInt(p1); + int v2 = GetInt(p2); if (v1 > v2) std::swap(v1, v2); state.Tics = (int16_t)clamp(v1, 0, INT16_MAX); state.TicRange = (uint16_t)clamp(v2 - v1, 0, UINT16_MAX); @@ -2346,7 +2349,7 @@ void ZCCCompiler::CompileStates() auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); if (code != nullptr) { - auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action); + auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action, (int)sl->Frames->Len()); state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false); } } From 010fd038beed8d3c46d4a763040387462857e29a Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 01:19:41 +0100 Subject: [PATCH 173/255] - scriptified A_KeenDie. - added an 'exact' parameter to FThinkerIterator's Next function. This is mainly for scripting which allows to do a lot more checks natively when running the iterator while looking for one specific class. --- src/CMakeLists.txt | 1 - src/dobject.cpp | 6 +++++ src/dthinker.cpp | 8 ++++-- src/dthinker.h | 6 ++--- src/g_doom/a_doommisc.cpp | 1 - src/g_doom/a_keen.cpp | 42 ----------------------------- src/g_shared/a_action.cpp | 3 ++- wadsrc/static/zscript/actor.txt | 3 +-- wadsrc/static/zscript/base.txt | 7 ++--- wadsrc/static/zscript/doom/keen.txt | 37 +++++++++++++++++++++++++ 10 files changed, 59 insertions(+), 55 deletions(-) delete mode 100644 src/g_doom/a_keen.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index adc90444d..9b4985a73 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -837,7 +837,6 @@ set( NOT_COMPILED_SOURCE_FILES sc_man_scanner.re g_doom/a_bossbrain.cpp g_doom/a_doomweaps.cpp - g_doom/a_keen.cpp g_doom/a_lostsoul.cpp g_doom/a_painelemental.cpp g_doom/a_revenant.cpp diff --git a/src/dobject.cpp b/src/dobject.cpp index 56d12787f..d057a71d3 100644 --- a/src/dobject.cpp +++ b/src/dobject.cpp @@ -369,6 +369,12 @@ DEFINE_ACTION_FUNCTION(DObject, Destroy) return 0; } +DEFINE_ACTION_FUNCTION(DObject, GetClass) +{ + PARAM_SELF_PROLOGUE(DObject); + ACTION_RETURN_OBJECT(self->GetClass()); +} + //========================================================================== // // diff --git a/src/dthinker.cpp b/src/dthinker.cpp index 022e147da..bacd53eee 100644 --- a/src/dthinker.cpp +++ b/src/dthinker.cpp @@ -480,7 +480,7 @@ void FThinkerIterator::Reinit () m_SearchingFresh = false; } -DThinker *FThinkerIterator::Next () +DThinker *FThinkerIterator::Next (bool exact) { if (m_ParentType == NULL) { @@ -496,7 +496,11 @@ DThinker *FThinkerIterator::Next () { DThinker *thinker = m_CurrThinker; m_CurrThinker = thinker->NextThinker; - if (thinker->IsKindOf(m_ParentType)) + if (exact) + { + if (thinker->IsA(m_ParentType)) return thinker; + } + else if (thinker->IsKindOf(m_ParentType)) { return thinker; } diff --git a/src/dthinker.h b/src/dthinker.h index 3f9647297..95985c2fb 100644 --- a/src/dthinker.h +++ b/src/dthinker.h @@ -121,7 +121,7 @@ private: public: FThinkerIterator (const PClass *type, int statnum=MAX_STATNUM+1); FThinkerIterator (const PClass *type, int statnum, DThinker *prev); - DThinker *Next (); + DThinker *Next (bool exact = false); void Reinit (); }; @@ -146,9 +146,9 @@ public: TThinkerIterator (const char *subclass, int statnum=MAX_STATNUM+1) : FThinkerIterator(PClass::FindClass(subclass), statnum) { } - T *Next () + T *Next (bool exact = false) { - return static_cast(FThinkerIterator::Next ()); + return static_cast(FThinkerIterator::Next (exact)); } }; diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 31ee228f8..534ed400e 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -24,7 +24,6 @@ // Include all the other Doom stuff here to reduce compile time #include "a_bossbrain.cpp" #include "a_doomweaps.cpp" -#include "a_keen.cpp" #include "a_lostsoul.cpp" #include "a_painelemental.cpp" #include "a_revenant.cpp" diff --git a/src/g_doom/a_keen.cpp b/src/g_doom/a_keen.cpp deleted file mode 100644 index b22f141b4..000000000 --- a/src/g_doom/a_keen.cpp +++ /dev/null @@ -1,42 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "p_local.h" -#include "p_spec.h" -#include "p_enemy.h" -#include "a_action.h" -#include "vm.h" -*/ - -// -// A_KeenDie -// DOOM II special, map 32. -// Uses special tag 666 by default. -// - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KeenDie) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT_DEF(doortag); - - A_Unblock(self, false); - - // scan the remaining thinkers to see if all Keens are dead - AActor *other; - TThinkerIterator iterator; - const PClass *matchClass = self->GetClass (); - - while ( (other = iterator.Next ()) ) - { - if (other != self && other->health > 0 && other->IsA (matchClass)) - { - // other Keen not dead - return 0; - } - } - - EV_DoDoor (DDoor::doorOpen, NULL, NULL, doortag, 2., 0, 0, 0); - return 0; -} - - diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index 0ec388de8..e1fa9a7fa 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -105,7 +105,8 @@ void A_Unblock(AActor *self, bool drop) DEFINE_ACTION_FUNCTION(AActor, A_NoBlocking) { PARAM_SELF_PROLOGUE(AActor); - A_Unblock(self, true); + PARAM_BOOL_DEF(drop); + A_Unblock(self, drop); return 0; } diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 091fba4b5..c6175b6f1 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -227,7 +227,7 @@ class Actor : Thinker native native void A_MonsterRail(); native void A_BFGSpray(class spraytype = "BFGExtra", int numrays = 40, int damagecount = 15, float angle = 90, float distance = 16*64, float vrange = 32, int damage = 0, int flags = 0); native void A_Pain(); - native void A_NoBlocking(); + native void A_NoBlocking(bool drop = true); void A_Fall() { A_NoBlocking(); } native void A_XScream(); native void A_Look(); @@ -241,7 +241,6 @@ class Actor : Thinker native native void A_BossDeath(); native void A_SkullAttack(float speed = 20); native void A_BetaSkullAttack(); - native void A_KeenDie(int doortag = 666); native void A_Detonate(); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); diff --git a/wadsrc/static/zscript/base.txt b/wadsrc/static/zscript/base.txt index cca39f1e2..4564f0e86 100644 --- a/wadsrc/static/zscript/base.txt +++ b/wadsrc/static/zscript/base.txt @@ -1,6 +1,7 @@ class Object native { /*virtual*/ native void Destroy(); + native class GetClass(); } class Thinker : Object native @@ -14,8 +15,8 @@ class ThinkerIterator : Object native MAX_STATNUM = 127 } - native static ThinkerIterator Create(class type = "Actor", int statnum=MAX_STATNUM+1); - native Thinker Next(); + native static ThinkerIterator Create(class type = "Actor", int statnum=MAX_STATNUM+1); + native Thinker Next(bool exact = false); native void Reinit(); } @@ -23,7 +24,7 @@ class DropItem : Object native { /* native fields listed for reference only for now native readonly DropItem Next; - native readonly name ItemName; // internally called 'name' which clashes with the type. + native readonly name Name; native readonly int Probability; native readonly int Amount; */ diff --git a/wadsrc/static/zscript/doom/keen.txt b/wadsrc/static/zscript/doom/keen.txt index a60e924ef..6d596c717 100644 --- a/wadsrc/static/zscript/doom/keen.txt +++ b/wadsrc/static/zscript/doom/keen.txt @@ -42,3 +42,40 @@ class CommanderKeen : Actor Goto Spawn; } } + + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + + // + // A_KeenDie + // DOOM II special, map 32. + // Uses special tag 666 by default. + // + + void A_KeenDie(int doortag = 666) + { + A_NoBlocking(false); + + // scan the remaining thinkers to see if all Keens are dead + ThinkerIterator it = ThinkerIterator.Create(GetClass()); + Actor mo; + while (mo = Actor(it.Next(true))) + { + if (mo.health > 0 && mo != self) + { + // other Keen not dead + return; + } + } + Door_Open(doortag, 16); + } +} + + From 514bcfb128afa13af1fad5216ad0c50361d71690 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 01:24:52 +0100 Subject: [PATCH 174/255] Print a clearer error message if a function name is encountered without parentheses. --- src/scripting/codegeneration/codegen.cpp | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 9e86fff8f..4111805ea 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5075,7 +5075,14 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } else { - ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); + if (sym->IsKindOf(RUNTIME_CLASS(PFunction))) + { + ScriptPosition.Message(MSG_ERROR, "Function '%s' used without ().\n", Identifier.GetChars()); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'.\n", Identifier.GetChars()); + } delete this; return nullptr; } From 76c34d7b2fc2d737384796d807778a41db92503d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 09:50:53 +0100 Subject: [PATCH 175/255] - block access to private and protected data for the external variabler getter functions. - fixed: The state index comparison against 0 was broken. - fixed: Resolving codegen nodes must set the strictness flag per function so that ZSCRIPT and DECORATE are done properly. --- src/p_actionfunctions.cpp | 4 ++-- src/p_setup.cpp | 2 +- src/scripting/codegeneration/codegen.cpp | 2 +- src/scripting/vm/vmbuilder.cpp | 3 +++ 4 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 9ed20daf8..1cfc44ae2 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -5031,7 +5031,7 @@ static PField *GetVar(DObject *self, FName varname) { PField *var = dyn_cast(self->GetClass()->Symbols.FindSymbol(varname, true)); - if (var == NULL || (var->Flags & VARF_Native) || !var->Type->IsKindOf(RUNTIME_CLASS(PBasicType))) + if (var == NULL || (var->Flags & (VARF_Native | VARF_Private | VARF_Protected | VARF_Static)) || !var->Type->IsKindOf(RUNTIME_CLASS(PBasicType))) { Printf("%s is not a user variable in class %s\n", varname.GetChars(), self->GetClass()->TypeName.GetChars()); @@ -5080,7 +5080,7 @@ static PField *GetArrayVar(DObject *self, FName varname, int pos) { PField *var = dyn_cast(self->GetClass()->Symbols.FindSymbol(varname, true)); - if (var == NULL || (var->Flags & VARF_Native) || + if (var == NULL || (var->Flags & (VARF_Native | VARF_Private | VARF_Protected | VARF_Static)) || !var->Type->IsKindOf(RUNTIME_CLASS(PArray)) || !static_cast(var->Type)->ElementType->IsKindOf(RUNTIME_CLASS(PBasicType))) { diff --git a/src/p_setup.cpp b/src/p_setup.cpp index aafed854b..11aef9d8d 100644 --- a/src/p_setup.cpp +++ b/src/p_setup.cpp @@ -1688,7 +1688,7 @@ static void SetMapThingUserData(AActor *actor, unsigned udi) udi++; - if (var == NULL || (var->Flags & VARF_Native) || !var->Type->IsKindOf(RUNTIME_CLASS(PBasicType))) + if (var == NULL || (var->Flags & (VARF_Native|VARF_Private|VARF_Protected|VARF_Static)) || !var->Type->IsKindOf(RUNTIME_CLASS(PBasicType))) { DPrintf(DMSG_WARNING, "%s is not a user variable in class %s\n", varname.GetChars(), actor->GetClass()->TypeName.GetChars()); diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4111805ea..db6355f84 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -7886,7 +7886,7 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) delete this; return nullptr; } - else if (Index->isConstant() && static_cast(Index) < 0) + else if (Index->isConstant() && static_cast(Index)->GetValue() < 0) { ScriptPosition.Message(MSG_ERROR, "State index must be positive"); delete this; diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 41ec4b920..5b792e7cc 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -713,6 +713,7 @@ void FFunctionBuildList::Build() ctx.FunctionArgs.Push(local); } + FScriptPosition::StrictErrors = !item.FromDecorate; item.Code = item.Code->Resolve(ctx); item.Proto = ctx.ReturnProto; @@ -758,4 +759,6 @@ void FFunctionBuildList::Build() fprintf(dump, "\n*************************************************************************\n%i code bytes\n", codesize * 4); fclose(dump); } + FScriptPosition::StrictErrors = false; + } \ No newline at end of file From b890f2b60892f6d2a337a5c21b6e86a46e9cc666 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 10:38:23 +0100 Subject: [PATCH 176/255] - fixed retrieval of constant for state index. --- src/scripting/codegeneration/codegen.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index db6355f84..f19e8901f 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -7886,7 +7886,7 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) delete this; return nullptr; } - else if (Index->isConstant() && static_cast(Index)->GetValue() < 0) + else if (Index->isConstant() && static_cast(Index)->GetValue().GetInt() < 0) { ScriptPosition.Message(MSG_ERROR, "State index must be positive"); delete this; From 24925c88a80e24478883a47dab8e5000e34b3e61 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 13:51:46 +0100 Subject: [PATCH 177/255] - added readonly pointers. They need to be defined with 'readonly'. These are significantly different from declaring a field readonly in that they do not disallow modification of the variable itself but what it points to. For the actor defaults this is necessary to prevent accidental modification. A readonly pointer is actually a different type than a regular pointer. - fixed code generation for dynamic cast. It was missing the jump instruction after the compare. --- src/dobjtype.cpp | 14 +++++++------- src/dobjtype.h | 5 +++-- src/scripting/codegeneration/codegen.cpp | 19 +++++++++++++++---- src/scripting/zscript/zcc-parse.lemon | 16 +++++++++++++++- src/scripting/zscript/zcc_compile.cpp | 10 +++++----- src/scripting/zscript/zcc_parser.h | 1 + wadsrc/static/zscript/actor.txt | 2 +- 7 files changed, 47 insertions(+), 20 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index f1726adbf..1b5d3bc7e 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -1467,7 +1467,7 @@ END_POINTERS //========================================================================== PPointer::PPointer() -: PBasicType(sizeof(void *), __alignof(void *)), PointedType(NULL) +: PBasicType(sizeof(void *), __alignof(void *)), PointedType(NULL), IsConst(false) { mDescriptiveName = "NullPointer"; SetOps(); @@ -1479,10 +1479,10 @@ PPointer::PPointer() // //========================================================================== -PPointer::PPointer(PType *pointsat) -: PBasicType(sizeof(void *), __alignof(void *)), PointedType(pointsat) +PPointer::PPointer(PType *pointsat, bool isconst) +: PBasicType(sizeof(void *), __alignof(void *)), PointedType(pointsat), IsConst(isconst) { - mDescriptiveName.Format("Pointer<%s>", pointsat->DescriptiveName()); + mDescriptiveName.Format("Pointer<%s%s>", pointsat->DescriptiveName(), isconst? "readonly " : ""); SetOps(); } @@ -1570,14 +1570,14 @@ bool PPointer::ReadValue(FSerializer &ar, const char *key, void *addr) const // //========================================================================== -PPointer *NewPointer(PType *type) +PPointer *NewPointer(PType *type, bool isconst) { size_t bucket; - PType *ptype = TypeTable.FindType(RUNTIME_CLASS(PPointer), (intptr_t)type, 0, &bucket); + PType *ptype = TypeTable.FindType(RUNTIME_CLASS(PPointer), (intptr_t)type, isconst ? 1 : 0, &bucket); if (ptype == NULL) { ptype = new PPointer(type); - TypeTable.AddType(ptype, RUNTIME_CLASS(PPointer), (intptr_t)type, 0, bucket); + TypeTable.AddType(ptype, RUNTIME_CLASS(PPointer), (intptr_t)type, isconst ? 1 : 0, bucket); } return static_cast(ptype); } diff --git a/src/dobjtype.h b/src/dobjtype.h index 30e22e868..9cf663983 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -535,9 +535,10 @@ class PPointer : public PBasicType HAS_OBJECT_POINTERS; public: PPointer(); - PPointer(PType *pointsat); + PPointer(PType *pointsat, bool isconst = false); PType *PointedType; + bool IsConst; virtual bool IsMatch(intptr_t id1, intptr_t id2) const; virtual void GetTypeIDs(intptr_t &id1, intptr_t &id2) const; @@ -877,7 +878,7 @@ PVector *NewVector(unsigned int size); PMap *NewMap(PType *keytype, PType *valuetype); PArray *NewArray(PType *type, unsigned int count); PDynArray *NewDynArray(PType *type); -PPointer *NewPointer(PType *type); +PPointer *NewPointer(PType *type, bool isconst = false); PClassPointer *NewClassPointer(PClass *restrict); PEnum *NewEnum(FName name, PTypeBase *outer); PStruct *NewStruct(FName name, PTypeBase *outer); diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f19e8901f..39034c752 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -241,6 +241,7 @@ static bool AreCompatiblePointerTypes(PType *dest, PType *source) auto fromtype = static_cast(source); auto totype = static_cast(dest); if (fromtype == nullptr) return true; + if (totype->IsConst && !fromtype->IsConst) return false; if (fromtype == totype) return true; if (fromtype->PointedType->IsKindOf(RUNTIME_CLASS(PClass)) && totype->PointedType->IsKindOf(RUNTIME_CLASS(PClass))) { @@ -3852,8 +3853,7 @@ ExpEmit FxTypeCheck::Emit(VMFunctionBuilder *build) FxDynamicCast::FxDynamicCast(PClass * cls, FxExpression *r) : FxExpression(EFX_DynamicCast, r->ScriptPosition) { - expr = new FxTypeCast(r, NewPointer(RUNTIME_CLASS(DObject)), true, true); - ValueType = NewPointer(cls); + expr = r; CastType = cls; } @@ -3878,6 +3878,15 @@ FxExpression *FxDynamicCast::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); SAFE_RESOLVE(expr, ctx); + bool constflag = expr->ValueType->IsKindOf(RUNTIME_CLASS(PPointer)) && static_cast(expr->ValueType)->IsConst; + expr = new FxTypeCast(expr, NewPointer(RUNTIME_CLASS(DObject), constflag), true, true); + expr = expr->Resolve(ctx); + if (expr == nullptr) + { + delete this; + return nullptr; + } + ValueType = NewPointer(CastType, constflag); return this; } @@ -3903,7 +3912,8 @@ ExpEmit FxDynamicCast::Emit(VMFunctionBuilder *build) build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), 2, 1); build->Emit(OP_RESULT, 0, REGT_INT, check.RegNum); - auto patch = build->Emit(OP_EQ_K, 0, check.RegNum, build->GetConstantInt(0)); + build->Emit(OP_EQ_K, 0, check.RegNum, build->GetConstantInt(0)); + auto patch = build->Emit(OP_JMP, 0); build->Emit(OP_LKP, out.RegNum, build->GetConstantAddress(nullptr, ATAG_OBJECT)); build->BackpatchToHere(patch); return out; @@ -5439,7 +5449,8 @@ FxStructMember::~FxStructMember() bool FxStructMember::RequestAddress(bool *writable) { AddressRequested = true; - if (writable != nullptr) *writable = AddressWritable && !(membervar->Flags & VARF_ReadOnly); + if (writable != nullptr) *writable = (AddressWritable && !(membervar->Flags & VARF_ReadOnly) && + (!classx->ValueType->IsKindOf(RUNTIME_CLASS(PPointer)) || !static_cast(classx->ValueType)->IsConst)); return true; } diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 9d22765fc..666eff5a2 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -668,6 +668,7 @@ type_name(X) ::= type_name1(A). NEW_AST_NODE(BasicType, type, A); type->Type = (EZCCBuiltinType)A.Int; type->UserType = NULL; + type->isconst = false; X = type; } type_name(X) ::= IDENTIFIER(A). /* User-defined type (struct, enum, or class) */ @@ -676,14 +677,27 @@ type_name(X) ::= IDENTIFIER(A). /* User-defined type (struct, enum, or class) NEW_AST_NODE(Identifier, id, A); type->Type = ZCC_UserType; type->UserType = id; + type->isconst = false; id->Id = A.Name(); X = type; } +type_name(X) ::= READONLY LT IDENTIFIER(A) GT. +{ + NEW_AST_NODE(BasicType, type, A); + NEW_AST_NODE(Identifier, id, A); + type->Type = ZCC_UserType; + type->UserType = id; + type->isconst = true; + id->Id = A.Name(); + X = type; +} + type_name(X) ::= DOT dottable_id(A). { NEW_AST_NODE(BasicType, type, A); type->Type = ZCC_UserType; type->UserType = A; + type->isconst = false; X = type; } @@ -698,7 +712,7 @@ type_name(X) ::= DOT dottable_id(A). %type type_list {ZCC_Type *} %type type_list_or_void {ZCC_Type *} %type type_or_array {ZCC_Type *} -%type class_restrictor {ZCC_Identifier *} + %type class_restrictor {ZCC_Identifier *} %type array_size{ZCC_Expression *} %type array_size_expr{ZCC_Expression *} diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f296a91b6..d6bf1d7f3 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1481,16 +1481,16 @@ PType *ZCCCompiler::ResolveUserType(ZCC_BasicType *type, PSymbolTable *symt) if (sym == nullptr && symt != &GlobalSymbols) sym = GlobalSymbols.FindSymbolInTable(type->UserType->Id, table); if (sym != nullptr && sym->IsKindOf(RUNTIME_CLASS(PSymbolType))) { - auto type = static_cast(sym)->Type; - if (type->IsKindOf(RUNTIME_CLASS(PEnum))) + auto ptype = static_cast(sym)->Type; + if (ptype->IsKindOf(RUNTIME_CLASS(PEnum))) { return TypeSInt32; // hack this to an integer until we can resolve the enum mess. } - if (type->IsKindOf(RUNTIME_CLASS(PClass))) + if (ptype->IsKindOf(RUNTIME_CLASS(PClass))) { - return NewPointer(type); + return NewPointer(ptype, type->isconst); } - return type; + return ptype; } Error(type, "Unable to resolve %s as type.", FName(type->UserType->Id).GetChars()); return TypeError; diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 715fa0be6..01ea0d2d0 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -310,6 +310,7 @@ struct ZCC_BasicType : ZCC_Type { EZCCBuiltinType Type; ZCC_Identifier *UserType; + bool isconst; }; struct ZCC_MapType : ZCC_Type diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index c6175b6f1..fdadab53c 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -53,7 +53,7 @@ class Actor : Thinker native return GetPointer(ptr_select1) == GetPointer(ptr_select2); } - native static /*readonly*/ Actor GetDefaultByType(class cls); + native static readonly GetDefaultByType(class cls); native void SetDamage(int dmg); native static bool isDehState(state st); native void SetOrigin(vector3 newpos, bool moving); From 98fa3d2d939d663acc1e2cf95c92dc0940f8c130 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 17:14:16 +0100 Subject: [PATCH 178/255] - added an accessor to the actor defaults. This might have been possible with less work using a function but that would have necessitated some type casts when using it on subclasses. - scriptified A_BarrelDestroy to test the above. --- src/dobjtype.cpp | 4 +- src/g_doom/a_doommisc.cpp | 18 ---- src/namedef.h | 1 + src/scripting/codegeneration/codegen.cpp | 126 ++++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 6 +- src/scripting/zscript/zcc-parse.lemon | 8 ++ wadsrc/static/zscript/actor.txt | 1 - wadsrc/static/zscript/doom/doommisc.txt | 17 +++ 8 files changed, 157 insertions(+), 24 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 1b5d3bc7e..e3c638062 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -1508,10 +1508,10 @@ void PPointer::SetOps() bool PPointer::IsMatch(intptr_t id1, intptr_t id2) const { - assert(id2 == 0); + assert(id2 == 0 || id2 == 1); PType *pointat = (PType *)id1; - return pointat == PointedType; + return pointat == PointedType && (!!id2) == IsConst; } //========================================================================== diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 534ed400e..9f3178295 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -29,21 +29,3 @@ #include "a_revenant.cpp" #include "a_scriptedmarine.cpp" -// The barrel of green goop ------------------------------------------------ - -DEFINE_ACTION_FUNCTION(AActor, A_BarrelDestroy) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (dmflags2 & DF2_BARRELS_RESPAWN) - { - self->Height = self->GetDefault()->Height; - self->renderflags |= RF_INVISIBLE; - self->flags &= ~MF_SOLID; - } - else - { - self->Destroy (); - } - return 0; -} diff --git a/src/namedef.h b/src/namedef.h index 809c28a9c..8f1a54337 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -683,6 +683,7 @@ xx(BuiltinNameToClass) xx(BuiltinFindMultiNameState) xx(BuiltinFindSingleNameState) xx(BuiltinHandleRuntimeState) +xx(BuiltinGetDefault) xx(Damage) // basic type names diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 39034c752..4ece6ad4f 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5015,6 +5015,27 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) delete this; return x->Resolve(ctx); } + + if (Identifier == NAME_Default) + { + if (ctx.Function->Variants[0].SelfClass == nullptr) + { + ScriptPosition.Message(MSG_ERROR, "Unable to access class defaults from static function"); + delete this; + return nullptr; + } + if (!ctx.Function->Variants[0].SelfClass->IsDescendantOf(RUNTIME_CLASS(AActor))) + { + ScriptPosition.Message(MSG_ERROR, "'Default' requires an actor type."); + delete this; + return nullptr; + } + + FxExpression * x = new FxClassDefaults(new FxSelf(ScriptPosition), ScriptPosition); + delete this; + return x->Resolve(ctx); + } + // Ugh, the horror. Constants need to be taken from the owning class, but members from the self class to catch invalid accesses here... // see if the current class (if valid) defines something with this name. PSymbolTable *symtbl; @@ -5348,6 +5369,95 @@ ExpEmit FxSelf::Emit(VMFunctionBuilder *build) } +//========================================================================== +// +// +// +//========================================================================== + +FxClassDefaults::FxClassDefaults(FxExpression *X, const FScriptPosition &pos) + : FxExpression(EFX_ClassDefaults, pos) +{ + obj = X; + EmitTail = false; +} + +FxClassDefaults::~FxClassDefaults() +{ + SAFE_DELETE(obj); +} + + +//========================================================================== +// +// +// +//========================================================================== + +PPrototype *FxClassDefaults::ReturnProto() +{ + EmitTail = true; + return FxExpression::ReturnProto(); +} + +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxClassDefaults::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + SAFE_RESOLVE(obj, ctx); + assert(obj->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))); + ValueType = NewPointer(static_cast(obj->ValueType)->PointedType, true); + return this; +} + +//========================================================================== +// +// +// +//========================================================================== + +int BuiltinGetDefault(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) +{ + assert(numparam == 1); + PARAM_POINTER_AT(0, obj, DObject); + ACTION_RETURN_OBJECT(obj->GetClass()->Defaults); +} + +//========================================================================== +// +// +// +//========================================================================== + +ExpEmit FxClassDefaults::Emit(VMFunctionBuilder *build) +{ + EmitParameter(build, obj, ScriptPosition); + PSymbol *sym = FindBuiltinFunction(NAME_BuiltinGetDefault, BuiltinGetDefault); + + assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); + assert(((PSymbolVMFunction *)sym)->Function != nullptr); + auto callfunc = ((PSymbolVMFunction *)sym)->Function; + int opcode = (EmitTail ? OP_TAIL_K : OP_CALL_K); + build->Emit(opcode, build->GetConstantAddress(callfunc, ATAG_OBJECT), 1, 1); + + if (EmitTail) + { + ExpEmit call; + call.Final = true; + return call; + } + + ExpEmit out(build, REGT_POINTER); + build->Emit(OP_RESULT, 0, REGT_POINTER, out.RegNum); + return out; + +} + //========================================================================== // // @@ -5465,6 +5575,21 @@ FxExpression *FxStructMember::Resolve(FCompileContext &ctx) CHECKRESOLVED(); SAFE_RESOLVE(classx, ctx); + if (membervar->SymbolName == NAME_Default) + { + if (!classx->ValueType->IsKindOf(RUNTIME_CLASS(PPointer)) + || !static_cast(classx->ValueType)->PointedType->IsKindOf(RUNTIME_CLASS(AActor))) + { + ScriptPosition.Message(MSG_ERROR, "'Default' requires an actor type."); + delete this; + return nullptr; + } + FxExpression * x = new FxClassDefaults(classx, ScriptPosition); + classx = nullptr; + delete this; + return x->Resolve(ctx); + } + if (classx->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) { PPointer *ptrtype = dyn_cast(classx->ValueType); @@ -5581,7 +5706,6 @@ FxClassMember::FxClassMember(FxExpression *x, PField* mem, const FScriptPosition : FxStructMember(x, mem, pos) { ExprType = EFX_ClassMember; - //if (classx->IsDefaultObject()) Readonly=true; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index b118b8d5d..a244e519e 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -355,12 +355,14 @@ public: class FxClassDefaults : public FxExpression { FxExpression *obj; + bool EmitTail; public: - FxClassDefaults(FxExpression*, const FScriptPosition &); + FxClassDefaults(FxExpression *, const FScriptPosition &); ~FxClassDefaults(); + PPrototype *ReturnProto(); FxExpression *Resolve(FCompileContext&); - bool IsDefaultObject() const; + ExpEmit Emit(VMFunctionBuilder *build); }; //========================================================================== diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 666eff5a2..fc707428e 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -224,6 +224,14 @@ dottable_id(X) ::= dottable_id(A) DOT IDENTIFIER(B). A->AppendSibling(id2); X = A; /*X-overwrites-A*/ } +dottable_id(X) ::= dottable_id(A) DOT DEFAULT. +{ + NEW_AST_NODE(Identifier,id2,A); + id2->Id = NAME_Default; + A->AppendSibling(id2); + X = A; /*X-overwrites-A*/ +} + // a bit of a hack to allow the 'color' token to be used inside default properties. // as a variable name it is practically meaningless because it cannot defined // as such anywhere so it will always produce an error during processing. diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index fdadab53c..efdeb3ef1 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -357,7 +357,6 @@ class Actor : Thinker native native int A_Explode(int damage = -1, int distance = -1, int flags = XF_HURTSOURCE, bool alert = false, int fulldamagedistance = 0, int nails = 0, int naildamage = 10, class pufftype = "BulletPuff", name damagetype = "none"); native void A_Stop(); native void A_Respawn(int flags = 1); - native void A_BarrelDestroy(); native void A_QueueCorpse(); native void A_DeQueueCorpse(); native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = null); diff --git a/wadsrc/static/zscript/doom/doommisc.txt b/wadsrc/static/zscript/doom/doommisc.txt index 80e330a68..a11c411f8 100644 --- a/wadsrc/static/zscript/doom/doommisc.txt +++ b/wadsrc/static/zscript/doom/doommisc.txt @@ -34,6 +34,23 @@ class ExplosiveBarrel : Actor } } +extend class Actor +{ + void A_BarrelDestroy() + { + if (GetCVar("sv_barrelrespawn")) + { + Height = Default.Height; + bInvisible = true; + bSolid = false; + } + else + { + Destroy(); + } + } +} + // Bullet puff ------------------------------------------------------------- class BulletPuff : Actor From 1b77a8f491300c31096f7cc00de9f16c6ce6d8f7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 18:05:57 +0100 Subject: [PATCH 179/255] - fixed: Tacking on a return statement should only be done if the function has branches that actually reach the end. Otherwise it may interfere with return type deduction. - used the return check to optimize out unneeded jumps at the end of an if statement's first block. --- src/scripting/codegeneration/codegen.cpp | 52 +++++++++++++++++++++++- src/scripting/codegeneration/codegen.h | 5 +++ src/scripting/vm/vmbuilder.cpp | 7 ++++ src/scripting/zscript/zcc_compile.cpp | 6 +-- 4 files changed, 65 insertions(+), 5 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 4ece6ad4f..5ab66c4c2 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6879,6 +6879,18 @@ FxExpression *FxSequence::Resolve(FCompileContext &ctx) return this; } +//========================================================================== +// +// FxSequence :: CheckReturn +// +//========================================================================== + +bool FxSequence::CheckReturn() +{ + // a sequence always returns when its last element returns. + return Expressions.Size() > 0 && Expressions.Last()->CheckReturn(); +} + //========================================================================== // // FxSequence :: Emit @@ -7194,6 +7206,24 @@ ExpEmit FxSwitchStatement::Emit(VMFunctionBuilder *build) return ExpEmit(); } +//========================================================================== +// +// FxSequence :: CheckReturn +// +//========================================================================== + +bool FxSwitchStatement::CheckReturn() +{ + //A switch statement returns when it contains no breaks and ends with a return + for (auto line : *Content) + { + if (line->ExprType == EFX_JumpStatement) + { + return false; // Break means that the end of the statement will be reached, Continue cannot happen in the last statement of the last block. + } + } + return Content->Size() > 0 && Content->Last()->CheckReturn(); +} //========================================================================== // @@ -7355,17 +7385,35 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) v.Free(build); if (path2 != nullptr) { - size_t path1jump = build->Emit(OP_JMP, 0); + size_t path1jump; + + // if the branch ends with a return we do not need a terminating jmp. + if (!path1->CheckReturn()) path1jump = build->Emit(OP_JMP, 0); + else path1jump = 0xffffffff; // Evaluate second path build->BackpatchToHere(jumpspot); v = path2->Emit(build); v.Free(build); jumpspot = path1jump; } - build->BackpatchToHere(jumpspot); + if (jumpspot != 0xffffffff) build->BackpatchToHere(jumpspot); return ExpEmit(); } + +//========================================================================== +// +// FxIfStatement :: CheckReturn +// +//========================================================================== + +bool FxIfStatement::CheckReturn() +{ + //An if statement returns if both branches return, if present. + return (WhenTrue == nullptr || WhenTrue->CheckReturn()) && + (WhenFalse == nullptr || WhenFalse->CheckReturn()); +} + //========================================================================== // // FxLoopStatement :: Resolve diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index a244e519e..f4426da90 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -297,6 +297,7 @@ public: virtual bool RequestAddress(bool *writable); virtual PPrototype *ReturnProto(); virtual VMFunction *GetDirectFunction(); + virtual bool CheckReturn() { return false; } bool IsNumeric() const { return ValueType != TypeName && ValueType->GetRegCount() == 1 && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT); } bool IsFloat() const { return ValueType->GetRegType() == REGT_FLOAT && ValueType->GetRegCount() == 1; } bool IsInteger() const { return ValueType != TypeName && (ValueType->GetRegType() == REGT_INT); } @@ -1390,6 +1391,7 @@ public: ExpEmit Emit(VMFunctionBuilder *build); void Add(FxExpression *expr) { if (expr != NULL) Expressions.Push(expr); expr->NeedResult = false; } VMFunction *GetDirectFunction(); + bool CheckReturn(); }; //========================================================================== @@ -1438,6 +1440,7 @@ public: ~FxSwitchStatement(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); + bool CheckReturn(); }; //========================================================================== @@ -1476,6 +1479,7 @@ public: ~FxIfStatement(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); + bool CheckReturn(); }; //========================================================================== @@ -1589,6 +1593,7 @@ public: FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); VMFunction *GetDirectFunction(); + bool CheckReturn() { return true; } }; //========================================================================== diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 5b792e7cc..f8451e62c 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -715,6 +715,13 @@ void FFunctionBuildList::Build() FScriptPosition::StrictErrors = !item.FromDecorate; item.Code = item.Code->Resolve(ctx); + if (!item.Code->CheckReturn()) + { + auto newcmpd = new FxCompoundStatement(item.Code->ScriptPosition); + newcmpd->Add(item.Code); + newcmpd->Add(new FxReturnStatement(nullptr, item.Code->ScriptPosition)); + item.Code = newcmpd->Resolve(ctx); + } item.Proto = ctx.ReturnProto; // Make sure resolving it didn't obliterate it. diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index d6bf1d7f3..44b2f489c 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2464,15 +2464,15 @@ FxExpression *ZCCCompiler::ConvertAST(PClass *cls, ZCC_TreeNode *ast) // This must be done here so that we can check for a trailing return statement. auto x = new FxCompoundStatement(*ast); auto compound = static_cast(ast); - bool isreturn = false; + //bool isreturn = false; auto node = compound->Content; if (node != nullptr) do { x->Add(ConvertNode(node)); - isreturn = node->NodeType == AST_ReturnStmt; + //isreturn = node->NodeType == AST_ReturnStmt; node = static_cast(node->SiblingNext); } while (node != compound->Content); - if (!isreturn) x->Add(new FxReturnStatement(nullptr, *ast)); + //if (!isreturn) x->Add(new FxReturnStatement(nullptr, *ast)); return x; } } From 0851d698de84259448b013050af40054619f722f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 18:15:53 +0100 Subject: [PATCH 180/255] - don't run constant state indices through the runtime checker. --- src/scripting/codegeneration/codegen.cpp | 30 +++++++++++++++++++----- 1 file changed, 24 insertions(+), 6 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 5ab66c4c2..cfff4ef35 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1431,11 +1431,29 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) delete this; return nullptr; } - FxExpression *x = new FxRuntimeStateIndex(basex); - x = x->Resolve(ctx); - basex = nullptr; - delete this; - return x; + if (basex->isConstant()) + { + int i = static_cast(basex)->GetValue().GetInt(); + if (i < 0) + { + ScriptPosition.Message(MSG_ERROR, "State index must be positive"); + delete this; + return nullptr; + } + FxExpression *x = new FxStateByIndex(i, ScriptPosition); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } + else + { + FxExpression *x = new FxRuntimeStateIndex(basex); + x = x->Resolve(ctx); + basex = nullptr; + delete this; + return x; + } } } else if (ValueType->IsKindOf(RUNTIME_CLASS(PClassPointer))) @@ -8019,7 +8037,7 @@ FxExpression *FxStateByIndex::Resolve(FCompileContext &ctx) ABORT(ctx.Class); auto aclass = dyn_cast(ctx.Class); - // This expression type can only be used from DECORATE, so there's no need to consider the possibility of calling it from a non-actor. + // This expression type can only be used from actors, for everything else it has already produced a compile error. assert(aclass != nullptr && aclass->NumOwnedStates > 0); if (aclass->NumOwnedStates <= index) From 0f9ebff3ee14cb8423c78dbbee7340e862666844 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 18:56:04 +0100 Subject: [PATCH 181/255] - fixed: The return checking code must be inside the nullptr check for item.code. --- src/scripting/vm/vmbuilder.cpp | 15 ++++++++------- 1 file changed, 8 insertions(+), 7 deletions(-) diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index f8451e62c..aa6188f90 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -715,13 +715,6 @@ void FFunctionBuildList::Build() FScriptPosition::StrictErrors = !item.FromDecorate; item.Code = item.Code->Resolve(ctx); - if (!item.Code->CheckReturn()) - { - auto newcmpd = new FxCompoundStatement(item.Code->ScriptPosition); - newcmpd->Add(item.Code); - newcmpd->Add(new FxReturnStatement(nullptr, item.Code->ScriptPosition)); - item.Code = newcmpd->Resolve(ctx); - } item.Proto = ctx.ReturnProto; // Make sure resolving it didn't obliterate it. @@ -729,6 +722,14 @@ void FFunctionBuildList::Build() { assert(item.Proto != nullptr); + if (!item.Code->CheckReturn()) + { + auto newcmpd = new FxCompoundStatement(item.Code->ScriptPosition); + newcmpd->Add(item.Code); + newcmpd->Add(new FxReturnStatement(nullptr, item.Code->ScriptPosition)); + item.Code = newcmpd->Resolve(ctx); + } + // Generate prototype for anonymous functions. VMScriptFunction *sfunc = item.Function; // create a new prototype from the now known return type and the argument list of the function's template prototype. From b59f4e950f83602b4058fe3bfde546b1c7da164e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 5 Nov 2016 21:02:26 +0100 Subject: [PATCH 182/255] - fixed: The return prototyxpe may only be retrieved after the return state of the function has been checked. Also made this a real error message instead of an assert because it will inevitably result in a crash if the prototype cannot be generated, making diagnostics impossible. --- src/scripting/vm/vmbuilder.cpp | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index aa6188f90..f8ca44ba6 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -715,13 +715,10 @@ void FFunctionBuildList::Build() FScriptPosition::StrictErrors = !item.FromDecorate; item.Code = item.Code->Resolve(ctx); - item.Proto = ctx.ReturnProto; // Make sure resolving it didn't obliterate it. if (item.Code != nullptr) { - assert(item.Proto != nullptr); - if (!item.Code->CheckReturn()) { auto newcmpd = new FxCompoundStatement(item.Code->ScriptPosition); @@ -730,6 +727,13 @@ void FFunctionBuildList::Build() item.Code = newcmpd->Resolve(ctx); } + item.Proto = ctx.ReturnProto; + if (item.Proto == nullptr) + { + item.Code->ScriptPosition.Message(MSG_ERROR, "Function %s without prototype", item.PrintableName.GetChars()); + continue; + } + // Generate prototype for anonymous functions. VMScriptFunction *sfunc = item.Function; // create a new prototype from the now known return type and the argument list of the function's template prototype. From c9a96ed0aef5eeb2c3d851483c585c766699727e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 01:34:54 +0100 Subject: [PATCH 183/255] - fixed: CALL_ACTION always set 3 args, even for normal methods. Also moved this to a sunfunction because the macro created a lot of code. --- src/scripting/vm/vm.h | 7 +++---- src/scripting/vm/vmframe.cpp | 7 +++++++ 2 files changed, 10 insertions(+), 4 deletions(-) diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 811fb82e0..3120bbd61 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -1034,10 +1034,9 @@ struct AFuncDesc //#define DECLARE_PARAMINFO AActor *self, AActor *stateowner, FState *CallingState, int ParameterIndex, StateCallData *statecall //#define PUSH_PARAMINFO self, stateowner, CallingState, ParameterIndex, statecall -#define CALL_ACTION(name,self) { /*AF_##name(self, self, NULL, 0, NULL)*/ \ - VMValue params[3] = { self, self, VMValue(NULL, ATAG_GENERIC) }; \ - stack->Call(name##_VMPtr, params, countof(params), NULL, 0, NULL); \ - } +class AActor; +void CallAction(VMFrameStack *stack, VMFunction *vmfunc, AActor *self); +#define CALL_ACTION(name, self) CallAction(stack, name##_VMPtr, self); #define ACTION_RETURN_STATE(v) do { FState *state = v; if (numret > 0) { assert(ret != NULL); ret->SetPointer(state, ATAG_STATE); return 1; } return 0; } while(0) diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index c54b585e9..1ccf3321e 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -491,3 +491,10 @@ int VMFrameStack::Call(VMFunction *func, VMValue *params, int numparams, VMRetur throw; } } + +class AActor; +void CallAction(VMFrameStack *stack, VMFunction *vmfunc, AActor *self) +{ + VMValue params[3] = { self, self, VMValue(nullptr, ATAG_GENERIC) }; + stack->Call(vmfunc, params, vmfunc->ImplicitArgs, nullptr, 0, nullptr); +} From 0130bde07740e5717a3c7c796a3c8c06ad6a99fd Mon Sep 17 00:00:00 2001 From: Major Cooke Date: Sat, 5 Nov 2016 20:15:41 -0500 Subject: [PATCH 184/255] Do not allow DMG_FORCED to penetrate player ultimate degreelessness/buddha. --- src/p_interaction.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/p_interaction.cpp b/src/p_interaction.cpp index b4ecc827e..ec8b5e495 100644 --- a/src/p_interaction.cpp +++ b/src/p_interaction.cpp @@ -1254,11 +1254,10 @@ int P_DamageMobj (AActor *target, AActor *inflictor, AActor *source, int damage, damage = target->health - 1; } - if (!(flags & DMG_FORCED)) { // check the real player, not a voodoo doll here for invulnerability effects if ((!telefragDamage && ((player->mo->flags2 & MF2_INVULNERABLE) || - (player->cheats & CF_GODMODE))) || + (player->cheats & CF_GODMODE)) && !(flags & DMG_FORCED)) || (player->cheats & CF_GODMODE2) || (player->mo->flags5 & MF5_NODAMAGE)) //Absolutely no hurting if NODAMAGE is involved. Same for GODMODE2. { // player is invulnerable, so don't hurt him @@ -1331,7 +1330,8 @@ int P_DamageMobj (AActor *target, AActor *inflictor, AActor *source, int damage, // but telefragging should still do enough damage to kill the player) // Ignore players that are already dead. // [MC]Buddha2 absorbs telefrag damage, and anything else thrown their way. - if (!(flags & DMG_FORCED) && (((player->cheats & CF_BUDDHA2) || (((player->cheats & CF_BUDDHA) || (player->mo->flags7 & MF7_BUDDHA)) && !telefragDamage)) && (player->playerstate != PST_DEAD))) + if ((((player->cheats & CF_BUDDHA2) || + (((player->cheats & CF_BUDDHA) || (player->mo->flags7 & MF7_BUDDHA)) && !telefragDamage && !(flags & DMG_FORCED))) && (player->playerstate != PST_DEAD))) { // If this is a voodoo doll we need to handle the real player as well. player->mo->health = target->health = player->health = 1; From c3ae56028934cc38ce3e08e415712a4ab27c7fbf Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 09:22:03 +0100 Subject: [PATCH 185/255] - scriptified two more trivial functions. --- src/p_enemy.cpp | 30 +----------------------------- wadsrc/static/zscript/actor.txt | 4 ++-- 2 files changed, 3 insertions(+), 31 deletions(-) diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 833732008..20a549a51 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -3061,20 +3061,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_XScream) return 0; } -//=========================================================================== -// -// A_ScreamAndUnblock -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_ScreamAndUnblock) -{ - PARAM_SELF_PROLOGUE(AActor); - CALL_ACTION(A_Scream, self); - A_Unblock(self, true); - return 0; -} - //=========================================================================== // // A_ActiveSound @@ -3086,25 +3072,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_ActiveSound) PARAM_SELF_PROLOGUE(AActor); if (self->ActiveSound) { - S_Sound (self, CHAN_VOICE, self->ActiveSound, 1, ATTN_NORM); + S_Sound(self, CHAN_VOICE, self->ActiveSound, 1, ATTN_NORM); } return 0; } -//=========================================================================== -// -// A_ActiveAndUnblock -// -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_ActiveAndUnblock) -{ - PARAM_SELF_PROLOGUE(AActor); - CALL_ACTION(A_ActiveSound, self); - A_Unblock(self, true); - return 0; -} - //--------------------------------------------------------------------------- // // Modifies the drop amount of this item according to the current skill's diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index efdeb3ef1..0365be657 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -130,6 +130,8 @@ class Actor : Thinker native void A_SetRipperLevel(int level) { RipperLevel = level; } void A_SetRipMin(int minimum) { RipLevelMin = minimum; } void A_SetRipMax(int maximum) { RipLevelMax = maximum; } + void A_ScreamAndUnblock() { A_Scream(); A_NoBlocking(); } + void A_ActiveAndUnblock() { A_ActiveSound(); A_NoBlocking(); } void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false) { @@ -246,8 +248,6 @@ class Actor : Thinker native native void A_M_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff"); - native void A_ScreamAndUnblock(); - native void A_ActiveAndUnblock(); native void A_ActiveSound(); native void A_FastChase(); From dbde0971ef7f508161ab5851d1540921a2d76dc4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 10:28:01 +0100 Subject: [PATCH 186/255] - removed the second 'calculated' return value from the damage function call in GetMissileDamage as it is no longer needed or even code being generated for. --- src/p_mobj.cpp | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index a567f5486..3ea4a25e1 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -3197,14 +3197,13 @@ int AActor::GetMissileDamage (int mask, int add) } VMFrameStack stack; VMValue param = this; - VMReturn results[2]; + VMReturn result; - int amount, calculated = false; + int amount; - results[0].IntAt(&amount); - results[1].IntAt(&calculated); + result.IntAt(&amount); - if (stack.Call(DamageFunc, ¶m, 1, results, 2) < 1) + if (stack.Call(DamageFunc, ¶m, 1, &result, 1) < 1) { // No results return 0; } From 062574b7266a8ffcde3bf04c9d32d6e11318dcce Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 11:36:12 +0100 Subject: [PATCH 187/255] - fixed damage handling in A_BetaSkullAttack. For unknown reasons this completely bypassed the normal damage function semantics and even multiplied that with a random value. - made some tests about calling script code from native functions. * scriptified A_SkullAttack to have something to test * changed the A_SkullAttack call in A_PainShootSkull. * use a macro to declare the function pointer. Using local static variable init directly results in hideous code for the need of being thread-safe (which, even if the engine was made multithreaded is not needed here.) * Importsnt node here: Apparently passing an actor pointer to the VMValue constructor results in the void * version being called, not the DObject * version. --- src/g_doom/a_doommisc.cpp | 1 - src/g_doom/a_lostsoul.cpp | 86 ---------------------- src/g_doom/a_painelemental.cpp | 10 ++- src/info.cpp | 2 +- src/p_mobj.cpp | 15 ++++ src/r_utility.cpp | 24 ++++++ src/scripting/decorate/thingdef_states.cpp | 4 +- src/scripting/thingdef_data.cpp | 5 +- src/scripting/vm/vm.h | 3 +- src/scripting/vm/vmframe.cpp | 3 +- wadsrc/static/zscript/actor.txt | 4 +- wadsrc/static/zscript/doom/lostsoul.txt | 38 ++++++++++ 12 files changed, 97 insertions(+), 98 deletions(-) delete mode 100644 src/g_doom/a_lostsoul.cpp diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 9f3178295..1df9a4e7c 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -24,7 +24,6 @@ // Include all the other Doom stuff here to reduce compile time #include "a_bossbrain.cpp" #include "a_doomweaps.cpp" -#include "a_lostsoul.cpp" #include "a_painelemental.cpp" #include "a_revenant.cpp" #include "a_scriptedmarine.cpp" diff --git a/src/g_doom/a_lostsoul.cpp b/src/g_doom/a_lostsoul.cpp deleted file mode 100644 index 1c33f47a7..000000000 --- a/src/g_doom/a_lostsoul.cpp +++ /dev/null @@ -1,86 +0,0 @@ -/* -#include "templates.h" -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gi.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -*/ - - FRandom pr_oldsoul ("BetaLostSoul"); - -// -// SkullAttack -// Fly at the player like a missile. -// - -void A_SkullAttack(AActor *self, double speed) -{ - AActor *dest; - if (!self->target) - return; - - dest = self->target; - self->flags |= MF_SKULLFLY; - - S_Sound (self, CHAN_VOICE, self->AttackSound, 1, ATTN_NORM); - A_FaceTarget (self); - self->VelFromAngle(speed); - self->Vel.Z = (dest->Center() - self->Z()) / self->DistanceBySpeed(dest, speed); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT_DEF(speed); - - if (speed <= 0) - speed = SKULLSPEED; - A_SkullAttack(self, speed); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_BetaSkullAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - int damage; - if (!self || !self->target || self->target->GetSpecies() == self->GetSpecies()) - return 0; - S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM); - A_FaceTarget(self); - damage = (pr_oldsoul()%8+1)*self->GetMissileDamage(0,1); - P_DamageMobj(self->target, self, self, damage, NAME_None); - return 0; -} - - - -//========================================================================== -// -// CVAR transsouls -// -// How translucent things drawn with STYLE_SoulTrans are. Normally, only -// Lost Souls have this render style, but a dehacked patch could give other -// things this style. Values less than 0.25 will automatically be set to -// 0.25 to ensure some degree of visibility. Likewise, values above 1.0 will -// be set to 1.0, because anything higher doesn't make sense. -// -//========================================================================== - -CUSTOM_CVAR (Float, transsouls, 0.75f, CVAR_ARCHIVE) -{ - if (self < 0.25f) - { - self = 0.25f; - } - else if (self > 1.f) - { - self = 1.f; - } -} diff --git a/src/g_doom/a_painelemental.cpp b/src/g_doom/a_painelemental.cpp index 09160ddeb..f2db5a240 100644 --- a/src/g_doom/a_painelemental.cpp +++ b/src/g_doom/a_painelemental.cpp @@ -21,7 +21,7 @@ enum PA_Flags // A_PainShootSkull // Spawn a lost soul and launch it at the target // -void A_PainShootSkull (AActor *self, DAngle Angle, PClassActor *spawntype, int flags = 0, int limit = -1) +void A_PainShootSkull (VMFrameStack *stack, AActor *self, DAngle Angle, PClassActor *spawntype, int flags = 0, int limit = -1) { AActor *other; double prestep; @@ -137,7 +137,10 @@ void A_PainShootSkull (AActor *self, DAngle Angle, PClassActor *spawntype, int f other->CopyFriendliness (self, !(flags & PAF_NOTARGET)); if (!(flags & PAF_NOSKULLATTACK)) - A_SkullAttack(other, SKULLSPEED); + { + DECLARE_VMFUNC(AActor, A_SkullAttack); + CallAction(stack, A_SkullAttack, other); + } } @@ -148,7 +151,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_PainShootSkull) PARAM_FLOAT(angle); PARAM_INT_DEF(flags); PARAM_INT_DEF(limit); - A_PainShootSkull(self, angle, spawntype, flags, limit); + A_PainShootSkull(stack, self, angle, spawntype, flags, limit); + return 0; } diff --git a/src/info.cpp b/src/info.cpp index 26bd306fa..4705e0e53 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -68,7 +68,7 @@ cycle_t ActionCycles; void FState::SetAction(const char *name) { - ActionFunc = FindGlobalActionFunction(name)->Variants[0].Implementation; + ActionFunc = FindVMFunction(RUNTIME_CLASS(AActor), name); } bool FState::CallAction(AActor *self, AActor *stateowner, FStateParamInfo *info, FState **stateret) diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 3ea4a25e1..d0c0af1f5 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6445,6 +6445,12 @@ FName AActor::GetSpecies() return Species = thistype->TypeName; // [GZ] Speeds up future calls. } +DEFINE_ACTION_FUNCTION(AActor, GetSpecies) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_INT(self->GetSpecies()); +} + //========================================================================== // // AActor :: IsFriend @@ -6850,6 +6856,14 @@ DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) return 0; } +DEFINE_ACTION_FUNCTION(AActor, DistanceBySpeed) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(targ, AActor); + PARAM_FLOAT(speed); + ACTION_RETURN_FLOAT(self->DistanceBySpeed(targ, speed)); +} + DEFINE_ACTION_FUNCTION(AActor, SetXYZ) { PARAM_SELF_PROLOGUE(AActor); @@ -6879,6 +6893,7 @@ DEFINE_ACTION_FUNCTION(AActor, Vec2OffsetZ) PARAM_BOOL_DEF(absolute); ACTION_RETURN_VEC3(self->Vec2OffsetZ(x, y, z, absolute)); } + //---------------------------------------------------------------------------- // // DropItem handling diff --git a/src/r_utility.cpp b/src/r_utility.cpp index b009912f0..158834929 100644 --- a/src/r_utility.cpp +++ b/src/r_utility.cpp @@ -1104,3 +1104,27 @@ void FCanvasTextureInfo::Mark() } } + +//========================================================================== +// +// CVAR transsouls +// +// How translucent things drawn with STYLE_SoulTrans are. Normally, only +// Lost Souls have this render style. +// Values less than 0.25 will automatically be set to +// 0.25 to ensure some degree of visibility. Likewise, values above 1.0 will +// be set to 1.0, because anything higher doesn't make sense. +// +//========================================================================== + +CUSTOM_CVAR(Float, transsouls, 0.75f, CVAR_ARCHIVE) +{ + if (self < 0.25f) + { + self = 0.25f; + } + else if (self > 1.f) + { + self = 1.f; + } +} diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 59cf30938..3b9930928 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -99,7 +99,9 @@ FxVMFunctionCall *DoActionSpecials(FScanner &sc, FState & state, Baggage &bag) { sc.ScriptError ("Too many arguments to %s", specname.GetChars()); } - return new FxVMFunctionCall(new FxSelf(sc), FindGlobalActionFunction("A_CallSpecial"), args, sc, false); + auto f = dyn_cast(RUNTIME_CLASS(AActor)->Symbols.FindSymbol("A_CallSpecial", false)); + assert(f != nullptr); + return new FxVMFunctionCall(new FxSelf(sc), f, args, sc, false); } return NULL; } diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 74c685ea8..8152e9977 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -602,9 +602,10 @@ AFuncDesc *FindFunction(const char * string) // //========================================================================== -PFunction *FindGlobalActionFunction(const char *name) +VMFunction *FindVMFunction(PClass *cls, const char *name) { - return dyn_cast(RUNTIME_CLASS(AActor)->Symbols.FindSymbol(name, false)); + auto f = dyn_cast(cls->Symbols.FindSymbol(name, true)); + return f == nullptr ? nullptr : f->Variants[0].Implementation; } diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 3120bbd61..abce2f557 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -1071,7 +1071,8 @@ void CallAction(VMFrameStack *stack, VMFunction *vmfunc, AActor *self); class PFunction; -PFunction *FindGlobalActionFunction(const char *name); +VMFunction *FindVMFunction(PClass *cls, const char *name); +#define DECLARE_VMFUNC(cls, name) static VMFunction *name; if (name == nullptr) name = FindVMFunction(RUNTIME_CLASS(cls), #name); diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index 1ccf3321e..f622e114d 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -495,6 +495,7 @@ int VMFrameStack::Call(VMFunction *func, VMValue *params, int numparams, VMRetur class AActor; void CallAction(VMFrameStack *stack, VMFunction *vmfunc, AActor *self) { - VMValue params[3] = { self, self, VMValue(nullptr, ATAG_GENERIC) }; + // Without the type cast this picks the 'void *' assignment... + VMValue params[3] = { (DObject*)self, (DObject*)self, VMValue(nullptr, ATAG_GENERIC) }; stack->Call(vmfunc, params, vmfunc->ImplicitArgs, nullptr, 0, nullptr); } diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 0365be657..287808b67 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -81,6 +81,8 @@ class Actor : Thinker native native void CopyFriendliness (Actor other, bool changeTarget, bool resetHealth = true); native bool LookForPlayers(bool allaround); native bool TeleportMove(Vector3 pos, bool telefrag, bool modifyactor = true); + native double DistanceBySpeed(Actor other, double speed); + native name GetSpecies(); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); @@ -241,8 +243,6 @@ class Actor : Thinker native native void A_SkelFist(); native void A_SkelMissile(); native void A_BossDeath(); - native void A_SkullAttack(float speed = 20); - native void A_BetaSkullAttack(); native void A_Detonate(); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); diff --git a/wadsrc/static/zscript/doom/lostsoul.txt b/wadsrc/static/zscript/doom/lostsoul.txt index 69574e5c7..00158e071 100644 --- a/wadsrc/static/zscript/doom/lostsoul.txt +++ b/wadsrc/static/zscript/doom/lostsoul.txt @@ -81,3 +81,41 @@ class BetaSkull : LostSoul Wait; } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + const SKULLSPEED = 20; + + void A_SkullAttack(float skullspeed = SKULLSPEED) + { + if (target == null) return; + + if (skullspeed <= 0) skullspeed = SKULLSPEED; + + bSkullfly = true; + A_PlaySound(AttackSound, CHAN_VOICE); + A_FaceTarget(); + VelFromAngle(skullspeed); + Vel.Z = (target.pos.Z + target.Height/2 - Vel.Z) / DistanceBySpeed(target, speed); + } + + void A_BetaSkullAttack() + { + if (target == null || target.GetSpecies() == self.GetSpecies()) return; + + A_PlaySound(AttackSound, CHAN_WEAPON); + A_FaceTarget(); + + int damage = GetMissileDamage(7,1); + target.DamageMobj(self, self, damage, 'None'); + } +} + + + From c354000f1ce0dfdd49aa4e1839b79e189b320bbd Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 12:00:16 +0100 Subject: [PATCH 188/255] - block "" and 0 as valid state names in ZScript. There were common workarounds for the lack of a null pointer in DECORATE which no longer are supported as those and would produce errors now. --- src/scripting/codegeneration/codegen.cpp | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index cfff4ef35..f296ac6e7 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1411,7 +1411,14 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) // Right now this only supports string constants. There should be an option to pass a string variable, too. if (basex->isConstant() && (basex->ValueType == TypeString || basex->ValueType == TypeName)) { - FxExpression *x = new FxMultiNameState(static_cast(basex)->GetValue().GetString(), basex->ScriptPosition); + const char *s = static_cast(basex)->GetValue().GetString(); + if (*s == 0 && !ctx.FromDecorate) // DECORATE should never get here at all, but let's better be safe. + { + ScriptPosition.Message(MSG_ERROR, "State jump to empty label."); + delete this; + return nullptr; + } + FxExpression *x = new FxMultiNameState(s, basex->ScriptPosition); x = x->Resolve(ctx); basex = nullptr; delete this; @@ -1434,7 +1441,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) if (basex->isConstant()) { int i = static_cast(basex)->GetValue().GetInt(); - if (i < 0) + if (i <= 0) { ScriptPosition.Message(MSG_ERROR, "State index must be positive"); delete this; @@ -8087,7 +8094,7 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) delete this; return nullptr; } - else if (Index->isConstant() && static_cast(Index)->GetValue().GetInt() < 0) + else if (Index->isConstant() && static_cast(Index)->GetValue().GetInt() <= 0) { ScriptPosition.Message(MSG_ERROR, "State index must be positive"); delete this; From 2ac0046cdaa0efc9ef6d5298716ede192ab76957 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 13:14:46 +0100 Subject: [PATCH 189/255] - fixed and cleaned up state index jump handling * use the function build list instead of the function to pass the info. The function is permanent so not the best place for compile-time info. * pass along the current state index which is needed to calculate the target state. --- src/dobjtype.h | 1 - src/scripting/codegeneration/codegen.cpp | 12 +++++++----- src/scripting/codegeneration/codegen.h | 6 ++++-- src/scripting/decorate/thingdef_states.cpp | 2 +- src/scripting/thingdef.cpp | 5 ++--- src/scripting/thingdef.h | 2 +- src/scripting/vm/vmbuilder.cpp | 6 ++++-- src/scripting/vm/vmbuilder.h | 4 +++- src/scripting/zscript/zcc_compile.cpp | 4 ++-- 9 files changed, 24 insertions(+), 18 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index 9cf663983..fd8bfb60a 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -719,7 +719,6 @@ public: }; TArray Variants; PClass *OwningClass = nullptr; - int StateCount = 0; // needed to process state indices later. unsigned AddVariant(PPrototype *proto, TArray &argflags, TArray &argnames, VMFunction *impl, int flags); int GetImplicitArgs() diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f296ac6e7..ea61d42df 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -93,12 +93,14 @@ static const FLOP FxFlops[] = // //========================================================================== -FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret, bool fromdecorate) : ReturnProto(ret), Function(fnc), Class(nullptr), FromDecorate(fromdecorate) +FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret, bool fromdecorate, int stateindex, int statecount) + : ReturnProto(ret), Function(fnc), Class(nullptr), FromDecorate(fromdecorate), StateIndex(stateindex), StateCount(statecount) { if (fnc != nullptr) Class = fnc->OwningClass; } -FCompileContext::FCompileContext(PClass *cls, bool fromdecorate) : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(fromdecorate) +FCompileContext::FCompileContext(PClass *cls, bool fromdecorate) + : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(fromdecorate), StateIndex(-1), StateCount(0) { } @@ -1426,13 +1428,13 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) } else if (basex->IsNumeric() && basex->ValueType != TypeSound && basex->ValueType != TypeColor) { - if (ctx.Function->SymbolName != NAME_None || !(ctx.Function->Variants[0].Flags & VARF_Action)) + if (ctx.StateIndex < 0) { ScriptPosition.Message(MSG_ERROR, "State jumps with index can only be used in anonymous state functions."); delete this; return nullptr; } - if (ctx.Function->StateCount != 1) + if (ctx.StateCount != 1) { ScriptPosition.Message(MSG_ERROR, "State jumps with index cannot be used on multistate definitions"); delete this; @@ -1447,7 +1449,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) delete this; return nullptr; } - FxExpression *x = new FxStateByIndex(i, ScriptPosition); + FxExpression *x = new FxStateByIndex(ctx.StateIndex + i, ScriptPosition); x = x->Resolve(ctx); basex = nullptr; delete this; diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index f4426da90..3cc86d1e6 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -73,10 +73,12 @@ struct FCompileContext PPrototype *ReturnProto; PFunction *Function; // The function that is currently being compiled (or nullptr for constant evaluation.) PClass *Class; // The type of the owning class. - bool FromDecorate; + bool FromDecorate; // DECORATE must silence some warnings and demote some errors. + int StateIndex; // index in actor's state table for anonymous functions, otherwise -1 (not used by DECORATE which pre-resolves state indices) + int StateCount; // amount of states an anoymous function is being used on (must be 1 for state indices to be allowed.) TDeletingArray FunctionArgs; - FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate); + FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate, int stateindex, int statecount); FCompileContext(PClass *cls, bool fromdecorate); // only to be used to resolve constants! PSymbol *FindInClass(FName identifier, PSymbolTable *&symt); diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index 3b9930928..d17cb5d4d 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -324,7 +324,7 @@ do_stop: endofstate: if (ScriptCode != nullptr) { - auto funcsym = CreateAnonymousFunction(actor, nullptr, VARF_Method | VARF_Action, (int)statestring.Len()); + auto funcsym = CreateAnonymousFunction(actor, nullptr, VARF_Method | VARF_Action); state.ActionFunc = FunctionBuildList.AddFunction(funcsym, ScriptCode, FStringf("%s.StateFunction.%d", actor->TypeName.GetChars(), bag.statedef.GetStateCount()), true); } int count = bag.statedef.AddStates(&state, statestring); diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 6f30f8add..8c42e8987 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -132,7 +132,7 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArray rets(1); TArray args; @@ -143,7 +143,6 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i SetImplicitArgs(&args, &argflags, &argnames, containingclass, flags); PFunction *sym = new PFunction(containingclass, NAME_None); // anonymous functions do not have names. - sym->StateCount = statecount; sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, flags); return sym; } @@ -202,7 +201,7 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, else { auto dmg = new FxReturnStatement(new FxIntCast(id, true), id->ScriptPosition); - auto funcsym = CreateAnonymousFunction(info, TypeSInt32, VARF_Method, 0); + auto funcsym = CreateAnonymousFunction(info, TypeSInt32, VARF_Method); defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, dmg, FStringf("%s.DamageFunction", info->TypeName.GetChars()), fromDecorate); } } diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 3511d1ee1..b2d34231d 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -153,7 +153,7 @@ FxExpression *ParseActions(FScanner &sc, FState state, FString statestring, Bagg class FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestring, Baggage &bag); FName CheckCastKludges(FName in); void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); -PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags, int statecount); +PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc, bool *error); void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, bool fromDecorate); diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index f8ca44ba6..0d517b6ef 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -653,7 +653,7 @@ void VMFunctionBuilder::BackpatchToHere(size_t loc) //========================================================================== FFunctionBuildList FunctionBuildList; -VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool fromdecorate) +VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool fromdecorate, int stateindex, int statecount) { auto func = code->GetDirectFunction(); if (func != nullptr) @@ -673,6 +673,8 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c it.Function->ImplicitArgs = functype->GetImplicitArgs(); it.Proto = nullptr; it.FromDecorate = fromdecorate; + it.StateIndex = stateindex; + it.StateCount = statecount; // set prototype for named functions. if (it.Func->SymbolName != NAME_None) @@ -698,7 +700,7 @@ void FFunctionBuildList::Build() assert(item.Code != NULL); // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate); + FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate, item.StateIndex, item.StateCount); // Allocate registers for the function's arguments and create local variable nodes before starting to resolve it. VMFunctionBuilder buildit(item.Func->GetImplicitArgs()); diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index 9a97c216d..452a7882c 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -106,13 +106,15 @@ class FFunctionBuildList PPrototype *Proto = nullptr; VMScriptFunction *Function = nullptr; FString PrintableName; + int StateIndex; + int StateCount; bool FromDecorate; }; TArray mItems; public: - VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool fromdecorate); + VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool fromdecorate, int currentstate = -1, int statecnt = 0); void Build(); }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 44b2f489c..f52976512 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2349,8 +2349,8 @@ void ZCCCompiler::CompileStates() auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); if (code != nullptr) { - auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action, (int)sl->Frames->Len()); - state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false); + auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action); + state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false, statedef.GetStateCount(), (int)sl->Frames->Len()); } } From 398433b5e6c76bf08c89e0ac447f887a4a1cc561 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 13:20:22 +0100 Subject: [PATCH 190/255] - fixed: Explicit casts to bool were missing. --- src/scripting/codegeneration/codegen.cpp | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index ea61d42df..b2d0b2f0a 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6083,6 +6083,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) switch (MethodName) { + case NAME_Bool: case NAME_Int: case NAME_uInt: case NAME_Double: @@ -6092,7 +6093,9 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_State: if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) { - PType *type = MethodName == NAME_Int ? TypeSInt32 : + PType *type = + MethodName == NAME_Bool ? TypeBool : + MethodName == NAME_Int ? TypeSInt32 : MethodName == NAME_uInt ? TypeUInt32 : MethodName == NAME_Double ? TypeFloat64 : MethodName == NAME_Name ? TypeName : From 6414fd301b729b1ce1d418129ff41f48b6313bab Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 13:21:47 +0100 Subject: [PATCH 191/255] - let's add a 'float' cast, too, just in case. It still will cast to double, because single precision floats only can exist as memory values. --- src/scripting/codegeneration/codegen.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index b2d0b2f0a..58f73a891 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6086,6 +6086,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Bool: case NAME_Int: case NAME_uInt: + case NAME_Float: case NAME_Double: case NAME_Name: case NAME_Color: @@ -6097,6 +6098,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) MethodName == NAME_Bool ? TypeBool : MethodName == NAME_Int ? TypeSInt32 : MethodName == NAME_uInt ? TypeUInt32 : + MethodName == NAME_Float ? TypeFloat64 : MethodName == NAME_Double ? TypeFloat64 : MethodName == NAME_Name ? TypeName : MethodName == NAME_Color ? TypeColor : From 647fd53a1582385c1f5b618dbba96d583eeba260 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 14:14:54 +0100 Subject: [PATCH 192/255] - fixed: An 'if' statement with only one branch may never considered to be always returning. --- src/scripting/codegeneration/codegen.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 58f73a891..61b23cc15 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -7441,9 +7441,9 @@ ExpEmit FxIfStatement::Emit(VMFunctionBuilder *build) bool FxIfStatement::CheckReturn() { - //An if statement returns if both branches return, if present. - return (WhenTrue == nullptr || WhenTrue->CheckReturn()) && - (WhenFalse == nullptr || WhenFalse->CheckReturn()); + //An if statement returns if both branches return. Both branches must be present. + return WhenTrue != nullptr && WhenTrue->CheckReturn() && + WhenFalse != nullptr && WhenFalse->CheckReturn(); } //========================================================================== From 10ef430baefcf8e6ada0dcb853a2228867c5dd40 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 14:18:13 +0100 Subject: [PATCH 193/255] Revert "Do not allow DMG_FORCED to penetrate player ultimate degreelessness/buddha." This reverts commit 0130bde07740e5717a3c7c796a3c8c06ad6a99fd. This wasn't supposed to get merged, so get rid of it again. The change in semantics here is not acceptable. --- src/p_interaction.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/p_interaction.cpp b/src/p_interaction.cpp index ec8b5e495..b4ecc827e 100644 --- a/src/p_interaction.cpp +++ b/src/p_interaction.cpp @@ -1254,10 +1254,11 @@ int P_DamageMobj (AActor *target, AActor *inflictor, AActor *source, int damage, damage = target->health - 1; } + if (!(flags & DMG_FORCED)) { // check the real player, not a voodoo doll here for invulnerability effects if ((!telefragDamage && ((player->mo->flags2 & MF2_INVULNERABLE) || - (player->cheats & CF_GODMODE)) && !(flags & DMG_FORCED)) || + (player->cheats & CF_GODMODE))) || (player->cheats & CF_GODMODE2) || (player->mo->flags5 & MF5_NODAMAGE)) //Absolutely no hurting if NODAMAGE is involved. Same for GODMODE2. { // player is invulnerable, so don't hurt him @@ -1330,8 +1331,7 @@ int P_DamageMobj (AActor *target, AActor *inflictor, AActor *source, int damage, // but telefragging should still do enough damage to kill the player) // Ignore players that are already dead. // [MC]Buddha2 absorbs telefrag damage, and anything else thrown their way. - if ((((player->cheats & CF_BUDDHA2) || - (((player->cheats & CF_BUDDHA) || (player->mo->flags7 & MF7_BUDDHA)) && !telefragDamage && !(flags & DMG_FORCED))) && (player->playerstate != PST_DEAD))) + if (!(flags & DMG_FORCED) && (((player->cheats & CF_BUDDHA2) || (((player->cheats & CF_BUDDHA) || (player->mo->flags7 & MF7_BUDDHA)) && !telefragDamage)) && (player->playerstate != PST_DEAD))) { // If this is a voodoo doll we need to handle the real player as well. player->mo->health = target->health = player->health = 1; From 2583da968018947be7eeb09bbb7ebe7ed143d756 Mon Sep 17 00:00:00 2001 From: Major Cooke Date: Sun, 6 Nov 2016 07:44:30 -0600 Subject: [PATCH 194/255] Do not allow DMG_FORCED to bypass ultimate degreeslessness/buddha for players. --- src/p_interaction.cpp | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/p_interaction.cpp b/src/p_interaction.cpp index b4ecc827e..48d13bebf 100644 --- a/src/p_interaction.cpp +++ b/src/p_interaction.cpp @@ -1242,6 +1242,11 @@ int P_DamageMobj (AActor *target, AActor *inflictor, AActor *source, int damage, // if (player) { + // Don't allow DMG_FORCED to work on ultimate degreeslessness/buddha and nodamage. + if ((player->cheats & (CF_GODMODE2 | CF_BUDDHA2)) || (player->mo->flags5 & MF5_NODAMAGE)) + { + flags &= ~DMG_FORCED; + } //Added by MC: Lets bots look allround for enemies if they survive an ambush. if (player->Bot != NULL) { From 7da4e0d03dfc68498e385ef42417db3289ae277e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 6 Nov 2016 23:10:23 +0100 Subject: [PATCH 195/255] - removed a parsing hack for the old internal definitions. - fixed: The state cast hack for DECORATE could not properly create state constants. Instead they were passed to FxRuntimeStateIndex without resolving them to something constant. This adds proper handling of constant indices within that class. --- src/scripting/codegeneration/codegen.cpp | 24 +++++++++++++++++++---- src/scripting/decorate/thingdef_parse.cpp | 8 ++------ 2 files changed, 22 insertions(+), 10 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 61b23cc15..fa9fe13c9 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -8101,11 +8101,27 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) delete this; return nullptr; } - else if (Index->isConstant() && static_cast(Index)->GetValue().GetInt() <= 0) + else if (Index->isConstant()) { - ScriptPosition.Message(MSG_ERROR, "State index must be positive"); - delete this; - return nullptr; + int index = static_cast(Index)->GetValue().GetInt(); + if (index < 0 || (index == 0 && !ctx.FromDecorate)) + { + ScriptPosition.Message(MSG_ERROR, "State index must be positive"); + delete this; + return nullptr; + } + else if (index == 0) + { + auto x = new FxConstant((FState*)nullptr, ScriptPosition); + delete this; + return x->Resolve(ctx); + } + else + { + auto x = new FxStateByIndex(index, ScriptPosition); + delete this; + return x->Resolve(ctx); + } } else if (Index->ValueType->GetRegType() != REGT_INT) { // Float. diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index b344a1228..430895060 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -181,15 +181,11 @@ FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool c { if (sc.String[0] == 0 || sc.Compare("None")) { - x = new FxConstant((FState*)NULL, sc); + x = new FxConstant((FState*)nullptr, sc); } else if (sc.Compare("*")) { - if (constant) - { - x = new FxConstant((FState*)(intptr_t)-1, sc); - } - else sc.ScriptError("Invalid state name '*'"); + sc.ScriptError("Invalid state name '*'"); } else { From b206d19df4bb32c8af1819d1b3b977c02cd7d528 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 01:10:56 +0100 Subject: [PATCH 196/255] - fixed: RegAvailability never set the number of allocated registers to more than 32. - fixed register allocation in ?: operator which was quite broken. --- src/CMakeLists.txt | 1 - src/scripting/codegeneration/codegen.cpp | 6 +++--- src/scripting/vm/vmbuilder.cpp | 12 ++++++------ 3 files changed, 9 insertions(+), 10 deletions(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index a20d9ff0b..d5d3e007b 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -850,7 +850,6 @@ set( NOT_COMPILED_SOURCE_FILES sc_man_scanner.re g_doom/a_bossbrain.cpp g_doom/a_doomweaps.cpp - g_doom/a_lostsoul.cpp g_doom/a_painelemental.cpp g_doom/a_revenant.cpp g_doom/a_scriptedmarine.cpp diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index fa9fe13c9..814c47717 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -4061,6 +4061,7 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) // Test condition. build->Emit(OP_EQ_K, 1, cond.RegNum, build->GetConstantInt(0)); falsejump = build->Emit(OP_JMP, 0); + cond.Free(build); // Evaluate true expression. if (truex->isConstant() && truex->ValueType->GetRegType() == REGT_INT) @@ -4073,6 +4074,7 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) ExpEmit trueop = truex->Emit(build); if (trueop.Konst) { + trueop.Free(build); if (trueop.RegType == REGT_FLOAT) { out = ExpEmit(build, REGT_FLOAT); @@ -4113,20 +4115,18 @@ ExpEmit FxConditional::Emit(VMFunctionBuilder *build) { if (falseop.RegType == REGT_FLOAT) { - out = ExpEmit(build, REGT_FLOAT); build->Emit(OP_LKF, out.RegNum, falseop.RegNum); } else if (falseop.RegType == REGT_POINTER) { - out = ExpEmit(build, REGT_POINTER); build->Emit(OP_LKP, out.RegNum, falseop.RegNum); } else { assert(falseop.RegType == REGT_STRING); - out = ExpEmit(build, REGT_STRING); build->Emit(OP_LKS, out.RegNum, falseop.RegNum); } + falseop.Free(build); } else { diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 0d517b6ef..bb6b626e7 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -336,10 +336,10 @@ int VMFunctionBuilder::RegAvailability::Get(int count) { return -1; } - + mask = count == 32 ? ~0u : (1 << count) - 1; - for (i = 0; i < 256/32; ++i) + for (i = 0; i < 256 / 32; ++i) { // Find the first word with free registers VM_UWORD bits = Used[i]; @@ -362,9 +362,9 @@ int VMFunctionBuilder::RegAvailability::Get(int count) { if (firstbit + count <= 32) { // Needed bits all fit in one word, so we got it. - if (firstbit + count > MostUsed) + if (i * 32 + firstbit + count > MostUsed) { - MostUsed = firstbit + count; + MostUsed = i * 32 + firstbit + count; } Used[i] |= mask << firstbit; return i * 32 + firstbit; @@ -374,9 +374,9 @@ int VMFunctionBuilder::RegAvailability::Get(int count) { // There is a next word. if (((Used[i + 1]) & (mask >> (32 - firstbit))) == 0) { // The next word has the needed open space, too. - if (firstbit + count > MostUsed) + if (i * 32 + firstbit + count > MostUsed) { - MostUsed = firstbit + count; + MostUsed = i * 32 + firstbit + count; } Used[i] |= mask << firstbit; Used[i + 1] |= mask >> (32 - firstbit); From dc055b74c153ca68aa2406d0111a445a24cfe7ab Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 09:54:46 +0100 Subject: [PATCH 197/255] - fixed the octal parser in strbin. Like its hex counterpart it needs to backtrack one character if it find the end of a sequence. - since ZScript already receives filtered strings, the 'T' converter for the properties should not do it again. --- src/cmdlib.cpp | 6 ++++++ src/scripting/zscript/zcc_compile.cpp | 5 +---- 2 files changed, 7 insertions(+), 4 deletions(-) diff --git a/src/cmdlib.cpp b/src/cmdlib.cpp index 3a3d2876d..5799a2342 100644 --- a/src/cmdlib.cpp +++ b/src/cmdlib.cpp @@ -632,7 +632,10 @@ int strbin (char *str) if (*p >= '0' && *p <= '7') c += *p-'0'; else + { + p--; break; + } p++; } *str++ = c; @@ -732,7 +735,10 @@ FString strbin1 (const char *start) if (*p >= '0' && *p <= '7') c += *p-'0'; else + { + p--; break; + } p++; } result << c; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f52976512..889cdb5fd 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1676,13 +1676,10 @@ void ZCCCompiler::DispatchProperty(FPropertyInfo *prop, ZCC_PropertyStmt *proper case 'C': // this parser accepts colors only in string form. pref.i = 1; case 'S': + case 'T': // a filtered string (ZScript only parses filtered strings so there's nothing to do here.) conv.s = GetString(exp); break; - case 'T': // a filtered string - conv.s = strings[strings.Reserve(1)] = strbin1(GetString(exp)); - break; - case 'L': // Either a number or a list of strings if (!GetString(exp, true)) { From 208fe28042f3d2624c50c31f2185b4f336e98ec1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 11:30:41 +0100 Subject: [PATCH 198/255] - properly clear all script compiler data for a restart. --- src/scripting/codegeneration/codegen.cpp | 5 ++--- src/scripting/vm/vmbuilder.cpp | 2 +- src/scripting/zscript/zcc_compile.cpp | 4 ---- src/scripting/zscript/zcc_parser.cpp | 15 +++++++-------- 4 files changed, 10 insertions(+), 16 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 814c47717..d3a5e0e8c 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -213,18 +213,17 @@ void ExpEmit::Reuse(VMFunctionBuilder *build) // it and install it a local symbol table. // //========================================================================== -static PSymbolTable Builtins; static PSymbol *FindBuiltinFunction(FName funcname, VMNativeFunction::NativeCallType func) { - PSymbol *sym = Builtins.FindSymbol(funcname, false); + PSymbol *sym = GlobalSymbols.FindSymbol(funcname, false); if (sym == nullptr) { PSymbolVMFunction *symfunc = new PSymbolVMFunction(funcname); VMNativeFunction *calldec = new VMNativeFunction(func, funcname); symfunc->Function = calldec; sym = symfunc; - Builtins.AddSymbol(sym); + GlobalSymbols.AddSymbol(sym); } return sym; } diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index bb6b626e7..1544ca4a6 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -774,5 +774,5 @@ void FFunctionBuildList::Build() fclose(dump); } FScriptPosition::StrictErrors = false; - + mItems.Clear(); } \ No newline at end of file diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 889cdb5fd..49711afb2 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -51,8 +51,6 @@ #include "codegeneration/codegen.h" #include "vmbuilder.h" -#define DEFINING_CONST ((PSymbolConst *)(void *)1) - //========================================================================== // // ZCCCompiler :: ProcessClass @@ -714,10 +712,8 @@ bool ZCCCompiler::CompileConstant(ZCC_ConstantDef *def, PSymbolTable *sym) { assert(def->Symbol == nullptr); - def->Symbol = DEFINING_CONST; // avoid recursion ZCC_Expression *val = Simplify(def->Value, sym, true); def->Value = val; - if (def->Symbol == DEFINING_CONST) def->Symbol = nullptr; return (val->NodeType == AST_ExprConstant); } diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 26fdeec43..1f0800302 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -199,9 +199,6 @@ static void InitTokenMap() TOKENDEF (TK_CanRaise, ZCC_CANRAISE); TOKENDEF (TK_Light, ZCC_LIGHT); TOKENDEF (TK_Extend, ZCC_EXTEND); - - ZCC_InitOperators(); - ZCC_InitConversions(); } #undef TOKENDEF #undef TOKENDEF2 @@ -293,11 +290,6 @@ parse_end: static void DoParse(int lumpnum) { - if (TokenMap.CountUsed() == 0) - { - InitTokenMap(); - } - FScanner sc; void *parser; ZCCToken value; @@ -400,6 +392,13 @@ static void DoParse(int lumpnum) void ParseScripts() { + if (TokenMap.CountUsed() == 0) + { + InitTokenMap(); + } + ZCC_InitOperators(); + ZCC_InitConversions(); + int lump, lastlump = 0; FScriptPosition::ResetErrorCounter(); while ((lump = Wads.FindLump("ZSCRIPT", &lastlump)) != -1) From 5e8c819a33abf09921f1a4ae440aed2d82f3727f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 11:53:49 +0100 Subject: [PATCH 199/255] - fixed checks in Powerup.Type property to properly deal with the differences between DECORATE and ZScript. - properly initialize Baggage everywhere it gets used. - fixed a few items with incorrect Powerup.Type settings that got flagged by the above changes. --- src/scripting/decorate/olddecorations.cpp | 1 + src/scripting/decorate/thingdef_parse.cpp | 1 + src/scripting/thingdef.h | 3 ++- src/scripting/thingdef_properties.cpp | 15 +++++++++++---- src/scripting/zscript/zcc_compile.cpp | 2 +- .../static/zscript/heretic/hereticartifacts.txt | 2 +- wadsrc/static/zscript/strife/strifeitems.txt | 8 ++++---- 7 files changed, 21 insertions(+), 11 deletions(-) diff --git a/src/scripting/decorate/olddecorations.cpp b/src/scripting/decorate/olddecorations.cpp index 75e49dbaa..6ccd0051a 100644 --- a/src/scripting/decorate/olddecorations.cpp +++ b/src/scripting/decorate/olddecorations.cpp @@ -158,6 +158,7 @@ void ParseOldDecoration(FScanner &sc, EDefinitionType def) type = DecoDerivedClass(FScriptPosition(sc), parent, typeName); ResetBaggage(&bag, parent); bag.Info = type; + bag.fromDecorate = true; #ifdef _DEBUG bag.ClassName = type->TypeName; #endif diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index 430895060..07da3cf57 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -1064,6 +1064,7 @@ static void ParseActor(FScanner &sc) PClassActor *info = NULL; Baggage bag; + bag.fromDecorate = true; info = ParseActorHeader(sc, &bag); sc.MustGetToken('{'); while (sc.MustGetAnyToken(), sc.TokenType != '}') diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index b2d34231d..6529059e6 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -117,7 +117,7 @@ struct Baggage PClassActor *Info; bool DropItemSet; bool StateSet; - bool fromZScript; + bool fromDecorate; int CurrentState; int Lumpnum; FStateDefinitions statedef; @@ -132,6 +132,7 @@ inline void ResetBaggage (Baggage *bag, PClassActor *stateclass) bag->DropItemList = NULL; bag->DropItemSet = false; bag->CurrentState = 0; + bag->fromDecorate = true; bag->StateSet = false; bag->statedef.MakeStateDefines(stateclass); } diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index 6f1455e43..aa4508950 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -2422,11 +2422,18 @@ DEFINE_CLASS_PROPERTY_PREFIX(powerup, type, S, PowerupGiver) // Yuck! What was I thinking when I decided to prepend "Power" to the name? // Now it's too late to change it... PClassActor *cls = PClass::FindActor(str); - if (cls == NULL || (!cls->IsDescendantOf(RUNTIME_CLASS(APowerup)) && !bag.fromZScript)) + if (cls == nullptr || !cls->IsDescendantOf(RUNTIME_CLASS(APowerup))) { - FString st; - st.Format("%s%s", strnicmp(str, "power", 5)? "Power" : "", str); - cls = FindClassTentativePowerup(st); + if (bag.fromDecorate) + { + FString st; + st.Format("%s%s", strnicmp(str, "power", 5) ? "Power" : "", str); + cls = FindClassTentativePowerup(st); + } + else + { + I_Error("Unknown powerup type %s", str); + } } defaults->PowerupType = cls; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 49711afb2..981dcbc2a 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1897,7 +1897,7 @@ void ZCCCompiler::InitDefaults() bag.Info = ti; bag.DropItemSet = false; bag.StateSet = false; - bag.fromZScript = true; + bag.fromDecorate = false; bag.CurrentState = 0; bag.Lumpnum = c->cls->SourceLump; bag.DropItemList = nullptr; diff --git a/wadsrc/static/zscript/heretic/hereticartifacts.txt b/wadsrc/static/zscript/heretic/hereticartifacts.txt index 94271c8cd..e239748ff 100644 --- a/wadsrc/static/zscript/heretic/hereticartifacts.txt +++ b/wadsrc/static/zscript/heretic/hereticartifacts.txt @@ -55,7 +55,7 @@ Class ArtiTomeOfPower : PowerupGiver native +FLOATBOB Inventory.PickupFlash "PickupFlash"; Inventory.Icon "ARTIPWBK"; - Powerup.Type "Weaponlevel2"; + Powerup.Type "PowerWeaponlevel2"; Inventory.PickupMessage "$TXT_ARTITOMEOFPOWER"; Tag "$TAG_ARTITOMEOFPOWER"; } diff --git a/wadsrc/static/zscript/strife/strifeitems.txt b/wadsrc/static/zscript/strife/strifeitems.txt index 3d8b4af54..cfc939413 100644 --- a/wadsrc/static/zscript/strife/strifeitems.txt +++ b/wadsrc/static/zscript/strife/strifeitems.txt @@ -198,7 +198,7 @@ class ShadowArmor : PowerupGiver RenderStyle "Translucent"; Tag "$TAG_SHADOWARMOR"; Inventory.MaxAmount 2; - Powerup.Type "Shadow"; + Powerup.Type "PowerShadow"; Inventory.Icon "I_SHD1"; Inventory.PickupSound "misc/i_pkup"; Inventory.PickupMessage "$TXT_SHADOWARMOR"; @@ -222,7 +222,7 @@ class EnvironmentalSuit : PowerupGiver +INVENTORY.INVBAR -INVENTORY.FANCYPICKUPSOUND Inventory.MaxAmount 5; - Powerup.Type "Mask"; + Powerup.Type "PowerMask"; Tag "$TAG_ENVSUIT"; Inventory.Icon "I_MASK"; Inventory.PickupSound "misc/i_pkup"; @@ -353,7 +353,7 @@ class Targeter : PowerupGiver +INVENTORY.INVBAR -INVENTORY.FANCYPICKUPSOUND Tag "$TAG_TARGETER"; - Powerup.Type "Targeter"; + Powerup.Type "PowerTargeter"; Inventory.MaxAmount 5; Inventory.Icon "I_TARG"; Inventory.PickupSound "misc/i_pkup"; @@ -478,7 +478,7 @@ class Scanner : PowerupGiver native Inventory.MaxAmount 1; Tag "$TAG_SCANNER"; Inventory.Icon "I_PMUP"; - Powerup.Type "Scanner"; + Powerup.Type "PowerScanner"; Inventory.PickupSound "misc/i_pkup"; Inventory.PickupMessage "$TXT_SCANNER"; } From 387287008cd2dd76f055ebca11c3681278b756e1 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 14:57:59 +0100 Subject: [PATCH 200/255] - fixed: Clamp was initialized with incorrect values. --- src/scripting/codegeneration/codegen.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index d3a5e0e8c..56691208f 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6164,7 +6164,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) pass[1] = (*ArgList)[1]; pass[0] = new FxMinMax(pass, NAME_Max, ScriptPosition); pass[1] = (*ArgList)[2]; - func = new FxMinMax(*ArgList, NAME_Min, ScriptPosition); + func = new FxMinMax(pass, NAME_Min, ScriptPosition); (*ArgList)[0] = (*ArgList)[1] = (*ArgList)[2] = nullptr; } break; From e3bee84860a1079e4592d1aa246035e3c89bc181 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 20:12:06 +0100 Subject: [PATCH 201/255] - fixed: Hexen's serpent was still using "None" for 'no state', which in ZScript is done with null. --- wadsrc/static/zscript/hexen/serpent.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/wadsrc/static/zscript/hexen/serpent.txt b/wadsrc/static/zscript/hexen/serpent.txt index d8886ccb2..70fb2195a 100644 --- a/wadsrc/static/zscript/hexen/serpent.txt +++ b/wadsrc/static/zscript/hexen/serpent.txt @@ -40,7 +40,7 @@ class Serpent : Actor SSPT H 10 A_Look; Loop; See: - SSPT HH 1 A_Chase("Melee", "None", CHF_NIGHTMAREFAST|CHF_NOPLAYACTIVE); + SSPT HH 1 A_Chase("Melee", null, CHF_NIGHTMAREFAST|CHF_NOPLAYACTIVE); SSPT H 2 A_SerpentHumpDecide; Loop; Pain: @@ -81,7 +81,7 @@ class Serpent : Actor SSPT [ 1 A_FreezeDeathChunks; Wait; Walk: - SSPT IJI 5 A_Chase("Attack", "None", CHF_NIGHTMAREFAST); + SSPT IJI 5 A_Chase("Attack", null, CHF_NIGHTMAREFAST); SSPT J 5 A_SerpentCheckForAttack; Goto Dive; Hump: From 75c20ebaa6431ca7338f2e2c3f6736f0ea96b3ab Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 21:30:08 +0100 Subject: [PATCH 202/255] - typo in Lostsoul definition. --- wadsrc/static/zscript/doom/lostsoul.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wadsrc/static/zscript/doom/lostsoul.txt b/wadsrc/static/zscript/doom/lostsoul.txt index 00158e071..7ef8b4cf0 100644 --- a/wadsrc/static/zscript/doom/lostsoul.txt +++ b/wadsrc/static/zscript/doom/lostsoul.txt @@ -102,7 +102,7 @@ extend class Actor A_PlaySound(AttackSound, CHAN_VOICE); A_FaceTarget(); VelFromAngle(skullspeed); - Vel.Z = (target.pos.Z + target.Height/2 - Vel.Z) / DistanceBySpeed(target, speed); + Vel.Z = (target.pos.Z + target.Height/2 - pos.Z) / DistanceBySpeed(target, speed); } void A_BetaSkullAttack() From cf9cdeb48028c0dc53aa0dc219fbb63dc65b70e6 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 23:16:25 +0100 Subject: [PATCH 203/255] - scriptified the Revenant's code. --- src/CMakeLists.txt | 1 - src/g_doom/a_doommisc.cpp | 1 - src/g_doom/a_revenant.cpp | 152 ------------------------ src/p_mobj.cpp | 56 ++++++++- wadsrc/static/zscript/actor.txt | 11 +- wadsrc/static/zscript/doom/revenant.txt | 120 +++++++++++++++++++ 6 files changed, 182 insertions(+), 159 deletions(-) delete mode 100644 src/g_doom/a_revenant.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index d5d3e007b..81f43f06b 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -851,7 +851,6 @@ set( NOT_COMPILED_SOURCE_FILES g_doom/a_bossbrain.cpp g_doom/a_doomweaps.cpp g_doom/a_painelemental.cpp - g_doom/a_revenant.cpp g_doom/a_scriptedmarine.cpp g_heretic/a_chicken.cpp g_heretic/a_dsparil.cpp diff --git a/src/g_doom/a_doommisc.cpp b/src/g_doom/a_doommisc.cpp index 1df9a4e7c..eabf887f0 100644 --- a/src/g_doom/a_doommisc.cpp +++ b/src/g_doom/a_doommisc.cpp @@ -25,6 +25,5 @@ #include "a_bossbrain.cpp" #include "a_doomweaps.cpp" #include "a_painelemental.cpp" -#include "a_revenant.cpp" #include "a_scriptedmarine.cpp" diff --git a/src/g_doom/a_revenant.cpp b/src/g_doom/a_revenant.cpp deleted file mode 100644 index 0ffaed753..000000000 --- a/src/g_doom/a_revenant.cpp +++ /dev/null @@ -1,152 +0,0 @@ -/* -#include "templates.h" -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "gstrings.h" -#include "a_action.h" -#include "vm.h" -#include "g_level.h" -*/ - -static FRandom pr_tracer ("Tracer"); -static FRandom pr_skelfist ("SkelFist"); - -// -// A_SkelMissile -// -DEFINE_ACTION_FUNCTION(AActor, A_SkelMissile) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *missile; - - if (!self->target) - return 0; - - A_FaceTarget (self); - self->AddZ(16.); - missile = P_SpawnMissile(self, self->target, PClass::FindActor("RevenantTracer")); - self->AddZ(-16.); - - if (missile != NULL) - { - missile->SetOrigin(missile->Vec3Offset(missile->Vel.X, missile->Vel.Y, 0.), false); - missile->tracer = self->target; - } - return 0; -} - -#define TRACEANGLE (16.875) - -DEFINE_ACTION_FUNCTION(AActor, A_Tracer) -{ - PARAM_SELF_PROLOGUE(AActor); - - double dist; - double slope; - AActor *dest; - AActor *smoke; - - // killough 1/18/98: this is why some missiles do not have smoke - // and some do. Also, internal demos start at random gametics, thus - // the bug in which revenants cause internal demos to go out of sync. - // - // killough 3/6/98: fix revenant internal demo bug by subtracting - // levelstarttic from gametic: - // - // [RH] level.time is always 0-based, so nothing special to do here. - - if (level.time & 3) - return 0; - - // spawn a puff of smoke behind the rocket - P_SpawnPuff (self, PClass::FindActor(NAME_BulletPuff), self->Pos(), self->Angles.Yaw, self->Angles.Yaw, 3); - - smoke = Spawn ("RevenantTracerSmoke", self->Vec3Offset(-self->Vel.X, -self->Vel.Y, 0.), ALLOW_REPLACE); - - smoke->Vel.Z = 1.; - smoke->tics -= pr_tracer()&3; - if (smoke->tics < 1) - smoke->tics = 1; - - // adjust direction - dest = self->tracer; - - if (!dest || dest->health <= 0 || self->Speed == 0 || !self->CanSeek(dest)) - return 0; - - // change angle - DAngle exact = self->AngleTo(dest); - DAngle diff = deltaangle(self->Angles.Yaw, exact); - - if (diff < 0) - { - self->Angles.Yaw -= TRACEANGLE; - if (deltaangle(self->Angles.Yaw, exact) > 0) - self->Angles.Yaw = exact; - } - else if (diff > 0) - { - self->Angles.Yaw += TRACEANGLE; - if (deltaangle(self->Angles.Yaw, exact) < 0.) - self->Angles.Yaw = exact; - } - - self->VelFromAngle(); - - if (!(self->flags3 & (MF3_FLOORHUGGER|MF3_CEILINGHUGGER))) - { - // change slope - dist = self->DistanceBySpeed(dest, self->Speed); - - if (dest->Height >= 56.) - { - slope = (dest->Z() + 40. - self->Z()) / dist; - } - else - { - slope = (dest->Z() + self->Height*(2./3) - self->Z()) / dist; - } - - if (slope < self->Vel.Z) - self->Vel.Z -= 1. / 8; - else - self->Vel.Z += 1. / 8; - } - return 0; -} - - -DEFINE_ACTION_FUNCTION(AActor, A_SkelWhoosh) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - A_FaceTarget (self); - S_Sound (self, CHAN_WEAPON, "skeleton/swing", 1, ATTN_NORM); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_SkelFist) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - return 0; - - A_FaceTarget (self); - - if (self->CheckMeleeRange ()) - { - int damage = ((pr_skelfist()%10)+1)*6; - S_Sound (self, CHAN_WEAPON, "skeleton/melee", 1, ATTN_NORM); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - } - return 0; -} diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index d0c0af1f5..21d32c2de 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -1871,6 +1871,13 @@ bool AActor::CanSeek(AActor *target) const return true; } +DEFINE_ACTION_FUNCTION(AActor, CanSeek) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(target, AActor); + ACTION_RETURN_BOOL(self->CanSeek(target)); +} + //---------------------------------------------------------------------------- // // FUNC P_SeekerMissile @@ -5424,7 +5431,20 @@ AActor *P_SpawnPuff (AActor *source, PClassActor *pufftype, const DVector3 &pos1 return puff; } - +DEFINE_ACTION_FUNCTION(AActor, SpawnPuff) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_CLASS(pufftype, AActor); + PARAM_FLOAT(x); + PARAM_FLOAT(y); + PARAM_FLOAT(z); + PARAM_ANGLE(hitdir); + PARAM_ANGLE(particledir); + PARAM_INT(updown); + PARAM_INT_DEF(flags); + PARAM_OBJECT_DEF(victim, AActor); + ACTION_RETURN_OBJECT(P_SpawnPuff(self, pufftype, DVector3(x, y, z), hitdir, particledir, updown, flags, victim)); +} //--------------------------------------------------------------------------- // @@ -6817,6 +6837,22 @@ void AActor::SetTranslation(const char *trname) // silently ignore if the name does not exist, this would create some insane message spam otherwise. } +DEFINE_ACTION_FUNCTION(AActor, deltaangle) // should this be global? +{ + PARAM_PROLOGUE; + PARAM_FLOAT(a1); + PARAM_FLOAT(a2); + ACTION_RETURN_FLOAT(deltaangle(DAngle(a1), DAngle(a2)).Degrees); +} + +DEFINE_ACTION_FUNCTION(AActor, AddZ) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(addz); + self->AddZ(addz); + return 0; +} + DEFINE_ACTION_FUNCTION(AActor, SetDamage) { PARAM_SELF_PROLOGUE(AActor); @@ -6856,6 +6892,14 @@ DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) return 0; } +DEFINE_ACTION_FUNCTION(AActor, AngleTo) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(targ, AActor); + PARAM_BOOL_DEF(absolute); + ACTION_RETURN_FLOAT(self->AngleTo(targ, absolute).Degrees); +} + DEFINE_ACTION_FUNCTION(AActor, DistanceBySpeed) { PARAM_SELF_PROLOGUE(AActor); @@ -6894,6 +6938,16 @@ DEFINE_ACTION_FUNCTION(AActor, Vec2OffsetZ) ACTION_RETURN_VEC3(self->Vec2OffsetZ(x, y, z, absolute)); } +DEFINE_ACTION_FUNCTION(AActor, Vec3Offset) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(x); + PARAM_FLOAT(y); + PARAM_FLOAT(z); + PARAM_BOOL_DEF(absolute); + ACTION_RETURN_VEC3(self->Vec3Offset(x, y, z, absolute)); +} + //---------------------------------------------------------------------------- // // DropItem handling diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 287808b67..5aa1af293 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -54,6 +54,7 @@ class Actor : Thinker native } native static readonly GetDefaultByType(class cls); + native static float deltaangle(float ang1, float ang2); native void SetDamage(int dmg); native static bool isDehState(state st); native void SetOrigin(vector3 newpos, bool moving); @@ -62,6 +63,8 @@ class Actor : Thinker native native static Actor Spawn(class type, vector3 pos = (0,0,0), int replace = NO_REPLACE); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); native Actor OldSpawnMissile(Actor dest, class type, Actor owner = null); + native Actor SpawnPuff(class pufftype, vector3 pos, float hitdir, float particledir, int updown, int flags = 0, Actor vict = null); + native void TraceBleed(int damage, Actor missile); native bool CheckMeleeRange(); native int DamageMobj(Actor inflictor, Actor source, int damage, Name mod, int flags = 0, double angle = 0); @@ -72,6 +75,10 @@ class Actor : Thinker native native bool SetState(state st, bool nofunction = false); native void LinkToWorld(); native void UnlinkFromWorld(); + native bool CanSeek(Actor target); + native double AngleTo(Actor target, bool absolute = false); + native void AddZ(float zadd); + native vector3 Vec3Offset(float x, float y, float z, bool absolute = false); native vector3 Vec3Angle(float length, float angle, float z = 0, bool absolute = false); native vector3 Vec2OffsetZ(float x, float y, float atz, bool absolute = false); native void VelFromAngle(float speed = 0, float angle = 0); @@ -238,10 +245,6 @@ class Actor : Thinker native native void A_Chase(state melee = null, state missile = null, int flags = 0); native void A_Scream(); native void A_VileChase(); - native void A_Tracer(); - native void A_SkelWhoosh(); - native void A_SkelFist(); - native void A_SkelMissile(); native void A_BossDeath(); native void A_Detonate(); native bool A_CallSpecial(int special, int arg1=0, int arg2=0, int arg3=0, int arg4=0, int arg5=0); diff --git a/wadsrc/static/zscript/doom/revenant.txt b/wadsrc/static/zscript/doom/revenant.txt index 7fc8b8e0d..2fc35c60f 100644 --- a/wadsrc/static/zscript/doom/revenant.txt +++ b/wadsrc/static/zscript/doom/revenant.txt @@ -120,3 +120,123 @@ class RevenantTracerSmoke : Actor Stop; } } + +//=========================================================================== +// +// Code (must be attached to Actor) +// +//=========================================================================== + +extend class Actor +{ + const TRACEANGLE = (16.875); + + void A_SkelMissile() + { + if (target == null) return; + A_FaceTarget(); + AddZ(16); + Actor missile = SpawnMissile(target, "RevenantTracer"); + AddZ(-16); + if (missile != null) + { + missile.SetOrigin(missile.Vec3Offset(missile.Vel.X, missile.Vel.Y, 0.), false); + missile.tracer = target; + } + } + + void A_SkelWhoosh() + { + if (target == null) return; + A_FaceTarget(); + A_PlaySound("skeleton/swing", CHAN_WEAPON); + } + + void A_SkelFist() + { + if (target == null) return; + A_FaceTarget(); + + if (CheckMeleeRange ()) + { + int damage = random[SkelFist](1, 10) * 6; + A_PlaySound("skeleton/melee", CHAN_WEAPON); + int newdam = target.DamageMobj (self, self, damage, 'Melee'); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + } + } + + void A_Tracer() + { + double dist; + double slope; + Actor dest; + Actor smoke; + + // killough 1/18/98: this is why some missiles do not have smoke + // and some do. Also, internal demos start at random gametics, thus + // the bug in which revenants cause internal demos to go out of sync. + // + // killough 3/6/98: fix revenant internal demo bug by subtracting + // levelstarttic from gametic: + // + // [RH] level.time is always 0-based, so nothing special to do here. + + if (level.time & 3) return; + + // spawn a puff of smoke behind the rocket + SpawnPuff ("BulletPuff", pos, angle, angle, 3); + smoke = Spawn ("RevenantTracerSmoke", Vec3Offset(-Vel.X, -Vel.Y, 0.), ALLOW_REPLACE); + + smoke.Vel.Z = 1.; + smoke.tics -= random[Tracer](0, 3); + if (smoke.tics < 1) + smoke.tics = 1; + + // adjust direction + dest = tracer; + + if (!dest || dest.health <= 0 || Speed == 0 || !CanSeek(dest)) + return; + + // change angle + double exact = AngleTo(dest); + double diff = deltaangle(angle, exact); + + if (diff < 0) + { + angle -= TRACEANGLE; + if (deltaangle(angle, exact) > 0) + angle = exact; + } + else if (diff > 0) + { + angle += TRACEANGLE; + if (deltaangle(angle, exact) < 0.) + angle = exact; + } + + VelFromAngle(); + + if (!bFloorHugger && !bCeilingHugger) + { + // change slope + dist = DistanceBySpeed(dest, Speed); + + if (dest.Height >= 56.) + { + slope = (dest.pos.z + 40. - pos.z) / dist; + } + else + { + slope = (dest.pos.z + Height*(2./3) - pos.z) / dist; + } + + if (slope < Vel.Z) + Vel.Z -= 1. / 8; + else + Vel.Z += 1. / 8; + } + } +} + From aac931192bebfb7e6624ec59c7f29db53619fc93 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 23:22:00 +0100 Subject: [PATCH 204/255] - fixed: Declaring a damage function must set regular damage to -1 to disable it. --- src/scripting/zscript/zcc_compile.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 981dcbc2a..41c3cde34 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1768,6 +1768,7 @@ void ZCCCompiler::ProcessDefaultProperty(PClassActor *cls, ZCC_PropertyStmt *pro { auto x = ConvertNode(prop->Values); CreateDamageFunction(cls, (AActor *)bag.Info->Defaults, x, false); + ((AActor *)bag.Info->Defaults)->DamageVal = -1; return; } From 3661e479d956c0191dc3242a8eda742e2ffce836 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 7 Nov 2016 23:29:54 +0100 Subject: [PATCH 205/255] - fixed: Runtime conversion of names to classes used the wrong argument to check the class type. --- src/scripting/codegeneration/codegen.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 56691208f..0972ed002 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -8001,7 +8001,7 @@ int BuiltinNameToClass(VMFrameStack *stack, VMValue *param, TArray &def FName clsname = ENamedName(param[0].i); const PClass *cls = PClass::FindClass(clsname); - const PClass *desttype = reinterpret_cast(param[0].a); + const PClass *desttype = reinterpret_cast(param[1].a); if (!cls->IsDescendantOf(desttype)) { From 7b7b66d8b7d9462e2b59b8dc4d9601fd2520d79f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 8 Nov 2016 11:12:56 +0100 Subject: [PATCH 206/255] - added a new variable flag that allows defining variables which can only be modified by internal script code but not by external mods. Currently this is used by the NoBlockmap and NoSector flags which need special handling for changing. --- src/dobjtype.h | 1 + src/scripting/codegeneration/codegen.cpp | 64 +++++++++++++++--------- src/scripting/codegeneration/codegen.h | 18 ++++--- src/scripting/thingdef_data.cpp | 6 +-- src/scripting/vm/vmbuilder.cpp | 5 +- src/scripting/vm/vmbuilder.h | 3 +- src/scripting/zscript/zcc_compile.cpp | 8 +-- src/scripting/zscript/zcc_compile.h | 3 +- src/scripting/zscript/zcc_parser.cpp | 2 +- 9 files changed, 67 insertions(+), 43 deletions(-) diff --git a/src/dobjtype.h b/src/dobjtype.h index fd8bfb60a..d907feeeb 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -30,6 +30,7 @@ enum VARF_Out = (1<<11), VARF_Implicit = (1<<12), // implicitly created parameters (i.e. do not compare types when checking function signatures) VARF_Static = (1<<13), // static class data (by necessity read only.) + VARF_InternalAccess = (1<<14), // overrides VARF_ReadOnly for internal script code. }; // Symbol information ------------------------------------------------------- diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 0972ed002..32ee2d012 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -53,6 +53,7 @@ #include "m_fixed.h" #include "vmbuilder.h" #include "v_text.h" +#include "w_wad.h" #include "math/cmath.h" extern FRandom pr_exrandom; @@ -93,14 +94,14 @@ static const FLOP FxFlops[] = // //========================================================================== -FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret, bool fromdecorate, int stateindex, int statecount) - : ReturnProto(ret), Function(fnc), Class(nullptr), FromDecorate(fromdecorate), StateIndex(stateindex), StateCount(statecount) +FCompileContext::FCompileContext(PFunction *fnc, PPrototype *ret, bool fromdecorate, int stateindex, int statecount, int lump) + : ReturnProto(ret), Function(fnc), Class(nullptr), FromDecorate(fromdecorate), StateIndex(stateindex), StateCount(statecount), Lump(lump) { if (fnc != nullptr) Class = fnc->OwningClass; } FCompileContext::FCompileContext(PClass *cls, bool fromdecorate) - : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(fromdecorate), StateIndex(-1), StateCount(0) + : ReturnProto(nullptr), Function(nullptr), Class(cls), FromDecorate(fromdecorate), StateIndex(-1), StateCount(0), Lump(-1) { } @@ -164,6 +165,13 @@ void FCompileContext::CheckReturn(PPrototype *proto, FScriptPosition &pos) } } +bool FCompileContext::CheckReadOnly(int flags) +{ + if (!(flags & VARF_ReadOnly)) return false; + if (!(flags & VARF_InternalAccess)) return true; + return Wads.GetLumpFile(Lump) != 0; +} + FxLocalVariableDeclaration *FCompileContext::FindLocalVariable(FName name) { if (Block == nullptr) @@ -307,7 +315,7 @@ FxExpression *FxExpression::Resolve(FCompileContext &ctx) // //========================================================================== -bool FxExpression::RequestAddress(bool *writable) +bool FxExpression::RequestAddress(FCompileContext &ctx, bool *writable) { if (writable != nullptr) *writable = false; return false; @@ -1178,9 +1186,19 @@ FxExpression *FxColorCast::Resolve(FCompileContext &ctx) if (basex->isConstant()) { ExpVal constval = static_cast(basex)->GetValue(); - FxExpression *x = new FxConstant(V_GetColor(nullptr, constval.GetString()), ScriptPosition); - delete this; - return x; + if (constval.GetString().Len() == 0) + { + // empty string means 'no state'. This would otherwise just cause endless errors and have the same result anyway. + FxExpression *x = new FxConstant(-1, ScriptPosition); + delete this; + return x; + } + else + { + FxExpression *x = new FxConstant(V_GetColor(nullptr, constval.GetString()), ScriptPosition); + delete this; + return x; + } } return this; } @@ -1870,7 +1888,7 @@ FxExpression *FxSizeAlign::Resolve(FCompileContext& ctx) delete this; return nullptr; } - else if (!Operand->RequestAddress(nullptr)) + else if (!Operand->RequestAddress(ctx, nullptr)) { ScriptPosition.Message(MSG_ERROR, "Operand must be addressable to determine %s", Which == TK_AlignOf ? "alignment" : "size"); delete this; @@ -1907,7 +1925,7 @@ FxPreIncrDecr::~FxPreIncrDecr() SAFE_DELETE(Base); } -bool FxPreIncrDecr::RequestAddress(bool *writable) +bool FxPreIncrDecr::RequestAddress(FCompileContext &ctx, bool *writable) { AddressRequested = true; if (writable != nullptr) *writable = AddressWritable; @@ -1933,7 +1951,7 @@ FxExpression *FxPreIncrDecr::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (!Base->RequestAddress(&AddressWritable) || !AddressWritable ) + if (!Base->RequestAddress(ctx, &AddressWritable) || !AddressWritable ) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); delete this; @@ -2019,7 +2037,7 @@ FxExpression *FxPostIncrDecr::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (!Base->RequestAddress(&AddressWritable) || !AddressWritable) + if (!Base->RequestAddress(ctx, &AddressWritable) || !AddressWritable) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); delete this; @@ -2107,7 +2125,7 @@ FxAssign::~FxAssign() } /* I don't think we should allow constructs like (a = b) = c;... -bool FxAssign::RequestAddress(bool *writable) +bool FxAssign::RequestAddress(FCompileContext &ctx, bool *writable) { AddressRequested = true; if (writable != nullptr) *writable = AddressWritable; @@ -2177,7 +2195,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) SAFE_RESOLVE(Right, ctx); } - if (!Base->RequestAddress(&AddressWritable) || !AddressWritable) + if (!Base->RequestAddress(ctx, &AddressWritable) || !AddressWritable) { ScriptPosition.Message(MSG_ERROR, "Expression must be a modifiable value"); delete this; @@ -2188,7 +2206,7 @@ FxExpression *FxAssign::Resolve(FCompileContext &ctx) if (Base->ExprType == EFX_StructMember || Base->ExprType == EFX_ClassMember) { auto f = static_cast(Base)->membervar; - if (f->BitValue != -1 && !(f->Flags & VARF_ReadOnly)) + if (f->BitValue != -1 && !ctx.CheckReadOnly(f->Flags)) { IsBitWrite = f->BitValue; return this; @@ -5335,10 +5353,10 @@ FxExpression *FxLocalVariable::Resolve(FCompileContext &ctx) return this; } -bool FxLocalVariable::RequestAddress(bool *writable) +bool FxLocalVariable::RequestAddress(FCompileContext &ctx, bool *writable) { AddressRequested = true; - if (writable != nullptr) *writable = !(Variable->VarFlags & VARF_ReadOnly); + if (writable != nullptr) *writable = !ctx.CheckReadOnly(Variable->VarFlags); return true; } @@ -5504,10 +5522,10 @@ FxGlobalVariable::FxGlobalVariable(PField* mem, const FScriptPosition &pos) // //========================================================================== -bool FxGlobalVariable::RequestAddress(bool *writable) +bool FxGlobalVariable::RequestAddress(FCompileContext &ctx, bool *writable) { AddressRequested = true; - if (writable != nullptr) *writable = AddressWritable && !(membervar->Flags & VARF_ReadOnly); + if (writable != nullptr) *writable = AddressWritable && !ctx.CheckReadOnly(membervar->Flags); return true; } @@ -5582,10 +5600,10 @@ FxStructMember::~FxStructMember() // //========================================================================== -bool FxStructMember::RequestAddress(bool *writable) +bool FxStructMember::RequestAddress(FCompileContext &ctx, bool *writable) { AddressRequested = true; - if (writable != nullptr) *writable = (AddressWritable && !(membervar->Flags & VARF_ReadOnly) && + if (writable != nullptr) *writable = (AddressWritable && !ctx.CheckReadOnly(membervar->Flags) && (!classx->ValueType->IsKindOf(RUNTIME_CLASS(PPointer)) || !static_cast(classx->ValueType)->IsConst)); return true; } @@ -5662,7 +5680,7 @@ FxExpression *FxStructMember::Resolve(FCompileContext &ctx) } else { - if (!(classx->RequestAddress(&AddressWritable))) + if (!(classx->RequestAddress(ctx, &AddressWritable))) { ScriptPosition.Message(MSG_ERROR, "unable to dereference left side of %s", membervar->SymbolName.GetChars()); delete this; @@ -5767,7 +5785,7 @@ FxArrayElement::~FxArrayElement() // //========================================================================== -bool FxArrayElement::RequestAddress(bool *writable) +bool FxArrayElement::RequestAddress(FCompileContext &ctx, bool *writable) { AddressRequested = true; if (writable != nullptr) *writable = AddressWritable; @@ -5830,7 +5848,7 @@ FxExpression *FxArrayElement::Resolve(FCompileContext &ctx) delete this; return nullptr; } - if (!Array->RequestAddress(&AddressWritable)) + if (!Array->RequestAddress(ctx, &AddressWritable)) { ScriptPosition.Message(MSG_ERROR, "Unable to dereference array."); delete this; diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 3cc86d1e6..df0ba7594 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -76,9 +76,10 @@ struct FCompileContext bool FromDecorate; // DECORATE must silence some warnings and demote some errors. int StateIndex; // index in actor's state table for anonymous functions, otherwise -1 (not used by DECORATE which pre-resolves state indices) int StateCount; // amount of states an anoymous function is being used on (must be 1 for state indices to be allowed.) + int Lump; TDeletingArray FunctionArgs; - FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate, int stateindex, int statecount); + FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate, int stateindex, int statecount, int lump); FCompileContext(PClass *cls, bool fromdecorate); // only to be used to resolve constants! PSymbol *FindInClass(FName identifier, PSymbolTable *&symt); @@ -87,6 +88,7 @@ struct FCompileContext void HandleJumps(int token, FxExpression *handler); void CheckReturn(PPrototype *proto, FScriptPosition &pos); + bool CheckReadOnly(int flags); FxLocalVariableDeclaration *FindLocalVariable(FName name); }; @@ -296,7 +298,7 @@ public: virtual FxExpression *Resolve(FCompileContext &ctx); virtual bool isConstant() const; - virtual bool RequestAddress(bool *writable); + virtual bool RequestAddress(FCompileContext &ctx, bool *writable); virtual PPrototype *ReturnProto(); virtual VMFunction *GetDirectFunction(); virtual bool CheckReturn() { return false; } @@ -715,7 +717,7 @@ public: FxPreIncrDecr(FxExpression *base, int token); ~FxPreIncrDecr(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(bool *writable); + bool RequestAddress(FCompileContext &ctx, bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -758,7 +760,7 @@ public: FxAssign(FxExpression *base, FxExpression *right, bool ismodify = false); ~FxAssign(); FxExpression *Resolve(FCompileContext&); - //bool RequestAddress(bool *writable); + //bool RequestAddress(FCompileContext &ctx, bool *writable); ExpEmit Emit(VMFunctionBuilder *build); ExpEmit Address; @@ -1157,7 +1159,7 @@ public: FxGlobalVariable(PField*, const FScriptPosition&); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(bool *writable); + bool RequestAddress(FCompileContext &ctx, bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1178,7 +1180,7 @@ public: FxStructMember(FxExpression*, PField*, const FScriptPosition&); ~FxStructMember(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(bool *writable); + bool RequestAddress(FCompileContext &ctx, bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1210,7 +1212,7 @@ public: FxLocalVariable(FxLocalVariableDeclaration*, const FScriptPosition&); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(bool *writable); + bool RequestAddress(FCompileContext &ctx, bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1245,7 +1247,7 @@ public: FxArrayElement(FxExpression*, FxExpression*); ~FxArrayElement(); FxExpression *Resolve(FCompileContext&); - bool RequestAddress(bool *writable); + bool RequestAddress(FCompileContext &ctx, bool *writable); ExpEmit Emit(VMFunctionBuilder *build); }; diff --git a/src/scripting/thingdef_data.cpp b/src/scripting/thingdef_data.cpp index 8152e9977..4ccc72748 100644 --- a/src/scripting/thingdef_data.cpp +++ b/src/scripting/thingdef_data.cpp @@ -55,7 +55,7 @@ static TArray AFTable; // [RH] Keep GCC quiet by not using offsetof on Actor types. #define DEFINE_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native } -#define DEFINE_READONLY_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native|VARF_ReadOnly } +#define DEFINE_PROTECTED_FLAG(prefix, name, type, variable) { (unsigned int)prefix##_##name, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native|VARF_ReadOnly|VARF_InternalAccess } #define DEFINE_FLAG2(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native } #define DEFINE_FLAG2_DEPRECATED(symbol, name, type, variable) { (unsigned int)symbol, #name, (int)(size_t)&((type*)1)->variable - 1, sizeof(((type *)0)->variable), VARF_Native|VARF_Deprecated } #define DEFINE_DEPRECATED_FLAG(name) { DEPF_##name, #name, -1, 0, true } @@ -99,8 +99,8 @@ FFlagDef ActorFlagDefs[]= DEFINE_FLAG(MF, SPECIAL, APlayerPawn, flags), DEFINE_FLAG(MF, SOLID, AActor, flags), DEFINE_FLAG(MF, SHOOTABLE, AActor, flags), - DEFINE_FLAG(MF, NOSECTOR, AActor, flags), - DEFINE_FLAG(MF, NOBLOCKMAP, AActor, flags), + DEFINE_PROTECTED_FLAG(MF, NOSECTOR, AActor, flags), + DEFINE_PROTECTED_FLAG(MF, NOBLOCKMAP, AActor, flags), DEFINE_FLAG(MF, AMBUSH, AActor, flags), DEFINE_FLAG(MF, JUSTHIT, AActor, flags), DEFINE_FLAG(MF, JUSTATTACKED, AActor, flags), diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index 1544ca4a6..e5ed249b1 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -653,7 +653,7 @@ void VMFunctionBuilder::BackpatchToHere(size_t loc) //========================================================================== FFunctionBuildList FunctionBuildList; -VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool fromdecorate, int stateindex, int statecount) +VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *code, const FString &name, bool fromdecorate, int stateindex, int statecount, int lumpnum) { auto func = code->GetDirectFunction(); if (func != nullptr) @@ -675,6 +675,7 @@ VMFunction *FFunctionBuildList::AddFunction(PFunction *functype, FxExpression *c it.FromDecorate = fromdecorate; it.StateIndex = stateindex; it.StateCount = statecount; + it.Lump = lumpnum; // set prototype for named functions. if (it.Func->SymbolName != NAME_None) @@ -700,7 +701,7 @@ void FFunctionBuildList::Build() assert(item.Code != NULL); // We don't know the return type in advance for anonymous functions. - FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate, item.StateIndex, item.StateCount); + FCompileContext ctx(item.Func, item.Func->SymbolName == NAME_None ? nullptr : item.Func->Variants[0].Proto, item.FromDecorate, item.StateIndex, item.StateCount, item.Lump); // Allocate registers for the function's arguments and create local variable nodes before starting to resolve it. VMFunctionBuilder buildit(item.Func->GetImplicitArgs()); diff --git a/src/scripting/vm/vmbuilder.h b/src/scripting/vm/vmbuilder.h index 452a7882c..5394dec32 100644 --- a/src/scripting/vm/vmbuilder.h +++ b/src/scripting/vm/vmbuilder.h @@ -108,13 +108,14 @@ class FFunctionBuildList FString PrintableName; int StateIndex; int StateCount; + int Lump; bool FromDecorate; }; TArray mItems; public: - VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool fromdecorate, int currentstate = -1, int statecnt = 0); + VMFunction *AddFunction(PFunction *func, FxExpression *code, const FString &name, bool fromdecorate, int currentstate = -1, int statecnt = 0, int lumpnum = -1); void Build(); }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 41c3cde34..2965357dd 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -217,8 +217,8 @@ void ZCCCompiler::ProcessStruct(ZCC_Struct *cnode, PSymbolTreeNode *treenode, ZC // //========================================================================== -ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, PSymbolTable &_outsymbols) - : Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast) +ZCCCompiler::ZCCCompiler(ZCC_AST &ast, DObject *_outer, PSymbolTable &_symbols, PSymbolTable &_outsymbols, int lumpnum) + : Outer(_outer), GlobalTreeNodes(&_symbols), OutputSymbols(&_outsymbols), AST(ast), Lump(lumpnum) { FScriptPosition::ResetErrorCounter(); // Group top-level nodes by type @@ -2146,7 +2146,7 @@ void ZCCCompiler::InitFunctions() auto code = ConvertAST(c->Type(), f->Body); if (code != nullptr) { - sym->Variants[0].Implementation = FunctionBuildList.AddFunction(sym, code, FStringf("%s.%s", c->Type()->TypeName.GetChars(), FName(f->Name).GetChars()), false); + sym->Variants[0].Implementation = FunctionBuildList.AddFunction(sym, code, FStringf("%s.%s", c->Type()->TypeName.GetChars(), FName(f->Name).GetChars()), false, -1, 0, Lump); } } if (sym->Variants[0].Implementation != nullptr && hasdefault) // do not copy empty default lists, they only waste space and processing time. @@ -2344,7 +2344,7 @@ void ZCCCompiler::CompileStates() if (code != nullptr) { auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action); - state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false, statedef.GetStateCount(), (int)sl->Frames->Len()); + state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false, statedef.GetStateCount(), (int)sl->Frames->Len(), Lump); } } diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 4ad72769a..c901fc42e 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -78,7 +78,7 @@ struct ZCC_ConstantWork class ZCCCompiler { public: - ZCCCompiler(ZCC_AST &tree, DObject *outer, PSymbolTable &symbols, PSymbolTable &outsymbols); + ZCCCompiler(ZCC_AST &tree, DObject *outer, PSymbolTable &symbols, PSymbolTable &outsymbols, int lumpnum); ~ZCCCompiler(); int Compile(); @@ -149,6 +149,7 @@ private: PSymbolTable *GlobalTreeNodes; PSymbolTable *OutputSymbols; ZCC_AST &AST; + int Lump; }; void ZCC_InitConversions(); diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 1f0800302..c84b72c66 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -374,7 +374,7 @@ static void DoParse(int lumpnum) PSymbolTable symtable; symtable.SetName("Global_Node"); - ZCCCompiler cc(state, NULL, symtable, GlobalSymbols); + ZCCCompiler cc(state, NULL, symtable, GlobalSymbols, lumpnum); cc.Compile(); if (FScriptPosition::ErrorCounter > 0) From 701ffb868b45ddf7fe21acb0f9af9237b201f5ec Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 8 Nov 2016 22:36:44 +0100 Subject: [PATCH 207/255] - fixed: The first argument of string-based ACS specials was missing a string to name cast. --- src/scripting/codegeneration/codegen.cpp | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 32ee2d012..63302d600 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6409,7 +6409,16 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) } else if (Special < 0 && i == 0) { - if ((*ArgList)[i]->ValueType != TypeName) + if ((*ArgList)[i]->ValueType == TypeString) + { + (*ArgList)[i] = new FxNameCast((*ArgList)[i]); + (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); + if ((*ArgList)[i] == nullptr) + { + failed = true; + } + } + else if ((*ArgList)[i]->ValueType != TypeName) { ScriptPosition.Message(MSG_ERROR, "Name expected for parameter %d", i); failed = true; From 0b3585c83f35e84510b1db22d8723b9a2be178df Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sat, 5 Nov 2016 17:08:54 +0100 Subject: [PATCH 208/255] Separate the pointer list from the implement macro --- src/b_bot.cpp | 16 +++-- src/d_dehacked.cpp | 8 ++- src/decallib.cpp | 8 ++- src/dobject.h | 14 ++-- src/dobjtype.cpp | 70 +++++++++++++------- src/dsectoreffect.cpp | 8 ++- src/fragglescript/t_prepro.cpp | 6 +- src/fragglescript/t_script.cpp | 103 ++++++++++++++++-------------- src/fragglescript/t_variable.cpp | 8 ++- src/g_hexen/a_spike.cpp | 8 ++- src/g_shared/a_action.cpp | 6 +- src/g_shared/a_decals.cpp | 10 +-- src/g_shared/a_flashfader.cpp | 8 ++- src/g_shared/a_morph.cpp | 8 ++- src/g_shared/a_movingcamera.cpp | 26 +++++--- src/g_shared/a_pickups.cpp | 8 ++- src/g_shared/a_quake.cpp | 8 ++- src/g_shared/a_soundsequence.cpp | 6 +- src/g_shared/a_weaponpiece.cpp | 7 +- src/g_shared/a_weapons.cpp | 12 ++-- src/g_shared/hudmessages.cpp | 8 ++- src/g_shared/sbarinfo.cpp | 10 +-- src/g_shared/shared_sbar.cpp | 10 +-- src/info.cpp | 6 +- src/intermission/intermission.cpp | 7 +- src/m_cheat.cpp | 6 +- src/menu/menu.cpp | 8 ++- src/p_acs.cpp | 30 +++++---- src/p_floor.cpp | 10 +-- src/p_mobj.cpp | 34 +++++----- src/p_pillar.cpp | 10 +-- src/p_pspr.cpp | 8 ++- src/p_pusher.cpp | 7 +- src/p_scroll.cpp | 11 ++-- src/p_user.cpp | 10 +-- src/po_man.cpp | 8 ++- src/r_data/r_interpolate.cpp | 9 ++- src/s_sndseq.cpp | 22 ++++--- src/scripting/vm/vmframe.cpp | 7 +- 39 files changed, 341 insertions(+), 228 deletions(-) diff --git a/src/b_bot.cpp b/src/b_bot.cpp index c4d702c8e..dee20d295 100644 --- a/src/b_bot.cpp +++ b/src/b_bot.cpp @@ -16,13 +16,15 @@ #include "d_player.h" IMPLEMENT_POINTY_CLASS(DBot) - DECLARE_POINTER(dest) - DECLARE_POINTER(prev) - DECLARE_POINTER(enemy) - DECLARE_POINTER(missile) - DECLARE_POINTER(mate) - DECLARE_POINTER(last_mate) -END_POINTERS + +IMPLEMENT_POINTERS_START(DBot) + IMPLEMENT_POINTER(dest) + IMPLEMENT_POINTER(prev) + IMPLEMENT_POINTER(enemy) + IMPLEMENT_POINTER(missile) + IMPLEMENT_POINTER(mate) + IMPLEMENT_POINTER(last_mate) +IMPLEMENT_POINTERS_END DBot::DBot () : DThinker(STAT_BOT) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 896e174d6..4e2b326ff 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -231,9 +231,11 @@ DehInfo deh = // from the original actor's defaults. The original actor is then changed to // spawn the new class. -IMPLEMENT_POINTY_CLASS (ADehackedPickup) - DECLARE_POINTER (RealPickup) -END_POINTERS +IMPLEMENT_POINTY_CLASS(ADehackedPickup) + +IMPLEMENT_POINTERS_START(ADehackedPickup) + IMPLEMENT_POINTER(RealPickup) +IMPLEMENT_POINTERS_END TArray TouchedActors; diff --git a/src/decallib.cpp b/src/decallib.cpp index fc7e465dc..2f7492516 100644 --- a/src/decallib.cpp +++ b/src/decallib.cpp @@ -119,9 +119,11 @@ protected: DDecalThinker () : DThinker (STAT_DECALTHINKER) {} }; -IMPLEMENT_POINTY_CLASS (DDecalThinker) - DECLARE_POINTER (TheDecal) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DDecalThinker) + +IMPLEMENT_POINTERS_START(DDecalThinker) + IMPLEMENT_POINTER(TheDecal) +IMPLEMENT_POINTERS_END void DDecalThinker::Serialize(FSerializer &arc) { diff --git a/src/dobject.h b/src/dobject.h index ea0a44a85..620bc8af3 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -151,11 +151,6 @@ protected: \ #define HAS_FIELDS \ static void InitNativeFields(); -// Taking the address of a field in an object at address 1 instead of -// address 0 keeps GCC from complaining about possible misuse of offsetof. -#define DECLARE_POINTER(field) (size_t)&((ThisClass*)1)->field - 1, -#define END_POINTERS ~(size_t)0 }; - #if defined(_MSC_VER) # pragma section(".creg$u",read) # define _DECLARE_TI(cls) __declspec(allocate(".creg$u")) ClassReg * const cls::RegistrationInfoPtr = &cls::RegistrationInfo; @@ -182,12 +177,10 @@ protected: \ #define IMPLEMENT_POINTY_CLASS(cls) \ _IMP_CREATE_OBJ(cls) \ _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor, nullptr) \ - const size_t cls::PointerOffsets[] = { #define IMPLEMENT_POINTY_CLASS_WITH_FIELDS(cls) \ _IMP_CREATE_OBJ(cls) \ _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor, cls::InitNativeFields) \ - const size_t cls::PointerOffsets[] = { #define IMPLEMENT_CLASS(cls) \ _IMP_CREATE_OBJ(cls) \ @@ -202,7 +195,12 @@ protected: \ #define IMPLEMENT_ABSTRACT_POINTY_CLASS(cls) \ _IMP_PCLASS(cls,cls::PointerOffsets,nullptr,nullptr) \ - const size_t cls::PointerOffsets[] = { + +// Taking the address of a field in an object at address 1 instead of +// address 0 keeps GCC from complaining about possible misuse of offsetof. +#define IMPLEMENT_POINTERS_START(cls) const size_t cls::PointerOffsets[] = { +#define IMPLEMENT_POINTER(field) (size_t)&((ThisClass*)1)->field - 1, +#define IMPLEMENT_POINTERS_END ~(size_t)0 }; enum EObjectFlags { diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index e3c638062..f9f987a42 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -188,8 +188,10 @@ PClassClass::PClassClass() /* PType ******************************************************************/ IMPLEMENT_ABSTRACT_POINTY_CLASS(PType) - DECLARE_POINTER(HashNext) -END_POINTERS + +IMPLEMENT_POINTERS_START(PType) + IMPLEMENT_POINTER(HashNext) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -643,8 +645,10 @@ IMPLEMENT_ABSTRACT_CLASS(PCompoundType) /* PNamedType *************************************************************/ IMPLEMENT_ABSTRACT_POINTY_CLASS(PNamedType) - DECLARE_POINTER(Outer) -END_POINTERS + +IMPLEMENT_POINTERS_START(PNamedType) + IMPLEMENT_POINTER(Outer) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -1457,8 +1461,10 @@ bool PStatePointer::ReadValue(FSerializer &ar, const char *key, void *addr) cons /* PPointer ***************************************************************/ IMPLEMENT_POINTY_CLASS(PPointer) - DECLARE_POINTER(PointedType) -END_POINTERS + +IMPLEMENT_POINTERS_START(PPointer) + IMPLEMENT_POINTER(PointedType) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -1586,8 +1592,10 @@ PPointer *NewPointer(PType *type, bool isconst) /* PClassPointer **********************************************************/ IMPLEMENT_POINTY_CLASS(PClassPointer) - DECLARE_POINTER(ClassRestriction) -END_POINTERS + +IMPLEMENT_POINTERS_START(PClassPointer) + IMPLEMENT_POINTER(ClassRestriction) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -1665,8 +1673,10 @@ PClassPointer *NewClassPointer(PClass *restrict) /* PEnum ******************************************************************/ IMPLEMENT_POINTY_CLASS(PEnum) - DECLARE_POINTER(ValueType) -END_POINTERS + +IMPLEMENT_POINTERS_START(PEnum) + IMPLEMENT_POINTER(ValueType) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -1716,8 +1726,10 @@ PEnum *NewEnum(FName name, PTypeBase *outer) /* PArray *****************************************************************/ IMPLEMENT_POINTY_CLASS(PArray) - DECLARE_POINTER(ElementType) -END_POINTERS + +IMPLEMENT_POINTERS_START(PArray) + IMPLEMENT_POINTER(ElementType) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -1913,8 +1925,10 @@ PVector *NewVector(unsigned int size) /* PDynArray **************************************************************/ IMPLEMENT_POINTY_CLASS(PDynArray) - DECLARE_POINTER(ElementType) -END_POINTERS + +IMPLEMENT_POINTERS_START(PDynArray) + IMPLEMENT_POINTER(ElementType) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -1994,9 +2008,11 @@ PDynArray *NewDynArray(PType *type) /* PMap *******************************************************************/ IMPLEMENT_POINTY_CLASS(PMap) - DECLARE_POINTER(KeyType) - DECLARE_POINTER(ValueType) -END_POINTERS + +IMPLEMENT_POINTERS_START(PMap) + IMPLEMENT_POINTER(KeyType) + IMPLEMENT_POINTER(ValueType) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -2486,8 +2502,10 @@ unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArra /* PClass *****************************************************************/ IMPLEMENT_POINTY_CLASS(PClass) - DECLARE_POINTER(ParentClass) -END_POINTERS + +IMPLEMENT_POINTERS_START(PClass) + IMPLEMENT_POINTER(ParentClass) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -3407,12 +3425,18 @@ IMPLEMENT_ABSTRACT_CLASS(PSymbol); IMPLEMENT_CLASS(PSymbolConst); IMPLEMENT_CLASS(PSymbolConstNumeric); IMPLEMENT_CLASS(PSymbolConstString); + IMPLEMENT_POINTY_CLASS(PSymbolType) - DECLARE_POINTER(Type) -END_POINTERS + +IMPLEMENT_POINTERS_START(PSymbolType) + IMPLEMENT_POINTER(Type) +IMPLEMENT_POINTERS_END + IMPLEMENT_POINTY_CLASS(PSymbolVMFunction) - DECLARE_POINTER(Function) -END_POINTERS + +IMPLEMENT_POINTERS_START(PSymbolVMFunction) + IMPLEMENT_POINTER(Function) +IMPLEMENT_POINTERS_END IMPLEMENT_CLASS(PSymbolTreeNode) //========================================================================== diff --git a/src/dsectoreffect.cpp b/src/dsectoreffect.cpp index 815b49dc4..7b29dbf05 100644 --- a/src/dsectoreffect.cpp +++ b/src/dsectoreffect.cpp @@ -71,9 +71,11 @@ void DSectorEffect::Serialize(FSerializer &arc) arc("sector", m_Sector); } -IMPLEMENT_POINTY_CLASS (DMover) - DECLARE_POINTER(interpolation) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DMover) + +IMPLEMENT_POINTERS_START(DMover) + IMPLEMENT_POINTER(interpolation) +IMPLEMENT_POINTERS_END DMover::DMover () { diff --git a/src/fragglescript/t_prepro.cpp b/src/fragglescript/t_prepro.cpp index 619b6d570..2c667878d 100644 --- a/src/fragglescript/t_prepro.cpp +++ b/src/fragglescript/t_prepro.cpp @@ -72,8 +72,10 @@ //========================================================================== IMPLEMENT_POINTY_CLASS(DFsSection) - DECLARE_POINTER(next) -END_POINTERS + +IMPLEMENT_POINTERS_START(DFsSection) + IMPLEMENT_POINTER(next) +IMPLEMENT_POINTERS_END //========================================================================== // diff --git a/src/fragglescript/t_script.cpp b/src/fragglescript/t_script.cpp index f1376b7eb..f14cbe25f 100644 --- a/src/fragglescript/t_script.cpp +++ b/src/fragglescript/t_script.cpp @@ -75,23 +75,23 @@ AActor *trigger_obj; // //========================================================================== -#define DECLARE_16_POINTERS(v, i) \ - DECLARE_POINTER(v[i]) \ - DECLARE_POINTER(v[i+1]) \ - DECLARE_POINTER(v[i+2]) \ - DECLARE_POINTER(v[i+3]) \ - DECLARE_POINTER(v[i+4]) \ - DECLARE_POINTER(v[i+5]) \ - DECLARE_POINTER(v[i+6]) \ - DECLARE_POINTER(v[i+7]) \ - DECLARE_POINTER(v[i+8]) \ - DECLARE_POINTER(v[i+9]) \ - DECLARE_POINTER(v[i+10]) \ - DECLARE_POINTER(v[i+11]) \ - DECLARE_POINTER(v[i+12]) \ - DECLARE_POINTER(v[i+13]) \ - DECLARE_POINTER(v[i+14]) \ - DECLARE_POINTER(v[i+15]) \ +#define IMPLEMENT_16_POINTERS(v, i) \ + IMPLEMENT_POINTER(v[i]) \ + IMPLEMENT_POINTER(v[i+1]) \ + IMPLEMENT_POINTER(v[i+2]) \ + IMPLEMENT_POINTER(v[i+3]) \ + IMPLEMENT_POINTER(v[i+4]) \ + IMPLEMENT_POINTER(v[i+5]) \ + IMPLEMENT_POINTER(v[i+6]) \ + IMPLEMENT_POINTER(v[i+7]) \ + IMPLEMENT_POINTER(v[i+8]) \ + IMPLEMENT_POINTER(v[i+9]) \ + IMPLEMENT_POINTER(v[i+10]) \ + IMPLEMENT_POINTER(v[i+11]) \ + IMPLEMENT_POINTER(v[i+12]) \ + IMPLEMENT_POINTER(v[i+13]) \ + IMPLEMENT_POINTER(v[i+14]) \ + IMPLEMENT_POINTER(v[i+15]) \ //========================================================================== // @@ -100,29 +100,31 @@ AActor *trigger_obj; //========================================================================== IMPLEMENT_POINTY_CLASS(DFsScript) - DECLARE_POINTER(parent) - DECLARE_POINTER(trigger) - DECLARE_16_POINTERS(sections, 0) - DECLARE_POINTER(sections[16]) - DECLARE_16_POINTERS(variables, 0) - DECLARE_16_POINTERS(children, 0) - DECLARE_16_POINTERS(children, 16) - DECLARE_16_POINTERS(children, 32) - DECLARE_16_POINTERS(children, 48) - DECLARE_16_POINTERS(children, 64) - DECLARE_16_POINTERS(children, 80) - DECLARE_16_POINTERS(children, 96) - DECLARE_16_POINTERS(children, 112) - DECLARE_16_POINTERS(children, 128) - DECLARE_16_POINTERS(children, 144) - DECLARE_16_POINTERS(children, 160) - DECLARE_16_POINTERS(children, 176) - DECLARE_16_POINTERS(children, 192) - DECLARE_16_POINTERS(children, 208) - DECLARE_16_POINTERS(children, 224) - DECLARE_16_POINTERS(children, 240) - DECLARE_POINTER(children[256]) -END_POINTERS + +IMPLEMENT_POINTERS_START(DFsScript) + IMPLEMENT_POINTER(parent) + IMPLEMENT_POINTER(trigger) + IMPLEMENT_16_POINTERS(sections, 0) + IMPLEMENT_POINTER(sections[16]) + IMPLEMENT_16_POINTERS(variables, 0) + IMPLEMENT_16_POINTERS(children, 0) + IMPLEMENT_16_POINTERS(children, 16) + IMPLEMENT_16_POINTERS(children, 32) + IMPLEMENT_16_POINTERS(children, 48) + IMPLEMENT_16_POINTERS(children, 64) + IMPLEMENT_16_POINTERS(children, 80) + IMPLEMENT_16_POINTERS(children, 96) + IMPLEMENT_16_POINTERS(children, 112) + IMPLEMENT_16_POINTERS(children, 128) + IMPLEMENT_16_POINTERS(children, 144) + IMPLEMENT_16_POINTERS(children, 160) + IMPLEMENT_16_POINTERS(children, 176) + IMPLEMENT_16_POINTERS(children, 192) + IMPLEMENT_16_POINTERS(children, 208) + IMPLEMENT_16_POINTERS(children, 224) + IMPLEMENT_16_POINTERS(children, 240) + IMPLEMENT_POINTER(children[256]) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -268,11 +270,13 @@ void DFsScript::ParseScript(char *position) //========================================================================== IMPLEMENT_POINTY_CLASS(DRunningScript) - DECLARE_POINTER(prev) - DECLARE_POINTER(next) - DECLARE_POINTER(trigger) - DECLARE_16_POINTERS(variables, 0) -END_POINTERS + +IMPLEMENT_POINTERS_START(DRunningScript) + IMPLEMENT_POINTER(prev) + IMPLEMENT_POINTER(next) + IMPLEMENT_POINTER(trigger) + IMPLEMENT_16_POINTERS(variables, 0) +IMPLEMENT_POINTERS_END //========================================================================== // @@ -375,10 +379,13 @@ void DRunningScript::Serialize(FSerializer &arc) // The main thinker // //========================================================================== + IMPLEMENT_POINTY_CLASS(DFraggleThinker) - DECLARE_POINTER(RunningScripts) - DECLARE_POINTER(LevelScript) -END_POINTERS + +IMPLEMENT_POINTERS_START(DFraggleThinker) + IMPLEMENT_POINTER(RunningScripts) + IMPLEMENT_POINTER(LevelScript) +IMPLEMENT_POINTERS_END TObjPtr DFraggleThinker::ActiveThinker; diff --git a/src/fragglescript/t_variable.cpp b/src/fragglescript/t_variable.cpp index 125f32367..895602f53 100644 --- a/src/fragglescript/t_variable.cpp +++ b/src/fragglescript/t_variable.cpp @@ -180,9 +180,11 @@ AActor* actorvalue(const svalue_t &svalue) //========================================================================== IMPLEMENT_POINTY_CLASS(DFsVariable) - DECLARE_POINTER (next) - DECLARE_POINTER (actor) -END_POINTERS + +IMPLEMENT_POINTERS_START(DFsVariable) + IMPLEMENT_POINTER(next) + IMPLEMENT_POINTER(actor) +IMPLEMENT_POINTERS_END //========================================================================== // diff --git a/src/g_hexen/a_spike.cpp b/src/g_hexen/a_spike.cpp index 3f5f4d2e8..faf3c3083 100644 --- a/src/g_hexen/a_spike.cpp +++ b/src/g_hexen/a_spike.cpp @@ -31,9 +31,11 @@ public: TObjPtr DirtClump; }; -IMPLEMENT_POINTY_CLASS (AThrustFloor) - DECLARE_POINTER (DirtClump) -END_POINTERS +IMPLEMENT_POINTY_CLASS(AThrustFloor) + +IMPLEMENT_POINTERS_START(AThrustFloor) + IMPLEMENT_POINTER(DirtClump) +IMPLEMENT_POINTERS_END void AThrustFloor::Serialize(FSerializer &arc) { diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index e1fa9a7fa..4925e3c25 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -305,8 +305,10 @@ private: }; IMPLEMENT_POINTY_CLASS(DCorpsePointer) - DECLARE_POINTER(Corpse) -END_POINTERS + +IMPLEMENT_POINTERS_START(DCorpsePointer) + IMPLEMENT_POINTER(Corpse) +IMPLEMENT_POINTERS_END CUSTOM_CVAR(Int, sv_corpsequeuesize, 64, CVAR_ARCHIVE|CVAR_SERVERINFO) { diff --git a/src/g_shared/a_decals.cpp b/src/g_shared/a_decals.cpp index e02ab1a52..b06191607 100644 --- a/src/g_shared/a_decals.cpp +++ b/src/g_shared/a_decals.cpp @@ -58,10 +58,12 @@ static int ImpactCount; CVAR (Bool, cl_spreaddecals, true, CVAR_ARCHIVE) -IMPLEMENT_POINTY_CLASS (DBaseDecal) - DECLARE_POINTER(WallPrev) - DECLARE_POINTER(WallNext) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DBaseDecal) + +IMPLEMENT_POINTERS_START(DBaseDecal) + IMPLEMENT_POINTER(WallPrev) + IMPLEMENT_POINTER(WallNext) +IMPLEMENT_POINTERS_END IMPLEMENT_CLASS (DImpactDecal) diff --git a/src/g_shared/a_flashfader.cpp b/src/g_shared/a_flashfader.cpp index 71673e5c7..61b305f44 100644 --- a/src/g_shared/a_flashfader.cpp +++ b/src/g_shared/a_flashfader.cpp @@ -3,9 +3,11 @@ #include "d_player.h" #include "serializer.h" -IMPLEMENT_POINTY_CLASS (DFlashFader) - DECLARE_POINTER (ForWho) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DFlashFader) + +IMPLEMENT_POINTERS_START(DFlashFader) + IMPLEMENT_POINTER(ForWho) +IMPLEMENT_POINTERS_END DFlashFader::DFlashFader () { diff --git a/src/g_shared/a_morph.cpp b/src/g_shared/a_morph.cpp index 46ae5cac7..3323a0a4c 100644 --- a/src/g_shared/a_morph.cpp +++ b/src/g_shared/a_morph.cpp @@ -650,9 +650,11 @@ void AMorphProjectile::Serialize(FSerializer &arc) // Morphed Monster (you must subclass this to do something useful) --------- -IMPLEMENT_POINTY_CLASS (AMorphedMonster) - DECLARE_POINTER (UnmorphedMe) -END_POINTERS +IMPLEMENT_POINTY_CLASS(AMorphedMonster) + +IMPLEMENT_POINTERS_START(AMorphedMonster) + IMPLEMENT_POINTER(UnmorphedMe) +IMPLEMENT_POINTERS_END void AMorphedMonster::Serialize(FSerializer &arc) { diff --git a/src/g_shared/a_movingcamera.cpp b/src/g_shared/a_movingcamera.cpp index 76f128b15..e60c94036 100644 --- a/src/g_shared/a_movingcamera.cpp +++ b/src/g_shared/a_movingcamera.cpp @@ -66,9 +66,11 @@ public: TObjPtr Next; }; -IMPLEMENT_POINTY_CLASS (AInterpolationPoint) - DECLARE_POINTER (Next) -END_POINTERS +IMPLEMENT_POINTY_CLASS(AInterpolationPoint) + +IMPLEMENT_POINTERS_START(AInterpolationPoint) + IMPLEMENT_POINTER(Next) +IMPLEMENT_POINTERS_END void AInterpolationPoint::Serialize(FSerializer &arc) { @@ -176,10 +178,12 @@ protected: int HoldTime; }; -IMPLEMENT_POINTY_CLASS (APathFollower) - DECLARE_POINTER (PrevNode) - DECLARE_POINTER (CurrNode) -END_POINTERS +IMPLEMENT_POINTY_CLASS(APathFollower) + +IMPLEMENT_POINTERS_START(APathFollower) + IMPLEMENT_POINTER(PrevNode) + IMPLEMENT_POINTER(CurrNode) +IMPLEMENT_POINTERS_END void APathFollower::Serialize(FSerializer &arc) { @@ -592,9 +596,11 @@ protected: TObjPtr Activator; }; -IMPLEMENT_POINTY_CLASS (AMovingCamera) - DECLARE_POINTER (Activator) -END_POINTERS +IMPLEMENT_POINTY_CLASS(AMovingCamera) + +IMPLEMENT_POINTERS_START(AMovingCamera) + IMPLEMENT_POINTER(Activator) +IMPLEMENT_POINTERS_END void AMovingCamera::Serialize(FSerializer &arc) { diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index ae7516d17..155878bac 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -470,9 +470,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialPosition) int AInventory::StaticLastMessageTic; const char *AInventory::StaticLastMessage; -IMPLEMENT_POINTY_CLASS (AInventory) - DECLARE_POINTER (Owner) -END_POINTERS +IMPLEMENT_POINTY_CLASS(AInventory) + +IMPLEMENT_POINTERS_START(AInventory) + IMPLEMENT_POINTER(Owner) +IMPLEMENT_POINTERS_END //=========================================================================== // diff --git a/src/g_shared/a_quake.cpp b/src/g_shared/a_quake.cpp index 98e505b2b..1a0c6a0fd 100644 --- a/src/g_shared/a_quake.cpp +++ b/src/g_shared/a_quake.cpp @@ -14,9 +14,11 @@ static FRandom pr_quake ("Quake"); -IMPLEMENT_POINTY_CLASS (DEarthquake) - DECLARE_POINTER (m_Spot) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DEarthquake) + +IMPLEMENT_POINTERS_START(DEarthquake) + IMPLEMENT_POINTER(m_Spot) +IMPLEMENT_POINTERS_END //========================================================================== // diff --git a/src/g_shared/a_soundsequence.cpp b/src/g_shared/a_soundsequence.cpp index f09b5b7ad..3741a3914 100644 --- a/src/g_shared/a_soundsequence.cpp +++ b/src/g_shared/a_soundsequence.cpp @@ -81,8 +81,10 @@ public: }; IMPLEMENT_POINTY_CLASS(ASoundSequenceSlot) - DECLARE_POINTER(Sequence) -END_POINTERS + +IMPLEMENT_POINTERS_START(ASoundSequenceSlot) + IMPLEMENT_POINTER(Sequence) +IMPLEMENT_POINTERS_END //========================================================================== // diff --git a/src/g_shared/a_weaponpiece.cpp b/src/g_shared/a_weaponpiece.cpp index aefce18c1..4b0a6dcbf 100644 --- a/src/g_shared/a_weaponpiece.cpp +++ b/src/g_shared/a_weaponpiece.cpp @@ -24,10 +24,11 @@ void AWeaponHolder::Serialize(FSerializer &arc) ("pieceweapon", PieceWeapon); } +IMPLEMENT_POINTY_CLASS(AWeaponPiece) -IMPLEMENT_POINTY_CLASS (AWeaponPiece) - DECLARE_POINTER (FullWeapon) -END_POINTERS +IMPLEMENT_POINTERS_START(AWeaponPiece) + IMPLEMENT_POINTER(FullWeapon) +IMPLEMENT_POINTERS_END void AWeaponPiece::Serialize(FSerializer &arc) diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index 7e6aefb7a..ec5e32be8 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -21,11 +21,13 @@ #define BONUSADD 6 -IMPLEMENT_POINTY_CLASS (AWeapon) - DECLARE_POINTER (Ammo1) - DECLARE_POINTER (Ammo2) - DECLARE_POINTER (SisterWeapon) -END_POINTERS +IMPLEMENT_POINTY_CLASS(AWeapon) + +IMPLEMENT_POINTERS_START(AWeapon) + IMPLEMENT_POINTER(Ammo1) + IMPLEMENT_POINTER(Ammo2) + IMPLEMENT_POINTER(SisterWeapon) +IMPLEMENT_POINTERS_END FString WeaponSection; TArray KeyConfWeapons; diff --git a/src/g_shared/hudmessages.cpp b/src/g_shared/hudmessages.cpp index b86cf6417..783d1624d 100644 --- a/src/g_shared/hudmessages.cpp +++ b/src/g_shared/hudmessages.cpp @@ -44,9 +44,11 @@ EXTERN_CVAR(Int, con_scaletext) int active_con_scaletext(); -IMPLEMENT_POINTY_CLASS (DHUDMessage) - DECLARE_POINTER(Next) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DHUDMessage) + +IMPLEMENT_POINTERS_START(DHUDMessage) + IMPLEMENT_POINTER(Next) +IMPLEMENT_POINTERS_END IMPLEMENT_CLASS (DHUDMessageFadeOut) IMPLEMENT_CLASS (DHUDMessageFadeInOut) diff --git a/src/g_shared/sbarinfo.cpp b/src/g_shared/sbarinfo.cpp index 2e764a403..d0cd2defc 100644 --- a/src/g_shared/sbarinfo.cpp +++ b/src/g_shared/sbarinfo.cpp @@ -1532,10 +1532,12 @@ private: }; IMPLEMENT_POINTY_CLASS(DSBarInfo) - DECLARE_POINTER(ammo1) - DECLARE_POINTER(ammo2) - DECLARE_POINTER(armor) -END_POINTERS + +IMPLEMENT_POINTERS_START(DSBarInfo) + IMPLEMENT_POINTER(ammo1) + IMPLEMENT_POINTER(ammo2) + IMPLEMENT_POINTER(armor) +IMPLEMENT_POINTERS_END DBaseStatusBar *CreateCustomStatusBar (int script) { diff --git a/src/g_shared/shared_sbar.cpp b/src/g_shared/shared_sbar.cpp index 191b097d2..524ec4f1f 100644 --- a/src/g_shared/shared_sbar.cpp +++ b/src/g_shared/shared_sbar.cpp @@ -63,10 +63,12 @@ #define POWERUPICONSIZE 32 IMPLEMENT_POINTY_CLASS(DBaseStatusBar) - DECLARE_POINTER(Messages[0]) - DECLARE_POINTER(Messages[1]) - DECLARE_POINTER(Messages[2]) -END_POINTERS + +IMPLEMENT_POINTERS_START(DBaseStatusBar) + IMPLEMENT_POINTER(Messages[0]) + IMPLEMENT_POINTER(Messages[1]) + IMPLEMENT_POINTER(Messages[2]) +IMPLEMENT_POINTERS_END EXTERN_CVAR (Bool, am_showmonsters) EXTERN_CVAR (Bool, am_showsecrets) diff --git a/src/info.cpp b/src/info.cpp index 4705e0e53..12753b21b 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -154,8 +154,10 @@ int GetSpriteIndex(const char * spritename, bool add) } IMPLEMENT_POINTY_CLASS(PClassActor) - DECLARE_POINTER(DropItems) -END_POINTERS + +IMPLEMENT_POINTERS_START(PClassActor) + IMPLEMENT_POINTER(DropItems) +IMPLEMENT_POINTERS_END //========================================================================== // diff --git a/src/intermission/intermission.cpp b/src/intermission/intermission.cpp index ba4566e9d..527062bb6 100644 --- a/src/intermission/intermission.cpp +++ b/src/intermission/intermission.cpp @@ -59,9 +59,12 @@ IMPLEMENT_CLASS(DIntermissionScreenFader) IMPLEMENT_CLASS(DIntermissionScreenText) IMPLEMENT_CLASS(DIntermissionScreenCast) IMPLEMENT_CLASS(DIntermissionScreenScroller) + IMPLEMENT_POINTY_CLASS(DIntermissionController) - DECLARE_POINTER(mScreen) -END_POINTERS + +IMPLEMENT_POINTERS_START(DIntermissionController) + IMPLEMENT_POINTER(mScreen) +IMPLEMENT_POINTERS_END extern int NoWipe; diff --git a/src/m_cheat.cpp b/src/m_cheat.cpp index 7c110a52c..7348f5881 100644 --- a/src/m_cheat.cpp +++ b/src/m_cheat.cpp @@ -1034,8 +1034,10 @@ public: }; IMPLEMENT_POINTY_CLASS(DSuicider) - DECLARE_POINTER(Pawn) -END_POINTERS + +IMPLEMENT_POINTERS_START(DSuicider) + IMPLEMENT_POINTER(Pawn) +IMPLEMENT_POINTERS_END void cht_Suicide (player_t *plyr) { diff --git a/src/menu/menu.cpp b/src/menu/menu.cpp index 7e938230e..c4e0a4d98 100644 --- a/src/menu/menu.cpp +++ b/src/menu/menu.cpp @@ -91,9 +91,11 @@ static bool MenuEnabled = true; // //============================================================================ -IMPLEMENT_POINTY_CLASS (DMenu) - DECLARE_POINTER(mParentMenu) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DMenu) + +IMPLEMENT_POINTERS_START(DMenu) + IMPLEMENT_POINTER(mParentMenu) +IMPLEMENT_POINTERS_END DMenu::DMenu(DMenu *parent) { diff --git a/src/p_acs.cpp b/src/p_acs.cpp index 4024bc9f9..1fac7e8fe 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -1369,9 +1369,11 @@ private: DPlaneWatcher() {} }; -IMPLEMENT_POINTY_CLASS (DPlaneWatcher) - DECLARE_POINTER (Activator) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DPlaneWatcher) + +IMPLEMENT_POINTERS_START(DPlaneWatcher) + IMPLEMENT_POINTER(Activator) +IMPLEMENT_POINTERS_END DPlaneWatcher::DPlaneWatcher (AActor *it, line_t *line, int lineSide, bool ceiling, int tag, int height, int special, @@ -2858,10 +2860,12 @@ void FBehavior::StaticStopMyScripts (AActor *actor) //---- The ACS Interpreter ----// -IMPLEMENT_POINTY_CLASS (DACSThinker) - DECLARE_POINTER(LastScript) - DECLARE_POINTER(Scripts) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DACSThinker) + +IMPLEMENT_POINTERS_START(DACSThinker) + IMPLEMENT_POINTER(LastScript) + IMPLEMENT_POINTER(Scripts) +IMPLEMENT_POINTERS_END TObjPtr DACSThinker::ActiveThinker; @@ -2987,11 +2991,13 @@ void DACSThinker::StopScriptsFor (AActor *actor) } } -IMPLEMENT_POINTY_CLASS (DLevelScript) - DECLARE_POINTER(next) - DECLARE_POINTER(prev) - DECLARE_POINTER(activator) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DLevelScript) + +IMPLEMENT_POINTERS_START(DLevelScript) + IMPLEMENT_POINTER(next) + IMPLEMENT_POINTER(prev) + IMPLEMENT_POINTER(activator) +IMPLEMENT_POINTERS_END //========================================================================== // diff --git a/src/p_floor.cpp b/src/p_floor.cpp index 62479e340..23fdc7575 100644 --- a/src/p_floor.cpp +++ b/src/p_floor.cpp @@ -815,10 +815,12 @@ bool EV_DoDonut (int tag, line_t *line, double pillarspeed, double slimespeed) // //========================================================================== -IMPLEMENT_POINTY_CLASS (DElevator) - DECLARE_POINTER(m_Interp_Floor) - DECLARE_POINTER(m_Interp_Ceiling) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DElevator) + +IMPLEMENT_POINTERS_START(DElevator) + IMPLEMENT_POINTER(m_Interp_Floor) + IMPLEMENT_POINTER(m_Interp_Ceiling) +IMPLEMENT_POINTERS_END DElevator::DElevator () { diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 21d32c2de..f36760856 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -132,18 +132,20 @@ CVAR (Int, cl_bloodtype, 0, CVAR_ARCHIVE); // CODE -------------------------------------------------------------------- IMPLEMENT_POINTY_CLASS_WITH_FIELDS (AActor) - DECLARE_POINTER (target) - DECLARE_POINTER (lastenemy) - DECLARE_POINTER (tracer) - DECLARE_POINTER (goal) - DECLARE_POINTER (LastLookActor) - DECLARE_POINTER (Inventory) - DECLARE_POINTER (LastHeard) - DECLARE_POINTER (master) - DECLARE_POINTER (Poisoner) - DECLARE_POINTER (DamageFunc) - DECLARE_POINTER (alternative) -END_POINTERS + +IMPLEMENT_POINTERS_START(AActor) + IMPLEMENT_POINTER(target) + IMPLEMENT_POINTER(lastenemy) + IMPLEMENT_POINTER(tracer) + IMPLEMENT_POINTER(goal) + IMPLEMENT_POINTER(LastLookActor) + IMPLEMENT_POINTER(Inventory) + IMPLEMENT_POINTER(LastHeard) + IMPLEMENT_POINTER(master) + IMPLEMENT_POINTER(Poisoner) + IMPLEMENT_POINTER(DamageFunc) + IMPLEMENT_POINTER(alternative) +IMPLEMENT_POINTERS_END AActor::~AActor () { @@ -6953,9 +6955,12 @@ DEFINE_ACTION_FUNCTION(AActor, Vec3Offset) // DropItem handling // //---------------------------------------------------------------------------- + IMPLEMENT_POINTY_CLASS_WITH_FIELDS(DDropItem) - DECLARE_POINTER(Next) -END_POINTERS + +IMPLEMENT_POINTERS_START(DDropItem) + IMPLEMENT_POINTER(Next) +IMPLEMENT_POINTERS_END void DDropItem::InitNativeFields() { @@ -6967,7 +6972,6 @@ void DDropItem::InitNativeFields() meta->AddNativeField("Amount", TypeSInt32, myoffsetof(DDropItem, Amount)); } - void PrintMiscActorInfo(AActor *query) { if (query) diff --git a/src/p_pillar.cpp b/src/p_pillar.cpp index a55bd5cdb..52078daad 100644 --- a/src/p_pillar.cpp +++ b/src/p_pillar.cpp @@ -40,10 +40,12 @@ #include "serializer.h" #include "r_data/r_interpolate.h" -IMPLEMENT_POINTY_CLASS (DPillar) - DECLARE_POINTER(m_Interp_Floor) - DECLARE_POINTER(m_Interp_Ceiling) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DPillar) + +IMPLEMENT_POINTERS_START(DPillar) + IMPLEMENT_POINTER(m_Interp_Floor) + IMPLEMENT_POINTER(m_Interp_Ceiling) +IMPLEMENT_POINTERS_END DPillar::DPillar () { diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index bb39083da..b2e59ade4 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -100,9 +100,11 @@ static const FGenericButtons ButtonChecks[] = //------------------------------------------------------------------------ IMPLEMENT_POINTY_CLASS(DPSprite) - DECLARE_POINTER(Caller) - DECLARE_POINTER(Next) -END_POINTERS + +IMPLEMENT_POINTERS_START(DPSprite) + IMPLEMENT_POINTER(Caller) + IMPLEMENT_POINTER(Next) +IMPLEMENT_POINTERS_END //------------------------------------------------------------------------ // diff --git a/src/p_pusher.cpp b/src/p_pusher.cpp index 38c9c9720..d211f1c3c 100644 --- a/src/p_pusher.cpp +++ b/src/p_pusher.cpp @@ -74,10 +74,11 @@ protected: friend bool PIT_PushThing (AActor *thing); }; +IMPLEMENT_POINTY_CLASS(DPusher) -IMPLEMENT_POINTY_CLASS (DPusher) - DECLARE_POINTER (m_Source) -END_POINTERS +IMPLEMENT_POINTERS_START(DPusher) + IMPLEMENT_POINTER(m_Source) +IMPLEMENT_POINTERS_END DPusher::DPusher () { diff --git a/src/p_scroll.cpp b/src/p_scroll.cpp index f2ece8b3d..3918bc072 100644 --- a/src/p_scroll.cpp +++ b/src/p_scroll.cpp @@ -73,12 +73,13 @@ private: } }; +IMPLEMENT_POINTY_CLASS(DScroller) -IMPLEMENT_POINTY_CLASS (DScroller) - DECLARE_POINTER (m_Interpolations[0]) - DECLARE_POINTER (m_Interpolations[1]) - DECLARE_POINTER (m_Interpolations[2]) -END_POINTERS +IMPLEMENT_POINTERS_START(DScroller) + IMPLEMENT_POINTER(m_Interpolations[0]) + IMPLEMENT_POINTER(m_Interpolations[1]) + IMPLEMENT_POINTER(m_Interpolations[2]) +IMPLEMENT_POINTERS_END //----------------------------------------------------------------------------- diff --git a/src/p_user.cpp b/src/p_user.cpp index cd791623b..0efe422a3 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -622,10 +622,12 @@ void player_t::SendPitchLimits() const // //=========================================================================== -IMPLEMENT_POINTY_CLASS (APlayerPawn) - DECLARE_POINTER(InvFirst) - DECLARE_POINTER(InvSel) -END_POINTERS +IMPLEMENT_POINTY_CLASS(APlayerPawn) + +IMPLEMENT_POINTERS_START(APlayerPawn) + IMPLEMENT_POINTER(InvFirst) + IMPLEMENT_POINTER(InvSel) +IMPLEMENT_POINTERS_END IMPLEMENT_CLASS (APlayerChunk) diff --git a/src/po_man.cpp b/src/po_man.cpp index c779a8049..c80e72992 100644 --- a/src/po_man.cpp +++ b/src/po_man.cpp @@ -172,9 +172,11 @@ static FPolyNode *FreePolyNodes; // //========================================================================== -IMPLEMENT_POINTY_CLASS (DPolyAction) - DECLARE_POINTER(m_Interpolation) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DPolyAction) + +IMPLEMENT_POINTERS_START(DPolyAction) + IMPLEMENT_POINTER(m_Interpolation) +IMPLEMENT_POINTERS_END DPolyAction::DPolyAction () { diff --git a/src/r_data/r_interpolate.cpp b/src/r_data/r_interpolate.cpp index c944f0fa5..fdb8affc6 100644 --- a/src/r_data/r_interpolate.cpp +++ b/src/r_data/r_interpolate.cpp @@ -162,9 +162,12 @@ public: //========================================================================== IMPLEMENT_ABSTRACT_POINTY_CLASS(DInterpolation) -DECLARE_POINTER(Next) -DECLARE_POINTER(Prev) -END_POINTERS + +IMPLEMENT_POINTERS_START(DInterpolation) + IMPLEMENT_POINTER(Next) + IMPLEMENT_POINTER(Prev) +IMPLEMENT_POINTERS_END + IMPLEMENT_CLASS(DSectorPlaneInterpolation) IMPLEMENT_CLASS(DSectorScrollInterpolation) IMPLEMENT_CLASS(DWallScrollInterpolation) diff --git a/src/s_sndseq.cpp b/src/s_sndseq.cpp index 3b39965ff..baf33fd0c 100644 --- a/src/s_sndseq.cpp +++ b/src/s_sndseq.cpp @@ -285,12 +285,14 @@ void DSeqNode::SerializeSequences (FSerializer &arc) arc("sndseqlisthead", SequenceListHead); } -IMPLEMENT_POINTY_CLASS (DSeqNode) - DECLARE_POINTER(m_ChildSeqNode) - DECLARE_POINTER(m_ParentSeqNode) - DECLARE_POINTER(m_Next) - DECLARE_POINTER(m_Prev) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DSeqNode) + +IMPLEMENT_POINTERS_START(DSeqNode) + IMPLEMENT_POINTER(m_ChildSeqNode) + IMPLEMENT_POINTER(m_ParentSeqNode) + IMPLEMENT_POINTER(m_Next) + IMPLEMENT_POINTER(m_Prev) +IMPLEMENT_POINTERS_END DSeqNode::DSeqNode () : m_SequenceChoices(0) @@ -427,9 +429,11 @@ FName DSeqNode::GetSequenceName () const return Sequences[m_Sequence]->SeqName; } -IMPLEMENT_POINTY_CLASS (DSeqActorNode) - DECLARE_POINTER (m_Actor) -END_POINTERS +IMPLEMENT_POINTY_CLASS(DSeqActorNode) + +IMPLEMENT_POINTERS_START(DSeqActorNode) + IMPLEMENT_POINTER(m_Actor) +IMPLEMENT_POINTERS_END void DSeqActorNode::Serialize(FSerializer &arc) { diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index f622e114d..22728749c 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -36,8 +36,11 @@ IMPLEMENT_CLASS(VMException) IMPLEMENT_ABSTRACT_POINTY_CLASS(VMFunction) - DECLARE_POINTER(Proto) -END_POINTERS + +IMPLEMENT_POINTERS_START(VMFunction) + IMPLEMENT_POINTER(Proto) +IMPLEMENT_POINTERS_END + IMPLEMENT_CLASS(VMScriptFunction) IMPLEMENT_CLASS(VMNativeFunction) From bb2d61de508e9c33657185a86853bcbc31843667 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sat, 5 Nov 2016 18:27:14 +0100 Subject: [PATCH 209/255] Replaced the many implement macros with a single one that takes arguments instead --- src/b_bot.cpp | 2 +- src/c_dispatch.cpp | 4 +- src/d_dehacked.cpp | 2 +- src/decallib.cpp | 11 ++-- src/dobject.h | 41 +++++-------- src/dobjgc.cpp | 3 +- src/dobjtype.cpp | 73 +++++++++++------------ src/dsectoreffect.cpp | 10 ++-- src/dthinker.cpp | 4 +- src/fragglescript/t_func.cpp | 4 +- src/fragglescript/t_prepro.cpp | 2 +- src/fragglescript/t_script.cpp | 6 +- src/fragglescript/t_variable.cpp | 2 +- src/g_doom/a_scriptedmarine.cpp | 2 +- src/g_heretic/a_chicken.cpp | 2 +- src/g_heretic/a_hereticartifacts.cpp | 6 +- src/g_heretic/a_hereticweaps.cpp | 21 ++++--- src/g_heretic/a_ironlich.cpp | 2 +- src/g_hexen/a_boostarmor.cpp | 2 +- src/g_hexen/a_clericflame.cpp | 2 +- src/g_hexen/a_clericholy.cpp | 4 +- src/g_hexen/a_clericstaff.cpp | 2 +- src/g_hexen/a_fighteraxe.cpp | 2 +- src/g_hexen/a_fighterplayer.cpp | 6 +- src/g_hexen/a_fighterquietus.cpp | 2 +- src/g_hexen/a_flechette.cpp | 14 ++--- src/g_hexen/a_healingradius.cpp | 2 +- src/g_hexen/a_heresiarch.cpp | 10 ++-- src/g_hexen/a_hexenspecialdecs.cpp | 6 +- src/g_hexen/a_magecone.cpp | 2 +- src/g_hexen/a_magelightning.cpp | 4 +- src/g_hexen/a_magestaff.cpp | 4 +- src/g_hexen/a_pig.cpp | 2 +- src/g_hexen/a_spike.cpp | 2 +- src/g_hexen/a_summon.cpp | 2 +- src/g_hexen/a_teleportother.cpp | 4 +- src/g_level.cpp | 2 +- src/g_raven/a_artitele.cpp | 2 +- src/g_raven/a_minotaur.cpp | 4 +- src/g_shared/a_action.cpp | 6 +- src/g_shared/a_armor.cpp | 11 ++-- src/g_shared/a_artifacts.cpp | 54 ++++++++--------- src/g_shared/a_bridge.cpp | 4 +- src/g_shared/a_camera.cpp | 4 +- src/g_shared/a_debris.cpp | 2 +- src/g_shared/a_decals.cpp | 6 +- src/g_shared/a_fastprojectile.cpp | 3 +- src/g_shared/a_flashfader.cpp | 2 +- src/g_shared/a_fountain.cpp | 2 +- src/g_shared/a_hatetarget.cpp | 2 +- src/g_shared/a_keys.cpp | 2 +- src/g_shared/a_lightning.cpp | 2 +- src/g_shared/a_mapmarker.cpp | 2 +- src/g_shared/a_morph.cpp | 4 +- src/g_shared/a_movingcamera.cpp | 10 ++-- src/g_shared/a_pickups.cpp | 27 ++++----- src/g_shared/a_puzzleitems.cpp | 4 +- src/g_shared/a_quake.cpp | 2 +- src/g_shared/a_randomspawner.cpp | 2 +- src/g_shared/a_secrettrigger.cpp | 2 +- src/g_shared/a_sectoraction.cpp | 25 ++++---- src/g_shared/a_setcolor.cpp | 4 +- src/g_shared/a_skies.cpp | 12 ++-- src/g_shared/a_soundenvironment.cpp | 2 +- src/g_shared/a_soundsequence.cpp | 4 +- src/g_shared/a_spark.cpp | 2 +- src/g_shared/a_specialspot.cpp | 5 +- src/g_shared/a_waterzone.cpp | 2 +- src/g_shared/a_weaponpiece.cpp | 6 +- src/g_shared/a_weapons.cpp | 6 +- src/g_shared/hudmessages.cpp | 8 +-- src/g_shared/sbarinfo.cpp | 2 +- src/g_shared/shared_sbar.cpp | 2 +- src/g_strife/a_coin.cpp | 2 +- src/g_strife/a_loremaster.cpp | 2 +- src/g_strife/a_programmer.cpp | 2 +- src/g_strife/a_rebels.cpp | 2 +- src/g_strife/a_spectral.cpp | 2 +- src/g_strife/a_strifeitems.cpp | 28 ++++----- src/g_strife/a_strifestuff.cpp | 6 +- src/g_strife/a_strifeweapons.cpp | 6 +- src/g_strife/strife_sbar.cpp | 2 +- src/info.cpp | 2 +- src/intermission/intermission.cpp | 13 ++-- src/m_argv.cpp | 2 +- src/m_cheat.cpp | 2 +- src/menu/colorpickermenu.cpp | 2 +- src/menu/joystickmenu.cpp | 2 +- src/menu/listmenu.cpp | 2 +- src/menu/loadsavemenu.cpp | 6 +- src/menu/menu.cpp | 2 +- src/menu/menuinput.cpp | 2 +- src/menu/messagebox.cpp | 10 ++-- src/menu/optionmenu.cpp | 7 +-- src/menu/optionmenuitems.h | 2 +- src/menu/playermenu.cpp | 2 +- src/menu/readthis.cpp | 2 +- src/menu/videomenu.cpp | 2 +- src/p_acs.cpp | 6 +- src/p_buildmap.cpp | 2 +- src/p_ceiling.cpp | 2 +- src/p_conversation.cpp | 2 +- src/p_doors.cpp | 4 +- src/p_floor.cpp | 11 ++-- src/p_lights.cpp | 16 ++--- src/p_mobj.cpp | 4 +- src/p_pillar.cpp | 2 +- src/p_plats.cpp | 2 +- src/p_pspr.cpp | 2 +- src/p_pusher.cpp | 2 +- src/p_scroll.cpp | 2 +- src/p_spec.cpp | 4 +- src/p_switch.cpp | 2 +- src/p_teleport.cpp | 2 +- src/p_user.cpp | 6 +- src/po_man.cpp | 10 ++-- src/posix/sdl/sdlvideo.cpp | 3 +- src/r_data/r_interpolate.cpp | 10 ++-- src/s_advsound.cpp | 4 +- src/s_sndseq.cpp | 8 +-- src/scripting/decorate/olddecorations.cpp | 3 +- src/scripting/vm/vmframe.cpp | 8 +-- src/v_video.cpp | 8 +-- src/win32/fb_d3d9.cpp | 2 +- src/win32/fb_ddraw.cpp | 2 +- src/win32/win32video.cpp | 2 +- 126 files changed, 365 insertions(+), 388 deletions(-) diff --git a/src/b_bot.cpp b/src/b_bot.cpp index dee20d295..42b34f1df 100644 --- a/src/b_bot.cpp +++ b/src/b_bot.cpp @@ -15,7 +15,7 @@ #include "serializer.h" #include "d_player.h" -IMPLEMENT_POINTY_CLASS(DBot) +IMPLEMENT_CLASS(DBot, false, true, false) IMPLEMENT_POINTERS_START(DBot) IMPLEMENT_POINTER(dest) diff --git a/src/c_dispatch.cpp b/src/c_dispatch.cpp index c3fc9bae1..e7ccc8922 100644 --- a/src/c_dispatch.cpp +++ b/src/c_dispatch.cpp @@ -187,7 +187,7 @@ static const char *KeyConfCommands[] = // CODE -------------------------------------------------------------------- -IMPLEMENT_CLASS (DWaitingCommand) +IMPLEMENT_CLASS(DWaitingCommand, false, false, false) void DWaitingCommand::Serialize(FSerializer &arc) { @@ -225,7 +225,7 @@ void DWaitingCommand::Tick () } } -IMPLEMENT_CLASS (DStoredCommand) +IMPLEMENT_CLASS(DStoredCommand, false, false, false) DStoredCommand::DStoredCommand () { diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 4e2b326ff..afaf7001b 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -231,7 +231,7 @@ DehInfo deh = // from the original actor's defaults. The original actor is then changed to // spawn the new class. -IMPLEMENT_POINTY_CLASS(ADehackedPickup) +IMPLEMENT_CLASS(ADehackedPickup, false, true, false) IMPLEMENT_POINTERS_START(ADehackedPickup) IMPLEMENT_POINTER(RealPickup) diff --git a/src/decallib.cpp b/src/decallib.cpp index 2f7492516..626497062 100644 --- a/src/decallib.cpp +++ b/src/decallib.cpp @@ -119,7 +119,7 @@ protected: DDecalThinker () : DThinker (STAT_DECALTHINKER) {} }; -IMPLEMENT_POINTY_CLASS(DDecalThinker) +IMPLEMENT_CLASS(DDecalThinker, false, true, false) IMPLEMENT_POINTERS_START(DDecalThinker) IMPLEMENT_POINTER(TheDecal) @@ -1153,7 +1153,7 @@ FDecalAnimator::~FDecalAnimator () { } -IMPLEMENT_CLASS (DDecalFader) +IMPLEMENT_CLASS(DDecalFader, false, false, false) void DDecalFader::Serialize(FSerializer &arc) { @@ -1202,7 +1202,7 @@ DThinker *FDecalFaderAnim::CreateThinker (DBaseDecal *actor, side_t *wall) const return fader; } -IMPLEMENT_CLASS (DDecalStretcher) +IMPLEMENT_CLASS(DDecalStretcher, false, false, false) void DDecalStretcher::Serialize(FSerializer &arc) { @@ -1290,7 +1290,7 @@ void DDecalStretcher::Tick () } } -IMPLEMENT_CLASS (DDecalSlider) +IMPLEMENT_CLASS(DDecalSlider, false, false, false) void DDecalSlider::Serialize(FSerializer &arc) { @@ -1370,8 +1370,7 @@ FDecalAnimator *FDecalLib::FindAnimator (const char *name) return NULL; } - -IMPLEMENT_CLASS (DDecalColorer) +IMPLEMENT_CLASS(DDecalColorer, false, false, false) void DDecalColorer::Serialize(FSerializer &arc) { diff --git a/src/dobject.h b/src/dobject.h index 620bc8af3..dd0d40772 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -158,9 +158,9 @@ protected: \ # define _DECLARE_TI(cls) ClassReg * const cls::RegistrationInfoPtr __attribute__((section(SECTION_CREG))) = &cls::RegistrationInfo; #endif -#define _IMP_PCLASS(cls,ptrs,create, initn) \ +#define _IMP_PCLASS(cls, ptrs, create, initn) \ ClassReg cls::RegistrationInfo = {\ - NULL, \ + nullptr, \ #cls, \ &cls::Super::RegistrationInfo, \ ptrs, \ @@ -171,30 +171,9 @@ protected: \ _DECLARE_TI(cls) \ PClass *cls::StaticType() const { return RegistrationInfo.MyClass; } -#define _IMP_CREATE_OBJ(cls) \ - void cls::InPlaceConstructor(void *mem) { new((EInPlace *)mem) cls; } - -#define IMPLEMENT_POINTY_CLASS(cls) \ - _IMP_CREATE_OBJ(cls) \ - _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor, nullptr) \ - -#define IMPLEMENT_POINTY_CLASS_WITH_FIELDS(cls) \ - _IMP_CREATE_OBJ(cls) \ - _IMP_PCLASS(cls,cls::PointerOffsets,cls::InPlaceConstructor, cls::InitNativeFields) \ - -#define IMPLEMENT_CLASS(cls) \ - _IMP_CREATE_OBJ(cls) \ - _IMP_PCLASS(cls,nullptr,cls::InPlaceConstructor, nullptr) - -#define IMPLEMENT_CLASS_WITH_FIELDS(cls) \ - _IMP_CREATE_OBJ(cls) \ - _IMP_PCLASS(cls,nullptr,cls::InPlaceConstructor, cls::InitNativeFields) - -#define IMPLEMENT_ABSTRACT_CLASS(cls) \ - _IMP_PCLASS(cls,nullptr,nullptr,nullptr) - -#define IMPLEMENT_ABSTRACT_POINTY_CLASS(cls) \ - _IMP_PCLASS(cls,cls::PointerOffsets,nullptr,nullptr) \ +#define IMPLEMENT_CLASS(cls, isabstract, ptrs, fields) \ + _X_CONSTRUCTOR_##isabstract##(cls) \ + _IMP_PCLASS(cls, _X_POINTERS_##ptrs##(cls), _X_ABSTRACT_##isabstract##(cls), _X_FIELDS_##fields##(cls)) // Taking the address of a field in an object at address 1 instead of // address 0 keeps GCC from complaining about possible misuse of offsetof. @@ -202,6 +181,16 @@ protected: \ #define IMPLEMENT_POINTER(field) (size_t)&((ThisClass*)1)->field - 1, #define IMPLEMENT_POINTERS_END ~(size_t)0 }; +// Possible arguments for the IMPLEMENT_CLASS macro +#define _X_POINTERS_true(cls) cls::PointerOffsets +#define _X_POINTERS_false(cls) nullptr +#define _X_FIELDS_true(cls) cls::InitNativeFields +#define _X_FIELDS_false(cls) nullptr +#define _X_CONSTRUCTOR_true(cls) +#define _X_CONSTRUCTOR_false(cls) void cls::InPlaceConstructor(void *mem) { new((EInPlace *)mem) cls; } +#define _X_ABSTRACT_true(cls) nullptr +#define _X_ABSTRACT_false(cls) cls::InPlaceConstructor + enum EObjectFlags { // GC flags diff --git a/src/dobjgc.cpp b/src/dobjgc.cpp index 28715a0ec..fa59392d5 100644 --- a/src/dobjgc.cpp +++ b/src/dobjgc.cpp @@ -125,7 +125,8 @@ public: int PolyNum; int SideNum; }; -IMPLEMENT_CLASS(DSectorMarker) + +IMPLEMENT_CLASS(DSectorMarker, false, false, false) // EXTERNAL FUNCTION PROTOTYPES -------------------------------------------- diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index f9f987a42..9d3022966 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -93,8 +93,8 @@ static const size_t TheEnd = ~(size_t)0; // CODE -------------------------------------------------------------------- -IMPLEMENT_CLASS(PErrorType) -IMPLEMENT_CLASS(PVoidType) +IMPLEMENT_CLASS(PErrorType, false, false, false) +IMPLEMENT_CLASS(PVoidType, false, false, false) void DumpTypeTable() { @@ -141,7 +141,7 @@ void DumpTypeTable() /* PClassType *************************************************************/ -IMPLEMENT_CLASS(PClassType) +IMPLEMENT_CLASS(PClassType, false, false, false) //========================================================================== // @@ -169,7 +169,7 @@ void PClassType::Derive(PClass *newclass) /* PClassClass ************************************************************/ -IMPLEMENT_CLASS(PClassClass) +IMPLEMENT_CLASS(PClassClass, false, false, false) //========================================================================== // @@ -187,7 +187,7 @@ PClassClass::PClassClass() /* PType ******************************************************************/ -IMPLEMENT_ABSTRACT_POINTY_CLASS(PType) +IMPLEMENT_CLASS(PType, true, true, false) IMPLEMENT_POINTERS_START(PType) IMPLEMENT_POINTER(HashNext) @@ -614,7 +614,7 @@ void PType::StaticInit() /* PBasicType *************************************************************/ -IMPLEMENT_ABSTRACT_CLASS(PBasicType) +IMPLEMENT_CLASS(PBasicType, true, false, false) //========================================================================== // @@ -640,11 +640,11 @@ PBasicType::PBasicType(unsigned int size, unsigned int align) /* PCompoundType **********************************************************/ -IMPLEMENT_ABSTRACT_CLASS(PCompoundType) +IMPLEMENT_CLASS(PCompoundType, true, false, false) /* PNamedType *************************************************************/ -IMPLEMENT_ABSTRACT_POINTY_CLASS(PNamedType) +IMPLEMENT_CLASS(PNamedType, true, true, false) IMPLEMENT_POINTERS_START(PNamedType) IMPLEMENT_POINTER(Outer) @@ -692,7 +692,7 @@ FString PNamedType::QualifiedName() const /* PInt *******************************************************************/ -IMPLEMENT_CLASS(PInt) +IMPLEMENT_CLASS(PInt, false, false, false) //========================================================================== // @@ -931,7 +931,7 @@ double PInt::GetValueFloat(void *addr) const /* PBool ******************************************************************/ -IMPLEMENT_CLASS(PBool) +IMPLEMENT_CLASS(PBool, false, false, false) //========================================================================== // @@ -952,7 +952,7 @@ PBool::PBool() /* PFloat *****************************************************************/ -IMPLEMENT_CLASS(PFloat) +IMPLEMENT_CLASS(PFloat, false, false, false) //========================================================================== // @@ -1202,7 +1202,7 @@ void PFloat::SetOps() /* PString ****************************************************************/ -IMPLEMENT_CLASS(PString) +IMPLEMENT_CLASS(PString, false, false, false) //========================================================================== // @@ -1299,7 +1299,7 @@ void PString::DestroyValue(void *addr) const /* PName ******************************************************************/ -IMPLEMENT_CLASS(PName) +IMPLEMENT_CLASS(PName, false, false, false) //========================================================================== // @@ -1349,7 +1349,7 @@ bool PName::ReadValue(FSerializer &ar, const char *key, void *addr) const /* PSound *****************************************************************/ -IMPLEMENT_CLASS(PSound) +IMPLEMENT_CLASS(PSound, false, false, false) //========================================================================== // @@ -1399,7 +1399,7 @@ bool PSound::ReadValue(FSerializer &ar, const char *key, void *addr) const /* PColor *****************************************************************/ -IMPLEMENT_CLASS(PColor) +IMPLEMENT_CLASS(PColor, false, false, false) //========================================================================== // @@ -1416,7 +1416,7 @@ PColor::PColor() /* PStatePointer **********************************************************/ -IMPLEMENT_CLASS(PStatePointer) +IMPLEMENT_CLASS(PStatePointer, false, false, false) //========================================================================== // @@ -1460,7 +1460,7 @@ bool PStatePointer::ReadValue(FSerializer &ar, const char *key, void *addr) cons /* PPointer ***************************************************************/ -IMPLEMENT_POINTY_CLASS(PPointer) +IMPLEMENT_CLASS(PPointer, false, true, false) IMPLEMENT_POINTERS_START(PPointer) IMPLEMENT_POINTER(PointedType) @@ -1591,7 +1591,7 @@ PPointer *NewPointer(PType *type, bool isconst) /* PClassPointer **********************************************************/ -IMPLEMENT_POINTY_CLASS(PClassPointer) +IMPLEMENT_CLASS(PClassPointer, false, true, false) IMPLEMENT_POINTERS_START(PClassPointer) IMPLEMENT_POINTER(ClassRestriction) @@ -1672,7 +1672,7 @@ PClassPointer *NewClassPointer(PClass *restrict) /* PEnum ******************************************************************/ -IMPLEMENT_POINTY_CLASS(PEnum) +IMPLEMENT_CLASS(PEnum, false, true, false) IMPLEMENT_POINTERS_START(PEnum) IMPLEMENT_POINTER(ValueType) @@ -1725,7 +1725,7 @@ PEnum *NewEnum(FName name, PTypeBase *outer) /* PArray *****************************************************************/ -IMPLEMENT_POINTY_CLASS(PArray) +IMPLEMENT_CLASS(PArray, false, true, false) IMPLEMENT_POINTERS_START(PArray) IMPLEMENT_POINTER(ElementType) @@ -1874,7 +1874,7 @@ PArray *NewArray(PType *type, unsigned int count) /* PVector ****************************************************************/ -IMPLEMENT_CLASS(PVector) +IMPLEMENT_CLASS(PVector, false, false, false) //========================================================================== // @@ -1924,7 +1924,7 @@ PVector *NewVector(unsigned int size) /* PDynArray **************************************************************/ -IMPLEMENT_POINTY_CLASS(PDynArray) +IMPLEMENT_CLASS(PDynArray, false, true, false) IMPLEMENT_POINTERS_START(PDynArray) IMPLEMENT_POINTER(ElementType) @@ -2007,7 +2007,7 @@ PDynArray *NewDynArray(PType *type) /* PMap *******************************************************************/ -IMPLEMENT_POINTY_CLASS(PMap) +IMPLEMENT_CLASS(PMap, false, true, false) IMPLEMENT_POINTERS_START(PMap) IMPLEMENT_POINTER(KeyType) @@ -2091,7 +2091,7 @@ PMap *NewMap(PType *keytype, PType *valuetype) /* PStruct ****************************************************************/ -IMPLEMENT_CLASS(PStruct) +IMPLEMENT_CLASS(PStruct, false, false, false) //========================================================================== // @@ -2312,7 +2312,7 @@ PStruct *NewStruct(FName name, PTypeBase *outer) /* PField *****************************************************************/ -IMPLEMENT_CLASS(PField) +IMPLEMENT_CLASS(PField, false, false, false) //========================================================================== // @@ -2357,7 +2357,7 @@ PField::PField(FName name, PType *type, DWORD flags, size_t offset, int bitvalue /* PPrototype *************************************************************/ -IMPLEMENT_CLASS(PPrototype) +IMPLEMENT_CLASS(PPrototype, false, false, false) //========================================================================== // @@ -2443,7 +2443,7 @@ PPrototype *NewPrototype(const TArray &rettypes, const TArray /* PFunction **************************************************************/ -IMPLEMENT_CLASS(PFunction) +IMPLEMENT_CLASS(PFunction, false, false, false) //========================================================================== // @@ -2501,7 +2501,7 @@ unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArra /* PClass *****************************************************************/ -IMPLEMENT_POINTY_CLASS(PClass) +IMPLEMENT_CLASS(PClass, false, true, false) IMPLEMENT_POINTERS_START(PClass) IMPLEMENT_POINTER(ParentClass) @@ -3420,24 +3420,23 @@ CCMD(typetable) // Symbol tables ------------------------------------------------------------ -IMPLEMENT_ABSTRACT_CLASS(PTypeBase); -IMPLEMENT_ABSTRACT_CLASS(PSymbol); -IMPLEMENT_CLASS(PSymbolConst); -IMPLEMENT_CLASS(PSymbolConstNumeric); -IMPLEMENT_CLASS(PSymbolConstString); - -IMPLEMENT_POINTY_CLASS(PSymbolType) +IMPLEMENT_CLASS(PTypeBase, true, false, false); +IMPLEMENT_CLASS(PSymbol, true, false, false); +IMPLEMENT_CLASS(PSymbolConst, false, false, false); +IMPLEMENT_CLASS(PSymbolConstNumeric, false, false, false); +IMPLEMENT_CLASS(PSymbolConstString, false, false, false); +IMPLEMENT_CLASS(PSymbolTreeNode, false, false, false) +IMPLEMENT_CLASS(PSymbolType, false, true, false) IMPLEMENT_POINTERS_START(PSymbolType) IMPLEMENT_POINTER(Type) IMPLEMENT_POINTERS_END -IMPLEMENT_POINTY_CLASS(PSymbolVMFunction) +IMPLEMENT_CLASS(PSymbolVMFunction, false, true, false) IMPLEMENT_POINTERS_START(PSymbolVMFunction) IMPLEMENT_POINTER(Function) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(PSymbolTreeNode) //========================================================================== // diff --git a/src/dsectoreffect.cpp b/src/dsectoreffect.cpp index 7b29dbf05..e07f9eace 100644 --- a/src/dsectoreffect.cpp +++ b/src/dsectoreffect.cpp @@ -31,7 +31,7 @@ #include "serializer.h" #include "doomstat.h" -IMPLEMENT_CLASS (DSectorEffect) +IMPLEMENT_CLASS(DSectorEffect, false, false, false) DSectorEffect::DSectorEffect () : DThinker(STAT_SECTOREFFECT) @@ -71,7 +71,7 @@ void DSectorEffect::Serialize(FSerializer &arc) arc("sector", m_Sector); } -IMPLEMENT_POINTY_CLASS(DMover) +IMPLEMENT_CLASS(DMover, false, true, false) IMPLEMENT_POINTERS_START(DMover) IMPLEMENT_POINTER(interpolation) @@ -108,9 +108,7 @@ void DMover::StopInterpolation(bool force) } } - - -IMPLEMENT_CLASS (DMovingFloor) +IMPLEMENT_CLASS(DMovingFloor, false, false, false) DMovingFloor::DMovingFloor () { @@ -123,7 +121,7 @@ DMovingFloor::DMovingFloor (sector_t *sector) interpolation = sector->SetInterpolation(sector_t::FloorMove, true); } -IMPLEMENT_CLASS (DMovingCeiling) +IMPLEMENT_CLASS(DMovingCeiling, false, false, false) DMovingCeiling::DMovingCeiling () { diff --git a/src/dthinker.cpp b/src/dthinker.cpp index bacd53eee..246b9ed2c 100644 --- a/src/dthinker.cpp +++ b/src/dthinker.cpp @@ -47,7 +47,7 @@ extern cycle_t BotSupportCycles; extern cycle_t ActionCycles; extern int BotWTG; -IMPLEMENT_CLASS (DThinker) +IMPLEMENT_CLASS(DThinker, false, false, false) DThinker *NextToThink; @@ -538,7 +538,7 @@ public: } }; -IMPLEMENT_CLASS(DThinkerIterator); +IMPLEMENT_CLASS(DThinkerIterator, false, false, false); DEFINE_ACTION_FUNCTION(DThinkerIterator, Create) { PARAM_PROLOGUE; diff --git a/src/fragglescript/t_func.cpp b/src/fragglescript/t_func.cpp index 6d3102372..737376ecb 100644 --- a/src/fragglescript/t_func.cpp +++ b/src/fragglescript/t_func.cpp @@ -1785,9 +1785,7 @@ public: void Destroy() { Super::Destroy(); m_Sector->lightingdata=NULL; } }; - - -IMPLEMENT_CLASS (DLightLevel) +IMPLEMENT_CLASS(DLightLevel, false, false, false) void DLightLevel::Serialize(FSerializer &arc) { diff --git a/src/fragglescript/t_prepro.cpp b/src/fragglescript/t_prepro.cpp index 2c667878d..0a3ec6a0d 100644 --- a/src/fragglescript/t_prepro.cpp +++ b/src/fragglescript/t_prepro.cpp @@ -71,7 +71,7 @@ // //========================================================================== -IMPLEMENT_POINTY_CLASS(DFsSection) +IMPLEMENT_CLASS(DFsSection, false, true, false) IMPLEMENT_POINTERS_START(DFsSection) IMPLEMENT_POINTER(next) diff --git a/src/fragglescript/t_script.cpp b/src/fragglescript/t_script.cpp index f14cbe25f..326cad621 100644 --- a/src/fragglescript/t_script.cpp +++ b/src/fragglescript/t_script.cpp @@ -99,7 +99,7 @@ AActor *trigger_obj; // //========================================================================== -IMPLEMENT_POINTY_CLASS(DFsScript) +IMPLEMENT_CLASS(DFsScript, false, true, false) IMPLEMENT_POINTERS_START(DFsScript) IMPLEMENT_POINTER(parent) @@ -269,7 +269,7 @@ void DFsScript::ParseScript(char *position) // //========================================================================== -IMPLEMENT_POINTY_CLASS(DRunningScript) +IMPLEMENT_CLASS(DRunningScript, false, true, false) IMPLEMENT_POINTERS_START(DRunningScript) IMPLEMENT_POINTER(prev) @@ -380,7 +380,7 @@ void DRunningScript::Serialize(FSerializer &arc) // //========================================================================== -IMPLEMENT_POINTY_CLASS(DFraggleThinker) +IMPLEMENT_CLASS(DFraggleThinker, false, true, false) IMPLEMENT_POINTERS_START(DFraggleThinker) IMPLEMENT_POINTER(RunningScripts) diff --git a/src/fragglescript/t_variable.cpp b/src/fragglescript/t_variable.cpp index 895602f53..cebf0160c 100644 --- a/src/fragglescript/t_variable.cpp +++ b/src/fragglescript/t_variable.cpp @@ -179,7 +179,7 @@ AActor* actorvalue(const svalue_t &svalue) // //========================================================================== -IMPLEMENT_POINTY_CLASS(DFsVariable) +IMPLEMENT_CLASS(DFsVariable, false, true, false) IMPLEMENT_POINTERS_START(DFsVariable) IMPLEMENT_POINTER(next) diff --git a/src/g_doom/a_scriptedmarine.cpp b/src/g_doom/a_scriptedmarine.cpp index 4bf828342..134271395 100644 --- a/src/g_doom/a_scriptedmarine.cpp +++ b/src/g_doom/a_scriptedmarine.cpp @@ -19,7 +19,7 @@ static FRandom pr_m_gunshot ("SMarineGunshot"); static FRandom pr_m_saw ("SMarineSaw"); static FRandom pr_m_fireshotgun2 ("SMarineFireSSG"); -IMPLEMENT_CLASS (AScriptedMarine) +IMPLEMENT_CLASS(AScriptedMarine, false, false, false) void AScriptedMarine::Serialize(FSerializer &arc) { diff --git a/src/g_heretic/a_chicken.cpp b/src/g_heretic/a_chicken.cpp index 883eac353..762d10594 100644 --- a/src/g_heretic/a_chicken.cpp +++ b/src/g_heretic/a_chicken.cpp @@ -29,7 +29,7 @@ public: void MorphPlayerThink (); }; -IMPLEMENT_CLASS(AChickenPlayer) +IMPLEMENT_CLASS(AChickenPlayer, false, false, false) void AChickenPlayer::MorphPlayerThink () { diff --git a/src/g_heretic/a_hereticartifacts.cpp b/src/g_heretic/a_hereticartifacts.cpp index eceb2cfe1..9078d0940 100644 --- a/src/g_heretic/a_hereticartifacts.cpp +++ b/src/g_heretic/a_hereticartifacts.cpp @@ -17,8 +17,7 @@ public: bool Use (bool pickup); }; - -IMPLEMENT_CLASS (AArtiTomeOfPower) +IMPLEMENT_CLASS(AArtiTomeOfPower, false, false, false) bool AArtiTomeOfPower::Use (bool pickup) { @@ -64,8 +63,7 @@ public: bool Use (bool pickup); }; - -IMPLEMENT_CLASS (AArtiTimeBomb) +IMPLEMENT_CLASS(AArtiTimeBomb, false, false, false) bool AArtiTimeBomb::Use (bool pickup) { diff --git a/src/g_heretic/a_hereticweaps.cpp b/src/g_heretic/a_hereticweaps.cpp index 51d759640..b32056374 100644 --- a/src/g_heretic/a_hereticweaps.cpp +++ b/src/g_heretic/a_hereticweaps.cpp @@ -358,7 +358,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (AMaceFX4) +IMPLEMENT_CLASS(AMaceFX4, false, false, false) int AMaceFX4::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -726,7 +726,7 @@ void ABlasterFX1::Effect () } } -IMPLEMENT_CLASS(ABlasterFX1) +IMPLEMENT_CLASS(ABlasterFX1, false, false, false) // Ripper ------------------------------------------------------------------- @@ -738,7 +738,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(ARipper) +IMPLEMENT_CLASS(ARipper, false, false, false) int ARipper::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -828,7 +828,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (AHornRodFX2) +IMPLEMENT_CLASS(AHornRodFX2, false, false, false) int AHornRodFX2::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -849,7 +849,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (ARainPillar) +IMPLEMENT_CLASS(ARainPillar, false, false, false) int ARainPillar::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -871,7 +871,7 @@ public: TObjPtr Rain1, Rain2; }; -IMPLEMENT_CLASS (ARainTracker) +IMPLEMENT_CLASS(ARainTracker, false, false, false) void ARainTracker::Serialize(FSerializer &arc) { @@ -1158,8 +1158,8 @@ public: void EndPowerup (); }; -IMPLEMENT_CLASS (APhoenixRod) -IMPLEMENT_CLASS (APhoenixRodPowered) +IMPLEMENT_CLASS(APhoenixRod, false, false, false) +IMPLEMENT_CLASS(APhoenixRodPowered, false, false, false) void APhoenixRodPowered::EndPowerup () { @@ -1177,8 +1177,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; - -IMPLEMENT_CLASS (APhoenixFX1) +IMPLEMENT_CLASS(APhoenixFX1, false, false, false) int APhoenixFX1::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -1199,7 +1198,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (APhoenixFX2) +IMPLEMENT_CLASS(APhoenixFX2, false, false, false) int APhoenixFX2::DoSpecialDamage (AActor *target, int damage, FName damagetype) { diff --git a/src/g_heretic/a_ironlich.cpp b/src/g_heretic/a_ironlich.cpp index e2e1cb021..3870219d9 100644 --- a/src/g_heretic/a_ironlich.cpp +++ b/src/g_heretic/a_ironlich.cpp @@ -22,7 +22,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AWhirlwind) +IMPLEMENT_CLASS(AWhirlwind, false, false, false) int AWhirlwind::DoSpecialDamage (AActor *target, int damage, FName damagetype) { diff --git a/src/g_hexen/a_boostarmor.cpp b/src/g_hexen/a_boostarmor.cpp index 3234174f3..77fbf3dbd 100644 --- a/src/g_hexen/a_boostarmor.cpp +++ b/src/g_hexen/a_boostarmor.cpp @@ -17,7 +17,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiBoostArmor) +IMPLEMENT_CLASS(AArtiBoostArmor, false, false, false) bool AArtiBoostArmor::Use (bool pickup) { diff --git a/src/g_hexen/a_clericflame.cpp b/src/g_hexen/a_clericflame.cpp index 56267b8e6..c0c6cb3ed 100644 --- a/src/g_hexen/a_clericflame.cpp +++ b/src/g_hexen/a_clericflame.cpp @@ -33,7 +33,7 @@ public: void Effect (); }; -IMPLEMENT_CLASS (ACFlameMissile) +IMPLEMENT_CLASS(ACFlameMissile, false, false, false) void ACFlameMissile::BeginPlay () { diff --git a/src/g_hexen/a_clericholy.cpp b/src/g_hexen/a_clericholy.cpp index b87bd3986..931c75e89 100644 --- a/src/g_hexen/a_clericholy.cpp +++ b/src/g_hexen/a_clericholy.cpp @@ -58,11 +58,11 @@ public: BYTE CHolyCount; }; -IMPLEMENT_CLASS (ACWeapWraithverge) +IMPLEMENT_CLASS(ACWeapWraithverge, false, false, false) // Holy Spirit -------------------------------------------------------------- -IMPLEMENT_CLASS (AHolySpirit) +IMPLEMENT_CLASS(AHolySpirit, false, false, false) bool AHolySpirit::Slam(AActor *thing) { diff --git a/src/g_hexen/a_clericstaff.cpp b/src/g_hexen/a_clericstaff.cpp index a0e6b94c6..940a87884 100644 --- a/src/g_hexen/a_clericstaff.cpp +++ b/src/g_hexen/a_clericstaff.cpp @@ -25,7 +25,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (ACStaffMissile) +IMPLEMENT_CLASS(ACStaffMissile, false, false, false) int ACStaffMissile::DoSpecialDamage (AActor *target, int damage, FName damagetype) { diff --git a/src/g_hexen/a_fighteraxe.cpp b/src/g_hexen/a_fighteraxe.cpp index 696dda019..89e317012 100644 --- a/src/g_hexen/a_fighteraxe.cpp +++ b/src/g_hexen/a_fighteraxe.cpp @@ -38,7 +38,7 @@ public: FState *GetAtkState (bool hold); }; -IMPLEMENT_CLASS (AFWeapAxe) +IMPLEMENT_CLASS(AFWeapAxe, false, false, false) FState *AFWeapAxe::GetUpState () { diff --git a/src/g_hexen/a_fighterplayer.cpp b/src/g_hexen/a_fighterplayer.cpp index 020cec78e..7e18f9c28 100644 --- a/src/g_hexen/a_fighterplayer.cpp +++ b/src/g_hexen/a_fighterplayer.cpp @@ -11,9 +11,9 @@ #include "vm.h" */ -IMPLEMENT_CLASS (AFighterWeapon) -IMPLEMENT_CLASS (AClericWeapon) -IMPLEMENT_CLASS (AMageWeapon) +IMPLEMENT_CLASS(AFighterWeapon, false, false, false) +IMPLEMENT_CLASS(AClericWeapon, false, false, false) +IMPLEMENT_CLASS(AMageWeapon, false, false, false) static FRandom pr_fpatk ("FPunchAttack"); diff --git a/src/g_hexen/a_fighterquietus.cpp b/src/g_hexen/a_fighterquietus.cpp index 6a4daabb2..c000a9faf 100644 --- a/src/g_hexen/a_fighterquietus.cpp +++ b/src/g_hexen/a_fighterquietus.cpp @@ -59,7 +59,7 @@ public: int DoSpecialDamage(AActor *victim, int damage, FName damagetype); }; -IMPLEMENT_CLASS (AFSwordMissile) +IMPLEMENT_CLASS(AFSwordMissile, false, false, false) int AFSwordMissile::DoSpecialDamage(AActor *victim, int damage, FName damagetype) { diff --git a/src/g_hexen/a_flechette.cpp b/src/g_hexen/a_flechette.cpp index bc13d5cf7..3da16db9c 100644 --- a/src/g_hexen/a_flechette.cpp +++ b/src/g_hexen/a_flechette.cpp @@ -24,7 +24,7 @@ DECLARE_ACTION(A_CheckThrowBomb) // Poison Bag Artifact (Flechette) ------------------------------------------ -IMPLEMENT_CLASS (AArtiPoisonBag) +IMPLEMENT_CLASS(AArtiPoisonBag, false, false, false) // Poison Bag 1 (The Cleric's) ---------------------------------------------- @@ -35,7 +35,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiPoisonBag1) +IMPLEMENT_CLASS(AArtiPoisonBag1, false, false, false) bool AArtiPoisonBag1::Use (bool pickup) { @@ -60,7 +60,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiPoisonBag2) +IMPLEMENT_CLASS(AArtiPoisonBag2, false, false, false) bool AArtiPoisonBag2::Use (bool pickup) { @@ -85,7 +85,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiPoisonBag3) +IMPLEMENT_CLASS(AArtiPoisonBag3, false, false, false) bool AArtiPoisonBag3::Use (bool pickup) { @@ -136,7 +136,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiPoisonBagGiver) +IMPLEMENT_CLASS(AArtiPoisonBagGiver, false, false, false) bool AArtiPoisonBagGiver::Use (bool pickup) { @@ -167,7 +167,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiPoisonBagShooter) +IMPLEMENT_CLASS(AArtiPoisonBagShooter, false, false, false) bool AArtiPoisonBagShooter::Use (bool pickup) { @@ -296,7 +296,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS (APoisonCloud) +IMPLEMENT_CLASS(APoisonCloud, false, false, false) void APoisonCloud::BeginPlay () { diff --git a/src/g_hexen/a_healingradius.cpp b/src/g_hexen/a_healingradius.cpp index c381f3964..3d4eef0ae 100644 --- a/src/g_hexen/a_healingradius.cpp +++ b/src/g_hexen/a_healingradius.cpp @@ -25,7 +25,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiHealingRadius) +IMPLEMENT_CLASS(AArtiHealingRadius, false, false, false) bool AArtiHealingRadius::Use (bool pickup) { diff --git a/src/g_hexen/a_heresiarch.cpp b/src/g_hexen/a_heresiarch.cpp index 03ffcc5d6..964fdd44f 100644 --- a/src/g_hexen/a_heresiarch.cpp +++ b/src/g_hexen/a_heresiarch.cpp @@ -72,7 +72,7 @@ public: void Die (AActor *source, AActor *inflictor, int dmgflags); }; -IMPLEMENT_CLASS (AHeresiarch) +IMPLEMENT_CLASS(AHeresiarch, false, false, false) void AHeresiarch::Serialize(FSerializer &arc) { @@ -122,7 +122,7 @@ public: } }; -IMPLEMENT_CLASS (ASorcBall) +IMPLEMENT_CLASS(ASorcBall, false, false, false) // First ball (purple) - fires projectiles ---------------------------------- @@ -140,7 +140,7 @@ public: virtual void CastSorcererSpell (); }; -IMPLEMENT_CLASS (ASorcBall1) +IMPLEMENT_CLASS(ASorcBall1, false, false, false) // Second ball (blue) - generates the shield -------------------------------- @@ -156,7 +156,7 @@ public: virtual void CastSorcererSpell (); }; -IMPLEMENT_CLASS (ASorcBall2) +IMPLEMENT_CLASS(ASorcBall2, false, false, false) // Third ball (green) - summons Bishops ------------------------------------- @@ -172,7 +172,7 @@ public: virtual void CastSorcererSpell (); }; -IMPLEMENT_CLASS (ASorcBall3) +IMPLEMENT_CLASS(ASorcBall3, false, false, false) // Sorcerer spell 1 (The burning, bouncing head thing) ---------------------- diff --git a/src/g_hexen/a_hexenspecialdecs.cpp b/src/g_hexen/a_hexenspecialdecs.cpp index 866fc8372..cad6f617d 100644 --- a/src/g_hexen/a_hexenspecialdecs.cpp +++ b/src/g_hexen/a_hexenspecialdecs.cpp @@ -39,7 +39,7 @@ public: void HitFloor (); }; -IMPLEMENT_CLASS (APottery1) +IMPLEMENT_CLASS(APottery1, false, false, false) void APottery1::HitFloor () { @@ -136,7 +136,7 @@ public: void PostBeginPlay (); }; -IMPLEMENT_CLASS (AZCorpseLynchedNoHeart) +IMPLEMENT_CLASS(AZCorpseLynchedNoHeart, false, false, false) void AZCorpseLynchedNoHeart::PostBeginPlay () { @@ -344,7 +344,7 @@ public: void Activate (AActor *activator); }; -IMPLEMENT_CLASS (AZBell) +IMPLEMENT_CLASS(AZBell, false, false, false) void AZBell::Activate (AActor *activator) { diff --git a/src/g_hexen/a_magecone.cpp b/src/g_hexen/a_magecone.cpp index 57e68c16f..b2dd969b7 100644 --- a/src/g_hexen/a_magecone.cpp +++ b/src/g_hexen/a_magecone.cpp @@ -32,7 +32,7 @@ public: int DoSpecialDamage (AActor *victim, int damage, FName damagetype); }; -IMPLEMENT_CLASS (AFrostMissile) +IMPLEMENT_CLASS(AFrostMissile, false, false, false) int AFrostMissile::DoSpecialDamage (AActor *victim, int damage, FName damagetype) { diff --git a/src/g_hexen/a_magelightning.cpp b/src/g_hexen/a_magelightning.cpp index 192fd03e0..039755ff5 100644 --- a/src/g_hexen/a_magelightning.cpp +++ b/src/g_hexen/a_magelightning.cpp @@ -34,7 +34,7 @@ public: int SpecialMissileHit (AActor *victim); }; -IMPLEMENT_CLASS(ALightning) +IMPLEMENT_CLASS(ALightning, false, false, false) int ALightning::SpecialMissileHit (AActor *thing) { @@ -87,7 +87,7 @@ public: int SpecialMissileHit (AActor *thing); }; -IMPLEMENT_CLASS (ALightningZap) +IMPLEMENT_CLASS(ALightningZap, false, false, false) int ALightningZap::SpecialMissileHit (AActor *thing) { diff --git a/src/g_hexen/a_magestaff.cpp b/src/g_hexen/a_magestaff.cpp index 710af8198..2660117c3 100644 --- a/src/g_hexen/a_magestaff.cpp +++ b/src/g_hexen/a_magestaff.cpp @@ -56,7 +56,7 @@ public: BYTE MStaffCount; }; -IMPLEMENT_CLASS (AMWeapBloodscourge) +IMPLEMENT_CLASS(AMWeapBloodscourge, false, false, false) // Mage Staff FX2 (Bloodscourge) -------------------------------------------- @@ -68,7 +68,7 @@ public: bool SpecialBlastHandling (AActor *source, double strength); }; -IMPLEMENT_CLASS (AMageStaffFX2) +IMPLEMENT_CLASS(AMageStaffFX2, false, false, false) int AMageStaffFX2::SpecialMissileHit (AActor *victim) { diff --git a/src/g_hexen/a_pig.cpp b/src/g_hexen/a_pig.cpp index cafcbcda3..c12a9f50a 100644 --- a/src/g_hexen/a_pig.cpp +++ b/src/g_hexen/a_pig.cpp @@ -27,7 +27,7 @@ public: void MorphPlayerThink (); }; -IMPLEMENT_CLASS (APigPlayer) +IMPLEMENT_CLASS(APigPlayer, false, false, false) void APigPlayer::MorphPlayerThink () { diff --git a/src/g_hexen/a_spike.cpp b/src/g_hexen/a_spike.cpp index faf3c3083..1559467db 100644 --- a/src/g_hexen/a_spike.cpp +++ b/src/g_hexen/a_spike.cpp @@ -31,7 +31,7 @@ public: TObjPtr DirtClump; }; -IMPLEMENT_POINTY_CLASS(AThrustFloor) +IMPLEMENT_CLASS(AThrustFloor, false, true, false) IMPLEMENT_POINTERS_START(AThrustFloor) IMPLEMENT_POINTER(DirtClump) diff --git a/src/g_hexen/a_summon.cpp b/src/g_hexen/a_summon.cpp index e1b2bae09..e98c52352 100644 --- a/src/g_hexen/a_summon.cpp +++ b/src/g_hexen/a_summon.cpp @@ -21,7 +21,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiDarkServant) +IMPLEMENT_CLASS(AArtiDarkServant, false, false, false) //============================================================================ // diff --git a/src/g_hexen/a_teleportother.cpp b/src/g_hexen/a_teleportother.cpp index 99d6876a5..68ba73bc4 100644 --- a/src/g_hexen/a_teleportother.cpp +++ b/src/g_hexen/a_teleportother.cpp @@ -34,7 +34,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiTeleportOther) +IMPLEMENT_CLASS(AArtiTeleportOther, false, false, false) // Teleport Other FX -------------------------------------------------------- @@ -45,7 +45,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (ATelOtherFX1) +IMPLEMENT_CLASS(ATelOtherFX1, false, false, false) static void TeloSpawn (AActor *source, const char *type) { diff --git a/src/g_level.cpp b/src/g_level.cpp index b13a39e20..e377d70f6 100644 --- a/src/g_level.cpp +++ b/src/g_level.cpp @@ -903,7 +903,7 @@ public: void Tick (); }; -IMPLEMENT_CLASS (DAutosaver) +IMPLEMENT_CLASS(DAutosaver, false, false, false) void DAutosaver::Tick () { diff --git a/src/g_raven/a_artitele.cpp b/src/g_raven/a_artitele.cpp index 9a43f8518..0910e5f23 100644 --- a/src/g_raven/a_artitele.cpp +++ b/src/g_raven/a_artitele.cpp @@ -23,7 +23,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AArtiTeleport) +IMPLEMENT_CLASS(AArtiTeleport, false, false, false) bool AArtiTeleport::Use (bool pickup) { diff --git a/src/g_raven/a_minotaur.cpp b/src/g_raven/a_minotaur.cpp index 209afc9f4..c906234c8 100644 --- a/src/g_raven/a_minotaur.cpp +++ b/src/g_raven/a_minotaur.cpp @@ -31,7 +31,7 @@ void P_MinotaurSlam (AActor *source, AActor *target); DECLARE_ACTION(A_MinotaurLook) -IMPLEMENT_CLASS(AMinotaur) +IMPLEMENT_CLASS(AMinotaur, false, false, false) void AMinotaur::Tick () { @@ -72,7 +72,7 @@ int AMinotaur::DoSpecialDamage (AActor *target, int damage, FName damagetype) // Minotaur Friend ---------------------------------------------------------- -IMPLEMENT_CLASS(AMinotaurFriend) +IMPLEMENT_CLASS(AMinotaurFriend, false, false, false) void AMinotaurFriend::BeginPlay () { diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index 4925e3c25..20ab4aad0 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -29,7 +29,7 @@ public: void Deactivate (AActor *activator); }; -IMPLEMENT_CLASS (ASwitchableDecoration) +IMPLEMENT_CLASS(ASwitchableDecoration, false, false, false) void ASwitchableDecoration::Activate (AActor *activator) { @@ -50,7 +50,7 @@ public: void Deactivate (AActor *activator) {} }; -IMPLEMENT_CLASS (ASwitchingDecoration) +IMPLEMENT_CLASS(ASwitchingDecoration, false, false, false) //---------------------------------------------------------------------------- // @@ -304,7 +304,7 @@ private: DCorpsePointer () {} }; -IMPLEMENT_POINTY_CLASS(DCorpsePointer) +IMPLEMENT_CLASS(DCorpsePointer, false, true, false) IMPLEMENT_POINTERS_START(DCorpsePointer) IMPLEMENT_POINTER(Corpse) diff --git a/src/g_shared/a_armor.cpp b/src/g_shared/a_armor.cpp index 50472e51d..b1935bd1d 100644 --- a/src/g_shared/a_armor.cpp +++ b/src/g_shared/a_armor.cpp @@ -8,12 +8,11 @@ #include "d_player.h" #include "serializer.h" - -IMPLEMENT_CLASS (AArmor) -IMPLEMENT_CLASS (ABasicArmor) -IMPLEMENT_CLASS (ABasicArmorPickup) -IMPLEMENT_CLASS (ABasicArmorBonus) -IMPLEMENT_CLASS (AHexenArmor) +IMPLEMENT_CLASS(AArmor, false, false, false) +IMPLEMENT_CLASS(ABasicArmor, false, false, false) +IMPLEMENT_CLASS(ABasicArmorPickup, false, false, false) +IMPLEMENT_CLASS(ABasicArmorBonus, false, false, false) +IMPLEMENT_CLASS(AHexenArmor, false, false, false) //=========================================================================== // diff --git a/src/g_shared/a_artifacts.cpp b/src/g_shared/a_artifacts.cpp index 7e4970e04..97771021d 100644 --- a/src/g_shared/a_artifacts.cpp +++ b/src/g_shared/a_artifacts.cpp @@ -40,11 +40,11 @@ static FRandom pr_torch ("Torch"); #define TIMEFREEZE_TICS ( 12 * TICRATE ) */ -IMPLEMENT_CLASS (APowerup) +IMPLEMENT_CLASS(APowerup, false, false, false) // Powerup-Giver ------------------------------------------------------------- -IMPLEMENT_CLASS(PClassPowerupGiver) +IMPLEMENT_CLASS(PClassPowerupGiver, false, false, false) void PClassPowerupGiver::ReplaceClassRef(PClass *oldclass, PClass *newclass) { @@ -376,7 +376,7 @@ bool APowerup::GetNoTeleportFreeze () // Invulnerability Powerup --------------------------------------------------- -IMPLEMENT_CLASS (APowerInvulnerable) +IMPLEMENT_CLASS(APowerInvulnerable, false, false, false) //=========================================================================== // @@ -513,7 +513,7 @@ int APowerInvulnerable::AlterWeaponSprite (visstyle_t *vis) // Strength (aka Berserk) Powerup -------------------------------------------- -IMPLEMENT_CLASS (APowerStrength) +IMPLEMENT_CLASS(APowerStrength, false, false, false) //=========================================================================== // @@ -578,7 +578,7 @@ PalEntry APowerStrength::GetBlend () // Invisibility Powerup ------------------------------------------------------ -IMPLEMENT_CLASS (APowerInvisibility) +IMPLEMENT_CLASS(APowerInvisibility, false, false, false) // Invisibility flag combos #define INVISIBILITY_FLAGS1 (MF_SHADOW) @@ -783,7 +783,7 @@ bool APowerInvisibility::HandlePickup (AInventory *item) // Ironfeet Powerup ---------------------------------------------------------- -IMPLEMENT_CLASS (APowerIronFeet) +IMPLEMENT_CLASS(APowerIronFeet, false, false, false) //=========================================================================== // @@ -820,7 +820,7 @@ void APowerIronFeet::DoEffect () // Strife Environment Suit Powerup ------------------------------------------- -IMPLEMENT_CLASS (APowerMask) +IMPLEMENT_CLASS(APowerMask, false, false, false) //=========================================================================== // @@ -857,7 +857,7 @@ void APowerMask::DoEffect () // Light-Amp Powerup --------------------------------------------------------- -IMPLEMENT_CLASS (APowerLightAmp) +IMPLEMENT_CLASS(APowerLightAmp, false, false, false) //=========================================================================== // @@ -899,7 +899,7 @@ void APowerLightAmp::EndEffect () // Torch Powerup ------------------------------------------------------------- -IMPLEMENT_CLASS (APowerTorch) +IMPLEMENT_CLASS(APowerTorch, false, false, false) //=========================================================================== // @@ -962,7 +962,7 @@ void APowerTorch::DoEffect () // Flight (aka Wings of Wrath) powerup --------------------------------------- -IMPLEMENT_CLASS (APowerFlight) +IMPLEMENT_CLASS(APowerFlight, false, false, false) //=========================================================================== // @@ -1102,7 +1102,7 @@ bool APowerFlight::DrawPowerup (int x, int y) // Weapon Level 2 (aka Tome of Power) Powerup -------------------------------- -IMPLEMENT_CLASS (APowerWeaponLevel2) +IMPLEMENT_CLASS(APowerWeaponLevel2, false, false, false) //=========================================================================== // @@ -1193,7 +1193,7 @@ public: void Tick (); }; -IMPLEMENT_CLASS (APlayerSpeedTrail) +IMPLEMENT_CLASS(APlayerSpeedTrail, false, false, false) //=========================================================================== // @@ -1216,7 +1216,7 @@ void APlayerSpeedTrail::Tick () // Speed Powerup ------------------------------------------------------------- -IMPLEMENT_CLASS (APowerSpeed) +IMPLEMENT_CLASS(APowerSpeed, false, false, false) //=========================================================================== // @@ -1303,11 +1303,11 @@ void APowerSpeed::DoEffect () // Minotaur (aka Dark Servant) powerup --------------------------------------- -IMPLEMENT_CLASS (APowerMinotaur) +IMPLEMENT_CLASS(APowerMinotaur, false, false, false) // Targeter powerup --------------------------------------------------------- -IMPLEMENT_CLASS (APowerTargeter) +IMPLEMENT_CLASS(APowerTargeter, false, false, false) void APowerTargeter::Travelled () { @@ -1422,7 +1422,7 @@ void APowerTargeter::PositionAccuracy () // Frightener Powerup -------------------------------- -IMPLEMENT_CLASS (APowerFrightener) +IMPLEMENT_CLASS(APowerFrightener, false, false, false) //=========================================================================== // @@ -1458,7 +1458,7 @@ void APowerFrightener::EndEffect () // Buddha Powerup -------------------------------- -IMPLEMENT_CLASS (APowerBuddha) +IMPLEMENT_CLASS(APowerBuddha, false, false, false) //=========================================================================== // @@ -1494,11 +1494,11 @@ void APowerBuddha::EndEffect () // Scanner powerup ---------------------------------------------------------- -IMPLEMENT_CLASS (APowerScanner) +IMPLEMENT_CLASS(APowerScanner, false, false, false) // Time freezer powerup ----------------------------------------------------- -IMPLEMENT_CLASS( APowerTimeFreezer) +IMPLEMENT_CLASS( APowerTimeFreezer, false, false, false) //=========================================================================== // @@ -1625,7 +1625,7 @@ void APowerTimeFreezer::EndEffect() // Damage powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerDamage) +IMPLEMENT_CLASS(APowerDamage, false, false, false) //=========================================================================== // @@ -1682,7 +1682,7 @@ void APowerDamage::ModifyDamage(int damage, FName damageType, int &newdamage, bo // Quarter damage powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerProtection) +IMPLEMENT_CLASS(APowerProtection, false, false, false) #define PROTECTION_FLAGS3 (MF3_NORADIUSDMG | MF3_DONTMORPH | MF3_DONTSQUASH | MF3_DONTBLAST | MF3_NOTELEOTHER) #define PROTECTION_FLAGS5 (MF5_NOPAIN | MF5_DONTRIP) @@ -1760,7 +1760,7 @@ void APowerProtection::ModifyDamage(int damage, FName damageType, int &newdamage // Drain rune ------------------------------------------------------- -IMPLEMENT_CLASS(APowerDrain) +IMPLEMENT_CLASS(APowerDrain, false, false, false) //=========================================================================== // @@ -1800,7 +1800,7 @@ void APowerDrain::EndEffect( ) // Regeneration rune ------------------------------------------------------- -IMPLEMENT_CLASS(APowerRegeneration) +IMPLEMENT_CLASS(APowerRegeneration, false, false, false) //=========================================================================== // @@ -1822,7 +1822,7 @@ void APowerRegeneration::DoEffect() // High jump rune ------------------------------------------------------- -IMPLEMENT_CLASS(APowerHighJump) +IMPLEMENT_CLASS(APowerHighJump, false, false, false) //=========================================================================== // @@ -1860,7 +1860,7 @@ void APowerHighJump::EndEffect( ) // Double firing speed rune --------------------------------------------- -IMPLEMENT_CLASS(APowerDoubleFiringSpeed) +IMPLEMENT_CLASS(APowerDoubleFiringSpeed, false, false, false) //=========================================================================== // @@ -1898,7 +1898,7 @@ void APowerDoubleFiringSpeed::EndEffect( ) // Morph powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerMorph) +IMPLEMENT_CLASS(APowerMorph, false, false, false) //=========================================================================== // @@ -2002,7 +2002,7 @@ void APowerMorph::EndEffect( ) // Infinite Ammo Powerup ----------------------------------------------------- -IMPLEMENT_CLASS(APowerInfiniteAmmo) +IMPLEMENT_CLASS(APowerInfiniteAmmo, false, false, false) //=========================================================================== // diff --git a/src/g_shared/a_bridge.cpp b/src/g_shared/a_bridge.cpp index 3cd7ee172..6409a0709 100644 --- a/src/g_shared/a_bridge.cpp +++ b/src/g_shared/a_bridge.cpp @@ -41,7 +41,7 @@ public: void Destroy(); }; -IMPLEMENT_CLASS(ACustomBridge) +IMPLEMENT_CLASS(ACustomBridge, false, false, false) void ACustomBridge::BeginPlay () { @@ -156,7 +156,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS(AInvisibleBridge) +IMPLEMENT_CLASS(AInvisibleBridge, false, false, false) void AInvisibleBridge::BeginPlay () { diff --git a/src/g_shared/a_camera.cpp b/src/g_shared/a_camera.cpp index fb3d81533..a29b4b81d 100644 --- a/src/g_shared/a_camera.cpp +++ b/src/g_shared/a_camera.cpp @@ -64,7 +64,7 @@ protected: DAngle Range; }; -IMPLEMENT_CLASS (ASecurityCamera) +IMPLEMENT_CLASS(ASecurityCamera, false, false, false) void ASecurityCamera::Serialize(FSerializer &arc) { @@ -124,7 +124,7 @@ protected: DAngle MaxPitchChange; }; -IMPLEMENT_CLASS (AAimingCamera) +IMPLEMENT_CLASS(AAimingCamera, false, false, false) void AAimingCamera::Serialize(FSerializer &arc) { diff --git a/src/g_shared/a_debris.cpp b/src/g_shared/a_debris.cpp index 895c3b170..9624ff5d6 100644 --- a/src/g_shared/a_debris.cpp +++ b/src/g_shared/a_debris.cpp @@ -25,7 +25,7 @@ public: } }; -IMPLEMENT_CLASS(AGlassShard) +IMPLEMENT_CLASS(AGlassShard, false, false, false) // Dirt stuff diff --git a/src/g_shared/a_decals.cpp b/src/g_shared/a_decals.cpp index b06191607..5347664f5 100644 --- a/src/g_shared/a_decals.cpp +++ b/src/g_shared/a_decals.cpp @@ -58,14 +58,14 @@ static int ImpactCount; CVAR (Bool, cl_spreaddecals, true, CVAR_ARCHIVE) -IMPLEMENT_POINTY_CLASS(DBaseDecal) +IMPLEMENT_CLASS(DBaseDecal, false, true, false) IMPLEMENT_POINTERS_START(DBaseDecal) IMPLEMENT_POINTER(WallPrev) IMPLEMENT_POINTER(WallNext) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS (DImpactDecal) +IMPLEMENT_CLASS(DImpactDecal, false, false, false) DBaseDecal::DBaseDecal () : DThinker(STAT_DECAL), @@ -746,7 +746,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS (ADecal) +IMPLEMENT_CLASS(ADecal, false, false, false) void ADecal::BeginPlay () { diff --git a/src/g_shared/a_fastprojectile.cpp b/src/g_shared/a_fastprojectile.cpp index 82349c1a7..a0774a6f6 100644 --- a/src/g_shared/a_fastprojectile.cpp +++ b/src/g_shared/a_fastprojectile.cpp @@ -7,8 +7,7 @@ #include "b_bot.h" #include "p_checkposition.h" - -IMPLEMENT_CLASS(AFastProjectile) +IMPLEMENT_CLASS(AFastProjectile, false, false, false) //---------------------------------------------------------------------------- diff --git a/src/g_shared/a_flashfader.cpp b/src/g_shared/a_flashfader.cpp index 61b305f44..8406ec299 100644 --- a/src/g_shared/a_flashfader.cpp +++ b/src/g_shared/a_flashfader.cpp @@ -3,7 +3,7 @@ #include "d_player.h" #include "serializer.h" -IMPLEMENT_POINTY_CLASS(DFlashFader) +IMPLEMENT_CLASS(DFlashFader, false, true, false) IMPLEMENT_POINTERS_START(DFlashFader) IMPLEMENT_POINTER(ForWho) diff --git a/src/g_shared/a_fountain.cpp b/src/g_shared/a_fountain.cpp index 970bd8aaa..bd415e729 100644 --- a/src/g_shared/a_fountain.cpp +++ b/src/g_shared/a_fountain.cpp @@ -46,7 +46,7 @@ public: void Deactivate (AActor *activator); }; -IMPLEMENT_CLASS (AParticleFountain) +IMPLEMENT_CLASS(AParticleFountain, false, false, false) void AParticleFountain::PostBeginPlay () { diff --git a/src/g_shared/a_hatetarget.cpp b/src/g_shared/a_hatetarget.cpp index 4d0d9a8e7..361ccb1f2 100644 --- a/src/g_shared/a_hatetarget.cpp +++ b/src/g_shared/a_hatetarget.cpp @@ -46,7 +46,7 @@ public: int TakeSpecialDamage(AActor *inflictor, AActor *source, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AHateTarget) +IMPLEMENT_CLASS(AHateTarget, false, false, false) void AHateTarget::BeginPlay() { diff --git a/src/g_shared/a_keys.cpp b/src/g_shared/a_keys.cpp index 2d2b5be87..07685be31 100644 --- a/src/g_shared/a_keys.cpp +++ b/src/g_shared/a_keys.cpp @@ -470,7 +470,7 @@ bool P_CheckKeys (AActor *owner, int keynum, bool remote) // //========================================================================== -IMPLEMENT_CLASS (AKey) +IMPLEMENT_CLASS(AKey, false, false, false) bool AKey::HandlePickup (AInventory *item) { diff --git a/src/g_shared/a_lightning.cpp b/src/g_shared/a_lightning.cpp index 3eaedffc9..0fe3683da 100644 --- a/src/g_shared/a_lightning.cpp +++ b/src/g_shared/a_lightning.cpp @@ -13,7 +13,7 @@ static FRandom pr_lightning ("Lightning"); -IMPLEMENT_CLASS (DLightningThinker) +IMPLEMENT_CLASS(DLightningThinker, false, false, false) DLightningThinker::DLightningThinker () : DThinker (STAT_LIGHTNING) diff --git a/src/g_shared/a_mapmarker.cpp b/src/g_shared/a_mapmarker.cpp index f8d7128c3..3c4d99b30 100644 --- a/src/g_shared/a_mapmarker.cpp +++ b/src/g_shared/a_mapmarker.cpp @@ -51,7 +51,7 @@ // //-------------------------------------------------------------------------- -IMPLEMENT_CLASS(AMapMarker) +IMPLEMENT_CLASS(AMapMarker, false, false, false) void AMapMarker::BeginPlay () { diff --git a/src/g_shared/a_morph.cpp b/src/g_shared/a_morph.cpp index 3323a0a4c..9ce33e12d 100644 --- a/src/g_shared/a_morph.cpp +++ b/src/g_shared/a_morph.cpp @@ -616,7 +616,7 @@ void InitAllPowerupEffects(AInventory *item) // Base class for morphing projectiles -------------------------------------- -IMPLEMENT_CLASS(AMorphProjectile) +IMPLEMENT_CLASS(AMorphProjectile, false, false, false) int AMorphProjectile::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -650,7 +650,7 @@ void AMorphProjectile::Serialize(FSerializer &arc) // Morphed Monster (you must subclass this to do something useful) --------- -IMPLEMENT_POINTY_CLASS(AMorphedMonster) +IMPLEMENT_CLASS(AMorphedMonster, false, true, false) IMPLEMENT_POINTERS_START(AMorphedMonster) IMPLEMENT_POINTER(UnmorphedMe) diff --git a/src/g_shared/a_movingcamera.cpp b/src/g_shared/a_movingcamera.cpp index e60c94036..89a1193cc 100644 --- a/src/g_shared/a_movingcamera.cpp +++ b/src/g_shared/a_movingcamera.cpp @@ -66,7 +66,7 @@ public: TObjPtr Next; }; -IMPLEMENT_POINTY_CLASS(AInterpolationPoint) +IMPLEMENT_CLASS(AInterpolationPoint, false, true, false) IMPLEMENT_POINTERS_START(AInterpolationPoint) IMPLEMENT_POINTER(Next) @@ -135,7 +135,7 @@ public: void Tick () {} // Does absolutely nothing itself }; -IMPLEMENT_CLASS (AInterpolationSpecial) +IMPLEMENT_CLASS(AInterpolationSpecial, false, false, false) /* == PathFollower: something that follows a camera path @@ -178,7 +178,7 @@ protected: int HoldTime; }; -IMPLEMENT_POINTY_CLASS(APathFollower) +IMPLEMENT_CLASS(APathFollower, false, true, false) IMPLEMENT_POINTERS_START(APathFollower) IMPLEMENT_POINTER(PrevNode) @@ -480,7 +480,7 @@ protected: bool Interpolate (); }; -IMPLEMENT_CLASS (AActorMover) +IMPLEMENT_CLASS(AActorMover, false, false, false) void AActorMover::BeginPlay() { @@ -596,7 +596,7 @@ protected: TObjPtr Activator; }; -IMPLEMENT_POINTY_CLASS(AMovingCamera) +IMPLEMENT_CLASS(AMovingCamera, false, true, false) IMPLEMENT_POINTERS_START(AMovingCamera) IMPLEMENT_POINTER(Activator) diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index 155878bac..2b7fcb79a 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -24,7 +24,7 @@ static FRandom pr_restore ("RestorePos"); -IMPLEMENT_CLASS(PClassInventory) +IMPLEMENT_CLASS(PClassInventory, false, false, false) PClassInventory::PClassInventory() { @@ -71,7 +71,7 @@ void PClassInventory::Finalize(FStateDefinitions &statedef) ((AActor*)Defaults)->flags |= MF_SPECIAL; } -IMPLEMENT_CLASS(PClassAmmo) +IMPLEMENT_CLASS(PClassAmmo, false, false, false) PClassAmmo::PClassAmmo() { @@ -87,7 +87,7 @@ void PClassAmmo::DeriveData(PClass *newclass) newc->DropAmount = DropAmount; } -IMPLEMENT_CLASS (AAmmo) +IMPLEMENT_CLASS(AAmmo, false, false, false) //=========================================================================== // @@ -470,7 +470,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialPosition) int AInventory::StaticLastMessageTic; const char *AInventory::StaticLastMessage; -IMPLEMENT_POINTY_CLASS(AInventory) +IMPLEMENT_CLASS(AInventory, false, true, false) IMPLEMENT_POINTERS_START(AInventory) IMPLEMENT_POINTER(Owner) @@ -1354,7 +1354,7 @@ bool AInventory::DrawPowerup (int x, int y) /* AArtifact implementation */ /***************************************************************************/ -IMPLEMENT_CLASS (APowerupGiver) +IMPLEMENT_CLASS(APowerupGiver, false, false, false) //=========================================================================== // @@ -1644,8 +1644,8 @@ void AInventory::DetachFromOwner () { } -IMPLEMENT_CLASS(AStateProvider) -IMPLEMENT_CLASS (ACustomInventory) +IMPLEMENT_CLASS(AStateProvider, false, false, false) +IMPLEMENT_CLASS(ACustomInventory, false, false, false) //=========================================================================== // @@ -1690,7 +1690,7 @@ bool ACustomInventory::TryPickup (AActor *&toucher) return useok; } -IMPLEMENT_CLASS(PClassHealth) +IMPLEMENT_CLASS(PClassHealth, false, false, false) //=========================================================================== // @@ -1719,7 +1719,7 @@ void PClassHealth::DeriveData(PClass *newclass) newc->LowHealthMessage = LowHealthMessage; } -IMPLEMENT_CLASS (AHealth) +IMPLEMENT_CLASS(AHealth, false, false, false) //=========================================================================== // @@ -1762,7 +1762,7 @@ bool AHealth::TryPickup (AActor *&other) return false; } -IMPLEMENT_CLASS (AHealthPickup) +IMPLEMENT_CLASS(AHealthPickup, false, false, false) //=========================================================================== // @@ -2015,9 +2015,8 @@ void ABackpackItem::DetachFromOwner () // //=========================================================================== -IMPLEMENT_CLASS(ABackpackItem) - -IMPLEMENT_CLASS (AMapRevealer) +IMPLEMENT_CLASS(ABackpackItem, false, false, false) +IMPLEMENT_CLASS(AMapRevealer, false, false, false) //=========================================================================== // @@ -2042,7 +2041,7 @@ bool AMapRevealer::TryPickup (AActor *&toucher) // //=========================================================================== -IMPLEMENT_CLASS(AScoreItem) +IMPLEMENT_CLASS(AScoreItem, false, false, false) //=========================================================================== // diff --git a/src/g_shared/a_puzzleitems.cpp b/src/g_shared/a_puzzleitems.cpp index 233066edc..ba3f90dc8 100644 --- a/src/g_shared/a_puzzleitems.cpp +++ b/src/g_shared/a_puzzleitems.cpp @@ -8,7 +8,7 @@ #include "doomstat.h" #include "v_font.h" -IMPLEMENT_CLASS(PClassPuzzleItem) +IMPLEMENT_CLASS(PClassPuzzleItem, false, false, false) void PClassPuzzleItem::DeriveData(PClass *newclass) { @@ -17,7 +17,7 @@ void PClassPuzzleItem::DeriveData(PClass *newclass) static_cast(newclass)->PuzzFailMessage = PuzzFailMessage; } -IMPLEMENT_CLASS(APuzzleItem) +IMPLEMENT_CLASS(APuzzleItem, false, false, false) bool APuzzleItem::HandlePickup (AInventory *item) { diff --git a/src/g_shared/a_quake.cpp b/src/g_shared/a_quake.cpp index 1a0c6a0fd..d2a2e5e5b 100644 --- a/src/g_shared/a_quake.cpp +++ b/src/g_shared/a_quake.cpp @@ -14,7 +14,7 @@ static FRandom pr_quake ("Quake"); -IMPLEMENT_POINTY_CLASS(DEarthquake) +IMPLEMENT_CLASS(DEarthquake, false, true, false) IMPLEMENT_POINTERS_START(DEarthquake) IMPLEMENT_POINTER(m_Spot) diff --git a/src/g_shared/a_randomspawner.cpp b/src/g_shared/a_randomspawner.cpp index 3ab67425d..ca85a1349 100644 --- a/src/g_shared/a_randomspawner.cpp +++ b/src/g_shared/a_randomspawner.cpp @@ -231,4 +231,4 @@ class ARandomSpawner : public AActor }; -IMPLEMENT_CLASS (ARandomSpawner) +IMPLEMENT_CLASS(ARandomSpawner, false, false, false) diff --git a/src/g_shared/a_secrettrigger.cpp b/src/g_shared/a_secrettrigger.cpp index 286ea5011..712856571 100644 --- a/src/g_shared/a_secrettrigger.cpp +++ b/src/g_shared/a_secrettrigger.cpp @@ -50,7 +50,7 @@ public: void Activate (AActor *activator); }; -IMPLEMENT_CLASS (ASecretTrigger) +IMPLEMENT_CLASS(ASecretTrigger, false, false, false) void ASecretTrigger::PostBeginPlay () { diff --git a/src/g_shared/a_sectoraction.cpp b/src/g_shared/a_sectoraction.cpp index 38435e16b..88e504aa9 100644 --- a/src/g_shared/a_sectoraction.cpp +++ b/src/g_shared/a_sectoraction.cpp @@ -37,7 +37,7 @@ // The base class for sector actions ---------------------------------------- -IMPLEMENT_CLASS (ASectorAction) +IMPLEMENT_CLASS(ASectorAction, false, false, false) ASectorAction::ASectorAction (bool activatedByUse) : ActivatedByUse (activatedByUse) {} @@ -142,7 +142,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActEnter) +IMPLEMENT_CLASS(ASecActEnter, false, false, false) bool ASecActEnter::DoTriggerAction (AActor *triggerer, int activationType) @@ -160,7 +160,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActExit) +IMPLEMENT_CLASS(ASecActExit, false, false, false) bool ASecActExit::DoTriggerAction (AActor *triggerer, int activationType) @@ -180,7 +180,8 @@ public: // Skull Tag uses 9999 for a special that is triggered whenever // the player is on the sector's floor. I think this is more useful. -IMPLEMENT_CLASS (ASecActHitFloor) + +IMPLEMENT_CLASS(ASecActHitFloor, false, false, false) bool ASecActHitFloor::DoTriggerAction (AActor *triggerer, int activationType) @@ -198,7 +199,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActHitCeil) +IMPLEMENT_CLASS(ASecActHitCeil, false, false, false) bool ASecActHitCeil::DoTriggerAction (AActor *triggerer, int activationType) @@ -217,7 +218,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActUse) +IMPLEMENT_CLASS(ASecActUse, false, false, false) bool ASecActUse::DoTriggerAction (AActor *triggerer, int activationType) @@ -236,7 +237,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActUseWall) +IMPLEMENT_CLASS(ASecActUseWall, false, false, false) bool ASecActUseWall::DoTriggerAction (AActor *triggerer, int activationType) @@ -254,7 +255,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActEyesDive) +IMPLEMENT_CLASS(ASecActEyesDive, false, false, false) bool ASecActEyesDive::DoTriggerAction (AActor *triggerer, int activationType) @@ -272,7 +273,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActEyesSurface) +IMPLEMENT_CLASS(ASecActEyesSurface, false, false, false) bool ASecActEyesSurface::DoTriggerAction (AActor *triggerer, int activationType) @@ -290,7 +291,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActEyesBelowC) +IMPLEMENT_CLASS(ASecActEyesBelowC, false, false, false) bool ASecActEyesBelowC::DoTriggerAction (AActor *triggerer, int activationType) @@ -308,7 +309,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActEyesAboveC) +IMPLEMENT_CLASS(ASecActEyesAboveC, false, false, false) bool ASecActEyesAboveC::DoTriggerAction (AActor *triggerer, int activationType) @@ -326,7 +327,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS (ASecActHitFakeFloor) +IMPLEMENT_CLASS(ASecActHitFakeFloor, false, false, false) bool ASecActHitFakeFloor::DoTriggerAction (AActor *triggerer, int activationType) diff --git a/src/g_shared/a_setcolor.cpp b/src/g_shared/a_setcolor.cpp index 4e2725756..579c57706 100644 --- a/src/g_shared/a_setcolor.cpp +++ b/src/g_shared/a_setcolor.cpp @@ -15,7 +15,7 @@ class AColorSetter : public AActor }; -IMPLEMENT_CLASS(AColorSetter) +IMPLEMENT_CLASS(AColorSetter, false, false, false) class AFadeSetter : public AActor { @@ -30,4 +30,4 @@ class AFadeSetter : public AActor }; -IMPLEMENT_CLASS(AFadeSetter) +IMPLEMENT_CLASS(AFadeSetter, false, false, false) diff --git a/src/g_shared/a_skies.cpp b/src/g_shared/a_skies.cpp index 89c785e3e..f58779387 100644 --- a/src/g_shared/a_skies.cpp +++ b/src/g_shared/a_skies.cpp @@ -42,7 +42,7 @@ // arg0 = Visibility*4 for this skybox -IMPLEMENT_CLASS (ASkyViewpoint) +IMPLEMENT_CLASS(ASkyViewpoint, false, false, false) // If this actor has no TID, make it the default sky box void ASkyViewpoint::BeginPlay () @@ -73,7 +73,7 @@ void ASkyViewpoint::Destroy () Super::Destroy(); } -IMPLEMENT_CLASS (ASkyCamCompat) +IMPLEMENT_CLASS(ASkyCamCompat, false, false, false) void ASkyCamCompat::BeginPlay() { @@ -98,7 +98,7 @@ public: void PostBeginPlay (); }; -IMPLEMENT_CLASS (ASkyPicker) +IMPLEMENT_CLASS(ASkyPicker, false, false, false) void ASkyPicker::PostBeginPlay () { @@ -142,7 +142,7 @@ void ASkyPicker::PostBeginPlay () // arg0 = opacity of plane; 0 = invisible, 255 = fully opaque -IMPLEMENT_CLASS (AStackPoint) +IMPLEMENT_CLASS(AStackPoint, false, false, false) void AStackPoint::BeginPlay () { @@ -160,7 +160,7 @@ public: void Destroy (); }; -IMPLEMENT_CLASS (ASectorSilencer) +IMPLEMENT_CLASS(ASectorSilencer, false, false, false) void ASectorSilencer::BeginPlay () { @@ -184,7 +184,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS (ASectorFlagSetter) +IMPLEMENT_CLASS(ASectorFlagSetter, false, false, false) void ASectorFlagSetter::BeginPlay () { diff --git a/src/g_shared/a_soundenvironment.cpp b/src/g_shared/a_soundenvironment.cpp index ba0171157..6d381dbe5 100644 --- a/src/g_shared/a_soundenvironment.cpp +++ b/src/g_shared/a_soundenvironment.cpp @@ -46,7 +46,7 @@ public: void Activate (AActor *deactivator); }; -IMPLEMENT_CLASS (ASoundEnvironment) +IMPLEMENT_CLASS(ASoundEnvironment, false, false, false) void ASoundEnvironment::PostBeginPlay () { diff --git a/src/g_shared/a_soundsequence.cpp b/src/g_shared/a_soundsequence.cpp index 3741a3914..01453fc9c 100644 --- a/src/g_shared/a_soundsequence.cpp +++ b/src/g_shared/a_soundsequence.cpp @@ -80,7 +80,7 @@ public: TObjPtr Sequence; }; -IMPLEMENT_POINTY_CLASS(ASoundSequenceSlot) +IMPLEMENT_CLASS(ASoundSequenceSlot, false, true, false) IMPLEMENT_POINTERS_START(ASoundSequenceSlot) IMPLEMENT_POINTER(Sequence) @@ -111,7 +111,7 @@ public: void MarkPrecacheSounds () const; }; -IMPLEMENT_CLASS (ASoundSequence) +IMPLEMENT_CLASS(ASoundSequence, false, false, false) //========================================================================== // diff --git a/src/g_shared/a_spark.cpp b/src/g_shared/a_spark.cpp index 4bc9dc4c4..ce6148068 100644 --- a/src/g_shared/a_spark.cpp +++ b/src/g_shared/a_spark.cpp @@ -45,7 +45,7 @@ public: void Activate (AActor *activator); }; -IMPLEMENT_CLASS (ASpark) +IMPLEMENT_CLASS(ASpark, false, false, false) void ASpark::Activate (AActor *activator) { diff --git a/src/g_shared/a_specialspot.cpp b/src/g_shared/a_specialspot.cpp index c47116f79..1011fcb92 100644 --- a/src/g_shared/a_specialspot.cpp +++ b/src/g_shared/a_specialspot.cpp @@ -45,9 +45,8 @@ static FRandom pr_spot ("SpecialSpot"); static FRandom pr_spawnmace ("SpawnMace"); - -IMPLEMENT_CLASS(DSpotState) -IMPLEMENT_CLASS (ASpecialSpot) +IMPLEMENT_CLASS(DSpotState, false, false, false) +IMPLEMENT_CLASS(ASpecialSpot, false, false, false) TObjPtr DSpotState::SpotState; //---------------------------------------------------------------------------- diff --git a/src/g_shared/a_waterzone.cpp b/src/g_shared/a_waterzone.cpp index 50fc6825b..65cdf96f6 100644 --- a/src/g_shared/a_waterzone.cpp +++ b/src/g_shared/a_waterzone.cpp @@ -42,7 +42,7 @@ public: void PostBeginPlay (); }; -IMPLEMENT_CLASS (AWaterZone) +IMPLEMENT_CLASS(AWaterZone, false, false, false) void AWaterZone::PostBeginPlay () { diff --git a/src/g_shared/a_weaponpiece.cpp b/src/g_shared/a_weaponpiece.cpp index 4b0a6dcbf..68c631d9b 100644 --- a/src/g_shared/a_weaponpiece.cpp +++ b/src/g_shared/a_weaponpiece.cpp @@ -3,8 +3,8 @@ #include "doomstat.h" #include "serializer.h" -IMPLEMENT_CLASS(PClassWeaponPiece) -IMPLEMENT_CLASS (AWeaponHolder) +IMPLEMENT_CLASS(PClassWeaponPiece, false, false, false) +IMPLEMENT_CLASS(AWeaponHolder, false, false, false) void PClassWeaponPiece::ReplaceClassRef(PClass *oldclass, PClass *newclass) { @@ -24,7 +24,7 @@ void AWeaponHolder::Serialize(FSerializer &arc) ("pieceweapon", PieceWeapon); } -IMPLEMENT_POINTY_CLASS(AWeaponPiece) +IMPLEMENT_CLASS(AWeaponPiece, false, true, false) IMPLEMENT_POINTERS_START(AWeaponPiece) IMPLEMENT_POINTER(FullWeapon) diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index ec5e32be8..adaf4c9e3 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -21,7 +21,7 @@ #define BONUSADD 6 -IMPLEMENT_POINTY_CLASS(AWeapon) +IMPLEMENT_CLASS(AWeapon, false, true, false) IMPLEMENT_POINTERS_START(AWeapon) IMPLEMENT_POINTER(Ammo1) @@ -38,7 +38,7 @@ TMap Weapons_hton; static int ntoh_cmp(const void *a, const void *b); -IMPLEMENT_CLASS(PClassWeapon) +IMPLEMENT_CLASS(PClassWeapon, false, false, false) PClassWeapon::PClassWeapon() { @@ -791,7 +791,7 @@ FState *AWeapon::GetStateForButtonName (FName button) /* Weapon giver ***********************************************************/ -IMPLEMENT_CLASS(AWeaponGiver) +IMPLEMENT_CLASS(AWeaponGiver, false, false, false) void AWeaponGiver::Serialize(FSerializer &arc) { diff --git a/src/g_shared/hudmessages.cpp b/src/g_shared/hudmessages.cpp index 783d1624d..947f68ae4 100644 --- a/src/g_shared/hudmessages.cpp +++ b/src/g_shared/hudmessages.cpp @@ -44,15 +44,15 @@ EXTERN_CVAR(Int, con_scaletext) int active_con_scaletext(); -IMPLEMENT_POINTY_CLASS(DHUDMessage) +IMPLEMENT_CLASS(DHUDMessage, false, true, false) IMPLEMENT_POINTERS_START(DHUDMessage) IMPLEMENT_POINTER(Next) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS (DHUDMessageFadeOut) -IMPLEMENT_CLASS (DHUDMessageFadeInOut) -IMPLEMENT_CLASS (DHUDMessageTypeOnFadeOut) +IMPLEMENT_CLASS(DHUDMessageFadeOut, false, false, false) +IMPLEMENT_CLASS(DHUDMessageFadeInOut, false, false, false) +IMPLEMENT_CLASS(DHUDMessageTypeOnFadeOut, false, false, false) /************************************************************************* * Basic HUD message. Appears and disappears without any special effects * diff --git a/src/g_shared/sbarinfo.cpp b/src/g_shared/sbarinfo.cpp index d0cd2defc..7675865ad 100644 --- a/src/g_shared/sbarinfo.cpp +++ b/src/g_shared/sbarinfo.cpp @@ -1531,7 +1531,7 @@ private: SBarInfoMainBlock *lastPopup; }; -IMPLEMENT_POINTY_CLASS(DSBarInfo) +IMPLEMENT_CLASS(DSBarInfo, false, true, false) IMPLEMENT_POINTERS_START(DSBarInfo) IMPLEMENT_POINTER(ammo1) diff --git a/src/g_shared/shared_sbar.cpp b/src/g_shared/shared_sbar.cpp index 524ec4f1f..abf48c6a1 100644 --- a/src/g_shared/shared_sbar.cpp +++ b/src/g_shared/shared_sbar.cpp @@ -62,7 +62,7 @@ #define XHAIRPICKUPSIZE (2+XHAIRSHRINKSIZE) #define POWERUPICONSIZE 32 -IMPLEMENT_POINTY_CLASS(DBaseStatusBar) +IMPLEMENT_CLASS(DBaseStatusBar, false, true, false) IMPLEMENT_POINTERS_START(DBaseStatusBar) IMPLEMENT_POINTER(Messages[0]) diff --git a/src/g_strife/a_coin.cpp b/src/g_strife/a_coin.cpp index 5848164bd..281c97921 100644 --- a/src/g_strife/a_coin.cpp +++ b/src/g_strife/a_coin.cpp @@ -6,7 +6,7 @@ // Coin --------------------------------------------------------------------- -IMPLEMENT_CLASS (ACoin) +IMPLEMENT_CLASS(ACoin, false, false, false) const char *ACoin::PickupMessage () { diff --git a/src/g_strife/a_loremaster.cpp b/src/g_strife/a_loremaster.cpp index 504324590..4bb2fec0e 100644 --- a/src/g_strife/a_loremaster.cpp +++ b/src/g_strife/a_loremaster.cpp @@ -17,7 +17,7 @@ public: int DoSpecialDamage (AActor *victim, int damage, FName damagetype); }; -IMPLEMENT_CLASS (ALoreShot) +IMPLEMENT_CLASS(ALoreShot, false, false, false) int ALoreShot::DoSpecialDamage (AActor *victim, int damage, FName damagetype) { diff --git a/src/g_strife/a_programmer.cpp b/src/g_strife/a_programmer.cpp index b46b47e70..70310eef2 100644 --- a/src/g_strife/a_programmer.cpp +++ b/src/g_strife/a_programmer.cpp @@ -23,7 +23,7 @@ public: PalEntry GetBlend (); }; -IMPLEMENT_CLASS (AProgLevelEnder) +IMPLEMENT_CLASS(AProgLevelEnder, false, false, false) //============================================================================ // diff --git a/src/g_strife/a_rebels.cpp b/src/g_strife/a_rebels.cpp index e460dd91a..bef34d03b 100644 --- a/src/g_strife/a_rebels.cpp +++ b/src/g_strife/a_rebels.cpp @@ -47,7 +47,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (ATeleporterBeacon) +IMPLEMENT_CLASS(ATeleporterBeacon, false, false, false) bool ATeleporterBeacon::Use (bool pickup) { diff --git a/src/g_strife/a_spectral.cpp b/src/g_strife/a_spectral.cpp index b348e54dc..d1dff1fb1 100644 --- a/src/g_strife/a_spectral.cpp +++ b/src/g_strife/a_spectral.cpp @@ -16,7 +16,7 @@ public: void Touch (AActor *toucher); }; -IMPLEMENT_CLASS (ASpectralMonster) +IMPLEMENT_CLASS(ASpectralMonster, false, false, false) void ASpectralMonster::Touch (AActor *toucher) { diff --git a/src/g_strife/a_strifeitems.cpp b/src/g_strife/a_strifeitems.cpp index 6cda8a0fc..f937da570 100644 --- a/src/g_strife/a_strifeitems.cpp +++ b/src/g_strife/a_strifeitems.cpp @@ -19,7 +19,7 @@ */ // Degnin Ore --------------------------------------------------------------- -IMPLEMENT_CLASS(ADegninOre) +IMPLEMENT_CLASS(ADegninOre, false, false, false) DEFINE_ACTION_FUNCTION(AActor, A_RemoveForceField) { @@ -75,7 +75,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS (AHealthTraining) +IMPLEMENT_CLASS(AHealthTraining, false, false, false) bool AHealthTraining::TryPickup (AActor *&toucher) { @@ -105,7 +105,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS (AScanner) +IMPLEMENT_CLASS(AScanner, false, false, false) bool AScanner::Use (bool pickup) { @@ -130,7 +130,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS (APrisonPass) +IMPLEMENT_CLASS(APrisonPass, false, false, false) bool APrisonPass::TryPickup (AActor *&toucher) { @@ -163,7 +163,7 @@ bool APrisonPass::SpecialDropAction (AActor *dropper) // actions and cannot be held. ---------------------------------------------- //--------------------------------------------------------------------------- -IMPLEMENT_CLASS (ADummyStrifeItem) +IMPLEMENT_CLASS(ADummyStrifeItem, false, false, false) // Sound the alarm! --------------------------------------------------------- @@ -175,7 +175,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS (ARaiseAlarm) +IMPLEMENT_CLASS(ARaiseAlarm, false, false, false) bool ARaiseAlarm::TryPickup (AActor *&toucher) { @@ -209,7 +209,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS (AOpenDoor222) +IMPLEMENT_CLASS(AOpenDoor222, false, false, false) bool AOpenDoor222::TryPickup (AActor *&toucher) { @@ -228,7 +228,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS (ACloseDoor222) +IMPLEMENT_CLASS(ACloseDoor222, false, false, false) bool ACloseDoor222::TryPickup (AActor *&toucher) { @@ -262,7 +262,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS (AOpenDoor224) +IMPLEMENT_CLASS(AOpenDoor224, false, false, false) bool AOpenDoor224::TryPickup (AActor *&toucher) { @@ -287,7 +287,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS (AAmmoFillup) +IMPLEMENT_CLASS(AAmmoFillup, false, false, false) bool AAmmoFillup::TryPickup (AActor *&toucher) { @@ -325,7 +325,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS (AHealthFillup) +IMPLEMENT_CLASS(AHealthFillup, false, false, false) bool AHealthFillup::TryPickup (AActor *&toucher) { @@ -342,7 +342,7 @@ bool AHealthFillup::TryPickup (AActor *&toucher) // Upgrade Stamina ---------------------------------------------------------- -IMPLEMENT_CLASS (AUpgradeStamina) +IMPLEMENT_CLASS(AUpgradeStamina, false, false, false) bool AUpgradeStamina::TryPickup (AActor *&toucher) { @@ -360,7 +360,7 @@ bool AUpgradeStamina::TryPickup (AActor *&toucher) // Upgrade Accuracy --------------------------------------------------------- -IMPLEMENT_CLASS (AUpgradeAccuracy) +IMPLEMENT_CLASS(AUpgradeAccuracy, false, false, false) bool AUpgradeAccuracy::TryPickup (AActor *&toucher) { @@ -373,7 +373,7 @@ bool AUpgradeAccuracy::TryPickup (AActor *&toucher) // Start a slideshow -------------------------------------------------------- -IMPLEMENT_CLASS (ASlideshowStarter) +IMPLEMENT_CLASS(ASlideshowStarter, false, false, false) bool ASlideshowStarter::TryPickup (AActor *&toucher) { diff --git a/src/g_strife/a_strifestuff.cpp b/src/g_strife/a_strifestuff.cpp index ef60b77e7..f4a724bc4 100644 --- a/src/g_strife/a_strifestuff.cpp +++ b/src/g_strife/a_strifestuff.cpp @@ -72,7 +72,7 @@ public: int TakeSpecialDamage (AActor *inflictor, AActor *source, int damage, FName damagetype); }; -IMPLEMENT_CLASS (AForceFieldGuard) +IMPLEMENT_CLASS(AForceFieldGuard, false, false, false) int AForceFieldGuard::TakeSpecialDamage (AActor *inflictor, AActor *source, int damage, FName damagetype) { @@ -197,7 +197,7 @@ public: void Die (AActor *source, AActor *inflictor, int dmgflags); }; -IMPLEMENT_CLASS (APowerCoupling) +IMPLEMENT_CLASS(APowerCoupling, false, false, false) void APowerCoupling::Die (AActor *source, AActor *inflictor, int dmgflags) { @@ -239,7 +239,7 @@ public: } }; -IMPLEMENT_CLASS (AMeat) +IMPLEMENT_CLASS(AMeat, false, false, false) //========================================================================== // diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index 41ceff087..ec153d675 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -184,7 +184,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (APoisonBolt) +IMPLEMENT_CLASS(APoisonBolt, false, false, false) int APoisonBolt::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -607,7 +607,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS (APhosphorousFire) +IMPLEMENT_CLASS(APhosphorousFire, false, false, false) int APhosphorousFire::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -734,7 +734,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireGrenade) // The Almighty Sigil! ------------------------------------------------------ -IMPLEMENT_CLASS(ASigil) +IMPLEMENT_CLASS(ASigil, false, false, false) //============================================================================ // diff --git a/src/g_strife/strife_sbar.cpp b/src/g_strife/strife_sbar.cpp index 122846a82..3d0089777 100644 --- a/src/g_strife/strife_sbar.cpp +++ b/src/g_strife/strife_sbar.cpp @@ -851,7 +851,7 @@ private: double ItemFlash; }; -IMPLEMENT_CLASS(DStrifeStatusBar); +IMPLEMENT_CLASS(DStrifeStatusBar, false, false, false); DBaseStatusBar *CreateStrifeStatusBar () { diff --git a/src/info.cpp b/src/info.cpp index 12753b21b..3e14d7fed 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -153,7 +153,7 @@ int GetSpriteIndex(const char * spritename, bool add) return (lastindex = (int)sprites.Push (temp)); } -IMPLEMENT_POINTY_CLASS(PClassActor) +IMPLEMENT_CLASS(PClassActor, false, true, false) IMPLEMENT_POINTERS_START(PClassActor) IMPLEMENT_POINTER(DropItems) diff --git a/src/intermission/intermission.cpp b/src/intermission/intermission.cpp index 527062bb6..94288bfdf 100644 --- a/src/intermission/intermission.cpp +++ b/src/intermission/intermission.cpp @@ -54,13 +54,12 @@ FIntermissionDescriptorList IntermissionDescriptors; -IMPLEMENT_CLASS(DIntermissionScreen) -IMPLEMENT_CLASS(DIntermissionScreenFader) -IMPLEMENT_CLASS(DIntermissionScreenText) -IMPLEMENT_CLASS(DIntermissionScreenCast) -IMPLEMENT_CLASS(DIntermissionScreenScroller) - -IMPLEMENT_POINTY_CLASS(DIntermissionController) +IMPLEMENT_CLASS(DIntermissionScreen, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenFader, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenText, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenCast, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenScroller, false, false, false) +IMPLEMENT_CLASS(DIntermissionController, false, true, false) IMPLEMENT_POINTERS_START(DIntermissionController) IMPLEMENT_POINTER(mScreen) diff --git a/src/m_argv.cpp b/src/m_argv.cpp index 5d4aa97a3..924c9dd5c 100644 --- a/src/m_argv.cpp +++ b/src/m_argv.cpp @@ -37,7 +37,7 @@ #include "cmdlib.h" #include "i_system.h" -IMPLEMENT_CLASS (DArgs) +IMPLEMENT_CLASS(DArgs, false, false, false) //=========================================================================== // diff --git a/src/m_cheat.cpp b/src/m_cheat.cpp index 7348f5881..94c1ef3df 100644 --- a/src/m_cheat.cpp +++ b/src/m_cheat.cpp @@ -1033,7 +1033,7 @@ public: } }; -IMPLEMENT_POINTY_CLASS(DSuicider) +IMPLEMENT_CLASS(DSuicider, false, true, false) IMPLEMENT_POINTERS_START(DSuicider) IMPLEMENT_POINTER(Pawn) diff --git a/src/menu/colorpickermenu.cpp b/src/menu/colorpickermenu.cpp index affcf7c9f..110ed2c3e 100644 --- a/src/menu/colorpickermenu.cpp +++ b/src/menu/colorpickermenu.cpp @@ -331,7 +331,7 @@ public: } }; -IMPLEMENT_ABSTRACT_CLASS(DColorPickerMenu) +IMPLEMENT_CLASS(DColorPickerMenu, true, false, false) CCMD(undocolorpic) { diff --git a/src/menu/joystickmenu.cpp b/src/menu/joystickmenu.cpp index 174b45d4b..8e05391a6 100644 --- a/src/menu/joystickmenu.cpp +++ b/src/menu/joystickmenu.cpp @@ -236,7 +236,7 @@ class DJoystickConfigMenu : public DOptionMenu DECLARE_CLASS(DJoystickConfigMenu, DOptionMenu) }; -IMPLEMENT_CLASS(DJoystickConfigMenu) +IMPLEMENT_CLASS(DJoystickConfigMenu, false, false, false) //============================================================================= // diff --git a/src/menu/listmenu.cpp b/src/menu/listmenu.cpp index bcb61d6eb..645636dad 100644 --- a/src/menu/listmenu.cpp +++ b/src/menu/listmenu.cpp @@ -42,7 +42,7 @@ #include "d_event.h" #include "menu/menu.h" -IMPLEMENT_CLASS(DListMenu) +IMPLEMENT_CLASS(DListMenu, false, false, false) //============================================================================= // diff --git a/src/menu/loadsavemenu.cpp b/src/menu/loadsavemenu.cpp index 99c34ab3e..69976726e 100644 --- a/src/menu/loadsavemenu.cpp +++ b/src/menu/loadsavemenu.cpp @@ -119,7 +119,7 @@ public: }; -IMPLEMENT_CLASS(DLoadSaveMenu) +IMPLEMENT_CLASS(DLoadSaveMenu, false, false, false) TArray DLoadSaveMenu::SaveGames; int DLoadSaveMenu::LastSaved = -1; @@ -934,7 +934,7 @@ public: }; -IMPLEMENT_CLASS(DSaveMenu) +IMPLEMENT_CLASS(DSaveMenu, false, false, false) //============================================================================= @@ -1102,7 +1102,7 @@ public: bool MenuEvent (int mkey, bool fromcontroller); }; -IMPLEMENT_CLASS(DLoadMenu) +IMPLEMENT_CLASS(DLoadMenu, false, false, false) //============================================================================= diff --git a/src/menu/menu.cpp b/src/menu/menu.cpp index c4e0a4d98..6717ffcf2 100644 --- a/src/menu/menu.cpp +++ b/src/menu/menu.cpp @@ -91,7 +91,7 @@ static bool MenuEnabled = true; // //============================================================================ -IMPLEMENT_POINTY_CLASS(DMenu) +IMPLEMENT_CLASS(DMenu, false, true, false) IMPLEMENT_POINTERS_START(DMenu) IMPLEMENT_POINTER(mParentMenu) diff --git a/src/menu/menuinput.cpp b/src/menu/menuinput.cpp index 39d7a8c0b..12ef4525d 100644 --- a/src/menu/menuinput.cpp +++ b/src/menu/menuinput.cpp @@ -44,7 +44,7 @@ // [TP] New #includes #include "v_text.h" -IMPLEMENT_ABSTRACT_CLASS(DTextEnterMenu) +IMPLEMENT_CLASS(DTextEnterMenu, true, false, false) #define INPUTGRID_WIDTH 13 #define INPUTGRID_HEIGHT 5 diff --git a/src/menu/messagebox.cpp b/src/menu/messagebox.cpp index a72a37740..7915f44b3 100644 --- a/src/menu/messagebox.cpp +++ b/src/menu/messagebox.cpp @@ -73,7 +73,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DMessageBoxMenu) +IMPLEMENT_CLASS(DMessageBoxMenu, false, false, false) //============================================================================= // @@ -365,7 +365,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DQuitMenu) +IMPLEMENT_CLASS(DQuitMenu, false, false, false) //============================================================================= // @@ -458,7 +458,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DEndGameMenu) +IMPLEMENT_CLASS(DEndGameMenu, false, false, false) //============================================================================= // @@ -536,7 +536,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DQuickSaveMenu) +IMPLEMENT_CLASS(DQuickSaveMenu, false, false, false) //============================================================================= // @@ -632,7 +632,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DQuickLoadMenu) +IMPLEMENT_CLASS(DQuickLoadMenu, false, false, false) //============================================================================= // diff --git a/src/menu/optionmenu.cpp b/src/menu/optionmenu.cpp index efea7d910..46bbae665 100644 --- a/src/menu/optionmenu.cpp +++ b/src/menu/optionmenu.cpp @@ -64,8 +64,7 @@ void M_DrawConText (int color, int x, int y, const char *str) TAG_DONE); } - -IMPLEMENT_CLASS(DOptionMenu) +IMPLEMENT_CLASS(DOptionMenu, false, false, false) //============================================================================= // @@ -579,7 +578,7 @@ public: } }; -IMPLEMENT_CLASS(DGameplayMenu) +IMPLEMENT_CLASS(DGameplayMenu, false, false, false) class DCompatibilityMenu : public DOptionMenu { @@ -601,4 +600,4 @@ public: } }; -IMPLEMENT_CLASS(DCompatibilityMenu) +IMPLEMENT_CLASS(DCompatibilityMenu, false, false, false) diff --git a/src/menu/optionmenuitems.h b/src/menu/optionmenuitems.h index 0fadeca37..2d3c8c25f 100644 --- a/src/menu/optionmenuitems.h +++ b/src/menu/optionmenuitems.h @@ -399,7 +399,7 @@ public: }; #ifndef NO_IMP -IMPLEMENT_ABSTRACT_CLASS(DEnterKey) +IMPLEMENT_CLASS(DEnterKey, true, false, false) #endif //============================================================================= diff --git a/src/menu/playermenu.cpp b/src/menu/playermenu.cpp index ce542c2f2..bc22c8e12 100644 --- a/src/menu/playermenu.cpp +++ b/src/menu/playermenu.cpp @@ -526,7 +526,7 @@ public: void Drawer (); }; -IMPLEMENT_CLASS(DPlayerMenu) +IMPLEMENT_CLASS(DPlayerMenu, false, false, false) //============================================================================= // diff --git a/src/menu/readthis.cpp b/src/menu/readthis.cpp index 0aa3c2fcd..ce03ec84b 100644 --- a/src/menu/readthis.cpp +++ b/src/menu/readthis.cpp @@ -54,7 +54,7 @@ public: bool MouseEvent(int type, int x, int y); }; -IMPLEMENT_CLASS(DReadThisMenu) +IMPLEMENT_CLASS(DReadThisMenu, false, false, false) //============================================================================= // diff --git a/src/menu/videomenu.cpp b/src/menu/videomenu.cpp index b1b4d792f..6fec9ce6d 100644 --- a/src/menu/videomenu.cpp +++ b/src/menu/videomenu.cpp @@ -183,7 +183,7 @@ public: } }; -IMPLEMENT_CLASS(DVideoModeMenu) +IMPLEMENT_CLASS(DVideoModeMenu, false, false, false) //============================================================================= diff --git a/src/p_acs.cpp b/src/p_acs.cpp index 1fac7e8fe..dc646da18 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -1369,7 +1369,7 @@ private: DPlaneWatcher() {} }; -IMPLEMENT_POINTY_CLASS(DPlaneWatcher) +IMPLEMENT_CLASS(DPlaneWatcher, false, true, false) IMPLEMENT_POINTERS_START(DPlaneWatcher) IMPLEMENT_POINTER(Activator) @@ -2860,7 +2860,7 @@ void FBehavior::StaticStopMyScripts (AActor *actor) //---- The ACS Interpreter ----// -IMPLEMENT_POINTY_CLASS(DACSThinker) +IMPLEMENT_CLASS(DACSThinker, false, true, false) IMPLEMENT_POINTERS_START(DACSThinker) IMPLEMENT_POINTER(LastScript) @@ -2991,7 +2991,7 @@ void DACSThinker::StopScriptsFor (AActor *actor) } } -IMPLEMENT_POINTY_CLASS(DLevelScript) +IMPLEMENT_CLASS(DLevelScript, false, true, false) IMPLEMENT_POINTERS_START(DLevelScript) IMPLEMENT_POINTER(next) diff --git a/src/p_buildmap.cpp b/src/p_buildmap.cpp index 7e65bf05d..ce2221ca1 100644 --- a/src/p_buildmap.cpp +++ b/src/p_buildmap.cpp @@ -865,7 +865,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS (ACustomSprite) +IMPLEMENT_CLASS(ACustomSprite, false, false, false) void ACustomSprite::BeginPlay () { diff --git a/src/p_ceiling.cpp b/src/p_ceiling.cpp index 29b0c5095..53100f9ca 100644 --- a/src/p_ceiling.cpp +++ b/src/p_ceiling.cpp @@ -38,7 +38,7 @@ // //============================================================================ -IMPLEMENT_CLASS (DCeiling) +IMPLEMENT_CLASS(DCeiling, false, false, false) DCeiling::DCeiling () { diff --git a/src/p_conversation.cpp b/src/p_conversation.cpp index 0bc2b98a8..ad434b535 100644 --- a/src/p_conversation.cpp +++ b/src/p_conversation.cpp @@ -1103,7 +1103,7 @@ public: }; -IMPLEMENT_ABSTRACT_CLASS(DConversationMenu) +IMPLEMENT_CLASS(DConversationMenu, true, false, false) int DConversationMenu::mSelection; // needs to be preserved if the same dialogue is restarted diff --git a/src/p_doors.cpp b/src/p_doors.cpp index 33e37218d..568e88058 100644 --- a/src/p_doors.cpp +++ b/src/p_doors.cpp @@ -45,7 +45,7 @@ // //============================================================================ -IMPLEMENT_CLASS (DDoor) +IMPLEMENT_CLASS(DDoor, false, false, false) DDoor::DDoor () { @@ -513,7 +513,7 @@ bool EV_DoDoor (DDoor::EVlDoor type, line_t *line, AActor *thing, // //============================================================================ -IMPLEMENT_CLASS (DAnimatedDoor) +IMPLEMENT_CLASS(DAnimatedDoor, false, false, false) DAnimatedDoor::DAnimatedDoor () { diff --git a/src/p_floor.cpp b/src/p_floor.cpp index 23fdc7575..a89330b2a 100644 --- a/src/p_floor.cpp +++ b/src/p_floor.cpp @@ -64,7 +64,7 @@ static void StartFloorSound (sector_t *sec) // //========================================================================== -IMPLEMENT_CLASS (DFloor) +IMPLEMENT_CLASS(DFloor, false, false, false) DFloor::DFloor () { @@ -815,7 +815,7 @@ bool EV_DoDonut (int tag, line_t *line, double pillarspeed, double slimespeed) // //========================================================================== -IMPLEMENT_POINTY_CLASS(DElevator) +IMPLEMENT_CLASS(DElevator, false, true, false) IMPLEMENT_POINTERS_START(DElevator) IMPLEMENT_POINTER(m_Interp_Floor) @@ -1105,10 +1105,9 @@ bool EV_DoChange (line_t *line, EChange changetype, int tag) // //========================================================================== -IMPLEMENT_CLASS (DWaggleBase) - -IMPLEMENT_CLASS (DFloorWaggle) -IMPLEMENT_CLASS (DCeilingWaggle) +IMPLEMENT_CLASS(DWaggleBase, false, false, false) +IMPLEMENT_CLASS(DFloorWaggle, false, false, false) +IMPLEMENT_CLASS(DCeilingWaggle, false, false, false) DWaggleBase::DWaggleBase () { diff --git a/src/p_lights.cpp b/src/p_lights.cpp index fb3ab339e..c2c2127a2 100644 --- a/src/p_lights.cpp +++ b/src/p_lights.cpp @@ -173,7 +173,7 @@ private: // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DLighting) +IMPLEMENT_CLASS(DLighting, false, false, false) DLighting::DLighting () { @@ -191,7 +191,7 @@ DLighting::DLighting (sector_t *sector) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DFireFlicker) +IMPLEMENT_CLASS(DFireFlicker, false, false, false) DFireFlicker::DFireFlicker () { @@ -258,7 +258,7 @@ DFireFlicker::DFireFlicker (sector_t *sector, int upper, int lower) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DFlicker) +IMPLEMENT_CLASS(DFlicker, false, false, false) DFlicker::DFlicker () { @@ -334,7 +334,7 @@ void EV_StartLightFlickering (int tag, int upper, int lower) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DLightFlash) +IMPLEMENT_CLASS(DLightFlash, false, false, false) DLightFlash::DLightFlash () { @@ -409,7 +409,7 @@ DLightFlash::DLightFlash (sector_t *sector, int min, int max) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DStrobe) +IMPLEMENT_CLASS(DStrobe, false, false, false) DStrobe::DStrobe () { @@ -667,7 +667,7 @@ void EV_LightChange (int tag, int value) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DGlow) +IMPLEMENT_CLASS(DGlow, false, false, false) DGlow::DGlow () { @@ -736,7 +736,7 @@ DGlow::DGlow (sector_t *sector) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DGlow2) +IMPLEMENT_CLASS(DGlow2, false, false, false) DGlow2::DGlow2 () { @@ -869,7 +869,7 @@ void EV_StartLightFading (int tag, int value, int tics) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS (DPhased) +IMPLEMENT_CLASS(DPhased, false, false, false) DPhased::DPhased () { diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index f36760856..3cc961d84 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -131,7 +131,7 @@ CVAR (Int, cl_bloodtype, 0, CVAR_ARCHIVE); // CODE -------------------------------------------------------------------- -IMPLEMENT_POINTY_CLASS_WITH_FIELDS (AActor) +IMPLEMENT_CLASS(AActor, false, true, true) IMPLEMENT_POINTERS_START(AActor) IMPLEMENT_POINTER(target) @@ -6956,7 +6956,7 @@ DEFINE_ACTION_FUNCTION(AActor, Vec3Offset) // //---------------------------------------------------------------------------- -IMPLEMENT_POINTY_CLASS_WITH_FIELDS(DDropItem) +IMPLEMENT_CLASS(DDropItem, false, true, true) IMPLEMENT_POINTERS_START(DDropItem) IMPLEMENT_POINTER(Next) diff --git a/src/p_pillar.cpp b/src/p_pillar.cpp index 52078daad..fecfbd024 100644 --- a/src/p_pillar.cpp +++ b/src/p_pillar.cpp @@ -40,7 +40,7 @@ #include "serializer.h" #include "r_data/r_interpolate.h" -IMPLEMENT_POINTY_CLASS(DPillar) +IMPLEMENT_CLASS(DPillar, false, true, false) IMPLEMENT_POINTERS_START(DPillar) IMPLEMENT_POINTER(m_Interp_Floor) diff --git a/src/p_plats.cpp b/src/p_plats.cpp index 868f47138..3bd708916 100644 --- a/src/p_plats.cpp +++ b/src/p_plats.cpp @@ -35,7 +35,7 @@ static FRandom pr_doplat ("DoPlat"); -IMPLEMENT_CLASS (DPlat) +IMPLEMENT_CLASS(DPlat, false, false, false) DPlat::DPlat () { diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index b2e59ade4..b64bb22a7 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -99,7 +99,7 @@ static const FGenericButtons ButtonChecks[] = // //------------------------------------------------------------------------ -IMPLEMENT_POINTY_CLASS(DPSprite) +IMPLEMENT_CLASS(DPSprite, false, true, false) IMPLEMENT_POINTERS_START(DPSprite) IMPLEMENT_POINTER(Caller) diff --git a/src/p_pusher.cpp b/src/p_pusher.cpp index d211f1c3c..250e8ee3d 100644 --- a/src/p_pusher.cpp +++ b/src/p_pusher.cpp @@ -74,7 +74,7 @@ protected: friend bool PIT_PushThing (AActor *thing); }; -IMPLEMENT_POINTY_CLASS(DPusher) +IMPLEMENT_CLASS(DPusher, false, true, false) IMPLEMENT_POINTERS_START(DPusher) IMPLEMENT_POINTER(m_Source) diff --git a/src/p_scroll.cpp b/src/p_scroll.cpp index 3918bc072..67f6499d6 100644 --- a/src/p_scroll.cpp +++ b/src/p_scroll.cpp @@ -73,7 +73,7 @@ private: } }; -IMPLEMENT_POINTY_CLASS(DScroller) +IMPLEMENT_CLASS(DScroller, false, true, false) IMPLEMENT_POINTERS_START(DScroller) IMPLEMENT_POINTER(m_Interpolations[0]) diff --git a/src/p_spec.cpp b/src/p_spec.cpp index dc878bc33..e9ac49419 100644 --- a/src/p_spec.cpp +++ b/src/p_spec.cpp @@ -660,7 +660,7 @@ protected: short LastLight; }; -IMPLEMENT_CLASS (DLightTransfer) +IMPLEMENT_CLASS(DLightTransfer, false, false, false) void DLightTransfer::Serialize(FSerializer &arc) { @@ -750,7 +750,7 @@ protected: BYTE Flags; }; -IMPLEMENT_CLASS (DWallLightTransfer) +IMPLEMENT_CLASS(DWallLightTransfer, false, false, false) void DWallLightTransfer::Serialize(FSerializer &arc) { diff --git a/src/p_switch.cpp b/src/p_switch.cpp index c60b0fdcd..027b5d99d 100644 --- a/src/p_switch.cpp +++ b/src/p_switch.cpp @@ -320,7 +320,7 @@ bool P_ChangeSwitchTexture (side_t *side, int useAgain, BYTE special, bool *ques // //========================================================================== -IMPLEMENT_CLASS (DActiveButton) +IMPLEMENT_CLASS(DActiveButton, false, false, false) DActiveButton::DActiveButton () { diff --git a/src/p_teleport.cpp b/src/p_teleport.cpp index f65e2f402..85ee8a1c8 100644 --- a/src/p_teleport.cpp +++ b/src/p_teleport.cpp @@ -47,7 +47,7 @@ extern void P_CalcHeight (player_t *player); CVAR (Bool, telezoom, true, CVAR_ARCHIVE|CVAR_GLOBALCONFIG); -IMPLEMENT_CLASS (ATeleportFog) +IMPLEMENT_CLASS(ATeleportFog, false, false, false) void ATeleportFog::PostBeginPlay () { diff --git a/src/p_user.cpp b/src/p_user.cpp index 0efe422a3..266d216bb 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -508,7 +508,7 @@ int player_t::GetSpawnClass() // //=========================================================================== -IMPLEMENT_CLASS(PClassPlayerPawn) +IMPLEMENT_CLASS(PClassPlayerPawn, false, false, false) PClassPlayerPawn::PClassPlayerPawn() { @@ -622,14 +622,14 @@ void player_t::SendPitchLimits() const // //=========================================================================== -IMPLEMENT_POINTY_CLASS(APlayerPawn) +IMPLEMENT_CLASS(APlayerPawn, false, true, false) IMPLEMENT_POINTERS_START(APlayerPawn) IMPLEMENT_POINTER(InvFirst) IMPLEMENT_POINTER(InvSel) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS (APlayerChunk) +IMPLEMENT_CLASS(APlayerChunk, false, false, false) void APlayerPawn::Serialize(FSerializer &arc) { diff --git a/src/po_man.cpp b/src/po_man.cpp index c80e72992..3261e34f3 100644 --- a/src/po_man.cpp +++ b/src/po_man.cpp @@ -172,7 +172,7 @@ static FPolyNode *FreePolyNodes; // //========================================================================== -IMPLEMENT_POINTY_CLASS(DPolyAction) +IMPLEMENT_CLASS(DPolyAction, false, true, false) IMPLEMENT_POINTERS_START(DPolyAction) IMPLEMENT_POINTER(m_Interpolation) @@ -240,7 +240,7 @@ void DPolyAction::StopInterpolation () // //========================================================================== -IMPLEMENT_CLASS (DRotatePoly) +IMPLEMENT_CLASS(DRotatePoly, false, false, false) DRotatePoly::DRotatePoly () { @@ -257,7 +257,7 @@ DRotatePoly::DRotatePoly (int polyNum) // //========================================================================== -IMPLEMENT_CLASS (DMovePoly) +IMPLEMENT_CLASS(DMovePoly, false, false, false) DMovePoly::DMovePoly () { @@ -284,7 +284,7 @@ DMovePoly::DMovePoly (int polyNum) // //========================================================================== -IMPLEMENT_CLASS(DMovePolyTo) +IMPLEMENT_CLASS(DMovePolyTo, false, false, false) DMovePolyTo::DMovePolyTo() { @@ -309,7 +309,7 @@ DMovePolyTo::DMovePolyTo(int polyNum) // //========================================================================== -IMPLEMENT_CLASS (DPolyDoor) +IMPLEMENT_CLASS(DPolyDoor, false, false, false) DPolyDoor::DPolyDoor () { diff --git a/src/posix/sdl/sdlvideo.cpp b/src/posix/sdl/sdlvideo.cpp index 04c3a3f2e..29b741561 100644 --- a/src/posix/sdl/sdlvideo.cpp +++ b/src/posix/sdl/sdlvideo.cpp @@ -78,7 +78,8 @@ private: SDLFB () {} }; -IMPLEMENT_CLASS(SDLFB) + +IMPLEMENT_CLASS(SDLFB, false, false, false) struct MiniModeInfo { diff --git a/src/r_data/r_interpolate.cpp b/src/r_data/r_interpolate.cpp index fdb8affc6..911127f07 100644 --- a/src/r_data/r_interpolate.cpp +++ b/src/r_data/r_interpolate.cpp @@ -161,17 +161,17 @@ public: // //========================================================================== -IMPLEMENT_ABSTRACT_POINTY_CLASS(DInterpolation) +IMPLEMENT_CLASS(DInterpolation, true, true, false) IMPLEMENT_POINTERS_START(DInterpolation) IMPLEMENT_POINTER(Next) IMPLEMENT_POINTER(Prev) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(DSectorPlaneInterpolation) -IMPLEMENT_CLASS(DSectorScrollInterpolation) -IMPLEMENT_CLASS(DWallScrollInterpolation) -IMPLEMENT_CLASS(DPolyobjInterpolation) +IMPLEMENT_CLASS(DSectorPlaneInterpolation, false, false, false) +IMPLEMENT_CLASS(DSectorScrollInterpolation, false, false, false) +IMPLEMENT_CLASS(DWallScrollInterpolation, false, false, false) +IMPLEMENT_CLASS(DPolyobjInterpolation, false, false, false) //========================================================================== // diff --git a/src/s_advsound.cpp b/src/s_advsound.cpp index 0db9365c2..1aedcb1fb 100644 --- a/src/s_advsound.cpp +++ b/src/s_advsound.cpp @@ -2213,7 +2213,7 @@ private: int NextCheck; }; -IMPLEMENT_CLASS (AAmbientSound) +IMPLEMENT_CLASS(AAmbientSound, false, false, false) //========================================================================== // @@ -2470,7 +2470,7 @@ public: virtual void PostBeginPlay(); }; -IMPLEMENT_CLASS(AMusicChanger) +IMPLEMENT_CLASS(AMusicChanger, false, false, false) bool AMusicChanger::DoTriggerAction (AActor *triggerer, int activationType) { diff --git a/src/s_sndseq.cpp b/src/s_sndseq.cpp index baf33fd0c..449baa4d6 100644 --- a/src/s_sndseq.cpp +++ b/src/s_sndseq.cpp @@ -285,7 +285,7 @@ void DSeqNode::SerializeSequences (FSerializer &arc) arc("sndseqlisthead", SequenceListHead); } -IMPLEMENT_POINTY_CLASS(DSeqNode) +IMPLEMENT_CLASS(DSeqNode, false, true, false) IMPLEMENT_POINTERS_START(DSeqNode) IMPLEMENT_POINTER(m_ChildSeqNode) @@ -429,7 +429,7 @@ FName DSeqNode::GetSequenceName () const return Sequences[m_Sequence]->SeqName; } -IMPLEMENT_POINTY_CLASS(DSeqActorNode) +IMPLEMENT_CLASS(DSeqActorNode, false, true, false) IMPLEMENT_POINTERS_START(DSeqActorNode) IMPLEMENT_POINTER(m_Actor) @@ -441,7 +441,7 @@ void DSeqActorNode::Serialize(FSerializer &arc) arc("actor", m_Actor); } -IMPLEMENT_CLASS (DSeqPolyNode) +IMPLEMENT_CLASS(DSeqPolyNode, false, false, false) void DSeqPolyNode::Serialize(FSerializer &arc) { @@ -449,7 +449,7 @@ void DSeqPolyNode::Serialize(FSerializer &arc) arc("poly", m_Poly); } -IMPLEMENT_CLASS (DSeqSectorNode) +IMPLEMENT_CLASS(DSeqSectorNode, false, false, false) void DSeqSectorNode::Serialize(FSerializer &arc) { diff --git a/src/scripting/decorate/olddecorations.cpp b/src/scripting/decorate/olddecorations.cpp index 6ccd0051a..63ae447cf 100644 --- a/src/scripting/decorate/olddecorations.cpp +++ b/src/scripting/decorate/olddecorations.cpp @@ -95,7 +95,8 @@ public: // The special was already executed by TryPickup, so do nothing here } }; -IMPLEMENT_CLASS (AFakeInventory) + +IMPLEMENT_CLASS(AFakeInventory, false, false, false) // PUBLIC FUNCTION PROTOTYPES ---------------------------------------------- diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index 22728749c..3070c1b4d 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -34,15 +34,15 @@ #include #include "vm.h" -IMPLEMENT_CLASS(VMException) -IMPLEMENT_ABSTRACT_POINTY_CLASS(VMFunction) +IMPLEMENT_CLASS(VMException, false, false, false) +IMPLEMENT_CLASS(VMFunction, true, true, false) IMPLEMENT_POINTERS_START(VMFunction) IMPLEMENT_POINTER(Proto) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(VMScriptFunction) -IMPLEMENT_CLASS(VMNativeFunction) +IMPLEMENT_CLASS(VMScriptFunction, false, false, false) +IMPLEMENT_CLASS(VMNativeFunction, false, false, false) VMScriptFunction::VMScriptFunction(FName name) { diff --git a/src/v_video.cpp b/src/v_video.cpp index b1f1ced9c..f79f31b1c 100644 --- a/src/v_video.cpp +++ b/src/v_video.cpp @@ -69,8 +69,8 @@ int active_con_scale(); FRenderer *Renderer; -IMPLEMENT_ABSTRACT_CLASS (DCanvas) -IMPLEMENT_ABSTRACT_CLASS (DFrameBuffer) +IMPLEMENT_CLASS(DCanvas, true, false, false) +IMPLEMENT_CLASS(DFrameBuffer, true, false, false) #if defined(_DEBUG) && defined(_M_IX86) #define DBGBREAK { __asm int 3 } @@ -106,11 +106,11 @@ public: float Gamma; }; -IMPLEMENT_ABSTRACT_CLASS (DDummyFrameBuffer) +IMPLEMENT_CLASS(DDummyFrameBuffer, true, false, false) // SimpleCanvas is not really abstract, but this macro does not // try to generate a CreateNew() function. -IMPLEMENT_ABSTRACT_CLASS (DSimpleCanvas) +IMPLEMENT_CLASS(DSimpleCanvas, true, false, false) class FPaletteTester : public FTexture { diff --git a/src/win32/fb_d3d9.cpp b/src/win32/fb_d3d9.cpp index 10ab11c72..a79ef1a3f 100644 --- a/src/win32/fb_d3d9.cpp +++ b/src/win32/fb_d3d9.cpp @@ -91,7 +91,7 @@ // TYPES ------------------------------------------------------------------- -IMPLEMENT_CLASS(D3DFB) +IMPLEMENT_CLASS(D3DFB, false, false, false) struct D3DFB::PackedTexture { diff --git a/src/win32/fb_ddraw.cpp b/src/win32/fb_ddraw.cpp index 7cc603786..dcd6d37a9 100644 --- a/src/win32/fb_ddraw.cpp +++ b/src/win32/fb_ddraw.cpp @@ -61,7 +61,7 @@ // TYPES ------------------------------------------------------------------- -IMPLEMENT_CLASS(DDrawFB) +IMPLEMENT_CLASS(DDrawFB, false, false, false) // EXTERNAL FUNCTION PROTOTYPES -------------------------------------------- diff --git a/src/win32/win32video.cpp b/src/win32/win32video.cpp index 8eb2349ec..b8aded5c1 100644 --- a/src/win32/win32video.cpp +++ b/src/win32/win32video.cpp @@ -78,7 +78,7 @@ // TYPES ------------------------------------------------------------------- -IMPLEMENT_ABSTRACT_CLASS(BaseWinFB) +IMPLEMENT_CLASS(BaseWinFB, true, false, false) typedef IDirect3D9 *(WINAPI *DIRECT3DCREATE9FUNC)(UINT SDKVersion); typedef HRESULT (WINAPI *DIRECTDRAWCREATEFUNC)(GUID FAR *lpGUID, LPDIRECTDRAW FAR *lplpDD, IUnknown FAR *pUnkOuter); From ad19e439a6ea1a6adf38d8489cd1c356fbcf15fe Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Tue, 1 Nov 2016 04:58:10 +0100 Subject: [PATCH 210/255] Implement a general and easy-to-use way of overriding native virtual functions --- src/dobject.h | 76 ++++++++++++++++++++++++++++++++++++++++++++++++++- 1 file changed, 75 insertions(+), 1 deletion(-) diff --git a/src/dobject.h b/src/dobject.h index dd0d40772..fb631c91c 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -125,8 +125,8 @@ enum EInPlace { EC_InPlace }; public: \ virtual PClass *StaticType() const; \ static ClassReg RegistrationInfo, * const RegistrationInfoPtr; \ -private: \ typedef parent Super; \ +private: \ typedef cls ThisClass; #define DECLARE_ABSTRACT_CLASS_WITH_META(cls,parent,meta) \ @@ -151,6 +151,34 @@ protected: \ #define HAS_FIELDS \ static void InitNativeFields(); +// Templates really are powerful +#define VMEXPORTED_NATIVES_START \ + template class ExportedNatives : public ExportedNatives {}; \ + template<> class ExportedNatives { \ + protected: ExportedNatives() {} \ + public: \ + static ExportedNatives *Get() { static ExportedNatives *Instance = nullptr; if (Instance == nullptr) Instance = new ExportedNatives; return Instance; } \ + ExportedNatives(const ExportedNatives&) = delete; \ + ExportedNatives(ExportedNatives&&) = delete; + +#define VMEXPORTED_NATIVES_FUNC(func) \ + template ret func(void *ptr, args ... arglist) { return ret(); } + +#define VMEXPORTED_NATIVES_END }; + +#define VMEXPORT_NATIVES_START(cls, parent) \ + template<> class ExportedNatives : public ExportedNatives { \ + protected: ExportedNatives() {} \ + public: \ + static ExportedNatives *Get() { static ExportedNatives *Instance = nullptr; if (Instance == nullptr) Instance = new ExportedNatives; return Instance; } \ + ExportedNatives(const ExportedNatives&) = delete; \ + ExportedNatives(ExportedNatives&&) = delete; + +#define VMEXPORT_NATIVES_FUNC(func) \ + template ret func(void *ptr, args ... arglist) { return static_cast(ptr)->object::##func(arglist...); } + +#define VMEXPORT_NATIVES_END(cls) }; + #if defined(_MSC_VER) # pragma section(".creg$u",read) # define _DECLARE_TI(cls) __declspec(allocate(".creg$u")) ClassReg * const cls::RegistrationInfoPtr = &cls::RegistrationInfo; @@ -576,6 +604,52 @@ protected: } }; +template +class DVMObject : public T +{ +public: + static char *FormatClassName() + { + static char *name = nullptr; + if (name == nullptr) + { + name = new char[64]; + mysnprintf(name, 64, "DVMObject<%s>", Super::RegistrationInfo.Name); + atterm([]{ delete[] DVMObject::RegistrationInfo.Name; }); + } + return name; + } + + virtual PClass *StaticType() const + { + return RegistrationInfo.MyClass; + } + static ClassReg RegistrationInfo; + static ClassReg * const RegistrationInfoPtr; + typedef T Super; + +private: + typedef DVMObject ThisClass; + static void InPlaceConstructor(void *mem) + { + new((EInPlace *)mem) DVMObject; + } +}; + +template +ClassReg DVMObject::RegistrationInfo = +{ + nullptr, + DVMObject::FormatClassName(), + &DVMObject::Super::RegistrationInfo, + nullptr, + DVMObject::InPlaceConstructor, + nullptr, + sizeof(DVMObject), + DVMObject::MetaClassNum +}; +template _DECLARE_TI(DVMObject) + // When you write to a pointer to an Object, you must call this for // proper bookkeeping in case the Object holding this pointer has // already been processed by the GC. From 33e2c74642192ca8bacd5f763a37fb0593c54258 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 6 Nov 2016 11:28:01 +0100 Subject: [PATCH 211/255] Provide a way to expose a native class to zscript for virtual functions overriding --- src/dobject.cpp | 17 +++++++++-------- src/dobject.h | 11 ++++++++--- src/dobjtype.cpp | 8 ++++++-- src/dobjtype.h | 1 + 4 files changed, 24 insertions(+), 13 deletions(-) diff --git a/src/dobject.cpp b/src/dobject.cpp index d057a71d3..e21d07526 100644 --- a/src/dobject.cpp +++ b/src/dobject.cpp @@ -57,14 +57,15 @@ ClassReg DObject::RegistrationInfo = { - NULL, // MyClass - "DObject", // Name - NULL, // ParentType - NULL, // Pointers - &DObject::InPlaceConstructor, // ConstructNative - &DObject::InitNativeFields, - sizeof(DObject), // SizeOf - CLASSREG_PClass, // MetaClassNum + nullptr, // MyClass + "DObject", // Name + nullptr, // ParentType + &DVMObject::RegistrationInfo, // VMExport + nullptr, // Pointers + &DObject::InPlaceConstructor, // ConstructNative + &DObject::InitNativeFields, // InitNatives + sizeof(DObject), // SizeOf + CLASSREG_PClass, // MetaClassNum }; _DECLARE_TI(DObject) diff --git a/src/dobject.h b/src/dobject.h index fb631c91c..24ba4997c 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -109,6 +109,7 @@ struct ClassReg PClass *MyClass; const char *Name; ClassReg *ParentType; + ClassReg *VMExport; const size_t *Pointers; void (*ConstructNative)(void *); void(*InitNatives)(); @@ -186,11 +187,12 @@ protected: \ # define _DECLARE_TI(cls) ClassReg * const cls::RegistrationInfoPtr __attribute__((section(SECTION_CREG))) = &cls::RegistrationInfo; #endif -#define _IMP_PCLASS(cls, ptrs, create, initn) \ +#define _IMP_PCLASS(cls, ptrs, create, initn, vmexport) \ ClassReg cls::RegistrationInfo = {\ nullptr, \ #cls, \ &cls::Super::RegistrationInfo, \ + vmexport, \ ptrs, \ create, \ initn, \ @@ -199,9 +201,9 @@ protected: \ _DECLARE_TI(cls) \ PClass *cls::StaticType() const { return RegistrationInfo.MyClass; } -#define IMPLEMENT_CLASS(cls, isabstract, ptrs, fields) \ +#define IMPLEMENT_CLASS(cls, isabstract, ptrs, fields, vmexport) \ _X_CONSTRUCTOR_##isabstract##(cls) \ - _IMP_PCLASS(cls, _X_POINTERS_##ptrs##(cls), _X_ABSTRACT_##isabstract##(cls), _X_FIELDS_##fields##(cls)) + _IMP_PCLASS(cls, _X_POINTERS_##ptrs##(cls), _X_ABSTRACT_##isabstract##(cls), _X_FIELDS_##fields##(cls), _X_VMEXPORT_##vmexport##(cls)) // Taking the address of a field in an object at address 1 instead of // address 0 keeps GCC from complaining about possible misuse of offsetof. @@ -218,6 +220,8 @@ protected: \ #define _X_CONSTRUCTOR_false(cls) void cls::InPlaceConstructor(void *mem) { new((EInPlace *)mem) cls; } #define _X_ABSTRACT_true(cls) nullptr #define _X_ABSTRACT_false(cls) cls::InPlaceConstructor +#define _X_VMEXPORT_true(cls) &DVMObject::RegistrationInfo +#define _X_VMEXPORT_false(cls) nullptr enum EObjectFlags { @@ -643,6 +647,7 @@ ClassReg DVMObject::RegistrationInfo = DVMObject::FormatClassName(), &DVMObject::Super::RegistrationInfo, nullptr, + nullptr, DVMObject::InPlaceConstructor, nullptr, sizeof(DVMObject), diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 9d3022966..89b9986cc 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2847,7 +2847,7 @@ PClass *ClassReg::RegisterClass() assert(0 && "Class registry has an invalid meta class identifier"); } - if (metaclasses[MetaClassNum]->MyClass == NULL) + if (metaclasses[MetaClassNum]->MyClass == nullptr) { // Make sure the meta class is already registered before registering this one metaclasses[MetaClassNum]->RegisterClass(); } @@ -2855,10 +2855,14 @@ PClass *ClassReg::RegisterClass() SetupClass(cls); cls->InsertIntoHash(); - if (ParentType != NULL) + if (ParentType != nullptr) { cls->ParentClass = ParentType->RegisterClass(); } + if (VMExport != nullptr) + { + cls->VMExported = VMExport->RegisterClass(); + } return cls; } diff --git a/src/dobjtype.h b/src/dobjtype.h index d907feeeb..e1f95a828 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -769,6 +769,7 @@ public: // Per-class information ------------------------------------- PClass *ParentClass; // the class this class derives from + PClass *VMExported; // this is here to allow script classes to override native virtual functions const size_t *Pointers; // object pointers defined by this class *only* const size_t *FlatPointers; // object pointers defined by this class and all its superclasses; not initialized by default BYTE *Defaults; From 7dbc4710f1e7bce2af53f9e6b9212e0f9e6d375e Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 6 Nov 2016 19:43:19 +0100 Subject: [PATCH 212/255] Add the new argument to all uses of the implement macro --- src/b_bot.cpp | 2 +- src/c_dispatch.cpp | 4 +- src/d_dehacked.cpp | 2 +- src/decallib.cpp | 10 ++-- src/dobjgc.cpp | 2 +- src/dobjtype.cpp | 72 +++++++++++------------ src/dsectoreffect.cpp | 8 +-- src/dthinker.cpp | 4 +- src/fragglescript/t_func.cpp | 2 +- src/fragglescript/t_prepro.cpp | 2 +- src/fragglescript/t_script.cpp | 6 +- src/fragglescript/t_variable.cpp | 2 +- src/g_doom/a_scriptedmarine.cpp | 2 +- src/g_heretic/a_chicken.cpp | 2 +- src/g_heretic/a_hereticartifacts.cpp | 4 +- src/g_heretic/a_hereticweaps.cpp | 20 +++---- src/g_heretic/a_ironlich.cpp | 2 +- src/g_hexen/a_boostarmor.cpp | 2 +- src/g_hexen/a_clericflame.cpp | 2 +- src/g_hexen/a_clericholy.cpp | 4 +- src/g_hexen/a_clericstaff.cpp | 2 +- src/g_hexen/a_fighteraxe.cpp | 2 +- src/g_hexen/a_fighterplayer.cpp | 6 +- src/g_hexen/a_fighterquietus.cpp | 2 +- src/g_hexen/a_flechette.cpp | 14 ++--- src/g_hexen/a_healingradius.cpp | 2 +- src/g_hexen/a_heresiarch.cpp | 10 ++-- src/g_hexen/a_hexenspecialdecs.cpp | 6 +- src/g_hexen/a_magecone.cpp | 2 +- src/g_hexen/a_magelightning.cpp | 4 +- src/g_hexen/a_magestaff.cpp | 4 +- src/g_hexen/a_pig.cpp | 2 +- src/g_hexen/a_spike.cpp | 2 +- src/g_hexen/a_summon.cpp | 2 +- src/g_hexen/a_teleportother.cpp | 4 +- src/g_level.cpp | 2 +- src/g_raven/a_artitele.cpp | 2 +- src/g_raven/a_minotaur.cpp | 4 +- src/g_shared/a_action.cpp | 6 +- src/g_shared/a_armor.cpp | 10 ++-- src/g_shared/a_artifacts.cpp | 54 ++++++++--------- src/g_shared/a_bridge.cpp | 4 +- src/g_shared/a_camera.cpp | 4 +- src/g_shared/a_debris.cpp | 2 +- src/g_shared/a_decals.cpp | 6 +- src/g_shared/a_fastprojectile.cpp | 2 +- src/g_shared/a_flashfader.cpp | 2 +- src/g_shared/a_fountain.cpp | 2 +- src/g_shared/a_hatetarget.cpp | 2 +- src/g_shared/a_keys.cpp | 2 +- src/g_shared/a_lightning.cpp | 2 +- src/g_shared/a_mapmarker.cpp | 2 +- src/g_shared/a_morph.cpp | 4 +- src/g_shared/a_movingcamera.cpp | 10 ++-- src/g_shared/a_pickups.cpp | 26 ++++---- src/g_shared/a_puzzleitems.cpp | 4 +- src/g_shared/a_quake.cpp | 2 +- src/g_shared/a_randomspawner.cpp | 2 +- src/g_shared/a_secrettrigger.cpp | 2 +- src/g_shared/a_sectoraction.cpp | 24 ++++---- src/g_shared/a_setcolor.cpp | 4 +- src/g_shared/a_skies.cpp | 12 ++-- src/g_shared/a_soundenvironment.cpp | 2 +- src/g_shared/a_soundsequence.cpp | 4 +- src/g_shared/a_spark.cpp | 2 +- src/g_shared/a_specialspot.cpp | 4 +- src/g_shared/a_waterzone.cpp | 2 +- src/g_shared/a_weaponpiece.cpp | 6 +- src/g_shared/a_weapons.cpp | 6 +- src/g_shared/hudmessages.cpp | 8 +-- src/g_shared/sbarinfo.cpp | 2 +- src/g_shared/shared_sbar.cpp | 2 +- src/g_strife/a_coin.cpp | 2 +- src/g_strife/a_loremaster.cpp | 2 +- src/g_strife/a_programmer.cpp | 2 +- src/g_strife/a_rebels.cpp | 2 +- src/g_strife/a_spectral.cpp | 2 +- src/g_strife/a_strifeitems.cpp | 28 ++++----- src/g_strife/a_strifestuff.cpp | 6 +- src/g_strife/a_strifeweapons.cpp | 6 +- src/g_strife/strife_sbar.cpp | 2 +- src/info.cpp | 2 +- src/intermission/intermission.cpp | 12 ++-- src/m_argv.cpp | 2 +- src/m_cheat.cpp | 2 +- src/menu/colorpickermenu.cpp | 2 +- src/menu/joystickmenu.cpp | 2 +- src/menu/listmenu.cpp | 2 +- src/menu/loadsavemenu.cpp | 6 +- src/menu/menu.cpp | 2 +- src/menu/menuinput.cpp | 2 +- src/menu/messagebox.cpp | 10 ++-- src/menu/optionmenu.cpp | 6 +- src/menu/optionmenuitems.h | 2 +- src/menu/playermenu.cpp | 2 +- src/menu/readthis.cpp | 2 +- src/menu/videomenu.cpp | 2 +- src/p_acs.cpp | 6 +- src/p_buildmap.cpp | 2 +- src/p_ceiling.cpp | 2 +- src/p_conversation.cpp | 2 +- src/p_doors.cpp | 4 +- src/p_floor.cpp | 10 ++-- src/p_lights.cpp | 16 ++--- src/p_mobj.cpp | 4 +- src/p_pillar.cpp | 2 +- src/p_plats.cpp | 2 +- src/p_pspr.cpp | 2 +- src/p_pusher.cpp | 2 +- src/p_scroll.cpp | 2 +- src/p_spec.cpp | 4 +- src/p_switch.cpp | 2 +- src/p_teleport.cpp | 2 +- src/p_user.cpp | 6 +- src/po_man.cpp | 10 ++-- src/posix/sdl/sdlvideo.cpp | 2 +- src/r_data/r_interpolate.cpp | 10 ++-- src/s_advsound.cpp | 4 +- src/s_sndseq.cpp | 8 +-- src/scripting/decorate/olddecorations.cpp | 2 +- src/scripting/vm/vmframe.cpp | 8 +-- src/v_video.cpp | 8 +-- src/win32/fb_d3d9.cpp | 2 +- src/win32/fb_ddraw.cpp | 2 +- src/win32/win32video.cpp | 2 +- 125 files changed, 346 insertions(+), 346 deletions(-) diff --git a/src/b_bot.cpp b/src/b_bot.cpp index 42b34f1df..93d71092d 100644 --- a/src/b_bot.cpp +++ b/src/b_bot.cpp @@ -15,7 +15,7 @@ #include "serializer.h" #include "d_player.h" -IMPLEMENT_CLASS(DBot, false, true, false) +IMPLEMENT_CLASS(DBot, false, true, false, false) IMPLEMENT_POINTERS_START(DBot) IMPLEMENT_POINTER(dest) diff --git a/src/c_dispatch.cpp b/src/c_dispatch.cpp index e7ccc8922..71aeea0fa 100644 --- a/src/c_dispatch.cpp +++ b/src/c_dispatch.cpp @@ -187,7 +187,7 @@ static const char *KeyConfCommands[] = // CODE -------------------------------------------------------------------- -IMPLEMENT_CLASS(DWaitingCommand, false, false, false) +IMPLEMENT_CLASS(DWaitingCommand, false, false, false, false) void DWaitingCommand::Serialize(FSerializer &arc) { @@ -225,7 +225,7 @@ void DWaitingCommand::Tick () } } -IMPLEMENT_CLASS(DStoredCommand, false, false, false) +IMPLEMENT_CLASS(DStoredCommand, false, false, false, false) DStoredCommand::DStoredCommand () { diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index afaf7001b..8258a656e 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -231,7 +231,7 @@ DehInfo deh = // from the original actor's defaults. The original actor is then changed to // spawn the new class. -IMPLEMENT_CLASS(ADehackedPickup, false, true, false) +IMPLEMENT_CLASS(ADehackedPickup, false, true, false, false) IMPLEMENT_POINTERS_START(ADehackedPickup) IMPLEMENT_POINTER(RealPickup) diff --git a/src/decallib.cpp b/src/decallib.cpp index 626497062..970bd7458 100644 --- a/src/decallib.cpp +++ b/src/decallib.cpp @@ -119,7 +119,7 @@ protected: DDecalThinker () : DThinker (STAT_DECALTHINKER) {} }; -IMPLEMENT_CLASS(DDecalThinker, false, true, false) +IMPLEMENT_CLASS(DDecalThinker, false, true, false, false) IMPLEMENT_POINTERS_START(DDecalThinker) IMPLEMENT_POINTER(TheDecal) @@ -1153,7 +1153,7 @@ FDecalAnimator::~FDecalAnimator () { } -IMPLEMENT_CLASS(DDecalFader, false, false, false) +IMPLEMENT_CLASS(DDecalFader, false, false, false, false) void DDecalFader::Serialize(FSerializer &arc) { @@ -1202,7 +1202,7 @@ DThinker *FDecalFaderAnim::CreateThinker (DBaseDecal *actor, side_t *wall) const return fader; } -IMPLEMENT_CLASS(DDecalStretcher, false, false, false) +IMPLEMENT_CLASS(DDecalStretcher, false, false, false, false) void DDecalStretcher::Serialize(FSerializer &arc) { @@ -1290,7 +1290,7 @@ void DDecalStretcher::Tick () } } -IMPLEMENT_CLASS(DDecalSlider, false, false, false) +IMPLEMENT_CLASS(DDecalSlider, false, false, false, false) void DDecalSlider::Serialize(FSerializer &arc) { @@ -1370,7 +1370,7 @@ FDecalAnimator *FDecalLib::FindAnimator (const char *name) return NULL; } -IMPLEMENT_CLASS(DDecalColorer, false, false, false) +IMPLEMENT_CLASS(DDecalColorer, false, false, false, false) void DDecalColorer::Serialize(FSerializer &arc) { diff --git a/src/dobjgc.cpp b/src/dobjgc.cpp index fa59392d5..fa8723e90 100644 --- a/src/dobjgc.cpp +++ b/src/dobjgc.cpp @@ -126,7 +126,7 @@ public: int SideNum; }; -IMPLEMENT_CLASS(DSectorMarker, false, false, false) +IMPLEMENT_CLASS(DSectorMarker, false, false, false, false) // EXTERNAL FUNCTION PROTOTYPES -------------------------------------------- diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 89b9986cc..71bfd542b 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -93,8 +93,8 @@ static const size_t TheEnd = ~(size_t)0; // CODE -------------------------------------------------------------------- -IMPLEMENT_CLASS(PErrorType, false, false, false) -IMPLEMENT_CLASS(PVoidType, false, false, false) +IMPLEMENT_CLASS(PErrorType, false, false, false, false) +IMPLEMENT_CLASS(PVoidType, false, false, false, false) void DumpTypeTable() { @@ -141,7 +141,7 @@ void DumpTypeTable() /* PClassType *************************************************************/ -IMPLEMENT_CLASS(PClassType, false, false, false) +IMPLEMENT_CLASS(PClassType, false, false, false, false) //========================================================================== // @@ -169,7 +169,7 @@ void PClassType::Derive(PClass *newclass) /* PClassClass ************************************************************/ -IMPLEMENT_CLASS(PClassClass, false, false, false) +IMPLEMENT_CLASS(PClassClass, false, false, false, false) //========================================================================== // @@ -187,7 +187,7 @@ PClassClass::PClassClass() /* PType ******************************************************************/ -IMPLEMENT_CLASS(PType, true, true, false) +IMPLEMENT_CLASS(PType, true, true, false, false) IMPLEMENT_POINTERS_START(PType) IMPLEMENT_POINTER(HashNext) @@ -614,7 +614,7 @@ void PType::StaticInit() /* PBasicType *************************************************************/ -IMPLEMENT_CLASS(PBasicType, true, false, false) +IMPLEMENT_CLASS(PBasicType, true, false, false, false) //========================================================================== // @@ -640,11 +640,11 @@ PBasicType::PBasicType(unsigned int size, unsigned int align) /* PCompoundType **********************************************************/ -IMPLEMENT_CLASS(PCompoundType, true, false, false) +IMPLEMENT_CLASS(PCompoundType, true, false, false, false) /* PNamedType *************************************************************/ -IMPLEMENT_CLASS(PNamedType, true, true, false) +IMPLEMENT_CLASS(PNamedType, true, true, false, false) IMPLEMENT_POINTERS_START(PNamedType) IMPLEMENT_POINTER(Outer) @@ -692,7 +692,7 @@ FString PNamedType::QualifiedName() const /* PInt *******************************************************************/ -IMPLEMENT_CLASS(PInt, false, false, false) +IMPLEMENT_CLASS(PInt, false, false, false, false) //========================================================================== // @@ -931,7 +931,7 @@ double PInt::GetValueFloat(void *addr) const /* PBool ******************************************************************/ -IMPLEMENT_CLASS(PBool, false, false, false) +IMPLEMENT_CLASS(PBool, false, false, false, false) //========================================================================== // @@ -952,7 +952,7 @@ PBool::PBool() /* PFloat *****************************************************************/ -IMPLEMENT_CLASS(PFloat, false, false, false) +IMPLEMENT_CLASS(PFloat, false, false, false, false) //========================================================================== // @@ -1202,7 +1202,7 @@ void PFloat::SetOps() /* PString ****************************************************************/ -IMPLEMENT_CLASS(PString, false, false, false) +IMPLEMENT_CLASS(PString, false, false, false, false) //========================================================================== // @@ -1299,7 +1299,7 @@ void PString::DestroyValue(void *addr) const /* PName ******************************************************************/ -IMPLEMENT_CLASS(PName, false, false, false) +IMPLEMENT_CLASS(PName, false, false, false, false) //========================================================================== // @@ -1349,7 +1349,7 @@ bool PName::ReadValue(FSerializer &ar, const char *key, void *addr) const /* PSound *****************************************************************/ -IMPLEMENT_CLASS(PSound, false, false, false) +IMPLEMENT_CLASS(PSound, false, false, false, false) //========================================================================== // @@ -1399,7 +1399,7 @@ bool PSound::ReadValue(FSerializer &ar, const char *key, void *addr) const /* PColor *****************************************************************/ -IMPLEMENT_CLASS(PColor, false, false, false) +IMPLEMENT_CLASS(PColor, false, false, false, false) //========================================================================== // @@ -1416,7 +1416,7 @@ PColor::PColor() /* PStatePointer **********************************************************/ -IMPLEMENT_CLASS(PStatePointer, false, false, false) +IMPLEMENT_CLASS(PStatePointer, false, false, false, false) //========================================================================== // @@ -1460,7 +1460,7 @@ bool PStatePointer::ReadValue(FSerializer &ar, const char *key, void *addr) cons /* PPointer ***************************************************************/ -IMPLEMENT_CLASS(PPointer, false, true, false) +IMPLEMENT_CLASS(PPointer, false, true, false, false) IMPLEMENT_POINTERS_START(PPointer) IMPLEMENT_POINTER(PointedType) @@ -1591,7 +1591,7 @@ PPointer *NewPointer(PType *type, bool isconst) /* PClassPointer **********************************************************/ -IMPLEMENT_CLASS(PClassPointer, false, true, false) +IMPLEMENT_CLASS(PClassPointer, false, true, false, false) IMPLEMENT_POINTERS_START(PClassPointer) IMPLEMENT_POINTER(ClassRestriction) @@ -1672,7 +1672,7 @@ PClassPointer *NewClassPointer(PClass *restrict) /* PEnum ******************************************************************/ -IMPLEMENT_CLASS(PEnum, false, true, false) +IMPLEMENT_CLASS(PEnum, false, true, false, false) IMPLEMENT_POINTERS_START(PEnum) IMPLEMENT_POINTER(ValueType) @@ -1725,7 +1725,7 @@ PEnum *NewEnum(FName name, PTypeBase *outer) /* PArray *****************************************************************/ -IMPLEMENT_CLASS(PArray, false, true, false) +IMPLEMENT_CLASS(PArray, false, true, false, false) IMPLEMENT_POINTERS_START(PArray) IMPLEMENT_POINTER(ElementType) @@ -1874,7 +1874,7 @@ PArray *NewArray(PType *type, unsigned int count) /* PVector ****************************************************************/ -IMPLEMENT_CLASS(PVector, false, false, false) +IMPLEMENT_CLASS(PVector, false, false, false, false) //========================================================================== // @@ -1924,7 +1924,7 @@ PVector *NewVector(unsigned int size) /* PDynArray **************************************************************/ -IMPLEMENT_CLASS(PDynArray, false, true, false) +IMPLEMENT_CLASS(PDynArray, false, true, false, false) IMPLEMENT_POINTERS_START(PDynArray) IMPLEMENT_POINTER(ElementType) @@ -2007,7 +2007,7 @@ PDynArray *NewDynArray(PType *type) /* PMap *******************************************************************/ -IMPLEMENT_CLASS(PMap, false, true, false) +IMPLEMENT_CLASS(PMap, false, true, false, false) IMPLEMENT_POINTERS_START(PMap) IMPLEMENT_POINTER(KeyType) @@ -2091,7 +2091,7 @@ PMap *NewMap(PType *keytype, PType *valuetype) /* PStruct ****************************************************************/ -IMPLEMENT_CLASS(PStruct, false, false, false) +IMPLEMENT_CLASS(PStruct, false, false, false, false) //========================================================================== // @@ -2312,7 +2312,7 @@ PStruct *NewStruct(FName name, PTypeBase *outer) /* PField *****************************************************************/ -IMPLEMENT_CLASS(PField, false, false, false) +IMPLEMENT_CLASS(PField, false, false, false, false) //========================================================================== // @@ -2357,7 +2357,7 @@ PField::PField(FName name, PType *type, DWORD flags, size_t offset, int bitvalue /* PPrototype *************************************************************/ -IMPLEMENT_CLASS(PPrototype, false, false, false) +IMPLEMENT_CLASS(PPrototype, false, false, false, false) //========================================================================== // @@ -2443,7 +2443,7 @@ PPrototype *NewPrototype(const TArray &rettypes, const TArray /* PFunction **************************************************************/ -IMPLEMENT_CLASS(PFunction, false, false, false) +IMPLEMENT_CLASS(PFunction, false, false, false, false) //========================================================================== // @@ -2501,7 +2501,7 @@ unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArra /* PClass *****************************************************************/ -IMPLEMENT_CLASS(PClass, false, true, false) +IMPLEMENT_CLASS(PClass, false, true, false, false) IMPLEMENT_POINTERS_START(PClass) IMPLEMENT_POINTER(ParentClass) @@ -3424,19 +3424,19 @@ CCMD(typetable) // Symbol tables ------------------------------------------------------------ -IMPLEMENT_CLASS(PTypeBase, true, false, false); -IMPLEMENT_CLASS(PSymbol, true, false, false); -IMPLEMENT_CLASS(PSymbolConst, false, false, false); -IMPLEMENT_CLASS(PSymbolConstNumeric, false, false, false); -IMPLEMENT_CLASS(PSymbolConstString, false, false, false); -IMPLEMENT_CLASS(PSymbolTreeNode, false, false, false) -IMPLEMENT_CLASS(PSymbolType, false, true, false) +IMPLEMENT_CLASS(PTypeBase, true, false, false, false); +IMPLEMENT_CLASS(PSymbol, true, false, false, false); +IMPLEMENT_CLASS(PSymbolConst, false, false, false, false); +IMPLEMENT_CLASS(PSymbolConstNumeric, false, false, false, false); +IMPLEMENT_CLASS(PSymbolConstString, false, false, false, false); +IMPLEMENT_CLASS(PSymbolTreeNode, false, false, false, false) +IMPLEMENT_CLASS(PSymbolType, false, true, false, false) IMPLEMENT_POINTERS_START(PSymbolType) IMPLEMENT_POINTER(Type) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(PSymbolVMFunction, false, true, false) +IMPLEMENT_CLASS(PSymbolVMFunction, false, true, false, false) IMPLEMENT_POINTERS_START(PSymbolVMFunction) IMPLEMENT_POINTER(Function) diff --git a/src/dsectoreffect.cpp b/src/dsectoreffect.cpp index e07f9eace..700a407fd 100644 --- a/src/dsectoreffect.cpp +++ b/src/dsectoreffect.cpp @@ -31,7 +31,7 @@ #include "serializer.h" #include "doomstat.h" -IMPLEMENT_CLASS(DSectorEffect, false, false, false) +IMPLEMENT_CLASS(DSectorEffect, false, false, false, false) DSectorEffect::DSectorEffect () : DThinker(STAT_SECTOREFFECT) @@ -71,7 +71,7 @@ void DSectorEffect::Serialize(FSerializer &arc) arc("sector", m_Sector); } -IMPLEMENT_CLASS(DMover, false, true, false) +IMPLEMENT_CLASS(DMover, false, true, false, false) IMPLEMENT_POINTERS_START(DMover) IMPLEMENT_POINTER(interpolation) @@ -108,7 +108,7 @@ void DMover::StopInterpolation(bool force) } } -IMPLEMENT_CLASS(DMovingFloor, false, false, false) +IMPLEMENT_CLASS(DMovingFloor, false, false, false, false) DMovingFloor::DMovingFloor () { @@ -121,7 +121,7 @@ DMovingFloor::DMovingFloor (sector_t *sector) interpolation = sector->SetInterpolation(sector_t::FloorMove, true); } -IMPLEMENT_CLASS(DMovingCeiling, false, false, false) +IMPLEMENT_CLASS(DMovingCeiling, false, false, false, false) DMovingCeiling::DMovingCeiling () { diff --git a/src/dthinker.cpp b/src/dthinker.cpp index 246b9ed2c..9c87c46b4 100644 --- a/src/dthinker.cpp +++ b/src/dthinker.cpp @@ -47,7 +47,7 @@ extern cycle_t BotSupportCycles; extern cycle_t ActionCycles; extern int BotWTG; -IMPLEMENT_CLASS(DThinker, false, false, false) +IMPLEMENT_CLASS(DThinker, false, false, false, false) DThinker *NextToThink; @@ -538,7 +538,7 @@ public: } }; -IMPLEMENT_CLASS(DThinkerIterator, false, false, false); +IMPLEMENT_CLASS(DThinkerIterator, false, false, false, false); DEFINE_ACTION_FUNCTION(DThinkerIterator, Create) { PARAM_PROLOGUE; diff --git a/src/fragglescript/t_func.cpp b/src/fragglescript/t_func.cpp index 737376ecb..ddc1a4bd4 100644 --- a/src/fragglescript/t_func.cpp +++ b/src/fragglescript/t_func.cpp @@ -1785,7 +1785,7 @@ public: void Destroy() { Super::Destroy(); m_Sector->lightingdata=NULL; } }; -IMPLEMENT_CLASS(DLightLevel, false, false, false) +IMPLEMENT_CLASS(DLightLevel, false, false, false, false) void DLightLevel::Serialize(FSerializer &arc) { diff --git a/src/fragglescript/t_prepro.cpp b/src/fragglescript/t_prepro.cpp index 0a3ec6a0d..2129df54f 100644 --- a/src/fragglescript/t_prepro.cpp +++ b/src/fragglescript/t_prepro.cpp @@ -71,7 +71,7 @@ // //========================================================================== -IMPLEMENT_CLASS(DFsSection, false, true, false) +IMPLEMENT_CLASS(DFsSection, false, true, false, false) IMPLEMENT_POINTERS_START(DFsSection) IMPLEMENT_POINTER(next) diff --git a/src/fragglescript/t_script.cpp b/src/fragglescript/t_script.cpp index 326cad621..a40122623 100644 --- a/src/fragglescript/t_script.cpp +++ b/src/fragglescript/t_script.cpp @@ -99,7 +99,7 @@ AActor *trigger_obj; // //========================================================================== -IMPLEMENT_CLASS(DFsScript, false, true, false) +IMPLEMENT_CLASS(DFsScript, false, true, false, false) IMPLEMENT_POINTERS_START(DFsScript) IMPLEMENT_POINTER(parent) @@ -269,7 +269,7 @@ void DFsScript::ParseScript(char *position) // //========================================================================== -IMPLEMENT_CLASS(DRunningScript, false, true, false) +IMPLEMENT_CLASS(DRunningScript, false, true, false, false) IMPLEMENT_POINTERS_START(DRunningScript) IMPLEMENT_POINTER(prev) @@ -380,7 +380,7 @@ void DRunningScript::Serialize(FSerializer &arc) // //========================================================================== -IMPLEMENT_CLASS(DFraggleThinker, false, true, false) +IMPLEMENT_CLASS(DFraggleThinker, false, true, false, false) IMPLEMENT_POINTERS_START(DFraggleThinker) IMPLEMENT_POINTER(RunningScripts) diff --git a/src/fragglescript/t_variable.cpp b/src/fragglescript/t_variable.cpp index cebf0160c..23d24b78a 100644 --- a/src/fragglescript/t_variable.cpp +++ b/src/fragglescript/t_variable.cpp @@ -179,7 +179,7 @@ AActor* actorvalue(const svalue_t &svalue) // //========================================================================== -IMPLEMENT_CLASS(DFsVariable, false, true, false) +IMPLEMENT_CLASS(DFsVariable, false, true, false, false) IMPLEMENT_POINTERS_START(DFsVariable) IMPLEMENT_POINTER(next) diff --git a/src/g_doom/a_scriptedmarine.cpp b/src/g_doom/a_scriptedmarine.cpp index 134271395..da2c7f791 100644 --- a/src/g_doom/a_scriptedmarine.cpp +++ b/src/g_doom/a_scriptedmarine.cpp @@ -19,7 +19,7 @@ static FRandom pr_m_gunshot ("SMarineGunshot"); static FRandom pr_m_saw ("SMarineSaw"); static FRandom pr_m_fireshotgun2 ("SMarineFireSSG"); -IMPLEMENT_CLASS(AScriptedMarine, false, false, false) +IMPLEMENT_CLASS(AScriptedMarine, false, false, false, false) void AScriptedMarine::Serialize(FSerializer &arc) { diff --git a/src/g_heretic/a_chicken.cpp b/src/g_heretic/a_chicken.cpp index 762d10594..fa26f7315 100644 --- a/src/g_heretic/a_chicken.cpp +++ b/src/g_heretic/a_chicken.cpp @@ -29,7 +29,7 @@ public: void MorphPlayerThink (); }; -IMPLEMENT_CLASS(AChickenPlayer, false, false, false) +IMPLEMENT_CLASS(AChickenPlayer, false, false, false, false) void AChickenPlayer::MorphPlayerThink () { diff --git a/src/g_heretic/a_hereticartifacts.cpp b/src/g_heretic/a_hereticartifacts.cpp index 9078d0940..169d0e771 100644 --- a/src/g_heretic/a_hereticartifacts.cpp +++ b/src/g_heretic/a_hereticartifacts.cpp @@ -17,7 +17,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiTomeOfPower, false, false, false) +IMPLEMENT_CLASS(AArtiTomeOfPower, false, false, false, false) bool AArtiTomeOfPower::Use (bool pickup) { @@ -63,7 +63,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiTimeBomb, false, false, false) +IMPLEMENT_CLASS(AArtiTimeBomb, false, false, false, false) bool AArtiTimeBomb::Use (bool pickup) { diff --git a/src/g_heretic/a_hereticweaps.cpp b/src/g_heretic/a_hereticweaps.cpp index b32056374..38991b87d 100644 --- a/src/g_heretic/a_hereticweaps.cpp +++ b/src/g_heretic/a_hereticweaps.cpp @@ -358,7 +358,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AMaceFX4, false, false, false) +IMPLEMENT_CLASS(AMaceFX4, false, false, false, false) int AMaceFX4::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -726,7 +726,7 @@ void ABlasterFX1::Effect () } } -IMPLEMENT_CLASS(ABlasterFX1, false, false, false) +IMPLEMENT_CLASS(ABlasterFX1, false, false, false, false) // Ripper ------------------------------------------------------------------- @@ -738,7 +738,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(ARipper, false, false, false) +IMPLEMENT_CLASS(ARipper, false, false, false, false) int ARipper::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -828,7 +828,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AHornRodFX2, false, false, false) +IMPLEMENT_CLASS(AHornRodFX2, false, false, false, false) int AHornRodFX2::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -849,7 +849,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(ARainPillar, false, false, false) +IMPLEMENT_CLASS(ARainPillar, false, false, false, false) int ARainPillar::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -871,7 +871,7 @@ public: TObjPtr Rain1, Rain2; }; -IMPLEMENT_CLASS(ARainTracker, false, false, false) +IMPLEMENT_CLASS(ARainTracker, false, false, false, false) void ARainTracker::Serialize(FSerializer &arc) { @@ -1158,8 +1158,8 @@ public: void EndPowerup (); }; -IMPLEMENT_CLASS(APhoenixRod, false, false, false) -IMPLEMENT_CLASS(APhoenixRodPowered, false, false, false) +IMPLEMENT_CLASS(APhoenixRod, false, false, false, false) +IMPLEMENT_CLASS(APhoenixRodPowered, false, false, false, false) void APhoenixRodPowered::EndPowerup () { @@ -1177,7 +1177,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(APhoenixFX1, false, false, false) +IMPLEMENT_CLASS(APhoenixFX1, false, false, false, false) int APhoenixFX1::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -1198,7 +1198,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(APhoenixFX2, false, false, false) +IMPLEMENT_CLASS(APhoenixFX2, false, false, false, false) int APhoenixFX2::DoSpecialDamage (AActor *target, int damage, FName damagetype) { diff --git a/src/g_heretic/a_ironlich.cpp b/src/g_heretic/a_ironlich.cpp index 3870219d9..8068c251b 100644 --- a/src/g_heretic/a_ironlich.cpp +++ b/src/g_heretic/a_ironlich.cpp @@ -22,7 +22,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AWhirlwind, false, false, false) +IMPLEMENT_CLASS(AWhirlwind, false, false, false, false) int AWhirlwind::DoSpecialDamage (AActor *target, int damage, FName damagetype) { diff --git a/src/g_hexen/a_boostarmor.cpp b/src/g_hexen/a_boostarmor.cpp index 77fbf3dbd..1323af8a5 100644 --- a/src/g_hexen/a_boostarmor.cpp +++ b/src/g_hexen/a_boostarmor.cpp @@ -17,7 +17,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiBoostArmor, false, false, false) +IMPLEMENT_CLASS(AArtiBoostArmor, false, false, false, false) bool AArtiBoostArmor::Use (bool pickup) { diff --git a/src/g_hexen/a_clericflame.cpp b/src/g_hexen/a_clericflame.cpp index c0c6cb3ed..f0e9c16b2 100644 --- a/src/g_hexen/a_clericflame.cpp +++ b/src/g_hexen/a_clericflame.cpp @@ -33,7 +33,7 @@ public: void Effect (); }; -IMPLEMENT_CLASS(ACFlameMissile, false, false, false) +IMPLEMENT_CLASS(ACFlameMissile, false, false, false, false) void ACFlameMissile::BeginPlay () { diff --git a/src/g_hexen/a_clericholy.cpp b/src/g_hexen/a_clericholy.cpp index 931c75e89..d09c3f6aa 100644 --- a/src/g_hexen/a_clericholy.cpp +++ b/src/g_hexen/a_clericholy.cpp @@ -58,11 +58,11 @@ public: BYTE CHolyCount; }; -IMPLEMENT_CLASS(ACWeapWraithverge, false, false, false) +IMPLEMENT_CLASS(ACWeapWraithverge, false, false, false, false) // Holy Spirit -------------------------------------------------------------- -IMPLEMENT_CLASS(AHolySpirit, false, false, false) +IMPLEMENT_CLASS(AHolySpirit, false, false, false, false) bool AHolySpirit::Slam(AActor *thing) { diff --git a/src/g_hexen/a_clericstaff.cpp b/src/g_hexen/a_clericstaff.cpp index 940a87884..a4050a1ef 100644 --- a/src/g_hexen/a_clericstaff.cpp +++ b/src/g_hexen/a_clericstaff.cpp @@ -25,7 +25,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(ACStaffMissile, false, false, false) +IMPLEMENT_CLASS(ACStaffMissile, false, false, false, false) int ACStaffMissile::DoSpecialDamage (AActor *target, int damage, FName damagetype) { diff --git a/src/g_hexen/a_fighteraxe.cpp b/src/g_hexen/a_fighteraxe.cpp index 89e317012..4260f4eb4 100644 --- a/src/g_hexen/a_fighteraxe.cpp +++ b/src/g_hexen/a_fighteraxe.cpp @@ -38,7 +38,7 @@ public: FState *GetAtkState (bool hold); }; -IMPLEMENT_CLASS(AFWeapAxe, false, false, false) +IMPLEMENT_CLASS(AFWeapAxe, false, false, false, false) FState *AFWeapAxe::GetUpState () { diff --git a/src/g_hexen/a_fighterplayer.cpp b/src/g_hexen/a_fighterplayer.cpp index 7e18f9c28..ff4348520 100644 --- a/src/g_hexen/a_fighterplayer.cpp +++ b/src/g_hexen/a_fighterplayer.cpp @@ -11,9 +11,9 @@ #include "vm.h" */ -IMPLEMENT_CLASS(AFighterWeapon, false, false, false) -IMPLEMENT_CLASS(AClericWeapon, false, false, false) -IMPLEMENT_CLASS(AMageWeapon, false, false, false) +IMPLEMENT_CLASS(AFighterWeapon, false, false, false, false) +IMPLEMENT_CLASS(AClericWeapon, false, false, false, false) +IMPLEMENT_CLASS(AMageWeapon, false, false, false, false) static FRandom pr_fpatk ("FPunchAttack"); diff --git a/src/g_hexen/a_fighterquietus.cpp b/src/g_hexen/a_fighterquietus.cpp index c000a9faf..c900794ed 100644 --- a/src/g_hexen/a_fighterquietus.cpp +++ b/src/g_hexen/a_fighterquietus.cpp @@ -59,7 +59,7 @@ public: int DoSpecialDamage(AActor *victim, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AFSwordMissile, false, false, false) +IMPLEMENT_CLASS(AFSwordMissile, false, false, false, false) int AFSwordMissile::DoSpecialDamage(AActor *victim, int damage, FName damagetype) { diff --git a/src/g_hexen/a_flechette.cpp b/src/g_hexen/a_flechette.cpp index 3da16db9c..335842887 100644 --- a/src/g_hexen/a_flechette.cpp +++ b/src/g_hexen/a_flechette.cpp @@ -24,7 +24,7 @@ DECLARE_ACTION(A_CheckThrowBomb) // Poison Bag Artifact (Flechette) ------------------------------------------ -IMPLEMENT_CLASS(AArtiPoisonBag, false, false, false) +IMPLEMENT_CLASS(AArtiPoisonBag, false, false, false, false) // Poison Bag 1 (The Cleric's) ---------------------------------------------- @@ -35,7 +35,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiPoisonBag1, false, false, false) +IMPLEMENT_CLASS(AArtiPoisonBag1, false, false, false, false) bool AArtiPoisonBag1::Use (bool pickup) { @@ -60,7 +60,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiPoisonBag2, false, false, false) +IMPLEMENT_CLASS(AArtiPoisonBag2, false, false, false, false) bool AArtiPoisonBag2::Use (bool pickup) { @@ -85,7 +85,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiPoisonBag3, false, false, false) +IMPLEMENT_CLASS(AArtiPoisonBag3, false, false, false, false) bool AArtiPoisonBag3::Use (bool pickup) { @@ -136,7 +136,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiPoisonBagGiver, false, false, false) +IMPLEMENT_CLASS(AArtiPoisonBagGiver, false, false, false, false) bool AArtiPoisonBagGiver::Use (bool pickup) { @@ -167,7 +167,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiPoisonBagShooter, false, false, false) +IMPLEMENT_CLASS(AArtiPoisonBagShooter, false, false, false, false) bool AArtiPoisonBagShooter::Use (bool pickup) { @@ -296,7 +296,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS(APoisonCloud, false, false, false) +IMPLEMENT_CLASS(APoisonCloud, false, false, false, false) void APoisonCloud::BeginPlay () { diff --git a/src/g_hexen/a_healingradius.cpp b/src/g_hexen/a_healingradius.cpp index 3d4eef0ae..25efbc3ca 100644 --- a/src/g_hexen/a_healingradius.cpp +++ b/src/g_hexen/a_healingradius.cpp @@ -25,7 +25,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiHealingRadius, false, false, false) +IMPLEMENT_CLASS(AArtiHealingRadius, false, false, false, false) bool AArtiHealingRadius::Use (bool pickup) { diff --git a/src/g_hexen/a_heresiarch.cpp b/src/g_hexen/a_heresiarch.cpp index 964fdd44f..32ad9ab69 100644 --- a/src/g_hexen/a_heresiarch.cpp +++ b/src/g_hexen/a_heresiarch.cpp @@ -72,7 +72,7 @@ public: void Die (AActor *source, AActor *inflictor, int dmgflags); }; -IMPLEMENT_CLASS(AHeresiarch, false, false, false) +IMPLEMENT_CLASS(AHeresiarch, false, false, false, false) void AHeresiarch::Serialize(FSerializer &arc) { @@ -122,7 +122,7 @@ public: } }; -IMPLEMENT_CLASS(ASorcBall, false, false, false) +IMPLEMENT_CLASS(ASorcBall, false, false, false, false) // First ball (purple) - fires projectiles ---------------------------------- @@ -140,7 +140,7 @@ public: virtual void CastSorcererSpell (); }; -IMPLEMENT_CLASS(ASorcBall1, false, false, false) +IMPLEMENT_CLASS(ASorcBall1, false, false, false, false) // Second ball (blue) - generates the shield -------------------------------- @@ -156,7 +156,7 @@ public: virtual void CastSorcererSpell (); }; -IMPLEMENT_CLASS(ASorcBall2, false, false, false) +IMPLEMENT_CLASS(ASorcBall2, false, false, false, false) // Third ball (green) - summons Bishops ------------------------------------- @@ -172,7 +172,7 @@ public: virtual void CastSorcererSpell (); }; -IMPLEMENT_CLASS(ASorcBall3, false, false, false) +IMPLEMENT_CLASS(ASorcBall3, false, false, false, false) // Sorcerer spell 1 (The burning, bouncing head thing) ---------------------- diff --git a/src/g_hexen/a_hexenspecialdecs.cpp b/src/g_hexen/a_hexenspecialdecs.cpp index cad6f617d..6d441ba57 100644 --- a/src/g_hexen/a_hexenspecialdecs.cpp +++ b/src/g_hexen/a_hexenspecialdecs.cpp @@ -39,7 +39,7 @@ public: void HitFloor (); }; -IMPLEMENT_CLASS(APottery1, false, false, false) +IMPLEMENT_CLASS(APottery1, false, false, false, false) void APottery1::HitFloor () { @@ -136,7 +136,7 @@ public: void PostBeginPlay (); }; -IMPLEMENT_CLASS(AZCorpseLynchedNoHeart, false, false, false) +IMPLEMENT_CLASS(AZCorpseLynchedNoHeart, false, false, false, false) void AZCorpseLynchedNoHeart::PostBeginPlay () { @@ -344,7 +344,7 @@ public: void Activate (AActor *activator); }; -IMPLEMENT_CLASS(AZBell, false, false, false) +IMPLEMENT_CLASS(AZBell, false, false, false, false) void AZBell::Activate (AActor *activator) { diff --git a/src/g_hexen/a_magecone.cpp b/src/g_hexen/a_magecone.cpp index b2dd969b7..f2b97fcd9 100644 --- a/src/g_hexen/a_magecone.cpp +++ b/src/g_hexen/a_magecone.cpp @@ -32,7 +32,7 @@ public: int DoSpecialDamage (AActor *victim, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AFrostMissile, false, false, false) +IMPLEMENT_CLASS(AFrostMissile, false, false, false, false) int AFrostMissile::DoSpecialDamage (AActor *victim, int damage, FName damagetype) { diff --git a/src/g_hexen/a_magelightning.cpp b/src/g_hexen/a_magelightning.cpp index 039755ff5..7e11b64ed 100644 --- a/src/g_hexen/a_magelightning.cpp +++ b/src/g_hexen/a_magelightning.cpp @@ -34,7 +34,7 @@ public: int SpecialMissileHit (AActor *victim); }; -IMPLEMENT_CLASS(ALightning, false, false, false) +IMPLEMENT_CLASS(ALightning, false, false, false, false) int ALightning::SpecialMissileHit (AActor *thing) { @@ -87,7 +87,7 @@ public: int SpecialMissileHit (AActor *thing); }; -IMPLEMENT_CLASS(ALightningZap, false, false, false) +IMPLEMENT_CLASS(ALightningZap, false, false, false, false) int ALightningZap::SpecialMissileHit (AActor *thing) { diff --git a/src/g_hexen/a_magestaff.cpp b/src/g_hexen/a_magestaff.cpp index 2660117c3..acef2e5cd 100644 --- a/src/g_hexen/a_magestaff.cpp +++ b/src/g_hexen/a_magestaff.cpp @@ -56,7 +56,7 @@ public: BYTE MStaffCount; }; -IMPLEMENT_CLASS(AMWeapBloodscourge, false, false, false) +IMPLEMENT_CLASS(AMWeapBloodscourge, false, false, false, false) // Mage Staff FX2 (Bloodscourge) -------------------------------------------- @@ -68,7 +68,7 @@ public: bool SpecialBlastHandling (AActor *source, double strength); }; -IMPLEMENT_CLASS(AMageStaffFX2, false, false, false) +IMPLEMENT_CLASS(AMageStaffFX2, false, false, false, false) int AMageStaffFX2::SpecialMissileHit (AActor *victim) { diff --git a/src/g_hexen/a_pig.cpp b/src/g_hexen/a_pig.cpp index c12a9f50a..a0a0cc844 100644 --- a/src/g_hexen/a_pig.cpp +++ b/src/g_hexen/a_pig.cpp @@ -27,7 +27,7 @@ public: void MorphPlayerThink (); }; -IMPLEMENT_CLASS(APigPlayer, false, false, false) +IMPLEMENT_CLASS(APigPlayer, false, false, false, false) void APigPlayer::MorphPlayerThink () { diff --git a/src/g_hexen/a_spike.cpp b/src/g_hexen/a_spike.cpp index 1559467db..9b2cb5d6e 100644 --- a/src/g_hexen/a_spike.cpp +++ b/src/g_hexen/a_spike.cpp @@ -31,7 +31,7 @@ public: TObjPtr DirtClump; }; -IMPLEMENT_CLASS(AThrustFloor, false, true, false) +IMPLEMENT_CLASS(AThrustFloor, false, true, false, false) IMPLEMENT_POINTERS_START(AThrustFloor) IMPLEMENT_POINTER(DirtClump) diff --git a/src/g_hexen/a_summon.cpp b/src/g_hexen/a_summon.cpp index e98c52352..7c0746c91 100644 --- a/src/g_hexen/a_summon.cpp +++ b/src/g_hexen/a_summon.cpp @@ -21,7 +21,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiDarkServant, false, false, false) +IMPLEMENT_CLASS(AArtiDarkServant, false, false, false, false) //============================================================================ // diff --git a/src/g_hexen/a_teleportother.cpp b/src/g_hexen/a_teleportother.cpp index 68ba73bc4..4eeba53f9 100644 --- a/src/g_hexen/a_teleportother.cpp +++ b/src/g_hexen/a_teleportother.cpp @@ -34,7 +34,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiTeleportOther, false, false, false) +IMPLEMENT_CLASS(AArtiTeleportOther, false, false, false, false) // Teleport Other FX -------------------------------------------------------- @@ -45,7 +45,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(ATelOtherFX1, false, false, false) +IMPLEMENT_CLASS(ATelOtherFX1, false, false, false, false) static void TeloSpawn (AActor *source, const char *type) { diff --git a/src/g_level.cpp b/src/g_level.cpp index e377d70f6..9a955a03e 100644 --- a/src/g_level.cpp +++ b/src/g_level.cpp @@ -903,7 +903,7 @@ public: void Tick (); }; -IMPLEMENT_CLASS(DAutosaver, false, false, false) +IMPLEMENT_CLASS(DAutosaver, false, false, false, false) void DAutosaver::Tick () { diff --git a/src/g_raven/a_artitele.cpp b/src/g_raven/a_artitele.cpp index 0910e5f23..35387df45 100644 --- a/src/g_raven/a_artitele.cpp +++ b/src/g_raven/a_artitele.cpp @@ -23,7 +23,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AArtiTeleport, false, false, false) +IMPLEMENT_CLASS(AArtiTeleport, false, false, false, false) bool AArtiTeleport::Use (bool pickup) { diff --git a/src/g_raven/a_minotaur.cpp b/src/g_raven/a_minotaur.cpp index c906234c8..36946ba87 100644 --- a/src/g_raven/a_minotaur.cpp +++ b/src/g_raven/a_minotaur.cpp @@ -31,7 +31,7 @@ void P_MinotaurSlam (AActor *source, AActor *target); DECLARE_ACTION(A_MinotaurLook) -IMPLEMENT_CLASS(AMinotaur, false, false, false) +IMPLEMENT_CLASS(AMinotaur, false, false, false, false) void AMinotaur::Tick () { @@ -72,7 +72,7 @@ int AMinotaur::DoSpecialDamage (AActor *target, int damage, FName damagetype) // Minotaur Friend ---------------------------------------------------------- -IMPLEMENT_CLASS(AMinotaurFriend, false, false, false) +IMPLEMENT_CLASS(AMinotaurFriend, false, false, false, false) void AMinotaurFriend::BeginPlay () { diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index 20ab4aad0..61be39a0e 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -29,7 +29,7 @@ public: void Deactivate (AActor *activator); }; -IMPLEMENT_CLASS(ASwitchableDecoration, false, false, false) +IMPLEMENT_CLASS(ASwitchableDecoration, false, false, false, false) void ASwitchableDecoration::Activate (AActor *activator) { @@ -50,7 +50,7 @@ public: void Deactivate (AActor *activator) {} }; -IMPLEMENT_CLASS(ASwitchingDecoration, false, false, false) +IMPLEMENT_CLASS(ASwitchingDecoration, false, false, false, false) //---------------------------------------------------------------------------- // @@ -304,7 +304,7 @@ private: DCorpsePointer () {} }; -IMPLEMENT_CLASS(DCorpsePointer, false, true, false) +IMPLEMENT_CLASS(DCorpsePointer, false, true, false, false) IMPLEMENT_POINTERS_START(DCorpsePointer) IMPLEMENT_POINTER(Corpse) diff --git a/src/g_shared/a_armor.cpp b/src/g_shared/a_armor.cpp index b1935bd1d..636441a9d 100644 --- a/src/g_shared/a_armor.cpp +++ b/src/g_shared/a_armor.cpp @@ -8,11 +8,11 @@ #include "d_player.h" #include "serializer.h" -IMPLEMENT_CLASS(AArmor, false, false, false) -IMPLEMENT_CLASS(ABasicArmor, false, false, false) -IMPLEMENT_CLASS(ABasicArmorPickup, false, false, false) -IMPLEMENT_CLASS(ABasicArmorBonus, false, false, false) -IMPLEMENT_CLASS(AHexenArmor, false, false, false) +IMPLEMENT_CLASS(AArmor, false, false, false, false) +IMPLEMENT_CLASS(ABasicArmor, false, false, false, false) +IMPLEMENT_CLASS(ABasicArmorPickup, false, false, false, false) +IMPLEMENT_CLASS(ABasicArmorBonus, false, false, false, false) +IMPLEMENT_CLASS(AHexenArmor, false, false, false, false) //=========================================================================== // diff --git a/src/g_shared/a_artifacts.cpp b/src/g_shared/a_artifacts.cpp index 97771021d..7cf05613a 100644 --- a/src/g_shared/a_artifacts.cpp +++ b/src/g_shared/a_artifacts.cpp @@ -40,11 +40,11 @@ static FRandom pr_torch ("Torch"); #define TIMEFREEZE_TICS ( 12 * TICRATE ) */ -IMPLEMENT_CLASS(APowerup, false, false, false) +IMPLEMENT_CLASS(APowerup, false, false, false, false) // Powerup-Giver ------------------------------------------------------------- -IMPLEMENT_CLASS(PClassPowerupGiver, false, false, false) +IMPLEMENT_CLASS(PClassPowerupGiver, false, false, false, false) void PClassPowerupGiver::ReplaceClassRef(PClass *oldclass, PClass *newclass) { @@ -376,7 +376,7 @@ bool APowerup::GetNoTeleportFreeze () // Invulnerability Powerup --------------------------------------------------- -IMPLEMENT_CLASS(APowerInvulnerable, false, false, false) +IMPLEMENT_CLASS(APowerInvulnerable, false, false, false, false) //=========================================================================== // @@ -513,7 +513,7 @@ int APowerInvulnerable::AlterWeaponSprite (visstyle_t *vis) // Strength (aka Berserk) Powerup -------------------------------------------- -IMPLEMENT_CLASS(APowerStrength, false, false, false) +IMPLEMENT_CLASS(APowerStrength, false, false, false, false) //=========================================================================== // @@ -578,7 +578,7 @@ PalEntry APowerStrength::GetBlend () // Invisibility Powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerInvisibility, false, false, false) +IMPLEMENT_CLASS(APowerInvisibility, false, false, false, false) // Invisibility flag combos #define INVISIBILITY_FLAGS1 (MF_SHADOW) @@ -783,7 +783,7 @@ bool APowerInvisibility::HandlePickup (AInventory *item) // Ironfeet Powerup ---------------------------------------------------------- -IMPLEMENT_CLASS(APowerIronFeet, false, false, false) +IMPLEMENT_CLASS(APowerIronFeet, false, false, false, false) //=========================================================================== // @@ -820,7 +820,7 @@ void APowerIronFeet::DoEffect () // Strife Environment Suit Powerup ------------------------------------------- -IMPLEMENT_CLASS(APowerMask, false, false, false) +IMPLEMENT_CLASS(APowerMask, false, false, false, false) //=========================================================================== // @@ -857,7 +857,7 @@ void APowerMask::DoEffect () // Light-Amp Powerup --------------------------------------------------------- -IMPLEMENT_CLASS(APowerLightAmp, false, false, false) +IMPLEMENT_CLASS(APowerLightAmp, false, false, false, false) //=========================================================================== // @@ -899,7 +899,7 @@ void APowerLightAmp::EndEffect () // Torch Powerup ------------------------------------------------------------- -IMPLEMENT_CLASS(APowerTorch, false, false, false) +IMPLEMENT_CLASS(APowerTorch, false, false, false, false) //=========================================================================== // @@ -962,7 +962,7 @@ void APowerTorch::DoEffect () // Flight (aka Wings of Wrath) powerup --------------------------------------- -IMPLEMENT_CLASS(APowerFlight, false, false, false) +IMPLEMENT_CLASS(APowerFlight, false, false, false, false) //=========================================================================== // @@ -1102,7 +1102,7 @@ bool APowerFlight::DrawPowerup (int x, int y) // Weapon Level 2 (aka Tome of Power) Powerup -------------------------------- -IMPLEMENT_CLASS(APowerWeaponLevel2, false, false, false) +IMPLEMENT_CLASS(APowerWeaponLevel2, false, false, false, false) //=========================================================================== // @@ -1193,7 +1193,7 @@ public: void Tick (); }; -IMPLEMENT_CLASS(APlayerSpeedTrail, false, false, false) +IMPLEMENT_CLASS(APlayerSpeedTrail, false, false, false, false) //=========================================================================== // @@ -1216,7 +1216,7 @@ void APlayerSpeedTrail::Tick () // Speed Powerup ------------------------------------------------------------- -IMPLEMENT_CLASS(APowerSpeed, false, false, false) +IMPLEMENT_CLASS(APowerSpeed, false, false, false, false) //=========================================================================== // @@ -1303,11 +1303,11 @@ void APowerSpeed::DoEffect () // Minotaur (aka Dark Servant) powerup --------------------------------------- -IMPLEMENT_CLASS(APowerMinotaur, false, false, false) +IMPLEMENT_CLASS(APowerMinotaur, false, false, false, false) // Targeter powerup --------------------------------------------------------- -IMPLEMENT_CLASS(APowerTargeter, false, false, false) +IMPLEMENT_CLASS(APowerTargeter, false, false, false, false) void APowerTargeter::Travelled () { @@ -1422,7 +1422,7 @@ void APowerTargeter::PositionAccuracy () // Frightener Powerup -------------------------------- -IMPLEMENT_CLASS(APowerFrightener, false, false, false) +IMPLEMENT_CLASS(APowerFrightener, false, false, false, false) //=========================================================================== // @@ -1458,7 +1458,7 @@ void APowerFrightener::EndEffect () // Buddha Powerup -------------------------------- -IMPLEMENT_CLASS(APowerBuddha, false, false, false) +IMPLEMENT_CLASS(APowerBuddha, false, false, false, false) //=========================================================================== // @@ -1494,11 +1494,11 @@ void APowerBuddha::EndEffect () // Scanner powerup ---------------------------------------------------------- -IMPLEMENT_CLASS(APowerScanner, false, false, false) +IMPLEMENT_CLASS(APowerScanner, false, false, false, false) // Time freezer powerup ----------------------------------------------------- -IMPLEMENT_CLASS( APowerTimeFreezer, false, false, false) +IMPLEMENT_CLASS( APowerTimeFreezer, false, false, false, false) //=========================================================================== // @@ -1625,7 +1625,7 @@ void APowerTimeFreezer::EndEffect() // Damage powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerDamage, false, false, false) +IMPLEMENT_CLASS(APowerDamage, false, false, false, false) //=========================================================================== // @@ -1682,7 +1682,7 @@ void APowerDamage::ModifyDamage(int damage, FName damageType, int &newdamage, bo // Quarter damage powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerProtection, false, false, false) +IMPLEMENT_CLASS(APowerProtection, false, false, false, false) #define PROTECTION_FLAGS3 (MF3_NORADIUSDMG | MF3_DONTMORPH | MF3_DONTSQUASH | MF3_DONTBLAST | MF3_NOTELEOTHER) #define PROTECTION_FLAGS5 (MF5_NOPAIN | MF5_DONTRIP) @@ -1760,7 +1760,7 @@ void APowerProtection::ModifyDamage(int damage, FName damageType, int &newdamage // Drain rune ------------------------------------------------------- -IMPLEMENT_CLASS(APowerDrain, false, false, false) +IMPLEMENT_CLASS(APowerDrain, false, false, false, false) //=========================================================================== // @@ -1800,7 +1800,7 @@ void APowerDrain::EndEffect( ) // Regeneration rune ------------------------------------------------------- -IMPLEMENT_CLASS(APowerRegeneration, false, false, false) +IMPLEMENT_CLASS(APowerRegeneration, false, false, false, false) //=========================================================================== // @@ -1822,7 +1822,7 @@ void APowerRegeneration::DoEffect() // High jump rune ------------------------------------------------------- -IMPLEMENT_CLASS(APowerHighJump, false, false, false) +IMPLEMENT_CLASS(APowerHighJump, false, false, false, false) //=========================================================================== // @@ -1860,7 +1860,7 @@ void APowerHighJump::EndEffect( ) // Double firing speed rune --------------------------------------------- -IMPLEMENT_CLASS(APowerDoubleFiringSpeed, false, false, false) +IMPLEMENT_CLASS(APowerDoubleFiringSpeed, false, false, false, false) //=========================================================================== // @@ -1898,7 +1898,7 @@ void APowerDoubleFiringSpeed::EndEffect( ) // Morph powerup ------------------------------------------------------ -IMPLEMENT_CLASS(APowerMorph, false, false, false) +IMPLEMENT_CLASS(APowerMorph, false, false, false, false) //=========================================================================== // @@ -2002,7 +2002,7 @@ void APowerMorph::EndEffect( ) // Infinite Ammo Powerup ----------------------------------------------------- -IMPLEMENT_CLASS(APowerInfiniteAmmo, false, false, false) +IMPLEMENT_CLASS(APowerInfiniteAmmo, false, false, false, false) //=========================================================================== // diff --git a/src/g_shared/a_bridge.cpp b/src/g_shared/a_bridge.cpp index 6409a0709..ab0df27e1 100644 --- a/src/g_shared/a_bridge.cpp +++ b/src/g_shared/a_bridge.cpp @@ -41,7 +41,7 @@ public: void Destroy(); }; -IMPLEMENT_CLASS(ACustomBridge, false, false, false) +IMPLEMENT_CLASS(ACustomBridge, false, false, false, false) void ACustomBridge::BeginPlay () { @@ -156,7 +156,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS(AInvisibleBridge, false, false, false) +IMPLEMENT_CLASS(AInvisibleBridge, false, false, false, false) void AInvisibleBridge::BeginPlay () { diff --git a/src/g_shared/a_camera.cpp b/src/g_shared/a_camera.cpp index a29b4b81d..ae34c3cbc 100644 --- a/src/g_shared/a_camera.cpp +++ b/src/g_shared/a_camera.cpp @@ -64,7 +64,7 @@ protected: DAngle Range; }; -IMPLEMENT_CLASS(ASecurityCamera, false, false, false) +IMPLEMENT_CLASS(ASecurityCamera, false, false, false, false) void ASecurityCamera::Serialize(FSerializer &arc) { @@ -124,7 +124,7 @@ protected: DAngle MaxPitchChange; }; -IMPLEMENT_CLASS(AAimingCamera, false, false, false) +IMPLEMENT_CLASS(AAimingCamera, false, false, false, false) void AAimingCamera::Serialize(FSerializer &arc) { diff --git a/src/g_shared/a_debris.cpp b/src/g_shared/a_debris.cpp index 9624ff5d6..3be3c2240 100644 --- a/src/g_shared/a_debris.cpp +++ b/src/g_shared/a_debris.cpp @@ -25,7 +25,7 @@ public: } }; -IMPLEMENT_CLASS(AGlassShard, false, false, false) +IMPLEMENT_CLASS(AGlassShard, false, false, false, false) // Dirt stuff diff --git a/src/g_shared/a_decals.cpp b/src/g_shared/a_decals.cpp index 5347664f5..06563f995 100644 --- a/src/g_shared/a_decals.cpp +++ b/src/g_shared/a_decals.cpp @@ -58,14 +58,14 @@ static int ImpactCount; CVAR (Bool, cl_spreaddecals, true, CVAR_ARCHIVE) -IMPLEMENT_CLASS(DBaseDecal, false, true, false) +IMPLEMENT_CLASS(DBaseDecal, false, true, false, false) IMPLEMENT_POINTERS_START(DBaseDecal) IMPLEMENT_POINTER(WallPrev) IMPLEMENT_POINTER(WallNext) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(DImpactDecal, false, false, false) +IMPLEMENT_CLASS(DImpactDecal, false, false, false, false) DBaseDecal::DBaseDecal () : DThinker(STAT_DECAL), @@ -746,7 +746,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS(ADecal, false, false, false) +IMPLEMENT_CLASS(ADecal, false, false, false, false) void ADecal::BeginPlay () { diff --git a/src/g_shared/a_fastprojectile.cpp b/src/g_shared/a_fastprojectile.cpp index a0774a6f6..ffca8a8fa 100644 --- a/src/g_shared/a_fastprojectile.cpp +++ b/src/g_shared/a_fastprojectile.cpp @@ -7,7 +7,7 @@ #include "b_bot.h" #include "p_checkposition.h" -IMPLEMENT_CLASS(AFastProjectile, false, false, false) +IMPLEMENT_CLASS(AFastProjectile, false, false, false, false) //---------------------------------------------------------------------------- diff --git a/src/g_shared/a_flashfader.cpp b/src/g_shared/a_flashfader.cpp index 8406ec299..8602f7a86 100644 --- a/src/g_shared/a_flashfader.cpp +++ b/src/g_shared/a_flashfader.cpp @@ -3,7 +3,7 @@ #include "d_player.h" #include "serializer.h" -IMPLEMENT_CLASS(DFlashFader, false, true, false) +IMPLEMENT_CLASS(DFlashFader, false, true, false, false) IMPLEMENT_POINTERS_START(DFlashFader) IMPLEMENT_POINTER(ForWho) diff --git a/src/g_shared/a_fountain.cpp b/src/g_shared/a_fountain.cpp index bd415e729..e89745fc7 100644 --- a/src/g_shared/a_fountain.cpp +++ b/src/g_shared/a_fountain.cpp @@ -46,7 +46,7 @@ public: void Deactivate (AActor *activator); }; -IMPLEMENT_CLASS(AParticleFountain, false, false, false) +IMPLEMENT_CLASS(AParticleFountain, false, false, false, false) void AParticleFountain::PostBeginPlay () { diff --git a/src/g_shared/a_hatetarget.cpp b/src/g_shared/a_hatetarget.cpp index 361ccb1f2..7d25bdb31 100644 --- a/src/g_shared/a_hatetarget.cpp +++ b/src/g_shared/a_hatetarget.cpp @@ -46,7 +46,7 @@ public: int TakeSpecialDamage(AActor *inflictor, AActor *source, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AHateTarget, false, false, false) +IMPLEMENT_CLASS(AHateTarget, false, false, false, false) void AHateTarget::BeginPlay() { diff --git a/src/g_shared/a_keys.cpp b/src/g_shared/a_keys.cpp index 07685be31..69fbe48af 100644 --- a/src/g_shared/a_keys.cpp +++ b/src/g_shared/a_keys.cpp @@ -470,7 +470,7 @@ bool P_CheckKeys (AActor *owner, int keynum, bool remote) // //========================================================================== -IMPLEMENT_CLASS(AKey, false, false, false) +IMPLEMENT_CLASS(AKey, false, false, false, false) bool AKey::HandlePickup (AInventory *item) { diff --git a/src/g_shared/a_lightning.cpp b/src/g_shared/a_lightning.cpp index 0fe3683da..f00560fc8 100644 --- a/src/g_shared/a_lightning.cpp +++ b/src/g_shared/a_lightning.cpp @@ -13,7 +13,7 @@ static FRandom pr_lightning ("Lightning"); -IMPLEMENT_CLASS(DLightningThinker, false, false, false) +IMPLEMENT_CLASS(DLightningThinker, false, false, false, false) DLightningThinker::DLightningThinker () : DThinker (STAT_LIGHTNING) diff --git a/src/g_shared/a_mapmarker.cpp b/src/g_shared/a_mapmarker.cpp index 3c4d99b30..d874042c5 100644 --- a/src/g_shared/a_mapmarker.cpp +++ b/src/g_shared/a_mapmarker.cpp @@ -51,7 +51,7 @@ // //-------------------------------------------------------------------------- -IMPLEMENT_CLASS(AMapMarker, false, false, false) +IMPLEMENT_CLASS(AMapMarker, false, false, false, false) void AMapMarker::BeginPlay () { diff --git a/src/g_shared/a_morph.cpp b/src/g_shared/a_morph.cpp index 9ce33e12d..506f18b2f 100644 --- a/src/g_shared/a_morph.cpp +++ b/src/g_shared/a_morph.cpp @@ -616,7 +616,7 @@ void InitAllPowerupEffects(AInventory *item) // Base class for morphing projectiles -------------------------------------- -IMPLEMENT_CLASS(AMorphProjectile, false, false, false) +IMPLEMENT_CLASS(AMorphProjectile, false, false, false, false) int AMorphProjectile::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -650,7 +650,7 @@ void AMorphProjectile::Serialize(FSerializer &arc) // Morphed Monster (you must subclass this to do something useful) --------- -IMPLEMENT_CLASS(AMorphedMonster, false, true, false) +IMPLEMENT_CLASS(AMorphedMonster, false, true, false, false) IMPLEMENT_POINTERS_START(AMorphedMonster) IMPLEMENT_POINTER(UnmorphedMe) diff --git a/src/g_shared/a_movingcamera.cpp b/src/g_shared/a_movingcamera.cpp index 89a1193cc..030f5d368 100644 --- a/src/g_shared/a_movingcamera.cpp +++ b/src/g_shared/a_movingcamera.cpp @@ -66,7 +66,7 @@ public: TObjPtr Next; }; -IMPLEMENT_CLASS(AInterpolationPoint, false, true, false) +IMPLEMENT_CLASS(AInterpolationPoint, false, true, false, false) IMPLEMENT_POINTERS_START(AInterpolationPoint) IMPLEMENT_POINTER(Next) @@ -135,7 +135,7 @@ public: void Tick () {} // Does absolutely nothing itself }; -IMPLEMENT_CLASS(AInterpolationSpecial, false, false, false) +IMPLEMENT_CLASS(AInterpolationSpecial, false, false, false, false) /* == PathFollower: something that follows a camera path @@ -178,7 +178,7 @@ protected: int HoldTime; }; -IMPLEMENT_CLASS(APathFollower, false, true, false) +IMPLEMENT_CLASS(APathFollower, false, true, false, false) IMPLEMENT_POINTERS_START(APathFollower) IMPLEMENT_POINTER(PrevNode) @@ -480,7 +480,7 @@ protected: bool Interpolate (); }; -IMPLEMENT_CLASS(AActorMover, false, false, false) +IMPLEMENT_CLASS(AActorMover, false, false, false, false) void AActorMover::BeginPlay() { @@ -596,7 +596,7 @@ protected: TObjPtr Activator; }; -IMPLEMENT_CLASS(AMovingCamera, false, true, false) +IMPLEMENT_CLASS(AMovingCamera, false, true, false, false) IMPLEMENT_POINTERS_START(AMovingCamera) IMPLEMENT_POINTER(Activator) diff --git a/src/g_shared/a_pickups.cpp b/src/g_shared/a_pickups.cpp index 2b7fcb79a..223a2f75f 100644 --- a/src/g_shared/a_pickups.cpp +++ b/src/g_shared/a_pickups.cpp @@ -24,7 +24,7 @@ static FRandom pr_restore ("RestorePos"); -IMPLEMENT_CLASS(PClassInventory, false, false, false) +IMPLEMENT_CLASS(PClassInventory, false, false, false, false) PClassInventory::PClassInventory() { @@ -71,7 +71,7 @@ void PClassInventory::Finalize(FStateDefinitions &statedef) ((AActor*)Defaults)->flags |= MF_SPECIAL; } -IMPLEMENT_CLASS(PClassAmmo, false, false, false) +IMPLEMENT_CLASS(PClassAmmo, false, false, false, false) PClassAmmo::PClassAmmo() { @@ -87,7 +87,7 @@ void PClassAmmo::DeriveData(PClass *newclass) newc->DropAmount = DropAmount; } -IMPLEMENT_CLASS(AAmmo, false, false, false) +IMPLEMENT_CLASS(AAmmo, false, false, false, false) //=========================================================================== // @@ -470,7 +470,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialPosition) int AInventory::StaticLastMessageTic; const char *AInventory::StaticLastMessage; -IMPLEMENT_CLASS(AInventory, false, true, false) +IMPLEMENT_CLASS(AInventory, false, true, false, false) IMPLEMENT_POINTERS_START(AInventory) IMPLEMENT_POINTER(Owner) @@ -1354,7 +1354,7 @@ bool AInventory::DrawPowerup (int x, int y) /* AArtifact implementation */ /***************************************************************************/ -IMPLEMENT_CLASS(APowerupGiver, false, false, false) +IMPLEMENT_CLASS(APowerupGiver, false, false, false, false) //=========================================================================== // @@ -1644,8 +1644,8 @@ void AInventory::DetachFromOwner () { } -IMPLEMENT_CLASS(AStateProvider, false, false, false) -IMPLEMENT_CLASS(ACustomInventory, false, false, false) +IMPLEMENT_CLASS(AStateProvider, false, false, false, false) +IMPLEMENT_CLASS(ACustomInventory, false, false, false, false) //=========================================================================== // @@ -1690,7 +1690,7 @@ bool ACustomInventory::TryPickup (AActor *&toucher) return useok; } -IMPLEMENT_CLASS(PClassHealth, false, false, false) +IMPLEMENT_CLASS(PClassHealth, false, false, false, false) //=========================================================================== // @@ -1719,7 +1719,7 @@ void PClassHealth::DeriveData(PClass *newclass) newc->LowHealthMessage = LowHealthMessage; } -IMPLEMENT_CLASS(AHealth, false, false, false) +IMPLEMENT_CLASS(AHealth, false, false, false, false) //=========================================================================== // @@ -1762,7 +1762,7 @@ bool AHealth::TryPickup (AActor *&other) return false; } -IMPLEMENT_CLASS(AHealthPickup, false, false, false) +IMPLEMENT_CLASS(AHealthPickup, false, false, false, false) //=========================================================================== // @@ -2015,8 +2015,8 @@ void ABackpackItem::DetachFromOwner () // //=========================================================================== -IMPLEMENT_CLASS(ABackpackItem, false, false, false) -IMPLEMENT_CLASS(AMapRevealer, false, false, false) +IMPLEMENT_CLASS(ABackpackItem, false, false, false, false) +IMPLEMENT_CLASS(AMapRevealer, false, false, false, false) //=========================================================================== // @@ -2041,7 +2041,7 @@ bool AMapRevealer::TryPickup (AActor *&toucher) // //=========================================================================== -IMPLEMENT_CLASS(AScoreItem, false, false, false) +IMPLEMENT_CLASS(AScoreItem, false, false, false, false) //=========================================================================== // diff --git a/src/g_shared/a_puzzleitems.cpp b/src/g_shared/a_puzzleitems.cpp index ba3f90dc8..d243dc73c 100644 --- a/src/g_shared/a_puzzleitems.cpp +++ b/src/g_shared/a_puzzleitems.cpp @@ -8,7 +8,7 @@ #include "doomstat.h" #include "v_font.h" -IMPLEMENT_CLASS(PClassPuzzleItem, false, false, false) +IMPLEMENT_CLASS(PClassPuzzleItem, false, false, false, false) void PClassPuzzleItem::DeriveData(PClass *newclass) { @@ -17,7 +17,7 @@ void PClassPuzzleItem::DeriveData(PClass *newclass) static_cast(newclass)->PuzzFailMessage = PuzzFailMessage; } -IMPLEMENT_CLASS(APuzzleItem, false, false, false) +IMPLEMENT_CLASS(APuzzleItem, false, false, false, false) bool APuzzleItem::HandlePickup (AInventory *item) { diff --git a/src/g_shared/a_quake.cpp b/src/g_shared/a_quake.cpp index d2a2e5e5b..80a53ee08 100644 --- a/src/g_shared/a_quake.cpp +++ b/src/g_shared/a_quake.cpp @@ -14,7 +14,7 @@ static FRandom pr_quake ("Quake"); -IMPLEMENT_CLASS(DEarthquake, false, true, false) +IMPLEMENT_CLASS(DEarthquake, false, true, false, false) IMPLEMENT_POINTERS_START(DEarthquake) IMPLEMENT_POINTER(m_Spot) diff --git a/src/g_shared/a_randomspawner.cpp b/src/g_shared/a_randomspawner.cpp index ca85a1349..2b2c82956 100644 --- a/src/g_shared/a_randomspawner.cpp +++ b/src/g_shared/a_randomspawner.cpp @@ -231,4 +231,4 @@ class ARandomSpawner : public AActor }; -IMPLEMENT_CLASS(ARandomSpawner, false, false, false) +IMPLEMENT_CLASS(ARandomSpawner, false, false, false, false) diff --git a/src/g_shared/a_secrettrigger.cpp b/src/g_shared/a_secrettrigger.cpp index 712856571..372cef07d 100644 --- a/src/g_shared/a_secrettrigger.cpp +++ b/src/g_shared/a_secrettrigger.cpp @@ -50,7 +50,7 @@ public: void Activate (AActor *activator); }; -IMPLEMENT_CLASS(ASecretTrigger, false, false, false) +IMPLEMENT_CLASS(ASecretTrigger, false, false, false, false) void ASecretTrigger::PostBeginPlay () { diff --git a/src/g_shared/a_sectoraction.cpp b/src/g_shared/a_sectoraction.cpp index 88e504aa9..61a69b1b3 100644 --- a/src/g_shared/a_sectoraction.cpp +++ b/src/g_shared/a_sectoraction.cpp @@ -37,7 +37,7 @@ // The base class for sector actions ---------------------------------------- -IMPLEMENT_CLASS(ASectorAction, false, false, false) +IMPLEMENT_CLASS(ASectorAction, false, false, false, false) ASectorAction::ASectorAction (bool activatedByUse) : ActivatedByUse (activatedByUse) {} @@ -142,7 +142,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActEnter, false, false, false) +IMPLEMENT_CLASS(ASecActEnter, false, false, false, false) bool ASecActEnter::DoTriggerAction (AActor *triggerer, int activationType) @@ -160,7 +160,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActExit, false, false, false) +IMPLEMENT_CLASS(ASecActExit, false, false, false, false) bool ASecActExit::DoTriggerAction (AActor *triggerer, int activationType) @@ -181,7 +181,7 @@ public: // Skull Tag uses 9999 for a special that is triggered whenever // the player is on the sector's floor. I think this is more useful. -IMPLEMENT_CLASS(ASecActHitFloor, false, false, false) +IMPLEMENT_CLASS(ASecActHitFloor, false, false, false, false) bool ASecActHitFloor::DoTriggerAction (AActor *triggerer, int activationType) @@ -199,7 +199,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActHitCeil, false, false, false) +IMPLEMENT_CLASS(ASecActHitCeil, false, false, false, false) bool ASecActHitCeil::DoTriggerAction (AActor *triggerer, int activationType) @@ -218,7 +218,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActUse, false, false, false) +IMPLEMENT_CLASS(ASecActUse, false, false, false, false) bool ASecActUse::DoTriggerAction (AActor *triggerer, int activationType) @@ -237,7 +237,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActUseWall, false, false, false) +IMPLEMENT_CLASS(ASecActUseWall, false, false, false, false) bool ASecActUseWall::DoTriggerAction (AActor *triggerer, int activationType) @@ -255,7 +255,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActEyesDive, false, false, false) +IMPLEMENT_CLASS(ASecActEyesDive, false, false, false, false) bool ASecActEyesDive::DoTriggerAction (AActor *triggerer, int activationType) @@ -273,7 +273,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActEyesSurface, false, false, false) +IMPLEMENT_CLASS(ASecActEyesSurface, false, false, false, false) bool ASecActEyesSurface::DoTriggerAction (AActor *triggerer, int activationType) @@ -291,7 +291,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActEyesBelowC, false, false, false) +IMPLEMENT_CLASS(ASecActEyesBelowC, false, false, false, false) bool ASecActEyesBelowC::DoTriggerAction (AActor *triggerer, int activationType) @@ -309,7 +309,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActEyesAboveC, false, false, false) +IMPLEMENT_CLASS(ASecActEyesAboveC, false, false, false, false) bool ASecActEyesAboveC::DoTriggerAction (AActor *triggerer, int activationType) @@ -327,7 +327,7 @@ public: bool DoTriggerAction (AActor *triggerer, int activationType); }; -IMPLEMENT_CLASS(ASecActHitFakeFloor, false, false, false) +IMPLEMENT_CLASS(ASecActHitFakeFloor, false, false, false, false) bool ASecActHitFakeFloor::DoTriggerAction (AActor *triggerer, int activationType) diff --git a/src/g_shared/a_setcolor.cpp b/src/g_shared/a_setcolor.cpp index 579c57706..585b9fcf6 100644 --- a/src/g_shared/a_setcolor.cpp +++ b/src/g_shared/a_setcolor.cpp @@ -15,7 +15,7 @@ class AColorSetter : public AActor }; -IMPLEMENT_CLASS(AColorSetter, false, false, false) +IMPLEMENT_CLASS(AColorSetter, false, false, false, false) class AFadeSetter : public AActor { @@ -30,4 +30,4 @@ class AFadeSetter : public AActor }; -IMPLEMENT_CLASS(AFadeSetter, false, false, false) +IMPLEMENT_CLASS(AFadeSetter, false, false, false, false) diff --git a/src/g_shared/a_skies.cpp b/src/g_shared/a_skies.cpp index f58779387..148a452e0 100644 --- a/src/g_shared/a_skies.cpp +++ b/src/g_shared/a_skies.cpp @@ -42,7 +42,7 @@ // arg0 = Visibility*4 for this skybox -IMPLEMENT_CLASS(ASkyViewpoint, false, false, false) +IMPLEMENT_CLASS(ASkyViewpoint, false, false, false, false) // If this actor has no TID, make it the default sky box void ASkyViewpoint::BeginPlay () @@ -73,7 +73,7 @@ void ASkyViewpoint::Destroy () Super::Destroy(); } -IMPLEMENT_CLASS(ASkyCamCompat, false, false, false) +IMPLEMENT_CLASS(ASkyCamCompat, false, false, false, false) void ASkyCamCompat::BeginPlay() { @@ -98,7 +98,7 @@ public: void PostBeginPlay (); }; -IMPLEMENT_CLASS(ASkyPicker, false, false, false) +IMPLEMENT_CLASS(ASkyPicker, false, false, false, false) void ASkyPicker::PostBeginPlay () { @@ -142,7 +142,7 @@ void ASkyPicker::PostBeginPlay () // arg0 = opacity of plane; 0 = invisible, 255 = fully opaque -IMPLEMENT_CLASS(AStackPoint, false, false, false) +IMPLEMENT_CLASS(AStackPoint, false, false, false, false) void AStackPoint::BeginPlay () { @@ -160,7 +160,7 @@ public: void Destroy (); }; -IMPLEMENT_CLASS(ASectorSilencer, false, false, false) +IMPLEMENT_CLASS(ASectorSilencer, false, false, false, false) void ASectorSilencer::BeginPlay () { @@ -184,7 +184,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS(ASectorFlagSetter, false, false, false) +IMPLEMENT_CLASS(ASectorFlagSetter, false, false, false, false) void ASectorFlagSetter::BeginPlay () { diff --git a/src/g_shared/a_soundenvironment.cpp b/src/g_shared/a_soundenvironment.cpp index 6d381dbe5..8e5cb133b 100644 --- a/src/g_shared/a_soundenvironment.cpp +++ b/src/g_shared/a_soundenvironment.cpp @@ -46,7 +46,7 @@ public: void Activate (AActor *deactivator); }; -IMPLEMENT_CLASS(ASoundEnvironment, false, false, false) +IMPLEMENT_CLASS(ASoundEnvironment, false, false, false, false) void ASoundEnvironment::PostBeginPlay () { diff --git a/src/g_shared/a_soundsequence.cpp b/src/g_shared/a_soundsequence.cpp index 01453fc9c..25380a4c7 100644 --- a/src/g_shared/a_soundsequence.cpp +++ b/src/g_shared/a_soundsequence.cpp @@ -80,7 +80,7 @@ public: TObjPtr Sequence; }; -IMPLEMENT_CLASS(ASoundSequenceSlot, false, true, false) +IMPLEMENT_CLASS(ASoundSequenceSlot, false, true, false, false) IMPLEMENT_POINTERS_START(ASoundSequenceSlot) IMPLEMENT_POINTER(Sequence) @@ -111,7 +111,7 @@ public: void MarkPrecacheSounds () const; }; -IMPLEMENT_CLASS(ASoundSequence, false, false, false) +IMPLEMENT_CLASS(ASoundSequence, false, false, false, false) //========================================================================== // diff --git a/src/g_shared/a_spark.cpp b/src/g_shared/a_spark.cpp index ce6148068..654ad710b 100644 --- a/src/g_shared/a_spark.cpp +++ b/src/g_shared/a_spark.cpp @@ -45,7 +45,7 @@ public: void Activate (AActor *activator); }; -IMPLEMENT_CLASS(ASpark, false, false, false) +IMPLEMENT_CLASS(ASpark, false, false, false, false) void ASpark::Activate (AActor *activator) { diff --git a/src/g_shared/a_specialspot.cpp b/src/g_shared/a_specialspot.cpp index 1011fcb92..86d0b5e8a 100644 --- a/src/g_shared/a_specialspot.cpp +++ b/src/g_shared/a_specialspot.cpp @@ -45,8 +45,8 @@ static FRandom pr_spot ("SpecialSpot"); static FRandom pr_spawnmace ("SpawnMace"); -IMPLEMENT_CLASS(DSpotState, false, false, false) -IMPLEMENT_CLASS(ASpecialSpot, false, false, false) +IMPLEMENT_CLASS(DSpotState, false, false, false, false) +IMPLEMENT_CLASS(ASpecialSpot, false, false, false, false) TObjPtr DSpotState::SpotState; //---------------------------------------------------------------------------- diff --git a/src/g_shared/a_waterzone.cpp b/src/g_shared/a_waterzone.cpp index 65cdf96f6..556d08d7a 100644 --- a/src/g_shared/a_waterzone.cpp +++ b/src/g_shared/a_waterzone.cpp @@ -42,7 +42,7 @@ public: void PostBeginPlay (); }; -IMPLEMENT_CLASS(AWaterZone, false, false, false) +IMPLEMENT_CLASS(AWaterZone, false, false, false, false) void AWaterZone::PostBeginPlay () { diff --git a/src/g_shared/a_weaponpiece.cpp b/src/g_shared/a_weaponpiece.cpp index 68c631d9b..7aa9591e9 100644 --- a/src/g_shared/a_weaponpiece.cpp +++ b/src/g_shared/a_weaponpiece.cpp @@ -3,8 +3,8 @@ #include "doomstat.h" #include "serializer.h" -IMPLEMENT_CLASS(PClassWeaponPiece, false, false, false) -IMPLEMENT_CLASS(AWeaponHolder, false, false, false) +IMPLEMENT_CLASS(PClassWeaponPiece, false, false, false, false) +IMPLEMENT_CLASS(AWeaponHolder, false, false, false, false) void PClassWeaponPiece::ReplaceClassRef(PClass *oldclass, PClass *newclass) { @@ -24,7 +24,7 @@ void AWeaponHolder::Serialize(FSerializer &arc) ("pieceweapon", PieceWeapon); } -IMPLEMENT_CLASS(AWeaponPiece, false, true, false) +IMPLEMENT_CLASS(AWeaponPiece, false, true, false, false) IMPLEMENT_POINTERS_START(AWeaponPiece) IMPLEMENT_POINTER(FullWeapon) diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index adaf4c9e3..9063c6c2c 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -21,7 +21,7 @@ #define BONUSADD 6 -IMPLEMENT_CLASS(AWeapon, false, true, false) +IMPLEMENT_CLASS(AWeapon, false, true, false, false) IMPLEMENT_POINTERS_START(AWeapon) IMPLEMENT_POINTER(Ammo1) @@ -38,7 +38,7 @@ TMap Weapons_hton; static int ntoh_cmp(const void *a, const void *b); -IMPLEMENT_CLASS(PClassWeapon, false, false, false) +IMPLEMENT_CLASS(PClassWeapon, false, false, false, false) PClassWeapon::PClassWeapon() { @@ -791,7 +791,7 @@ FState *AWeapon::GetStateForButtonName (FName button) /* Weapon giver ***********************************************************/ -IMPLEMENT_CLASS(AWeaponGiver, false, false, false) +IMPLEMENT_CLASS(AWeaponGiver, false, false, false, false) void AWeaponGiver::Serialize(FSerializer &arc) { diff --git a/src/g_shared/hudmessages.cpp b/src/g_shared/hudmessages.cpp index 947f68ae4..e9370ae79 100644 --- a/src/g_shared/hudmessages.cpp +++ b/src/g_shared/hudmessages.cpp @@ -44,15 +44,15 @@ EXTERN_CVAR(Int, con_scaletext) int active_con_scaletext(); -IMPLEMENT_CLASS(DHUDMessage, false, true, false) +IMPLEMENT_CLASS(DHUDMessage, false, true, false, false) IMPLEMENT_POINTERS_START(DHUDMessage) IMPLEMENT_POINTER(Next) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(DHUDMessageFadeOut, false, false, false) -IMPLEMENT_CLASS(DHUDMessageFadeInOut, false, false, false) -IMPLEMENT_CLASS(DHUDMessageTypeOnFadeOut, false, false, false) +IMPLEMENT_CLASS(DHUDMessageFadeOut, false, false, false, false) +IMPLEMENT_CLASS(DHUDMessageFadeInOut, false, false, false, false) +IMPLEMENT_CLASS(DHUDMessageTypeOnFadeOut, false, false, false, false) /************************************************************************* * Basic HUD message. Appears and disappears without any special effects * diff --git a/src/g_shared/sbarinfo.cpp b/src/g_shared/sbarinfo.cpp index 7675865ad..304101311 100644 --- a/src/g_shared/sbarinfo.cpp +++ b/src/g_shared/sbarinfo.cpp @@ -1531,7 +1531,7 @@ private: SBarInfoMainBlock *lastPopup; }; -IMPLEMENT_CLASS(DSBarInfo, false, true, false) +IMPLEMENT_CLASS(DSBarInfo, false, true, false, false) IMPLEMENT_POINTERS_START(DSBarInfo) IMPLEMENT_POINTER(ammo1) diff --git a/src/g_shared/shared_sbar.cpp b/src/g_shared/shared_sbar.cpp index abf48c6a1..4bc15d4bf 100644 --- a/src/g_shared/shared_sbar.cpp +++ b/src/g_shared/shared_sbar.cpp @@ -62,7 +62,7 @@ #define XHAIRPICKUPSIZE (2+XHAIRSHRINKSIZE) #define POWERUPICONSIZE 32 -IMPLEMENT_CLASS(DBaseStatusBar, false, true, false) +IMPLEMENT_CLASS(DBaseStatusBar, false, true, false, false) IMPLEMENT_POINTERS_START(DBaseStatusBar) IMPLEMENT_POINTER(Messages[0]) diff --git a/src/g_strife/a_coin.cpp b/src/g_strife/a_coin.cpp index 281c97921..87c4619d3 100644 --- a/src/g_strife/a_coin.cpp +++ b/src/g_strife/a_coin.cpp @@ -6,7 +6,7 @@ // Coin --------------------------------------------------------------------- -IMPLEMENT_CLASS(ACoin, false, false, false) +IMPLEMENT_CLASS(ACoin, false, false, false, false) const char *ACoin::PickupMessage () { diff --git a/src/g_strife/a_loremaster.cpp b/src/g_strife/a_loremaster.cpp index 4bb2fec0e..0f1bef7cc 100644 --- a/src/g_strife/a_loremaster.cpp +++ b/src/g_strife/a_loremaster.cpp @@ -17,7 +17,7 @@ public: int DoSpecialDamage (AActor *victim, int damage, FName damagetype); }; -IMPLEMENT_CLASS(ALoreShot, false, false, false) +IMPLEMENT_CLASS(ALoreShot, false, false, false, false) int ALoreShot::DoSpecialDamage (AActor *victim, int damage, FName damagetype) { diff --git a/src/g_strife/a_programmer.cpp b/src/g_strife/a_programmer.cpp index 70310eef2..c00e7fb01 100644 --- a/src/g_strife/a_programmer.cpp +++ b/src/g_strife/a_programmer.cpp @@ -23,7 +23,7 @@ public: PalEntry GetBlend (); }; -IMPLEMENT_CLASS(AProgLevelEnder, false, false, false) +IMPLEMENT_CLASS(AProgLevelEnder, false, false, false, false) //============================================================================ // diff --git a/src/g_strife/a_rebels.cpp b/src/g_strife/a_rebels.cpp index bef34d03b..7f21886bf 100644 --- a/src/g_strife/a_rebels.cpp +++ b/src/g_strife/a_rebels.cpp @@ -47,7 +47,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(ATeleporterBeacon, false, false, false) +IMPLEMENT_CLASS(ATeleporterBeacon, false, false, false, false) bool ATeleporterBeacon::Use (bool pickup) { diff --git a/src/g_strife/a_spectral.cpp b/src/g_strife/a_spectral.cpp index d1dff1fb1..c7012accf 100644 --- a/src/g_strife/a_spectral.cpp +++ b/src/g_strife/a_spectral.cpp @@ -16,7 +16,7 @@ public: void Touch (AActor *toucher); }; -IMPLEMENT_CLASS(ASpectralMonster, false, false, false) +IMPLEMENT_CLASS(ASpectralMonster, false, false, false, false) void ASpectralMonster::Touch (AActor *toucher) { diff --git a/src/g_strife/a_strifeitems.cpp b/src/g_strife/a_strifeitems.cpp index f937da570..c1b9d75d6 100644 --- a/src/g_strife/a_strifeitems.cpp +++ b/src/g_strife/a_strifeitems.cpp @@ -19,7 +19,7 @@ */ // Degnin Ore --------------------------------------------------------------- -IMPLEMENT_CLASS(ADegninOre, false, false, false) +IMPLEMENT_CLASS(ADegninOre, false, false, false, false) DEFINE_ACTION_FUNCTION(AActor, A_RemoveForceField) { @@ -75,7 +75,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS(AHealthTraining, false, false, false) +IMPLEMENT_CLASS(AHealthTraining, false, false, false, false) bool AHealthTraining::TryPickup (AActor *&toucher) { @@ -105,7 +105,7 @@ public: bool Use (bool pickup); }; -IMPLEMENT_CLASS(AScanner, false, false, false) +IMPLEMENT_CLASS(AScanner, false, false, false, false) bool AScanner::Use (bool pickup) { @@ -130,7 +130,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS(APrisonPass, false, false, false) +IMPLEMENT_CLASS(APrisonPass, false, false, false, false) bool APrisonPass::TryPickup (AActor *&toucher) { @@ -163,7 +163,7 @@ bool APrisonPass::SpecialDropAction (AActor *dropper) // actions and cannot be held. ---------------------------------------------- //--------------------------------------------------------------------------- -IMPLEMENT_CLASS(ADummyStrifeItem, false, false, false) +IMPLEMENT_CLASS(ADummyStrifeItem, false, false, false, false) // Sound the alarm! --------------------------------------------------------- @@ -175,7 +175,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS(ARaiseAlarm, false, false, false) +IMPLEMENT_CLASS(ARaiseAlarm, false, false, false, false) bool ARaiseAlarm::TryPickup (AActor *&toucher) { @@ -209,7 +209,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS(AOpenDoor222, false, false, false) +IMPLEMENT_CLASS(AOpenDoor222, false, false, false, false) bool AOpenDoor222::TryPickup (AActor *&toucher) { @@ -228,7 +228,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS(ACloseDoor222, false, false, false) +IMPLEMENT_CLASS(ACloseDoor222, false, false, false, false) bool ACloseDoor222::TryPickup (AActor *&toucher) { @@ -262,7 +262,7 @@ public: bool SpecialDropAction (AActor *dropper); }; -IMPLEMENT_CLASS(AOpenDoor224, false, false, false) +IMPLEMENT_CLASS(AOpenDoor224, false, false, false, false) bool AOpenDoor224::TryPickup (AActor *&toucher) { @@ -287,7 +287,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS(AAmmoFillup, false, false, false) +IMPLEMENT_CLASS(AAmmoFillup, false, false, false, false) bool AAmmoFillup::TryPickup (AActor *&toucher) { @@ -325,7 +325,7 @@ public: bool TryPickup (AActor *&toucher); }; -IMPLEMENT_CLASS(AHealthFillup, false, false, false) +IMPLEMENT_CLASS(AHealthFillup, false, false, false, false) bool AHealthFillup::TryPickup (AActor *&toucher) { @@ -342,7 +342,7 @@ bool AHealthFillup::TryPickup (AActor *&toucher) // Upgrade Stamina ---------------------------------------------------------- -IMPLEMENT_CLASS(AUpgradeStamina, false, false, false) +IMPLEMENT_CLASS(AUpgradeStamina, false, false, false, false) bool AUpgradeStamina::TryPickup (AActor *&toucher) { @@ -360,7 +360,7 @@ bool AUpgradeStamina::TryPickup (AActor *&toucher) // Upgrade Accuracy --------------------------------------------------------- -IMPLEMENT_CLASS(AUpgradeAccuracy, false, false, false) +IMPLEMENT_CLASS(AUpgradeAccuracy, false, false, false, false) bool AUpgradeAccuracy::TryPickup (AActor *&toucher) { @@ -373,7 +373,7 @@ bool AUpgradeAccuracy::TryPickup (AActor *&toucher) // Start a slideshow -------------------------------------------------------- -IMPLEMENT_CLASS(ASlideshowStarter, false, false, false) +IMPLEMENT_CLASS(ASlideshowStarter, false, false, false, false) bool ASlideshowStarter::TryPickup (AActor *&toucher) { diff --git a/src/g_strife/a_strifestuff.cpp b/src/g_strife/a_strifestuff.cpp index f4a724bc4..1580f127f 100644 --- a/src/g_strife/a_strifestuff.cpp +++ b/src/g_strife/a_strifestuff.cpp @@ -72,7 +72,7 @@ public: int TakeSpecialDamage (AActor *inflictor, AActor *source, int damage, FName damagetype); }; -IMPLEMENT_CLASS(AForceFieldGuard, false, false, false) +IMPLEMENT_CLASS(AForceFieldGuard, false, false, false, false) int AForceFieldGuard::TakeSpecialDamage (AActor *inflictor, AActor *source, int damage, FName damagetype) { @@ -197,7 +197,7 @@ public: void Die (AActor *source, AActor *inflictor, int dmgflags); }; -IMPLEMENT_CLASS(APowerCoupling, false, false, false) +IMPLEMENT_CLASS(APowerCoupling, false, false, false, false) void APowerCoupling::Die (AActor *source, AActor *inflictor, int dmgflags) { @@ -239,7 +239,7 @@ public: } }; -IMPLEMENT_CLASS(AMeat, false, false, false) +IMPLEMENT_CLASS(AMeat, false, false, false, false) //========================================================================== // diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index ec153d675..3e9eb69b6 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -184,7 +184,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(APoisonBolt, false, false, false) +IMPLEMENT_CLASS(APoisonBolt, false, false, false, false) int APoisonBolt::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -607,7 +607,7 @@ public: int DoSpecialDamage (AActor *target, int damage, FName damagetype); }; -IMPLEMENT_CLASS(APhosphorousFire, false, false, false) +IMPLEMENT_CLASS(APhosphorousFire, false, false, false, false) int APhosphorousFire::DoSpecialDamage (AActor *target, int damage, FName damagetype) { @@ -734,7 +734,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireGrenade) // The Almighty Sigil! ------------------------------------------------------ -IMPLEMENT_CLASS(ASigil, false, false, false) +IMPLEMENT_CLASS(ASigil, false, false, false, false) //============================================================================ // diff --git a/src/g_strife/strife_sbar.cpp b/src/g_strife/strife_sbar.cpp index 3d0089777..73e31e676 100644 --- a/src/g_strife/strife_sbar.cpp +++ b/src/g_strife/strife_sbar.cpp @@ -851,7 +851,7 @@ private: double ItemFlash; }; -IMPLEMENT_CLASS(DStrifeStatusBar, false, false, false); +IMPLEMENT_CLASS(DStrifeStatusBar, false, false, false, false); DBaseStatusBar *CreateStrifeStatusBar () { diff --git a/src/info.cpp b/src/info.cpp index 3e14d7fed..09d0905f6 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -153,7 +153,7 @@ int GetSpriteIndex(const char * spritename, bool add) return (lastindex = (int)sprites.Push (temp)); } -IMPLEMENT_CLASS(PClassActor, false, true, false) +IMPLEMENT_CLASS(PClassActor, false, true, false, false) IMPLEMENT_POINTERS_START(PClassActor) IMPLEMENT_POINTER(DropItems) diff --git a/src/intermission/intermission.cpp b/src/intermission/intermission.cpp index 94288bfdf..be8f58e19 100644 --- a/src/intermission/intermission.cpp +++ b/src/intermission/intermission.cpp @@ -54,12 +54,12 @@ FIntermissionDescriptorList IntermissionDescriptors; -IMPLEMENT_CLASS(DIntermissionScreen, false, false, false) -IMPLEMENT_CLASS(DIntermissionScreenFader, false, false, false) -IMPLEMENT_CLASS(DIntermissionScreenText, false, false, false) -IMPLEMENT_CLASS(DIntermissionScreenCast, false, false, false) -IMPLEMENT_CLASS(DIntermissionScreenScroller, false, false, false) -IMPLEMENT_CLASS(DIntermissionController, false, true, false) +IMPLEMENT_CLASS(DIntermissionScreen, false, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenFader, false, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenText, false, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenCast, false, false, false, false) +IMPLEMENT_CLASS(DIntermissionScreenScroller, false, false, false, false) +IMPLEMENT_CLASS(DIntermissionController, false, true, false, false) IMPLEMENT_POINTERS_START(DIntermissionController) IMPLEMENT_POINTER(mScreen) diff --git a/src/m_argv.cpp b/src/m_argv.cpp index 924c9dd5c..7d82ed834 100644 --- a/src/m_argv.cpp +++ b/src/m_argv.cpp @@ -37,7 +37,7 @@ #include "cmdlib.h" #include "i_system.h" -IMPLEMENT_CLASS(DArgs, false, false, false) +IMPLEMENT_CLASS(DArgs, false, false, false, false) //=========================================================================== // diff --git a/src/m_cheat.cpp b/src/m_cheat.cpp index 94c1ef3df..c53192ee7 100644 --- a/src/m_cheat.cpp +++ b/src/m_cheat.cpp @@ -1033,7 +1033,7 @@ public: } }; -IMPLEMENT_CLASS(DSuicider, false, true, false) +IMPLEMENT_CLASS(DSuicider, false, true, false, false) IMPLEMENT_POINTERS_START(DSuicider) IMPLEMENT_POINTER(Pawn) diff --git a/src/menu/colorpickermenu.cpp b/src/menu/colorpickermenu.cpp index 110ed2c3e..639c6bbef 100644 --- a/src/menu/colorpickermenu.cpp +++ b/src/menu/colorpickermenu.cpp @@ -331,7 +331,7 @@ public: } }; -IMPLEMENT_CLASS(DColorPickerMenu, true, false, false) +IMPLEMENT_CLASS(DColorPickerMenu, true, false, false, false) CCMD(undocolorpic) { diff --git a/src/menu/joystickmenu.cpp b/src/menu/joystickmenu.cpp index 8e05391a6..cca13ad44 100644 --- a/src/menu/joystickmenu.cpp +++ b/src/menu/joystickmenu.cpp @@ -236,7 +236,7 @@ class DJoystickConfigMenu : public DOptionMenu DECLARE_CLASS(DJoystickConfigMenu, DOptionMenu) }; -IMPLEMENT_CLASS(DJoystickConfigMenu, false, false, false) +IMPLEMENT_CLASS(DJoystickConfigMenu, false, false, false, false) //============================================================================= // diff --git a/src/menu/listmenu.cpp b/src/menu/listmenu.cpp index 645636dad..7fdd0c5bc 100644 --- a/src/menu/listmenu.cpp +++ b/src/menu/listmenu.cpp @@ -42,7 +42,7 @@ #include "d_event.h" #include "menu/menu.h" -IMPLEMENT_CLASS(DListMenu, false, false, false) +IMPLEMENT_CLASS(DListMenu, false, false, false, false) //============================================================================= // diff --git a/src/menu/loadsavemenu.cpp b/src/menu/loadsavemenu.cpp index 69976726e..6d543228c 100644 --- a/src/menu/loadsavemenu.cpp +++ b/src/menu/loadsavemenu.cpp @@ -119,7 +119,7 @@ public: }; -IMPLEMENT_CLASS(DLoadSaveMenu, false, false, false) +IMPLEMENT_CLASS(DLoadSaveMenu, false, false, false, false) TArray DLoadSaveMenu::SaveGames; int DLoadSaveMenu::LastSaved = -1; @@ -934,7 +934,7 @@ public: }; -IMPLEMENT_CLASS(DSaveMenu, false, false, false) +IMPLEMENT_CLASS(DSaveMenu, false, false, false, false) //============================================================================= @@ -1102,7 +1102,7 @@ public: bool MenuEvent (int mkey, bool fromcontroller); }; -IMPLEMENT_CLASS(DLoadMenu, false, false, false) +IMPLEMENT_CLASS(DLoadMenu, false, false, false, false) //============================================================================= diff --git a/src/menu/menu.cpp b/src/menu/menu.cpp index 6717ffcf2..6648c32b4 100644 --- a/src/menu/menu.cpp +++ b/src/menu/menu.cpp @@ -91,7 +91,7 @@ static bool MenuEnabled = true; // //============================================================================ -IMPLEMENT_CLASS(DMenu, false, true, false) +IMPLEMENT_CLASS(DMenu, false, true, false, false) IMPLEMENT_POINTERS_START(DMenu) IMPLEMENT_POINTER(mParentMenu) diff --git a/src/menu/menuinput.cpp b/src/menu/menuinput.cpp index 12ef4525d..c33e9fed2 100644 --- a/src/menu/menuinput.cpp +++ b/src/menu/menuinput.cpp @@ -44,7 +44,7 @@ // [TP] New #includes #include "v_text.h" -IMPLEMENT_CLASS(DTextEnterMenu, true, false, false) +IMPLEMENT_CLASS(DTextEnterMenu, true, false, false, false) #define INPUTGRID_WIDTH 13 #define INPUTGRID_HEIGHT 5 diff --git a/src/menu/messagebox.cpp b/src/menu/messagebox.cpp index 7915f44b3..de8fa1027 100644 --- a/src/menu/messagebox.cpp +++ b/src/menu/messagebox.cpp @@ -73,7 +73,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DMessageBoxMenu, false, false, false) +IMPLEMENT_CLASS(DMessageBoxMenu, false, false, false, false) //============================================================================= // @@ -365,7 +365,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DQuitMenu, false, false, false) +IMPLEMENT_CLASS(DQuitMenu, false, false, false, false) //============================================================================= // @@ -458,7 +458,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DEndGameMenu, false, false, false) +IMPLEMENT_CLASS(DEndGameMenu, false, false, false, false) //============================================================================= // @@ -536,7 +536,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DQuickSaveMenu, false, false, false) +IMPLEMENT_CLASS(DQuickSaveMenu, false, false, false, false) //============================================================================= // @@ -632,7 +632,7 @@ public: virtual void HandleResult(bool res); }; -IMPLEMENT_CLASS(DQuickLoadMenu, false, false, false) +IMPLEMENT_CLASS(DQuickLoadMenu, false, false, false, false) //============================================================================= // diff --git a/src/menu/optionmenu.cpp b/src/menu/optionmenu.cpp index 46bbae665..1631c3d4b 100644 --- a/src/menu/optionmenu.cpp +++ b/src/menu/optionmenu.cpp @@ -64,7 +64,7 @@ void M_DrawConText (int color, int x, int y, const char *str) TAG_DONE); } -IMPLEMENT_CLASS(DOptionMenu, false, false, false) +IMPLEMENT_CLASS(DOptionMenu, false, false, false, false) //============================================================================= // @@ -578,7 +578,7 @@ public: } }; -IMPLEMENT_CLASS(DGameplayMenu, false, false, false) +IMPLEMENT_CLASS(DGameplayMenu, false, false, false, false) class DCompatibilityMenu : public DOptionMenu { @@ -600,4 +600,4 @@ public: } }; -IMPLEMENT_CLASS(DCompatibilityMenu, false, false, false) +IMPLEMENT_CLASS(DCompatibilityMenu, false, false, false, false) diff --git a/src/menu/optionmenuitems.h b/src/menu/optionmenuitems.h index 2d3c8c25f..e83f4ada4 100644 --- a/src/menu/optionmenuitems.h +++ b/src/menu/optionmenuitems.h @@ -399,7 +399,7 @@ public: }; #ifndef NO_IMP -IMPLEMENT_CLASS(DEnterKey, true, false, false) +IMPLEMENT_CLASS(DEnterKey, true, false, false, false) #endif //============================================================================= diff --git a/src/menu/playermenu.cpp b/src/menu/playermenu.cpp index bc22c8e12..e32c7dd61 100644 --- a/src/menu/playermenu.cpp +++ b/src/menu/playermenu.cpp @@ -526,7 +526,7 @@ public: void Drawer (); }; -IMPLEMENT_CLASS(DPlayerMenu, false, false, false) +IMPLEMENT_CLASS(DPlayerMenu, false, false, false, false) //============================================================================= // diff --git a/src/menu/readthis.cpp b/src/menu/readthis.cpp index ce03ec84b..0dfc47e73 100644 --- a/src/menu/readthis.cpp +++ b/src/menu/readthis.cpp @@ -54,7 +54,7 @@ public: bool MouseEvent(int type, int x, int y); }; -IMPLEMENT_CLASS(DReadThisMenu, false, false, false) +IMPLEMENT_CLASS(DReadThisMenu, false, false, false, false) //============================================================================= // diff --git a/src/menu/videomenu.cpp b/src/menu/videomenu.cpp index 6fec9ce6d..37f59149e 100644 --- a/src/menu/videomenu.cpp +++ b/src/menu/videomenu.cpp @@ -183,7 +183,7 @@ public: } }; -IMPLEMENT_CLASS(DVideoModeMenu, false, false, false) +IMPLEMENT_CLASS(DVideoModeMenu, false, false, false, false) //============================================================================= diff --git a/src/p_acs.cpp b/src/p_acs.cpp index dc646da18..da8f76d7f 100644 --- a/src/p_acs.cpp +++ b/src/p_acs.cpp @@ -1369,7 +1369,7 @@ private: DPlaneWatcher() {} }; -IMPLEMENT_CLASS(DPlaneWatcher, false, true, false) +IMPLEMENT_CLASS(DPlaneWatcher, false, true, false, false) IMPLEMENT_POINTERS_START(DPlaneWatcher) IMPLEMENT_POINTER(Activator) @@ -2860,7 +2860,7 @@ void FBehavior::StaticStopMyScripts (AActor *actor) //---- The ACS Interpreter ----// -IMPLEMENT_CLASS(DACSThinker, false, true, false) +IMPLEMENT_CLASS(DACSThinker, false, true, false, false) IMPLEMENT_POINTERS_START(DACSThinker) IMPLEMENT_POINTER(LastScript) @@ -2991,7 +2991,7 @@ void DACSThinker::StopScriptsFor (AActor *actor) } } -IMPLEMENT_CLASS(DLevelScript, false, true, false) +IMPLEMENT_CLASS(DLevelScript, false, true, false, false) IMPLEMENT_POINTERS_START(DLevelScript) IMPLEMENT_POINTER(next) diff --git a/src/p_buildmap.cpp b/src/p_buildmap.cpp index ce2221ca1..b3526c60d 100644 --- a/src/p_buildmap.cpp +++ b/src/p_buildmap.cpp @@ -865,7 +865,7 @@ public: void BeginPlay (); }; -IMPLEMENT_CLASS(ACustomSprite, false, false, false) +IMPLEMENT_CLASS(ACustomSprite, false, false, false, false) void ACustomSprite::BeginPlay () { diff --git a/src/p_ceiling.cpp b/src/p_ceiling.cpp index 53100f9ca..d22dd6371 100644 --- a/src/p_ceiling.cpp +++ b/src/p_ceiling.cpp @@ -38,7 +38,7 @@ // //============================================================================ -IMPLEMENT_CLASS(DCeiling, false, false, false) +IMPLEMENT_CLASS(DCeiling, false, false, false, false) DCeiling::DCeiling () { diff --git a/src/p_conversation.cpp b/src/p_conversation.cpp index ad434b535..5b37268b8 100644 --- a/src/p_conversation.cpp +++ b/src/p_conversation.cpp @@ -1103,7 +1103,7 @@ public: }; -IMPLEMENT_CLASS(DConversationMenu, true, false, false) +IMPLEMENT_CLASS(DConversationMenu, true, false, false, false) int DConversationMenu::mSelection; // needs to be preserved if the same dialogue is restarted diff --git a/src/p_doors.cpp b/src/p_doors.cpp index 568e88058..542308fa6 100644 --- a/src/p_doors.cpp +++ b/src/p_doors.cpp @@ -45,7 +45,7 @@ // //============================================================================ -IMPLEMENT_CLASS(DDoor, false, false, false) +IMPLEMENT_CLASS(DDoor, false, false, false, false) DDoor::DDoor () { @@ -513,7 +513,7 @@ bool EV_DoDoor (DDoor::EVlDoor type, line_t *line, AActor *thing, // //============================================================================ -IMPLEMENT_CLASS(DAnimatedDoor, false, false, false) +IMPLEMENT_CLASS(DAnimatedDoor, false, false, false, false) DAnimatedDoor::DAnimatedDoor () { diff --git a/src/p_floor.cpp b/src/p_floor.cpp index a89330b2a..7b5ff5cc9 100644 --- a/src/p_floor.cpp +++ b/src/p_floor.cpp @@ -64,7 +64,7 @@ static void StartFloorSound (sector_t *sec) // //========================================================================== -IMPLEMENT_CLASS(DFloor, false, false, false) +IMPLEMENT_CLASS(DFloor, false, false, false, false) DFloor::DFloor () { @@ -815,7 +815,7 @@ bool EV_DoDonut (int tag, line_t *line, double pillarspeed, double slimespeed) // //========================================================================== -IMPLEMENT_CLASS(DElevator, false, true, false) +IMPLEMENT_CLASS(DElevator, false, true, false, false) IMPLEMENT_POINTERS_START(DElevator) IMPLEMENT_POINTER(m_Interp_Floor) @@ -1105,9 +1105,9 @@ bool EV_DoChange (line_t *line, EChange changetype, int tag) // //========================================================================== -IMPLEMENT_CLASS(DWaggleBase, false, false, false) -IMPLEMENT_CLASS(DFloorWaggle, false, false, false) -IMPLEMENT_CLASS(DCeilingWaggle, false, false, false) +IMPLEMENT_CLASS(DWaggleBase, false, false, false, false) +IMPLEMENT_CLASS(DFloorWaggle, false, false, false, false) +IMPLEMENT_CLASS(DCeilingWaggle, false, false, false, false) DWaggleBase::DWaggleBase () { diff --git a/src/p_lights.cpp b/src/p_lights.cpp index c2c2127a2..c44a22d4b 100644 --- a/src/p_lights.cpp +++ b/src/p_lights.cpp @@ -173,7 +173,7 @@ private: // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DLighting, false, false, false) +IMPLEMENT_CLASS(DLighting, false, false, false, false) DLighting::DLighting () { @@ -191,7 +191,7 @@ DLighting::DLighting (sector_t *sector) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DFireFlicker, false, false, false) +IMPLEMENT_CLASS(DFireFlicker, false, false, false, false) DFireFlicker::DFireFlicker () { @@ -258,7 +258,7 @@ DFireFlicker::DFireFlicker (sector_t *sector, int upper, int lower) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DFlicker, false, false, false) +IMPLEMENT_CLASS(DFlicker, false, false, false, false) DFlicker::DFlicker () { @@ -334,7 +334,7 @@ void EV_StartLightFlickering (int tag, int upper, int lower) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DLightFlash, false, false, false) +IMPLEMENT_CLASS(DLightFlash, false, false, false, false) DLightFlash::DLightFlash () { @@ -409,7 +409,7 @@ DLightFlash::DLightFlash (sector_t *sector, int min, int max) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DStrobe, false, false, false) +IMPLEMENT_CLASS(DStrobe, false, false, false, false) DStrobe::DStrobe () { @@ -667,7 +667,7 @@ void EV_LightChange (int tag, int value) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DGlow, false, false, false) +IMPLEMENT_CLASS(DGlow, false, false, false, false) DGlow::DGlow () { @@ -736,7 +736,7 @@ DGlow::DGlow (sector_t *sector) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DGlow2, false, false, false) +IMPLEMENT_CLASS(DGlow2, false, false, false, false) DGlow2::DGlow2 () { @@ -869,7 +869,7 @@ void EV_StartLightFading (int tag, int value, int tics) // //----------------------------------------------------------------------------- -IMPLEMENT_CLASS(DPhased, false, false, false) +IMPLEMENT_CLASS(DPhased, false, false, false, false) DPhased::DPhased () { diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 3cc961d84..0fb8794cf 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -131,7 +131,7 @@ CVAR (Int, cl_bloodtype, 0, CVAR_ARCHIVE); // CODE -------------------------------------------------------------------- -IMPLEMENT_CLASS(AActor, false, true, true) +IMPLEMENT_CLASS(AActor, false, true, true, false) IMPLEMENT_POINTERS_START(AActor) IMPLEMENT_POINTER(target) @@ -6956,7 +6956,7 @@ DEFINE_ACTION_FUNCTION(AActor, Vec3Offset) // //---------------------------------------------------------------------------- -IMPLEMENT_CLASS(DDropItem, false, true, true) +IMPLEMENT_CLASS(DDropItem, false, true, true, false) IMPLEMENT_POINTERS_START(DDropItem) IMPLEMENT_POINTER(Next) diff --git a/src/p_pillar.cpp b/src/p_pillar.cpp index fecfbd024..27eb13ec5 100644 --- a/src/p_pillar.cpp +++ b/src/p_pillar.cpp @@ -40,7 +40,7 @@ #include "serializer.h" #include "r_data/r_interpolate.h" -IMPLEMENT_CLASS(DPillar, false, true, false) +IMPLEMENT_CLASS(DPillar, false, true, false, false) IMPLEMENT_POINTERS_START(DPillar) IMPLEMENT_POINTER(m_Interp_Floor) diff --git a/src/p_plats.cpp b/src/p_plats.cpp index 3bd708916..9924a0f9c 100644 --- a/src/p_plats.cpp +++ b/src/p_plats.cpp @@ -35,7 +35,7 @@ static FRandom pr_doplat ("DoPlat"); -IMPLEMENT_CLASS(DPlat, false, false, false) +IMPLEMENT_CLASS(DPlat, false, false, false, false) DPlat::DPlat () { diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index b64bb22a7..d279a180c 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -99,7 +99,7 @@ static const FGenericButtons ButtonChecks[] = // //------------------------------------------------------------------------ -IMPLEMENT_CLASS(DPSprite, false, true, false) +IMPLEMENT_CLASS(DPSprite, false, true, false, false) IMPLEMENT_POINTERS_START(DPSprite) IMPLEMENT_POINTER(Caller) diff --git a/src/p_pusher.cpp b/src/p_pusher.cpp index 250e8ee3d..f2f982a7f 100644 --- a/src/p_pusher.cpp +++ b/src/p_pusher.cpp @@ -74,7 +74,7 @@ protected: friend bool PIT_PushThing (AActor *thing); }; -IMPLEMENT_CLASS(DPusher, false, true, false) +IMPLEMENT_CLASS(DPusher, false, true, false, false) IMPLEMENT_POINTERS_START(DPusher) IMPLEMENT_POINTER(m_Source) diff --git a/src/p_scroll.cpp b/src/p_scroll.cpp index 67f6499d6..f44eac25a 100644 --- a/src/p_scroll.cpp +++ b/src/p_scroll.cpp @@ -73,7 +73,7 @@ private: } }; -IMPLEMENT_CLASS(DScroller, false, true, false) +IMPLEMENT_CLASS(DScroller, false, true, false, false) IMPLEMENT_POINTERS_START(DScroller) IMPLEMENT_POINTER(m_Interpolations[0]) diff --git a/src/p_spec.cpp b/src/p_spec.cpp index e9ac49419..e687d5724 100644 --- a/src/p_spec.cpp +++ b/src/p_spec.cpp @@ -660,7 +660,7 @@ protected: short LastLight; }; -IMPLEMENT_CLASS(DLightTransfer, false, false, false) +IMPLEMENT_CLASS(DLightTransfer, false, false, false, false) void DLightTransfer::Serialize(FSerializer &arc) { @@ -750,7 +750,7 @@ protected: BYTE Flags; }; -IMPLEMENT_CLASS(DWallLightTransfer, false, false, false) +IMPLEMENT_CLASS(DWallLightTransfer, false, false, false, false) void DWallLightTransfer::Serialize(FSerializer &arc) { diff --git a/src/p_switch.cpp b/src/p_switch.cpp index 027b5d99d..2d5423f08 100644 --- a/src/p_switch.cpp +++ b/src/p_switch.cpp @@ -320,7 +320,7 @@ bool P_ChangeSwitchTexture (side_t *side, int useAgain, BYTE special, bool *ques // //========================================================================== -IMPLEMENT_CLASS(DActiveButton, false, false, false) +IMPLEMENT_CLASS(DActiveButton, false, false, false, false) DActiveButton::DActiveButton () { diff --git a/src/p_teleport.cpp b/src/p_teleport.cpp index 85ee8a1c8..01595ff65 100644 --- a/src/p_teleport.cpp +++ b/src/p_teleport.cpp @@ -47,7 +47,7 @@ extern void P_CalcHeight (player_t *player); CVAR (Bool, telezoom, true, CVAR_ARCHIVE|CVAR_GLOBALCONFIG); -IMPLEMENT_CLASS(ATeleportFog, false, false, false) +IMPLEMENT_CLASS(ATeleportFog, false, false, false, false) void ATeleportFog::PostBeginPlay () { diff --git a/src/p_user.cpp b/src/p_user.cpp index 266d216bb..0b7d9c354 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -508,7 +508,7 @@ int player_t::GetSpawnClass() // //=========================================================================== -IMPLEMENT_CLASS(PClassPlayerPawn, false, false, false) +IMPLEMENT_CLASS(PClassPlayerPawn, false, false, false, false) PClassPlayerPawn::PClassPlayerPawn() { @@ -622,14 +622,14 @@ void player_t::SendPitchLimits() const // //=========================================================================== -IMPLEMENT_CLASS(APlayerPawn, false, true, false) +IMPLEMENT_CLASS(APlayerPawn, false, true, false, false) IMPLEMENT_POINTERS_START(APlayerPawn) IMPLEMENT_POINTER(InvFirst) IMPLEMENT_POINTER(InvSel) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(APlayerChunk, false, false, false) +IMPLEMENT_CLASS(APlayerChunk, false, false, false, false) void APlayerPawn::Serialize(FSerializer &arc) { diff --git a/src/po_man.cpp b/src/po_man.cpp index 3261e34f3..4e304daa8 100644 --- a/src/po_man.cpp +++ b/src/po_man.cpp @@ -172,7 +172,7 @@ static FPolyNode *FreePolyNodes; // //========================================================================== -IMPLEMENT_CLASS(DPolyAction, false, true, false) +IMPLEMENT_CLASS(DPolyAction, false, true, false, false) IMPLEMENT_POINTERS_START(DPolyAction) IMPLEMENT_POINTER(m_Interpolation) @@ -240,7 +240,7 @@ void DPolyAction::StopInterpolation () // //========================================================================== -IMPLEMENT_CLASS(DRotatePoly, false, false, false) +IMPLEMENT_CLASS(DRotatePoly, false, false, false, false) DRotatePoly::DRotatePoly () { @@ -257,7 +257,7 @@ DRotatePoly::DRotatePoly (int polyNum) // //========================================================================== -IMPLEMENT_CLASS(DMovePoly, false, false, false) +IMPLEMENT_CLASS(DMovePoly, false, false, false, false) DMovePoly::DMovePoly () { @@ -284,7 +284,7 @@ DMovePoly::DMovePoly (int polyNum) // //========================================================================== -IMPLEMENT_CLASS(DMovePolyTo, false, false, false) +IMPLEMENT_CLASS(DMovePolyTo, false, false, false, false) DMovePolyTo::DMovePolyTo() { @@ -309,7 +309,7 @@ DMovePolyTo::DMovePolyTo(int polyNum) // //========================================================================== -IMPLEMENT_CLASS(DPolyDoor, false, false, false) +IMPLEMENT_CLASS(DPolyDoor, false, false, false, false) DPolyDoor::DPolyDoor () { diff --git a/src/posix/sdl/sdlvideo.cpp b/src/posix/sdl/sdlvideo.cpp index 29b741561..a1e6056ca 100644 --- a/src/posix/sdl/sdlvideo.cpp +++ b/src/posix/sdl/sdlvideo.cpp @@ -79,7 +79,7 @@ private: SDLFB () {} }; -IMPLEMENT_CLASS(SDLFB, false, false, false) +IMPLEMENT_CLASS(SDLFB, false, false, false, false) struct MiniModeInfo { diff --git a/src/r_data/r_interpolate.cpp b/src/r_data/r_interpolate.cpp index 911127f07..c98adb47b 100644 --- a/src/r_data/r_interpolate.cpp +++ b/src/r_data/r_interpolate.cpp @@ -161,17 +161,17 @@ public: // //========================================================================== -IMPLEMENT_CLASS(DInterpolation, true, true, false) +IMPLEMENT_CLASS(DInterpolation, true, true, false, false) IMPLEMENT_POINTERS_START(DInterpolation) IMPLEMENT_POINTER(Next) IMPLEMENT_POINTER(Prev) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(DSectorPlaneInterpolation, false, false, false) -IMPLEMENT_CLASS(DSectorScrollInterpolation, false, false, false) -IMPLEMENT_CLASS(DWallScrollInterpolation, false, false, false) -IMPLEMENT_CLASS(DPolyobjInterpolation, false, false, false) +IMPLEMENT_CLASS(DSectorPlaneInterpolation, false, false, false, false) +IMPLEMENT_CLASS(DSectorScrollInterpolation, false, false, false, false) +IMPLEMENT_CLASS(DWallScrollInterpolation, false, false, false, false) +IMPLEMENT_CLASS(DPolyobjInterpolation, false, false, false, false) //========================================================================== // diff --git a/src/s_advsound.cpp b/src/s_advsound.cpp index 1aedcb1fb..c68df5f3c 100644 --- a/src/s_advsound.cpp +++ b/src/s_advsound.cpp @@ -2213,7 +2213,7 @@ private: int NextCheck; }; -IMPLEMENT_CLASS(AAmbientSound, false, false, false) +IMPLEMENT_CLASS(AAmbientSound, false, false, false, false) //========================================================================== // @@ -2470,7 +2470,7 @@ public: virtual void PostBeginPlay(); }; -IMPLEMENT_CLASS(AMusicChanger, false, false, false) +IMPLEMENT_CLASS(AMusicChanger, false, false, false, false) bool AMusicChanger::DoTriggerAction (AActor *triggerer, int activationType) { diff --git a/src/s_sndseq.cpp b/src/s_sndseq.cpp index 449baa4d6..1bed35ed5 100644 --- a/src/s_sndseq.cpp +++ b/src/s_sndseq.cpp @@ -285,7 +285,7 @@ void DSeqNode::SerializeSequences (FSerializer &arc) arc("sndseqlisthead", SequenceListHead); } -IMPLEMENT_CLASS(DSeqNode, false, true, false) +IMPLEMENT_CLASS(DSeqNode, false, true, false, false) IMPLEMENT_POINTERS_START(DSeqNode) IMPLEMENT_POINTER(m_ChildSeqNode) @@ -429,7 +429,7 @@ FName DSeqNode::GetSequenceName () const return Sequences[m_Sequence]->SeqName; } -IMPLEMENT_CLASS(DSeqActorNode, false, true, false) +IMPLEMENT_CLASS(DSeqActorNode, false, true, false, false) IMPLEMENT_POINTERS_START(DSeqActorNode) IMPLEMENT_POINTER(m_Actor) @@ -441,7 +441,7 @@ void DSeqActorNode::Serialize(FSerializer &arc) arc("actor", m_Actor); } -IMPLEMENT_CLASS(DSeqPolyNode, false, false, false) +IMPLEMENT_CLASS(DSeqPolyNode, false, false, false, false) void DSeqPolyNode::Serialize(FSerializer &arc) { @@ -449,7 +449,7 @@ void DSeqPolyNode::Serialize(FSerializer &arc) arc("poly", m_Poly); } -IMPLEMENT_CLASS(DSeqSectorNode, false, false, false) +IMPLEMENT_CLASS(DSeqSectorNode, false, false, false, false) void DSeqSectorNode::Serialize(FSerializer &arc) { diff --git a/src/scripting/decorate/olddecorations.cpp b/src/scripting/decorate/olddecorations.cpp index 63ae447cf..d1b79328f 100644 --- a/src/scripting/decorate/olddecorations.cpp +++ b/src/scripting/decorate/olddecorations.cpp @@ -96,7 +96,7 @@ public: } }; -IMPLEMENT_CLASS(AFakeInventory, false, false, false) +IMPLEMENT_CLASS(AFakeInventory, false, false, false, false) // PUBLIC FUNCTION PROTOTYPES ---------------------------------------------- diff --git a/src/scripting/vm/vmframe.cpp b/src/scripting/vm/vmframe.cpp index 3070c1b4d..3a593861c 100644 --- a/src/scripting/vm/vmframe.cpp +++ b/src/scripting/vm/vmframe.cpp @@ -34,15 +34,15 @@ #include #include "vm.h" -IMPLEMENT_CLASS(VMException, false, false, false) -IMPLEMENT_CLASS(VMFunction, true, true, false) +IMPLEMENT_CLASS(VMException, false, false, false, false) +IMPLEMENT_CLASS(VMFunction, true, true, false, false) IMPLEMENT_POINTERS_START(VMFunction) IMPLEMENT_POINTER(Proto) IMPLEMENT_POINTERS_END -IMPLEMENT_CLASS(VMScriptFunction, false, false, false) -IMPLEMENT_CLASS(VMNativeFunction, false, false, false) +IMPLEMENT_CLASS(VMScriptFunction, false, false, false, false) +IMPLEMENT_CLASS(VMNativeFunction, false, false, false, false) VMScriptFunction::VMScriptFunction(FName name) { diff --git a/src/v_video.cpp b/src/v_video.cpp index f79f31b1c..e3954385a 100644 --- a/src/v_video.cpp +++ b/src/v_video.cpp @@ -69,8 +69,8 @@ int active_con_scale(); FRenderer *Renderer; -IMPLEMENT_CLASS(DCanvas, true, false, false) -IMPLEMENT_CLASS(DFrameBuffer, true, false, false) +IMPLEMENT_CLASS(DCanvas, true, false, false, false) +IMPLEMENT_CLASS(DFrameBuffer, true, false, false, false) #if defined(_DEBUG) && defined(_M_IX86) #define DBGBREAK { __asm int 3 } @@ -106,11 +106,11 @@ public: float Gamma; }; -IMPLEMENT_CLASS(DDummyFrameBuffer, true, false, false) +IMPLEMENT_CLASS(DDummyFrameBuffer, true, false, false, false) // SimpleCanvas is not really abstract, but this macro does not // try to generate a CreateNew() function. -IMPLEMENT_CLASS(DSimpleCanvas, true, false, false) +IMPLEMENT_CLASS(DSimpleCanvas, true, false, false, false) class FPaletteTester : public FTexture { diff --git a/src/win32/fb_d3d9.cpp b/src/win32/fb_d3d9.cpp index a79ef1a3f..6d162bbec 100644 --- a/src/win32/fb_d3d9.cpp +++ b/src/win32/fb_d3d9.cpp @@ -91,7 +91,7 @@ // TYPES ------------------------------------------------------------------- -IMPLEMENT_CLASS(D3DFB, false, false, false) +IMPLEMENT_CLASS(D3DFB, false, false, false, false) struct D3DFB::PackedTexture { diff --git a/src/win32/fb_ddraw.cpp b/src/win32/fb_ddraw.cpp index dcd6d37a9..bd5a4db23 100644 --- a/src/win32/fb_ddraw.cpp +++ b/src/win32/fb_ddraw.cpp @@ -61,7 +61,7 @@ // TYPES ------------------------------------------------------------------- -IMPLEMENT_CLASS(DDrawFB, false, false, false) +IMPLEMENT_CLASS(DDrawFB, false, false, false, false) // EXTERNAL FUNCTION PROTOTYPES -------------------------------------------- diff --git a/src/win32/win32video.cpp b/src/win32/win32video.cpp index b8aded5c1..d7c5d5bf5 100644 --- a/src/win32/win32video.cpp +++ b/src/win32/win32video.cpp @@ -78,7 +78,7 @@ // TYPES ------------------------------------------------------------------- -IMPLEMENT_CLASS(BaseWinFB, true, false, false) +IMPLEMENT_CLASS(BaseWinFB, true, false, false, false) typedef IDirect3D9 *(WINAPI *DIRECT3DCREATE9FUNC)(UINT SDKVersion); typedef HRESULT (WINAPI *DIRECTDRAWCREATEFUNC)(GUID FAR *lpGUID, LPDIRECTDRAW FAR *lplpDD, IUnknown FAR *pUnkOuter); From 26dc0c6df21e2e9f792b79149c51e13960ae8582 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 6 Nov 2016 11:40:17 +0100 Subject: [PATCH 213/255] TODO: Find a better place to insert the classes in the hierarchy --- src/scripting/zscript/zcc_compile.cpp | 46 +++++++++++++++++++++++++++ 1 file changed, 46 insertions(+) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 2965357dd..421b27fb1 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -51,6 +51,8 @@ #include "codegeneration/codegen.h" #include "vmbuilder.h" +#define DEFAULTS_VMEXPORT ((BYTE *)(void *)1) + //========================================================================== // // ZCCCompiler :: ProcessClass @@ -498,6 +500,26 @@ void ZCCCompiler::CreateClassTypes() } else { + // The parent was the last native class in the inheritance tree. + // There is probably a better place for this somewhere else + // TODO: Do this somewhere else or find a less hackish way to do it + if (!parent->bRuntimeClass) + { + //assert(parent->VMExported != nullptr); // Ideally the macro would be used on all inheritable-native classes + /**/ if (parent->VMExported != nullptr) { /**/ // remove the if condition when all done + + parent = parent->VMExported; + assert(parent->bRuntimeClass == false); + + if (parent->Defaults == nullptr) + { + // We have to manually do that since zscript knows nothing about these + parent->Defaults = DEFAULTS_VMEXPORT; + } + + /**/ } /**/ + } + // We will never get here if the name is a duplicate, so we can just do the assignment. c->cls->Type = parent->FindClassTentative(c->NodeName()); } @@ -1887,6 +1909,16 @@ void ZCCCompiler::InitDefaults() { // Copy the parent's defaults and meta data. auto ti = static_cast(c->Type()); + + // Hack for the DVMObjects as they weren't in the list originally + // TODO: process them in a non hackish way obviously + if (ti->ParentClass->Defaults == DEFAULTS_VMEXPORT) + { + ti->ParentClass->Defaults = nullptr; + static_cast(ti->ParentClass)->InitializeNativeDefaults(); + ti->ParentClass->ParentClass->DeriveData(ti->ParentClass); + } + ti->InitializeNativeDefaults(); ti->ParentClass->DeriveData(ti); @@ -2239,6 +2271,20 @@ void ZCCCompiler::CompileStates() if (c->States.Size()) Error(c->cls, "%s: States can only be defined for actors.", c->Type()->TypeName.GetChars()); continue; } + + // Same here, hack in the DVMObject as they weren't in the list originally + // TODO: process them in a non hackish way obviously + if (c->Type()->bRuntimeClass == true && c->Type()->ParentClass->bRuntimeClass == false) + { + auto vmtype = static_cast(c->Type()->ParentClass); + if (vmtype->StateList == nullptr) + { + FStateDefinitions vmstates; + vmstates.MakeStateDefines(dyn_cast(vmtype->ParentClass)); + vmtype->Finalize(vmstates); + } + } + FString statename; // The state builder wants the label as one complete string, not separated into tokens. FStateDefinitions statedef; statedef.MakeStateDefines(dyn_cast(c->Type()->ParentClass)); From fb2a843c031b0e2d36ad4043b9f412dda826ec99 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Mon, 7 Nov 2016 00:30:26 +0100 Subject: [PATCH 214/255] Test on a few methods/classes --- src/actor.h | 4 ++++ src/dobject.h | 30 ++++++++++++++++++++++++++++++ src/dthinker.cpp | 2 +- src/dthinker.h | 4 ++++ src/p_mobj.cpp | 2 +- src/p_user.cpp | 2 +- 6 files changed, 41 insertions(+), 3 deletions(-) diff --git a/src/actor.h b/src/actor.h index 833cd2c0a..6f5ba46a3 100644 --- a/src/actor.h +++ b/src/actor.h @@ -1419,6 +1419,10 @@ public: }; +VMEXPORT_NATIVES_START(AActor, DThinker) + VMEXPORT_NATIVES_FUNC(DropInventory) +VMEXPORT_NATIVES_END(AActor) + class FActorIterator { public: diff --git a/src/dobject.h b/src/dobject.h index 24ba4997c..183d17dd2 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -608,6 +608,8 @@ protected: } }; +class AInventory;// + template class DVMObject : public T { @@ -638,6 +640,23 @@ private: { new((EInPlace *)mem) DVMObject; } + +public: + void Destroy() + { + Printf("Destroy\n"); + ExportedNatives::Get()->Destroy(this); + } + void Tick() + { + Printf("Tick\n"); + ExportedNatives::Get()->Tick(this); + } + AInventory *DropInventory(AInventory *item) + { + Printf("DropInventory\n"); + return ExportedNatives::Get()->DropInventory(this, item); + } }; template @@ -655,6 +674,17 @@ ClassReg DVMObject::RegistrationInfo = }; template _DECLARE_TI(DVMObject) +//Initial list +VMEXPORTED_NATIVES_START + VMEXPORTED_NATIVES_FUNC(Destroy) + VMEXPORTED_NATIVES_FUNC(Tick) + VMEXPORTED_NATIVES_FUNC(DropInventory) +VMEXPORTED_NATIVES_END + +VMEXPORT_NATIVES_START(DObject, void) + VMEXPORT_NATIVES_FUNC(Destroy) +VMEXPORT_NATIVES_END(DObject) + // When you write to a pointer to an Object, you must call this for // proper bookkeeping in case the Object holding this pointer has // already been processed by the GC. diff --git a/src/dthinker.cpp b/src/dthinker.cpp index 9c87c46b4..912b5642e 100644 --- a/src/dthinker.cpp +++ b/src/dthinker.cpp @@ -47,7 +47,7 @@ extern cycle_t BotSupportCycles; extern cycle_t ActionCycles; extern int BotWTG; -IMPLEMENT_CLASS(DThinker, false, false, false, false) +IMPLEMENT_CLASS(DThinker, false, false, false, true) DThinker *NextToThink; diff --git a/src/dthinker.h b/src/dthinker.h index 95985c2fb..e1020544c 100644 --- a/src/dthinker.h +++ b/src/dthinker.h @@ -108,6 +108,10 @@ private: DThinker *NextThinker, *PrevThinker; }; +VMEXPORT_NATIVES_START(DThinker, DObject) + VMEXPORT_NATIVES_FUNC(Tick) +VMEXPORT_NATIVES_END(DThinker) + class FThinkerIterator { protected: diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 0fb8794cf..7c973351f 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -131,7 +131,7 @@ CVAR (Int, cl_bloodtype, 0, CVAR_ARCHIVE); // CODE -------------------------------------------------------------------- -IMPLEMENT_CLASS(AActor, false, true, true, false) +IMPLEMENT_CLASS(AActor, false, true, true, true) IMPLEMENT_POINTERS_START(AActor) IMPLEMENT_POINTER(target) diff --git a/src/p_user.cpp b/src/p_user.cpp index 0b7d9c354..f4e52ac2f 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -622,7 +622,7 @@ void player_t::SendPitchLimits() const // //=========================================================================== -IMPLEMENT_CLASS(APlayerPawn, false, true, false, false) +IMPLEMENT_CLASS(APlayerPawn, false, true, false, true) IMPLEMENT_POINTERS_START(APlayerPawn) IMPLEMENT_POINTER(InvFirst) From 5151547df0be103b17a563af40bb9f8f5145ffa9 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Wed, 9 Nov 2016 20:28:46 +0100 Subject: [PATCH 215/255] - fixed: String comparisons with constants did not work. --- src/scripting/codegeneration/codegen.cpp | 5 +++++ src/scripting/zscript/zcc_compile.cpp | 2 ++ 2 files changed, 7 insertions(+) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 63302d600..af92bf72f 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -3251,10 +3251,15 @@ ExpEmit FxCompareEq::Emit(VMFunctionBuilder *build) int a = Operator == TK_Eq ? CMP_EQ : Operator == TK_Neq ? CMP_EQ | CMP_CHECK : CMP_EQ | CMP_APPROX; + if (op1.Konst) a|= CMP_BK; + if (op2.Konst) a |= CMP_CK; + build->Emit(OP_LI, to.RegNum, 0, 0); build->Emit(OP_CMPS, a, op1.RegNum, op2.RegNum); build->Emit(OP_JMP, 1); build->Emit(OP_LI, to.RegNum, 1); + op1.Free(build); + op2.Free(build); return to; } else diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 421b27fb1..7e895d049 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -497,6 +497,8 @@ void ZCCCompiler::CreateClassTypes() DPrintf(DMSG_SPAMMY, "Registered %s as native with parent %s\n", me->TypeName.GetChars(), parent->TypeName.GetChars()); } c->cls->Type = me; + auto ac = dyn_cast(me); + if (ac != nullptr) ac->SourceLumpName = *c->cls->SourceName; } else { From e0bd6a2c0ad96f91984f2020611a957e1b13c8e0 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 10 Nov 2016 13:37:38 +0100 Subject: [PATCH 216/255] - fixed a memory leak in the compiler. - removed test Printfs. --- src/CMakeLists.txt | 1 - src/dobject.h | 3 - src/g_pch.h | 1 + .../codegeneration/functioncalls.cpp | 76 ------------------- src/scripting/zscript/zcc_compile.cpp | 4 + src/scripting/zscript/zcc_compile.h | 2 + 6 files changed, 7 insertions(+), 80 deletions(-) delete mode 100644 src/scripting/codegeneration/functioncalls.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 81f43f06b..8b75d7b62 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -1247,7 +1247,6 @@ set (PCH_SOURCES scripting/thingdef_data.cpp scripting/thingdef_properties.cpp scripting/codegeneration/codegen.cpp - scripting/codegeneration/functioncalls.cpp scripting/decorate/olddecorations.cpp scripting/decorate/thingdef_exp.cpp scripting/decorate/thingdef_parse.cpp diff --git a/src/dobject.h b/src/dobject.h index 183d17dd2..3c4b23248 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -644,17 +644,14 @@ private: public: void Destroy() { - Printf("Destroy\n"); ExportedNatives::Get()->Destroy(this); } void Tick() { - Printf("Tick\n"); ExportedNatives::Get()->Tick(this); } AInventory *DropInventory(AInventory *item) { - Printf("DropInventory\n"); return ExportedNatives::Get()->DropInventory(this, item); } }; diff --git a/src/g_pch.h b/src/g_pch.h index 3f44cf9b5..a22649815 100644 --- a/src/g_pch.h +++ b/src/g_pch.h @@ -18,3 +18,4 @@ #include #include #include +#include diff --git a/src/scripting/codegeneration/functioncalls.cpp b/src/scripting/codegeneration/functioncalls.cpp deleted file mode 100644 index ca2b437e7..000000000 --- a/src/scripting/codegeneration/functioncalls.cpp +++ /dev/null @@ -1,76 +0,0 @@ -#if 0 -/* -** cg_functioncall.cpp -** -**--------------------------------------------------------------------------- -** Copyright 2016 Christoph Oelckers -** All rights reserved. -** -** Redistribution and use in source and binary forms, with or without -** modification, are permitted provided that the following conditions -** are met: -** -** 1. Redistributions of source code must retain the above copyright -** notice, this list of conditions and the following disclaimer. -** 2. Redistributions in binary form must reproduce the above copyright -** notice, this list of conditions and the following disclaimer in the -** documentation and/or other materials provided with the distribution. -** 3. The name of the author may not be used to endorse or promote products -** derived from this software without specific prior written permission. -** -** THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR -** IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES -** OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. -** IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, -** INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT -** NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF -** THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -**--------------------------------------------------------------------------- -** -*/ - -#include "doomtype.h" -#include "codegen.h" -#include "thingdef.h" -#include "zscript/zcc_parser.h" - -// just some rough concepts for now... - - -//========================================================================== -// -// -// -//========================================================================== - -FxExpression *ConvertFunctionCall(ZCC_Expression *function, FArgumentList *args, PClass *cls, FScriptPosition &sc) -{ - - switch(function->NodeType) - { - case AST_ExprID: - return new FxFunctionCall( ConvertSimpleFunctionCall(static_cast(function), args, cls, sc); - - case AST_ExprMemberAccess: - return ConvertMemberCall(fcall); - - case AST_ExprBinary: - // Array access syntax is wrapped into a ZCC_ExprBinary object. - break; - - default: - break; - } - Error(fcall, "Invalid function identifier"); - return new FxNop(*fcall); // return something so that we can continue -} - - - assert(fcall->Function->NodeType == AST_ExprID); // of course this cannot remain. Right now nothing more complex can come along but later this will have to be decomposed into 'self' and the actual function name. - auto fname = static_cast(fcall->Function)->Identifier; - return new FxFunctionCall(nullptr, fname, ConvertNodeList(fcall->Parameters), *ast); - -#endif \ No newline at end of file diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 7e895d049..0d99ee5c2 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2839,10 +2839,14 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } else if (args->Size() == 1) { + auto arg = (*args)[0]; + (*args)[0] = nullptr; + delete args; return new FxReturnStatement((*args)[0], *ast); } else { + delete args; Error(ast, "Return with multiple values not implemented yet."); return new FxReturnStatement(nullptr, *ast); } diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index c901fc42e..2e38d68d2 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -1,6 +1,8 @@ #ifndef ZCC_COMPILE_H #define ZCC_COMPILE_H +#include + struct Baggage; struct FPropertyInfo; class AActor; From a60bdc2bfb5130a937bce69f6e0e7786d4dc2ad3 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Thu, 10 Nov 2016 15:13:31 +0100 Subject: [PATCH 217/255] use a memory arena for allocating code generation nodes. - Since the number of small allocations here is extremely high this will help a lot to prevent fragmentation and since most nodes are collected up front and this is done when no large resources are being loaded it won't cause heap spikes. let Emit methods delete FxExpression arrays when they are done. - For some reason the deletion process does not work 100%, there are always some nodes left behind and so far I haven't found them. This ensures that these arrays do not live any longer than needed. --- src/memarena.cpp | 11 +- src/memarena.h | 3 +- src/scripting/codegeneration/codegen.cpp | 276 +++++++++++---------- src/scripting/codegeneration/codegen.h | 36 ++- src/scripting/decorate/thingdef_exp.cpp | 34 +-- src/scripting/decorate/thingdef_states.cpp | 16 +- src/scripting/vm/vmbuilder.cpp | 1 + src/scripting/zscript/zcc_compile.cpp | 34 +-- src/scripting/zscript/zcc_compile.h | 2 +- 9 files changed, 209 insertions(+), 204 deletions(-) diff --git a/src/memarena.cpp b/src/memarena.cpp index b15fb12ea..e6e9edd6e 100644 --- a/src/memarena.cpp +++ b/src/memarena.cpp @@ -43,8 +43,6 @@ #include "c_dispatch.h" #include "zstring.h" -#define BLOCK_SIZE (10*1024) - struct FMemArena::Block { Block *NextBlock; @@ -74,10 +72,11 @@ static inline void *RoundPointer(void *ptr) // //========================================================================== -FMemArena::FMemArena() +FMemArena::FMemArena(int bs) { TopBlock = NULL; FreeBlocks = NULL; + BlockSize = bs; } //========================================================================== @@ -191,14 +190,14 @@ FMemArena::Block *FMemArena::AddBlock(size_t size) if (mem == NULL) { // Allocate a new block - if (size < BLOCK_SIZE) + if (size < BlockSize) { - size = BLOCK_SIZE; + size = BlockSize; } else { // Stick some free space at the end so we can use this block for // other things. - size += BLOCK_SIZE/2; + size += BlockSize/2; } mem = (Block *)M_Malloc(size); mem->Limit = (BYTE *)mem + size; diff --git a/src/memarena.h b/src/memarena.h index 73dbb5932..cc0c8f148 100644 --- a/src/memarena.h +++ b/src/memarena.h @@ -40,7 +40,7 @@ class FMemArena { public: - FMemArena(); + FMemArena(int blocksize = 10*1024); ~FMemArena(); void *Alloc(size_t size); @@ -55,6 +55,7 @@ protected: Block *TopBlock; Block *FreeBlocks; + int BlockSize; }; // An arena specializing in storage of FStrings. It knows how to free them, diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index af92bf72f..316ae4246 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -57,6 +57,7 @@ #include "math/cmath.h" extern FRandom pr_exrandom; +FMemArena FxAlloc(65536); struct FLOP { @@ -483,7 +484,9 @@ FxVectorValue::FxVectorValue(FxExpression *x, FxExpression *y, FxExpression *z, FxVectorValue::~FxVectorValue() { for (auto &a : xyz) + { SAFE_DELETE(a); + } } FxExpression *FxVectorValue::Resolve(FCompileContext&ctx) @@ -3721,6 +3724,8 @@ ExpEmit FxBinaryLogical::Emit(VMFunctionBuilder *build) build->Emit(OP_JMP, 1); auto ctarget = build->Emit(OP_LI, to.RegNum, (Operator == TK_AndAnd) ? 0 : 1); for (auto addr : patchspots) build->Backpatch(addr, ctarget); + list.Clear(); + list.ShrinkToFit(); return to; } @@ -4362,6 +4367,7 @@ FxMinMax::FxMinMax(TArray &expr, FName type, const FScriptPositio for (unsigned i = 0; i < expr.Size(); ++i) { choices[i] = expr[i]; + expr[i] = nullptr; } } @@ -4713,10 +4719,12 @@ FxRandomPick::FxRandomPick(FRandom *r, TArray &expr, bool floaty, if (floaty) { choices[index] = new FxFloatCast(expr[index]); + expr[index] = nullptr; } else { choices[index] = new FxIntCast(expr[index], nowarn); + expr[index] = nullptr; } } @@ -5218,6 +5226,11 @@ FxMemberIdentifier::FxMemberIdentifier(FxExpression *left, FName name, const FSc ExprType = EFX_MemberIdentifier; } +FxMemberIdentifier::~FxMemberIdentifier() +{ + SAFE_DELETE(Object); +} + //========================================================================== // // @@ -5277,6 +5290,7 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) return nullptr; } auto x = isclass? new FxClassMember(Object, vsym, ScriptPosition) : new FxStructMember(Object, vsym, ScriptPosition); + Object = nullptr; delete this; return x->Resolve(ctx); } @@ -5313,6 +5327,7 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); } auto x = new FxStructMember(Object, vsym, ScriptPosition); + Object = nullptr; delete this; return x->Resolve(ctx); } @@ -5942,12 +5957,12 @@ ExpEmit FxArrayElement::Emit(VMFunctionBuilder *build) // //========================================================================== -FxFunctionCall::FxFunctionCall(FName methodname, FName rngname, FArgumentList *args, const FScriptPosition &pos) +FxFunctionCall::FxFunctionCall(FName methodname, FName rngname, FArgumentList &args, const FScriptPosition &pos) : FxExpression(EFX_FunctionCall, pos) { MethodName = methodname; RNG = &pr_exrandom; - ArgList = args; + ArgList = std::move(args); if (rngname != NAME_None) { switch (MethodName) @@ -5976,7 +5991,6 @@ FxFunctionCall::FxFunctionCall(FName methodname, FName rngname, FArgumentList *a FxFunctionCall::~FxFunctionCall() { - SAFE_DELETE(ArgList); } //========================================================================== @@ -5985,9 +5999,9 @@ FxFunctionCall::~FxFunctionCall() // //========================================================================== -static bool CheckArgSize(FName fname, FArgumentList *args, int min, int max, FScriptPosition &sc) +static bool CheckArgSize(FName fname, FArgumentList &args, int min, int max, FScriptPosition &sc) { - int s = args ? args->Size() : 0; + int s = args.Size(); if (s < min) { sc.Message(MSG_ERROR, "Insufficient arguments in call to %s, expected %d, got %d", fname.GetChars(), min, s); @@ -6030,7 +6044,6 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) } auto self = !(afd->Variants[0].Flags & VARF_Static)? new FxSelf(ScriptPosition) : nullptr; auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, false); - ArgList = nullptr; delete this; return x->Resolve(ctx); } @@ -6040,7 +6053,6 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) if (MethodName == FxFlops[i].Name) { FxExpression *x = new FxFlopFunctionCall(i, ArgList, ScriptPosition); - ArgList = nullptr; delete this; return x->Resolve(ctx); } @@ -6059,7 +6071,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) } if (special != 0 && min >= 0) { - int paramcount = ArgList? ArgList->Size() : 0; + int paramcount = ArgList.Size(); if (paramcount < min) { ScriptPosition.Message(MSG_ERROR, "Not enough parameters for '%s' (expected %d, got %d)", @@ -6076,7 +6088,6 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) } FxExpression *self = (ctx.Function && ctx.Function->Variants[0].Flags & VARF_Method) ? new FxSelf(ScriptPosition) : nullptr; FxExpression *x = new FxActionSpecialCall(self, special, ArgList, ScriptPosition); - ArgList = nullptr; delete this; return x->Resolve(ctx); } @@ -6086,8 +6097,8 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) { - FxExpression *x = new FxDynamicCast(cls, (*ArgList)[0]); - (*ArgList)[0] = nullptr; + FxExpression *x = new FxDynamicCast(cls, ArgList[0]); + ArgList[0] = nullptr; delete this; return x->Resolve(ctx); } @@ -6126,29 +6137,29 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) MethodName == NAME_Color ? TypeColor : MethodName == NAME_State? TypeState :(PType*)TypeSound; - func = new FxTypeCast((*ArgList)[0], type, true, true); - (*ArgList)[0] = nullptr; + func = new FxTypeCast(ArgList[0], type, true, true); + ArgList[0] = nullptr; } break; case NAME_Random: // allow calling Random without arguments to default to (0, 255) - if (ArgList->Size() == 0) + if (ArgList.Size() == 0) { func = new FxRandom(RNG, new FxConstant(0, ScriptPosition), new FxConstant(255, ScriptPosition), ScriptPosition, ctx.FromDecorate); } else if (CheckArgSize(NAME_Random, ArgList, 2, 2, ScriptPosition)) { - func = new FxRandom(RNG, (*ArgList)[0], (*ArgList)[1], ScriptPosition, ctx.FromDecorate); - (*ArgList)[0] = (*ArgList)[1] = nullptr; + func = new FxRandom(RNG, ArgList[0], ArgList[1], ScriptPosition, ctx.FromDecorate); + ArgList[0] = ArgList[1] = nullptr; } break; case NAME_FRandom: if (CheckArgSize(NAME_FRandom, ArgList, 2, 2, ScriptPosition)) { - func = new FxFRandom(RNG, (*ArgList)[0], (*ArgList)[1], ScriptPosition); - (*ArgList)[0] = (*ArgList)[1] = nullptr; + func = new FxFRandom(RNG, ArgList[0], ArgList[1], ScriptPosition); + ArgList[0] = ArgList[1] = nullptr; } break; @@ -6156,16 +6167,15 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_FRandomPick: if (CheckArgSize(MethodName, ArgList, 1, -1, ScriptPosition)) { - func = new FxRandomPick(RNG, *ArgList, MethodName == NAME_FRandomPick, ScriptPosition, ctx.FromDecorate); - for (auto &i : *ArgList) i = nullptr; + func = new FxRandomPick(RNG, ArgList, MethodName == NAME_FRandomPick, ScriptPosition, ctx.FromDecorate); } break; case NAME_Random2: if (CheckArgSize(NAME_Random2, ArgList, 0, 1, ScriptPosition)) { - func = new FxRandom2(RNG, ArgList->Size() == 0? nullptr : (*ArgList)[0], ScriptPosition, ctx.FromDecorate); - if (ArgList->Size() > 0) (*ArgList)[0] = nullptr; + func = new FxRandom2(RNG, ArgList.Size() == 0? nullptr : ArgList[0], ScriptPosition, ctx.FromDecorate); + if (ArgList.Size() > 0) ArgList[0] = nullptr; } break; @@ -6173,8 +6183,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Max: if (CheckArgSize(MethodName, ArgList, 2, -1, ScriptPosition)) { - func = new FxMinMax(*ArgList, MethodName, ScriptPosition); - for (auto &i : *ArgList) i = nullptr; + func = new FxMinMax(ArgList, MethodName, ScriptPosition); } break; @@ -6183,20 +6192,20 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) { TArray pass; pass.Resize(2); - pass[0] = (*ArgList)[0]; - pass[1] = (*ArgList)[1]; + pass[0] = ArgList[0]; + pass[1] = ArgList[1]; pass[0] = new FxMinMax(pass, NAME_Max, ScriptPosition); - pass[1] = (*ArgList)[2]; + pass[1] = ArgList[2]; func = new FxMinMax(pass, NAME_Min, ScriptPosition); - (*ArgList)[0] = (*ArgList)[1] = (*ArgList)[2] = nullptr; + ArgList[0] = ArgList[1] = ArgList[2] = nullptr; } break; case NAME_Abs: if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) { - func = new FxAbs((*ArgList)[0]); - (*ArgList)[0] = nullptr; + func = new FxAbs(ArgList[0]); + ArgList[0] = nullptr; } break; @@ -6204,8 +6213,8 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_VectorAngle: if (CheckArgSize(MethodName, ArgList, 2, 2, ScriptPosition)) { - func = MethodName == NAME_ATan2 ? new FxATan2((*ArgList)[0], (*ArgList)[1], ScriptPosition) : new FxATan2((*ArgList)[1], (*ArgList)[0], ScriptPosition); - (*ArgList)[0] = (*ArgList)[1] = nullptr; + func = MethodName == NAME_ATan2 ? new FxATan2(ArgList[0], ArgList[1], ScriptPosition) : new FxATan2(ArgList[1], ArgList[0], ScriptPosition); + ArgList[0] = ArgList[1] = nullptr; } break; @@ -6229,12 +6238,12 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) // //========================================================================== -FxMemberFunctionCall::FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos) +FxMemberFunctionCall::FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList &args, const FScriptPosition &pos) : FxExpression(EFX_MemberFunctionCall, pos) { Self = self; MethodName = methodname; - ArgList = args; + ArgList = std::move(args); } //========================================================================== @@ -6246,7 +6255,6 @@ FxMemberFunctionCall::FxMemberFunctionCall(FxExpression *self, FName methodname, FxMemberFunctionCall::~FxMemberFunctionCall() { SAFE_DELETE(Self); - SAFE_DELETE(ArgList); } //========================================================================== @@ -6342,7 +6350,6 @@ isresolved: // do not pass the self pointer to static functions. auto self = (afd->Variants[0].Flags & VARF_Method) ? Self : nullptr; auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, staticonly); - ArgList = nullptr; if (Self == self) Self = nullptr; delete this; return x->Resolve(ctx); @@ -6358,12 +6365,12 @@ isresolved: // //========================================================================== -FxActionSpecialCall::FxActionSpecialCall(FxExpression *self, int special, FArgumentList *args, const FScriptPosition &pos) +FxActionSpecialCall::FxActionSpecialCall(FxExpression *self, int special, FArgumentList &args, const FScriptPosition &pos) : FxExpression(EFX_ActionSpecialCall, pos) { Self = self; Special = special; - ArgList = args; + ArgList = std::move(args); EmitTail = false; } @@ -6376,7 +6383,6 @@ FxActionSpecialCall::FxActionSpecialCall(FxExpression *self, int special, FArgum FxActionSpecialCall::~FxActionSpecialCall() { SAFE_DELETE(Self); - SAFE_DELETE(ArgList); } //========================================================================== @@ -6403,51 +6409,48 @@ FxExpression *FxActionSpecialCall::Resolve(FCompileContext& ctx) bool failed = false; SAFE_RESOLVE_OPT(Self, ctx); - if (ArgList != nullptr) + for (unsigned i = 0; i < ArgList.Size(); i++) { - for (unsigned i = 0; i < ArgList->Size(); i++) + ArgList[i] = ArgList[i]->Resolve(ctx); + if (ArgList[i] == nullptr) { - (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); - if ((*ArgList)[i] == nullptr) + failed = true; + } + else if (Special < 0 && i == 0) + { + if (ArgList[i]->ValueType == TypeString) { + ArgList[i] = new FxNameCast(ArgList[i]); + ArgList[i] = ArgList[i]->Resolve(ctx); + if (ArgList[i] == nullptr) + { + failed = true; + } + } + else if (ArgList[i]->ValueType != TypeName) + { + ScriptPosition.Message(MSG_ERROR, "Name expected for parameter %d", i); failed = true; } - else if (Special < 0 && i == 0) - { - if ((*ArgList)[i]->ValueType == TypeString) - { - (*ArgList)[i] = new FxNameCast((*ArgList)[i]); - (*ArgList)[i] = (*ArgList)[i]->Resolve(ctx); - if ((*ArgList)[i] == nullptr) - { - failed = true; - } - } - else if ((*ArgList)[i]->ValueType != TypeName) - { - ScriptPosition.Message(MSG_ERROR, "Name expected for parameter %d", i); - failed = true; - } - } - else if (!(*ArgList)[i]->IsInteger()) - { - if ((*ArgList)[i]->ValueType->GetRegType() == REGT_FLOAT /* lax */) - { - (*ArgList)[i] = new FxIntCast((*ArgList)[i], ctx.FromDecorate); - } - else - { - ScriptPosition.Message(MSG_ERROR, "Integer expected for parameter %d", i); - failed = true; - } - } } - if (failed) + else if (!ArgList[i]->IsInteger()) { - delete this; - return nullptr; + if (ArgList[i]->ValueType->GetRegType() == REGT_FLOAT /* lax */) + { + ArgList[i] = new FxIntCast(ArgList[i], ctx.FromDecorate); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Integer expected for parameter %d", i); + failed = true; + } } } + if (failed) + { + delete this; + return nullptr; + } ValueType = TypeSInt32; return this; } @@ -6481,30 +6484,27 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) // fixme: This really should use the Self pointer that got passed to this class instead of just using the first argument from the function. // Once static functions are possible, or specials can be called through a member access operator this won't work anymore. build->Emit(OP_PARAM, 0, REGT_POINTER, 0); // pass self - if (ArgList != nullptr) + for (; i < ArgList.Size(); ++i) { - for (; i < ArgList->Size(); ++i) + FxExpression *argex = ArgList[i]; + if (Special < 0 && i == 0) { - FxExpression *argex = (*ArgList)[i]; - if (Special < 0 && i == 0) + assert(argex->ValueType == TypeName); + assert(argex->isConstant()); + build->EmitParamInt(-static_cast(argex)->GetValue().GetName()); + } + else + { + assert(argex->ValueType->GetRegType() == REGT_INT); + if (argex->isConstant()) { - assert(argex->ValueType == TypeName); - assert(argex->isConstant()); - build->EmitParamInt(-static_cast(argex)->GetValue().GetName()); + build->EmitParamInt(static_cast(argex)->GetValue().GetInt()); } else { - assert(argex->ValueType->GetRegType() == REGT_INT); - if (argex->isConstant()) - { - build->EmitParamInt(static_cast(argex)->GetValue().GetInt()); - } - else - { - ExpEmit arg(argex->Emit(build)); - build->Emit(OP_PARAM, 0, arg.RegType, arg.RegNum); - arg.Free(build); - } + ExpEmit arg(argex->Emit(build)); + build->Emit(OP_PARAM, 0, arg.RegType, arg.RegNum); + arg.Free(build); } } } @@ -6515,6 +6515,8 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); assert(((PSymbolVMFunction *)sym)->Function != nullptr); callfunc = ((PSymbolVMFunction *)sym)->Function; + ArgList.Clear(); + ArgList.ShrinkToFit(); if (EmitTail) { @@ -6536,12 +6538,12 @@ ExpEmit FxActionSpecialCall::Emit(VMFunctionBuilder *build) // //========================================================================== -FxVMFunctionCall::FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool novirtual) +FxVMFunctionCall::FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList &args, const FScriptPosition &pos, bool novirtual) : FxExpression(EFX_VMFunctionCall, pos) { Self = self; Function = func; - ArgList = args; + ArgList = std::move(args); EmitTail = false; NoVirtual = novirtual; } @@ -6554,7 +6556,6 @@ FxVMFunctionCall::FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumen FxVMFunctionCall::~FxVMFunctionCall() { - SAFE_DELETE(ArgList); } //========================================================================== @@ -6581,7 +6582,7 @@ VMFunction *FxVMFunctionCall::GetDirectFunction() // then it can be a "direct" function. That is, the DECORATE // definition can call that function directly without wrapping // it inside VM code. - if ((ArgList ? ArgList->Size() : 0) == 0 && !(Function->Variants[0].Flags & VARF_Virtual)) + if (ArgList.Size() == 0 && !(Function->Variants[0].Flags & VARF_Virtual)) { return Function->Variants[0].Implementation; } @@ -6613,18 +6614,18 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) return nullptr; } - if (ArgList != nullptr) + if (ArgList.Size() > 0) { bool foundvarargs = false; PType * type = nullptr; - if (argtypes.Last() != nullptr && ArgList->Size() + implicit > argtypes.Size()) + if (argtypes.Last() != nullptr && ArgList.Size() + implicit > argtypes.Size()) { ScriptPosition.Message(MSG_ERROR, "Too many arguments in call to %s", Function->SymbolName.GetChars()); delete this; return nullptr; } - for (unsigned i = 0; i < ArgList->Size(); i++) + for (unsigned i = 0; i < ArgList.Size(); i++) { // Varargs must all have the same type as the last typed argument. A_Jump is the only function using it. if (!foundvarargs) @@ -6634,12 +6635,12 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) } assert(type != nullptr); - FxExpression *x = new FxTypeCast((*ArgList)[i], type, false); + FxExpression *x = new FxTypeCast(ArgList[i], type, false); x = x->Resolve(ctx); failed |= (x == nullptr); - (*ArgList)[i] = x; + ArgList[i] = x; } - int numargs = ArgList->Size() + implicit; + int numargs = ArgList.Size() + implicit; if ((unsigned)numargs < argtypes.Size() && argtypes[numargs] != nullptr) { auto flags = Function->Variants[0].ArgFlags[numargs]; @@ -6679,13 +6680,15 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) { assert(build->Registers[REGT_POINTER].GetMostUsed() >= build->NumImplicits); - int count = 0; (ArgList ? ArgList->Size() : 0); + int count = 0; if (count == 1) { ExpEmit reg; if (CheckEmitCast(build, EmitTail, reg)) { + ArgList.Clear(); + ArgList.ShrinkToFit(); return reg; } } @@ -6718,13 +6721,13 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) selfemit.Free(build); } // Emit code to pass explicit parameters - if (ArgList != nullptr) + for (unsigned i = 0; i < ArgList.Size(); ++i) { - for (unsigned i = 0; i < ArgList->Size(); ++i) - { - count += EmitParameter(build, (*ArgList)[i], ScriptPosition); - } + count += EmitParameter(build, ArgList[i], ScriptPosition); } + ArgList.Clear(); + ArgList.ShrinkToFit(); + // Get a constant register for this function VMFunction *vmfunc = Function->Variants[0].Implementation; int funcaddr = build->GetConstantAddress(vmfunc, ATAG_OBJECT); @@ -6766,7 +6769,7 @@ bool FxVMFunctionCall::CheckEmitCast(VMFunctionBuilder *build, bool returnit, Ex funcname == NAME___decorate_internal_state__ || funcname == NAME___decorate_internal_float__) { - FxExpression *arg = (*ArgList)[0]; + FxExpression *arg = ArgList[0]; if (returnit) { if (arg->isConstant() && @@ -6799,12 +6802,12 @@ bool FxVMFunctionCall::CheckEmitCast(VMFunctionBuilder *build, bool returnit, Ex // //========================================================================== -FxFlopFunctionCall::FxFlopFunctionCall(size_t index, FArgumentList *args, const FScriptPosition &pos) +FxFlopFunctionCall::FxFlopFunctionCall(size_t index, FArgumentList &args, const FScriptPosition &pos) : FxExpression(EFX_FlopFunctionCall, pos) { assert(index < countof(FxFlops) && "FLOP index out of range"); Index = (int)index; - ArgList = args; + ArgList = std::move(args); } //========================================================================== @@ -6815,44 +6818,43 @@ FxFlopFunctionCall::FxFlopFunctionCall(size_t index, FArgumentList *args, const FxFlopFunctionCall::~FxFlopFunctionCall() { - SAFE_DELETE(ArgList); } FxExpression *FxFlopFunctionCall::Resolve(FCompileContext& ctx) { CHECKRESOLVED(); - if (ArgList == nullptr || ArgList->Size() != 1) + if (ArgList.Size() != 1) { ScriptPosition.Message(MSG_ERROR, "%s only has one parameter", FName(FxFlops[Index].Name).GetChars()); delete this; return nullptr; } - (*ArgList)[0] = (*ArgList)[0]->Resolve(ctx); - if ((*ArgList)[0] == nullptr) + ArgList[0] = ArgList[0]->Resolve(ctx); + if (ArgList[0] == nullptr) { delete this; return nullptr; } - if (!(*ArgList)[0]->IsNumeric()) + if (!ArgList[0]->IsNumeric()) { ScriptPosition.Message(MSG_ERROR, "numeric value expected for parameter"); delete this; return nullptr; } - if ((*ArgList)[0]->isConstant()) + if (ArgList[0]->isConstant()) { - double v = static_cast((*ArgList)[0])->GetValue().GetFloat(); + double v = static_cast(ArgList[0])->GetValue().GetFloat(); v = FxFlops[Index].Evaluate(v); FxExpression *x = new FxConstant(v, ScriptPosition); delete this; return x; } - if ((*ArgList)[0]->ValueType->GetRegType() == REGT_INT) + if (ArgList[0]->ValueType->GetRegType() == REGT_INT) { - (*ArgList)[0] = new FxFloatCast((*ArgList)[0]); + ArgList[0] = new FxFloatCast(ArgList[0]); } ValueType = TypeFloat64; return this; @@ -6865,10 +6867,12 @@ FxExpression *FxFlopFunctionCall::Resolve(FCompileContext& ctx) ExpEmit FxFlopFunctionCall::Emit(VMFunctionBuilder *build) { - ExpEmit v = (*ArgList)[0]->Emit(build); + ExpEmit v = ArgList[0]->Emit(build); assert(!v.Konst && v.RegType == REGT_FLOAT); build->Emit(OP_FLOP, v.RegNum, v.RegNum, FxFlops[Index].Flop); + ArgList.Clear(); + ArgList.ShrinkToFit(); return v; } @@ -7081,17 +7085,16 @@ bool FxCompoundStatement::CheckLocalVariable(FName name) // //========================================================================== -FxSwitchStatement::FxSwitchStatement(FxExpression *cond, FArgumentList *content, const FScriptPosition &pos) +FxSwitchStatement::FxSwitchStatement(FxExpression *cond, FArgumentList &content, const FScriptPosition &pos) : FxExpression(EFX_SwitchStatement, pos) { Condition = new FxIntCast(cond, false); - Content = content; + Content = std::move(content); } FxSwitchStatement::~FxSwitchStatement() { SAFE_DELETE(Condition); - SAFE_DELETE(Content); } FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) @@ -7099,7 +7102,7 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) CHECKRESOLVED(); SAFE_RESOLVE(Condition, ctx); - if (Content == nullptr || Content->Size() == 0) + if (Content.Size() == 0) { ScriptPosition.Message(MSG_WARNING, "Empty switch statement"); if (Condition->isConstant()) @@ -7117,7 +7120,7 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) } } - for (auto &line : *Content) + for (auto &line : Content) { // Do not resolve breaks, they need special treatment inside switch blocks. if (line->ExprType != EFX_JumpStatement || static_cast(line)->Token != TK_Break) @@ -7130,7 +7133,7 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) if (Condition->isConstant()) { ScriptPosition.Message(MSG_WARNING, "Case expression is constant"); - auto &content = *Content; + auto &content = Content; int defaultindex = -1; int defaultbreak = -1; int caseindex = -1; @@ -7182,7 +7185,7 @@ FxExpression *FxSwitchStatement::Resolve(FCompileContext &ctx) int mincase = INT_MAX; int maxcase = INT_MIN; - for (auto line : *Content) + for (auto line : Content) { if (line->ExprType == EFX_CaseStatement) { @@ -7227,7 +7230,7 @@ ExpEmit FxSwitchStatement::Emit(VMFunctionBuilder *build) size_t DefaultAddress = build->Emit(OP_JMP, 0); TArray BreakAddresses; - for (auto line : *Content) + for (auto line : Content) { switch (line->ExprType) { @@ -7266,6 +7269,8 @@ ExpEmit FxSwitchStatement::Emit(VMFunctionBuilder *build) { build->BackpatchToHere(addr); } + Content.Clear(); + Content.ShrinkToFit(); return ExpEmit(); } @@ -7278,14 +7283,14 @@ ExpEmit FxSwitchStatement::Emit(VMFunctionBuilder *build) bool FxSwitchStatement::CheckReturn() { //A switch statement returns when it contains no breaks and ends with a return - for (auto line : *Content) + for (auto line : Content) { if (line->ExprType == EFX_JumpStatement) { return false; // Break means that the end of the statement will be reached, Continue cannot happen in the last statement of the last block. } } - return Content->Size() > 0 && Content->Last()->CheckReturn(); + return Content.Size() > 0 && Content.Last()->CheckReturn(); } //========================================================================== @@ -8414,6 +8419,8 @@ ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), names.Size() + 1, 1); build->Emit(OP_RESULT, 0, REGT_POINTER, dest.RegNum); + names.Clear(); + names.ShrinkToFit(); return dest; } @@ -8433,6 +8440,11 @@ FxLocalVariableDeclaration::FxLocalVariableDeclaration(PType *type, FName name, Init = initval == nullptr? nullptr : new FxTypeCast(initval, type, false); } +FxLocalVariableDeclaration::~FxLocalVariableDeclaration() +{ + SAFE_DELETE(Init); +} + FxExpression *FxLocalVariableDeclaration::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index df0ba7594..46d419051 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -56,6 +56,8 @@ class VMFunctionBuilder; class FxJumpStatement; +extern FMemArena FxAlloc; + //========================================================================== // // @@ -317,6 +319,14 @@ public: bool isresolved = false; bool NeedResult = true; // should be set to false if not needed and properly handled by all nodes for their subnodes to eliminate redundant code EFxType ExprType; + + void *operator new(size_t size) + { + return FxAlloc.Alloc(size); + } + + void operator delete(void *block) {} + void operator delete[](void *block) {} }; //========================================================================== @@ -347,6 +357,7 @@ class FxMemberIdentifier : public FxIdentifier public: FxMemberIdentifier(FxExpression *obj, FName i, const FScriptPosition &p); + ~FxMemberIdentifier(); FxExpression *Resolve(FCompileContext&); }; @@ -1264,11 +1275,11 @@ class FxFunctionCall : public FxExpression { FName MethodName; FRandom *RNG; - FArgumentList *ArgList; + FArgumentList ArgList; public: - FxFunctionCall(FName methodname, FName rngname, FArgumentList *args, const FScriptPosition &pos); + FxFunctionCall(FName methodname, FName rngname, FArgumentList &args, const FScriptPosition &pos); ~FxFunctionCall(); FxExpression *Resolve(FCompileContext&); }; @@ -1284,11 +1295,11 @@ class FxMemberFunctionCall : public FxExpression { FxExpression *Self; FName MethodName; - FArgumentList *ArgList; + FArgumentList ArgList; public: - FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList *args, const FScriptPosition &pos); + FxMemberFunctionCall(FxExpression *self, FName methodname, FArgumentList &args, const FScriptPosition &pos); ~FxMemberFunctionCall(); FxExpression *Resolve(FCompileContext&); }; @@ -1305,11 +1316,11 @@ class FxActionSpecialCall : public FxExpression int Special; bool EmitTail; FxExpression *Self; - FArgumentList *ArgList; + FArgumentList ArgList; public: - FxActionSpecialCall(FxExpression *self, int special, FArgumentList *args, const FScriptPosition &pos); + FxActionSpecialCall(FxExpression *self, int special, FArgumentList &args, const FScriptPosition &pos); ~FxActionSpecialCall(); FxExpression *Resolve(FCompileContext&); PPrototype *ReturnProto(); @@ -1325,11 +1336,11 @@ public: class FxFlopFunctionCall : public FxExpression { int Index; - FArgumentList *ArgList; + FArgumentList ArgList; public: - FxFlopFunctionCall(size_t index, FArgumentList *args, const FScriptPosition &pos); + FxFlopFunctionCall(size_t index, FArgumentList &args, const FScriptPosition &pos); ~FxFlopFunctionCall(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); @@ -1366,10 +1377,10 @@ class FxVMFunctionCall : public FxExpression bool NoVirtual; FxExpression *Self; PFunction *Function; - FArgumentList *ArgList; + FArgumentList ArgList; public: - FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList *args, const FScriptPosition &pos, bool novirtual); + FxVMFunctionCall(FxExpression *self, PFunction *func, FArgumentList &args, const FScriptPosition &pos, bool novirtual); ~FxVMFunctionCall(); FxExpression *Resolve(FCompileContext&); PPrototype *ReturnProto(); @@ -1429,7 +1440,7 @@ public: class FxSwitchStatement : public FxExpression { FxExpression *Condition; - FArgumentList *Content; + FArgumentList Content; struct CaseAddr { @@ -1440,7 +1451,7 @@ class FxSwitchStatement : public FxExpression TArray CaseAddresses; public: - FxSwitchStatement(FxExpression *cond, FArgumentList *content, const FScriptPosition &pos); + FxSwitchStatement(FxExpression *cond, FArgumentList &content, const FScriptPosition &pos); ~FxSwitchStatement(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); @@ -1714,6 +1725,7 @@ public: int RegNum = -1; FxLocalVariableDeclaration(PType *type, FName name, FxExpression *initval, int varflags, const FScriptPosition &p); + ~FxLocalVariableDeclaration(); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); void Release(VMFunctionBuilder *build); diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index c63677e0c..7e4c3b398 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -482,7 +482,6 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) else if (sc.CheckToken(TK_Identifier)) { FName identifier = FName(sc.String); - FArgumentList *args; PFunction *func; switch (identifier) @@ -503,18 +502,12 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) // There is an action function ACS_NamedExecuteWithResult which must be ignored here for this to work. if (func != nullptr && identifier != NAME_ACS_NamedExecuteWithResult) { - args = new FArgumentList; + FArgumentList args; if (sc.CheckToken('(')) { sc.UnGet(); - ParseFunctionParameters(sc, cls, *args, func, "", nullptr); + ParseFunctionParameters(sc, cls, args, func, "", nullptr); } - if (args->Size() == 0) - { - delete args; - args = nullptr; - } - return new FxVMFunctionCall(new FxSelf(sc), func, args, sc, false); } } @@ -536,26 +529,17 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) case NAME_VectorAngle: return ParseAtan2(sc, identifier, cls); default: - args = new FArgumentList; - try + FArgumentList args; + if (!sc.CheckToken(')')) { - if (!sc.CheckToken(')')) + do { - do - { - args->Push(ParseExpressionM (sc, cls)); - } - while (sc.CheckToken(',')); - sc.MustGetToken(')'); + args.Push(ParseExpressionM (sc, cls)); } - return new FxFunctionCall(identifier, NAME_None, args, sc); + while (sc.CheckToken(',')); + sc.MustGetToken(')'); } - catch (...) - { - delete args; - throw; - } - break; + return new FxFunctionCall(identifier, NAME_None, args, sc); } } else diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index d17cb5d4d..e3cb74c32 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -75,8 +75,8 @@ FxVMFunctionCall *DoActionSpecials(FScanner &sc, FState & state, Baggage &bag) if (special > 0 && min_args >= 0) { - FArgumentList *args = new FArgumentList; - args->Push(new FxConstant(special, sc)); + FArgumentList args; + args.Push(new FxConstant(special, sc)); i = 0; // Make this consistent with all other parameter parsing @@ -84,7 +84,7 @@ FxVMFunctionCall *DoActionSpecials(FScanner &sc, FState & state, Baggage &bag) { while (i < 5) { - args->Push(new FxIntCast(ParseExpression(sc, bag.Info), true)); + args.Push(new FxIntCast(ParseExpression(sc, bag.Info), true)); i++; if (!sc.CheckToken (',')) break; } @@ -571,13 +571,9 @@ FxVMFunctionCall *ParseAction(FScanner &sc, FState state, FString statestring, B PFunction *afd = dyn_cast(bag.Info->Symbols.FindSymbol(symname, true)); if (afd != NULL) { - FArgumentList *args = new FArgumentList; - ParseFunctionParameters(sc, bag.Info, *args, afd, statestring, &bag.statedef); - call = new FxVMFunctionCall(new FxSelf(sc), afd, args->Size() > 0 ? args : NULL, sc, false); - if (args->Size() == 0) - { - delete args; - } + FArgumentList args; + ParseFunctionParameters(sc, bag.Info, args, afd, statestring, &bag.statedef); + call = new FxVMFunctionCall(new FxSelf(sc), afd, args, sc, false); return call; } sc.ScriptError("Invalid parameter '%s'\n", sc.String); diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index e5ed249b1..acb67e2f5 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -776,4 +776,5 @@ void FFunctionBuildList::Build() } FScriptPosition::StrictErrors = false; mItems.Clear(); + FxAlloc.FreeAllBlocks(); } \ No newline at end of file diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 0d99ee5c2..7db62d6fb 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2239,7 +2239,7 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClass *cls, ZCC_TreeNode *af) if (fc->Parameters == nullptr && !(afd->Variants[0].Flags & VARF_Virtual)) { // We can use this function directly without wrapping it in a caller. - return new FxVMFunctionCall(new FxSelf(*af), afd, nullptr, *af, false); + return new FxVMFunctionCall(new FxSelf(*af), afd, FArgumentList(), *af, false); } } else @@ -2563,16 +2563,17 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) // - class members // - array syntax for random() calls. // Everything else coming here is a syntax error. + FArgumentList args; switch (fcall->Function->NodeType) { case AST_ExprID: // The function name is a simple identifier. - return new FxFunctionCall(static_cast(fcall->Function)->Identifier, NAME_None, ConvertNodeList(fcall->Parameters), *ast); + return new FxFunctionCall(static_cast(fcall->Function)->Identifier, NAME_None, ConvertNodeList(args, fcall->Parameters), *ast); case AST_ExprMemberAccess: { auto ema = static_cast(fcall->Function); - return new FxMemberFunctionCall(ConvertNode(ema->Left), ema->Right, ConvertNodeList(fcall->Parameters), *ast); + return new FxMemberFunctionCall(ConvertNode(ema->Left), ema->Right, ConvertNodeList(args, fcall->Parameters), *ast); } case AST_ExprBinary: @@ -2582,7 +2583,7 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) auto binary = static_cast(fcall->Function); if (binary->Left->NodeType == AST_ExprID && binary->Right->NodeType == AST_ExprID) { - return new FxFunctionCall(static_cast(binary->Left)->Identifier, static_cast(binary->Right)->Identifier, ConvertNodeList(fcall->Parameters), *ast); + return new FxFunctionCall(static_cast(binary->Left)->Identifier, static_cast(binary->Right)->Identifier, ConvertNodeList(args, fcall->Parameters), *ast); } } // fall through if this isn't an array access node. @@ -2832,21 +2833,20 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) case AST_ReturnStmt: { auto ret = static_cast(ast); - FArgumentList *args = ConvertNodeList(ret->Values); - if (args->Size() == 0) + FArgumentList args; + ConvertNodeList(args, ret->Values); + if (args.Size() == 0) { return new FxReturnStatement(nullptr, *ast); } - else if (args->Size() == 1) + else if (args.Size() == 1) { - auto arg = (*args)[0]; - (*args)[0] = nullptr; - delete args; - return new FxReturnStatement((*args)[0], *ast); + auto arg = args[0]; + args[0] = nullptr; + return new FxReturnStatement(arg, *ast); } else { - delete args; Error(ast, "Return with multiple values not implemented yet."); return new FxReturnStatement(nullptr, *ast); } @@ -2893,7 +2893,8 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) { // The switch content is wrapped into a compound statement which needs to be unraveled here. auto cmpnd = static_cast(swtch->Content); - return new FxSwitchStatement(ConvertNode(swtch->Condition), ConvertNodeList(cmpnd->Content), *ast); + FArgumentList args; + return new FxSwitchStatement(ConvertNode(swtch->Condition), ConvertNodeList(args, cmpnd->Content), *ast); } } @@ -2922,17 +2923,16 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) } -FArgumentList *ZCCCompiler::ConvertNodeList(ZCC_TreeNode *head) +FArgumentList &ZCCCompiler::ConvertNodeList(FArgumentList &args, ZCC_TreeNode *head) { - FArgumentList *list = new FArgumentList; if (head != nullptr) { auto node = head; do { - list->Push(ConvertNode(node)); + args.Push(ConvertNode(node)); node = node->SiblingNext; } while (node != head); } - return list; + return args; } \ No newline at end of file diff --git a/src/scripting/zscript/zcc_compile.h b/src/scripting/zscript/zcc_compile.h index 2e38d68d2..2e8840a46 100644 --- a/src/scripting/zscript/zcc_compile.h +++ b/src/scripting/zscript/zcc_compile.h @@ -144,7 +144,7 @@ private: FxExpression *ConvertAST(PClass *cclass, ZCC_TreeNode *ast); FxExpression *ConvertNode(ZCC_TreeNode *node); - FArgumentList *ConvertNodeList(ZCC_TreeNode *head); + FArgumentList &ConvertNodeList(FArgumentList &, ZCC_TreeNode *head); DObject *Outer; PClass *ConvertClass; // class type to be used when resoving symbold while converting an AST From 15ddf70f58721314d71e1cd051eb09a92182b087 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 09:27:52 +0100 Subject: [PATCH 218/255] - typo --- src/p_mobj.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 7c973351f..3205067b8 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -310,7 +310,7 @@ void AActor::InitNativeFields() meta->AddNativeField("DeathType", TypeName, myoffsetof(AActor, DeathType)); meta->AddNativeField("DamageFactor", TypeFloat64, myoffsetof(AActor, DamageFactor)); meta->AddNativeField("DamageMultiply", TypeFloat64, myoffsetof(AActor, DamageMultiply)); - meta->AddNativeField("TelefogSpurceType", TypeActorClass, myoffsetof(AActor, TeleFogSourceType)); + meta->AddNativeField("TelefogSourceType", TypeActorClass, myoffsetof(AActor, TeleFogSourceType)); meta->AddNativeField("TelefogDestType", TypeActorClass, myoffsetof(AActor, TeleFogDestType)); meta->AddNativeField("SpawnState", TypeState, myoffsetof(AActor, SpawnState), VARF_ReadOnly); meta->AddNativeField("SeeState", TypeState, myoffsetof(AActor, SeeState), VARF_ReadOnly); From 65299312813c91dbcd856ce113e55f6c97c3d05f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 14:40:32 +0100 Subject: [PATCH 219/255] fixed and completed the special field init code. Strings can now be used as class members, and so can structs which contain strings. - made 'DamageMultiply' an actor property and moved the initialization of ConversationRoot to the property handler for the compiler to get this stuff out of the type classes. - consolidate default initialization into one function which performs all the required setup. The original implementation did this when adding the fields but that cannot work because at that time no defaults have been created yet. - fixed: When deriving a class the child class's defaults also must initialize the copied parent fields with special initialization. This part was completely missing. - removed DECORATE code for parsing native classes because it's no longer needed. --- src/dobjtype.cpp | 66 +++++++++++++++++------ src/dobjtype.h | 9 +++- src/info.cpp | 29 ---------- src/info.h | 1 - src/scripting/decorate/thingdef_parse.cpp | 38 ++----------- src/scripting/thingdef.h | 2 - src/scripting/thingdef_properties.cpp | 9 ++++ src/scripting/zscript/zcc_compile.cpp | 10 +++- wadsrc/static/zscript/actor.txt | 3 +- 9 files changed, 81 insertions(+), 86 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 71bfd542b..0e17299cd 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2778,14 +2778,14 @@ void PClass::StaticBootstrap() PClass::PClass() { Size = sizeof(DObject); - ParentClass = NULL; - Pointers = NULL; - FlatPointers = NULL; - HashNext = NULL; - Defaults = NULL; + ParentClass = nullptr; + Pointers = nullptr; + FlatPointers = nullptr; + HashNext = nullptr; + Defaults = nullptr; bRuntimeClass = false; bExported = false; - ConstructNative = NULL; + ConstructNative = nullptr; mDescriptiveName = "Class"; PClass::AllClasses.Push(this); @@ -2969,10 +2969,7 @@ DObject *PClass::CreateNew() const ConstructNative (mem); ((DObject *)mem)->SetClass (const_cast(this)); - if (Defaults != NULL) - { - InitializeSpecials(mem); - } + InitializeSpecials(mem); return (DObject *)mem; } @@ -3037,16 +3034,52 @@ void PClass::Derive(PClass *newclass) { newclass->ParentClass = this; newclass->ConstructNative = ConstructNative; + newclass->Symbols.SetParentTable(&this->Symbols); + newclass->InitializeDefaults(); +} - // Set up default instance of the new class. - newclass->Defaults = (BYTE *)M_Malloc(newclass->Size); - if (Defaults) memcpy(newclass->Defaults, Defaults, Size); - if (newclass->Size > Size) +//========================================================================== +// +// PClassActor :: InitializeNativeDefaults +// +//========================================================================== + +void PClass::InitializeDefaults() +{ + assert(Defaults == NULL); + Defaults = (BYTE *)M_Malloc(Size); + if (ParentClass->Defaults != NULL) { - memset(newclass->Defaults + Size, 0, newclass->Size - Size); + memcpy(Defaults, ParentClass->Defaults, ParentClass->Size); + if (Size > ParentClass->Size) + { + memset(Defaults + ParentClass->Size, 0, Size - ParentClass->Size); + } + } + else + { + memset(Defaults, 0, Size); } - newclass->Symbols.SetParentTable(&this->Symbols); + if (bRuntimeClass) + { + // Copy parent values from the parent defaults. + assert(ParentClass != NULL); + ParentClass->InitializeSpecials(Defaults); + + // and initialize our own special values. + auto it = Symbols.GetIterator(); + PSymbolTable::MapType::Pair *pair; + + while (it.NextPair(pair)) + { + auto field = dyn_cast(pair->Value); + if (field != nullptr && !(field->Flags & VARF_Native)) + { + field->Type->SetDefaultValue(Defaults, unsigned(field->Offset), &SpecialInits); + } + } + } } //========================================================================== @@ -3136,7 +3169,6 @@ PField *PClass::AddField(FName name, PType *type, DWORD flags) { Defaults = (BYTE *)M_Realloc(Defaults, Size); memset(Defaults + oldsize, 0, Size - oldsize); - type->SetDefaultValue(Defaults, unsigned(field->Offset), &SpecialInits); } return field; } diff --git a/src/dobjtype.h b/src/dobjtype.h index e1f95a828..62860d0bd 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -137,6 +137,13 @@ struct PSymbolTable // Frees all symbols from this table. void ReleaseSymbols(); + typedef TMap MapType; + + MapType::Iterator GetIterator() + { + return MapType::Iterator(Symbols); + } + // add a name to help debugging. #ifdef _DEBUG FString name; @@ -147,7 +154,6 @@ struct PSymbolTable private: - typedef TMap MapType; PSymbolTable *ParentSymbolTable; MapType Symbols; @@ -761,6 +767,7 @@ public: void WriteAllFields(FSerializer &ar, const void *addr) const; bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; bool ReadAllFields(FSerializer &ar, void *addr) const; + void InitializeDefaults(); virtual void DeriveData(PClass *newclass) {} static void StaticInit(); diff --git a/src/info.cpp b/src/info.cpp index 09d0905f6..83b455fb4 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -355,35 +355,6 @@ size_t PClassActor::PropagateMark() return Super::PropagateMark(); } -//========================================================================== -// -// PClassActor :: InitializeNativeDefaults -// -// This is used by DECORATE to assign ActorInfos to internal classes -// -//========================================================================== - -void PClassActor::InitializeNativeDefaults() -{ - assert(Defaults == NULL); - Defaults = (BYTE *)M_Malloc(Size); - if (ParentClass->Defaults != NULL) - { - memcpy(Defaults, ParentClass->Defaults, ParentClass->Size); - if (Size > ParentClass->Size) - { - memset(Defaults + ParentClass->Size, 0, Size - ParentClass->Size); - } - } - else - { - memset (Defaults, 0, Size); - // Non-DECORATE properties that must be set. - ((AActor*)Defaults)->DamageMultiply = 1.; // fixme: Make this a DECORATE property. - ((AActor*)Defaults)->ConversationRoot = -1; - } -} - //========================================================================== // // PClassActor :: SetReplacement diff --git a/src/info.h b/src/info.h index ad25bdcaf..6aee02bed 100644 --- a/src/info.h +++ b/src/info.h @@ -234,7 +234,6 @@ public: void SetDamageFactor(FName type, double factor); void SetPainChance(FName type, int chance); size_t PropagateMark(); - void InitializeNativeDefaults(); bool SetReplacement(FName replaceName); void SetDropItems(DDropItem *drops); virtual void Finalize(FStateDefinitions &statedef); diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index 07da3cf57..baa662047 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -875,7 +875,7 @@ static void ParseActorProperty(FScanner &sc, Baggage &bag) // Starts a new actor definition // //========================================================================== -PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName parentName, bool native) +PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName parentName) { PClassActor *replacee = NULL; PClassActor *ti = NULL; @@ -908,36 +908,7 @@ PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName par parent = RUNTIME_CLASS(AActor); } } - - if (native) - { - ti = PClass::FindActor(typeName); - if (ti == NULL) - { - extern void DumpTypeTable(); - DumpTypeTable(); - sc.Message(MSG_ERROR, "Unknown native actor '%s'", typeName.GetChars()); - goto create; - } - else if (ti != RUNTIME_CLASS(AActor) && ti->ParentClass->NativeClass() != parent->NativeClass()) - { - sc.Message(MSG_ERROR, "Native class '%s' does not inherit from '%s'", typeName.GetChars(), parentName.GetChars()); - parent = RUNTIME_CLASS(AActor); - goto create; - } - else if (ti->Defaults != NULL) - { - sc.Message(MSG_ERROR, "Redefinition of internal class '%s'", typeName.GetChars()); - goto create; - } - ti->InitializeNativeDefaults(); - ti->ParentClass->DeriveData(ti); - } - else - { - create: - ti = DecoDerivedClass(sc, parent, typeName); - } + ti = DecoDerivedClass(sc, parent, typeName); ti->Replacee = ti->Replacement = NULL; ti->DoomEdNum = -1; @@ -1025,12 +996,13 @@ static PClassActor *ParseActorHeader(FScanner &sc, Baggage *bag) if (sc.CheckString("native")) { - native = true; + sc.ScriptMessage("Cannot define native classes in DECORATE"); + FScriptPosition::ErrorCounter++; } try { - PClassActor *info = CreateNewActor(sc, typeName, parentName, native); + PClassActor *info = CreateNewActor(sc, typeName, parentName); info->DoomEdNum = DoomEdNum > 0 ? DoomEdNum : -1; info->SourceLumpName = Wads.GetLumpFullPath(sc.LumpNum); diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 6529059e6..2c13d8eb7 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -164,8 +164,6 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, // //========================================================================== -PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName parentName, bool native); - void HandleActorFlag(FScanner &sc, Baggage &bag, const char *part1, const char *part2, int mod); FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool constant); diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index aa4508950..45d78557c 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -652,6 +652,15 @@ DEFINE_PROPERTY(damage, X, Actor) CreateDamageFunction(bag.Info, defaults, id, true); } +//========================================================================== +// +//========================================================================== +DEFINE_PROPERTY(damagemultiply, F, Actor) +{ + PROP_FLOAT_PARM(dmgm, 0); + defaults->DamageMultiply = dmgm; +} + //========================================================================== // //========================================================================== diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 7db62d6fb..a2e2262f2 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1917,13 +1917,19 @@ void ZCCCompiler::InitDefaults() if (ti->ParentClass->Defaults == DEFAULTS_VMEXPORT) { ti->ParentClass->Defaults = nullptr; - static_cast(ti->ParentClass)->InitializeNativeDefaults(); + ti->ParentClass->InitializeDefaults(); ti->ParentClass->ParentClass->DeriveData(ti->ParentClass); } - ti->InitializeNativeDefaults(); + ti->InitializeDefaults(); ti->ParentClass->DeriveData(ti); + // We need special treatment for this one field in AActor's defaults which cannot be made visible to DECORATE as a property. + // It's better to do this here under controlled conditions than deeper down in the class type classes. + if (ti == RUNTIME_CLASS(AActor)) + { + ((AActor*)ti->Defaults)->ConversationRoot = 1; + } Baggage bag; #ifdef _DEBUG diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 5aa1af293..c70ab28a1 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -23,7 +23,8 @@ class Actor : Thinker native FloatBobPhase -1; // randomly initialize by default Gravity 1; Friction 1; - DamageFactor 1.0; + DamageFactor 1.0; // damage multiplier as target of damage. + DamageMultiply 1.0; // damage multiplier as source of damage. PushFactor 0.25; WeaveIndexXY 0; WeaveIndexZ 16; From 5e8c8b80c9ee796d06b8d0fd628d706fc75e7b6c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 14:51:36 +0100 Subject: [PATCH 220/255] - removed bogus token paste operator. --- src/dobject.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/dobject.h b/src/dobject.h index 3c4b23248..22ebf1305 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -176,7 +176,7 @@ protected: \ ExportedNatives(ExportedNatives&&) = delete; #define VMEXPORT_NATIVES_FUNC(func) \ - template ret func(void *ptr, args ... arglist) { return static_cast(ptr)->object::##func(arglist...); } + template ret func(void *ptr, args ... arglist) { return static_cast(ptr)->object::func(arglist...); } #define VMEXPORT_NATIVES_END(cls) }; From 8d01ba77339b2fdbcde36077929c106c6591e787 Mon Sep 17 00:00:00 2001 From: Edoardo Prezioso Date: Fri, 11 Nov 2016 15:22:53 +0100 Subject: [PATCH 221/255] - Fixed Clang errors with delayed templates on. --- src/dobject.h | 11 ++++++----- src/scripting/zscript/zcc_compile.cpp | 3 ++- 2 files changed, 8 insertions(+), 6 deletions(-) diff --git a/src/dobject.h b/src/dobject.h index 22ebf1305..d6bae3dad 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -36,6 +36,7 @@ #include #include "doomtype.h" +#include "i_system.h" class PClass; @@ -202,8 +203,8 @@ protected: \ PClass *cls::StaticType() const { return RegistrationInfo.MyClass; } #define IMPLEMENT_CLASS(cls, isabstract, ptrs, fields, vmexport) \ - _X_CONSTRUCTOR_##isabstract##(cls) \ - _IMP_PCLASS(cls, _X_POINTERS_##ptrs##(cls), _X_ABSTRACT_##isabstract##(cls), _X_FIELDS_##fields##(cls), _X_VMEXPORT_##vmexport##(cls)) + _X_CONSTRUCTOR_##isabstract(cls) \ + _IMP_PCLASS(cls, _X_POINTERS_##ptrs(cls), _X_ABSTRACT_##isabstract(cls), _X_FIELDS_##fields(cls), _X_VMEXPORT_##vmexport(cls)) // Taking the address of a field in an object at address 1 instead of // address 0 keeps GCC from complaining about possible misuse of offsetof. @@ -644,15 +645,15 @@ private: public: void Destroy() { - ExportedNatives::Get()->Destroy(this); + ExportedNatives::Get()->template Destroy(this); } void Tick() { - ExportedNatives::Get()->Tick(this); + ExportedNatives::Get()->template Tick(this); } AInventory *DropInventory(AInventory *item) { - return ExportedNatives::Get()->DropInventory(this, item); + return ExportedNatives::Get()->template DropInventory(this, item); } }; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index a2e2262f2..7d338cc69 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2244,8 +2244,9 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClass *cls, ZCC_TreeNode *af) { if (fc->Parameters == nullptr && !(afd->Variants[0].Flags & VARF_Virtual)) { + FArgumentList argumentlist; // We can use this function directly without wrapping it in a caller. - return new FxVMFunctionCall(new FxSelf(*af), afd, FArgumentList(), *af, false); + return new FxVMFunctionCall(new FxSelf(*af), afd, argumentlist, *af, false); } } else From a1aceaf04fb3e427b2c8bd9074ab4dcb1e4ff21d Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Fri, 11 Nov 2016 16:01:09 +0100 Subject: [PATCH 222/255] Fixed the remaining errors with GCC --- src/dobject.h | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/dobject.h b/src/dobject.h index d6bae3dad..60668ceec 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -609,6 +609,13 @@ protected: } }; +//Initial list +VMEXPORTED_NATIVES_START + VMEXPORTED_NATIVES_FUNC(Destroy) + VMEXPORTED_NATIVES_FUNC(Tick) + VMEXPORTED_NATIVES_FUNC(DropInventory) +VMEXPORTED_NATIVES_END + class AInventory;// template @@ -672,13 +679,6 @@ ClassReg DVMObject::RegistrationInfo = }; template _DECLARE_TI(DVMObject) -//Initial list -VMEXPORTED_NATIVES_START - VMEXPORTED_NATIVES_FUNC(Destroy) - VMEXPORTED_NATIVES_FUNC(Tick) - VMEXPORTED_NATIVES_FUNC(DropInventory) -VMEXPORTED_NATIVES_END - VMEXPORT_NATIVES_START(DObject, void) VMEXPORT_NATIVES_FUNC(Destroy) VMEXPORT_NATIVES_END(DObject) From 72e77a6c657ee5ed7b8c762723692fb21c6d53c2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 20:05:07 +0100 Subject: [PATCH 223/255] - implemented handling for virtual function. Syntax-wise I chose to make it as strict as possible to reduce the chance of errors: Virtual base functions must be declared with the 'virtual' keyword, and overrides in child classes with the 'override' keyword. This way any mismatch in parameters that otherwise would cause silent failure will outright produce a compile error. --- src/d_dehacked.cpp | 1 - src/dobjtype.cpp | 88 +++++++++++++++++++----- src/dobjtype.h | 9 ++- src/sc_man_scanner.re | 1 + src/sc_man_tokens.h | 1 + src/scripting/codegeneration/codegen.cpp | 76 ++++++++++++++------ src/scripting/vm/vm.h | 2 + src/scripting/vm/vmdisasm.cpp | 1 + src/scripting/vm/vmexec.h | 9 +++ src/scripting/vm/vmops.h | 1 + src/scripting/zscript/zcc-parse.lemon | 2 + src/scripting/zscript/zcc_compile.cpp | 72 +++++++++++++++++-- src/scripting/zscript/zcc_parser.cpp | 2 + src/scripting/zscript/zcc_parser.h | 2 + wadsrc/static/zscript/base.txt | 2 +- 15 files changed, 222 insertions(+), 47 deletions(-) diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index 8258a656e..eef9b137a 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -3030,7 +3030,6 @@ void FinishDehPatch () while (subclass == nullptr); AActor *defaults2 = GetDefaultByType (subclass); - memcpy ((void *)defaults2, (void *)defaults1, sizeof(AActor)); // Make a copy of the replaced class's state labels FStateDefinitions statedef; diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index 0e17299cd..b7e666fc1 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -156,14 +156,14 @@ PClassType::PClassType() //========================================================================== // -// PClassType :: Derive +// PClassType :: DeriveData // //========================================================================== -void PClassType::Derive(PClass *newclass) +void PClassType::DeriveData(PClass *newclass) { assert(newclass->IsKindOf(RUNTIME_CLASS(PClassType))); - Super::Derive(newclass); + Super::DeriveData(newclass); static_cast(newclass)->TypeTableType = TypeTableType; } @@ -3030,12 +3030,14 @@ void PClass::DestroySpecials(void *addr) const // //========================================================================== -void PClass::Derive(PClass *newclass) +void PClass::Derive(PClass *newclass, FName name) { + newclass->bRuntimeClass = true; newclass->ParentClass = this; newclass->ConstructNative = ConstructNative; newclass->Symbols.SetParentTable(&this->Symbols); - newclass->InitializeDefaults(); + newclass->TypeName = name; + newclass->mDescriptiveName.Format("Class<%s>", name.GetChars()); } //========================================================================== @@ -3082,6 +3084,18 @@ void PClass::InitializeDefaults() } } +//========================================================================== +// +// PClass :: DeriveData +// +// Copies inheritable data to the child class. +// +//========================================================================== + +void PClass::DeriveData(PClass *newclass) +{ +} + //========================================================================== // // PClass :: CreateDerivedClass @@ -3126,11 +3140,10 @@ PClass *PClass::CreateDerivedClass(FName name, unsigned int size) // Create a new type object of the same type as us. (We may be a derived class of PClass.) type = static_cast(GetClass()->CreateNew()); - type->TypeName = name; type->Size = size; - type->bRuntimeClass = true; - type->mDescriptiveName.Format("Class<%s>", name.GetChars()); - Derive(type); + Derive(type, name); + type->InitializeDefaults(); + type->Virtuals = Virtuals; DeriveData(type); if (!notnew) { @@ -3178,8 +3191,7 @@ PField *PClass::AddField(FName name, PType *type, DWORD flags) // PClass :: FindClassTentative // // Like FindClass but creates a placeholder if no class is found. -// CreateDerivedClass will automatically fill in the placeholder when the -// actual class is defined. +// This will be filled in when the actual class is constructed. // //========================================================================== @@ -3201,17 +3213,59 @@ PClass *PClass::FindClassTentative(FName name, bool fatal) PClass *type = static_cast(GetClass()->CreateNew()); DPrintf(DMSG_SPAMMY, "Creating placeholder class %s : %s\n", name.GetChars(), TypeName.GetChars()); - type->TypeName = name; - type->ParentClass = this; - type->ConstructNative = ConstructNative; + Derive(type, name); type->Size = TentativeClass; - type->bRuntimeClass = true; - type->mDescriptiveName.Format("Class<%s>", name.GetChars()); - type->Symbols.SetParentTable(&Symbols); TypeTable.AddType(type, RUNTIME_CLASS(PClass), (intptr_t)type->Outer, name, bucket); return type; } +//========================================================================== +// +// PClass :: FindVirtualIndex +// +// Compares a prototype with the existing list of virtual functions +// and returns an index if something matching is found. +// +//========================================================================== + +int PClass::FindVirtualIndex(FName name, PPrototype *proto) +{ + for (unsigned i = 0; i < Virtuals.Size(); i++) + { + if (Virtuals[i]->Name == name) + { + auto vproto = Virtuals[i]->Proto; + if (vproto->ReturnTypes.Size() != proto->ReturnTypes.Size() || + vproto->ArgumentTypes.Size() != proto->ArgumentTypes.Size()) + { + continue; // number of parameters does not match, so it's incompatible + } + bool fail = false; + // The first argument is self and will mismatch so just skip it. + for (unsigned a = 1; a < proto->ArgumentTypes.Size(); a++) + { + if (proto->ArgumentTypes[a] != vproto->ArgumentTypes[a]) + { + fail = true; + break; + } + } + if (fail) continue; + + for (unsigned a = 0; a < proto->ReturnTypes.Size(); a++) + { + if (proto->ReturnTypes[a] != vproto->ReturnTypes[a]) + { + fail = true; + break; + } + } + if (!fail) return i; + } + } + return -1; +} + //========================================================================== // // PClass :: BuildFlatPointers diff --git a/src/dobjtype.h b/src/dobjtype.h index 62860d0bd..7746dce29 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -31,6 +31,7 @@ enum VARF_Implicit = (1<<12), // implicitly created parameters (i.e. do not compare types when checking function signatures) VARF_Static = (1<<13), // static class data (by necessity read only.) VARF_InternalAccess = (1<<14), // overrides VARF_ReadOnly for internal script code. + VARF_Override = (1<<15), // overrides a virtual function from the parent class. }; // Symbol information ------------------------------------------------------- @@ -756,7 +757,7 @@ protected: // We unravel _WITH_META here just as we did for PType. enum { MetaClassNum = CLASSREG_PClassClass }; TArray SpecialInits; - virtual void Derive(PClass *newclass); + void Derive(PClass *newclass, FName name); void InitializeSpecials(void *addr) const; void SetSuper(); public: @@ -768,8 +769,9 @@ public: bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; bool ReadAllFields(FSerializer &ar, void *addr) const; void InitializeDefaults(); + int FindVirtualIndex(FName name, PPrototype *proto); + virtual void DeriveData(PClass *newclass); - virtual void DeriveData(PClass *newclass) {} static void StaticInit(); static void StaticShutdown(); static void StaticBootstrap(); @@ -782,6 +784,7 @@ public: BYTE *Defaults; bool bRuntimeClass; // class was defined at run-time, not compile-time bool bExported; // This type has been declared in a script + TArray Virtuals; // virtual function table void (*ConstructNative)(void *); @@ -838,7 +841,7 @@ class PClassType : public PClass protected: public: PClassType(); - virtual void Derive(PClass *newclass); + virtual void DeriveData(PClass *newclass); PClass *TypeTableType; // The type to use for hashing into the type table }; diff --git a/src/sc_man_scanner.re b/src/sc_man_scanner.re index bc0a4b2e2..194582d73 100644 --- a/src/sc_man_scanner.re +++ b/src/sc_man_scanner.re @@ -168,6 +168,7 @@ std2: 'optional' { RET(TK_Optional); } 'export' { RET(TK_Export); } 'virtual' { RET(TK_Virtual); } + 'override' { RET(TK_Override); } 'super' { RET(TK_Super); } 'global' { RET(TK_Global); } 'stop' { RET(TK_Stop); } diff --git a/src/sc_man_tokens.h b/src/sc_man_tokens.h index 2b93c9ac2..801d02be3 100644 --- a/src/sc_man_tokens.h +++ b/src/sc_man_tokens.h @@ -105,6 +105,7 @@ xx(TK_Iterator, "'iterator'") xx(TK_Optional, "'optional'") xx(TK_Export, "'expert'") xx(TK_Virtual, "'virtual'") +xx(TK_Override, "'override'") xx(TK_Super, "'super'") xx(TK_Null, "'null'") xx(TK_Global, "'global'") diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 316ae4246..49b1d6bae 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6693,12 +6693,16 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } } + VMFunction *vmfunc = Function->Variants[0].Implementation; + bool staticcall = (vmfunc->Final || vmfunc->VirtualIndex == -1 || NoVirtual); + count = 0; // Emit code to pass implied parameters + ExpEmit selfemit; if (Function->Variants[0].Flags & VARF_Method) { assert(Self != nullptr); - ExpEmit selfemit = Self->Emit(build); + selfemit = Self->Emit(build); assert(selfemit.RegType == REGT_POINTER); build->Emit(OP_PARAM, 0, selfemit.RegType, selfemit.RegNum); count += 1; @@ -6718,8 +6722,9 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) } count += 2; } - selfemit.Free(build); + if (staticcall) selfemit.Free(build); } + else staticcall = true; // Emit code to pass explicit parameters for (unsigned i = 0; i < ArgList.Size(); ++i) { @@ -6729,27 +6734,56 @@ ExpEmit FxVMFunctionCall::Emit(VMFunctionBuilder *build) ArgList.ShrinkToFit(); // Get a constant register for this function - VMFunction *vmfunc = Function->Variants[0].Implementation; - int funcaddr = build->GetConstantAddress(vmfunc, ATAG_OBJECT); - // Emit the call - if (EmitTail) - { // Tail call - build->Emit(OP_TAIL_K, funcaddr, count, 0); - ExpEmit call; - call.Final = true; - return call; - } - else if (vmfunc->Proto->ReturnTypes.Size() > 0) - { // Call, expecting one result - ExpEmit reg(build, vmfunc->Proto->ReturnTypes[0]->GetRegType(), vmfunc->Proto->ReturnTypes[0]->GetRegCount()); - build->Emit(OP_CALL_K, funcaddr, count, 1); - build->Emit(OP_RESULT, 0, EncodeRegType(reg), reg.RegNum); - return reg; + if (staticcall) + { + int funcaddr = build->GetConstantAddress(vmfunc, ATAG_OBJECT); + // Emit the call + if (EmitTail) + { // Tail call + build->Emit(OP_TAIL_K, funcaddr, count, 0); + ExpEmit call; + call.Final = true; + return call; + } + else if (vmfunc->Proto->ReturnTypes.Size() > 0) + { // Call, expecting one result + ExpEmit reg(build, vmfunc->Proto->ReturnTypes[0]->GetRegType(), vmfunc->Proto->ReturnTypes[0]->GetRegCount()); + build->Emit(OP_CALL_K, funcaddr, count, 1); + build->Emit(OP_RESULT, 0, EncodeRegType(reg), reg.RegNum); + return reg; + } + else + { // Call, expecting no results + build->Emit(OP_CALL_K, funcaddr, count, 0); + return ExpEmit(); + } } else - { // Call, expecting no results - build->Emit(OP_CALL_K, funcaddr, count, 0); - return ExpEmit(); + { + selfemit.Free(build); + ExpEmit funcreg(build, REGT_POINTER); + build->Emit(OP_VTBL, funcreg.RegNum, selfemit.RegNum, vmfunc->VirtualIndex); + if (EmitTail) + { // Tail call + build->Emit(OP_TAIL, funcreg.RegNum, count, 0); + ExpEmit call; + call.Final = true; + return call; + } + else if (vmfunc->Proto->ReturnTypes.Size() > 0) + { // Call, expecting one result + ExpEmit reg(build, vmfunc->Proto->ReturnTypes[0]->GetRegType(), vmfunc->Proto->ReturnTypes[0]->GetRegCount()); + build->Emit(OP_CALL, funcreg.RegNum, count, 1); + build->Emit(OP_RESULT, 0, EncodeRegType(reg), reg.RegNum); + return reg; + } + else + { // Call, expecting no results + build->Emit(OP_CALL, funcreg.RegNum, count, 0); + return ExpEmit(); + } + + } } diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index abce2f557..6c7878a9a 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -655,7 +655,9 @@ class VMFunction : public DObject HAS_OBJECT_POINTERS; public: bool Native; + bool Final = false; // cannot be overridden BYTE ImplicitArgs = 0; // either 0 for static, 1 for method or 3 for action + int VirtualIndex = -1; FName Name; TArray DefaultArgs; diff --git a/src/scripting/vm/vmdisasm.cpp b/src/scripting/vm/vmdisasm.cpp index 239a0dc51..49c929f05 100644 --- a/src/scripting/vm/vmdisasm.cpp +++ b/src/scripting/vm/vmdisasm.cpp @@ -84,6 +84,7 @@ #define RPI8 MODE_AP | MODE_BIMMZ | MODE_CUNUSED #define KPI8 MODE_AKP | MODE_BIMMZ | MODE_CUNUSED #define RPI8I8 MODE_AP | MODE_BIMMZ | MODE_CIMMZ +#define RPRPI8 MODE_AP | MODE_BP | MODE_CIMMZ #define KPI8I8 MODE_AKP | MODE_BIMMZ | MODE_CIMMZ #define I8BCP MODE_AIMMZ | MODE_BCJOINT | MODE_BCPARAM #define THROW MODE_AIMMZ | MODE_BCTHROW diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index 69f406dd8..a6eda2a24 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -525,6 +525,15 @@ begin: } } NEXTOP; + OP(VTBL): + ASSERTA(a); ASSERTA(B); + { + auto o = (DObject*)reg.a[B]; + auto p = o->GetClass(); + assert(C < p->Virtuals.Size()); + reg.a[a] = p->Virtuals[C]; + } + NEXTOP; OP(CALL_K): ASSERTKA(a); assert(konstatag[a] == ATAG_OBJECT); diff --git a/src/scripting/vm/vmops.h b/src/scripting/vm/vmops.h index e7ff19c22..368f143bd 100644 --- a/src/scripting/vm/vmops.h +++ b/src/scripting/vm/vmops.h @@ -82,6 +82,7 @@ xx(PARAM, param, __BCP), // push parameter encoded in BC for function call (B=r xx(PARAMI, parami, I24), // push immediate, signed integer for function call xx(CALL, call, RPI8I8), // Call function pkA with parameter count B and expected result count C xx(CALL_K, call, KPI8I8), +xx(VTBL, vtbl, RPRPI8), // dereferences a virtual method table. xx(TAIL, tail, RPI8), // Call+Ret in a single instruction xx(TAIL_K, tail, KPI8), xx(RESULT, result, __BCP), // Result should go in register encoded in BC (in caller, after CALL) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index fc707428e..6caef777e 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -905,6 +905,8 @@ decl_flags(X) ::= decl_flags(A) META(T). { X.Int = A.Int | ZCC_Meta; X.SourceLo decl_flags(X) ::= decl_flags(A) ACTION(T). { X.Int = A.Int | ZCC_Action; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } decl_flags(X) ::= decl_flags(A) READONLY(T). { X.Int = A.Int | ZCC_ReadOnly; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } decl_flags(X) ::= decl_flags(A) DEPRECATED(T). { X.Int = A.Int | ZCC_Deprecated; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } +decl_flags(X) ::= decl_flags(A) VIRTUAL(T). { X.Int = A.Int | ZCC_Virtual; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } +decl_flags(X) ::= decl_flags(A) OVERRIDE(T). { X.Int = A.Int | ZCC_Override; X.SourceLoc = A.SourceLoc ? A.SourceLoc : T.SourceLoc; } func_const(X) ::= . { X.Int = 0; X.SourceLoc = stat->sc->GetMessageLine(); } func_const(X) ::= CONST(T). { X.Int = ZCC_FuncConst; X.SourceLoc = T.SourceLoc; } diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 7d338cc69..6c837cead 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1258,7 +1258,7 @@ bool ZCCCompiler::CompileFields(PStruct *type, TArray &Fiel PType *fieldtype = DetermineType(type, field, field->Names->Name, field->Type, true, true); // For structs only allow 'deprecated', for classes exclude function qualifiers. - int notallowed = forstruct? ~ZCC_Deprecated : ZCC_Latent | ZCC_Final | ZCC_Action | ZCC_Static | ZCC_FuncConst | ZCC_Abstract; + int notallowed = forstruct? ~ZCC_Deprecated : ZCC_Latent | ZCC_Final | ZCC_Action | ZCC_Static | ZCC_FuncConst | ZCC_Abstract | ZCC_Virtual | ZCC_Override; if (field->Flags & notallowed) { @@ -1894,6 +1894,7 @@ void ZCCCompiler::InitDefaults() if (!c->Type()->IsDescendantOf(RUNTIME_CLASS(AActor))) { if (c->Defaults.Size()) Error(c->cls, "%s: Non-actor classes may not have defaults", c->Type()->TypeName.GetChars()); + if (c->Type()->ParentClass) c->Type()->ParentClass->DeriveData(c->Type()); } else { @@ -1989,6 +1990,16 @@ void ZCCCompiler::InitFunctions() for (auto c : Classes) { + // cannot be done earlier because it requires the parent class to be processed by this code, too. + if (c->Type()->ParentClass != nullptr) + { + if (c->Type()->ParentClass->Virtuals.Size() == 0) + { + // This a VMClass which didn't get processed here. + c->Type()->ParentClass->Virtuals = c->Type()->ParentClass->ParentClass->Virtuals; + } + c->Type()->Virtuals = c->Type()->ParentClass->Virtuals; + } for (auto f : c->Functions) { rets.Clear(); @@ -2030,13 +2041,32 @@ void ZCCCompiler::InitFunctions() if (f->Flags & ZCC_Private) varflags |= VARF_Private; if (f->Flags & ZCC_Protected) varflags |= VARF_Protected; if (f->Flags & ZCC_Deprecated) varflags |= VARF_Deprecated; + if (f->Flags & ZCC_Virtual) varflags |= VARF_Virtual; + if (f->Flags & ZCC_Override) varflags |= VARF_Override; if (f->Flags & ZCC_Action) varflags |= VARF_Action|VARF_Final, implicitargs = 3; // Action implies Final. if (f->Flags & ZCC_Static) varflags = (varflags & ~VARF_Method) | VARF_Final, implicitargs = 0; // Static implies Final. - if ((f->Flags & (ZCC_Action | ZCC_Static)) == (ZCC_Action | ZCC_Static)) + + if (varflags & VARF_Override) varflags &= ~VARF_Virtual; // allow 'virtual override'. + // Only one of these flags may be used. + static int exclude[] = { ZCC_Virtual, ZCC_Override, ZCC_Action, ZCC_Static }; + static const char * print[] = { "virtual", "override", "action", "static" }; + int fc = 0; + FString build; + for (int i = 0; i < 4; i++) { - Error(f, "%s: Action and Static on the same function is not allowed.", FName(f->Name).GetChars()); + if (f->Flags & exclude[i]) + { + fc++; + if (build.Len() > 0) build += ", "; + build += print[i]; + } + } + if (fc > 1) + { + Error(f, "Invalid combination of qualifiers %s on function %s.", FName(f->Name).GetChars(), build.GetChars() ); varflags |= VARF_Method; } + if (varflags & VARF_Override) varflags |= VARF_Virtual; // Now that the flags are checked, make all override functions virtual as well. if (f->Flags & ZCC_Native) { @@ -2193,7 +2223,41 @@ void ZCCCompiler::InitFunctions() { sym->Variants[0].Implementation->DefaultArgs = std::move(argdefaults); } - // todo: Check inheritance. + + if (varflags & VARF_Virtual) + { + if (varflags & VARF_Final) + { + sym->Variants[0].Implementation->Final = true; + } + int vindex = c->Type()->FindVirtualIndex(sym->SymbolName, sym->Variants[0].Proto); + // specifying 'override' is necessary to prevent one of the biggest problem spots with virtual inheritance: Mismatching argument types. + if (varflags & VARF_Override) + { + if (vindex == -1) + { + Error(p, "Attempt to override non-existent virtual function %s", FName(f->Name).GetChars()); + } + else + { + auto oldfunc = c->Type()->Virtuals[vindex]; + if (oldfunc->Final) + { + Error(p, "Attempt to override final function %s", FName(f->Name).GetChars()); + } + c->Type()->Virtuals[vindex] = sym->Variants[0].Implementation; + sym->Variants[0].Implementation->VirtualIndex = vindex; + } + } + else + { + if (vindex != -1) + { + Error(p, "Function %s attempts to override parent function without 'override' qualifier", FName(f->Name).GetChars()); + } + sym->Variants[0].Implementation->VirtualIndex = c->Type()->Virtuals.Push(sym->Variants[0].Implementation); + } + } } } } diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index c84b72c66..098a38d82 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -123,6 +123,8 @@ static void InitTokenMap() TOKENDEF (TK_Private, ZCC_PRIVATE); TOKENDEF (TK_Protected, ZCC_PROTECTED); TOKENDEF (TK_Latent, ZCC_LATENT); + TOKENDEF (TK_Virtual, ZCC_VIRTUAL); + TOKENDEF (TK_Override, ZCC_OVERRIDE); TOKENDEF (TK_Final, ZCC_FINAL); TOKENDEF (TK_Meta, ZCC_META); TOKENDEF (TK_Deprecated, ZCC_DEPRECATED); diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index 01ea0d2d0..ec8bd956a 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -33,6 +33,8 @@ enum ZCC_FuncConst = 1 << 10, ZCC_Abstract = 1 << 11, ZCC_Extension = 1 << 12, + ZCC_Virtual = 1 << 13, + ZCC_Override = 1 << 14, }; // Function parameter modifiers diff --git a/wadsrc/static/zscript/base.txt b/wadsrc/static/zscript/base.txt index 4564f0e86..33c1c6135 100644 --- a/wadsrc/static/zscript/base.txt +++ b/wadsrc/static/zscript/base.txt @@ -1,6 +1,6 @@ class Object native { - /*virtual*/ native void Destroy(); + virtual native void Destroy(); native class GetClass(); } From 924096694e700b7d8c9678ae8484487487ece845 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 21:52:08 +0100 Subject: [PATCH 224/255] - implemented super calls and proper dispatch of scripted virtual overrides for Destroy. --- src/dobject.cpp | 1 + src/dobject.h | 30 +++++++++++++++++-- src/scripting/codegeneration/codegen.cpp | 38 ++++++++++++++++++++++-- src/scripting/codegeneration/codegen.h | 18 +++++++++++ src/scripting/zscript/zcc_compile.cpp | 10 +++++++ 5 files changed, 93 insertions(+), 4 deletions(-) diff --git a/src/dobject.cpp b/src/dobject.cpp index e21d07526..6fa7d5317 100644 --- a/src/dobject.cpp +++ b/src/dobject.cpp @@ -366,6 +366,7 @@ void DObject::Destroy () DEFINE_ACTION_FUNCTION(DObject, Destroy) { PARAM_SELF_PROLOGUE(DObject); + self->VMSuperCall(); self->Destroy(); return 0; } diff --git a/src/dobject.h b/src/dobject.h index 60668ceec..d5e11a04c 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -235,7 +235,6 @@ enum EObjectFlags OF_EuthanizeMe = 1 << 5, // Object wants to die OF_Cleanup = 1 << 6, // Object is now being deleted by the collector OF_YesReallyDelete = 1 << 7, // Object is being deleted outside the collector, and this is okay, so don't print a warning - OF_Transient = 1 << 11, // Object should not be archived (references to it will be nulled on disk) OF_WhiteBits = OF_White0 | OF_White1, OF_MarkBits = OF_WhiteBits | OF_Black, @@ -244,6 +243,8 @@ enum EObjectFlags OF_JustSpawned = 1 << 8, // Thinker was spawned this tic OF_SerialSuccess = 1 << 9, // For debugging Serialize() calls OF_Sentinel = 1 << 10, // Object is serving as the sentinel in a ring list + OF_Transient = 1 << 11, // Object should not be archived (references to it will be nulled on disk) + OF_SuperCall = 1 << 12, // A super call from the VM is about to be performed }; template class TObjPtr; @@ -498,6 +499,11 @@ public: void SerializeUserVars(FSerializer &arc); virtual void Serialize(FSerializer &arc); + void VMSuperCall() + { + ObjectFlags |= OF_SuperCall; + } + void ClearClass() { Class = NULL; @@ -652,7 +658,27 @@ private: public: void Destroy() { - ExportedNatives::Get()->template Destroy(this); + if (ObjectFlags & OF_SuperCall) + { + ObjectFlags &= OF_SuperCall; + ExportedNatives::Get()->template Destroy(this); + } + else + { + static int VIndex = -1; + if (VIndex < 0) + { + // Look up the virtual function index in the defining class because this may have gotten overloaded in subclasses with something different than a virtual override. + auto sym = dyn_cast(RUNTIME_CLASS(DObject)->Symbols.FindSymbol("Destroy", false)); + assert(sym != nullptr); + VIndex = sym->Variants[0].Implementation->VirtualIndex; + assert(VIndex >= 0); + } + // Without the type cast this picks the 'void *' assignment... + VMValue params[1] = { (DObject*)this }; + VMFrameStack stack; + stack.Call(GetClass()->Virtuals[VIndex], params, 1, nullptr, 0, nullptr); + } } void Tick() { diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 49b1d6bae..dfe02404b 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -1350,7 +1350,7 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) // first deal with the simple types if (ValueType == TypeError || basex->ValueType == TypeError) { - ScriptPosition.Message(MSG_ERROR, "Trying to cast to invalid type. This error message means that somewhere in the script compiler an error check is missing."); + ScriptPosition.Message(MSG_ERROR, "Trying to cast to invalid type."); delete this; return nullptr; } @@ -5433,6 +5433,25 @@ ExpEmit FxSelf::Emit(VMFunctionBuilder *build) } +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxSuper::Resolve(FCompileContext& ctx) +{ + CHECKRESOLVED(); + if (ctx.Function == nullptr || ctx.Function->Variants[0].SelfClass == nullptr) + { + ScriptPosition.Message(MSG_ERROR, "super used outside of a member function"); + delete this; + return nullptr; + } + ValueType = TypeError; // this intentionally resolves to an invalid type so that it cannot be used outside of super calls. + return this; +} + //========================================================================== // // @@ -6268,6 +6287,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) ABORT(ctx.Class); PClass *cls; bool staticonly = false; + bool novirtual = false; if (Self->ExprType == EFX_Identifier) { @@ -6282,6 +6302,15 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) } SAFE_RESOLVE(Self, ctx); + if (Self->ExprType == EFX_Super) + { + // give the node the proper value type now that we know it's properly used. + cls = ctx.Function->Variants[0].SelfClass->ParentClass; + Self->ValueType = NewPointer(cls); + Self->ExprType = EFX_Self; + novirtual = true; // super calls are always non-virtual + } + if (Self->IsVector()) { // handle builtins: Vectors got 2: Length and Unit. @@ -6349,7 +6378,7 @@ isresolved: // do not pass the self pointer to static functions. auto self = (afd->Variants[0].Flags & VARF_Method) ? Self : nullptr; - auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, staticonly); + auto x = new FxVMFunctionCall(self, afd, ArgList, ScriptPosition, staticonly|novirtual); if (Self == self) Self = nullptr; delete this; return x->Resolve(ctx); @@ -6971,6 +7000,11 @@ FxExpression *FxSequence::Resolve(FCompileContext &ctx) { fail = true; } + if (Expressions[i]->ValueType == TypeError) + { + ScriptPosition.Message(MSG_ERROR, "Invalid statement"); + fail = true; + } } if (fail) { diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 46d419051..d5f812d52 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -276,6 +276,7 @@ enum EFxType EFX_TypeCheck, EFX_DynamicCast, EFX_GlobalVariable, + EFX_Super, EFX_COUNT }; @@ -1241,6 +1242,23 @@ public: ExpEmit Emit(VMFunctionBuilder *build); }; +//========================================================================== +// +// FxSuper +// +//========================================================================== + +class FxSuper : public FxSelf +{ +public: + FxSuper(const FScriptPosition&pos) + : FxSelf(pos) + { + ExprType = EFX_Super; + } + FxExpression *Resolve(FCompileContext&); +}; + //========================================================================== // // FxArrayElement diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 6c837cead..f52e0e062 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2898,6 +2898,16 @@ FxExpression *ZCCCompiler::ConvertNode(ZCC_TreeNode *ast) return list; } + case AST_Expression: + { + auto ret = static_cast(ast); + if (ret->Operation == PEX_Super) + { + return new FxSuper(*ast); + } + break; + } + case AST_ExpressionStmt: return ConvertNode(static_cast(ast)->Expression); From a5f9eb5be1f885346d1fa00a8edb1b6d0489b4b6 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 22:14:29 +0100 Subject: [PATCH 225/255] - Scriptified Heretic's knight. --- src/CMakeLists.txt | 1 - src/g_heretic/a_hereticmisc.cpp | 1 - src/g_heretic/a_knight.cpp | 70 ------------------------ src/p_mobj.cpp | 9 +++ src/scripting/codegeneration/codegen.cpp | 2 +- wadsrc/static/zscript/actor.txt | 1 + wadsrc/static/zscript/heretic/knight.txt | 49 +++++++++++++++-- 7 files changed, 55 insertions(+), 78 deletions(-) delete mode 100644 src/g_heretic/a_knight.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 8b75d7b62..9f5b0346c 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -857,7 +857,6 @@ set( NOT_COMPILED_SOURCE_FILES g_heretic/a_hereticartifacts.cpp g_heretic/a_hereticweaps.cpp g_heretic/a_ironlich.cpp - g_heretic/a_knight.cpp g_heretic/a_wizard.cpp g_hexen/a_bats.cpp g_hexen/a_bishop.cpp diff --git a/src/g_heretic/a_hereticmisc.cpp b/src/g_heretic/a_hereticmisc.cpp index 2ea39a4bc..c6192b8e2 100644 --- a/src/g_heretic/a_hereticmisc.cpp +++ b/src/g_heretic/a_hereticmisc.cpp @@ -26,7 +26,6 @@ #include "a_hereticartifacts.cpp" #include "a_hereticweaps.cpp" #include "a_ironlich.cpp" -#include "a_knight.cpp" #include "a_wizard.cpp" diff --git a/src/g_heretic/a_knight.cpp b/src/g_heretic/a_knight.cpp deleted file mode 100644 index a3125f77d..000000000 --- a/src/g_heretic/a_knight.cpp +++ /dev/null @@ -1,70 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "a_action.h" -#include "a_sharedglobal.h" -#include "gstrings.h" -#include "vm.h" -*/ - -static FRandom pr_dripblood ("DripBlood"); -static FRandom pr_knightatk ("KnightAttack"); - -//---------------------------------------------------------------------------- -// -// PROC A_DripBlood -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_DripBlood) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - double xo = pr_dripblood.Random2() / 32.; - double yo = pr_dripblood.Random2() / 32.; - mo = Spawn ("Blood", self->Vec3Offset(xo, yo, 0.), ALLOW_REPLACE); - mo->Vel.X = pr_dripblood.Random2 () / 64.; - mo->Vel.Y = pr_dripblood.Random2() / 64.; - mo->Gravity = 1./8; - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_KnightAttack -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_KnightAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - { - return 0; - } - if (self->CheckMeleeRange ()) - { - int damage = pr_knightatk.HitDice (3); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - S_Sound (self, CHAN_BODY, "hknight/melee", 1, ATTN_NORM); - return 0; - } - // Throw axe - S_Sound (self, CHAN_BODY, self->AttackSound, 1, ATTN_NORM); - if (self->flags & MF_SHADOW || pr_knightatk () < 40) - { // Red axe - P_SpawnMissileZ (self, self->Z() + 36, self->target, PClass::FindActor("RedAxe")); - return 0; - } - // Green axe - P_SpawnMissileZ (self, self->Z() + 36, self->target, PClass::FindActor("KnightAxe")); - return 0; -} - diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 3205067b8..400fe8c74 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6077,6 +6077,15 @@ AActor *P_SpawnMissileZ (AActor *source, double z, AActor *dest, PClassActor *ty return P_SpawnMissileXYZ (source->PosAtZ(z), source, dest, type); } +DEFINE_ACTION_FUNCTION(AActor, SpawnMissileZ) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(z); + PARAM_OBJECT(dest, AActor); + PARAM_CLASS(type, AActor); + ACTION_RETURN_OBJECT(P_SpawnMissileZ(self, z, dest, type)); +} + AActor *P_SpawnMissileXYZ (DVector3 pos, AActor *source, AActor *dest, PClassActor *type, bool checkspawn, AActor *owner) { if (source == NULL) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index dfe02404b..5e212dfe3 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -7000,7 +7000,7 @@ FxExpression *FxSequence::Resolve(FCompileContext &ctx) { fail = true; } - if (Expressions[i]->ValueType == TypeError) + else if (Expressions[i]->ValueType == TypeError) { ScriptPosition.Message(MSG_ERROR, "Invalid statement"); fail = true; diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index c70ab28a1..0baac6bf0 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -63,6 +63,7 @@ class Actor : Thinker native native Actor GetPointer(int aaptr); native static Actor Spawn(class type, vector3 pos = (0,0,0), int replace = NO_REPLACE); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); + native Actor SpawnMissileZ (double z, Actor dest, class type); native Actor OldSpawnMissile(Actor dest, class type, Actor owner = null); native Actor SpawnPuff(class pufftype, vector3 pos, float hitdir, float particledir, int updown, int flags = 0, Actor vict = null); diff --git a/wadsrc/static/zscript/heretic/knight.txt b/wadsrc/static/zscript/heretic/knight.txt index 1eb341859..01b7252c6 100644 --- a/wadsrc/static/zscript/heretic/knight.txt +++ b/wadsrc/static/zscript/heretic/knight.txt @@ -22,8 +22,6 @@ class Knight : Actor HitObituary "$OB_BONEKNIGHTHIT"; DropItem "CrossbowAmmo", 84, 5; } - - native void A_KnightAttack (); States { @@ -56,6 +54,34 @@ class Knight : Actor Stop; } + //---------------------------------------------------------------------------- + // + // PROC A_KnightAttack + // + //---------------------------------------------------------------------------- + + void A_KnightAttack () + { + if (!target) return; + if (CheckMeleeRange ()) + { + int damage = random[KnightAttack](1, 8) * 3; + int newdam = target.DamageMobj (self, self, damage, 'Melee'); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + A_PlaySound ("hknight/melee", CHAN_BODY); + return; + } + // Throw axe + A_PlaySound (AttackSound, CHAN_BODY); + if (self.bShadow || random[KnightAttack]() < 40) + { // Red axe + SpawnMissileZ (pos.Z + 36, target, "RedAxe"); + } + else + { // Green axe + SpawnMissileZ (pos.Z + 36, target, "KnightAxe"); + } + } } @@ -116,8 +142,6 @@ class RedAxe : KnightAxe Damage 7; } - native void A_DripBlood (); - States { Spawn: @@ -127,5 +151,20 @@ class RedAxe : KnightAxe RAXE CDE 6 BRIGHT; Stop; } + + //---------------------------------------------------------------------------- + // + // PROC A_DripBlood + // + //---------------------------------------------------------------------------- + + void A_DripBlood () + { + double xo = random2[DripBlood]() / 32.0; + double yo = random2[DripBlood]() / 32.0; + Actor mo = Spawn ("Blood", Vec3Offset(xo, yo, 0.), ALLOW_REPLACE); + mo.Vel.X = random2[DripBlood]() / 64.0; + mo.Vel.Y = random2[DripBlood]() / 64.0; + mo.Gravity = 1./8; + } } - From 14a9c13113982870410856bb7faf8d6633208d4f Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Fri, 11 Nov 2016 23:32:13 +0100 Subject: [PATCH 226/255] - scriptified Heretic's wizard. --- src/CMakeLists.txt | 1 - src/g_heretic/a_wizard.cpp | 95 ------------------------ src/p_mobj.cpp | 27 +++++++ src/scripting/codegeneration/codegen.cpp | 14 +++- wadsrc/static/zscript/actor.txt | 24 ++++++ wadsrc/static/zscript/constants.txt | 7 ++ wadsrc/static/zscript/heretic/wizard.txt | 69 +++++++++++++++-- 7 files changed, 135 insertions(+), 102 deletions(-) delete mode 100644 src/g_heretic/a_wizard.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 9f5b0346c..b2f23afb1 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -857,7 +857,6 @@ set( NOT_COMPILED_SOURCE_FILES g_heretic/a_hereticartifacts.cpp g_heretic/a_hereticweaps.cpp g_heretic/a_ironlich.cpp - g_heretic/a_wizard.cpp g_hexen/a_bats.cpp g_hexen/a_bishop.cpp g_hexen/a_blastradius.cpp diff --git a/src/g_heretic/a_wizard.cpp b/src/g_heretic/a_wizard.cpp deleted file mode 100644 index 271fd5592..000000000 --- a/src/g_heretic/a_wizard.cpp +++ /dev/null @@ -1,95 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "s_sound.h" -#include "p_local.h" -#include "p_enemy.h" -#include "a_action.h" -#include "gstrings.h" -#include "vm.h" -*/ - -static FRandom pr_wizatk3 ("WizAtk3"); - -//---------------------------------------------------------------------------- -// -// PROC A_GhostOff -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_GhostOff) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->RenderStyle = STYLE_Normal; - self->flags3 &= ~MF3_GHOST; - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_WizAtk1 -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_WizAtk1) -{ - PARAM_SELF_PROLOGUE(AActor); - - A_FaceTarget (self); - CALL_ACTION(A_GhostOff, self); - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_WizAtk2 -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_WizAtk2) -{ - PARAM_SELF_PROLOGUE(AActor); - - A_FaceTarget (self); - self->Alpha = HR_SHADOW; - self->RenderStyle = STYLE_Translucent; - self->flags3 |= MF3_GHOST; - return 0; -} - -//---------------------------------------------------------------------------- -// -// PROC A_WizAtk3 -// -//---------------------------------------------------------------------------- - -DEFINE_ACTION_FUNCTION(AActor, A_WizAtk3) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - CALL_ACTION(A_GhostOff, self); - if (!self->target) - { - return 0; - } - S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM); - if (self->CheckMeleeRange()) - { - int damage = pr_wizatk3.HitDice (4); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - return 0; - } - PClassActor *fx = PClass::FindActor("WizardFX1"); - mo = P_SpawnMissile (self, self->target, fx); - if (mo != NULL) - { - P_SpawnMissileAngle(self, fx, mo->Angles.Yaw - 45. / 8, mo->Vel.Z); - P_SpawnMissileAngle(self, fx, mo->Angles.Yaw + 45. / 8, mo->Vel.Z); - } - return 0; -} diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 400fe8c74..94b739135 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6041,6 +6041,13 @@ static double GetDefaultSpeed(PClassActor *type) return GetDefaultByType(type)->Speed; } +DEFINE_ACTION_FUNCTION(AActor, GetDefaultSpeed) +{ + PARAM_PROLOGUE; + PARAM_CLASS(type, AActor); + ACTION_RETURN_FLOAT(GetDefaultSpeed(type)); +} + //--------------------------------------------------------------------------- // // FUNC P_SpawnMissile @@ -6283,6 +6290,19 @@ AActor *P_SpawnMissileAngleZSpeed (AActor *source, double z, return (!checkspawn || P_CheckMissileSpawn(mo, source->radius)) ? mo : NULL; } +DEFINE_ACTION_FUNCTION(AActor, SpawnMissileAngleZSpeed) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(z); + PARAM_CLASS(type, AActor); + PARAM_ANGLE(angle); + PARAM_FLOAT(vz); + PARAM_FLOAT(speed); + PARAM_OBJECT_DEF(owner, AActor); + PARAM_BOOL_DEF(checkspawn); + ACTION_RETURN_OBJECT(P_SpawnMissileAngleZSpeed(self, z, type, angle, vz, speed, owner, checkspawn)); +} + /* ================ = @@ -6879,6 +6899,13 @@ DEFINE_ACTION_FUNCTION(AActor, GetDefaultByType) ACTION_RETURN_OBJECT(GetDefaultByType(cls)); } +DEFINE_ACTION_FUNCTION(AActor, GetBobOffset) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT_DEF(frac); + ACTION_RETURN_FLOAT(self->GetBobOffset(frac)); +} + // This combines all 3 variations of the internal function DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) { diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 5e212dfe3..2759e41ba 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6680,7 +6680,19 @@ FxExpression *FxVMFunctionCall::Resolve(FCompileContext& ctx) return nullptr; } } - + } + else + { + if ((unsigned)implicit < argtypes.Size() && argtypes[implicit] != nullptr) + { + auto flags = Function->Variants[0].ArgFlags[implicit]; + if (!(flags & VARF_Optional)) + { + ScriptPosition.Message(MSG_ERROR, "Insufficient arguments in call to %s", Function->SymbolName.GetChars()); + delete this; + return nullptr; + } + } } if (failed) { diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 0baac6bf0..d9fd23a46 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -56,6 +56,8 @@ class Actor : Thinker native native static readonly GetDefaultByType(class cls); native static float deltaangle(float ang1, float ang2); + native static float GetDefaultSpeed(class type); + native float GetBobOffset(float frac = 0); native void SetDamage(int dmg); native static bool isDehState(state st); native void SetOrigin(vector3 newpos, bool moving); @@ -64,6 +66,8 @@ class Actor : Thinker native native static Actor Spawn(class type, vector3 pos = (0,0,0), int replace = NO_REPLACE); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); native Actor SpawnMissileZ (double z, Actor dest, class type); + native Actor SpawnMissileAngleZSpeed (double z, class type, float angle, double vz, double speed, Actor owner = null, bool checkspawn = true); + native Actor OldSpawnMissile(Actor dest, class type, Actor owner = null); native Actor SpawnPuff(class pufftype, vector3 pos, float hitdir, float particledir, int updown, int flags = 0, Actor vict = null); @@ -143,6 +147,26 @@ class Actor : Thinker native void A_SetRipMax(int maximum) { RipLevelMax = maximum; } void A_ScreamAndUnblock() { A_Scream(); A_NoBlocking(); } void A_ActiveAndUnblock() { A_ActiveSound(); A_NoBlocking(); } + + //--------------------------------------------------------------------------- + // + // FUNC P_SpawnMissileAngle + // + // Returns NULL if the missile exploded immediately, otherwise returns + // a mobj_t pointer to the missile. + // + //--------------------------------------------------------------------------- + + Actor SpawnMissileAngle (class type, float angle, double vz) + { + return SpawnMissileAngleZSpeed (pos.z + 32 + GetBobOffset(), type, angle, vz, GetDefaultSpeed (type)); + } + + Actor SpawnMissileAngleZ (double z, class type, double angle, double vz) + { + return SpawnMissileAngleZSpeed (z, type, angle, vz, GetDefaultSpeed (type)); + } + void A_SetScale(float scalex, float scaley = 0, int ptr = AAPTR_DEFAULT, bool usezero = false) { diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 9562e3f40..7c3038a74 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -883,3 +883,10 @@ enum EReplace NO_REPLACE = 0, ALLOW_REPLACE = 1 } + +// This translucency value produces the closest match to Heretic's TINTTAB. +// ~40% of the value of the overlaid image shows through. +const HR_SHADOW = (0x6800 / 65536.); +// Hexen's TINTTAB is the same as Heretic's, just reversed. +const HX_SHADOW = (0x9800 / 65536.); +const HX_ALTSHADOW = (0x6800 / 65536.); diff --git a/wadsrc/static/zscript/heretic/wizard.txt b/wadsrc/static/zscript/heretic/wizard.txt index d33e2dd8a..d146ae220 100644 --- a/wadsrc/static/zscript/heretic/wizard.txt +++ b/wadsrc/static/zscript/heretic/wizard.txt @@ -26,11 +26,6 @@ class Wizard : Actor DropItem "ArtiTomeOfPower", 4, 0; } - native void A_GhostOff (); - native void A_WizAtk1 (); - native void A_WizAtk2 (); - native void A_WizAtk3 (); - States { Spawn: @@ -70,6 +65,70 @@ class Wizard : Actor WZRD M -1 A_SetFloorClip; Stop; } + + //---------------------------------------------------------------------------- + // + // PROC A_GhostOff + // + //---------------------------------------------------------------------------- + + void A_GhostOff () + { + A_SetRenderStyle(1.0, STYLE_Normal); + bGhost = false; + } + + //---------------------------------------------------------------------------- + // + // PROC A_WizAtk1 + // + //---------------------------------------------------------------------------- + + void A_WizAtk1 () + { + A_FaceTarget (); + A_GhostOff(); + } + + //---------------------------------------------------------------------------- + // + // PROC A_WizAtk2 + // + //---------------------------------------------------------------------------- + + void A_WizAtk2 () + { + A_FaceTarget (); + A_SetRenderStyle(HR_SHADOW, STYLE_Translucent); + bGhost = true; + } + + //---------------------------------------------------------------------------- + // + // PROC A_WizAtk3 + // + //---------------------------------------------------------------------------- + + void A_WizAtk3 () + { + A_GhostOff(); + if (!target) return; + A_PlaySound (AttackSound, CHAN_WEAPON); + if (CheckMeleeRange()) + { + int damage = random[WizAtk3](1, 8) * 4; + int newdam = target.DamageMobj (self, self, damage, 'Melee'); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + return; + } + Actor mo = SpawnMissile (target, "WizardFX1"); + if (mo != null) + { + SpawnMissileAngle("WizardFX1", mo.Angle - 45. / 8, mo.Vel.Z); + SpawnMissileAngle("WizardFX1", mo.Angle + 45. / 8, mo.Vel.Z); + } + } + } // Projectile -------------------------------------------------------- From 696af7d7e540a85cc11fc667ddc0f6817b470271 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 00:33:40 +0100 Subject: [PATCH 227/255] - Moved all virtual function related template code to its own file because it depends on includes that cannot be done in dobject.h. --- src/actor.h | 4 - src/dobject.cpp | 1 + src/dobject.h | 120 ----------------------------- src/dthinker.cpp | 1 + src/dthinker.h | 4 - src/g_heretic/a_hereticmisc.cpp | 1 - src/p_mobj.cpp | 1 + src/p_user.cpp | 1 + src/virtual.h | 132 ++++++++++++++++++++++++++++++++ 9 files changed, 136 insertions(+), 129 deletions(-) create mode 100644 src/virtual.h diff --git a/src/actor.h b/src/actor.h index 6f5ba46a3..833cd2c0a 100644 --- a/src/actor.h +++ b/src/actor.h @@ -1419,10 +1419,6 @@ public: }; -VMEXPORT_NATIVES_START(AActor, DThinker) - VMEXPORT_NATIVES_FUNC(DropInventory) -VMEXPORT_NATIVES_END(AActor) - class FActorIterator { public: diff --git a/src/dobject.cpp b/src/dobject.cpp index 6fa7d5317..ad575bebc 100644 --- a/src/dobject.cpp +++ b/src/dobject.cpp @@ -48,6 +48,7 @@ #include "a_sharedglobal.h" #include "dsectoreffect.h" #include "serializer.h" +#include "virtual.h" //========================================================================== // diff --git a/src/dobject.h b/src/dobject.h index d5e11a04c..d858e577f 100644 --- a/src/dobject.h +++ b/src/dobject.h @@ -153,34 +153,6 @@ protected: \ #define HAS_FIELDS \ static void InitNativeFields(); -// Templates really are powerful -#define VMEXPORTED_NATIVES_START \ - template class ExportedNatives : public ExportedNatives {}; \ - template<> class ExportedNatives { \ - protected: ExportedNatives() {} \ - public: \ - static ExportedNatives *Get() { static ExportedNatives *Instance = nullptr; if (Instance == nullptr) Instance = new ExportedNatives; return Instance; } \ - ExportedNatives(const ExportedNatives&) = delete; \ - ExportedNatives(ExportedNatives&&) = delete; - -#define VMEXPORTED_NATIVES_FUNC(func) \ - template ret func(void *ptr, args ... arglist) { return ret(); } - -#define VMEXPORTED_NATIVES_END }; - -#define VMEXPORT_NATIVES_START(cls, parent) \ - template<> class ExportedNatives : public ExportedNatives { \ - protected: ExportedNatives() {} \ - public: \ - static ExportedNatives *Get() { static ExportedNatives *Instance = nullptr; if (Instance == nullptr) Instance = new ExportedNatives; return Instance; } \ - ExportedNatives(const ExportedNatives&) = delete; \ - ExportedNatives(ExportedNatives&&) = delete; - -#define VMEXPORT_NATIVES_FUNC(func) \ - template ret func(void *ptr, args ... arglist) { return static_cast(ptr)->object::func(arglist...); } - -#define VMEXPORT_NATIVES_END(cls) }; - #if defined(_MSC_VER) # pragma section(".creg$u",read) # define _DECLARE_TI(cls) __declspec(allocate(".creg$u")) ClassReg * const cls::RegistrationInfoPtr = &cls::RegistrationInfo; @@ -615,100 +587,8 @@ protected: } }; -//Initial list -VMEXPORTED_NATIVES_START - VMEXPORTED_NATIVES_FUNC(Destroy) - VMEXPORTED_NATIVES_FUNC(Tick) - VMEXPORTED_NATIVES_FUNC(DropInventory) -VMEXPORTED_NATIVES_END - class AInventory;// -template -class DVMObject : public T -{ -public: - static char *FormatClassName() - { - static char *name = nullptr; - if (name == nullptr) - { - name = new char[64]; - mysnprintf(name, 64, "DVMObject<%s>", Super::RegistrationInfo.Name); - atterm([]{ delete[] DVMObject::RegistrationInfo.Name; }); - } - return name; - } - - virtual PClass *StaticType() const - { - return RegistrationInfo.MyClass; - } - static ClassReg RegistrationInfo; - static ClassReg * const RegistrationInfoPtr; - typedef T Super; - -private: - typedef DVMObject ThisClass; - static void InPlaceConstructor(void *mem) - { - new((EInPlace *)mem) DVMObject; - } - -public: - void Destroy() - { - if (ObjectFlags & OF_SuperCall) - { - ObjectFlags &= OF_SuperCall; - ExportedNatives::Get()->template Destroy(this); - } - else - { - static int VIndex = -1; - if (VIndex < 0) - { - // Look up the virtual function index in the defining class because this may have gotten overloaded in subclasses with something different than a virtual override. - auto sym = dyn_cast(RUNTIME_CLASS(DObject)->Symbols.FindSymbol("Destroy", false)); - assert(sym != nullptr); - VIndex = sym->Variants[0].Implementation->VirtualIndex; - assert(VIndex >= 0); - } - // Without the type cast this picks the 'void *' assignment... - VMValue params[1] = { (DObject*)this }; - VMFrameStack stack; - stack.Call(GetClass()->Virtuals[VIndex], params, 1, nullptr, 0, nullptr); - } - } - void Tick() - { - ExportedNatives::Get()->template Tick(this); - } - AInventory *DropInventory(AInventory *item) - { - return ExportedNatives::Get()->template DropInventory(this, item); - } -}; - -template -ClassReg DVMObject::RegistrationInfo = -{ - nullptr, - DVMObject::FormatClassName(), - &DVMObject::Super::RegistrationInfo, - nullptr, - nullptr, - DVMObject::InPlaceConstructor, - nullptr, - sizeof(DVMObject), - DVMObject::MetaClassNum -}; -template _DECLARE_TI(DVMObject) - -VMEXPORT_NATIVES_START(DObject, void) - VMEXPORT_NATIVES_FUNC(Destroy) -VMEXPORT_NATIVES_END(DObject) - // When you write to a pointer to an Object, you must call this for // proper bookkeeping in case the Object holding this pointer has // already been processed by the GC. diff --git a/src/dthinker.cpp b/src/dthinker.cpp index 912b5642e..06cd5dbfa 100644 --- a/src/dthinker.cpp +++ b/src/dthinker.cpp @@ -40,6 +40,7 @@ #include "doomerrors.h" #include "serializer.h" #include "d_player.h" +#include "virtual.h" static cycle_t ThinkCycles; diff --git a/src/dthinker.h b/src/dthinker.h index e1020544c..95985c2fb 100644 --- a/src/dthinker.h +++ b/src/dthinker.h @@ -108,10 +108,6 @@ private: DThinker *NextThinker, *PrevThinker; }; -VMEXPORT_NATIVES_START(DThinker, DObject) - VMEXPORT_NATIVES_FUNC(Tick) -VMEXPORT_NATIVES_END(DThinker) - class FThinkerIterator { protected: diff --git a/src/g_heretic/a_hereticmisc.cpp b/src/g_heretic/a_hereticmisc.cpp index c6192b8e2..35b24eb93 100644 --- a/src/g_heretic/a_hereticmisc.cpp +++ b/src/g_heretic/a_hereticmisc.cpp @@ -26,7 +26,6 @@ #include "a_hereticartifacts.cpp" #include "a_hereticweaps.cpp" #include "a_ironlich.cpp" -#include "a_wizard.cpp" static FRandom pr_podpain ("PodPain"); diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 94b739135..65fd1ad34 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -72,6 +72,7 @@ #include "serializer.h" #include "r_utility.h" #include "thingdef.h" +#include "virtual.h" // MACROS ------------------------------------------------------------------ diff --git a/src/p_user.cpp b/src/p_user.cpp index f4e52ac2f..6b0b2cfe6 100644 --- a/src/p_user.cpp +++ b/src/p_user.cpp @@ -59,6 +59,7 @@ #include "p_blockmap.h" #include "a_morph.h" #include "p_spec.h" +#include "virtual.h" static FRandom pr_skullpop ("SkullPop"); diff --git a/src/virtual.h b/src/virtual.h new file mode 100644 index 000000000..377ec2ce8 --- /dev/null +++ b/src/virtual.h @@ -0,0 +1,132 @@ + + + +// Templates really are powerful +#define VMEXPORTED_NATIVES_START \ + template class ExportedNatives : public ExportedNatives {}; \ + template<> class ExportedNatives { \ + protected: ExportedNatives() {} \ + public: \ + static ExportedNatives *Get() { static ExportedNatives *Instance = nullptr; if (Instance == nullptr) Instance = new ExportedNatives; return Instance; } \ + ExportedNatives(const ExportedNatives&) = delete; \ + ExportedNatives(ExportedNatives&&) = delete; + +#define VMEXPORTED_NATIVES_FUNC(func) \ + template ret func(void *ptr, args ... arglist) { return ret(); } + +#define VMEXPORTED_NATIVES_END }; + +#define VMEXPORT_NATIVES_START(cls, parent) \ + template<> class ExportedNatives : public ExportedNatives { \ + protected: ExportedNatives() {} \ + public: \ + static ExportedNatives *Get() { static ExportedNatives *Instance = nullptr; if (Instance == nullptr) Instance = new ExportedNatives; return Instance; } \ + ExportedNatives(const ExportedNatives&) = delete; \ + ExportedNatives(ExportedNatives&&) = delete; + +#define VMEXPORT_NATIVES_FUNC(func) \ + template ret func(void *ptr, args ... arglist) { return static_cast(ptr)->object::func(arglist...); } + +#define VMEXPORT_NATIVES_END(cls) }; + + +//Initial list +VMEXPORTED_NATIVES_START + VMEXPORTED_NATIVES_FUNC(Destroy) + VMEXPORTED_NATIVES_FUNC(Tick) + VMEXPORTED_NATIVES_FUNC(DropInventory) +VMEXPORTED_NATIVES_END + +template +class DVMObject : public T +{ +public: + static char *FormatClassName() + { + static char *name = nullptr; + if (name == nullptr) + { + name = new char[64]; + mysnprintf(name, 64, "DVMObject<%s>", Super::RegistrationInfo.Name); + atterm([]{ delete[] DVMObject::RegistrationInfo.Name; }); + } + return name; + } + + virtual PClass *StaticType() const + { + return RegistrationInfo.MyClass; + } + static ClassReg RegistrationInfo; + static ClassReg * const RegistrationInfoPtr; + typedef T Super; + +private: + typedef DVMObject ThisClass; + static void InPlaceConstructor(void *mem) + { + new((EInPlace *)mem) DVMObject; + } + +public: + void Destroy() + { + if (ObjectFlags & OF_SuperCall) + { + ObjectFlags &= OF_SuperCall; + ExportedNatives::Get()->template Destroy(this); + } + else + { + static int VIndex = -1; + if (VIndex < 0) + { + // Look up the virtual function index in the defining class because this may have gotten overloaded in subclasses with something different than a virtual override. + auto sym = dyn_cast(RUNTIME_CLASS(DObject)->Symbols.FindSymbol("Destroy", false)); + assert(sym != nullptr); + VIndex = sym->Variants[0].Implementation->VirtualIndex; + assert(VIndex >= 0); + } + // Without the type cast this picks the 'void *' assignment... + VMValue params[1] = { (DObject*)this }; + VMFrameStack stack; + stack.Call(GetClass()->Virtuals[VIndex], params, 1, nullptr, 0, nullptr); + } + } + void Tick() + { + ExportedNatives::Get()->template Tick(this); + } + AInventory *DropInventory(AInventory *item) + { + return ExportedNatives::Get()->template DropInventory(this, item); + } +}; + +template +ClassReg DVMObject::RegistrationInfo = +{ + nullptr, + DVMObject::FormatClassName(), + &DVMObject::Super::RegistrationInfo, + nullptr, + nullptr, + DVMObject::InPlaceConstructor, + nullptr, + sizeof(DVMObject), + DVMObject::MetaClassNum +}; +template _DECLARE_TI(DVMObject) + +VMEXPORT_NATIVES_START(DObject, void) + VMEXPORT_NATIVES_FUNC(Destroy) +VMEXPORT_NATIVES_END(DObject) + +VMEXPORT_NATIVES_START(DThinker, DObject) + VMEXPORT_NATIVES_FUNC(Tick) +VMEXPORT_NATIVES_END(DThinker) + +VMEXPORT_NATIVES_START(AActor, DThinker) + VMEXPORT_NATIVES_FUNC(DropInventory) +VMEXPORT_NATIVES_END(AActor) + From 5bc89e7efcda661f5a2ebc5ffdc1b59ebb5f0eda Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 00:57:21 +0100 Subject: [PATCH 228/255] - added a VM handler for PostBeginPlay. - made a few changes to let the templates compile again on Linux. --- src/virtual.h | 16 ++++++++++++---- 1 file changed, 12 insertions(+), 4 deletions(-) diff --git a/src/virtual.h b/src/virtual.h index 377ec2ce8..188519f71 100644 --- a/src/virtual.h +++ b/src/virtual.h @@ -34,6 +34,7 @@ VMEXPORTED_NATIVES_START VMEXPORTED_NATIVES_FUNC(Destroy) VMEXPORTED_NATIVES_FUNC(Tick) + VMEXPORTED_NATIVES_FUNC(PostBeginPlay) VMEXPORTED_NATIVES_FUNC(DropInventory) VMEXPORTED_NATIVES_END @@ -71,9 +72,9 @@ private: public: void Destroy() { - if (ObjectFlags & OF_SuperCall) + if (this->ObjectFlags & OF_SuperCall) { - ObjectFlags &= OF_SuperCall; + this->ObjectFlags &= OF_SuperCall; ExportedNatives::Get()->template Destroy(this); } else @@ -90,13 +91,19 @@ public: // Without the type cast this picks the 'void *' assignment... VMValue params[1] = { (DObject*)this }; VMFrameStack stack; - stack.Call(GetClass()->Virtuals[VIndex], params, 1, nullptr, 0, nullptr); + stack.Call(this->GetClass()->Virtuals[VIndex], params, 1, nullptr, 0, nullptr); } } void Tick() { ExportedNatives::Get()->template Tick(this); } + + void PostBeginPlay() + { + ExportedNatives::Get()->template PostBeginPlay(this); + } + AInventory *DropInventory(AInventory *item) { return ExportedNatives::Get()->template DropInventory(this, item); @@ -124,7 +131,8 @@ VMEXPORT_NATIVES_END(DObject) VMEXPORT_NATIVES_START(DThinker, DObject) VMEXPORT_NATIVES_FUNC(Tick) -VMEXPORT_NATIVES_END(DThinker) + VMEXPORT_NATIVES_FUNC(PostBeginPlay) + VMEXPORT_NATIVES_END(DThinker) VMEXPORT_NATIVES_START(AActor, DThinker) VMEXPORT_NATIVES_FUNC(DropInventory) From 34fc6323a471c2f46bd47bffdab39ed27fe997c8 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 09:33:43 +0100 Subject: [PATCH 229/255] - scriptified Hexen's bats. - removed AMinotaurFriend::IsOkayToAttack. The condition it checks (i.e. friendliness with player) is already covered by the base version of this function so this is quite redundant. - removed a few 'virtual' qualifiers from functions that never get overridden. --- src/actor.h | 8 +-- src/g_hexen/a_bats.cpp | 98 ---------------------------- src/g_hexen/a_hexenmisc.cpp | 1 - src/g_raven/a_minotaur.cpp | 6 -- src/g_raven/ravenshared.h | 1 - src/p_mobj.cpp | 8 +++ src/virtual.h | 10 +-- wadsrc/static/zscript/actor.txt | 7 ++ wadsrc/static/zscript/hexen/bats.txt | 82 +++++++++++++++++++++-- 9 files changed, 98 insertions(+), 123 deletions(-) delete mode 100644 src/g_hexen/a_bats.cpp diff --git a/src/actor.h b/src/actor.h index 833cd2c0a..122839850 100644 --- a/src/actor.h +++ b/src/actor.h @@ -614,7 +614,7 @@ public: virtual void BeginPlay(); // Called immediately after the actor is created virtual void PostBeginPlay(); // Called immediately before the actor's first tick - virtual void LevelSpawned(); // Called after BeginPlay if this actor was spawned by the world + void LevelSpawned(); // Called after BeginPlay if this actor was spawned by the world virtual void HandleSpawnFlags(); // Translates SpawnFlags into in-game flags. virtual void MarkPrecacheSounds() const; // Marks sounds used by this actor for precaching. @@ -733,7 +733,7 @@ public: void ObtainInventory (AActor *other); // Die. Now. - virtual bool Massacre (); + bool Massacre (); // Transforms the actor into a finely-ground paste virtual bool Grind(bool items); @@ -958,7 +958,7 @@ public: { SetOrigin(Pos() + vel, true); } - virtual void SetOrigin(double x, double y, double z, bool moving); + void SetOrigin(double x, double y, double z, bool moving); void SetOrigin(const DVector3 & npos, bool moving) { SetOrigin(npos.X, npos.Y, npos.Z, moving); @@ -970,7 +970,7 @@ public: bool IsInsideVisibleAngles() const; // Calculate amount of missile damage - virtual int GetMissileDamage(int mask, int add); + int GetMissileDamage(int mask, int add); bool CanSeek(AActor *target) const; diff --git a/src/g_hexen/a_bats.cpp b/src/g_hexen/a_bats.cpp deleted file mode 100644 index 02fc6111e..000000000 --- a/src/g_hexen/a_bats.cpp +++ /dev/null @@ -1,98 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "m_random.h" -#include "p_local.h" -#include "s_sound.h" -#include "vm.h" -*/ - -static FRandom pr_batspawn ("BatSpawn"); -static FRandom pr_batmove ("BatMove"); - -//=========================================================================== -// Bat Spawner Variables -// special1 frequency counter -// special2 -// args[0] frequency of spawn (1=fastest, 10=slowest) -// args[1] spread angle (0..255) -// args[2] -// args[3] duration of bats (in octics) -// args[4] turn amount per move (in degrees) -// -// Bat Variables -// special2 lifetime counter -// args[4] turn amount per move (in degrees) -//=========================================================================== - -DEFINE_ACTION_FUNCTION(AActor, A_BatSpawnInit) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->special1 = 0; // Frequency count - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_BatSpawn) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - int delta; - DAngle angle; - - // Countdown until next spawn - if (self->special1-- > 0) return 0; - self->special1 = self->args[0]; // Reset frequency count - - delta = self->args[1]; - if (delta==0) delta=1; - - angle = self->Angles.Yaw + (((pr_batspawn() % delta) - (delta >> 1)) * (360 / 256.)); - - mo = P_SpawnMissileAngle (self, PClass::FindActor("Bat"), angle, 0); - if (mo) - { - mo->args[0] = pr_batspawn()&63; // floatbob index - mo->args[4] = self->args[4]; // turn degrees - mo->special2 = self->args[3]<<3; // Set lifetime - mo->target = self; - } - return 0; -} - - -DEFINE_ACTION_FUNCTION(AActor, A_BatMove) -{ - PARAM_SELF_PROLOGUE(AActor); - - DAngle newangle; - - if (self->special2 < 0) - { - self->SetState (self->FindState(NAME_Death)); - } - self->special2 -= 2; // Called every 2 tics - - if (pr_batmove()<128) - { - newangle = self->Angles.Yaw + self->args[4]; - } - else - { - newangle = self->Angles.Yaw - self->args[4]; - } - - // Adjust velocity vector to new direction - self->VelFromAngle(self->Speed, newangle); - - if (pr_batmove()<15) - { - S_Sound (self, CHAN_VOICE, "BatScream", 1, ATTN_IDLE); - } - - // Handle Z movement - self->SetZ(self->target->Z() + 2 * BobSin(self->args[0])); - self->args[0] = (self->args[0]+3)&63; - return 0; -} diff --git a/src/g_hexen/a_hexenmisc.cpp b/src/g_hexen/a_hexenmisc.cpp index 2c91f37b2..da17d37be 100644 --- a/src/g_hexen/a_hexenmisc.cpp +++ b/src/g_hexen/a_hexenmisc.cpp @@ -27,7 +27,6 @@ #include "vm.h" // Include all the Hexen stuff here to reduce compile time -#include "a_bats.cpp" #include "a_bishop.cpp" #include "a_blastradius.cpp" #include "a_boostarmor.cpp" diff --git a/src/g_raven/a_minotaur.cpp b/src/g_raven/a_minotaur.cpp index 36946ba87..dd4e4a8b8 100644 --- a/src/g_raven/a_minotaur.cpp +++ b/src/g_raven/a_minotaur.cpp @@ -117,12 +117,6 @@ void AMinotaurFriend::Die (AActor *source, AActor *inflictor, int dmgflags) } } -bool AMinotaurFriend::OkayToSwitchTarget (AActor *other) -{ - if (other == tracer) return false; // Do not target the master - return Super::OkayToSwitchTarget (other); -} - // Action functions for the minotaur ---------------------------------------- //---------------------------------------------------------------------------- diff --git a/src/g_raven/ravenshared.h b/src/g_raven/ravenshared.h index 81824a957..3c6019ae7 100644 --- a/src/g_raven/ravenshared.h +++ b/src/g_raven/ravenshared.h @@ -21,7 +21,6 @@ public: int StartTime; void Die (AActor *source, AActor *inflictor, int dmgflags); - bool OkayToSwitchTarget (AActor *other); void BeginPlay (); void Serialize(FSerializer &arc); diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 65fd1ad34..83e4d0282 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6885,6 +6885,14 @@ DEFINE_ACTION_FUNCTION(AActor, AddZ) return 0; } +DEFINE_ACTION_FUNCTION(AActor, SetZ) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_FLOAT(z); + self->SetZ(z); + return 0; +} + DEFINE_ACTION_FUNCTION(AActor, SetDamage) { PARAM_SELF_PROLOGUE(AActor); diff --git a/src/virtual.h b/src/virtual.h index 188519f71..d3a2bfa3a 100644 --- a/src/virtual.h +++ b/src/virtual.h @@ -35,7 +35,6 @@ VMEXPORTED_NATIVES_START VMEXPORTED_NATIVES_FUNC(Destroy) VMEXPORTED_NATIVES_FUNC(Tick) VMEXPORTED_NATIVES_FUNC(PostBeginPlay) - VMEXPORTED_NATIVES_FUNC(DropInventory) VMEXPORTED_NATIVES_END template @@ -103,11 +102,6 @@ public: { ExportedNatives::Get()->template PostBeginPlay(this); } - - AInventory *DropInventory(AInventory *item) - { - return ExportedNatives::Get()->template DropInventory(this, item); - } }; template @@ -134,7 +128,7 @@ VMEXPORT_NATIVES_START(DThinker, DObject) VMEXPORT_NATIVES_FUNC(PostBeginPlay) VMEXPORT_NATIVES_END(DThinker) +/* VMEXPORT_NATIVES_START(AActor, DThinker) - VMEXPORT_NATIVES_FUNC(DropInventory) VMEXPORT_NATIVES_END(AActor) - +*/ \ No newline at end of file diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index d9fd23a46..2fd6c4e03 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -53,6 +53,12 @@ class Actor : Thinker native { return GetPointer(ptr_select1) == GetPointer(ptr_select2); } + + static double BobSin(double fb) + { + return sin(fb * (180./32)) * 8; + } + native static readonly GetDefaultByType(class cls); native static float deltaangle(float ang1, float ang2); @@ -84,6 +90,7 @@ class Actor : Thinker native native bool CanSeek(Actor target); native double AngleTo(Actor target, bool absolute = false); native void AddZ(float zadd); + native void SetZ(float z); native vector3 Vec3Offset(float x, float y, float z, bool absolute = false); native vector3 Vec3Angle(float length, float angle, float z = 0, bool absolute = false); native vector3 Vec2OffsetZ(float x, float y, float atz, bool absolute = false); diff --git a/wadsrc/static/zscript/hexen/bats.txt b/wadsrc/static/zscript/hexen/bats.txt index 1e6ee459f..a530da176 100644 --- a/wadsrc/static/zscript/hexen/bats.txt +++ b/wadsrc/static/zscript/hexen/bats.txt @@ -9,9 +9,6 @@ class BatSpawner : SwitchableDecoration RenderStyle "None"; } - native void A_BatSpawnInit(); - native void A_BatSpawn(); - States { Spawn: @@ -24,6 +21,48 @@ class BatSpawner : SwitchableDecoration TNT1 A -1; Stop; } + + //=========================================================================== + // Bat Spawner Variables + // special1 frequency counter + // special2 + // args[0] frequency of spawn (1=fastest, 10=slowest) + // args[1] spread angle (0..255) + // args[2] + // args[3] duration of bats (in octics) + // args[4] turn amount per move (in degrees) + // + // Bat Variables + // special2 lifetime counter + // args[4] turn amount per move (in degrees) + //=========================================================================== + + void A_BatSpawnInit() + { + special1 = 0; // Frequency count + } + + void A_BatSpawn() + { + // Countdown until next spawn + if (special1-- > 0) return; + special1 = args[0]; // Reset frequency count + + int delta = args[1]; + if (delta == 0) delta = 1; + + double ang = Angle + (((random[BatSpawn]() % delta) - (delta >> 1)) * (360 / 256.)); + + Actor mo = SpawnMissileAngle ("Bat", ang, 0); + if (mo) + { + mo.args[0] = random[BatSpawn]() & 63; // floatbob index + mo.args[4] = args[4]; // turn degrees + mo.special2 = args[3] << 3; // Set lifetime + mo.target = self; + } + } + } // Bat ---------------------------------------------------------------------- @@ -39,8 +78,6 @@ class Bat : Actor +NOTELEPORT +CANPASS } - native void A_BatMove(); - States { Spawn: @@ -50,4 +87,39 @@ class Bat : Actor ABAT A 2; Stop; } + + void A_BatMove() + { + if (special2 < 0) + { + SetState ("Death"); + } + special2 -= 2; // Called every 2 tics + + double newangle; + if (random[BatMove]() < 128) + { + newangle = Angle + args[4]; + } + else + { + newangle = Angle - args[4]; + } + + // Adjust velocity vector to new direction + VelFromAngle(Speed, newangle); + + if (random[BatMove]() < 15) + { + A_PlaySound ("BatScream", CHAN_VOICE, 1, false, ATTN_IDLE); + } + + // Handle Z movement + SetZ(target.pos.Z + 2 * BobSin(args[0])); + args[0] = (args[0] + 3) & 63; + } } + + + + From 30a21710801b367e904cceb5b15e636173593d05 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 10:06:26 +0100 Subject: [PATCH 230/255] - let "" be synonymous with 'none' in ZScript. --- src/scripting/codegeneration/codegen.h | 6 +++++- src/scripting/vm/vmexec.h | 2 +- 2 files changed, 6 insertions(+), 2 deletions(-) diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index d5f812d52..2f82dba57 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -192,7 +192,11 @@ struct ExpVal FName GetName() const { - if (Type == TypeString) return FName(*(FString *)&pointer); + if (Type == TypeString) + { + if (((FString *)&pointer)->Len() == 0) return NAME_None; + return FName(*(FString *)&pointer); + } return Type == TypeName ? ENamedName(Int) : NAME_None; } }; diff --git a/src/scripting/vm/vmexec.h b/src/scripting/vm/vmexec.h index a6eda2a24..02e0db3de 100644 --- a/src/scripting/vm/vmexec.h +++ b/src/scripting/vm/vmexec.h @@ -1686,7 +1686,7 @@ static void DoCast(const VMRegisters ®, const VMFrame *f, int a, int b, int c case CAST_S2N: ASSERTD(a); ASSERTS(b); - reg.d[a] = FName(reg.s[b]); + reg.d[a] = reg.s[b].Len() == 0? FName(NAME_None) : FName(reg.s[b]); break; case CAST_N2S: From e009cbec9e80b93f91244b3d81d850f549018d8b Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 10:17:57 +0100 Subject: [PATCH 231/255] - fixed: PClass::StaticShutdown did not remove the class pointers for VM base classes from their class registration entries. --- src/dobjtype.cpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index b7e666fc1..a7d70ca39 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2731,9 +2731,11 @@ void PClass::StaticShutdown () FAutoSegIterator probe(CRegHead, CRegTail); - while (*++probe != NULL) + while (*++probe != nullptr) { - ((ClassReg *)*probe)->MyClass = NULL; + auto cr = ((ClassReg *)*probe); + cr->MyClass = nullptr; + if (cr->VMExport != nullptr) cr->VMExport->MyClass = nullptr; } } From 479b216c06bbcd176cbeed8d8476c723b71bda8c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 13:09:19 +0100 Subject: [PATCH 232/255] - fixed: ZScript did not properly fill in tentatively created classes from defaults processing. The proper setup for such classes was only done in CreateDerivedClass, but not in FindClassTentative itself. This extends CreateDerivedClass to allow it to create a class without fully initializing it. --- src/dobjtype.cpp | 28 ++++++++++++++++++--------- src/dobjtype.h | 11 +---------- src/scripting/zscript/zcc_compile.cpp | 25 +++++++++++++++--------- src/scripting/zscript/zcc_parser.cpp | 1 - 4 files changed, 36 insertions(+), 29 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index a7d70ca39..a6408c307 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -3120,12 +3120,19 @@ PClass *PClass::CreateDerivedClass(FName name, unsigned int size) { if (existclass->Size == TentativeClass) { - type = const_cast(existclass); - if (!IsDescendantOf(type->ParentClass)) + if (!IsDescendantOf(existclass->ParentClass)) { - I_Error("%s must inherit from %s but doesn't.", name.GetChars(), type->ParentClass->TypeName.GetChars()); + I_Error("%s must inherit from %s but doesn't.", name.GetChars(), existclass->ParentClass->TypeName.GetChars()); + } + + if (size == TentativeClass) + { + // see if we can reuse the existing class. This is only possible if the inheritance is identical. Otherwise it needs to be replaced. + if (this == existclass->ParentClass) + { + return existclass; + } } - DPrintf(DMSG_SPAMMY, "Defining placeholder class %s\n", name.GetChars()); notnew = true; } else @@ -3142,11 +3149,14 @@ PClass *PClass::CreateDerivedClass(FName name, unsigned int size) // Create a new type object of the same type as us. (We may be a derived class of PClass.) type = static_cast(GetClass()->CreateNew()); - type->Size = size; Derive(type, name); - type->InitializeDefaults(); - type->Virtuals = Virtuals; - DeriveData(type); + type->Size = size; + if (size != TentativeClass) + { + type->InitializeDefaults(); + type->Virtuals = Virtuals; + DeriveData(type); + } if (!notnew) { type->InsertIntoHash(); @@ -3197,7 +3207,7 @@ PField *PClass::AddField(FName name, PType *type, DWORD flags) // //========================================================================== -PClass *PClass::FindClassTentative(FName name, bool fatal) +PClass *PClass::FindClassTentative(FName name) { if (name == NAME_None) { diff --git a/src/dobjtype.h b/src/dobjtype.h index 7746dce29..be15193a4 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -145,15 +145,6 @@ struct PSymbolTable return MapType::Iterator(Symbols); } - // add a name to help debugging. -#ifdef _DEBUG - FString name; - void SetName(const char *nm) { name = nm; } -#else - void SetName(const char *) {} -#endif - - private: PSymbolTable *ParentSymbolTable; @@ -828,7 +819,7 @@ public: static PClassActor *FindActor(const FString &name) { return FindActor(FName(name, true)); } static PClassActor *FindActor(ENamedName name) { return FindActor(FName(name)); } static PClassActor *FindActor(FName name); - PClass *FindClassTentative(FName name, bool fatal = true); // not static! + PClass *FindClassTentative(FName name); static TArray AllClasses; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index f52e0e062..c42ef299a 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -89,10 +89,6 @@ void ZCCCompiler::ProcessClass(ZCC_Class *cnode, PSymbolTreeNode *treenode) PSymbolTreeNode *childnode; ZCC_Enum *enumType = nullptr; - FString name; - name << "nodes - " << FName(cnode->NodeName); - cls->TreeNodes.SetName(name); - // Need to check if the class actually has a body. if (node != nullptr) do { @@ -418,7 +414,6 @@ void ZCCCompiler::CreateStructTypes() s->Outer = s->OuterDef == nullptr? nullptr : s->OuterDef->Type; s->strct->Type = NewStruct(s->NodeName(), s->Outer); s->strct->Symbol = new PSymbolType(s->NodeName(), s->Type()); - s->Type()->Symbols.SetName(FName(s->NodeName())); GlobalSymbols.AddSymbol(s->strct->Symbol); for (auto e : s->Enums) @@ -486,6 +481,7 @@ void ZCCCompiler::CreateClassTypes() if (me == nullptr) { Error(c->cls, "Unknown native class %s", c->NodeName().GetChars()); + // Create a placeholder so that the compiler can continue looking for errors. me = parent->FindClassTentative(c->NodeName()); } else if (me->bRuntimeClass) @@ -523,12 +519,25 @@ void ZCCCompiler::CreateClassTypes() } // We will never get here if the name is a duplicate, so we can just do the assignment. - c->cls->Type = parent->FindClassTentative(c->NodeName()); + try + { + c->cls->Type = parent->CreateDerivedClass(c->NodeName(), TentativeClass); + if (c->Type() == nullptr) + { + Error(c->cls, "Class name %s already exists", c->NodeName().GetChars()); + } + } + catch (CRecoverableError &err) + { + Error(c->cls, "%s", err.GetMessage()); + // create a placeholder so that the compiler can continue looking for errors. + c->cls->Type = nullptr; + } } + if (c->Type() == nullptr) c->cls->Type = parent->FindClassTentative(c->NodeName()); c->Type()->bExported = true; // this class is accessible to script side type casts. (The reason for this flag is that types like PInt need to be skipped.) c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); GlobalSymbols.AddSymbol(c->cls->Symbol); - c->Type()->Symbols.SetName(c->NodeName()); Classes.Push(c); OrigClasses.Delete(i--); donesomething = true; @@ -553,7 +562,6 @@ void ZCCCompiler::CreateClassTypes() c->cls->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName()); c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); GlobalSymbols.AddSymbol(c->cls->Symbol); - c->Type()->Symbols.SetName(c->NodeName()); Classes.Push(c); OrigClasses.Delete(i--); donesomething = true; @@ -569,7 +577,6 @@ void ZCCCompiler::CreateClassTypes() Error(c->cls, "Class %s has circular inheritance", FName(c->NodeName()).GetChars()); c->cls->Type = RUNTIME_CLASS(DObject)->FindClassTentative(c->NodeName()); c->cls->Symbol = new PSymbolType(c->NodeName(), c->Type()); - c->Type()->Symbols.SetName(FName(c->NodeName()).GetChars()); GlobalSymbols.AddSymbol(c->cls->Symbol); Classes.Push(c); } diff --git a/src/scripting/zscript/zcc_parser.cpp b/src/scripting/zscript/zcc_parser.cpp index 098a38d82..de3d2c7e1 100644 --- a/src/scripting/zscript/zcc_parser.cpp +++ b/src/scripting/zscript/zcc_parser.cpp @@ -375,7 +375,6 @@ static void DoParse(int lumpnum) } PSymbolTable symtable; - symtable.SetName("Global_Node"); ZCCCompiler cc(state, NULL, symtable, GlobalSymbols, lumpnum); cc.Compile(); From 5adb2fe690c67050c39e1f60fd327764b9a4800d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 13:11:32 +0100 Subject: [PATCH 233/255] - fixed copy/paste error in A_UnsetReflectiveInvulnerable. --- wadsrc/static/zscript/actor.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 2fd6c4e03..a65062cfb 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -130,7 +130,7 @@ class Actor : Thinker native void A_SetReflective() { bReflective = true; } void A_UnSetReflective() { bReflective = false; } void A_SetReflectiveInvulnerable() { bInvulnerable = true; bReflective = true; } - void A_UnSetReflectiveInvulnerable() { bInvulnerable = true; bReflective = false; } + void A_UnSetReflectiveInvulnerable() { bInvulnerable = false; bReflective = false; } void A_SetShootable() { bShootable = true; bNonShootable = false; } void A_UnSetShootable() { bShootable = false; bNonShootable = true; } void A_NoGravity() { bNoGravity = true; } From fe74a144315be2a97412490d86c22e3e946b9459 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 14:48:10 +0100 Subject: [PATCH 234/255] - fixed: A_GiveInventory should not try to give stuff to an owned inventory item, because it doesn't own its Inventory pointer - it is used for the linked list of the owner's inventory. --- src/CMakeLists.txt | 1 - src/p_actionfunctions.cpp | 5 +++++ 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index b2f23afb1..66371220b 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -857,7 +857,6 @@ set( NOT_COMPILED_SOURCE_FILES g_heretic/a_hereticartifacts.cpp g_heretic/a_hereticweaps.cpp g_heretic/a_ironlich.cpp - g_hexen/a_bats.cpp g_hexen/a_bishop.cpp g_hexen/a_blastradius.cpp g_hexen/a_boostarmor.cpp diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 1cfc44ae2..a99ba9ab6 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -2491,6 +2491,11 @@ static bool DoGiveInventory(AActor *receiver, bool orresult, VM_ARGS) { // If there's nothing to receive it, it's obviously a fail, right? return false; } + // Owned inventory items cannot own anything because their Inventory pointer is repurposed for the owner's linked list. + if (receiver->IsKindOf(RUNTIME_CLASS(AInventory)) && static_cast(receiver)->Owner != nullptr) + { + return false; + } if (amount <= 0) { From a603af805c8aebfa637aa2847e7e0e3aaa6b8bc6 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 15:21:59 +0100 Subject: [PATCH 235/255] - fixed identifier resolution in FxIdentifier for action functions with a different invoker than self. - fixed creation of direct function invocations on a state line. In order to receive the implicit arguments this needs to be wrapped into a compound statement so that the local variable getter works. --- src/dobjtype.cpp | 4 ++++ src/scripting/codegeneration/codegen.cpp | 30 ++++++++++++++++-------- src/scripting/zscript/zcc_compile.cpp | 4 +++- 3 files changed, 27 insertions(+), 11 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index a6408c307..c2b1008df 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2495,6 +2495,10 @@ unsigned PFunction::AddVariant(PPrototype *proto, TArray &argflags, TArra variant.SelfClass = dyn_cast(selftypeptr->PointedType); assert(variant.SelfClass != nullptr); } + else + { + variant.SelfClass = nullptr; + } return Variants.Push(variant); } diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 2759e41ba..dac88aa76 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5096,14 +5096,11 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) // Ugh, the horror. Constants need to be taken from the owning class, but members from the self class to catch invalid accesses here... // see if the current class (if valid) defines something with this name. PSymbolTable *symtbl; - if ((sym = ctx.FindInClass(Identifier, symtbl)) != nullptr) + + // first check fields in self + if ((sym = ctx.FindInSelfClass(Identifier, symtbl)) != nullptr) { - if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) - { - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as class constant\n", Identifier.GetChars()); - newex = FxConstant::MakeConstant(sym, ScriptPosition); - } - else if (sym->IsKindOf(RUNTIME_CLASS(PField))) + if (sym->IsKindOf(RUNTIME_CLASS(PField))) { if (!ctx.Function) { @@ -5161,6 +5158,18 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as member variable, index %d\n", Identifier.GetChars(), vsym->Offset); newex = new FxClassMember((new FxSelf(ScriptPosition))->Resolve(ctx), vsym, ScriptPosition); } + } + + // now constants in the owning class. + if (newex == nullptr && (sym = ctx.FindInClass(Identifier, symtbl)) != nullptr) + { + if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) + { + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as class constant\n", Identifier.GetChars()); + newex = FxConstant::MakeConstant(sym, ScriptPosition); + delete this; + return newex->Resolve(ctx); + } else { if (sym->IsKindOf(RUNTIME_CLASS(PFunction))) @@ -5177,7 +5186,7 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } // now check the global identifiers. - else if ((sym = ctx.FindGlobal(Identifier)) != nullptr) + if (newex == nullptr && (sym = ctx.FindGlobal(Identifier)) != nullptr) { if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) { @@ -5197,12 +5206,13 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } // and line specials - else if ((num = P_FindLineSpecial(Identifier, nullptr, nullptr))) + if (newex == nullptr && (num = P_FindLineSpecial(Identifier, nullptr, nullptr))) { ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as line special %d\n", Identifier.GetChars(), num); newex = new FxConstant(num, ScriptPosition); } - else + + if (newex == nullptr) { ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); delete this; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index c42ef299a..c5ac21783 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2577,7 +2577,9 @@ FxExpression *ZCCCompiler::ConvertAST(PClass *cls, ZCC_TreeNode *ast) // there are two possibilities here: either a single function call or a compound statement. For a compound statement we also need to check if the last thing added was a return. if (ast->NodeType == AST_ExprFuncCall) { - return new FxReturnStatement(ConvertNode(ast), *ast); + auto cp = new FxCompoundStatement(*ast); + cp->Add(new FxReturnStatement(ConvertNode(ast), *ast)); + return cp; } else { From 91938cd35b69ef72f975a852d973567a347ade6e Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 15:26:29 +0100 Subject: [PATCH 236/255] - fixed: The pointer defaulr for GetDistance was incorrect. --- wadsrc/static/zscript/actor.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index a65062cfb..8a5b56e0c 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -107,7 +107,7 @@ class Actor : Thinker native // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); native int CountInv(class itemtype, int ptr_select = AAPTR_DEFAULT); - native float GetDistance(bool checkz, int ptr = AAPTR_DEFAULT); + native float GetDistance(bool checkz, int ptr = AAPTR_TARGET); native float GetAngle(int flags, int ptr = AAPTR_DEFAULT); native float GetZAt(float px = 0, float py = 0, float angle = 0, int flags = 0, int pick_pointer = AAPTR_DEFAULT); native int GetSpawnHealth(); From 8f8017836ffb6839fb767991ac06ea92ca1b85e4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 16:32:26 +0100 Subject: [PATCH 237/255] - scriptified Hexen's Bishop. --- src/CMakeLists.txt | 1 - src/g_hexen/a_bishop.cpp | 230 ------------------------- src/g_hexen/a_hexenmisc.cpp | 1 - src/p_mobj.cpp | 24 +++ wadsrc/static/zscript/actor.txt | 2 +- wadsrc/static/zscript/hexen/bishop.txt | 180 ++++++++++++++++++- 6 files changed, 196 insertions(+), 242 deletions(-) delete mode 100644 src/g_hexen/a_bishop.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index 66371220b..d0f73bc9b 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -857,7 +857,6 @@ set( NOT_COMPILED_SOURCE_FILES g_heretic/a_hereticartifacts.cpp g_heretic/a_hereticweaps.cpp g_heretic/a_ironlich.cpp - g_hexen/a_bishop.cpp g_hexen/a_blastradius.cpp g_hexen/a_boostarmor.cpp g_hexen/a_centaur.cpp diff --git a/src/g_hexen/a_bishop.cpp b/src/g_hexen/a_bishop.cpp deleted file mode 100644 index bd9f24061..000000000 --- a/src/g_hexen/a_bishop.cpp +++ /dev/null @@ -1,230 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "p_local.h" -#include "s_sound.h" -#include "a_action.h" -#include "m_random.h" -#include "a_hexenglobal.h" -#include "vm.h" -*/ - -static FRandom pr_boom ("BishopBoom"); -static FRandom pr_atk ("BishopAttack"); -static FRandom pr_decide ("BishopDecide"); -static FRandom pr_doblur ("BishopDoBlur"); -static FRandom pr_sblur ("BishopSpawnBlur"); -static FRandom pr_pain ("BishopPainBlur"); - -//============================================================================ -// -// A_BishopAttack -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (!self->target) - { - return 0; - } - S_Sound (self, CHAN_BODY, self->AttackSound, 1, ATTN_NORM); - if (self->CheckMeleeRange()) - { - int damage = pr_atk.HitDice (4); - int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee); - P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self); - return 0; - } - self->special1 = (pr_atk() & 3) + 5; - return 0; -} - -//============================================================================ -// -// A_BishopAttack2 -// -// Spawns one of a string of bishop missiles -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopAttack2) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - if (!self->target || !self->special1) - { - self->special1 = 0; - self->SetState (self->SeeState); - return 0; - } - mo = P_SpawnMissile (self, self->target, PClass::FindActor("BishopFX")); - if (mo != NULL) - { - mo->tracer = self->target; - } - self->special1--; - return 0; -} - -//============================================================================ -// -// A_BishopMissileWeave -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopMissileWeave) -{ - PARAM_SELF_PROLOGUE(AActor); - - A_Weave(self, 2, 2, 2., 1.); - return 0; -} - -//============================================================================ -// -// A_BishopDecide -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopDecide) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (pr_decide() < 220) - { - return 0; - } - else - { - self->SetState (self->FindState ("Blur")); - } - return 0; -} - -//============================================================================ -// -// A_BishopDoBlur -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopDoBlur) -{ - PARAM_SELF_PROLOGUE(AActor); - - self->special1 = (pr_doblur() & 3) + 3; // Random number of blurs - if (pr_doblur() < 120) - { - self->Thrust(self->Angles.Yaw + 90, 11); - } - else if (pr_doblur() > 125) - { - self->Thrust(self->Angles.Yaw - 90, 11); - } - else - { // Thrust forward - self->Thrust(11); - } - S_Sound (self, CHAN_BODY, "BishopBlur", 1, ATTN_NORM); - return 0; -} - -//============================================================================ -// -// A_BishopSpawnBlur -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopSpawnBlur) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - if (!--self->special1) - { - self->Vel.X = self->Vel.Y = 0; - if (pr_sblur() > 96) - { - self->SetState (self->SeeState); - } - else - { - self->SetState (self->MissileState); - } - } - mo = Spawn ("BishopBlur", self->Pos(), ALLOW_REPLACE); - if (mo) - { - mo->Angles.Yaw = self->Angles.Yaw; - } - return 0; -} - -//============================================================================ -// -// A_BishopChase -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopChase) -{ - PARAM_SELF_PROLOGUE(AActor); - - double newz = self->Z() - BobSin(self->special2) / 2.; - self->special2 = (self->special2 + 4) & 63; - newz += BobSin(self->special2) / 2.; - self->SetZ(newz); - return 0; -} - -//============================================================================ -// -// A_BishopPuff -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopPuff) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - mo = Spawn ("BishopPuff", self->PosPlusZ(40.), ALLOW_REPLACE); - if (mo) - { - mo->Vel.Z = -.5; - } - return 0; -} - -//============================================================================ -// -// A_BishopPainBlur -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_BishopPainBlur) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - if (pr_pain() < 64) - { - self->SetState (self->FindState ("Blur")); - return 0; - } - double xo = pr_pain.Random2() / 16.; - double yo = pr_pain.Random2() / 16.; - double zo = pr_pain.Random2() / 32.; - mo = Spawn ("BishopPainBlur", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE); - if (mo) - { - mo->Angles.Yaw = self->Angles.Yaw; - } - return 0; -} diff --git a/src/g_hexen/a_hexenmisc.cpp b/src/g_hexen/a_hexenmisc.cpp index da17d37be..1bb722d06 100644 --- a/src/g_hexen/a_hexenmisc.cpp +++ b/src/g_hexen/a_hexenmisc.cpp @@ -27,7 +27,6 @@ #include "vm.h" // Include all the Hexen stuff here to reduce compile time -#include "a_bishop.cpp" #include "a_blastradius.cpp" #include "a_boostarmor.cpp" #include "a_centaur.cpp" diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 83e4d0282..bd05941b3 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -6939,6 +6939,30 @@ DEFINE_ACTION_FUNCTION(AActor, VelFromAngle) return 0; } +// This combines all 3 variations of the internal function +DEFINE_ACTION_FUNCTION(AActor, Thrust) +{ + PARAM_SELF_PROLOGUE(AActor); + if (numparam == 1) + { + self->Thrust(); + } + else + { + PARAM_FLOAT(speed); + if (numparam == 2) + { + self->Thrust(speed); + } + else + { + PARAM_ANGLE(angle); + self->Thrust(angle, speed); + } + } + return 0; +} + DEFINE_ACTION_FUNCTION(AActor, AngleTo) { PARAM_SELF_PROLOGUE(AActor); diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 8a5b56e0c..97b961eea 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -95,6 +95,7 @@ class Actor : Thinker native native vector3 Vec3Angle(float length, float angle, float z = 0, bool absolute = false); native vector3 Vec2OffsetZ(float x, float y, float atz, bool absolute = false); native void VelFromAngle(float speed = 0, float angle = 0); + native void Thrust(float speed = 0, float angle = 0); native bool isFriend(Actor other); native void AdjustFloorClip(); native DropItem GetDropItems(); @@ -292,7 +293,6 @@ class Actor : Thinker native native void A_GenericFreezeDeath(); native void A_IceGuyDie(); native void A_CentaurDefend(); - native void A_BishopMissileWeave(); native void A_CStaffMissileSlither(); native void A_PlayerScream(); native void A_SkullPop(class skulltype = "BloodySkull"); diff --git a/wadsrc/static/zscript/hexen/bishop.txt b/wadsrc/static/zscript/hexen/bishop.txt index d116ee932..d846a6402 100644 --- a/wadsrc/static/zscript/hexen/bishop.txt +++ b/wadsrc/static/zscript/hexen/bishop.txt @@ -3,6 +3,9 @@ class Bishop : Actor { + int missilecount; + int bobstate; + Default { Health 130; @@ -23,14 +26,6 @@ class Bishop : Actor Obituary"$OB_BISHOP"; } - native void A_BishopChase(); - native void A_BishopDecide(); - native void A_BishopDoBlur(); - native void A_BishopSpawnBlur(); - native void A_BishopPainBlur(); - native void A_BishopAttack(); - native void A_BishopAttack2(); - States { Spawn: @@ -67,7 +62,7 @@ class Bishop : Actor BISH J 5 BRIGHT A_Explode(random[BishopBoom](25,40)); BISH K 5 Bright; BISH LM 4 Bright; - BISH N 4 A_SpawnItemEx("BishopPuff", 0,0,40, 0,0,0.5); + BISH N 4 A_SpawnItemEx("BishopPuff", 0,0,40, 0,0,-0.5); BISH O 4 A_QueueCorpse; BISH P -1; Stop; @@ -76,6 +71,172 @@ class Bishop : Actor BISH X 1 A_FreezeDeathChunks; Wait; } + + + + //============================================================================ + // + // A_BishopAttack + // + //============================================================================ + + void A_BishopAttack() + { + if (!target) + { + return; + } + A_PlaySound (AttackSound, CHAN_BODY); + if (CheckMeleeRange()) + { + int damage = random[BishopAttack](1, 8) * 4; + int newdam = target.DamageMobj (self, self, damage, 'Melee'); + target.TraceBleed (newdam > 0 ? newdam : damage, self); + return; + } + missilecount = (random[BishopAttack]() & 3) + 5; + } + + //============================================================================ + // + // A_BishopAttack2 + // + // Spawns one of a string of bishop missiles + //============================================================================ + + void A_BishopAttack2() + { + if (!target || !missilecount) + { + missilecount = 0; + SetState (SeeState); + return; + } + Actor mo = SpawnMissile (target, "BishopFX"); + if (mo != null) + { + mo.tracer = target; + } + missilecount--; + return; + } + + //============================================================================ + // + // A_BishopDecide + // + //============================================================================ + + void A_BishopDecide() + { + if (random[BishopDecide]() >= 220) + { + SetState ("Blur"); + } + } + + //============================================================================ + // + // A_BishopDoBlur + // + //============================================================================ + + void A_BishopDoBlur() + { + missilecount = (random[BishopDoBlur]() & 3) + 3; // Random number of blurs + if (random[BishopDoBlur]() < 120) + { + Thrust(11, Angle + 90); + } + else if (random[BishopDoBlur]() > 125) + { + Thrust(11, Angle - 90); + } + else + { // Thrust forward + Thrust(11); + } + A_PlaySound ("BishopBlur", CHAN_BODY); + } + + //============================================================================ + // + // A_BishopSpawnBlur + // + //============================================================================ + + void A_BishopSpawnBlur() + { + if (!--missilecount) + { + Vel.XY = (0,0);// = Vel.Y = 0; + if (random[BishopSpawnBlur]() > 96) + { + SetState (SeeState); + } + else + { + SetState (MissileState); + } + } + Actor mo = Spawn ("BishopBlur", Pos, ALLOW_REPLACE); + if (mo) + { + mo.angle = angle; + } + } + + //============================================================================ + // + // A_BishopChase + // + //============================================================================ + + void A_BishopChase() + { + double newz = pos.z - BobSin(bobstate) / 2.; + bobstate = (bobstate + 4) & 63; + newz += BobSin(bobstate) / 2.; + SetZ(newz); + } + + //============================================================================ + // + // A_BishopPainBlur + // + //============================================================================ + + void A_BishopPainBlur() + { + if (random[BishopPainBlur]() < 64) + { + SetState ("Blur"); + return; + } + double xo = random2[BishopPainBlur]() / 16.; + double yo = random2[BishopPainBlue]() / 16.; + double zo = random2[BishopPainBlue]() / 32.; + Actor mo = Spawn ("BishopPainBlur", Vec3Offset(xo, yo, zo), ALLOW_REPLACE); + if (mo) + { + mo.angle = angle; + } + } + +} + +extend class Actor +{ + //============================================================================ + // + // A_BishopMissileWeave (this function must be in Actor) + // + //============================================================================ + + void A_BishopMissileWeave() + { + A_Weave(2, 2, 2., 1.); + } } // Bishop puff -------------------------------------------------------------- @@ -164,3 +325,4 @@ class BishopBlur : Actor Stop; } } + From 213b3f1fe486b63e79ef5a7dd7c3855d2592974d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 17:21:11 +0100 Subject: [PATCH 238/255] - scriptified Hexen's Centaur. --- src/CMakeLists.txt | 1 - src/g_hexen/a_centaur.cpp | 30 ------------------------- src/g_hexen/a_hexenmisc.cpp | 1 - wadsrc/static/zscript/actor.txt | 1 - wadsrc/static/zscript/hexen/centaur.txt | 23 +++++++++++++++++-- wadsrc/static/zscript/hexen/demons.txt | 26 ++++++++++++--------- 6 files changed, 37 insertions(+), 45 deletions(-) delete mode 100644 src/g_hexen/a_centaur.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index d0f73bc9b..ffd9f339a 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -859,7 +859,6 @@ set( NOT_COMPILED_SOURCE_FILES g_heretic/a_ironlich.cpp g_hexen/a_blastradius.cpp g_hexen/a_boostarmor.cpp - g_hexen/a_centaur.cpp g_hexen/a_clericflame.cpp g_hexen/a_clericholy.cpp g_hexen/a_clericmace.cpp diff --git a/src/g_hexen/a_centaur.cpp b/src/g_hexen/a_centaur.cpp deleted file mode 100644 index 9bf5e6046..000000000 --- a/src/g_hexen/a_centaur.cpp +++ /dev/null @@ -1,30 +0,0 @@ -/* -#include "actor.h" -#include "p_enemy.h" -#include "a_action.h" -#include "m_random.h" -#include "vm.h" -*/ - -static FRandom pr_centaurdefend ("CentaurDefend"); - -//============================================================================ -// -// A_CentaurDefend -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_CentaurDefend) -{ - PARAM_SELF_PROLOGUE(AActor); - - A_FaceTarget (self); - if (self->CheckMeleeRange() && pr_centaurdefend() < 32) - { - // This should unset REFLECTIVE as well - // (unless you want the Centaur to reflect projectiles forever!) - self->flags2&=~(MF2_REFLECTIVE|MF2_INVULNERABLE); - self->SetState (self->MeleeState); - } - return 0; -} diff --git a/src/g_hexen/a_hexenmisc.cpp b/src/g_hexen/a_hexenmisc.cpp index 1bb722d06..3676bf21b 100644 --- a/src/g_hexen/a_hexenmisc.cpp +++ b/src/g_hexen/a_hexenmisc.cpp @@ -29,7 +29,6 @@ // Include all the Hexen stuff here to reduce compile time #include "a_blastradius.cpp" #include "a_boostarmor.cpp" -#include "a_centaur.cpp" #include "a_clericflame.cpp" #include "a_clericholy.cpp" #include "a_clericmace.cpp" diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 97b961eea..c7a009038 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -292,7 +292,6 @@ class Actor : Thinker native native void A_FreezeDeathChunks(); native void A_GenericFreezeDeath(); native void A_IceGuyDie(); - native void A_CentaurDefend(); native void A_CStaffMissileSlither(); native void A_PlayerScream(); native void A_SkullPop(class skulltype = "BloodySkull"); diff --git a/wadsrc/static/zscript/hexen/centaur.txt b/wadsrc/static/zscript/hexen/centaur.txt index 37a8d6b11..f8c8e2c3d 100644 --- a/wadsrc/static/zscript/hexen/centaur.txt +++ b/wadsrc/static/zscript/hexen/centaur.txt @@ -54,14 +54,17 @@ class Centaur : Actor XDeath: CTXD A 4; CTXD B 4 A_NoBlocking; - CTXD C 0 A_SpawnItemEx("CentaurSword", 0, 0, 45, + CTXD C 4 + { + A_SpawnItemEx("CentaurSword", 0, 0, 45, 1 + random[CentaurDrop](-128,127)*0.03125, 1 + random[CentaurDrop](-128,127)*0.03125, 8 + random[CentaurDrop](0,255)*0.015625, 270); - CTXD C 4 A_SpawnItemEx("CentaurShield", 0, 0, 45, + A_SpawnItemEx("CentaurShield", 0, 0, 45, 1 + random[CentaurDrop](-128,127)*0.03125, 1 + random[CentaurDrop](-128,127)*0.03125, 8 + random[CentaurDrop](0,255)*0.015625, 90); + } CTXD D 3 A_Scream; CTXD E 4 A_QueueCorpse; CTXD F 3; @@ -74,6 +77,22 @@ class Centaur : Actor CENT U 5 A_FreezeDeath; CENT U 1 A_FreezeDeathChunks; Wait; + } +} + +extend class Actor +{ + void A_CentaurDefend() + { + A_FaceTarget (); + if (CheckMeleeRange() && random[CentaurDefend]() < 32) + { + // This should unset REFLECTIVE as well + // (unless you want the Centaur to reflect projectiles forever!) + bReflective = false; + bInvulnerable = false; + SetState(MeleeState); + } } } diff --git a/wadsrc/static/zscript/hexen/demons.txt b/wadsrc/static/zscript/hexen/demons.txt index 56b4f3bda..8aa65629d 100644 --- a/wadsrc/static/zscript/hexen/demons.txt +++ b/wadsrc/static/zscript/hexen/demons.txt @@ -56,11 +56,14 @@ class Demon1 : Actor Stop; XDeath: DEMN H 6; - DEMN I 0 A_SpawnItemEx("Demon1Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags); - DEMN I 0 A_SpawnItemEx("Demon1Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); - DEMN I 0 A_SpawnItemEx("Demon1Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); - DEMN I 0 A_SpawnItemEx("Demon1Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); - DEMN I 6 A_SpawnItemEx("Demon1Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEMN I 6 + { + A_SpawnItemEx("Demon1Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags); + A_SpawnItemEx("Demon1Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + A_SpawnItemEx("Demon1Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + A_SpawnItemEx("Demon1Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + A_SpawnItemEx("Demon1Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + } Goto Death+2; Ice: DEMN Q 5 A_FreezeDeath; @@ -261,11 +264,14 @@ class Demon2 : Demon1 Stop; XDeath: DEM2 H 6; - DEM2 I 0 A_SpawnItemEx("Demon2Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags); - DEM2 I 0 A_SpawnItemEx("Demon2Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); - DEM2 I 0 A_SpawnItemEx("Demon2Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); - DEM2 I 0 A_SpawnItemEx("Demon2Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); - DEM2 I 6 A_SpawnItemEx("Demon2Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + DEM2 I 6 + { + A_SpawnItemEx("Demon2Chunk1", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle+90), frandom[DemonChunks](1,4.984375)*sin(Angle+90), 8, 90, ChunkFlags); + A_SpawnItemEx("Demon2Chunk2", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + A_SpawnItemEx("Demon2Chunk3", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + A_SpawnItemEx("Demon2Chunk4", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + A_SpawnItemEx("Demon2Chunk5", 0,0,45, frandom[DemonChunks](1,4.984375)*cos(Angle-90), frandom[DemonChunks](1,4.984375)*sin(Angle-90), 8, 270, ChunkFlags); + } Goto Death+2; } } From 49ef5415138938554f4cfdedc13a06bcaf977fbf Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sat, 12 Nov 2016 19:16:47 +0100 Subject: [PATCH 239/255] - scriptified Hexen's Firedemon. --- src/CMakeLists.txt | 1 - src/g_hexen/a_firedemon.cpp | 248 ---------------------- src/g_hexen/a_hexenmisc.cpp | 1 - src/g_shared/a_action.cpp | 7 + src/p_enemy.cpp | 18 +- src/p_mobj.cpp | 14 ++ wadsrc/static/zscript/actor.txt | 6 + wadsrc/static/zscript/hexen/firedemon.txt | 227 +++++++++++++++++++- 8 files changed, 264 insertions(+), 258 deletions(-) delete mode 100644 src/g_hexen/a_firedemon.cpp diff --git a/src/CMakeLists.txt b/src/CMakeLists.txt index ffd9f339a..3c165c345 100644 --- a/src/CMakeLists.txt +++ b/src/CMakeLists.txt @@ -868,7 +868,6 @@ set( NOT_COMPILED_SOURCE_FILES g_hexen/a_fighterhammer.cpp g_hexen/a_fighterplayer.cpp g_hexen/a_fighterquietus.cpp - g_hexen/a_firedemon.cpp g_hexen/a_flechette.cpp g_hexen/a_flies.cpp g_hexen/a_fog.cpp diff --git a/src/g_hexen/a_firedemon.cpp b/src/g_hexen/a_firedemon.cpp deleted file mode 100644 index cc9beaaeb..000000000 --- a/src/g_hexen/a_firedemon.cpp +++ /dev/null @@ -1,248 +0,0 @@ -/* -#include "actor.h" -#include "info.h" -#include "p_local.h" -#include "s_sound.h" -#include "p_enemy.h" -#include "a_action.h" -#include "m_random.h" -#include "vm.h" -*/ - -#define FIREDEMON_ATTACK_RANGE (64*8.) - -static FRandom pr_firedemonrock ("FireDemonRock"); -static FRandom pr_smbounce ("SMBounce"); -static FRandom pr_firedemonchase ("FiredChase"); -static FRandom pr_firedemonsplotch ("FiredSplotch"); - -//============================================================================ -// Fire Demon AI -// -// special1 index into floatbob -// special2 whether strafing or not -//============================================================================ - -//============================================================================ -// -// A_FiredSpawnRock -// -//============================================================================ - -void A_FiredSpawnRock (AActor *actor) -{ - AActor *mo; - PClassActor *rtype; - - switch (pr_firedemonrock() % 5) - { - case 0: - rtype = PClass::FindActor("FireDemonRock1"); - break; - case 1: - rtype = PClass::FindActor("FireDemonRock2"); - break; - case 2: - rtype = PClass::FindActor("FireDemonRock3"); - break; - case 3: - rtype = PClass::FindActor("FireDemonRock4"); - break; - case 4: - default: - rtype = PClass::FindActor("FireDemonRock5"); - break; - } - - double xo = (pr_firedemonrock() - 128) / 16.; - double yo = (pr_firedemonrock() - 128) / 16.; - double zo = pr_firedemonrock() / 32.; - mo = Spawn (rtype, actor->Vec3Offset(xo, yo, zo), ALLOW_REPLACE); - if (mo) - { - mo->target = actor; - mo->Vel.X = (pr_firedemonrock() - 128) / 64.; - mo->Vel.Y = (pr_firedemonrock() - 128) / 64.; - mo->Vel.Z = (pr_firedemonrock() / 64.); - mo->special1 = 2; // Number bounces - } - - // Initialize fire demon - actor->special2 = 0; - actor->flags &= ~MF_JUSTATTACKED; -} - -//============================================================================ -// -// A_FiredRocks -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_FiredRocks) -{ - PARAM_SELF_PROLOGUE(AActor); - - A_FiredSpawnRock (self); - A_FiredSpawnRock (self); - A_FiredSpawnRock (self); - A_FiredSpawnRock (self); - A_FiredSpawnRock (self); - return 0; -} - -//============================================================================ -// -// A_SmBounce -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_SmBounce) -{ - PARAM_SELF_PROLOGUE(AActor); - - // give some more velocity (x,y,&z) - self->SetZ(self->floorz + 1); - self->Vel.Z = 2. + pr_smbounce() / 64.; - self->Vel.X = pr_smbounce() % 3; - self->Vel.Y = pr_smbounce() % 3; - return 0; -} - -//============================================================================ -// -// A_FiredAttack -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_FiredAttack) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (self->target == NULL) - return 0; - AActor *mo = P_SpawnMissile (self, self->target, PClass::FindActor("FireDemonMissile")); - if (mo) S_Sound (self, CHAN_BODY, "FireDemonAttack", 1, ATTN_NORM); - return 0; -} - -//============================================================================ -// -// A_FiredChase -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_FiredChase) -{ - PARAM_SELF_PROLOGUE(AActor); - - int weaveindex = self->special1; - AActor *target = self->target; - DAngle ang; - double dist; - - if (self->reactiontime) self->reactiontime--; - if (self->threshold) self->threshold--; - - // Float up and down - self->AddZ(BobSin(weaveindex)); - self->special1 = (weaveindex + 2) & 63; - - // Ensure it stays above certain height - if (self->Z() < self->floorz + 64) - { - self->AddZ(2); - } - - if(!self->target || !(self->target->flags&MF_SHOOTABLE)) - { // Invalid target - P_LookForPlayers (self,true, NULL); - return 0; - } - - // Strafe - if (self->special2 > 0) - { - self->special2--; - } - else - { - self->special2 = 0; - self->Vel.X = self->Vel.Y = 0; - dist = self->Distance2D(target); - if (dist < FIREDEMON_ATTACK_RANGE) - { - if (pr_firedemonchase() < 30) - { - ang = self->AngleTo(target); - if (pr_firedemonchase() < 128) - ang += 90; - else - ang -= 90; - self->Thrust(ang, 8); - self->special2 = 3; // strafe time - } - } - } - - FaceMovementDirection (self); - - // Normal movement - if (!self->special2) - { - if (--self->movecount<0 || !P_Move (self)) - { - P_NewChaseDir (self); - } - } - - // Do missile attack - if (!(self->flags & MF_JUSTATTACKED)) - { - if (P_CheckMissileRange (self) && (pr_firedemonchase() < 20)) - { - self->SetState (self->MissileState); - self->flags |= MF_JUSTATTACKED; - return 0; - } - } - else - { - self->flags &= ~MF_JUSTATTACKED; - } - - // make active sound - if (pr_firedemonchase() < 3) - { - self->PlayActiveSound (); - } - return 0; -} - -//============================================================================ -// -// A_FiredSplotch -// -//============================================================================ - -DEFINE_ACTION_FUNCTION(AActor, A_FiredSplotch) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *mo; - - mo = Spawn ("FireDemonSplotch1", self->Pos(), ALLOW_REPLACE); - if (mo) - { - mo->Vel.X = (pr_firedemonsplotch() - 128) / 32.; - mo->Vel.Y = (pr_firedemonsplotch() - 128) / 32.; - mo->Vel.Z = (pr_firedemonsplotch() / 64.) + 3; - } - mo = Spawn ("FireDemonSplotch2", self->Pos(), ALLOW_REPLACE); - if (mo) - { - mo->Vel.X = (pr_firedemonsplotch() - 128) / 32.; - mo->Vel.Y = (pr_firedemonsplotch() - 128) / 32.; - mo->Vel.Z = (pr_firedemonsplotch() / 64.) + 3; - } - return 0; -} diff --git a/src/g_hexen/a_hexenmisc.cpp b/src/g_hexen/a_hexenmisc.cpp index 3676bf21b..1a635ff71 100644 --- a/src/g_hexen/a_hexenmisc.cpp +++ b/src/g_hexen/a_hexenmisc.cpp @@ -38,7 +38,6 @@ #include "a_fighterhammer.cpp" #include "a_fighterplayer.cpp" #include "a_fighterquietus.cpp" -#include "a_firedemon.cpp" #include "a_flechette.cpp" #include "a_flies.cpp" #include "a_fog.cpp" diff --git a/src/g_shared/a_action.cpp b/src/g_shared/a_action.cpp index 61be39a0e..edd97a6d4 100644 --- a/src/g_shared/a_action.cpp +++ b/src/g_shared/a_action.cpp @@ -449,3 +449,10 @@ void FaceMovementDirection(AActor *actor) break; } } + +DEFINE_ACTION_FUNCTION(AActor, FaceMovementDirection) +{ + PARAM_SELF_PROLOGUE(AActor); + FaceMovementDirection(self); + return 0; +} diff --git a/src/p_enemy.cpp b/src/p_enemy.cpp index 20a549a51..cbddb4840 100644 --- a/src/p_enemy.cpp +++ b/src/p_enemy.cpp @@ -414,6 +414,12 @@ bool P_CheckMissileRange (AActor *actor) return actor->SuggestMissileAttack (dist); } +DEFINE_ACTION_FUNCTION(AActor, CheckMissileRange) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_BOOL(P_CheckMissileRange(self)); +} + bool AActor::SuggestMissileAttack (double dist) { // new version encapsulates the different behavior in flags instead of virtual functions @@ -707,6 +713,11 @@ bool P_Move (AActor *actor) } return true; } +DEFINE_ACTION_FUNCTION(AActor, MonsterMove) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_BOOL(P_Move(self)); +} //============================================================================= @@ -1030,7 +1041,12 @@ void P_NewChaseDir(AActor * actor) } - +DEFINE_ACTION_FUNCTION(AActor, NewChaseDir) +{ + PARAM_SELF_PROLOGUE(AActor); + P_NewChaseDir(self); + return 0; +} //============================================================================= diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index bd05941b3..db6b9a287 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -3327,6 +3327,13 @@ void AActor::PlayActiveSound () } } +DEFINE_ACTION_FUNCTION(AActor, PlayActiveSound) +{ + PARAM_SELF_PROLOGUE(AActor); + self->PlayActiveSound(); + return 0; +} + bool AActor::IsOkayToAttack (AActor *link) { if (!(player // Original AActor::IsOkayToAttack was only for players @@ -6877,6 +6884,13 @@ DEFINE_ACTION_FUNCTION(AActor, deltaangle) // should this be global? ACTION_RETURN_FLOAT(deltaangle(DAngle(a1), DAngle(a2)).Degrees); } +DEFINE_ACTION_FUNCTION(AActor, Distance2D) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_OBJECT(other, AActor); + ACTION_RETURN_FLOAT(self->Distance2D(other)); +} + DEFINE_ACTION_FUNCTION(AActor, AddZ) { PARAM_SELF_PROLOGUE(AActor); diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index c7a009038..48b5f7ded 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -66,9 +66,11 @@ class Actor : Thinker native native float GetBobOffset(float frac = 0); native void SetDamage(int dmg); native static bool isDehState(state st); + native double Distance2D(Actor other); native void SetOrigin(vector3 newpos, bool moving); native void SetXYZ(vector3 newpos); native Actor GetPointer(int aaptr); + native void FaceMovementDirection(); native static Actor Spawn(class type, vector3 pos = (0,0,0), int replace = NO_REPLACE); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); native Actor SpawnMissileZ (double z, Actor dest, class type); @@ -84,6 +86,9 @@ class Actor : Thinker native native Actor, int LineAttack(double angle, double distance, double pitch, int damage, Name damageType, class pufftype, int flags = 0, out FTranslatedLineTarget victim = null); native bool CheckSight(Actor target, int flags = 0); native bool HitFriend(); + native bool MonsterMove(); + native void NewChaseDir(); + native bool CheckMissileRange(); native bool SetState(state st, bool nofunction = false); native void LinkToWorld(); native void UnlinkFromWorld(); @@ -104,6 +109,7 @@ class Actor : Thinker native native bool TeleportMove(Vector3 pos, bool telefrag, bool modifyactor = true); native double DistanceBySpeed(Actor other, double speed); native name GetSpecies(); + native void PlayActiveSound(); // DECORATE compatible functions native bool CheckClass(class checkclass, int ptr_select = AAPTR_DEFAULT, bool match_superclass = false); diff --git a/wadsrc/static/zscript/hexen/firedemon.txt b/wadsrc/static/zscript/hexen/firedemon.txt index 001e1629f..b425ecb11 100644 --- a/wadsrc/static/zscript/hexen/firedemon.txt +++ b/wadsrc/static/zscript/hexen/firedemon.txt @@ -3,6 +3,9 @@ class FireDemon : Actor { + const FIREDEMON_ATTACK_RANGE = 64*8.; + int strafecount; + Default { Health 80; @@ -23,11 +26,6 @@ class FireDemon : Actor Obituary "$OB_FIREDEMON"; } - native void A_FiredRocks(); - native void A_FiredChase(); - native void A_FiredAttack(); - native void A_FiredSplotch(); - States { Spawn: @@ -71,6 +69,208 @@ class FireDemon : Actor FDMN R 1 A_FreezeDeathChunks; Wait; } + + + + + //============================================================================ + // Fire Demon AI + // + // special1 index into floatbob + // strafecount whether strafing or not + //============================================================================ + + //============================================================================ + // + // A_FiredSpawnRock + // + //============================================================================ + + private void A_FiredSpawnRock () + { + Actor mo; + class rtype; + + switch (random[FireDemonRock](0, 4)) + { + case 0: + rtype = "FireDemonRock1"; + break; + case 1: + rtype = "FireDemonRock2"; + break; + case 2: + rtype = "FireDemonRock3"; + break; + case 3: + rtype = "FireDemonRock4"; + break; + case 4: + default: + rtype = "FireDemonRock5"; + break; + } + + double xo = (random[FireDemonRock]() - 128) / 16.; + double yo = (random[FireDemonRock]() - 128) / 16.; + double zo = random[FireDemonRock]() / 32.; + mo = Spawn (rtype, Vec3Offset(xo, yo, zo), ALLOW_REPLACE); + if (mo) + { + mo.target = self; + mo.Vel.X = (random[FireDemonRock]() - 128) / 64.; + mo.Vel.Y = (random[FireDemonRock]() - 128) / 64.; + mo.Vel.Z = (random[FireDemonRock]() / 64.); + mo.special1 = 2; // Number bounces + } + + // Initialize fire demon + strafecount = 0; + bJustAttacked = false; + } + + //============================================================================ + // + // A_FiredRocks + // + //============================================================================ + void A_FiredRocks() + { + A_FiredSpawnRock (); + A_FiredSpawnRock (); + A_FiredSpawnRock (); + A_FiredSpawnRock (); + A_FiredSpawnRock (); + } + + //============================================================================ + // + // A_FiredAttack + // + //============================================================================ + + void A_FiredAttack() + { + if (target == null) return; + Actor mo = SpawnMissile (target, "FireDemonMissile"); + if (mo) A_PlaySound ("FireDemonAttack", CHAN_BODY); + } + + //============================================================================ + // + // A_FiredChase + // + //============================================================================ + + void A_FiredChase() + { + int weaveindex = special1; + double ang; + double dist; + + if (reactiontime) reactiontime--; + if (threshold) threshold--; + + // Float up and down + AddZ(BobSin(weaveindex)); + special1 = (weaveindex + 2) & 63; + + // Ensure it stays above certain height + if (pos.Z < floorz + 64) + { + AddZ(2); + } + + if(!target || !target.bShootable) + { // Invalid target + LookForPlayers (true); + return; + } + + // Strafe + if (strafecount > 0) + { + strafecount--; + } + else + { + strafecount = 0; + Vel.X = Vel.Y = 0; + dist = Distance2D(target); + if (dist < FIREDEMON_ATTACK_RANGE) + { + if (random[FiredChase]() < 30) + { + ang = AngleTo(target); + if (random[FiredChase]() < 128) + ang += 90; + else + ang -= 90; + Thrust(8, ang); + strafecount = 3; // strafe time + } + } + } + + FaceMovementDirection (); + + // Normal movement + if (!strafecount) + { + if (--movecount<0 || !MonsterMove ()) + { + NewChaseDir (); + } + } + + // Do missile attack + if (!bJustAttacked) + { + if (CheckMissileRange () && (random[FiredChase]() < 20)) + { + SetState (MissileState); + bJustAttacked = true; + return; + } + } + else + { + bJustAttacked = false; + } + + // make active sound + if (random[FiredChase]() < 3) + { + PlayActiveSound (); + } + } + + //============================================================================ + // + // A_FiredSplotch + // + //============================================================================ + + void A_FiredSplotch() + { + Actor mo; + + mo = Spawn ("FireDemonSplotch1", Pos, ALLOW_REPLACE); + if (mo) + { + mo.Vel.X = (random[FireDemonSplotch]() - 128) / 32.; + mo.Vel.Y = (random[FireDemonSplotch]() - 128) / 32.; + mo.Vel.Z = (random[FireDemonSplotch]() / 64.) + 3; + } + mo = Spawn ("FireDemonSplotch2", Pos, ALLOW_REPLACE); + if (mo) + { + mo.Vel.X = (random[FireDemonSplotch]() - 128) / 32.; + mo.Vel.Y = (random[FireDemonSplotch]() - 128) / 32.; + mo.Vel.Z = (random[FireDemonSplotch]() / 64.) + 3; + } + } + } // FireDemonSplotch1 ------------------------------------------------------- @@ -124,8 +324,6 @@ class FireDemonRock1 : Actor +NOTELEPORT } - native void A_SmBounce(); - States { Spawn: @@ -137,6 +335,21 @@ class FireDemonRock1 : Actor FDMN S 200; Stop; } + + //============================================================================ + // + // A_SmBounce + // + //============================================================================ + + void A_SmBounce() + { + // give some more velocity (x,y,&z) + SetZ(floorz + 1); + Vel.Z = 2. + random[SMBounce]() / 64.; + Vel.X = random[SMBounce](0, 2); + Vel.Y = random[SMBounce](0, 2); + } } // FireDemonRock2 ------------------------------------------------------------ From ac0413838ccebd4e20dd1a85896aad3b3bc6fae3 Mon Sep 17 00:00:00 2001 From: Leonard2 Date: Sun, 13 Nov 2016 09:34:05 +0100 Subject: [PATCH 240/255] Fixed: A StateProvider actor could no longer use its own user variables Refactored the FxIdentifier code a bit to avoid code duplication --- src/scripting/codegeneration/codegen.cpp | 249 ++++++++++------------- src/scripting/codegeneration/codegen.h | 7 +- 2 files changed, 117 insertions(+), 139 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index dac88aa76..f59a2753d 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5102,65 +5102,31 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) { if (sym->IsKindOf(RUNTIME_CLASS(PField))) { - if (!ctx.Function) - { - ScriptPosition.Message(MSG_ERROR, "Cannot resolve class member outside a function", sym->SymbolName.GetChars()); - delete this; - return nullptr; - } - PField *vsym = static_cast(sym); - - // We have 4 cases to consider here: - // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. - // 2. This is a static function - // 3. This is an action function with a restricted self pointer - // 4. This is a normal member or unrestricted action function. - if ((vsym->Flags & VARF_Deprecated) && !ctx.FromDecorate) - { - ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", sym->SymbolName.GetChars()); - } - if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) - { - ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", sym->SymbolName.GetChars()); - delete this; - return nullptr; - } - - if (vsym->Flags & VARF_Static) - { - // todo. For now these cannot be defined so let's just exit. - ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); - delete this; - return nullptr; - } - - if (ctx.Function->Variants[0].SelfClass == nullptr) - { - ScriptPosition.Message(MSG_ERROR, "Unable to access class member from static function"); - delete this; - return nullptr; - } + FxExpression *self = new FxSelf(ScriptPosition); + self = self->Resolve(ctx); + newex = ResolveMember(ctx, ctx.Function->Variants[0].SelfClass, self, ctx.Function->Variants[0].SelfClass); + ABORT(newex); if (ctx.Function->Variants[0].SelfClass != ctx.Class) { // Check if the restricted class can access it. PSymbol *sym2; - if ((sym2 = ctx.FindInSelfClass(Identifier, symtbl)) != nullptr) + if ((sym2 = ctx.FindInClass(Identifier, symtbl)) != nullptr) { if (sym != sym2) { + // At the moment this cannot happen as the only possibility is SelfClass being an AActor and OwningClass an AStateProvider which comes from AActor anyways. ScriptPosition.Message(MSG_ERROR, "Member variable of %s not accessible through restricted self pointer", ctx.Class->TypeName.GetChars()); + delete newex; delete this; return nullptr; } } } - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as member variable, index %d\n", Identifier.GetChars(), vsym->Offset); - newex = new FxClassMember((new FxSelf(ScriptPosition))->Resolve(ctx), vsym, ScriptPosition); } } - // now constants in the owning class. + // now check in the owning class. if (newex == nullptr && (sym = ctx.FindInClass(Identifier, symtbl)) != nullptr) { if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) @@ -5170,6 +5136,23 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) delete this; return newex->Resolve(ctx); } + else if (ctx.FromDecorate && ctx.Class->IsDescendantOf(RUNTIME_CLASS(AStateProvider)) && sym->IsKindOf(RUNTIME_CLASS(PField))) + { + if (~ctx.Function->Variants[0].Flags & VARF_Action) + { + // No stateowner pointer to rely on, complete ambiguity. + // Abort here instead of risking a crash. + ScriptPosition.Message(MSG_ERROR, "Member variable access from non-action function within a StateProvider."); + delete this; + return nullptr; + } + + FxExpression *self = new FxSelf(ScriptPosition, true); + self = self->Resolve(ctx); + newex = ResolveMember(ctx, ctx.Class, self, ctx.Class); + ABORT(newex); + ScriptPosition.Message(MSG_WARNING, "Self pointer used in ambiguous context; VM execution may abort!"); + } else { if (sym->IsKindOf(RUNTIME_CLASS(PFunction))) @@ -5222,6 +5205,78 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) return newex? newex->Resolve(ctx) : nullptr; } +//========================================================================== +// +// +// +//========================================================================== + +FxExpression *FxIdentifier::ResolveMember(FCompileContext &ctx, PClass *classctx, FxExpression *&object, PStruct *objtype) +{ + PSymbol *sym; + PSymbolTable *symtbl; + bool isclass = objtype->IsKindOf(RUNTIME_CLASS(PClass)); + if ((sym = objtype->Symbols.FindSymbolInTable(Identifier, symtbl)) != nullptr) + { + if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) + { + ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as %s constant\n", Identifier.GetChars(), isclass ? "class" : "struct"); + delete object; + object = nullptr; + return FxConstant::MakeConstant(sym, ScriptPosition); + } + else if (sym->IsKindOf(RUNTIME_CLASS(PField))) + { + PField *vsym = static_cast(sym); + + // We have 4 cases to consider here: + // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. + // 2. This is a static function + // 3. This is an action function with a restricted self pointer + // 4. This is a normal member or unrestricted action function. + if (vsym->Flags & VARF_Deprecated && !ctx.FromDecorate) + { + ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); + } + if ((vsym->Flags & VARF_Private) && symtbl != &classctx->Symbols) + { + ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); + return nullptr; + } + + if (vsym->Flags & VARF_Static) + { + // todo. For now these cannot be defined so let's just exit. + ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); + return nullptr; + } + auto x = isclass ? new FxClassMember(object, vsym, ScriptPosition) : new FxStructMember(object, vsym, ScriptPosition); + object = nullptr; + return x->Resolve(ctx); + } + else + { + if (sym->IsKindOf(RUNTIME_CLASS(PFunction))) + { + ScriptPosition.Message(MSG_ERROR, "Function '%s' used without ().\n", Identifier.GetChars()); + } + else + { + ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'.\n", Identifier.GetChars()); + } + delete object; + object = nullptr; + return nullptr; + } + } + else + { + ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); + delete object; + object = nullptr; + return nullptr; + } +} //========================================================================== // @@ -5249,111 +5304,25 @@ FxMemberIdentifier::~FxMemberIdentifier() FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) { - PSymbol * sym; - FxExpression *newex = nullptr; - CHECKRESOLVED(); SAFE_RESOLVE(Object, ctx); if (Object->ValueType->IsKindOf(RUNTIME_CLASS(PPointer))) { - PSymbolTable *symtbl; auto ptype = static_cast(Object->ValueType)->PointedType; - - if (ptype->IsKindOf(RUNTIME_CLASS(PStruct))) // PClass is a child class of PStruct so this covers both. + if (ptype->IsKindOf(RUNTIME_CLASS(PStruct))) { - PStruct *cls = static_cast(ptype); - bool isclass = cls->IsKindOf(RUNTIME_CLASS(PClass)); - if ((sym = cls->Symbols.FindSymbolInTable(Identifier, symtbl)) != nullptr) - { - if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) - { - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as %s constant\n", Identifier.GetChars(), isclass? "class" : "struct"); - newex = FxConstant::MakeConstant(sym, ScriptPosition); - } - else if (sym->IsKindOf(RUNTIME_CLASS(PField))) - { - PField *vsym = static_cast(sym); - - // We have 4 cases to consider here: - // 1. The symbol is a static/meta member (not implemented yet) which is always accessible. - // 2. This is a static function - // 3. This is an action function with a restricted self pointer - // 4. This is a normal member or unrestricted action function. - if (vsym->Flags & VARF_Deprecated) - { - ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); - } - if ((vsym->Flags & VARF_Private) && symtbl != &ctx.Class->Symbols) - { - ScriptPosition.Message(MSG_ERROR, "Private member %s not accessible", vsym->SymbolName.GetChars()); - delete this; - return nullptr; - } - - if (vsym->Flags & VARF_Static) - { - // todo. For now these cannot be defined so let's just exit. - ScriptPosition.Message(MSG_ERROR, "Static members not implemented yet."); - delete this; - return nullptr; - } - auto x = isclass? new FxClassMember(Object, vsym, ScriptPosition) : new FxStructMember(Object, vsym, ScriptPosition); - Object = nullptr; - delete this; - return x->Resolve(ctx); - } - else - { - ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); - delete this; - return nullptr; - } - } - else - { - ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); - delete this; - return nullptr; - } + auto ret = ResolveMember(ctx, ctx.Class, Object, static_cast(ptype)); + delete this; + return ret; } } else if (Object->ValueType->IsA(RUNTIME_CLASS(PStruct))) { - if ((sym = Object->ValueType->Symbols.FindSymbol(Identifier, false)) != nullptr) - { - if (sym->IsKindOf(RUNTIME_CLASS(PSymbolConst))) - { - ScriptPosition.Message(MSG_DEBUGLOG, "Resolving name '%s' as struct constant\n", Identifier.GetChars()); - newex = FxConstant::MakeConstant(sym, ScriptPosition); - } - else if (sym->IsKindOf(RUNTIME_CLASS(PField))) - { - PField *vsym = static_cast(sym); - - if (vsym->Flags & VARF_Deprecated) - { - ScriptPosition.Message(MSG_WARNING, "Accessing deprecated member variable %s", vsym->SymbolName.GetChars()); - } - auto x = new FxStructMember(Object, vsym, ScriptPosition); - Object = nullptr; - delete this; - return x->Resolve(ctx); - } - else - { - ScriptPosition.Message(MSG_ERROR, "Invalid member identifier '%s'\n", Identifier.GetChars()); - delete this; - return nullptr; - } - } - else - { - ScriptPosition.Message(MSG_ERROR, "Unknown identifier '%s'", Identifier.GetChars()); - delete this; - return nullptr; - } + auto ret = ResolveMember(ctx, ctx.Class, Object, static_cast(Object->ValueType)); + delete this; + return ret; } ScriptPosition.Message(MSG_ERROR, "Left side of %s is not a struct or class", Identifier.GetChars()); @@ -5361,7 +5330,6 @@ FxExpression *FxMemberIdentifier::Resolve(FCompileContext& ctx) return nullptr; } - //========================================================================== // // @@ -5406,9 +5374,10 @@ ExpEmit FxLocalVariable::Emit(VMFunctionBuilder *build) // //========================================================================== -FxSelf::FxSelf(const FScriptPosition &pos) +FxSelf::FxSelf(const FScriptPosition &pos, bool deccheck) : FxExpression(EFX_Self, pos) { + check = deccheck; } //========================================================================== @@ -5438,6 +5407,12 @@ FxExpression *FxSelf::Resolve(FCompileContext& ctx) ExpEmit FxSelf::Emit(VMFunctionBuilder *build) { + if (check) + { + build->Emit(OP_EQA_R, 1, 0, 1); + build->Emit(OP_JMP, 1); + build->Emit(OP_THROW, 2, X_BAD_SELF); + } // self is always the first pointer passed to the function return ExpEmit(0, REGT_POINTER, false, true); } diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 2f82dba57..0f937b0cd 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -347,12 +347,13 @@ public: FxIdentifier(FName i, const FScriptPosition &p); FxExpression *Resolve(FCompileContext&); + FxExpression *ResolveMember(FCompileContext&, PClass*, FxExpression*&, PStruct*); }; //========================================================================== // -// FxIdentifier +// FxMemberIdentifier // //========================================================================== @@ -1240,8 +1241,10 @@ public: class FxSelf : public FxExpression { + bool check; + public: - FxSelf(const FScriptPosition&); + FxSelf(const FScriptPosition&, bool deccheck = false); FxExpression *Resolve(FCompileContext&); ExpEmit Emit(VMFunctionBuilder *build); }; From f238f0ba5ca520cbf9a6a96b49bb00623993ab64 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 13 Nov 2016 12:02:41 +0100 Subject: [PATCH 241/255] - try to preserve a bit more information about incorrect use of user variables to print more meaningful error messages. This is not complete yet and will need integration with the previous commit. --- src/dobjtype.cpp | 1 + src/dobjtype.h | 1 + src/p_actionfunctions.cpp | 10 ++++ src/p_pspr.cpp | 9 ++++ src/sc_man.cpp | 11 +++-- src/sc_man.h | 4 +- src/scripting/codegeneration/codegen.cpp | 2 +- src/scripting/codegeneration/codegen.h | 1 + src/scripting/decorate/thingdef_parse.cpp | 1 + src/scripting/thingdef.cpp | 58 +++++++++++++++++++++++ src/scripting/vm/vm.h | 1 + 11 files changed, 94 insertions(+), 5 deletions(-) diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index c2b1008df..f3fda2b14 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -2791,6 +2791,7 @@ PClass::PClass() Defaults = nullptr; bRuntimeClass = false; bExported = false; + bDecorateClass = false; ConstructNative = nullptr; mDescriptiveName = "Class"; diff --git a/src/dobjtype.h b/src/dobjtype.h index be15193a4..e1bfd0796 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -775,6 +775,7 @@ public: BYTE *Defaults; bool bRuntimeClass; // class was defined at run-time, not compile-time bool bExported; // This type has been declared in a script + bool bDecorateClass; // may be subject to some idiosyncracies due to DECORATE backwards compatibility TArray Virtuals; // virtual function table void (*ConstructNative)(void *); diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index a99ba9ab6..74d828d55 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -78,6 +78,7 @@ #include "p_spec.h" #include "templates.h" #include "vm.h" +#include "v_text.h" #include "thingdef.h" #include "math/cmath.h" @@ -132,6 +133,15 @@ bool ACustomInventory::CallStateChain (AActor *actor, FState *state) if (state->ActionFunc != NULL) { + if (state->ActionFunc->Unsafe) + { + // If an unsafe function (i.e. one that accesses user variables) is being detected, print a warning once and remove the bogus function. We may not call it because that would inevitably crash. + auto owner = FState::StaticFindStateOwner(state); + Printf(TEXTCOLOR_RED "Unsafe state call in state %s.%d to %s which accesses user variables. The action function has been removed from this state\n", + owner->TypeName.GetChars(), state - owner->OwnedStates, static_cast(state->ActionFunc)->PrintableName.GetChars()); + state->ActionFunc = nullptr; + } + VMFrameStack stack; PPrototype *proto = state->ActionFunc->Proto; VMReturn *wantret; diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index d279a180c..56562ab21 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -29,6 +29,7 @@ #include "g_level.h" #include "d_player.h" #include "serializer.h" +#include "v_text.h" // MACROS ------------------------------------------------------------------ @@ -337,6 +338,14 @@ void DPSprite::SetState(FState *newstate, bool pending) { FState *nextstate; FStateParamInfo stp = { newstate, STATE_Psprite, ID }; + if (newstate->ActionFunc != nullptr && newstate->ActionFunc->Unsafe) + { + // If an unsafe function (i.e. one that accesses user variables) is being detected, print a warning once and remove the bogus function. We may not call it because that would inevitably crash. + auto owner = FState::StaticFindStateOwner(newstate); + Printf(TEXTCOLOR_RED "Unsafe state call in state %s.%d to %s which accesses user variables. The action function has been removed from this state\n", + owner->TypeName.GetChars(), newstate - owner->OwnedStates, static_cast(newstate->ActionFunc)->PrintableName.GetChars()); + newstate->ActionFunc = nullptr; + } if (newstate->CallAction(Owner->mo, Caller, &stp, &nextstate)) { // It's possible this call resulted in this very layer being replaced. diff --git a/src/sc_man.cpp b/src/sc_man.cpp index f48d6b461..254caed62 100644 --- a/src/sc_man.cpp +++ b/src/sc_man.cpp @@ -1046,7 +1046,10 @@ void FScriptPosition::Message (int severity, const char *message, ...) const { FString composed; - if ((severity == MSG_DEBUG || severity == MSG_DEBUGLOG) && developer < DMSG_NOTIFY) return; + if (severity == MSG_DEBUGLOG && developer < DMSG_NOTIFY) return; + if (severity == MSG_DEBUGERROR && developer < DMSG_ERROR) return; + if (severity == MSG_DEBUGWARN && developer < DMSG_WARNING) return; + if (severity == MSG_DEBUGMSG && developer < DMSG_NOTIFY) return; if (severity == MSG_OPTERROR) { severity = StrictErrors || strictdecorate ? MSG_ERROR : MSG_WARNING; @@ -1073,9 +1076,11 @@ void FScriptPosition::Message (int severity, const char *message, ...) const return; case MSG_WARNING: + case MSG_DEBUGWARN: + case MSG_DEBUGERROR: // This is intentionally not being printed as an 'error', the difference to MSG_DEBUGWARN is only the severity level at which it gets triggered. WarnCounter++; type = "warning"; - color = TEXTCOLOR_YELLOW; + color = TEXTCOLOR_ORANGE; break; case MSG_ERROR: @@ -1085,7 +1090,7 @@ void FScriptPosition::Message (int severity, const char *message, ...) const break; case MSG_MESSAGE: - case MSG_DEBUG: + case MSG_DEBUGMSG: type = "message"; color = TEXTCOLOR_GREEN; break; diff --git a/src/sc_man.h b/src/sc_man.h index 5eeacd892..fde6efbed 100644 --- a/src/sc_man.h +++ b/src/sc_man.h @@ -125,7 +125,9 @@ enum MSG_FATAL, MSG_ERROR, MSG_OPTERROR, - MSG_DEBUG, + MSG_DEBUGERROR, + MSG_DEBUGWARN, + MSG_DEBUGMSG, MSG_LOG, MSG_DEBUGLOG, MSG_MESSAGE diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index f59a2753d..2ce1b4265 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -8073,7 +8073,7 @@ FxExpression *FxClassTypeCast::Resolve(FCompileContext &ctx) delete this; return nullptr; } - ScriptPosition.Message(MSG_DEBUG, "resolving '%s' as class name", clsname.GetChars()); + ScriptPosition.Message(MSG_DEBUGLOG, "resolving '%s' as class name", clsname.GetChars()); } } FxExpression *x = new FxConstant(cls, to, ScriptPosition); diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index 0f937b0cd..b9679ad31 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -79,6 +79,7 @@ struct FCompileContext int StateIndex; // index in actor's state table for anonymous functions, otherwise -1 (not used by DECORATE which pre-resolves state indices) int StateCount; // amount of states an anoymous function is being used on (must be 1 for state indices to be allowed.) int Lump; + bool Unsafe = false; TDeletingArray FunctionArgs; FCompileContext(PFunction *func, PPrototype *ret, bool fromdecorate, int stateindex, int statecount, int lump); diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index baa662047..e292e1844 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -909,6 +909,7 @@ PClassActor *CreateNewActor(const FScriptPosition &sc, FName typeName, FName par } } ti = DecoDerivedClass(sc, parent, typeName); + ti->bDecorateClass = true; // we only set this for 'modern' DECORATE. The original stuff is so limited that it cannot do anything that may require flagging. ti->Replacee = ti->Replacement = NULL; ti->DoomEdNum = -1; diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index 8c42e8987..d163ffb38 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -206,6 +206,55 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, } } +//========================================================================== +// +// CheckForUnsafeStates +// +// Performs a quick analysis to find potentially bad states. +// This is not perfect because it cannot track jumps by function. +// For such cases a runtime check in the relevant places is also present. +// +//========================================================================== +static int CheckForUnsafeStates(PClassActor *obj) +{ + static ENamedName weaponstates[] = { NAME_Ready, NAME_Deselect, NAME_Select, NAME_Fire, NAME_AltFire, NAME_Hold, NAME_AltHold, NAME_Flash, NAME_AltFlash, NAME_None }; + static ENamedName pickupstates[] = { NAME_Pickup, NAME_Drop, NAME_Use, NAME_None }; + TMap checked; + ENamedName *test; + int errors = 0; + + if (obj->IsDescendantOf(RUNTIME_CLASS(AWeapon))) + { + if (obj->Size == RUNTIME_CLASS(AWeapon)->Size) return 0; // This class cannot have user variables. + test = weaponstates; + } + else if (obj->IsDescendantOf(RUNTIME_CLASS(ACustomInventory))) + { + if (obj->Size == RUNTIME_CLASS(ACustomInventory)->Size) return 0; // This class cannot have user variables. + test = pickupstates; + } + else return 0; // something else derived from AStateProvider. We do not know what this may be. + + for (; *test != NAME_None; test++) + { + FState *state = obj->FindState(*test); + while (state != nullptr && checked.CheckKey(state) == nullptr) // have we checked this state already. If yes, we can stop checking the current chain. + { + checked[state] = true; + if (state->ActionFunc && state->ActionFunc->Unsafe) + { + // If an unsafe function (i.e. one that accesses user variables) is being detected, print a warning once and remove the bogus function. We may not call it because that would inevitably crash. + auto owner = FState::StaticFindStateOwner(state); + Printf(TEXTCOLOR_RED "Unsafe state call in state %s.%d to %s, reached by %s.%s which accesses user variables.\n", + owner->TypeName.GetChars(), state - owner->OwnedStates, static_cast(state->ActionFunc)->PrintableName.GetChars(), obj->TypeName.GetChars(), FName(*test).GetChars()); + errors++; + } + state = state->NextState; + } + } + return errors; +} + //========================================================================== // // LoadActors @@ -253,6 +302,15 @@ void LoadActors () errorcount++; continue; } + + if (ti->bDecorateClass && ti->IsDescendantOf(RUNTIME_CLASS(AStateProvider))) + { + // either a DECORATE based weapon or CustomInventory. + // These are subject to relaxed rules for user variables in states. + // Although there is a runtime check for bogus states, let's do a quick analysis if any of the known entry points + // hits an unsafe state. If we can find something here it can be handled wuth a compile error rather than a runtime error. + errorcount += CheckForUnsafeStates(ti); + } } if (errorcount > 0) { diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 6c7878a9a..019d6c3a6 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -656,6 +656,7 @@ class VMFunction : public DObject public: bool Native; bool Final = false; // cannot be overridden + bool Unsafe = false; // Contains references to class fields that are unsafe for psp and item state calls. BYTE ImplicitArgs = 0; // either 0 for static, 1 for method or 3 for action int VirtualIndex = -1; FName Name; From 7d49a8296350954c50fc57c8cdeea7121cbd25a2 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 13 Nov 2016 12:37:28 +0100 Subject: [PATCH 242/255] removed some unneeded checks - since we now look for fields in the base class first the restriction check is no longer needed as it was for a different mode of looking up the identifier. - In DECORATE we do not need to bother with non-action functions. Non-action functions cannot be defined from DECORATE so there's no need to check if we are in one. - make the warning for unsafe access a debug message because this can affect legitimate code. --- src/scripting/codegeneration/codegen.cpp | 29 ++---------------------- 1 file changed, 2 insertions(+), 27 deletions(-) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 2ce1b4265..8543326cf 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5106,23 +5106,6 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) self = self->Resolve(ctx); newex = ResolveMember(ctx, ctx.Function->Variants[0].SelfClass, self, ctx.Function->Variants[0].SelfClass); ABORT(newex); - - if (ctx.Function->Variants[0].SelfClass != ctx.Class) - { - // Check if the restricted class can access it. - PSymbol *sym2; - if ((sym2 = ctx.FindInClass(Identifier, symtbl)) != nullptr) - { - if (sym != sym2) - { - // At the moment this cannot happen as the only possibility is SelfClass being an AActor and OwningClass an AStateProvider which comes from AActor anyways. - ScriptPosition.Message(MSG_ERROR, "Member variable of %s not accessible through restricted self pointer", ctx.Class->TypeName.GetChars()); - delete newex; - delete this; - return nullptr; - } - } - } } } @@ -5138,20 +5121,12 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) } else if (ctx.FromDecorate && ctx.Class->IsDescendantOf(RUNTIME_CLASS(AStateProvider)) && sym->IsKindOf(RUNTIME_CLASS(PField))) { - if (~ctx.Function->Variants[0].Flags & VARF_Action) - { - // No stateowner pointer to rely on, complete ambiguity. - // Abort here instead of risking a crash. - ScriptPosition.Message(MSG_ERROR, "Member variable access from non-action function within a StateProvider."); - delete this; - return nullptr; - } - FxExpression *self = new FxSelf(ScriptPosition, true); self = self->Resolve(ctx); newex = ResolveMember(ctx, ctx.Class, self, ctx.Class); ABORT(newex); - ScriptPosition.Message(MSG_WARNING, "Self pointer used in ambiguous context; VM execution may abort!"); + ScriptPosition.Message(MSG_DEBUGWARN, "Self pointer used in ambiguous context; VM execution may abort!"); + ctx.Unsafe = true; } else { From a2f4cd7cdad9d850e02cdea65648d32440a562d4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 13 Nov 2016 14:20:30 +0100 Subject: [PATCH 243/255] - fixed: All functions that are callable from weapon states and not members of Actor need to be declared 'action'. With the stricter type checks of the self pointer that were now implemented these all produced errors. --- src/g_doom/a_doomweaps.cpp | 39 --------------- src/g_heretic/a_chicken.cpp | 6 +-- src/g_heretic/a_hereticweaps.cpp | 30 ++++++------ src/g_hexen/a_clericflame.cpp | 2 +- src/g_hexen/a_clericholy.cpp | 4 +- src/g_hexen/a_clericmace.cpp | 2 +- src/g_hexen/a_clericstaff.cpp | 8 +-- src/g_hexen/a_fighteraxe.cpp | 19 +++---- src/g_hexen/a_fighterhammer.cpp | 4 +- src/g_hexen/a_fighterplayer.cpp | 2 +- src/g_hexen/a_fighterquietus.cpp | 2 +- src/g_hexen/a_magecone.cpp | 2 +- src/g_hexen/a_magelightning.cpp | 4 +- src/g_hexen/a_magestaff.cpp | 4 +- src/g_hexen/a_pig.cpp | 2 +- src/g_strife/a_strifeweapons.cpp | 44 ++++++++--------- src/p_actionfunctions.cpp | 4 +- src/p_pspr.cpp | 49 +++---------------- src/scripting/codegeneration/codegen.cpp | 20 +++++++- src/scripting/zscript/zcc_compile.cpp | 9 +++- wadsrc/static/zscript/actor.txt | 1 - wadsrc/static/zscript/heretic/chicken.txt | 6 +-- .../static/zscript/heretic/hereticweaps.txt | 30 ++++++------ wadsrc/static/zscript/hexen/clericflame.txt | 2 +- wadsrc/static/zscript/hexen/clericholy.txt | 4 +- wadsrc/static/zscript/hexen/clericmace.txt | 2 +- wadsrc/static/zscript/hexen/clericstaff.txt | 8 +-- wadsrc/static/zscript/hexen/fighteraxe.txt | 12 ++--- wadsrc/static/zscript/hexen/fighterfist.txt | 2 +- wadsrc/static/zscript/hexen/fighterhammer.txt | 4 +- .../static/zscript/hexen/fighterquietus.txt | 2 +- wadsrc/static/zscript/hexen/magecone.txt | 2 +- wadsrc/static/zscript/hexen/magelightning.txt | 4 +- wadsrc/static/zscript/hexen/magestaff.txt | 4 +- wadsrc/static/zscript/hexen/pig.txt | 2 +- wadsrc/static/zscript/shared/inventory.txt | 41 +++++++++------- wadsrc/static/zscript/strife/sigil.txt | 20 ++++---- .../static/zscript/strife/strifeweapons.txt | 20 ++++---- 38 files changed, 185 insertions(+), 237 deletions(-) diff --git a/src/g_doom/a_doomweaps.cpp b/src/g_doom/a_doomweaps.cpp index 37ff05c70..bc962800f 100644 --- a/src/g_doom/a_doomweaps.cpp +++ b/src/g_doom/a_doomweaps.cpp @@ -336,29 +336,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun2) return 0; } -DEFINE_ACTION_FUNCTION(AActor, A_OpenShotgun2) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_WEAPON, "weapons/sshoto", 1, ATTN_NORM); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_LoadShotgun2) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_WEAPON, "weapons/sshotl", 1, ATTN_NORM); - return 0; -} - -DEFINE_ACTION_FUNCTION(AActor, A_CloseShotgun2) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_WEAPON, "weapons/sshotc", 1, ATTN_NORM); - A_ReFire (self); - return 0; -} - - //------------------------------------------------------------------------------------ // // Setting a random flash like some of Doom's weapons can easily crash when the @@ -593,12 +570,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireRailgunLeft) return 0; } -DEFINE_ACTION_FUNCTION(AActor, A_RailWait) -{ - // Okay, this was stupid. Just use a NULL function instead of this. - return 0; -} - // // A_FireBFG // @@ -717,16 +688,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray) return 0; } -// -// A_BFGsound -// -DEFINE_ACTION_FUNCTION(AActor, A_BFGsound) -{ - PARAM_SELF_PROLOGUE(AActor); - S_Sound (self, CHAN_WEAPON, "weapons/bfgf", 1, ATTN_NORM); - return 0; -} - // // A_FireOldBFG // diff --git a/src/g_heretic/a_chicken.cpp b/src/g_heretic/a_chicken.cpp index fa26f7315..8a109d46d 100644 --- a/src/g_heretic/a_chicken.cpp +++ b/src/g_heretic/a_chicken.cpp @@ -138,7 +138,7 @@ void P_UpdateBeak (AActor *self) DEFINE_ACTION_FUNCTION(AActor, A_BeakRaise) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -170,7 +170,7 @@ void P_PlayPeck (AActor *chicken) DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; @@ -205,7 +205,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL1) DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; diff --git a/src/g_heretic/a_hereticweaps.cpp b/src/g_heretic/a_hereticweaps.cpp index 38991b87d..a888be884 100644 --- a/src/g_heretic/a_hereticweaps.cpp +++ b/src/g_heretic/a_hereticweaps.cpp @@ -61,7 +61,7 @@ extern bool P_AutoUseChaosDevice (player_t *player); DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StaffAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; DAngle slope; @@ -107,7 +107,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StaffAttack) DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; @@ -144,7 +144,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL1) DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); int i; DAngle angle; @@ -187,7 +187,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL2) DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -216,7 +216,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL1) DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -247,7 +247,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL2) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GauntletAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle Angle; int damage; @@ -421,7 +421,7 @@ void FireMacePL1B (AActor *actor) DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *ball; player_t *player; @@ -579,7 +579,7 @@ boom: DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -761,7 +761,7 @@ int ARipper::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_FireBlasterPL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; @@ -888,7 +888,7 @@ void ARainTracker::Serialize(FSerializer &arc) DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -924,7 +924,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL1) DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; AActor *MissileActor; @@ -1217,7 +1217,7 @@ int APhoenixFX2::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -1270,7 +1270,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PhoenixPuff) DEFINE_ACTION_FUNCTION(AActor, A_InitPhoenixPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { @@ -1293,7 +1293,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_InitPhoenixPL2) DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *mo; @@ -1346,7 +1346,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL2) DEFINE_ACTION_FUNCTION(AActor, A_ShutdownPhoenixPL2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; diff --git a/src/g_hexen/a_clericflame.cpp b/src/g_hexen/a_clericflame.cpp index f0e9c16b2..2c66cb42d 100644 --- a/src/g_hexen/a_clericflame.cpp +++ b/src/g_hexen/a_clericflame.cpp @@ -66,7 +66,7 @@ void ACFlameMissile::Effect () DEFINE_ACTION_FUNCTION(AActor, A_CFlameAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; diff --git a/src/g_hexen/a_clericholy.cpp b/src/g_hexen/a_clericholy.cpp index d09c3f6aa..362434b02 100644 --- a/src/g_hexen/a_clericholy.cpp +++ b/src/g_hexen/a_clericholy.cpp @@ -211,7 +211,7 @@ void SpawnSpiritTail (AActor *spirit) DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; FTranslatedLineTarget t; @@ -245,7 +245,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack) DEFINE_ACTION_FUNCTION(AActor, A_CHolyPalette) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { diff --git a/src/g_hexen/a_clericmace.cpp b/src/g_hexen/a_clericmace.cpp index 9b8148930..a15196cf8 100644 --- a/src/g_hexen/a_clericmace.cpp +++ b/src/g_hexen/a_clericmace.cpp @@ -15,7 +15,7 @@ static FRandom pr_maceatk ("CMaceAttack"); DEFINE_ACTION_FUNCTION(AActor, A_CMaceAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; diff --git a/src/g_hexen/a_clericstaff.cpp b/src/g_hexen/a_clericstaff.cpp index a4050a1ef..a838357d6 100644 --- a/src/g_hexen/a_clericstaff.cpp +++ b/src/g_hexen/a_clericstaff.cpp @@ -46,7 +46,7 @@ int ACStaffMissile::DoSpecialDamage (AActor *target, int damage, FName damagetyp DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheck) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); APlayerPawn *pmo; int damage; @@ -115,7 +115,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheck) DEFINE_ACTION_FUNCTION(AActor, A_CStaffAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *mo; player_t *player; @@ -167,7 +167,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffMissileSlither) DEFINE_ACTION_FUNCTION(AActor, A_CStaffInitBlink) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); self->weaponspecial = (pr_blink()>>1)+20; return 0; @@ -181,7 +181,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffInitBlink) DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheckBlink) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player && self->player->ReadyWeapon) { diff --git a/src/g_hexen/a_fighteraxe.cpp b/src/g_hexen/a_fighteraxe.cpp index 4260f4eb4..1dc02d599 100644 --- a/src/g_hexen/a_fighteraxe.cpp +++ b/src/g_hexen/a_fighteraxe.cpp @@ -19,13 +19,6 @@ DECLARE_ACTION(A_Raise) static FRandom pr_axeatk ("FAxeAtk"); -void A_FAxeCheckReady (AActor *actor); -void A_FAxeCheckUp (AActor *actor); -void A_FAxeCheckAtk (AActor *actor); -void A_FAxeCheckReadyG (AActor *actor); -void A_FAxeCheckUpG (AActor *actor); -void A_FAxeAttack (AActor *actor); - // The Fighter's Axe -------------------------------------------------------- class AFWeapAxe : public AFighterWeapon @@ -68,7 +61,7 @@ FState *AFWeapAxe::GetAtkState (bool hold) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReady) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -95,7 +88,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReady) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReadyG) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -122,7 +115,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckReadyG) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUp) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -149,7 +142,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUp) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUpG) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -176,7 +169,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckUpG) DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckAtk) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; @@ -199,7 +192,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeCheckAtk) DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int power; diff --git a/src/g_hexen/a_fighterhammer.cpp b/src/g_hexen/a_fighterhammer.cpp index faa15d8af..84eca78b7 100644 --- a/src/g_hexen/a_fighterhammer.cpp +++ b/src/g_hexen/a_fighterhammer.cpp @@ -25,7 +25,7 @@ static FRandom pr_hammeratk ("FHammerAtk"); DEFINE_ACTION_FUNCTION(AActor, A_FHammerAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; @@ -95,7 +95,7 @@ hammerdone: DEFINE_ACTION_FUNCTION(AActor, A_FHammerThrow) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *mo; player_t *player; diff --git a/src/g_hexen/a_fighterplayer.cpp b/src/g_hexen/a_fighterplayer.cpp index ff4348520..7e1502a1c 100644 --- a/src/g_hexen/a_fighterplayer.cpp +++ b/src/g_hexen/a_fighterplayer.cpp @@ -99,7 +99,7 @@ static bool TryPunch(APlayerPawn *pmo, DAngle angle, int damage, int power) DEFINE_ACTION_FUNCTION(AActor, A_FPunchAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); int damage; int i; diff --git a/src/g_hexen/a_fighterquietus.cpp b/src/g_hexen/a_fighterquietus.cpp index c900794ed..8f73ef48e 100644 --- a/src/g_hexen/a_fighterquietus.cpp +++ b/src/g_hexen/a_fighterquietus.cpp @@ -78,7 +78,7 @@ int AFSwordMissile::DoSpecialDamage(AActor *victim, int damage, FName damagetype DEFINE_ACTION_FUNCTION(AActor, A_FSwordAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player; diff --git a/src/g_hexen/a_magecone.cpp b/src/g_hexen/a_magecone.cpp index f2b97fcd9..da53a829c 100644 --- a/src/g_hexen/a_magecone.cpp +++ b/src/g_hexen/a_magecone.cpp @@ -51,7 +51,7 @@ int AFrostMissile::DoSpecialDamage (AActor *victim, int damage, FName damagetype DEFINE_ACTION_FUNCTION(AActor, A_FireConePL1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; diff --git a/src/g_hexen/a_magelightning.cpp b/src/g_hexen/a_magelightning.cpp index 7e11b64ed..b06d22ce5 100644 --- a/src/g_hexen/a_magelightning.cpp +++ b/src/g_hexen/a_magelightning.cpp @@ -126,7 +126,7 @@ int ALightningZap::SpecialMissileHit (AActor *thing) DEFINE_ACTION_FUNCTION(AActor, A_LightningReady) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DoReadyWeapon(self); if (pr_lightningready() < 160) @@ -257,7 +257,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningZap) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MLightningAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS_DEF(floor, AActor); PARAM_CLASS_DEF(ceiling, AActor); diff --git a/src/g_hexen/a_magestaff.cpp b/src/g_hexen/a_magestaff.cpp index acef2e5cd..0b78bd279 100644 --- a/src/g_hexen/a_magestaff.cpp +++ b/src/g_hexen/a_magestaff.cpp @@ -122,7 +122,7 @@ void MStaffSpawn (AActor *pmo, DAngle angle, AActor *alttarget) DEFINE_ACTION_FUNCTION(AActor, A_MStaffAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; player_t *player; @@ -167,7 +167,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MStaffAttack) DEFINE_ACTION_FUNCTION(AActor, A_MStaffPalette) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { diff --git a/src/g_hexen/a_pig.cpp b/src/g_hexen/a_pig.cpp index a0a0cc844..41054da00 100644 --- a/src/g_hexen/a_pig.cpp +++ b/src/g_hexen/a_pig.cpp @@ -58,7 +58,7 @@ void APigPlayer::MorphPlayerThink () DEFINE_ACTION_FUNCTION(AActor, A_SnoutAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; diff --git a/src/g_strife/a_strifeweapons.cpp b/src/g_strife/a_strifeweapons.cpp index 3e9eb69b6..be8452046 100644 --- a/src/g_strife/a_strifeweapons.cpp +++ b/src/g_strife/a_strifeweapons.cpp @@ -94,7 +94,7 @@ void P_DaggerAlert (AActor *target, AActor *emitter) DEFINE_ACTION_FUNCTION(AActor, A_JabDagger) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DAngle angle; int damage; @@ -212,7 +212,7 @@ int APoisonBolt::DoSpecialDamage (AActor *target, int damage, FName damagetype) DEFINE_ACTION_FUNCTION(AActor, A_ClearFlash) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; @@ -231,7 +231,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ClearFlash) DEFINE_ACTION_FUNCTION(AActor, A_ShowElectricFlash) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != nullptr) { @@ -248,7 +248,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ShowElectricFlash) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireArrow) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS(ti, AActor); DAngle savedangle; @@ -307,7 +307,7 @@ void P_StrifeGunShot (AActor *mo, bool accurate, DAngle pitch) DEFINE_ACTION_FUNCTION(AActor, A_FireAssaultGun) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); bool accurate; @@ -343,7 +343,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireAssaultGun) DEFINE_ACTION_FUNCTION(AActor, A_FireMiniMissile) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; DAngle savedangle; @@ -413,7 +413,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlameDie) DEFINE_ACTION_FUNCTION(AActor, A_FireFlamer) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; @@ -450,7 +450,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireFlamer) DEFINE_ACTION_FUNCTION(AActor, A_FireMauler1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { @@ -494,7 +494,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMauler1) DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2Pre) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/mauler2charge", 1, ATTN_NORM); @@ -516,7 +516,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2Pre) DEFINE_ACTION_FUNCTION(AActor, A_FireMauler2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { @@ -688,7 +688,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Burnination) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireGrenade) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_CLASS(grenadetype, AActor); PARAM_ANGLE(angleofs); PARAM_STATE(flash) @@ -821,7 +821,7 @@ AInventory *ASigil::CreateCopy (AActor *other) DEFINE_ACTION_FUNCTION(AActor, A_SelectPiece) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); int pieces = MIN (static_cast(self)->NumPieces, 5); @@ -847,7 +847,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectPiece) DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilView) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DPSprite *pspr; int pieces; @@ -874,7 +874,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilView) DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilDown) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DPSprite *pspr; int pieces; @@ -904,7 +904,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilDown) DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilAttack) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); DPSprite *pspr; int pieces; @@ -927,7 +927,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SelectSigilAttack) DEFINE_ACTION_FUNCTION(AActor, A_SigilCharge) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); S_Sound (self, CHAN_WEAPON, "weapons/sigilcharge", 1, ATTN_NORM); if (self->player != NULL) @@ -945,7 +945,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SigilCharge) DEFINE_ACTION_FUNCTION(AActor, A_LightInverse) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { @@ -962,7 +962,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightInverse) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil1) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *spot; player_t *player = self->player; @@ -1007,7 +1007,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil1) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil2) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; @@ -1029,7 +1029,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil2) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil3) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *spot; player_t *player = self->player; @@ -1063,7 +1063,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil3) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil4) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); AActor *spot; player_t *player = self->player; @@ -1103,7 +1103,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSigil4) DEFINE_ACTION_FUNCTION(AActor, A_FireSigil5) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 74d828d55..b6ecb5cf8 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -4643,7 +4643,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckForReload) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if ( self->player == NULL || self->player->ReadyWeapon == NULL ) { @@ -4696,7 +4696,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckForReload) DEFINE_ACTION_FUNCTION(AActor, A_ResetReloadCounter) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player == NULL || self->player->ReadyWeapon == NULL) return 0; diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index 56562ab21..4938063ec 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -753,7 +753,7 @@ void DoReadyWeapon(AActor *self) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_WeaponReady) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT_DEF(flags); DoReadyWeaponToSwitch(self, !(flags & WRF_NoSwitch)); @@ -885,7 +885,7 @@ static void P_CheckWeaponButtons (player_t *player) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_ReFire) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_STATE_DEF(state); A_ReFire(self, state); return 0; @@ -923,7 +923,7 @@ void A_ReFire(AActor *self, FState *state) DEFINE_ACTION_FUNCTION(AInventory, A_ClearReFire) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; if (NULL != player) @@ -945,7 +945,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_ClearReFire) DEFINE_ACTION_FUNCTION(AInventory, A_CheckReload) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self->player != NULL) { @@ -1133,7 +1133,7 @@ DEFINE_ACTION_FUNCTION(AActor, OverlayID) DEFINE_ACTION_FUNCTION(AInventory, A_Lower) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); player_t *player = self->player; DPSprite *psp; @@ -1181,7 +1181,7 @@ DEFINE_ACTION_FUNCTION(AInventory, A_Lower) DEFINE_ACTION_FUNCTION(AInventory, A_Raise) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); if (self == nullptr) { @@ -1293,7 +1293,7 @@ enum GF_Flags DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_GunFlash) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_STATE_DEF(flash); PARAM_INT_DEF(flags); @@ -1381,42 +1381,9 @@ void P_GunShot (AActor *mo, bool accurate, PClassActor *pufftype, DAngle pitch) P_LineAttack (mo, angle, PLAYERMISSILERANGE, pitch, damage, NAME_Hitscan, pufftype); } -DEFINE_ACTION_FUNCTION(AInventory, A_Light0) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (self->player != NULL) - { - self->player->extralight = 0; - } - return 0; -} - -DEFINE_ACTION_FUNCTION(AInventory, A_Light1) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (self->player != NULL) - { - self->player->extralight = 1; - } - return 0; -} - -DEFINE_ACTION_FUNCTION(AInventory, A_Light2) -{ - PARAM_SELF_PROLOGUE(AActor); - - if (self->player != NULL) - { - self->player->extralight = 2; - } - return 0; -} - DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_Light) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT(light); if (self->player != NULL) diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 8543326cf..cbe9183e2 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6007,6 +6007,24 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) PFunction *afd = FindClassMemberFunction(ctx.Class, ctx.Class, MethodName, ScriptPosition, &error); + // Action functions in state providers need special treatment because self is of type Actor here. + if (afd != nullptr && ctx.Class->IsDescendantOf(RUNTIME_CLASS(AStateProvider)) && (ctx.Function->Variants[0].Flags & VARF_Action)) + { + // Only accept static and action functions from the current class. Calling a member function will require explicit use of 'invoker'. + if ((afd->Variants[0].Flags & (VARF_Method|VARF_Action)) == VARF_Method) + { + // Everything else that may be used here must pass the selfclass check, i.e. it must be reachable from Actor. + // Note that FuncClass is still the current item because for symbol privacy checks this is relevant. + afd = FindClassMemberFunction(ctx.Function->Variants[0].SelfClass, ctx.Class, MethodName, ScriptPosition, &error); + if (afd == nullptr) + { + ScriptPosition.Message(MSG_ERROR, "Unable to call non-action function %s from here. Please use 'invoker.%s' to call it.", MethodName.GetChars(), MethodName.GetChars()); + delete this; + return nullptr; + } + } + } + if (error) { delete this; @@ -6306,7 +6324,7 @@ FxExpression *FxMemberFunctionCall::Resolve(FCompileContext& ctx) isresolved: bool error = false; - PFunction *afd = FindClassMemberFunction(cls, cls, MethodName, ScriptPosition, &error); + PFunction *afd = FindClassMemberFunction(cls, ctx.Class, MethodName, ScriptPosition, &error); if (error) { delete this; diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index c5ac21783..7e0af9ee4 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2317,7 +2317,14 @@ FxExpression *ZCCCompiler::SetupActionFunction(PClass *cls, ZCC_TreeNode *af) { FArgumentList argumentlist; // We can use this function directly without wrapping it in a caller. - return new FxVMFunctionCall(new FxSelf(*af), afd, argumentlist, *af, false); + if ((afd->Variants[0].Flags & VARF_Action) || !cls->IsDescendantOf(RUNTIME_CLASS(AStateProvider)) || !afd->Variants[0].SelfClass->IsDescendantOf(RUNTIME_CLASS(AStateProvider))) + { + return new FxVMFunctionCall(new FxSelf(*af), afd, argumentlist, *af, false); + } + else + { + Error(af, "Cannot use non-action function %s here.", FName(id->Identifier).GetChars()); + } } } else diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 48b5f7ded..7634ccaea 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -317,7 +317,6 @@ class Actor : Thinker native native void A_Countdown(); native void A_AlertMonsters(float maxdist = 0, int flags = 0); native void A_ClearSoundTarget(); - native void A_FireAssaultGun(); native void A_CheckTerrain(); deprecated native void A_MissileAttack(); diff --git a/wadsrc/static/zscript/heretic/chicken.txt b/wadsrc/static/zscript/heretic/chicken.txt index 77e2b0a92..2e5ada81c 100644 --- a/wadsrc/static/zscript/heretic/chicken.txt +++ b/wadsrc/static/zscript/heretic/chicken.txt @@ -26,8 +26,8 @@ class Beak : Weapon Weapon.SisterWeapon "BeakPowered"; } - native void A_BeakRaise (); - native void A_BeakAttackPL1(); + action native void A_BeakRaise (); + action native void A_BeakAttackPL1(); States { @@ -55,7 +55,7 @@ class BeakPowered : Beak Weapon.SisterWeapon "Beak"; } - native void A_BeakAttackPL2(); + action native void A_BeakAttackPL2(); States { diff --git a/wadsrc/static/zscript/heretic/hereticweaps.txt b/wadsrc/static/zscript/heretic/hereticweaps.txt index ae5e97179..4c254500b 100644 --- a/wadsrc/static/zscript/heretic/hereticweaps.txt +++ b/wadsrc/static/zscript/heretic/hereticweaps.txt @@ -23,7 +23,7 @@ class Staff : HereticWeapon Tag "$TAG_STAFF"; } - native void A_StaffAttack (int damage, class puff); + action native void A_StaffAttack (int damage, class puff); States { @@ -142,7 +142,7 @@ class GoldWand : HereticWeapon Tag "$TAG_GOLDWAND"; } - native void A_FireGoldWandPL1 (); + action native void A_FireGoldWandPL1 (); States { @@ -178,7 +178,7 @@ class GoldWandPowered : GoldWand Tag "$TAG_GOLDWANDP"; } - native void A_FireGoldWandPL2 (); + action native void A_FireGoldWandPL2 (); States { @@ -294,7 +294,7 @@ class Crossbow : HereticWeapon Tag "$TAG_CROSSBOW"; } - native void A_FireCrossbowPL1 (); + action native void A_FireCrossbowPL1 (); States { @@ -330,7 +330,7 @@ class CrossbowPowered : Crossbow Tag "$TAG_CROSSBOWP"; } - native void A_FireCrossbowPL2(); + action native void A_FireCrossbowPL2(); States { @@ -462,7 +462,7 @@ class Gauntlets : Weapon Obituary "$OB_MPGAUNTLETS"; } - native void A_GauntletAttack (int power); + action native void A_GauntletAttack (int power); States { @@ -574,7 +574,7 @@ class Mace : HereticWeapon Tag "$TAG_MACE"; } - native void A_FireMacePL1(); + action native void A_FireMacePL1(); States { @@ -611,7 +611,7 @@ class MacePowered : Mace Tag "$TAG_MACEP"; } - native void A_FireMacePL2(); + action native void A_FireMacePL2(); States { @@ -778,7 +778,7 @@ class Blaster : HereticWeapon Obituary "$OB_MPBLASTER"; } - native void A_FireBlasterPL1(); + action native void A_FireBlasterPL1(); States { @@ -950,7 +950,7 @@ class SkullRod : HereticWeapon Tag "$TAG_SKULLROD"; } - native void A_FireSkullRodPL1(); + action native void A_FireSkullRodPL1(); States { @@ -984,7 +984,7 @@ class SkullRodPowered : SkullRod Tag "$TAG_SKULLRODP"; } - native void A_FireSkullRodPL2(); + action native void A_FireSkullRodPL2(); States { @@ -1140,7 +1140,7 @@ class PhoenixRod : Weapon native Tag "$TAG_PHOENIXROD"; } - native void A_FirePhoenixPL1(); + action native void A_FirePhoenixPL1(); States { @@ -1176,9 +1176,9 @@ class PhoenixRodPowered : PhoenixRod native Tag "$TAG_PHOENIXRODP"; } - native void A_InitPhoenixPL2(); - native void A_FirePhoenixPL2(); - native void A_ShutdownPhoenixPL2(); + action native void A_InitPhoenixPL2(); + action native void A_FirePhoenixPL2(); + action native void A_ShutdownPhoenixPL2(); States { diff --git a/wadsrc/static/zscript/hexen/clericflame.txt b/wadsrc/static/zscript/hexen/clericflame.txt index e72496530..13fca8ad1 100644 --- a/wadsrc/static/zscript/hexen/clericflame.txt +++ b/wadsrc/static/zscript/hexen/clericflame.txt @@ -16,7 +16,7 @@ class CWeapFlame : ClericWeapon Tag "$TAG_CWEAPFLAME"; } - native void A_CFlameAttack(); + action native void A_CFlameAttack(); States { diff --git a/wadsrc/static/zscript/hexen/clericholy.txt b/wadsrc/static/zscript/hexen/clericholy.txt index 6fc9cf43d..1a4372f4d 100644 --- a/wadsrc/static/zscript/hexen/clericholy.txt +++ b/wadsrc/static/zscript/hexen/clericholy.txt @@ -96,8 +96,8 @@ class CWeapWraithverge : ClericWeapon native Inventory.PickupSound "WeaponBuild"; } - native void A_CHolyAttack(); - native void A_CHolyPalette(); + action native void A_CHolyAttack(); + action native void A_CHolyPalette(); States { diff --git a/wadsrc/static/zscript/hexen/clericmace.txt b/wadsrc/static/zscript/hexen/clericmace.txt index b47974d4b..5e00b9c3b 100644 --- a/wadsrc/static/zscript/hexen/clericmace.txt +++ b/wadsrc/static/zscript/hexen/clericmace.txt @@ -13,7 +13,7 @@ class CWeapMace : ClericWeapon Tag "$TAG_CWEAPMACE"; } - native void A_CMaceAttack(); + action native void A_CMaceAttack(); States { diff --git a/wadsrc/static/zscript/hexen/clericstaff.txt b/wadsrc/static/zscript/hexen/clericstaff.txt index c33f14a80..7ae0e9da3 100644 --- a/wadsrc/static/zscript/hexen/clericstaff.txt +++ b/wadsrc/static/zscript/hexen/clericstaff.txt @@ -16,10 +16,10 @@ class CWeapStaff : ClericWeapon Tag "$TAG_CWEAPSTAFF"; } - native void A_CStaffInitBlink(); - native void A_CStaffCheckBlink(); - native void A_CStaffCheck(); - native void A_CStaffAttack(); + action native void A_CStaffInitBlink(); + action native void A_CStaffCheckBlink(); + action native void A_CStaffCheck(); + action native void A_CStaffAttack(); States { diff --git a/wadsrc/static/zscript/hexen/fighteraxe.txt b/wadsrc/static/zscript/hexen/fighteraxe.txt index 436172bef..30b235192 100644 --- a/wadsrc/static/zscript/hexen/fighteraxe.txt +++ b/wadsrc/static/zscript/hexen/fighteraxe.txt @@ -17,12 +17,12 @@ class FWeapAxe : FighterWeapon native Tag "$TAG_FWEAPAXE"; } - native void A_FAxeCheckUp(); - native void A_FAxeCheckReady(); - native void A_FAxeCheckAtk(); - native void A_FAxeAttack(); - native void A_FAxeCheckUpG(); - native void A_FAxeCheckReadyG(); + action native void A_FAxeCheckUp(); + action native void A_FAxeCheckReady(); + action native void A_FAxeCheckAtk(); + action native void A_FAxeAttack(); + action native void A_FAxeCheckUpG(); + action native void A_FAxeCheckReadyG(); States { diff --git a/wadsrc/static/zscript/hexen/fighterfist.txt b/wadsrc/static/zscript/hexen/fighterfist.txt index e556ebd87..8428ebe7d 100644 --- a/wadsrc/static/zscript/hexen/fighterfist.txt +++ b/wadsrc/static/zscript/hexen/fighterfist.txt @@ -13,7 +13,7 @@ class FWeapFist : FighterWeapon Tag "$TAG_FWEAPFIST"; } - native void A_FPunchAttack(); + action native void A_FPunchAttack(); States { diff --git a/wadsrc/static/zscript/hexen/fighterhammer.txt b/wadsrc/static/zscript/hexen/fighterhammer.txt index 0104c7670..f415cbb72 100644 --- a/wadsrc/static/zscript/hexen/fighterhammer.txt +++ b/wadsrc/static/zscript/hexen/fighterhammer.txt @@ -18,8 +18,8 @@ class FWeapHammer : FighterWeapon Tag "$TAG_FWEAPHAMMER"; } - native void A_FHammerAttack(); - native void A_FHammerThrow(); + action native void A_FHammerAttack(); + action native void A_FHammerThrow(); States { diff --git a/wadsrc/static/zscript/hexen/fighterquietus.txt b/wadsrc/static/zscript/hexen/fighterquietus.txt index 2430cd70c..7c94f7901 100644 --- a/wadsrc/static/zscript/hexen/fighterquietus.txt +++ b/wadsrc/static/zscript/hexen/fighterquietus.txt @@ -97,7 +97,7 @@ class FWeapQuietus : FighterWeapon Tag "$TAG_FWEAPQUIETUS"; } - native void A_FSwordAttack(); + action native void A_FSwordAttack(); States { diff --git a/wadsrc/static/zscript/hexen/magecone.txt b/wadsrc/static/zscript/hexen/magecone.txt index 471b5b0b7..a9f2d29dc 100644 --- a/wadsrc/static/zscript/hexen/magecone.txt +++ b/wadsrc/static/zscript/hexen/magecone.txt @@ -17,7 +17,7 @@ class MWeapFrost : MageWeapon Tag "$TAG_MWEAPFROST"; } - native void A_FireConePL1(); + action native void A_FireConePL1(); States { diff --git a/wadsrc/static/zscript/hexen/magelightning.txt b/wadsrc/static/zscript/hexen/magelightning.txt index 46687e813..154776d15 100644 --- a/wadsrc/static/zscript/hexen/magelightning.txt +++ b/wadsrc/static/zscript/hexen/magelightning.txt @@ -16,8 +16,8 @@ class MWeapLightning : MageWeapon Tag "$TAG_MWEAPLIGHTNING"; } - native void A_LightningReady(); - native void A_MLightningAttack(class floor = "LightningFloor", class ceiling = "LightningCeiling"); + action native void A_LightningReady(); + action native void A_MLightningAttack(class floor = "LightningFloor", class ceiling = "LightningCeiling"); States { diff --git a/wadsrc/static/zscript/hexen/magestaff.txt b/wadsrc/static/zscript/hexen/magestaff.txt index 9338febe6..c11542834 100644 --- a/wadsrc/static/zscript/hexen/magestaff.txt +++ b/wadsrc/static/zscript/hexen/magestaff.txt @@ -97,8 +97,8 @@ class MWeapBloodscourge : MageWeapon native Tag "$TAG_MWEAPBLOODSCOURGE"; } - native void A_MStaffAttack(); - native void A_MStaffPalette(); + action native void A_MStaffAttack(); + action native void A_MStaffPalette(); States { diff --git a/wadsrc/static/zscript/hexen/pig.txt b/wadsrc/static/zscript/hexen/pig.txt index 6362ff36e..8fa446882 100644 --- a/wadsrc/static/zscript/hexen/pig.txt +++ b/wadsrc/static/zscript/hexen/pig.txt @@ -34,7 +34,7 @@ class Snout : Weapon Weapon.YAdjust 10; } - native void A_SnoutAttack (); + action native void A_SnoutAttack (); States { diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index 4a9cde740..fc037d13f 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -46,20 +46,22 @@ class StateProvider : Inventory native action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); action native void A_RailAttack(int damage, int spawnofs_xy = 0, bool useammo = true, color color1 = 0, color color2 = 0, int flags = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = "none", float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); - native void A_Light(int extralight); - native void A_Light0(); - native void A_Light1(); - native void A_Light2(); - native void A_LightInverse(); - native void A_WeaponReady(int flags = 0); - native void A_Lower(); - native void A_Raise(); + native action void A_Light(int extralight); + action void A_Light0() { A_Light(0); } + action void A_Light1() { A_Light(1); } + action void A_Light2() { A_Light(2); } + action native void A_LightInverse(); + action native void A_WeaponReady(int flags = 0); + action native void A_Lower(); + action native void A_Raise(); action native void A_FirePistol(); action native void A_FireShotgun(); action native void A_FireShotgun2(); - native void A_OpenShotgun2(); - native void A_LoadShotgun2(); - native void A_CloseShotgun2(); + + action void A_OpenShotgun2() { A_PlaySound("weapons/sshoto", CHAN_WEAPON); } + action void A_LoadShotgun2() { A_PlaySound("weapons/sshotl", CHAN_WEAPON); } + action void A_CloseShotgun2() { A_PlaySound("weapons/sshotc", CHAN_WEAPON); } + action native void A_FireCGun(); action native void A_FireSTGrenade(class grenadetype = "Grenade"); action native void A_FireMissile(); @@ -67,17 +69,18 @@ class StateProvider : Inventory native action native void A_FireRailgun(); action native void A_FireRailgunLeft(); action native void A_FireRailgunRight(); - native void A_RailWait(); - native void A_BFGsound(); + action void A_RailWait() {} + action void A_BFGsound() { A_PlaySound("weapons/bfgf", CHAN_WEAPON); } action native void A_FireBFG(); action native void A_FireOldBFG(); - native void A_ReFire(state flash = null); - native void A_ClearReFire(); - native void A_CheckReload(); - native void A_GunFlash(state flash = null, int flags = 0); + action native void A_ReFire(state flash = null); + action native void A_ClearReFire(); + action native void A_CheckReload(); + action native void A_GunFlash(state flash = null, int flags = 0); + action native void A_FireAssaultGun(); action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); - native state A_CheckForReload(int counter, state label, bool dontincrement = false); - native void A_ResetReloadCounter(); + action native state A_CheckForReload(int counter, state label, bool dontincrement = false); + action native void A_ResetReloadCounter(); } class ScoreItem : Inventory native diff --git a/wadsrc/static/zscript/strife/sigil.txt b/wadsrc/static/zscript/strife/sigil.txt index dab1db2f5..d8b1f80f8 100644 --- a/wadsrc/static/zscript/strife/sigil.txt +++ b/wadsrc/static/zscript/strife/sigil.txt @@ -16,16 +16,16 @@ class Sigil : Weapon native Inventory.PickupMessage "$TXT_SIGIL"; } - native void A_SelectPiece (); - native void A_SelectSigilView (); - native void A_SelectSigilDown (); - native void A_SelectSigilAttack (); - native void A_SigilCharge (); - native void A_FireSigil1 (); - native void A_FireSigil2 (); - native void A_FireSigil3 (); - native void A_FireSigil4 (); - native void A_FireSigil5 (); + action native void A_SelectPiece (); + action native void A_SelectSigilView (); + action native void A_SelectSigilDown (); + action native void A_SelectSigilAttack (); + action native void A_SigilCharge (); + action native void A_FireSigil1 (); + action native void A_FireSigil2 (); + action native void A_FireSigil3 (); + action native void A_FireSigil4 (); + action native void A_FireSigil5 (); States { diff --git a/wadsrc/static/zscript/strife/strifeweapons.txt b/wadsrc/static/zscript/strife/strifeweapons.txt index bf94706c9..178b2b27a 100644 --- a/wadsrc/static/zscript/strife/strifeweapons.txt +++ b/wadsrc/static/zscript/strife/strifeweapons.txt @@ -62,7 +62,7 @@ class PunchDagger : StrifeWeapon Tag "$TAG_PUNCHDAGGER"; } - native void A_JabDagger (); + action native void A_JabDagger (); States { @@ -184,9 +184,9 @@ class StrifeCrossbow : StrifeWeapon Inventory.Icon "CBOWA0"; } - native void A_ClearFlash (); - native void A_ShowElectricFlash (); - native void A_FireArrow (class proj); + action native void A_ClearFlash (); + action native void A_ShowElectricFlash (); + action native void A_FireArrow (class proj); States { @@ -331,7 +331,7 @@ class MiniMissileLauncher : StrifeWeapon Inventory.PickupMessage "$TXT_MMLAUNCHER"; } - native void A_FireMiniMissile (); + action native void A_FireMiniMissile (); States { @@ -446,7 +446,7 @@ class FlameThrower : StrifeWeapon Inventory.PickupMessage "$TXT_FLAMER"; } - native void A_FireFlamer (); + action native void A_FireFlamer (); States { @@ -528,7 +528,7 @@ class Mauler : StrifeWeapon Obituary "$OB_MPMAULER1"; } - native void A_FireMauler1 (); + action native void A_FireMauler1 (); States { @@ -571,8 +571,8 @@ class Mauler2 : Mauler Tag "$TAG_MAULER2"; } - native void A_FireMauler2Pre (); - native void A_FireMauler2 (); + action native void A_FireMauler2Pre (); + action native void A_FireMauler2 (); States { @@ -816,7 +816,7 @@ class StrifeGrenadeLauncher : StrifeWeapon Inventory.PickupMessage "$TXT_GLAUNCHER"; } - native void A_FireGrenade (class grenadetype, float angleofs, state flash); + action native void A_FireGrenade (class grenadetype, float angleofs, state flash); States { From 1e6a632774f5db7e604362ab0963c30fe68304e9 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Sun, 13 Nov 2016 14:48:27 +0100 Subject: [PATCH 244/255] - copy the Unsafe flag to the actual function. This must have gotten lost during the merge between my own code and Leonard2's fix. Now even in DECORATE it is possible to report most cases in which user variables are accessed from non-item states as an error. This will report all states which can be traced by a direct link from a special state label. It will not find states that only get used via A_Jump etc. --- src/scripting/vm/vmbuilder.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/scripting/vm/vmbuilder.cpp b/src/scripting/vm/vmbuilder.cpp index acb67e2f5..19d89fc6f 100644 --- a/src/scripting/vm/vmbuilder.cpp +++ b/src/scripting/vm/vmbuilder.cpp @@ -762,6 +762,7 @@ void FFunctionBuildList::Build() codesize += sfunc->CodeSize; } sfunc->PrintableName = item.PrintableName; + sfunc->Unsafe = ctx.Unsafe; } delete item.Code; if (dump != nullptr) From ac86a535e7c3c7899c70519a9b22714141ca5b46 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 14:12:27 +0100 Subject: [PATCH 245/255] - fixed: State labels were resolved in the calling function's context instead of the called function one's. This could cause problems with functions that take states as parameters but use them to set them internally instead of passing them through the A_Jump interface back to the caller, like A_Chase or A_LookEx. This required some quite significant refactoring because the entire state resolution logic had been baked into the compiler which turned out to be a major maintenance problem. Fixed this by adding a new builtin type 'statelabel'. This is an opaque identifier representing a state, with the actual data either directly encoded into the number for single label state or an index into a state information table. The state resolution is now the task of the called function as it should always have remained. Note, that this required giving back the 'action' qualifier to most state jumping functions. - refactored most A_Jump checkers to a two stage setup with a pure checker that returns a boolean and a scripted A_Jump wrapper, for some simpler checks the checker function was entirely omitted and calculated inline in the A_Jump function. It is strongly recommended to use the boolean checkers unless using an inline function invocation in a state as they lead to vastly clearer code and offer more flexibility. - let Min() and Max() use the OP_MIN and OP_MAX opcodes. Although these were present, these function were implemented using some grossly inefficient branching tests. - the DECORATE 'state' cast kludge will now actually call ResolveState because a state label is not a state and needs conversion. --- src/d_dehacked.cpp | 2 +- src/dobjtype.cpp | 29 +- src/dobjtype.h | 14 +- src/info.h | 38 ++ src/namedef.h | 4 +- src/p_actionfunctions.cpp | 429 +++--------------- src/p_mobj.cpp | 4 +- src/p_pspr.cpp | 19 +- src/p_pspr.h | 1 + src/p_states.cpp | 90 ++++ src/scripting/codegeneration/codegen.cpp | 273 +++-------- src/scripting/codegeneration/codegen.h | 8 +- src/scripting/decorate/thingdef_parse.cpp | 5 +- src/scripting/decorate/thingdef_states.cpp | 7 +- src/scripting/vm/vm.h | 12 +- src/scripting/zscript/zcc_compile.cpp | 10 +- wadsrc/static/zscript.txt | 1 + wadsrc/static/zscript/actor.txt | 47 +- wadsrc/static/zscript/actor_checks.txt | 274 +++++++++++ wadsrc/static/zscript/doom/bossbrain.txt | 2 +- wadsrc/static/zscript/heretic/hereticimp.txt | 2 +- wadsrc/static/zscript/hexen/bats.txt | 2 +- wadsrc/static/zscript/hexen/bishop.txt | 4 +- wadsrc/static/zscript/shared/inventory.txt | 8 +- .../static/zscript/strife/strifeweapons.txt | 2 +- 25 files changed, 641 insertions(+), 646 deletions(-) create mode 100644 wadsrc/static/zscript/actor_checks.txt diff --git a/src/d_dehacked.cpp b/src/d_dehacked.cpp index eef9b137a..880cd7dfe 100644 --- a/src/d_dehacked.cpp +++ b/src/d_dehacked.cpp @@ -1494,7 +1494,7 @@ static int PatchFrame (int frameNum) DEFINE_ACTION_FUNCTION(AActor, isDEHState) { PARAM_PROLOGUE; - PARAM_STATE(state); + PARAM_POINTER(state, FState); ACTION_RETURN_BOOL(state != nullptr && (state->DefineFlags & SDF_DEHACKED)); } diff --git a/src/dobjtype.cpp b/src/dobjtype.cpp index f3fda2b14..2c88da92a 100644 --- a/src/dobjtype.cpp +++ b/src/dobjtype.cpp @@ -82,6 +82,7 @@ PName *TypeName; PSound *TypeSound; PColor *TypeColor; PStatePointer *TypeState; +PStateLabel *TypeStateLabel; PStruct *TypeVector2; PStruct *TypeVector3; PPointer *TypeNullPtr; @@ -546,7 +547,8 @@ void PType::StaticInit() RUNTIME_CLASS(PPrototype)->TypeTableType = RUNTIME_CLASS(PPrototype); RUNTIME_CLASS(PClass)->TypeTableType = RUNTIME_CLASS(PClass); RUNTIME_CLASS(PStatePointer)->TypeTableType = RUNTIME_CLASS(PStatePointer); - + RUNTIME_CLASS(PStateLabel)->TypeTableType = RUNTIME_CLASS(PStateLabel); + // Create types and add them type the type table. TypeTable.AddType(TypeError = new PErrorType); TypeTable.AddType(TypeVoid = new PVoidType); @@ -564,6 +566,7 @@ void PType::StaticInit() TypeTable.AddType(TypeSound = new PSound); TypeTable.AddType(TypeColor = new PColor); TypeTable.AddType(TypeState = new PStatePointer); + TypeTable.AddType(TypeStateLabel = new PStateLabel); TypeTable.AddType(TypeNullPtr = new PPointer); TypeVector2 = new PStruct(NAME_Vector2, nullptr); @@ -701,7 +704,7 @@ IMPLEMENT_CLASS(PInt, false, false, false, false) //========================================================================== PInt::PInt() -: PBasicType(4, 4), Unsigned(false) +: PBasicType(4, 4), Unsigned(false), IntCompatible(true) { mDescriptiveName = "SInt32"; Symbols.AddSymbol(new PSymbolConstNumeric(NAME_Min, this, -0x7FFFFFFF - 1)); @@ -715,8 +718,8 @@ PInt::PInt() // //========================================================================== -PInt::PInt(unsigned int size, bool unsign) -: PBasicType(size, size), Unsigned(unsign) +PInt::PInt(unsigned int size, bool unsign, bool compatible) +: PBasicType(size, size), Unsigned(unsign), IntCompatible(compatible) { mDescriptiveName.Format("%cInt%d", unsign? 'U':'S', size); @@ -1308,7 +1311,7 @@ IMPLEMENT_CLASS(PName, false, false, false, false) //========================================================================== PName::PName() -: PInt(sizeof(FName), true) +: PInt(sizeof(FName), true, false) { mDescriptiveName = "Name"; assert(sizeof(FName) == __alignof(FName)); @@ -1414,6 +1417,22 @@ PColor::PColor() assert(sizeof(PalEntry) == __alignof(PalEntry)); } +/* PStateLabel *****************************************************************/ + +IMPLEMENT_CLASS(PStateLabel, false, false, false, false) + +//========================================================================== +// +// PStateLabel Default Constructor +// +//========================================================================== + +PStateLabel::PStateLabel() + : PInt(sizeof(int), false, false) +{ + mDescriptiveName = "StateLabel"; +} + /* PStatePointer **********************************************************/ IMPLEMENT_CLASS(PStatePointer, false, false, false, false) diff --git a/src/dobjtype.h b/src/dobjtype.h index e1bfd0796..1ca5df832 100644 --- a/src/dobjtype.h +++ b/src/dobjtype.h @@ -227,6 +227,7 @@ public: PType(unsigned int size = 1, unsigned int align = 1); virtual ~PType(); + virtual bool isNumeric() { return false; } bool AddConversion(PType *target, void (*convertconst)(ZCC_ExprConstant *, class FSharedStringArena &)); @@ -417,7 +418,7 @@ class PInt : public PBasicType { DECLARE_CLASS(PInt, PBasicType); public: - PInt(unsigned int size, bool unsign); + PInt(unsigned int size, bool unsign, bool compatible = true); void WriteValue(FSerializer &ar, const char *key,const void *addr) const override; bool ReadValue(FSerializer &ar, const char *key,void *addr) const override; @@ -426,8 +427,10 @@ public: virtual void SetValue(void *addr, double val); virtual int GetValueInt(void *addr) const; virtual double GetValueFloat(void *addr) const; + virtual bool isNumeric() override { return IntCompatible; } bool Unsigned; + bool IntCompatible; protected: PInt(); void SetOps(); @@ -453,6 +456,7 @@ public: virtual void SetValue(void *addr, double val); virtual int GetValueInt(void *addr) const; virtual double GetValueFloat(void *addr) const; + virtual bool isNumeric() override { return true; } protected: PFloat(); void SetOps(); @@ -516,6 +520,13 @@ public: PColor(); }; +class PStateLabel : public PInt +{ + DECLARE_CLASS(PStateLabel, PInt); +public: + PStateLabel(); +}; + // Pointers ----------------------------------------------------------------- class PStatePointer : public PBasicType @@ -903,6 +914,7 @@ extern PColor *TypeColor; extern PStruct *TypeVector2; extern PStruct *TypeVector3; extern PStatePointer *TypeState; +extern PStateLabel *TypeStateLabel; extern PPointer *TypeNullPtr; // A constant value --------------------------------------------------------- diff --git a/src/info.h b/src/info.h index 6aee02bed..e198bb26c 100644 --- a/src/info.h +++ b/src/info.h @@ -313,6 +313,44 @@ struct FDoomEdEntry int Args[5]; }; +struct FStateLabelStorage +{ + TArray Storage; + + int AddPointer(FState *ptr) + { + if (ptr != nullptr) + { + int pos = Storage.Reserve(sizeof(ptr) + sizeof(int)); + memset(&Storage[pos], 0, sizeof(int)); + memcpy(&Storage[pos + sizeof(int)], &ptr, sizeof(ptr)); + return pos / 4 + 1; + } + else return 0; + } + + int AddNames(TArray &names) + { + int siz = names.Size(); + if (siz > 1) + { + int pos = Storage.Reserve(sizeof(int) + sizeof(FName) * names.Size()); + memcpy(&Storage[pos], &siz, sizeof(int)); + memcpy(&Storage[pos + sizeof(int)], &names[0], sizeof(FName) * names.Size()); + return pos / 4 + 1; + } + else + { + // don't store single name states in the array. + return names[0].GetIndex() + 0x10000000; + } + } + + FState *GetState(int pos, PClassActor *cls); +}; + +extern FStateLabelStorage StateLabels; + enum ESpecialMapthings { SMT_Player1Start = 1, diff --git a/src/namedef.h b/src/namedef.h index 8f1a54337..ee7d08f40 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -730,10 +730,10 @@ xx(stateinfo) xx(__decorate_internal_int__) xx(__decorate_internal_bool__) -xx(__decorate_internal_state__) xx(__decorate_internal_float__) +xx(ResolveState) xx(DamageFunction) xx(Length) xx(Unit) -xx(A_Jump) \ No newline at end of file +xx(StateLabel) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index b6ecb5cf8..9440dc0d6 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -715,7 +715,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, CountProximity) //=========================================================================== // -// __decorate_internal_state__ // __decorate_internal_int__ // __decorate_internal_bool__ // __decorate_internal_float__ @@ -725,13 +724,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, CountProximity) // //=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, __decorate_internal_state__) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(returnme); - ACTION_RETURN_STATE(returnme); -} - DEFINE_ACTION_FUNCTION_PARAMS(AActor, __decorate_internal_int__) { PARAM_SELF_PROLOGUE(AActor); @@ -1158,7 +1150,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BulletAttack) //========================================================================== DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Jump) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT(maxchance); paramnum++; // Increment paramnum to point at the first jump target @@ -1166,7 +1158,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Jump) if (count > 0 && (maxchance >= 256 || pr_cajump() < maxchance)) { int jumpnum = (count == 1 ? 0 : (pr_cajump() % count)); - PARAM_STATE_AT(paramnum + jumpnum, jumpto); + PARAM_STATE_ACTION_AT(paramnum + jumpnum, jumpto); ACTION_RETURN_STATE(jumpto); } ACTION_RETURN_STATE(NULL); @@ -1177,137 +1169,22 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Jump) // State jump function // //========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfHealthLower) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_INT (health); - PARAM_STATE (jump); - PARAM_INT_DEF (ptr_selector); - AActor *measured; - - measured = COPY_AAPTR(self, ptr_selector); - - if (measured != NULL && measured->health < health) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - -//========================================================================== -// -// State jump function -// -//========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetOutsideMeleeRange) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); - - if (!self->CheckMeleeRange()) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - -//========================================================================== -// -// State jump function -// -//========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInsideMeleeRange) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); - - if (self->CheckMeleeRange()) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - -//========================================================================== -// -// State jump function -// -//========================================================================== -static int DoJumpIfCloser(AActor *target, VM_ARGS) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_FLOAT (dist); - PARAM_STATE (jump); - PARAM_BOOL_DEF(noz); - - if (!target) - { // No target - no jump - ACTION_RETURN_STATE(NULL); - } - if (self->Distance2D(target) < dist && - (noz || - ((self->Z() > target->Z() && self->Z() - target->Top() < dist) || - (self->Z() <= target->Z() && target->Z() - self->Top() < dist)))) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfCloser) -{ - PARAM_SELF_PROLOGUE(AActor); - - AActor *target; - - if (self->player == NULL) - { - target = self->target; - } - else - { - // Does the player aim at something that can be shot? - FTranslatedLineTarget t; - P_BulletSlope(self, &t, ALF_PORTALRESTRICT); - target = t.linetarget; - } - return DoJumpIfCloser(target, VM_ARGS_NAMES); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTracerCloser) -{ - PARAM_SELF_PROLOGUE(AActor); - return DoJumpIfCloser(self->tracer, VM_ARGS_NAMES); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfMasterCloser) -{ - PARAM_SELF_PROLOGUE(AActor); - return DoJumpIfCloser(self->master, VM_ARGS_NAMES); -} - -//========================================================================== -// -// State jump function -// -//========================================================================== -int DoJumpIfInventory(AActor *owner, VM_ARGS) +DEFINE_ACTION_FUNCTION(AActor, CheckInventory) { PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS (itemtype, AInventory); PARAM_INT (itemamount); - PARAM_STATE (label); - PARAM_INT_DEF (setowner) { setowner = AAPTR_DEFAULT; } + PARAM_INT_DEF (setowner); - if (itemtype == NULL) + if (itemtype == nullptr) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } - owner = COPY_AAPTR(owner, setowner); - if (owner == NULL) + AActor *owner = COPY_AAPTR(self, setowner); + if (owner == nullptr) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } AInventory *item = owner->FindInventory(itemtype); @@ -1318,48 +1195,32 @@ int DoJumpIfInventory(AActor *owner, VM_ARGS) { if (item->Amount >= itemamount) { - ACTION_RETURN_STATE(label); + ACTION_RETURN_BOOL(true); } } else if (item->Amount >= item->MaxAmount) { - ACTION_RETURN_STATE(label); + ACTION_RETURN_BOOL(true); } } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInventory) -{ - PARAM_SELF_PROLOGUE(AActor); - return DoJumpIfInventory(self, VM_ARGS_NAMES); -} - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetInventory) -{ - PARAM_SELF_PROLOGUE(AActor); - return DoJumpIfInventory(self->target, VM_ARGS_NAMES); -} //========================================================================== // // State jump function // //========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfArmorType) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckArmorType) { PARAM_SELF_PROLOGUE(AActor); PARAM_NAME (type); - PARAM_STATE (label); PARAM_INT_DEF(amount); ABasicArmor *armor = (ABasicArmor *)self->FindInventory(NAME_BasicArmor); - if (armor && armor->ArmorType == type && armor->Amount >= amount) - { - ACTION_RETURN_STATE(label); - } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(armor && armor->ArmorType == type && armor->Amount >= amount); } //========================================================================== @@ -1910,7 +1771,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CustomComboAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfNoAmmo) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_STATE(jump); + PARAM_STATE_ACTION(jump); if (!ACTION_CALL_FROM_PSPRITE() || self->player->ReadyWeapon == nullptr) { @@ -3637,10 +3498,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SpawnParticle) // jumps if no player can see this actor // //=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSight) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckIfSeen) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); for (int i = 0; i < MAXPLAYERS; i++) { @@ -3649,17 +3509,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSight) // Always check sight from each player. if (P_CheckSight(players[i].mo, self, SF_IGNOREVISIBILITY)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } // If a player is viewing from a non-player, then check that too. if (players[i].camera != NULL && players[i].camera->player == NULL && P_CheckSight(players[i].camera, self, SF_IGNOREVISIBILITY)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } } } - ACTION_RETURN_STATE(jump); + ACTION_RETURN_BOOL(true); } //=========================================================================== @@ -3706,11 +3566,10 @@ static bool DoCheckSightOrRange(AActor *self, AActor *camera, double range, bool return false; } -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSightOrRange) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckSightOrRange) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(range); - PARAM_STATE(jump); PARAM_BOOL_DEF(twodi); range *= range; @@ -3721,25 +3580,24 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSightOrRange) // Always check from each player. if (DoCheckSightOrRange(self, players[i].mo, range, twodi, true)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } // If a player is viewing from a non-player, check that too. if (players[i].camera != NULL && players[i].camera->player == NULL && DoCheckSightOrRange(self, players[i].camera, range, twodi, true)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } } } - ACTION_RETURN_STATE(jump); + ACTION_RETURN_BOOL(true); } -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckRange) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckRange) { PARAM_SELF_PROLOGUE(AActor); PARAM_FLOAT(range); - PARAM_STATE(jump); PARAM_BOOL_DEF(twodi); range *= range; @@ -3750,17 +3608,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckRange) // Always check from each player. if (DoCheckSightOrRange(self, players[i].mo, range, twodi, false)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } // If a player is viewing from a non-player, check that too. if (players[i].camera != NULL && players[i].camera->player == NULL && DoCheckSightOrRange(self, players[i].camera, range, twodi, false)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } } } - ACTION_RETURN_STATE(jump); + ACTION_RETURN_BOOL(false); } @@ -3813,20 +3671,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetBlend) } -//=========================================================================== -// -// A_JumpIf -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIf) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_BOOL (condition); - PARAM_STATE (jump); - - ACTION_RETURN_STATE(condition ? jump : NULL); -} - //=========================================================================== // // A_CountdownArg @@ -3917,43 +3761,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Burst) return 0; } -//=========================================================================== -// -// A_CheckFloor -// [GRB] Jumps if actor is standing on floor -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFloor) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); - - if (self->Z() <= self->floorz) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - -//=========================================================================== -// -// A_CheckCeiling -// [GZ] Totally copied from A_CheckFloor, jumps if actor touches ceiling -// - -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckCeiling) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); - - if (self->Top() >= self->ceilingz) // Height needs to be counted - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - //=========================================================================== // // A_Stop @@ -4077,17 +3884,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Respawn) // //========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PlayerSkinCheck) +DEFINE_ACTION_FUNCTION(AActor, PlayerSkinCheck) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); - if (self->player != NULL && - skins[self->player->userinfo.GetSkin()].othergame) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(self->player != NULL && + skins[self->player->userinfo.GetSkin()].othergame); } // [KS] *** Start of my modifications *** @@ -4220,7 +4022,7 @@ ETraceStatus CheckLOFTraceFunc(FTraceResults &trace, void *userdata) return TRACE_Abort; } -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckLOF) { // Check line of fire @@ -4233,7 +4035,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) DVector3 vel; PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE (jump); PARAM_INT_DEF (flags) PARAM_FLOAT_DEF (range) PARAM_FLOAT_DEF (minrange) @@ -4290,7 +4091,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) double distance = self->Distance3D(target); if (distance > range) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } } @@ -4339,7 +4140,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) } else { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } double cp = pitch.Cos(); @@ -4377,7 +4178,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) { if (minrange > 0 && trace.Distance < minrange) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if ((trace.HitType == TRACE_HitActor) && (trace.Actor != NULL) && !(lof_data.BadActor)) { @@ -4385,9 +4186,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckLOF) if (flags & (CLOFF_SETMASTER)) self->master = trace.Actor; if (flags & (CLOFF_SETTRACER)) self->tracer = trace.Actor; } - ACTION_RETURN_STATE(jump); + ACTION_RETURN_BOOL(true); } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } //========================================================================== @@ -4422,10 +4223,9 @@ enum JLOS_flags JLOSF_CHECKTRACER = 1 << 12, }; -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckIfTargetInLOS) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE (jump); PARAM_ANGLE_DEF (fov) PARAM_INT_DEF (flags) PARAM_FLOAT_DEF (dist_max) @@ -4456,11 +4256,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) if (target == NULL) { // [KS] Let's not call P_CheckSight unnecessarily in this case. - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if ((flags & JLOSF_DEADNOJUMP) && (target->health <= 0)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } doCheckSight = !(flags & JLOSF_NOSIGHT); @@ -4472,7 +4272,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) if (!t.linetarget) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } target = t.linetarget; @@ -4498,24 +4298,24 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) // [FDARI] If target is not a combatant, don't jump if ( (flags & JLOSF_COMBATANTONLY) && (!target->player) && !(target->flags3 & MF3_ISMONSTER)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } // [FDARI] If actors share team, don't jump if ((flags & JLOSF_ALLYNOJUMP) && self->IsFriend(target)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } double distance = self->Distance3D(target); if (dist_max && (distance > dist_max)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if (dist_close && (distance < dist_close)) { if (flags & JLOSF_CLOSENOJUMP) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if (flags & JLOSF_CLOSENOFOV) fov = 0.; @@ -4529,7 +4329,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) if (doCheckSight && !P_CheckSight (viewport, target, SF_IGNOREVISIBILITY)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if (flags & JLOSF_FLIPFOV) @@ -4546,10 +4346,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) if (an > (fov / 2)) { - ACTION_RETURN_STATE(NULL); // [KS] Outside of FOV - return + ACTION_RETURN_BOOL(false); // [KS] Outside of FOV - return } } - ACTION_RETURN_STATE(jump); + ACTION_RETURN_BOOL(true); } @@ -4560,10 +4360,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfTargetInLOS) // //========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckIfInTargetLOS) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE (jump); PARAM_ANGLE_DEF (fov) PARAM_INT_DEF (flags) PARAM_FLOAT_DEF (dist_max) @@ -4589,19 +4388,19 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) if (target == NULL) { // [KS] Let's not call P_CheckSight unnecessarily in this case. - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if ((flags & JLOSF_DEADNOJUMP) && (target->health <= 0)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } double distance = self->Distance3D(target); if (dist_max && (distance > dist_max)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } bool doCheckSight = !(flags & JLOSF_NOSIGHT); @@ -4610,7 +4409,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) { if (flags & JLOSF_CLOSENOJUMP) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if (flags & JLOSF_CLOSENOFOV) fov = 0.; @@ -4625,14 +4424,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfInTargetLOS) if (an > (fov / 2)) { - ACTION_RETURN_STATE(NULL); // [KS] Outside of FOV - return + ACTION_RETURN_BOOL(false); // [KS] Outside of FOV - return } } if (doCheckSight && !P_CheckSight (target, self, SF_IGNOREVISIBILITY)) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } - ACTION_RETURN_STATE(jump); + ACTION_RETURN_BOOL(true); } //=========================================================================== @@ -4650,7 +4449,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckForReload) ACTION_RETURN_STATE(NULL); } PARAM_INT (count); - PARAM_STATE (jump); + PARAM_STATE_ACTION (jump); PARAM_BOOL_DEF (dontincrement); if (numret > 0) @@ -4727,24 +4526,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ChangeFlag) // //=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckFlag) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckFlag) { PARAM_SELF_PROLOGUE(AActor); PARAM_STRING (flagname); - PARAM_STATE (jumpto); PARAM_INT_DEF (checkpointer); AActor *owner = COPY_AAPTR(self, checkpointer); - if (owner == NULL) - { - ACTION_RETURN_STATE(NULL); - } - - if (CheckActorFlag(owner, flagname)) - { - ACTION_RETURN_STATE(jumpto); - } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(owner != nullptr && CheckActorFlag(owner, flagname)); } @@ -5175,7 +4964,7 @@ enum T_Flags DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Teleport) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_STATE_DEF (teleport_state) PARAM_CLASS_DEF (target_type, ASpecialSpot) PARAM_CLASS_DEF (fog_type, AActor) @@ -5605,7 +5394,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_WolfAttack) DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Warp) { - PARAM_SELF_PROLOGUE(AActor); + PARAM_ACTION_PROLOGUE(AActor); PARAM_INT(destination_selector); PARAM_FLOAT_DEF(xofs) PARAM_FLOAT_DEF(yofs) @@ -5902,27 +5691,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_RadiusGive) ACTION_RETURN_INT(given); } -//=========================================================================== -// -// A_CheckSpecies -// -//=========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckSpecies) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); - PARAM_NAME_DEF(species); - PARAM_INT_DEF(ptr); - - AActor *mobj = COPY_AAPTR(self, ptr); - - if (mobj != NULL && jump && mobj->GetSpecies() == species) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); -} - //========================================================================== // // A_SetTics @@ -6666,44 +6434,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_ResetHealth) return 0; } -//=========================================================================== -// A_JumpIfHigherOrLower -// -// Jumps if a target, master, or tracer is higher or lower than the calling -// actor. Can also specify how much higher/lower the actor needs to be than -// itself. Can also take into account the height of the actor in question, -// depending on which it's checking. This means adding height of the -// calling actor's self if the pointer is higher, or height of the pointer -// if its lower. -//=========================================================================== - -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_JumpIfHigherOrLower) -{ - PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(high); - PARAM_STATE(low); - PARAM_FLOAT_DEF(offsethigh); - PARAM_FLOAT_DEF(offsetlow); - PARAM_BOOL_DEF(includeHeight); - PARAM_INT_DEF(ptr); - - AActor *mobj = COPY_AAPTR(self, ptr); - - - if (mobj != NULL && mobj != self) //AAPTR_DEFAULT is completely useless in this regard. - { - if ((high) && (mobj->Z() > ((includeHeight ? self->Height : 0) + self->Z() + offsethigh))) - { - ACTION_RETURN_STATE(high); - } - else if ((low) && (mobj->Z() + (includeHeight ? mobj->Height : 0)) < (self->Z() + offsetlow)) - { - ACTION_RETURN_STATE(low); - } - } - ACTION_RETURN_STATE(NULL); -} - //=========================================================================== // A_SetSpecies(str species, ptr) // @@ -6760,29 +6490,16 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetChaseThreshold) // Checks to see if a certain actor class is close to the // actor/pointer within distance, in numbers. //========================================================================== -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckProximity) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckProximity) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(jump); PARAM_CLASS(classname, AActor); PARAM_FLOAT(distance); PARAM_INT_DEF(count); PARAM_INT_DEF(flags); PARAM_INT_DEF(ptr); - if (!jump) - { - if (!(flags & (CPXF_SETTARGET | CPXF_SETMASTER | CPXF_SETTRACER))) - { - ACTION_RETURN_STATE(NULL); - } - } - - if (P_Thing_CheckProximity(self, classname, distance, count, flags, ptr) && jump) - { - ACTION_RETURN_STATE(jump); - } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(!!P_Thing_CheckProximity(self, classname, distance, count, flags, ptr)); } /*=========================================================================== @@ -6806,10 +6523,9 @@ enum CBF CBF_ABSOLUTEANGLE = 1 << 8, //Absolute angle for offsets. }; -DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckBlock) +DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckBlock) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(block) PARAM_INT_DEF(flags) PARAM_INT_DEF(ptr) PARAM_FLOAT_DEF(xofs) @@ -6822,7 +6538,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckBlock) //Needs at least one state jump to work. if (!mobj) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if (!(flags & CBF_ABSOLUTEANGLE)) @@ -6872,7 +6588,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckBlock) if (checker) { - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL(false); } if (mobj->BlockingMobj) @@ -6886,23 +6602,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_CheckBlock) } } - //[MC] If modders don't want jumping, but just getting the pointer, only abort at - //this point. I.e. A_CheckBlock("",CBF_SETTRACER) is like having CBF_NOLINES. - //It gets the mobj blocking, if any, and doesn't jump at all. - if (!block) - { - ACTION_RETURN_STATE(NULL); - } //[MC] I don't know why I let myself be persuaded not to include a flag. //If an actor is loaded with pointers, they don't really have any options to spare. //Also, fail if a dropoff or a step is too great to pass over when checking for dropoffs. - if ((!(flags & CBF_NOACTORS) && (mobj->BlockingMobj)) || (!(flags & CBF_NOLINES) && mobj->BlockingLine != NULL) || - ((flags & CBF_DROPOFF) && !checker)) - { - ACTION_RETURN_STATE(block); - } - ACTION_RETURN_STATE(NULL); + ACTION_RETURN_BOOL((!(flags & CBF_NOACTORS) && (mobj->BlockingMobj)) || (!(flags & CBF_NOLINES) && mobj->BlockingLine != NULL) || + ((flags & CBF_DROPOFF) && !checker)); } //=========================================================================== diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index db6b9a287..05cfb7cc4 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -159,6 +159,7 @@ extern FFlagDef ActorFlagDefs[]; void AActor::InitNativeFields() { + PType *TypePlayer = NewPointer(TypeVoid); // placeholder PType *TypeActor = NewPointer(RUNTIME_CLASS(AActor)); PType *TypeActorClass = NewClassPointer(RUNTIME_CLASS(AActor)); PType *TypeInventory = NewPointer(RUNTIME_CLASS(AInventory)); @@ -168,6 +169,7 @@ void AActor::InitNativeFields() auto meta = RUNTIME_CLASS(AActor); + meta->AddNativeField("Player", TypePlayer, myoffsetof(AActor, player)); meta->AddNativeField("Pos", TypeVector3, myoffsetof(AActor, __Pos), VARF_ReadOnly); meta->AddNativeField(NAME_X, TypeFloat64, myoffsetof(AActor, __Pos.X), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! meta->AddNativeField(NAME_Y, TypeFloat64, myoffsetof(AActor, __Pos.Y), VARF_ReadOnly | VARF_Deprecated); // must remain read-only! @@ -694,7 +696,7 @@ bool AActor::SetState (FState *newstate, bool nofunction) DEFINE_ACTION_FUNCTION(AActor, SetState) { PARAM_SELF_PROLOGUE(AActor); - PARAM_STATE(state); + PARAM_POINTER(state, FState); PARAM_BOOL_DEF(nofunction); ACTION_RETURN_BOOL(self->SetState(state, nofunction)); }; diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index 4938063ec..f371c6888 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -886,7 +886,7 @@ static void P_CheckWeaponButtons (player_t *player) DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_ReFire) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_STATE_DEF(state); + PARAM_STATE_ACTION_DEF(state); A_ReFire(self, state); return 0; } @@ -1224,7 +1224,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Overlay) { PARAM_ACTION_PROLOGUE(AActor); PARAM_INT (layer); - PARAM_STATE_DEF(state); + PARAM_STATE_ACTION_DEF(state); PARAM_BOOL_DEF(dontoverride); player_t *player = self->player; @@ -1294,7 +1294,7 @@ enum GF_Flags DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_GunFlash) { PARAM_ACTION_PROLOGUE(AActor); - PARAM_STATE_DEF(flash); + PARAM_STATE_ACTION_DEF(flash); PARAM_INT_DEF(flags); player_t *player = self->player; @@ -1361,6 +1361,19 @@ DAngle P_BulletSlope (AActor *mo, FTranslatedLineTarget *pLineTarget, int aimfla return pitch; } +AActor *P_AimTarget(AActor *mo) +{ + FTranslatedLineTarget t; + P_BulletSlope(mo, &t, ALF_PORTALRESTRICT); + return t.linetarget; +} + +DEFINE_ACTION_FUNCTION(AActor, AimTarget) +{ + PARAM_SELF_PROLOGUE(AActor); + ACTION_RETURN_OBJECT(P_AimTarget(self)); +} + // // P_GunShot diff --git a/src/p_pspr.h b/src/p_pspr.h index 2809216a7..3f819714c 100644 --- a/src/p_pspr.h +++ b/src/p_pspr.h @@ -110,6 +110,7 @@ void P_FireWeapon (player_t *player); void P_DropWeapon (player_t *player); void P_BobWeapon (player_t *player, float *x, float *y, double ticfrac); DAngle P_BulletSlope (AActor *mo, FTranslatedLineTarget *pLineTarget = NULL, int aimflags = 0); +AActor *P_AimTarget(AActor *mo); void P_GunShot (AActor *mo, bool accurate, PClassActor *pufftype, DAngle pitch); diff --git a/src/p_states.cpp b/src/p_states.cpp index 00b011e3d..2c1b88eaf 100644 --- a/src/p_states.cpp +++ b/src/p_states.cpp @@ -42,6 +42,9 @@ #include "vm.h" #include "thingdef.h" +// stores indices for symbolic state labels for some old-style DECORATE functions. +FStateLabelStorage StateLabels; + // Each state is owned by an actor. Actors can own any number of // states, but a single state cannot be owned by more than one // actor. States are archived by recording the actor they belong @@ -258,7 +261,94 @@ FState *PClassActor::FindStateByString(const char *name, bool exact) } +//========================================================================== +// +// validate a runtime state index. +// +//========================================================================== +static bool VerifyJumpTarget(PClassActor *cls, FState *CallingState, int index) +{ + while (cls != RUNTIME_CLASS(AActor)) + { + // both calling and target state need to belong to the same class. + if (cls->OwnsState(CallingState)) + { + return cls->OwnsState(CallingState + index); + } + + // We can safely assume the ParentClass is of type PClassActor + // since we stop when we see the Actor base class. + cls = static_cast(cls->ParentClass); + } + return false; +} + +//========================================================================== +// +// Get a statw pointer from a symbolic label +// +//========================================================================== + +FState *FStateLabelStorage::GetState(int pos, PClassActor *cls) +{ + if (pos > 0x10000000) + { + return cls? cls->FindState(ENamedName(pos - 0x10000000)) : nullptr; + } + else if (pos < 0) + { + // decode the combined value produced by the script. + int index = (pos >> 16) & 32767; + pos = ((pos & 65535) - 1) * 4; + FState *state; + memcpy(&state, &Storage[pos + sizeof(int)], sizeof(state)); + if (VerifyJumpTarget(cls, state, index)) + return state + index; + else + return nullptr; + } + else if (pos > 0) + { + int val; + pos = (pos - 1) * 4; + memcpy(&val, &Storage[pos], sizeof(int)); + + if (val == 0) + { + FState *state; + memcpy(&state, &Storage[pos + sizeof(int)], sizeof(state)); + return state; + } + else if (cls != nullptr) + { + FName *labels = (FName*)&Storage[pos + sizeof(int)]; + return cls->FindState(val, labels, false); + } + } + return nullptr; +} + +//========================================================================== +// +// State label conversion function for scripts +// +//========================================================================== + +DEFINE_ACTION_FUNCTION(AActor, FindState) +{ + PARAM_SELF_PROLOGUE(AActor); + PARAM_STATE(newstate); + ACTION_RETURN_STATE(newstate); +} + +// same as above but context aware. +DEFINE_ACTION_FUNCTION_PARAMS(AActor, ResolveState) +{ + PARAM_ACTION_PROLOGUE(AActor); + PARAM_STATE_ACTION(newstate); + ACTION_RETURN_STATE(newstate); +} //========================================================================== // diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index cbe9183e2..103e38eff 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -812,7 +812,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) if (basex->ValueType->GetRegType() == REGT_INT) { - if (basex->ValueType != TypeName || Explicit) // names can be converted to int, but only with an explicit type cast. + if (basex->ValueType->isNumeric() || Explicit) // names can be converted to int, but only with an explicit type cast. { FxExpression *x = basex; x->ValueType = ValueType; @@ -822,7 +822,7 @@ FxExpression *FxIntCast::Resolve(FCompileContext &ctx) } else { - // Ugh. This should abort, but too many mods fell into this logic hole somewhere, so this seroious error needs to be reduced to a warning. :( + // Ugh. This should abort, but too many mods fell into this logic hole somewhere, so this serious error needs to be reduced to a warning. :( // At least in ZScript, MSG_OPTERROR always means to report an error, not a warning so the problem only exists in DECORATE. if (!basex->isConstant()) ScriptPosition.Message(MSG_OPTERROR, "Numeric type expected, got a name"); @@ -919,7 +919,7 @@ FxExpression *FxFloatCast::Resolve(FCompileContext &ctx) } else if (basex->ValueType->GetRegType() == REGT_INT) { - if (basex->ValueType != TypeName) + if (basex->ValueType->isNumeric()) { if (basex->isConstant()) { @@ -1428,8 +1428,15 @@ FxExpression *FxTypeCast::Resolve(FCompileContext &ctx) delete this; return x; } - else if (ValueType == TypeState) + else if (ValueType == TypeStateLabel) { + if (basex->ValueType == TypeNullPtr) + { + auto x = new FxConstant(0, ScriptPosition); + x->ValueType = TypeStateLabel; + delete this; + return x; + } // Right now this only supports string constants. There should be an option to pass a string variable, too. if (basex->isConstant() && (basex->ValueType == TypeString || basex->ValueType == TypeName)) { @@ -4022,6 +4029,10 @@ FxExpression *FxConditional::Resolve(FCompileContext& ctx) ValueType = TypeSInt32; else if (truex->IsNumeric() && falsex->IsNumeric()) ValueType = TypeFloat64; + else if (truex->IsPointer() && falsex->ValueType == TypeNullPtr) + ValueType = truex->ValueType; + else if (falsex->IsPointer() && truex->ValueType == TypeNullPtr) + ValueType = falsex->ValueType; else ValueType = TypeVoid; //else if (truex->ValueType != falsex->ValueType) @@ -4519,23 +4530,21 @@ static void EmitLoad(VMFunctionBuilder *build, const ExpEmit resultreg, const Ex ExpEmit FxMinMax::Emit(VMFunctionBuilder *build) { unsigned i; - int opcode, opA; + int opcode; assert(choices.Size() > 0); - assert(OP_LTF_RK == OP_LTF_RR+1); - assert(OP_LT_RK == OP_LT_RR+1); - assert(OP_LEF_RK == OP_LEF_RR+1); - assert(OP_LE_RK == OP_LE_RR+1); + assert(OP_MAXF_RK == OP_MAXF_RR+1); + assert(OP_MAX_RK == OP_MAX_RR+1); + assert(OP_MIN_RK == OP_MIN_RR+1); + assert(OP_MIN_RK == OP_MIN_RR+1); if (Type == NAME_Min) { - opcode = ValueType->GetRegType() == REGT_FLOAT ? OP_LEF_RR : OP_LE_RR; - opA = 1; + opcode = ValueType->GetRegType() == REGT_FLOAT ? OP_MINF_RR : OP_MIN_RR; } else { - opcode = ValueType->GetRegType() == REGT_FLOAT ? OP_LTF_RR : OP_LT_RR; - opA = 0; + opcode = ValueType->GetRegType() == REGT_FLOAT ? OP_MAXF_RR : OP_MAX_RR; } ExpEmit bestreg; @@ -4556,17 +4565,8 @@ ExpEmit FxMinMax::Emit(VMFunctionBuilder *build) { ExpEmit checkreg = choices[i]->Emit(build); assert(checkreg.RegType == bestreg.RegType); - build->Emit(opcode + checkreg.Konst, opA, bestreg.RegNum, checkreg.RegNum); - build->Emit(OP_JMP, 1); - if (checkreg.Konst) - { - build->Emit(bestreg.RegType == REGT_FLOAT ? OP_LKF : OP_LK, bestreg.RegNum, checkreg.RegNum); - } - else - { - build->Emit(bestreg.RegType == REGT_FLOAT ? OP_MOVEF : OP_MOVE, bestreg.RegNum, checkreg.RegNum, 0); - checkreg.Free(build); - } + build->Emit(opcode + checkreg.Konst, bestreg.RegNum, bestreg.RegNum, checkreg.RegNum); + checkreg.Free(build); } return bestreg; } @@ -6121,7 +6121,6 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Name: case NAME_Color: case NAME_Sound: - case NAME_State: if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) { PType *type = @@ -6131,8 +6130,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) MethodName == NAME_Float ? TypeFloat64 : MethodName == NAME_Double ? TypeFloat64 : MethodName == NAME_Name ? TypeName : - MethodName == NAME_Color ? TypeColor : - MethodName == NAME_State? TypeState :(PType*)TypeSound; + MethodName == NAME_Color ? TypeColor : (PType*)TypeSound; func = new FxTypeCast(ArgList[0], type, true, true); ArgList[0] = nullptr; @@ -6819,7 +6817,6 @@ bool FxVMFunctionCall::CheckEmitCast(VMFunctionBuilder *build, bool returnit, Ex FName funcname = Function->SymbolName; if (funcname == NAME___decorate_internal_int__ || funcname == NAME___decorate_internal_bool__ || - funcname == NAME___decorate_internal_state__ || funcname == NAME___decorate_internal_float__) { FxExpression *arg = ArgList[0]; @@ -7926,6 +7923,13 @@ FxExpression *FxReturnStatement::Resolve(FCompileContext &ctx) } else { + // If we already know the real return type we need at least try to cast the value to its proper type (unless in an anonymous function.) + if (ctx.ReturnProto != nullptr && ctx.Function->SymbolName != NAME_None) + { + Value = new FxTypeCast(Value, ctx.ReturnProto->ReturnTypes[0], false, false); + Value = Value->Resolve(ctx); + ABORT(Value); + } retproto = Value->ReturnProto(); } @@ -8135,7 +8139,9 @@ ExpEmit FxClassTypeCast::Emit(VMFunctionBuilder *build) //========================================================================== // -// +// Symbolic state labels. +// Conversion will not happen inside the compiler anymore because it causes +// just too many problems. // //========================================================================== @@ -8155,7 +8161,9 @@ FxExpression *FxStateByIndex::Resolve(FCompileContext &ctx) delete this; return nullptr; } - FxExpression *x = new FxConstant(aclass->OwnedStates + index, ScriptPosition); + int symlabel = StateLabels.AddPointer(aclass->OwnedStates + index); + FxExpression *x = new FxConstant(symlabel, ScriptPosition); + x->ValueType = TypeStateLabel; delete this; return x; } @@ -8169,8 +8177,7 @@ FxExpression *FxStateByIndex::Resolve(FCompileContext &ctx) FxRuntimeStateIndex::FxRuntimeStateIndex(FxExpression *index) : FxExpression(EFX_RuntimeStateIndex, index->ScriptPosition), Index(index) { - EmitTail = false; - ValueType = TypeState; + ValueType = TypeStateLabel; } FxRuntimeStateIndex::~FxRuntimeStateIndex() @@ -8178,12 +8185,6 @@ FxRuntimeStateIndex::~FxRuntimeStateIndex() SAFE_DELETE(Index); } -PPrototype *FxRuntimeStateIndex::ReturnProto() -{ - EmitTail = true; - return FxExpression::ReturnProto(); -} - FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); @@ -8206,13 +8207,15 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) } else if (index == 0) { - auto x = new FxConstant((FState*)nullptr, ScriptPosition); + int symlabel = StateLabels.AddPointer(nullptr); + auto x = new FxConstant(symlabel, ScriptPosition); delete this; - return x->Resolve(ctx); + x->ValueType = TypeStateLabel; + return x; } else { - auto x = new FxStateByIndex(index, ScriptPosition); + auto x = new FxStateByIndex(ctx.StateIndex + index, ScriptPosition); delete this; return x->Resolve(ctx); } @@ -8222,84 +8225,21 @@ FxExpression *FxRuntimeStateIndex::Resolve(FCompileContext &ctx) Index = new FxIntCast(Index, ctx.FromDecorate); SAFE_RESOLVE(Index, ctx); } - + auto aclass = dyn_cast(ctx.Class); + assert(aclass != nullptr && aclass->NumOwnedStates > 0); + symlabel = StateLabels.AddPointer(aclass->OwnedStates + ctx.StateIndex); + ValueType = TypeStateLabel; return this; } -static bool VerifyJumpTarget(AActor *stateowner, FStateParamInfo *stateinfo, int index) -{ - PClassActor *cls = stateowner->GetClass(); - - if (stateinfo->mCallingState != nullptr) - { - while (cls != RUNTIME_CLASS(AActor)) - { - // both calling and target state need to belong to the same class. - if (cls->OwnsState(stateinfo->mCallingState)) - { - return cls->OwnsState(stateinfo->mCallingState + index); - } - - // We can safely assume the ParentClass is of type PClassActor - // since we stop when we see the Actor base class. - cls = static_cast(cls->ParentClass); - } - } - return false; -} - -static int BuiltinHandleRuntimeState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) -{ - PARAM_PROLOGUE; - PARAM_OBJECT(stateowner, AActor); - PARAM_POINTER(stateinfo, FStateParamInfo); - PARAM_INT(index); - - if (index == 0 || !VerifyJumpTarget(stateowner, stateinfo, index)) - { - // Null is returned if the location was invalid which means that no jump will be performed - // if used as return value - // 0 always meant the same thing so we handle it here for compatibility - ACTION_RETURN_STATE(nullptr); - } - else - { - ACTION_RETURN_STATE(stateinfo->mCallingState + index); - } -} - ExpEmit FxRuntimeStateIndex::Emit(VMFunctionBuilder *build) { - // This can only be called from inline state functions which must be VARF_Action. - assert(build->NumImplicits >= NAP && build->Registers[REGT_POINTER].GetMostUsed() >= build->NumImplicits && - "FxRuntimeStateIndex is only valid inside action functions"); - - ExpEmit out(build, REGT_POINTER); - - build->Emit(OP_PARAM, 0, REGT_POINTER, 1); // stateowner - build->Emit(OP_PARAM, 0, REGT_POINTER, 2); // stateinfo - ExpEmit id = Index->Emit(build); - build->Emit(OP_PARAM, 0, REGT_INT | (id.Konst ? REGT_KONST : 0), id.RegNum); // index - - VMFunction *callfunc; - PSymbol *sym; - - sym = FindBuiltinFunction(NAME_BuiltinHandleRuntimeState, BuiltinHandleRuntimeState); - assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != nullptr); - callfunc = ((PSymbolVMFunction *)sym)->Function; - - if (EmitTail) - { - build->Emit(OP_TAIL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), 3, 1); - out.Final = true; - } - else - { - build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), 3, 1); - build->Emit(OP_RESULT, 0, REGT_POINTER, out.RegNum); - } - + ExpEmit out = Index->Emit(build); + // out = (clamp(Index, 0, 32767) << 16) | symlabel | 0x80000000; 0x80000000 is here to make it negative. + build->Emit(OP_MAX_RK, out.RegNum, out.RegNum, build->GetConstantInt(0)); + build->Emit(OP_MIN_RK, out.RegNum, out.RegNum, build->GetConstantInt(32767)); + build->Emit(OP_SLL_RI, out.RegNum, out.RegNum, 16); + build->Emit(OP_OR_RK, out.RegNum, out.RegNum, build->GetConstantInt(symlabel|0x80000000)); return out; } @@ -8340,6 +8280,7 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) { CHECKRESOLVED(); ABORT(ctx.Class); + int symlabel; if (names[0] == NAME_None) { @@ -8379,107 +8320,17 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) return this; } } - FxExpression *x = new FxConstant(destination, ScriptPosition); - delete this; - return x; - } - names.Delete(0); - names.ShrinkToFit(); - ValueType = TypeState; - return this; -} - -//========================================================================== -// -// -// -//========================================================================== - -static int DoFindState(VMFrameStack *stack, VMValue *param, int numparam, VMReturn *ret, FName *names, int numnames) -{ - PARAM_OBJECT_AT(0, self, AActor); - FState *state = self->GetClass()->FindState(numparam - 1, names); - if (state == nullptr) - { - const char *dot = ""; - Printf("Jump target '"); - for (int i = 0; i < numparam - 1; i++) - { - Printf("%s%s", dot, names[i].GetChars()); - dot = "."; - } - Printf("' not found in %s\n", self->GetClass()->TypeName.GetChars()); - } - ret->SetPointer(state, ATAG_STATE); - return 1; -} - -// Find a state with any number of dots in its name. -int BuiltinFindMultiNameState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) -{ - assert(numparam > 1); - assert(numret == 1); - assert(ret->RegType == REGT_POINTER); - - FName *names = (FName *)alloca((numparam - 1) * sizeof(FName)); - for (int i = 1; i < numparam; ++i) - { - PARAM_NAME_AT(i, zaname); - names[i - 1] = zaname; - } - return DoFindState(stack, param, numparam, ret, names, numparam - 1); -} - -// Find a state without any dots in its name. -int BuiltinFindSingleNameState(VMFrameStack *stack, VMValue *param, TArray &defaultparam, int numparam, VMReturn *ret, int numret) -{ - assert(numparam == 2); - assert(numret == 1); - assert(ret->RegType == REGT_POINTER); - - PARAM_NAME_AT(1, zaname); - return DoFindState(stack, param, numparam, ret, &zaname, 1); -} - -ExpEmit FxMultiNameState::Emit(VMFunctionBuilder *build) -{ - ExpEmit dest(build, REGT_POINTER); - if (build->NumImplicits == NAP) - { - build->Emit(OP_PARAM, 0, REGT_POINTER, 1); // pass stateowner + symlabel = StateLabels.AddPointer(destination); } else { - build->Emit(OP_PARAM, 0, REGT_POINTER, 0); // pass self + names.Delete(0); + symlabel = StateLabels.AddNames(names); } - for (unsigned i = 0; i < names.Size(); ++i) - { - build->EmitParamInt(names[i]); - } - - // For one name, use the BuiltinFindSingleNameState function. For more than - // one name, use the BuiltinFindMultiNameState function. - VMFunction *callfunc; - PSymbol *sym; - - if (names.Size() == 1) - { - sym = FindBuiltinFunction(NAME_BuiltinFindSingleNameState, BuiltinFindSingleNameState); - } - else - { - sym = FindBuiltinFunction(NAME_BuiltinFindMultiNameState, BuiltinFindMultiNameState); - } - - assert(sym->IsKindOf(RUNTIME_CLASS(PSymbolVMFunction))); - assert(((PSymbolVMFunction *)sym)->Function != nullptr); - callfunc = ((PSymbolVMFunction *)sym)->Function; - - build->Emit(OP_CALL_K, build->GetConstantAddress(callfunc, ATAG_OBJECT), names.Size() + 1, 1); - build->Emit(OP_RESULT, 0, REGT_POINTER, dest.RegNum); - names.Clear(); - names.ShrinkToFit(); - return dest; + FxExpression *x = new FxConstant(symlabel, ScriptPosition); + x->ValueType = TypeStateLabel; + delete this; + return x; } //========================================================================== diff --git a/src/scripting/codegeneration/codegen.h b/src/scripting/codegeneration/codegen.h index b9679ad31..f1778512f 100644 --- a/src/scripting/codegeneration/codegen.h +++ b/src/scripting/codegeneration/codegen.h @@ -310,9 +310,9 @@ public: virtual PPrototype *ReturnProto(); virtual VMFunction *GetDirectFunction(); virtual bool CheckReturn() { return false; } - bool IsNumeric() const { return ValueType != TypeName && ValueType->GetRegCount() == 1 && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT); } + bool IsNumeric() const { return ValueType->isNumeric(); } bool IsFloat() const { return ValueType->GetRegType() == REGT_FLOAT && ValueType->GetRegCount() == 1; } - bool IsInteger() const { return ValueType != TypeName && (ValueType->GetRegType() == REGT_INT); } + bool IsInteger() const { return ValueType->isNumeric() && (ValueType->GetRegType() == REGT_INT); } bool IsPointer() const { return ValueType->GetRegType() == REGT_POINTER; } bool IsVector() const { return ValueType == TypeVector2 || ValueType == TypeVector3; }; bool IsBoolCompat() const { return ValueType->GetRegCount() == 1 && (ValueType->GetRegType() == REGT_INT || ValueType->GetRegType() == REGT_FLOAT || ValueType->GetRegType() == REGT_POINTER); } @@ -1684,14 +1684,13 @@ public: class FxRuntimeStateIndex : public FxExpression { - bool EmitTail; FxExpression *Index; + int symlabel; public: FxRuntimeStateIndex(FxExpression *index); ~FxRuntimeStateIndex(); FxExpression *Resolve(FCompileContext&); - PPrototype *ReturnProto(); ExpEmit Emit(VMFunctionBuilder *build); }; @@ -1709,7 +1708,6 @@ public: FxMultiNameState(const char *statestring, const FScriptPosition &pos); FxExpression *Resolve(FCompileContext&); - ExpEmit Emit(VMFunctionBuilder *build); }; //========================================================================== diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index e292e1844..151d88521 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -174,14 +174,15 @@ FxExpression *ParseParameter(FScanner &sc, PClassActor *cls, PType *type, bool c val.Int = v; x = new FxConstant(val, sc); } - else if (type == TypeState) + else if (type == TypeStateLabel) { // This forces quotation marks around the state name. if (sc.CheckToken(TK_StringConst)) { if (sc.String[0] == 0 || sc.Compare("None")) { - x = new FxConstant((FState*)nullptr, sc); + x = new FxConstant(0, sc); + x->ValueType = TypeStateLabel; } else if (sc.Compare("*")) { diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index e3cb74c32..c9be2c747 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -626,7 +626,7 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArray 0) { FxExpression *x; - if (statedef != NULL && params[pnum] == TypeState && sc.CheckNumber()) + if (statedef != NULL && params[pnum] == TypeStateLabel && sc.CheckNumber()) { // Special case: State label as an offset if (sc.Number > 0 && statestring.Len() > 1) @@ -646,7 +646,8 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArrayValueType = TypeStateLabel; } } else @@ -703,7 +704,7 @@ FName CheckCastKludges(FName in) case NAME_Bool: return NAME___decorate_internal_bool__; case NAME_State: - return NAME___decorate_internal_state__; + return NAME_ResolveState; case NAME_Float: return NAME___decorate_internal_float__; default: diff --git a/src/scripting/vm/vm.h b/src/scripting/vm/vm.h index 019d6c3a6..2f98c8d81 100644 --- a/src/scripting/vm/vm.h +++ b/src/scripting/vm/vm.h @@ -940,15 +940,12 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_FLOAT_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); double x = param[p].f; #define PARAM_ANGLE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_FLOAT); DAngle x = param[p].f; #define PARAM_STRING_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_STRING); FString x = param[p].s(); -#define PARAM_STATE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_STATE || param[p].atag == ATAG_GENERIC || param[p].a == NULL)); FState *x = (FState *)param[p].a; +#define PARAM_STATE_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_INT); FState *x = (FState *)StateLabels.GetState(param[p].i, self->GetClass()); +#define PARAM_STATE_ACTION_AT(p,x) assert((p) < numparam); assert(param[p].Type == REGT_INT); FState *x = (FState *)StateLabels.GetState(param[p].i, stateowner->GetClass()); #define PARAM_POINTER_AT(p,x,type) assert((p) < numparam); assert(param[p].Type == REGT_POINTER); type *x = (type *)param[p].a; #define PARAM_OBJECT_AT(p,x,type) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); type *x = (type *)param[p].a; assert(x == NULL || x->IsKindOf(RUNTIME_CLASS(type))); #define PARAM_CLASS_AT(p,x,base) assert((p) < numparam); assert(param[p].Type == REGT_POINTER && (param[p].atag == ATAG_OBJECT || param[p].a == NULL)); base::MetaClass *x = (base::MetaClass *)param[p].a; assert(x == NULL || x->IsDescendantOf(RUNTIME_CLASS(base))); -// For optional paramaters. These have dangling elses for you to fill in the default assignment. e.g.: -// PARAM_INT_OPT(0,myint) { myint = 55; } -// Just make sure to fill it in when using these macros, because the compiler isn't likely -// to give useful error messages if you don't. #define PARAM_EXISTS(p) ((p) < numparam && param[p].Type != REGT_NIL) #define ASSERTINT(p) assert((p).Type == REGT_INT) #define ASSERTFLOAT(p) assert((p).Type == REGT_FLOAT) @@ -965,7 +962,8 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_FLOAT_DEF_AT(p,x) double x; if (PARAM_EXISTS(p)) { ASSERTFLOAT(param[p]); x = param[p].f; } else { ASSERTFLOAT(defaultparam[p]); x = defaultparam[p].f; } #define PARAM_ANGLE_DEF_AT(p,x) DAngle x; if (PARAM_EXISTS(p)) { ASSERTFLOAT(param[p]); x = param[p].f; } else { ASSERTFLOAT(defaultparam[p]); x = defaultparam[p].f; } #define PARAM_STRING_DEF_AT(p,x) FString x; if (PARAM_EXISTS(p)) { ASSERTSTRING(param[p]); x = param[p].s; } else { ASSERTSTRING(defaultparam[p]); x = defaultparam[p].s; } -#define PARAM_STATE_DEF_AT(p,x) FState *x; if (PARAM_EXISTS(p)) { ASSERTSTATE(param[p]); x = (FState*)param[p].a; } else { ASSERTSTATE(defaultparam[p]); x = (FState*)defaultparam[p].a; } +#define PARAM_STATE_DEF_AT(p,x) FState *x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = (FState*)StateLabels.GetState(param[p].i, self->GetClass()); } else { ASSERTINT(defaultparam[p]); x = (FState*)StateLabels.GetState(defaultparam[p].i, self->GetClass()); } +#define PARAM_STATE_ACTION_DEF_AT(p,x) FState *x; if (PARAM_EXISTS(p)) { ASSERTINT(param[p]); x = (FState*)StateLabels.GetState(param[p].i, stateowner->GetClass()); } else { ASSERTINT(defaultparam[p]); x = (FState*)StateLabels.GetState(defaultparam[p].i, stateowner->GetClass()); } #define PARAM_POINTER_DEF_AT(p,x,t) t *x; if (PARAM_EXISTS(p)) { ASSERTPOINTER(param[p]); x = (t*)param[p].a; } else { ASSERTPOINTER(defaultparam[p]); x = (t*)defaultparam[p].a; } #define PARAM_OBJECT_DEF_AT(p,x,t) t *x; if (PARAM_EXISTS(p)) { ASSERTOBJECT(param[p]); x = (t*)param[p].a; } else { ASSERTOBJECT(defaultparam[p]); x = (t*)defaultparam[p].a; } #define PARAM_CLASS_DEF_AT(p,x,t) t::MetaClass *x; if (PARAM_EXISTS(p)) { ASSERTOBJECT(param[p]); x = (t::MetaClass*)param[p].a; } else { ASSERTOBJECT(defaultparam[p]); x = (t::MetaClass*)defaultparam[p].a; } @@ -982,6 +980,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_ANGLE(x) ++paramnum; PARAM_ANGLE_AT(paramnum,x) #define PARAM_STRING(x) ++paramnum; PARAM_STRING_AT(paramnum,x) #define PARAM_STATE(x) ++paramnum; PARAM_STATE_AT(paramnum,x) +#define PARAM_STATE_ACTION(x) ++paramnum; PARAM_STATE_ACTION_AT(paramnum,x) #define PARAM_POINTER(x,type) ++paramnum; PARAM_POINTER_AT(paramnum,x,type) #define PARAM_OBJECT(x,type) ++paramnum; PARAM_OBJECT_AT(paramnum,x,type) #define PARAM_CLASS(x,base) ++paramnum; PARAM_CLASS_AT(paramnum,x,base) @@ -995,6 +994,7 @@ void VMDisasm(FILE *out, const VMOP *code, int codesize, const VMScriptFunction #define PARAM_ANGLE_DEF(x) ++paramnum; PARAM_ANGLE_DEF_AT(paramnum,x) #define PARAM_STRING_DEF(x) ++paramnum; PARAM_STRING_DEF_AT(paramnum,x) #define PARAM_STATE_DEF(x) ++paramnum; PARAM_STATE_DEF_AT(paramnum,x) +#define PARAM_STATE_ACTION_DEF(x) ++paramnum; PARAM_STATE_ACTION_DEF_AT(paramnum,x) #define PARAM_POINTER_DEF(x,type) ++paramnum; PARAM_POINTER_DEF_AT(paramnum,x,type) #define PARAM_OBJECT_DEF(x,type) ++paramnum; PARAM_OBJECT_DEF_AT(paramnum,x,type) #define PARAM_CLASS_DEF(x,base) ++paramnum; PARAM_CLASS_DEF_AT(paramnum,x,base) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 7e0af9ee4..b8c0a2a38 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -1429,7 +1429,15 @@ PType *ZCCCompiler::DetermineType(PType *outertype, ZCC_TreeNode *field, FName n break; case ZCC_UserType: - retval = ResolveUserType(btype, &outertype->Symbols); + // statelabel is not a token - there really is no need to, it works just as well as an identifier. Maybe the same should be done for some other types, too? + if (btype->UserType->Id == NAME_StateLabel) + { + retval = TypeStateLabel; + } + else + { + retval = ResolveUserType(btype, &outertype->Symbols); + } break; } break; diff --git a/wadsrc/static/zscript.txt b/wadsrc/static/zscript.txt index 8ea4bb114..42f32a447 100644 --- a/wadsrc/static/zscript.txt +++ b/wadsrc/static/zscript.txt @@ -1,6 +1,7 @@ zscript/base.txt zscript/constants.txt zscript/actor.txt +zscript/actor_checks.txt zscript/shared/inventory.txt zscript/shared/player.txt diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 7634ccaea..f3cd9aa3c 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -71,6 +71,7 @@ class Actor : Thinker native native void SetXYZ(vector3 newpos); native Actor GetPointer(int aaptr); native void FaceMovementDirection(); + native Actor AimTarget(); native static Actor Spawn(class type, vector3 pos = (0,0,0), int replace = NO_REPLACE); native Actor SpawnMissile(Actor dest, class type, Actor owner = null); native Actor SpawnMissileZ (double z, Actor dest, class type); @@ -90,6 +91,9 @@ class Actor : Thinker native native void NewChaseDir(); native bool CheckMissileRange(); native bool SetState(state st, bool nofunction = false); + native state FindState(statelabel st); // do we need exact later? + bool SetStateLabel(statelabel st, bool nofunction = false) { return SetState(FindState(st), nofunction); } + native action state ResolveState(statelabel st); // this one, unlike FindState, is context aware. native void LinkToWorld(); native void UnlinkFromWorld(); native bool CanSeek(Actor target); @@ -282,7 +286,7 @@ class Actor : Thinker native void A_Fall() { A_NoBlocking(); } native void A_XScream(); native void A_Look(); - native void A_Chase(state melee = null, state missile = null, int flags = 0); + native void A_Chase(statelabel melee = null, statelabel missile = null, int flags = 0); native void A_Scream(); native void A_VileChase(); native void A_BossDeath(); @@ -332,18 +336,10 @@ class Actor : Thinker native deprecated native void A_PlaySoundEx(sound whattoplay, name slot, bool looping = false, int attenuation = 0); deprecated native void A_StopSoundEx(name slot); native void A_SeekerMissile(int threshold, int turnmax, int flags = 0, int chance = 50, int distance = 10); - native state A_Jump(int chance, state label, ...); + native action state A_Jump(int chance, statelabel label, ...); native void A_CustomMissile(class missiletype, float spawnheight = 32, float spawnofs_xy = 0, float angle = 0, int flags = 0, float pitch = 0, int ptr = AAPTR_TARGET); native void A_CustomBulletAttack(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", float range = 0, int flags = 0, int ptr = AAPTR_TARGET, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); native void A_CustomRailgun(int damage, int spawnofs_xy = 0, color color1 = 0, color color2 = 0, int flags = 0, int aim = 0, float maxdiff = 0, class pufftype = "BulletPuff", float spread_xy = 0, float spread_z = 0, float range = 0, int duration = 0, float sparsity = 1.0, float driftspeed = 1.0, class spawnclass = null, float spawnofs_z = 0, int spiraloffset = 270, int limit = 0); - native state A_JumpIfHealthLower(int health, state label, int ptr_selector = AAPTR_DEFAULT); - native state A_JumpIfCloser(float distance, state label, bool noz = false); - native state A_JumpIfTracerCloser(float distance, state label, bool noz = false); - native state A_JumpIfMasterCloser(float distance, state label, bool noz = false); - native state A_JumpIfTargetOutsideMeleeRange(state label); - native state A_JumpIfTargetInsideMeleeRange(state label); - native state A_JumpIfInventory(class itemtype, int itemamount, state label, int owner = AAPTR_DEFAULT); - native state A_JumpIfArmorType(name Type, state label, int amount = 1); native bool A_SetInventory(class itemtype, int amount, int ptr = AAPTR_DEFAULT, bool beyondMax = false); native bool A_GiveInventory(class itemtype, int amount = 0, int giveto = AAPTR_DEFAULT); native bool A_TakeInventory(class itemtype, int amount = 0, int flags = 0, int giveto = AAPTR_DEFAULT); @@ -361,33 +357,29 @@ class Actor : Thinker native native void A_FadeTo(float target, float amount = 0.1, int flags = 0); native void A_SpawnDebris(class spawntype, bool transfer_translation = false, float mult_h = 1, float mult_v = 1); native void A_SpawnParticle(color color1, int flags = 0, int lifetime = 35, float size = 1, float angle = 0, float xoff = 0, float yoff = 0, float zoff = 0, float velx = 0, float vely = 0, float velz = 0, float accelx = 0, float accely = 0, float accelz = 0, float startalphaf = 1, float fadestepf = -1, float sizestep = 0); - native state A_CheckSight(state label); native void A_ExtChase(bool usemelee, bool usemissile, bool playactive = true, bool nightmarefast = false); native void A_DropInventory(class itemtype); native void A_SetBlend(color color1, float alpha, int tics, color color2 = 0); deprecated native void A_ChangeFlag(string flagname, bool value); - deprecated native state A_CheckFlag(string flagname, state label, int check_pointer = AAPTR_DEFAULT); native void A_ChangeCountFlags(int kill = FLAG_NO_CHANGE, int item = FLAG_NO_CHANGE, int secret = FLAG_NO_CHANGE); - native state A_JumpIf(bool expression, state label); native void A_RaiseMaster(bool copy = 0); native void A_RaiseChildren(bool copy = 0); native void A_RaiseSiblings(bool copy = 0); - native state A_CheckFloor(state label); - native state A_CheckCeiling(state label); - native state A_PlayerSkinCheck(state label); deprecated native void A_BasicAttack(int meleedamage, sound meleesound, class missiletype, float missileheight); - native state, bool A_Teleport(state teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 128, int ptr = AAPTR_DEFAULT); - native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, state success_state = null, float heightoffset = 0, float radiusoffset = 0, float pitch = 0); action native bool A_ThrowGrenade(class itemtype, float zheight = 0, float xyvel = 0, float zvel = 0, bool useammo = true); native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); + + native state, bool A_Teleport(statelabel teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 128, int ptr = AAPTR_DEFAULT); + native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, statelabel success_state = null, float heightoffset = 0, float radiusoffset = 0, float pitch = 0); + native void A_CountdownArg(int argnum, statelabel targstate = null); + native state A_MonsterRefire(int chance, statelabel label); + native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, statelabel label = null); + native void A_Recoil(float xyvel); - native state A_JumpIfInTargetInventory(class itemtype, int amount, state label, int forward_ptr = AAPTR_DEFAULT); native bool A_GiveToTarget(class itemtype, int amount = 0, int forward_ptr = AAPTR_DEFAULT); native bool A_TakeFromTarget(class itemtype, int amount = 0, int flags = 0, int forward_ptr = AAPTR_DEFAULT); native int A_RadiusGive(class itemtype, float distance, int flags, int amount = 0, class filter = null, name species = "None", float mindist = 0, int limit = 0); - native state A_CheckSpecies(state jump, name species = 'none', int ptr = AAPTR_DEFAULT); - native void A_CountdownArg(int argnum, state targstate = null); native void A_CustomMeleeAttack(int damage = 0, sound meleesound = "", sound misssound = "", name damagetype = "none", bool bleed = true); native void A_CustomComboAttack(class missiletype, float spawnheight, int damage, sound meleesound = "", name damagetype = "none", bool bleed = true); native void A_Burst(class chunktype); @@ -399,11 +391,7 @@ class Actor : Thinker native native void A_Respawn(int flags = 1); native void A_QueueCorpse(); native void A_DeQueueCorpse(); - native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, state label = null); native void A_ClearLastHeard(); - native state A_CheckLOF(state jump, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); - native state A_JumpIfTargetInLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); - native state A_JumpIfInTargetLOS (state label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); native bool A_SelectWeapon(class whichweapon, int flags = 0); action native void A_Punch(); native void A_Feathers(); @@ -416,7 +404,6 @@ class Actor : Thinker native native void A_RemoveForcefield(); native void A_DropWeaponPieces(class p1, class p2, class p3); native void A_PigPain (); - native state A_MonsterRefire(int chance, state label); native void A_SetAngle(float angle = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetPitch(float pitch, int flags = 0, int ptr = AAPTR_DEFAULT); native void A_SetRoll(float roll, int flags = 0, int ptr = AAPTR_DEFAULT); @@ -455,13 +442,8 @@ class Actor : Thinker native native void A_SwapTeleFog(); native void A_SetHealth(int health, int ptr = AAPTR_DEFAULT); native void A_ResetHealth(int ptr = AAPTR_DEFAULT); - native state A_JumpIfHigherOrLower(state high, state low, float offsethigh = 0, float offsetlow = 0, bool includeHeight = true, int ptr = AAPTR_TARGET); native void A_SetSpecies(name species, int ptr = AAPTR_DEFAULT); native void A_SetChaseThreshold(int threshold, bool def = false, int ptr = AAPTR_DEFAULT); - native state A_CheckProximity(state jump, class classname, float distance, int count = 1, int flags = 0, int ptr = AAPTR_DEFAULT); - native state A_CheckBlock(state block, int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0); - native state A_CheckSightOrRange(float distance, state label, bool two_dimension = false); - native state A_CheckRange(float distance, state label, bool two_dimension = false); native bool A_FaceMovementDirection(float offset = 0, float anglelimit = 0, float pitchlimit = 0, int flags = 0, int ptr = AAPTR_DEFAULT); native int A_ClearOverlays(int sstart = 0, int sstop = 0, bool safety = true); native bool A_CopySpriteFrame(int from, int to, int flags = 0); @@ -472,7 +454,7 @@ class Actor : Thinker native native void A_TransferPointer(int ptr_source, int ptr_recepient, int sourcefield, int recepientfield=AAPTR_DEFAULT, int flags=0); native void A_CopyFriendliness(int ptr_source = AAPTR_MASTER); - action native bool A_Overlay(int layer, state start = null, bool nooverride = false); + action native bool A_Overlay(int layer, statelabel start = null, bool nooverride = false); native void A_WeaponOffset(float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayOffset(int layer = PSP_WEAPON, float wx = 0, float wy = 32, int flags = 0); action native void A_OverlayFlags(int layer, int flags, bool set); @@ -525,7 +507,6 @@ class Actor : Thinker native } // Internal functions - deprecated private native state __decorate_internal_state__(state s); deprecated private native int __decorate_internal_int__(int i); deprecated private native bool __decorate_internal_bool__(bool b); deprecated private native float __decorate_internal_float__(float f); diff --git a/wadsrc/static/zscript/actor_checks.txt b/wadsrc/static/zscript/actor_checks.txt new file mode 100644 index 000000000..806539753 --- /dev/null +++ b/wadsrc/static/zscript/actor_checks.txt @@ -0,0 +1,274 @@ +extend class Actor +{ + //========================================================================== + // + // This file contains all the A_Jump* checker functions, all split up + // into an actual checker and a simple wrapper around ResolveState. + // + //========================================================================== + + action state A_JumpIf(bool expression, statelabel label) + { + return expression? ResolveState(label) : null; + } + + + //========================================================================== + // + // + // + //========================================================================== + + action state A_JumpIfHealthLower(int health, statelabel label, int ptr_selector = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr_selector); + return aptr && aptr.health < health? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + bool CheckIfCloser(Actor targ, float dist, bool noz = false) + { + if (!targ) return false; + return + (Distance2D(target) < dist && (noz || + ((pos.z > targ.pos.z && pos.z - targ.pos.z - targ.height < dist) || + (pos.z <= targ.pos.z && targ.pos.z - pos.z - height < dist) + ) + )); + } + + action state A_JumpIfCloser(float distance, statelabel label, bool noz = false) + { + Actor targ; + + if (player == NULL) + { + targ = target; + } + else + { + // Does the player aim at something that can be shot? + targ = AimTarget(); + } + + return CheckIfCloser(targ, distance, noz)? ResolveState(label) : null; + } + + action state A_JumpIfTracerCloser(float distance, statelabel label, bool noz = false) + { + return CheckIfCloser(tracer, distance, noz)? ResolveState(label) : null; + } + + action state A_JumpIfMasterCloser(float distance, statelabel label, bool noz = false) + { + return CheckIfCloser(master, distance, noz)? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + action state A_JumpIfTargetOutsideMeleeRange(statelabel label) + { + return CheckMeleeRange()? null : ResolveState(label); + } + + action state A_JumpIfTargetInsideMeleeRange(statelabel label) + { + return CheckMeleeRange()? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + native bool CheckInventory(class itemtype, int itemamount, int owner = AAPTR_DEFAULT); + + action state A_JumpIfInventory(class itemtype, int itemamount, statelabel label, int owner = AAPTR_DEFAULT) + { + return CheckInventory(itemtype, itemamount, owner)? ResolveState(label) : null; + } + + action state A_JumpIfInTargetInventory(class itemtype, int amount, statelabel label, int forward_ptr = AAPTR_DEFAULT) + { + if (target == null) return null; + return target.CheckInventory(itemtype, amount, forward_ptr)? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + native bool CheckArmorType(name Type, int amount = 1); + + action state A_JumpIfArmorType(name Type, statelabel label, int amount = 1) + { + return CheckArmorType(Type, amount)? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + native bool CheckIfSeen(); + native bool CheckSightOrRange(float distance, bool two_dimension = false); + native bool CheckRange(float distance, bool two_dimension = false); + + action state A_CheckSight(statelabel label) + { + return CheckIfSeen()? ResolveState(label) : null; + } + + action state A_CheckSightOrRange(float distance, statelabel label, bool two_dimension = false) + { + return CheckSightOrRange(distance, two_dimension)? ResolveState(label) : null; + } + + action state A_CheckRange(float distance, statelabel label, bool two_dimension = false) + { + return CheckRange(distance, two_dimension)? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + action state A_CheckFloor(statelabel label) + { + return pos.z <= floorz? ResolveState(label) : null; + } + + action state A_CheckCeiling(statelabel label) + { + return pos.z + height >= ceilingz? ResolveState(label) : null; + } + + //========================================================================== + // + // since this is deprecated the checker is private. + // + //========================================================================== + + private native bool CheckFlag(string flagname, int check_pointer = AAPTR_DEFAULT); + + deprecated action state A_CheckFlag(string flagname, statelabel label, int check_pointer = AAPTR_DEFAULT) + { + return CheckFlag(flagname, check_pointer)? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + native bool PlayerSkinCheck(); + + action state A_PlayerSkinCheck(statelabel label) + { + return PlayerSkinCheck()? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + action state A_CheckSpecies(statelabel label, name species = 'none', int ptr = AAPTR_DEFAULT) + { + Actor aptr = GetPointer(ptr); + return aptr && aptr.GetSpecies() == species? ResolveState(label) : null; + } + + //========================================================================== + // + // + // + //========================================================================== + + native bool CheckLOF(int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0); + native bool CheckIfTargetInLOS (float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); + native bool CheckIfInTargetLOS (float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0); + native bool CheckProximity(class classname, float distance, int count = 1, int flags = 0, int ptr = AAPTR_DEFAULT); + native bool CheckBlock(int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0); + + action state A_CheckLOF(statelabel label, int flags = 0, float range = 0, float minrange = 0, float angle = 0, float pitch = 0, float offsetheight = 0, float offsetwidth = 0, int ptr_target = AAPTR_DEFAULT, float offsetforward = 0) + { + return CheckLOF(flags, range, minrange, angle, pitch, offsetheight, offsetwidth, ptr_target, offsetforward)? ResolveState(label) : null; + } + + action state A_JumpIfTargetInLOS (statelabel label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0) + { + return CheckIfTargetInLOS(fov, flags, dist_max, dist_close)? ResolveState(label) : null; + } + + action state A_JumpIfInTargetLOS (statelabel label, float fov = 0, int flags = 0, float dist_max = 0, float dist_close = 0) + { + return CheckIfInTargetLOS(fov, flags, dist_max, dist_close)? ResolveState(label) : null; + } + + action state A_CheckProximity(statelabel label, class classname, float distance, int count = 1, int flags = 0, int ptr = AAPTR_DEFAULT) + { + // This one was doing some weird stuff that needs to be preserved. + state jumpto = ResolveState(label); + if (!jumpto) + { + if (!(flags & (CPXF_SETTARGET | CPXF_SETMASTER | CPXF_SETTRACER))) + { + return null; + } + } + return CheckProximity(classname, distance, count, flags, ptr)? jumpto : null; + } + + action state A_CheckBlock(statelabel label, int flags = 0, int ptr = AAPTR_DEFAULT, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0) + { + return CheckBlock(flags, ptr, xofs, yofs, zofs, angle)? ResolveState(label) : null; + } + + //=========================================================================== + // A_JumpIfHigherOrLower + // + // Jumps if a target, master, or tracer is higher or lower than the calling + // actor. Can also specify how much higher/lower the actor needs to be than + // itself. Can also take into account the height of the actor in question, + // depending on which it's checking. This means adding height of the + // calling actor's self if the pointer is higher, or height of the pointer + // if its lower. + //=========================================================================== + + action state A_JumpIfHigherOrLower(statelabel high, statelabel low, float offsethigh = 0, float offsetlow = 0, bool includeHeight = true, int ptr = AAPTR_TARGET) + { + Actor mobj = GetPointer(ptr); + + if (mobj != null && mobj != self) //AAPTR_DEFAULT is completely useless in this regard. + { + if ((high) && (mobj.pos.z > ((includeHeight ? Height : 0) + pos.z + offsethigh))) + { + return ResolveState(high); + } + else if ((low) && (mobj.pos.z + (includeHeight ? mobj.Height : 0)) < (pos.z + offsetlow)) + { + return ResolveState(low); + } + } + return null; + } + +} \ No newline at end of file diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt index b1aa901a3..f097e2c3b 100644 --- a/wadsrc/static/zscript/doom/bossbrain.txt +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -162,7 +162,7 @@ extend class Actor boom.DeathSound = "misc/brainexplode"; boom.Vel.z = random[BrainScream](0, 255)/128.; - boom.SetState ("BossBrain::Brainexplode"); + boom.SetStateLabel ("BossBrain::Brainexplode"); boom.bRocketTrail = false; boom.SetDamage(0); // disables collision detection which is not wanted here boom.tics -= random[BrainScream](0, 7); diff --git a/wadsrc/static/zscript/heretic/hereticimp.txt b/wadsrc/static/zscript/heretic/hereticimp.txt index 34738ed56..c1443de03 100644 --- a/wadsrc/static/zscript/heretic/hereticimp.txt +++ b/wadsrc/static/zscript/heretic/hereticimp.txt @@ -113,7 +113,7 @@ class HereticImp : Actor if (extremecrash) { - SetState ("XCrash"); + SetStateLabel ("XCrash"); } } diff --git a/wadsrc/static/zscript/hexen/bats.txt b/wadsrc/static/zscript/hexen/bats.txt index a530da176..aaefaaeb7 100644 --- a/wadsrc/static/zscript/hexen/bats.txt +++ b/wadsrc/static/zscript/hexen/bats.txt @@ -92,7 +92,7 @@ class Bat : Actor { if (special2 < 0) { - SetState ("Death"); + SetStateLabel ("Death"); } special2 -= 2; // Called every 2 tics diff --git a/wadsrc/static/zscript/hexen/bishop.txt b/wadsrc/static/zscript/hexen/bishop.txt index d846a6402..32f0f3e63 100644 --- a/wadsrc/static/zscript/hexen/bishop.txt +++ b/wadsrc/static/zscript/hexen/bishop.txt @@ -131,7 +131,7 @@ class Bishop : Actor { if (random[BishopDecide]() >= 220) { - SetState ("Blur"); + SetStateLabel ("Blur"); } } @@ -210,7 +210,7 @@ class Bishop : Actor { if (random[BishopPainBlur]() < 64) { - SetState ("Blur"); + SetStateLabel ("Blur"); return; } double xo = random2[BishopPainBlur]() / 16.; diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index fc037d13f..e38ddbdb1 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -41,7 +41,7 @@ class Inventory : Actor native class StateProvider : Inventory native { - action native state A_JumpIfNoAmmo(state label); + action native state A_JumpIfNoAmmo(statelabel label); action native void A_CustomPunch(int damage, bool norandom = false, int flags = CPF_USEAMMO, class pufftype = "BulletPuff", float range = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus", sound MeleeSound = 0, sound MissSound = ""); action native void A_FireBullets(float spread_xy, float spread_z, int numbullets, int damageperbullet, class pufftype = "BulletPuff", int flags = 1, float range = 0, class missile = null, float Spawnheight = 32, float Spawnofs_xy = 0); action native void A_FireCustomMissile(class missiletype, float angle = 0, bool useammo = true, float spawnofs_xy = 0, float spawnheight = 0, int flags = 0, float pitch = 0); @@ -73,13 +73,13 @@ class StateProvider : Inventory native action void A_BFGsound() { A_PlaySound("weapons/bfgf", CHAN_WEAPON); } action native void A_FireBFG(); action native void A_FireOldBFG(); - action native void A_ReFire(state flash = null); + action native void A_ReFire(statelabel flash = null); action native void A_ClearReFire(); action native void A_CheckReload(); - action native void A_GunFlash(state flash = null, int flags = 0); + action native void A_GunFlash(statelabel flash = null, int flags = 0); action native void A_FireAssaultGun(); action native void A_Saw(sound fullsound = "weapons/sawfull", sound hitsound = "weapons/sawhit", int damage = 2, class pufftype = "BulletPuff", int flags = 0, float range = 0, float spread_xy = 2.8125, float spread_z = 0, float lifesteal = 0, int lifestealmax = 0, class armorbonustype = "ArmorBonus"); - action native state A_CheckForReload(int counter, state label, bool dontincrement = false); + action native state A_CheckForReload(int counter, statelabel label, bool dontincrement = false); action native void A_ResetReloadCounter(); } diff --git a/wadsrc/static/zscript/strife/strifeweapons.txt b/wadsrc/static/zscript/strife/strifeweapons.txt index 178b2b27a..9e4463893 100644 --- a/wadsrc/static/zscript/strife/strifeweapons.txt +++ b/wadsrc/static/zscript/strife/strifeweapons.txt @@ -816,7 +816,7 @@ class StrifeGrenadeLauncher : StrifeWeapon Inventory.PickupMessage "$TXT_GLAUNCHER"; } - action native void A_FireGrenade (class grenadetype, float angleofs, state flash); + action native void A_FireGrenade (class grenadetype, float angleofs, statelabel flash); States { From 56a3dcfe800b7a5b6578e62c86e8f0d47aadba1d Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 15:02:44 +0100 Subject: [PATCH 246/255] - moved the 'brainexplode' state to the rocket, which is the actor which actually uses it. This appears to be the only case where an actor was set to a state owned by a completely unrelated actor which would present some problems with state owner checking in AActor::SetState, so let's better get rid of it ASAP. I believe the only reason this wasn't changed when all actors were exported 8 years ago was that old binary DEHSUPP lump. --- src/namedef.h | 1 - src/scripting/decorate/thingdef_exp.cpp | 4 ++++ wadsrc/static/dehsupp.txt | 2 +- wadsrc/static/zscript/doom/bossbrain.txt | 6 +----- wadsrc/static/zscript/doom/doomweapons.txt | 4 ++++ 5 files changed, 10 insertions(+), 7 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index ee7d08f40..f8475f716 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -209,7 +209,6 @@ xx(XDeath) xx(Burn) //xx(Ice) // already defined above xx(Disintegrate) -xx(Brainexplode) // Weapon animator names. xx(Select) diff --git a/src/scripting/decorate/thingdef_exp.cpp b/src/scripting/decorate/thingdef_exp.cpp index 7e4c3b398..229c8f1f4 100644 --- a/src/scripting/decorate/thingdef_exp.cpp +++ b/src/scripting/decorate/thingdef_exp.cpp @@ -476,6 +476,10 @@ static FxExpression *ParseExpression0 (FScanner &sc, PClassActor *cls) { exp = new FxRuntimeStateIndex(ParseExpressionM(sc, cls)); } + // The parsed expression is of type 'statelabel', but we want a real state here so we must convert it. + FArgumentList args; + args.Push(exp); + exp = new FxFunctionCall(NAME_ResolveState, NAME_None, args, sc); sc.MustGetToken(')'); return exp; } diff --git a/wadsrc/static/dehsupp.txt b/wadsrc/static/dehsupp.txt index 78948677f..436e894b4 100644 --- a/wadsrc/static/dehsupp.txt +++ b/wadsrc/static/dehsupp.txt @@ -327,7 +327,7 @@ StateMap BossEye, Spawn, 3, // S_BRAINEYE - S_BRAINEYE1 SpawnShot, Spawn, 4, // S_SPAWN1 - S_SPAWN4 SpawnFire, Spawn, 8, // S_SPAWNFIRE1 - S_SPAWNFIRE8 - BossBrain, BrainExplode, 3, // S_BRAINEXPLODE1 - S_BRAINEXPLODE3 + Rocket, BrainExplode, 3, // S_BRAINEXPLODE1 - S_BRAINEXPLODE3 GreenArmor, Spawn, 2, // S_ARM1 - S_ARM1A BlueArmor, Spawn, 2, // S_ARM2 - S_ARM2A ExplosiveBarrel, Spawn, 7, // S_BAR1 - S_BEXP5 diff --git a/wadsrc/static/zscript/doom/bossbrain.txt b/wadsrc/static/zscript/doom/bossbrain.txt index f097e2c3b..6a72de2bf 100644 --- a/wadsrc/static/zscript/doom/bossbrain.txt +++ b/wadsrc/static/zscript/doom/bossbrain.txt @@ -20,10 +20,6 @@ class BossBrain : Actor } States { - BrainExplode: - MISL BC 10 Bright; - MISL D 10 A_BrainExplode; - Stop; Spawn: BBRN A -1; Stop; @@ -162,7 +158,7 @@ extend class Actor boom.DeathSound = "misc/brainexplode"; boom.Vel.z = random[BrainScream](0, 255)/128.; - boom.SetStateLabel ("BossBrain::Brainexplode"); + boom.SetStateLabel ("Brainexplode"); boom.bRocketTrail = false; boom.SetDamage(0); // disables collision detection which is not wanted here boom.tics -= random[BrainScream](0, 7); diff --git a/wadsrc/static/zscript/doom/doomweapons.txt b/wadsrc/static/zscript/doom/doomweapons.txt index 41f2c434f..a6eecd189 100644 --- a/wadsrc/static/zscript/doom/doomweapons.txt +++ b/wadsrc/static/zscript/doom/doomweapons.txt @@ -357,6 +357,10 @@ class Rocket : Actor MISL C 6 Bright; MISL D 4 Bright; Stop; + BrainExplode: + MISL BC 10 Bright; + MISL D 10 A_BrainExplode; + Stop; } } From ba62a86c80c58c7a78935e925be59606195e6302 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 15:48:34 +0100 Subject: [PATCH 247/255] - fixed: A_SetInventory still had default initializers. --- src/p_actionfunctions.cpp | 4 ++-- src/scripting/codegeneration/codegen.cpp | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index ff7aa2af6..d61dc100c 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -2464,8 +2464,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SetInventory) PARAM_SELF_PROLOGUE(AActor); PARAM_CLASS(itemtype, AInventory); PARAM_INT(amount); - PARAM_INT_DEF(ptr) { ptr = AAPTR_DEFAULT; } - PARAM_BOOL_DEF(beyondMax) { beyondMax = false; } + PARAM_INT_DEF(ptr); + PARAM_BOOL_DEF(beyondMax); bool res = false; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 103e38eff..89b3a81a3 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -8299,7 +8299,7 @@ FxExpression *FxMultiNameState::Resolve(FCompileContext &ctx) delete this; return nullptr; } - else if (!scope->IsAncestorOf(ctx.Class) && ctx.Class != RUNTIME_CLASS(AActor)) // AActor needs access to subclasses in a few places. TBD: Relax this for non-action functions? + else if (!scope->IsAncestorOf(ctx.Class)) { ScriptPosition.Message(MSG_ERROR, "'%s' is not an ancestor of '%s'", names[0].GetChars(), ctx.Class->TypeName.GetChars()); delete this; From 199e2e2f9c1904343d8c01ffbcdf81c785ed420c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 17:50:09 +0100 Subject: [PATCH 248/255] - fixed CheckRange return value. - removed the error message for multiple state blocks in DECORATE. - added some constants for state types. --- src/info.h | 15 ++++++++++++++- src/p_actionfunctions.cpp | 2 +- src/scripting/decorate/thingdef_parse.cpp | 5 ----- src/scripting/thingdef.h | 5 +++++ wadsrc/static/zscript/constants.txt | 8 ++++++++ 5 files changed, 28 insertions(+), 7 deletions(-) diff --git a/src/info.h b/src/info.h index e198bb26c..86d653fe4 100644 --- a/src/info.h +++ b/src/info.h @@ -67,6 +67,14 @@ enum EStateDefineFlags SDF_DEHACKED = 8, // Identify a state as having been modified by a dehacked lump }; +enum EStateUseFlags +{ + SUF_ACTOR = 1, + SUF_OVERLAY = 2, + SUF_WEAPON = 4, + SUF_ITEM = 8, +}; + enum EStateType : int // this must ensure proper alignment. { STATE_Actor, @@ -97,11 +105,12 @@ struct FState WORD sprite; SWORD Tics; WORD TicRange; + short Light; BYTE Frame; + BYTE UseFlags; BYTE DefineFlags; // Unused byte so let's use it during state creation. int Misc1; // Was changed to SBYTE, reverted to long for MBF compat int Misc2; // Was changed to BYTE, reverted to long for MBF compat - short Light; BYTE Fullbright:1; // State is fullbright BYTE SameFrame:1; // Ignore Frame (except when spawning actor) BYTE Fast:1; @@ -153,6 +162,10 @@ struct FState { Frame = frame - 'A'; } + inline bool CheckUse(int usetype) + { + return !!(UseFlags & usetype); + } void SetAction(VMFunction *func) { ActionFunc = func; } void ClearAction() { ActionFunc = NULL; } void SetAction(const char *name); diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index d61dc100c..d56c7ee64 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -3622,7 +3622,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, CheckRange) } } } - ACTION_RETURN_BOOL(false); + ACTION_RETURN_BOOL(true); } diff --git a/src/scripting/decorate/thingdef_parse.cpp b/src/scripting/decorate/thingdef_parse.cpp index 151d88521..490d9cf79 100644 --- a/src/scripting/decorate/thingdef_parse.cpp +++ b/src/scripting/decorate/thingdef_parse.cpp @@ -1062,11 +1062,6 @@ static void ParseActor(FScanner &sc) break; case TK_States: - if (bag.StateSet) - { - sc.ScriptMessage("'%s' contains multiple state declarations", bag.Info->TypeName.GetChars()); - FScriptPosition::ErrorCounter++; - } ParseStates(sc, bag.Info, (AActor *)bag.Info->Defaults, bag); bag.StateSet = true; break; diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 2c13d8eb7..3ff347ac6 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -63,6 +63,7 @@ class FStateDefinitions FState *laststatebeforelabel; intptr_t lastlabel; TArray StateArray; + uint8_t UseType; static FStateDefine *FindStateLabelInList(TArray &list, FName name, bool create); static FStateLabels *CreateStateLabelList(TArray &statelist); @@ -74,6 +75,10 @@ class FStateDefinitions FState *ResolveGotoLabel(AActor *actor, PClassActor *mytype, char *name); static void FixStatePointers(PClassActor *actor, TArray & list); void ResolveGotoLabels(PClassActor *actor, AActor *defaults, TArray & list); + void SetUseType(int type) + { + UseType = uint8_t(type); + } public: diff --git a/wadsrc/static/zscript/constants.txt b/wadsrc/static/zscript/constants.txt index 7c3038a74..5e47bbc7e 100644 --- a/wadsrc/static/zscript/constants.txt +++ b/wadsrc/static/zscript/constants.txt @@ -1,6 +1,14 @@ // for flag changer functions. const FLAG_NO_CHANGE = -1; +enum EStateUseFlags +{ + SUF_ACTOR = 1, + SUF_OVERLAY = 2, + SUF_WEAPON = 4, + SUF_ITEM = 8, +}; + // Flags for A_PainAttack enum EPainAttackFlags { From a8e2f4d539b6ec525259a3b70eddf8f46d8f74de Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 18:11:44 +0100 Subject: [PATCH 249/255] - added missing 'action' qualifiers to A_Warp and A_Teleport --- wadsrc/static/zscript/actor.txt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index f3cd9aa3c..441db62f3 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -370,8 +370,8 @@ class Actor : Thinker native native void A_Weave(int xspeed, int yspeed, float xdist, float ydist); - native state, bool A_Teleport(statelabel teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 128, int ptr = AAPTR_DEFAULT); - native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, statelabel success_state = null, float heightoffset = 0, float radiusoffset = 0, float pitch = 0); + action native state, bool A_Teleport(statelabel teleportstate = null, class targettype = "BossSpot", class fogtype = "TeleportFog", int flags = 0, float mindist = 0, float maxdist = 128, int ptr = AAPTR_DEFAULT); + action native state, bool A_Warp(int ptr_destination, float xofs = 0, float yofs = 0, float zofs = 0, float angle = 0, int flags = 0, statelabel success_state = null, float heightoffset = 0, float radiusoffset = 0, float pitch = 0); native void A_CountdownArg(int argnum, statelabel targstate = null); native state A_MonsterRefire(int chance, statelabel label); native void A_LookEx(int flags = 0, float minseedist = 0, float maxseedist = 0, float maxheardist = 0, float fov = 0, statelabel label = null); From 384f4fe7cea52be6a09b97455071e2a11858e3c7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 18:31:12 +0100 Subject: [PATCH 250/255] - added a 'DefaultStateUsage' property so that this setting can be properly set up for the classes that can inject states into other actors. --- src/info.cpp | 1 + src/info.h | 1 + src/scripting/codegeneration/codegen.cpp | 2 + src/scripting/thingdef_properties.cpp | 9 ++++ wadsrc/static/zscript/actor.txt | 1 + wadsrc/static/zscript/shared/inventory.txt | 63 ++++++++++++---------- 6 files changed, 49 insertions(+), 28 deletions(-) diff --git a/src/info.cpp b/src/info.cpp index 83b455fb4..e771108c3 100644 --- a/src/info.cpp +++ b/src/info.cpp @@ -285,6 +285,7 @@ void PClassActor::DeriveData(PClass *newclass) assert(newclass->IsKindOf(RUNTIME_CLASS(PClassActor))); PClassActor *newa = static_cast(newclass); + newa->DefaultStateUsage = DefaultStateUsage; newa->Obituary = Obituary; newa->HitObituary = HitObituary; newa->DeathHeight = DeathHeight; diff --git a/src/info.h b/src/info.h index 86d653fe4..0b7d4dfc3 100644 --- a/src/info.h +++ b/src/info.h @@ -271,6 +271,7 @@ public: PClassActor *Replacee; int NumOwnedStates; BYTE GameFilter; + uint8_t DefaultStateUsage; // state flag defaults for blocks without a qualifier. WORD SpawnID; WORD ConversationID; SWORD DoomEdNum; diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 89b3a81a3..24da14321 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -6121,6 +6121,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) case NAME_Name: case NAME_Color: case NAME_Sound: + case NAME_State: if (CheckArgSize(MethodName, ArgList, 1, 1, ScriptPosition)) { PType *type = @@ -6130,6 +6131,7 @@ FxExpression *FxFunctionCall::Resolve(FCompileContext& ctx) MethodName == NAME_Float ? TypeFloat64 : MethodName == NAME_Double ? TypeFloat64 : MethodName == NAME_Name ? TypeName : + MethodName == NAME_State ? TypeState : MethodName == NAME_Color ? TypeColor : (PType*)TypeSound; func = new FxTypeCast(ArgList[0], type, true, true); diff --git a/src/scripting/thingdef_properties.cpp b/src/scripting/thingdef_properties.cpp index 45d78557c..7faab937b 100644 --- a/src/scripting/thingdef_properties.cpp +++ b/src/scripting/thingdef_properties.cpp @@ -533,6 +533,15 @@ DEFINE_PROPERTY(skip_super, 0, Actor) ResetBaggage (&bag, RUNTIME_CLASS(AActor)); } +//========================================================================== +// for internal use only - please do not document! +//========================================================================== +DEFINE_PROPERTY(defaultstateusage, I, Actor) +{ + PROP_INT_PARM(use, 0); + static_cast(bag.Info)->DefaultStateUsage = use; + +} //========================================================================== // //========================================================================== diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index 441db62f3..c55c7cd3a 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -45,6 +45,7 @@ class Actor : Thinker native StencilColor "00 00 00"; VisibleAngles 0, 0; VisiblePitch 0, 0; + DefaultStateUsage SUF_ACTOR|SUF_OVERLAY; } // Functions diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index e38ddbdb1..9bc99cefb 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -88,9 +88,9 @@ class ScoreItem : Inventory native Default { Height 10; - +COUNTITEM; + +COUNTITEM Inventory.Amount 1; - +Inventory.ALWAYSPICKUP; + +Inventory.ALWAYSPICKUP } } @@ -98,7 +98,7 @@ class Ammo : Inventory native { Default { - +INVENTORY.KEEPDEPLETED; + +INVENTORY.KEEPDEPLETED Inventory.PickupSound "misc/ammo_pkup"; } } @@ -119,7 +119,7 @@ class BasicArmor : Armor native { Default { - +Inventory.KEEPDEPLETED; + +Inventory.KEEPDEPLETED } } @@ -127,8 +127,8 @@ class BasicArmorBonus : Armor native { Default { - +Inventory.AUTOACTIVATE; - +Inventory.ALWAYSPICKUP; + +Inventory.AUTOACTIVATE + +Inventory.ALWAYSPICKUP Inventory.MaxAmount 0; Armor.SavePercent 33.335; } @@ -147,8 +147,8 @@ class HexenArmor : Armor native { Default { - +Inventory.KEEPDEPLETED; - +Inventory.UNDROPPABLE; + +Inventory.KEEPDEPLETED + +Inventory.UNDROPPABLE } } @@ -156,7 +156,13 @@ class DehackedPickup : Inventory native {} class FakeInventory : Inventory native {} -class CustomInventory : StateProvider native {} +class CustomInventory : StateProvider native +{ + Default + { + DefaultStateUsage SUF_ACTOR|SUF_OVERLAY|SUF_ITEM; + } +} class Health : Inventory native { @@ -173,7 +179,7 @@ class HealthPickup : Inventory native Default { Inventory.DefMaxAmount; - +INVENTORY.INVBAR; + +INVENTORY.INVBAR } } @@ -192,8 +198,8 @@ class PowerupGiver : Inventory native Default { Inventory.DefMaxAmount; - +INVENTORY.INVBAR; - +INVENTORY.FANCYPICKUPSOUND; + +INVENTORY.INVBAR + +INVENTORY.FANCYPICKUPSOUND Inventory.PickupSound "misc/p_pkup"; } } @@ -215,7 +221,7 @@ class PowerStrength : Powerup native { Powerup.Duration 1; Powerup.Color "ff 00 00", 0.5; - +INVENTORY.HUBPOWER; + +INVENTORY.HUBPOWER } } @@ -245,7 +251,7 @@ class PowerShadow : PowerInvisibility { Default { - +INVENTORY.HUBPOWER; + +INVENTORY.HUBPOWER Powerup.Duration -55; Powerup.Strength 75; Powerup.Mode "Cumulative"; @@ -267,7 +273,7 @@ class PowerMask : PowerIronFeet native { Powerup.Duration -80; Powerup.Color "00 00 00", 0; - +INVENTORY.HUBPOWER; + +INVENTORY.HUBPOWER Inventory.Icon "I_MASK"; } } @@ -287,7 +293,7 @@ class PowerFlight : Powerup native Default { Powerup.Duration -60; - +INVENTORY.HUBPOWER; + +INVENTORY.HUBPOWER } } @@ -297,7 +303,7 @@ class PowerWeaponLevel2 : Powerup native { Powerup.Duration -40; Inventory.Icon "SPINBK0"; - +INVENTORY.NOTELEPORTFREEZE; + +INVENTORY.NOTELEPORTFREEZE } } @@ -308,7 +314,7 @@ class PowerSpeed : Powerup native Powerup.Duration -45; Speed 1.5; Inventory.Icon "SPBOOT0"; - +INVENTORY.NOTELEPORTFREEZE; + +INVENTORY.NOTELEPORTFREEZE } } @@ -318,8 +324,8 @@ class PlayerSpeedTrail native { Default { - +NOBLOCKMAP; - +NOGRAVITY; + +NOBLOCKMAP + +NOGRAVITY Alpha 0.6; RenderStyle "Translucent"; } @@ -339,7 +345,7 @@ class PowerTargeter : Powerup native Default { Powerup.Duration -160; - +INVENTORY.HUBPOWER; + +INVENTORY.HUBPOWER } States { @@ -374,7 +380,7 @@ class PowerScanner : Powerup native Default { Powerup.Duration -80; - +INVENTORY.HUBPOWER; + +INVENTORY.HUBPOWER } } @@ -445,8 +451,8 @@ class PuzzleItem : Inventory native { Default { - +NOGRAVITY; - +INVENTORY.INVBAR; + +NOGRAVITY + +INVENTORY.INVBAR Inventory.DefMaxAmount; Inventory.UseSound "PuzzleSuccess"; Inventory.PickupSound "misc/i_pkup"; @@ -462,7 +468,8 @@ class Weapon : StateProvider native Weapon.BobSpeed 1.0; Weapon.BobRangeX 1.0; Weapon.BobRangeY 1.0; - +WEAPONSPAWN; + +WEAPONSPAWN + DefaultStateUsage SUF_ACTOR|SUF_OVERLAY|SUF_ITEM; } States { @@ -491,9 +498,9 @@ class WeaponHolder : Inventory native { Default { - +NOBLOCKMAP; - +NOSECTOR; - +INVENTORY.UNDROPPABLE; + +NOBLOCKMAP + +NOSECTOR + +INVENTORY.UNDROPPABLE } } From 7bcd83f0c1c8646cecb5421b13b58d104fad1f97 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 19:35:29 +0100 Subject: [PATCH 251/255] - parser for states flags. --- src/resourcefiles/file_zip.cpp | 82 ++++++++++++---------- src/scripting/decorate/thingdef_states.cpp | 17 +++++ src/scripting/thingdef.h | 6 -- src/scripting/zscript/ast.cpp | 1 + src/scripting/zscript/zcc-parse.lemon | 23 ++++++ src/scripting/zscript/zcc_parser.h | 1 + 6 files changed, 87 insertions(+), 43 deletions(-) diff --git a/src/resourcefiles/file_zip.cpp b/src/resourcefiles/file_zip.cpp index 8713fe554..3f4548040 100644 --- a/src/resourcefiles/file_zip.cpp +++ b/src/resourcefiles/file_zip.cpp @@ -53,50 +53,58 @@ static bool UncompressZipLump(char *Cache, FileReader *Reader, int Method, int LumpSize, int CompressedSize, int GPFlags) { - switch (Method) + try { - case METHOD_STORED: - { - Reader->Read(Cache, LumpSize); - break; - } + switch (Method) + { + case METHOD_STORED: + { + Reader->Read(Cache, LumpSize); + break; + } - case METHOD_DEFLATE: - { - FileReaderZ frz(*Reader, true); - frz.Read(Cache, LumpSize); - break; - } + case METHOD_DEFLATE: + { + FileReaderZ frz(*Reader, true); + frz.Read(Cache, LumpSize); + break; + } - case METHOD_BZIP2: - { - FileReaderBZ2 frz(*Reader); - frz.Read(Cache, LumpSize); - break; - } + case METHOD_BZIP2: + { + FileReaderBZ2 frz(*Reader); + frz.Read(Cache, LumpSize); + break; + } - case METHOD_LZMA: - { - FileReaderLZMA frz(*Reader, LumpSize, true); - frz.Read(Cache, LumpSize); - break; - } + case METHOD_LZMA: + { + FileReaderLZMA frz(*Reader, LumpSize, true); + frz.Read(Cache, LumpSize); + break; + } - case METHOD_IMPLODE: - { - FZipExploder exploder; - exploder.Explode((unsigned char *)Cache, LumpSize, Reader, CompressedSize, GPFlags); - break; - } + case METHOD_IMPLODE: + { + FZipExploder exploder; + exploder.Explode((unsigned char *)Cache, LumpSize, Reader, CompressedSize, GPFlags); + break; + } - case METHOD_SHRINK: - { - ShrinkLoop((unsigned char *)Cache, LumpSize, Reader, CompressedSize); - break; - } + case METHOD_SHRINK: + { + ShrinkLoop((unsigned char *)Cache, LumpSize, Reader, CompressedSize); + break; + } - default: - assert(0); + default: + assert(0); + return false; + } + } + catch (CRecoverableError &err) + { + Printf("%s\n", err.GetMessage()); return false; } return true; diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index c9be2c747..db424ed44 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -144,6 +144,22 @@ void ParseStates(FScanner &sc, PClassActor * actor, AActor * defaults, Baggage & char lastsprite[5] = ""; FxExpression *ScriptCode; FArgumentList *args = nullptr; + int flagdef = actor->DefaultStateUsage; + + if (sc.CheckString("(")) + { + flagdef = 0; + do + { + sc.MustGetString(); + if (sc.Compare("Actor")) flagdef |= SUF_ACTOR; + else if (sc.Compare("Overlay")) flagdef |= SUF_OVERLAY; + else if (sc.Compare("Weapon")) flagdef |= SUF_WEAPON; + else if (sc.Compare("Item")) flagdef |= SUF_ITEM; + else sc.ScriptError("Unknown state block qualifier %s", sc.String); + } while (sc.CheckString(",")); + sc.MustGetStringName(")"); + } sc.MustGetStringName ("{"); sc.SetEscape(false); // disable escape sequences in the state parser @@ -151,6 +167,7 @@ void ParseStates(FScanner &sc, PClassActor * actor, AActor * defaults, Baggage & { ScriptCode = nullptr; memset(&state,0,sizeof(state)); + state.UseFlags = (uint8_t)flagdef; statestring = ParseStateString(sc); if (!statestring.CompareNoCase("GOTO")) { diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index 3ff347ac6..eeea42f87 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -63,7 +63,6 @@ class FStateDefinitions FState *laststatebeforelabel; intptr_t lastlabel; TArray StateArray; - uint8_t UseType; static FStateDefine *FindStateLabelInList(TArray &list, FName name, bool create); static FStateLabels *CreateStateLabelList(TArray &statelist); @@ -75,11 +74,6 @@ class FStateDefinitions FState *ResolveGotoLabel(AActor *actor, PClassActor *mytype, char *name); static void FixStatePointers(PClassActor *actor, TArray & list); void ResolveGotoLabels(PClassActor *actor, AActor *defaults, TArray & list); - void SetUseType(int type) - { - UseType = uint8_t(type); - } - public: FStateDefinitions() diff --git a/src/scripting/zscript/ast.cpp b/src/scripting/zscript/ast.cpp index cb0240dea..c24867837 100644 --- a/src/scripting/zscript/ast.cpp +++ b/src/scripting/zscript/ast.cpp @@ -358,6 +358,7 @@ static void PrintStates(FLispString &out, ZCC_TreeNode *node) ZCC_States *snode = (ZCC_States *)node; out.Break(); out.Open("states"); + PrintNodes(out, snode->Flags, false, true); PrintNodes(out, snode->Body, false, true); out.Close(); } diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 6caef777e..1882aa41c 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -418,14 +418,37 @@ enumerator(X) ::= IDENTIFIER(A) EQ expr(B). /* Expression must be constant. */ %type state_call_params {ZCC_FuncParm *} %type state_opts {StateOpts} +%type states_opts { ZCC_Identifier *} +%type states_opt { ZCC_Identifier *} states_def(X) ::= STATES(T) scanner_mode LBRACE states_body(A) RBRACE. +states_def(X) ::= STATES(T) states_opts(B) scanner_mode LBRACE states_body(A) RBRACE. { NEW_AST_NODE(States,def,T); + def->Flags = B; def->Body = A; X = def; } +states_opts(X) ::= . { X = nullptr; } +states_opts(X) ::= LPAREN states_opt(A) RPAREN. { X = A; /*X-overwrites-A*/ } + +states_opt(X) ::= IDENTIFIER(A). +{ + NEW_AST_NODE(Identifier,id,A); + id->Id = A.Name(); + X = id; +} + +states_opt(X) ::= states_opt(A) COMMA IDENTIFIER(B). +{ + NEW_AST_NODE(Identifier,id,B); + id->Id = B.Name(); + X = A; /*X-overwrites-A*/ + X->AppendSibling(id); +} + + /* We use a special scanner mode to allow for sprite names and frame characters * to not be quoted even if they contain special characters. The scanner_mode * nonterminal is used to enter this mode. The scanner automatically leaves it diff --git a/src/scripting/zscript/zcc_parser.h b/src/scripting/zscript/zcc_parser.h index ec8bd956a..1a187af82 100644 --- a/src/scripting/zscript/zcc_parser.h +++ b/src/scripting/zscript/zcc_parser.h @@ -228,6 +228,7 @@ struct ZCC_EnumTerminator : ZCC_TreeNode struct ZCC_States : ZCC_TreeNode { struct ZCC_StatePart *Body; + ZCC_Identifier *Flags; }; struct ZCC_StatePart : ZCC_TreeNode From c797319314ec1f3e28de335e4b6a07e9229df37c Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 20:00:01 +0100 Subject: [PATCH 252/255] - fixed parser for state block options. - fixed incorrect flags for weapons. --- src/scripting/zscript/zcc-parse.lemon | 1 - wadsrc/static/zscript/shared/inventory.txt | 2 +- 2 files changed, 1 insertion(+), 2 deletions(-) diff --git a/src/scripting/zscript/zcc-parse.lemon b/src/scripting/zscript/zcc-parse.lemon index 1882aa41c..a29d3d943 100644 --- a/src/scripting/zscript/zcc-parse.lemon +++ b/src/scripting/zscript/zcc-parse.lemon @@ -421,7 +421,6 @@ enumerator(X) ::= IDENTIFIER(A) EQ expr(B). /* Expression must be constant. */ %type states_opts { ZCC_Identifier *} %type states_opt { ZCC_Identifier *} -states_def(X) ::= STATES(T) scanner_mode LBRACE states_body(A) RBRACE. states_def(X) ::= STATES(T) states_opts(B) scanner_mode LBRACE states_body(A) RBRACE. { NEW_AST_NODE(States,def,T); diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index 9bc99cefb..c6fb203a8 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -469,7 +469,7 @@ class Weapon : StateProvider native Weapon.BobRangeX 1.0; Weapon.BobRangeY 1.0; +WEAPONSPAWN - DefaultStateUsage SUF_ACTOR|SUF_OVERLAY|SUF_ITEM; + DefaultStateUsage SUF_ACTOR|SUF_OVERLAY|SUF_WEAPON; } States { From 4f998fa87951c1c2f5324a3688b0e721fccd49c4 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Mon, 14 Nov 2016 23:24:10 +0100 Subject: [PATCH 253/255] - finished the state usage parser. - added state usage specifiers to Actor and Inventory. The states in these classes must be set to full access so that any existing mod can link to them. --- src/namedef.h | 1 + src/scripting/zscript/zcc_compile.cpp | 33 ++++++++++++++++++++++ wadsrc/static/zscript/actor.txt | 2 +- wadsrc/static/zscript/shared/inventory.txt | 2 +- 4 files changed, 36 insertions(+), 2 deletions(-) diff --git a/src/namedef.h b/src/namedef.h index f8475f716..e9324d44b 100644 --- a/src/namedef.h +++ b/src/namedef.h @@ -736,3 +736,4 @@ xx(DamageFunction) xx(Length) xx(Unit) xx(StateLabel) +xx(Overlay) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index b8c0a2a38..2603fea7d 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2387,6 +2387,39 @@ void ZCCCompiler::CompileStates() for (auto s : c->States) { + int flags; + if (s->Flags != nullptr) + { + flags = 0; + auto p = s->Flags; + do + { + switch (p->Id) + { + case NAME_Actor: + flags |= SUF_ACTOR; + break; + case NAME_Overlay: + flags |= SUF_OVERLAY; + break; + case NAME_Weapon: + flags |= SUF_WEAPON; + break; + case NAME_Item: + flags |= SUF_ITEM; + break; + default: + Error(p, "Unknown States qualifier %s", FName(p->Id).GetChars()); + break; + } + + p = static_cast(p->SiblingNext); + } while (p != s->Flags); + } + else + { + flags = static_cast(c->Type())->DefaultStateUsage; + } auto st = s->Body; if (st != nullptr) do { diff --git a/wadsrc/static/zscript/actor.txt b/wadsrc/static/zscript/actor.txt index c55c7cd3a..09b5683c8 100644 --- a/wadsrc/static/zscript/actor.txt +++ b/wadsrc/static/zscript/actor.txt @@ -489,7 +489,7 @@ class Actor : Thinker native return ACS_ExecuteAlways(-int(script), mapnum, arg1, arg2, arg3); } - States + States(Actor, Overlay, Weapon, Item) { Spawn: TNT1 A -1; diff --git a/wadsrc/static/zscript/shared/inventory.txt b/wadsrc/static/zscript/shared/inventory.txt index c6fb203a8..a6d7af835 100644 --- a/wadsrc/static/zscript/shared/inventory.txt +++ b/wadsrc/static/zscript/shared/inventory.txt @@ -16,7 +16,7 @@ class Inventory : Actor native private native void A_RestoreSpecialThing1(); private native void A_RestoreSpecialThing2(); - States + States(Actor, Overlay, Weapon, Item) { HideDoomish: TNT1 A 1050; From 647e1399f13606f65207320d1254d3fc318b71a7 Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 15 Nov 2016 00:18:57 +0100 Subject: [PATCH 254/255] - added runtime checks for the state usage flags. --- src/p_actionfunctions.cpp | 7 +++++++ src/p_mobj.cpp | 8 ++++++++ src/p_pspr.cpp | 10 ++++++++++ src/scripting/zscript/zcc_compile.cpp | 1 + 4 files changed, 26 insertions(+) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index d56c7ee64..1c0f846b9 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -128,6 +128,13 @@ bool ACustomInventory::CallStateChain (AActor *actor, FState *state) while (state != NULL) { + if (!(state->UseFlags & SUF_ITEM)) + { + auto so = FState::StaticFindStateOwner(state); + Printf("State %s.%d not flagged for use in CustomInventory state chains.\n", so->TypeName.GetChars(), int(state - so->OwnedStates)); + return false; + } + this->state = state; nextstate = NULL; // assume no jump diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index 05cfb7cc4..c7f181838 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -626,6 +626,14 @@ bool AActor::SetState (FState *newstate, bool nofunction) { prevsprite = -1; } + if (!(newstate->UseFlags & SUF_ACTOR)) + { + auto so = FState::StaticFindStateOwner(newstate); + Printf("State %s.%d in %s not flagged for use as an actor sprite\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates), GetClass()->TypeName.GetChars()); + state = nullptr; + Destroy(); + return false; + } state = newstate; tics = GetTics(newstate); renderflags = (renderflags & ~RF_FULLBRIGHT) | ActorRenderFlags::FromInt (newstate->GetFullbright()); diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index f371c6888..1d39d907e 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -296,6 +296,16 @@ void DPSprite::SetState(FState *newstate, bool pending) Destroy(); return; } + + if (!(newstate->UseFlags & (SUF_OVERLAY|SUF_WEAPON))) // Weapon and overlay are mostly the same, the main difference is that weapon states restrict the self pointer to class Actor. + { + auto so = FState::StaticFindStateOwner(newstate); + Printf("State %s.%d not flagged for use in overlays or weapons\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates)); + State = nullptr; + Destroy(); + return; + } + State = newstate; if (newstate->sprite != SPR_FIXED) diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 2603fea7d..48be582cf 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2437,6 +2437,7 @@ void ZCCCompiler::CompileStates() auto sl = static_cast(st); FState state; memset(&state, 0, sizeof(state)); + state.UseFlags = flags; if (sl->Sprite->Len() != 4) { Error(sl, "Sprite name must be exactly 4 characters. Found '%s'", sl->Sprite->GetChars()); From 96d093d01f0675d65873c30f80edc026affe896b Mon Sep 17 00:00:00 2001 From: Christoph Oelckers Date: Tue, 15 Nov 2016 11:21:08 +0100 Subject: [PATCH 255/255] - added compile time checks for bad state links and state label references. - preserve a state's source line information for the postprocessing phase so that the checker can output more useful information. - added missing check for weapon psprites to DPSprite::SetState. --- src/p_actionfunctions.cpp | 2 +- src/p_mobj.cpp | 2 +- src/p_pspr.cpp | 13 +- src/p_states.cpp | 5 +- src/scripting/codegeneration/codegen.cpp | 5 +- src/scripting/decorate/olddecorations.cpp | 25 ++-- src/scripting/decorate/thingdef_states.cpp | 6 +- src/scripting/thingdef.cpp | 149 +++++++++++++++++---- src/scripting/thingdef.h | 9 +- src/scripting/zscript/zcc_compile.cpp | 8 +- 10 files changed, 179 insertions(+), 45 deletions(-) diff --git a/src/p_actionfunctions.cpp b/src/p_actionfunctions.cpp index 1c0f846b9..d59b45256 100644 --- a/src/p_actionfunctions.cpp +++ b/src/p_actionfunctions.cpp @@ -131,7 +131,7 @@ bool ACustomInventory::CallStateChain (AActor *actor, FState *state) if (!(state->UseFlags & SUF_ITEM)) { auto so = FState::StaticFindStateOwner(state); - Printf("State %s.%d not flagged for use in CustomInventory state chains.\n", so->TypeName.GetChars(), int(state - so->OwnedStates)); + Printf(TEXTCOLOR_RED "State %s.%d not flagged for use in CustomInventory state chains.\n", so->TypeName.GetChars(), int(state - so->OwnedStates)); return false; } diff --git a/src/p_mobj.cpp b/src/p_mobj.cpp index c7f181838..ce74684cc 100644 --- a/src/p_mobj.cpp +++ b/src/p_mobj.cpp @@ -629,7 +629,7 @@ bool AActor::SetState (FState *newstate, bool nofunction) if (!(newstate->UseFlags & SUF_ACTOR)) { auto so = FState::StaticFindStateOwner(newstate); - Printf("State %s.%d in %s not flagged for use as an actor sprite\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates), GetClass()->TypeName.GetChars()); + Printf(TEXTCOLOR_RED "State %s.%d in %s not flagged for use as an actor sprite\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates), GetClass()->TypeName.GetChars()); state = nullptr; Destroy(); return false; diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index 1d39d907e..9ae7b530d 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -300,11 +300,22 @@ void DPSprite::SetState(FState *newstate, bool pending) if (!(newstate->UseFlags & (SUF_OVERLAY|SUF_WEAPON))) // Weapon and overlay are mostly the same, the main difference is that weapon states restrict the self pointer to class Actor. { auto so = FState::StaticFindStateOwner(newstate); - Printf("State %s.%d not flagged for use in overlays or weapons\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates)); + Printf(TEXTCOLOR_RED "State %s.%d not flagged for use in overlays or weapons\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates)); State = nullptr; Destroy(); return; } + else if (!(newstate->UseFlags & SUF_WEAPON)) + { + if (Caller->IsKindOf(RUNTIME_CLASS(AWeapon))) + { + auto so = FState::StaticFindStateOwner(newstate); + Printf(TEXTCOLOR_RED "State %s.%d not flagged for use in weapons\n", so->TypeName.GetChars(), int(newstate - so->OwnedStates)); + State = nullptr; + Destroy(); + return; + } + } State = newstate; diff --git a/src/p_states.cpp b/src/p_states.cpp index 2c1b88eaf..f7f237c77 100644 --- a/src/p_states.cpp +++ b/src/p_states.cpp @@ -913,7 +913,7 @@ bool FStateDefinitions::SetLoop() // //========================================================================== -int FStateDefinitions::AddStates(FState *state, const char *framechars) +int FStateDefinitions::AddStates(FState *state, const char *framechars, const FScriptPosition &sc) { bool error = false; int frame = 0; @@ -939,6 +939,7 @@ int FStateDefinitions::AddStates(FState *state, const char *framechars) state->Frame = frame; state->SameFrame = noframe; StateArray.Push(*state); + SourceLines.Push(sc); ++count; // NODELAY flag is not carried past the first state @@ -968,6 +969,7 @@ int FStateDefinitions::FinishStates(PClassActor *actor, AActor *defaults) memcpy(realstates, &StateArray[0], count*sizeof(FState)); actor->OwnedStates = realstates; actor->NumOwnedStates = count; + SaveStateSourceLines(realstates, SourceLines); // adjust the state pointers // In the case new states are added these must be adjusted, too! @@ -1012,6 +1014,7 @@ int FStateDefinitions::FinishStates(PClassActor *actor, AActor *defaults) } + //========================================================================== // // Prints all state label info to the logfile diff --git a/src/scripting/codegeneration/codegen.cpp b/src/scripting/codegeneration/codegen.cpp index 24da14321..626dcde24 100644 --- a/src/scripting/codegeneration/codegen.cpp +++ b/src/scripting/codegeneration/codegen.cpp @@ -5119,13 +5119,14 @@ FxExpression *FxIdentifier::Resolve(FCompileContext& ctx) delete this; return newex->Resolve(ctx); } - else if (ctx.FromDecorate && ctx.Class->IsDescendantOf(RUNTIME_CLASS(AStateProvider)) && sym->IsKindOf(RUNTIME_CLASS(PField))) + // Do this check for ZScript as well, so that a clearer error message can be printed. MSG_OPTERROR will default to MSG_ERROR there. + else if (ctx.Function->Variants[0].SelfClass != ctx.Class && sym->IsKindOf(RUNTIME_CLASS(PField))) { FxExpression *self = new FxSelf(ScriptPosition, true); self = self->Resolve(ctx); newex = ResolveMember(ctx, ctx.Class, self, ctx.Class); ABORT(newex); - ScriptPosition.Message(MSG_DEBUGWARN, "Self pointer used in ambiguous context; VM execution may abort!"); + ScriptPosition.Message(MSG_OPTERROR, "Self pointer used in ambiguous context; VM execution may abort!"); ctx.Unsafe = true; } else diff --git a/src/scripting/decorate/olddecorations.cpp b/src/scripting/decorate/olddecorations.cpp index d1b79328f..a4cf20de4 100644 --- a/src/scripting/decorate/olddecorations.cpp +++ b/src/scripting/decorate/olddecorations.cpp @@ -103,8 +103,8 @@ IMPLEMENT_CLASS(AFakeInventory, false, false, false, false) // PRIVATE FUNCTION PROTOTYPES --------------------------------------------- static void ParseInsideDecoration (Baggage &bag, AActor *defaults, - FExtraInfo &extra, EDefinitionType def, FScanner &sc, TArray &StateArray); -static void ParseSpriteFrames (PClassActor *info, TArray &states, FScanner &sc); + FExtraInfo &extra, EDefinitionType def, FScanner &sc, TArray &StateArray, TArray &SourceLines); +static void ParseSpriteFrames (PClassActor *info, TArray &states, TArray &SourceLines, FScanner &sc); // PRIVATE DATA DEFINITIONS ------------------------------------------------ @@ -147,6 +147,7 @@ void ParseOldDecoration(FScanner &sc, EDefinitionType def) { Baggage bag; TArray StateArray; + TArray SourceLines; FExtraInfo extra; PClassActor *type; PClassActor *parent; @@ -168,7 +169,7 @@ void ParseOldDecoration(FScanner &sc, EDefinitionType def) sc.MustGetStringName("{"); memset (&extra, 0, sizeof(extra)); - ParseInsideDecoration (bag, (AActor *)(type->Defaults), extra, def, sc, StateArray); + ParseInsideDecoration (bag, (AActor *)(type->Defaults), extra, def, sc, StateArray, SourceLines); bag.Info->NumOwnedStates = StateArray.Size(); if (bag.Info->NumOwnedStates == 0) @@ -192,11 +193,14 @@ void ParseOldDecoration(FScanner &sc, EDefinitionType def) { // Make a copy of the final frozen frame for A_FreezeDeathChunks FState icecopy = StateArray[extra.IceDeathEnd-1]; + FScriptPosition icepos = SourceLines[extra.IceDeathEnd - 1]; StateArray.Push (icecopy); + SourceLines.Push(icepos); type->NumOwnedStates += 1; } type->OwnedStates = new FState[type->NumOwnedStates]; + SaveStateSourceLines(type->OwnedStates, SourceLines); memcpy (type->OwnedStates, &StateArray[0], type->NumOwnedStates * sizeof(type->OwnedStates[0])); if (type->NumOwnedStates == 1) { @@ -353,7 +357,7 @@ void ParseOldDecoration(FScanner &sc, EDefinitionType def) //========================================================================== static void ParseInsideDecoration (Baggage &bag, AActor *defaults, - FExtraInfo &extra, EDefinitionType def, FScanner &sc, TArray &StateArray) + FExtraInfo &extra, EDefinitionType def, FScanner &sc, TArray &StateArray, TArray &SourceLines) { AFakeInventory *const inv = static_cast(defaults); char sprite[5] = "TNT1"; @@ -403,7 +407,7 @@ static void ParseInsideDecoration (Baggage &bag, AActor *defaults, { sc.MustGetString (); extra.SpawnStart = StateArray.Size(); - ParseSpriteFrames (bag.Info, StateArray, sc); + ParseSpriteFrames (bag.Info, StateArray, SourceLines, sc); extra.SpawnEnd = StateArray.Size(); } else if ((def == DEF_BreakableDecoration || def == DEF_Projectile) && @@ -411,21 +415,21 @@ static void ParseInsideDecoration (Baggage &bag, AActor *defaults, { sc.MustGetString (); extra.DeathStart = StateArray.Size(); - ParseSpriteFrames (bag.Info, StateArray, sc); + ParseSpriteFrames (bag.Info, StateArray, SourceLines, sc); extra.DeathEnd = StateArray.Size(); } else if (def == DEF_BreakableDecoration && sc.Compare ("IceDeathFrames")) { sc.MustGetString (); extra.IceDeathStart = StateArray.Size(); - ParseSpriteFrames (bag.Info, StateArray, sc); + ParseSpriteFrames (bag.Info, StateArray, SourceLines, sc); extra.IceDeathEnd = StateArray.Size(); } else if (def == DEF_BreakableDecoration && sc.Compare ("BurnDeathFrames")) { sc.MustGetString (); extra.FireDeathStart = StateArray.Size(); - ParseSpriteFrames (bag.Info, StateArray, sc); + ParseSpriteFrames (bag.Info, StateArray, SourceLines, sc); extra.FireDeathEnd = StateArray.Size(); } else if (def == DEF_BreakableDecoration && sc.Compare ("GenericIceDeath")) @@ -650,12 +654,13 @@ static void ParseInsideDecoration (Baggage &bag, AActor *defaults, // "10:A, 15:B, 8:C, 6:B" //========================================================================== -static void ParseSpriteFrames (PClassActor *info, TArray &states, FScanner &sc) +static void ParseSpriteFrames (PClassActor *info, TArray &states, TArray &SourceLines, FScanner &sc) { FState state; char *token = strtok (sc.String, ",\t\n\r"); memset (&state, 0, sizeof(state)); + state.UseFlags = info->DefaultStateUsage; while (token != NULL) { @@ -705,6 +710,7 @@ static void ParseSpriteFrames (PClassActor *info, TArray &states, FScann if (!firstState) { states.Push (state); + SourceLines.Push(sc); } firstState = false; state.Frame = *token-'A'; @@ -714,6 +720,7 @@ static void ParseSpriteFrames (PClassActor *info, TArray &states, FScann if (!firstState) { states.Push (state); + SourceLines.Push(sc); } token = strtok (NULL, ",\t\n\r"); diff --git a/src/scripting/decorate/thingdef_states.cpp b/src/scripting/decorate/thingdef_states.cpp index db424ed44..cad542d1b 100644 --- a/src/scripting/decorate/thingdef_states.cpp +++ b/src/scripting/decorate/thingdef_states.cpp @@ -145,6 +145,7 @@ void ParseStates(FScanner &sc, PClassActor * actor, AActor * defaults, Baggage & FxExpression *ScriptCode; FArgumentList *args = nullptr; int flagdef = actor->DefaultStateUsage; + FScriptPosition scp; if (sc.CheckString("(")) { @@ -238,6 +239,7 @@ do_stop: sc.ScriptError ("Sprite names must be exactly 4 characters\n"); } + scp = sc; state.sprite = GetSpriteIndex(statestring); state.Misc1 = state.Misc2 = 0; sc.MustGetString(); @@ -341,10 +343,10 @@ do_stop: endofstate: if (ScriptCode != nullptr) { - auto funcsym = CreateAnonymousFunction(actor, nullptr, VARF_Method | VARF_Action); + auto funcsym = CreateAnonymousFunction(actor, nullptr, state.UseFlags); state.ActionFunc = FunctionBuildList.AddFunction(funcsym, ScriptCode, FStringf("%s.StateFunction.%d", actor->TypeName.GetChars(), bag.statedef.GetStateCount()), true); } - int count = bag.statedef.AddStates(&state, statestring); + int count = bag.statedef.AddStates(&state, statestring, scp); if (count < 0) { sc.ScriptError("Invalid frame character string '%s'", statestring.GetChars()); diff --git a/src/scripting/thingdef.cpp b/src/scripting/thingdef.cpp index d163ffb38..bf6b08ea7 100644 --- a/src/scripting/thingdef.cpp +++ b/src/scripting/thingdef.cpp @@ -72,6 +72,30 @@ void InitThingdef(); // STATIC FUNCTION PROTOTYPES -------------------------------------------- PClassActor *QuestItemClasses[31]; + +static TMap StateSourceLines; +static FScriptPosition unknownstatesource("unknown file", 0); + +//========================================================================== +// +// Saves the state's source lines for error messages during postprocessing +// +//========================================================================== + +void SaveStateSourceLines(FState *firststate, TArray &positions) +{ + for (unsigned i = 0; i < positions.Size(); i++) + { + StateSourceLines[firststate + i] = positions[i]; + } +} + +FScriptPosition & GetStateSource(FState *state) +{ + auto check = StateSourceLines.CheckKey(state); + return check ? *check : unknownstatesource; +} + //========================================================================== // // SetImplicitArgs @@ -80,7 +104,7 @@ PClassActor *QuestItemClasses[31]; // //========================================================================== -void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags) +void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags, int useflags) { // Must be called before adding any other arguments. assert(args == nullptr || args->Size() == 0); @@ -98,8 +122,8 @@ void SetImplicitArgs(TArray *args, TArray *argflags, TArrayIsDescendantOf(RUNTIME_CLASS(AStateProvider))) + // Special treatment for weapons and CustomInventory flagged functions: 'self' is not the defining class but the actual user of the item, so this pointer must be of type 'Actor' + if (useflags & (SUF_WEAPON|SUF_ITEM)) { args->Insert(0, NewPointer(RUNTIME_CLASS(AActor))); // this must go in before the real pointer to the containing class. } @@ -139,11 +163,14 @@ PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, i TArray argflags; TArray argnames; + // Functions that only get flagged for actors do not need the additional two context parameters. + int fflags = (flags& (SUF_OVERLAY | SUF_WEAPON | SUF_ITEM)) ? VARF_Action | VARF_Method : VARF_Method; + rets[0] = returntype != nullptr? returntype : TypeError; // Use TypeError as placeholder if we do not know the return type yet. - SetImplicitArgs(&args, &argflags, &argnames, containingclass, flags); + SetImplicitArgs(&args, &argflags, &argnames, containingclass, fflags, flags); PFunction *sym = new PFunction(containingclass, NAME_None); // anonymous functions do not have names. - sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, flags); + sym->AddVariant(NewPrototype(rets, args), argflags, argnames, nullptr, fflags); return sym; } @@ -201,7 +228,7 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, else { auto dmg = new FxReturnStatement(new FxIntCast(id, true), id->ScriptPosition); - auto funcsym = CreateAnonymousFunction(info, TypeSInt32, VARF_Method); + auto funcsym = CreateAnonymousFunction(info, TypeSInt32, 0); defaults->DamageFunc = FunctionBuildList.AddFunction(funcsym, dmg, FStringf("%s.DamageFunction", info->TypeName.GetChars()), fromDecorate); } } @@ -215,25 +242,24 @@ void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, // For such cases a runtime check in the relevant places is also present. // //========================================================================== -static int CheckForUnsafeStates(PClassActor *obj) +static void CheckForUnsafeStates(PClassActor *obj) { static ENamedName weaponstates[] = { NAME_Ready, NAME_Deselect, NAME_Select, NAME_Fire, NAME_AltFire, NAME_Hold, NAME_AltHold, NAME_Flash, NAME_AltFlash, NAME_None }; static ENamedName pickupstates[] = { NAME_Pickup, NAME_Drop, NAME_Use, NAME_None }; TMap checked; ENamedName *test; - int errors = 0; if (obj->IsDescendantOf(RUNTIME_CLASS(AWeapon))) { - if (obj->Size == RUNTIME_CLASS(AWeapon)->Size) return 0; // This class cannot have user variables. + if (obj->Size == RUNTIME_CLASS(AWeapon)->Size) return; // This class cannot have user variables. test = weaponstates; } else if (obj->IsDescendantOf(RUNTIME_CLASS(ACustomInventory))) { - if (obj->Size == RUNTIME_CLASS(ACustomInventory)->Size) return 0; // This class cannot have user variables. + if (obj->Size == RUNTIME_CLASS(ACustomInventory)->Size) return; // This class cannot have user variables. test = pickupstates; } - else return 0; // something else derived from AStateProvider. We do not know what this may be. + else return; // something else derived from AStateProvider. We do not know what this may be. for (; *test != NAME_None; test++) { @@ -245,14 +271,87 @@ static int CheckForUnsafeStates(PClassActor *obj) { // If an unsafe function (i.e. one that accesses user variables) is being detected, print a warning once and remove the bogus function. We may not call it because that would inevitably crash. auto owner = FState::StaticFindStateOwner(state); - Printf(TEXTCOLOR_RED "Unsafe state call in state %s.%d to %s, reached by %s.%s which accesses user variables.\n", - owner->TypeName.GetChars(), state - owner->OwnedStates, static_cast(state->ActionFunc)->PrintableName.GetChars(), obj->TypeName.GetChars(), FName(*test).GetChars()); - errors++; + GetStateSource(state).Message(MSG_ERROR, TEXTCOLOR_RED "Unsafe state call in state %s.%d which accesses user variables, reached by %s.%s.\n", + owner->TypeName.GetChars(), state - owner->OwnedStates, obj->TypeName.GetChars(), FName(*test).GetChars()); } state = state->NextState; } } - return errors; +} + +//========================================================================== +// +// CheckStates +// +// Checks if states link to ones with proper restrictions +// Checks that all base labels refer a string with proper restrictions. +// For these cases a runtime check in the relevant places is also present. +// +//========================================================================== + +static void CheckLabel(PClassActor *obj, FStateLabel *slb, int useflag, FName statename, const char *descript) +{ + auto state = slb->State; + if (state != nullptr) + { + if (!(state->UseFlags & useflag)) + { + auto owner = FState::StaticFindStateOwner(state); + GetStateSource(state).Message(MSG_ERROR, TEXTCOLOR_RED "%s references state %s.%d as %s state, but this state is not flagged for use as %s.\n", + obj->TypeName.GetChars(), owner->TypeName.GetChars(), int(state - owner->OwnedStates), statename.GetChars(), descript); + } + } + if (slb->Children != nullptr) + { + for (int i = 0; i < slb->Children->NumLabels; i++) + { + auto state = slb->Children->Labels[i].State; + CheckLabel(obj, &slb->Children->Labels[i], useflag, statename, descript); + } + } +} + +static void CheckStateLabels(PClassActor *obj, ENamedName *test, int useflag, const char *descript) +{ + FStateLabels *labels = obj->StateList; + + for (; *test != NAME_None; test++) + { + auto label = labels->FindLabel(*test); + if (label != nullptr) + { + CheckLabel(obj, label, useflag, *test, descript); + } + } +} + + +static void CheckStates(PClassActor *obj) +{ + static ENamedName actorstates[] = { NAME_Spawn, NAME_See, NAME_Melee, NAME_Missile, NAME_Pain, NAME_Death, NAME_Wound, NAME_Raise, NAME_Yes, NAME_No, NAME_Greetings, NAME_None }; + static ENamedName weaponstates[] = { NAME_Ready, NAME_Deselect, NAME_Select, NAME_Fire, NAME_AltFire, NAME_Hold, NAME_AltHold, NAME_Flash, NAME_AltFlash, NAME_None }; + static ENamedName pickupstates[] = { NAME_Pickup, NAME_Drop, NAME_Use, NAME_None }; + TMap checked; + + CheckStateLabels(obj, actorstates, SUF_ACTOR, "actor sprites"); + + if (obj->IsDescendantOf(RUNTIME_CLASS(AWeapon))) + { + CheckStateLabels(obj, weaponstates, SUF_WEAPON, "weapon sprites"); + } + else if (obj->IsDescendantOf(RUNTIME_CLASS(ACustomInventory))) + { + CheckStateLabels(obj, pickupstates, SUF_ITEM, "CustomInventory state chain"); + } + for (int i = 0; i < obj->NumOwnedStates; i++) + { + auto state = obj->OwnedStates + i; + if (state->NextState && (state->UseFlags & state->NextState->UseFlags) != state->UseFlags) + { + GetStateSource(state).Message(MSG_ERROR, TEXTCOLOR_RED "State %s.%d links to a state with incompatible restrictions.\n", + obj->TypeName.GetChars(), int(state - obj->OwnedStates)); + } + } } //========================================================================== @@ -285,41 +384,44 @@ void LoadActors () { I_Error("%d errors while parsing DECORATE scripts", FScriptPosition::ErrorCounter); } + FScriptPosition::ResetErrorCounter(); - int errorcount = 0; for (auto ti : PClassActor::AllActorClasses) { if (ti->Size == TentativeClass) { Printf(TEXTCOLOR_RED "Class %s referenced but not defined\n", ti->TypeName.GetChars()); - errorcount++; + FScriptPosition::ErrorCounter++; continue; } if (GetDefaultByType(ti) == nullptr) { Printf(TEXTCOLOR_RED "No ActorInfo defined for class '%s'\n", ti->TypeName.GetChars()); - errorcount++; + FScriptPosition::ErrorCounter++; continue; } + + CheckStates(ti); + if (ti->bDecorateClass && ti->IsDescendantOf(RUNTIME_CLASS(AStateProvider))) { // either a DECORATE based weapon or CustomInventory. // These are subject to relaxed rules for user variables in states. // Although there is a runtime check for bogus states, let's do a quick analysis if any of the known entry points // hits an unsafe state. If we can find something here it can be handled wuth a compile error rather than a runtime error. - errorcount += CheckForUnsafeStates(ti); + CheckForUnsafeStates(ti); } + } - if (errorcount > 0) + if (FScriptPosition::ErrorCounter > 0) { - I_Error("%d errors during actor postprocessing", errorcount); + I_Error("%d errors during actor postprocessing", FScriptPosition::ErrorCounter); } timer.Unclock(); - if (!batchrun) Printf("DECORATE parsing took %.2f ms\n", timer.TimeMS()); - // Base time: ~52 ms + if (!batchrun) Printf("script parsing took %.2f ms\n", timer.TimeMS()); // Since these are defined in DECORATE now the table has to be initialized here. for (int i = 0; i < 31; i++) @@ -328,4 +430,5 @@ void LoadActors () mysnprintf(fmt, countof(fmt), "QuestItem%d", i + 1); QuestItemClasses[i] = PClass::FindActor(fmt); } + StateSourceLines.Clear(); } diff --git a/src/scripting/thingdef.h b/src/scripting/thingdef.h index eeea42f87..7218a84e6 100644 --- a/src/scripting/thingdef.h +++ b/src/scripting/thingdef.h @@ -63,6 +63,7 @@ class FStateDefinitions FState *laststatebeforelabel; intptr_t lastlabel; TArray StateArray; + TArray SourceLines; static FStateDefine *FindStateLabelInList(TArray &list, FName name, bool create); static FStateLabels *CreateStateLabelList(TArray &statelist); @@ -97,10 +98,14 @@ public: bool SetStop(); bool SetWait(); bool SetLoop(); - int AddStates(FState *state, const char *framechars); + int AddStates(FState *state, const char *framechars, const FScriptPosition &sc); int GetStateCount() const { return StateArray.Size(); } }; + +void SaveStateSourceLines(FState *firststate, TArray &positions); +FScriptPosition & GetStateSource(FState *state); + //========================================================================== // // Extra info maintained while defining an actor. @@ -152,7 +157,7 @@ void ParseFunctionParameters(FScanner &sc, PClassActor *cls, TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags); +void SetImplicitArgs(TArray *args, TArray *argflags, TArray *argnames, PClass *cls, DWORD funcflags, int useflags); PFunction *CreateAnonymousFunction(PClass *containingclass, PType *returntype, int flags); PFunction *FindClassMemberFunction(PClass *cls, PClass *funccls, FName name, FScriptPosition &sc, bool *error); void CreateDamageFunction(PClassActor *info, AActor *defaults, FxExpression *id, bool fromDecorate); diff --git a/src/scripting/zscript/zcc_compile.cpp b/src/scripting/zscript/zcc_compile.cpp index 48be582cf..57475c50e 100644 --- a/src/scripting/zscript/zcc_compile.cpp +++ b/src/scripting/zscript/zcc_compile.cpp @@ -2096,7 +2096,9 @@ void ZCCCompiler::InitFunctions() (*afd->VMPointer)->ImplicitArgs = BYTE(implicitargs); } } - SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags); + // Todo: parse these values from the definition + int tempuseflags = (varflags & VARF_Action) ? SUF_WEAPON | SUF_ITEM | SUF_OVERLAY | SUF_ACTOR : SUF_ACTOR; + SetImplicitArgs(&args, &argflags, &argnames, c->Type(), varflags, tempuseflags); argdefaults.Resize(argnames.Size()); auto p = f->Params; bool hasoptionals = false; @@ -2518,12 +2520,12 @@ void ZCCCompiler::CompileStates() auto code = SetupActionFunction(static_cast(c->Type()), sl->Action); if (code != nullptr) { - auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, VARF_Method | VARF_Action); + auto funcsym = CreateAnonymousFunction(c->Type(), nullptr, state.UseFlags); state.ActionFunc = FunctionBuildList.AddFunction(funcsym, code, FStringf("%s.StateFunction.%d", c->Type()->TypeName.GetChars(), statedef.GetStateCount()), false, statedef.GetStateCount(), (int)sl->Frames->Len(), Lump); } } - int count = statedef.AddStates(&state, sl->Frames->GetChars()); + int count = statedef.AddStates(&state, sl->Frames->GetChars(), *sl); if (count < 0) { Error(sl, "Invalid frame character string '%s'", sl->Frames->GetChars());