예제 #1
0
        public void CheckForLavaAndWater(Body Body, DwarfTime gameTime, ChunkManager chunks)
        {
            foreach (var coordinate in VoxelHelpers.EnumerateCoordinatesInBoundingBox(Body.BoundingBox))
            {
                var voxel = new VoxelHandle(chunks.ChunkData, coordinate);
                if (!voxel.IsValid || voxel.LiquidLevel == 0)
                {
                    continue;
                }

                if (voxel.LiquidType == LiquidType.Lava)
                {
                    Heat += 100.0f;
                }
                else if (voxel.LiquidType == LiquidType.Water)
                {
                    Heat = Math.Max(0.0f, Heat - 100.0f);
                }
            }
        }
예제 #2
0
        public IEnumerable <VoxelHandle> Select(BoundingBox buffer, Vector3 start, Vector3 end)
        {
            switch (Brush)
            {
            case VoxelBrush.Box:
                return(VoxelHelpers.EnumerateCoordinatesInBoundingBox(buffer)
                       .Select(c => new VoxelHandle(Chunks.ChunkData, c))
                       .Where(v => v.IsValid));

            case VoxelBrush.Shell:
                return(EnumerateShell(buffer)
                       .Select(c => new VoxelHandle(Chunks.ChunkData, c))
                       .Where(v => v.IsValid));

            case VoxelBrush.Stairs:
                return(EnumerateStairVoxels(buffer, start, end, SelectionType == VoxelSelectionType.SelectFilled)
                       .Select(c => new VoxelHandle(Chunks.ChunkData, c))
                       .Where(v => v.IsValid));

            default:
                throw new InvalidOperationException("VoxelBrush has invalid value");
            }
        }
