/**/
PlayerParachute()
{
	level endon("ex_gameover");
	self endon("disconnect");

	if(level.ex_parachutes == 2 && level.ex_roundbased && game["roundnumber"] > 0) return;

	// If player has already parachuted and parachutes is set to parachute only once per map/round
	if(isDefined(self.pers["ex_haveparachuted"]))
		return;

	// If parachutes is set for attackers only then check for attacker self team
	if(level.ex_parachutesonlyattackers == 1 && game["attackers"] != self.pers["team"])
		return;

	self.ex_isparachuting = undefined;
	self.landed = false;

	// Starting point for player
	ix = self.origin[0] - 150 + randomint(300);
	iy = self.origin[1] - 150 + randomint(300);

	// Calculate starting altitude
	if(level.ex_planes_altitude) iz = level.ex_planes_altitude - randomint(100);
		else iz = 6000 - randomint(100);

	// Endpoint for player is 24 units above spawn point (origin)
	endpoint = self.origin + ( 0, 0, 24); // I use a low value here to avoid getting stuck

	// Check how high the path is clear
	trace = bulletTrace(endpoint, (endpoint + (0,0,iz)), false, undefined);
	pos = trace["position"];
	iz = pos[2];

	// Limit the altitude
	if(level.ex_parachuteslimitaltitude)
	{
		if((iz-endpoint[2]) > level.ex_parachuteslimitaltitude)
			iz=endpoint[2] + level.ex_parachuteslimitaltitude - randomint(100);
	}

	// Starting point ready
	startpoint = ( ix, iy, iz);

	// Calculate distance between start and end
	distance = distance(startpoint, endpoint);

	// Don't parachute distances below 350 units (3.5 seconds)
	if(distance < 350)
		return;

	// Now we are clear to parachute
	self.ex_isparachuting = true;

	if(level.ex_parachutes == 1 || level.ex_parachutes == 2)
		self.pers["ex_haveparachuted"] = true;

	//create a model to attach everything to
	self.parachute = spawn ("script_model",(0,0,0));
	if(level.ex_spwn_time && level.ex_spwn_invisible && isDefined(self.ex_spawnprotected)) self.parachute hide();
	self.parachute setModel("xmodel/am_fallschirm");
	self.parachute.origin = self.origin;
	self.parachute.angles = self.angles + (0,0,90);

	// Link player to self.anchor
	self.anchor = spawn("script_model", (0,0,0));
	self.anchor.origin = self.parachute.origin;
	self.anchor.angles = self.angles;
	self.parachute linkto(self.anchor);
	self linkto(self.anchor);
	falltime = distance/100 + randomint(6);
	self.anchor.origin = startpoint;
	self.anchor moveto(endpoint, falltime);

	// Disable weapon & make player invulnerable
	if(level.ex_parachutesprotection)
	{
		if(level.ex_parachutesprotection == 1) self disableweapon();
		self.ex_invulnerable = true;
	}

	self playLocalSound ("para_plane");
	self.anchor playLoopSound ("para_wind");

	while(isPlayer(self) && isAlive(self) && self.anchor.origin[2] > endpoint[2])
	{
		self setClientCvar("cl_stance", "0");
		self.anchor.angles = self.angles;
		if(level.ex_spwn_time && level.ex_spwn_invisible && !isDefined(self.ex_spawnprotected)) self.parachute show();
		wait .1;
	}

	if(isPlayer(self) && isalive(self))
	{
		self unlink();
		self playSound("para_land");
		earthquake(0.4, 1.2, self.origin, 70);

		self.anchor stopLoopSound();

		if(level.ex_parachutesprotection)
		{
			if(level.ex_parachutesprotection == 1) self enableweapon();
			if(!isDefined(self.ex_spawnprotected)) self.ex_invulnerable = false;
		}

		self.ex_isparachuting = undefined;
	}

	if(isDefined(self))
	{
		self unlink();
		if(isdefined(self.dbody)) self.dbody delete();
	}

	// Parachute clean up
	chute = spawn("script_model", (0,0,0));
	if(level.ex_spwn_time && level.ex_spwn_invisible && isDefined(self.ex_spawnprotected)) chute hide();
	chute setModel("xmodel/am_fallschirm");
	chute.origin = self.parachute.origin;
	chute.angles = self.parachute.angles;
	self.parachute delete();
	self.anchor delete();
	chute rotatepitch(85,10,9,1);
	chute moveto(endpoint - (0,400,400), 7,6,1);
	wait 5;
	chute delete();
}
