public static Vector GravityForce(MaterialPoint b1, MaterialPoint b2, double G) { double forceAbs; Vector forceOX; if (b1.Coordinates == b2.Coordinates) { return(Vector.ZeroVector()); } forceAbs = G * (b1.Mass * b2.Mass) / (Math.Pow(b1.DistanceTo(b2), 2)); forceOX = new Vector(forceAbs, 0); forceOX = forceOX.RotateTo(b2.Coordinates - b1.Coordinates); return(forceOX); }
private void UpdateField() { Vector[] forces = new Vector[Bodies.Count]; Vector currForce, acceleration; int i, j; bool countingNeeded = true; for (i = 0; i < Bodies.Count; i++) { forces[i] = Vector.ZeroVector(); } for (i = 0; i < Bodies.Count; i++) { for (j = 0; j < Bodies.Count; j++) { if (i == j) { continue; } if (CollisionsType == CollisionType.InelasticCollisions) { /*Check if bodies collided*/ if (Bodies[i] is PhysicalBody && Bodies[j] is PhysicalBody) { if (Bodies[i].DistanceTo(Bodies[j]) < ((PhysicalBody)Bodies[i]).Diameter + ((PhysicalBody)Bodies[j]).Diameter) { MaterialPoint newBody = new PhysicalBody( coordinates: Bodies[i].Coordinates, mass: Bodies[i].Mass + Bodies[j].Mass, /*Momentum conservation law*/ velocity: (Bodies[i].Velocity * Bodies[i].Mass + Bodies[j].Velocity * Bodies[j].Mass) / (Bodies[i].Mass + Bodies[j].Mass), /*Sum of volumes*/ diameter: Math.Pow(Math.Pow(((PhysicalBody)Bodies[i]).Diameter, 3) + Math.Pow(((PhysicalBody)Bodies[j]).Diameter, 3), (double)1 / 3) ); /*First must be deleted the last. In other cases this will cause an exception*/ BodyDeletedRaise(Math.Max(i, j)); BodyDeletedRaise(Math.Min(i, j)); Bodies.RemoveAt(Math.Max(i, j)); Bodies.RemoveAt(Math.Min(i, j)); BodyAddedRaise(newBody); Bodies.Add(newBody); countingNeeded = false; } } } else if (CollisionsType == CollisionType.ElasticCollisions) { /*Check if bodies collided*/ if (Bodies[i] is PhysicalBody && Bodies[j] is PhysicalBody) { if (Bodies[i].DistanceTo(Bodies[j]) < ((PhysicalBody)Bodies[i]).Diameter + ((PhysicalBody)Bodies[j]).Diameter) { double m1 = Bodies[i].Mass, m2 = Bodies[j].Mass; Vector v1 = Bodies[i].Velocity, v2 = Bodies[j].Velocity; /*Momentum conservation law*/ Bodies[i].Velocity = (m1 - m2) / (m1 + m2) * (v1 - v2) + v2; Bodies[j].Velocity = (2 * m1 * v1) / (m1 + m2) + v2; countingNeeded = false; } } } if (countingNeeded) { currForce = MaterialPoint.GravityForce(Bodies[i], Bodies[j], G); forces[i] += currForce; } } } for (i = 0; i < Bodies.Count; i++) { acceleration = forces[i] / Bodies[i].Mass; Bodies[i].Velocity = Bodies[i].Velocity + acceleration * DeltaTime; Bodies[i].Coordinates += Bodies[i].Velocity * DeltaTime; } }
private void BodyAddedRaise(MaterialPoint body) { BodyAdded?.Invoke(body); }
public double DistanceTo(MaterialPoint b2) => (Coordinates - b2.Coordinates).Length;