fix spectating edge cases
This commit is contained in:
		
							parent
							
								
									6933e8bf68
								
							
						
					
					
						commit
						d3372f846a
					
				
							
								
								
									
										176
									
								
								source/client.qc
									
									
									
									
									
								
							
							
						
						
									
										176
									
								
								source/client.qc
									
									
									
									
									
								
							|  | @ -22,28 +22,21 @@ void() SetChangeParms = { | |||
| 	} | ||||
| 
 | ||||
| 	// remove items | ||||
| 	self.items &= ~(IT_KEY1 | IT_KEY2 | IT_INVISIBILITY | IT_INVULNERABILITY | IT_SUIT | IT_QUAD); | ||||
| 	self.items &= ~(IT_KEY1 | IT_KEY2 | IT_INVISIBILITY | IT_INVULNERABILITY | | ||||
| 	                IT_SUIT | IT_QUAD); | ||||
| 
 | ||||
| 	// cap super health | ||||
| 	if(self.health > 100) { | ||||
| 		self.health = 100; | ||||
| 	} | ||||
| 	if(self.health < 50) { | ||||
| 		self.health = 50; | ||||
| 	} | ||||
| 	parm1 = self.items; | ||||
| 	parm2 = self.health; | ||||
| 	parm3 = self.armorvalue; | ||||
| 	if(self.ammo_shells < 25) { | ||||
| 		parm4 = 25; | ||||
| 	} else { | ||||
| 		parm4 = self.ammo_shells; | ||||
| 	} | ||||
| 	parm5 = self.ammo_nails; | ||||
| 	parm6 = self.ammo_rockets; | ||||
| 	parm7 = self.ammo_cells; | ||||
| 	parm8 = self.weapon; | ||||
| 	parm9 = self.armortype * 100; | ||||
| 	self.health = minmax(self.health, 50, 100); | ||||
| 
 | ||||
| 	parm1  = self.items; | ||||
| 	parm2  = self.health; | ||||
| 	parm3  = self.armorvalue; | ||||
| 	parm4  = (self.ammo_shells < 25 ? 25 : self.ammo_shells); | ||||
| 	parm5  = self.ammo_nails; | ||||
| 	parm6  = self.ammo_rockets; | ||||
| 	parm7  = self.ammo_cells; | ||||
| 	parm8  = self.weapon; | ||||
| 	parm9  = self.armortype * 100; | ||||
| 	parm10 = self.pronoun; | ||||
| }; | ||||
| 
 | ||||
|  | @ -66,16 +59,16 @@ void() DecodeLevelParms = { | |||
| 		} | ||||
| 	} | ||||
| 
 | ||||
| 	self.items = parm1; | ||||
| 	self.health = parm2; | ||||
| 	self.armorvalue = parm3; | ||||
| 	self.ammo_shells = parm4; | ||||
| 	self.ammo_nails = parm5; | ||||
| 	self.items        = parm1; | ||||
| 	self.health       = parm2; | ||||
| 	self.armorvalue   = parm3; | ||||
| 	self.ammo_shells  = parm4; | ||||
| 	self.ammo_nails   = parm5; | ||||
| 	self.ammo_rockets = parm6; | ||||
| 	self.ammo_cells = parm7; | ||||
| 	self.weapon = parm8; | ||||
| 	self.armortype = parm9 * 0.01; | ||||
| 	self.pronoun = parm10; | ||||
| 	self.ammo_cells   = parm7; | ||||
| 	self.weapon       = parm8; | ||||
| 	self.armortype    = parm9 * 0.01; | ||||
| 	self.pronoun      = parm10; | ||||
| }; | ||||
| 
 | ||||
