using System.Collections;
using System.Collections.Generic;
using UnityEngine;
using cfg;
using System.Threading.Tasks;
using Base.Common;
using System.IO;

public class EnemyCreater : MonoBehaviour
{
    public static EnemyCreater instance;
    public List<SingleCreateEnemyConfig> cfgCreateEnemy;
    public List<bool> created;
    public Dictionary<int, List<Enemy>> enemyDic;

    private void Awake()
    {
        if (!instance)
        {
            instance = this;
        }
        else
        {
            DestroyImmediate(gameObject);
            return;
        }
        enemyDic = new Dictionary<int, List<Enemy>>();
    }

    private void Start()
    {
        cfgCreateEnemy = GameManager.instance.allCfgData.CfgCreateEnemy.DataList;
        created = new List<bool>();
        for (int i = 0; i < cfgCreateEnemy.Count; i++)
        {
            created.Add(false);
        }
    }

    public void OnGameTimeChange(float gameTime)
    {
        for (int i = 0; i < cfgCreateEnemy.Count; i++)
        {
            if (cfgCreateEnemy[i].Time <= gameTime && !created[i])
            {
                created[i] = true;
                StartCreateEnemy(i);
            }
        }
    }

    public async void StartCreateEnemy(int id)
    {
        SingleCreateEnemyConfig singleCreateEnemy = cfgCreateEnemy[id];
        for (int i = 0; i < singleCreateEnemy.Count; i++)
        {
            if (!instance)
            {
                return;
            }
            Vector3 pos = new Vector3(singleCreateEnemy.Position[0], singleCreateEnemy.Position[1] + Random.Range(-singleCreateEnemy.YRandomRange/2, singleCreateEnemy.YRandomRange / 2), singleCreateEnemy.Position[2]);
            CreateEnemy(singleCreateEnemy.EnemyID, pos, singleCreateEnemy.HPRatio, singleCreateEnemy.AttackRatio);
            await Task.Delay((int)(singleCreateEnemy.TimeInterval * 1000));
        }
    }

    public void CreateEnemy(int enemyId, Vector3 pos, float hpRatio, float attackRatio)
    {
        SingleEnemyConfig cfgEnemy = GameManager.instance.allCfgData.CfgEnemy.Get(enemyId);
        GameObject enemyObj = Util.Instantiate(cfgEnemy.EnemyPrefab, pos);
        Enemy enemy = enemyObj.GetComponent<Enemy>();
        enemy.id = enemyId;
        if (!enemyDic.ContainsKey(enemyId))
        {
            enemyDic.Add(enemyId, new List<Enemy>());
        }
        enemyDic[enemyId].Add(enemy);
        enemy.totalHp = (int)(cfgEnemy.HP * hpRatio);
        for (int i = 0; i < cfgEnemy.Attack1.Count; i++)
        {
            AttackInfo attackInfo = enemy.attack1Infos[i];
            attackInfo.damage = (int)(cfgEnemy.Attack1[i] * attackRatio);
            enemy.attack1Infos[i] = attackInfo;
        }
        for (int i = 0; i < cfgEnemy.Attack1.Count; i++)
        {
            AttackInfo attackInfo = enemy.attack2Infos[i];
            attackInfo.damage = (int)(cfgEnemy.Attack2[i] * attackRatio);
            enemy.attack2Infos[i] = attackInfo;
        }
        if (enemy.canFly)
        {
            enemy.flyHeight = enemy.transform.position.y;
        }
        enemy.Init();
        GameObject prefab = Resources.Load<GameObject>(cfgEnemy.EnemyPrefab);
        int sortingOrder = prefab.GetComponent<Enemy>().sortingOrder;
        enemy.SetSortingOrder(sortingOrder + enemyDic[enemyId].Count);
    }

    public void OnEnemyRecycle(Enemy enemy)
    {
        if (!enemyDic.ContainsKey(enemy.id))
        {
            return;
        }
        enemyDic[enemy.id].Remove(enemy);
        SingleEnemyConfig cfgEnemy = GameManager.instance.allCfgData.CfgEnemy.Get(enemy.id);
        for (int i = 0; i < enemyDic[enemy.id].Count; i++)
        {
            enemyDic[enemy.id][i].SetSortingOrder(enemy.id * 1000 + i);
        }
    }

    public Enemy GetMinDisOtherEnemy(Enemy self)
    {
        Enemy minDisEnemy = null;
        foreach (var item in enemyDic)
        {
            for (int i = 0; i < item.Value.Count; i++)
            {
                if (item.Value[i] != self && !item.Value[i].isDie && item.Value[i].gameObject.activeInHierarchy)
                {
                    if (!minDisEnemy || (minDisEnemy.transform.position - self.transform.position).magnitude 
                        > (item.Value[i].transform.position - self.transform.position).magnitude)
                    {
                        minDisEnemy = item.Value[i];
                    }
                }
            }
        }
        return minDisEnemy;
    }
}
