예제 #1
0
        void HandleSetRaidDifficulty(SetRaidDifficulty setRaidDifficulty)
        {
            DifficultyRecord difficultyEntry = CliDB.DifficultyStorage.LookupByKey(setRaidDifficulty.DifficultyID);

            if (difficultyEntry == null)
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent an invalid instance mode {1}!",
                             GetPlayer().GetGUID().ToString(), setRaidDifficulty.DifficultyID);
                return;
            }

            if (difficultyEntry.InstanceType != MapTypes.Raid)
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent an non-dungeon instance mode {1}!",
                             GetPlayer().GetGUID().ToString(), difficultyEntry.Id);
                return;
            }

            if (!difficultyEntry.Flags.HasAnyFlag(DifficultyFlags.CanSelect))
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent unselectable instance mode {1}!",
                             GetPlayer().GetGUID().ToString(), difficultyEntry.Id);
                return;
            }

            if (((int)(difficultyEntry.Flags & DifficultyFlags.Legacy) >> 5) != setRaidDifficulty.Legacy)
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent not matching legacy difficulty {1}!",
                             GetPlayer().GetGUID().ToString(), difficultyEntry.Id);
                return;
            }

            Difficulty difficultyID = (Difficulty)difficultyEntry.Id;

            if (difficultyID == (setRaidDifficulty.Legacy != 0 ? GetPlayer().GetLegacyRaidDifficultyID() : GetPlayer().GetRaidDifficultyID()))
            {
                return;
            }

            // cannot reset while in an instance
            Map map = GetPlayer().GetMap();

            if (map && map.IsDungeon())
            {
                Log.outDebug(LogFilter.Network, "WorldSession:HandleSetRaidDifficulty: player (Name: {0}, {1} tried to reset the instance while inside!",
                             GetPlayer().GetName(), GetPlayer().GetGUID().ToString());
                return;
            }

            Group group = GetPlayer().GetGroup();

            if (group)
            {
                if (group.IsLeader(GetPlayer().GetGUID()))
                {
                    for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
                    {
                        Player groupGuy = refe.GetSource();
                        if (!groupGuy)
                        {
                            continue;
                        }

                        if (!groupGuy.IsInMap(groupGuy))
                        {
                            return;
                        }

                        if (groupGuy.GetMap().IsRaid())
                        {
                            Log.outDebug(LogFilter.Network, "WorldSession:HandleSetRaidDifficulty: player {0} tried to reset the instance while inside!", GetPlayer().GetGUID().ToString());
                            return;
                        }
                    }
                    // the difficulty is set even if the instances can't be reset
                    group.ResetInstances(InstanceResetMethod.ChangeDifficulty, true, setRaidDifficulty.Legacy != 0, GetPlayer());
                    if (setRaidDifficulty.Legacy != 0)
                    {
                        group.SetLegacyRaidDifficultyID(difficultyID);
                    }
                    else
                    {
                        group.SetRaidDifficultyID(difficultyID);
                    }
                }
            }
            else
            {
                GetPlayer().ResetInstances(InstanceResetMethod.ChangeDifficulty, true, setRaidDifficulty.Legacy != 0);
                if (setRaidDifficulty.Legacy != 0)
                {
                    GetPlayer().SetLegacyRaidDifficultyID(difficultyID);
                }
                else
                {
                    GetPlayer().SetRaidDifficultyID(difficultyID);
                }

                GetPlayer().SendRaidDifficulty(setRaidDifficulty.Legacy != 0);
            }
        }