예제 #3
0
        public void Update()
        {
            MouseState    mouse    = Mouse.GetState();
            KeyboardState keyboard = Keyboard.GetState();

            var underMouse = GetVoxelUnderMouse();
            // Keep track of whether a new voxel has been selected.
            bool newVoxel = underMouse.IsValid && underMouse != VoxelUnderMouse;

            if (!underMouse.IsValid)
            {
                return;
            }

            VoxelUnderMouse = underMouse;

            // Update the cursor light.
            World.CursorLightPos = underMouse.WorldPosition + new Vector3(0.5f, 0.5f, 0.5f);

            // Get the type of the voxel and display it to the player.
            if (Enabled && !underMouse.IsEmpty && underMouse.IsExplored)
            {
                string info = underMouse.Type.Name;

                // If it belongs to a room, display that information.
                if (World.PlayerFaction.RoomBuilder.IsInRoom(underMouse))
                {
                    Room room = World.PlayerFaction.RoomBuilder.GetMostLikelyRoom(underMouse);

                    if (room != null)
                    {
                        info += " (" + room.ID + ")";
                    }
                }
                World.ShowInfo(info);
            }

            // Do nothing if not enabled.
            if (!Enabled)
            {
                return;
            }

            bool altPressed = false;

            // If the left or right ALT keys are pressed, we can adjust the height of the selection
            // for building pits and tall walls using the mouse wheel.
            if (keyboard.IsKeyDown(Keys.LeftAlt) || keyboard.IsKeyDown(Keys.RightAlt))
            {
                var change = mouse.ScrollWheelValue - LastMouseWheel;
                BoxYOffset += (change) * 0.01f;
                int offset = (int)BoxYOffset;
                if (offset != PrevBoxYOffsetInt)
                {
                    DragSound.Play(World.CursorLightPos);
                    newVoxel = true;
                }
                PrevBoxYOffsetInt = offset;
                altPressed        = true;
            }
            else
            {
                PrevBoxYOffsetInt = 0;
            }
            LastMouseWheel = mouse.ScrollWheelValue;

            // Draw a box around the current voxel under the mouse.
            if (underMouse.IsValid)
            {
                BoundingBox box = underMouse.GetBoundingBox().Expand(0.05f);
                Drawer3D.DrawBox(box, CurrentColor, CurrentWidth, true);
            }

            // If the left mouse button is pressed, update the slection buffer.
            if (isLeftPressed)
            {
                // On release, select voxels.
                if (mouse.LeftButton == ButtonState.Released)
                {
                    ReleaseSound.Play(World.CursorLightPos);
                    isLeftPressed = false;
                    LeftReleasedCallback();
                    BoxYOffset        = 0;
                    PrevBoxYOffsetInt = 0;
                }
                // Otherwise, update the selection buffer
                else
                {
                    if (SelectionBuffer.Count == 0)
                    {
                        FirstVoxel = underMouse;
                        SelectionBuffer.Add(underMouse);
                    }
                    else
                    {
                        SelectionBuffer.Clear();
                        SelectionBuffer.Add(FirstVoxel);
                        SelectionBuffer.Add(underMouse);
                        BoundingBox buffer = GetSelectionBox();

                        // Update the selection box to account for offsets from mouse wheel.
                        if (BoxYOffset > 0)
                        {
                            buffer.Max.Y += (int)BoxYOffset;
                        }
                        else if (BoxYOffset < 0)
                        {
                            buffer.Min.Y += (int)BoxYOffset;
                        }

                        SelectionBuffer = Select(buffer, FirstVoxel.WorldPosition, underMouse.WorldPosition).ToList();

                        if (!altPressed && Brush != VoxelBrush.Stairs)
                        {
                            if (SelectionType == VoxelSelectionType.SelectFilled)
                            {
                                SelectionBuffer.RemoveAll(v =>
                                {
                                    if (v.Equals(underMouse))
                                    {
                                        return(false);
                                    }
                                    return(v.IsExplored && !VoxelHelpers.DoesVoxelHaveVisibleSurface(
                                               Chunks.ChunkData, v));
                                });
                            }
                        }

                        if (newVoxel)
                        {
                            DragSound.Play(World.CursorLightPos, SelectionBuffer.Count / 20.0f);
                            Dragged.Invoke(SelectionBuffer, InputManager.MouseButton.Left);
                        }
                    }
                }
            }
            // If the mouse was not previously pressed, but is now pressed, then notify us of that.
            else if (mouse.LeftButton == ButtonState.Pressed)
            {
                ClickSound.Play(World.CursorLightPos);;
                isLeftPressed     = true;
                BoxYOffset        = 0;
                PrevBoxYOffsetInt = 0;
            }

            // Case where the right mouse button is pressed (mirrors left mouse button)
            // TODO(Break this into a function)
            if (isRightPressed)
            {
                if (mouse.RightButton == ButtonState.Released)
                {
                    ReleaseSound.Play(World.CursorLightPos);
                    isRightPressed = false;
                    RightReleasedCallback();
                    BoxYOffset        = 0;
                    PrevBoxYOffsetInt = 0;
                }
                else
                {
                    if (SelectionBuffer.Count == 0)
                    {
                        SelectionBuffer.Add(underMouse);
                        FirstVoxel = underMouse;
                    }
                    else
                    {
                        SelectionBuffer.Clear();
                        SelectionBuffer.Add(FirstVoxel);
                        SelectionBuffer.Add(underMouse);
                        BoundingBox buffer = GetSelectionBox();
                        if (BoxYOffset > 0)
                        {
                            buffer.Max.Y += (int)BoxYOffset;
                        }
                        else if (BoxYOffset < 0)
                        {
                            buffer.Min.Y += (int)BoxYOffset;
                        }

                        SelectionBuffer = VoxelHelpers.EnumerateCoordinatesInBoundingBox(buffer)
                                          .Select(c => new VoxelHandle(Chunks.ChunkData, c))
                                          .Where(v => v.IsValid)
                                          .ToList();

                        if (newVoxel)
                        {
                            DragSound.Play(World.CursorLightPos, SelectionBuffer.Count / 20.0f);
                            Dragged.Invoke(SelectionBuffer, InputManager.MouseButton.Right);
                        }
                    }
                }
            }
            else if (mouse.RightButton == ButtonState.Pressed)
            {
                ClickSound.Play(World.CursorLightPos);
                RightPressedCallback();
                BoxYOffset     = 0;
                isRightPressed = true;
            }
        }
