示例#1
0
        public void VoteForTeam(Player player, bool approve)
        {
            if (Votes.Select(v=>v.Player).ToList().Contains(player))
                throw new Exception("Player has already voted..");

            Votes.Add(new Vote { Player = player, Approve = approve });
        }
示例#2
0
        public void SubmitQuest(Player player, bool success)
        {
            if (Quests.Select(v => v.Player).ToList().Contains(player))
                throw new Exception("Player has already submitted their quest card..");

            Quests.Add(new Quest { Player = player, Success = success });
        }
        public TeamModel(Player player, Core.VoteTrack team, int totalPlayers, int teamNumber)
        {
            if (team.Leader != null)
            {
                Leader = team.Leader.Name;
                TeamSummary = string.Format("Team {0}, as proposed by {1}", teamNumber.ToWords(), Leader);
            }
            if (team.Excalibur != null)
            {
                ExcaliburUsedBy = team.Excalibur.Holder.Name;
                ExcaliburUsedOn = team.Excalibur.UsedOn != null ? team.Excalibur.UsedOn.Player.Name : "No One";
                if (player == team.Excalibur.Holder)
                {
                    ExcaliburResult = team.Excalibur.OriginalMissionWasSuccess.HasValue ? (team.Excalibur.OriginalMissionWasSuccess.Value ? "questsuccess" : "questfail") : "";
                }
                else
                {
                    ExcaliburResult = "quest";
                }
            }
            TeamMembers = team.Players.Select(p => new TeamMemberModel { Player = p.Name, HasExcalibur = team.Excalibur != null && p.Name == ExcaliburUsedBy }).ToList();
            Vote = team.Votes.OrderBy(v=>v.Player.Name).Select(v => new VoteModel(v, team.Votes.Count != totalPlayers)).ToList();

            var hidden = team.QuestCards.Count != TeamMembers.Count;
            if (team.Excalibur != null && team.Excalibur.UsedOn == null && !team.Excalibur.Skipped)
                hidden = true;
            QuestCards = team.QuestCards.OrderBy(q=> q.Success).Select(q => new QuestCardModel(q.Success, hidden)).ToList();

            Messages = team.Messages.Select(m => new MessageModel(m.Player.Name, m.Message)).ToList();
        }
示例#4
0
 public Team(Player leader)
 {
     Leader = leader;
     TeamMembers = new List<Player>();
     Votes = new List<Vote>();
     Quests = new List<Quest>();
 }
 public VoteTrack(Player leader, int size, int requiredFails)
 {
     Leader = leader;
     QuestSize = size;
     RequiredFails = requiredFails;
     Players = new List<Player>();
     Votes = new List<VoteToken>();
     QuestCards = new List<QuestCard>();
     Messages = new List<PlayerMessage>();
 }
示例#6
0
        public void AddToTeam(Player player, Player proposedPlayer)
        {
            if (TeamMembers.Contains(proposedPlayer))
                throw new Exception("Player is already on team..");

            if (player != Leader)
                throw new Exception("Hax. Player is not the leader of this team");

            TeamMembers.Add(proposedPlayer);
        }
示例#7
0
        public Quest(Player ladyOfTheLakeHolder, int teamSize, int requiredFails)
        {
            QuestSize = teamSize;
            RequiredFails = requiredFails;

            if (ladyOfTheLakeHolder != null)
            {
                LadyOfTheLake = new LadyOfTheLakeUse { Holder = ladyOfTheLakeHolder };
            }

            VoteTracks = new List<VoteTrack>();
        }
 public LadyOfTheLakeUseModel(LadyOfTheLakeUse use, Player player)
 {
     UsedBy = use.Holder.Name;
     UsedOn = use.Target == null ? string.Empty : use.Target.Name;
     if (player == use.Holder)
     {
         Result = use.IsEvil ? "evil" : "good";
     }
     else
     {
         Result = "allegiance";
     }
 }
 public ExcaliburUseModel(ExcaliburUse use, Player player)
 {
     UsedBy = use.Holder.Name;
     UsedOn = use.UsedOn != null ? use.UsedOn.Player.Name : "No One";
     if (player == use.Holder)
     {
         Result = use.OriginalMissionWasSuccess.HasValue ? (use.OriginalMissionWasSuccess.Value ? "evil" : "good") : "";
     }
     else
     {
         Result = "allegiance";
     }
 }