| /* | ||||
|  | @ -231,14 +224,15 @@ void() execute_changelevel = { | |||
| 
 | ||||
| 	other = find(world, classname, "player"); | ||||
| 	while(other != world) { | ||||
| 		other.view_ofs = VEC_ORIGIN; | ||||
| 		other.angles = other.v_angle = pos.mangle; | ||||
| 		other.fixangle = TRUE; // turn this way immediately | ||||
| 		other.nextthink = time + 0.5; | ||||
| 		other.view_ofs   = VEC_ORIGIN; | ||||
| 		other.angles     = other.v_angle = pos.mangle; | ||||
| 		other.fixangle   = TRUE; // turn this way immediately | ||||
| 		other.nextthink  = time + 0.5; | ||||
| 		other.takedamage = DAMAGE_NO; | ||||
| 		other.solid = SOLID_NOT; | ||||
| 		other.movetype = MOVETYPE_NONE; | ||||
| 		other.solid      = SOLID_NOT; | ||||
| 		other.movetype   = MOVETYPE_NONE; | ||||
| 		other.modelindex = 0; | ||||
| 		other.spectating = SPECTATING_INTERMISSION; | ||||
| 		setorigin(other, pos.origin); | ||||
| 		other = find(other, classname, "player"); | ||||
| 	} | ||||
|  | @ -295,7 +289,7 @@ void() trigger_changelevel = { | |||
| /* | ||||
| ============================================================================= | ||||
| 
 | ||||
| 				PLAYER GAME EDGE FUNCTIONS | ||||
| PLAYER GAME EDGE FUNCTIONS | ||||
| 
 | ||||
| ============================================================================= | ||||
| */ | ||||
|  | @ -304,6 +298,7 @@ void() become_spectator = { | |||
| 	float not_dead; | ||||
| 	entity pl; | ||||
| 
 | ||||
| 	self.spectating   = (self.lives ? SPECTATING_SPECTATING : SPECTATING_DEAD); | ||||
| 	self.health       = self.max_health; | ||||
| 	self.armortype    = 0; | ||||
| 	self.armorvalue   = 0; | ||||
|  | @ -455,7 +450,7 @@ void() PutClientInServer = { | |||
| 			} else { | ||||
| 				bprint(ftos(self.lives), " lives left\n"); | ||||
| 			} | ||||
| 		} else { | ||||
| 		} else if(self.lives == 0) { | ||||
| 			self.lives = sf_lives; | ||||
| 			dprint("lives reset to ", ftos(sf_lives), "\n"); | ||||
| 		} | ||||
|  | @ -465,22 +460,23 @@ void() PutClientInServer = { | |||
| 
 | ||||
| 	spot = SelectSpawnPoint(); | ||||
| 
 | ||||
| 	self.classname = "player"; | ||||
| 	self.health = 100; | ||||
| 	self.takedamage = DAMAGE_AIM; | ||||
| 	self.solid = SOLID_SLIDEBOX; | ||||
| 	self.movetype = MOVETYPE_WALK; | ||||
| 	self.show_hostile = 0; | ||||
| 	self.max_health = 100; | ||||
| 	self.flags = FL_CLIENT; | ||||
| 	self.air_finished = time + 12; | ||||
| 	self.dmg = 2; // initial water damage | ||||
| 	self.classname             = "player"; | ||||
| 	self.health                = 100; | ||||
| 	self.takedamage            = DAMAGE_AIM; | ||||
| 	self.solid                 = SOLID_SLIDEBOX; | ||||
| 	self.movetype              = MOVETYPE_WALK; | ||||
| 	self.show_hostile          = 0; | ||||
| 	self.max_health            = 100; | ||||
| 	self.flags                 = FL_CLIENT; | ||||
| 	self.air_finished          = time + 12; | ||||
| 	self.dmg                   = 2; // initial water damage | ||||
| 	self.super_damage_finished = 0; | ||||
| 	self.radsuit_finished = 0; | ||||
| 	self.invisible_finished = 0; | ||||
| 	self.invincible_finished = 0; | ||||
| 	self.effects = 0; | ||||
| 	self.invincible_time = 0; | ||||
| 	self.radsuit_finished      = 0; | ||||
| 	self.invisible_finished    = 0; | ||||
| 	self.invincible_finished   = 0; | ||||
| 	self.effects               = 0; | ||||
| 	self.invincible_time       = 0; | ||||
| 	self.spectating            = SPECTATING_NOT; | ||||
| 
 | ||||
| 	DecodeLevelParms(); | ||||
| 
 | ||||
|  | @ -524,7 +520,7 @@ void() PutClientInServer = { | |||
| /* | ||||
| ============================================================================= | ||||
| 
 | ||||
| 				QUAKED FUNCTIONS | ||||
| QUAKED FUNCTIONS | ||||
| 
 | ||||
| ============================================================================= | ||||
| */ | ||||
|  | @ -620,8 +616,7 @@ Exit deathmatch games upon conditions | |||
| ============ | ||||
| */ | ||||
| void() CheckRules = { | ||||
| 	float timelimit; | ||||
| 	float fraglimit; | ||||
| 	float timelimit, fraglimit; | ||||
| 
 | ||||
| 	if(gameover) { // someone else quit the game already | ||||
| 		return; | ||||
|  | @ -630,12 +625,8 @@ void() CheckRules = { | |||
| 	timelimit = cvar("timelimit") * 60; | ||||
| 	fraglimit = cvar("fraglimit"); | ||||
| 
 | ||||
| 	if(timelimit && time >= timelimit) { | ||||
| 		NextLevel(); | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	if(fraglimit && self.frags >= fraglimit) { | ||||
| 	if((timelimit && time >= timelimit) || | ||||
| 	   (fraglimit && self.frags >= fraglimit)) { | ||||
| 		NextLevel(); | ||||
| 		return; | ||||
| 	} | ||||
|  | @ -707,17 +698,12 @@ void() PlayerJump = { | |||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	if(!(self.flags & FL_ONGROUND)) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	if(!(self.flags & FL_JUMPRELEASED)) { | ||||
| 	if(!(self.flags & FL_ONGROUND) || !(self.flags & FL_JUMPRELEASED)) { | ||||
| 		return; // don't pogo stick | ||||
| 	} | ||||
| 
 | ||||
| 	self.flags = self.flags - (self.flags & FL_JUMPRELEASED); | ||||
| 
 | ||||
| 	self.flags = self.flags - FL_ONGROUND; // don't stairwalk | ||||
| 	self.flags -= (self.flags & FL_JUMPRELEASED); | ||||
| 	self.flags -= FL_ONGROUND; // don't stairwalk | ||||
| 
 | ||||
| 	self.button2 = 0; | ||||
| 	// player jumping sound | ||||
|  | @ -732,11 +718,7 @@ WaterMove | |||
| ============ | ||||
| */ | ||||
| void() WaterMove = { | ||||
| 	//dprint(ftos(self.waterlevel)); | ||||
| 	if(self.movetype == MOVETYPE_NOCLIP) { | ||||
| 		return; | ||||
| 	} | ||||
| 	if(self.health < 0) { | ||||
| 	if(self.movetype == MOVETYPE_NOCLIP || self.health < 0) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
|  | @ -843,13 +825,12 @@ Called every frame before physics are run | |||
| ================ | ||||
| */ | ||||
| void() PlayerPreThink = { | ||||
| 	// otherwise a button could be missed between the think tics | ||||
| 	if(intermission_running) { | ||||
| 		IntermissionThink(); // otherwise a button could be missed between | ||||
| 		return; // the think tics | ||||
| 	} | ||||
| 
 | ||||
| 	if(self.view_ofs == VEC_ORIGIN) { | ||||
| 		return; // intermission, finale or spectating | ||||
| 		IntermissionThink(); | ||||
| 		return; | ||||
| 	} else if(self.spectating) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	makevectors(self.v_angle); // is this still used | ||||
|  | @ -895,7 +876,7 @@ Check for turning off powerups | |||
| ================ | ||||
| */ | ||||
| void() CheckPowerups = { | ||||
| 	if(self.health <= 0) { | ||||
| 	if(self.health <= 0 || self.spectating) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
|  | @ -1020,16 +1001,18 @@ Called every frame after physics are run | |||
| ================ | ||||
| */ | ||||
| void() PlayerPostThink = { | ||||
| 	if(self.view_ofs == VEC_ORIGIN) { | ||||
| 		return; // intermission, finale or spectating | ||||
| 	if(time >= self.attack_finished) { | ||||
| 		ImpulseCommands(); | ||||
| 	} | ||||
| 	if(self.deadflag) { | ||||
| 
 | ||||
| 	if(self.spectating || self.deadflag) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	// do weapon stuff | ||||
| 
 | ||||
| 	W_WeaponFrame(); | ||||
| 	if(time >= self.attack_finished) { | ||||
| 		W_WeaponFrame(); | ||||
| 	} | ||||
| 
 | ||||
| 	// check to see if player landed and play landing sound | ||||
| 	if(self.jump_flag < -300 && self.flags & FL_ONGROUND && self.health > 0) { | ||||
|  | @ -1076,20 +1059,23 @@ called when a player disconnects from a server | |||
| ============ | ||||
| */ | ||||
| void() ClientDisconnect = { | ||||
| 	// if the level end trigger has been activated, just return | ||||
| 	// since they aren't *really* leaving | ||||
| 	if(gameover) { | ||||
| 		return; | ||||
| 	} | ||||
| 	// if the level end trigger has been activated, just return | ||||
| 	// since they aren't *really* leaving | ||||
| 
 | ||||
| 	// let everyone else know | ||||
| 	bprint(self.netname, " left the game with ", ftos(self.frags), " frags\n"); | ||||
| 	sound(self, CHAN_BODY, "player/tornoff2.wav", 1, ATTN_NONE); | ||||
| 	set_suicide_frame(); | ||||
| 
 | ||||
| 	if(!self.spectating) { | ||||
| 		sound(self, CHAN_BODY, "player/tornoff2.wav", 1, ATTN_NONE); | ||||
| 		set_suicide_frame(); | ||||
| 	} | ||||
| }; | ||||
| 
 | ||||
| void() cheat = { | ||||
| 	if((deathmatch || coop) && !sf_cheats) { | ||||
| 	if(((deathmatch || coop) && !sf_cheats) || self.spectating) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
|  | @ -1114,13 +1100,13 @@ void() cheat = { | |||
| }; | ||||
| 
 | ||||
| void() cheat_quad = { | ||||
| 	if((deathmatch || coop) && !sf_cheats) { | ||||
| 	if(((deathmatch || coop) && !sf_cheats) || self.spectating) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	self.super_time = 1; | ||||
| 	self.super_time            = 1; | ||||
| 	self.super_damage_finished = time + 30; | ||||
| 	self.items = self.items | IT_QUAD; | ||||
| 	self.items                 = self.items | IT_QUAD; | ||||
| }; | ||||
| 
 | ||||
| string(float pro) pronoun_subject = { | ||||
|  | @ -1545,7 +1531,7 @@ Player entered the suicide command | |||
| ============ | ||||
| */ | ||||
| void() ClientKill = { | ||||
| 	if(self.view_ofs != VEC_ORIGIN) { | ||||
| 	if(!self.spectating) { | ||||
| 		reset_death_vel(); | ||||
| 		self.frags--; // extra penalty | ||||
| 		ClientObituary(self, self); | ||||
|  |  | |||
|  | @ -485,22 +485,6 @@ enum { | |||
| 	WORLD_BASE, | ||||
| }; | ||||
| 
 | ||||
| enum { | ||||
| 	PRO_NONE, | ||||
| 
 | ||||
| 	// alphabetically sorted, based on pronoun.is and what i've seen used | ||||
| 	PRO_FAE, | ||||
| 	PRO_HE, | ||||
| 	PRO_IT, | ||||
| 	PRO_SHE, | ||||
| 	PRO_THEY, | ||||
| 	PRO_XEY, | ||||
| 	PRO_ZE_H, | ||||
| 	PRO_ZE_Z, | ||||
| 
 | ||||
| 	PRO_MAX, | ||||
| }; | ||||
| 
 | ||||
| enum { | ||||
| 	DOOR_START_OPEN = 1, | ||||
| 	DOOR_DONT_LINK = 4, | ||||
|  | @ -574,6 +558,23 @@ enum { | |||
| 	SIGIL_4 = 8, | ||||
| }; | ||||
| 
 | ||||
| // super co-op additions | ||||
| enum { | ||||
| 	PRO_NONE, | ||||
| 
 | ||||
| 	// alphabetically sorted, based on pronoun.is and what i've seen used | ||||
| 	PRO_FAE, | ||||
| 	PRO_HE, | ||||
| 	PRO_IT, | ||||
| 	PRO_SHE, | ||||
| 	PRO_THEY, | ||||
| 	PRO_XEY, | ||||
| 	PRO_ZE_H, | ||||
| 	PRO_ZE_Z, | ||||
| 
 | ||||
| 	PRO_MAX, | ||||
| }; | ||||
| 
 | ||||
| enum { | ||||
| 	SF_CHEATS    = 1, | ||||
| 	SF_LIVES_BEG = 1, | ||||
|  | @ -581,6 +582,14 @@ enum { | |||
| 	SF_LIVES_MSK = 14, | ||||
| 	SF_DIST_AMMO = 16, | ||||
| }; | ||||
| 
 | ||||
| enum { | ||||
| 	SPECTATING_NOT, | ||||
| 	SPECTATING_DEAD, | ||||
| 	SPECTATING_SPECTATING, | ||||
| 	SPECTATING_INTERMISSION, | ||||
| 	SPECTATING_FINALE, | ||||
| }; | ||||
| #pragma noref 0 | ||||
| 
 | ||||
| // globals -------------------------------------------------------------------| | ||||
|  | @ -753,6 +762,7 @@ float ext_con_set; | |||
| // super co-op additions | ||||
| .float pronoun; | ||||
| .float lives; | ||||
| .float spectating; | ||||
| 
 | ||||
| // functions -----------------------------------------------------------------| | ||||
| 
 | ||||
|  | @ -921,4 +931,6 @@ void() func_train_find; | |||
| 
 | ||||
| void(vector p) boss_missile; | ||||
| 
 | ||||
| void() ImpulseCommands; | ||||
| 
 | ||||
| // EOF | ||||
|  |  | |||
|  | @ -116,15 +116,16 @@ void() finale_1 = { | |||
| 
 | ||||
| 	pl = find(world, classname, "player"); | ||||
| 	while(pl != world) { | ||||
| 		pl.view_ofs = VEC_ORIGIN; | ||||
| 		pl.angles = other.v_angle = pos.mangle; | ||||
| 		pl.fixangle = TRUE; // turn this way immediately | ||||
| 		pl.map = self.map; | ||||
| 		pl.nextthink = time + 0.5; | ||||
| 		pl.view_ofs   = VEC_ORIGIN; | ||||
| 		pl.angles     = other.v_angle = pos.mangle; | ||||
| 		pl.fixangle   = TRUE; // turn this way immediately | ||||
| 		pl.map        = self.map; | ||||
| 		pl.nextthink  = time + 0.5; | ||||
| 		pl.takedamage = DAMAGE_NO; | ||||
| 		pl.solid = SOLID_NOT; | ||||
| 		pl.movetype = MOVETYPE_NONE; | ||||
| 		pl.solid      = SOLID_NOT; | ||||
| 		pl.movetype   = MOVETYPE_NONE; | ||||
| 		pl.modelindex = 0; | ||||
| 		pl.spectating = SPECTATING_FINALE; | ||||
| 		setorigin(pl, pos.origin); | ||||
| 		pl = find(pl, classname, "player"); | ||||
| 	} | ||||
|  |  | |||
|  | @ -1051,12 +1051,6 @@ Called every frame so impulse events can be handled as well as possible | |||
| ============ | ||||
| */ | ||||
| void() W_WeaponFrame = { | ||||
| 	if(time < self.attack_finished) { | ||||
| 		return; | ||||
| 	} | ||||
| 
 | ||||
| 	ImpulseCommands(); | ||||
| 
 | ||||
| 	// check for attack | ||||
| 	if(self.button0) { | ||||
| 		SuperDamageSound(); | ||||
|  |  | |||
		Loading…
	
		Reference in New Issue
	
	Block a user