//**********************************************************************
// RESPAWN FUNCTIONS
//**********************************************************************
// get all of our spawns into their arrays
init_spawns()
{
// grab CSDM file
new mapName[32], csdmFile[64], lineData[64];
get_configsdir(cfgDir,31);
get_mapname(mapName,31);
formatex(csdmFile,63,"%s/csdm/%s.spawns.cfg",cfgDir,mapName);
// collect CSDM spawns
if(file_exists(csdmFile))
{
new csdmData[10][6];
new file = fopen(csdmFile,"rt");
while(file && !feof(file))
{
fgets(file,lineData,63);
// invalid spawn
if(!lineData[0] || str_count(lineData,' ') < 2)
continue;
// BREAK IT UP!
parse(lineData,csdmData[0],5,csdmData[1],5,csdmData[2],5,csdmData[3],5,csdmData[4],5,csdmData[5],5,csdmData[6],5,csdmData[7],5,csdmData[8],5,csdmData[9],5);
// origin
spawns[spawnCount][0] = floatstr(csdmData[0]);
spawns[spawnCount][1] = floatstr(csdmData[1]);
spawns[spawnCount][2] = floatstr(csdmData[2]);
// angles
spawns[spawnCount][3] = floatstr(csdmData[3]);
spawns[spawnCount][4] = floatstr(csdmData[4]);
spawns[spawnCount][5] = floatstr(csdmData[5]);
// team, csdmData[6], unused
// vangles
spawns[spawnCount][6] = floatstr(csdmData[7]);
spawns[spawnCount][7] = floatstr(csdmData[8]);
spawns[spawnCount][8] = floatstr(csdmData[9]);
spawnCount++;
csdmSpawnCount++;
if(spawnCount >= MAX_SPAWNS) break;
}
if(file) fclose(file);
}
// collect regular, boring spawns
else
{
collect_spawns("info_player_deathmatch");
collect_spawns("info_player_start");
}
}
// collect boring spawns into our spawn data
collect_spawns(classname[])
{
new ent = maxPlayers, Float:spawnData[3];
while((ent = fm_find_ent_by_class(ent,classname)))
{
// origin
pev(ent,pev_origin,spawnData);
spawns[spawnCount][0] = spawnData[0];
spawns[spawnCount][1] = spawnData[1];
spawns[spawnCount][2] = spawnData[2];
// angles
pev(ent,pev_angles,spawnData);
spawns[spawnCount][3] = spawnData[0];
spawns[spawnCount][4] = spawnData[1];
spawns[spawnCount][5] = spawnData[2];
// vangles
spawns[spawnCount][6] = spawnData[0];
spawns[spawnCount][7] = spawnData[1];
spawns[spawnCount][8] = spawnData[2];
spawnCount++;
if(spawnCount >= MAX_SPAWNS) break;
}
}
public restore_respawn(id,lvl,cid)
{
if(!cmd_access(id,lvl,cid,1))
return PLUGIN_HANDLED
new teamid = get_user_team(id)
if(teamid == 1 || teamid == 2)
{
if(g_StopRespawn[id])
{
g_StopRespawn[id] = false
begin_respawn(id)
console_print(id, "Spawning is re-enable")
return PLUGIN_HANDLED
}
else
{
g_StopRespawn[id] = true
//user_silentkill(id)
console_print(id, "Stop re-spawning")
return PLUGIN_HANDLED
}
}
return PLUGIN_CONTINUE
}
// bring someone back to life
public begin_respawn(id)
{
if(!ggActive || !get_pcvar_num(gg_dm) || !is_user_connected(id) || g_StopRespawn[id])
return;
// now on spectator
if(!on_valid_team(id)) return;
// alive, and not in the broken sort of way
if(is_user_alive(id) && !pev(id,pev_iuser1))
return;
// round is over, or bomb is planted
if(roundEnded || (bombStatus[3] == BOMB_PLANTED && !get_pcvar_num(gg_dm_spawn_afterplant)))
return;
new Float:delay = get_pcvar_float(gg_dm_spawn_delay);
if(delay < 0.1) delay = 0.1;
new dm_countdown = get_pcvar_num(gg_dm_countdown);
if((dm_countdown & 1) || (dm_countdown & 2))
{
respawn_timeleft[id] = floatround(delay);
respawn_countdown(id);
}
remove_task(TASK_RESPAWN+id);
set_task(delay,"respawn",TASK_RESPAWN+id);
}
// show the respawn countdown to a player
public respawn_countdown(id)
{
if(!is_user_connected(id) || is_user_alive(id))
{
respawn_timeleft[id] = 0;
return;
}
new dm_countdown = get_pcvar_num(gg_dm_countdown);
if(dm_countdown & 1)
client_print(id,print_center,"%L",id,"RESPAWN_COUNTDOWN",respawn_timeleft[id]);
if(dm_countdown & 2)
{
set_hudmessage(255,255,255,-1.0,0.75,0,6.0,1.0,0.1,0.5);
ShowSyncHudMsg(id,hudSyncCountdown,"%L",id,"RESPAWN_COUNTDOWN",respawn_timeleft[id]);
}
if(--respawn_timeleft[id] >= 1) set_task(1.0,"respawn_countdown",id);
}
// REALLY bring someone back to life
public respawn(taskid)
{
new id = taskid-TASK_RESPAWN;
if(!is_user_connected(id) || !ggActive) return;
// round is over, or bomb is planted
if(roundEnded || (bombStatus[3] == BOMB_PLANTED && !get_pcvar_num(gg_dm_spawn_afterplant)))
return;
// now on spectator
if(!on_valid_team(id)) return;
// clear countdown
new dm_countdown = get_pcvar_num(gg_dm_countdown);
if(dm_countdown & 1) client_print(id,print_center," ");
if(dm_countdown & 2) ClearSyncHud(id,hudSyncCountdown);
// alive, and not in the broken sort of way
if(is_user_alive(id)) return;
static model[22];
// remove his dropped weapons from before
new ent = maxPlayers;
while((ent = fm_find_ent_by_class(ent,"weaponbox")))
{
pev(ent,pev_model,model,21);
// don't remove the bomb!! (thanks ToT | V!PER)
if(equal(model,"models/w_c4.mdl",15) || equal(model,"models/w_backpack.mdl"))
continue;
// this is mine
if(pev(ent,pev_owner) == id) dllfunc(DLLFunc_Think,ent);
}
new spawn_random = get_pcvar_num(gg_dm_spawn_random);
if(spawn_random) spawnSounds[id] = 0;
ExecuteHamB(Ham_CS_RoundRespawn,id); // note the B
if(spawn_random)
{
do_random_spawn(id,spawn_random);
spawnSounds[id] = 1;
// to be fair, play a spawn noise at new location
engfunc(EngFunc_EmitSound,id,CHAN_ITEM,"items/gunpickup2.wav",VOL_NORM,ATTN_NORM,0,PITCH_NORM);
}
new Float:time = get_pcvar_float(gg_dm_sp_time);
new mode = get_pcvar_num(gg_dm_sp_mode);
new buttons = pev(id,pev_button);
// spawn protection
//if(time > 0.0 && mode && !(buttons & IN_ATTACK) && !(buttons & IN_ATTACK2))
if(time > 0.0 && mode)
{
spawnProtected[id] = 1;
if(mode == 2)
{
new team = get_user_team(id)
fm_set_user_godmode(id,1);
if(team == 1)
{
fm_set_rendering(id, kRenderFxGlowShell, 255, 0, 0, kRenderNormal, 16)
}
if(team == 2)
{
fm_set_rendering(id, kRenderFxGlowShell, 0, 0, 255, kRenderNormal, 16)
}
}else fm_set_rendering(id,kRenderFxGlowShell,100,100,100,kRenderNormal,8); // gray/white
set_task(time,"remove_spawn_protection",TASK_REMOVE_PROTECTION+id);
}
}
public On_ClientPreThink(taskid)
{
new id = taskid;
new buttons = pev(id,pev_button);
if (!spawnProtected[id] || !is_user_connected(id))
return;
if ( (buttons & IN_ATTACK) || (buttons & IN_ATTACK2) )
{
RemoveProtection(taskid)
}
}
RemoveProtection(taskid)
{
new id = taskid;
if (spawnProtected[id])
remove_task(spawnProtected[id])
ProtectionOver(id)
}
public ProtectionOver(taskid)
{
new id = taskid;
spawnProtected[id] = 0;
if(!is_user_connected(id)) return;
if(get_pcvar_num(gg_dm_sp_mode) == 2) fm_set_user_godmode(id,0);
fm_set_rendering(id); // reset back to normal
}
// place a user at a random spawn
do_random_spawn(id,spawn_random)
{
// not even alive, don't bother
if(!is_user_alive(id)) return;
// no spawns???
if(spawnCount <= 0) return;
// no CSDM spawns, mode 2
if(spawn_random == 2 && !csdmSpawnCount)
return;
static Float:vecHolder[3];
new sp_index = random_num(0,spawnCount-1);
// get origin for comparisons
vecHolder[0] = spawns[sp_index][0];
vecHolder[1] = spawns[sp_index][1];
vecHolder[2] = spawns[sp_index][2];
// this one is taken
if(!is_hull_vacant(vecHolder,HULL_HUMAN) && spawnCount > 1)
{
// attempt to pick another random one up to three times
new i;
for(i=0;i<3;i++)
{
sp_index = random_num(0,spawnCount-1);
vecHolder[0] = spawns[sp_index][0];
vecHolder[1] = spawns[sp_index][1];
vecHolder[2] = spawns[sp_index][2];
if(is_hull_vacant(vecHolder,HULL_HUMAN)) break;
}
// we made it through the entire loop, no free spaces
if(i == 3)
{
// just find the first available
for(i=sp_index+1;i!=sp_index;i++)
{
// start over when we reach the end
if(i >= spawnCount) i = 0;
vecHolder[0] = spawns[i][0];
vecHolder[1] = spawns[i][1];
vecHolder[2] = spawns[i][2];
// free space! office space!
if(is_hull_vacant(vecHolder,HULL_HUMAN))
{
sp_index = i;
break;
}
}
}
}
// origin
vecHolder[0] = spawns[sp_index][0];
vecHolder[1] = spawns[sp_index][1];
vecHolder[2] = spawns[sp_index][2];
engfunc(EngFunc_SetOrigin,id,vecHolder);
// angles
vecHolder[0] = spawns[sp_index][3];
vecHolder[1] = spawns[sp_index][4];
vecHolder[2] = spawns[sp_index][5];
set_pev(id,pev_angles,vecHolder);
// vangles
vecHolder[0] = spawns[sp_index][6];
vecHolder[1] = spawns[sp_index][7];
vecHolder[2] = spawns[sp_index][8];
set_pev(id,pev_v_angle,vecHolder);
set_pev(id,pev_fixangle,1);
}
// get rid of the spawn protection effects
public remove_spawn_protection(taskid)
{
new id = taskid-TASK_REMOVE_PROTECTION;
spawnProtected[id] = 0;
if(!is_user_connected(id)) return;
if(get_pcvar_num(gg_dm_sp_mode) == 2) fm_set_user_godmode(id,0);
fm_set_rendering(id); // reset back to normal
}