示例#10
0
        void UseExcalibur(Player player, Player proposedPlayer)
        {
            if (proposedPlayer!=null)
            {
                CurrentVoteTrack.Excalibur.UsedOn = CurrentVoteTrack.QuestCards.First(p => p.Player == proposedPlayer);
                CurrentVoteTrack.Excalibur.OriginalMissionWasSuccess = CurrentVoteTrack.Excalibur.UsedOn.Success;
                CurrentVoteTrack.Excalibur.UsedOn.Success = !CurrentVoteTrack.Excalibur.UsedOn.Success;
            }
            else
            {
                CurrentVoteTrack.Excalibur.Skipped = true;
            }

            QuestFinished();
        }
示例#11
0
        void UseLadyOfTheLake(Player target)
        {
            CurrentQuest.LadyOfTheLake.Target = target;
            CurrentQuest.LadyOfTheLake.IsEvil = IsCharacterEvil(target.Character, CurrentLancelotAllegianceSwitched);
            CurrentHolderOfLadyOfTheLake = target;

            QuestFinished();
        }
示例#12
0
 private void RemoveFromTeam(Player target)
 {
     CurrentVoteTrack.Players.Remove(target);
 }
示例#13
0
        void SubmitQuest(Player player, bool success)
        {
            CurrentVoteTrack.QuestCards.Add(new QuestCard { Player = player, Success = success });

            if (CurrentVoteTrack.QuestCards.Count == CurrentVoteTrack.QuestSize)
            {
                if (CurrentVoteTrack.Excalibur != null)
                {
                    GameState = State.UsingExcalibur;
                }
                else
                {
                    QuestFinished();
                }
            }
        }
示例#14
0
 public void SubmitQuest(Player player, bool success)
 {
     CurrentTeam.SubmitQuest(player, success);
 }
示例#15
0
        void NextQuest(Player leader)
        {
            if (RoundTables.Count == 0)
                return;

            var roundTable = RoundTables[Quests.Count];
            var quest = new Quest(CurrentHolderOfLadyOfTheLake, roundTable.TeamSize, roundTable.RequiredFails);
            var team = new VoteTrack(leader, roundTable.TeamSize, roundTable.RequiredFails);
            quest.VoteTracks.Add(team);
            Quests.Add(quest);
            GameState = State.ChoosingTeam;
        }
 public static ComputerPlayer Factory(Player.Type type, Guid playerGuid)
 {
     switch (type)
     {
         case Player.Type.TrustBot:
         default:
             return new TrustBot(playerGuid);
     }
 }
