Exemple #1
0
    public static void RK4Integrate(ref Vector3d position, ref Vector3d velocity, double dt,
                                    PlanetRigidbody self, PlanetAggregator aggr)
    {
        Vector3d p1, p2, p3, p4;
        Vector3d v1, v2, v3, v4;
        Vector3d a1, a2, a3, a4;

        p1 = position;
        v1 = velocity;
        a1 = aggr.ComputeNetGravity(p1, self);

        p2 = position + 0.5 * v1 * dt;
        v2 = velocity + 0.5 * a1 * dt;
        a2 = aggr.ComputeNetGravity(p2, self);

        p3 = position + 0.5 * v2 * dt;
        v3 = velocity + 0.5 * a2 * dt;
        a3 = aggr.ComputeNetGravity(p3, self);

        p4 = position + v3 * dt;
        v4 = velocity + a3 * dt;
        a4 = aggr.ComputeNetGravity(p4, self);

        position += (dt / 6.0) * (v1 + 2.0 * v2 + 2.0 * v3 + v4);
        velocity += (dt / 6.0) * (a1 + 2.0 * a2 + 2.0 * a3 + a4);
    }
Exemple #2
0
    public static void MeanAccelerationIntegrate(ref Vector3d position, ref Vector3d velocity, Vector3d acceleration, double dt,
                                                 PlanetRigidbody self, PlanetAggregator aggr)
    {
        Vector3d expected_position     = position + (velocity * dt);
        Vector3d expected_acceleration = aggr.ComputeNetGravity(expected_position, self);
        Vector3d new_velocity          = velocity + (0.5 * (acceleration + expected_acceleration) * dt);

        position += 0.5 * (velocity + new_velocity) * dt;
        velocity  = new_velocity;
    }
Exemple #3
0
    public Vector3d ComputeNetGravity(Vector3d position, PlanetRigidbody self)
    {
        Vector3d net = Vector3d.zero;

        foreach (PlanetRigidbody body in bodies)
        {
            if (body != self)
            {
                net += ComputeGravityForce(position, body);
            }
        }
        return(net);
    }
    void Draw()
    {
        // do this kind of iterative thing to do the arc sweeps
        List <Vector3> positions = new List <Vector3>();

        Vector3d position     = new Vector3d(transform.position);
        Vector3d velocity     = new Vector3d(transform.forward * speed);
        Vector3d acceleration = Vector3d.zero;

        positions.Add(position.ToVector3());

        for (int i = 0; i < steps; i++)
        {
            //acceleration = aggregator.ComputeNetGravity(position, planet);
            PlanetRigidbody.RK4Integrate(ref position, ref velocity, timestep, planet, aggregator);
            positions.Add(position.ToVector3());
        }

        trajectory.positionCount = positions.Count;
        trajectory.SetPositions(positions.ToArray());
    }
Exemple #5
0
    public Vector3d ComputeGravityForce(Vector3d position, PlanetRigidbody body)
    {
        Vector3d body_pos = new Vector3d(
            (double)body.transform.position.x,
            (double)body.transform.position.y,
            (double)body.transform.position.z
            );

        double r = Vector3d.SqrDistance(position, body_pos);

        // I'm fine with this approximation because it solves the problem of the div by zero of
        // objects trying to attract themselves, and two objects centers overlapping is pretty nonsense
        // conceptually
        if (r <= Vector3d.MIN_DOUBLE)
        {
            return(Vector3d.zero);
        }

        double a = (double)body.mass / r;

        return((body_pos - position).normalized * a);
    }
 void Awake()
 {
     aggregator = GameObject.Find("Planet Aggregator").GetComponent <PlanetAggregator>();
     planet     = GetComponent <PlanetRigidbody>();
     trajectory = GetComponent <LineRenderer>();
 }
Exemple #7
0
 // Here we assume constant acceleration for the duration of the timestep
 public static void EulerIntegrate(ref Vector3d position, ref Vector3d velocity, Vector3d acceleration, double dt,
                                   PlanetRigidbody self, PlanetAggregator aggr)
 {
     velocity += acceleration * dt;
     position += velocity * dt;
 }