using System.Collections.Generic;
using System.IO;
using UnityEditor;
using UnityEngine;
using WS;

///<summary>语音预制件创建</summary>
public class VoiceEditor : EditorWindow
{
    [MenuItem("Tools/Framework/自动生成语音预制件")]
    public static void ShowVoice()
    {
        VoiceEditor window = EditorWindow.GetWindow<VoiceEditor>("生成语音预制件");
        window.Show();
    }

    ///<summary>加载路径</summary>
    private string loadpath = "Assets/GameResources/Audio/";
    ///<summary>保存路径</summary>
    private string savepath = "Assets/Resources/Audio/";
    ///<summary>识别不同的后缀名</summary>
    private string[] suffix = new string[] { "*.mp3", "*.wav", "*.ogg" };
    ///<summary>配置文件</summary>
    private List<ResourcePath> Config = new List<ResourcePath>();
    ///<summary>滑杆</summary>
    private Vector2 pos;
    ///<summary>路径</summary>
    private string path;

    private void OnEnable()
    {
        path = $"{Application.dataPath}/Resources/Config/Framework/VoiceConfig.txt";
        if (ConfigHelper.ConfigExists(path))
        {
            Config = ConfigHelper.FileLoadConfig<List<ResourcePath>>(path);
        }
    }

    private void OnGUI()
    {
        EditorGUILayout.BeginHorizontal();
        GUILayout.Label("");
        GUILayout.Label("只支持 mp3、wav、ogg 格式，如有其它格式请在 VoiceEditor 脚本的 suffix 参数增加", GUILayout.Width(500));
        GUILayout.Label("");
        EditorGUILayout.EndHorizontal();

        EditorGUILayout.BeginHorizontal();
        GUILayout.Label("读取路径:", GUILayout.Width(65));
        loadpath = EditorGUILayout.TextField(loadpath);
        EditorGUILayout.EndHorizontal();

        EditorGUILayout.BeginHorizontal();
        GUILayout.Label($"保存路径:", GUILayout.Width(65));
        EditorGUILayout.TextField(savepath);
        EditorGUILayout.EndHorizontal();

        EditorGUILayout.BeginHorizontal();
        GUILayout.Label("");
        if (GUILayout.Button("生成预制件", GUILayout.Width(100)))
        {
            //所有的语音文件
            List<string> allfilepath = new List<string>();
            for (int i = 0; i < suffix.Length; i++)
            {
                string[] temp = Directory.GetFiles(loadpath, suffix[i], SearchOption.AllDirectories);
                allfilepath.AddRange(temp);
            }

            //已经处理为预制件的语音
            List<string> allprefabpath = new List<string>();
            string[] temp_1 = Directory.GetFiles(savepath, "*.prefab", SearchOption.AllDirectories);
            allprefabpath.AddRange(temp_1);

            ToSetString(allfilepath);
            ToSetString(allprefabpath);

            //文件名称
            List<string> filenames = new List<string>();
            for (int i = 0; i < allfilepath.Count; i++)
            {
                FileInfo fi = new FileInfo(allfilepath[i]);
                filenames.Add(fi.Name.Replace(fi.Extension, ""));
            }

            //删除 语音已经被删除 的语音预制件
            for (int i = allprefabpath.Count - 1; i >= 0; i--)
            {
                FileInfo fi = new FileInfo(allprefabpath[i]);
                string prefabname = fi.Name.Replace(fi.Extension, "");
                if (!IsExists(filenames, prefabname))
                {
                    AssetDatabase.DeleteAsset(allprefabpath[i]);
                    allprefabpath.Remove(allprefabpath[i]);
                    AssetDatabase.SaveAssets();
                    AssetDatabase.Refresh();
                    int index = Config.FindIndex(v => v.Name == prefabname);
                    Config.RemoveAt(index);
                }
                else
                    allprefabpath[i] = fi.Name.Replace(fi.Extension, "");
            }

            //删除都没有的
            for (int i = Config.Count - 1; i >= 0; i--)
            {
                if (!IsExists(filenames, Config[i].Name))
                {
                    Config.Remove(Config[i]);
                }
            }

            //创建预制件
            for (int i = 0; i < allfilepath.Count; i++)
            {
                FileInfo fi = new FileInfo(allfilepath[i]);
                var filename = fi.Name.Replace(fi.Extension, "");
                if (Config.Exists(v => v.Name == filename))//已存在
                    continue;
                AudioClip clip = AssetDatabase.LoadAssetAtPath<AudioClip>(allfilepath[i]);
                if (null != clip)
                {
                    if (IsExists(allprefabpath, filename))//已经创建预制件，跳过该步骤
                        continue;
                    GameObject go = new GameObject();
                    go.name = filename;
                    AudioSource source = go.AddComponent<AudioSource>();
                    source.playOnAwake = false;
                    source.clip = clip;
                    string filepath = allfilepath[i].Replace(loadpath, "").Replace(fi.Name, "");
                    if (string.IsNullOrEmpty(filepath))
                        filepath = savepath;
                    else
                        filepath = $"{savepath}/{filepath}";
                    if (!Directory.Exists(filepath))
                        Directory.CreateDirectory(filepath);
                    filepath = $"{filepath}/{filename}.prefab";
                    GameObject savego = PrefabUtility.SaveAsPrefabAsset(go, filepath);
                    GameObject.DestroyImmediate(go);
                    EditorUtility.SetDirty(savego);
                    Resources.UnloadAsset(clip);
                    AssetDatabase.SaveAssets();
                    AssetDatabase.Refresh();
                    ResourcePath data = new ResourcePath();
                    data.Name = filename;
                    data.Path = filepath.Replace("Assets/Resources/", "").Replace(".prefab", "").Replace("//", "/");
                    Config.Add(data);
                }
            }
            ConfigHelper.SaveConfig(Config, path);
            DeleteEmptyFolders(savepath);
            AssetDatabase.SaveAssets();
            AssetDatabase.Refresh();
        }
        GUILayout.Label("");
        EditorGUILayout.EndHorizontal();
        GUILayout.Label("");

        pos = EditorGUILayout.BeginScrollView(pos);
        for (int i = 0; i < Config.Count; i++)
        {
            EditorGUILayout.BeginHorizontal();
            GUILayout.Label("Voice 名称", GUILayout.Width(70));
            GUILayout.Label(Config[i].Name, GUILayout.Width(200));
            GUILayout.Label("Voice 路径", GUILayout.Width(70));
            GUILayout.Label(Config[i].Path);
            EditorGUILayout.EndHorizontal();
        }
        EditorGUILayout.EndScrollView();
    }

    ///<summary>集合中是否存在</summary>
    private bool IsExists(List<string> list, string str)
    {
        return list.Exists(s => s == str);
    }

    ///<summary>删除空文件夹</summary>
    private void DeleteEmptyFolders(string path)
    {
        var dir = new DirectoryInfo(path);
        var subdirs = dir.GetDirectories("*.*", SearchOption.AllDirectories);

        foreach (var subdir in subdirs)
        {
            if (!Directory.Exists(subdir.FullName)) continue;

            var subFiles = subdir.GetFileSystemInfos("*.*", SearchOption.AllDirectories);

            var findFile = false;
            foreach (var sub in subFiles)
            {
                findFile = (sub.Attributes & FileAttributes.Directory) == 0;

                if (findFile) break;
            }
            if (!findFile) subdir.Delete(true);
        }
    }

    ///<summary>转意符</summary>
    private void ToSetString(List<string> list)
    {
        for (int i = 0; i < list.Count; i++)
        {
            list[i] = list[i].Replace(@"\", "/");
        }
    }
}