mirror of
https://github.com/yquake2/yquake2remaster.git
synced 2025-03-14 23:12:41 +00:00
game: add misc_player_mannequin from ReRelease code
Based on: https://github.com/Paril/quake2-rerelease-dll.git
This commit is contained in:
parent
c6338f0c36
commit
4e22fc255d
8 changed files with 232 additions and 7 deletions
|
@ -163,7 +163,6 @@ Goals, fully finished goals could be checked in [here](CHANGELOG):
|
|||
* [ ] Rearange surfaces in vulkan render before render,
|
||||
* [ ] Fully implement `target_camera`,
|
||||
* [ ] Fully implement `misc_flare`,
|
||||
* [ ] Fully implement `misc_player_mannequin`,
|
||||
* [ ] Single player ReRelease support,
|
||||
* [ ] Support effects and additional flags for ReRelease when possible.
|
||||
* [ ] Use shared model cache in client code insted reimplemnet in each render,
|
||||
|
|
|
@ -26,6 +26,7 @@
|
|||
*/
|
||||
|
||||
#include "header/local.h"
|
||||
#include "monster/misc/player.h"
|
||||
|
||||
int debristhisframe;
|
||||
int gibsthisframe;
|
||||
|
@ -3351,6 +3352,219 @@ SP_misc_flare(edict_t* ent)
|
|||
gi.linkentity(ent);
|
||||
}
|
||||
|
||||
void
|
||||
misc_player_mannequin_use(edict_t * self, edict_t * other, edict_t * activator)
|
||||
{
|
||||
self->monsterinfo.aiflags |= AI_TARGET_ANGER;
|
||||
self->enemy = activator;
|
||||
|
||||
switch ( self->count )
|
||||
{
|
||||
case GESTURE_FLIP_OFF:
|
||||
self->s.frame = FRAME_flip01;
|
||||
self->monsterinfo.nextframe = FRAME_flip12;
|
||||
break;
|
||||
|
||||
case GESTURE_SALUTE:
|
||||
self->s.frame = FRAME_salute01;
|
||||
self->monsterinfo.nextframe = FRAME_salute11;
|
||||
break;
|
||||
|
||||
case GESTURE_TAUNT:
|
||||
self->s.frame = FRAME_taunt01;
|
||||
self->monsterinfo.nextframe = FRAME_taunt17;
|
||||
break;
|
||||
|
||||
case GESTURE_WAVE:
|
||||
self->s.frame = FRAME_wave01;
|
||||
self->monsterinfo.nextframe = FRAME_wave11;
|
||||
break;
|
||||
|
||||
case GESTURE_POINT:
|
||||
self->s.frame = FRAME_point01;
|
||||
self->monsterinfo.nextframe = FRAME_point12;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
misc_player_mannequin_think(edict_t * self)
|
||||
{
|
||||
if (self->last_sound_time <= level.time)
|
||||
{
|
||||
self->s.frame++;
|
||||
|
||||
if ((self->monsterinfo.aiflags & AI_TARGET_ANGER) == 0)
|
||||
{
|
||||
if (self->s.frame > FRAME_stand40)
|
||||
{
|
||||
self->s.frame = FRAME_stand01;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (self->s.frame > self->monsterinfo.nextframe)
|
||||
{
|
||||
self->s.frame = FRAME_stand01;
|
||||
self->monsterinfo.aiflags &= ~AI_TARGET_ANGER;
|
||||
self->enemy = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
self->last_sound_time = level.time + FRAMETIME;
|
||||
}
|
||||
|
||||
if (self->enemy)
|
||||
{
|
||||
vec3_t vec;
|
||||
|
||||
VectorSubtract(self->enemy->s.origin, self->s.origin, vec);
|
||||
self->ideal_yaw = vectoyaw(vec);
|
||||
M_ChangeYaw(self);
|
||||
}
|
||||
|
||||
self->nextthink = level.time + FRAMETIME;
|
||||
}
|
||||
|
||||
void
|
||||
SetupMannequinModel(edict_t * self, int modelType, const char *weapon, const char *skin)
|
||||
{
|
||||
const char *model_name = NULL;
|
||||
const char *default_skin = NULL;
|
||||
|
||||
switch (modelType)
|
||||
{
|
||||
case 1:
|
||||
{
|
||||
self->s.skinnum = (MAX_CLIENTS - 1);
|
||||
model_name = "female";
|
||||
default_skin = "venus";
|
||||
break;
|
||||
}
|
||||
|
||||
case 2:
|
||||
{
|
||||
self->s.skinnum = (MAX_CLIENTS - 2);
|
||||
model_name = "male";
|
||||
default_skin = "rampage";
|
||||
break;
|
||||
}
|
||||
|
||||
case 3:
|
||||
{
|
||||
self->s.skinnum = (MAX_CLIENTS - 3);
|
||||
model_name = "cyborg";
|
||||
default_skin = "oni911";
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
{
|
||||
self->s.skinnum = (MAX_CLIENTS - 1);
|
||||
model_name = "female";
|
||||
default_skin = "venus";
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (model_name)
|
||||
{
|
||||
char line[MAX_QPATH] = {0};
|
||||
|
||||
snprintf(line, sizeof(line), "players/%s/tris.md2", model_name);
|
||||
self->model = ED_NewString(line, true);
|
||||
|
||||
if (weapon)
|
||||
{
|
||||
snprintf(line, sizeof(line), "players/%s/%s.md2", model_name, weapon);
|
||||
}
|
||||
else
|
||||
{
|
||||
snprintf(line, sizeof(line), "players/%s/w_hyperblaster.md2", model_name);
|
||||
}
|
||||
self->s.modelindex2 = gi.modelindex(line);
|
||||
|
||||
if (skin)
|
||||
{
|
||||
snprintf(line, sizeof(line), "%s/%s", model_name, skin);
|
||||
}
|
||||
else
|
||||
{
|
||||
snprintf(line, sizeof(line), "%s/%s", model_name, default_skin);
|
||||
}
|
||||
gi.configstring(CS_PLAYERSKINS + self->s.skinnum, line);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* QUAKED misc_player_mannequin (1.0 1.0 0.0) (-32 -32 -32) (32 32 32)
|
||||
* Creates a player mannequin that stands around.
|
||||
*
|
||||
* NOTE: this is currently very limited, and only allows one unique model
|
||||
* from each of the three player model types.
|
||||
*
|
||||
*
|
||||
* "distance" - Sets the type of gesture mannequin when use when triggered
|
||||
* "height" - Sets the type of model to use ( valid numbers: 1 - 3 )
|
||||
* "goals" - Name of the weapon to use.
|
||||
* "image" - Name of the player skin to use.
|
||||
* "radius" - How much to scale the model in-game
|
||||
*/
|
||||
void
|
||||
SP_misc_player_mannequin(edict_t * self)
|
||||
{
|
||||
int i;
|
||||
|
||||
self->movetype = MOVETYPE_NONE;
|
||||
self->solid = SOLID_BBOX;
|
||||
if (!st.effects)
|
||||
{
|
||||
self->s.effects = 0;
|
||||
}
|
||||
|
||||
if (!st.renderfx)
|
||||
{
|
||||
self->s.renderfx = RF_MINLIGHT;
|
||||
}
|
||||
|
||||
VectorSet(self->mins, -16, -16, -24);
|
||||
VectorSet(self->maxs, 16, 16, 32);
|
||||
self->yaw_speed = 30;
|
||||
self->ideal_yaw = 0;
|
||||
self->last_sound_time = level.time + FRAMETIME;
|
||||
self->s.modelindex = CUSTOM_PLAYER_MODEL;
|
||||
self->count = st.distance;
|
||||
|
||||
SetupMannequinModel(self, st.height, st.goals, st.image);
|
||||
|
||||
VectorSet(self->rrs.scale, 1.0f, 1.0f, 1.0f);
|
||||
if (ai_model_scale->value > 0.0f)
|
||||
{
|
||||
VectorSet(self->rrs.scale,
|
||||
ai_model_scale->value, ai_model_scale->value, ai_model_scale->value);
|
||||
}
|
||||
else if (st.radius > 0.0f)
|
||||
{
|
||||
VectorSet(self->rrs.scale,
|
||||
st.radius, st.radius, st.radius);
|
||||
}
|
||||
|
||||
for (i = 0;i < 3; i++)
|
||||
{
|
||||
self->mins[i] *= self->rrs.scale[i];
|
||||
self->maxs[i] *= self->rrs.scale[i];
|
||||
}
|
||||
|
||||
self->think = misc_player_mannequin_think;
|
||||
self->nextthink = level.time + FRAMETIME;
|
||||
|
||||
if (self->targetname)
|
||||
{
|
||||
self->use = misc_player_mannequin_use;
|
||||
}
|
||||
|
||||
gi.linkentity(self);
|
||||
}
|
||||
|
||||
/*
|
||||
* QUAKED misc_model (1 0 0) (-8 -8 -8) (8 8 8)
|
||||
|
|
|
@ -422,6 +422,9 @@ typedef struct
|
|||
float fade_end_dist;
|
||||
char *image;
|
||||
unsigned rgba;
|
||||
char *goals;
|
||||
int effects;
|
||||
int renderfx;
|
||||
|
||||
/* Addional fields for models */
|
||||
vec3_t scale;
|
||||
|
|
|
@ -58,14 +58,17 @@
|
|||
{"origin", FOFS(s.origin), F_VECTOR},
|
||||
{"angles", FOFS(s.angles), F_VECTOR},
|
||||
{"angle", FOFS(s.angles), F_ANGLEHACK},
|
||||
{"health_multiplier", STOFS(health_multiplier), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"rgb", STOFS(rgba), F_RGBA, FFL_SPAWNTEMP},
|
||||
{"rgba", STOFS(rgba), F_RGBA, FFL_SPAWNTEMP},
|
||||
{"scale", STOFS(scale), F_VECTOR, FFL_SPAWNTEMP},
|
||||
{"radius", STOFS(radius), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"fade_start_dist", STOFS(fade_start_dist), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"effects", STOFS(effects), F_INT, FFL_SPAWNTEMP},
|
||||
{"fade_end_dist", STOFS(fade_end_dist), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"fade_start_dist", STOFS(fade_start_dist), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"goals", STOFS(goals), F_LRAWSTRING, FFL_SPAWNTEMP},
|
||||
{"health_multiplier", STOFS(health_multiplier), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"image", STOFS(image), F_LRAWSTRING, FFL_SPAWNTEMP},
|
||||
{"radius", STOFS(radius), F_FLOAT, FFL_SPAWNTEMP},
|
||||
{"renderfx", STOFS(renderfx), F_INT, FFL_SPAWNTEMP},
|
||||
{"rgba", STOFS(rgba), F_RGBA, FFL_SPAWNTEMP},
|
||||
{"rgb", STOFS(rgba), F_RGBA, FFL_SPAWNTEMP},
|
||||
{"scale", STOFS(scale), F_VECTOR, FFL_SPAWNTEMP},
|
||||
{"goalentity", FOFS(goalentity), F_EDICT, FFL_NOSPAWN},
|
||||
{"movetarget", FOFS(movetarget), F_EDICT, FFL_NOSPAWN},
|
||||
{"enemy", FOFS(enemy), F_EDICT, FFL_NOSPAWN},
|
||||
|
|
|
@ -1031,6 +1031,8 @@ extern void misc_easterchick_think ( edict_t * self ) ;
|
|||
extern void misc_eastertank_think ( edict_t * self ) ;
|
||||
extern void misc_nuke_core_use ( edict_t * self , edict_t * other , edict_t * activator ) ;
|
||||
extern void misc_flare_use ( edict_t * self , edict_t * other , edict_t * activator ) ;
|
||||
extern void misc_player_mannequin_use ( edict_t * self , edict_t * other , edict_t * activator ) ;
|
||||
extern void misc_player_mannequin_think ( edict_t * self ) ;
|
||||
extern void misc_satellite_dish_think ( edict_t * self ) ;
|
||||
extern void misc_satellite_dish_use ( edict_t * self , edict_t * other , edict_t * activator ) ;
|
||||
extern void misc_strogg_ship_use ( edict_t * self , edict_t * other , edict_t * activator ) ;
|
||||
|
|
|
@ -1009,6 +1009,8 @@
|
|||
{"misc_eastertank_think", (byte *)misc_eastertank_think},
|
||||
{"misc_nuke_core_use", (byte *)misc_nuke_core_use},
|
||||
{"misc_flare_use", (byte *)misc_flare_use},
|
||||
{"misc_player_mannequin_use", (byte *)misc_player_mannequin_use},
|
||||
{"misc_player_mannequin_think", (byte *)misc_player_mannequin_think},
|
||||
{"misc_satellite_dish_think", (byte *)misc_satellite_dish_think},
|
||||
{"misc_satellite_dish_use", (byte *)misc_satellite_dish_use},
|
||||
{"misc_strogg_ship_use", (byte *)misc_strogg_ship_use},
|
||||
|
|
|
@ -93,6 +93,7 @@ extern void SP_misc_nuke ( edict_t * ent ) ;
|
|||
extern void SP_misc_nuke_core ( edict_t * ent ) ;
|
||||
extern void SP_misc_flare ( edict_t * ent ) ;
|
||||
extern void SP_misc_model ( edict_t * ent ) ;
|
||||
extern void SP_misc_player_mannequin ( edict_t * ent ) ;
|
||||
extern void SP_misc_satellite_dish ( edict_t * ent ) ;
|
||||
extern void SP_misc_strogg_ship ( edict_t * ent ) ;
|
||||
extern void SP_misc_teleporter ( edict_t * ent ) ;
|
||||
|
|
|
@ -98,6 +98,7 @@
|
|||
{"misc_nuke_core", SP_misc_nuke_core},
|
||||
{"misc_flare", SP_misc_flare},
|
||||
{"misc_model", SP_misc_model},
|
||||
{"misc_player_mannequin", SP_misc_player_mannequin},
|
||||
{"misc_satellite_dish", SP_misc_satellite_dish},
|
||||
{"misc_strogg_ship", SP_misc_strogg_ship},
|
||||
{"misc_teleporter", SP_misc_teleporter},
|
||||
|
|
Loading…
Reference in a new issue