Пример #1
0
 private static RailEntity.NeighborConnection FindConnectionPoint(RailEntity A, RailEntity B)
 {
     if (!A.NeighborRails.Any(n => n.NeighborID == B.GlobalID))
     {
         return(null);
     }
     return(A.NeighborRails.First(n => n.NeighborID == B.GlobalID));
 }
Пример #2
0
        public static RailEntity CreatePreviewBody(ComponentManager Manager, VoxelHandle Location, JunctionPiece Piece)
        {
            var r = new RailEntity(Manager, Location, Piece);

            Manager.RootComponent.AddChild(r);
            r.SetFlagRecursive(GameComponent.Flag.Active, false);

            foreach (var tinter in r.EnumerateAll().OfType <Tinter>())
            {
                tinter.Stipple = true;
            }

            r.SetFlag(GameComponent.Flag.ShouldSerialize, false);
            //Todo: Add craft details component.
            return(r);
        }
Пример #3
0
        public static IEnumerable <uint> EnumerateForwardNetworkConnections(RailEntity Leaving, RailEntity Entering)
        {
            if (Leaving == null)
            {
                foreach (var neighbor in Entering.NeighborRails)
                {
                    yield return(neighbor.NeighborID);
                }
                yield break;
            }

            var connectionPoint = FindConnectionPoint(Leaving, Entering);

            if (connectionPoint != null)
            {
                if (Library.GetRailPiece(Entering.GetPiece().RailPiece).HasValue(out var enteringPiece))
                {
                    var transformToEntitySpace = Matrix.CreateRotationY((float)Math.PI * 0.5f * (float)Entering.GetPiece().Orientation) * Entering.GlobalTransform;
                    var backConnection         = FindConnectionPoint(Entering, Leaving);

                    var connection = FindConnectionFromTransformedEntrancePoint(enteringPiece, transformToEntitySpace,
                                                                                backConnection.Raised ? (connectionPoint.Position - Vector3.UnitY) : connectionPoint.Position);

                    if (connection != null)
                    {
                        foreach (var exit in connection.Exits)
                        {
                            var transformedExit = Vector3.Transform(exit, transformToEntitySpace);
                            foreach (var neighbor in Entering.NeighborRails)
                            {
                                if (neighbor.Raised)
                                {
                                    transformedExit += Vector3.UnitY;
                                }

                                if ((neighbor.Position - transformedExit).LengthSquared() < 0.01f)
                                {
                                    yield return(neighbor.NeighborID);
                                }
                            }
                        }
                    }
                }
            }
        }
