r2233 - in trunk/data: . qcsrc/server

DONOTREPLY at icculus.org DONOTREPLY at icculus.org
Fri Mar 16 04:20:49 EDT 2007


Author: div0
Date: 2007-03-16 04:20:49 -0400 (Fri, 16 Mar 2007)
New Revision: 2233

Modified:
   trunk/data/default.cfg
   trunk/data/qcsrc/server/cl_weaponsystem.qc
   trunk/data/qcsrc/server/clientcommands.qc
   trunk/data/qcsrc/server/g_world.qc
   trunk/data/qcsrc/server/w_crylink.qc
   trunk/data/qcsrc/server/w_electro.qc
   trunk/data/qcsrc/server/w_grenadelauncher.qc
   trunk/data/qcsrc/server/w_hagar.qc
   trunk/data/qcsrc/server/w_laser.qc
   trunk/data/qcsrc/server/w_rocketlauncher.qc
Log:
added: g_projectiles_newton_style
selects different styles of projectile velocity physics:
0 = Quake
1 = Newton
2 = Newton + aimfix
3 = Quake + Newton-like velocity addition (actually not correct, but may have better gameplay)
4 = tZorkian


Modified: trunk/data/default.cfg
===================================================================
--- trunk/data/default.cfg	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/default.cfg	2007-03-16 08:20:49 UTC (rev 2233)
@@ -788,3 +788,11 @@
 seta _alientrap_net_banlist ""
 
 set g_waypoints_for_items 1 // make waypoints out of items; values: 0 = never, 1 = unless the mapper prevents it by worldspawn.spawnflags & 1, 2 = always
+
+set g_projectiles_newton_style 0
+// possible values:
+//   0: absolute velocity projectiles (like Quake)
+//   1: relative velocity projectiles, "Newtonian" (like Tribes 2)
+//   2: relative velocity projectiles, but aim is precorrected so projectiles hit the crosshair (note: strafe rockets then are SLOWER than ones shot while standing; happens in 1 too when aiming correctly which is hard)
+//   3: absolute velocity + player velocity component in shot direction (note: does NOT yield the right relative velocity, but may be good enough)
+//   4: just add the player velocity length to the absolute velocity (tZork's sniper rockets)

Modified: trunk/data/qcsrc/server/cl_weaponsystem.qc
===================================================================
--- trunk/data/qcsrc/server/cl_weaponsystem.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/cl_weaponsystem.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -393,3 +393,81 @@
 	// VorteX: haste can be added here
 };
 
+void(entity missile) W_SetupProjectileVelocity =
+{
+	vector pvelocity;
+	vector mdirection;
+	float mspeed;
+	float outspeed;
+	float nstyle;
+	vector mvelocity;
+	vector outvelocity;
+
+	if(missile.owner == world)
+		error("Unowned missile");
+	pvelocity = missile.owner.velocity;
+	mvelocity = missile.velocity;
+	mdirection = normalize(mvelocity);
+	mspeed = vlen(mvelocity);
+
+	nstyle = cvar("g_projectiles_newton_style");
+	if(nstyle == 0)
+	{
+		// absolute velocity
+		outvelocity = mvelocity;
+	}
+	else if(nstyle == 1)
+	{
+		// true Newtonian projectiles
+		outvelocity = pvelocity + mvelocity;
+	}
+	else if(nstyle == 2)
+	{
+		// true Newtonian projectiles with automatic aim adjustment
+		//
+		// solve: |outspeed * mdirection - pvelocity| = mspeed
+		// outspeed^2 - 2 * outspeed * (mdirection * pvelocity) + pvelocity^2 - mspeed^2 = 0
+		// outspeed = (mdirection * pvelocity) +- sqrt((mdirection * pvelocity)^2 - pvelocity^2 + mspeed^2)
+		// PLUS SIGN!
+		// not defined?
+		// then...
+		// pvelocity^2 - (mdirection * pvelocity)^2 > mspeed^2
+		// velocity without mdirection component > mspeed
+		// fire at smallest possible mspeed that works?
+		// |(mdirection * pvelocity) * pvelocity - pvelocity| = mspeed
+
+		float D;
+		float p;
+		float q;
+		p = mdirection * pvelocity;
+		q = pvelocity * pvelocity - mspeed * mspeed;
+		D = p * p - q;
+		if(D < 0)
+		{
+			dprint("impossible shot, adjusting\n");
+			D = 0;
+		}
+		outspeed = p + sqrt(D);
+		outspeed = bound(mspeed * 0.7, outspeed, mspeed * 5.0);
+		outvelocity = mdirection * outspeed;
+	}
+	else if(nstyle == 3)
+	{
+		// pseudo-Newtonian:
+		outspeed = mspeed + mdirection * pvelocity;
+		outspeed = bound(mspeed * 0.7, outspeed, mspeed * 5.0);
+		outvelocity = mdirection * outspeed;
+	}
+	else if(nstyle == 4)
+	{
+		// tZorkian:
+		outspeed = mspeed + vlen(pvelocity);
+		outvelocity = mdirection * outspeed;
+	}
+	else
+		error("g_projectiles_newton_style must be 0 (absolute), 1 (Newtonian), 2 (Newtonian + aimfix), 3 (pseudo Newtonian) or 4 (tZorkian)!");
+
+	dprint("Adjusted from ", vtos(missile.velocity));
+	missile.velocity = outvelocity;
+	dprint(" to ", vtos(missile.velocity), "\n");
+}

