Merge pull request #512 from carnivoroussociety/master

[Blood] Add vanilla enemies cvar
This commit is contained in:
Mitchell Richters 2021-08-23 11:51:50 +10:00 committed by GitHub
commit 252a2387af
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
17 changed files with 105 additions and 74 deletions

View file

@ -84,7 +84,8 @@ CVARD(Bool, cl_exhumedoldturn, false, CVAR_ARCHIVE, "enable/disable legacy turni
CVARD(Bool, cl_hudinterpolation, true, CVAR_ARCHIVE, "enable/disable HUD (weapon drawer) interpolation")
CVARD(Bool, cl_bloodvanillarun, true, CVAR_ARCHIVE, "enable/disable Blood's vanilla run mode")
CVARD(Bool, cl_bloodvanillabobbing, true, CVAR_ARCHIVE, "enable/disable Blood's vanilla bobbing while not using vanilla run mode")
CVARD(Bool, cl_bloodvanillaexplosions, false, CVAR_ARCHIVE, "enable/disable Blood's original explosion behavior")
CVARD(Bool, cl_bloodvanillaexplosions, false, CVAR_ARCHIVE, "enable/disable Blood's vanilla explosion behavior")
CVARD(Bool, cl_bloodvanillaenemies, false, CVAR_ARCHIVE, "enable/disable Blood's vanilla enemy behavior")
CVARD(Bool, cl_bloodqavinterp, true, CVAR_ARCHIVE, "enable/disable Blood's QAV interpolation")
CVARD(Bool, cl_bloodweapinterp, false, CVAR_ARCHIVE, "enable/disable Blood's weapon interpolation. Depends on 'cl_bloodqavinterp'")
CVARD(Bool, cl_bloodoldweapbalance, false, CVAR_ARCHIVE, "enable/disable legacy 1.0 weapon handling for Blood")

View file

@ -30,6 +30,7 @@ EXTERN_CVAR(Bool, cl_hudinterpolation)
EXTERN_CVAR(Bool, cl_bloodvanillarun)
EXTERN_CVAR(Bool, cl_bloodvanillabobbing)
EXTERN_CVAR(Bool, cl_bloodvanillaexplosions)
EXTERN_CVAR(Bool, cl_bloodvanillaenemies)
EXTERN_CVAR(Bool, cl_bloodqavinterp)
EXTERN_CVAR(Bool, cl_bloodweapinterp)
EXTERN_CVAR(Bool, cl_bloodoldweapbalance)

View file

@ -2540,7 +2540,7 @@ void actInit(bool bSaveLoad)
{
if (act->s().type == kItemWeaponVoodooDoll)
{
act->s().type = kAmmoItemVoodooDoll;
act->s().type = kItemAmmoVoodooDoll;
break;
}
}
@ -2661,7 +2661,7 @@ void actRadiusDamage(DBloodActor* source, int x, int y, int z, int nSector, int
{
uint8_t sectmap[(kMaxSectors + 7) >> 3];
auto pOwner = source->GetOwner();
const bool newSectCheckMethod = !cl_bloodvanillaexplosions && pOwner && pOwner->IsDudeActor() && !VanillaMode() && !DemoRecordStatus(); // use new sector checking logic
const bool newSectCheckMethod = !cl_bloodvanillaexplosions && pOwner && pOwner->IsDudeActor() && !VanillaMode(); // use new sector checking logic
GetClosestSpriteSectors(nSector, x, y, nDist, sectmap, nullptr, newSectCheckMethod);
nDist <<= 4;
if (flags & 2)
@ -3092,7 +3092,7 @@ static bool actKillDudeStage1(DBloodActor* actor, DAMAGE_TYPE damageType)
break;
case kDudeTinyCaleb:
if (VanillaMode() || DemoRecordStatus())
if (cl_bloodvanillaenemies || VanillaMode())
break;
if (damageType == kDamageBurn && pXSprite->medium == kMediumNormal)
{
@ -3936,7 +3936,7 @@ static void actImpactMissile(DBloodActor* missileActor, int hitCode)
actBurnSprite(missileActor->GetOwner(), actorHit, 360);
// by NoOne: make Life Leech heal user, just like it was in 1.0x versions
if (gGameOptions.weaponsV10x && !VanillaMode() && !DemoRecordStatus() && pDudeInfo != nullptr)
if (gGameOptions.weaponsV10x && !VanillaMode() && pDudeInfo != nullptr)
{
if (missileOwner->IsDudeActor() && missileOwner->hasX() && missileOwner->x().health != 0)
actHealDude(missileOwner, nDamage >> 2, getDudeInfo(missileOwner->s().type)->startHealth);
@ -4012,7 +4012,7 @@ static void actImpactMissile(DBloodActor* missileActor, int hitCode)
break;
case kMissileFireball:
case kMissileFireballNapam:
case kMissileFireballNapalm:
if (hitCode == 3 && pSpriteHit && (pThingInfo || pDudeInfo))
{
if (pThingInfo && pSpriteHit->type == kThingTNTBarrel && actorHit->x().burnTime == 0)
@ -4042,7 +4042,7 @@ static void actImpactMissile(DBloodActor* missileActor, int hitCode)
actRadiusDamage(missileOwner, pMissile->x, pMissile->y, pMissile->z, pMissile->sectnum, 16, 20, 10, kDamageBullet, 6, 480);
// by NoOne: allow additional bullet damage for Flare Gun
if (gGameOptions.weaponsV10x && !VanillaMode() && !DemoRecordStatus())
if (gGameOptions.weaponsV10x && !VanillaMode())
{
int nDamage = (20 + Random(10)) << 4;
actDamageSprite(missileOwner, actorHit, kDamageBullet, nDamage);
@ -4646,11 +4646,15 @@ int MoveThing(spritetype *pSprite)
assert(nSector >= 0 && nSector < kMaxSectors);
int top, bottom;
GetSpriteExtents(pSprite, &top, &bottom);
const int bakCompat = enginecompatibility_mode;
if (xvel[nSprite] || yvel[nSprite])
{
short bakCstat = pSprite->cstat;
pSprite->cstat &= ~257;
if ((pSprite->owner >= 0) && !cl_bloodvanillaexplosions && !VanillaMode())
enginecompatibility_mode = ENGINECOMPATIBILITY_NONE; // improved clipmove accuracy
v8 = gSpriteHit[nXSprite].hit = ClipMove((int*)&pSprite->x, (int*)&pSprite->y, (int*)&pSprite->z, &nSector, xvel[nSprite]>>12, yvel[nSprite]>>12, pSprite->clipdist<<2, (pSprite->z-top)/4, (bottom-pSprite->z)/4, CLIPMASK0);
enginecompatibility_mode = bakCompat; // restore
pSprite->cstat = bakCstat;
assert(nSector >= 0);
if (pSprite->sectnum != nSector)
@ -5012,7 +5016,7 @@ void MoveDude(spritetype *pSprite)
}
if (pPlayer && zvel[nSprite] > 0x155555 && !pPlayer->fallScream && pXSprite->height > 0)
{
const bool playerAlive = (pXSprite->health > 0) || VanillaMode() || DemoRecordStatus(); // only trigger falling scream if player is alive or vanilla mode
const bool playerAlive = (pXSprite->health > 0) || VanillaMode(); // only trigger falling scream if player is alive or vanilla mode
if (playerAlive)
{
pPlayer->fallScream = 1;
@ -5110,7 +5114,7 @@ void MoveDude(spritetype *pSprite)
break;
case kDudeBurningCultist:
{
const bool fixRandomCultist = (pSprite->inittype >= kDudeBase) && (pSprite->inittype < kDudeMax) && !VanillaMode() && !DemoRecordStatus(); // fix burning cultists randomly switching types underwater
const bool fixRandomCultist = !cl_bloodvanillaenemies && (pSprite->inittype >= kDudeBase) && (pSprite->inittype < kDudeMax) && !VanillaMode(); // fix burning cultists randomly switching types underwater
if (Chance(chance))
pSprite->type = kDudeCultistTommy;
else
@ -5427,6 +5431,8 @@ int MoveMissile(spritetype *pSprite)
int top, bottom;
GetSpriteExtents(pSprite, &top, &bottom);
int i = 1;
const int bakCompat = enginecompatibility_mode;
const bool isFlameSprite = (pSprite->type == kMissileFlameSpray || pSprite->type == kMissileFlameHound); // do not use accurate clipmove for flame based sprites (changes damage too much)
while (1)
{
int x = pSprite->x;
@ -5434,7 +5440,10 @@ int MoveMissile(spritetype *pSprite)
int z = pSprite->z;
int nSector2 = pSprite->sectnum;
clipmoveboxtracenum = 1;
if ((pSprite->owner >= 0) && !isFlameSprite && !cl_bloodvanillaexplosions && !VanillaMode())
enginecompatibility_mode = ENGINECOMPATIBILITY_NONE; // improved clipmove accuracy
int vdx = ClipMove(&x, &y, &z, &nSector2, vx, vy, pSprite->clipdist<<2, (z-top)/4, (bottom-z)/4, CLIPMASK0);
enginecompatibility_mode = bakCompat; // restore
clipmoveboxtracenum = 3;
short nSector = nSector2;
if (nSector2 < 0)
@ -5547,7 +5556,7 @@ void actExplodeSprite(spritetype *pSprite)
switch (pSprite->type)
{
case kMissileFireballNapam:
case kMissileFireballNapalm:
nType = kExplosionNapalm;
seqSpawn(4, 3, nXSprite, -1);
if (Chance(0x8000))
@ -6004,7 +6013,7 @@ void actProcessSprites(void)
// the new flag newSectCheckMethod for GetClosestSpriteSectors() does rectify these issues, but this may cause unintended side effects for level scripted explosions
// so only allow this new checking method for dude spawned explosions
short gAffectedXWalls[kMaxXWalls];
const bool newSectCheckMethod = !cl_bloodvanillaexplosions && pOwner && pOwner->IsDudeActor() && !VanillaMode() && !DemoRecordStatus(); // use new sector checking logic
const bool newSectCheckMethod = !cl_bloodvanillaexplosions && pOwner && pOwner->IsDudeActor() && !VanillaMode(); // use new sector checking logic
GetClosestSpriteSectors(nSector, x, y, radius, sectmap, gAffectedXWalls, newSectCheckMethod);
for (int i = 0; i < kMaxXWalls; i++)
@ -6197,7 +6206,7 @@ void actProcessSprites(void)
if (nXSprite > 0)
{
XSPRITE *pXSprite = &xsprite[nXSprite];
const bool fixBurnGlitch = IsBurningDude(pSprite) && !VanillaMode() && !DemoRecordStatus(); // if enemies are burning, always apply burning damage per tick
const bool fixBurnGlitch = !cl_bloodvanillaenemies && IsBurningDude(pSprite) && !VanillaMode(); // if enemies are burning, always apply burning damage per tick
if ((pXSprite->burnTime > 0) || fixBurnGlitch)
{
switch (pSprite->type)
@ -6710,7 +6719,7 @@ void actBuildMissile(spritetype* pMissile, int nXSprite, int nSprite) {
seqSpawn(2, 3, nXSprite, -1);
sfxPlay3DSound(pMissile, 493, 0, 0);
break;
case kMissileFireballNapam:
case kMissileFireballNapalm:
seqSpawn(61, 3, nXSprite, nNapalmClient);
sfxPlay3DSound(pMissile, 441, 0, 0);
break;

View file

@ -177,7 +177,7 @@ bool CanMove(spritetype *pSprite, int a2, int nAngle, int nRange)
// It makes ignore danger if enemy immune to N damageType. As result Cerberus start acting like
// in Blood 1.0 so it can move normally to player. It's up to you for adding rest of enemies here as
// i don't think it will broke something in game.
if (!VanillaMode() && Crusher && isImmune(pSprite, pXSector->damageType, 16)) return true;
if (!cl_bloodvanillaenemies && !VanillaMode() && Crusher && isImmune(pSprite, pXSector->damageType, 16)) return true;
fallthrough__;
case kDudeZombieButcher:
case kDudeSpiderBrown:
@ -1033,7 +1033,7 @@ int aiDamageSprite(DBloodActor* source, DBloodActor* actor, DAMAGE_TYPE nDmgType
DUDEEXTRA *pDudeExtra = &gDudeExtra[pSprite->extra];
pDudeExtra->recoil = 1;
}
const bool fixRandomCultist = (pSprite->inittype >= kDudeBase) && (pSprite->inittype < kDudeMax) && !VanillaMode() && !DemoRecordStatus(); // fix burning cultists randomly switching types underwater
const bool fixRandomCultist = !cl_bloodvanillaenemies && (pSprite->inittype >= kDudeBase) && (pSprite->inittype < kDudeMax) && !VanillaMode(); // fix burning cultists randomly switching types underwater
switch (pSprite->type)
{
case kDudeCultistTommy:
@ -1110,7 +1110,7 @@ int aiDamageSprite(DBloodActor* source, DBloodActor* actor, DAMAGE_TYPE nDmgType
case kDudeTinyCaleb:
if (nDmgType == kDamageBurn && pXSprite->health <= (unsigned int)pDudeInfo->fleeHealth/* && (pXSprite->at17_6 != 1 || pXSprite->at17_6 != 2)*/)
{
if (!VanillaMode() && !DemoRecordStatus()) // fix burning sprite for tiny caleb
if (!cl_bloodvanillaenemies && !VanillaMode()) // fix burning sprite for tiny caleb
{
pSprite->type = kDudeBurningTinyCaleb;
aiNewState(actor, &tinycalebBurnGoto);
@ -1480,7 +1480,7 @@ void aiLookForTarget(spritetype *pSprite, XSPRITE *pXSprite)
if (pXSprite->state)
{
uint8_t sectmap[(kMaxSectors+7)>>3];
const bool newSectCheckMethod = !VanillaMode() && !DemoRecordStatus(); // use new sector checking logic
const bool newSectCheckMethod = !cl_bloodvanillaenemies && !VanillaMode(); // use new sector checking logic
GetClosestSpriteSectors(pSprite->sectnum, pSprite->x, pSprite->y, 400, sectmap, nullptr, newSectCheckMethod);
int nSprite2;

View file

@ -95,7 +95,7 @@ void StompSeqCallback(int, DBloodActor* actor1)
int nSector = pSprite->sectnum;
int v1c = 5+2*gGameOptions.nDifficulty;
int v10 = 25+30*gGameOptions.nDifficulty;
const bool newSectCheckMethod = !VanillaMode() && !DemoRecordStatus(); // use new sector checking logic
const bool newSectCheckMethod = !cl_bloodvanillaenemies && !VanillaMode(); // use new sector checking logic
GetClosestSpriteSectors(nSector, x, y, vc, sectmap, nullptr, newSectCheckMethod);
char v4 = 0;
int hit = HitScan(pSprite, pSprite->z, dx, dy, 0, CLIPMASK1, 0);

View file

@ -42,25 +42,22 @@ AISTATE spidGoto = { kAiStateMove, 7, -1, 600, NULL, aiMoveForward, spidThinkGot
AISTATE spidSearch = { kAiStateSearch, 7, -1, 1800, NULL, aiMoveForward, spidThinkSearch, &spidIdle };
AISTATE spidBite = { kAiStateChase, 6, nSpidBiteClient, 60, NULL, NULL, NULL, &spidChase };
AISTATE spidJump = { kAiStateChase, 8, nSpidJumpClient, 60, NULL, aiMoveForward, NULL, &spidChase };
AISTATE spid13A92C = { kAiStateOther, 0, dword_279B50, 60, NULL, NULL, NULL, &spidIdle };
AISTATE spidBirth = { kAiStateOther, 0, nSpidBirthClient, 60, NULL, NULL, NULL, &spidIdle };
static char sub_70D30(XSPRITE *pXDude, int a2, int a3)
static char SpidPoisonPlayer(XSPRITE *pXDude, int nBlind, int max)
{
assert(pXDude != NULL);
int nDude = pXDude->reference;
spritetype *pDude = &sprite[nDude];
if (IsPlayerSprite(pDude))
{
a2 <<= 4;
a3 <<= 4;
if (IsPlayerSprite(pDude))
nBlind <<= 4;
max <<= 4;
PLAYER *pPlayer = &gPlayer[pDude->type-kDudePlayer1];
if (pPlayer->blindEffect < max)
{
PLAYER *pPlayer = &gPlayer[pDude->type-kDudePlayer1];
if (a3 > pPlayer->blindEffect)
{
pPlayer->blindEffect = ClipHigh(pPlayer->blindEffect+a2, a3);
return 1;
}
pPlayer->blindEffect = ClipHigh(pPlayer->blindEffect+nBlind, max);
return 1;
}
}
return 0;
@ -93,11 +90,11 @@ void SpidBiteSeqCallback(int, DBloodActor* actor)
break;
case kDudeSpiderRed:
actFireVector(pSprite, 0, 0, dx, dy, dz, kVectorSpiderBite);
if (Chance(0x5000)) sub_70D30(pXTarget, 4, 16);
if (Chance(0x5000)) SpidPoisonPlayer(pXTarget, 4, 16);
break;
case kDudeSpiderBlack:
actFireVector(pSprite, 0, 0, dx, dy, dz, kVectorSpiderBite);
sub_70D30(pXTarget, 8, 16);
SpidPoisonPlayer(pXTarget, 8, 16);
break;
case kDudeSpiderMother: {
actFireVector(pSprite, 0, 0, dx, dy, dz, kVectorSpiderBite);
@ -106,9 +103,9 @@ void SpidBiteSeqCallback(int, DBloodActor* actor)
dy += Random2(2000);
dz += Random2(2000);
actFireVector(pSprite, 0, 0, dx, dy, dz, kVectorSpiderBite);
sub_70D30(pXTarget, 8, 16);
}
SpidPoisonPlayer(pXTarget, 8, 16);
break;
}
}
}
@ -141,7 +138,7 @@ void SpidJumpSeqCallback(int, DBloodActor* actor)
}
}
void sub_71370(int, DBloodActor* actor)
void SpidBirthSeqCallback(int, DBloodActor* actor)
{
XSPRITE* pXSprite = &actor->x();
spritetype* pSprite = &actor->s();
@ -249,7 +246,7 @@ static void spidThinkChase(DBloodActor* actor)
if (nDist < 0x733 && nDist > 0x399 && abs(nDeltaAngle) < 85)
aiNewState(actor, &spidJump);
else if (Chance(0x8000))
aiNewState(actor, &spid13A92C);
aiNewState(actor, &spidBirth);
break;
}

View file

@ -313,7 +313,7 @@ extern AISTATE spidGoto;
extern AISTATE spidSearch;
extern AISTATE spidBite;
extern AISTATE spidJump;
extern AISTATE spid13A92C;
extern AISTATE spidBirth;
extern AISTATE tchernobogIdle;
extern AISTATE tchernobogSearch;

View file

@ -619,7 +619,7 @@ static void unicultThinkChase(DBloodActor* actor)
mdist = 2500;
fallthrough__;
case kMissileFireball:
case kMissileFireballNapam:
case kMissileFireballNapalm:
case kMissileFireballCerberus:
case kMissileFireballTchernobog:
if (mdist == defDist) mdist = 3000;
@ -834,7 +834,7 @@ static void unicultThinkChase(DBloodActor* actor)
case kMissileTeslaAlt:
case kMissileFlareAlt:
case kMissileFireball:
case kMissileFireballNapam:
case kMissileFireballNapalm:
case kMissileFireballCerberus:
case kMissileFireballTchernobog: {
// allow attack if dude is far from object, but target is close to it
@ -1328,7 +1328,7 @@ void scaleDamage(XSPRITE* pXSprite) {
curScale[kDmgSpirit] = 32 + Random(18);
break;
case kMissileFireball:
case kMissileFireballNapam:
case kMissileFireballNapalm:
case kMissileFireballCerberus:
case kMissileFireballTchernobog:
curScale[kDmgBurn] = 50;

View file

@ -172,17 +172,35 @@ enum {
// (weapons)
kItemWeaponBase = 40,
kItemWeaponRandom = kItemWeaponBase,
kItemWeaponSawedoff = 41,
kItemWeaponTommygun = 42,
kItemWeaponFlarePistol = 43,
kItemWeaponVoodooDoll = 44,
kItemWeaponTeslaCannon = 45,
kItemWeaponNapalmLauncher = 46,
kItemWeaponPitchfork = 47,
kItemWeaponSprayCan = 48,
kItemWeaponTNT = 49,
kItemWeaponLifeLeech = 50,
kItemWeaponMax = 51,
// items (ammos)
kItemAmmoBase = 60,
kItemAmmoSprayCan = kItemAmmoBase,
kItemAmmoTNTBundle = 62,
kItemAmmoTNTBox = 63,
kItemAmmoProxBombBundle = 64,
kItemAmmoRemoteBombBundle = 65,
kItemAmmoTrappedSoul = 66,
kItemAmmoSawedoffFew = 67,
kItemAmmoSawedoffBox = 68,
kItemAmmoTommygunFew = 69,
kAmmoItemVoodooDoll = 70,
kItemAmmoVoodooDoll = 70,
kItemAmmoTommygunDrum = 72,
kItemAmmoTeslaCharge = 73,
kItemAmmoFlares = 76,
kItemAmmoGasolineCan = 79,
kItemAmmoMax = 81,
kItemBase = 100,
@ -302,7 +320,7 @@ enum {
kMissilePukeGreen = 309,
kMissileUnused = 310,
kMissileArcGargoyle = 311,
kMissileFireballNapam = 312,
kMissileFireballNapalm = 312,
kMissileFireballCerberus = 313,
kMissileFireballTchernobog = 314,
kMissileLifeLeechRegular = 315,

View file

@ -886,23 +886,20 @@ int GetClosestSpriteSectors(int nSector, int x, int y, int nDist, uint8_t *pSect
int x2 = wall[nWallB].x, y2 = wall[nWallB].y;
int nLength = approxDist(x1-x2, y1-y2);
const int nDist2 = (nDist+(nDist>>1))<<4;
if (nLength > nDist2) // if span is greater than range * 1.5, test midsection
nLength = ClipRange(nLength / nDist2, 1, 4); // never split more than 4 times
for (int k = 0; true; k++) // subdivide span into smaller chunks towards direction
{
nLength = ClipRange(nLength / nDist2, 1, 4); // never split more than 4 times
for (int k = 0; k < nLength; k++) // subdivide span into smaller chunks towards direction
{
const int xcenter = (x1+x2)>>1, ycenter = (y1+y2)>>1;
withinRange = CheckProximityPoint(xcenter, ycenter, 0, x, y, 0, nDist);
if (withinRange)
break;
if ((k+1) == nLength) // reached end, no point in calculating direction/center again
break;
const bool bDir = approxDist(x-x1, y-y1) < approxDist(x-x2, y-y2);
if (bDir) // step closer and check again
x2 = xcenter, y2 = ycenter;
else
x1 = xcenter, y1 = ycenter;
}
const int xcenter = (x1+x2)>>1, ycenter = (y1+y2)>>1;
withinRange = CheckProximityPoint(xcenter, ycenter, 0, x, y, 0, nDist);
if (withinRange)
break;
if (k == (nLength-1)) // reached end
break;
const bool bDir = approxDist(x-x1, y-y1) < approxDist(x-x2, y-y2);
if (bDir) // step closer and check again
x2 = xcenter, y2 = ycenter;
else
x1 = xcenter, y1 = ycenter;
}
}
if (withinRange) // if new sector is within range, set to current sector and test walls

View file

@ -318,7 +318,7 @@ static AISTATE* allAIStates[] =
&spidSearch,
&spidBite,
&spidJump,
&spid13A92C,
&spidBirth,
&tchernobogIdle,
&tchernobogSearch,
&tchernobogChase,

View file

@ -491,7 +491,7 @@ void nnExtInitModernStuff(bool bSaveLoad) {
nnExtResetGlobals();
// use true random only for single player mode, otherwise use Blood's default one.
if (gGameOptions.nGameType == 0 && !VanillaMode() && !DemoRecordStatus()) {
if (gGameOptions.nGameType == 0 && !VanillaMode()) {
gStdRandom.seed(std::random_device()());

View file

@ -75,7 +75,7 @@ static void (*seqClientCallback[])(int, DBloodActor*) = {
ratBiteSeqCallback,
SpidBiteSeqCallback,
SpidJumpSeqCallback,
sub_71370,
SpidBirthSeqCallback,
sub_71BD4,
sub_720AC,
sub_71A90,

View file

@ -43,7 +43,7 @@ void sub_70284(int, DBloodActor*);
void ratBiteSeqCallback(int, DBloodActor*);
void SpidBiteSeqCallback(int, DBloodActor*);
void SpidJumpSeqCallback(int, DBloodActor*);
void sub_71370(int, DBloodActor*);
void SpidBirthSeqCallback(int, DBloodActor*);
void sub_71A90(int, DBloodActor*);
void sub_71BD4(int, DBloodActor*);
void sub_720AC(int, DBloodActor*);
@ -104,7 +104,7 @@ enum
nRatBiteClient,
nSpidBiteClient,
nSpidJumpClient,
dword_279B50,
nSpidBirthClient,
dword_279B54,
dword_279B58,
dword_279B5C,

View file

@ -1466,6 +1466,7 @@ void OperateTeleport(unsigned int nSector, XSECTOR *pXSector)
{
playerResetInertia(pPlayer);
pPlayer->zViewVel = pPlayer->zWeaponVel = 0;
pPlayer->angle.settarget(pSprite->ang, true);
}
}
}

View file

@ -151,7 +151,7 @@ static bool checkFired6or7(PLAYER *pPlayer)
case 6:
return 1;
case 7:
if (VanillaMode() || DemoRecordStatus())
if (VanillaMode())
return 0;
return 1;
}
@ -717,7 +717,7 @@ void WeaponLower(PLAYER *pPlayer)
}
break;
case 7: // throwing ignited alt fire spray
if (VanillaMode() || DemoRecordStatus() || (pPlayer->newWeapon != 0))
if (VanillaMode() || (pPlayer->newWeapon != 0))
break;
pPlayer->weaponState = 1;
StartQAV(pPlayer, 11, -1, 0);
@ -1465,7 +1465,7 @@ void AltFireVoodoo(int nTrigger, PLAYER *pPlayer)
// by NoOne: trying to simulate v1.0x voodoo here.
// dunno how exactly it works, but at least it not spend all the ammo on alt fire
if (gGameOptions.weaponsV10x && !VanillaMode() && !DemoRecordStatus()) {
if (gGameOptions.weaponsV10x && !VanillaMode()) {
int nCount = ClipHigh(pPlayer->ammoCount[9], pPlayer->aimTargetsCount);
if (nCount > 0)
{
@ -1622,7 +1622,7 @@ void FireNapalm(int nTrigger, PLAYER *pPlayer)
offset = 50;
break;
}
playerFireMissile(pPlayer, offset, pPlayer->aim.dx, pPlayer->aim.dy, pPlayer->aim.dz, kMissileFireballNapam);
playerFireMissile(pPlayer, offset, pPlayer->aim.dx, pPlayer->aim.dy, pPlayer->aim.dz, kMissileFireballNapalm);
sfxPlay3DSound(pSprite, 480, 2, 0);
UseAmmo(pPlayer, 4, 1);
pPlayer->flashEffect = 1;
@ -1631,8 +1631,8 @@ void FireNapalm(int nTrigger, PLAYER *pPlayer)
void FireNapalm2(int , PLAYER *pPlayer)
{
spritetype *pSprite = pPlayer->pSprite;
playerFireMissile(pPlayer, -120, pPlayer->aim.dx, pPlayer->aim.dy, pPlayer->aim.dz, kMissileFireballNapam);
playerFireMissile(pPlayer, 120, pPlayer->aim.dx, pPlayer->aim.dy, pPlayer->aim.dz, kMissileFireballNapam);
playerFireMissile(pPlayer, -120, pPlayer->aim.dx, pPlayer->aim.dy, pPlayer->aim.dz, kMissileFireballNapalm);
playerFireMissile(pPlayer, 120, pPlayer->aim.dx, pPlayer->aim.dy, pPlayer->aim.dz, kMissileFireballNapalm);
sfxPlay3DSound(pSprite, 480, 2, 0);
UseAmmo(pPlayer, 4, 2);
pPlayer->flashEffect = 1;
@ -2196,7 +2196,7 @@ void WeaponProcess(PLAYER *pPlayer) {
}
if (pPlayer->newWeapon)
{
if (pPlayer->isUnderwater && BannedUnderwater(pPlayer->newWeapon) && !checkFired6or7(pPlayer) && !VanillaMode() && !DemoRecordStatus()) // skip banned weapons when underwater and using next/prev weapon key inputs
if (pPlayer->isUnderwater && BannedUnderwater(pPlayer->newWeapon) && !checkFired6or7(pPlayer) && !VanillaMode()) // skip banned weapons when underwater and using next/prev weapon key inputs
{
if (prevNewWeaponVal == WeaponSel_Next || prevNewWeaponVal == WeaponSel_Prev) // if player switched weapons
{
@ -2247,7 +2247,7 @@ void WeaponProcess(PLAYER *pPlayer) {
pPlayer->newWeapon = kWeapRemote;
}
}
else if ((pPlayer->newWeapon == kWeapSpraycan) && !VanillaMode() && !DemoRecordStatus())
else if ((pPlayer->newWeapon == kWeapSpraycan) && !VanillaMode())
{
if ((pPlayer->curWeapon == kWeapSpraycan) && (pPlayer->weaponState == 2)) // fix spray can state glitch when switching from spray to tnt and back quickly
{
@ -2570,10 +2570,10 @@ void WeaponProcess(PLAYER *pPlayer) {
case kWeapNapalm:
if (powerupCheck(pPlayer, kPwUpTwoGuns))
// by NoOne: allow napalm launcher alt fire act like in v1.0x versions
if (gGameOptions.weaponsV10x && !VanillaMode() && !DemoRecordStatus()) StartQAV(pPlayer, kQAV2NAPFIR2, nClientFireNapalm2);
else StartQAV(pPlayer, kQAV2NAPFIRE, nClientAltFireNapalm, 0);
if (gGameOptions.weaponsV10x && !VanillaMode()) StartQAV(pPlayer, kQAV2NAPFIR2, nClientFireNapalm2);
else StartQAV(pPlayer, kQAV2NAPFIRE, nClientAltFireNapalm);
else
StartQAV(pPlayer, kQAVNAPFIRE, (gGameOptions.weaponsV10x && !VanillaMode() && !DemoRecordStatus()) ? nClientFireNapalm : nClientAltFireNapalm);
StartQAV(pPlayer, kQAVNAPFIRE, (gGameOptions.weaponsV10x && !VanillaMode()) ? nClientFireNapalm : nClientAltFireNapalm);
return;
case kWeapFlareGun:
if (CheckAmmo(pPlayer, 1, 8))
@ -2618,7 +2618,7 @@ void teslaHit(spritetype *pMissile, int a2)
int nDist = 300;
int nSector = pMissile->sectnum;
int nOwner = pMissile->owner;
const bool newSectCheckMethod = !VanillaMode() && !DemoRecordStatus(); // use new sector checking logic
const bool newSectCheckMethod = !cl_bloodvanillaexplosions && !VanillaMode(); // use new sector checking logic
GetClosestSpriteSectors(nSector, x, y, nDist, sectmap, nullptr, newSectCheckMethod);
bool v4 = true;
DBloodActor* actor = nullptr;

View file

@ -962,6 +962,12 @@ OptionValue "ExplosBehavior"
1, "$OPTVAL_OLD"
}
OptionValue "EnemyBehavior"
{
0, "$OPTVAL_DEFAULT"
1, "$OPTVAL_OLD"
}
OptionMenu GameplayOptions protected
{
@ -984,6 +990,7 @@ OptionMenu GameplayOptions protected
{
Option "$PLRMNU_EQUIP", "cl_weaponswitch", "WeapSwitch"
Option "$EXPLOS_BEHAVIOR", "cl_bloodvanillaexplosions", "ExplosBehavior"
Option "$ENEMY_BEHAVIOR", "cl_bloodvanillaenemies", "EnemyBehavior"
}
ifgame(Exhumed)
{