示例#17
0
        private double ProbabilityOfEvil(Player player)
        {
            var knowledge = _game.PlayerKnowledge(_player, player);
            if (knowledge == Knowledge.Evil || (knowledge == Knowledge.EvilLancelot && !_game.CurrentLancelotAllegianceSwitched) || (knowledge == Knowledge.Lancelot && _game.CurrentLancelotAllegianceSwitched))
            {
                return 100;
            }

            if (knowledge == Knowledge.Good || (knowledge == Knowledge.EvilLancelot && _game.CurrentLancelotAllegianceSwitched) || (knowledge == Knowledge.Lancelot && !_game.CurrentLancelotAllegianceSwitched))
            {
                return 0;
            }

            double evilProbability = 0;

            var evilCharactersInGame = _game.CharacterCards.Count(c => _game.IsCharacterEvil(c, false));
            if (_IAmEvil)
            {
                evilCharactersInGame--;
            }

            evilProbability = (double)evilCharactersInGame / (double)(_game.Players.Count - 1);

            int correctVotes = 0, votesCounted = 0;

            //nothing confirmed, look at quest behaviour
            foreach (var round in _game.Quests)
            {
                var onTeam = round.VoteTracks.Last().Players.Contains(player);
                if (onTeam)
                {
                    var fails = round.VoteTracks.Last().QuestCards.Count(q => !q.Success);
                    var size = round.VoteTracks.Last().Players.Count();

                    if (round.VoteTracks.Last().Players.Contains(_player))
                    {
                        if (_IAmEvil) { fails = fails - 1; }
                        size = size - 1;
                    }

                    int roundEvilProbability = (int)(((double)fails / (double)size) * 100.0);
                    if (roundEvilProbability > evilProbability)
                    {
                        evilProbability = roundEvilProbability;
                    }
                }

                if(round.VoteTracks.Count() < 5) { //ignore last round as everyone votes accept
                    if (round.CurrentVoteTrack.Votes.Count == _game.Players.Count)
                    {
                        var vote = round.VoteTracks.Last().Votes.FirstOrDefault(v => v.Player == player);
                        if (vote.Approve == round.IsSuccess.Value)
                            correctVotes++;
                        votesCounted++;
                    }
                }
            }

            //if they vote correctly each round they're probably merlin.
            //todo handle off by a couple
            //also check known evils instead of just outcome
            if (correctVotes == votesCounted && votesCounted > 1)
            {
                evilProbability = 0;
            }

            return evilProbability;
        }
示例#18
0
        void AddToTeam(Player proposedPlayer)
        {
            CurrentVoteTrack.Players.Add(proposedPlayer);

            if (CurrentVoteTrack.Players.Count == CurrentVoteTrack.QuestSize)
            {
                if (Rules != null && Rules.Contains(Rule.ExcaliburExists))
                {
                    GameState = State.AssigningExcalibur;
                }
                else
                {
                    GameState = State.VotingForTeam;
                }
            }
        }
示例#19
0
        void VoteForTeam(Player player, bool approve)
        {
            CurrentVoteTrack.Votes.Add(new VoteToken { Approve = approve, Player = player });

            if (CurrentVoteTrack.Votes.Count < Players.Count)
                return;

            //on the last vote, if it fails, create the next quest
            var rejects = CurrentVoteTrack.Votes.Count(v => !v.Approve);
            if (rejects >= Math.Ceiling(Players.Count / 2.0))
            {
                if (CurrentQuest.VoteTracks.Count == 5)
                {
                    GameState = State.EternalChaos;
                    Winners = Players.Where(p => IsCharacterEvil(p.Character, CurrentLancelotAllegianceSwitched)).ToList();
                }
                else
                {
                    CurrentQuest.VoteTracks.Add(new VoteTrack(Players.Next(CurrentVoteTrack.Leader), CurrentQuest.QuestSize, CurrentQuest.RequiredFails));
                    GameState = State.ChoosingTeam;
                }
            }
            else
            {
                GameState = State.Questing;
            }
        }