Пример #4
0
        public override void OnVoxelsSelected(List <VoxelHandle> refs, InputManager.MouseButton button)
        {
            if (Command.Contains("Build/"))
            {
                if (Library.CreateZone(Command.Substring(6), World).HasValue(out var zone))
                {
                    World.AddZone(zone);
                    zone.CompleteRoomImmediately(refs);
                }
            }
            if (Command.Contains("Spawn/"))
            {
                string type = Command.Substring(6);
                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    if (vox.IsEmpty)
                    {
                        var offset = Vector3.Zero;

                        if (Library.GetCraftable(type).HasValue(out var craftItem))
                        {
                            offset = craftItem.SpawnOffset;
                        }

                        var body = EntityFactory.CreateEntity <GameComponent>(type, vox.WorldPosition + new Vector3(0.5f, 0.0f, 0.5f) + offset);
                        if (body != null)
                        {
                            body.PropogateTransforms();

                            if (craftItem != null)
                            {
                                if (craftItem.AddToOwnedPool)
                                {
                                    World.PlayerFaction.OwnedObjects.Add(body);
                                }

                                if (craftItem.Deconstructable)
                                {
                                    body.Tags.Add("Deconstructable"); // Todo: Should not need to set tag every time item is created. Inherint?
                                }
                            }
                        }
                    }
                }
            }
            else if (Command.Contains("Resource/"))
            {
                string type = Command.Substring("Resource/".Length);
                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    var body = World.ComponentManager.RootComponent.AddChild(new ResourceEntity(World.ComponentManager, new Resource(type), vox.WorldPosition + new Vector3(0.5f, 0.5f, 0.5f)));
                    body.PropogateTransforms();
                }
            }
            else if (Command.Contains("Rail/"))
            {
                string type     = Command.Substring("Rail/".Length);
                var    junction = new Rail.JunctionPiece
                {
                    RailPiece   = type,
                    Orientation = Rail.PieceOrientation.North,
                    Offset      = Point.Zero
                };

                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    if (vox.IsEmpty)
                    {
                        var entity = new Rail.RailEntity(World.ComponentManager, vox, junction);
                        World.ComponentManager.RootComponent.AddChild(entity);
                    }
                }
            }
            else if (Command.Contains("Grass/"))
            {
                var type = Library.GetGrassType(Command.Substring(6));
                if (type != null)
                {
                    foreach (var vox in refs.Where(v => v.IsValid))
                    {
                        var v = vox;
                        if (!vox.IsEmpty)
                        {
                            v.GrassType  = type.ID;
                            v.GrassDecay = type.InitialDecayValue;
                        }
                    }
                }
            }
            else if (Command.Contains("Decal/"))
            {
                var type = Library.GetDecalType(Command.Substring(6));
                if (type != null)
                {
                    foreach (var vox in refs.Where(v => v.IsValid))
                    {
                        var v = vox;
                        if (!vox.IsEmpty)
                        {
                            v.DecalType = type.ID;
                        }
                    }
                }
            }
            else if (Command.Contains("Disease"))
            {
                foreach (var creature in World.EnumerateIntersectingObjects(VoxelHelpers.GetVoxelBoundingBox(refs), CollisionType.Both).OfType <Creature>())
                {
                    creature.Stats.AcquireDisease(DiseaseLibrary.GetRandomDisease());
                }
            }
            else
            {
                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    if (Command.Contains("Place/"))
                    {
                        string type = Command.Substring(6);
                        var    v    = vox;
                        if (Library.GetVoxelType(type).HasValue(out VoxelType vType))
                        {
                            v.Type = vType;
                        }
                        v.QuickSetLiquid(LiquidType.None, 0);

                        if (type == "Magic")
                        {
                            World.ComponentManager.RootComponent.AddChild(
                                new DestroyOnTimer(World.ComponentManager, World.ChunkManager, vox)
                            {
                                DestroyTimer = new Timer(5.0f + MathFunctions.Rand(-0.5f, 0.5f), true)
                            });
                        }
                    }
                    else
                    {
                        switch (Command)
                        {
                        case "Delete Block":
                        {
                            var v = vox;
                            World.OnVoxelDestroyed(vox);
                            v.Type = Library.EmptyVoxelType;
                            v.QuickSetLiquid(LiquidType.None, 0);
                        }
                        break;

                        case "Nuke Column":
                        {
                            for (var y = 1; y < World.WorldSizeInVoxels.Y; ++y)
                            {
                                var v = World.ChunkManager.CreateVoxelHandle(new GlobalVoxelCoordinate(vox.Coordinate.X, y, vox.Coordinate.Z));
                                v.Type = Library.EmptyVoxelType;
                                v.QuickSetLiquid(LiquidType.None, 0);
                            }
                        }
                        break;

                        case "Kill Block":
                            foreach (var selected in refs)
                            {
                                if (!selected.IsEmpty)
                                {
                                    VoxelHelpers.KillVoxel(World, selected);
                                }
                            }
                            break;

                        case "Fill Water":
                        {
                            if (vox.IsEmpty)
                            {
                                var v = vox;
                                v.QuickSetLiquid(LiquidType.Water, WaterManager.maxWaterLevel);
                            }
                        }
                        break;

                        case "Fill Lava":
                        {
                            if (vox.IsEmpty)
                            {
                                var v = vox;
                                v.QuickSetLiquid(LiquidType.Lava, WaterManager.maxWaterLevel);
                            }
                        }
                        break;

                        case "Fire":
                        {
                            foreach (var flam2 in World.EnumerateIntersectingObjects(vox.GetBoundingBox(), CollisionType.Both).OfType <Flammable>())
                            {
                                flam2.Heat = flam2.Flashpoint + 1;
                            }
                        }
                        break;

                        default:
                            break;
                        }
                    }
                }
            }
        }
