using UnityEngine;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System;

namespace GGJ16
{

    public class PlayerService : MonoBehaviour, IPlayerService
    {
        public static int FollowersPerPriests = 4;
        public static int FollowersPerAssassins = 1;
        public static int FollowersPerPreachers = 5;
        public static int MoreFollowers = 5;



        public List<PlayerData> players;
        Dictionary<int, bool> stillAlive;

        //Instance of PlayerService
        public static PlayerService instance;

        public PlayerService()
        {
            
        }
        void Awake()
        {
            if (instance != null)
            {
                Debug.LogError("Singleton violation");
                return;
            }

            instance = this;
        }

        // Use this for initialization
        void Start()
        {
            stillAlive = new Dictionary<int, bool>() { { 1, true }, { 2, true }, { 3, true }, };
            players = new List<PlayerData>();
            players.Add(new PlayerData(1));
            players.Add(new PlayerData(2));
            players.Add(new PlayerData(3));
        }

        // Update is called once per frame
        void Update()
        {

        }

        public void SpecialAttack(int rivalID, int followersKilled)
        {
            //attack another temple
            //rival gets x followers killed
            //can only be used after 5 turns.
            //    after 10 turns it doubles the carnage
        }

        public void Sacrifice(int playerID)
        {
            int priests = players.Where(p => p.GetPlayerID() == playerID).First().GetPriests();
            int preachers = players.Where(p => p.GetPlayerID() == playerID).First().GetPreacherList().Count;
            int level = players.Where(p => p.GetPlayerID() == playerID).First().GetAdvantage();

            if (preachers >= level + 2 && priests >= level + 2)
            {
                players.Where(p => p.GetPlayerID() == playerID).First().KillPreachers(level + 2);
                players.Where(p => p.GetPlayerID() == playerID).First().KillPriests(level + 2);
                players.Where(p => p.GetPlayerID() == playerID).First().levelUp();
            }
            else
            {
                throw new InsufficientFundsException();
            }
        }

        public void SendAssassin(int rivalID, int CurrentPlayerID, int maximumKills)
        {
            int killed = UnityEngine.Random.Range(0, maximumKills);
            int advantage = players.Where(p => p.GetPlayerID() == rivalID).First().GetAdvantage();
            int numberOfFollowers = players.Where(p => p.GetPlayerID() == rivalID).First().GetFollowers();
            int numberOfPriests = players.Where(p => p.GetPlayerID() == rivalID).First().GetPriests();
            int numberOfPreachers = players.Where(p => p.GetPlayerID() == rivalID).First().GetPreacherList().Count;
            int priestsKilled = 0;
            int preachersKilled = 0;
            int FollowersKilled = 0;
            maximumKills = numberOfFollowers + numberOfPreachers + numberOfPriests;
            killed = System.Math.Min(killed, maximumKills);
            if (numberOfFollowers < FollowersPerAssassins)
            {
                throw new InsufficientFundsException();
            }
            for (int i = 0; i < killed; i++)
            {
                int whoDied = UnityEngine.Random.Range(advantage, maximumKills);
                if (whoDied < numberOfFollowers)
                {
                    FollowersKilled++;
                }
                else if ((numberOfPriests > 0) && (whoDied < numberOfFollowers + numberOfPriests))
                {
                    priestsKilled++;
                }
                else if (numberOfPriests > 0)
                {
                    preachersKilled++;
                }
            }
            players.Where(p => p.GetPlayerID() == rivalID).First().KillFollowers(FollowersKilled);
            players.Where(p => p.GetPlayerID() == rivalID).First().KillPriests(priestsKilled);
            players.Where(p => p.GetPlayerID() == rivalID).First().KillPreachers(preachersKilled);

            players.Where(p => p.GetPlayerID() == CurrentPlayerID).First().KillFollowers(FollowersPerAssassins);
        }

        public void RecruitPriest(int recruiterID)
        {
            if (players.Where(p => p.GetPlayerID() == recruiterID).First().GetFollowers() < FollowersPerPriests)
            {
                throw new InsufficientFundsException();
            }
            players.Where(p => p.GetPlayerID() == recruiterID).First().KillFollowers(FollowersPerPriests);
            players.Where(p => p.GetPlayerID() == recruiterID).First().AddPriest();
        }

        public void SendPreacher(int currentPlayerID, int rivalID)
        {
            if (players.Where(p => p.GetPlayerID() == currentPlayerID).First().GetFollowers() < FollowersPerPriests)
            {
                throw new InsufficientFundsException();
            }
            players.Where(p => p.GetPlayerID() == currentPlayerID).First().KillFollowers(FollowersPerPreachers);
            players.Where(p => p.GetPlayerID() == currentPlayerID).First().AddPreacher(rivalID);
        }

        public void GetMoreFollowers(int playerID)
        {
            int advantage = players.Where(p => p.GetPlayerID() == playerID).First().GetAdvantage();
            players.Where(p => p.GetPlayerID() == playerID).First().AddFollowers(MoreFollowers * (advantage + 1));
        }

        public void StartTurn(int playerID)
        {
            players.Where(p => p.GetPlayerID() == playerID).First().AddFollowers();
            int newFollowers = 0;
            int priestNumber = players.Where(p => p.GetPlayerID() == playerID).First().GetPriests();
            List<int> preachers = players.Where(p => p.GetPlayerID() == playerID).First().GetPreacherList();
            int advantage = players.Where(p => p.GetPlayerID() == playerID).First().GetAdvantage();
            newFollowers += (priestNumber * (advantage + 1));

            foreach (int preacher in preachers)
            {
                newFollowers += (advantage + 1);
                players.Where(p => p.GetPlayerID() == preacher).First().KillFollowers(advantage + 1);
            }
            players.Where(p => p.GetPlayerID() == playerID).First().AddFollowers(newFollowers);
        }

        public bool IsLoser(int playerID)
        {
            bool isAlive = players.Where(p => p.GetPlayerID() == playerID).First().IsAlive();
            if(!isAlive)
            {
                stillAlive[playerID] = false;
            }
            return isAlive;
        }

        public bool IsStillAlive(int playerID)
        {
            return stillAlive[playerID];
        }
    }
}