예제 #2
0
        void HandleMoveWorldportAck()
        {
            // ignore unexpected far teleports
            if (!GetPlayer().IsBeingTeleportedFar())
            {
                return;
            }

            bool seamlessTeleport = GetPlayer().IsBeingTeleportedSeamlessly();

            GetPlayer().SetSemaphoreTeleportFar(false);

            // get the teleport destination
            WorldLocation loc = GetPlayer().GetTeleportDest();

            // possible errors in the coordinate validity check
            if (!GridDefines.IsValidMapCoord(loc))
            {
                LogoutPlayer(false);
                return;
            }

            // get the destination map entry, not the current one, this will fix homebind and reset greeting
            MapRecord        mapEntry  = CliDB.MapStorage.LookupByKey(loc.GetMapId());
            InstanceTemplate mInstance = Global.ObjectMgr.GetInstanceTemplate(loc.GetMapId());

            // reset instance validity, except if going to an instance inside an instance
            if (!GetPlayer().m_InstanceValid&& mInstance == null)
            {
                GetPlayer().m_InstanceValid = true;
            }

            Map oldMap = GetPlayer().GetMap();
            Map newMap = Global.MapMgr.CreateMap(loc.GetMapId(), GetPlayer());

            if (GetPlayer().IsInWorld)
            {
                Log.outError(LogFilter.Network, "Player (Name {0}) is still in world when teleported from map {1} to new map {2}", GetPlayer().GetName(), oldMap.GetId(), loc.GetMapId());
                oldMap.RemovePlayerFromMap(GetPlayer(), false);
            }

            // relocate the player to the teleport destination
            // the CannotEnter checks are done in TeleporTo but conditions may change
            // while the player is in transit, for example the map may get full
            if (newMap == null || newMap.CannotEnter(GetPlayer()) != 0)
            {
                Log.outError(LogFilter.Network, "Map {0} could not be created for {1} ({2}), porting player to homebind", loc.GetMapId(), newMap ? newMap.GetMapName() : "Unknown", GetPlayer().GetGUID().ToString());
                GetPlayer().TeleportTo(GetPlayer().GetHomebind());
                return;
            }

            float z = loc.GetPositionZ();

            if (GetPlayer().HasUnitMovementFlag(MovementFlag.Hover))
            {
                z += GetPlayer().GetFloatValue(UnitFields.HoverHeight);
            }

            GetPlayer().Relocate(loc.GetPositionX(), loc.GetPositionY(), z, loc.GetOrientation());

            GetPlayer().ResetMap();
            GetPlayer().SetMap(newMap);

            ResumeToken resumeToken = new ResumeToken();

            resumeToken.SequenceIndex = _player.m_movementCounter;
            resumeToken.Reason        = seamlessTeleport ? 2 : 1u;
            SendPacket(resumeToken);

            if (!seamlessTeleport)
            {
                GetPlayer().SendInitialPacketsBeforeAddToMap();
            }

            if (!GetPlayer().GetMap().AddPlayerToMap(GetPlayer(), !seamlessTeleport))
            {
                Log.outError(LogFilter.Network, "WORLD: failed to teleport player {0} ({1}) to map {2} ({3}) because of unknown reason!",
                             GetPlayer().GetName(), GetPlayer().GetGUID().ToString(), loc.GetMapId(), newMap ? newMap.GetMapName() : "Unknown");
                GetPlayer().ResetMap();
                GetPlayer().SetMap(oldMap);
                GetPlayer().TeleportTo(GetPlayer().GetHomebind());
                return;
            }

            // Battleground state prepare (in case join to BG), at relogin/tele player not invited
            // only add to bg group and object, if the player was invited (else he entered through command)
            if (GetPlayer().InBattleground())
            {
                // cleanup setting if outdated
                if (!mapEntry.IsBattlegroundOrArena())
                {
                    // We're not in BG
                    GetPlayer().SetBattlegroundId(0, BattlegroundTypeId.None);
                    // reset destination bg team
                    GetPlayer().SetBGTeam(0);
                }
                // join to bg case
                else
                {
                    Battleground bg = GetPlayer().GetBattleground();
                    if (bg)
                    {
                        if (GetPlayer().IsInvitedForBattlegroundInstance(GetPlayer().GetBattlegroundId()))
                        {
                            bg.AddPlayer(GetPlayer());
                        }
                    }
                }
            }

            if (!seamlessTeleport)
            {
                GetPlayer().SendInitialPacketsAfterAddToMap();
            }
            else
            {
                GetPlayer().UpdateVisibilityForPlayer();
                Garrison garrison = GetPlayer().GetGarrison();
                if (garrison != null)
                {
                    garrison.SendRemoteInfo();
                }
            }

            // flight fast teleport case
            if (GetPlayer().GetMotionMaster().GetCurrentMovementGeneratorType() == MovementGeneratorType.Flight)
            {
                if (!GetPlayer().InBattleground())
                {
                    if (!seamlessTeleport)
                    {
                        // short preparations to continue flight
                        FlightPathMovementGenerator flight = (FlightPathMovementGenerator)GetPlayer().GetMotionMaster().top();
                        flight.Initialize(GetPlayer());
                    }
                    return;
                }

                // Battlegroundstate prepare, stop flight
                GetPlayer().GetMotionMaster().MovementExpired();
                GetPlayer().CleanupAfterTaxiFlight();
            }

            // resurrect character at enter into instance where his corpse exist after add to map
            if (mapEntry.IsDungeon() && !GetPlayer().IsAlive())
            {
                if (GetPlayer().GetCorpseLocation().GetMapId() == mapEntry.Id)
                {
                    GetPlayer().ResurrectPlayer(0.5f, false);
                    GetPlayer().SpawnCorpseBones();
                }
            }

            bool allowMount = !mapEntry.IsDungeon() || mapEntry.IsBattlegroundOrArena();

            if (mInstance != null)
            {
                // check if this instance has a reset time and send it to player if so
                Difficulty          diff    = newMap.GetDifficultyID();
                MapDifficultyRecord mapDiff = Global.DB2Mgr.GetMapDifficultyData(mapEntry.Id, diff);
                if (mapDiff != null)
                {
                    if (mapDiff.GetRaidDuration() != 0)
                    {
                        long timeReset = Global.InstanceSaveMgr.GetResetTimeFor(mapEntry.Id, diff);
                        if (timeReset != 0)
                        {
                            uint timeleft = (uint)(timeReset - Time.UnixTime);
                            GetPlayer().SendInstanceResetWarning(mapEntry.Id, diff, timeleft, true);
                        }
                    }
                }

                // check if instance is valid
                if (!GetPlayer().CheckInstanceValidity(false))
                {
                    GetPlayer().m_InstanceValid = false;
                }

                // instance mounting is handled in InstanceTemplate
                allowMount = mInstance.AllowMount;
            }

            // mount allow check
            if (!allowMount)
            {
                GetPlayer().RemoveAurasByType(AuraType.Mounted);
            }

            // update zone immediately, otherwise leave channel will cause crash in mtmap
            uint newzone, newarea;

            GetPlayer().GetZoneAndAreaId(out newzone, out newarea);
            GetPlayer().UpdateZone(newzone, newarea);

            // honorless target
            if (GetPlayer().pvpInfo.IsHostile)
            {
                GetPlayer().CastSpell(GetPlayer(), 2479, true);
            }

            // in friendly area
            else if (GetPlayer().IsPvP() && !GetPlayer().HasFlag(PlayerFields.Flags, PlayerFlags.InPVP))
            {
                GetPlayer().UpdatePvP(false, false);
            }

            // resummon pet
            GetPlayer().ResummonPetTemporaryUnSummonedIfAny();

            //lets process all delayed operations on successful teleport
            GetPlayer().ProcessDelayedOperations();
        }