Пример #5
0
        public override void OnVoxelsSelected(List <VoxelHandle> refs, InputManager.MouseButton button)
        {
            if (Command.Contains("Build/"))
            {
                string         type = Command.Substring(6);
                BuildRoomOrder des  = new BuildRoomOrder(RoomLibrary.CreateRoom(Player.Faction, type, refs, false, Player.World), Player.Faction, Player.World);
                des.ToBuild.Designations = refs;
                Player.Faction.RoomBuilder.BuildDesignations.Add(des);
                Player.Faction.RoomBuilder.DesignatedRooms.Add(des.ToBuild);
                des.Build();
            }
            if (Command.Contains("Spawn/"))
            {
                string type = Command.Substring(6);
                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    if (vox.IsEmpty)
                    {
                        var craftItem = CraftLibrary.GetCraftable(type);
                        var offset    = Vector3.Zero;

                        if (craftItem != null)
                        {
                            offset = craftItem.SpawnOffset;
                        }

                        var body = EntityFactory.CreateEntity <Body>(type, vox.WorldPosition + new Vector3(0.5f, 0.0f, 0.5f) + offset);
                        if (body != null)
                        {
                            body.PropogateTransforms();

                            if (craftItem != null)
                            {
                                if (craftItem.AddToOwnedPool)
                                {
                                    Player.Faction.OwnedObjects.Add(body);
                                }

                                if (craftItem.Moveable)
                                {
                                    body.Tags.Add("Moveable");
                                }

                                if (craftItem.Deconstructable)
                                {
                                    body.Tags.Add("Deconstructable");
                                }
                            }
                        }
                    }
                }
            }
            else if (Command.Contains("Rail/"))
            {
                string type     = Command.Substring("Rail/".Length);
                var    junction = new Rail.JunctionPiece
                {
                    RailPiece   = type,
                    Orientation = Rail.PieceOrientation.North,
                    Offset      = Point.Zero
                };

                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    if (vox.IsEmpty)
                    {
                        var entity = new Rail.RailEntity(Player.World.ComponentManager, vox, junction);
                        Player.World.ComponentManager.RootComponent.AddChild(entity);
                    }
                }
            }
            else if (Command.Contains("Grass/"))
            {
                var type = GrassLibrary.GetGrassType(Command.Substring(6));
                foreach (var vox in refs.Where(v => v.IsValid))
                {
                    var v = vox;
                    if (!vox.IsEmpty)
                    {
                        v.GrassType = type.ID;
                    }
                }
            }
            else if (Command.Contains("Decal/"))
            {
                var type = DecalLibrary.GetGrassType(Command.Substring(6));
                foreach (var vox in refs.Where(v => v.IsValid))
                {
                    var v = vox;
                    if (!vox.IsEmpty)
                    {
                        v.Decal = DecalType.EncodeDecal(DecalOrientation, type.ID);
                    }
                }
            }
            else
            {
                foreach (var vox in refs.Where(vox => vox.IsValid))
                {
                    if (Command.Contains("Place/"))
                    {
                        string type = Command.Substring(6);
                        var    v    = vox;
                        v.Type = VoxelLibrary.GetVoxelType(type);
                        v.QuickSetLiquid(LiquidType.None, 0);

                        if (type == "Magic")
                        {
                            Player.World.ComponentManager.RootComponent.AddChild(
                                new DestroyOnTimer(Player.World.ComponentManager, Player.World.ChunkManager, vox)
                            {
                                DestroyTimer = new Timer(5.0f + MathFunctions.Rand(-0.5f, 0.5f), true)
                            });
                        }
                    }
                    else
                    {
                        switch (Command)
                        {
                        case "Delete Block":
                        {
                            var v = vox;
                            Player.World.Master.Faction.OnVoxelDestroyed(vox);
                            v.Type = VoxelLibrary.emptyType;
                            v.QuickSetLiquid(LiquidType.None, 0);
                        }
                        break;

                        case "Kill Block":
                            foreach (var selected in refs)
                            {
                                if (!selected.IsEmpty)
                                {
                                    Player.World.ChunkManager.KillVoxel(selected);
                                }
                            }
                            break;

                        case "Fill Water":
                        {
                            if (vox.IsEmpty)
                            {
                                var v = vox;
                                v.QuickSetLiquid(LiquidType.Water, WaterManager.maxWaterLevel);
                            }
                        }
                        break;

                        case "Fill Lava":
                        {
                            if (vox.IsEmpty)
                            {
                                var v = vox;
                                v.QuickSetLiquid(LiquidType.Lava, WaterManager.maxWaterLevel);
                            }
                        }
                        break;

                        case "Fire":
                        {
                            foreach (var flam2 in Player.World.EnumerateIntersectingObjects(vox.GetBoundingBox(), CollisionType.Both).OfType <Flammable>())
                            {
                                flam2.Heat = flam2.Flashpoint + 1;
                            }
                        }
                        break;

                        case "Kill Things":
                        {
                            foreach (var comp in Player.World.EnumerateIntersectingObjects(vox.GetBoundingBox(), CollisionType.Both))
                            {
                                comp.Die();
                            }
                        }
                        break;

                        case "Disease":
                        {
                            foreach (var creature in Player.World.EnumerateIntersectingObjects(vox.GetBoundingBox(), CollisionType.Both).OfType <Creature>())
                            {
                                var disease = Datastructures.SelectRandom(DiseaseLibrary.Diseases);
                                creature.AcquireDisease(disease.Name);
                            }
                            break;
                        }

                        default:
                            break;
                        }
                    }
                }
            }
        }
