예제 #1
0
 void ConsumeMulch()
 {
     // consumes a mulch block if health below a certain amount and the only occupant of that mulch
     if (health < maxHealth / 3)
     {
         int  x            = (int)transform.position.x;
         int  y            = (int)(transform.position.y - 0.5f);
         int  z            = (int)transform.position.z;
         bool soloOccupied = true;
         if (wm.GetBlock(x, y, z) is Antymology.Terrain.MulchBlock && x > 5 && y > 5 && z > 5 &&
             x < ConfigurationManager.Instance.World_Diameter * ConfigurationManager.Instance.Chunk_Diameter - 5 &&
             y < ConfigurationManager.Instance.World_Height * ConfigurationManager.Instance.Chunk_Diameter - 5 &&
             z < ConfigurationManager.Instance.World_Diameter * ConfigurationManager.Instance.Chunk_Diameter - 5)
         {
             foreach (GameObject ant in wm.Ants)
             {
                 if (transform.position == ant.transform.position && !GameObject.ReferenceEquals(gameObject, ant))
                 {
                     soloOccupied = false;
                 }
             }
             if (soloOccupied)
             {
                 AbstractBlock newBlock = new Antymology.Terrain.AirBlock();
                 wm.SetBlock(x, y, z, newBlock);
                 transform.position = new Vector3(transform.position.x, transform.position.y - 1, transform.position.z);
                 wm.surfaceBlocks[x, z]--;
                 health = 1000;
             }
         }
     }
 }
예제 #2
0
        /// <summary>
        /// Secrete some pheromone. The queen's pheromone is more intense.
        /// </summary>
        void Secrete(bool type, float amount)
        {
            int multiplier = 1;

            if (isQueen)
            {
                multiplier *= 10;
            }
            AirBlock here = (AirBlock)Surrounding[1, 3, 1];

            here.pheromoneDeposits.AddOrUpdate(type, amount, (k, v) => v + amount * multiplier);
        }
예제 #3
0
        /// <summary>
        /// Generates the preliminary world data based on perlin noise.
        /// </summary>
        private void GeneratePreliminaryWorld()
        {
            for (int x = 0; x < Blocks.GetLength(0); x++)
            {
                for (int z = 0; z < Blocks.GetLength(2); z++)
                {
                    /**
                     * These numbers have been fine-tuned and tweaked through trial and error.
                     * Altering these numbers may produce weird looking worlds.
                     **/
                    int stoneCeiling = SimplexNoise.GetPerlinNoise(x, 0, z, 10, 3, 1.2) +
                                       SimplexNoise.GetPerlinNoise(x, 300, z, 20, 4, 0) +
                                       10;
                    int grassHeight = SimplexNoise.GetPerlinNoise(x, 100, z, 30, 10, 0);
                    int foodHeight  = SimplexNoise.GetPerlinNoise(x, 200, z, 20, 5, 1.5);

                    Topography[x, z] = stoneCeiling + grassHeight + foodHeight;

                    for (int y = 0; y < Blocks.GetLength(1); y++)
                    {
                        if (y <= stoneCeiling)
                        {
                            Blocks[x, y, z] = new StoneBlock();
                        }
                        else if (y <= stoneCeiling + grassHeight)
                        {
                            Blocks[x, y, z] = new GrassBlock();
                        }
                        else if (y <= stoneCeiling + grassHeight + foodHeight)
                        {
                            Blocks[x, y, z] = new MulchBlock();
                        }
                        else
                        {
                            Blocks[x, y, z] = new AirBlock();
                        }
                        if
                        (
                            x == 0 ||
                            x >= Blocks.GetLength(0) - 1 ||
                            z == 0 ||
                            z >= Blocks.GetLength(2) - 1 ||
                            y == 0
                        )
                        {
                            Blocks[x, y, z] = new ContainerBlock();
                        }
                    }
                }
            }
        }
예제 #4
0
        /// <summary>
        /// This method performs a deep copy of the initial world state to a backup array for later restoration.
        /// </summary>
        private void CopyBlocks()
        {
            for (int x = 0; x < Blocks.GetLength(0); x++)
            {
                for (int y = 0; y < Blocks.GetLength(1); y++)
                {
                    for (int z = 0; z < Blocks.GetLength(2); z++)
                    {
                        if (Blocks[x, y, z] is AirBlock)
                        {
                            InitialBlocks[x, y, z] = new AirBlock();
                        }
                        else if (Blocks[x, y, z] is MulchBlock)
                        {
                            InitialBlocks[x, y, z] = new MulchBlock();
                        }
                        else if (Blocks[x, y, z] is ContainerBlock)
                        {
                            InitialBlocks[x, y, z] = new ContainerBlock();
                        }
                        else if (Blocks[x, y, z] is GrassBlock)
                        {
                            InitialBlocks[x, y, z] = new GrassBlock();
                        }
                        else if (Blocks[x, y, z] is StoneBlock)
                        {
                            InitialBlocks[x, y, z] = new StoneBlock();
                        }
                        else if (Blocks[x, y, z] is AcidicBlock)
                        {
                            InitialBlocks[x, y, z] = new AcidicBlock();
                        }
                        else if (Blocks[x, y, z] is NestBlock)
                        {
                            InitialBlocks[x, y, z] = new NestBlock();
                        }

                        InitialBlocks[x, y, z].worldXCoordinate = x;
                        InitialBlocks[x, y, z].worldYCoordinate = y;
                        InitialBlocks[x, y, z].worldZCoordinate = z;
                    }
                }
            }
        }
