
IR Goggles
You'll notice everybody while using these because everyone glows red!
I made this tutorial up
quickly because, frankly, I don't like powerups or anything which are not
items. So I decided to convert Psykotik's old tutorial to something
more... class-oriented. Enjoy.
Add in the blue code and take out any pink code. Pay attention to anything in
green.
First, we should add the item to the itemlist in g_items.c - go down to the itemlist[] decleration and add
this item somewhere in the middle:
/*
item_irgoggles - added by nobody */
{
"item_irgoggles",
Pickup_Powerup,
Use_IRGoggles,
NULL,
NULL,
"items/pkup.wav",
"models/ammo/nuke/tris.md2", EF_ROTATE,
NULL,
"k_comhead",
"IR Goggles",
2,
60,
NULL,
IT_POWERUP,
0,
NULL,
0,
""
},
Next. We need to define a
function which is called "Use_IRGoggles".
Go down to the bottom of the file, and add this function. Noticing any
similarity to the Scope tutorial yet?? :)
/*
=================
Use_IRGoggles
=================
*/
void Use_IRGoggles (edict_t *ent, gitem_t *item)
{
if (ent->client->goggles) // we're on
{
ent->client->goggles = 0;
ent->client->ps.rdflags
&= ~RDF_IRGOGGLES;
}
else // we're off
{
ent->client->goggles = 1;
ent->client->ps.rdflags |=
RDF_IRGOGGLES;
}
}
Next, we need a forward declaration for this function. Stick this line down at the bottom of g_local.h. This allows the function to be used before it is technically declared.
void Use_IRGoggles (edict_t *ent, gitem_t *item);
That set up the item and
command for the goggles, toggling the ent->client->goggles variable and setting
the RDF_IRGOGGLES flag as necessary.
Now we need to set up the drain of cells on the goggles. Open up the p_client.c file and go down into ClientThink.
Right before the line "gi.linkentity(ent);" add the following:
//
PSY: GOGGLES DRAIN
if (ent->client->goggles)
{
if
(ent->client->pers.inventory[ITEM_INDEX(FindItem("Cells"))]
>= 1)
{
ent->client->goggledrain++;
if
(ent->client->goggledrain == 10)
{
ent->client->pers.inventory[ITEM_INDEX(FindItem("Cells"))]
-= 1;
ent->client->goggledrain = 0;
}
}
else
{
ent->client->ps.rdflags &= ~RDF_IRGOGGLES;
ent->client->goggles = 0;
}
}
This handles the goggle drain. You need one more block of code, to make the players visible to the Infrared scanning. Go into p_view.c and find G_SetClientEffects(). Go down right before the line "if (ent->powerarmor_time > level.time)":
if
(!(ent->s.renderfx & RF_IR_VISIBLE))
ent->s.renderfx |=
RF_IR_VISIBLE;
This ensures that the player is always visible (even dead) to IR. The final thing you need to do is go into g_local.h and add in two new client variables into the gclient_s structure, after the line "qboolean update_chase;" insert the following:
// this structure
is cleared on each PutClientInServer(),
// except for 'client->pers'
struct gclient_s
{
// known to server
player_state_t ps; // communicated
by server to clients
int ping;
...
edict_t *chase_target; // player we
are chasing
qboolean update_chase; // need to
update chase info?
int goggles;
int goggledrain;
};
And, finally - insert this code into InitClientPersistant, which is in p_client.c.
/*
==============
InitClientPersistant
This is only called when the game first initializes in single player,
but is called after each death and level change in deathmatch
==============
*/
void InitClientPersistant (gclient_t *client)
{
gitem_t *item;
memset (&client->pers, 0,
sizeof(client->pers));
item = FindItem("IR Goggles");
client->pers.selected_item = ITEM_INDEX(item);
client->pers.inventory[client->pers.selected_item] = 1;
item = FindItem("Blaster");
client->pers.selected_item = ITEM_INDEX(item);
client->pers.inventory[client->pers.selected_item] = 1;
client->pers.weapon = item;
client->pers.health = 100;
client->pers.max_health = 100;
client->pers.max_bullets = 200;
client->pers.max_shells = 100;
client->pers.max_rockets = 50;
client->pers.max_grenades = 50;
client->pers.max_cells = 200;
client->pers.max_slugs = 50;
client->pers.connected = true;
}
And that's it! IR goggles! Enjoy!
Tutorial by Psykotik, with a item-based rework from (nobody)
Quake Style -
Tutorials