예제 #1
0
    // Create an NBody and check it's mass
    public void CirclePrediction()
    {
        const float    mass        = 1000f;
        GameObject     star        = TestSetupUtils.CreateNBody(mass, new Vector3(0, 0, 0));
        NBody          starNbody   = star.GetComponent <NBody>();
        const float    orbitRadius = 10f;
        GameObject     planet      = TestSetupUtils.CreatePlanetInOrbitUniversal(starNbody, 1f, orbitRadius);
        OrbitUniversal orbitU      = planet.GetComponent <OrbitUniversal>();

        OrbitPredictor op = TestSetupUtils.AddOrbitPredictor(planet, star);

        Assert.NotNull(op);

        double[] p_values = { 10, 100, 1000 };
        foreach (double p in p_values)
        {
            Debug.LogFormat("#### CirclePrediction p={0}", p);
            orbitU.p = p;
            TestSetupUtils.SetupGravityEngine(star, planet);
            op.TestRunnerSetup();

            OrbitUniversal predictedOrbit = op.GetOrbitUniversal();
            Assert.NotNull(predictedOrbit);
            CompareOrbits(orbitU, predictedOrbit, small);
        }
    }
    // Use this for initialization
    void Start()
    {
        ge     = GravityEngine.Instance();
        x_axis = new Vector3d(1, 0, 0);

        // mass scaling will cancel in this ratio
        soiRadius = OrbitUtils.SoiRadius(planet, moonBody);

        // TODO: allow moon to be OrbitUniversal as well.
        OrbitUniversal moonOrbit = moonBody.gameObject.GetComponent <OrbitUniversal>();

        if (moonOrbit == null)
        {
            Debug.LogError("Moon is required to have OrbitUniversal");
        }
        moonRadius = moonOrbit.GetMajorAxis();

        shipOrbit = spaceship.GetComponent <OrbitUniversal>();
        if (shipOrbit == null)
        {
            Debug.LogError("Require that the ship have an OrbitU");
        }
        if (shipOrbit.evolveMode != OrbitUniversal.EvolveMode.KEPLERS_EQN)
        {
            Debug.LogError("Controller requires ship on-rails but spaceship is off-rails");
        }

        // assuming circular orbit for ship
        shipRadius = shipOrbit.GetApogee();

        shipOrbitPredictor = spaceship.GetComponentInChildren <OrbitPredictor>();
    }
예제 #3
0
    // Create an NBody and check it's mass
    public void EccentricityPrediction()
    {
        const float    mass        = 1000f;
        GameObject     star        = TestSetupUtils.CreateNBody(mass, new Vector3(0, 0, 0));
        NBody          starNbody   = star.GetComponent <NBody>();
        const float    orbitRadius = 10f;
        GameObject     planet      = TestSetupUtils.CreatePlanetInOrbitUniversal(starNbody, 1f, orbitRadius);
        OrbitUniversal orbitU      = planet.GetComponent <OrbitUniversal>();

        OrbitPredictor op = TestSetupUtils.AddOrbitPredictor(planet, star);

        Assert.NotNull(op);

        double[] ecc_values = { 0, 0.1, 0.7, 0.9, 0.99, 1.01, 1.5, 2 };
        foreach (double ecc in ecc_values)
        {
            Debug.LogFormat("#### EccentricityPrediction ecc={0}", ecc);
            orbitU.eccentricity = ecc;
            TestSetupUtils.SetupGravityEngine(star, planet);
            op.TestRunnerSetup();

            OrbitUniversal predictedOrbit = op.GetOrbitUniversal();
            Assert.NotNull(predictedOrbit);
            CompareOrbits(orbitU, predictedOrbit, small);
        }
    }
예제 #4
0
    // Create an NBody and check it's mass
    public void InclinationPrediction()
    {
        const float    mass        = 1000f;
        GameObject     star        = TestSetupUtils.CreateNBody(mass, new Vector3(0, 0, 0));
        NBody          starNbody   = star.GetComponent <NBody>();
        const float    orbitRadius = 10f;
        GameObject     planet      = TestSetupUtils.CreatePlanetInOrbitUniversal(starNbody, 1f, orbitRadius);
        OrbitUniversal orbitU      = planet.GetComponent <OrbitUniversal>();

        OrbitPredictor op = TestSetupUtils.AddOrbitPredictor(planet, star);

        Assert.NotNull(op);

        double[] incl_values = { 0, 1, 5, 10, 30, 45, 60, 90, 145, 179, 180 };
        foreach (double incl in incl_values)
        {
            Debug.LogFormat("#### InclinationPrediction incl={0}", incl);
            orbitU.inclination = incl;
            TestSetupUtils.SetupGravityEngine(star, planet);
            op.TestRunnerSetup();

            OrbitUniversal predictedOrbit = op.GetOrbitUniversal();
            Assert.NotNull(predictedOrbit);
            CompareOrbits(orbitU, predictedOrbit, small);
        }
    }