예제 #3
0
        void HandleSetDungeonDifficulty(SetDungeonDifficulty setDungeonDifficulty)
        {
            DifficultyRecord difficultyEntry = CliDB.DifficultyStorage.LookupByKey(setDungeonDifficulty.DifficultyID);

            if (difficultyEntry == null)
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent an invalid instance mode {1}!",
                             GetPlayer().GetGUID().ToString(), setDungeonDifficulty.DifficultyID);
                return;
            }

            if (difficultyEntry.InstanceType != MapTypes.Instance)
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent an non-dungeon instance mode {1}!",
                             GetPlayer().GetGUID().ToString(), difficultyEntry.Id);
                return;
            }

            if (!difficultyEntry.Flags.HasAnyFlag(DifficultyFlags.CanSelect))
            {
                Log.outDebug(LogFilter.Network, "WorldSession.HandleSetDungeonDifficulty: {0} sent unselectable instance mode {1}!",
                             GetPlayer().GetGUID().ToString(), difficultyEntry.Id);
                return;
            }

            Difficulty difficultyID = (Difficulty)difficultyEntry.Id;

            if (difficultyID == GetPlayer().GetDungeonDifficultyID())
            {
                return;
            }

            // cannot reset while in an instance
            Map map = GetPlayer().GetMap();

            if (map && map.IsDungeon())
            {
                Log.outDebug(LogFilter.Network, "WorldSession:HandleSetDungeonDifficulty: player (Name: {0}, {1}) tried to reset the instance while player is inside!",
                             GetPlayer().GetName(), GetPlayer().GetGUID().ToString());
                return;
            }

            Group group = GetPlayer().GetGroup();

            if (group)
            {
                if (group.IsLeader(GetPlayer().GetGUID()))
                {
                    for (GroupReference refe = group.GetFirstMember(); refe != null; refe = refe.Next())
                    {
                        Player groupGuy = refe.GetSource();
                        if (!groupGuy)
                        {
                            continue;
                        }

                        if (!groupGuy.IsInMap(groupGuy))
                        {
                            return;
                        }

                        if (groupGuy.GetMap().IsNonRaidDungeon())
                        {
                            Log.outDebug(LogFilter.Network, "WorldSession:HandleSetDungeonDifficulty: {0} tried to reset the instance while group member (Name: {1}, {2}) is inside!",
                                         GetPlayer().GetGUID().ToString(), groupGuy.GetName(), groupGuy.GetGUID().ToString());
                            return;
                        }
                    }
                    // the difficulty is set even if the instances can't be reset
                    //_player.SendDungeonDifficulty(true);
                    group.ResetInstances(InstanceResetMethod.ChangeDifficulty, false, false, GetPlayer());
                    group.SetDungeonDifficultyID(difficultyID);
                }
            }
            else
            {
                GetPlayer().ResetInstances(InstanceResetMethod.ChangeDifficulty, false, false);
                GetPlayer().SetDungeonDifficultyID(difficultyID);
                GetPlayer().SendDungeonDifficulty();
            }
        }
