public static NavigationMesh GenerateNavigationMesh(CellGrid From)
        {
            var meshes = new List<Gem.Geo.Mesh>();
            From.ForEachTile((c, x, y, z) =>
                {
                    // Avoid adding tiles that have a tile directly above them.
                    if (z != (From.depth - 1))
                        if (From.CellAt(x, y, z + 1).Tile != null) return;

                    if (c.Tile != null)
                    {
                        var mesh = c.Tile.NavigationMesh;
                        if (mesh != null)
                        {
                            mesh = Gem.Geo.Gen.Copy(mesh);
                            Gem.Geo.Gen.Transform(mesh, Matrix.CreateTranslation(x + 0.5f, y + 0.5f, z));
                            mesh.Tag = c;
                            meshes.Add(mesh);
                        }
                    }
                });

            var rawNavMesh = Gem.Geo.Gen.Merge(meshes.ToArray());
            rawNavMesh = Gem.Geo.Gen.WeldCopy(rawNavMesh);

            var navMesh = new Gem.Geo.EdgeMesh(rawNavMesh);
            return NavigationMesh.Create(navMesh);
        }
        public static Gem.Geo.Mesh ChunkGeometry(CellGrid Grid, BlockSet Blocks)
        {
            InitializeStaticData();

            var models = new List<Gem.Geo.Mesh>();

            Grid.forAll((cell, x, y, z) =>
                {
                    if (cell.Block != null)
                    {
                        var cube = CreateNormalBlockMesh(Blocks.Tiles, cell.Block);

                        if (cell.Block.Orientable)
                            Gem.Geo.Gen.Transform(cube, Matrix.CreateRotationZ(
                                (Gem.Math.Angle.PI / 2) * (int)cell.BlockOrientation));

                        Gem.Geo.Gen.Transform(cube, Matrix.CreateTranslation(x + 0.5f, y + 0.5f, z + 0.5f));

                        models.Add(cube);

                        if (!String.IsNullOrEmpty(cell.Block.Hanging) && Grid.check(x, y, z - 1) && !Grid.CellAt(x, y, z - 1).IsSolid)
                        {
                            var hangingBlock = Blocks.Templates[cell.Block.Hanging];
                            cube = CreateNormalBlockMesh(Blocks.Tiles, hangingBlock);
                            if (hangingBlock.Orientable)
                                Gem.Geo.Gen.Transform(cube, Matrix.CreateRotationZ(
                                    (Gem.Math.Angle.PI / 2) * (int)cell.BlockOrientation));

                            Gem.Geo.Gen.Transform(cube, Matrix.CreateTranslation(x + 0.5f, y + 0.5f, z - 0.5f));

                            models.Add(cube);
                        }
                    }

                    if (cell.Decal != null)
                    {
                        var navMesh = cell.Block == null ? ShapeTemplates[cell.Decal.Shape].NavigationMesh : ShapeTemplates[cell.Block.Shape].NavigationMesh;
                        var copy = Gem.Geo.Gen.Copy(navMesh);
                        Gem.Geo.Gen.MorphEx(copy, (inV) =>
                        {
                            var r = inV;
                            r.TextureCoordinate = Vector2.Transform(r.TextureCoordinate, Blocks.Tiles.TileMatrix(cell.Decal.Top));
                            return r;
                        });

                        if (cell.Block != null && cell.Block.Orientable)
                            Gem.Geo.Gen.Transform(copy, Matrix.CreateRotationZ(
                                (Gem.Math.Angle.PI / 2) * (int)cell.BlockOrientation));

                        // Nav meshes are not centered at 0.5, so they don't need to be translated as much.
                        Gem.Geo.Gen.Transform(copy, Matrix.CreateTranslation(x + 0.5f, y + 0.5f, z));

                        models.Add(copy);
                    }

                    if (cell.Task != null)
                    {
                        var markerCube = CreateMarkerBlockMesh(Blocks.Tiles, cell.Task.MarkerTile);
                        Gem.Geo.Gen.Transform(markerCube, Matrix.CreateTranslation(x, y, z));
                        models.Add(markerCube);
                    }

                    if (cell.HasFlag(CellFlags.Storehouse) && cell.Navigatable && cell.NavigationMesh != null)
                    {
                        var navMesh = Gem.Geo.Gen.TransformCopy(cell.NavigationMesh, Matrix.CreateTranslation(0.0f, 0.0f, 0.02f));
                        Gem.Geo.Gen.MorphEx(navMesh, (inV) =>
                        {
                            var r = inV;
                            r.TextureCoordinate = Vector2.Transform(r.TextureCoordinate, Blocks.Tiles.TileMatrix(TileNames.Storehouse));
                            return r;
                        });
                        models.Add(navMesh);
                    }

                    //if (cell.Block != null && cell.NavigationMesh != null)
                    //{
                    //    var navMesh = Gem.Geo.Gen.TransformCopy(cell.NavigationMesh, Matrix.CreateTranslation(0.0f, 0.0f, 0.02f));
                    //    Gem.Geo.Gen.MorphEx(navMesh, (inV) =>
                    //    {
                    //        var r = inV;
                    //        r.TextureCoordinate = Vector2.Transform(r.TextureCoordinate, Tiles.TileMatrix(3));
                    //        return r;
                    //    });
                    //    models.Add(navMesh);
                    //}

                    var offsetsIndex = 0;
                    if (ResourceOffsets.ContainsKey(cell.Resources.Count))
                        offsetsIndex = cell.Resources.Count;

                    for (int i = 0; i < cell.Resources.Count; ++i)
                    {
                        var resourceCube = CreateResourceBlockMesh(Blocks.Tiles, Blocks.Templates[cell.Resources[i]]);
                        Gem.Geo.Gen.Transform(resourceCube, Matrix.CreateTranslation(cell.CenterPoint
                            + ResourceOffsets[offsetsIndex][i % ResourceOffsets[offsetsIndex].Length]
                            + new Vector3(0.0f, 0.0f, (cell.Block == null ? 0.0f : cell.Block.ResourceHeightOffset))));
                        models.Add(resourceCube);
                    }

                });

            return Gem.Geo.Gen.Merge(models.ToArray());
        }
