Example #1
0
        /// <summary>
        /// Disables an existing atmosphere, or adds a new one if there is none
        /// </summary>
        private void ToggleAtmosphere(CelestialBody body)
        {
            // Disable an existing atmosphere
            if (body.atmosphere)
            {
                // Disable the Atmosphere from Ground
                AtmosphereFromGround[] afgs = body.GetComponentsInChildren <AtmosphereFromGround>();
                foreach (AtmosphereFromGround afg in afgs)
                {
                    afg.gameObject.SetActive(false);
                }

                // Disable the Light controller
                MaterialSetDirection[] msds = body.GetComponentsInChildren <MaterialSetDirection>();
                foreach (MaterialSetDirection msd in msds)
                {
                    msd.gameObject.SetActive(false);
                }

                // No Atmosphere :(
                body.atmosphere = false;

                // Get the material
                Renderer  renderer   = body.scaledBody.GetComponent <Renderer>();
                Material  material   = renderer.sharedMaterial;
                Texture2D diffuseMap = (Texture2D)material.GetTexture("_MainTex");
                Texture2D bumpMap    = (Texture2D)material.GetTexture("_BumpMap");

                // Create a new scaled material
                Material newMaterial = new Material(Shader.Find("Terrain/Scaled Planet (Simple)"));
                newMaterial.SetTexture("_MainTex", diffuseMap);
                newMaterial.SetTexture("_BumpMap", bumpMap);
                newMaterial.SetFloat("_Shininess", material.GetFloat("_Shininess")); // TODO: Investigate
                newMaterial.SetColor("_SpecColor", material.GetColor("_SpecColor")); // TODO: Investigate

                // Apply the material
                renderer.sharedMaterial = newMaterial;

                // Backup the old material
                GameObject backupGameObject = new GameObject("Backup");
                backupGameObject.SetActive(false);
                backupGameObject.AddComponent <MeshRenderer>().material = material;
                backupGameObject.transform.parent = body.scaledBody.transform;

                // Update state
                toRestore.Add(body);
            }
            else
            {
                // Add a new atmosphere, this could get funny
                // We will just copy Laythe for the most parts
                body.atmosphere = true;
                body.atmosphereContainsOxygen = GetRandom(HighLogic.CurrentGame.Seed, 0, 99) < 10; // Oxygen is rare
                body.atmosphereDepth          = (body.pqsController.radiusMax / 10) * GetRandomDouble(HighLogic.CurrentGame.Seed, 0.8, 1.2);
                body.atmosphereAdiabaticIndex =
                    1.39999997615814 * GetRandomDouble(HighLogic.CurrentGame.Seed, 0.8, 1.2);
                body.atmosphereGasMassLapseRate =
                    4.84741125702493 * GetRandomDouble(HighLogic.CurrentGame.Seed, 0.8, 1.2);
                body.atmosphereMolarMass = 0.0289644002914429 * GetRandomDouble(HighLogic.CurrentGame.Seed, 0.8, 1.2);
                Double multiplier = GetRandomDouble(HighLogic.CurrentGame.Seed, 0, 1);
                body.atmospherePressureSeaLevel    = (595 * multiplier) + 5;
                body.atmosphereTemperatureSeaLevel = (270 * multiplier) + 240;
                body.atmDensityASL = (6.9 * multiplier) + 0.1;
                body.atmosphereTemperatureLapseRate         = GetRandomDouble(HighLogic.CurrentGame.Seed, 0.004, 0.005);
                body.atmospherePressureCurveIsNormalized    = true;
                body.atmosphereTemperatureCurveIsNormalized = true;
                body.atmosphereUsePressureCurve             = true;
                body.atmosphereUseTemperatureCurve          = true;

                // Select a curve template
                KeyValuePair <FloatCurve, FloatCurve> template =
                    GetRandomElement(HighLogic.CurrentGame.Seed, CurveTemplates.Atmospheres);
                body.atmospherePressureCurve    = template.Key;
                body.atmosphereTemperatureCurve = template.Value;

                // Now add the visuals
                GameObject scaledVersion = body.scaledBody;

                // Add the material light direction behavior
                MaterialSetDirection materialLightDirection = scaledVersion.AddComponent <MaterialSetDirection>();
                materialLightDirection.valueName = "_localLightDirection";

                // Create the atmosphere shell game object
                GameObject scaledAtmosphere = new GameObject("Atmosphere");
                scaledAtmosphere.transform.parent        = scaledVersion.transform;
                scaledAtmosphere.transform.position      = scaledVersion.transform.position;
                scaledAtmosphere.transform.localPosition = Vector3.zero;
                scaledAtmosphere.layer = 9;
                MeshRenderer mrenderer = scaledAtmosphere.AddComponent <MeshRenderer>();
                mrenderer.sharedMaterial = new Material(Shader.Find("AtmosphereFromGround"));
                MeshFilter meshFilter = scaledAtmosphere.AddComponent <MeshFilter>();
                meshFilter.sharedMesh = Templates.ReferenceGeosphere;
                AtmosphereFromGround atmosphereFromGround = scaledAtmosphere.AddComponent <AtmosphereFromGround>();

                // Get the average color of the current texture
                Renderer  renderer    = body.scaledBody.GetComponent <Renderer>();
                Material  material    = renderer.sharedMaterial;
                Texture2D diffuseMap  = Utility.CreateReadable((Texture2D)material.GetTexture("_MainTex"));
                Texture2D bumpMap     = (Texture2D)material.GetTexture("_BumpMap");
                Color     average     = Utility.GetAverageColor(diffuseMap);
                Color     altered     = AlterColor(average);
                Color     darkAltered = Utility.Dark(altered);

                body.afg = atmosphereFromGround;
                atmosphereFromGround.planet     = body;
                atmosphereFromGround.sunLight   = Planetarium.fetch.Sun.gameObject;
                atmosphereFromGround.mainCamera = PlanetariumCamera.fetch.transform;
                atmosphereFromGround.waveLength = new Color(1 - darkAltered.r, 1 - darkAltered.g, 1 - darkAltered.b, 0.5f);

                // Ambient Light
                body.atmosphericAmbientColor = altered;

                // Scaled Material
                Material newMaterial = new Material(Shader.Find("Terrain/Scaled Planet (RimAerial)"));
                newMaterial.SetTexture("_MainTex", diffuseMap);
                newMaterial.SetTexture("_BumpMap", bumpMap);
                newMaterial.SetFloat("_Shininess", material.GetFloat("_Shininess")); // TODO: Investigate
                newMaterial.SetColor("_SpecColor", material.GetColor("_SpecColor")); // TODO: Investigate
                newMaterial.SetFloat("_rimPower", (Single)GetRandomDouble(HighLogic.CurrentGame.Seed, 3.8, 5));
                newMaterial.SetFloat("_rimBlend", 1f);

                // Generate the atmosphere rim texture
                Gradient gradient = new Gradient();
                gradient.Add(0f, altered);
                gradient.Add(0.2f, new Color(0.0549f, 0.0784f, 0.141f, 1f));
                gradient.Add(1f, new Color(0.0196f, 0.0196f, 0.0196f, 1f));

                // Generate the ramp from a gradient
                Texture2D ramp   = new Texture2D(512, 1);
                Color[]   colors = ramp.GetPixels(0);
                for (Int32 i = 0; i < colors.Length; i++)
                {
                    // Compute the position in the gradient
                    Single k = (Single)i / colors.Length;
                    colors[i] = gradient.ColorAt(k);
                }
                ramp.SetPixels(colors, 0);
                ramp.Apply(true, false);
                ramp.wrapMode   = TextureWrapMode.Clamp;
                ramp.mipMapBias = 0.0f;

                // Set the color ramp
                newMaterial.SetTexture("_rimColorRamp", ramp);

                // Apply the material
                renderer.sharedMaterial = newMaterial;

                // Backup the old material
                GameObject backupGameObject = new GameObject("Backup");
                backupGameObject.SetActive(false);
                backupGameObject.AddComponent <MeshRenderer>().material = material;
                backupGameObject.transform.parent = scaledVersion.transform;

                // Update state
                toDelete.Add(body);
            }
        }