예제 #4
0
        public static bool IsValidPlacement(
            VoxelHandle Location,
            ResourceType CraftType,
            WorldManager World,
            GameComponent PreviewBody,
            String Verb,
            String PastParticple)
        {
            if (CraftType == null)
            {
                return(false);
            }

            switch (CraftType.Placement_PlacementRequirement)
            {
            case ResourceType.PlacementRequirement.NearWall:
            {
                var neighborFound = VoxelHelpers.EnumerateManhattanNeighbors2D(Location.Coordinate)
                                    .Select(c => new VoxelHandle(World.ChunkManager, c))
                                    .Any(v => v.IsValid && !v.IsEmpty);

                if (!neighborFound)
                {
                    World.UserInterface.ShowTooltip("Must be " + PastParticple + " next to wall!");
                    return(false);
                }

                break;
            }

            case ResourceType.PlacementRequirement.OnGround:
            {
                var below = VoxelHelpers.GetNeighbor(Location, new GlobalVoxelOffset(0, -1, 0));

                if (!below.IsValid || below.IsEmpty)
                {
                    World.UserInterface.ShowTooltip("Must be " + PastParticple + " on solid ground!");
                    return(false);
                }
                break;
            }
            }

            if (PreviewBody != null)
            {
                // Just check for any intersecting body in octtree.

                var previewBox = PreviewBody.GetRotatedBoundingBox();
                var sensorBox  = previewBox;

                GenericVoxelListener sensor;
                if (PreviewBody.GetComponent <GenericVoxelListener>().HasValue(out sensor))
                {
                    sensorBox = sensor.GetRotatedBoundingBox();
                }

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

                foreach (var intersectingObject in World.EnumerateIntersectingObjects(sensorBox, CollisionType.Static))
                {
                    if (Object.ReferenceEquals(intersectingObject, sensor))
                    {
                        continue;
                    }
                    var objectRoot = intersectingObject.GetRoot() as GameComponent;
                    if (objectRoot is WorkPile)
                    {
                        continue;
                    }
                    if (objectRoot == PreviewBody)
                    {
                        continue;
                    }
                    if (objectRoot.IsDead)
                    {
                        continue;
                    }
                    if (objectRoot != null && objectRoot.GetRotatedBoundingBox().Intersects(previewBox))
                    {
                        World.UserInterface.ShowTooltip("Can't " + Verb + " here: intersects " + objectRoot.Name);
                        return(false);
                    }
                }

                bool intersectsWall = VoxelHelpers.EnumerateCoordinatesInBoundingBox
                                          (PreviewBody.GetRotatedBoundingBox().Expand(-0.1f)).Any(
                    v =>
                {
                    var tvh = new VoxelHandle(World.ChunkManager, v);
                    return(tvh.IsValid && !tvh.IsEmpty);
                });

                var  current    = new VoxelHandle(World.ChunkManager, GlobalVoxelCoordinate.FromVector3(PreviewBody.Position));
                bool underwater = current.IsValid && current.LiquidType != LiquidType.None;

                if (underwater)
                {
                    World.UserInterface.ShowTooltip("Can't " + Verb + " here: underwater or in lava.");
                    return(false);
                }

                if (intersectsWall && CraftType.Placement_PlacementRequirement != ResourceType.PlacementRequirement.NearWall)
                {
                    World.UserInterface.ShowTooltip("Can't " + Verb + " here: intersects wall.");
                    return(false);
                }
            }
            World.UserInterface.ShowTooltip("");
            return(true);
        }