Modified: trunk/data/qcsrc/server/clientcommands.qc
===================================================================
--- trunk/data/qcsrc/server/clientcommands.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/clientcommands.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -79,7 +79,6 @@
 }
 
 void SV_ParseClientCommand(string s) {
-	local float index;
 	local string cmd;
 
 	tokenize(s);

Modified: trunk/data/qcsrc/server/g_world.qc
===================================================================
--- trunk/data/qcsrc/server/g_world.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/g_world.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -3,6 +3,8 @@
 string GetMapname();
 void GotoNextMap();
 void HandleMaplistShuffleCommands();
+void MapVote_Start(float n);
+float MapVote_Think();
 
 void SetDefaultAlpha()
 {
@@ -648,6 +650,29 @@
 	// isn't chosen in the first pass that should have been
 }
 
+float() MapListMethod =
+{
+	float nextMap;
+
+	nextMap = -1;
+
+	if(nextMap == -1)
+		if(cvar("g_maplist_shuffle") > 0)
+			nextMap = MaplistMethod_Shuffle(cvar("g_maplist_shuffle") + 1);
+
+	if(nextMap == -1)
+		if(cvar("g_maplist_selectrandom"))
+			nextMap = MaplistMethod_Random();
+
+	if(nextMap == -1)
+		nextMap = MaplistMethod_Iterate();
+
+	if(nextMap == -1)
+		nextMap = MaplistMethod_Repeat();
+
+	return nextMap;
+}
+
 void() GotoNextMap =
 {
 	//local string nextmap;
@@ -709,40 +734,33 @@
 			return;
 		}
 
-		for(allowReset = 1; allowReset >= 0; --allowReset)
+		if(cvar("g_vote_maps"))
 		{
-			Maplist_Init();
-			nextMap = -1;
+			MapVote_Start(cvar("g_vote_maps"));
+		}
+		else
+		{
+			for(allowReset = 1; allowReset >= 0; --allowReset)
+			{
+				Maplist_Init();
+				nextMap = MapListMethod();
 
-			if(nextMap == -1)
-				if(cvar("g_maplist_shuffle") > 0)
-					nextMap = MaplistMethod_Shuffle(cvar("g_maplist_shuffle") + 1);
-
-			if(nextMap == -1)
-				if(cvar("g_maplist_selectrandom"))
-					nextMap = MaplistMethod_Random();
-
-			if(nextMap == -1)
-				nextMap = MaplistMethod_Iterate();
-
-			if(nextMap == -1)
-				nextMap = MaplistMethod_Repeat();
-
-			if(nextMap >= 0)
-			{
-				Map_Goto(nextMap);
-				break;
-			}
-			else // PERMANENT FAILURE
-			{
-				if(allowReset)
+				if(nextMap >= 0)
 				{
-					bprint( "Maplist contains no single playable map!  Resetting it to default map list.\n" );
-					cvar_set("g_maplist", cvar_string("g_maplist_defaultlist"));
+					Map_Goto(nextMap);
+					break;
 				}
-				else
+				else // PERMANENT FAILURE
 				{
-					error("Everything is broken - not even the default map list works. Please report this to the developers.");
+					if(allowReset)
+					{
+						bprint( "Maplist contains no single playable map!  Resetting it to default map list.\n" );
+						cvar_set("g_maplist", cvar_string("g_maplist_defaultlist"));
+					}
+					else
+					{
+						error("Everything is broken - not even the default map list works. Please report this to the developers.");
+					}
 				}
 			}
 		}
@@ -760,6 +778,9 @@
 .float autoscreenshot;
 void() IntermissionThink =
 {
+	if(MapVote_Think())
+		return;
+
 	if(cvar("sv_autoscreenshot"))
 	if(self.autoscreenshot)
 	if(time > self.autoscreenshot)
@@ -1590,3 +1611,206 @@
 	if(status == WINNING_YES)
 		NextLevel();
 };
+
+float MapVote_starttime;
+float MapVote_nexttime;
+string MapVote_maps[10];
+float MapVote_votes[10];
+float MapVote_nmaps;
+float MapVote_round;
+.float MapVote_selected;
+
+void MapVote_Clear()
+{
+	entity e;
+	for(e = world; (e = findflags(e, flags, FL_CLIENT)) != world; ) if(clienttype(e) == CLIENTTYPE_REAL)
+		e.MapVote_selected = 0;
+}
+
+void MapVote_Start(float n)
+{
+	float m;
+	float i;
+	float j;
+	float k;
+	string ms;
+
+	MapVote_starttime = time;
+
+	Maplist_Init();
+	for(i = 0; i < n; ++i)
+	{
+		for(j = 0; j < 41; ++j)
+		{
+			m = MapListMethod();
+			if(m < 0)
+				goto out;
+			ms = strzone(argv(m));
+			for(k = 0; k < i; ++k)
+			{
+				if(MapVote_maps[k] == ms)
+					goto tryagain;
+			}
+			MapVote_maps[i] = ms;
+			goto next;
+:tryagain
+		}
+		// failed to find a new map in 42 attempts?
+		// give up
+		goto out;
+:next
+	}
+:out
+	MapVote_nmaps = i;
+	MapVote_Clear();
+}
+
+float RandomSelection_value;
+float RandomSelection_prio;
+float RandomSelection_n;
+void RandomSelection_init()
+{
+	RandomSelection_n = 0;
+	RandomSelection_prio = 0;
+}
+void RandomSelection_store(float value, float prio)
+{
+	if(prio > RandomSelection_prio)
+	{
+		RandomSelection_prio = prio;
+		RandomSelection_n = 1;
+		RandomSelection_value = value;
+	}
+	else if(prio == RandomSelection_prio)
+	{
+		RandomSelection_n += 1;
+		if(ceil(random() * RandomSelection_n) == 1)
+			RandomSelection_value = value;
+	}
+}
+
+void MapVote_Decide(float n)
+{
+	localcmd(strcat("exec \"maps/", MapVote_maps[n], ".mapcfg\"\n"));
+}
+
+float MapVote_Update()
+{
+	if(MapVote_nmaps == 0)
+	{
+		error("No maps found.");
+		return 0;
+	}
+	else if(MapVote_nmaps == 1)
+	{
+		MapVote_Decide(0);
+		return 1;
+	}
+	else
+	{
+		// check if we have a winner...
+		float firstPlace;
+		float firstPlaceVotes;
+		float secondPlace;
+		float secondPlaceVotes;
+		float votesTotal;
+		float notVoted;
+		entity e;
+		float i;
+
+		votesTotal = 0;
+		notVoted = 0;
+
+		for(i = 0; i < MapVote_nmaps; ++i)
+			MapVote_votes[i] = 0;
+		for(e = world; (e = findflags(e, flags, FL_CLIENT)) != world; ) if(clienttype(e) == CLIENTTYPE_REAL)
+		{
+			if(e.MapVote_selected == 0)
+			{
+				++notVoted;
+			}
+			else
+			{
+				MapVote_votes[e.MapVote_selected - 1] = MapVote_votes[e.MapVote_selected - 1] + 1;
+				++votesTotal;
+			}
+		}
+
+		RandomSelection_init();
+		for(i = 0; i < MapVote_nmaps; ++i)
+			RandomSelection_store(i, MapVote_votes[i]);
+		firstPlace = RandomSelection_value;
+		firstPlaceVotes = RandomSelection_prio;
+
+		RandomSelection_init();
+		for(i = 0; i < MapVote_nmaps; ++i)
+			if(i != firstPlace)
+				RandomSelection_store(i, MapVote_votes[i]);
+		secondPlace = RandomSelection_value;
+		secondPlaceVotes = RandomSelection_prio;
+
+		// absolute majority?
+		if(2 * firstPlaceVotes >= votesTotal + notVoted)
+		{
+			MapVote_Decide(firstPlace);
+			return 1;
+		}
+
+		if(time > MapVote_starttime + 10)
+			if(MapVote_round == 0)
+			{
+				MapVote_round = 1;
+				if(MapVote_nmaps > 2)
+				{
+					// clear all others
+					for(e = world; (e = findflags(e, flags, FL_CLIENT)) != world; ) if(clienttype(e) == CLIENTTYPE_REAL)
+						if(e.MapVote_selected != firstPlace)
+							if(e.MapVote_selected != secondPlace)
+								e.MapVote_selected = 0;
+					for(i = 0; i < MapVote_nmaps; ++i) if(i != firstPlace) if(i != secondPlace)
+					{
+						strunzone(MapVote_maps[i]);
+						MapVote_maps[i] = "";
+					}
+				}
+			}
+
+		if(time > MapVote_starttime + 15)
+		{
+			// simple majority suffices
+			MapVote_Decide(firstPlace);
+			return 1;
+		}
+
+		return 0;
+	}
+}
+
+void MapVote_Display()
+{
+}
+
+void MapVote_Keypressed(float k)
+{
+	// self pressed k
+}
+
+float MapVote_Think()
+{
+	if(!MapVote_starttime)
+		return 0;
+
+	if(time > MapVote_nexttime)
+	{
+		if(MapVote_Update())
+			return 1;
+		MapVote_nexttime = time + 5;
+	}
+
+	if(self.impulse >= 1 && self.impulse <= 10)
+		MapVote_Keypressed(self.impulse);
+
+	MapVote_Display();
+
+	return 1;
+}

Modified: trunk/data/qcsrc/server/w_crylink.qc
===================================================================
--- trunk/data/qcsrc/server/w_crylink.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/w_crylink.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -96,6 +96,7 @@
 		setorigin (proj, w_shotorg);
 
 		proj.velocity = (w_shotdir + randomvec() * cvar("g_balance_crylink_primary_spread")) * cvar("g_balance_crylink_primary_speed");
+		W_SetupProjectileVelocity(proj);
 		proj.touch = W_Crylink_Touch;
 		proj.think = SUB_Remove;
 		proj.nextthink = time + cvar("g_balance_crylink_primary_lifetime");
@@ -140,6 +141,7 @@
 		setorigin (proj, w_shotorg);
 
 		proj.velocity = (w_shotdir + (((counter + 0.5) / shots) * 2 - 1) * v_right * cvar("g_balance_crylink_secondary_spread")) * cvar("g_balance_crylink_secondary_speed");
+		W_SetupProjectileVelocity(proj);
 		proj.touch = W_Crylink_Touch2;
 		proj.think = SUB_Remove;
 		proj.nextthink = time + cvar("g_balance_crylink_secondary_lifetime");

Modified: trunk/data/qcsrc/server/w_electro.qc
===================================================================
--- trunk/data/qcsrc/server/w_electro.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/w_electro.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -103,6 +103,7 @@
 	proj.effects = EF_BRIGHTFIELD | EF_FULLBRIGHT | EF_NOSHADOW | EF_LOWPRECISION;
 	proj.movetype = MOVETYPE_FLY;
 	proj.velocity = w_shotdir * cvar("g_balance_electro_primary_speed");
+	W_SetupProjectileVelocity(proj);
 	proj.angles = vectoangles(proj.velocity);
 	proj.touch = W_Plasma_TouchExplode;
 	proj.flags = FL_PROJECTILE;
@@ -136,6 +137,7 @@
 	//proj.glow_color = 45;
 	proj.movetype = MOVETYPE_BOUNCE;
 	proj.velocity = v_forward * cvar("g_balance_electro_secondary_speed") + v_up * cvar("g_balance_electro_secondary_speed_up");
+	W_SetupProjectileVelocity(proj);
 	proj.touch = W_Plasma_Touch;
 	setmodel(proj, "models/ebomb.mdl");
 	setsize(proj, '0 0 -3', '0 0 -3');

Modified: trunk/data/qcsrc/server/w_grenadelauncher.qc
===================================================================
--- trunk/data/qcsrc/server/w_grenadelauncher.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/w_grenadelauncher.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -99,6 +99,7 @@
 	gren.think = W_Grenade_Explode;
 	gren.touch = W_Grenade_Touch1;
 	gren.velocity = v_forward * cvar("g_balance_grenadelauncher_primary_speed") + v_up * cvar("g_balance_grenadelauncher_primary_speed_up");
+	W_SetupProjectileVelocity(gren);
 	gren.avelocity_x = random () * -500 - 500;
 
 	gren.angles = vectoangles (gren.velocity);
@@ -133,6 +134,7 @@
 	gren.damageforcescale = 4;
 	gren.event_damage = W_Grenade_Damage;
 	gren.velocity = v_forward * cvar("g_balance_grenadelauncher_secondary_speed") + v_up * cvar("g_balance_grenadelauncher_secondary_speed_up");
+	W_SetupProjectileVelocity(gren);
 	gren.avelocity = '100 150 100';
 
 	gren.angles = vectoangles (gren.velocity);

Modified: trunk/data/qcsrc/server/w_hagar.qc
===================================================================
--- trunk/data/qcsrc/server/w_hagar.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/w_hagar.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -104,6 +104,7 @@
 
 	missile.movetype = MOVETYPE_FLY;
 	missile.velocity = (w_shotdir + randomvec() * cvar("g_balance_hagar_primary_spread")) * cvar("g_balance_hagar_primary_speed");
+	W_SetupProjectileVelocity(missile);
 
 	missile.angles = vectoangles (missile.velocity);
 	missile.flags = FL_PROJECTILE;
@@ -139,6 +140,7 @@
 
 	missile.movetype = MOVETYPE_BOUNCEMISSILE;
 	missile.velocity = (w_shotdir + randomvec() * cvar("g_balance_hagar_secondary_spread")) * cvar("g_balance_hagar_secondary_speed");
+	W_SetupProjectileVelocity(missile);
 	missile.avelocity = '100 10 10';
 
 	missile.angles = vectoangles (missile.velocity);

Modified: trunk/data/qcsrc/server/w_laser.qc
===================================================================
--- trunk/data/qcsrc/server/w_laser.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/w_laser.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -48,6 +48,7 @@
 	setorigin (missile, w_shotorg);
 
 	missile.velocity = w_shotdir * cvar("g_balance_laser_speed");
+	W_SetupProjectileVelocity(missile);
 	missile.angles = vectoangles (missile.velocity);
 	//missile.glow_color = 250; // 244, 250
 	//missile.glow_size = 120;

Modified: trunk/data/qcsrc/server/w_rocketlauncher.qc
===================================================================
--- trunk/data/qcsrc/server/w_rocketlauncher.qc	2007-03-15 17:49:07 UTC (rev 2232)
+++ trunk/data/qcsrc/server/w_rocketlauncher.qc	2007-03-16 08:20:49 UTC (rev 2233)
@@ -210,6 +210,7 @@
 		missile.velocity = w_shotdir * cvar("g_balance_rocketlauncher_laserguided_speed");
 	else
 		missile.velocity = w_shotdir * cvar("g_balance_rocketlauncher_speed");
+	W_SetupProjectileVelocity(missile);
 	missile.angles = vectoangles (missile.velocity);
 
 	missile.touch = W_Rocket_Touch;




More information about the nexuiz-commits mailing list