예제 #5
0
    void DigIfTooHigh()
    {
        // try to avoid getting stuck too high on a peak
        float groundHeight = transform.position.y - 0.5f;
        int   x            = (int)transform.position.x;
        int   z            = (int)transform.position.z;

        if (wm.surfaceBlocks[x - 1, z] + 2 < groundHeight && wm.surfaceBlocks[x + 1, z] + 2 < groundHeight && wm.surfaceBlocks[x, z - 1] + 2 < groundHeight && wm.surfaceBlocks[x, z + 1] + 2 < groundHeight)
        {
            int y = (int)(transform.position.y - 0.5f);
            if (wm.GetBlock(x, y, z) is Antymology.Terrain.GrassBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.StoneBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.AcidicBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.NestBlock)
            {
                AbstractBlock newBlock = new Antymology.Terrain.AirBlock();
                wm.SetBlock(x, y, z, newBlock);
                transform.position = new Vector3(transform.position.x, transform.position.y - 1, transform.position.z);
                wm.surfaceBlocks[x, z]--;
            }
        }
    }
예제 #6
0
    void Dig()
    {
        // dig up grasss, stone, acid, nest, or mulch blocks. helps to avoid getting stuck
        int x = (int)transform.position.x;
        int y = (int)(transform.position.y - 0.5f);
        int z = (int)transform.position.z;

        if (wm.GetBlock(x, y, z) is Antymology.Terrain.AirBlock)
        {
            transform.position = new Vector3(transform.position.x, transform.position.y - 1, transform.position.z);
            return;
        }
        if (wm.GetBlock(x, y, z) is Antymology.Terrain.GrassBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.StoneBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.AcidicBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.NestBlock || wm.GetBlock(x, y, z) is Antymology.Terrain.MulchBlock)
        {
            AbstractBlock newBlock = new Antymology.Terrain.AirBlock();
            wm.SetBlock(x, y, z, newBlock);
            transform.position = new Vector3(transform.position.x, transform.position.y - 1, transform.position.z);
            wm.surfaceBlocks[x, z]--;
        }
    }
예제 #7
0
 /// <summary>
 /// THIS CURRENTLY ONLY EXISTS AS A WAY OF SHOWING YOU WHATS POSSIBLE.
 /// </summary>
 /// <param name="neighbours"></param>
 public void Diffuse(AbstractBlock[,,] neighbours)
 {
     for (int i = 0; i < neighbours.GetLength(0); ++i)
     {
         for (int j = 0; i < neighbours.GetLength(1); ++j)
         {
             for (int k = 0; i < neighbours.GetLength(2); ++k)
             {
                 AirBlock neighbour = neighbours[i, j, k] as AirBlock;
                 if (neighbour != null)
                 {
                     foreach (KeyValuePair <bool, double> entry in neighbour.pheromoneDeposits)
                     {
                         pheromoneDeposits[entry.Key]           = (pheromoneDeposits[entry.Key] + neighbour.pheromoneDeposits[entry.Key]) / 2;
                         neighbour.pheromoneDeposits[entry.Key] = pheromoneDeposits[entry.Key];
                     }
                 }
             }
         }
     }
 }
예제 #8
0
        public void Reset(NeuralNetwork nextGen)
        {
            for (int i = 0; i < Blocks.GetLength(0); ++i)
            {
                for (int j = 0; j < Blocks.GetLength(1); ++j)
                {
                    for (int k = 0; k < Blocks.GetLength(2); ++k)
                    {
                        Blocks[i, j, k] = new AirBlock();
                    }
                }
            }

            Destroy(GameObject.Find("Chunks"));
            for (int i = 0; i < Ants.Length; ++i)
            {
                Destroy(Ants[i]);
            }

            AntDirective = nextGen;
            Init();
        }
