Friendly fire and keep keys settings for multiplayer (#177)

# Conflicts:
#	source/blood/src/levels.h
#	source/blood/src/network.h
This commit is contained in:
CommonLoon102 2019-09-20 10:11:07 +00:00 committed by Christoph Oelckers
parent 56365d65ce
commit edc6e2c0f7
7 changed files with 46 additions and 20 deletions

View file

@ -3601,6 +3601,17 @@ int actDamageSprite(int nSource, spritetype *pSprite, DAMAGE_TYPE a3, int a4)
PLAYER *pSourcePlayer = NULL;
if (IsPlayerSprite(&sprite[nSource]))
pSourcePlayer = &gPlayer[sprite[nSource].type-kDudePlayer1];
if (!gGameOptions.bFriendlyFire && pSourcePlayer != NULL && (gGameOptions.nGameType == 1 || gGameOptions.nGameType == 3) && IsPlayerSprite(pSprite))
{
PLAYER *pTargetPlayer = &gPlayer[pSprite->type-kDudePlayer1];
if (pSourcePlayer != pTargetPlayer)
{
if (gGameOptions.nGameType == 1)
return 0;
if (gGameOptions.nGameType == 3 && (pSourcePlayer->at2ea&3) == (pTargetPlayer->at2ea&3))
return 0;
}
}
switch (pSprite->statnum)
{
case 6:

View file

@ -533,6 +533,8 @@ void StartLevel(GAMEOPTIONS *gameOptions)
gGameOptions.nWeaponSettings = gPacketStartGame.weaponSettings;
gGameOptions.nItemSettings = gPacketStartGame.itemSettings;
gGameOptions.nRespawnSettings = gPacketStartGame.respawnSettings;
gGameOptions.bFriendlyFire = gPacketStartGame.bFriendlyFire;
gGameOptions.bKeepKeysOnRespawn = gPacketStartGame.bKeepKeysOnRespawn;
if (gPacketStartGame.userMap)
levelAddUserMap(gPacketStartGame.userMapName);
else
@ -684,6 +686,8 @@ void StartNetworkLevel(void)
gGameOptions.nWeaponSettings = gPacketStartGame.weaponSettings;
gGameOptions.nItemSettings = gPacketStartGame.itemSettings;
gGameOptions.nRespawnSettings = gPacketStartGame.respawnSettings;
gGameOptions.bFriendlyFire = gPacketStartGame.bFriendlyFire;
gGameOptions.bKeepKeysOnRespawn = gPacketStartGame.bKeepKeysOnRespawn;
///////
gGameOptions.weaponsV10x = gPacketStartGame.weaponsV10x;

View file

@ -54,6 +54,8 @@ struct GAMEOPTIONS {
int nWeaponRespawnTime;
int nItemRespawnTime;
int nSpecialRespawnTime;
bool bFriendlyFire;
bool bKeepKeysOnRespawn;
};
#pragma pack(pop)

View file

@ -277,15 +277,17 @@ CGameMenuItemZEditBitmap itemLoadGame10(NULL, 3, 20, 150, 320, strRestoreGameStr
CGameMenuItemBitmapLS itemLoadGamePic(NULL, 3, 0, 0, 2518);
CGameMenuItemTitle itemNetStartTitle("MULTIPLAYER", 1, 160, 20, 2038);
CGameMenuItemZCycle itemNetStart1("GAME", 1, 20, 35, 280, 0, 0, zNetGameTypes, 3, 0);
CGameMenuItemZCycle itemNetStart2("EPISODE", 1, 20, 50, 280, 0, SetupNetLevels, NULL, 0, 0);
CGameMenuItemZCycle itemNetStart3("LEVEL", 1, 20, 65, 280, 0, NULL, NULL, 0, 0);
CGameMenuItemZCycle itemNetStart4("DIFFICULTY", 1, 20, 80, 280, 0, 0, zDiffStrings, 5, 0);
CGameMenuItemZCycle itemNetStart5("MONSTERS", 1, 20, 95, 280, 0, 0, zMonsterStrings, 3, 0);
CGameMenuItemZCycle itemNetStart6("WEAPONS", 1, 20, 110, 280, 0, 0, zWeaponStrings, 4, 0);
CGameMenuItemZCycle itemNetStart7("ITEMS", 1, 20, 125, 280, 0, 0, zItemStrings, 3, 0);
CGameMenuItemZEdit itemNetStart9("USER MAP:", 1, 20, 155, 280, zUserMapName, 13, 0, NULL, 0);
CGameMenuItemChain itemNetStart10("START GAME", 1, 20, 170, 280, 0, 0, -1, StartNetGame, 0);
CGameMenuItemZCycle itemNetStart1("GAME:", 3, 66, 60, 180, 0, 0, zNetGameTypes, 3, 0);
CGameMenuItemZCycle itemNetStart2("EPISODE:", 3, 66, 70, 180, 0, SetupNetLevels, NULL, 0, 0);
CGameMenuItemZCycle itemNetStart3("LEVEL:", 3, 66, 80, 180, 0, NULL, NULL, 0, 0);
CGameMenuItemZCycle itemNetStart4("DIFFICULTY:", 3, 66, 90, 180, 0, 0, zDiffStrings, 5, 0);
CGameMenuItemZCycle itemNetStart5("MONSTERS:", 3, 66, 100, 180, 0, 0, zMonsterStrings, 3, 0);
CGameMenuItemZCycle itemNetStart6("WEAPONS:", 3, 66, 110, 180, 0, 0, zWeaponStrings, 4, 0);
CGameMenuItemZCycle itemNetStart7("ITEMS:", 3, 66, 120, 180, 0, 0, zItemStrings, 3, 0);
CGameMenuItemZBool itemNetStart8("FRIENDLY FIRE:", 3, 66, 130, 180, true, 0, NULL, NULL);
CGameMenuItemZBool itemNetStart9("KEEP KEYS ON RESPAWN:", 3, 66, 140, 180, false, 0, NULL, NULL);
CGameMenuItemZEdit itemNetStart10("USER MAP:", 3, 66, 150, 180, zUserMapName, 13, 0, NULL, 0);
CGameMenuItemChain itemNetStart11("START GAME", 1, 66, 165, 280, 0, 0, -1, StartNetGame, 0);
CGameMenuItemText itemLoadingText("LOADING...", 1, 160, 100, 1);
@ -883,8 +885,10 @@ void SetupNetStartMenu(void)
menuNetStart.Add(&itemNetStart5, false);
menuNetStart.Add(&itemNetStart6, false);
menuNetStart.Add(&itemNetStart7, false);
menuNetStart.Add(&itemNetStart8, false);
menuNetStart.Add(&itemNetStart9, false);
menuNetStart.Add(&itemNetStart10, false);
menuNetStart.Add(&itemNetStart11, false);
itemNetStart1.SetTextIndex(1);
itemNetStart4.SetTextIndex(2);
itemNetStart5.SetTextIndex(0);
@ -2156,9 +2160,11 @@ void StartNetGame(CGameMenuItemChain *pItem)
gPacketStartGame.weaponSettings = itemNetStart6.m_nFocus;
gPacketStartGame.itemSettings = itemNetStart7.m_nFocus;
gPacketStartGame.respawnSettings = 0;
gPacketStartGame.bFriendlyFire = itemNetStart8.at20;
gPacketStartGame.bKeepKeysOnRespawn = itemNetStart9.at20;
gPacketStartGame.unk = 0;
gPacketStartGame.userMapName[0] = 0;
strncpy(gPacketStartGame.userMapName, itemNetStart9.at20, 13);
strncpy(gPacketStartGame.userMapName, itemNetStart10.at20, 13);
gPacketStartGame.userMapName[12] = 0;
gPacketStartGame.userMap = gPacketStartGame.userMapName[0] != 0;
netBroadcastNewGame();

View file

@ -76,6 +76,8 @@ struct PKT_STARTGAME {
char episodeId, levelId;
int unk;
char userMap, userMapName[13];
bool bFriendlyFire;
bool bKeepKeysOnRespawn;
};
extern PKT_STARTGAME gPacketStartGame;

View file

@ -349,10 +349,10 @@ ARMORDATA armorData[5] = {
};
void PlayerSurvive(int, int);
void PlayerKeelsOver(int, int);
void PlayerKneelsOver(int, int);
int nPlayerSurviveClient = seqRegisterClient(PlayerSurvive);
int nPlayerKeelClient = seqRegisterClient(PlayerKeelsOver);
int nPlayerKneelClient = seqRegisterClient(PlayerKneelsOver);
struct VICTORY {
const char *at0;
@ -934,8 +934,9 @@ void playerStart(int nPlayer)
pPlayer->at1ca.dz = 0;
pPlayer->at1d6 = -1;
pPlayer->at6b = pPlayer->at73;
for (int i = 0; i < 8; i++)
pPlayer->at88[i] = gGameOptions.nGameType >= 2;
if (!(gGameOptions.nGameType == 1 && gGameOptions.bKeepKeysOnRespawn))
for (int i = 0; i < 8; i++)
pPlayer->at88[i] = gGameOptions.nGameType >= 2;
pPlayer->at90 = 0;
for (int i = 0; i < 8; i++)
pPlayer->at91[i] = -1;
@ -2157,7 +2158,7 @@ int playerDamageSprite(int nSource, PLAYER *pPlayer, DAMAGE_TYPE nDamageType, in
int nXSector = sector[pSprite->sectnum].extra;
DUDEINFO *pDudeInfo = &dudeInfo[pSprite->type-kDudeBase];
int nDeathSeqID = -1;
int v18 = -1;
int nKneelingPlayer = -1;
int nSprite = pSprite->index;
char va = playerSeqPlaying(pPlayer, 16);
if (!pXSprite->health)
@ -2252,7 +2253,7 @@ int playerDamageSprite(int nSource, PLAYER *pPlayer, DAMAGE_TYPE nDamageType, in
DAMAGEINFO *pDamageInfo = &damageInfo[nDamageType];
sfxPlay3DSound(pSprite, pDamageInfo->at10[0], 0, 2);
nDeathSeqID = 16;
v18 = nPlayerKeelClient;
nKneelingPlayer = nPlayerKneelClient;
powerupActivate(pPlayer, 28);
pXSprite->target = nSource;
evPost(pSprite->index, 3, 15, CALLBACK_ID_13);
@ -2282,7 +2283,7 @@ int playerDamageSprite(int nSource, PLAYER *pPlayer, DAMAGE_TYPE nDamageType, in
trTriggerSprite(nSprite, pXSprite, 0);
}
dassert(gSysRes.Lookup(pDudeInfo->seqStartID + nDeathSeqID, "SEQ") != NULL);
seqSpawn(pDudeInfo->seqStartID+nDeathSeqID, 3, nXSprite, v18);
seqSpawn(pDudeInfo->seqStartID+nDeathSeqID, 3, nXSprite, nKneelingPlayer);
return nDamage;
}
@ -2369,7 +2370,7 @@ void PlayerSurvive(int, int nXSprite)
}
}
void PlayerKeelsOver(int, int nXSprite)
void PlayerKneelsOver(int, int nXSprite)
{
XSPRITE *pXSprite = &xsprite[nXSprite];
for (int p = connecthead; p >= 0; p = connectpoint2[p])

View file

@ -114,7 +114,7 @@ struct PLAYER {
int at202[kMaxPowerUps]; // [13]: cloak of invisibility, [14]: death mask (invulnerability), [15]: jump boots, [17]: guns akimbo, [18]: diving suit, [21]: crystal ball, [24]: reflective shots, [25]: beast vision, [26]: cloak of shadow
int at2c6; // frags
int at2ca[8];
int at2ea;
int at2ea; // color (team)
int at2ee; // killer
int at2f2;
int at2f6;
@ -249,7 +249,7 @@ int UseAmmo(PLAYER *pPlayer, int nAmmoType, int nDec);
void sub_41250(PLAYER *pPlayer);
void playerLandingSound(PLAYER *pPlayer);
void PlayerSurvive(int, int nXSprite);
void PlayerKeelsOver(int, int nXSprite);
void PlayerKneelsOver(int, int nXSprite);
bool isGrown(spritetype* pSprite);
bool isShrinked(spritetype* pSprite);
bool shrinkPlayerSize(PLAYER* pPlayer, int divider);