Пример #6
0
        public static bool CanPlace(WorldManager World, RailEntity PreviewEntity)
        {
            // Todo: Make sure this uses BuildObjectTool.IsValidPlacement to enforce building rules.

            var junctionPiece  = PreviewEntity.GetPiece();
            var actualPosition = PreviewEntity.GetContainingVoxel();

            if (!actualPosition.IsValid)
            {
                return(false);
            }
            if (!actualPosition.IsEmpty)
            {
                return(false);
            }

            if (actualPosition.Coordinate.Y == 0)
            {
                return(false);                                  // ???
            }
            var voxelUnder = VoxelHelpers.GetVoxelBelow(actualPosition);

            if (voxelUnder.IsEmpty)
            {
                return(false);
            }
            var box = actualPosition.GetBoundingBox().Expand(-0.2f);

            foreach (var entity in World.EnumerateIntersectingObjects(box, CollisionType.Static))
            {
                if ((entity as GameComponent).IsDead)
                {
                    continue;
                }

                if (Object.ReferenceEquals(entity, PreviewEntity))
                {
                    continue;
                }
                if (Object.ReferenceEquals(entity.GetRoot(), PreviewEntity.GetRoot()))
                {
                    continue;
                }
                if (entity is GenericVoxelListener)
                {
                    continue;
                }
                if (entity is WorkPile)
                {
                    continue;
                }
                if (entity is Health)
                {
                    continue;
                }
                if (entity is CraftDetails)
                {
                    continue;
                }
                if (entity is SimpleSprite)
                {
                    continue;
                }

                if (FindPossibleCombination(junctionPiece, entity).HasValue(out var possibleCombination))
                {
                    var combinedPiece = new Rail.JunctionPiece
                    {
                        RailPiece   = possibleCombination.Result,
                        Orientation = Rail.OrientationHelper.Rotate((entity as RailEntity).GetPiece().Orientation, (int)possibleCombination.ResultRelativeOrientation),
                    };

                    PreviewEntity.UpdatePiece(combinedPiece, PreviewEntity.GetContainingVoxel());
                    return(true);
                }

                if (Debugger.Switches.DrawToolDebugInfo)
                {
                    Drawer3D.DrawBox(box, Color.Yellow, 0.2f, false);
                }

                World.UserInterface.ShowTooltip(String.Format("Can't place {0}. Entity in the way: {1}", junctionPiece.RailPiece, entity.ToString()));
                return(false);
            }

            return(true);
        }
Пример #7
0
        public static bool CanPlace(GameMaster Player, RailEntity PreviewEntity)
        {
            // Todo: Make sure this uses BuildObjectTool.IsValidPlacement to enforce building rules.

            var junctionPiece  = PreviewEntity.GetPiece();
            var actualPosition = PreviewEntity.GetContainingVoxel();

            if (!actualPosition.IsValid)
            {
                return(false);
            }
            if (!actualPosition.IsEmpty)
            {
                return(false);
            }

            if (actualPosition.Coordinate.Y == 0)
            {
                return(false);                                  // ???
            }
            var local      = actualPosition.Coordinate.GetLocalVoxelCoordinate();
            var voxelUnder = new VoxelHandle(actualPosition.Chunk, new LocalVoxelCoordinate(local.X, local.Y - 1, local.Z));

            if (voxelUnder.IsEmpty)
            {
                return(false);
            }

            foreach (var entity in Player.World.EnumerateIntersectingObjects(actualPosition.GetBoundingBox().Expand(-0.2f), CollisionType.Static))
            {
                if ((entity as GameComponent).IsDead)
                {
                    continue;
                }

                if (Object.ReferenceEquals(entity, PreviewEntity))
                {
                    continue;
                }
                if (entity is GenericVoxelListener)
                {
                    continue;
                }
                if (entity is WorkPile)
                {
                    continue;
                }

                var possibleCombination = FindPossibleCombination(junctionPiece, entity);
                if (possibleCombination != null)
                {
                    var combinedPiece = new Rail.JunctionPiece
                    {
                        RailPiece   = possibleCombination.Result,
                        Orientation = Rail.OrientationHelper.Rotate((entity as RailEntity).GetPiece().Orientation, (int)possibleCombination.ResultRelativeOrientation),
                    };

                    PreviewEntity.UpdatePiece(combinedPiece, PreviewEntity.GetContainingVoxel());
                    return(true);
                }

                if (Debugger.Switches.DrawBoundingBoxes)
                {
                    Drawer3D.DrawBox(entity.GetBoundingBox(), Color.Yellow, 0.1f, false);
                    Player.World.ShowTooltip(String.Format("Can't place {0}. Entity in the way: {1}", junctionPiece.RailPiece, entity.ToString()));
                }

                return(false);
            }

            return(true);
        }