示例#20
0
        public Knowledge PlayerKnowledge(Player myself, Player someoneelse)
        {
            if (myself == null)
                return Knowledge.Player;

            //lancelots can know each other
            if (Rules.Contains(Rule.LancelotsKnowEachOther))
            {
                if ((myself.Character == Character.Lancelot || myself.Character == Character.EvilLancelot) && (someoneelse.Character == Character.Lancelot))
                {
                    return Knowledge.Lancelot;
                }
                if ((myself.Character == Character.Lancelot || myself.Character == Character.EvilLancelot) && (someoneelse.Character == Character.EvilLancelot))
                {
                    return Knowledge.EvilLancelot;
                }
            }

            //minions know each other (except oberon)
            if (myself.Character == Character.Assassin || myself.Character == Character.Morgana || myself.Character == Character.MinionOfMordred || myself.Character == Character.Mordred)
            {
                if (someoneelse.Character == Character.Assassin || someoneelse.Character == Character.Morgana || someoneelse.Character == Character.MinionOfMordred || someoneelse.Character == Character.Mordred || someoneelse.Character == Character.EvilLancelot)
                {
                    return Knowledge.Evil;
                }
            }

            //merlin knows minions (except mordred)
            if (myself.Character == Character.Merlin)
            {
                if (someoneelse.Character == Character.Assassin || someoneelse.Character == Character.Morgana || someoneelse.Character == Character.MinionOfMordred || someoneelse.Character == Character.Oberon || someoneelse.Character == Character.EvilLancelot)
                {
                    return Knowledge.Evil;
                }
            }

            //percy knows merlin and morgana
            if (myself.Character == Character.Percival)
            {
                if (someoneelse.Character == Character.Merlin || someoneelse.Character == Character.Morgana)
                {
                    return Knowledge.Magical;
                }
            }

            return Knowledge.Player;
        }