예제 #5
0
        public static bool IsValidPlacement(
            VoxelHandle Location,
            CraftItem CraftType,
            GameMaster Player,
            Body PreviewBody,
            String Verb,
            String PastParticple)
        {
            if (CraftType == null)
            {
                return(false);
            }

            if (!String.IsNullOrEmpty(CraftType.CraftLocation) &&
                Player.Faction.FindNearestItemWithTags(CraftType.CraftLocation, Location.WorldPosition, false, null) == null)
            {
                Player.World.ShowTooltip("Can't " + Verb + ", need " + CraftType.CraftLocation);
                return(false);
            }

            foreach (var req in CraftType.Prerequisites)
            {
                switch (req)
                {
                case CraftItem.CraftPrereq.NearWall:
                {
                    var neighborFound = VoxelHelpers.EnumerateManhattanNeighbors2D(Location.Coordinate)
                                        .Select(c => new VoxelHandle(Player.World.ChunkManager.ChunkData, c))
                                        .Any(v => v.IsValid && !v.IsEmpty);

                    if (!neighborFound)
                    {
                        Player.World.ShowTooltip("Must be " + PastParticple + " next to wall!");
                        return(false);
                    }

                    break;
                }

                case CraftItem.CraftPrereq.OnGround:
                {
                    var below = VoxelHelpers.GetNeighbor(Location, new GlobalVoxelOffset(0, -1, 0));

                    if (!below.IsValid || below.IsEmpty)
                    {
                        Player.World.ShowTooltip("Must be " + PastParticple + " on solid ground!");
                        return(false);
                    }
                    break;
                }
                }
            }

            if (PreviewBody != null)
            {
                // Just check for any intersecting body in octtree.

                var previewBox = PreviewBody.GetRotatedBoundingBox();
                var sensorBox  = previewBox;
                var sensor     = PreviewBody.GetComponent <GenericVoxelListener>();
                if (sensor != null)
                {
                    sensorBox = sensor.GetRotatedBoundingBox();
                }
                if (Debugger.Switches.DrawToolDebugInfo)
                {
                    Drawer3D.DrawBox(sensorBox, Color.Yellow, 0.1f, false);
                }

                foreach (var intersectingObject in Player.World.EnumerateIntersectingObjects(sensorBox, CollisionType.Static))
                {
                    if (Object.ReferenceEquals(intersectingObject, sensor))
                    {
                        continue;
                    }
                    var objectRoot = intersectingObject.GetRoot() as Body;
                    if (objectRoot is WorkPile)
                    {
                        continue;
                    }
                    if (objectRoot != null && objectRoot.GetRotatedBoundingBox().Intersects(previewBox))
                    {
                        Player.World.ShowTooltip("Can't " + Verb + " here: intersects " + objectRoot.Name);
                        return(false);
                    }
                }

                bool intersectsWall = VoxelHelpers.EnumerateCoordinatesInBoundingBox
                                          (PreviewBody.GetRotatedBoundingBox().Expand(-0.1f)).Any(
                    v =>
                {
                    var tvh = new VoxelHandle(Player.World.ChunkManager.ChunkData, v);
                    return(tvh.IsValid && !tvh.IsEmpty);
                });
                var  current    = new VoxelHandle(Player.World.ChunkManager.ChunkData, GlobalVoxelCoordinate.FromVector3(PreviewBody.Position));
                bool underwater = current.IsValid && current.LiquidType != LiquidType.None;
                if (underwater)
                {
                    Player.World.ShowTooltip("Can't " + Verb + " here: underwater or in lava.");
                    return(false);
                }
                if (intersectsWall && !CraftType.Prerequisites.Contains(CraftItem.CraftPrereq.NearWall))
                {
                    Player.World.ShowTooltip("Can't " + Verb + " here: intersects wall.");
                    return(false);
                }
            }
            Player.World.ShowTooltip("");
            return(true);
        }
예제 #6
0
        public void CheckSurroundings(GameComponent Body, DwarfTime gameTime, ChunkManager chunks)
        {
            if (Heat > Flashpoint)
            {
                var insideBodies = World.EnumerateIntersectingObjects(Body.GetBoundingBox());

                foreach (var body in insideBodies.Where(b => b != Parent && b.Active && b.Parent == Manager.RootComponent))
                {
                    var flames = body.GetComponent <Flammable>();
                    if (flames != null)
                    {
                        flames.Heat += 100;
                    }
                }
                SoundManager.PlaySound(ContentPaths.Audio.fire, Body.Position, true);
            }

            float expansion = Heat > Flashpoint ? 1.0f : 0.0f;

            foreach (var coordinate in VoxelHelpers.EnumerateCoordinatesInBoundingBox(Body.BoundingBox.Expand(expansion)))
            {
                var voxel = new VoxelHandle(chunks, coordinate);
                if (!voxel.IsValid)
                {
                    continue;
                }

                if (Heat > Flashpoint && MathFunctions.RandEvent(0.5f))
                {
                    if (voxel.Type.IsFlammable)
                    {
                        if (MathFunctions.RandEvent(0.1f))
                        {
                            var existingItems = World.EnumerateIntersectingObjects(voxel.GetBoundingBox().Expand(-0.1f));


                            if (!existingItems.Any(e => e is Fire))
                            {
                                EntityFactory.CreateEntity <Fire>("Fire", voxel.GetBoundingBox().Center());
                            }
                            SoundManager.PlaySound(ContentPaths.Audio.Oscar.sfx_env_lava_spread, voxel.GetBoundingBox().Center(), true, 1.0f);
                            VoxelHelpers.KillVoxel(World, voxel);
                        }
                    }

                    if (voxel.GrassType != 0x0)
                    {
                        if (MathFunctions.RandEvent(0.1f))
                        {
                            var box = voxel.GetBoundingBox().Expand(-0.1f);
                            box.Min += Vector3.One; // Todo: Why shifting one on every axis?
                            box.Max += Vector3.One;
                            if (!World.EnumerateIntersectingObjects(box).Any(e => e is Fire))
                            {
                                EntityFactory.CreateEntity <Fire>("Fire", box.Center());
                            }
                        }

                        if (MathFunctions.RandEvent(0.5f))
                        {
                            SoundManager.PlaySound(ContentPaths.Audio.Oscar.sfx_env_lava_spread, voxel.GetBoundingBox().Center(), true, 1.0f);
                            voxel.GrassType = 0x0;
                        }
                    }
                }

                if (voxel.LiquidLevel <= 0)
                {
                    continue;
                }
                if (voxel.LiquidType == LiquidType.Lava)
                {
                    Heat += 100.0f;
                }
                else if (voxel.LiquidType == LiquidType.Water)
                {
                    Heat = Heat * 0.25f;
                }
            }
        }
