aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs
diff options
context:
space:
mode:
authorRobert Adams2013-04-23 18:31:12 -0700
committerRobert Adams2013-04-23 18:31:12 -0700
commit522ab85045066cb58bb76881032adab7cc6a2d68 (patch)
treeed9343f819b4c4e08adafdc44c2fbbfdd33e41fe /OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs
parentrevert CSJ2K.dll to version in use prior to commit d4fa2c69ed2895dcab76e0df1b... (diff)
downloadopensim-SC_OLD-522ab85045066cb58bb76881032adab7cc6a2d68.zip
opensim-SC_OLD-522ab85045066cb58bb76881032adab7cc6a2d68.tar.gz
opensim-SC_OLD-522ab85045066cb58bb76881032adab7cc6a2d68.tar.bz2
opensim-SC_OLD-522ab85045066cb58bb76881032adab7cc6a2d68.tar.xz
BulletSim: improve avatar stair walking up. Add more parameters to control force
of both position change and up force that move avatars over barrier. Default parameters are for steps up to 0.5m in height.
Diffstat (limited to 'OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs')
-rwxr-xr-xOpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs103
1 files changed, 85 insertions, 18 deletions
diff --git a/OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs b/OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs
index 8416740..bd5ee0b1 100755
--- a/OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs
+++ b/OpenSim/Region/Physics/BulletSPlugin/BSActorAvatarMove.cs
@@ -40,10 +40,16 @@ public class BSActorAvatarMove : BSActor
40{ 40{
41 BSVMotor m_velocityMotor; 41 BSVMotor m_velocityMotor;
42 42
43 // Set to true if we think we're going up stairs.
44 // This state is remembered because collisions will turn on and off as we go up stairs.
45 int m_walkingUpStairs;
46 float m_lastStepUp;
47
43 public BSActorAvatarMove(BSScene physicsScene, BSPhysObject pObj, string actorName) 48 public BSActorAvatarMove(BSScene physicsScene, BSPhysObject pObj, string actorName)
44 : base(physicsScene, pObj, actorName) 49 : base(physicsScene, pObj, actorName)
45 { 50 {
46 m_velocityMotor = null; 51 m_velocityMotor = null;
52 m_walkingUpStairs = 0;
47 m_physicsScene.DetailLog("{0},BSActorAvatarMove,constructor", m_controllingPrim.LocalID); 53 m_physicsScene.DetailLog("{0},BSActorAvatarMove,constructor", m_controllingPrim.LocalID);
48 } 54 }
49 55
@@ -119,6 +125,8 @@ public class BSActorAvatarMove : BSActor
119 SetVelocityAndTarget(m_controllingPrim.RawVelocity, m_controllingPrim.TargetVelocity, true /* inTaintTime */); 125 SetVelocityAndTarget(m_controllingPrim.RawVelocity, m_controllingPrim.TargetVelocity, true /* inTaintTime */);
120 126
121 m_physicsScene.BeforeStep += Mover; 127 m_physicsScene.BeforeStep += Mover;
128
129 m_walkingUpStairs = 0;
122 } 130 }
123 } 131 }
124 132
@@ -216,8 +224,6 @@ public class BSActorAvatarMove : BSActor
216 // 'stepVelocity' is now the speed we'd like the avatar to move in. Turn that into an instantanous force. 224 // 'stepVelocity' is now the speed we'd like the avatar to move in. Turn that into an instantanous force.
217 OMV.Vector3 moveForce = (stepVelocity - m_controllingPrim.RawVelocity) * m_controllingPrim.Mass; 225 OMV.Vector3 moveForce = (stepVelocity - m_controllingPrim.RawVelocity) * m_controllingPrim.Mass;
218 226
219 // Should we check for move force being small and forcing velocity to zero?
220
221 // Add special movement force to allow avatars to walk up stepped surfaces. 227 // Add special movement force to allow avatars to walk up stepped surfaces.
222 moveForce += WalkUpStairs(); 228 moveForce += WalkUpStairs();
223 229
@@ -233,24 +239,33 @@ public class BSActorAvatarMove : BSActor
233 { 239 {
234 OMV.Vector3 ret = OMV.Vector3.Zero; 240 OMV.Vector3 ret = OMV.Vector3.Zero;
235 241
242 m_physicsScene.DetailLog("{0},BSCharacter.WalkUpStairs,IsColliding={1},flying={2},targSpeed={3},collisions={4},avHeight={5}",
243 m_controllingPrim.LocalID, m_controllingPrim.IsColliding, m_controllingPrim.Flying,
244 m_controllingPrim.TargetVelocitySpeed, m_controllingPrim.CollisionsLastTick.Count, m_controllingPrim.Size.Z);
236 // This test is done if moving forward, not flying and is colliding with something. 245 // This test is done if moving forward, not flying and is colliding with something.
237 // DetailLog("{0},BSCharacter.WalkUpStairs,IsColliding={1},flying={2},targSpeed={3},collisions={4}", 246 // Check for stairs climbing if colliding, not flying and moving forward
238 // LocalID, IsColliding, Flying, TargetSpeed, CollisionsLastTick.Count); 247 if ( m_controllingPrim.IsColliding
239 if (m_controllingPrim.IsColliding && !m_controllingPrim.Flying && m_controllingPrim.TargetVelocitySpeed > 0.1f /* && ForwardSpeed < 0.1f */) 248 && !m_controllingPrim.Flying
249 && m_controllingPrim.TargetVelocitySpeed > 0.1f )
240 { 250 {
241 // The range near the character's feet where we will consider stairs 251 // The range near the character's feet where we will consider stairs
242 float nearFeetHeightMin = m_controllingPrim.RawPosition.Z - (m_controllingPrim.Size.Z / 2f) + 0.05f; 252 // float nearFeetHeightMin = m_controllingPrim.RawPosition.Z - (m_controllingPrim.Size.Z / 2f) + 0.05f;
253 // Note: there is a problem with the computation of the capsule height. Thus RawPosition is off
254 // from the height. Revisit size and this computation when height is scaled properly.
255 float nearFeetHeightMin = m_controllingPrim.RawPosition.Z - (m_controllingPrim.Size.Z / 2f) - 0.05f;
243 float nearFeetHeightMax = nearFeetHeightMin + BSParam.AvatarStepHeight; 256 float nearFeetHeightMax = nearFeetHeightMin + BSParam.AvatarStepHeight;
244 257
245 // Look for a collision point that is near the character's feet and is oriented the same as the charactor is 258 // Look for a collision point that is near the character's feet and is oriented the same as the charactor is.
259 // Find the highest 'good' collision.
260 OMV.Vector3 highestTouchPosition = OMV.Vector3.Zero;
246 foreach (KeyValuePair<uint, ContactPoint> kvp in m_controllingPrim.CollisionsLastTick.m_objCollisionList) 261 foreach (KeyValuePair<uint, ContactPoint> kvp in m_controllingPrim.CollisionsLastTick.m_objCollisionList)
247 { 262 {
248 // Don't care about collisions with the terrain 263 // Don't care about collisions with the terrain
249 if (kvp.Key > m_physicsScene.TerrainManager.HighestTerrainID) 264 if (kvp.Key > m_physicsScene.TerrainManager.HighestTerrainID)
250 { 265 {
251 OMV.Vector3 touchPosition = kvp.Value.Position; 266 OMV.Vector3 touchPosition = kvp.Value.Position;
252 // DetailLog("{0},BSCharacter.WalkUpStairs,min={1},max={2},touch={3}", 267 m_physicsScene.DetailLog("{0},BSCharacter.WalkUpStairs,min={1},max={2},touch={3}",
253 // LocalID, nearFeetHeightMin, nearFeetHeightMax, touchPosition); 268 m_controllingPrim.LocalID, nearFeetHeightMin, nearFeetHeightMax, touchPosition);
254 if (touchPosition.Z >= nearFeetHeightMin && touchPosition.Z <= nearFeetHeightMax) 269 if (touchPosition.Z >= nearFeetHeightMin && touchPosition.Z <= nearFeetHeightMax)
255 { 270 {
256 // This contact is within the 'near the feet' range. 271 // This contact is within the 'near the feet' range.
@@ -261,24 +276,76 @@ public class BSActorAvatarMove : BSActor
261 float diff = Math.Abs(OMV.Vector3.Distance(directionFacing, touchNormal)); 276 float diff = Math.Abs(OMV.Vector3.Distance(directionFacing, touchNormal));
262 if (diff < BSParam.AvatarStepApproachFactor) 277 if (diff < BSParam.AvatarStepApproachFactor)
263 { 278 {
264 // Found the stairs contact point. Push up a little to raise the character. 279 if (highestTouchPosition.Z < touchPosition.Z)
265 float upForce = (touchPosition.Z - nearFeetHeightMin) * m_controllingPrim.Mass * BSParam.AvatarStepForceFactor; 280 highestTouchPosition = touchPosition;
266 ret = new OMV.Vector3(0f, 0f, upForce);
267
268 // Also move the avatar up for the new height
269 OMV.Vector3 displacement = new OMV.Vector3(0f, 0f, BSParam.AvatarStepHeight / 2f);
270 m_controllingPrim.ForcePosition = m_controllingPrim.RawPosition + displacement;
271 } 281 }
272 m_physicsScene.DetailLog("{0},BSCharacter.WalkUpStairs,touchPos={1},nearFeetMin={2},faceDir={3},norm={4},diff={5},ret={6}",
273 m_controllingPrim.LocalID, touchPosition, nearFeetHeightMin, directionFacing, touchNormal, diff, ret);
274 } 282 }
275 } 283 }
276 } 284 }
285 m_walkingUpStairs = 0;
286 // If there is a good step sensing, move the avatar over the step.
287 if (highestTouchPosition != OMV.Vector3.Zero)
288 {
289 // Remember that we are going up stairs. This is needed because collisions
290 // will stop when we move up so this smoothes out that effect.
291 m_walkingUpStairs = BSParam.AvatarStepSmoothingSteps;
292
293 m_lastStepUp = highestTouchPosition.Z - nearFeetHeightMin;
294 ret = ComputeStairCorrection(m_lastStepUp);
295 m_physicsScene.DetailLog("{0},BSCharacter.WalkUpStairs,touchPos={1},nearFeetMin={2},ret={3}",
296 m_controllingPrim.LocalID, highestTouchPosition, nearFeetHeightMin, ret);
297 }
298 }
299 else
300 {
301 // If we used to be going up stairs but are not now, smooth the case where collision goes away while
302 // we are bouncing up the stairs.
303 if (m_walkingUpStairs > 0)
304 {
305 m_walkingUpStairs--;
306 ret = ComputeStairCorrection(m_lastStepUp);
307 }
277 } 308 }
278 309
279 return ret; 310 return ret;
280 } 311 }
281 312
313 private OMV.Vector3 ComputeStairCorrection(float stepUp)
314 {
315 OMV.Vector3 ret = OMV.Vector3.Zero;
316 OMV.Vector3 displacement = OMV.Vector3.Zero;
317
318 if (stepUp > 0f)
319 {
320 // Found the stairs contact point. Push up a little to raise the character.
321 if (BSParam.AvatarStepForceFactor > 0f)
322 {
323 float upForce = stepUp * m_controllingPrim.Mass * BSParam.AvatarStepForceFactor;
324 ret = new OMV.Vector3(0f, 0f, upForce);
325 }
326
327 // Also move the avatar up for the new height
328 if (BSParam.AvatarStepUpCorrectionFactor > 0f)
329 {
330 // Move the avatar up related to the height of the collision
331 displacement = new OMV.Vector3(0f, 0f, stepUp * BSParam.AvatarStepUpCorrectionFactor);
332 m_controllingPrim.ForcePosition = m_controllingPrim.RawPosition + displacement;
333 }
334 else
335 {
336 if (BSParam.AvatarStepUpCorrectionFactor < 0f)
337 {
338 // Move the avatar up about the specified step height
339 displacement = new OMV.Vector3(0f, 0f, BSParam.AvatarStepHeight);
340 m_controllingPrim.ForcePosition = m_controllingPrim.RawPosition + displacement;
341 }
342 }
343 m_physicsScene.DetailLog("{0},BSCharacter.WalkUpStairs.ComputeStairCorrection,disp={1},force={2}",
344 m_controllingPrim.LocalID, displacement, ret);
345
346 }
347 return ret;
348 }
282} 349}
283} 350}
284 351