Пример #1
0
        public void Restore(GameBackupModel backup)
        {
            if (GameStatus != GameStatusType.Created)
            {
                throw new Exception("Нельзя восстановить игру, так как она уже была запущена.");
            }

            StoredEvents.AddRange(backup.StoredEvents);
            GameStatus = backup.GameStatus;
            LaunchTime = backup.LaunchTime;
            EndTime    = backup.EndTime;

            foreach (var td in backup.TeamProgress)
            {
                LocalTeam team = Teams.Single(x => x.Id == td.Key);
                team.Progress = new TeamGameProgress(
                    Config.Grid[Teams.IndexOf(team)],
                    td.Value.LastHintTime,
                    td.Value.LastTaskCompleteTime,
                    td.Value.CurrentTaskIndex
                    );
            }

            NewEvents.Add(new GameRestored(DateTime.Now));
            SendBroadcastMessage("Игра была восстановлена после перезапуска");
        }
Пример #2
0
        public override void Run(GameManager gm)
        {
            LocalTeam team = gm.Teams.First(x => x.Id == TeamId);

            team.Progress = new TeamGameProgress(gm.Config.Grid[gm.Teams.IndexOf(team)], AddDate);
            team.SendMessage(gm.Noticer, $"Ваше первое задание: {team.Progress.GetCurrentTask().Task}");
        }
Пример #3
0
        public override void Run(GameManager gm)
        {
            LocalTeam team = gm.Teams.First(x => x.Id == TeamId);

            team.Progress.LastHintTime = AddDate;
            GameTask task = team.Progress.GetCurrentTask();

            team.SendMessage(gm.Noticer, $"Слив адреса: {task.Hint2} ({task.Address})");
        }
Пример #4
0
        public override void Run(GameManager gm)
        {
            LocalTeam team = gm.Teams.First(x => x.Id == TeamId);

            team.Progress.CompleteTask(AddDate, TaskIndex);

            if (team.Progress.IsAllTaskCompleted())
            {
                team.SendMessage(gm.Noticer, $"Задание слито!\r\nВсе задания выполнены, возвращайтесь на место сбора.");
            }
            else
            {
                team.SendMessage(gm.Noticer, $"Задание слито!\r\nВаше следующее задание:\r\n{team.Progress.GetCurrentTask().Task}");
            }
        }
Пример #5
0
        /// <summary>
        /// Обрабатывает один фрейм игры, на текущий момент времени.
        /// </summary>
        public void Iterate()
        {
            if (GameStatus != GameStatusType.InProgress && GameStatus != GameStatusType.Stopped)
            {
                return;
            }
            lock (_locker)
            {
                // Запоминаем время начала итерации
                DateTime curTime = DateTime.Now;

                int eventsCount = NewEvents.Count;

                // STEP 1: Обрабатываем все ивенты (если они есть)
                if (eventsCount > 0)
                {
                    // Получаем список ивентов, обрабатываемый на текущей итерации
                    List <GameEvent> processedEvents = NewEvents.GetRange(0, eventsCount).OrderBy(x => x.AddDate).ToList();
                    NewEvents.RemoveRange(0, eventsCount);

                    // Выполняем каждый ивент
                    foreach (GameEvent currentEvent in processedEvents)
                    {
                        currentEvent.Run(this);
                    }

                    // Добавляем все обработанные ивенты в список
                    StoredEvents.AddRange(processedEvents);
                }

                // STEP 2: Добавляем новые ивенты, если прошло необходимое время (подсказка, слив адреса, слив задания)
                if (GameStatus != GameStatusType.Stopped)
                {
                    foreach (LocalTeam t in Teams)
                    {
                        // Получение первого задания, если прошло достаточно времени и команда еще не начала играть.
                        if (t.Progress == null)
                        {
                            if (curTime > ((DateTime)LaunchTime).AddSeconds(Setting.SecondsDelayStart * Teams.IndexOf(t)))
                            {
                                NewEvents.Add(new TeamStartsPlay(curTime, t.Id));
                            }
                            continue;
                        }

                        if (t.Progress.IsAllTaskCompleted())
                        {
                            continue;
                        }

                        // Кол-во секунд, прошедшее со сдачи последнего задания
                        double lastCompleteTaskSec = curTime.Subtract(t.Progress.LastTaskCompleteTime).TotalSeconds;
                        // Кол-во секунд, прошедшее с получения последней подсказки
                        double lastHintSec = curTime.Subtract(t.Progress.LastHintTime).TotalSeconds;

                        // ... сливаем задание
                        if (lastCompleteTaskSec > (Setting.TaskDropDelaySec + Setting.Hint2DelaySec + Setting.Hint1DelaySec))
                        {
                            NewEvents.Add(new TeamDropTask(curTime, t.Id, t.Progress.CurrentTaskIndex));
                        }
                        // ... сливаем адрес
                        else if (lastCompleteTaskSec > (Setting.Hint2DelaySec + Setting.Hint1DelaySec) && lastHintSec > Setting.Hint2DelaySec)
                        {
                            NewEvents.Add(new TeamGetAddress(curTime, t.Id, t.Progress.CurrentTaskIndex));
                        }
                        // ... сливаем подсказку
                        else if (lastCompleteTaskSec > (Setting.Hint1DelaySec) && lastHintSec > Setting.Hint1DelaySec)
                        {
                            NewEvents.Add(new TeamGetHint(curTime, t.Id, t.Progress.CurrentTaskIndex));
                        }
                    }
                }

                // STEP 3: Анализируем пришедшие сообщения от пользователей и добавляем новые ивенты
                List <Message> inputMessages = Noticer.PullInput();
                foreach (Message m in inputMessages)
                {
                    LocalTeam playerTeam = Teams.First(x => x.Id == m.Player.TeamId);

                    if (playerTeam.Progress == null)
                    {
                        m.Player.SendMessage(Noticer, $"Ваша команда еще не получила первое задание.");
                        continue;
                    }

                    if (playerTeam.Progress.GetCurrentTask() == null)
                    {
                        m.Player.SendMessage(Noticer, $"Ваша команда уже выполнила все задания.");
                        continue;
                    }

                    switch (m.Text)
                    {
                    case "задание": m.Player.SendMessage(Noticer, $"Какая-то подсказка."); continue;
                    }

                    if (playerTeam.Progress.GetCurrentTask().Code == m.Text)
                    {
                        NewEvents.Add(new PlayerCompletedTask(curTime, playerTeam.Id, m.Player.Id, playerTeam.Progress.CurrentTaskIndex));
                    }
                    else
                    {
                        NewEvents.Add(new PlayerFailedTask(curTime, playerTeam.Id, m.Player.Id, playerTeam.Progress.CurrentTaskIndex));
                    }
                }

                // STEP 4: Завершение игры
                // Переводим игру в статус "останавливается", если пришло время конца игры.
                if (GameStatus == GameStatusType.InProgress &&
                    curTime.Subtract((DateTime)LaunchTime).TotalMinutes > Setting.GameDurationMin)
                {
                    NewEvents.Add(new GameStopped(DateTime.Now));
                }

                // Если после остановки игры прошло необходимое кол-во минут - завершаем игру.
                if (GameStatus == GameStatusType.Stopped &&
                    EndTime != null && curTime > EndTime?.AddMinutes(Setting.GameClosingDurationMin))
                {
                    GameStatus = GameStatusType.Ended;
                    SendBroadcastMessage("Приём кодов завершён.");
                }
            }
        }