예제 #7
0
 public IEnumerable <GlobalVoxelCoordinate> Select(BoundingBox Bounds, Vector3 Start, Vector3 End, bool Invert)
 {
     return(VoxelHelpers.EnumerateCoordinatesInBoundingBox(Bounds));
 }
예제 #8
0
        public override void Update(DwarfGame game, DwarfTime time)
        {
            if (Player.IsCameraRotationModeActive())
            {
                return;
            }
            Player.VoxSelector.Enabled                   = false;
            Player.VoxSelector.SelectionType             = VoxelSelectionType.SelectEmpty;
            Player.BodySelector.Enabled                  = SelectedBody == null;
            Player.BodySelector.AllowRightClickSelection = true;

            if (Player.World.IsMouseOverGui)
            {
                Player.World.SetMouse(Player.World.MousePointer);
            }
            else
            {
                Player.World.SetMouse(new Gui.MousePointer("mouse", 1, 9));
            }


            if (SelectedBody != null)
            {
                var craftDetails = SelectedBody.GetRoot().GetComponent <CraftDetails>();

                var voxelUnderMouse = Player.VoxSelector.VoxelUnderMouse;
                if (voxelUnderMouse != prevVoxel && voxelUnderMouse.IsValid && voxelUnderMouse.IsEmpty)
                {
                    SoundManager.PlaySound(ContentPaths.Audio.Oscar.sfx_gui_click_voxel, voxelUnderMouse.WorldPosition,
                                           0.1f);

                    var offset = Vector3.Zero;
                    if (craftDetails != null && CraftLibrary.CraftItems.ContainsKey(craftDetails.CraftType))
                    {
                        offset = CraftLibrary.CraftItems[craftDetails.CraftType].SpawnOffset;
                    }

                    SelectedBody.LocalPosition = voxelUnderMouse.WorldPosition + Vector3.One * 0.5f + offset;
                    SelectedBody.HasMoved      = true;
                    SelectedBody.UpdateTransform();
                    if (OverrideOrientation)
                    {
                        SelectedBody.Orient(CurrentOrientation);
                    }
                    else
                    {
                        SelectedBody.OrientToWalls();
                    }
                    SelectedBody.UpdateBoundingBox();
                    SelectedBody.UpdateTransform();
                    SelectedBody.PropogateTransforms();
                    SelectedBody.UpdateBoundingBox();
                }

                var intersectsAnyOther =
                    Player.Faction.OwnedObjects.FirstOrDefault(
                        o => o != SelectedBody && o.Tags.Contains("Moveable") && o.GetRotatedBoundingBox().Intersects(SelectedBody.GetRotatedBoundingBox().Expand(-0.5f)));
                Drawer3D.DrawBox(SelectedBody.GetRotatedBoundingBox(), Color.White, 0.05f, false);

                bool intersectsWall = VoxelHelpers.EnumerateCoordinatesInBoundingBox(
                    SelectedBody.GetRotatedBoundingBox().Expand(-0.25f)).Any(
                    v =>
                {
                    var tvh = new VoxelHandle(Player.VoxSelector.Chunks.ChunkData, v);
                    return(tvh.IsValid && !tvh.IsEmpty);
                });
                var tinter = SelectedBody.GetRoot().GetComponent <Tinter>();
                if (tinter != null)
                {
                    tinter.VertexColorTint = intersectsAnyOther == null && !intersectsWall ? Color.Green : Color.Red;
                }
                MouseState mouse = Mouse.GetState();
                if (mouse.LeftButton == ButtonState.Released && mouseDown)
                {
                    mouseDown = false;
                    if (intersectsAnyOther == null && !intersectsWall)
                    {
                        SoundManager.PlaySound(ContentPaths.Audio.Oscar.sfx_gui_confirm_selection, SelectedBody.Position, 0.5f);
                        SelectedBody.UpdateTransform();
                        SelectedBody.PropogateTransforms();
                        SelectedBody.UpdateBoundingBox();
                        SelectedBody        = null;
                        OverrideOrientation = false;
                        CurrentOrientation  = 0;
                        if (tinter != null)
                        {
                            tinter.VertexColorTint = Color.White;
                        }
                    }
                    else if (!intersectsWall)
                    {
                        Player.World.ShowToolPopup("Can't move here: intersects " + intersectsAnyOther.Name);
                    }
                    else
                    {
                        Player.World.ShowToolPopup("Can't move here: intersects wall.");
                    }
                }
                else if (mouse.LeftButton == ButtonState.Pressed)
                {
                    mouseDown = true;
                }
                prevVoxel = voxelUnderMouse;
            }

            HandleOrientation();
        }
