From: vortex <vortex@d7cf8633-e32d-0410-b094-e92efae38249>
Date: Thu, 8 Dec 2011 23:22:00 +0000 (+0000)
Subject: ODE: experimental 'erp' field for per-entity control of Error Restitution (was only... 
X-Git-Tag: xonotic-v0.6.0~102^2~15
X-Git-Url: https://git.rm.cloudns.org/?a=commitdiff_plain;h=f052f75917ec06f67495b941f5faa4a315fa09fa;p=xonotic%2Fdarkplaces.git

ODE: experimental 'erp' field for per-entity control of Error Restitution (was only controlled globally by cvar). For more sharp collisions it helps to set high ERP for small objects and low or 0 on big ones (as high ERP on large and high-mass objects tends to explode pretty badly).

git-svn-id: svn://svn.icculus.org/twilight/trunk/darkplaces@11604 d7cf8633-e32d-0410-b094-e92efae38249
---

diff --git a/prvm_offsets.h b/prvm_offsets.h
index 639240ea..d194b1fd 100644
--- a/prvm_offsets.h
+++ b/prvm_offsets.h
@@ -31,6 +31,7 @@ PRVM_DECLARE_clientfieldfloat(lerpfrac4)
 PRVM_DECLARE_clientfieldfloat(mass)
 PRVM_DECLARE_clientfieldvector(massofs)
 PRVM_DECLARE_clientfieldfloat(friction)
+PRVM_DECLARE_clientfieldfloat(erp)
 PRVM_DECLARE_clientfieldfloat(modelindex)
 PRVM_DECLARE_clientfieldfloat(movetype)
 PRVM_DECLARE_clientfieldfloat(nextthink)
@@ -311,6 +312,7 @@ PRVM_DECLARE_field(ltime)
 PRVM_DECLARE_field(mass)
 PRVM_DECLARE_field(massofs)
 PRVM_DECLARE_field(friction)
+PRVM_DECLARE_field(erp)
 PRVM_DECLARE_field(max_health)
 PRVM_DECLARE_field(maxs)
 PRVM_DECLARE_field(message)
@@ -670,6 +672,7 @@ PRVM_DECLARE_serverfieldfloat(ltime)
 PRVM_DECLARE_serverfieldfloat(mass)
 PRVM_DECLARE_serverfieldvector(massofs)
 PRVM_DECLARE_serverfieldfloat(friction)
+PRVM_DECLARE_serverfieldfloat(erp)
 PRVM_DECLARE_serverfieldfloat(max_health)
 PRVM_DECLARE_serverfieldfloat(modelflags)
 PRVM_DECLARE_serverfieldfloat(modelindex)
diff --git a/world.c b/world.c
index 5e145119..fa1ccbc7 100644
--- a/world.c
+++ b/world.c
@@ -2527,6 +2527,7 @@ static void nearCallback (void *data, dGeomID o1, dGeomID o2)
 	float bouncestop1 = 60.0f / 800.0f;
 	float bouncefactor2 = 0.0f;
 	float bouncestop2 = 60.0f / 800.0f;
+	float erp;
 	dVector3 grav;
 	prvm_edict_t *ed1, *ed2;
 
@@ -2606,6 +2607,10 @@ static void nearCallback (void *data, dGeomID o1, dGeomID o2)
 	dWorldGetGravity((dWorldID)world->physics.ode_world, grav);
 	bouncestop1 *= fabs(grav[2]);
 
+	// get erp
+	// select object that moves faster ang get it's erp
+	erp = (VectorLength2(PRVM_gameedictvector(ed1, velocity)) > VectorLength2(PRVM_gameedictvector(ed2, velocity))) ? PRVM_gameedictfloat(ed1, erp) : PRVM_gameedictfloat(ed2, erp);
+
 	// generate contact points between the two non-space geoms
 	numcontacts = dCollide(o1, o2, MAX_CONTACTS, &(contact[0].geom), sizeof(contact[0]));
 	// add these contact points to the simulation
@@ -2613,7 +2618,7 @@ static void nearCallback (void *data, dGeomID o1, dGeomID o2)
 	{
 		contact[i].surface.mode = (physics_ode_contact_mu.value != -1 ? dContactApprox1 : 0) | (physics_ode_contact_erp.value != -1 ? dContactSoftERP : 0) | (physics_ode_contact_cfm.value != -1 ? dContactSoftCFM : 0) | (bouncefactor1 > 0 ? dContactBounce : 0);
 		contact[i].surface.mu = physics_ode_contact_mu.value * ed1->priv.server->ode_friction * ed2->priv.server->ode_friction;
-		contact[i].surface.soft_erp = physics_ode_contact_erp.value;
+		contact[i].surface.soft_erp = physics_ode_contact_erp.value + erp;
 		contact[i].surface.soft_cfm = physics_ode_contact_cfm.value;
 		contact[i].surface.bounce = bouncefactor1;
 		contact[i].surface.bounce_vel = bouncestop1;