예제 #9
0
        public void Reset()
        {
            for (int i = 0; i < Blocks.GetLength(0); ++i)
            {
                for (int j = 0; j < Blocks.GetLength(1); ++j)
                {
                    for (int k = 0; k < Blocks.GetLength(2); ++k)
                    {
                        Blocks[i, j, k] = new AirBlock();
                    }
                }
            }

            Destroy(GameObject.Find("Chunks"));
            for (int i = 0; i < Ants.Length; ++i)
            {
                Destroy(Ants[i]);
            }

            AntDirective.randomizeBiases();
            AntDirective.randomizeWeights();
            Init();
        }
예제 #10
0
        private void FixedUpdate()
        {
            if (ConfigurationManager.Instance.loadTopColony)
            {
                if (Input.GetKeyUp(KeyCode.KeypadPlus))
                {
                    topColony.MoveColony();
                }

                return;
            }


            if (Input.GetKeyUp(KeyCode.End))
            {
                pause = !pause;
            }

            if (pause && !Input.GetKeyUp(KeyCode.KeypadPlus))
            {
                return;
            }
            // Update all ants

            // Must determine when to respawn everything
            bool allDead = true;

            // If all colonies dead, regenerate world and colonies
            foreach (Agents.Colony colony in colonies)
            {
                if (!colony.isAllDead())
                {
                    allDead = false;

                    // Move all ants according to their environment and nervous system
                    colony.MoveColony();
                }
            }

            if (allDead)
            {
                generation++;

                float bestFitness = topColony.fitness();
                foreach (Agents.Colony colony in colonies)
                {
                    if (colony.getTotalNestBlocks() > bestFitness)
                    {
                        topColony.DestroyColony();
                        topColony           = colony;
                        bestFitness         = colony.fitness();
                        noNewTopColonySince = generation;
                    }
                }


                // Remove all but the best
                foreach (Agents.Colony colony1 in colonies)
                {
                    if (colony1 != topColony)
                    {
                        colony1.DestroyColony();
                    }
                }



                Debug.Log("On generation " + generation.ToString() + " the best colony produced " + Mathf.Max(new float[] { colonies[0].getTotalNestBlocks(), colonies[1].getTotalNestBlocks(), colonies[2].getTotalNestBlocks(), colonies[3].getTotalNestBlocks() }).ToString() + " blocks.");
                Debug.Log("BUT no new top colony since generation " + noNewTopColonySince.ToString() + " with a global best of " + bestFitness.ToString());
                Debug.Log("Queen of Top Colony size - nodes: " + topColony.queen.GetComponent <Agents.Ant>().getNervousSystem().nodes.Count.ToString() + " connections " + topColony.queen.GetComponent <Agents.Ant>().getNervousSystem().connections.Count.ToString());

                if (bestFitness > prevBestFitness)
                {
                    prevBestFitness = bestFitness;
                    Serialize(new Agents.SerializableNS(topColony.bestAnt.GetComponent <Antymology.Agents.Ant>().getNervousSystem()), "ant.dat");
                    Serialize(new Agents.SerializableNS(topColony.queen.GetComponent <Antymology.Agents.Ant>().getNervousSystem()), "queen.dat");
                }


                // Resetting the world
                if (generation % 10 == 0)
                {
                    // Reset the world. Every 20 generations
                    RNG          = new System.Random((int)Time.time);
                    SimplexNoise = new SimplexNoise((int)Time.time);
                    // Initialize a new 3D array of blocks with size of the number of chunks times the size of each chunk
                    Blocks = new AbstractBlock[
                        ConfigurationManager.Instance.World_Diameter * ConfigurationManager.Instance.Chunk_Diameter,
                        ConfigurationManager.Instance.World_Height *ConfigurationManager.Instance.Chunk_Diameter,
                        ConfigurationManager.Instance.World_Diameter *ConfigurationManager.Instance.Chunk_Diameter];

                    for (int i = 0; i < ConfigurationManager.Instance.World_Diameter * ConfigurationManager.Instance.Chunk_Diameter; i++)
                    {
                        for (int j = 0; j < ConfigurationManager.Instance.World_Height * ConfigurationManager.Instance.Chunk_Diameter; j++)
                        {
                            for (int k = 0; k < ConfigurationManager.Instance.World_Diameter * ConfigurationManager.Instance.Chunk_Diameter; k++)
                            {
                                Blocks[i, j, k] = new AirBlock();
                            }
                        }
                    }


                    GameObject chunks = GameObject.Find("Chunks");
                    Destroy(chunks);

                    // Initialize a new 3D array of chunks with size of the number of chunks
                    Chunks = new Chunk[
                        ConfigurationManager.Instance.World_Diameter,
                        ConfigurationManager.Instance.World_Height,
                        ConfigurationManager.Instance.World_Diameter];


                    GenerateData();
                    GenerateChunks();
                }

                GenerateAnts();
            }
        }