示例#21
0
        public List<AvailableAction> AvailableActions(Player player)
        {
            var actions = new List<AvailableAction>();
            switch (GameState)
            {
                case State.Lobby:
                    if (player == null && Players.Count < 10)
                    {
                        actions.Add(AvailableAction.FreeText(Action.Type.Join));
                    }
                    else
                    {
                        if (player == Players.First())
                        {
                            actions.Add(AvailableAction.FreeText(Action.Type.SetGameName));
                            actions.Add(AvailableAction.FreeText(Action.Type.AddBot));
                            actions.Add(AvailableAction.Items(Action.Type.AddCharacterCard, Enum.GetNames(typeof(Character)).ToList()));

                            if (CharacterCards.Count > 0)
                            {
                                actions.Add(AvailableAction.Items(Action.Type.RemoveCharacterCard, CharacterCards.Select(t => t.ToString()).ToList()));
                            }

                            var otherRules = Enum.GetValues(typeof(Rule)).Cast<Rule>().ToList().Except(Rules).Select(r=>r.ToString()).ToList();
                            if (otherRules.Count>0)
                            {
                                actions.Add(AvailableAction.Items(Action.Type.AddRule, otherRules));
                            }
                            if (Rules.Count > 0)
                            {
                                actions.Add(AvailableAction.Items(Action.Type.RemoveRule, Rules.Select(r=>r.ToString()).ToList()));
                            }

                            if (IsValid())
                            {
                                actions.Add(AvailableAction.FreeText(Action.Type.Start));
                            }
                        }
                    }

                    return actions;
                case State.ChoosingTeam:
                    if (CurrentVoteTrack != null && player == CurrentVoteTrack.Leader)
                    {
                        actions.Add(AvailableAction.Items(Action.Type.AddToTeam, Players.Except(CurrentVoteTrack.Players).Select(p=>p.Name).ToList()));
                    }
                    if (CurrentVoteTrack != null && player == CurrentVoteTrack.Leader && CurrentVoteTrack.Players.Any())
                    {
                        actions.Add(AvailableAction.Items(Action.Type.RemoveFromTeam, CurrentVoteTrack.Players.Select(p => p.Name).ToList()));
                    }
                    break;
                case State.AssigningExcalibur:
                    if (player == CurrentVoteTrack.Leader)
                    {
                        actions.Add(AvailableAction.Items(Action.Type.AssignExcalibur, CurrentVoteTrack.Players.Where(p=>p!=CurrentVoteTrack.Leader).Select(p => p.Name).ToList()));
                    }
                    break;
                case State.VotingForTeam:
                    if (player!=null && !CurrentVoteTrack.Votes.Any(v => v.Player == player))
                    {
                        actions.Add(AvailableAction.Action(Action.Type.VoteApprove));
                        actions.Add(AvailableAction.Action(Action.Type.VoteReject));
                    }
                    break;
                case State.Questing:
                    if (CurrentVoteTrack.Players.Contains(player) && !CurrentVoteTrack.QuestCards.Any(q => q.Player == player))
                    {
                        //good must always vote success
                        if (Rules.Contains(Rule.GoodMustAlwaysSucceedQuests) && !IsCharacterEvil(player.Character, CurrentLancelotAllegianceSwitched))
                        {
                            actions.Add(AvailableAction.Action(Action.Type.SucceedQuest));
                        }
                        else
                        {
                            //lancelot fanatasism
                            if (Rules.Contains(Rule.LancelotsMustVoteFanatically) && (player.Character == Character.Lancelot || player.Character == Character.EvilLancelot))
                            {
                                if (IsCharacterEvil(player.Character, CurrentLancelotAllegianceSwitched))
                                {
                                    actions.Add(AvailableAction.Action(Action.Type.FailQuest));
                                }
                                else
                                {
                                    actions.Add(AvailableAction.Action(Action.Type.SucceedQuest));
                                }
                            }
                            else
                            {
                                actions.Add(AvailableAction.Action(Action.Type.SucceedQuest));
                                actions.Add(AvailableAction.Action(Action.Type.FailQuest));
                            }
                        }
                    }
                    break;
                case State.UsingExcalibur:
                    if (CurrentVoteTrack.Excalibur.Holder == player)
                    {
                        actions.Add(AvailableAction.Items(Action.Type.UseExcalibur, CurrentVoteTrack.Players.Where(p => p != player).Select(p => p.Name).ToList()));
                        actions.Last().ActionItems.Insert(0, "");
                    }
                    break;
                case State.LadyOfTheLake:
                    if (Rules.Contains(Rule.LadyOfTheLakeExists) && CurrentQuest.LadyOfTheLake != null && CurrentQuest.LadyOfTheLake.Holder == player && CurrentQuest.LadyOfTheLake.Target == null)
                    {
                        var list = Players.Except(Players.Where(p => Quests.Any(r => r.LadyOfTheLake != null && r.LadyOfTheLake.Holder == p))).Select(p => p.Name).ToList();
                        actions.Add(AvailableAction.Items(Action.Type.UseTheLadyOfTheLake, list));
                    }
                    break;
                case Game.State.GuessingMerlin:
                    if (player != null && player.Character == Character.Assassin)
                    {
                        actions.Add(AvailableAction.Items(Action.Type.GuessMerlin, Players.Where(p => p != player).Select(p => p.Name).ToList()));
                    }
                    break;
            }
            if (player != null)
            {
                actions.Add(AvailableAction.FreeText(Action.Type.Message));
            }
            return actions;
        }
示例#22
0
 private bool IKnowTheyAreEvil(Player player, Game game)
 {
     var knowledge = game.PlayerKnowledge(_player, player);
     if (knowledge == Knowledge.Evil || (knowledge == Knowledge.EvilLancelot && !game.CurrentLancelotAllegianceSwitched) || (knowledge == Knowledge.Lancelot && game.CurrentLancelotAllegianceSwitched))
     {
         return true;
     }
     return false;
 }
示例#23
0
 public void AddToTeam(Player player, Player proposedPlayer)
 {
     CurrentTeam.AddToTeam(player, proposedPlayer);
 }