예제 #4
0
        void OnLevelSelected(LevelCore level)
        {
            Selection.Level = level;

            Difficulty.For(level);
        }
예제 #5
0
        public bool IsDisabledFor(DisableType type, uint entry, Unit unit, byte flags = 0)
        {
            Cypher.Assert(type < DisableType.Max);
            if (!m_DisableMap.ContainsKey(type) || m_DisableMap[type].Empty())
            {
                return(false);
            }

            var data = m_DisableMap[type].LookupByKey(entry);

            if (data == null)    // not disabled
            {
                return(false);
            }

            switch (type)
            {
            case DisableType.Spell:
            {
                byte spellFlags = data.flags;
                if (unit != null)
                {
                    if ((spellFlags.HasAnyFlag(DisableFlags.SpellPlayer) && unit.IsTypeId(TypeId.Player)) ||
                        (unit.IsTypeId(TypeId.Unit) && ((unit.IsPet() && spellFlags.HasAnyFlag(DisableFlags.SpellPet)) || spellFlags.HasAnyFlag(DisableFlags.SpellCreature))))
                    {
                        if (spellFlags.HasAnyFlag(DisableFlags.SpellMap))
                        {
                            List <uint> mapIds = data.param0;
                            if (mapIds.Contains(unit.GetMapId()))
                            {
                                return(true);                                               // Spell is disabled on current map
                            }
                            if (!spellFlags.HasAnyFlag(DisableFlags.SpellArea))
                            {
                                return(false);                                              // Spell is disabled on another map, but not this one, return false
                            }
                            // Spell is disabled in an area, but not explicitly our current mapId. Continue processing.
                        }

                        if (spellFlags.HasAnyFlag(DisableFlags.SpellArea))
                        {
                            var areaIds = data.param1;
                            if (areaIds.Contains(unit.GetAreaId()))
                            {
                                return(true);                                               // Spell is disabled in this area
                            }
                            return(false);                                                  // Spell is disabled in another area, but not this one, return false
                        }
                        else
                        {
                            return(true);                                                   // Spell disabled for all maps
                        }
                    }

                    return(false);
                }
                else if (spellFlags.HasAnyFlag(DisableFlags.SpellDeprecatedSpell))            // call not from spellcast
                {
                    return(true);
                }
                else if (flags.HasAnyFlag(DisableFlags.SpellLOS))
                {
                    return(spellFlags.HasAnyFlag(DisableFlags.SpellLOS));
                }

                break;
            }

            case DisableType.Map:
            case DisableType.LFGMap:
                Player player = unit.ToPlayer();
                if (player != null)
                {
                    MapRecord mapEntry = CliDB.MapStorage.LookupByKey(entry);
                    if (mapEntry.IsDungeon())
                    {
                        byte       disabledModes    = data.flags;
                        Difficulty targetDifficulty = player.GetDifficultyID(mapEntry);
                        Global.DB2Mgr.GetDownscaledMapDifficultyData(entry, ref targetDifficulty);
                        switch (targetDifficulty)
                        {
                        case Difficulty.Normal:
                            return(disabledModes.HasAnyFlag(DisableFlags.DungeonStatusNormal));

                        case Difficulty.Heroic:
                            return(disabledModes.HasAnyFlag(DisableFlags.DungeonStatusHeroic));

                        case Difficulty.Raid10HC:
                            return(disabledModes.HasAnyFlag(DisableFlags.DungeonStatusHeroic10Man));

                        case Difficulty.Raid25HC:
                            return(disabledModes.HasAnyFlag(DisableFlags.DungeonStatusHeroic25Man));

                        default:
                            return(false);
                        }
                    }
                    else if (mapEntry.InstanceType == MapTypes.Common)
                    {
                        return(true);
                    }
                }
                return(false);

            case DisableType.Quest:
                if (unit == null)
                {
                    return(true);
                }
                Player player1 = unit.ToPlayer();
                if (player1 != null)
                {
                    if (player1.IsGameMaster())
                    {
                        return(false);
                    }
                }
                return(true);

            case DisableType.Battleground:
            case DisableType.OutdoorPVP:
            case DisableType.Criteria:
            case DisableType.MMAP:
                return(true);

            case DisableType.VMAP:
                return(flags.HasAnyFlag(data.flags));
            }

            return(false);
        }
