/// <summary> /// Sweeps a convex shape against the physics world reporting all hits on the path even if they ignore collisions, beware convex sweeps can be very costly especially if they are long /// </summary> /// <param name="shape">Shape to sweep</param> /// <param name="startPos">Location to start the sweep from</param> /// <param name="rotation">Rotation of the shape during the sweep</param> /// <param name="sweep">Direction in which to sweep, the length of the vector is the length of the sweep</param> /// <param name="outSweepResults">All overlaps on the sweep path</param> /// <returns>True if any object was hit</returns> public bool MultiSweep(ConvexShape shape, ref SharpDX.Vector3 startPos, ref SharpDX.Quaternion rotation, ref SharpDX.Vector3 sweep, List <SRaycastResult> outSweepResults) { RigidTransform startTransform = new RigidTransform(startPos.ToBepu(), rotation.ToBepu()); Vector3 sweepVector = sweep.ToBepu(); List <RayCastResult> physicsResults = new List <RayCastResult>(); if (m_physicSpace.ConvexCast(shape, ref startTransform, ref sweepVector, physicsResults)) { foreach (RayCastResult physicsResult in physicsResults) { if (physicsResult.HitObject.Tag is CEntity gameEntity) { SRaycastResult gameResult = new SRaycastResult() { HitEntity = gameEntity, Location = physicsResult.HitData.Location.ToSharp(), Normal = -physicsResult.HitData.Normal.ToSharp(), Distance = physicsResult.HitData.T, bIsSolidHit = false }; outSweepResults.Add(gameResult); } } return(outSweepResults.Count > 0); } return(false); }
public ref BEPUutilities.Vector3 CopyTo(ref BEPUutilities.Vector3 toVec) { toVec.X = x; toVec.Y = y; toVec.Z = z; return(ref toVec); }
/// <summary> /// Constructs a thruster originating at the given position, pushing in the given direction. /// </summary> /// <param name="targetEntity">Entity that the force will be applied to.</param> /// <param name="pos">Origin of the force.</param> /// <param name="dir">Direction of the force.</param> /// <param name="time">Total lifespan of the force. A lifespan of zero is infinite.</param> public Thruster(Entity targetEntity, BEPUutilities.Vector3 pos, BEPUutilities.Vector3 dir, float time) { Target = targetEntity; Position = pos; Direction = dir; LifeSpan = time; }
public static ref BEPUutilities.Vector3 CopyTo(this Vector3 vec, ref BEPUutilities.Vector3 toVec) { toVec.X = vec.x; toVec.Y = vec.y; toVec.Z = vec.z; return(ref toVec); }
/// <summary> /// Sweeps a convex shape against the physics world reporting all hits on the path that are not ignored by the filter, beware convex sweeps can be very costly especially if they are long /// </summary> /// <param name="shape">Shape to sweep</param> /// <param name="startPos">Location to start the sweep from</param> /// <param name="rotation">Rotation of the shape during the sweep</param> /// <param name="sweep">Direction in which to sweep, the length of the vector is the length of the sweep</param> /// <param name="sweepRules">Collision rules to filter the sweep hits, anything above "NoSolver" is ignored</param> /// <param name="outSweepResults">All overlaps on the sweep path</param> /// <returns>True if any object was hit</returns> public bool MultiSweep(ConvexShape shape, ref SharpDX.Vector3 startPos, ref SharpDX.Quaternion rotation, ref SharpDX.Vector3 sweep, CollisionRules sweepRules, List <SRaycastResult> outSweepResults) { SimpleCollisionRulesOwner rulesOwner = new SimpleCollisionRulesOwner(sweepRules); RigidTransform startTransform = new RigidTransform(startPos.ToBepu(), rotation.ToBepu()); Vector3 sweepVector = sweep.ToBepu(); List <RayCastResult> physicsResults = new List <RayCastResult>(); if (m_physicSpace.ConvexCast(shape, ref startTransform, ref sweepVector, GetOverlapFilter(rulesOwner), physicsResults)) { foreach (RayCastResult physicsResult in physicsResults) { if (physicsResult.HitObject.Tag is CEntity gameEntity) { CollisionRule rule = CollisionRules.GetCollisionRule(physicsResult.HitObject, rulesOwner); SRaycastResult gameResult = new SRaycastResult() { HitEntity = gameEntity, Location = physicsResult.HitData.Location.ToSharp(), Normal = -physicsResult.HitData.Normal.ToSharp(), Distance = physicsResult.HitData.T, bIsSolidHit = rule <= CollisionRule.Normal }; outSweepResults.Add(gameResult); } } return(outSweepResults.Count > 0); } return(false); }
/// <summary> /// A convex-shaped ray-trace method for the special case of needing to handle Voxel collision types. /// </summary> /// <param name="shape">The shape of the convex ray source object.</param> /// <param name="start">The start of the ray.</param> /// <param name="dir">The normalized vector of the direction of the ray.</param> /// <param name="len">The length of the ray.</param> /// <param name="considerSolid">What materials are 'solid'.</param> /// <param name="filter">A function to identify what entities should be filtered out.</param> /// <param name="rayHit">Outputs the result of the ray trace.</param> /// <returns>Whether there was a collision.</returns> public bool SpecialCaseConvexTrace(ConvexShape shape, Location start, Location dir, double len, MaterialSolidity considerSolid, Func <BroadPhaseEntry, bool> filter, out RayCastResult rayHit) { RigidTransform rt = new RigidTransform(start.ToBVector(), BEPUutilities.Quaternion.Identity); BEPUutilities.Vector3 sweep = (dir * len).ToBVector(); RayCastResult best = new RayCastResult(new RayHit() { T = len }, null); bool hA = false; if (considerSolid.HasFlag(MaterialSolidity.FULLSOLID)) { if (PhysicsWorld.ConvexCast(shape, ref rt, ref sweep, filter, out RayCastResult rcr)) { best = rcr; hA = true; } } if (considerSolid == MaterialSolidity.FULLSOLID) { rayHit = best; return(hA); } sweep = dir.ToBVector(); AABB box = new AABB() { Min = start, Max = start }; box.Include(start + dir * len); foreach (KeyValuePair <Vector3i, Chunk> chunk in LoadedChunks) { if (chunk.Value == null || chunk.Value.FCO == null) { continue; } if (!box.Intersects(new AABB() { Min = chunk.Value.WorldPosition.ToLocation() * Chunk.CHUNK_SIZE, Max = chunk.Value.WorldPosition.ToLocation() * Chunk.CHUNK_SIZE + new Location(Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE) })) { continue; } if (chunk.Value.FCO.ConvexCast(shape, ref rt, ref sweep, len, considerSolid, out RayHit temp)) { hA = true; if (temp.T < best.HitData.T) { best.HitData = temp; best.HitObject = chunk.Value.FCO; } } } rayHit = best; return(hA); }
public override void ExclusiveUpdate() { if (Helicopter.HeloPilot == null) { return; // Don't fly when there's nobody driving this! } // Collect the helicopter's relative "up" vector BEPUutilities.Vector3 up = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitZ, Entity.Orientation); // Apply the amount of force necessary to counteract downward force, within a limit. // POTENTIAL: Adjust according to orientation? double uspeed = Math.Min(Helicopter.LiftStrength, -(Entity.LinearVelocity.Z + Entity.Space.ForceUpdater.Gravity.Z) * Entity.Mass); if (uspeed < 0f) { uspeed += (uspeed - Helicopter.FallStrength) * Helicopter.HeloPilot.SprintOrWalk; } else { uspeed += (Helicopter.LiftStrength - uspeed) * Helicopter.HeloPilot.SprintOrWalk; } BEPUutilities.Vector3 upvel = up * uspeed * Delta; Entity.ApplyLinearImpulse(ref upvel); // Rotate slightly to move in a direction. // At the same time, fight against existing rotation. BEPUutilities.Vector3 VecUp = new BEPUutilities.Vector3(Helicopter.HeloPilot.XMove * 0.2f * Helicopter.HeloTiltMod, Helicopter.HeloPilot.YMove * -0.2f * Helicopter.HeloTiltMod, 1); // TODO: Simplify yawrel calculation. float tyaw = (float)(Utilities.MatrixToAngles(Matrix.CreateFromQuaternion(Entity.Orientation)).Z * Utilities.PI180); BEPUutilities.Quaternion yawrel = BEPUutilities.Quaternion.CreateFromAxisAngle(BEPUutilities.Vector3.UnitZ, tyaw); VecUp = BEPUutilities.Quaternion.Transform(VecUp, yawrel); VecUp.Normalize(); VecUp.Y = -VecUp.Y; BEPUutilities.Vector3 axis = BEPUutilities.Vector3.Cross(VecUp, up); double len = axis.Length(); if (len > 0) { axis /= len; float angle = (float)Math.Asin(len); if (!float.IsNaN(angle)) { double avel = BEPUutilities.Vector3.Dot(Entity.AngularVelocity, axis); BEPUutilities.Vector3 torque = axis * ((-angle) - 0.3f * avel); torque *= Entity.Mass * Delta * 30; Entity.ApplyAngularImpulse(ref torque); } } // Spin in place float rotation = (Helicopter.HeloPilot.ItemRight ? -1f : 0f) + (Helicopter.HeloPilot.ItemLeft ? 1f : 0f); if (rotation * rotation > 0f) { BEPUutilities.Vector3 rot = new BEPUutilities.Vector3(0, 0, rotation * 15f * Delta * Entity.Mass); Entity.ApplyAngularImpulse(ref rot); } // Apply air drag Entity.ModifyLinearDamping(0.3f); // TODO: arbitrary constant Entity.ModifyAngularDamping(0.6f); // TODO: arbitrary constant // Ensure we're active if flying! Entity.ActivityInformation.Activate(); }
public void ChunkMarchAndDraw() { Vector3i start = ChunkLocFor(TheClient.MainWorldView.CameraPos); HashSet <Vector3i> seen = new HashSet <Vector3i>(); Queue <Vector3i> toSee = new Queue <Vector3i>(); HashSet <Vector3i> toSeeSet = new HashSet <Vector3i>(); toSee.Enqueue(start); toSeeSet.Add(start); while (toSee.Count > 0) { Vector3i cur = toSee.Dequeue(); toSeeSet.Remove(cur); if ((Math.Abs(cur.X - start.X) > MaxRenderDistanceChunks) || (Math.Abs(cur.Y - start.Y) > MaxRenderDistanceChunks) || (Math.Abs(cur.Z - start.Z) > MaxRenderDistanceChunks)) { continue; } seen.Add(cur); Chunk chcur = GetChunk(cur); if (chcur != null) { chcur.Render(); chToRender.Add(chcur); } for (int i = 0; i < MoveDirs.Length; i++) { Vector3i t = cur + MoveDirs[i]; if (!seen.Contains(t) && !toSeeSet.Contains(t)) { for (int j = 0; j < MoveDirs.Length; j++) { if (BEPUutilities.Vector3.Dot(MoveDirs[j].ToVector3(), (TheClient.MainWorldView.CameraTarget - TheClient.MainWorldView.CameraPos).ToBVector()) < -0.8f) // TODO: what is this? Is it needed? { continue; } Vector3i nt = cur + MoveDirs[j]; if (!seen.Contains(nt) && !toSeeSet.Contains(nt)) { BEPUutilities.Vector3 min = nt.ToVector3() * Chunk.CHUNK_SIZE; if (TheClient.MainWorldView.CFrust == null || TheClient.MainWorldView.CFrust.ContainsBox(min, min + new BEPUutilities.Vector3(Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE))) { toSee.Enqueue(nt); toSeeSet.Add(nt); } else { seen.Add(nt); } } } } } } }
public MeshCollider(Mesh mesh) : base() { Mesh = mesh; bepu.Vector3[] vertices = new bepu.Vector3[Mesh.vertices.Length]; for (int i = 0; i < Mesh.vertices.Length; i++) { vertices[i] = Physics.VectorT2B(Mesh.vertices[i].Xyz); } shape = new ConvexHullShape(vertices); }
/// <summary> /// Applies the thruster forces. /// Called automatically by the owning space during a space update. /// </summary> /// <param name="dt">Simulation timestep.</param> void IDuringForcesUpdateable.Update(float dt) { //Transform the local position and direction into world space. BEPUutilities.Vector3 worldPosition = Target.Position + Matrix3x3.Transform(Position, Target.OrientationMatrix); BEPUutilities.Vector3 worldDirection = Matrix3x3.Transform(Direction, Target.OrientationMatrix); //Apply the force. Target.ApplyImpulse(worldPosition, worldDirection * dt); Age += dt; if (LifeSpan > 0 && Age > LifeSpan) { IsUpdating = false; //The thruster has finished firing. } }
/// <summary> /// Creates a character controller in the world /// </summary> /// <param name="characterControllerDescription"> </param> /// <returns></returns> public ICharacterController CreateCharacterController(CharacterControllerDescription characterControllerDescription) { var position = characterControllerDescription.Position; var correctedPosition = new Vector3(position.X, position.Y, position.Z); var bepuCharacterController = new BEPUCharacterController(correctedPosition, characterControllerDescription.Height - characterControllerDescription.Radius * 2f, characterControllerDescription.Radius, 1, characterControllerDescription.SlopeLimit); bepuCharacterController.Body.CollisionInformation.CollisionRules.Group = GetCollisionGroup(CollisionHelper.AvatarObjectColliderDescription.CollisionGroup); this.space.Add(bepuCharacterController); return(bepuCharacterController); }
public void Update(GameTime gameTime, bool inAtmosphere) { float thrustToUse = forwardThrustInSpace; if (inAtmosphere) { thrustToUse = forwardThrustInAtmosphere; } ShipObject.Transform.AbsoluteTransform = MonoMathHelper.GenerateMonoMatrixFromBepu(PhysicsBody.WorldTransform); if (IsActive) { var currentLeft = PhysicsBody.WorldTransform.Left; var currentForward = PhysicsBody.WorldTransform.Forward; var currentUp = PhysicsBody.WorldTransform.Up; Microsoft.Xna.Framework.Vector2 leftStick = SystemCore.Input.GetLeftStickState(playerIndex); leftStick.X = -leftStick.X; Microsoft.Xna.Framework.Vector2 rightStick = SystemCore.Input.GetRightStickState(playerIndex); float rightTrigger = SystemCore.Input.GetRightTrigger(playerIndex); if (rightTrigger > 0) { PhysicsBody.LinearVelocity += PhysicsBody.WorldTransform.Forward * (rightTrigger * (thrustToUse)); } float speed = 0.05f; BEPUutilities.Vector3 left = currentLeft * leftStick.Y * speed; PhysicsBody.AngularVelocity += currentLeft * leftStick.Y * speed; PhysicsBody.AngularVelocity += currentUp * leftStick.X * speed; if (SystemCore.Input.GamePadButtonDown(Buttons.RightShoulder, playerIndex)) { PhysicsBody.AngularVelocity += currentForward * speed; } if (SystemCore.Input.GamePadButtonDown(Buttons.LeftShoulder, playerIndex)) { PhysicsBody.AngularVelocity -= currentForward * speed; } PhysicsBody.LinearVelocity += PhysicsBody.WorldTransform.Up * rightStick.Y; PhysicsBody.LinearVelocity -= PhysicsBody.WorldTransform.Left * rightStick.X; } }
public override void SpawnBody() { PreHandleSpawn(); base.SpawnBody(); if (mode == ModelCollisionMode.PRECISE) { Offset = InternalOffset; } BEPUutilities.Vector3 offs = Offset.ToBVector(); transform = Matrix4d.CreateTranslation(ClientUtilities.ConvertD(Offset)); List<BEPUutilities.Vector3> tvecs = TheClient.Models.Handler.GetVertices(model.Original); if (tvecs.Count == 0) { ModelMin = new BEPUutilities.Vector3(0, 0, 0); ModelMax = new BEPUutilities.Vector3(0, 0, 0); } else { ModelMin = tvecs[0]; ModelMax = tvecs[0]; foreach (BEPUutilities.Vector3 vec in tvecs) { BEPUutilities.Vector3 tvec = vec + offs; if (tvec.X < ModelMin.X) { ModelMin.X = tvec.X; } if (tvec.Y < ModelMin.Y) { ModelMin.Y = tvec.Y; } if (tvec.Z < ModelMin.Z) { ModelMin.Z = tvec.Z; } if (tvec.X > ModelMax.X) { ModelMax.X = tvec.X; } if (tvec.Y > ModelMax.Y) { ModelMax.Y = tvec.Y; } if (tvec.Z > ModelMax.Z) { ModelMax.Z = tvec.Z; } } } if (GenBlockShadows) { double tx = ModelMax.X - ModelMin.X; double ty = ModelMax.Y - ModelMin.Y; BoxShape bs = new BoxShape(tx, ty, ModelMax.Z - ModelMin.Z); EntityCollidable tempCast = bs.GetCollidableInstance(); tempCast.LocalPosition = (ModelMax + ModelMin) * 0.5f + Body.Position; RigidTransform def = RigidTransform.Identity; tempCast.UpdateBoundingBoxForTransform(ref def); ShadowCastShape = tempCast.BoundingBox; BEPUutilities.Vector3 size = ShadowCastShape.Max - ShadowCastShape.Min; ShadowRadiusSquaredXY = size.X * size.X + size.Y * size.Y; } }
private void OnInputEvent(ReadOnlyCollection <SInputButtonEvent> buttonevents, string textinput) { foreach (var buttonEvent in buttonevents) { if (buttonEvent.button == EInputButton.MouseMiddleButton && buttonEvent.buttonEvent == EButtonEvent.Pressed) { CViewManager viewManager = m_gameWorld.ViewManager; int mouseAbsX = System.Windows.Forms.Cursor.Position.X - (int)viewManager.ScreenLeft; int mouseAbsY = System.Windows.Forms.Cursor.Position.Y - (int)viewManager.ScreenTop; if (mouseAbsX < 0 || mouseAbsY < 0) { return; } viewManager.GetViewInfo(out SSceneViewInfo viewInfo); Ray pickRay = Ray.GetPickRay(mouseAbsX, mouseAbsY, new ViewportF(0, 0, viewManager.ScreenWidth, viewManager.ScreenHeight), viewInfo.ViewMatrix * viewInfo.ProjectionMatrix); if (m_physicSpace.RayCast(pickRay.ToBepu(), 9999.0f, out RayCastResult result)) { float fieldRadius = 5.0f; float impulseStrength = 20.0f; List <BroadPhaseEntry> queryResults = new List <BroadPhaseEntry>(); BoundingSphere bs = new BoundingSphere(result.HitData.Location, fieldRadius); m_physicSpace.BroadPhase.QueryAccelerator.GetEntries(bs, queryResults); foreach (var entry in queryResults) { var entityCollision = entry as EntityCollidable; if (entityCollision != null) { var e = entityCollision.Entity; if (e.IsDynamic) { Vector3 toEntity = e.Position - result.HitData.Location; float length = toEntity.Length(); float strength = impulseStrength / length; toEntity.Y = 1.0f; toEntity.Normalize(); e.ApplyImpulse(e.Position, toEntity * strength); } } } } } } }
public override void ExclusiveUpdate() { if (Plane.PlanePilot == null) { return; // Don't fly when there's nobody driving this! } // TODO: Special case for motion on land: only push forward if W key is pressed? Or maybe apply that rule in general? // Collect the plane's relative vectors BEPUutilities.Vector3 forward = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitY, Entity.Orientation); BEPUutilities.Vector3 side = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitX, Entity.Orientation); BEPUutilities.Vector3 up = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitZ, Entity.Orientation); // Engines! if (Plane.PlanePilot.SprintOrWalk >= 0.0) { BEPUutilities.Vector3 force = forward * (Plane.PlaneRegularStrength + Plane.PlaneFastStrength) * Delta; entity.ApplyLinearImpulse(ref force); } double dotforw = BEPUutilities.Vector3.Dot(entity.LinearVelocity, forward); entity.ApplyImpulse(side * 5 + entity.Position, up * -Plane.PlanePilot.XMove * entity.Mass * dotforw * 0.5 * Delta); entity.ApplyImpulse(forward * 5 + entity.Position, side * ((Plane.PlanePilot.ItemRight ? 1 : 0) + (Plane.PlanePilot.ItemLeft ? -1 : 0)) * entity.Mass * dotforw * 0.5 * Delta); entity.ApplyImpulse(forward * 5 + entity.Position, up * Plane.PlanePilot.YMove * entity.Mass * 0.5 * Delta * dotforw); // Rotate the entity pre-emptively, and re-apply the movement velocity in this new direction! double vellen = entity.LinearVelocity.Length(); BEPUutilities.Vector3 normvel = entity.LinearVelocity / vellen; BEPUutilities.Vector3 norm_vel_transf = BEPUutilities.Quaternion.Transform(normvel, BEPUutilities.Quaternion.Inverse(entity.Orientation)); // Probably just 1,0,0 on whichever axis... can be simplified! BEPUutilities.Vector3 inc = entity.AngularVelocity * Delta * 0.5; BEPUutilities.Quaternion quat = new BEPUutilities.Quaternion(inc.X, inc.Y, inc.Z, 0); quat = quat * entity.Orientation; BEPUutilities.Quaternion orient = entity.Orientation; BEPUutilities.Quaternion.Add(ref orient, ref quat, out orient); orient.Normalize(); entity.Orientation = orient; entity.LinearVelocity = BEPUutilities.Quaternion.Transform(norm_vel_transf, orient) * vellen; entity.AngularVelocity *= 0.1; // Apply air drag Entity.ModifyLinearDamping(Plane.PlanePilot.SprintOrWalk < 0.0 ? 0.6 : 0.1); // TODO: arbitrary constant Entity.ModifyAngularDamping(0.5); // TODO: arbitrary constant // Ensure we're active if flying! Entity.ActivityInformation.Activate(); }
/// <summary> /// Sweeps a convex shape against the physics world reporting the closest hit to the start location, beware convex sweeps can be very costly especially if they are long /// </summary> /// <param name="shape">Shape to sweep</param> /// <param name="startPos">Location to start the sweep from</param> /// <param name="rotation">Rotation of the shape during the sweep</param> /// <param name="sweep">Direction in which to sweep, the length of the vector is the length of the sweep</param> /// <param name="filter">Function to filter hits</param> /// <param name="outSweepResult">Closest hit to the start location</param> /// <returns>True if any object was hit</returns> public bool ConvexSweep(ConvexShape shape, ref SharpDX.Vector3 startPos, ref SharpDX.Quaternion rotation, ref SharpDX.Vector3 sweep, Func <BroadPhaseEntry, bool> filter, ref SRaycastResult outSweepResult) { RigidTransform startTransform = new RigidTransform(startPos.ToBepu(), rotation.ToBepu()); Vector3 sweepVector = sweep.ToBepu(); if (m_physicSpace.ConvexCast(shape, ref startTransform, ref sweepVector, filter, out RayCastResult result)) { if (result.HitObject.Tag is CEntity gameEntity) { outSweepResult.HitEntity = gameEntity; outSweepResult.Location = result.HitData.Location.ToSharp(); outSweepResult.Normal = -result.HitData.Normal.ToSharp(); outSweepResult.Distance = result.HitData.T; outSweepResult.bIsSolidHit = true; return(true); } } return(false); }
/// <summary> /// Returns the list of ConvexCollidable's and Entities inside or touching the specified sphere. /// Result does not include static geometry and non-entity physical objects. /// </summary> /// <param name="world"></param> /// <param name="origin"></param> /// <param name="radius"></param> /// <returns></returns> public List <Entity> WeaponOverlap(Vector3 origin, float radius, Entity entToSkip) { BU.BoundingSphere sphere = new BU.BoundingSphere(MathConverter.Convert(origin), radius); SphereShape sphereShape = new SphereShape(radius); BU.Vector3 zeroSweep = BU.Vector3.Zero; BU.RigidTransform rigidXForm = new BU.RigidTransform(MathConverter.Convert(origin)); var candidates = PhysicsResources.GetBroadPhaseEntryList(); PhysSpace.BroadPhase.QueryAccelerator.BroadPhase.QueryAccelerator.GetEntries(sphere, candidates); var result = new List <Entity>(); foreach (var candidate in candidates) { BU.RayHit rayHit; bool r = candidate.ConvexCast(sphereShape, ref rigidXForm, ref zeroSweep, out rayHit); if (r) { var collidable = candidate as ConvexCollidable; var entity = collidable == null ? null : collidable.Entity.Tag as Entity; if (collidable == null) { continue; } if (entity == null) { continue; } result.Add(entity); } } result.RemoveAll(e => e == entToSkip); return(result); }
public void TryToAddBone(Bone bone, Vector3 grabbedLocation) { bool alreadyConstrainingBone = false; for (int i = 0; i < stateControls.Count; i++) { var entry = stateControls[i]; entry.GrabOffset = grabbedLocation - entry.Control.TargetBone.Position; stateControls[i] = entry; if (entry.Control.TargetBone == bone) { alreadyConstrainingBone = true; } } if (!alreadyConstrainingBone) { //Add a new control to the group for this bone. var entry = new ControlEntry { Control = GetControl(bone), GrabOffset = grabbedLocation - bone.Position }; stateControls.Add(entry); } distanceToTarget = Vector3.Dot(camera.WorldMatrix.Forward, grabbedLocation - camera.Position); }
public override void ExclusiveUpdate() { if (Plane.PlanePilot == null) { return; // Don't fly when there's nobody driving this! } // TODO: Special case for motion on land: only push forward if FORWARD key is pressed? Or maybe apply that rule in general? // Collect the plane's relative vectors BEPUutilities.Vector3 forward = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitY, Entity.Orientation); BEPUutilities.Vector3 side = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitX, Entity.Orientation); BEPUutilities.Vector3 up = BEPUutilities.Quaternion.Transform(BEPUutilities.Vector3.UnitZ, Entity.Orientation); // Engines! if (Plane.PlanePilot.SprintOrWalk >= 0.0) { BEPUutilities.Vector3 force = forward * (Plane.PlaneRegularStrength + Plane.PlaneFastStrength * Plane.PlanePilot.SprintOrWalk) * Delta; entity.ApplyLinearImpulse(ref force); } double dotforw = BEPUutilities.Vector3.Dot(entity.LinearVelocity, forward); double mval = 2.0 * (1.0 / Math.Max(1.0, entity.LinearVelocity.Length())); double rot_x = -Plane.PlanePilot.YMove * 0.5 * Delta * dotforw * mval; double rot_y = Plane.PlanePilot.XMove * dotforw * 0.5 * Delta * mval; double rot_z = -((Plane.PlanePilot.ItemRight ? 1 : 0) + (Plane.PlanePilot.ItemLeft ? -1 : 0)) * dotforw * 0.1 * Delta * mval; entity.AngularVelocity += BEPUutilities.Quaternion.Transform(new BEPUutilities.Vector3(rot_x, rot_y, rot_z), entity.Orientation); double vellen = entity.LinearVelocity.Length(); BEPUutilities.Vector3 newVel = forward * vellen; double forwVel = BEPUutilities.Vector3.Dot(entity.LinearVelocity, forward); double root = Math.Sqrt(Math.Sign(forwVel) * forwVel); entity.LinearVelocity += (newVel - entity.LinearVelocity) * BEPUutilities.MathHelper.Clamp(Delta, 0.01, 0.3) * Math.Min(2.0, root * 0.05); // Apply air drag Entity.ModifyLinearDamping(Plane.PlanePilot.SprintOrWalk < 0.0 ? 0.5 : 0.1); // TODO: arbitrary constants Entity.ModifyAngularDamping(0.995); // TODO: arbitrary constant // Ensure we're active if flying! Entity.ActivityInformation.Activate(); }
void BuildTinyTest(Vector3 position) { Bone[] bonesList = new Bone[2]; bonesList[0] = new Bone(position + new Vector3(0, 10, 0), Quaternion.Identity, 0.05f, 0.2f); bonesList[1] = new Bone(position + new Vector3(0, 12, 0), Quaternion.Identity, 0.05f * 100, 0.2f * 100); Cylinder[] boneEntitiesList = new Cylinder[2]; boneEntitiesList[0] = new Cylinder(bonesList[0].Position, bonesList[0].Radius, bonesList[0].Height, 10); boneEntitiesList[1] = new Cylinder(bonesList[1].Position, bonesList[1].Radius, bonesList[1].Height, 10); bones.Add(new BoneRelationship(bonesList[0], boneEntitiesList[0])); bones.Add(new BoneRelationship(bonesList[1], boneEntitiesList[1])); }
void BuildRing(Vector3 position) { int incrementCount = 20; float radius = 5; float anglePerIncrement = MathHelper.TwoPi / incrementCount; Bone[] bonesList = new Bone[incrementCount]; for (int i = 0; i < incrementCount; i++) { Vector3 bonePosition; #if !WINDOWS bonePosition = new Vector3(); #endif bonePosition.X = (float)Math.Cos(anglePerIncrement * i); bonePosition.Y = 0; bonePosition.Z = (float)Math.Sin(anglePerIncrement * i); bonePosition = bonePosition * radius + position; bonesList[i] = new Bone(bonePosition, Quaternion.Concatenate(Quaternion.CreateFromAxisAngle(Vector3.Right, MathHelper.PiOver2), Quaternion.CreateFromAxisAngle(Vector3.Up, -anglePerIncrement * i)), 0.5f, MathHelper.Pi * radius * 2 / incrementCount); } for (int i = 0; i < bonesList.Length; i++) { var boneA = bonesList[i]; var boneB = bonesList[(i + 1) % incrementCount]; var upA = Quaternion.Transform(Vector3.Up, boneA.Orientation); var upB = Quaternion.Transform(Vector3.Up, boneB.Orientation); joints.Add(new IKBallSocketJoint(boneA, boneB, (boneA.Position + upA * boneB.HalfHeight + boneB.Position - upB * boneB.HalfHeight) * .5f)); joints.Add(new IKSwingLimit(boneA, boneB, upA, upB, MathHelper.Pi * .5f)); } Cylinder[] boneEntitiesList = new Cylinder[incrementCount]; for (int i = 0; i < incrementCount; i++) { var boneEntity = new Cylinder(new MotionState { Position = bonesList[i].Position, Orientation = bonesList[i].Orientation }, bonesList[i].Height, bonesList[i].Radius, 10); bones.Add(new BoneRelationship(bonesList[i], boneEntity)); boneEntitiesList[i] = boneEntity; Space.Add(boneEntity); } for (int i = 0; i < incrementCount; i++) { var boneA = boneEntitiesList[i]; var boneB = boneEntitiesList[(i + 1) % incrementCount]; var upA = Quaternion.Transform(Vector3.Up, boneA.Orientation); var upB = Quaternion.Transform(Vector3.Up, boneB.Orientation); var joint = new BallSocketJoint(boneA, boneB, (boneA.Position + upA * boneB.Height * 0.5f + boneB.Position - upB * boneB.Height * 0.5f) * .5f); var swingLimit = new SwingLimit(boneA, boneB, upA, upB, MathHelper.Pi * .5f); Space.Add(swingLimit); Space.Add(joint); CollisionRules.AddRule(boneA, boneB, CollisionRule.NoBroadPhase); } }
void BuildRoboArmThing(Vector3 position) { //Make the IK representation Bone baseBone = new Bone(position, Quaternion.Identity, 1, 3); Bone upperArm = new Bone(baseBone.Position + new Vector3(0, 1.5f + 2, 0), Quaternion.Identity, .4f, 4); Bone lowerArm = new Bone(upperArm.Position + new Vector3(0, 2 + 1, 0), Quaternion.Identity, .7f, 2); Bone bonkDevice = new Bone(lowerArm.Position + new Vector3(0, 5, 0), Quaternion.Identity, .6f, 1.2f); joints.Add(new IKBallSocketJoint(baseBone, upperArm, baseBone.Position + new Vector3(0, 1.5f, 0))); joints.Add(new IKSwingLimit(baseBone, upperArm, Vector3.Up, Vector3.Up, MathHelper.PiOver4)); joints.Add(new IKBallSocketJoint(upperArm, lowerArm, upperArm.Position + new Vector3(0, 2f, 0))); joints.Add(new IKRevoluteJoint(upperArm, lowerArm, Vector3.Forward)); joints.Add(new IKSwingLimit(upperArm, lowerArm, Vector3.Up, Vector3.Up, MathHelper.PiOver4)); joints.Add(new IKPointOnLineJoint(lowerArm, bonkDevice, lowerArm.Position, Vector3.Up, bonkDevice.Position)); joints.Add(new IKAngularJoint(lowerArm, bonkDevice)); joints.Add(new IKLinearAxisLimit(lowerArm, bonkDevice, lowerArm.Position, Vector3.Up, bonkDevice.Position, 1.6f, 5)); //Make the dynamics representation Entity baseEntity = new Cylinder(baseBone.Position, baseBone.Height, baseBone.Radius, 10); Entity upperArmEntity = new Cylinder(upperArm.Position, upperArm.Height, upperArm.Radius, 7); Entity lowerArmEntity = new Cylinder(lowerArm.Position, lowerArm.Height, lowerArm.Radius, 5); Entity bonkDeviceEntity = new Cylinder(bonkDevice.Position, bonkDevice.Height, bonkDevice.Radius, 3); bonkDeviceEntity.Orientation = bonkDevice.Orientation; Space.Add(baseEntity); Space.Add(upperArmEntity); Space.Add(lowerArmEntity); Space.Add(bonkDeviceEntity); Space.Add(new BallSocketJoint(baseEntity, upperArmEntity, baseBone.Position + new Vector3(0, 1.5f, 0))); Space.Add(new SwingLimit(baseEntity, upperArmEntity, Vector3.Up, Vector3.Up, MathHelper.PiOver4)); Space.Add(new BallSocketJoint(upperArmEntity, lowerArmEntity, upperArm.Position + new Vector3(0, 2f, 0))); Space.Add(new RevoluteAngularJoint(upperArmEntity, lowerArmEntity, Vector3.Forward)); Space.Add(new SwingLimit(upperArmEntity, lowerArmEntity, Vector3.Up, Vector3.Up, MathHelper.PiOver4)); Space.Add(new PointOnLineJoint(lowerArmEntity, bonkDeviceEntity, lowerArm.Position, Vector3.Up, bonkDevice.Position)); var motor = new AngularMotor(lowerArmEntity, bonkDeviceEntity); motor.Settings.Mode = MotorMode.Servomechanism; Space.Add(motor); Space.Add(new LinearAxisLimit(lowerArmEntity, bonkDeviceEntity, lowerArm.Position, bonkDevice.Position, Vector3.Up, 1.6f, 5)); CollisionRules.AddRule(baseEntity, upperArmEntity, CollisionRule.NoBroadPhase); CollisionRules.AddRule(upperArmEntity, lowerArmEntity, CollisionRule.NoBroadPhase); CollisionRules.AddRule(lowerArmEntity, bonkDeviceEntity, CollisionRule.NoBroadPhase); //Relate the two! bones.Add(new BoneRelationship(baseBone, baseEntity)); bones.Add(new BoneRelationship(upperArm, upperArmEntity)); bones.Add(new BoneRelationship(lowerArm, lowerArmEntity)); bones.Add(new BoneRelationship(bonkDevice, bonkDeviceEntity)); }
/// <summary> /// Ticks the region, including all primary calculations and lighting updates. /// </summary> public void TickWorld(double delta) { timeSinceSkyPatch += delta; if (timeSinceSkyPatch > 5 || Math.Abs((SunAngle - pSunAng).BiggestValue()) > 10f) // TODO: CVar for this? { timeSinceSkyPatch = 0; CreateSkyBox(); } Engine.SunAdjustDirection = TheSun.Direction; Engine.SunAdjustBackupLight = new OpenTK.Vector4(TheSun.InternalLights[0].color, 1.0f); Engine.MainView.SunLight_Minimum = sl_min; Engine.MainView.SunLight_Maximum = sl_max; rTicks++; if (rTicks >= CVars.r_shadowpace.ValueI) { Vector3i playerChunkPos = TheRegion.ChunkLocFor(Player.GetPosition()); if (playerChunkPos != SunChunkPos || Math.Abs((SunAngle - pSunAng).BiggestValue()) > 0.1f) { SunChunkPos = playerChunkPos; Location corPos = (SunChunkPos.ToLocation() * Constants.CHUNK_WIDTH) + new Location(Constants.CHUNK_WIDTH * 0.5); TheSun.Direction = Utilities.ForwardVector_Deg(SunAngle.Yaw, SunAngle.Pitch); TheSun.Reposition(corPos - TheSun.Direction * 30 * 6); TheSunClouds.Direction = TheSun.Direction; TheSunClouds.Reposition(TheSun.EyePos); PlanetDir = Utilities.ForwardVector_Deg(PlanetAngle.Yaw, PlanetAngle.Pitch); ThePlanet.Direction = PlanetDir; ThePlanet.Reposition(corPos - ThePlanet.Direction * 30 * 6); BEPUutilities.Vector3 tsd = TheSun.Direction.ToBVector(); BEPUutilities.Vector3 tpd = PlanetDir.ToBVector(); BEPUutilities.Quaternion.GetQuaternionBetweenNormalizedVectors(ref tsd, ref tpd, out BEPUutilities.Quaternion diff); PlanetSunDist = (float)BEPUutilities.Quaternion.GetAngleFromQuaternion(ref diff) / (float)Utilities.PI180; if (PlanetSunDist < 75) { TheSun.InternalLights[0].color = new OpenTK.Vector3((float)Math.Min(SunLightDef.X * (PlanetSunDist / 15), 1), (float)Math.Min(SunLightDef.Y * (PlanetSunDist / 20), 1), (float)Math.Min(SunLightDef.Z * (PlanetSunDist / 60), 1)); TheSunClouds.InternalLights[0].color = new OpenTK.Vector3((float)Math.Min(CloudSunLightDef.X * (PlanetSunDist / 15), 1), (float)Math.Min(CloudSunLightDef.Y * (PlanetSunDist / 20), 1), (float)Math.Min(CloudSunLightDef.Z * (PlanetSunDist / 60), 1)); //ThePlanet.InternalLights[0].color = new OpenTK.Vector3(0, 0, 0); } else { TheSun.InternalLights[0].color = ClientUtilities.Convert(SunLightDef); TheSunClouds.InternalLights[0].color = ClientUtilities.Convert(CloudSunLightDef); //ThePlanet.InternalLights[0].color = ClientUtilities.Convert(PlanetLightDef * Math.Min((PlanetSunDist / 180f), 1f)); } PlanetLight = PlanetSunDist / 180f; if (SunAngle.Pitch < 10 && SunAngle.Pitch > -30) { float rel = 30 + (float)SunAngle.Pitch; if (rel == 0) { rel = 0.00001f; } rel = 1f - (rel / 40f); rel = Math.Max(Math.Min(rel, 1f), 0f); float rel2 = Math.Max(Math.Min(rel * 1.5f, 1f), 0f); TheSun.InternalLights[0].color = new OpenTK.Vector3(TheSun.InternalLights[0].color.X * rel2, TheSun.InternalLights[0].color.Y * rel, TheSun.InternalLights[0].color.Z * rel); TheSunClouds.InternalLights[0].color = new OpenTK.Vector3(TheSunClouds.InternalLights[0].color.X * rel2, TheSunClouds.InternalLights[0].color.Y * rel, TheSunClouds.InternalLights[0].color.Z * rel); MainWorldView.DesaturationAmount = (1f - rel) * 0.75f; MainWorldView.ambient = BaseAmbient * ((1f - rel) * 0.5f + 0.5f); sl_min = 0.2f - (1f - rel) * (0.2f - 0.05f); sl_max = 0.8f - (1f - rel) * (0.8f - 0.15f); SkyColor = SkyApproxColDefault * rel; } else if (SunAngle.Pitch >= 10) { TheSun.InternalLights[0].color = new OpenTK.Vector3(0, 0, 0); TheSunClouds.InternalLights[0].color = new OpenTK.Vector3(0, 0, 0); MainWorldView.DesaturationAmount = 0.75f; MainWorldView.ambient = BaseAmbient * 0.5f; sl_min = 0.05f; sl_max = 0.15f; SkyColor = Location.Zero; } else { sl_min = 0.2f; sl_max = 0.8f; MainWorldView.DesaturationAmount = 0f; MainWorldView.ambient = BaseAmbient; TheSun.InternalLights[0].color = ClientUtilities.Convert(SunLightDef); TheSunClouds.InternalLights[0].color = ClientUtilities.Convert(CloudSunLightDef); SkyColor = SkyApproxColDefault; } shouldRedrawShadows = true; } rTicks = 0; } TheRegion.TickWorld(delta); }
private void LoadShip() { Vector3[] vertices = new Vector3[0]; int[] indices = new int[0]; Model shipModel = Resources.Instance.GetModel("ship"); int mass = 5; Vector3 scale = new Vector3(3, 3, 3); ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid1"), out vertices, out indices); MobileMesh mobMesh = new MobileMesh(vertices, indices, new AffineTransform(scale, BEPUutilities.Quaternion.Identity, BEPUutilities.Vector3.Zero), BEPUphysics.CollisionShapes.MobileMeshSolidity.Solid, mass); mobMesh.Tag = "ship"; mobMesh.CollisionInformation.Events.InitialCollisionDetected += HandleCollision; space.Add(mobMesh); mobMesh.AngularDamping = 0; mobMesh.LinearDamping = 0; mobMesh.LinearVelocity = BEPUutilities.Vector3.Zero; mobMesh.AngularVelocity = BEPUutilities.Vector3.Zero; MobileMeshModel model = new MobileMeshModel(game, mobMesh, shipModel, scale.X, this, true); Ship = model; game.Components.Add(model); }
public override void Update(GameTime gameTime) { base.Update(gameTime); Stack<Emitter> toRemove = new Stack<Emitter>(); foreach (Emitter e in emitters) { e.Update(gameTime, Camera); if (e.Remove) { toRemove.Push(e); } } while (toRemove.Count > 0) emitters.Remove(toRemove.Pop()); Resources.Instance.RemainingAsteroids = modelLookup.Count; if (!Resources.Instance.GameOver) { ButtonState currentState = Mouse.GetState().LeftButton; Camera.Update((float)gameTime.ElapsedGameTime.TotalSeconds); RayCastResult rayCastResult; Vector3 rayStart = Camera.Position + Camera.Forward * 5; Vector3 rayDirection = Camera.Forward; space.RayCast(new BEPUutilities.Ray(rayStart, rayDirection), out rayCastResult); if (currentState != _prevState && _prevState == ButtonState.Pressed) { _shoot = true; Resources.Instance.GetSound("laser").Play(); } try { int obj = Convert.ToInt32(rayCastResult.HitObject.Tag); if (currentState != _prevState && _prevState == ButtonState.Pressed) { Resources.Instance.Score += 100; Resources.Instance.GetSound("explosion").Play(); Vector3 pos = new Vector3(modelLookup[obj]._mesh.Position.X, modelLookup[obj]._mesh.Position.Y, modelLookup[obj]._mesh.Position.Z); Console.WriteLine(pos.ToString()); emitters.Add(new Emitter(game, pos)); space.Remove(modelLookup[obj]._mesh); game.Components.Remove(modelLookup[obj]); modelLookup.Remove(obj); } } catch (Exception) { ;} space.Update(); _prevState = currentState; } }
private void CreateAsteroids() { Vector3[] vertices = new Vector3[0]; int[] indices = new int[0]; Model asteroidPicked = Resources.Instance.GetModel("asteroid1"); int mass = 0; Vector3 scale = new Vector3(0, 0, 0); List<Vector3> asteroidLocations = spawner.GetAsteroidLocations(); for (int i = 0; i < asteroidLocations.Count; i++) { int rand = GameInformation.Instance.Rand.Next(0, 5); switch (rand) { case 0: ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid1"), out vertices, out indices); asteroidPicked = Resources.Instance.GetModel("asteroid1"); scale = new Vector3(3, 3, 3); mass = 5; break; case 1: ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid2"), out vertices, out indices); asteroidPicked = Resources.Instance.GetModel("asteroid2"); scale = new Vector3(3, 3, 3); mass = 5; break; case 2: ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid3"), out vertices, out indices); asteroidPicked = Resources.Instance.GetModel("asteroid3"); scale = new Vector3(5, 5, 5); mass = 30; break; case 3: ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid4"), out vertices, out indices); asteroidPicked = Resources.Instance.GetModel("asteroid4"); scale = new Vector3(5, 5, 5); mass = 30; break; case 4: ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid5"), out vertices, out indices); asteroidPicked = Resources.Instance.GetModel("asteroid5"); scale = new Vector3(6, 6, 6); mass = 45; break; case 5: ModelDataExtractor.GetVerticesAndIndicesFromModel(Resources.Instance.GetModel("asteroid6"), out vertices, out indices); asteroidPicked = Resources.Instance.GetModel("asteroid6"); scale = new Vector3(6, 6, 6); mass = 45; break; } MobileMesh mobMesh = new MobileMesh(vertices, indices, new AffineTransform(scale, BEPUutilities.Quaternion.Identity, asteroidLocations[i]), BEPUphysics.CollisionShapes.MobileMeshSolidity.Solid, mass); mobMesh.CollisionInformation.Tag = i.ToString(); space.Add(mobMesh); mobMesh.AngularDamping = 0; mobMesh.LinearDamping = 0; mobMesh.LinearVelocity = new Vector3(GameInformation.Instance.Rand.Next(0, 30) - 15, GameInformation.Instance.Rand.Next(0, 30) - 15, GameInformation.Instance.Rand.Next(0, 30) - 15); mobMesh.AngularVelocity = new Vector3(GameInformation.Instance.Rand.Next(1, 10) - 5, GameInformation.Instance.Rand.Next(1, 10) - 5, GameInformation.Instance.Rand.Next(1, 10) - 5); MobileMeshModel model = new MobileMeshModel(game, mobMesh, asteroidPicked, scale.X, this); modelLookup.Add(i, model); game.Components.Add(model); } }
public Emitter(Game game, Vector3 position) { theGame = game; System = new ExplosionParticleSystem(game, game.Content); game.Components.Add(System); ParticleEmitter = new ParticleEmitter(System, 100, MathConverter.Convert(position)); Life = 0; Remove = false; this.Position = position; }
void BuildStick(Vector3 position) { //Set up a bone chain. float fullLength = 20; int linkCount = 20; float linkLength = fullLength / linkCount; float linkRadius = linkLength * 0.2f; var previousBoneEntity = new Cylinder(position, linkLength, linkRadius, 100); var previousBone = new Bone(previousBoneEntity.Position, previousBoneEntity.Orientation, previousBoneEntity.Radius, previousBoneEntity.Height); bones.Add(new BoneRelationship(previousBone, previousBoneEntity)); Space.Add(previousBoneEntity); for (int i = 1; i < linkCount; i++) { var boneEntity = new Cylinder(previousBone.Position + new Vector3(0, linkLength, 0), linkLength, linkRadius, 100); var bone = new Bone(boneEntity.Position, boneEntity.Orientation, boneEntity.Radius, boneEntity.Height); bones.Add(new BoneRelationship(bone, boneEntity)); Space.Add(boneEntity); //Make a relationship between the two bones and entities. CollisionRules.AddRule(previousBoneEntity, boneEntity, CollisionRule.NoBroadPhase); Vector3 anchor = (previousBoneEntity.Position + boneEntity.Position) / 2; var dynamicsBallSocketJoint = new BallSocketJoint(previousBoneEntity, boneEntity, anchor); var dynamicsAngularFriction = new NoRotationJoint(previousBoneEntity, boneEntity); Space.Add(dynamicsBallSocketJoint); Space.Add(dynamicsAngularFriction); var ikBallSocketJoint = new IKBallSocketJoint(previousBone, bone, anchor); //(the joint is auto-added to the bones; no solver-add is needed) var ikAngularJoint = new IKAngularJoint(previousBone, bone); joints.Add(ikBallSocketJoint); joints.Add(ikAngularJoint); previousBone = bone; previousBoneEntity = boneEntity; } }
// Start is called before the first frame update void Start() { world.ForceUpdater.Gravity = new BEPUutilities.Vector3(0, -9.81f, 0); // floor world.Add(new Box(new BEPUutilities.Vector3(0, -1.0f, 0), 30, 1, 30)); GameObject prefab = Resources.Load("elsa") as GameObject; GameObject actor = MonoBehaviour.Instantiate(prefab, new Vector3(0, 3, 0), Quaternion.Euler(new Vector3(0, 0, 0))) as GameObject; var ac = actor.AddComponent <testActor>(); ac.cc = new BEPUphysics.Character.CharacterController(new BEPUutilities.Vector3(0, 3, 0), 1.0f, 1.0f * 0.7f, 1.0f * 0.3f, 0.5f, 0.001f, 10f, 0.8f, 1.3f, 8f, 3f, 1.5f, 1000f, 0, 0, 0, 0, 0, 0); world.Add(ac.cc); var vertices = new BEPUutilities.Vector3[] { new BEPUutilities.Vector3(-0.454f, 0.087f, -0.413f), new BEPUutilities.Vector3(-0.454f, 0.087f, 0.29f), new BEPUutilities.Vector3(-0.454f, 0.79f, -0.413f), new BEPUutilities.Vector3(0.454f, 0.79f, -0.413f), new BEPUutilities.Vector3(0.454f, 0.087f, 0.29f), new BEPUutilities.Vector3(0.454f, 0.087f, -0.413f), new BEPUutilities.Vector3(-0.333f, 1f, -0.5f), new BEPUutilities.Vector3(-0.333f, 0f, 0.5f), new BEPUutilities.Vector3(0.333f, 1f, -0.5f), new BEPUutilities.Vector3(0.333f, 0f, 0.5f), new BEPUutilities.Vector3(-0.333f, 1f, -0.5f), new BEPUutilities.Vector3(-0.5f, 0f, -0.5f), new BEPUutilities.Vector3(-0.5f, 1f, -0.5f), new BEPUutilities.Vector3(0.5f, 0f, -0.5f), new BEPUutilities.Vector3(0.333f, 1f, -0.5f), new BEPUutilities.Vector3(0.5f, 1f, -0.5f), new BEPUutilities.Vector3(-0.5f, 1f, -0.5f), new BEPUutilities.Vector3(-0.474f, 1.058f, -0.5f), new BEPUutilities.Vector3(-0.355f, 1.058f, -0.5f), new BEPUutilities.Vector3(-0.5f, 0f, -0.5f), new BEPUutilities.Vector3(-0.333f, 0f, 0.5f), new BEPUutilities.Vector3(-0.5f, 0f, 0.5f), new BEPUutilities.Vector3(0.333f, 0f, 0.5f), new BEPUutilities.Vector3(0.5f, 0f, -0.5f), new BEPUutilities.Vector3(0.5f, 0f, 0.5f), new BEPUutilities.Vector3(0.355f, 0.058f, 0.5f), new BEPUutilities.Vector3(0.474f, 1.058f, -0.5f), new BEPUutilities.Vector3(0.355f, 1.058f, -0.5f), new BEPUutilities.Vector3(0.474f, 0.058f, 0.5f), new BEPUutilities.Vector3(-0.355f, 1.058f, -0.5f), new BEPUutilities.Vector3(-0.474f, 1.058f, -0.5f), new BEPUutilities.Vector3(-0.474f, 0.058f, 0.5f), new BEPUutilities.Vector3(-0.355f, 0.058f, 0.5f), new BEPUutilities.Vector3(0.333f, 1f, -0.5f), new BEPUutilities.Vector3(0.474f, 1.058f, -0.5f), new BEPUutilities.Vector3(0.5f, 1f, -0.5f), new BEPUutilities.Vector3(0.355f, 1.058f, -0.5f), new BEPUutilities.Vector3(0.474f, 0.058f, 0.5f), new BEPUutilities.Vector3(0.5f, 0f, 0.5f), new BEPUutilities.Vector3(0.5f, 1f, -0.5f), new BEPUutilities.Vector3(0.474f, 1.058f, -0.5f), new BEPUutilities.Vector3(0.333f, 0f, 0.5f), new BEPUutilities.Vector3(0.5f, 0f, 0.5f), new BEPUutilities.Vector3(0.474f, 0.058f, 0.5f), new BEPUutilities.Vector3(0.355f, 0.058f, 0.5f), new BEPUutilities.Vector3(0.355f, 0.058f, 0.5f), new BEPUutilities.Vector3(0.355f, 1.058f, -0.5f), new BEPUutilities.Vector3(0.333f, 1f, -0.5f), new BEPUutilities.Vector3(0.333f, 0f, 0.5f), new BEPUutilities.Vector3(-0.333f, 0f, 0.5f), new BEPUutilities.Vector3(-0.474f, 0.058f, 0.5f), new BEPUutilities.Vector3(-0.5f, 0f, 0.5f), new BEPUutilities.Vector3(-0.355f, 0.058f, 0.5f), new BEPUutilities.Vector3(-0.474f, 0.058f, 0.5f), new BEPUutilities.Vector3(-0.474f, 1.058f, -0.5f), new BEPUutilities.Vector3(-0.5f, 1f, -0.5f), new BEPUutilities.Vector3(-0.5f, 0f, 0.5f), new BEPUutilities.Vector3(-0.355f, 0.058f, 0.5f), new BEPUutilities.Vector3(-0.333f, 0f, 0.5f), new BEPUutilities.Vector3(-0.333f, 1f, -0.5f), new BEPUutilities.Vector3(-0.355f, 1.058f, -0.5f), new BEPUutilities.Vector3(-0.5f, 0.049f, -0.451f), new BEPUutilities.Vector3(-0.454f, 0.79f, -0.413f), new BEPUutilities.Vector3(-0.5f, 0.882f, -0.451f), new BEPUutilities.Vector3(-0.454f, 0.087f, -0.413f), new BEPUutilities.Vector3(-0.5f, 0.049f, 0.382f), new BEPUutilities.Vector3(-0.5f, 0.882f, -0.451f), new BEPUutilities.Vector3(-0.454f, 0.79f, -0.413f), new BEPUutilities.Vector3(-0.454f, 0.087f, 0.29f), new BEPUutilities.Vector3(-0.5f, 0.049f, -0.451f), new BEPUutilities.Vector3(-0.5f, 0.049f, 0.382f), new BEPUutilities.Vector3(-0.454f, 0.087f, 0.29f), new BEPUutilities.Vector3(-0.454f, 0.087f, -0.413f), new BEPUutilities.Vector3(0.5f, 0.049f, -0.451f), new BEPUutilities.Vector3(0.5f, 0.882f, -0.451f), new BEPUutilities.Vector3(0.454f, 0.79f, -0.413f), new BEPUutilities.Vector3(0.454f, 0.087f, -0.413f), new BEPUutilities.Vector3(0.454f, 0.087f, 0.29f), new BEPUutilities.Vector3(0.5f, 0.049f, -0.451f), new BEPUutilities.Vector3(0.454f, 0.087f, -0.413f), new BEPUutilities.Vector3(0.5f, 0.049f, 0.382f), new BEPUutilities.Vector3(0.5f, 0.049f, 0.382f), new BEPUutilities.Vector3(0.454f, 0.79f, -0.413f), new BEPUutilities.Vector3(0.5f, 0.882f, -0.451f), new BEPUutilities.Vector3(0.454f, 0.087f, 0.29f), new BEPUutilities.Vector3(-0.5f, 0f, -0.5f), new BEPUutilities.Vector3(-0.5f, 0.049f, -0.451f), new BEPUutilities.Vector3(-0.5f, 0.882f, -0.451f), new BEPUutilities.Vector3(-0.5f, 0.049f, 0.382f), new BEPUutilities.Vector3(-0.5f, 1f, -0.5f), new BEPUutilities.Vector3(-0.5f, 0f, 0.5f), new BEPUutilities.Vector3(0.5f, 0.882f, -0.451f), new BEPUutilities.Vector3(0.5f, 0.049f, -0.451f), new BEPUutilities.Vector3(0.5f, 0f, -0.5f), new BEPUutilities.Vector3(0.5f, 0.049f, 0.382f), new BEPUutilities.Vector3(0.5f, 1f, -0.5f), new BEPUutilities.Vector3(0.5f, 0f, 0.5f), }; int[] indices = new int[] { 0, 1, 2, 3, 4, 5, 6, 7, 8, 8, 7, 9, 10, 11, 12, 10, 13, 11, 10, 14, 13, 13, 14, 15, 10, 16, 17, 17, 18, 10, 19, 20, 21, 22, 20, 19, 19, 23, 22, 22, 23, 24, 25, 26, 27, 26, 25, 28, 29, 30, 31, 31, 32, 29, 33, 34, 35, 33, 36, 34, 37, 38, 39, 37, 39, 40, 41, 42, 43, 43, 44, 41, 45, 46, 47, 47, 48, 45, 49, 50, 51, 49, 52, 50, 53, 54, 55, 55, 56, 53, 57, 58, 59, 57, 59, 60, 61, 62, 63, 61, 64, 62, 65, 66, 67, 67, 68, 65, 69, 70, 71, 71, 72, 69, 73, 74, 75, 75, 76, 73, 77, 78, 79, 78, 77, 80, 81, 82, 83, 81, 84, 82, 85, 86, 87, 88, 86, 85, 85, 87, 89, 89, 87, 88, 85, 90, 88, 89, 88, 90, 91, 92, 93, 93, 92, 94, 93, 95, 91, 94, 91, 95, 93, 94, 96, 95, 96, 94 }; var stair = new BEPUphysics.BroadPhaseEntries.StaticMesh(vertices, indices, new BEPUutilities.AffineTransform(new BEPUutilities.Vector3(0.5f, 0.5f, 0.5f), BEPUutilities.Quaternion.Identity, new BEPUutilities.Vector3(0, 0, 0))); world.Add(stair); }
private void BuildSimulation(Vector3 offset, Simulator simulator) { //Create a lattice of dynamic objects. int width = 30; int height = 10; int length = 30; float spacing = 3; var dynamics = new LinearDynamic[width, height, length]; for (int widthIndex = 0; widthIndex < width; ++widthIndex) { for (int heightIndex = 0; heightIndex < height; ++heightIndex) { for (int lengthIndex = 0; lengthIndex < length; ++lengthIndex) { var dynamic = new LinearDynamic(10) { Position = offset + new Vector3(spacing * widthIndex, spacing * heightIndex + 10, spacing * lengthIndex) }; dynamics[widthIndex, heightIndex, lengthIndex] = dynamic; simulator.Add(dynamic); } } } Vector3 normal = new Vector3(0, 1, 0); Plane plane = new Plane(normal, -Vector3.Dot(offset, normal)); //Create a bunch of connections between the dynamic objects. for (int widthIndex = 0; widthIndex < width; ++widthIndex) { for (int heightIndex = 0; heightIndex < height; ++heightIndex) { for (int lengthIndex = 0; lengthIndex < length; ++lengthIndex) { //Create a connection with the dynamics at +x, +y, +z, +x+y+z, -x+y+z, +x-y+z, +x+y-z //+x if (widthIndex + 1 < width) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex + 1, heightIndex, lengthIndex])); } //+y if (heightIndex + 1 < height) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex, heightIndex + 1, lengthIndex])); } //+z if (lengthIndex + 1 < length) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex, heightIndex, lengthIndex + 1])); } //+x+y+z if (widthIndex + 1 < width && heightIndex + 1 < height && lengthIndex + 1 < length) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex + 1, heightIndex + 1, lengthIndex + 1])); } //-x+y+z if (widthIndex - 1 >= 0 && heightIndex + 1 < height && lengthIndex + 1 < length) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex - 1, heightIndex + 1, lengthIndex + 1])); } //+x-y+z if (widthIndex + 1 < width && heightIndex - 1 >= 0 && lengthIndex + 1 < length) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex + 1, heightIndex - 1, lengthIndex + 1])); } //+x+y-z if (widthIndex + 1 < width && heightIndex + 1 < height && lengthIndex - 1 >= 0) { simulator.Add(new DistanceConstraint(dynamics[widthIndex, heightIndex, lengthIndex], dynamics[widthIndex + 1, heightIndex + 1, lengthIndex - 1])); } //Create a plane constraint to stop the object from falling. simulator.Add(new PlaneCollisionConstraint(dynamics[widthIndex, heightIndex, lengthIndex], plane)); } } } }
private bool RayCastBones(Ray ray, out BoneRelationship hitBone, out Vector3 hitPosition) { float t = float.MaxValue; hitBone = new BoneRelationship(); hitPosition = new Vector3(); for (int i = 0; i < bones.Count; i++) { var bone = bones[i].Bone; RayHit hit; if (RayCast(bone, ray, out hit) && hit.T < t) { t = hit.T; hitPosition = hit.Location; hitBone = bones[i]; } } return t < float.MaxValue; }
public static bool EpsilonEqual(this BEPUutilities.Vector3 lhs, BEPUutilities.Vector3 rhs) { float epsilon = 0.0001f; return(Math.Abs(lhs.X - rhs.X) < epsilon && Math.Abs(lhs.Y - rhs.Y) < epsilon && Math.Abs(lhs.Z - rhs.Z) < epsilon); }
void BuildActionFigure(Vector3 position) { //Make a simple, poseable action figure, like the ActionFigureDemo. Entity body = new Box(position, 1.5f, 2, 1, 10); Space.Add(body); Entity head = new Sphere(body.Position + new Vector3(0, 2, 0), .5f, 5); Space.Add(head); //Connect the head to the body. var headBodyBallSocketAnchor = head.Position + new Vector3(0, -.75f, 0); Space.Add(new BallSocketJoint(body, head, headBodyBallSocketAnchor)); //Angular motors can be used to simulate friction when their goal velocity is 0. var angularMotor = new AngularMotor(body, head); angularMotor.Settings.MaximumForce = 150; //The maximum force of 'friction' in this joint. Space.Add(angularMotor); //Make the first arm. var upperLeftArm = new Box(body.Position + new Vector3(-1.6f, .8f, 0), 1, .5f, .5f, 5); Space.Add(upperLeftArm); var lowerLeftArm = new Box(upperLeftArm.Position + new Vector3(-1.4f, 0, 0), 1, .5f, .5f, 5); Space.Add(lowerLeftArm); var leftHand = new Box(lowerLeftArm.Position + new Vector3(-.8f, 0, 0), 0.5f, 0.3f, 0.5f, 4); Space.Add(leftHand); //Connect the body to the upper arm. var bodyUpperLeftArmBallSocketAnchor = upperLeftArm.Position + new Vector3(.7f, 0, 0); Space.Add(new BallSocketJoint(body, upperLeftArm, bodyUpperLeftArmBallSocketAnchor)); angularMotor = new AngularMotor(body, upperLeftArm); angularMotor.Settings.MaximumForce = 250; Space.Add(angularMotor); //Connect the upper arm to the lower arm. var upperLeftArmLowerLeftArmBallSocketAnchor = upperLeftArm.Position + new Vector3(-.7f, 0, 0); Space.Add(new BallSocketJoint(upperLeftArm, lowerLeftArm, upperLeftArmLowerLeftArmBallSocketAnchor)); angularMotor = new AngularMotor(upperLeftArm, lowerLeftArm); angularMotor.Settings.MaximumForce = 150; Space.Add(angularMotor); //Connect the lower arm to the hand. var lowerLeftArmLeftHandBallSocketAnchor = lowerLeftArm.Position + new Vector3(-.5f, 0, 0); Space.Add(new BallSocketJoint(lowerLeftArm, leftHand, lowerLeftArmLeftHandBallSocketAnchor)); angularMotor = new AngularMotor(lowerLeftArm, leftHand); angularMotor.Settings.MaximumForce = 150; Space.Add(angularMotor); //Make the second arm. var upperRightArm = new Box(body.Position + new Vector3(1.6f, .8f, 0), 1, .5f, .5f, 5); Space.Add(upperRightArm); var lowerRightArm = new Box(upperRightArm.Position + new Vector3(1.4f, 0, 0), 1, .5f, .5f, 5); Space.Add(lowerRightArm); var rightHand = new Box(lowerRightArm.Position + new Vector3(.8f, 0, 0), 0.5f, 0.3f, 0.5f, 4); Space.Add(rightHand); //Connect the body to the upper arm. var bodyUpperRightArmBallSocketAnchor = upperRightArm.Position + new Vector3(-.7f, 0, 0); Space.Add(new BallSocketJoint(body, upperRightArm, bodyUpperRightArmBallSocketAnchor)); //Angular motors can be used to simulate friction when their goal velocity is 0. angularMotor = new AngularMotor(body, upperRightArm); angularMotor.Settings.MaximumForce = 250; //The maximum force of 'friction' in this joint. Space.Add(angularMotor); //Connect the upper arm to the lower arm. var upperRightArmLowerRightArmBallSocketAnchor = upperRightArm.Position + new Vector3(.7f, 0, 0); Space.Add(new BallSocketJoint(upperRightArm, lowerRightArm, upperRightArmLowerRightArmBallSocketAnchor)); angularMotor = new AngularMotor(upperRightArm, lowerRightArm); angularMotor.Settings.MaximumForce = 150; Space.Add(angularMotor); //Connect the lower arm to the hand. var lowerRightArmRightHandBallSocketAnchor = lowerRightArm.Position + new Vector3(.5f, 0, 0); Space.Add(new BallSocketJoint(lowerRightArm, rightHand, lowerRightArmRightHandBallSocketAnchor)); angularMotor = new AngularMotor(lowerRightArm, rightHand); angularMotor.Settings.MaximumForce = 150; Space.Add(angularMotor); //Make the first leg. var upperLeftLeg = new Box(body.Position + new Vector3(-.6f, -2.1f, 0), .5f, 1.3f, .5f, 8); Space.Add(upperLeftLeg); var lowerLeftLeg = new Box(upperLeftLeg.Position + new Vector3(0, -1.7f, 0), .5f, 1.3f, .5f, 8); Space.Add(lowerLeftLeg); var leftFoot = new Box(lowerLeftLeg.Position + new Vector3(0, -.25f - 0.65f, 0.25f), .5f, .4f, 1, 8); Space.Add(leftFoot); //Connect the body to the upper leg. var bodyUpperLeftLegBallSocketAnchor = upperLeftLeg.Position + new Vector3(0, .9f, 0); Space.Add(new BallSocketJoint(body, upperLeftLeg, bodyUpperLeftLegBallSocketAnchor)); //Angular motors can be used to simulate friction when their goal velocity is 0. angularMotor = new AngularMotor(body, upperLeftLeg); angularMotor.Settings.MaximumForce = 350; //The maximum force of 'friction' in this joint. Space.Add(angularMotor); //Connect the upper leg to the lower leg. var upperLeftLegLowerLeftLegBallSocketAnchor = upperLeftLeg.Position + new Vector3(0, -.9f, 0); Space.Add(new BallSocketJoint(upperLeftLeg, lowerLeftLeg, upperLeftLegLowerLeftLegBallSocketAnchor)); angularMotor = new AngularMotor(upperLeftLeg, lowerLeftLeg); angularMotor.Settings.MaximumForce = 250; Space.Add(angularMotor); //Connect the lower leg to the foot. var lowerLeftLegLeftFootBallSocketAnchor = lowerLeftLeg.Position + new Vector3(0, -.65f, 0); Space.Add(new BallSocketJoint(lowerLeftLeg, leftFoot, lowerLeftLegLeftFootBallSocketAnchor)); angularMotor = new AngularMotor(lowerLeftLeg, leftFoot); angularMotor.Settings.MaximumForce = 250; Space.Add(angularMotor); //Make the second leg. var upperRightLeg = new Box(body.Position + new Vector3(.6f, -2.1f, 0), .5f, 1.3f, .5f, 8); Space.Add(upperRightLeg); var lowerRightLeg = new Box(upperRightLeg.Position + new Vector3(0, -1.7f, 0), .5f, 1.3f, .5f, 8); Space.Add(lowerRightLeg); var rightFoot = new Box(lowerRightLeg.Position + new Vector3(0, -.25f - 0.65f, 0.25f), .5f, .4f, 1, 8); Space.Add(rightFoot); //Connect the body to the upper leg. var bodyUpperRightLegBallSocketAnchor = upperRightLeg.Position + new Vector3(0, .9f, 0); Space.Add(new BallSocketJoint(body, upperRightLeg, bodyUpperRightLegBallSocketAnchor)); //Angular motors can be used to simulate friction when their goal velocity is 0. angularMotor = new AngularMotor(body, upperRightLeg); angularMotor.Settings.MaximumForce = 350; //The maximum force of 'friction' in this joint. Space.Add(angularMotor); //Connect the upper leg to the lower leg. var upperRightLegLowerRightLegBallSocketAnchor = upperRightLeg.Position + new Vector3(0, -.9f, 0); Space.Add(new BallSocketJoint(upperRightLeg, lowerRightLeg, upperRightLegLowerRightLegBallSocketAnchor)); angularMotor = new AngularMotor(upperRightLeg, lowerRightLeg); angularMotor.Settings.MaximumForce = 250; Space.Add(angularMotor); //Connect the lower leg to the foot. var lowerRightLegRightFootBallSocketAnchor = lowerRightLeg.Position + new Vector3(0, -.65f, 0); Space.Add(new BallSocketJoint(lowerRightLeg, rightFoot, lowerRightLegRightFootBallSocketAnchor)); angularMotor = new AngularMotor(lowerRightLeg, rightFoot); angularMotor.Settings.MaximumForce = 250; Space.Add(angularMotor); //Set up collision rules. CollisionRules.AddRule(head, body, CollisionRule.NoBroadPhase); CollisionRules.AddRule(body, upperLeftArm, CollisionRule.NoBroadPhase); CollisionRules.AddRule(upperLeftArm, lowerLeftArm, CollisionRule.NoBroadPhase); CollisionRules.AddRule(lowerLeftArm, leftHand, CollisionRule.NoBroadPhase); CollisionRules.AddRule(body, upperRightArm, CollisionRule.NoBroadPhase); CollisionRules.AddRule(upperRightArm, lowerRightArm, CollisionRule.NoBroadPhase); CollisionRules.AddRule(lowerRightArm, rightHand, CollisionRule.NoBroadPhase); CollisionRules.AddRule(body, upperLeftLeg, CollisionRule.NoBroadPhase); CollisionRules.AddRule(upperLeftLeg, lowerLeftLeg, CollisionRule.NoBroadPhase); CollisionRules.AddRule(lowerLeftLeg, leftFoot, CollisionRule.NoBroadPhase); CollisionRules.AddRule(body, upperRightLeg, CollisionRule.NoBroadPhase); CollisionRules.AddRule(upperRightLeg, lowerRightLeg, CollisionRule.NoBroadPhase); CollisionRules.AddRule(lowerRightLeg, rightFoot, CollisionRule.NoBroadPhase); //IK version! Bone bodyBone = new Bone(body.Position, Quaternion.Identity, .75f, 2); Bone headBone = new Bone(head.Position, Quaternion.Identity, .4f, .8f); Bone upperLeftArmBone = new Bone(upperLeftArm.Position, Quaternion.CreateFromAxisAngle(new Vector3(0, 0, 1), MathHelper.PiOver2), .25f, 1); Bone lowerLeftArmBone = new Bone(lowerLeftArm.Position, Quaternion.CreateFromAxisAngle(new Vector3(0, 0, 1), MathHelper.PiOver2), .25f, 1); Bone upperRightArmBone = new Bone(upperRightArm.Position, Quaternion.CreateFromAxisAngle(new Vector3(0, 0, 1), MathHelper.PiOver2), .25f, 1); Bone lowerRightArmBone = new Bone(lowerRightArm.Position, Quaternion.CreateFromAxisAngle(new Vector3(0, 0, 1), MathHelper.PiOver2), .25f, 1); Bone leftHandBone = new Bone(leftHand.Position, Quaternion.CreateFromAxisAngle(new Vector3(0, 0, 1), MathHelper.PiOver2), .2f, .5f); Bone rightHandBone = new Bone(rightHand.Position, Quaternion.CreateFromAxisAngle(new Vector3(0, 0, 1), MathHelper.PiOver2), .2f, .5f); Bone upperLeftLegBone = new Bone(upperLeftLeg.Position, Quaternion.Identity, .25f, 1.3f); Bone lowerLeftLegBone = new Bone(lowerLeftLeg.Position, Quaternion.Identity, .25f, 1.3f); Bone leftFootBone = new Bone(leftFoot.Position, Quaternion.CreateFromAxisAngle(new Vector3(1, 0, 0), MathHelper.PiOver2), .25f, 1); Bone upperRightLegBone = new Bone(upperRightLeg.Position, Quaternion.Identity, .25f, 1.3f); Bone lowerRightLegBone = new Bone(lowerRightLeg.Position, Quaternion.Identity, .25f, 1.3f); Bone rightFootBone = new Bone(rightFoot.Position, Quaternion.CreateFromAxisAngle(new Vector3(1, 0, 0), MathHelper.PiOver2), .25f, 1); bones.Add(new BoneRelationship(bodyBone, body)); bones.Add(new BoneRelationship(headBone, head)); bones.Add(new BoneRelationship(upperLeftArmBone, upperLeftArm)); bones.Add(new BoneRelationship(lowerLeftArmBone, lowerLeftArm)); bones.Add(new BoneRelationship(upperRightArmBone, upperRightArm)); bones.Add(new BoneRelationship(lowerRightArmBone, lowerRightArm)); bones.Add(new BoneRelationship(leftHandBone, leftHand)); bones.Add(new BoneRelationship(rightHandBone, rightHand)); bones.Add(new BoneRelationship(upperLeftLegBone, upperLeftLeg)); bones.Add(new BoneRelationship(lowerLeftLegBone, lowerLeftLeg)); bones.Add(new BoneRelationship(leftFootBone, leftFoot)); bones.Add(new BoneRelationship(upperRightLegBone, upperRightLeg)); bones.Add(new BoneRelationship(lowerRightLegBone, lowerRightLeg)); bones.Add(new BoneRelationship(rightFootBone, rightFoot)); //[We don't care about the return values here. A bit weird, but the constructor puts the reference where it needs to go.] joints.Add(new IKBallSocketJoint(bodyBone, headBone, headBodyBallSocketAnchor)); joints.Add(new IKSwingLimit(bodyBone, headBone, Vector3.Up, Vector3.Up, MathHelper.PiOver2)); joints.Add(new IKTwistLimit(bodyBone, headBone, Vector3.Up, Vector3.Up, MathHelper.PiOver2)); //Left arm joints.Add(new IKBallSocketJoint(bodyBone, upperLeftArmBone, bodyUpperLeftArmBallSocketAnchor)); joints.Add(new IKSwingLimit(bodyBone, upperLeftArmBone, Vector3.Normalize(new Vector3(-1, 0, .3f)), Vector3.Left, MathHelper.Pi * .65f)); joints.Add(new IKTwistLimit(bodyBone, upperLeftArmBone, Vector3.Left, Vector3.Left, MathHelper.PiOver2) { Rigidity = 0.08f }); joints.Add(new IKBallSocketJoint(upperLeftArmBone, lowerLeftArmBone, upperLeftArmLowerLeftArmBallSocketAnchor)); joints.Add(new IKSwivelHingeJoint(upperLeftArmBone, lowerLeftArmBone, Vector3.Up, Vector3.Left)); joints.Add(new IKSwingLimit(upperLeftArmBone, lowerLeftArmBone, Vector3.Normalize(new Vector3(-0.23f, 0, .97f)), Vector3.Left, MathHelper.Pi * 0.435f)); joints.Add(new IKTwistLimit(upperLeftArmBone, lowerLeftArmBone, Vector3.Left, Vector3.Left, MathHelper.PiOver4) { Rigidity = 0.08f }); joints.Add(new IKBallSocketJoint(lowerLeftArmBone, leftHandBone, lowerLeftArmLeftHandBallSocketAnchor)); joints.Add(new IKSwingLimit(lowerLeftArmBone, leftHandBone, Vector3.Left, Vector3.Left, MathHelper.PiOver2)); joints.Add(new IKTwistLimit(lowerLeftArmBone, leftHandBone, Vector3.Left, Vector3.Left, MathHelper.PiOver4) { Rigidity = 0.08f }); //Right arm joints.Add(new IKBallSocketJoint(bodyBone, upperRightArmBone, bodyUpperRightArmBallSocketAnchor)); joints.Add(new IKSwingLimit(bodyBone, upperRightArmBone, Vector3.Normalize(new Vector3(1, 0, .3f)), Vector3.Right, MathHelper.Pi * .65f)); joints.Add(new IKTwistLimit(bodyBone, upperRightArmBone, Vector3.Right, Vector3.Right, MathHelper.PiOver2) { Rigidity = 0.08f }); joints.Add(new IKBallSocketJoint(upperRightArmBone, lowerRightArmBone, upperRightArmLowerRightArmBallSocketAnchor)); joints.Add(new IKSwivelHingeJoint(upperRightArmBone, lowerRightArmBone, Vector3.Up, Vector3.Right)); joints.Add(new IKSwingLimit(upperRightArmBone, lowerRightArmBone, Vector3.Normalize(new Vector3(0.23f, 0, .97f)), Vector3.Right, MathHelper.Pi * 0.435f)); joints.Add(new IKTwistLimit(upperRightArmBone, lowerRightArmBone, Vector3.Right, Vector3.Right, MathHelper.PiOver4) { Rigidity = 0.08f }); joints.Add(new IKBallSocketJoint(lowerRightArmBone, rightHandBone, lowerRightArmRightHandBallSocketAnchor)); joints.Add(new IKSwingLimit(lowerRightArmBone, rightHandBone, Vector3.Right, Vector3.Right, MathHelper.PiOver2)); joints.Add(new IKTwistLimit(lowerRightArmBone, rightHandBone, Vector3.Right, Vector3.Right, MathHelper.PiOver4) { Rigidity = 0.08f }); //Left Leg joints.Add(new IKBallSocketJoint(bodyBone, upperLeftLegBone, bodyUpperLeftLegBallSocketAnchor)); joints.Add(new IKSwingLimit(bodyBone, upperLeftLegBone, Vector3.Normalize(new Vector3(-.3f, -1, .6f)), Vector3.Down, MathHelper.Pi * 0.6f)); joints.Add(new IKTwistLimit(bodyBone, upperLeftLegBone, Vector3.Up, Vector3.Up, MathHelper.PiOver4) { MeasurementAxisA = Vector3.Normalize(new Vector3(-1, 0, 1)), Rigidity = 0.08f }); joints.Add(new IKBallSocketJoint(upperLeftLegBone, lowerLeftLegBone, upperLeftLegLowerLeftLegBallSocketAnchor)); joints.Add(new IKSwivelHingeJoint(upperLeftLegBone, lowerLeftLegBone, Vector3.Left, Vector3.Down)); joints.Add(new IKTwistLimit(upperLeftLegBone, lowerLeftLegBone, Vector3.Up, Vector3.Up, MathHelper.Pi * .1f) { Rigidity = 0.08f }); joints.Add(new IKSwingLimit(upperLeftLegBone, lowerLeftLegBone, Vector3.Normalize(new Vector3(0, -.23f, -.97f)), Vector3.Down, MathHelper.Pi * 0.435f)); joints.Add(new IKBallSocketJoint(lowerLeftLegBone, leftFootBone, lowerLeftLegLeftFootBallSocketAnchor)); joints.Add(new IKTwistJoint(lowerLeftLegBone, leftFootBone, Vector3.Down, Vector3.Down) { Rigidity = 0.08f }); joints.Add(new IKSwingLimit(lowerLeftLegBone, leftFootBone, Vector3.Normalize(new Vector3(0, -1, -.3f)), Vector3.Down, MathHelper.Pi * 0.22f)); //Right leg joints.Add(new IKBallSocketJoint(bodyBone, upperRightLegBone, bodyUpperRightLegBallSocketAnchor)); joints.Add(new IKSwingLimit(bodyBone, upperRightLegBone, Vector3.Normalize(new Vector3(.3f, -1, .6f)), Vector3.Down, MathHelper.Pi * 0.6f)); joints.Add(new IKTwistLimit(bodyBone, upperRightLegBone, Vector3.Up, Vector3.Up, MathHelper.PiOver4) { MeasurementAxisA = Vector3.Normalize(new Vector3(1, 0, 1)), Rigidity = 0.08f }); joints.Add(new IKBallSocketJoint(upperRightLegBone, lowerRightLegBone, upperRightLegLowerRightLegBallSocketAnchor)); joints.Add(new IKSwivelHingeJoint(upperRightLegBone, lowerRightLegBone, Vector3.Right, Vector3.Down)); joints.Add(new IKTwistLimit(upperRightLegBone, lowerRightLegBone, Vector3.Up, Vector3.Up, MathHelper.Pi * .1f) { Rigidity = 0.08f }); joints.Add(new IKSwingLimit(upperRightLegBone, lowerRightLegBone, Vector3.Normalize(new Vector3(0, -.23f, -.97f)), Vector3.Down, MathHelper.Pi * 0.435f)); joints.Add(new IKBallSocketJoint(lowerRightLegBone, rightFootBone, lowerRightLegRightFootBallSocketAnchor)); joints.Add(new IKTwistJoint(lowerRightLegBone, rightFootBone, Vector3.Down, Vector3.Down) { Rigidity = 0.08f }); joints.Add(new IKSwingLimit(lowerRightLegBone, rightFootBone, Vector3.Normalize(new Vector3(0, -1, -.3f)), Vector3.Down, MathHelper.Pi * 0.22f)); }
internal void Teleport(Microsoft.Xna.Framework.Vector3 vector3) { BEPUutilities.Vector3 v = vector3.ToBepuVector(); PhysicsBody.Position = v; }
void BuildChain(Vector3 position) { //Set up a bone chain. int linkCount = 100; var previousBoneEntity = new Cylinder(position, 1, .2f, 10); var previousBone = new Bone(previousBoneEntity.Position, previousBoneEntity.Orientation, previousBoneEntity.Radius, previousBoneEntity.Height); bones.Add(new BoneRelationship(previousBone, previousBoneEntity)); Space.Add(previousBoneEntity); for (int i = 1; i < linkCount; i++) { var boneEntity = new Cylinder(previousBone.Position + new Vector3(0, 1, 0), 1, .2f, 10); var bone = new Bone(boneEntity.Position, boneEntity.Orientation, boneEntity.Radius, boneEntity.Height); bones.Add(new BoneRelationship(bone, boneEntity)); Space.Add(boneEntity); //Make a relationship between the two bones and entities. CollisionRules.AddRule(previousBoneEntity, boneEntity, CollisionRule.NoBroadPhase); Vector3 anchor = (previousBoneEntity.Position + boneEntity.Position) / 2; var dynamicsBallSocketJoint = new BallSocketJoint(previousBoneEntity, boneEntity, anchor); var dynamicsAngularFriction = new AngularMotor(previousBoneEntity, boneEntity); dynamicsAngularFriction.Settings.Mode = MotorMode.VelocityMotor; dynamicsAngularFriction.Settings.MaximumForce = 200; Space.Add(dynamicsBallSocketJoint); Space.Add(dynamicsAngularFriction); var ikBallSocketJoint = new IKBallSocketJoint(previousBone, bone, anchor); //(the joint is auto-added to the bones; no solver-add is needed) joints.Add(ikBallSocketJoint); previousBone = bone; previousBoneEntity = boneEntity; } }
public void Render() { TheClient.Rendering.SetColor(GetSunAdjust()); TheClient.Rendering.SetMinimumLight(0f); if (TheClient.RenderTextures) { GL.BindTexture(TextureTarget.Texture2D, 0); GL.BindTexture(TextureTarget.Texture2DArray, TheClient.TBlock.TextureID); GL.ActiveTexture(TextureUnit.Texture2); GL.BindTexture(TextureTarget.Texture2DArray, TheClient.TBlock.NormalTextureID); GL.ActiveTexture(TextureUnit.Texture1); GL.BindTexture(TextureTarget.Texture2DArray, TheClient.TBlock.HelpTextureID); GL.ActiveTexture(TextureUnit.Texture0); } /*foreach (Chunk chunk in LoadedChunks.Values) * { * if (TheClient.CFrust == null || TheClient.CFrust.ContainsBox(chunk.WorldPosition.ToLocation() * Chunk.CHUNK_SIZE, * chunk.WorldPosition.ToLocation() * Chunk.CHUNK_SIZE + new Location(Chunk.CHUNK_SIZE))) * { * chunk.Render(); * } * }*/ if (TheClient.MainWorldView.FBOid == FBOID.MAIN || TheClient.MainWorldView.FBOid == FBOID.NONE || TheClient.MainWorldView.FBOid == FBOID.FORWARD_SOLID) { chToRender.Clear(); if (TheClient.CVars.r_chunkmarch.ValueB) { ChunkMarchAndDraw(); } else { foreach (Chunk ch in LoadedChunks.Values) { BEPUutilities.Vector3 min = ch.WorldPosition.ToVector3() * Chunk.CHUNK_SIZE; if (TheClient.MainWorldView.CFrust == null || TheClient.MainWorldView.CFrust.ContainsBox(min, min + new BEPUutilities.Vector3(Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE))) { ch.Render(); chToRender.Add(ch); } } } } else if (TheClient.MainWorldView.FBOid == FBOID.SHADOWS) { foreach (Chunk ch in LoadedChunks.Values) { BEPUutilities.Vector3 min = ch.WorldPosition.ToVector3() * Chunk.CHUNK_SIZE; if (TheClient.MainWorldView.CFrust == null || TheClient.MainWorldView.CFrust.ContainsBox(min, min + new BEPUutilities.Vector3(Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE, Chunk.CHUNK_SIZE))) { ch.Render(); } } } else { foreach (Chunk ch in chToRender) { ch.Render(); } } if (TheClient.RenderTextures) { GL.BindTexture(TextureTarget.Texture2D, 0); GL.BindTexture(TextureTarget.Texture2DArray, 0); GL.ActiveTexture(TextureUnit.Texture2); GL.BindTexture(TextureTarget.Texture2DArray, 0); GL.ActiveTexture(TextureUnit.Texture1); GL.BindTexture(TextureTarget.Texture2DArray, 0); GL.ActiveTexture(TextureUnit.Texture0); } }
void BuildCyclicMesh(Vector3 position) { int widthCount = 5; int heightCount = 5; var boneMesh = new BoneRelationship[widthCount, heightCount]; for (int i = 0; i < widthCount; i++) { for (int j = 0; j < heightCount; j++) { var bonePosition = position + new Vector3(i, j, 0); boneMesh[i, j] = new BoneRelationship( new Bone(bonePosition, Quaternion.Identity, .4f, .8f), new Box(bonePosition, .8f, .8f, .8f, 10)); Space.Add(boneMesh[i, j].Entity); bones.Add(boneMesh[i, j]); } } for (int i = 0; i < widthCount; i++) { for (int j = 0; j < heightCount; j++) { if (i > 0) { var boneA = boneMesh[i, j]; var boneB = boneMesh[i - 1, j]; var anchor = (boneA.Entity.Position + boneB.Entity.Position) / 2; var dynamicsJoint = new BallSocketJoint(boneA.Entity, boneB.Entity, anchor); CollisionRules.AddRule(boneA.Entity, boneB.Entity, CollisionRule.NoBroadPhase); Space.Add(dynamicsJoint); joints.Add(new IKBallSocketJoint(boneA.Bone, boneB.Bone, anchor)); } if (j > 0) { var boneA = boneMesh[i, j]; var boneB = boneMesh[i, j - 1]; var anchor = (boneA.Entity.Position + boneB.Entity.Position) / 2; var dynamicsJoint = new BallSocketJoint(boneA.Entity, boneB.Entity, anchor); CollisionRules.AddRule(boneA.Entity, boneB.Entity, CollisionRule.NoBroadPhase); Space.Add(dynamicsJoint); joints.Add(new IKBallSocketJoint(boneA.Bone, boneB.Bone, anchor)); } if (i > 0 && j > 0) { var boneA = boneMesh[i, j]; var boneB = boneMesh[i - 1, j - 1]; var anchor = (boneA.Entity.Position + boneB.Entity.Position) / 2; var dynamicsJoint = new BallSocketJoint(boneA.Entity, boneB.Entity, anchor); CollisionRules.AddRule(boneA.Entity, boneB.Entity, CollisionRule.NoBroadPhase); Space.Add(dynamicsJoint); joints.Add(new IKBallSocketJoint(boneA.Bone, boneB.Bone, anchor)); } if (i < widthCount - 1 && j > 0) { var boneA = boneMesh[i, j]; var boneB = boneMesh[i + 1, j - 1]; var anchor = (boneA.Entity.Position + boneB.Entity.Position) / 2; var dynamicsJoint = new BallSocketJoint(boneA.Entity, boneB.Entity, anchor); CollisionRules.AddRule(boneA.Entity, boneB.Entity, CollisionRule.NoBroadPhase); Space.Add(dynamicsJoint); joints.Add(new IKBallSocketJoint(boneA.Bone, boneB.Bone, anchor)); } } } int limbCount = 4; var previous = boneMesh[boneMesh.GetLength(0) / 2, 0]; for (int i = 0; i < limbCount; i++) { Bone bone = new Bone(previous.Bone.Position + new Vector3(0, -0.8f, 0), Quaternion.Identity, .2f, .4f); Entity entity = new Box(bone.Position, .4f, .4f, .4f, 10); Space.Add(entity); var anchor = (entity.Position + previous.Entity.Position) / 2; Space.Add(new BallSocketJoint(entity, previous.Entity, anchor)); joints.Add(new IKBallSocketJoint(bone, previous.Bone, anchor)); CollisionRules.AddRule(entity, previous.Entity, CollisionRule.NoBroadPhase); previous = new BoneRelationship(bone, entity); bones.Add(previous); } previous = boneMesh[boneMesh.GetLength(0) / 2, boneMesh.GetLength(1) - 1]; for (int i = 0; i < limbCount; i++) { Bone bone = new Bone(previous.Bone.Position + new Vector3(0, 0.8f, 0), Quaternion.Identity, .2f, .4f); Entity entity = new Box(bone.Position, .4f, .4f, .4f, 10); Space.Add(entity); var anchor = (entity.Position + previous.Entity.Position) / 2; Space.Add(new BallSocketJoint(entity, previous.Entity, anchor)); CollisionRules.AddRule(entity, previous.Entity, CollisionRule.NoBroadPhase); joints.Add(new IKBallSocketJoint(bone, previous.Bone, anchor)); previous = new BoneRelationship(bone, entity); bones.Add(previous); } previous = boneMesh[0, boneMesh.GetLength(1) / 2]; for (int i = 0; i < limbCount; i++) { Bone bone = new Bone(previous.Bone.Position + new Vector3(-.8f, 0, 0), Quaternion.Identity, .2f, .4f); Entity entity = new Box(bone.Position, .4f, .4f, .4f, 10); Space.Add(entity); var anchor = (entity.Position + previous.Entity.Position) / 2; Space.Add(new BallSocketJoint(entity, previous.Entity, anchor)); CollisionRules.AddRule(entity, previous.Entity, CollisionRule.NoBroadPhase); joints.Add(new IKBallSocketJoint(bone, previous.Bone, anchor)); previous = new BoneRelationship(bone, entity); bones.Add(previous); } previous = boneMesh[boneMesh.GetLength(0) - 1, boneMesh.GetLength(1) / 2]; for (int i = 0; i < limbCount; i++) { Bone bone = new Bone(previous.Bone.Position + new Vector3(0.8f, 0, 0), Quaternion.Identity, .2f, .4f); Entity entity = new Box(bone.Position, .4f, .4f, .4f, 10); Space.Add(entity); var anchor = (entity.Position + previous.Entity.Position) / 2; Space.Add(new BallSocketJoint(entity, previous.Entity, anchor)); CollisionRules.AddRule(entity, previous.Entity, CollisionRule.NoBroadPhase); joints.Add(new IKBallSocketJoint(bone, previous.Bone, anchor)); previous = new BoneRelationship(bone, entity); bones.Add(previous); } }
public static UnityEngine.Vector3 FromBEPU(this BEPUutilities.Vector3 vec) { return(new UnityEngine.Vector3(vec.X, vec.Y, vec.Z)); }
void BuildJointTest(Vector3 position) { Bone a, b; a = new Bone(position + new Vector3(0, 5, 0), Quaternion.Identity, .5f, 1); b = new Bone(position + new Vector3(0, 7, 0), Quaternion.Identity, .5f, 1); //var ikJoint = new IKBallSocketJoint(a, b, (a.Position + b.Position) * 0.5f); //var ikLimit = new IKSwingLimit(a, b, Vector3.Up, Vector3.Up, MathHelper.PiOver2); //var ikRevolute = new IKRevoluteJoint(a, b, Vector3.Right); //var ikSwivelHingeJoint = new IKSwivelHingeJoint(a, b, Vector3.Right, Vector3.Up); //var ikAngularJoint = new IKAngularJoint(a, b); //var ikTwistLimit = new IKTwistLimit(a, b, Vector3.Up, Vector3.Up, MathHelper.PiOver2); //var ikDistanceLimit = new IKDistanceLimit(a, b, a.Position + new Vector3(0, 0.5f, 0), b.Position + new Vector3(0, -0.5f, 0), 1f, 4); //var ikLinearAxisLimit = new IKLinearAxisLimit(a, b, a.Position + new Vector3(0, 0.5f, 0), Vector3.Up, b.Position + new Vector3(0, -0.5f, 0), 0, 4); //var ikTwistJoint = new IKTwistJoint(a, b, Vector3.Up, Vector3.Up); //var ikPointOnLineJoint = new IKPointOnLineJoint(a, b, a.Position + new Vector3(0, 0.5f, 0), Vector3.Up, b.Position - new Vector3(0, 0.5f, 0)); var ikPointOnPlaneJoint = new IKPointOnPlaneJoint(a, b, a.Position + new Vector3(0, 1f, 0), Vector3.Up, b.Position - new Vector3(0, 1f, 0)); //ikPointOnLineJoint.Softness = 0; //ikPointOnLineJoint.ErrorCorrectionFactor = 0; //solver.VelocitySubiterationCount = 10; var entityA = new Cylinder(a.Position, 1, 0.5f, 10); var entityB = new Cylinder(b.Position, 1, 0.5f, 10); entityB.Orientation = b.Orientation; //var joint = new BallSocketJoint(entityA, entityB, (a.Position + b.Position) * 0.5f); //var limit = new SwingLimit(entityA, entityB, Vector3.Up, Vector3.Up, MathHelper.PiOver2); //var revolute = new RevoluteAngularJoint(entityA, entityB, Vector3.Right); //var swivelHingeJoint = new SwivelHingeAngularJoint(entityA, entityB, Vector3.Right, Vector3.Up); //var angularJoint = new NoRotationJoint(entityA, entityB); //var twistLimit = new TwistLimit(entityA, entityB, Vector3.Up, Vector3.Up, -MathHelper.PiOver2, MathHelper.PiOver2); //var distanceLimit = new DistanceLimit(entityA, entityB, ikDistanceLimit.AnchorA, ikDistanceLimit.AnchorB, ikDistanceLimit.MinimumDistance, ikDistanceLimit.MaximumDistance); //var linearAxisLimit = new LinearAxisLimit(entityA, entityB, ikLinearAxisLimit.LineAnchor, ikLinearAxisLimit.AnchorB, ikLinearAxisLimit.LineDirection, ikLinearAxisLimit.MinimumDistance, ikLinearAxisLimit.MaximumDistance); //var twistJoint = new TwistJoint(entityA, entityB, Vector3.Up, Vector3.Up); //var pointOnLineJoint = new PointOnLineJoint(entityA, entityB, ikPointOnLineJoint.LineAnchor, ikPointOnLineJoint.LineDirection, ikPointOnLineJoint.AnchorB); var pointOnPlaneJoint = new PointOnPlaneJoint(entityA, entityB, ikPointOnPlaneJoint.PlaneAnchor, ikPointOnPlaneJoint.PlaneNormal, ikPointOnPlaneJoint.AnchorB); Space.Add(entityA); Space.Add(entityB); //Space.Add(joint); //Space.Add(limit); //Space.Add(revolute); //Space.Add(swivelHingeJoint); //Space.Add(angularJoint); //Space.Add(twistLimit); //Space.Add(distanceLimit); //Space.Add(linearAxisLimit); //Space.Add(twistJoint); //Space.Add(pointOnLineJoint); Space.Add(pointOnPlaneJoint); bones.Add(new BoneRelationship(a, entityA)); bones.Add(new BoneRelationship(b, entityB)); }