예제 #5
0
    // Create an NBody and check it's mass
    public void OmegaUEllipsePrediction()
    {
        const float    mass        = 1000f;
        GameObject     star        = TestSetupUtils.CreateNBody(mass, new Vector3(0, 0, 0));
        NBody          starNbody   = star.GetComponent <NBody>();
        const float    orbitRadius = 10f;
        GameObject     planet      = TestSetupUtils.CreatePlanetInOrbitUniversal(starNbody, 1f, orbitRadius);
        OrbitUniversal orbitU      = planet.GetComponent <OrbitUniversal>();

        // Need a bit of incl, otherwise omegaU comes back as omegaL.
        orbitU.inclination  = 10;
        orbitU.eccentricity = 0.05;

        OrbitPredictor op = TestSetupUtils.AddOrbitPredictor(planet, star);

        Assert.NotNull(op);

        double[] ou_values = { 0, 1, 5, 10, 30, 60, 90, 180, 270, 355, 360 };
        foreach (double ou in ou_values)
        {
            Debug.LogFormat("#### OmegaUPrediction ou={0}", ou);
            orbitU.omega_uc = ou;
            TestSetupUtils.SetupGravityEngine(star, planet);
            op.TestRunnerSetup();

            OrbitUniversal predictedOrbit = op.GetOrbitUniversal();
            Assert.NotNull(predictedOrbit);
            CompareOrbits(orbitU, predictedOrbit, small);
        }
    }
    // Use this for initialization (must Awake, since start of GameLoop will set states)
    void Awake()
    {
        state      = State.SELECT_OBJECTIVE;
        intercepts = null;

        time_to_moon_phys = TIME_TO_MOON_SEC / GravityScaler.GetGameSecondPerPhysicsSecond();

        if (targets.Length == 0)
        {
            Debug.LogError("No targets configured");
        }
        // Player is spaceship 1, others are objectives

        // take first ship to tbe the player
        target = targets[0];


        // Need to configure objective chooser
        SetObjectiveOptions(targets);

        SetState(state);

        // add a trajectory intercepts component (it need to handle markers so it has
        // a monobehaviour base class).
        // The pair of spaceships to be checked will be selected dynamically
        trajIntercepts = gameObject.AddComponent <TrajectoryIntercepts>();
        trajIntercepts.interceptSymbol  = interceptMarker;
        trajIntercepts.rendezvousSymbol = rendezvousMarker;

        spaceshipGO = spaceshipCtrl.transform.parent.gameObject;
        // optional
        spaceshipOrbit = spaceshipGO.GetComponent <OrbitUniversal>();

        // only record the elements that are active at the start of the scene
        orbitPredictors = new List <OrbitPredictor>();
        foreach (OrbitPredictor op in  (OrbitPredictor[])Object.FindObjectsOfType(typeof(OrbitPredictor)))
        {
            if (op.gameObject.activeInHierarchy)
            {
                orbitPredictors.Add(op);
                if (op.transform.parent == spaceshipGO.transform)
                {
                    shipOrbitPredictor = op;
                }
            }
        }
        if (shipOrbitPredictor == null)
        {
            Debug.LogError("Did not find orbit predictor for ship");
        }

        orbitRenderers = new List <OrbitRenderer>();
        foreach (OrbitRenderer or in (OrbitRenderer[])Object.FindObjectsOfType(typeof(OrbitRenderer)))
        {
            if (or.gameObject.activeInHierarchy)
            {
                orbitRenderers.Add(or);
            }
        }
    }
예제 #7
0
    private void HyperInit(GameObject go, NBody nbody, GameObject parent)
    {
        OrbitHyper hyper = go.GetComponent <OrbitHyper>();

        if (hyper == null)
        {
            Debug.LogError("Failed to get OrbitHyper from prefab:" + go.name);
            return;
        }
        // Awkward test code
        if (parent == star)
        {
            hyper.perihelion = Random.Range(minRadius, maxRadius);
            // aribitrary - start at fixed distance from peri
            hyper.r_initial    = 1.0f * hyper.perihelion;
            hyper.inclination  = Random.Range(-80f, 80f);
            hyper.ecc          = Random.Range(1.1f, 2f);
            hyper.centerObject = parent;
        }
        hyper.SetNBody(nbody);
        hyper.Init();
        OrbitPredictor op = go.GetComponentInChildren <OrbitPredictor>();

        if (op != null)
        {
            op.SetNBody(nbody);
            op.SetCenterObject(parent);
        }
    }