예제 #6
0
        void HandleCalendarGetCalendar(CalendarGetCalendar calendarGetCalendar)
        {
            ObjectGuid guid = GetPlayer().GetGUID();

            long currTime = Time.UnixTime;

            CalendarSendCalendar packet = new CalendarSendCalendar();

            packet.ServerTime = currTime;

            var invites = Global.CalendarMgr.GetPlayerInvites(guid);

            foreach (var invite in invites)
            {
                CalendarSendCalendarInviteInfo inviteInfo = new CalendarSendCalendarInviteInfo();
                inviteInfo.EventID     = invite.EventId;
                inviteInfo.InviteID    = invite.InviteId;
                inviteInfo.InviterGuid = invite.SenderGuid;
                inviteInfo.Status      = invite.Status;
                inviteInfo.Moderator   = invite.Rank;
                CalendarEvent calendarEvent = Global.CalendarMgr.GetEvent(invite.EventId);
                if (calendarEvent != null)
                {
                    inviteInfo.InviteType = (byte)(calendarEvent.IsGuildEvent() && calendarEvent.GuildId == _player.GetGuildId() ? 1 : 0);
                }

                packet.Invites.Add(inviteInfo);
            }

            var playerEvents = Global.CalendarMgr.GetPlayerEvents(guid);

            foreach (var calendarEvent in playerEvents)
            {
                CalendarSendCalendarEventInfo eventInfo;
                eventInfo.EventID     = calendarEvent.EventId;
                eventInfo.Date        = calendarEvent.Date;
                eventInfo.EventClubID = calendarEvent.GuildId;
                eventInfo.EventName   = calendarEvent.Title;
                eventInfo.EventType   = calendarEvent.EventType;
                eventInfo.Flags       = calendarEvent.Flags;
                eventInfo.OwnerGuid   = calendarEvent.OwnerGuid;
                eventInfo.TextureID   = calendarEvent.TextureId;

                packet.Events.Add(eventInfo);
            }

            for (Difficulty i = 0; i < Difficulty.Max; ++i)
            {
                var boundInstances = _player.GetBoundInstances(i);
                if (boundInstances != null)
                {
                    foreach (var boundInstance in boundInstances.Values)
                    {
                        if (boundInstance.perm)
                        {
                            CalendarSendCalendarRaidLockoutInfo lockoutInfo;

                            InstanceSave save = boundInstance.save;
                            lockoutInfo.MapID        = (int)save.GetMapId();
                            lockoutInfo.DifficultyID = (uint)save.GetDifficultyID();
                            lockoutInfo.ExpireTime   = save.GetResetTime() - currTime;
                            lockoutInfo.InstanceID   = save.GetInstanceId(); // instance save id as unique instance copy id

                            packet.RaidLockouts.Add(lockoutInfo);
                        }
                    }
                }
            }

            SendPacket(packet);
        }