Example #2
0
        /// <summary>
        /// Changes the parameters of the body
        /// </summary>
        public override Boolean Tweak(CelestialBody body)
        {
            // Is the body a GasPlanet?
            if (body.hasSolidSurface || body.scaledBody.GetComponentsInChildren <SunShaderController>().Length != 0)
            {
                return(false);
            }

            // Is the body a barycenter?
            if (Storage.Has(body, "barycenter"))
            {
                return(false);
            }

            // Get the material of the body
            Renderer renderer = body.scaledBody.GetComponent <Renderer>();
            Material material = renderer.sharedMaterial;

            // Get the average color of the current texture
            Texture2D diffuseMap = Utility.CreateReadable((Texture2D)material.GetTexture("_MainTex"));
            Color     average    = Utility.GetAverageColor(diffuseMap);

            // Select a new color and apply it
            Color newColor = Utility.Dark(GetRandomElement(HighLogic.CurrentGame.Seed, Utility.colors));

            material.color = Utility.ReColor(newColor, average);

            // Does this planet have an atmosphere?
            if (!body.atmosphere)
            {
                return(true);
            }

            // Recolor the Atmosphere from Ground
            Color afgColor = new Color(1 - newColor.r, 1 - newColor.g, 1 - newColor.b, 1 - newColor.a);

            if (body.afg != null)
            {
                body.afg.waveLength = afgColor;
                EventData <AtmosphereFromGround> afgEvent =
                    GameEvents.FindEvent <EventData <AtmosphereFromGround> >("Kopernicus.RuntimeUtility.PatchAFG");
                afgEvent?.Add((afg) => afg.waveLength = afgColor);
            }
            body.atmosphericAmbientColor = newColor;

            // Generate the atmosphere rim texture
            Gradient gradient = new Gradient();

            gradient.Add(0f, newColor);
            gradient.Add(0.2f, new Color(0.0549f, 0.0784f, 0.141f, 1f));
            gradient.Add(1f, new Color(0.0196f, 0.0196f, 0.0196f, 1f));

            // Generate the ramp from a gradient
            Texture2D ramp = new Texture2D(512, 1);

            Color[] colors = ramp.GetPixels(0);
            for (Int32 i = 0; i < colors.Length; i++)
            {
                // Compute the position in the gradient
                Single k = (Single)i / colors.Length;
                colors[i] = gradient.ColorAt(k);
            }
            ramp.SetPixels(colors, 0);
            ramp.Apply(true, false);
            ramp.wrapMode   = TextureWrapMode.Clamp;
            ramp.mipMapBias = 0.0f;

            // Set the color ramp
            material.SetTexture("_rimColorRamp", ramp);

            // Apply the material
            renderer.sharedMaterial = material;

            //Report::Report.fetch.SetPrefix("PlanetaryBody: " + body.bodyDisplayName);
            //Report::Report.fetch.ReportLine("Color altered");
            //Report::Report.fetch.ReportSection();

            return(true);
        }