예제 #8
0
 // Use this for initialization
 void Start()
 {
     actualVels = new List <Vector2>();
     instance   = this;
     ResetConsistentLine();
     lineHitPlanet = false;
 }
예제 #9
0
    public static OrbitPredictor AddOrbitPredictor(GameObject planet, GameObject centerGo)
    {
        GameObject orbitPredictorGo = Instantiate(new GameObject());

        orbitPredictorGo.transform.SetParent(planet.transform);
        OrbitPredictor op = orbitPredictorGo.AddComponent <OrbitPredictor>();

        op.body       = planet;
        op.centerBody = centerGo;
        return(op);
    }
예제 #10
0
    public override void OnInspectorGUI()
    {
        GUI.changed = false;
        OrbitPredictor orbit = (OrbitPredictor)target;

        GameObject body;
        GameObject centerObject = orbit.centerBody;
        bool       vFromScript  = orbit.velocityFromScript;
        int        numPoints;

        centerObject = (GameObject)EditorGUILayout.ObjectField(
            new GUIContent("CenterObject", centerTip),
            orbit.centerBody,
            typeof(GameObject),
            true);

        body = (GameObject)EditorGUILayout.ObjectField(
            new GUIContent("Body", bodyTip),
            orbit.body,
            typeof(GameObject),
            true);

        vFromScript = EditorGUILayout.Toggle(new GUIContent("Velocity From Script", vTip), vFromScript);

        float hyperR = EditorGUILayout.FloatField(new GUIContent("Hyper Display Radius", vTip), orbit.hyperDisplayRadius);

        numPoints = EditorGUILayout.IntField(new GUIContent("Number of Points", hTip), orbit.numPoints);

        int projPoints = EditorGUILayout.IntField(new GUIContent("Number of Projection Points", hTip), orbit.numPlaneProjections);

        Vector3 planeNormal = EditorGUILayout.Vector3Field(new GUIContent("PlaneNormals", hTip), orbit.planeNormal);

        if (GUI.changed)
        {
            Undo.RecordObject(orbit, "OrbitEllipse Change");
            orbit.centerBody          = centerObject;
            orbit.body                = body;
            orbit.numPoints           = numPoints;
            orbit.velocityFromScript  = vFromScript;
            orbit.hyperDisplayRadius  = hyperR;
            orbit.numPlaneProjections = projPoints;
            orbit.planeNormal         = planeNormal;
            EditorUtility.SetDirty(orbit);
        }
    }
예제 #11
0
    public override void OnInspectorGUI()
    {
        GUI.changed = false;
        OrbitPredictor orbit = (OrbitPredictor)target;

        GameObject body;
        GameObject centerObject;
        int        numPoints;

        centerObject = (GameObject)EditorGUILayout.ObjectField(
            new GUIContent("CenterObject", centerTip),
            orbit.centerBody,
            typeof(GameObject),
            true);

        body = (GameObject)EditorGUILayout.ObjectField(
            new GUIContent("Body", bodyTip),
            orbit.body,
            typeof(GameObject),
            true);

        numPoints = EditorGUILayout.IntField(new GUIContent("Number of Points", rTip), orbit.numPoints);

        if (GUI.changed)
        {
            Undo.RecordObject(orbit, "OrbitEllipse Change");
            orbit.centerBody = centerObject;
            orbit.body       = body;
            orbit.numPoints  = numPoints;
            EditorUtility.SetDirty(orbit);
        }

        if (GUI.changed)
        {
            Undo.RecordObject(orbit, "OrbitPredictor Change");
            orbit.body       = body;
            orbit.centerBody = centerObject;
            EditorUtility.SetDirty(orbit);
        }
    }