예제 #9
0
        public bool IsValid(CraftDesignation designation)
        {
            if (!designation.Valid)
            {
                return(false);
            }

            if (IsDesignation(designation.Location))
            {
                World.ShowToolPopup("Something is already being built there!");
                return(false);
            }

            if (!String.IsNullOrEmpty(designation.ItemType.CraftLocation) &&
                Faction.FindNearestItemWithTags(designation.ItemType.CraftLocation, designation.Location.WorldPosition, false) ==
                null)
            {
                World.ShowToolPopup("Can't build, need " + designation.ItemType.CraftLocation);
                return(false);
            }

            if (!Faction.HasResources(designation.ItemType.RequiredResources))
            {
                string neededResources = "";

                foreach (Quantitiy <Resource.ResourceTags> amount in designation.ItemType.RequiredResources)
                {
                    neededResources += "" + amount.NumResources + " " + amount.ResourceType.ToString() + " ";
                }

                World.ShowToolPopup("Not enough resources! Need " + neededResources + ".");
                return(false);
            }

            foreach (var req in designation.ItemType.Prerequisites)
            {
                switch (req)
                {
                case CraftItem.CraftPrereq.NearWall:
                {
                    var neighborFound = VoxelHelpers.EnumerateManhattanNeighbors2D(designation.Location.Coordinate)
                                        .Select(c => new VoxelHandle(World.ChunkManager.ChunkData, c))
                                        .Any(v => v.IsValid && !v.IsEmpty);

                    if (!neighborFound)
                    {
                        World.ShowToolPopup("Must be built next to wall!");
                        return(false);
                    }

                    break;
                }

                case CraftItem.CraftPrereq.OnGround:
                {
                    var below = VoxelHelpers.GetNeighbor(designation.Location, new GlobalVoxelOffset(0, -1, 0));

                    if (!below.IsValid || below.IsEmpty)
                    {
                        World.ShowToolPopup("Must be built on solid ground!");
                        return(false);
                    }
                    break;
                }
                }
            }

            if (CurrentCraftBody != null)
            {
                var intersectsAnyOther = Faction.OwnedObjects.FirstOrDefault(
                    o => o != null &&
                    o != CurrentCraftBody &&
                    o.GetRotatedBoundingBox().Intersects(CurrentCraftBody.GetRotatedBoundingBox().Expand(-0.1f)));

                var intersectsBuildObjects = Faction.Designations.EnumerateEntityDesignations(DesignationType.Craft)
                                             .Any(d => d.Body != CurrentCraftBody && d.Body.GetRotatedBoundingBox().Intersects(
                                                      CurrentCraftBody.GetRotatedBoundingBox().Expand(-0.1f)));

                bool intersectsWall = VoxelHelpers.EnumerateCoordinatesInBoundingBox
                                          (CurrentCraftBody.GetRotatedBoundingBox().Expand(-0.1f)).Any(
                    v =>
                {
                    var tvh = new VoxelHandle(World.ChunkManager.ChunkData, v);
                    return(tvh.IsValid && !tvh.IsEmpty);
                });

                if (intersectsAnyOther != null)
                {
                    World.ShowToolPopup("Can't build here: intersects " + intersectsAnyOther.Name);
                }
                else if (intersectsBuildObjects)
                {
                    World.ShowToolPopup("Can't build here: intersects something else being built");
                }
                else if (intersectsWall && !designation.ItemType.Prerequisites.Contains(CraftItem.CraftPrereq.NearWall))
                {
                    World.ShowToolPopup("Can't build here: intersects wall.");
                }

                return(intersectsAnyOther == null && !intersectsBuildObjects &&
                       (!intersectsWall || designation.ItemType.Prerequisites.Contains(CraftItem.CraftPrereq.NearWall)));
            }
            return(true);
        }