mirror of
https://gitlab.com/ryandwyer/perfect-dark
synced 2026-07-10 22:01:43 -04:00
Refactor MP chr/config structs to allow a one config to many chrs relationship
This commit is contained in:
+18
-18
@@ -94,7 +94,7 @@ s32 amPickTargetMenuList(s32 operation, struct menuitem *item, union handlerdata
|
||||
struct chrdata *playerchr = g_Vars.currentplayer->prop->chr;
|
||||
|
||||
for (i = PLAYERCOUNT(); i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->team != playerchr->team) {
|
||||
if (g_MpChrs[i].team != playerchr->team) {
|
||||
count++;
|
||||
}
|
||||
}
|
||||
@@ -116,18 +116,18 @@ s32 amPickTargetMenuList(s32 operation, struct menuitem *item, union handlerdata
|
||||
|
||||
chrindex = -1;
|
||||
numremaining = data->list.value;
|
||||
botchr = g_MpAllChrPtrs[g_Vars.currentplayer->aibuddynums[g_AmMenus[g_AmIndex].screenindex - 2]];
|
||||
botchr = g_MpChrs[g_Vars.currentplayer->aibuddynums[g_AmMenus[g_AmIndex].screenindex - 2]].chr;
|
||||
playerchr = g_Vars.currentplayer->prop->chr;
|
||||
|
||||
do {
|
||||
chrindex++;
|
||||
|
||||
if (g_AmMenus[g_AmIndex].prevallbots) {
|
||||
if (playerchr == g_MpAllChrPtrs[chrindex] || playerchr->team != g_MpAllChrPtrs[chrindex]->team) {
|
||||
if (playerchr == g_MpChrs[chrindex].chr || playerchr->team != g_MpChrs[chrindex].team) {
|
||||
numremaining--;
|
||||
}
|
||||
} else {
|
||||
if (botchr != g_MpAllChrPtrs[chrindex]) {
|
||||
if (botchr != g_MpChrs[chrindex].chr) {
|
||||
numremaining--;
|
||||
}
|
||||
}
|
||||
@@ -137,10 +137,10 @@ s32 amPickTargetMenuList(s32 operation, struct menuitem *item, union handlerdata
|
||||
g_AmMenus[g_AmIndex].prevallbots = false;
|
||||
|
||||
for (i = 0; i < g_Vars.currentplayer->numaibuddies; i++) {
|
||||
botApplyAttack(g_MpAllChrPtrs[g_Vars.currentplayer->aibuddynums[i]], g_MpAllChrPtrs[chrindex]->prop);
|
||||
botApplyAttack(g_MpChrs[g_Vars.currentplayer->aibuddynums[i]].chr, g_MpChrs[chrindex].chr->prop);
|
||||
}
|
||||
} else {
|
||||
botApplyAttack(botchr, g_MpAllChrPtrs[chrindex]->prop);
|
||||
botApplyAttack(botchr, g_MpChrs[chrindex].chr->prop);
|
||||
}
|
||||
|
||||
menuPopDialog();
|
||||
@@ -158,24 +158,24 @@ s32 amPickTargetMenuList(s32 operation, struct menuitem *item, union handlerdata
|
||||
u32 colour;
|
||||
s32 numremaining = (s32)data->type19.unk04;
|
||||
s32 chrindex = -1;
|
||||
struct chrdata *botchr = g_MpAllChrPtrs[g_Vars.currentplayer->aibuddynums[g_AmMenus[g_AmIndex].screenindex - 2]];
|
||||
struct chrdata *botchr = g_MpChrs[g_Vars.currentplayer->aibuddynums[g_AmMenus[g_AmIndex].screenindex - 2]].chr;
|
||||
struct chrdata *playerchr = g_Vars.currentplayer->prop->chr;
|
||||
|
||||
do {
|
||||
chrindex++;
|
||||
|
||||
if (g_AmMenus[g_AmIndex].prevallbots) {
|
||||
if (playerchr == g_MpAllChrPtrs[chrindex] || playerchr->team != g_MpAllChrPtrs[chrindex]->team) {
|
||||
if (playerchr == g_MpChrs[chrindex].chr || playerchr->team != g_MpChrs[chrindex].team) {
|
||||
numremaining--;
|
||||
}
|
||||
} else {
|
||||
if (botchr != g_MpAllChrPtrs[chrindex]) {
|
||||
if (botchr != g_MpChrs[chrindex].chr) {
|
||||
numremaining--;
|
||||
}
|
||||
}
|
||||
} while (numremaining >= 0);
|
||||
|
||||
colour = teamcolours[g_MpAllChrConfigPtrs[chrindex]->team] | (renderdata->colour & 0xff);
|
||||
colour = teamcolours[g_MpChrs[chrindex].team] | (renderdata->colour & 0xff);
|
||||
|
||||
if (renderdata->unk10) {
|
||||
u32 weight = menuGetSinOscFrac(40) * 255;
|
||||
@@ -186,7 +186,7 @@ s32 amPickTargetMenuList(s32 operation, struct menuitem *item, union handlerdata
|
||||
y = renderdata->y + 1;
|
||||
|
||||
gdl = text0f153628(gdl);
|
||||
gdl = textRenderProjected(gdl, &x, &y, g_MpAllChrConfigPtrs[chrindex]->name, g_CharsHandelGothicSm, g_FontHandelGothicSm, colour, viGetWidth(), viGetHeight(), 0, 0);
|
||||
gdl = textRenderProjected(gdl, &x, &y, g_MpChrs[chrindex].config->name, g_CharsHandelGothicSm, g_FontHandelGothicSm, colour, viGetWidth(), viGetHeight(), 0, 0);
|
||||
gdl = text0f153780(gdl);
|
||||
return (s32)gdl;
|
||||
}
|
||||
@@ -335,10 +335,10 @@ void amApply(s32 slot)
|
||||
default:
|
||||
if (g_AmMenus[g_AmIndex].allbots) {
|
||||
for (i = 0; i < g_Vars.currentplayer->numaibuddies; i++) {
|
||||
botcmdApply(g_MpAllChrPtrs[g_Vars.currentplayer->aibuddynums[i]], g_AmBotCommands[slot]);
|
||||
botcmdApply(g_MpChrs[g_Vars.currentplayer->aibuddynums[i]].chr, g_AmBotCommands[slot]);
|
||||
}
|
||||
} else {
|
||||
botcmdApply(g_MpAllChrPtrs[g_Vars.currentplayer->aibuddynums[g_AmMenus[g_AmIndex].screenindex - 2]], g_AmBotCommands[slot]);
|
||||
botcmdApply(g_MpChrs[g_Vars.currentplayer->aibuddynums[g_AmMenus[g_AmIndex].screenindex - 2]].chr, g_AmBotCommands[slot]);
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -897,10 +897,10 @@ Gfx *amRenderAibotInfo(Gfx *gdl, s32 buddynum)
|
||||
|
||||
if (!g_AmMenus[g_AmIndex].allbots) {
|
||||
buddynum = g_Vars.currentplayer->aibuddynums[buddynum];
|
||||
aibotname = g_MpAllChrConfigPtrs[buddynum]->name;
|
||||
aibotname = g_MpChrs[buddynum].config->name;
|
||||
|
||||
if (g_MpAllChrPtrs[buddynum]->aibot) {
|
||||
weaponnum = g_MpAllChrPtrs[buddynum]->aibot->weaponnum;
|
||||
if (g_MpChrs[buddynum].chr->aibot) {
|
||||
weaponnum = g_MpChrs[buddynum].chr->aibot->weaponnum;
|
||||
} else {
|
||||
weaponnum = 0;
|
||||
}
|
||||
@@ -957,7 +957,7 @@ Gfx *amRenderAibotInfo(Gfx *gdl, s32 buddynum)
|
||||
0x000000ff, 320, 240, 0, 0);
|
||||
#endif
|
||||
|
||||
g_Vars.currentplayer->commandingaibot = g_MpAllChrPtrs[buddynum];
|
||||
g_Vars.currentplayer->commandingaibot = g_MpChrs[buddynum].chr;
|
||||
} else {
|
||||
char *title = langGet(L_MISC_215); // "All Simulants"
|
||||
|
||||
@@ -1295,7 +1295,7 @@ Gfx *amRender(Gfx *gdl)
|
||||
|
||||
if (mode == AMSLOTMODE_DEFAULT && g_AmMenus[g_AmIndex].screenindex >= 2) {
|
||||
s32 slotcmd = g_AmBotCommands[var800719a0[row][column]];
|
||||
s32 botcmd = g_MpAllChrPtrs[mpchrnum]->aibot->command;
|
||||
s32 botcmd = g_MpChrs[mpchrnum].chr->aibot->command;
|
||||
|
||||
if (slotcmd == botcmd) {
|
||||
mode = AMSLOTMODE_CURRENT;
|
||||
|
||||
+1
-1
@@ -4266,7 +4266,7 @@ struct defaultobj *bgunCreateThrownProjectile2(struct chrdata *chr, struct gset
|
||||
obj->hidden &= 0x0fffffff;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
playernum = mpPlayerGetIndex(chr);
|
||||
playernum = chr->chrnum;
|
||||
} else {
|
||||
playernum = playermgrGetPlayerNumByProp(chr->prop);
|
||||
}
|
||||
|
||||
+2
-2
@@ -634,7 +634,7 @@ void bwalk0f0c4d98(void)
|
||||
void bwalkUpdateSpeedSideways(f32 targetspeed, f32 accelspeed, s32 mult)
|
||||
{
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
targetspeed = (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.unk1c + 25.0f) / 100 * targetspeed;
|
||||
targetspeed = (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].unk1c + 25.0f) / 100 * targetspeed;
|
||||
}
|
||||
|
||||
if (g_Vars.currentplayer->speedstrafe > targetspeed) {
|
||||
@@ -657,7 +657,7 @@ void bwalkUpdateSpeedSideways(f32 targetspeed, f32 accelspeed, s32 mult)
|
||||
void bwalkUpdateSpeedForwards(f32 targetspeed, f32 accelspeed)
|
||||
{
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
targetspeed = (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.unk1c + 25.0f) / 100 * targetspeed;
|
||||
targetspeed = (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].unk1c + 25.0f) / 100 * targetspeed;
|
||||
}
|
||||
|
||||
if (g_Vars.currentplayer->speedgo < targetspeed) {
|
||||
|
||||
+67
-71
@@ -37,10 +37,6 @@
|
||||
#define PICKUPCRITERIA_CRITICAL 1
|
||||
#define PICKUPCRITERIA_ANY 2
|
||||
|
||||
struct chrdata *g_MpBotChrPtrs[MAX_BOTS];
|
||||
|
||||
u8 g_BotCount = 0;
|
||||
|
||||
struct botdifficulty g_BotDifficulties[] = {
|
||||
// shootdelay
|
||||
// | unk04
|
||||
@@ -261,8 +257,8 @@ void botSpawnAll(void)
|
||||
{
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_BotCount; i++) {
|
||||
botSpawn(g_MpBotChrPtrs[i], false);
|
||||
for (i = PLAYERCOUNT(); i < g_MpNumChrs; i++) {
|
||||
botSpawn(g_MpChrs[i].chr, false);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -750,7 +746,7 @@ bool botIsAboutToAttack(struct chrdata *chr, bool arg1)
|
||||
|
||||
if (chr->target != -1) {
|
||||
target = chrGetTargetProp(chr);
|
||||
mpindex = mpPlayerGetIndex(target->chr);
|
||||
mpindex = target->chr->chrnum;
|
||||
result = false;
|
||||
|
||||
if (chr->aibot->chrsinsight[mpindex]) {
|
||||
@@ -873,7 +869,7 @@ s32 botTick(struct prop *prop)
|
||||
&& aibot->chrdistances[aibot->followingplayernum] < 300
|
||||
&& aibot->unk1e4 >= g_Vars.lvframe60 - TICKS(60)
|
||||
&& aibot->config->difficulty != BOTDIFF_MEAT) {
|
||||
targetangle = chrGetInverseTheta(g_MpAllChrPtrs[aibot->followingplayernum]);
|
||||
targetangle = chrGetInverseTheta(g_MpChrs[aibot->followingplayernum].chr);
|
||||
} else if (chr->myaction == MA_AIBOTDEFEND
|
||||
&& aibot->unk1e4 >= g_Vars.lvframe60 - TICKS(60)
|
||||
&& aibot->config->difficulty != BOTDIFF_MEAT) {
|
||||
@@ -1255,7 +1251,7 @@ void botSetTarget(struct chrdata *botchr, s32 propnum)
|
||||
if (propnum >= 0) {
|
||||
otherchr = (g_Vars.props + propnum)->chr;
|
||||
|
||||
index = mpPlayerGetIndex(otherchr);
|
||||
index = otherchr->chrnum;
|
||||
|
||||
botchr->aibot->targetinsight = botchr->aibot->chrsinsight[index];
|
||||
botchr->aibot->targetlastseen60 = botchr->aibot->chrslastseen60[index];
|
||||
@@ -1489,7 +1485,7 @@ void botChooseGeneralTarget(struct chrdata *botchr)
|
||||
// and update stats about that chr
|
||||
aibot->queryplayernum = (aibot->queryplayernum + 1) % g_MpNumChrs;
|
||||
|
||||
trychr = mpGetChrFromPlayerIndex(aibot->queryplayernum);
|
||||
trychr = g_MpChrs[aibot->queryplayernum].chr;
|
||||
|
||||
if (trychr != botchr) {
|
||||
// This condition passes on average once every 4 minutes per player.
|
||||
@@ -1558,8 +1554,8 @@ void botChooseGeneralTarget(struct chrdata *botchr)
|
||||
if (botchr->myaction == MA_AIBOTATTACK
|
||||
&& aibot->attackingplayernum >= 0
|
||||
&& aibot->chrsinsight[aibot->attackingplayernum]
|
||||
&& !chrIsDead(g_MpAllChrPtrs[aibot->attackingplayernum])) {
|
||||
botSetTarget(botchr, g_MpAllChrPtrs[aibot->attackingplayernum]->prop - g_Vars.props);
|
||||
&& !chrIsDead(g_MpChrs[aibot->attackingplayernum].chr)) {
|
||||
botSetTarget(botchr, g_MpChrs[aibot->attackingplayernum].chr->prop - g_Vars.props);
|
||||
return;
|
||||
}
|
||||
|
||||
@@ -1596,7 +1592,7 @@ void botChooseGeneralTarget(struct chrdata *botchr)
|
||||
|
||||
for (tmp = 0; tmp < ARRAYCOUNT(aibot->chrnumsbydistanceasc); tmp++) {
|
||||
s32 i = aibot->chrnumsbydistanceasc[tmp];
|
||||
trychr = mpGetChrFromPlayerIndex(i);
|
||||
trychr = g_MpChrs[i].chr;
|
||||
|
||||
if (trychr != botchr
|
||||
&& !chrIsDead(trychr)
|
||||
@@ -1627,7 +1623,7 @@ void botChooseGeneralTarget(struct chrdata *botchr)
|
||||
|
||||
// Use closest out of sight chr
|
||||
if (closestavailablechrnum >= 0) {
|
||||
trychr = mpGetChrFromPlayerIndex(closestavailablechrnum);
|
||||
trychr = g_MpChrs[closestavailablechrnum].chr;
|
||||
botSetTarget(botchr, trychr->prop - g_Vars.props);
|
||||
return;
|
||||
}
|
||||
@@ -1639,7 +1635,7 @@ void botChooseGeneralTarget(struct chrdata *botchr)
|
||||
|
||||
// Bot has an existing target
|
||||
// If they're still in sight, keep the target
|
||||
playernum = mpPlayerGetIndex((g_Vars.props + botchr->target)->chr);
|
||||
playernum = (g_Vars.props + botchr->target)->chr->chrnum;
|
||||
|
||||
if (aibot->chrsinsight[playernum]) {
|
||||
botSetTarget(botchr, botchr->target);
|
||||
@@ -1650,7 +1646,7 @@ void botChooseGeneralTarget(struct chrdata *botchr)
|
||||
// Check for other chrs who are in sight, by distance
|
||||
for (i = 0; i < ARRAYCOUNT(aibot->chrnumsbydistanceasc); i++) {
|
||||
if (aibot->chrsinsight[aibot->chrnumsbydistanceasc[i]]) {
|
||||
trychr = mpGetChrFromPlayerIndex(aibot->chrnumsbydistanceasc[i]);
|
||||
trychr = g_MpChrs[aibot->chrnumsbydistanceasc[i]].chr;
|
||||
|
||||
if (trychr != botchr
|
||||
&& !chrIsDead(trychr)
|
||||
@@ -1683,7 +1679,7 @@ bool botCanFollow(struct chrdata *botchr, struct chrdata *leader)
|
||||
break;
|
||||
}
|
||||
|
||||
leader = g_MpAllChrPtrs[aibot->followingplayernum];
|
||||
leader = g_MpChrs[aibot->followingplayernum].chr;
|
||||
|
||||
if (leader == botchr) {
|
||||
// Can't follow - it would create a follow loop
|
||||
@@ -1707,10 +1703,12 @@ s32 botFindTeammateToFollow(struct chrdata *chr, f32 range)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (chr != g_MpAllChrPtrs[i]
|
||||
&& !chrIsDead(g_MpAllChrPtrs[i])
|
||||
&& chr->team == g_MpAllChrPtrs[i]->team
|
||||
&& botCanFollow(chr, g_MpAllChrPtrs[i])) {
|
||||
struct chrdata *loopchr = g_MpChrs[i].chr;
|
||||
|
||||
if (chr != loopchr
|
||||
&& !chrIsDead(loopchr)
|
||||
&& chr->team == loopchr->team
|
||||
&& botCanFollow(chr, loopchr)) {
|
||||
f32 distance = chr->aibot->chrdistances[i];
|
||||
|
||||
if (closestplayernum < 0 || distance < closestdistance) {
|
||||
@@ -2221,7 +2219,7 @@ s32 botGetTeamSize(struct chrdata *chr)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (chr->team == g_MpAllChrPtrs[i]->team) {
|
||||
if (chr->team == g_MpChrs[i].team) {
|
||||
count++;
|
||||
}
|
||||
}
|
||||
@@ -2235,9 +2233,9 @@ s32 botGetCountInTeamDoingCommand(struct chrdata *self, u32 command, bool includ
|
||||
s32 i;
|
||||
|
||||
for (i = PLAYERCOUNT(); i < g_MpNumChrs; i++) {
|
||||
if (self->team == g_MpAllChrPtrs[i]->team) {
|
||||
if (includeself || self != g_MpAllChrPtrs[i]) {
|
||||
if (command == g_MpAllChrPtrs[i]->aibot->command) {
|
||||
if (self->team == g_MpChrs[i].team) {
|
||||
if (includeself || self != g_MpChrs[i].chr) {
|
||||
if (command == g_MpChrs[i].chr->aibot->command) {
|
||||
count++;
|
||||
}
|
||||
}
|
||||
@@ -2249,7 +2247,7 @@ s32 botGetCountInTeamDoingCommand(struct chrdata *self, u32 command, bool includ
|
||||
|
||||
s32 botIsChrsCtcTokenHeld(struct chrdata *chr)
|
||||
{
|
||||
struct mpchrconfig *mpchr = g_MpAllChrConfigPtrs[mpPlayerGetIndex(chr)];
|
||||
struct mpchr *mpchr = &g_MpChrs[chr->chrnum];
|
||||
struct prop *prop = g_ScenarioData.ctc.tokens[mpchr->team];
|
||||
|
||||
return prop && (prop->type == PROPTYPE_CHR || prop->type == PROPTYPE_PLAYER);
|
||||
@@ -2278,10 +2276,10 @@ s32 botGetNumTeammatesDefendingHill(struct chrdata *bot)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (bot->team == g_MpAllChrPtrs[i]->team
|
||||
&& g_MpAllChrPtrs[i]->prop->rooms[0] == g_ScenarioData.koh.hillrooms[0]) {
|
||||
if (g_MpAllChrPtrs[i]->aibot->command == AIBOTCMD_DEFHILL
|
||||
|| g_MpAllChrPtrs[i]->aibot->command == AIBOTCMD_HOLDHILL) {
|
||||
struct chrdata *chr = g_MpChrs[i].chr;
|
||||
|
||||
if (bot->team == chr->team && chr->prop->rooms[0] == g_ScenarioData.koh.hillrooms[0]) {
|
||||
if (chr->aibot->command == AIBOTCMD_DEFHILL || chr->aibot->command == AIBOTCMD_HOLDHILL) {
|
||||
count++;
|
||||
}
|
||||
}
|
||||
@@ -2298,17 +2296,15 @@ s32 botGetNumTeammatesDefendingHill(struct chrdata *bot)
|
||||
*/
|
||||
s32 botGetNumOpponentsInHill(struct chrdata *chr)
|
||||
{
|
||||
struct mpchrconfig *mpchr = g_MpAllChrConfigPtrs[mpPlayerGetIndex(chr)];
|
||||
struct mpchrconfig *loopmpchr;
|
||||
struct mpchr *mpchr = &g_MpChrs[chr->chrnum];
|
||||
struct mpchr *loopmpchr;
|
||||
s32 countsperteam[8] = {0};
|
||||
s32 max = 0;
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->prop->rooms[0] == g_ScenarioData.koh.hillrooms[0]) {
|
||||
s32 mpindex = func0f18d074(i);
|
||||
|
||||
loopmpchr = MPCHR(mpindex);
|
||||
if (g_MpChrs[i].chr->prop->rooms[0] == g_ScenarioData.koh.hillrooms[0]) {
|
||||
loopmpchr = &g_MpChrs[i];
|
||||
|
||||
if (loopmpchr->team != mpchr->team) {
|
||||
countsperteam[loopmpchr->team]++;
|
||||
@@ -2588,7 +2584,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// KazeSim will attack people on sight regardless of command
|
||||
if (aibot->config->type == BOTTYPE_KAZE && chr->target != -1 && aibot->targetinsight) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(chrGetTargetProp(chr)->chr);
|
||||
aibot->attackingplayernum = chrGetTargetProp(chr)->chr->chrnum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
}
|
||||
|
||||
@@ -2612,7 +2608,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
&& !botIsTargetInvisible(chr, targetchr)
|
||||
&& botPassesCowardCheck(chr, targetchr)) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(targetchr);
|
||||
aibot->attackingplayernum = targetchr->chrnum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
}
|
||||
} else if (aibot->command == AIBOTCMD_FOLLOW) {
|
||||
@@ -2620,13 +2616,13 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// This is a human command only
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = true;
|
||||
aibot->followingplayernum = mpPlayerGetIndex((g_Vars.props + aibot->followprotectpropnum)->chr);
|
||||
aibot->followingplayernum = (g_Vars.props + aibot->followprotectpropnum)->chr->chrnum;
|
||||
} else if (aibot->command == AIBOTCMD_PROTECT) {
|
||||
// Protect the prop (player) given in followprotectpropnum
|
||||
// This is a human command only
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = false;
|
||||
aibot->followingplayernum = mpPlayerGetIndex((g_Vars.props + aibot->followprotectpropnum)->chr);
|
||||
aibot->followingplayernum = (g_Vars.props + aibot->followprotectpropnum)->chr->chrnum;
|
||||
} else if (aibot->command == AIBOTCMD_DEFEND) {
|
||||
// Defend the position given in defendholdpos
|
||||
// This is a human command only
|
||||
@@ -2642,7 +2638,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
if (g_MpSetup.scenario == MPSCENARIO_CAPTURETHECASE && !aibot->hascase) {
|
||||
// Make an array of pointers to other teams' tokens
|
||||
// but ignore enemy tokens held by other teams
|
||||
s32 botteamindex = radarGetTeamIndex(chr->team);
|
||||
s32 botteamindex = chr->team;
|
||||
s32 i;
|
||||
struct prop *tokens[4];
|
||||
s32 numtokens = 0;
|
||||
@@ -2700,7 +2696,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
} else if (botCanFollow(chr, tokens[index]->chr)) {
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = random() % 4 == 0;
|
||||
aibot->followingplayernum = mpPlayerGetIndex(tokens[index]->chr);
|
||||
aibot->followingplayernum = tokens[index]->chr->chrnum;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -2708,7 +2704,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// Capture the case - recover/protect bot's own token
|
||||
if (g_MpSetup.scenario == MPSCENARIO_CAPTURETHECASE) {
|
||||
// Find out where the bot's token is
|
||||
struct prop *token = g_ScenarioData.ctc.tokens[radarGetTeamIndex(chr->team)];
|
||||
struct prop *token = g_ScenarioData.ctc.tokens[chr->team];
|
||||
|
||||
if (token->type == PROPTYPE_CHR || token->type == PROPTYPE_PLAYER) {
|
||||
struct chrdata *tokenchr = token->chr;
|
||||
@@ -2718,7 +2714,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
if (botCanFollow(chr, tokenchr)) {
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = random() % 4 == 0;
|
||||
aibot->followingplayernum = mpPlayerGetIndex(tokenchr);
|
||||
aibot->followingplayernum = tokenchr->chrnum;
|
||||
}
|
||||
} else {
|
||||
// Held by an opponent - attack them
|
||||
@@ -2726,7 +2722,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
&& !botIsTargetInvisible(chr, tokenchr)
|
||||
&& botPassesCowardCheck(chr, tokenchr)) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(tokenchr);
|
||||
aibot->attackingplayernum = tokenchr->chrnum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
}
|
||||
}
|
||||
@@ -2749,7 +2745,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
&& botPassesCowardCheck(chr, chrGetTargetProp(chr)->chr)) {
|
||||
// Bot is in the hill and sees target - attack them
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(chrGetTargetProp(chr)->chr);
|
||||
aibot->attackingplayernum = chrGetTargetProp(chr)->chr->chrnum;
|
||||
aibot->abortattacktimer60 = TICKS(300);
|
||||
} else {
|
||||
// Go to the hill if not there already
|
||||
@@ -2808,13 +2804,13 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
if (botCanFollow(chr, uplinkchr)) {
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = random() % 4 == 0;
|
||||
aibot->followingplayernum = mpPlayerGetIndex(uplinkchr);
|
||||
aibot->followingplayernum = uplinkchr->chrnum;
|
||||
}
|
||||
} else {
|
||||
// Uplink is held by opponent - attack them
|
||||
if (!botIsTargetInvisible(chr, uplinkchr) && botPassesCowardCheck(chr, uplinkchr)) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(uplinkchr);
|
||||
aibot->attackingplayernum = uplinkchr->chrnum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
}
|
||||
}
|
||||
@@ -2839,12 +2835,12 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
if (botCanFollow(chr, tokenchr)) {
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = random() % 4 == 0;
|
||||
aibot->followingplayernum = mpPlayerGetIndex(tokenchr);
|
||||
aibot->followingplayernum = tokenchr->chrnum;
|
||||
}
|
||||
} else if (!botIsTargetInvisible(chr, tokenchr) && botPassesCowardCheck(chr, tokenchr)) {
|
||||
// Briefcase is held by opponent - attack them
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(tokenchr);
|
||||
aibot->attackingplayernum = tokenchr->chrnum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
}
|
||||
} else {
|
||||
@@ -2856,7 +2852,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
} else if (aibot->command == AIBOTCMD_POPCAP) {
|
||||
// Pop a cap - attack the target
|
||||
if (g_MpSetup.scenario == MPSCENARIO_POPACAP && g_ScenarioData.pac.victimindex >= 0) {
|
||||
struct prop *victimprop = g_MpAllChrPtrs[g_ScenarioData.pac.victims[g_ScenarioData.pac.victimindex]]->prop;
|
||||
struct prop *victimprop = g_MpChrs[g_ScenarioData.pac.victims[g_ScenarioData.pac.victimindex]].chr->prop;
|
||||
|
||||
if (victimprop != chr->prop) {
|
||||
// Victim is not the current bot
|
||||
@@ -2867,13 +2863,13 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
if (botCanFollow(chr, victimchr)) {
|
||||
newaction = MA_AIBOTFOLLOW;
|
||||
aibot->canbreakfollow = random() % 4 == 0;
|
||||
aibot->followingplayernum = mpPlayerGetIndex(victimchr);
|
||||
aibot->followingplayernum = victimchr->chrnum;
|
||||
}
|
||||
} else {
|
||||
// Victim is an opponent - attack them
|
||||
if (!botIsTargetInvisible(chr, victimchr) && botPassesCowardCheck(chr, victimchr)) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(victimchr);
|
||||
aibot->attackingplayernum = victimchr->chrnum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
}
|
||||
}
|
||||
@@ -2903,7 +2899,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
}
|
||||
} else if (g_MpSetup.scenario == MPSCENARIO_POPACAP) {
|
||||
if (g_ScenarioData.pac.victimindex >= 0) {
|
||||
struct prop *victimprop = g_MpAllChrPtrs[g_ScenarioData.pac.victims[g_ScenarioData.pac.victimindex]]->prop;
|
||||
struct prop *victimprop = g_MpChrs[g_ScenarioData.pac.victims[g_ScenarioData.pac.victimindex]].chr->prop;
|
||||
|
||||
if (victimprop == chr->prop) {
|
||||
// Current bot is the victim - follow a teammate for protection
|
||||
@@ -2924,7 +2920,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// If the bot is holding an opponent's token, take it home
|
||||
if (botShouldReturnCtcToken(chr)) {
|
||||
struct pad pad;
|
||||
s32 teamindex = g_ScenarioData.ctc.teamindexes[radarGetTeamIndex(chr->team)];
|
||||
s32 teamindex = g_ScenarioData.ctc.teamindexes[chr->team];
|
||||
newaction = MA_AIBOTGOTOPOS;
|
||||
padUnpack(g_ScenarioData.ctc.spawnpadsperteam[teamindex].homepad, PADFIELD_POS | PADFIELD_ROOM, &pad);
|
||||
aibot->gotopos.x = pad.pos.x;
|
||||
@@ -2937,7 +2933,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
} else if (g_MpSetup.scenario == MPSCENARIO_HACKERCENTRAL) {
|
||||
// If the bot has the uplink, go to the terminal
|
||||
if (g_ScenarioData.htm.uplink == chr->prop) {
|
||||
if (g_ScenarioData.htm.playernuminrange != mpPlayerGetIndex(chr)) {
|
||||
if (g_ScenarioData.htm.playernuminrange != chr->chrnum) {
|
||||
newaction = MA_AIBOTGOTOPROP;
|
||||
aibot->gotoprop = g_ScenarioData.htm.terminals[0].prop;
|
||||
} else {
|
||||
@@ -2952,7 +2948,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
if (aibot->config->type == BOTTYPE_VENGE) {
|
||||
// Attack the last player who killed the bot
|
||||
if (aibot->lastkilledbyplayernum >= 0
|
||||
&& !botIsTargetInvisible(chr, g_MpAllChrPtrs[aibot->lastkilledbyplayernum])) {
|
||||
&& !botIsTargetInvisible(chr, g_MpChrs[aibot->lastkilledbyplayernum].chr)) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = aibot->lastkilledbyplayernum;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
@@ -2961,11 +2957,11 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// Attack a single player the whole match
|
||||
if (aibot->feudplayernum < 0
|
||||
&& aibot->lastkilledbyplayernum >= 0
|
||||
&& !chrCompareTeams(chr, g_MpAllChrPtrs[aibot->lastkilledbyplayernum], COMPARE_FRIENDS)) {
|
||||
&& !chrCompareTeams(chr, g_MpChrs[aibot->lastkilledbyplayernum].chr, COMPARE_FRIENDS)) {
|
||||
aibot->feudplayernum = aibot->lastkilledbyplayernum;
|
||||
}
|
||||
|
||||
if (aibot->feudplayernum >= 0 && !botIsTargetInvisible(chr, g_MpAllChrPtrs[aibot->feudplayernum])) {
|
||||
if (aibot->feudplayernum >= 0 && !botIsTargetInvisible(chr, g_MpChrs[aibot->feudplayernum].chr)) {
|
||||
newaction = MA_AIBOTATTACK;
|
||||
aibot->abortattacktimer60 = -1;
|
||||
aibot->attackingplayernum = aibot->feudplayernum;
|
||||
@@ -2977,8 +2973,8 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < count; i++) {
|
||||
s32 playernum = func0f18d0e8(rankings[i].chrnum);
|
||||
struct chrdata *otherchr = mpGetChrFromPlayerIndex(playernum);
|
||||
s32 playernum = rankings[i].chrnum;
|
||||
struct chrdata *otherchr = g_MpChrs[playernum].chr;
|
||||
|
||||
if (otherchr != chr && !chrIsDead(otherchr)) {
|
||||
#if PAL
|
||||
@@ -3000,7 +2996,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
struct chrdata *otherchr = mpGetChrFromPlayerIndex(i);
|
||||
struct chrdata *otherchr = g_MpChrs[i].chr;
|
||||
|
||||
if (otherchr != chr
|
||||
&& !chrIsDead(otherchr)
|
||||
@@ -3131,7 +3127,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
}
|
||||
} else if (chr->myaction == MA_AIBOTATTACK) {
|
||||
if (aibot->attackingplayernum >= 0
|
||||
&& (chrIsDead(g_MpAllChrPtrs[aibot->attackingplayernum]) || !botPassesCowardCheck(chr, g_MpAllChrPtrs[aibot->attackingplayernum]))) {
|
||||
&& (chrIsDead(g_MpChrs[aibot->attackingplayernum].chr) || !botPassesCowardCheck(chr, g_MpChrs[aibot->attackingplayernum].chr))) {
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
} else if (aibot->attackingplayernum < 0
|
||||
&& (chr->target == -1
|
||||
@@ -3149,7 +3145,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
}
|
||||
} else if (chr->myaction == MA_AIBOTFOLLOW) {
|
||||
if (aibot->followingplayernum < 0
|
||||
|| chrIsDead(g_MpAllChrPtrs[aibot->followingplayernum])) {
|
||||
|| chrIsDead(g_MpChrs[aibot->followingplayernum].chr)) {
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
} else {
|
||||
botcmdTickDistMode(chr);
|
||||
@@ -3158,8 +3154,8 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
&& chr->target != -1
|
||||
&& aibot->targetinsight
|
||||
&& botPassesCowardCheck(chr, chrGetTargetProp(chr)->chr)) {
|
||||
f32 xdist = chr->prop->pos.x - g_MpAllChrPtrs[aibot->followingplayernum]->prop->pos.x;
|
||||
f32 zdist = chr->prop->pos.z - g_MpAllChrPtrs[aibot->followingplayernum]->prop->pos.z;
|
||||
f32 xdist = chr->prop->pos.x - g_MpChrs[aibot->followingplayernum].chr->prop->pos.x;
|
||||
f32 zdist = chr->prop->pos.z - g_MpChrs[aibot->followingplayernum].chr->prop->pos.z;
|
||||
|
||||
if (xdist < 0) {
|
||||
xdist = -xdist;
|
||||
@@ -3172,7 +3168,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// No y check?
|
||||
if (xdist < 500 && zdist < 500) {
|
||||
chr->myaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(chrGetTargetProp(chr)->chr);
|
||||
aibot->attackingplayernum = chrGetTargetProp(chr)->chr->chrnum;
|
||||
aibot->abortattacktimer60 = TICKS(300);
|
||||
aibot->distmode = -1;
|
||||
}
|
||||
@@ -3213,7 +3209,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
&& aibot->targetinsight
|
||||
&& botPassesCowardCheck(chr, chrGetTargetProp(chr)->chr)) {
|
||||
chr->myaction = MA_AIBOTATTACK;
|
||||
aibot->attackingplayernum = mpPlayerGetIndex(chrGetTargetProp(chr)->chr);
|
||||
aibot->attackingplayernum = chrGetTargetProp(chr)->chr->chrnum;
|
||||
aibot->abortattacktimer60 = TICKS(300);
|
||||
aibot->distmode = -1;
|
||||
}
|
||||
@@ -3254,13 +3250,13 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// empty
|
||||
} else if (g_MpSetup.scenario == MPSCENARIO_HACKERCENTRAL
|
||||
&& g_ScenarioData.htm.uplink == chr->prop
|
||||
&& g_ScenarioData.htm.playernuminrange == mpPlayerGetIndex(chr)) {
|
||||
&& g_ScenarioData.htm.playernuminrange == chr->chrnum) {
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
}
|
||||
} else if (chr->myaction == MA_AIBOTDOWNLOAD) {
|
||||
if (botCanDoCriticalPickup(chr)) {
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
} else if (g_ScenarioData.htm.playernuminrange != mpPlayerGetIndex(chr)) {
|
||||
} else if (g_ScenarioData.htm.playernuminrange != chr->chrnum) {
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
}
|
||||
}
|
||||
@@ -3269,7 +3265,7 @@ void botTickUnpaused(struct chrdata *chr)
|
||||
// route to them, even if it won't be followed
|
||||
botChooseGeneralTarget(chr);
|
||||
|
||||
if (mpPlayerGetIndex(chr) == (g_Vars.lvframenum % g_MpNumChrs) && chr->target != -1) {
|
||||
if (chr->chrnum == (g_Vars.lvframenum % g_MpNumChrs) && chr->target != -1) {
|
||||
struct prop *targetprop = chrGetTargetProp(chr);
|
||||
struct waypoint *first = waypointFindClosestToPos(&chr->prop->pos, chr->prop->rooms);
|
||||
struct waypoint *last = waypointFindClosestToPos(&targetprop->pos, targetprop->rooms);
|
||||
|
||||
+2
-2
@@ -223,8 +223,8 @@ bool botactShootFarsight(struct chrdata *chr, s32 arg1, struct coord *vector, st
|
||||
s32 value = fallback;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
oppchr = g_MpAllChrPtrs[i];
|
||||
oppprop = g_MpAllChrPtrs[i]->prop;
|
||||
oppchr = g_MpChrs[i].chr;
|
||||
oppprop = oppchr->prop;
|
||||
|
||||
if (oppprop->type == PROPTYPE_PLAYER) {
|
||||
struct player *player = g_Vars.players[playermgrGetPlayerNumByProp(oppprop)];
|
||||
|
||||
+2
-2
@@ -59,7 +59,7 @@ void botcmdTickDistMode(struct chrdata *chr)
|
||||
|
||||
if (chr->myaction == MA_AIBOTFOLLOW && aibot->followingplayernum >= 0) {
|
||||
limits = g_BotDistConfigs[BOTDISTCFG_FOLLOW];
|
||||
targetprop = g_MpAllChrPtrs[aibot->followingplayernum]->prop;
|
||||
targetprop = g_MpChrs[aibot->followingplayernum].chr->prop;
|
||||
insight = aibot->chrsinsight[aibot->followingplayernum];
|
||||
|
||||
if (chr->target != -1 && (confignum == BOTDISTCFG_CLOSE || confignum == BOTDISTCFG_KAZE)) {
|
||||
@@ -78,7 +78,7 @@ void botcmdTickDistMode(struct chrdata *chr)
|
||||
limits = g_BotDistConfigs[confignum];
|
||||
|
||||
if (chr->myaction == MA_AIBOTATTACK && aibot->attackingplayernum >= 0) {
|
||||
targetprop = g_MpAllChrPtrs[aibot->attackingplayernum]->prop;
|
||||
targetprop = g_MpChrs[aibot->attackingplayernum].chr->prop;
|
||||
insight = aibot->chrsinsight[aibot->attackingplayernum];
|
||||
} else if (chr->target != -1) {
|
||||
targetprop = chrGetTargetProp(chr);
|
||||
|
||||
+4
-4
@@ -633,7 +633,7 @@ void botinvScoreWeapon(struct chrdata *chr, s32 weaponnum, s32 funcnum, s32 arg3
|
||||
if (chr->aibot->config->difficulty > BOTDIFF_MEAT) {
|
||||
if (comparewithtarget) {
|
||||
if (chr->target != -1
|
||||
&& chr->aibot->chrsinsight[mpPlayerGetIndex(chrGetTargetProp(chr)->chr)] == 0
|
||||
&& chr->aibot->chrsinsight[chrGetTargetProp(chr)->chr->chrnum] == 0
|
||||
&& (chr->aibot->random1 % 2) == 0) {
|
||||
score1 += 10;
|
||||
} else {
|
||||
@@ -650,7 +650,7 @@ void botinvScoreWeapon(struct chrdata *chr, s32 weaponnum, s32 funcnum, s32 arg3
|
||||
if (chr->aibot->config->difficulty >= BOTDIFF_NORMAL) {
|
||||
if (comparewithtarget) {
|
||||
if (chr->target != -1
|
||||
&& chr->aibot->chrsinsight[mpPlayerGetIndex(chrGetTargetProp(chr)->chr)] == 0
|
||||
&& chr->aibot->chrsinsight[chrGetTargetProp(chr)->chr->chrnum] == 0
|
||||
&& (chr->aibot->random1 % 2) == 0) {
|
||||
score1 = 178;
|
||||
score2 = 188;
|
||||
@@ -983,8 +983,8 @@ void botinvTick(struct chrdata *chr)
|
||||
if (newweaponnum == WEAPON_COMBATKNIFE
|
||||
&& botactGetAmmoQuantityByWeapon(aibot, WEAPON_COMBATKNIFE, FUNC_SECONDARY, true) >= 2
|
||||
&& chr->target != -1
|
||||
&& chr->aibot->chrdistances[mpPlayerGetIndex(chrGetTargetProp(chr)->chr)] > 200
|
||||
&& chr->aibot->chrdistances[mpPlayerGetIndex(chrGetTargetProp(chr)->chr)] < 1500) {
|
||||
&& chr->aibot->chrdistances[chrGetTargetProp(chr)->chr->chrnum] > 200
|
||||
&& chr->aibot->chrdistances[chrGetTargetProp(chr)->chr->chrnum] < 1500) {
|
||||
newfuncnum = FUNC_SECONDARY;
|
||||
}
|
||||
|
||||
|
||||
+199
-219
@@ -14,18 +14,7 @@
|
||||
#include "data.h"
|
||||
#include "types.h"
|
||||
|
||||
void botmgrRemoveAll(void)
|
||||
{
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < MAX_BOTS; i++) {
|
||||
g_MpBotChrPtrs[i] = NULL;
|
||||
}
|
||||
|
||||
g_BotCount = 0;
|
||||
}
|
||||
|
||||
void botmgrAllocateBot(s32 chrnum, s32 aibotnum)
|
||||
void botmgrAllocateBot(s32 chrnum, s32 botcfgnum, s32 botnum)
|
||||
{
|
||||
s16 rooms[1];
|
||||
struct prop *prop;
|
||||
@@ -38,8 +27,8 @@ void botmgrAllocateBot(s32 chrnum, s32 aibotnum)
|
||||
|
||||
rooms[0] = -1;
|
||||
|
||||
headnum = mpGetHeadId(g_BotConfigsArray[aibotnum].base.mpheadnum);
|
||||
bodynum = mpGetBodyId(g_BotConfigsArray[aibotnum].base.mpbodynum);
|
||||
headnum = mpGetHeadId(g_BotConfigsArray[botcfgnum].base.mpheadnum);
|
||||
bodynum = mpGetBodyId(g_BotConfigsArray[botcfgnum].base.mpbodynum);
|
||||
|
||||
model = bodyAllocateModel(bodynum, headnum, 0);
|
||||
|
||||
@@ -55,6 +44,8 @@ void botmgrAllocateBot(s32 chrnum, s32 aibotnum)
|
||||
|
||||
chr = prop->chr;
|
||||
|
||||
g_MpChrs[chrnum].chr = chr;
|
||||
|
||||
chrSetChrnum(chr, chrnum);
|
||||
|
||||
chr->chrnum = chrnum;
|
||||
@@ -67,215 +58,204 @@ void botmgrAllocateBot(s32 chrnum, s32 aibotnum)
|
||||
chr->race = bodyGetRace(chr->bodynum);
|
||||
chr->flags = CHRFLAG0_CAN_EXAMINE_BODY; // reused flag?
|
||||
chr->flags2 = 0;
|
||||
chr->team = 1 << g_BotConfigsArray[aibotnum].base.team;
|
||||
chr->team = g_BotConfigsArray[botcfgnum].base.team;
|
||||
chr->squadron = 0;
|
||||
|
||||
if (g_BotCount < MAX_BOTS) {
|
||||
g_MpBotChrPtrs[g_BotCount] = chr;
|
||||
g_BotCount++;
|
||||
aibot = mempAlloc(sizeof(struct aibot), MEMPOOL_STAGE);
|
||||
chr->aibot = aibot;
|
||||
|
||||
aibot = mempAlloc(sizeof(struct aibot), MEMPOOL_STAGE);
|
||||
chr->aibot = aibot;
|
||||
|
||||
if (aibot == NULL) {
|
||||
g_MpBotChrPtrs[--g_BotCount] = NULL;
|
||||
return;
|
||||
}
|
||||
|
||||
aibot->chrdistances = mempAlloc(MAX_MPCHRS * sizeof(f32), MEMPOOL_STAGE);
|
||||
aibot->chrsinsight = mempAlloc(MAX_MPCHRS * sizeof(u8), MEMPOOL_STAGE);
|
||||
aibot->chrslastseen60 = mempAlloc(MAX_MPCHRS * sizeof(s32), MEMPOOL_STAGE);
|
||||
aibot->chrrooms = mempAlloc(MAX_MPCHRS * sizeof(s8), MEMPOOL_STAGE);
|
||||
|
||||
if (!aibot->chrdistances || !aibot->chrsinsight || !aibot->chrslastseen60 || !aibot->chrrooms) {
|
||||
g_MpBotChrPtrs[--g_BotCount] = NULL;
|
||||
return;
|
||||
}
|
||||
|
||||
chr->tude = 0;
|
||||
chr->voicebox = random() % 3;
|
||||
|
||||
if (g_HeadsAndBodies[chr->bodynum].ismale == false) {
|
||||
chr->voicebox = VOICEBOX_FEMALE;
|
||||
}
|
||||
|
||||
chr->target = -1;
|
||||
chr->naturalanim = 0;
|
||||
chr->myspecial = -1;
|
||||
chr->yvisang = 0;
|
||||
chr->teamscandist = 0;
|
||||
chr->convtalk = 0;
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
|
||||
g_MpAllChrPtrs[g_MpNumChrs] = chr;
|
||||
g_MpAllChrConfigPtrs[g_MpNumChrs] = &g_BotConfigsArray[aibotnum].base;
|
||||
g_MpNumChrs++;
|
||||
|
||||
aibot->ammoheld = mempAlloc(36 * sizeof(s32), MEMPOOL_STAGE);
|
||||
|
||||
for (i = 0; i < 33; i++) {
|
||||
aibot->ammoheld[i] = 0;
|
||||
}
|
||||
|
||||
aibot->config = &g_BotConfigsArray[aibotnum];
|
||||
|
||||
switch (g_BotConfigsArray[aibotnum].difficulty) {
|
||||
case BOTDIFF_MEAT:
|
||||
aibot->followchance = 0;
|
||||
break;
|
||||
case BOTDIFF_EASY:
|
||||
aibot->followchance = 10;
|
||||
break;
|
||||
default:
|
||||
case BOTDIFF_NORMAL:
|
||||
aibot->followchance = 20;
|
||||
break;
|
||||
case BOTDIFF_HARD:
|
||||
aibot->followchance = 40;
|
||||
break;
|
||||
case BOTDIFF_PERFECT:
|
||||
aibot->followchance = 60;
|
||||
break;
|
||||
case BOTDIFF_DARK:
|
||||
aibot->followchance = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
aibot->aibotnum = aibotnum;
|
||||
aibot->unk064 = 0;
|
||||
aibot->gotoprop = NULL;
|
||||
aibot->timeuntilreload60[0] = 0;
|
||||
aibot->timeuntilreload60[1] = 0;
|
||||
aibot->throwtimer60 = 0;
|
||||
aibot->unk040 = 0.0f;
|
||||
aibot->loadedammo[0] = 0;
|
||||
aibot->loadedammo[1] = 0;
|
||||
aibot->unk058 = 0;
|
||||
aibot->unk059 = 0;
|
||||
aibot->nextbullettimer60[0] = 0;
|
||||
aibot->nextbullettimer60[1] = 0;
|
||||
aibot->unk030 = 301;
|
||||
aibot->unk038 = 0;
|
||||
aibot->punchtimer60[HAND_LEFT] = -1;
|
||||
aibot->punchtimer60[HAND_RIGHT] = 0;
|
||||
aibot->attackingplayernum = -1;
|
||||
aibot->followingplayernum = -1;
|
||||
aibot->dangerouspropnum = -1;
|
||||
aibot->unk068 = 0;
|
||||
aibot->unk06c = 0.0f;
|
||||
aibot->unk070 = 0.0f;
|
||||
aibot->distmode = -1;
|
||||
aibot->lastkilledbyplayernum = -1;
|
||||
aibot->feudplayernum = -1;
|
||||
aibot->command = AIBOTCMD_NORMAL;
|
||||
aibot->unk098 = 0.0f;
|
||||
|
||||
aibot->defendholdpos.x = pos.x;
|
||||
aibot->defendholdpos.y = pos.y;
|
||||
aibot->defendholdpos.z = pos.z;
|
||||
|
||||
aibot->weaponnum = WEAPON_UNARMED;
|
||||
|
||||
aibot->burstsdone[0] = 0;
|
||||
aibot->burstsdone[1] = 0;
|
||||
aibot->skrocket = NULL;
|
||||
aibot->unk0a0 = 0;
|
||||
|
||||
aibot->gunfunc = FUNC_PRIMARY;
|
||||
aibot->iscloserangeweapon = true;
|
||||
aibot->teamisonlyai = false;
|
||||
aibot->hasbriefcase = false;
|
||||
aibot->hascase = false;
|
||||
aibot->cloakdeviceenabled = false;
|
||||
aibot->rcp120cloakenabled = false;
|
||||
aibot->unk04c_04 = false;
|
||||
aibot->unk04c_03 = false;
|
||||
aibot->hasuplink = false;
|
||||
aibot->unk04c_00 = false;
|
||||
|
||||
aibot->hillpadnum = -1;
|
||||
aibot->hillcovernum = -1;
|
||||
|
||||
aibot->lastknownhill = -1;
|
||||
aibot->cyclonedischarging[HAND_LEFT] = false;
|
||||
aibot->cyclonedischarging[HAND_RIGHT] = false;
|
||||
aibot->changeguntimer60 = 0;
|
||||
aibot->distmodettl60 = 0;
|
||||
aibot->forcemainloop = false;
|
||||
aibot->returntodefendtimer60 = 0;
|
||||
aibot->reaperspeed[HAND_LEFT] = 0;
|
||||
aibot->reaperspeed[HAND_RIGHT] = 0;
|
||||
aibot->maulercharge[HAND_LEFT] = 0.0f;
|
||||
aibot->maulercharge[HAND_RIGHT] = 0.0f;
|
||||
aibot->unk0a4 = model0001ae44(chr->model);
|
||||
aibot->angleoffset = 0.0f;
|
||||
aibot->speedtheta = 0.0f;
|
||||
aibot->unk0b0 = model0001ae44(chr->model);
|
||||
|
||||
aibot->unk0b4 = 0.0f;
|
||||
aibot->unk0b8 = 0.0f;
|
||||
aibot->shotspeed.x = 0.0f;
|
||||
aibot->shotspeed.y = 0.0f;
|
||||
aibot->shotspeed.z = 0.0f;
|
||||
aibot->commandtimer60 = 0;
|
||||
aibot->shootdelaytimer60 = 0;
|
||||
aibot->targetlastseen60 = -1;
|
||||
aibot->lastseenanytarget60 = -1;
|
||||
aibot->targetinsight = false;
|
||||
aibot->queryplayernum = 0;
|
||||
|
||||
for (i = 0; i < ARRAYCOUNT(aibot->chrnumsbydistanceasc); i++) {
|
||||
aibot->chrnumsbydistanceasc[i] = -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
aibot->chrdistances[i] = U32_MAX;
|
||||
aibot->chrsinsight[i] = 0;
|
||||
aibot->chrslastseen60[i] = -1;
|
||||
aibot->chrrooms[i] = -1;
|
||||
}
|
||||
|
||||
aibot->unk1c0 = 0.0f;
|
||||
aibot->unk1c4 = 0.0f;
|
||||
aibot->unk1c8 = 0.0f;
|
||||
aibot->unk1cc = -1;
|
||||
aibot->unk1d0 = 0;
|
||||
aibot->unk1d4 = 0.0f;
|
||||
aibot->unk1e4 = -1;
|
||||
aibot->waypoints[0] = NULL;
|
||||
aibot->unk208 = 0;
|
||||
aibot->random1 = random();
|
||||
aibot->random1ttl60 = 0;
|
||||
|
||||
for (i = 0; i < 6; i++) {
|
||||
aibot->killsbygunfunc[i][0] = 0.0f;
|
||||
aibot->killsbygunfunc[i][1] = 0.0f;
|
||||
|
||||
aibot->suicidesbygunfunc[i][0] = 0.0f;
|
||||
aibot->suicidesbygunfunc[i][1] = 0.0f;
|
||||
|
||||
aibot->equipdurations60[i][0] = 0;
|
||||
aibot->equipdurations60[i][1] = 0;
|
||||
|
||||
aibot->unk2a8[i] = 0;
|
||||
}
|
||||
|
||||
aibot->unk2a4 = 0;
|
||||
aibot->dampensuicidesttl60 = 0;
|
||||
aibot->unk2c4 = 0.0f;
|
||||
aibot->targetcloaktimer60 = 0;
|
||||
aibot->canseecloaked = false;
|
||||
|
||||
aibot->random2ttl60 = 0;
|
||||
aibot->random2 = random();
|
||||
aibot->randomfrac = RANDOMFRAC();
|
||||
aibot->cheap = false;
|
||||
aibot->unk078 = 0;
|
||||
aibot->unk050 = 0;
|
||||
aibot->unk09d = 0;
|
||||
|
||||
botinvInit(chr, 10);
|
||||
if (aibot == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
aibot->chrdistances = mempAlloc(g_MpNumChrs * sizeof(f32), MEMPOOL_STAGE);
|
||||
aibot->chrsinsight = mempAlloc(g_MpNumChrs * sizeof(u8), MEMPOOL_STAGE);
|
||||
aibot->chrslastseen60 = mempAlloc(g_MpNumChrs * sizeof(s32), MEMPOOL_STAGE);
|
||||
aibot->chrrooms = mempAlloc(g_MpNumChrs * sizeof(s8), MEMPOOL_STAGE);
|
||||
|
||||
if (!aibot->chrdistances || !aibot->chrsinsight || !aibot->chrslastseen60 || !aibot->chrrooms) {
|
||||
return;
|
||||
}
|
||||
|
||||
chr->tude = 0;
|
||||
chr->voicebox = random() % 3;
|
||||
|
||||
if (g_HeadsAndBodies[chr->bodynum].ismale == false) {
|
||||
chr->voicebox = VOICEBOX_FEMALE;
|
||||
}
|
||||
|
||||
chr->target = -1;
|
||||
chr->naturalanim = 0;
|
||||
chr->myspecial = -1;
|
||||
chr->yvisang = 0;
|
||||
chr->teamscandist = 0;
|
||||
chr->convtalk = 0;
|
||||
chr->myaction = MA_AIBOTMAINLOOP;
|
||||
|
||||
aibot->ammoheld = mempAlloc(36 * sizeof(s32), MEMPOOL_STAGE);
|
||||
|
||||
for (i = 0; i < 33; i++) {
|
||||
aibot->ammoheld[i] = 0;
|
||||
}
|
||||
|
||||
aibot->config = &g_BotConfigsArray[botcfgnum];
|
||||
|
||||
switch (g_BotConfigsArray[botcfgnum].difficulty) {
|
||||
case BOTDIFF_MEAT:
|
||||
aibot->followchance = 0;
|
||||
break;
|
||||
case BOTDIFF_EASY:
|
||||
aibot->followchance = 10;
|
||||
break;
|
||||
default:
|
||||
case BOTDIFF_NORMAL:
|
||||
aibot->followchance = 20;
|
||||
break;
|
||||
case BOTDIFF_HARD:
|
||||
aibot->followchance = 40;
|
||||
break;
|
||||
case BOTDIFF_PERFECT:
|
||||
aibot->followchance = 60;
|
||||
break;
|
||||
case BOTDIFF_DARK:
|
||||
aibot->followchance = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
aibot->aibotnum = botnum;
|
||||
aibot->unk064 = 0;
|
||||
aibot->gotoprop = NULL;
|
||||
aibot->timeuntilreload60[0] = 0;
|
||||
aibot->timeuntilreload60[1] = 0;
|
||||
aibot->throwtimer60 = 0;
|
||||
aibot->unk040 = 0.0f;
|
||||
aibot->loadedammo[0] = 0;
|
||||
aibot->loadedammo[1] = 0;
|
||||
aibot->unk058 = 0;
|
||||
aibot->unk059 = 0;
|
||||
aibot->nextbullettimer60[0] = 0;
|
||||
aibot->nextbullettimer60[1] = 0;
|
||||
aibot->unk030 = 301;
|
||||
aibot->unk038 = 0;
|
||||
aibot->punchtimer60[HAND_LEFT] = -1;
|
||||
aibot->punchtimer60[HAND_RIGHT] = 0;
|
||||
aibot->attackingplayernum = -1;
|
||||
aibot->followingplayernum = -1;
|
||||
aibot->dangerouspropnum = -1;
|
||||
aibot->unk068 = 0;
|
||||
aibot->unk06c = 0.0f;
|
||||
aibot->unk070 = 0.0f;
|
||||
aibot->distmode = -1;
|
||||
aibot->lastkilledbyplayernum = -1;
|
||||
aibot->feudplayernum = -1;
|
||||
aibot->command = AIBOTCMD_NORMAL;
|
||||
aibot->unk098 = 0.0f;
|
||||
|
||||
aibot->defendholdpos.x = pos.x;
|
||||
aibot->defendholdpos.y = pos.y;
|
||||
aibot->defendholdpos.z = pos.z;
|
||||
|
||||
aibot->weaponnum = WEAPON_UNARMED;
|
||||
|
||||
aibot->burstsdone[0] = 0;
|
||||
aibot->burstsdone[1] = 0;
|
||||
aibot->skrocket = NULL;
|
||||
aibot->unk0a0 = 0;
|
||||
|
||||
aibot->gunfunc = FUNC_PRIMARY;
|
||||
aibot->iscloserangeweapon = true;
|
||||
aibot->teamisonlyai = false;
|
||||
aibot->hasbriefcase = false;
|
||||
aibot->hascase = false;
|
||||
aibot->cloakdeviceenabled = false;
|
||||
aibot->rcp120cloakenabled = false;
|
||||
aibot->unk04c_04 = false;
|
||||
aibot->unk04c_03 = false;
|
||||
aibot->hasuplink = false;
|
||||
aibot->unk04c_00 = false;
|
||||
|
||||
aibot->hillpadnum = -1;
|
||||
aibot->hillcovernum = -1;
|
||||
|
||||
aibot->lastknownhill = -1;
|
||||
aibot->cyclonedischarging[HAND_LEFT] = false;
|
||||
aibot->cyclonedischarging[HAND_RIGHT] = false;
|
||||
aibot->changeguntimer60 = 0;
|
||||
aibot->distmodettl60 = 0;
|
||||
aibot->forcemainloop = false;
|
||||
aibot->returntodefendtimer60 = 0;
|
||||
aibot->reaperspeed[HAND_LEFT] = 0;
|
||||
aibot->reaperspeed[HAND_RIGHT] = 0;
|
||||
aibot->maulercharge[HAND_LEFT] = 0.0f;
|
||||
aibot->maulercharge[HAND_RIGHT] = 0.0f;
|
||||
aibot->unk0a4 = model0001ae44(chr->model);
|
||||
aibot->angleoffset = 0.0f;
|
||||
aibot->speedtheta = 0.0f;
|
||||
aibot->unk0b0 = model0001ae44(chr->model);
|
||||
|
||||
aibot->unk0b4 = 0.0f;
|
||||
aibot->unk0b8 = 0.0f;
|
||||
aibot->shotspeed.x = 0.0f;
|
||||
aibot->shotspeed.y = 0.0f;
|
||||
aibot->shotspeed.z = 0.0f;
|
||||
aibot->commandtimer60 = 0;
|
||||
aibot->shootdelaytimer60 = 0;
|
||||
aibot->targetlastseen60 = -1;
|
||||
aibot->lastseenanytarget60 = -1;
|
||||
aibot->targetinsight = false;
|
||||
aibot->queryplayernum = 0;
|
||||
|
||||
for (i = 0; i < ARRAYCOUNT(aibot->chrnumsbydistanceasc); i++) {
|
||||
aibot->chrnumsbydistanceasc[i] = -1;
|
||||
}
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
aibot->chrdistances[i] = U32_MAX;
|
||||
aibot->chrsinsight[i] = 0;
|
||||
aibot->chrslastseen60[i] = -1;
|
||||
aibot->chrrooms[i] = -1;
|
||||
}
|
||||
|
||||
aibot->unk1c0 = 0.0f;
|
||||
aibot->unk1c4 = 0.0f;
|
||||
aibot->unk1c8 = 0.0f;
|
||||
aibot->unk1cc = -1;
|
||||
aibot->unk1d0 = 0;
|
||||
aibot->unk1d4 = 0.0f;
|
||||
aibot->unk1e4 = -1;
|
||||
aibot->waypoints[0] = NULL;
|
||||
aibot->unk208 = 0;
|
||||
aibot->random1 = random();
|
||||
aibot->random1ttl60 = 0;
|
||||
|
||||
for (i = 0; i < 6; i++) {
|
||||
aibot->killsbygunfunc[i][0] = 0.0f;
|
||||
aibot->killsbygunfunc[i][1] = 0.0f;
|
||||
|
||||
aibot->suicidesbygunfunc[i][0] = 0.0f;
|
||||
aibot->suicidesbygunfunc[i][1] = 0.0f;
|
||||
|
||||
aibot->equipdurations60[i][0] = 0;
|
||||
aibot->equipdurations60[i][1] = 0;
|
||||
|
||||
aibot->unk2a8[i] = 0;
|
||||
}
|
||||
|
||||
aibot->unk2a4 = 0;
|
||||
aibot->dampensuicidesttl60 = 0;
|
||||
aibot->unk2c4 = 0.0f;
|
||||
aibot->targetcloaktimer60 = 0;
|
||||
aibot->canseecloaked = false;
|
||||
|
||||
aibot->random2ttl60 = 0;
|
||||
aibot->random2 = random();
|
||||
aibot->randomfrac = RANDOMFRAC();
|
||||
aibot->cheap = false;
|
||||
aibot->unk078 = 0;
|
||||
aibot->unk050 = 0;
|
||||
aibot->unk09d = 0;
|
||||
|
||||
botinvInit(chr, 10);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+1
-1
@@ -835,7 +835,7 @@ bool chr0f01f378(struct model *model, struct coord *arg1, struct coord *arg2, f3
|
||||
if (chr->lastshooter >= 0 && chr->timeshooter > 0) {
|
||||
shooter = chr->lastshooter;
|
||||
} else {
|
||||
shooter = mpPlayerGetIndex(chr);
|
||||
shooter = chr->chrnum;
|
||||
}
|
||||
|
||||
chrDie(chr, shooter);
|
||||
|
||||
@@ -2077,7 +2077,7 @@ void chrDamage(struct chrdata *chr, f32 damage, struct coord *vector, struct gse
|
||||
// (includes MP aibots, not applicable for solo chrs)
|
||||
if (g_Vars.mplayerisrunning) {
|
||||
if (aprop && (aprop->type == PROPTYPE_PLAYER || aprop->type == PROPTYPE_CHR)) {
|
||||
aplayernum = mpPlayerGetIndex(aprop->chr);
|
||||
aplayernum = aprop->chr->chrnum;
|
||||
}
|
||||
} else {
|
||||
if (aprop && aprop->type == PROPTYPE_PLAYER) {
|
||||
@@ -2510,7 +2510,7 @@ void chrDie(struct chrdata *chr, s32 aplayernum)
|
||||
chr->act_die.thudframe2 = -1;
|
||||
chr->act_die.timeextra = 0;
|
||||
|
||||
mpstatsRecordDeath(aplayernum, mpPlayerGetIndex(chr));
|
||||
mpstatsRecordDeath(aplayernum, chr->chrnum);
|
||||
botinvDropAll(chr, chr->aibot->weaponnum);
|
||||
|
||||
#if VERSION >= VERSION_NTSC_1_0
|
||||
@@ -5491,7 +5491,7 @@ void chrTickShoot(struct chrdata *chr, s32 handnum)
|
||||
s32 playernum = -1;
|
||||
|
||||
if (g_Vars.mplayerisrunning) {
|
||||
playernum = mpPlayerGetIndex(chr);
|
||||
playernum = chr->chrnum;
|
||||
}
|
||||
|
||||
bgunPlayPropHitSound(&gset, hitprop, -1);
|
||||
@@ -5521,7 +5521,7 @@ void chrTickShoot(struct chrdata *chr, s32 handnum)
|
||||
|
||||
// Create explosion if using Phoenix
|
||||
if (gset.weaponnum == WEAPON_PHOENIX && gset.weaponfunc == FUNC_SECONDARY) {
|
||||
s32 playernum = chr->aibot ? mpPlayerGetIndex(chr) : g_Vars.currentplayernum;
|
||||
s32 playernum = chr->aibot ? chr->chrnum : g_Vars.currentplayernum;
|
||||
|
||||
if (!queriedhitrooms) {
|
||||
func0f065e74(&gunpos, gunrooms, &hitpos, hitrooms);
|
||||
|
||||
@@ -962,7 +962,7 @@ void explosionInflictDamage(struct prop *expprop)
|
||||
}
|
||||
|
||||
{
|
||||
struct chrdata *ownerchr = mpGetChrFromPlayerIndex(exp->owner);
|
||||
struct chrdata *ownerchr = g_MpChrs[exp->owner].chr;
|
||||
|
||||
if (ownerchr) {
|
||||
ownerprop = ownerchr->prop;
|
||||
@@ -1178,7 +1178,7 @@ u32 explosionTick(struct prop *prop)
|
||||
|
||||
scorchsize *= 0.8f + 0.2f * RANDOMFRAC();
|
||||
|
||||
chr = mpGetChrFromPlayerIndex(exp->owner);
|
||||
chr = g_MpChrs[exp->owner].chr;
|
||||
|
||||
if (g_Rooms[exp->room].gfxdata) {
|
||||
if (g_Rooms[exp->room].gfxdata->xlublocks && bgTestHitInRoom(&prop->pos, &exp->unk3d0, exp->room, &hitthing)) {
|
||||
|
||||
+2
-1
@@ -350,6 +350,7 @@ void lvReset(s32 stagenum)
|
||||
propsndReset();
|
||||
setupLoadFiles(stagenum);
|
||||
scenarioReset();
|
||||
varsResetRoomProps();
|
||||
bodiesReset(stagenum);
|
||||
setupCreateProps(stagenum);
|
||||
explosionsReset();
|
||||
@@ -1688,7 +1689,7 @@ void lvTick(void)
|
||||
}
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->actiontype == ACT_DIE) {
|
||||
if (g_MpChrs[i].chr->actiontype == ACT_DIE) {
|
||||
numdying++;
|
||||
}
|
||||
}
|
||||
|
||||
+28
-30
@@ -3480,7 +3480,7 @@ Gfx *menuitemRankingRender(Gfx *gdl, struct menurendercontext *context)
|
||||
gdl = textRenderProjected(gdl, &x, &y, g_BossFile.teamnames[ranking->teamnum],
|
||||
g_CharsHandelGothicSm, g_FontHandelGothicSm, textcolour, context->width, context->height, 0, 0);
|
||||
} else {
|
||||
gdl = textRenderProjected(gdl, &x, &y, ranking->mpchr->name,
|
||||
gdl = textRenderProjected(gdl, &x, &y, ranking->mpchr->config->name,
|
||||
g_CharsHandelGothicSm, g_FontHandelGothicSm, textcolour, context->width, context->height, 0, 0);
|
||||
}
|
||||
|
||||
@@ -3563,7 +3563,7 @@ Gfx *menuitemPlayerStatsRender(Gfx *gdl, struct menurendercontext *context)
|
||||
s32 y;
|
||||
u32 maincolour;
|
||||
s32 playernum = g_MpSelectedPlayersForStats[g_MpPlayerNum];
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
u32 selectioncolour;
|
||||
s32 textheight;
|
||||
s32 textwidth;
|
||||
@@ -3594,7 +3594,7 @@ Gfx *menuitemPlayerStatsRender(Gfx *gdl, struct menurendercontext *context)
|
||||
x = context->x + 2;
|
||||
y = context->y + 1;
|
||||
|
||||
gdl = textRenderProjected(gdl, &x, &y, mpchr->name, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
gdl = textRenderProjected(gdl, &x, &y, mpchr->config->name, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
selectioncolour, context->width, context->height, 0, 0);
|
||||
|
||||
// "Suicides" heading
|
||||
@@ -3765,45 +3765,43 @@ Gfx *menuitemPlayerStatsRender(Gfx *gdl, struct menurendercontext *context)
|
||||
|
||||
ypos -= data->scrolloffset;
|
||||
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
struct mpchrconfig *loopmpchr = MPCHR(i);
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
struct mpchr *loopmpchr = MPCHR(i);
|
||||
|
||||
if (i != playernum) {
|
||||
// Name
|
||||
x = context->x + 29;
|
||||
y = context->y + ypos;
|
||||
gdl = textRenderProjected(gdl, &x, &y, loopmpchr->name, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
0x00ffffff, context->width, context->height, 0, 0);
|
||||
if (i != playernum) {
|
||||
// Name
|
||||
x = context->x + 29;
|
||||
y = context->y + ypos;
|
||||
gdl = textRenderProjected(gdl, &x, &y, loopmpchr->config->name, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
0x00ffffff, context->width, context->height, 0, 0);
|
||||
|
||||
// Num deaths
|
||||
sprintf(buffer, "%d\n", loopmpchr->killcounts[playernum]);
|
||||
textMeasure(&textheight, &textwidth, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm, 0);
|
||||
x = context->x - textwidth + 120;
|
||||
y = context->y + ypos;
|
||||
gdl = textRenderProjected(gdl, &x, &y, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
0xff4040ff, context->width, context->height, 0, 0);
|
||||
// Num deaths
|
||||
sprintf(buffer, "%d\n", loopmpchr->killcounts[playernum]);
|
||||
textMeasure(&textheight, &textwidth, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm, 0);
|
||||
x = context->x - textwidth + 120;
|
||||
y = context->y + ypos;
|
||||
gdl = textRenderProjected(gdl, &x, &y, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
0xff4040ff, context->width, context->height, 0, 0);
|
||||
|
||||
// Num kills
|
||||
sprintf(buffer, "%d\n", mpchr->killcounts[i]);
|
||||
textMeasure(&textheight, &textwidth, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm, 0);
|
||||
// Num kills
|
||||
sprintf(buffer, "%d\n", mpchr->killcounts[i]);
|
||||
textMeasure(&textheight, &textwidth, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm, 0);
|
||||
|
||||
#if VERSION == VERSION_JPN_FINAL
|
||||
x = context->x + 4;
|
||||
x = context->x + 4;
|
||||
#else
|
||||
x = context->x - textwidth + 25;
|
||||
x = context->x - textwidth + 25;
|
||||
#endif
|
||||
|
||||
y = context->y + ypos;
|
||||
gdl = textRenderProjected(gdl, &x, &y, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
0x00ff00ff, context->width, context->height, 0, 0);
|
||||
y = context->y + ypos;
|
||||
gdl = textRenderProjected(gdl, &x, &y, buffer, g_CharsHandelGothicSm, g_FontHandelGothicSm,
|
||||
0x00ff00ff, context->width, context->height, 0, 0);
|
||||
|
||||
#if VERSION == VERSION_JPN_FINAL
|
||||
ypos += 13;
|
||||
ypos += 13;
|
||||
#else
|
||||
ypos += 10;
|
||||
ypos += 10;
|
||||
#endif
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -73,7 +73,7 @@ void modelmgrAllocateSlots(s32 numobjs, s32 numchrs, bool haslaptops)
|
||||
g_ModelNumObjs = numobjs;
|
||||
g_ModelNumChrs = numchrs;
|
||||
|
||||
if (g_Vars.stagenum == STAGE_TITLE) {
|
||||
if (g_Vars.stagenum >= STAGE_TITLE) {
|
||||
g_MaxRwdataType1 = 35;
|
||||
g_MaxRwdataType2 = 25;
|
||||
g_MaxRwdataType3 = 20;
|
||||
|
||||
@@ -30,68 +30,17 @@ struct menudialogdef g_MpEndscreenSavePlayerMenuDialog;
|
||||
|
||||
s32 mpStatsForPlayerDropdownHandler(s32 operation, struct menuitem *item, union handlerdata *data)
|
||||
{
|
||||
struct mpchrconfig *mpchr;
|
||||
s32 v0;
|
||||
s32 v1;
|
||||
s32 a1;
|
||||
|
||||
switch (operation) {
|
||||
case MENUOP_GETOPTIONCOUNT:
|
||||
data->list.value = 0;
|
||||
|
||||
for (v0 = 0; v0 < MAX_MPCHRS; v0++) {
|
||||
if (g_MpSetup.chrslots & (1 << v0)) {
|
||||
data->list.value++;
|
||||
}
|
||||
}
|
||||
data->list.value = g_MpNumChrs;
|
||||
break;
|
||||
case MENUOP_GETOPTIONTEXT:
|
||||
v0 = 0;
|
||||
|
||||
for (a1 = 0; a1 < MAX_MPCHRS; a1++) {
|
||||
if (g_MpSetup.chrslots & (1 << a1)) {
|
||||
mpchr = MPCHR(a1);
|
||||
|
||||
if (v0 == data->list.value) {
|
||||
return (s32) mpchr->name;
|
||||
}
|
||||
|
||||
v0++;
|
||||
}
|
||||
}
|
||||
|
||||
return (s32) "";
|
||||
return (s32) g_MpChrs[data->list.value].config->name;
|
||||
case MENUOP_SET:
|
||||
v0 = 0;
|
||||
|
||||
for (a1 = 0; a1 < MAX_MPCHRS; a1++) {
|
||||
if (g_MpSetup.chrslots & (1 << a1)) {
|
||||
if (v0);
|
||||
|
||||
if (data->list.value == v0) {
|
||||
g_MpSelectedPlayersForStats[g_MpPlayerNum] = a1;
|
||||
}
|
||||
|
||||
v0++;
|
||||
}
|
||||
}
|
||||
|
||||
g_MpSelectedPlayersForStats[g_MpPlayerNum] = data->list.value;
|
||||
break;
|
||||
case MENUOP_GETSELECTEDINDEX:
|
||||
v0 = 0;
|
||||
|
||||
for (v1 = 0; v1 < MAX_MPCHRS; v1++) {
|
||||
if (g_MpSetup.chrslots & (1 << v1)) {
|
||||
if (v0);
|
||||
|
||||
if (g_MpSelectedPlayersForStats[g_MpPlayerNum] == v1) {
|
||||
data->list.value = v0;
|
||||
}
|
||||
|
||||
v0++;
|
||||
}
|
||||
}
|
||||
|
||||
data->list.value = g_MpSelectedPlayersForStats[g_MpPlayerNum];
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -425,10 +374,10 @@ char *mpMenuTextWeaponDescription(struct menuitem *item)
|
||||
|
||||
char *mpMenuTitleStatsFor(struct menudialogdef *dialogdef)
|
||||
{
|
||||
struct mpchrconfig *mpchr = MPCHR(g_MpSelectedPlayersForStats[g_MpPlayerNum]);
|
||||
struct mpchr *mpchr = MPCHR(g_MpSelectedPlayersForStats[g_MpPlayerNum]);
|
||||
|
||||
// "Stats for %s"
|
||||
sprintf(g_StringPointer, langGet(L_MPMENU_280), mpchr->name);
|
||||
sprintf(g_StringPointer, langGet(L_MPMENU_280), mpchr->config->name);
|
||||
return g_StringPointer;
|
||||
}
|
||||
|
||||
@@ -583,13 +532,13 @@ char *mpMenuTextPlacementWithSuffix(struct menuitem *item)
|
||||
L_MPMENU_275, // "12th"
|
||||
};
|
||||
|
||||
return langGet(suffixes[g_PlayerConfigsArray[g_MpPlayerNum].base.placement]);
|
||||
return langGet(suffixes[g_MpChrs[g_MpPlayerNum].placement]);
|
||||
}
|
||||
|
||||
s32 mpPlacementMenuHandler(s32 operation, struct menuitem *item, union handlerdata *data)
|
||||
{
|
||||
if (operation == MENUOP_GETCOLOUR) {
|
||||
if (g_PlayerConfigsArray[g_MpPlayerNum].base.placement == 0) { // winner
|
||||
if (g_MpChrs[g_MpPlayerNum].placement == 0) { // winner
|
||||
data->label.colour2 = colourBlend(data->label.colour2, 0xffff00ff, menuGetSinOscFrac(40) * 255);
|
||||
}
|
||||
}
|
||||
|
||||
+113
-210
@@ -29,10 +29,9 @@
|
||||
#include "types.h"
|
||||
|
||||
// bss
|
||||
struct chrdata *g_MpAllChrPtrs[MAX_MPCHRS];
|
||||
struct mpchrconfig *g_MpAllChrConfigPtrs[MAX_MPCHRS];
|
||||
s32 g_MpNumChrs;
|
||||
u32 var800ac534;
|
||||
s32 g_MpNumChrs;
|
||||
struct mpchr *g_MpChrs;
|
||||
struct mpbotconfig g_BotConfigsArray[MAX_BOTS];
|
||||
u8 g_MpSimulantDifficultiesPerNumPlayers[8][4];
|
||||
struct mpplayerconfig g_PlayerConfigsArray[6];
|
||||
@@ -122,19 +121,6 @@ f32 mpHandicapToDamageScale(u8 value)
|
||||
return tmp * tmp * 3 - 2;
|
||||
}
|
||||
|
||||
void func0f187838(struct mpchrconfig *mpchr)
|
||||
{
|
||||
s32 i = 0;
|
||||
|
||||
while (i < ARRAYCOUNT(mpchr->killcounts)) {
|
||||
mpchr->killcounts[i++] = 0;
|
||||
}
|
||||
|
||||
mpchr->numdeaths = 0;
|
||||
mpchr->numpoints = 0;
|
||||
mpchr->unk40 = 0;
|
||||
}
|
||||
|
||||
void mpStartMatch(void)
|
||||
{
|
||||
s32 i;
|
||||
@@ -195,22 +181,12 @@ void mpReset(void)
|
||||
|
||||
mpCalculatePlayerTitle(&g_PlayerConfigsArray[i]);
|
||||
|
||||
|
||||
g_PlayerConfigsArray[i].newtitle = g_PlayerConfigsArray[i].title;
|
||||
g_MpNumChrs++;
|
||||
mpindex++;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i != MAX_MPCHRS; i++) {
|
||||
struct mpchrconfig *mpchr = MPCHR(i);
|
||||
|
||||
func0f187838(mpchr);
|
||||
|
||||
#if VERSION >= VERSION_NTSC_1_0
|
||||
g_MpAllChrPtrs[i] = NULL;
|
||||
#endif
|
||||
}
|
||||
g_MpChrs = NULL;
|
||||
|
||||
g_MpSetup.paused = false;
|
||||
|
||||
@@ -286,19 +262,15 @@ void mpCalculateTeamIsOnlyAi(void)
|
||||
s32 i;
|
||||
s32 j;
|
||||
|
||||
// Iterate simulants, which go after players in the g_MpAllChrPtrs array
|
||||
// Iterate simulants
|
||||
for (i = playercount; i < g_MpNumChrs; i++) {
|
||||
if (!g_MpAllChrPtrs[i]) {
|
||||
continue;
|
||||
}
|
||||
|
||||
g_MpAllChrPtrs[i]->aibot->teamisonlyai = true;
|
||||
g_MpChrs[i].chr->aibot->teamisonlyai = true;
|
||||
|
||||
if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
// Iterate human players
|
||||
for (j = 0; j < playercount; j++) {
|
||||
if (g_MpAllChrPtrs[i]->team == g_MpAllChrPtrs[j]->team) {
|
||||
g_MpAllChrPtrs[i]->aibot->teamisonlyai = false;
|
||||
if (g_MpChrs[i].team == g_MpChrs[j].team) {
|
||||
g_MpChrs[i].chr->aibot->teamisonlyai = false;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -308,9 +280,7 @@ void mpCalculateTeamIsOnlyAi(void)
|
||||
|
||||
void func0f187fbc(s32 playernum)
|
||||
{
|
||||
g_PlayerConfigsArray[playernum].base.unk18 = 80;
|
||||
g_PlayerConfigsArray[playernum].base.unk1a = 80;
|
||||
g_PlayerConfigsArray[playernum].base.unk1c = 75;
|
||||
g_PlayerConfigsArray[playernum].unk1c = 75;
|
||||
}
|
||||
|
||||
void func0f187fec(void)
|
||||
@@ -358,7 +328,7 @@ void mpPlayerSetDefaults(s32 playernum, bool autonames)
|
||||
}
|
||||
|
||||
g_PlayerConfigsArray[playernum].base.mpheadnum = mpGetMpheadnumByMpbodynum(g_PlayerConfigsArray[playernum].base.mpbodynum);
|
||||
g_PlayerConfigsArray[playernum].base.displayoptions = MPDISPLAYOPTION_RADAR | MPDISPLAYOPTION_HIGHLIGHTTEAMS;
|
||||
g_PlayerConfigsArray[playernum].displayoptions = MPDISPLAYOPTION_RADAR | MPDISPLAYOPTION_HIGHLIGHTTEAMS;
|
||||
g_PlayerConfigsArray[playernum].fileguid.fileid = 0;
|
||||
g_PlayerConfigsArray[playernum].fileguid.deviceserial = 0;
|
||||
|
||||
@@ -596,7 +566,7 @@ s32 mpGetPlayerRankings(struct ranking *rankings)
|
||||
s32 i;
|
||||
s32 scores[MAX_MPCHRS];
|
||||
u32 rankablescores[MAX_MPCHRS];
|
||||
struct mpchrconfig *mpchrs[MAX_MPCHRS];
|
||||
struct mpchr *mpchrs[MAX_MPCHRS];
|
||||
s32 chrnums[MAX_MPCHRS];
|
||||
s32 count = 0;
|
||||
s32 numteams;
|
||||
@@ -605,7 +575,7 @@ s32 mpGetPlayerRankings(struct ranking *rankings)
|
||||
s32 loser;
|
||||
s32 score;
|
||||
s32 deaths;
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
s32 dstindex;
|
||||
bool found;
|
||||
u32 rankablescore;
|
||||
@@ -616,44 +586,42 @@ s32 mpGetPlayerRankings(struct ranking *rankings)
|
||||
}
|
||||
|
||||
// Populate 4 arrays with player info, sorted by highest score descending
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
mpchr = MPCHR(i);
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
mpchr = MPCHR(i);
|
||||
|
||||
scenarioCalculatePlayerScore(mpchr, i, &score, &deaths);
|
||||
scenarioCalculatePlayerScore(mpchr, i, &score, &deaths);
|
||||
|
||||
rankablescore = (score + 0x8000) << 16 | (0xffff - deaths);
|
||||
dstindex = 0;
|
||||
found = false;
|
||||
rankablescore = (score + 0x8000) << 16 | (0xffff - deaths);
|
||||
dstindex = 0;
|
||||
found = false;
|
||||
|
||||
// Find where this player should be placed in the sorted arrays
|
||||
for (j = 0; j < count && !found; j++) {
|
||||
if (rankablescore > rankablescores[j]) {
|
||||
dstindex = j;
|
||||
found = true;
|
||||
}
|
||||
// Find where this player should be placed in the sorted arrays
|
||||
for (j = 0; j < count && !found; j++) {
|
||||
if (rankablescore > rankablescores[j]) {
|
||||
dstindex = j;
|
||||
found = true;
|
||||
}
|
||||
|
||||
if (!found) {
|
||||
dstindex = count;
|
||||
}
|
||||
|
||||
// Shuffle everything forward after dstindex to create a gap
|
||||
for (j = count; j > dstindex; j--) {
|
||||
rankablescores[j] = rankablescores[j - 1];
|
||||
scores[j] = scores[j - 1];
|
||||
mpchrs[j] = mpchrs[j - 1];
|
||||
chrnums[j] = chrnums[j - 1];
|
||||
}
|
||||
|
||||
count++;
|
||||
|
||||
// Write the new figures
|
||||
rankablescores[dstindex] = (score + 0x8000) << 16 | (0xffff - deaths);
|
||||
scores[dstindex] = score;
|
||||
mpchrs[dstindex] = mpchr;
|
||||
chrnums[dstindex] = i;
|
||||
}
|
||||
|
||||
if (!found) {
|
||||
dstindex = count;
|
||||
}
|
||||
|
||||
// Shuffle everything forward after dstindex to create a gap
|
||||
for (j = count; j > dstindex; j--) {
|
||||
rankablescores[j] = rankablescores[j - 1];
|
||||
scores[j] = scores[j - 1];
|
||||
mpchrs[j] = mpchrs[j - 1];
|
||||
chrnums[j] = chrnums[j - 1];
|
||||
}
|
||||
|
||||
count++;
|
||||
|
||||
// Write the new figures
|
||||
rankablescores[dstindex] = (score + 0x8000) << 16 | (0xffff - deaths);
|
||||
scores[dstindex] = score;
|
||||
mpchrs[dstindex] = mpchr;
|
||||
chrnums[dstindex] = i;
|
||||
}
|
||||
|
||||
// Populate the rankings array, copy some values into the mpchr structs
|
||||
@@ -726,7 +694,7 @@ s32 mpGetPlayerRankings(struct ranking *rankings)
|
||||
*/
|
||||
s32 mpCalculateTeamScore(s32 teamnum, s32 *result)
|
||||
{
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
s32 teamscore = 0;
|
||||
s32 teamdeaths = 0;
|
||||
bool teamexists = false;
|
||||
@@ -735,16 +703,14 @@ s32 mpCalculateTeamScore(s32 teamnum, s32 *result)
|
||||
s32 score;
|
||||
s32 deaths;
|
||||
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
mpchr = MPCHR(i);
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
mpchr = MPCHR(i);
|
||||
|
||||
if (mpchr->team == teamnum) {
|
||||
scenarioCalculatePlayerScore(mpchr, i, &score, &deaths);
|
||||
teamexists = true;
|
||||
teamscore += score;
|
||||
teamdeaths += deaths;
|
||||
}
|
||||
if (mpchr->team == teamnum) {
|
||||
scenarioCalculatePlayerScore(mpchr, i, &score, &deaths);
|
||||
teamexists = true;
|
||||
teamscore += score;
|
||||
teamdeaths += deaths;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2177,8 +2143,8 @@ void mpCalculateAwards(void)
|
||||
// At the same time, populate the metrics array
|
||||
// which is a temporary array for award calculation.
|
||||
for (i = 0; i < playercount; i++) {
|
||||
struct mpchrconfig *mpchr = mpGetChrConfigBySlotNum(i);
|
||||
struct mpplayerconfig *mpplayer = (struct mpplayerconfig *)mpchr;
|
||||
struct mpchr *mpchr = MPCHR(i);
|
||||
struct mpplayerconfig *mpplayer = mpchr->playerconfig;
|
||||
s32 chrnum = mpGetChrIndexBySlotNum(i);
|
||||
s32 sum;
|
||||
|
||||
@@ -2193,7 +2159,7 @@ void mpCalculateAwards(void)
|
||||
metrics[i].numdeaths = 0;
|
||||
metrics[i].numsuicides = 0;
|
||||
|
||||
for (j = 0; j < MAX_MPCHRS; j++) {
|
||||
for (j = 0; j < g_MpNumChrs; j++) {
|
||||
if (chrnum == j) {
|
||||
metrics[i].numsuicides += mpchr->killcounts[j];
|
||||
} else {
|
||||
@@ -2201,8 +2167,8 @@ void mpCalculateAwards(void)
|
||||
}
|
||||
}
|
||||
|
||||
for (j = 0; j < MAX_MPCHRS; j++) {
|
||||
struct mpchrconfig *othermpchr = MPCHR(j);
|
||||
for (j = 0; j < g_MpNumChrs; j++) {
|
||||
struct mpchr *othermpchr = MPCHR(j);
|
||||
metrics[i].numdeaths += othermpchr->killcounts[chrnum];
|
||||
}
|
||||
|
||||
@@ -2258,16 +2224,14 @@ void mpCalculateAwards(void)
|
||||
if ((numchrs >= 2 && (g_MpSetup.options & MPOPTION_TEAMSENABLED) == 0) || numteams >= 2) {
|
||||
bool lost = false;
|
||||
|
||||
if (mpplayer->base.placement == 0) {
|
||||
for (j = 0; j < MAX_MPCHRS; j++) {
|
||||
if (g_MpSetup.chrslots & (1 << j)) {
|
||||
struct mpchrconfig *othermpchr = MPCHR(j);
|
||||
if (mpchr->placement == 0) {
|
||||
for (j = 0; j < g_MpNumChrs; j++) {
|
||||
struct mpchr *othermpchr = MPCHR(j);
|
||||
|
||||
if (othermpchr->rankablescore == mpplayer->base.rankablescore
|
||||
&& othermpchr != &mpplayer->base
|
||||
&& !((g_MpSetup.options & MPOPTION_TEAMSENABLED) && othermpchr->team == mpplayer->base.team)) {
|
||||
lost = true;
|
||||
}
|
||||
if (othermpchr->rankablescore == mpchr->rankablescore
|
||||
&& othermpchr != mpchr
|
||||
&& !((g_MpSetup.options & MPOPTION_TEAMSENABLED) && othermpchr->team == mpchr->team)) {
|
||||
lost = true;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2276,19 +2240,17 @@ void mpCalculateAwards(void)
|
||||
}
|
||||
}
|
||||
|
||||
if (((g_MpSetup.options & MPOPTION_TEAMSENABLED) == 0 && numchrs == mpplayer->base.placement + 1)
|
||||
|| ((g_MpSetup.options & MPOPTION_TEAMSENABLED) && numteams == mpplayer->base.placement + 1)) {
|
||||
if (((g_MpSetup.options & MPOPTION_TEAMSENABLED) == 0 && numchrs == mpchr->placement + 1)
|
||||
|| ((g_MpSetup.options & MPOPTION_TEAMSENABLED) && numteams == mpchr->placement + 1)) {
|
||||
bool won = false;
|
||||
|
||||
for (j = 0; j < MAX_MPCHRS; j++) {
|
||||
if (g_MpSetup.chrslots & (1 << j)) {
|
||||
struct mpchrconfig *othermpchr = MPCHR(j);
|
||||
for (j = 0; j < g_MpNumChrs; j++) {
|
||||
struct mpchr *othermpchr = MPCHR(j);
|
||||
|
||||
if (othermpchr->rankablescore == mpplayer->base.rankablescore
|
||||
&& &mpplayer->base != othermpchr
|
||||
&& !((g_MpSetup.options & MPOPTION_TEAMSENABLED) && othermpchr->team == mpplayer->base.team)) {
|
||||
won = true;
|
||||
}
|
||||
if (othermpchr->rankablescore == mpchr->rankablescore
|
||||
&& mpchr != othermpchr
|
||||
&& !((g_MpSetup.options & MPOPTION_TEAMSENABLED) && othermpchr->team == mpchr->team)) {
|
||||
won = true;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2462,43 +2424,41 @@ void mpCalculateAwards(void)
|
||||
s32 leastdeathsplayer = -1;
|
||||
s32 k;
|
||||
|
||||
for (k = 0; k < MAX_MPCHRS; k++) {
|
||||
if (g_MpSetup.chrslots & (1 << k)) {
|
||||
s32 totalkills = 0;
|
||||
struct mpchrconfig *mpchr = MPCHR(k);
|
||||
for (k = 0; k < g_MpNumChrs; k++) {
|
||||
s32 totalkills = 0;
|
||||
struct mpchr *mpchr = MPCHR(k);
|
||||
|
||||
for (j = 0; j < MAX_MPCHRS; j++) {
|
||||
// @bug: i should be k. The value of i was incremented after
|
||||
// the last iteration of its loop above so it'll be between
|
||||
// 1 and 4 inclusively depending on the number of players.
|
||||
// The bot nums start from 4 regardless of how many players
|
||||
// there are. So in a game with 4 humans, the kills on the
|
||||
// first bot will not be considered for the killmaster medal
|
||||
// which means the medal could go to a player who got fewer
|
||||
// total kills. Additionally, suicides are counted as kills
|
||||
// while the intention here was to omit them.
|
||||
if (i != j) {
|
||||
totalkills += mpchr->killcounts[j];
|
||||
}
|
||||
for (j = 0; j < g_MpNumChrs; j++) {
|
||||
// @bug: i should be k. The value of i was incremented after
|
||||
// the last iteration of its loop above so it'll be between
|
||||
// 1 and 4 inclusively depending on the number of players.
|
||||
// The bot nums start from 4 regardless of how many players
|
||||
// there are. So in a game with 4 humans, the kills on the
|
||||
// first bot will not be considered for the killmaster medal
|
||||
// which means the medal could go to a player who got fewer
|
||||
// total kills. Additionally, suicides are counted as kills
|
||||
// while the intention here was to omit them.
|
||||
if (i != j) {
|
||||
totalkills += mpchr->killcounts[j];
|
||||
}
|
||||
}
|
||||
|
||||
if (totalkills == mostkillsvalue) {
|
||||
mostkillsplayer = -1;
|
||||
}
|
||||
if (totalkills == mostkillsvalue) {
|
||||
mostkillsplayer = -1;
|
||||
}
|
||||
|
||||
if (totalkills > mostkillsvalue) {
|
||||
mostkillsplayer = k;
|
||||
mostkillsvalue = totalkills;
|
||||
}
|
||||
if (totalkills > mostkillsvalue) {
|
||||
mostkillsplayer = k;
|
||||
mostkillsvalue = totalkills;
|
||||
}
|
||||
|
||||
if (mpchr->numdeaths == leastdeathsvalue) {
|
||||
leastdeathsplayer = -1;
|
||||
}
|
||||
if (mpchr->numdeaths == leastdeathsvalue) {
|
||||
leastdeathsplayer = -1;
|
||||
}
|
||||
|
||||
if (mpchr->numdeaths < leastdeathsvalue) {
|
||||
leastdeathsplayer = k;
|
||||
leastdeathsvalue = mpchr->numdeaths;
|
||||
}
|
||||
if (mpchr->numdeaths < leastdeathsvalue) {
|
||||
leastdeathsplayer = k;
|
||||
leastdeathsvalue = mpchr->numdeaths;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2555,8 +2515,8 @@ void mpCalculateAwards(void)
|
||||
|
||||
// Recalculate title for all players
|
||||
for (i = 0; i < playercount; i++) {
|
||||
struct mpplayerconfig *mpchr = (struct mpplayerconfig *)mpGetChrConfigBySlotNum(i);
|
||||
mpCalculatePlayerTitle(mpchr);
|
||||
struct mpplayerconfig *mpcfg = (struct mpplayerconfig *)mpGetChrConfigBySlotNum(i);
|
||||
mpCalculatePlayerTitle(mpcfg);
|
||||
}
|
||||
}
|
||||
#else
|
||||
@@ -4409,7 +4369,7 @@ struct mpchrconfig *mpGetChrConfigBySlotNum(s32 slot)
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
if (count == slot) {
|
||||
result = MPCHR(i);
|
||||
result = MPCHRCONFIG(i);
|
||||
break;
|
||||
}
|
||||
|
||||
@@ -4442,7 +4402,7 @@ s32 mpGetChrIndexBySlotNum(s32 slot)
|
||||
}
|
||||
#endif
|
||||
|
||||
s32 mpGetNumChrs(void)
|
||||
s32 mpGetNumConfigs(void)
|
||||
{
|
||||
s32 count = 0;
|
||||
s32 i;
|
||||
@@ -4456,6 +4416,11 @@ s32 mpGetNumChrs(void)
|
||||
return count;
|
||||
}
|
||||
|
||||
s32 mpGetNumChrs(void)
|
||||
{
|
||||
return g_MpNumChrs;
|
||||
}
|
||||
|
||||
u8 mpFindUnusedTeamNum(void)
|
||||
{
|
||||
u8 teamnum = 0;
|
||||
@@ -4467,7 +4432,7 @@ u8 mpFindUnusedTeamNum(void)
|
||||
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
struct mpchrconfig *mpchr = MPCHR(i);
|
||||
struct mpchrconfig *mpchr = MPCHRCONFIG(i);
|
||||
|
||||
if (mpchr->team == teamnum) {
|
||||
available = false;
|
||||
@@ -4514,9 +4479,9 @@ void mpCreateBotFromProfile(s32 botnum, u8 profilenum)
|
||||
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
struct mpchrconfig *mpchr = MPCHR(i);
|
||||
struct mpchrconfig *mpcfg = MPCHRCONFIG(i);
|
||||
|
||||
if (mpchr->mpheadnum == headnum) {
|
||||
if (mpcfg->mpheadnum == headnum) {
|
||||
available = false;
|
||||
}
|
||||
}
|
||||
@@ -4699,68 +4664,6 @@ const char var7f1b8c04[] = "PakId for player %d: %d\n";
|
||||
const char var7f1b8c20[] = "Load Player - Result: %d\n";
|
||||
#endif
|
||||
|
||||
s32 mpPlayerGetIndex(struct chrdata *chr)
|
||||
{
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i] == chr) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
struct chrdata *mpGetChrFromPlayerIndex(s32 index)
|
||||
{
|
||||
if (index >= 0 && index < g_MpNumChrs) {
|
||||
return g_MpAllChrPtrs[index];
|
||||
}
|
||||
|
||||
return NULL;
|
||||
}
|
||||
|
||||
s32 func0f18d074(s32 index)
|
||||
{
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < 4; i++) {
|
||||
if (&g_PlayerConfigsArray[i].base == g_MpAllChrConfigPtrs[index]) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
|
||||
for (i = 0; i < MAX_BOTS; i++) {
|
||||
if (&g_BotConfigsArray[i].base == g_MpAllChrConfigPtrs[index]) {
|
||||
return i + 4;
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
s32 func0f18d0e8(s32 arg0)
|
||||
{
|
||||
s32 i;
|
||||
|
||||
if (arg0 < 4) {
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrConfigPtrs[i] == &g_PlayerConfigsArray[arg0].base) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrConfigPtrs[i] == &g_BotConfigsArray[arg0 - 4].base) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return -1;
|
||||
}
|
||||
|
||||
void mpplayerfileLoadGunFuncs(struct savebuffer *buffer, s32 playernum)
|
||||
{
|
||||
s32 bitsremaining = 35;
|
||||
@@ -4834,7 +4737,7 @@ void mpplayerfileLoadWad(s32 playernum, struct savebuffer *buffer, s32 arg2)
|
||||
savebufferReadGuid(buffer, &guid);
|
||||
}
|
||||
|
||||
g_PlayerConfigsArray[playernum].base.displayoptions = savebufferReadBits(buffer, 8);
|
||||
g_PlayerConfigsArray[playernum].displayoptions = savebufferReadBits(buffer, 8);
|
||||
g_PlayerConfigsArray[playernum].kills = savebufferReadBits(buffer, 20);
|
||||
g_PlayerConfigsArray[playernum].deaths = savebufferReadBits(buffer, 20);
|
||||
g_PlayerConfigsArray[playernum].gamesplayed = savebufferReadBits(buffer, 19);
|
||||
@@ -4887,7 +4790,7 @@ void mpplayerfileSaveWad(s32 playernum, struct savebuffer *buffer)
|
||||
savebufferWriteGuid(buffer, &guid);
|
||||
}
|
||||
|
||||
savebufferOr(buffer, g_PlayerConfigsArray[playernum].base.displayoptions, 8);
|
||||
savebufferOr(buffer, g_PlayerConfigsArray[playernum].displayoptions, 8);
|
||||
|
||||
if (g_PlayerConfigsArray[playernum].kills > 0xfffff) { // 1,048,575
|
||||
g_PlayerConfigsArray[playernum].kills = 0xfffff;
|
||||
|
||||
+29
-104
@@ -61,7 +61,7 @@ struct mpscenario {
|
||||
void (*tickfunc)(void);
|
||||
void (*tickchrfunc)(struct chrdata *chr);
|
||||
Gfx *(*hudfunc)(Gfx *gdl);
|
||||
void (*calcscorefunc)(struct mpchrconfig *mpchr, s32 chrnum, s32 *score, s32 *deaths);
|
||||
void (*calcscorefunc)(struct mpchr *mpchr, s32 chrnum, s32 *score, s32 *deaths);
|
||||
Gfx *(*radarextrafunc)(Gfx *gdl);
|
||||
bool (*radarchrfunc)(Gfx **gdl, struct prop *prop);
|
||||
bool (*highlightpropfunc)(struct prop *prop, s32 *colour);
|
||||
@@ -501,7 +501,7 @@ void scenarioCreateMatchStartHudmsgs(void)
|
||||
sprintf(scenarioname, "%s\n", langGet(g_MpScenarioOverviews[g_MpSetup.scenario].name));
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->aibot == NULL) {
|
||||
if (!g_MpChrs[i].isbot) {
|
||||
setCurrentPlayerNum(i);
|
||||
|
||||
if (g_BossFile.locktype == MPLOCKTYPE_CHALLENGE) {
|
||||
@@ -620,7 +620,7 @@ Gfx *scenarioRenderHud(Gfx *gdl)
|
||||
gDPSetRenderMode(gdl++, G_RM_OPA_SURF, G_RM_OPA_SURF2);
|
||||
gDPPipelineMode(gdl++, G_PM_1PRIMITIVE);
|
||||
|
||||
colour = var80087ce4[radarGetTeamIndex(chr->team)];
|
||||
colour = var80087ce4[chr->team];
|
||||
gDPSetFillColor(gdl++, colour);
|
||||
|
||||
viewleft = viGetViewLeft();
|
||||
@@ -666,9 +666,9 @@ Gfx *scenarioRenderHud(Gfx *gdl)
|
||||
*
|
||||
* If no callback is registered, the default calculation below will apply.
|
||||
*/
|
||||
void scenarioCalculatePlayerScore(struct mpchrconfig *mpchr, s32 chrnum, s32 *score, s32 *deaths)
|
||||
void scenarioCalculatePlayerScore(struct mpchr *mpchr, s32 chrnum, s32 *score, s32 *deaths)
|
||||
{
|
||||
struct mpchrconfig *othermpchr;
|
||||
struct mpchr *othermpchr;
|
||||
s32 i;
|
||||
|
||||
if (g_MpScenarios[g_MpSetup.scenario].calcscorefunc) {
|
||||
@@ -676,7 +676,7 @@ void scenarioCalculatePlayerScore(struct mpchrconfig *mpchr, s32 chrnum, s32 *sc
|
||||
} else {
|
||||
*score = 0;
|
||||
|
||||
for (i = 0; i < MAX_MPCHRS; i++) {
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (i == chrnum) {
|
||||
*score -= mpchr->killcounts[i];
|
||||
} else if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
@@ -739,7 +739,7 @@ bool scenarioHighlightProp(struct prop *prop, s32 *colour)
|
||||
struct defaultobj *obj = prop->obj;
|
||||
|
||||
if ((g_MpSetup.scenario != MPSCENARIO_COMBAT || (g_MpSetup.options & MPOPTION_NOPICKUPHIGHLIGHT) == 0)
|
||||
&& (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.displayoptions & MPDISPLAYOPTION_HIGHLIGHTPICKUPS)) {
|
||||
&& (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].displayoptions & MPDISPLAYOPTION_HIGHLIGHTPICKUPS)) {
|
||||
switch (obj->type) {
|
||||
case OBJTYPE_AMMOCRATE:
|
||||
case OBJTYPE_WEAPON:
|
||||
@@ -774,15 +774,15 @@ bool scenarioHighlightProp(struct prop *prop, s32 *colour)
|
||||
if (!pulse && !isunselectedbot
|
||||
&& (g_MpSetup.scenario != MPSCENARIO_COMBAT || (g_MpSetup.options & MPOPTION_NOPLAYERHIGHLIGHT) == 0)) {
|
||||
if ((g_MpSetup.options & MPOPTION_TEAMSENABLED)
|
||||
&& (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.displayoptions & MPDISPLAYOPTION_HIGHLIGHTTEAMS)) {
|
||||
&& (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].displayoptions & MPDISPLAYOPTION_HIGHLIGHTTEAMS)) {
|
||||
useteamcolour = true;
|
||||
} else if (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.displayoptions & MPDISPLAYOPTION_HIGHLIGHTPLAYERS) {
|
||||
} else if (g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].displayoptions & MPDISPLAYOPTION_HIGHLIGHTPLAYERS) {
|
||||
useblue = true;
|
||||
}
|
||||
}
|
||||
|
||||
if (useteamcolour) {
|
||||
u32 tmp = g_TeamColours[radarGetTeamIndex(prop->chr->team)];
|
||||
u32 tmp = g_TeamColours[prop->chr->team];
|
||||
|
||||
colour[0] = tmp >> 24 & 0xff;
|
||||
colour[1] = tmp >> 16 & 0xff;
|
||||
@@ -1062,12 +1062,12 @@ void scenarioCreateHudmsg(s32 playernum, char *message)
|
||||
*/
|
||||
bool scenarioChrsAreSameTeam(s32 playernum1, s32 playernum2)
|
||||
{
|
||||
struct mpchrconfig *achr;
|
||||
struct mpchrconfig *bchr;
|
||||
struct mpchr *achr;
|
||||
struct mpchr *bchr;
|
||||
|
||||
if ((g_MpSetup.options & MPOPTION_TEAMSENABLED) && playernum1 >= 0 && playernum2 >= 0) {
|
||||
s32 a = func0f18d074(playernum1);
|
||||
s32 b = func0f18d074(playernum2);
|
||||
s32 a = playernum1;
|
||||
s32 b = playernum2;
|
||||
|
||||
if (a >= 0 && b >= 0) {
|
||||
achr = MPCHR(a);
|
||||
@@ -1096,14 +1096,14 @@ s32 scenarioPickUpBriefcase(struct chrdata *chr, struct prop *prop)
|
||||
char text1[64];
|
||||
char text2[64];
|
||||
char text3[64];
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
|
||||
if (g_MpSetup.scenario == MPSCENARIO_HOLDTHEBRIEFCASE) {
|
||||
// Player or bot has picked up the briefcase
|
||||
g_ScenarioData.htb.token = chr->prop;
|
||||
|
||||
if (chr->aibot) {
|
||||
mpchr = g_MpAllChrConfigPtrs[mpPlayerGetIndex(chr)];
|
||||
mpchr = &g_MpChrs[chr->chrnum];
|
||||
propPlayPickupSound(prop, weapon->weaponnum);
|
||||
chr->aibot->hasbriefcase = true;
|
||||
botinvGiveSingleWeapon(chr, WEAPON_BRIEFCASE2);
|
||||
@@ -1115,16 +1115,8 @@ s32 scenarioPickUpBriefcase(struct chrdata *chr, struct prop *prop)
|
||||
weaponPlayPickupSound(WEAPON_BRIEFCASE2);
|
||||
}
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
// "%shas the Briefcase"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_000_2), scenarioRemoveLineBreaks(mpchr->name, 0), bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
#elif VERSION >= VERSION_PAL_BETA
|
||||
// "%shas the Briefcase"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_000_2), mpchr->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
#else
|
||||
// "%shas the\n%s"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_000), mpchr->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
#endif
|
||||
sprintf(text1, langGet(L_MPWEAPONS_000), mpchr->config->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
|
||||
prevplayernum = g_Vars.currentplayernum;
|
||||
|
||||
@@ -1154,7 +1146,7 @@ s32 scenarioPickUpBriefcase(struct chrdata *chr, struct prop *prop)
|
||||
#endif
|
||||
} else if (g_MpSetup.scenario == MPSCENARIO_CAPTURETHECASE) {
|
||||
if (chr->aibot) {
|
||||
mpchr = g_MpAllChrConfigPtrs[mpPlayerGetIndex(chr)];
|
||||
mpchr = &g_MpChrs[chr->chrnum];
|
||||
} else {
|
||||
mpchr = MPCHR(g_Vars.playerstats[g_Vars.currentplayernum].mpindex);
|
||||
}
|
||||
@@ -1180,34 +1172,14 @@ s32 scenarioPickUpBriefcase(struct chrdata *chr, struct prop *prop)
|
||||
invRemoveItemByNum(WEAPON_BRIEFCASE2);
|
||||
}
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
// "You captured the %s Briefcase"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_004), scenarioRemoveLineBreaks(g_BossFile.teamnames[i], 0));
|
||||
|
||||
// "%scaptured our Briefcase"
|
||||
sprintf(text2, langGet(L_MPWEAPONS_005), scenarioRemoveLineBreaks(mpchr->name, 0));
|
||||
|
||||
// "%scaptured the %s Briefcase"
|
||||
sprintf(text3, langGet(L_MPWEAPONS_006), scenarioRemoveLineBreaks(mpchr->name, 0), scenarioRemoveLineBreaks(g_BossFile.teamnames[i], 1));
|
||||
#elif VERSION >= VERSION_PAL_BETA
|
||||
// "You captured the %s Briefcase"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_004), g_BossFile.teamnames[i]);
|
||||
|
||||
// "%scaptured our Briefcase"
|
||||
sprintf(text2, langGet(L_MPWEAPONS_005), mpchr->name);
|
||||
|
||||
// "%scaptured the %s Briefcase"
|
||||
sprintf(text3, langGet(L_MPWEAPONS_006), mpchr->name, g_BossFile.teamnames[i]);
|
||||
#else
|
||||
// "You captured the %s%s"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_004), g_BossFile.teamnames[i], bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
|
||||
// "%scaptured our %s"
|
||||
sprintf(text2, langGet(L_MPWEAPONS_005), mpchr->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
sprintf(text2, langGet(L_MPWEAPONS_005), mpchr->config->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
|
||||
// "%scaptured the %s%s"
|
||||
sprintf(text3, langGet(L_MPWEAPONS_006), mpchr->name, g_BossFile.teamnames[i], bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
#endif
|
||||
sprintf(text3, langGet(L_MPWEAPONS_006), mpchr->config->name, g_BossFile.teamnames[i], bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
|
||||
prevplayernum = g_Vars.currentplayernum;
|
||||
|
||||
@@ -1218,23 +1190,13 @@ s32 scenarioPickUpBriefcase(struct chrdata *chr, struct prop *prop)
|
||||
for (i = 0; i < PLAYERCOUNT(); i++) {
|
||||
setCurrentPlayerNum(i);
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
if (!chr->aibot && i == prevplayernum) {
|
||||
hudmsgCreateWithFlags(text1, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
} else if (caseteam == g_MpAllChrConfigPtrs[i]->team) {
|
||||
hudmsgCreateWithFlags(text2, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
} else {
|
||||
hudmsgCreateWithFlags(text3, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
}
|
||||
#else
|
||||
if (!chr->aibot && i == prevplayernum) {
|
||||
hudmsgCreateWithFlags(text1, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
} else if (caseteam == g_MpAllChrConfigPtrs[i]->team) {
|
||||
} else if (caseteam == g_MpChrs[i].team) {
|
||||
hudmsgCreateWithFlags(text2, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
} else {
|
||||
hudmsgCreateWithFlags(text3, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
setCurrentPlayerNum(prevplayernum);
|
||||
@@ -1256,57 +1218,27 @@ s32 scenarioPickUpBriefcase(struct chrdata *chr, struct prop *prop)
|
||||
|
||||
g_ScenarioData.ctc.tokens[weapon->team] = chr->prop;
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
// "%shas the %s Briefcase"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_000_3), scenarioRemoveLineBreaks(mpchr->name, 0), scenarioRemoveLineBreaks(g_BossFile.teamnames[weapon->team], 1));
|
||||
|
||||
// "%shas our\nBriefcase"
|
||||
sprintf(text2, langGet(L_MPWEAPONS_002), scenarioRemoveLineBreaks(mpchr->name, 0));
|
||||
|
||||
// "Got the %s Briefcase"
|
||||
sprintf(text3, langGet(L_MPWEAPONS_003), scenarioRemoveLineBreaks(g_BossFile.teamnames[weapon->team], 0));
|
||||
#elif VERSION >= VERSION_PAL_BETA
|
||||
// "%shas the %s Briefcase"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_000_3), mpchr->name, g_BossFile.teamnames[weapon->team]);
|
||||
|
||||
// "%shas our\nBriefcase"
|
||||
sprintf(text2, langGet(L_MPWEAPONS_002), mpchr->name);
|
||||
|
||||
// "Got the %s Briefcase"
|
||||
sprintf(text3, langGet(L_MPWEAPONS_003), g_BossFile.teamnames[weapon->team]);
|
||||
#else
|
||||
// "%shas the %s%s"
|
||||
sprintf(text1, langGet(L_MPWEAPONS_001), mpchr->name, g_BossFile.teamnames[weapon->team], bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
sprintf(text1, langGet(L_MPWEAPONS_001), mpchr->config->name, g_BossFile.teamnames[weapon->team], bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
|
||||
// "%shas our %s"
|
||||
sprintf(text2, langGet(L_MPWEAPONS_002), mpchr->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
sprintf(text2, langGet(L_MPWEAPONS_002), mpchr->config->name, bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
|
||||
// "Got the %s%s"
|
||||
sprintf(text3, langGet(L_MPWEAPONS_003), g_BossFile.teamnames[weapon->team], bgunGetShortName(WEAPON_BRIEFCASE2));
|
||||
#endif
|
||||
|
||||
prevplayernum = g_Vars.currentplayernum;
|
||||
|
||||
for (i = 0; i < PLAYERCOUNT(); i++) {
|
||||
setCurrentPlayerNum(i);
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
if (!chr->aibot && i == prevplayernum) {
|
||||
hudmsgCreateWithFlags(text3, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
} else if (weapon->team == g_MpAllChrConfigPtrs[i]->team) {
|
||||
hudmsgCreateWithFlags(text2, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
} else {
|
||||
hudmsgCreateWithFlags(text1, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
}
|
||||
#else
|
||||
if (!chr->aibot && i == prevplayernum) {
|
||||
hudmsgCreateWithFlags(text3, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
} else if (weapon->team == g_MpAllChrConfigPtrs[i]->team) {
|
||||
} else if (weapon->team == g_MpChrs[i].team) {
|
||||
hudmsgCreateWithFlags(text2, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
} else {
|
||||
hudmsgCreateWithFlags(text1, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
setCurrentPlayerNum(prevplayernum);
|
||||
@@ -1394,7 +1326,7 @@ s32 scenarioPickUpUplink(struct chrdata *chr, struct prop *prop)
|
||||
{
|
||||
s32 i;
|
||||
char message[64];
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
u32 playernum;
|
||||
|
||||
if (g_MpSetup.scenario == MPSCENARIO_HACKERCENTRAL) {
|
||||
@@ -1405,21 +1337,14 @@ s32 scenarioPickUpUplink(struct chrdata *chr, struct prop *prop)
|
||||
g_ScenarioData.htm.uplink = chr->prop;
|
||||
|
||||
if (chr->aibot) {
|
||||
mpchr = g_MpAllChrConfigPtrs[mpPlayerGetIndex(chr)];
|
||||
mpchr = &g_MpChrs[chr->chrnum];
|
||||
} else {
|
||||
mpchr = MPCHR(g_Vars.playerstats[g_Vars.currentplayernum].mpindex);
|
||||
}
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
// "%shas the\nData Uplink%s"
|
||||
sprintf(message, langGet(L_MPWEAPONS_000), scenarioRemoveLineBreaks(mpchr->name, 0));
|
||||
#elif VERSION >= VERSION_PAL_BETA
|
||||
// "%shas the\nData Uplink%s"
|
||||
sprintf(message, langGet(L_MPWEAPONS_000), mpchr->name);
|
||||
#else
|
||||
// "%shas the\n%s"
|
||||
sprintf(message, langGet(L_MPWEAPONS_000), mpchr->name, bgunGetShortName(WEAPON_DATAUPLINK));
|
||||
#endif
|
||||
sprintf(message, langGet(L_MPWEAPONS_000), mpchr->config->name, bgunGetShortName(WEAPON_DATAUPLINK));
|
||||
|
||||
playernum = g_Vars.currentplayernum;
|
||||
|
||||
for (i = 0; i < PLAYERCOUNT(); i++) {
|
||||
@@ -1477,7 +1402,7 @@ void scenarioHandleActivatedProp(struct chrdata *chr, struct prop *prop)
|
||||
struct defaultobj *obj = prop->obj;
|
||||
|
||||
if (obj->flags3 & OBJFLAG3_HTMTERMINAL) {
|
||||
u32 mpindex = mpPlayerGetIndex(chr);
|
||||
u32 mpindex = chr->chrnum;
|
||||
|
||||
if ((obj->hidden & OBJHFLAG_ACTIVATED_BY_BOND) == 0) {
|
||||
obj->hidden &= 0x0fffffff;
|
||||
|
||||
@@ -139,7 +139,7 @@ void ctcInit(void)
|
||||
|
||||
for (k = 0; k < MAX_MPCHRS; k++) {
|
||||
if (g_MpSetup.chrslots & (1 << k)) {
|
||||
struct mpchrconfig *mpchr = MPCHR(k);
|
||||
struct mpchr *mpchr = MPCHR(k);
|
||||
|
||||
while (mpchr->team >= scenarioGetMaxTeams()) {
|
||||
mpchr->team -= scenarioGetMaxTeams();
|
||||
@@ -228,31 +228,21 @@ void ctcInitProps(void)
|
||||
|
||||
for (k = 0; k < MAX_MPCHRS; k++) {
|
||||
if (g_MpSetup.chrslots & (1 << k)) {
|
||||
mpchr = MPCHR(k);
|
||||
mpchr = MPCHRCONFIG(k);
|
||||
|
||||
while (mpchr->team >= scenarioGetMaxTeams()) {
|
||||
mpchr->team -= scenarioGetMaxTeams();
|
||||
}
|
||||
|
||||
#if VERSION >= VERSION_NTSC_1_0
|
||||
mpindex = func0f18d0e8(k);
|
||||
mpindex = k;
|
||||
|
||||
if (mpindex >= 0) {
|
||||
struct chrdata *chr = mpGetChrFromPlayerIndex(mpindex);
|
||||
struct chrdata *chr = g_MpChrs[mpindex].chr;
|
||||
|
||||
if (chr) {
|
||||
chr->team = 1 << mpchr->team;
|
||||
chr->team = mpchr->team;
|
||||
}
|
||||
}
|
||||
#else
|
||||
if (func0f18d0e8(k) >= 0) {
|
||||
struct chrdata *chr = mpGetChrFromPlayerIndex(func0f18d0e8(k));
|
||||
|
||||
if (chr) {
|
||||
chr->team = 1 << mpchr->team;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
g_ScenarioData.ctc.playercountsperteam[mpchr->team]++;
|
||||
}
|
||||
@@ -343,9 +333,9 @@ void ctcInitProps(void)
|
||||
}
|
||||
}
|
||||
|
||||
void ctcCalculatePlayerScore(struct mpchrconfig *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
void ctcCalculatePlayerScore(struct mpchr *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
{
|
||||
struct mpchrconfig *loopmpchr;
|
||||
struct mpchr *loopmpchr;
|
||||
s32 i;
|
||||
|
||||
*score = 0;
|
||||
@@ -400,7 +390,7 @@ bool ctcRadarChr(Gfx **gdl, struct prop *prop)
|
||||
if (prop == g_ScenarioData.ctc.tokens[i] &&
|
||||
(g_ScenarioData.ctc.tokens[i]->type == PROPTYPE_CHR || g_ScenarioData.ctc.tokens[i]->type == PROPTYPE_PLAYER)) {
|
||||
struct coord dist;
|
||||
s32 colour = g_TeamColours[radarGetTeamIndex(prop->chr->team)];
|
||||
s32 colour = g_TeamColours[prop->chr->team];
|
||||
dist.x = g_ScenarioData.ctc.tokens[i]->pos.x - g_Vars.currentplayer->prop->pos.x;
|
||||
dist.y = g_ScenarioData.ctc.tokens[i]->pos.y - g_Vars.currentplayer->prop->pos.y;
|
||||
dist.z = g_ScenarioData.ctc.tokens[i]->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
@@ -460,7 +450,7 @@ void ctcAddPad(s32 *cmd)
|
||||
bool ctcChooseSpawnLocation(f32 arg0, struct coord *pos, s16 *rooms, struct prop *prop, f32 *arg4)
|
||||
{
|
||||
struct chrdata *chr = prop->chr;
|
||||
s32 index = radarGetTeamIndex(chr->team);
|
||||
s32 index = chr->team;
|
||||
|
||||
if (g_ScenarioData.ctc.spawnpadsperteam[g_ScenarioData.ctc.teamindexes[index]].numspawnpads > 0) {
|
||||
*arg4 = playerChooseSpawnLocation(arg0, pos, rooms, prop,
|
||||
|
||||
@@ -381,8 +381,8 @@ void htmTick(void)
|
||||
// Check if a simulant is holding it
|
||||
if (g_ScenarioData.htm.uplink == NULL) {
|
||||
for (i = PLAYERCOUNT(); i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->aibot->hasuplink) {
|
||||
g_ScenarioData.htm.uplink = g_MpAllChrPtrs[i]->prop;
|
||||
if (g_MpChrs[i].chr->aibot->hasuplink) {
|
||||
g_ScenarioData.htm.uplink = g_MpChrs[i].chr->prop;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -403,7 +403,7 @@ void htmTickChr(struct chrdata *chr)
|
||||
|
||||
if (chr) {
|
||||
hasuplink = chr->aibot->hasuplink;
|
||||
playernum = mpPlayerGetIndex(chr);
|
||||
playernum = chr->chrnum;
|
||||
} else {
|
||||
hasuplink = invHasDataUplink() && bgunGetWeaponNum(HAND_RIGHT) == WEAPON_DATAUPLINK;
|
||||
playernum = g_Vars.currentplayernum;
|
||||
@@ -616,14 +616,14 @@ Gfx *htmRenderHud(Gfx *gdl)
|
||||
return gdl;
|
||||
}
|
||||
|
||||
void htmCalculatePlayerScore(struct mpchrconfig *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
void htmCalculatePlayerScore(struct mpchr *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
{
|
||||
struct mpchrconfig *loopmpchr;
|
||||
struct mpchr *loopmpchr;
|
||||
s32 i;
|
||||
s32 index;
|
||||
|
||||
*score = 0;
|
||||
index = func0f18d0e8(mpchrnum);
|
||||
index = mpchrnum;
|
||||
|
||||
if (index >= 0) {
|
||||
*score += g_ScenarioData.htm.numpoints[index] * 2;
|
||||
@@ -691,7 +691,7 @@ Gfx *htmRadarExtra(Gfx *gdl)
|
||||
bf = 0;
|
||||
af = 0;
|
||||
} else if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
u32 colour = g_TeamColours[radarGetTeamIndex(data->terminals[i].team)];
|
||||
u32 colour = g_TeamColours[data->terminals[i].team];
|
||||
rf = (colour >> 24) & 0xff;
|
||||
gf = ((colour >> 16) & 0xff);
|
||||
bf = ((colour >> 8) & 0xff);
|
||||
@@ -745,7 +745,7 @@ bool htmRadarChr(Gfx **gdl, struct prop *prop)
|
||||
dist.z = prop->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
|
||||
if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
u32 colour = g_TeamColours[radarGetTeamIndex(prop->chr->team)];
|
||||
u32 colour = g_TeamColours[prop->chr->team];
|
||||
*gdl = radarDrawDot(*gdl, g_ScenarioData.htm.uplink, &dist, colour, 0, 1);
|
||||
} else {
|
||||
*gdl = radarDrawDot(*gdl, g_ScenarioData.htm.uplink, &dist, 0x00ff0000, 0, 1);
|
||||
|
||||
@@ -320,13 +320,8 @@ void htbTick(void)
|
||||
// Check if a simulant is holding it
|
||||
if (g_ScenarioData.htb.token == NULL) {
|
||||
for (i = PLAYERCOUNT(); i < g_MpNumChrs; i++) {
|
||||
#if VERSION >= VERSION_NTSC_1_0
|
||||
if (g_MpAllChrPtrs[i]->prop && g_MpAllChrPtrs[i]->aibot->hasbriefcase)
|
||||
#else
|
||||
if (g_MpAllChrPtrs[i]->aibot->hasbriefcase)
|
||||
#endif
|
||||
{
|
||||
g_ScenarioData.htb.token = g_MpAllChrPtrs[i]->prop;
|
||||
if (g_MpChrs[i].chr->prop && g_MpChrs[i].chr->aibot->hasbriefcase) {
|
||||
g_ScenarioData.htb.token = g_MpChrs[i].chr->prop;
|
||||
break;
|
||||
}
|
||||
}
|
||||
@@ -356,7 +351,7 @@ void htbTickChr(struct chrdata *chr)
|
||||
|
||||
if (chr->aibot->unk0a0 >= TICKS(7200)) {
|
||||
sndStart(var80095200, SFX_MP_SCOREPOINT, NULL, -1, -1, -1, -1, -1);
|
||||
g_MpAllChrConfigPtrs[mpPlayerGetIndex(chr)]->numpoints++;
|
||||
g_MpChrs[chr->chrnum].numpoints++;
|
||||
chr->aibot->unk0a0 = 0;
|
||||
}
|
||||
} else {
|
||||
@@ -368,7 +363,7 @@ void htbTickChr(struct chrdata *chr)
|
||||
|
||||
if (g_Vars.currentplayerstats->tokenheldtime >= TICKS(7200)) {
|
||||
sndStart(var80095200, SFX_MP_SCOREPOINT, NULL, -1, -1, -1, -1, -1);
|
||||
g_MpAllChrConfigPtrs[g_Vars.currentplayernum]->numpoints++;
|
||||
g_MpChrs[g_Vars.currentplayernum].numpoints++;
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
hudmsgCreateWithFlags(langGet(L_MPWEAPONS_024), HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP); // "1 Point!"
|
||||
#else
|
||||
@@ -437,9 +432,9 @@ Gfx *htbRenderHud(Gfx *gdl)
|
||||
return gdl;
|
||||
}
|
||||
|
||||
void htbCalculatePlayerScore(struct mpchrconfig *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
void htbCalculatePlayerScore(struct mpchr *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
{
|
||||
struct mpchrconfig *loopmpchr;
|
||||
struct mpchr *loopmpchr;
|
||||
s32 i;
|
||||
|
||||
*score = 0;
|
||||
@@ -494,7 +489,7 @@ bool htbRadarChr(Gfx **gdl, struct prop *prop)
|
||||
dist.z = prop->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
|
||||
if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
u32 colour = g_TeamColours[radarGetTeamIndex(prop->chr->team)];
|
||||
u32 colour = g_TeamColours[prop->chr->team];
|
||||
*gdl = radarDrawDot(*gdl, g_ScenarioData.htb.token, &dist, colour, 0, 1);
|
||||
} else {
|
||||
*gdl = radarDrawDot(*gdl, g_ScenarioData.htb.token, &dist, 0x00ff0000, 0, 1);
|
||||
|
||||
@@ -337,7 +337,7 @@ void kohTick(void)
|
||||
|
||||
for (s0 = 0, numteamsinhill = 0; s0 < numchrsinhill; s0++) {
|
||||
chr = chrsinhill[s0]->chr;
|
||||
teamindex = radarGetTeamIndex(chr->team);
|
||||
teamindex = chr->team;
|
||||
|
||||
if (teamsinhill[teamindex] == 0) {
|
||||
numteamsinhill++;
|
||||
@@ -428,14 +428,14 @@ void kohTick(void)
|
||||
chr = g_Vars.currentplayer->prop->chr;
|
||||
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
if (radarGetTeamIndex(chr->team) == g_ScenarioData.koh.occupiedteam) {
|
||||
if (chr->team == g_ScenarioData.koh.occupiedteam) {
|
||||
// "We have the Hill!"
|
||||
hudmsgCreateWithFlags(langGet(L_MPWEAPONS_021), HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
} else {
|
||||
hudmsgCreateWithFlags(text, HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE | HUDMSGFLAG_NOWRAP);
|
||||
}
|
||||
#else
|
||||
if (radarGetTeamIndex(chr->team) == g_ScenarioData.koh.occupiedteam) {
|
||||
if (chr->team == g_ScenarioData.koh.occupiedteam) {
|
||||
// "We have the Hill!"
|
||||
hudmsgCreateWithFlags(langGet(L_MPWEAPONS_021), HUDMSGTYPE_MPSCENARIO, HUDMSGFLAG_ONLYIFALIVE);
|
||||
} else {
|
||||
@@ -460,11 +460,11 @@ void kohTick(void)
|
||||
// "press start" screen while their team mate scores the
|
||||
// hill, the dead player will always be awarded a point.
|
||||
for (playernum2 = 0; playernum2 < g_MpNumChrs; playernum2++) {
|
||||
if (radarGetTeamIndex(g_MpAllChrPtrs[playernum2]->team) == g_ScenarioData.koh.occupiedteam) {
|
||||
prop = g_MpAllChrPtrs[playernum2]->prop;
|
||||
if (g_MpChrs[playernum2].team == g_ScenarioData.koh.occupiedteam) {
|
||||
prop = g_MpChrs[playernum2].chr->prop;
|
||||
|
||||
if (prop->rooms[0] == g_ScenarioData.koh.hillrooms[0]) {
|
||||
g_MpAllChrConfigPtrs[playernum2]->numpoints++;
|
||||
g_MpChrs[playernum2].numpoints++;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -472,8 +472,8 @@ void kohTick(void)
|
||||
prevplayernum1 = g_Vars.currentplayernum;
|
||||
|
||||
for (playernum2 = 0; playernum2 < g_MpNumChrs; playernum2++) {
|
||||
if (g_MpAllChrPtrs[playernum2]->aibot == NULL
|
||||
&& radarGetTeamIndex(g_MpAllChrPtrs[playernum2]->team) == g_ScenarioData.koh.occupiedteam) {
|
||||
if (g_MpChrs[playernum2].chr->aibot == NULL
|
||||
&& g_MpChrs[playernum2].team == g_ScenarioData.koh.occupiedteam) {
|
||||
setCurrentPlayerNum(playernum2);
|
||||
|
||||
// "King of the Hill!"
|
||||
@@ -559,7 +559,7 @@ Gfx *kohRenderHud(Gfx *gdl)
|
||||
struct chrdata *chr = g_Vars.currentplayer->prop->chr;
|
||||
char text[64];
|
||||
|
||||
if (radarGetTeamIndex(chr->team) == g_ScenarioData.koh.occupiedteam && !g_ScenarioData.koh.movehill) {
|
||||
if (chr->team == g_ScenarioData.koh.occupiedteam && !g_ScenarioData.koh.movehill) {
|
||||
x = viGetViewLeft() + viGetViewWidth() / 2;
|
||||
y = viGetViewTop() + 10;
|
||||
|
||||
@@ -600,9 +600,9 @@ Gfx *kohRenderHud(Gfx *gdl)
|
||||
return gdl;
|
||||
}
|
||||
|
||||
void kohCalculatePlayerScore(struct mpchrconfig *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
void kohCalculatePlayerScore(struct mpchr *mpchr, s32 mpchrnum, s32 *score, s32 *deaths)
|
||||
{
|
||||
struct mpchrconfig *loopmpchr;
|
||||
struct mpchr *loopmpchr;
|
||||
s32 i;
|
||||
|
||||
*score = 0;
|
||||
|
||||
@@ -177,7 +177,7 @@ bool pacHighlightProp(struct prop *prop, s32 *colour)
|
||||
if (g_MpSetup.options & MPOPTION_PAC_HIGHLIGHTTARGET
|
||||
&& (prop->type == PROPTYPE_PLAYER || prop->type == PROPTYPE_CHR)
|
||||
&& data->victimindex != -1
|
||||
&& prop->chr == g_MpAllChrPtrs[data->victims[data->victimindex]]) {
|
||||
&& prop->chr == g_MpChrs[data->victims[data->victimindex]].chr) {
|
||||
colour[0] = 0;
|
||||
colour[1] = 0xff;
|
||||
colour[2] = 0;
|
||||
@@ -209,17 +209,9 @@ void pacApplyNextVictim(void)
|
||||
if (vplayernum == i) {
|
||||
sprintf(text, langGet(L_MPWEAPONS_013)); // "You are the victim!"
|
||||
} else if (scenarioChrsAreSameTeam(vplayernum, i)) {
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
sprintf(text, langGet(L_MPWEAPONS_014), scenarioRemoveLineBreaks(g_MpAllChrConfigPtrs[vplayernum]->name, 0)); // "Protect %s!"
|
||||
#else
|
||||
sprintf(text, langGet(L_MPWEAPONS_014), g_MpAllChrConfigPtrs[vplayernum]->name); // "Protect %s!"
|
||||
#endif
|
||||
sprintf(text, langGet(L_MPWEAPONS_014), g_MpChrs[vplayernum].config->name); // "Protect %s!"
|
||||
} else {
|
||||
#if VERSION >= VERSION_JPN_FINAL
|
||||
sprintf(text, langGet(L_MPWEAPONS_015), scenarioRemoveLineBreaks(g_MpAllChrConfigPtrs[vplayernum]->name, 0)); // "Get %s!"
|
||||
#else
|
||||
sprintf(text, langGet(L_MPWEAPONS_015), g_MpAllChrConfigPtrs[vplayernum]->name); // "Get %s!"
|
||||
#endif
|
||||
sprintf(text, langGet(L_MPWEAPONS_015), g_MpChrs[vplayernum].config->name); // "Get %s!"
|
||||
}
|
||||
|
||||
scenarioCreateHudmsg(i, text);
|
||||
@@ -331,14 +323,14 @@ Gfx *pacRenderHud(Gfx *gdl)
|
||||
return gdl;
|
||||
}
|
||||
|
||||
void pacCalculatePlayerScore(struct mpchrconfig *mpchr, s32 mpchrnum, s32 *score, s32 *arg3)
|
||||
void pacCalculatePlayerScore(struct mpchr *mpchr, s32 mpchrnum, s32 *score, s32 *arg3)
|
||||
{
|
||||
struct mpchrconfig *loopmpchr;
|
||||
struct mpchr *loopmpchr;
|
||||
s32 i;
|
||||
s32 index;
|
||||
|
||||
*score = 0;
|
||||
index = func0f18d0e8(mpchrnum);
|
||||
index = mpchrnum;
|
||||
|
||||
if (index >= 0) {
|
||||
*score += g_ScenarioData.pac.killcounts[index] * 2;
|
||||
@@ -377,7 +369,7 @@ bool pacRadarChr(Gfx **gdl, struct prop *prop)
|
||||
struct coord dist;
|
||||
|
||||
if ((g_MpSetup.options & MPOPTION_PAC_SHOWONRADAR) && data->victimindex >= 0) {
|
||||
struct prop *vprop = g_MpAllChrPtrs[data->victims[data->victimindex]]->prop;
|
||||
struct prop *vprop = g_MpChrs[data->victims[data->victimindex]].chr->prop;
|
||||
|
||||
if (vprop == prop) {
|
||||
dist.x = prop->pos.x - g_Vars.currentplayer->prop->pos.x;
|
||||
@@ -385,7 +377,7 @@ bool pacRadarChr(Gfx **gdl, struct prop *prop)
|
||||
dist.z = prop->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
|
||||
if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
u32 colour = g_TeamColours[radarGetTeamIndex(prop->chr->team)];
|
||||
u32 colour = g_TeamColours[prop->chr->team];
|
||||
*gdl = radarDrawDot(*gdl, vprop, &dist, colour, 0, 1);
|
||||
} else {
|
||||
*gdl = radarDrawDot(*gdl, vprop, &dist, 0x00ff0000, 0, 1);
|
||||
|
||||
+37
-51
@@ -416,15 +416,15 @@ s32 menuhandlerMpDisplayOptionCheckbox(s32 operation, struct menuitem *item, uni
|
||||
{
|
||||
switch (operation) {
|
||||
case MENUOP_GET:
|
||||
if ((g_PlayerConfigsArray[g_MpPlayerNum].base.displayoptions & item->param3) == 0) {
|
||||
if ((g_PlayerConfigsArray[g_MpPlayerNum].displayoptions & item->param3) == 0) {
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
case MENUOP_SET:
|
||||
g_PlayerConfigsArray[g_MpPlayerNum].base.displayoptions &= ~(u8)item->param3;
|
||||
g_PlayerConfigsArray[g_MpPlayerNum].displayoptions &= ~(u8)item->param3;
|
||||
|
||||
if (data->checkbox.value) {
|
||||
g_PlayerConfigsArray[g_MpPlayerNum].base.displayoptions |= (u8)item->param3;
|
||||
g_PlayerConfigsArray[g_MpPlayerNum].displayoptions |= (u8)item->param3;
|
||||
}
|
||||
break;
|
||||
}
|
||||
@@ -3196,43 +3196,35 @@ struct menudialogdef g_MpSimulantsMenuDialog = {
|
||||
s32 menuhandlerMpNTeams(s32 operation, struct menuitem *item, union handlerdata *data, s32 numteams)
|
||||
{
|
||||
if (operation == MENUOP_SET) {
|
||||
s32 numchrs = mpGetNumChrs();
|
||||
s32 numconfigs = mpGetNumConfigs();
|
||||
s32 array[] = {0, 0, 0, 0};
|
||||
s32 somevalue = (numchrs + numteams - 1) / numteams;
|
||||
s32 somevalue = (numconfigs + numteams - 1) / numteams;
|
||||
s32 teamsremaining = numteams;
|
||||
s32 chrsremaining = numchrs;
|
||||
s32 start = random() % numchrs;
|
||||
s32 configsremaining = numconfigs;
|
||||
s32 start = random() % numconfigs;
|
||||
|
||||
s32 i;
|
||||
s32 teamnum;
|
||||
|
||||
#if VERSION >= VERSION_NTSC_1_0
|
||||
if (!numchrs) {
|
||||
if (!numconfigs) {
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
i = (start + 1) % numchrs;
|
||||
i = (start + 1) % numconfigs;
|
||||
|
||||
do {
|
||||
struct mpchrconfig *mpchr = mpGetChrConfigBySlotNum(i);
|
||||
struct mpchrconfig *mpcfg = mpGetChrConfigBySlotNum(i);
|
||||
|
||||
#if VERSION >= VERSION_NTSC_1_0
|
||||
if (teamsremaining);
|
||||
#else
|
||||
if (start);
|
||||
#endif
|
||||
|
||||
if (teamsremaining >= chrsremaining) {
|
||||
if (teamsremaining >= configsremaining) {
|
||||
teamnum = random() % numteams;
|
||||
|
||||
while (true) {
|
||||
if (array[teamnum] == 0) {
|
||||
mpchr->team = teamnum;
|
||||
mpcfg->team = teamnum;
|
||||
|
||||
array[teamnum]++;
|
||||
teamsremaining--;
|
||||
chrsremaining--;
|
||||
configsremaining--;
|
||||
break;
|
||||
} else {
|
||||
teamnum = (teamnum + 1) % numteams;
|
||||
@@ -3243,14 +3235,14 @@ s32 menuhandlerMpNTeams(s32 operation, struct menuitem *item, union handlerdata
|
||||
|
||||
while (true) {
|
||||
if (array[teamnum] < somevalue) {
|
||||
mpchr->team = teamnum;
|
||||
mpcfg->team = teamnum;
|
||||
|
||||
if (array[teamnum] == 0) {
|
||||
teamsremaining--;
|
||||
}
|
||||
|
||||
array[teamnum]++;
|
||||
chrsremaining--;
|
||||
configsremaining--;
|
||||
break;
|
||||
} else {
|
||||
teamnum = (teamnum + 1) % numteams;
|
||||
@@ -3262,7 +3254,7 @@ s32 menuhandlerMpNTeams(s32 operation, struct menuitem *item, union handlerdata
|
||||
break;
|
||||
}
|
||||
|
||||
i = (i + 1) % numchrs;
|
||||
i = (i + 1) % numconfigs;
|
||||
} while (true);
|
||||
|
||||
menuPopDialog();
|
||||
@@ -3294,9 +3286,9 @@ s32 menuhandlerMpMaximumTeams(s32 operation, struct menuitem *item, union handle
|
||||
|
||||
for (i = 0; i != MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
struct mpchrconfig *mpchr = MPCHR(i);
|
||||
struct mpchrconfig *mpcfg = MPCHRCONFIG(i);
|
||||
|
||||
mpchr->team = team++;
|
||||
mpcfg->team = team++;
|
||||
|
||||
if (team >= scenarioGetMaxTeams()) {
|
||||
team = 0;
|
||||
@@ -3317,9 +3309,9 @@ s32 menuhandlerMpHumansVsSimulants(s32 operation, struct menuitem *item, union h
|
||||
|
||||
for (i = 0; i != MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
struct mpchrconfig *mpchr = MPCHR(i);
|
||||
struct mpchrconfig *mpcfg = MPCHRCONFIG(i);
|
||||
|
||||
mpchr->team = i < 4 ? 0 : 1;
|
||||
mpcfg->team = i < 4 ? 0 : 1;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3339,12 +3331,12 @@ s32 menuhandlerMpHumanSimulantPairs(s32 operation, struct menuitem *item, union
|
||||
|
||||
for (i = 0; i != MAX_MPCHRS; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
struct mpchrconfig *mpchr = MPCHR(i);
|
||||
struct mpchrconfig *mpcfg = MPCHRCONFIG(i);
|
||||
|
||||
if (i < 4) {
|
||||
mpchr->team = team_ids[playerindex++];
|
||||
mpcfg->team = team_ids[playerindex++];
|
||||
} else {
|
||||
mpchr->team = team_ids[simindex++];
|
||||
mpcfg->team = team_ids[simindex++];
|
||||
|
||||
if (simindex >= playerindex) {
|
||||
simindex = 0;
|
||||
@@ -3361,16 +3353,10 @@ s32 menuhandlerMpHumanSimulantPairs(s32 operation, struct menuitem *item, union
|
||||
|
||||
char *mpMenuTextChrNameForTeamSetup(struct menuitem *item)
|
||||
{
|
||||
struct mpchrconfig *mpchr = mpGetChrConfigBySlotNum(item->param);
|
||||
struct mpchrconfig *mpcfg = mpGetChrConfigBySlotNum(item->param);
|
||||
|
||||
if (mpchr) {
|
||||
if (mpchr >= &g_BotConfigsArray[0].base && mpchr < &g_BotConfigsArray[MAX_BOTS].base) {
|
||||
struct mpbotconfig *botconfig = (struct mpbotconfig *) mpchr;
|
||||
sprintf(g_StringPointer, "%dx %s\n", botconfig->quantity, mpchr->name);
|
||||
return g_StringPointer;
|
||||
}
|
||||
|
||||
return mpchr->name;
|
||||
if (mpcfg) {
|
||||
return mpcfg->name;
|
||||
}
|
||||
|
||||
return "";
|
||||
@@ -3395,27 +3381,27 @@ s32 func0f17dac4(s32 operation, struct menuitem *item, union handlerdata *data)
|
||||
|
||||
s32 menuhandlerMpTeamSlot(s32 operation, struct menuitem *item, union handlerdata *data)
|
||||
{
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchrconfig *mpcfg;
|
||||
|
||||
switch (operation) {
|
||||
case MENUOP_SET:
|
||||
mpchr = mpGetChrConfigBySlotNum(item->param);
|
||||
mpchr->team = data->dropdown.value;
|
||||
mpcfg = mpGetChrConfigBySlotNum(item->param);
|
||||
mpcfg->team = data->dropdown.value;
|
||||
break;
|
||||
case MENUOP_GETSELECTEDINDEX:
|
||||
mpchr = mpGetChrConfigBySlotNum(item->param);
|
||||
mpcfg = mpGetChrConfigBySlotNum(item->param);
|
||||
|
||||
if (!mpchr) {
|
||||
if (!mpcfg) {
|
||||
data->dropdown.value = 0xff;
|
||||
} else {
|
||||
data->dropdown.value = mpchr->team;
|
||||
data->dropdown.value = mpcfg->team;
|
||||
}
|
||||
|
||||
break;
|
||||
case MENUOP_CHECKDISABLED:
|
||||
mpchr = mpGetChrConfigBySlotNum(item->param);
|
||||
mpcfg = mpGetChrConfigBySlotNum(item->param);
|
||||
|
||||
if (!mpchr) {
|
||||
if (!mpcfg) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
@@ -4814,7 +4800,7 @@ void mpConfigureQuickTeamPlayers(void)
|
||||
|
||||
void mpConfigureQuickTeamSimulants(void)
|
||||
{
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchrconfig *mpcfg;
|
||||
s32 numchrs;
|
||||
s32 botnum;
|
||||
s32 i;
|
||||
@@ -4851,14 +4837,14 @@ void mpConfigureQuickTeamSimulants(void)
|
||||
break;
|
||||
case MPQUICKTEAM_PLAYERSIMTEAMS:
|
||||
for (i = mpGetNumChrs() - 1; i >= 0; i--) {
|
||||
mpchr = mpGetChrConfigBySlotNum(i);
|
||||
mpcfg = mpGetChrConfigBySlotNum(i);
|
||||
|
||||
for (j = 0; j < g_Vars.unk0004a0; j++) {
|
||||
botnum = mpGetSlotForNewBot();
|
||||
|
||||
if (botnum >= 0) {
|
||||
mpCreateBotFromProfile(botnum, g_Vars.mpsimdifficulty);
|
||||
g_BotConfigsArray[botnum].base.team = mpchr->team;
|
||||
g_BotConfigsArray[botnum].base.team = mpcfg->team;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+12
-12
@@ -137,7 +137,7 @@ void mpstatsRecordPlayerSuicide(void)
|
||||
s32 duration;
|
||||
s32 time;
|
||||
s32 mpindex;
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
time = playerGetMissionTime();
|
||||
@@ -192,9 +192,9 @@ void mpstatsRecordPlayerSuicide(void)
|
||||
void mpstatsRecordDeath(s32 aplayernum, s32 vplayernum)
|
||||
{
|
||||
s32 vmpindex = -1;
|
||||
struct mpchrconfig *vmpchr = NULL;
|
||||
struct mpchr *vmpchr = NULL;
|
||||
s32 ampindex;
|
||||
struct mpchrconfig *ampchr = NULL;
|
||||
struct mpchr *ampchr = NULL;
|
||||
s32 prevplayernum;
|
||||
char text[256];
|
||||
|
||||
@@ -204,7 +204,7 @@ void mpstatsRecordDeath(s32 aplayernum, s32 vplayernum)
|
||||
|
||||
// Find attacker and victim mpchrs
|
||||
if (aplayernum >= 0) {
|
||||
ampindex = func0f18d074(aplayernum);
|
||||
ampindex = aplayernum;
|
||||
|
||||
if (ampindex >= 0) {
|
||||
ampchr = MPCHR(ampindex);
|
||||
@@ -212,7 +212,7 @@ void mpstatsRecordDeath(s32 aplayernum, s32 vplayernum)
|
||||
}
|
||||
|
||||
if (vplayernum >= 0) {
|
||||
vmpindex = func0f18d074(vplayernum);
|
||||
vmpindex = vplayernum;
|
||||
|
||||
if (vmpindex >= 0) {
|
||||
vmpchr = MPCHR(vmpindex);
|
||||
@@ -246,7 +246,7 @@ void mpstatsRecordDeath(s32 aplayernum, s32 vplayernum)
|
||||
|
||||
if (g_Vars.normmplayerisrunning && aplayernum >= 0) {
|
||||
// "Killed by %s"
|
||||
sprintf(text, "%s %s", langGet(L_MISC_183), g_MpAllChrConfigPtrs[aplayernum]->name);
|
||||
sprintf(text, "%s %s", langGet(L_MISC_183), g_MpChrs[aplayernum].config->name);
|
||||
hudmsgCreate(text, HUDMSGTYPE_DEFAULT);
|
||||
}
|
||||
|
||||
@@ -266,7 +266,7 @@ void mpstatsRecordDeath(s32 aplayernum, s32 vplayernum)
|
||||
|
||||
if (g_Vars.normmplayerisrunning && vplayernum >= 0) {
|
||||
// "Killed %s"
|
||||
sprintf(text, "%s %s", langGet(L_MISC_184), g_MpAllChrConfigPtrs[vplayernum]->name);
|
||||
sprintf(text, "%s %s", langGet(L_MISC_184), g_MpChrs[vplayernum].config->name);
|
||||
hudmsgCreate(text, HUDMSGTYPE_DEFAULT);
|
||||
}
|
||||
|
||||
@@ -279,18 +279,18 @@ void mpstatsRecordDeath(s32 aplayernum, s32 vplayernum)
|
||||
&& aplayernum >= 0
|
||||
&& vplayernum >= PLAYERCOUNT()
|
||||
&& aplayernum != vplayernum) {
|
||||
g_MpAllChrPtrs[vplayernum]->aibot->lastkilledbyplayernum = aplayernum;
|
||||
g_MpChrs[vplayernum].chr->aibot->lastkilledbyplayernum = aplayernum;
|
||||
}
|
||||
}
|
||||
|
||||
if (g_Vars.normmplayerisrunning && aplayernum >= 0 && g_MpAllChrPtrs[aplayernum]->aibot) {
|
||||
s32 index = mpGetWeaponSlotByWeaponNum(g_MpAllChrPtrs[aplayernum]->aibot->weaponnum);
|
||||
if (g_Vars.normmplayerisrunning && aplayernum >= 0 && g_MpChrs[aplayernum].chr->aibot) {
|
||||
s32 index = mpGetWeaponSlotByWeaponNum(g_MpChrs[aplayernum].chr->aibot->weaponnum);
|
||||
|
||||
if (index >= 0) {
|
||||
if (aplayernum == vplayernum) {
|
||||
g_MpAllChrPtrs[aplayernum]->aibot->suicidesbygunfunc[index][g_MpAllChrPtrs[aplayernum]->aibot->gunfunc]++;
|
||||
g_MpChrs[aplayernum].chr->aibot->suicidesbygunfunc[index][g_MpChrs[aplayernum].chr->aibot->gunfunc]++;
|
||||
} else {
|
||||
g_MpAllChrPtrs[aplayernum]->aibot->killsbygunfunc[index][g_MpAllChrPtrs[aplayernum]->aibot->gunfunc]++;
|
||||
g_MpChrs[aplayernum].chr->aibot->killsbygunfunc[index][g_MpChrs[aplayernum].chr->aibot->gunfunc]++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
+11
-14
@@ -257,13 +257,15 @@ f32 playerChooseSpawnLocation(f32 chrradius, struct coord *dstpos, s16 *dstrooms
|
||||
|
||||
roomGetNeighbours(pad.room, neighbours, 20);
|
||||
|
||||
for (i = 0; i < g_BotCount; i++) {
|
||||
if (g_MpBotChrPtrs[i]->prop
|
||||
&& g_MpBotChrPtrs[i]->prop != prop
|
||||
&& (!prop || chrCompareTeams(prop->chr, g_MpBotChrPtrs[i], COMPARE_ENEMIES))) {
|
||||
xdiff = g_MpBotChrPtrs[i]->prop->pos.x - pad.pos.x;
|
||||
ydiff = g_MpBotChrPtrs[i]->prop->pos.y - pad.pos.y;
|
||||
zdiff = g_MpBotChrPtrs[i]->prop->pos.z - pad.pos.z;
|
||||
for (i = playercount; i < g_MpNumChrs; i++) {
|
||||
struct chrdata *chr = g_MpChrs[i].chr;
|
||||
|
||||
if (chr->prop
|
||||
&& chr->prop != prop
|
||||
&& (!prop || chrCompareTeams(prop->chr, chr, COMPARE_ENEMIES))) {
|
||||
xdiff = chr->prop->pos.x - pad.pos.x;
|
||||
ydiff = chr->prop->pos.y - pad.pos.y;
|
||||
zdiff = chr->prop->pos.z - pad.pos.z;
|
||||
|
||||
sqdist = xdiff * xdiff + ydiff * ydiff + zdiff * zdiff;
|
||||
|
||||
@@ -271,11 +273,11 @@ f32 playerChooseSpawnLocation(f32 chrradius, struct coord *dstpos, s16 *dstrooms
|
||||
bestsqdist = sqdist;
|
||||
}
|
||||
|
||||
if (arrayIntersects(tmppadrooms, g_MpBotChrPtrs[i]->prop->rooms)) {
|
||||
if (arrayIntersects(tmppadrooms, chr->prop->rooms)) {
|
||||
verybadpads[p] = true;
|
||||
}
|
||||
|
||||
if (verybadpads[p] || arrayIntersects(neighbours, g_MpBotChrPtrs[i]->prop->rooms)) {
|
||||
if (verybadpads[p] || arrayIntersects(neighbours, chr->prop->rooms)) {
|
||||
badpads[p] = true;
|
||||
}
|
||||
}
|
||||
@@ -924,11 +926,6 @@ void playerTickChrBody(void)
|
||||
g_Vars.currentplayer->prop->type = PROPTYPE_PLAYER;
|
||||
chr = g_Vars.currentplayer->prop->chr;
|
||||
|
||||
if (g_Vars.mplayerisrunning) {
|
||||
g_MpAllChrPtrs[g_Vars.currentplayernum] = chr;
|
||||
g_MpAllChrConfigPtrs[g_Vars.currentplayernum] = &g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base;
|
||||
}
|
||||
|
||||
chr->chrflags |= CHRCFLAG_00000001;
|
||||
|
||||
modelSetRootPosition(g_Vars.currentplayer->model00d4, &g_Vars.currentplayer->prop->pos);
|
||||
|
||||
+15
-8
@@ -605,10 +605,7 @@ void playermgrAllocatePlayer(s32 index)
|
||||
g_Vars.players[index]->lookaheadframe = 0;
|
||||
|
||||
g_Vars.players[index]->numaibuddies = 0;
|
||||
|
||||
for (i = 0; i < MAX_BOTS; i++) {
|
||||
g_Vars.players[index]->aibuddynums[i] = 0;
|
||||
}
|
||||
g_Vars.players[index]->aibuddynums = NULL;
|
||||
|
||||
g_Vars.players[index]->teleportstate = TELEPORTSTATE_INACTIVE;
|
||||
g_Vars.players[index]->teleporttime = 0;
|
||||
@@ -635,13 +632,23 @@ void playermgrAllocatePlayer(s32 index)
|
||||
|
||||
void playermgrCalculateAiBuddyNums(void)
|
||||
{
|
||||
s32 i;
|
||||
s32 chrnum;
|
||||
s32 playernum = g_Vars.currentplayernum;
|
||||
s32 playercount = PLAYERCOUNT();
|
||||
s32 numbuddies = 0;
|
||||
|
||||
for (i = playercount; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrConfigPtrs[i]->team == g_MpAllChrConfigPtrs[playernum]->team) {
|
||||
g_Vars.players[playernum]->aibuddynums[g_Vars.players[playernum]->numaibuddies] = i;
|
||||
for (chrnum = playercount; chrnum < g_MpNumChrs; chrnum++) {
|
||||
if (g_MpChrs[chrnum].team == g_MpChrs[playernum].team) {
|
||||
numbuddies++;
|
||||
}
|
||||
}
|
||||
|
||||
g_Vars.players[playernum]->aibuddynums = mempAlloc(numbuddies * sizeof(s16), MEMPOOL_STAGE);
|
||||
g_Vars.players[playernum]->numaibuddies = 0;
|
||||
|
||||
for (chrnum = playercount; chrnum < g_MpNumChrs; chrnum++) {
|
||||
if (g_MpChrs[chrnum].team == g_MpChrs[playernum].team) {
|
||||
g_Vars.players[playernum]->aibuddynums[g_Vars.players[playernum]->numaibuddies] = chrnum;
|
||||
g_Vars.players[playernum]->numaibuddies++;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -172,7 +172,12 @@ void playerReset(void)
|
||||
propEnable(g_Vars.currentplayer->prop);
|
||||
chrInit(g_Vars.currentplayer->prop);
|
||||
|
||||
g_Vars.currentplayer->prop->chr->team = 1 << g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.team;
|
||||
g_MpChrs[g_Vars.currentplayernum].chr = g_Vars.currentplayer->prop->chr;
|
||||
|
||||
chrSetChrnum(g_Vars.currentplayer->prop->chr, g_Vars.currentplayernum);
|
||||
g_Vars.currentplayer->prop->chr->chrnum = g_Vars.currentplayernum;
|
||||
|
||||
g_Vars.currentplayer->prop->chr->team = g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.team;
|
||||
|
||||
if (g_NumSpawnPoints > 0) {
|
||||
turnanglerad = M_BADTAU - scenarioChooseSpawnLocation(30, &pos, rooms, g_Vars.currentplayer->prop);
|
||||
|
||||
+19
-19
@@ -1991,8 +1991,8 @@ void objFree(struct defaultobj *obj, bool freeprop, bool canregen)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->aibot && g_MpAllChrPtrs[i]->aibot->skrocket == obj->prop) {
|
||||
g_MpAllChrPtrs[i]->aibot->skrocket = NULL;
|
||||
if (g_MpChrs[i].chr->aibot && g_MpChrs[i].chr->aibot->skrocket == obj->prop) {
|
||||
g_MpChrs[i].chr->aibot->skrocket = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -2062,8 +2062,8 @@ void objFree(struct defaultobj *obj, bool freeprop, bool canregen)
|
||||
s32 i;
|
||||
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
if (g_MpAllChrPtrs[i]->aibot && g_MpAllChrPtrs[i]->aibot->gotoprop == obj->prop) {
|
||||
g_MpAllChrPtrs[i]->aibot->gotoprop = NULL;
|
||||
if (g_MpChrs[i].chr->aibot && g_MpChrs[i].chr->aibot->gotoprop == obj->prop) {
|
||||
g_MpChrs[i].chr->aibot->gotoprop = NULL;
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -3905,7 +3905,7 @@ void weaponTick(struct prop *prop)
|
||||
s32 i;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
struct chrdata *chr = mpGetChrFromPlayerIndex(ownerplayernum);
|
||||
struct chrdata *chr = g_MpChrs[ownerplayernum].chr;
|
||||
|
||||
if (chr) {
|
||||
ownerprop = chr->prop;
|
||||
@@ -3965,7 +3965,7 @@ void weaponTick(struct prop *prop)
|
||||
|
||||
// If a player manages to throw a mine on themselves, it will not detonate.
|
||||
// You can't throw a mine on yourself anyway, so this check always passes
|
||||
if (prop->parent == NULL || parentchr == NULL || mpPlayerGetIndex(parentchr) != ownerplayernum) {
|
||||
if (prop->parent == NULL || parentchr == NULL || parentchr->chrnum != ownerplayernum) {
|
||||
if (g_PlayersDetonatingMines & 1 << ownerplayernum) {
|
||||
weapon->timer240 = 0;
|
||||
}
|
||||
@@ -4025,7 +4025,7 @@ void weaponTick(struct prop *prop)
|
||||
s32 ownerplayernum = (obj->hidden & 0xf0000000) >> 28;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
struct chrdata *chr = mpGetChrFromPlayerIndex(ownerplayernum);
|
||||
struct chrdata *chr = g_MpChrs[ownerplayernum].chr;
|
||||
|
||||
if (chr) {
|
||||
ownerprop = chr->prop;
|
||||
@@ -4401,7 +4401,7 @@ glabel var7f1aa2c4
|
||||
/* f06ea90: 13200008 */ beqz $t9,.NB0f06eab4
|
||||
/* f06ea94: 000f2702 */ srl $a0,$t7,0x1c
|
||||
/* f06ea98: afa00158 */ sw $zero,0x158($sp)
|
||||
/* f06ea9c: 0fc61c91 */ jal mpGetChrFromPlayerIndex
|
||||
/* f06ea9c: 0fc61c91 */ jal mpGetChrFromPlayernum
|
||||
/* f06eaa0: afa70170 */ sw $a3,0x170($sp)
|
||||
/* f06eaa4: 8fa50158 */ lw $a1,0x158($sp)
|
||||
/* f06eaa8: 10400002 */ beqz $v0,.NB0f06eab4
|
||||
@@ -4526,7 +4526,7 @@ glabel var7f1aa2c4
|
||||
/* f06ec60: 10800009 */ beqz $a0,.NB0f06ec88
|
||||
/* f06ec64: 00000000 */ sll $zero,$zero,0x0
|
||||
/* f06ec68: afa3014c */ sw $v1,0x14c($sp)
|
||||
/* f06ec6c: 0fc61c7f */ jal mpPlayerGetIndex
|
||||
/* f06ec6c: 0fc61c7f */ jal mpGetPlayernumFromChr
|
||||
/* f06ec70: afa70170 */ sw $a3,0x170($sp)
|
||||
/* f06ec74: 8fa3014c */ lw $v1,0x14c($sp)
|
||||
/* f06ec78: 3c058007 */ lui $a1,0x8007
|
||||
@@ -4733,7 +4733,7 @@ glabel var7f1aa2c4
|
||||
/* f06ef58: 11200008 */ beqz $t1,.NB0f06ef7c
|
||||
/* f06ef5c: 000d2702 */ srl $a0,$t5,0x1c
|
||||
/* f06ef60: afa00128 */ sw $zero,0x128($sp)
|
||||
/* f06ef64: 0fc61c91 */ jal mpGetChrFromPlayerIndex
|
||||
/* f06ef64: 0fc61c91 */ jal mpGetChrFromPlayernum
|
||||
/* f06ef68: afa70170 */ sw $a3,0x170($sp)
|
||||
/* f06ef6c: 8fa50128 */ lw $a1,0x128($sp)
|
||||
/* f06ef70: 10400002 */ beqz $v0,.NB0f06ef7c
|
||||
@@ -6191,7 +6191,7 @@ bool rocketTickFbw(struct weaponobj *rocket)
|
||||
// Check if close to an enemy
|
||||
if (ownerchr && rocket->timer240) {
|
||||
for (i = 0; i < g_MpNumChrs; i++) {
|
||||
struct chrdata *chr = mpGetChrFromPlayerIndex(i);
|
||||
struct chrdata *chr = g_MpChrs[i].chr;
|
||||
|
||||
if (chr != ownerchr
|
||||
&& !chrIsDead(chr)
|
||||
@@ -6209,7 +6209,7 @@ bool rocketTickFbw(struct weaponobj *rocket)
|
||||
|
||||
// Check if rocket can fly directly to target
|
||||
if (chrGetTargetProp(ownerchr) == chr->prop
|
||||
&& mpPlayerGetIndex(ownerchr) == g_Vars.lvframenum % g_MpNumChrs
|
||||
&& ownerchr->chrnum == g_Vars.lvframenum % g_MpNumChrs
|
||||
&& cdTestLos05(&rocketprop->pos, rocketprop->rooms, &chr->prop->pos, chr->prop->rooms,
|
||||
CDTYPE_OBJS | CDTYPE_DOORS | CDTYPE_PATHBLOCKER | CDTYPE_BG | CDTYPE_AIOPAQUE,
|
||||
GEOFLAG_BLOCK_SIGHT)) {
|
||||
@@ -7099,7 +7099,7 @@ s32 projectileTick(struct defaultobj *obj, bool *embedded)
|
||||
struct prop *ownerprop2 = NULL;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
struct chrdata *ownerchr = mpGetChrFromPlayerIndex(ownerplayernum);
|
||||
struct chrdata *ownerchr = g_MpChrs[ownerplayernum].chr;
|
||||
|
||||
if (ownerchr != NULL) {
|
||||
ownerprop2 = ownerchr->prop;
|
||||
@@ -8359,7 +8359,7 @@ void autogunTick(struct prop *prop)
|
||||
continue;
|
||||
}
|
||||
|
||||
chr = g_MpAllChrPtrs[autogun->nextchrtest];
|
||||
chr = g_MpChrs[autogun->nextchrtest].chr;
|
||||
|
||||
if (!chr->prop) {
|
||||
continue;
|
||||
@@ -8770,7 +8770,7 @@ void autogunTickShoot(struct prop *autogunprop)
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
// Multiplayer - it must be a laptop gun
|
||||
ownerchr = mpGetChrFromPlayerIndex(ownerplayernum);
|
||||
ownerchr = g_MpChrs[ownerplayernum].chr;
|
||||
|
||||
if (ownerchr) {
|
||||
ownerprop = ownerchr->prop;
|
||||
@@ -11896,7 +11896,7 @@ bool propobjInteract(struct prop *prop)
|
||||
s32 playernum;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
playernum = mpPlayerGetIndex(g_Vars.currentplayer->prop->chr);
|
||||
playernum = g_Vars.currentplayer->prop->chr->chrnum;
|
||||
} else {
|
||||
playernum = g_Vars.currentplayernum;
|
||||
}
|
||||
@@ -13628,7 +13628,7 @@ bool chrEquipWeapon(struct weaponobj *weapon, struct chrdata *chr)
|
||||
|
||||
if (weapon->base.prop && weapon->base.model) {
|
||||
if (g_Vars.mplayerisrunning) {
|
||||
s32 playernum = mpPlayerGetIndex(chr);
|
||||
s32 playernum = chr->chrnum;
|
||||
|
||||
weapon->base.hidden &= 0x0fffffff;
|
||||
weapon->base.hidden |= (playernum << 28) & 0xf0000000;
|
||||
@@ -13743,7 +13743,7 @@ struct autogunobj *laptopDeploy(s32 modelnum, struct gset *gset, struct chrdata
|
||||
s32 index;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
index = mpPlayerGetIndex(chr);
|
||||
index = chr->chrnum;
|
||||
} else {
|
||||
index = playermgrGetPlayerNumByProp(chr->prop);
|
||||
}
|
||||
@@ -13958,7 +13958,7 @@ struct weaponobj *weaponCreateProjectileFromGset(s32 modelnum, struct gset *gset
|
||||
prop = func0f08adc8(weapon, modeldef, prop, model);
|
||||
|
||||
if (g_Vars.mplayerisrunning) {
|
||||
s32 index = mpPlayerGetIndex(chr);
|
||||
s32 index = chr->chrnum;
|
||||
|
||||
weapon->base.hidden &= 0x0fffffff;
|
||||
weapon->base.hidden |= ((index << 28) & 0xf0000000);
|
||||
|
||||
+14
-37
@@ -86,31 +86,6 @@ Gfx *radarRenderBackground(Gfx *gdl, struct textureconfig *tconfig, s32 arg2, s3
|
||||
return gdl;
|
||||
}
|
||||
|
||||
s32 radarGetTeamIndex(s32 team)
|
||||
{
|
||||
s32 index = 0;
|
||||
|
||||
if (team & 1) {
|
||||
index = 0;
|
||||
} else if (team & 0x02) {
|
||||
index = 1;
|
||||
} else if (team & 0x04) {
|
||||
index = 2;
|
||||
} else if (team & 0x08) {
|
||||
index = 3;
|
||||
} else if (team & 0x10) {
|
||||
index = 4;
|
||||
} else if (team & 0x20) {
|
||||
index = 5;
|
||||
} else if (team & 0x40) {
|
||||
index = 6;
|
||||
} else if (team & 0x80) {
|
||||
index = 7;
|
||||
}
|
||||
|
||||
return index;
|
||||
}
|
||||
|
||||
Gfx *radarDrawDot(Gfx *gdl, struct prop *prop, struct coord *dist, u32 colour1, u32 colour2, bool swapcolours)
|
||||
{
|
||||
s32 x;
|
||||
@@ -250,7 +225,7 @@ Gfx *radarRender(Gfx *gdl)
|
||||
return gdl;
|
||||
}
|
||||
|
||||
if ((g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].base.displayoptions & 0x00000004) == 0) {
|
||||
if ((g_PlayerConfigsArray[g_Vars.currentplayerstats->mpindex].displayoptions & 0x00000004) == 0) {
|
||||
return gdl;
|
||||
}
|
||||
|
||||
@@ -317,7 +292,7 @@ Gfx *radarRender(Gfx *gdl)
|
||||
pos.y = g_Vars.players[i]->prop->pos.y - g_Vars.currentplayer->prop->pos.y;
|
||||
pos.z = g_Vars.players[i]->prop->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
|
||||
if (g_Vars.normmplayerisrunning && (g_MpSetup.options & MPOPTION_TEAMSENABLED)) {
|
||||
if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
s32 index = g_PlayerConfigsArray[g_Vars.playerstats[i].mpindex].base.team;
|
||||
colour = g_TeamColours[index];
|
||||
} else {
|
||||
@@ -330,21 +305,23 @@ Gfx *radarRender(Gfx *gdl)
|
||||
}
|
||||
|
||||
// Draw dots for MP simulants
|
||||
for (i = 0; i < g_BotCount; i++) {
|
||||
if (!chrIsDead(g_MpBotChrPtrs[i])
|
||||
&& (g_MpBotChrPtrs[i]->hidden & CHRHFLAG_CLOAKED) == 0
|
||||
&& scenarioRadarChr(&gdl, g_MpBotChrPtrs[i]->prop) == false) {
|
||||
pos.x = g_MpBotChrPtrs[i]->prop->pos.x - g_Vars.currentplayer->prop->pos.x;
|
||||
pos.y = g_MpBotChrPtrs[i]->prop->pos.y - g_Vars.currentplayer->prop->pos.y;
|
||||
pos.z = g_MpBotChrPtrs[i]->prop->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
for (i = playercount; i < g_MpNumChrs; i++) {
|
||||
struct chrdata *chr = g_MpChrs[i].chr;
|
||||
|
||||
if (g_Vars.normmplayerisrunning && (g_MpSetup.options & MPOPTION_TEAMSENABLED)) {
|
||||
colour = g_TeamColours[radarGetTeamIndex(g_MpBotChrPtrs[i]->team)];
|
||||
if (!chrIsDead(chr)
|
||||
&& (chr->hidden & CHRHFLAG_CLOAKED) == 0
|
||||
&& scenarioRadarChr(&gdl, chr->prop) == false) {
|
||||
pos.x = chr->prop->pos.x - g_Vars.currentplayer->prop->pos.x;
|
||||
pos.y = chr->prop->pos.y - g_Vars.currentplayer->prop->pos.y;
|
||||
pos.z = chr->prop->pos.z - g_Vars.currentplayer->prop->pos.z;
|
||||
|
||||
if (g_MpSetup.options & MPOPTION_TEAMSENABLED) {
|
||||
colour = g_TeamColours[chr->team];
|
||||
} else {
|
||||
colour = 0x00ff0000;
|
||||
}
|
||||
|
||||
gdl = radarDrawDot(gdl, g_MpBotChrPtrs[i]->prop, &pos, colour, 0, 0);
|
||||
gdl = radarDrawDot(gdl, chr->prop, &pos, colour, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+54
-13
@@ -819,15 +819,22 @@ s32 setupGetNumRequestedBots(void)
|
||||
|
||||
s32 setupCalculateMaxBots(s32 numrequested, bool haslaptops)
|
||||
{
|
||||
return numrequested;
|
||||
return numrequested > 8 ? 8 : numrequested;
|
||||
}
|
||||
|
||||
bool g_DebugEnable = false;
|
||||
|
||||
void setupAllocateEverything(void)
|
||||
{
|
||||
s32 numhumans;
|
||||
s32 numbotsrequested;
|
||||
bool haslaptops = false;
|
||||
s32 botcfgnum;
|
||||
s32 i;
|
||||
s32 j;
|
||||
s16 *killcounts;
|
||||
s32 chrnum = 0;
|
||||
|
||||
numhumans = PLAYERCOUNT();
|
||||
|
||||
// Count how many bots were requested
|
||||
numbotsrequested = setupGetNumRequestedBots();
|
||||
@@ -856,24 +863,58 @@ void setupAllocateEverything(void)
|
||||
chrmgrReset();
|
||||
chrmgrConfigure(g_NumBots);
|
||||
|
||||
botmgrRemoveAll();
|
||||
g_MpNumChrs = numhumans + g_NumBots;
|
||||
|
||||
if (g_Vars.normmplayerisrunning && mpHasSimulants()) {
|
||||
s32 chrnum = 0;
|
||||
g_MpChrs = mempAlloc(g_MpNumChrs * sizeof(struct mpchr), MEMPOOL_STAGE);
|
||||
|
||||
for (i = 0; i < MAX_BOTS; i++) {
|
||||
if ((g_MpSetup.chrslots & (1 << (i + 4))) && mpIsSimSlotEnabled(i)) {
|
||||
for (j = 0; j < g_BotConfigsArray[i].quantity; j++) {
|
||||
botmgrAllocateBot(chrnum, i);
|
||||
killcounts = mempAlloc(g_MpNumChrs * g_MpNumChrs * sizeof(s16), MEMPOOL_STAGE);
|
||||
|
||||
for (i = 0; i < g_MpNumChrs * g_MpNumChrs; i++) {
|
||||
killcounts[i] = 0;
|
||||
}
|
||||
|
||||
for (i = 0; i < 4; i++) {
|
||||
if (g_MpSetup.chrslots & (1 << i)) {
|
||||
// player->prop is null here, so chr gets copied later on in playerReset
|
||||
g_MpChrs[chrnum].isbot = false;
|
||||
g_MpChrs[chrnum].team = g_PlayerConfigsArray[i].base.team;
|
||||
g_MpChrs[chrnum].playerconfig = &g_PlayerConfigsArray[i];
|
||||
g_MpChrs[chrnum].placement = 0;
|
||||
g_MpChrs[chrnum].rankablescore = 0;
|
||||
g_MpChrs[chrnum].killcounts = &killcounts[chrnum * g_MpNumChrs];
|
||||
g_MpChrs[chrnum].numdeaths = 0;
|
||||
g_MpChrs[chrnum].numpoints = 0;
|
||||
|
||||
chrnum++;
|
||||
}
|
||||
}
|
||||
|
||||
if (mpHasSimulants()) {
|
||||
s32 botnum = 0;
|
||||
s32 botconfignum;
|
||||
|
||||
for (botcfgnum = 0; botcfgnum < MAX_BOTS; botcfgnum++) {
|
||||
if ((g_MpSetup.chrslots & (1 << (botcfgnum + 4))) && mpIsSimSlotEnabled(botcfgnum)) {
|
||||
for (i = 0; i < g_BotConfigsArray[botcfgnum].quantity; i++) {
|
||||
g_MpChrs[chrnum].isbot = true;
|
||||
g_MpChrs[chrnum].team = g_BotConfigsArray[botcfgnum].base.team;
|
||||
g_MpChrs[chrnum].botconfig = &g_BotConfigsArray[botcfgnum];
|
||||
g_MpChrs[chrnum].chr = NULL;
|
||||
g_MpChrs[chrnum].placement = 0;
|
||||
g_MpChrs[chrnum].rankablescore = 0;
|
||||
g_MpChrs[chrnum].killcounts = &killcounts[chrnum * g_MpNumChrs];
|
||||
g_MpChrs[chrnum].numdeaths = 0;
|
||||
g_MpChrs[chrnum].numpoints = 0;
|
||||
|
||||
botmgrAllocateBot(chrnum, botcfgnum, botnum);
|
||||
botnum++;
|
||||
chrnum++;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
scenarioInitProps();
|
||||
}
|
||||
scenarioInitProps();
|
||||
}
|
||||
|
||||
void setupCreateProps(s32 stagenum)
|
||||
@@ -1133,6 +1174,6 @@ void setupCreateProps(s32 stagenum)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
setupAllocateEverything();
|
||||
modelmgrAllocateSlots(0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -34,7 +34,7 @@ void varsReset(void)
|
||||
g_Vars.props[i].next = &g_Vars.props[i + 1];
|
||||
}
|
||||
|
||||
varsResetRoomProps();
|
||||
g_Vars.props[i].next = NULL;
|
||||
|
||||
if (g_Vars.normmplayerisrunning) {
|
||||
g_Vars.numpropstates = 4;
|
||||
|
||||
+1
-3
@@ -273,15 +273,13 @@ extern struct textureconfig *g_TexGeneralConfigs;
|
||||
extern struct textureconfig *g_TexRadarConfigs;
|
||||
extern struct scenariodata g_ScenarioData;
|
||||
extern u32 var800ac4cc;
|
||||
extern struct chrdata *g_MpAllChrPtrs[MAX_MPCHRS];
|
||||
extern struct mpchrconfig *g_MpAllChrConfigPtrs[MAX_MPCHRS];
|
||||
extern s32 g_MpNumChrs;
|
||||
extern struct mpchr *g_MpChrs;
|
||||
extern struct mpbotconfig g_BotConfigsArray[MAX_BOTS];
|
||||
extern u8 g_MpSimulantDifficultiesPerNumPlayers[8][4];
|
||||
extern struct mpplayerconfig g_PlayerConfigsArray[6];
|
||||
extern u8 g_AmBotCommands[16];
|
||||
extern struct mpsetup g_MpSetup;
|
||||
extern struct bossfile g_BossFile;
|
||||
extern struct chrdata *g_MpBotChrPtrs[MAX_BOTS];
|
||||
|
||||
#endif
|
||||
|
||||
@@ -34,7 +34,8 @@
|
||||
#define IS8MB() (g_Is4Mb != true)
|
||||
#define LINEHEIGHT (VERSION == VERSION_JPN_FINAL ? 14 : 11)
|
||||
#define MIXCOLOUR(dialog, property) dialog->transitionfrac < 0.0f ? g_MenuColourPalettes[dialog->type].property : colourBlend(g_MenuColourPalettes[dialog->type2].property, g_MenuColourPalettes[dialog->type].property, dialog->colourweight)
|
||||
#define MPCHR(index) ((index) < 4 ? &g_PlayerConfigsArray[index].base : &g_BotConfigsArray[(index) - 4].base)
|
||||
#define MPCHR(index) &g_MpChrs[index]
|
||||
#define MPCHRCONFIG(index) ((index) < 4 ? &g_PlayerConfigsArray[index].base : &g_BotConfigsArray[index - 4].base)
|
||||
#define PLAYERCOUNT() ((g_Vars.players[0] ? 1 : 0) + (g_Vars.players[1] ? 1 : 0) + (g_Vars.players[2] ? 1 : 0) + (g_Vars.players[3] ? 1 : 0))
|
||||
#define RANDOMFRAC() (random() * (1.0f / U32_MAX))
|
||||
#define SECSTOTIME240(secs) (secs * 240)
|
||||
|
||||
@@ -497,6 +497,7 @@ extern struct mpbody g_MpBodies[NUM_MPBODIES];
|
||||
extern struct mppreset g_MpPresets[NUM_MPPRESETS];
|
||||
extern u32 g_TeamColours[];
|
||||
extern u32 var80087ce4[];
|
||||
extern s32 g_NumBots;
|
||||
extern u8 g_BotCount;
|
||||
extern struct aibotweaponpreference g_AibotWeaponPreferences[];
|
||||
extern u32 var80087eb4;
|
||||
|
||||
@@ -5,6 +5,6 @@
|
||||
#include "types.h"
|
||||
|
||||
void botmgrRemoveAll(void);
|
||||
void botmgrAllocateBot(s32 chrnum, s32 aibotnum);
|
||||
void botmgrAllocateBot(s32 chrnum, s32 botcfgnum, s32 botnum);
|
||||
|
||||
#endif
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
#include "types.h"
|
||||
|
||||
f32 mpHandicapToDamageScale(u8 value);
|
||||
void func0f187838(struct mpchrconfig *mpchr);
|
||||
void func0f187838(struct mpchr *mpchr);
|
||||
void mpStartMatch(void);
|
||||
void mpReset(void);
|
||||
void mpCalculateTeamIsOnlyAi(void);
|
||||
@@ -82,6 +82,7 @@ s32 mpGetCurrentTrackSlotNum(void);
|
||||
s32 mpChooseTrack(void);
|
||||
struct mpchrconfig *mpGetChrConfigBySlotNum(s32 slot);
|
||||
s32 mpGetChrIndexBySlotNum(s32 slot);
|
||||
s32 mpGetNumConfigs(void);
|
||||
s32 mpGetNumChrs(void);
|
||||
u8 mpFindUnusedTeamNum(void);
|
||||
void mpCreateBotFromProfile(s32 botnum, u8 difficulty);
|
||||
@@ -93,10 +94,7 @@ bool mpHasUnusedBotSlots(void);
|
||||
bool mpIsSimSlotEnabled(s32 slot);
|
||||
s32 mpFindBotProfile(s32 type, s32 difficulty);
|
||||
void mpGenerateBotNames(void);
|
||||
s32 mpPlayerGetIndex(struct chrdata *chr);
|
||||
struct chrdata *mpGetChrFromPlayerIndex(s32 index);
|
||||
s32 func0f18d074(s32 index);
|
||||
s32 func0f18d0e8(s32 arg0);
|
||||
void mpplayerfileLoadGunFuncs(struct savebuffer *buffer, s32 playernum);
|
||||
void mpplayerfileSaveGunFuncs(struct savebuffer *buffer, s32 playernum);
|
||||
void mpplayerfileLoadWad(s32 playernum, struct savebuffer *buffer, s32 arg2);
|
||||
|
||||
@@ -106,7 +106,7 @@ char *mpMenuTextScenarioName(struct menuitem *item);
|
||||
s32 scenarioScenarioMenuHandler(s32 operation, struct menuitem *item, union handlerdata *data);
|
||||
void scenarioCreateMatchStartHudmsgs(void);
|
||||
Gfx *scenarioRenderHud(Gfx *gdl);
|
||||
void scenarioCalculatePlayerScore(struct mpchrconfig *mpchr, s32 chrnum, s32 *arg2, s32 *arg3);
|
||||
void scenarioCalculatePlayerScore(struct mpchr *mpchr, s32 chrnum, s32 *arg2, s32 *arg3);
|
||||
bool scenarioHighlightProp(struct prop *prop, s32 *colour);
|
||||
void scenarioReset(void);
|
||||
struct prop *scenarioCreateObj(s32 modelnum, s16 padnum, f32 arg2, u32 flags, u32 flags2, u32 flags3);
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
#include "types.h"
|
||||
|
||||
Gfx *radarRenderBackground(Gfx *gdl, struct textureconfig *tconfig, s32 arg2, s32 arg3, s32 arg4);
|
||||
s32 radarGetTeamIndex(s32 team);
|
||||
Gfx *radarDrawDot(Gfx *gdl, struct prop *prop, struct coord *dist, u32 colour1, u32 colour2, bool swapcolours);
|
||||
Gfx *radarRender(Gfx *gdl);
|
||||
Gfx *radarRenderRTrackedProps(Gfx *gdl);
|
||||
|
||||
@@ -7,5 +7,6 @@
|
||||
void varsInit(void);
|
||||
|
||||
void varsReset(void);
|
||||
void varsResetRoomProps(void);
|
||||
|
||||
#endif
|
||||
|
||||
+58
-51
@@ -2705,7 +2705,7 @@ struct player {
|
||||
/*0x1be0*/ f32 cachedlookahead;
|
||||
/*0x1be4*/ u16 lookaheadframe;
|
||||
/*0x1be6*/ u8 numaibuddies;
|
||||
/*0x1be7*/ u8 aibuddynums[MAX_BOTS];
|
||||
/*0x1be7*/ u16 *aibuddynums;
|
||||
/*0x1bf0*/ bool bondexploding;
|
||||
/*0x1bf4*/ s32 bondnextexplode; // lvframe60 of next explosion
|
||||
/*0x1bf8*/ s32 bondcurexplode; // Increases by 1 on each tick even when not exploding
|
||||
@@ -4146,62 +4146,69 @@ struct gamefile {
|
||||
/*0xb5*/ u8 weaponsfound[6];
|
||||
};
|
||||
|
||||
// Allocated during setup - contains configuration common to both players and bots
|
||||
struct mpchrconfig {
|
||||
/*0x00*/ char name[12]; // up to 10 visible chars plus line break plus null byte
|
||||
/*0x0c*/ u8 unk0c;
|
||||
/*0x0d*/ u8 unk0d;
|
||||
/*0x0e*/ u8 unk0e;
|
||||
/*0x0f*/ u8 mpheadnum;
|
||||
/*0x10*/ u8 mpbodynum;
|
||||
/*0x11*/ u8 team;
|
||||
/*0x14*/ u32 displayoptions;
|
||||
/*0x18*/ u16 unk18;
|
||||
/*0x1a*/ u16 unk1a;
|
||||
/*0x1c*/ u16 unk1c;
|
||||
/*0x1e*/ s8 placement; // 0 = winner, 1 = second place etc
|
||||
/*0x20*/ s32 rankablescore;
|
||||
/*0x24*/ s16 killcounts[MAX_MPCHRS]; // per player - each index is a chrslot
|
||||
/*0x3c*/ s16 numdeaths;
|
||||
/*0x3e*/ s16 numpoints;
|
||||
/*0x40*/ s16 unk40;
|
||||
char name[15]; // up to 10 visible chars plus line break plus null byte
|
||||
u8 mpheadnum;
|
||||
u8 mpbodynum;
|
||||
u8 team;
|
||||
};
|
||||
|
||||
// Allocated during setup - extension of mpchrconfig
|
||||
struct mpplayerconfig {
|
||||
/*0x00*/ struct mpchrconfig base;
|
||||
/*0x44*/ u8 controlmode;
|
||||
/*0x45*/ s8 contpad1;
|
||||
/*0x46*/ s8 contpad2;
|
||||
/*0x48*/ u16 options;
|
||||
/*0x4c*/ struct fileguid fileguid;
|
||||
/*0x54*/ u32 kills;
|
||||
/*0x58*/ u32 deaths;
|
||||
/*0x5c*/ u32 gamesplayed;
|
||||
/*0x60*/ u32 gameswon;
|
||||
/*0x64*/ u32 gameslost;
|
||||
/*0x68*/ u32 time;
|
||||
/*0x6c*/ u32 distance; // 1 unit = 100 metres
|
||||
/*0x70*/ u32 accuracy;
|
||||
/*0x74*/ u32 damagedealt;
|
||||
/*0x78*/ u32 painreceived;
|
||||
/*0x7c*/ u32 headshots;
|
||||
/*0x80*/ u32 ammoused;
|
||||
/*0x84*/ u32 accuracymedals;
|
||||
/*0x88*/ u32 headshotmedals;
|
||||
/*0x8c*/ u32 killmastermedals;
|
||||
/*0x90*/ u32 survivormedals;
|
||||
/*0x94*/ u8 medals;
|
||||
/*0x95*/ u8 title;
|
||||
/*0x96*/ u8 newtitle;
|
||||
/*0x97*/ u8 gunfuncs[6];
|
||||
/*0x9d*/ u8 handicap;
|
||||
struct mpchrconfig base;
|
||||
u32 displayoptions;
|
||||
u16 unk1c;
|
||||
u8 controlmode;
|
||||
s8 contpad1;
|
||||
s8 contpad2;
|
||||
u16 options;
|
||||
struct fileguid fileguid;
|
||||
u32 kills;
|
||||
u32 deaths;
|
||||
u32 gamesplayed;
|
||||
u32 gameswon;
|
||||
u32 gameslost;
|
||||
u32 time;
|
||||
u32 distance; // 1 unit = 100 metres
|
||||
u32 accuracy;
|
||||
u32 damagedealt;
|
||||
u32 painreceived;
|
||||
u32 headshots;
|
||||
u32 ammoused;
|
||||
u32 accuracymedals;
|
||||
u32 headshotmedals;
|
||||
u32 killmastermedals;
|
||||
u32 survivormedals;
|
||||
u8 medals;
|
||||
u8 title;
|
||||
u8 newtitle;
|
||||
u8 gunfuncs[6];
|
||||
u8 handicap;
|
||||
};
|
||||
|
||||
struct mpbotconfig {
|
||||
/*0x00*/ struct mpchrconfig base;
|
||||
/*0x44*/ u8 unk44[3];
|
||||
/*0x47*/ u8 type;
|
||||
/*0x48*/ u8 difficulty;
|
||||
/*0x4a*/ u16 quantity;
|
||||
struct mpchrconfig base;
|
||||
u8 type;
|
||||
u8 difficulty;
|
||||
u16 quantity;
|
||||
};
|
||||
|
||||
// Allocated at match start - one per chr
|
||||
struct mpchr {
|
||||
u8 isbot;
|
||||
u8 team;
|
||||
u16 placement; // 0 = winner, 1 = second place etc
|
||||
union {
|
||||
struct mpchrconfig *config;
|
||||
struct mpplayerconfig *playerconfig;
|
||||
struct mpbotconfig *botconfig;
|
||||
};
|
||||
struct chrdata *chr;
|
||||
s32 rankablescore;
|
||||
s16 *killcounts;
|
||||
s16 numdeaths;
|
||||
s16 numpoints;
|
||||
};
|
||||
|
||||
struct missionconfig {
|
||||
@@ -4788,7 +4795,7 @@ struct chrbio {
|
||||
};
|
||||
|
||||
struct ranking {
|
||||
struct mpchrconfig *mpchr;
|
||||
struct mpchr *mpchr;
|
||||
union {
|
||||
u32 teamnum;
|
||||
u32 chrnum;
|
||||
|
||||
+1
-1
@@ -87,7 +87,7 @@ struct stageallocation g_StageAllocations8Mb[] = {
|
||||
{ STAGE_MP_RUINS, "-ml0 -me0 -mgfx200 -mvtx200 -ma0" },
|
||||
{ STAGE_MP_FORTRESS, "-ml0 -me0 -mgfx200 -mvtx200 -ma0" },
|
||||
{ STAGE_MP_VILLA, "-ml0 -me0 -mgfx200 -mvtx200 -ma0" },
|
||||
{ STAGE_4MBMENU, "-mgfx100 -mvtx50 -ma50" },
|
||||
{ STAGE_4MBMENU, "-ml0 -me0 -mgfx120 -mvtx98 -ma400" },
|
||||
{ STAGE_TITLE, "-ml0 -me0 -mgfx80 -mvtx20 -ma001" },
|
||||
{ 0, "-ml0 -me0 -mgfx120 -mvtx98 -ma300" },
|
||||
};
|
||||
|
||||
+5
-1
@@ -165,7 +165,11 @@ void *mempAllocFromBank(struct memorypool *pool, u32 size, u8 poolnum)
|
||||
|
||||
void *mempAlloc(u32 len, u8 pool)
|
||||
{
|
||||
void *allocation = mempAllocFromBank(g_MempOnboardPools, len, pool);
|
||||
void *allocation;
|
||||
|
||||
len = ALIGN8(len);
|
||||
|
||||
allocation = mempAllocFromBank(g_MempOnboardPools, len, pool);
|
||||
|
||||
if (allocation) {
|
||||
return allocation;
|
||||
|
||||
Reference in New Issue
Block a user