gear/src/hu_tracers.c

305 lines
7.7 KiB
C
Raw Permalink Normal View History

2024-09-08 18:03:02 +12:00
/* Emacs style mode select -*- C++ -*-
*-----------------------------------------------------------------------------
*
*
* PrBoom: a Doom port merged with LxDoom and LSDLDoom
* based on BOOM, a modified and improved DOOM engine
* Copyright (C) 1999 by
* id Software, Chi Hoang, Lee Killough, Jim Flynn, Rand Phares, Ty Halderman
* Copyright (C) 1999-2000 by
* Jess Haas, Nicolas Kalkhof, Colin Phipps, Florian Schulze
* Copyright 2005, 2006 by
* Florian Schulze, Colin Phipps, Neil Stevens, Andrey Budko
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
* as published by the Free Software Foundation; either version 2
* of the License, or (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
* 02111-1307, USA.
*
* DESCRIPTION: tracers stuff
*
*-----------------------------------------------------------------------------
*/
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include "doomdef.h"
#include "doomstat.h"
#include "m_argv.h"
#include "m_misc.h"
#include "lprintf.h"
#include "hu_tracers.h"
dboolean traces_present;
hu_textline_t w_traces[NUMTRACES];
void TracerApply(tracertype_t index);
void GivenDamageReset(tracertype_t index);
void GivenDamageApply(tracertype_t index);
traceslist_t traces[NUMTRACES];
void InitTracers(void)
{
int i, p;
int value, count;
traceslistinit_t traces_init[NUMTRACES] = {
{"-trace_thingshealth", "health ", TracerApply, NULL},
{"-trace_thingspickup", "pickup ", TracerApply, NULL},
{"-trace_linescross" , "lcross ", TracerApply, NULL},
{"-trace_givendamage" , "damage ", GivenDamageApply, GivenDamageReset},
};
traces_present = false;
for (i = 0; i < NUMTRACES; i++)
{
strcpy(traces[i].cmd, traces_init[i].cmd);
strcpy(traces[i].prefix, traces_init[i].prefix);
traces[i].ApplyFunc = traces_init[i].ApplyFunc;
traces[i].ResetFunc = traces_init[i].ResetFunc;
count = 0;
traces[i].count = 0;
if ((p = M_CheckParm(traces[i].cmd)) && (p < myargc - 1))
{
while (count < 3 && p + count < myargc - 1 && M_StrToInt(myargv[p + 1 + count], &value))
{
sprintf(traces[i].items[count].value, "\x1b\x36%d\x1b\x33 0", value);
traces[i].items[count].index = value;
if (traces[i].ApplyFunc)
traces[i].ApplyFunc(i);
traces_present = true;
count++;
}
traces[i].count = count;
}
}
}
void TracerApply(tracertype_t index)
{
int i;
strcpy(traces[index].hudstr, traces[index].prefix);
for (i = 0; i < traces[index].count; i++)
{
sprintf(traces[index].hudstr + strlen(traces[index].hudstr),
"\x1b\x33%s ", traces[index].items[i].value);
}
}
void CheckThingsPickupTracer(mobj_t *mobj)
{
if (traces[TRACE_PICKUP].count)
{
int i;
for (i = 0; i < traces[TRACE_PICKUP].count; i++)
{
if (mobj->index == traces[TRACE_PICKUP].items[i].index)
{
sprintf(traces[TRACE_PICKUP].items[i].value,
"\x1b\x36%d \x1b\x33%05.2f",
traces[TRACE_PICKUP].items[i].index, (float)(leveltime)/35);
}
}
}
}
void CheckThingsHealthTracer(mobj_t *mobj)
{
if (traces[TRACE_HEALTH].count)
{
int i;
for (i = 0; i < traces[TRACE_HEALTH].count; i++)
{
if (mobj->index == traces[TRACE_HEALTH].items[i].index)
{
sprintf(traces[TRACE_HEALTH].items[i].value,
"\x1b\x36%d \x1b\x33%d",
mobj->index, mobj->health);
}
}
}
}
int crossed_lines_count = 0;
void CheckLinesCrossTracer(line_t *line)
{
if (traces[TRACE_CROSS].count)
{
int i;
crossed_lines_count++;
for (i = 0;i < traces[TRACE_CROSS].count; i++)
{
if (line->iLineID == traces[TRACE_CROSS].items[i].index)
{
if (!traces[TRACE_CROSS].items[i].data1)
{
sprintf(traces[TRACE_CROSS].items[i].value,
"\x1b\x36%d \x1b\x33%05.2f",
traces[TRACE_CROSS].items[i].index, (float)(leveltime)/35);
traces[TRACE_CROSS].items[i].data1 = 1;
}
}
}
}
}
void ClearLinesCrossTracer(void)
{
if (traces[TRACE_CROSS].count)
{
if (!crossed_lines_count)
{
int i;
for (i = 0; i < traces[TRACE_CROSS].count; i++)
{
traces[TRACE_CROSS].items[i].data1 = 0;
}
}
crossed_lines_count = 0;
}
}
static int given_damage_pertic[MAXTRACEITEMS];
static int given_damage_pertic_saved[MAXTRACEITEMS];
static int given_damage_total[MAXTRACEITEMS];
static int given_damage_processed[MAXTRACEITEMS];
void CheckGivenDamageTracer(mobj_t *mobj, int damage)
{
if (traces[TRACE_DAMAGE].count)
{
int i;
for (i = 0; i < traces[TRACE_DAMAGE].count; i++)
{
if (mobj->index == traces[TRACE_DAMAGE].items[i].index)
{
given_damage_processed[i] = false;
given_damage_pertic[i] += damage;
given_damage_total[i] += damage;
}
}
}
}
void GivenDamageApply(tracertype_t index)
{
if (traces[index].count)
{
int i;
for (i = 0; i < traces[index].count; i++)
{
if (!given_damage_processed[i])
{
given_damage_processed[i] = true;
given_damage_pertic_saved[i] = given_damage_pertic[i];
}
sprintf(traces[index].items[i].value,
"\x1b\x36%d \x1b\x33%d/\x1b\x33%d",
traces[index].items[i].index, given_damage_pertic_saved[i], given_damage_total[i]);
TracerApply(index);
}
}
}
void GivenDamageReset(tracertype_t index)
{
int i;
for (i = 0; i < traces[index].count; i++)
{
given_damage_pertic[i] = 0;
}
}
typedef struct {
int init_index;
int index;
} PACKEDATTR tracer_mapthing_t;
static tracer_mapthing_t *deathmatchstarts_indexes = NULL;
static tracer_mapthing_t playerstarts_indexes[MAXPLAYERS];
int num_deathmatchstarts_indexes = 0;
void TracerAddDeathmatchStart(int num, int index)
{
if (num >= num_deathmatchstarts_indexes)
{
num_deathmatchstarts_indexes = num + 1;
deathmatchstarts_indexes = realloc(
deathmatchstarts_indexes,
num_deathmatchstarts_indexes * sizeof(deathmatchstarts_indexes[0]));
}
deathmatchstarts_indexes[num].index = index;
}
void TracerAddPlayerStart(int num, int index)
{
if (traces_present)
{
//init
if (gametic == 0)
{
playerstarts_indexes[num].init_index = index;
playerstarts_indexes[num].index = index;
}
else
{
playerstarts_indexes[num].index = playerstarts_indexes[num].init_index;
}
}
}
int TracerGetDeathmatchStart(int index)
{
if (index >= num_deathmatchstarts_indexes)
I_Error("TracerGetDeathmatchStart: index out of bounds");
return deathmatchstarts_indexes[index].index;
}
int TracerGetPlayerStart(int index)
{
if (index >= MAXPLAYERS)
I_Error("TracerGetDeathmatchStart: index out of bounds");
return playerstarts_indexes[index].index;
}
void TracerClearStarts(void)
{
int i;
for (i = 0; i < MAXPLAYERS; i++)
{
playerstarts_indexes[i].index = 0;
}
num_deathmatchstarts_indexes = 0;
if (deathmatchstarts_indexes)
{
free(deathmatchstarts_indexes);
deathmatchstarts_indexes = NULL;
}
}