示例#24
0
        public void VoteForTeam(Player player, bool approve)
        {
            CurrentTeam.VoteForTeam(player, approve);

            //on the last vote, if it fails, create the next quest
            if (CurrentTeam.Votes.Count == TotalPlayers)
            {
                var rejects = CurrentTeam.Votes.Where(v => !v.Approve).Count();
                if (rejects >= Math.Ceiling(TotalPlayers / 2.0))
                {
                    _currentPlayer = NextPlayer;
                    Teams.Add(new Team(_players[_currentPlayer]));
                }
            }
        }
        public List<Action> DoSomething(Game game)
        {
            var actions = new List<Action>();
            _game = game;
            _player = _game.Players.First(p => p.Guid == PlayerGuid);
            _IAmEvil = _game.IsCharacterEvil(_player.Character, false);

            var availableActions = _game.AvailableActions(_player);
            if (availableActions.Count == 0)
                return null;

            if (availableActions.Any(a=>a.ActionType==ResistanceOnline.Core.Action.Type.VoteApprove))
            {
                actions.Add(new Action(PlayerGuid, TeamVote() ? Action.Type.VoteApprove : Action.Type.VoteReject));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.AssignExcalibur))
            {
                actions.Add( new Action(PlayerGuid, Action.Type.AssignExcalibur, AssignExcalibur().Name));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.UseExcalibur))
            {
                var target = UseExcalibur();
                var name = target==null? string.Empty : target.Name;
                actions.Add( new Action(PlayerGuid, Action.Type.UseExcalibur, name));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.FailQuest) || availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.SucceedQuest))
            {
                actions.Add( new Action(PlayerGuid, Quest() ? Action.Type.SucceedQuest : Action.Type.FailQuest));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.AddToTeam))
            {
                actions.Add( new Action(PlayerGuid, Action.Type.AddToTeam, ChooseTeamPlayer().Name));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.GuessMerlin))
            {
                actions.Add( new Action(PlayerGuid, Action.Type.GuessMerlin, GuessMerlin().Name));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.UseTheLadyOfTheLake))
            {
                actions.Add( new Action(PlayerGuid, Action.Type.UseTheLadyOfTheLake, LadyOfTheLakeTarget().Name));
            }

            if (availableActions.Any(a => a.ActionType == ResistanceOnline.Core.Action.Type.Message) && _thingsIWantToSay.Count > 0)
            {
                actions.AddRange(_thingsIWantToSay.Select(s => new Action(PlayerGuid, Action.Type.Message, s)).ToList());
            }

            return actions;
        }
示例#26
0
        void GuessMerlin(Player guess)
        {
            AssassinsGuessAtMerlin = guess;

            if (guess.Character == Character.Merlin)
            {
                GameState = State.EvilTriumphs;
                Winners = Players.Where(p => IsCharacterEvil(p.Character, CurrentLancelotAllegianceSwitched)).ToList();
            }
            else
            {
                Winners = Players.Where(p => !IsCharacterEvil(p.Character, CurrentLancelotAllegianceSwitched)).ToList();
                GameState = State.GoodPrevails;
            }
        }
示例#27
0
 private bool IsProbablyEvil(Player player)
 {
     var trust = ProbabilityOfEvil(player);
     return (new Random().Next(100) < trust);
 }
示例#28
0
        void JoinGame(string playerName, Guid playerGuid, Player.Type playerType = Player.Type.Human)
        {
            if (Players.Select(p => p.Guid).Contains(playerGuid))
                throw new InvalidOperationException("It's really not fair if you play as more than one player and you want the game to be fair don't you?");

            if (String.IsNullOrWhiteSpace(playerName))
                playerName = String.Empty;

            playerName = playerName.Uniquify(Players.Select(p => p.Name));

            Players.Add(new Player() { Name = playerName, Guid = playerGuid, PlayerType = playerType });

            RoundTables = StandardQuestSizes(Players.Count);
        }
示例#29
0
        void AssignExcalibur(Player proposedPlayer)
        {
            CurrentVoteTrack.Excalibur = new ExcaliburUse { Holder = proposedPlayer };

            GameState = State.VotingForTeam;
        }
示例#30
0
 void Message(Player player, string message)
 {
     CurrentQuest.CurrentVoteTrack.Messages.Add(new PlayerMessage { Player = player, Message = message });
 }