예제 #7
0
        public static void SetupTitleScreen()
        {
            Referee.OutofControl = false;
            Level = 0;
            Referee.Stop();
            Engine.SetLocation(new Location(new Description2D(0, 0, ScreenWidth, ScreenHeight)));
            Description2D logoDescription = new Description2D(Sprite.Sprites["gmtklogo"], ScreenWidth / 2, ScreenHeight / 2);
            Entity        logo            = new Entity(logoDescription);
            int           timer           = TPS * 2;

            logo.TickAction = (loc, ent) =>
            {
                bool isPress = Program.Mouse[(int)Actions.ACTION].IsPress();

                if (logoDescription.ImageIndex < Sprite.Sprites["gmtklogo"].HImages - 1 && timer == TPS * 2)
                {
                    if (isPress)
                    {
                        logoDescription.ImageIndex = Sprite.Sprites["gmtklogo"].HImages - 1;
                    }
                    else
                    {
                        logoDescription.ImageIndex++;
                    }
                }
                else
                {
                    if (timer-- == 0 || timer > 0 && isPress)
                    {
                        timer = -1;
                        logoDescription.ImageIndex = 0;

                        Engine.AddEntity(Text.Create("RuleScramble", new Font("", 24, FontStyle.Italic | FontStyle.Bold | FontStyle.Underline), ScreenWidth / 2, 16));
                        Engine.AddEntity(Button.Create("Story Mode", () =>
                        {
                            Levels[StartingLevel - 1].SetupLevel();

                            if (Program.Diff == Difficulty.NORMAL && Level == 7)
                            {
                                Lives = 3;
                            }
                            else if (Program.Diff == Difficulty.EASY && Level == 7)
                            {
                                Lives = 4;
                            }
                            else
                            {
                                Lives = 1;
                            }
                        }, ScreenWidth / 2 - 128 / 2, ScreenHeight / 2 - 48));
                        Engine.AddEntity(Button.Create("Arcade Mode", SetupCrazyMode, ScreenWidth / 2 - 128 / 2, ScreenHeight / 2 + 8));
                        Engine.AddEntity(Button.Create("Credits", SetupCredits, ScreenWidth / 2 - 128 / 2, ScreenHeight / 2 + 64));


                        Engine.AddEntity(Text.Create("Story:", new Font("Arial", 10, FontStyle.Regular), ScreenWidth / 2 + 112, ScreenHeight / 2 - 40));
                        Button easyButton   = null;
                        Button normalButton = null;
                        Button hardButton   = null;

                        Entity button = Button.Create("easy", () =>
                        {
                            Program.Diff            = Difficulty.EASY;
                            easyButton.IsSelected   = true;
                            normalButton.IsSelected = false;
                            hardButton.IsSelected   = false;
                        }, ScreenWidth / 2 + 80, ScreenHeight / 2 - 16, 64, 32);
                        Engine.AddEntity(button);
                        easyButton = button.Description as Button;
                        if (Program.Diff == Difficulty.EASY)
                        {
                            easyButton.IsSelected = true;
                        }

                        button = Button.Create("normal", () =>
                        {
                            Program.Diff            = Difficulty.NORMAL;
                            easyButton.IsSelected   = false;
                            normalButton.IsSelected = true;
                            hardButton.IsSelected   = false;
                        }, ScreenWidth / 2 + 80, ScreenHeight / 2 + 16, 64, 32);
                        Engine.AddEntity(button);
                        normalButton = button.Description as Button;
                        if (Program.Diff == Difficulty.NORMAL)
                        {
                            normalButton.IsSelected = true;
                        }

                        button = Button.Create("hard", () =>
                        {
                            Program.Diff            = Difficulty.HARD;
                            easyButton.IsSelected   = false;
                            normalButton.IsSelected = false;
                            hardButton.IsSelected   = true;
                        }, ScreenWidth / 2 + 80, ScreenHeight / 2 + 48, 64, 32);
                        Engine.AddEntity(button);
                        hardButton = button.Description as Button;
                        if (Program.Diff == Difficulty.HARD)
                        {
                            hardButton.IsSelected = true;
                        }

                        Engine.AddEntity(Text.Create("Controls:\nWASD+Mouse\n[Radial\nmove toward\nmouse]\nR: Reset\nEsc: Title", new Font("Arial", 10, FontStyle.Regular), ScreenWidth / 8 + 8, ScreenHeight / 2 - 48));
                    }
                }
            };

            Engine.AddEntity(logo);
        }