Beispiel #3
0
        public Simulation(EpisodeContentManager Content, float SimStepLength)
        {
            this.SimStepLength = SimStepLength;
            SimStepTime = 0.0f;

            var definitionFile = Content.OpenUnbuiltTextStream("blocks.txt").ReadToEnd();
            var loadedBlocks = BlockSetLoader.LoadDefinitionFile(definitionFile);
            Blocks = new BlockSet
            {
                Tiles = new TileSheet(Content.Load<Texture2D>("tiles"), 16, 16),
                Templates = loadedBlocks.NamedBlocks
            };

            World = new CellGrid(16, 16, 16);

            World.forAll((t, x, y, z) =>
                {
                    if (z <= 1) t.Block = Blocks.Templates["Grass"];
                    else t.Block = null;
                });

            World.CellAt(4, 4, 1).SetFlag(CellFlags.Storehouse, true);

            World.CellAt(1, 1, 2).Block = Blocks.Templates["Slope"];
            World.CellAt(1, 1, 2).BlockOrientation = CellLink.Directions.North;

            World.CellAt(1, 2, 2).Block = Blocks.Templates["Slope"];
            World.CellAt(1, 2, 2).BlockOrientation = CellLink.Directions.East;

            World.CellAt(1, 3, 2).Block = Blocks.Templates["Slope"];
            World.CellAt(1, 3, 2).BlockOrientation = CellLink.Directions.South;

            World.CellAt(1, 4, 2).Block = Blocks.Templates["Slope"];
            World.CellAt(1, 4, 2).BlockOrientation = CellLink.Directions.West;

            World.CellAt(8, 8, 6).Block = Blocks.Templates["Grass"];

            World.CellAt(6, 6, 1).Decal = Blocks.Templates["TrackH"];
            World.CellAt(7, 6, 2).Block = Blocks.Templates["Slope"];
            World.CellAt(7, 6, 2).BlockOrientation = CellLink.Directions.West;
            World.CellAt(7, 6, 2).Decal = Blocks.Templates["TrackV"];

            Actors = new List<Actor>();
            Tasks = new List<Task>();
            Minds = new List<GnomeMind>();

            World.PrepareNavigation();
            World.MarkDirtyChunk();

            for (int i = 0; i < 4; ++i)
            {
                var gnomeActor = new Gnome(this, Blocks.Tiles);
                gnomeActor.Location = new Coordinate(0, i, 1);
                Actors.Add(gnomeActor);
                Minds.Add(gnomeActor.Mind);
            }
        }