예제 #12
0
    private void AddBody()
    {
        // Pick a prefab
        int prefabNum = (int)Random.Range(0, planetPrefabs.Length);

        GameObject planet = Instantiate(planetPrefabs[prefabNum]) as GameObject;

        // make a child of this object
        planet.transform.parent = gameObject.transform;

        OrbitEllipse oe = planet.GetComponent <OrbitEllipse>();

        oe.centerObject = gameObject;
        // set ranges with appropriate limits
        oe.a           = Random.Range(Mathf.Max(a_min, 0.1f), a_max);
        oe.ecc         = Random.Range(Mathf.Max(ecc_min, 0f), Mathf.Min(0.99f, ecc_max));
        oe.inclination = Random.Range(Mathf.Max(0, incl_min), Mathf.Min(180f, incl_max));
        oe.omega_lc    = Random.Range(Mathf.Max(0, omega_lc_min), Mathf.Min(359.9f, omega_lc_max));
        oe.omega_uc    = Random.Range(Mathf.Max(0, omega_uc_min), Mathf.Min(359.9f, omega_uc_max));
        oe.phase       = Random.Range(Mathf.Max(0, phase_min), Mathf.Min(359.9f, phase_max));

        // If there is a MeshRenderer - apply scale
        MeshRenderer mr = planet.GetComponentInChildren <MeshRenderer>();

        if (mr != null)
        {
            mr.transform.localScale = Random.Range(Mathf.Max(scale_min, 0.01f), scale_max) * Vector3.one;
        }

        // If there is an OrbitPredictor, assign the parent
        OrbitPredictor op = planet.GetComponentInChildren <OrbitPredictor>();

        if (op != null)
        {
            op.body = planet;
            op.SetNBody(planet.GetComponent <NBody>());
            op.SetCenterObject(gameObject);
        }
        GravityEngine.Instance().AddBody(planet);
    }
예제 #13
0
    private void EllipseInit(GameObject go, NBody nbody, GameObject parent, string bodyType)
    {
        OrbitEllipse eb = go.GetComponent <OrbitEllipse>();

        eb.centerObject = parent;
        if (eb == null)
        {
            Debug.LogError("Failed to get OrbitEllipse from prefab:" + go.name);
            return;
        }
        // Awkward test code
        if (parent == star)
        {
            eb.paramBy     = EllipseBase.ParamBy.AXIS_A;
            eb.a           = Random.Range(minRadius, maxRadius);
            eb.inclination = Random.Range(-80f, 80f);
            eb.ecc         = Random.Range(minEccentricity, maxEccentricity);
        }
        else
        {
            // moon test, so keep "a" small
            eb.paramBy     = EllipseBase.ParamBy.AXIS_A;
            eb.a           = moonRadius;
            eb.inclination = Random.Range(-80f, 80f);
            eb.ecc         = 0;
        }
        if (bodyType == KEPLER)
        {
            eb.evolveMode = OrbitEllipse.evolveType.KEPLERS_EQN;
        }
        eb.Init();
        OrbitPredictor op = go.GetComponentInChildren <OrbitPredictor>();

        if (op != null)
        {
            op.SetNBody(nbody);
            op.SetCenterObject(parent);
        }
    }
예제 #14
0
    private void Start()
    {
        // (optional)
        ship1predictor = ship1.GetComponentInChildren <OrbitPredictor>();
        ship2predictor = ship2.GetComponentInChildren <OrbitPredictor>();

        nbodies = new NBody[] { ship1, ship2 };

        // optional to have RCS
        rcs = new ReactionControlSystem[nbodies.Length];
        for (int i = 0; i < nbodies.Length; i++)
        {
            rcs[i] = nbodies[i].GetComponentInChildren <ReactionControlSystem>();
            if (rcs[i] != null)
            {
                rcs[i].SetNBody(nbodies[i]);
            }
        }

        // required to have docking ports
        dockingPorts    = new DockingPort[nbodies.Length];
        dockingPorts[0] = ship1.GetComponentInChildren <DockingPort>();
        dockingPorts[1] = ship2.GetComponentInChildren <DockingPort>();
    }
    private void AddGhostBodies()
    {
        // Create a ghost moon and put soiEnter/Exit ships into orbit around it. Add all to GE
        // (ghost moon does not have an OrbitPredictor)
        ghostMoon      = new NBody[2];
        ghostMoonOrbit = new OrbitUniversal[2];
        for (int i = 0; i < 2; i++)
        {
            GameObject ghostMoonGO = Instantiate(moonBody.gameObject);
            ghostMoon[i]      = ghostMoonGO.GetComponent <NBody>();
            ghostMoonOrbit[i] = ghostMoonGO.GetComponent <OrbitUniversal>();
        }
        ghostMoon[MOON_SOI_ENTER].gameObject.name = "GhostMoon (SOI enter)";
        ghostMoon[MOON_SOI_EXIT].gameObject.name  = "GhostMoon (SOI exit)";
        ghostMoonSoiEnterOrbitPredictor           = ghostMoon[MOON_SOI_ENTER].GetComponentInChildren <OrbitPredictor>();

        ghostMoon[MOON_SOI_ENTER].GetComponentInChildren <LineRenderer>().material = toMoonMaterial;
        ghostMoon[MOON_SOI_EXIT].GetComponentInChildren <LineRenderer>().material  = fromMoonMaterial;

        ghostShip               = new NBody[NUM_GHOST_SHIPS];
        ghostShipOrbit          = new OrbitUniversal[NUM_GHOST_SHIPS];
        ghostShipOrbitPredictor = new OrbitPredictor[NUM_GHOST_SHIPS];
        GameObject ghostShipGO;

        for (int i = 0; i < NUM_GHOST_SHIPS; i++)
        {
            ghostShipGO                           = Instantiate(shipSOIPrefab);
            ghostShip[i]                          = ghostShipGO.GetComponent <NBody>();
            ghostShipOrbit[i]                     = ghostShipGO.GetComponent <OrbitUniversal>();
            ghostShipOrbit[i].p_inspector         = soiRadius;
            ghostShipOrbit[i].centerNbody         = planet;
            ghostShipOrbitPredictor[i]            = ghostShipGO.GetComponentInChildren <OrbitPredictor>();
            ghostShipOrbitPredictor[i].body       = ghostShipGO;
            ghostShipOrbitPredictor[i].centerBody = planet.gameObject;
            LineRenderer lineR = ghostShipOrbitPredictor[i].GetComponent <LineRenderer>();
            lineR.startWidth = lineWidth;
            lineR.endWidth   = lineWidth;
            ghostShipGO.transform.SetParent(planet.gameObject.transform);
        }

        // check prefab has orbitU in Kepler mode
        if (ghostShipOrbit[0].evolveMode != OrbitUniversal.EvolveMode.KEPLERS_EQN)
        {
            Debug.LogError("ShipSoi prefab must have an on-rails OrbitU");
            return;
        }

        ghostShip[TLI].gameObject.name  = "Ghost TLI";
        ghostShipOrbit[TLI].p_inspector = shipRadius;
        ghostShipOrbitPredictor[TLI].GetComponent <LineRenderer>().material = toMoonMaterial;

        // customize ghost ships as necessary
        // ENTER_SOI
        ghostShip[TO_MOON].gameObject.name  = "Ghost To Moon";
        ghostShipOrbit[TO_MOON].p_inspector = shipRadius;
        ghostShipOrbitPredictor[TO_MOON].GetComponent <LineRenderer>().material = toMoonMaterial;

        // SOI Enter
        ghostShip[ENTER_SOI].gameObject.name = "Ghost SOI Enter";
        ghostShip[ENTER_SOI].gameObject.transform.SetParent(ghostMoon[MOON_SOI_ENTER].gameObject.transform);
        Destroy(ghostShipOrbitPredictor[ENTER_SOI]);
        // Use OrbitPredictor to show SOI at entry
        //ghostShipOrbitPredictor[ENTER_SOI].centerBody = ghostMoon[MOON_SOI_ENTER].gameObject;
        //ghostShipOrbitPredictor[ENTER_SOI].GetComponent<LineRenderer>().material = aroundMoonMaterial;
        ghostShipOrbit[ENTER_SOI].centerNbody = ghostMoon[MOON_SOI_ENTER];

        // HYPER_SOI
        ghostShip[SOI_HYPER].gameObject.name = "Ghost SOI Hyper";
        ghostShip[SOI_HYPER].gameObject.transform.SetParent(ghostMoon[MOON_SOI_ENTER].gameObject.transform);
        ghostShipOrbitPredictor[SOI_HYPER].centerBody         = ghostMoon[MOON_SOI_ENTER].gameObject;
        ghostShipOrbitPredictor[SOI_HYPER].hyperDisplayRadius = soiRadius;
        ghostShipOrbit[SOI_HYPER].centerNbody = ghostMoon[MOON_SOI_ENTER];
        ghostShipOrbitPredictor[SOI_HYPER].GetComponent <LineRenderer>().material = aroundMoonMaterial;

        // EXIT_SOI
        ghostShip[EXIT_SOI].gameObject.name = "Ghost SOI Exit";
        ghostShipOrbitPredictor[EXIT_SOI].GetComponent <LineRenderer>().material = fromMoonMaterial;

        // Tell GE about everything
        ge.AddBody(ghostMoon[MOON_SOI_ENTER].gameObject); // also adds ENTER_SOI
        ge.AddBody(ghostShip[TLI].gameObject);
        ge.AddBody(ghostShip[TO_MOON].gameObject);
        ge.AddBody(ghostShip[EXIT_SOI].gameObject);
        ge.AddBody(ghostMoon[MOON_SOI_EXIT].gameObject);

        // set TLI ship to inactive and control pos/vel in ComputeTransfer
        ge.InactivateBody(ghostShip[TO_MOON].gameObject);
    }