#if UNITY_EDITOR
using System;
using System.Linq;
using UnityEditor;
using UnityEditor.Presets;
using UnityEngine;

namespace AllIn1VfxToolkit
{
    [CustomEditor(typeof(AllIn1ParticleHelperComponent)), CanEditMultipleObjects]
    public class AllIn1ParticleHelperEditor : Editor
    {
        private GUIStyle smallRedBoldLabel, smallBoldLabel, headerBoldLabel, propertiesStyle;

        private AllIn1VfxComponent all1Vfx;
        private ParticleSystem ps;
        private ParticleSystem.MainModule mainModule;
        private Color targetColor = Color.white;
        private int gradientColorKeyIndex = 0;
        private int helperNum;
        private SerializedProperty startColorProperty;
        private float timeSinceLastFetch = -1f;
        private float TIME_BETWEEN_FETCHES = 4f;

        private void OnEnable()
        {
            startColorProperty = serializedObject.FindProperty("startColor");
            LoadParticleHelpersAndPresets();
        }

        public override void OnInspectorGUI()
        {
            InitializeStyles();

            if(Selection.activeGameObject != null) ps = Selection.activeGameObject.GetComponent<ParticleSystem>();
            if(ps == null)
            {
                GUILayout.Label("Please add a Particle System to this Game Object", smallRedBoldLabel);
                EditorGUILayout.Space();
                if(GUILayout.Button("Add New Particle System")) Selection.activeGameObject.AddComponent<ParticleSystem>();
                return;
            }

            if(Selection.activeGameObject != null) all1Vfx = Selection.activeGameObject.GetComponent<AllIn1VfxComponent>();
            if(all1Vfx == null)
            {
                if(GUILayout.Button("Add All In 1 Vfx Component"))
                {
                    AllIn1VfxComponent t = Selection.activeGameObject.AddComponent<AllIn1VfxComponent>();
                    UnityEditorInternal.ComponentUtility.MoveComponentUp(t);
                }

                DrawLine(Color.grey, 1, 3);
            }

            mainModule = ps.main;

            helperNum = 1;
            EditorGUILayout.LabelField("Generic Helpers", headerBoldLabel, GUILayout.Height(20));
            HierarchyHelpers();
            ColorChangeUI();
            EditorGUILayout.Space();
            if(GUILayout.Button("Custom Data Auto Setup"))
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).CustomDataAutoSetup();
            EditorGUILayout.Space();

            DrawLine(Color.grey, 1, 3);
            EditorGUILayout.LabelField("Particle System Options and Presets", headerBoldLabel, GUILayout.Height(20));
            
            EditorGUI.BeginChangeCheck();
            GeneralOptions();
            EmissionOptions();
            ShapeOptions();
            OverLifetimeOptions();
            ParticleHelperPresets();
            ParticleSystemPresets();

            EditorGUILayout.Space();

            if(GUILayout.Button("Fetch Particle System Current Values"))
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).FetchAllCurrentValues();

            bool applyEverythingOnChange = ((AllIn1ParticleHelperComponent)target).applyEverythingOnChange;

            if(!applyEverythingOnChange)
            {
                if(GUILayout.Button("Apply All Options Settings"))
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).ApplyCurrentSettings();
            }

            bool toggle = ((AllIn1ParticleHelperComponent)target).applyEverythingOnChange;
            EditorGUIUtility.labelWidth = 190;
            toggle = EditorGUILayout.Toggle("Auto Apply On Change Property", toggle);
            EditorGUIUtility.labelWidth = 145;
            if(toggle != ((AllIn1ParticleHelperComponent)target).applyEverythingOnChange)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).applyEverythingOnChange = toggle;

            EditorGUILayout.Space();
            DrawLine(Color.grey, 1, 3);
            EditorGUILayout.Space();
            if(GUILayout.Button("Remove Component"))
                for(int i = targets.Length - 1; i >= 0; i--)
                    DestroyImmediate(targets[i] as AllIn1ParticleHelperComponent);

            if(EditorGUI.EndChangeCheck() && applyEverythingOnChange)
            {
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).ApplyCurrentSettings();
            }
        }
        
        private void InitializeStyles()
        {
            if(smallRedBoldLabel == null)
            {
                smallRedBoldLabel = new GUIStyle(EditorStyles.boldLabel) { normal = { textColor = new Color(0.86f, 0.31f, 0.3f) } };
                smallBoldLabel = new GUIStyle(EditorStyles.boldLabel);
                headerBoldLabel = new GUIStyle(EditorStyles.boldLabel) { fontSize = 13, alignment = TextAnchor.MiddleCenter };
                propertiesStyle = new GUIStyle(EditorStyles.helpBox) { margin = new RectOffset(0, 0, 0, 0) };
            }
        }

        private void HierarchyHelpers()
        {
            bool toggle = ((AllIn1ParticleHelperComponent)target).hierarchyHelpers;
            toggle = EditorGUILayout.BeginToggleGroup("Hierarchy Helpers", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).hierarchyHelpers)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).hierarchyHelpers = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);
                if(GUILayout.Button("Add Child Copy"))
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).CopyCurrentGameObject(false);
                if(GUILayout.Button("Add Sibling Copy"))
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).CopyCurrentGameObject(true);
                int nCopies = ((AllIn1ParticleHelperComponent)target).numberOfCopies;
                EditorGUI.BeginChangeCheck();
                nCopies = EditorGUILayout.IntField("New Copy Number", nCopies);
                if(EditorGUI.EndChangeCheck())
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).numberOfCopies = nCopies;
                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
        }

        private void ColorChangeUI()
        {
            bool toggle = ((AllIn1ParticleHelperComponent)target).colorChangeOption;
            toggle = EditorGUILayout.BeginToggleGroup("Palette Color Change", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).colorChangeOption)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).colorChangeOption = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);
                targetColor = EditorGUILayout.ColorField("New Color", targetColor);
                if(mainModule.startColor.mode == ParticleSystemGradientMode.Color ||
                   mainModule.startColor.mode == ParticleSystemGradientMode.TwoColors)
                {
                    if(GUILayout.Button("Recolor Particle System"))
                        for(int i = 0; i < targets.Length; i++)
                            ((AllIn1ParticleHelperComponent)targets[i]).HueShiftParticleSystem(targetColor);
                }
                else if(mainModule.startColor.mode == ParticleSystemGradientMode.Gradient ||
                        mainModule.startColor.mode == ParticleSystemGradientMode.RandomColor ||
                        mainModule.startColor.mode == ParticleSystemGradientMode.TwoGradients)
                {
                    EditorGUILayout.IntField("Gradient Reference Index", gradientColorKeyIndex, GUILayout.ExpandWidth(true));
                    if(GUILayout.Button("Recolor Particle System"))
                        for(int i = 0; i < targets.Length; i++)
                            ((AllIn1ParticleHelperComponent)targets[i]).HueShiftParticleSystem(targetColor, gradientColorKeyIndex);
                }

                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
        }

        private void GeneralOptions()
        {
            bool toggle = ((AllIn1ParticleHelperComponent)target).generalOptions;
            toggle = EditorGUILayout.BeginToggleGroup(helperNum + ".General Options", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).generalOptions)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).generalOptions = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);

                toggle = ((AllIn1ParticleHelperComponent)target).matchDurationToLifetime;
                EditorGUIUtility.labelWidth = 170;
                toggle = EditorGUILayout.Toggle("Match Duration To Lifetime?", toggle);
                EditorGUIUtility.labelWidth = 145;
                if(toggle != ((AllIn1ParticleHelperComponent)target).matchDurationToLifetime)
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).matchDurationToLifetime = toggle;

                toggle = ((AllIn1ParticleHelperComponent)target).randomRotation;
                toggle = EditorGUILayout.Toggle("Random Rotation?", toggle);
                if(toggle != ((AllIn1ParticleHelperComponent)target).randomRotation)
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).randomRotation = toggle;

                float minLifetime = ((AllIn1ParticleHelperComponent)target).minLifetime;
                float maxLifetime = ((AllIn1ParticleHelperComponent)target).maxLifetime;
                EditorGUI.BeginChangeCheck();
                EditorGUILayout.MinMaxSlider("Particle Lifetime", ref minLifetime, ref maxLifetime, 0, 30);
                minLifetime = EditorGUILayout.FloatField("Min Lifetime", minLifetime);
                maxLifetime = EditorGUILayout.FloatField("Max Lifetime", maxLifetime);
                if(EditorGUI.EndChangeCheck())
                {
                    minLifetime = Mathf.Clamp(minLifetime, 0, 1000);
                    maxLifetime = Mathf.Clamp(maxLifetime, 0, 1000);
                    if(minLifetime > maxLifetime) maxLifetime = minLifetime;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).minLifetime = minLifetime;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).maxLifetime = maxLifetime;
                }

                float minSpeed = ((AllIn1ParticleHelperComponent)target).minSpeed;
                float maxSpeed = ((AllIn1ParticleHelperComponent)target).maxSpeed;
                EditorGUI.BeginChangeCheck();
                EditorGUILayout.MinMaxSlider("Particle Speed", ref minSpeed, ref maxSpeed, 0, 30);
                minSpeed = EditorGUILayout.FloatField("Min Speed", minSpeed);
                maxSpeed = EditorGUILayout.FloatField("Max Speed", maxSpeed);
                if(EditorGUI.EndChangeCheck())
                {
                    minSpeed = Mathf.Clamp(minSpeed, 0, 1000);
                    maxSpeed = Mathf.Clamp(maxSpeed, 0, 1000);
                    if(minSpeed > maxSpeed) maxSpeed = minSpeed;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).minSpeed = minSpeed;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).maxSpeed = maxSpeed;
                }

                float minSize = ((AllIn1ParticleHelperComponent)target).minSize;
                float maxSize = ((AllIn1ParticleHelperComponent)target).maxSize;
                EditorGUI.BeginChangeCheck();
                EditorGUILayout.MinMaxSlider("Particle Size", ref minSize, ref maxSize, 0, 30);
                minSize = EditorGUILayout.FloatField("Min Size", minSize);
                maxSize = EditorGUILayout.FloatField("Max Size", maxSize);
                if(EditorGUI.EndChangeCheck())
                {
                    minSize = Mathf.Clamp(minSize, 0, 1000);
                    maxSize = Mathf.Clamp(maxSize, 0, 1000);
                    if(minSize > maxSize) maxSize = minSize;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).minSize = minSize;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).maxSize = maxSize;
                }

                EditorGUILayout.PropertyField(startColorProperty, new GUIContent("Start Color"));
                serializedObject.ApplyModifiedProperties();

                if(GUILayout.Button("Fetch Particle System General Values"))
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).FetchGeneralValues();

                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
            helperNum++;
        }

        private void EmissionOptions()
        {
            bool toggle = ((AllIn1ParticleHelperComponent)target).emissionOptions;
            toggle = EditorGUILayout.BeginToggleGroup(helperNum + ".Emission Options", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).emissionOptions)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).emissionOptions = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);

                toggle = ((AllIn1ParticleHelperComponent)target).isBurst;
                toggle = EditorGUILayout.Toggle("Use burst?", toggle);
                if(toggle != ((AllIn1ParticleHelperComponent)target).isBurst)
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).isBurst = toggle;

                float minNumberOfParticles = ((AllIn1ParticleHelperComponent)target).minNumberOfParticles;
                float maxNumberOfParticles = ((AllIn1ParticleHelperComponent)target).maxNumberOfParticles;
                EditorGUI.BeginChangeCheck();
                EditorGUILayout.MinMaxSlider("Number of Particles", ref minNumberOfParticles, ref maxNumberOfParticles, 0, 100);
                minNumberOfParticles = EditorGUILayout.IntField("Min Particles", Mathf.RoundToInt(minNumberOfParticles));
                maxNumberOfParticles = EditorGUILayout.IntField("Max Particles", Mathf.RoundToInt(maxNumberOfParticles));
                if(EditorGUI.EndChangeCheck())
                {
                    minNumberOfParticles = Mathf.Clamp(minNumberOfParticles, 0, 1000);
                    maxNumberOfParticles = Mathf.Clamp(maxNumberOfParticles, 0, 1000);
                    if(minNumberOfParticles > maxNumberOfParticles) maxNumberOfParticles = minNumberOfParticles;
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).minNumberOfParticles = Mathf.RoundToInt(minNumberOfParticles);
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).maxNumberOfParticles = Mathf.RoundToInt(maxNumberOfParticles);
                }

                if(GUILayout.Button("Fetch Particle System Emission Values"))
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).FetchEmissionValues();

                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
            helperNum++;
        }

        private void ShapeOptions()
        {
            bool toggle = ((AllIn1ParticleHelperComponent)target).shapeOptions;
            toggle = EditorGUILayout.BeginToggleGroup(helperNum + ".Shape Options", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).shapeOptions)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).shapeOptions = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);

                AllIn1ParticleHelperComponent.EmissionShapes tempSettings = ((AllIn1ParticleHelperComponent)target).currEmissionShape;
                EditorGUI.BeginChangeCheck();
                tempSettings = (AllIn1ParticleHelperComponent.EmissionShapes)EditorGUILayout.EnumPopup("New Shape", tempSettings);
                if(EditorGUI.EndChangeCheck())
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).currEmissionShape = tempSettings;

                if(GUILayout.Button("Fetch Particle System Shape Values"))
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).FetchShapeValues();

                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
            helperNum++;
        }

        private void OverLifetimeOptions()
        {
            bool toggle = ((AllIn1ParticleHelperComponent)target).overLifetimeOptions;
            toggle = EditorGUILayout.BeginToggleGroup(helperNum + ".Over Lifetime Options", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).overLifetimeOptions)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).overLifetimeOptions = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);

                AllIn1ParticleHelperComponent.LifetimeSettings tempColorLifetime = ((AllIn1ParticleHelperComponent)target).colorLifetime;
                EditorGUI.BeginChangeCheck();
                tempColorLifetime = (AllIn1ParticleHelperComponent.LifetimeSettings)EditorGUILayout.EnumPopup("Alpha Over Lifetime", tempColorLifetime);
                if(EditorGUI.EndChangeCheck())
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).colorLifetime = tempColorLifetime;

                AllIn1ParticleHelperComponent.LifetimeSettings tempScaleLifetime = ((AllIn1ParticleHelperComponent)target).sizeLifetime;
                EditorGUI.BeginChangeCheck();
                tempScaleLifetime = (AllIn1ParticleHelperComponent.LifetimeSettings)EditorGUILayout.EnumPopup("Scale Over Lifetime", tempScaleLifetime);
                if(EditorGUI.EndChangeCheck())
                    for(int i = 0; i < targets.Length; i++)
                        ((AllIn1ParticleHelperComponent)targets[i]).sizeLifetime = tempScaleLifetime;

                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
            helperNum++;
        }

        private int selectedIndex = 0;
        private AllIn1ParticleHelperSO[] particleHelpersPresets = null;

        private void ParticleHelperPresets()
        {
            Color iniBackgroundColor = GUI.backgroundColor;

            bool toggle = ((AllIn1ParticleHelperComponent)target).particleHelperPresets;
            toggle = EditorGUILayout.BeginToggleGroup(helperNum + ".Particle Helper Presets", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).particleHelperPresets)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).particleHelperPresets = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);
                
                GUI.backgroundColor = Color.cyan;
                if(GUILayout.Button("Fetch Particle Helper Presets")) LoadParticleHelpersAndPresets();
                GUI.backgroundColor = iniBackgroundColor;

                GUI.backgroundColor = Color.green;
                GUILayout.Label("Save Particle Helper Presets", smallBoldLabel);
                if(GUILayout.Button("Save Particle Helper Preset"))
                {
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).SaveParticleHelperPreset();
                    particleHelpersPresets = null;
                    LoadParticleHelpersAndPresets();
                }
                GUI.backgroundColor = iniBackgroundColor;

                DrawLine(Color.grey, 1, 3);

                GUILayout.Label("Load Particle Helper Presets", smallBoldLabel);
                bool particleHelpersPresetsAvailable = particleHelpersPresets != null && particleHelpersPresets.Length > 0;
                if(!particleHelpersPresetsAvailable)
                {
                    GUILayout.Label("No Particle Helper Presets found", smallRedBoldLabel);
                    if(Time.realtimeSinceStartup - timeSinceLastFetch > TIME_BETWEEN_FETCHES) LoadParticleHelpersAndPresets();
                }
                else
                {
                    string[] presetNames = new string[particleHelpersPresets.Length];
                    for(int i = 0; i < particleHelpersPresets.Length; i++) presetNames[i] = particleHelpersPresets[i].name;

                    GUI.backgroundColor = Color.cyan;
                    selectedIndex = EditorGUILayout.Popup("Particle Helper Presets", selectedIndex, presetNames);
                    GUI.backgroundColor = iniBackgroundColor;

                    GUI.backgroundColor = Color.yellow;
                    if(GUILayout.Button("Apply Particle Helper Preset"))
                        for(int i = 0; i < targets.Length; i++)
                            ((AllIn1ParticleHelperComponent)targets[i]).ApplyParticleHelperPreset(particleHelpersPresets[selectedIndex], true);
                    GUI.backgroundColor = iniBackgroundColor;
                }
                
                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
            helperNum++;
            GUI.backgroundColor = iniBackgroundColor;
        }
        
        private void LoadParticleHelpersAndPresets()
        {
            timeSinceLastFetch = Time.realtimeSinceStartup;
            string[] guids = AssetDatabase.FindAssets("t:AllIn1ParticleHelperSO");
            particleHelpersPresets = guids.Select(guid => AssetDatabase.LoadAssetAtPath<AllIn1ParticleHelperSO>(AssetDatabase.GUIDToAssetPath(guid))).ToArray();
            
            guids = AssetDatabase.FindAssets("t:Preset");
            particleSystemPresets = guids
                .Select(guid => AssetDatabase.LoadAssetAtPath<Preset>(AssetDatabase.GUIDToAssetPath(guid)))
                .Where(preset => preset != null && preset.GetTargetFullTypeName().Contains("ParticleSystem"))
                .ToArray();
        }

        private Preset[] particleSystemPresets = null;

        private void ParticleSystemPresets()
        {
            Color iniBackgroundColor = GUI.backgroundColor;

            bool toggle = ((AllIn1ParticleHelperComponent)target).particleSystemPresets;
            toggle = EditorGUILayout.BeginToggleGroup(helperNum + ".Particle System Presets", toggle);
            if(toggle != ((AllIn1ParticleHelperComponent)target).particleSystemPresets)
                for(int i = 0; i < targets.Length; i++)
                    ((AllIn1ParticleHelperComponent)targets[i]).particleSystemPresets = toggle;
            if(toggle)
            {
                EditorGUILayout.BeginVertical(propertiesStyle);

                GUI.backgroundColor = Color.cyan;
                if(GUILayout.Button("Fetch Particle System Presets")) LoadParticleHelpersAndPresets();
                GUI.backgroundColor = iniBackgroundColor;
                
                GUI.backgroundColor = Color.green;
                GUILayout.Label("Save Particle System Presets", smallBoldLabel);
                if(GUILayout.Button("Save Particle System Preset"))
                {
                    for(int i = 0; i < targets.Length; i++) ((AllIn1ParticleHelperComponent)targets[i]).SaveParticleSystemPreset();
                    particleSystemPresets = null;
                    LoadParticleHelpersAndPresets();
                }

                DrawLine(Color.grey, 1, 3);

                GUILayout.Label("Load Particle System Presets", smallBoldLabel);
                bool particleSystemPresetsAvailable = particleSystemPresets != null && particleSystemPresets.Length > 0;
                if(!particleSystemPresetsAvailable)
                {
                    GUILayout.Label("No Particle System Presets found", smallRedBoldLabel);
                    if(Time.realtimeSinceStartup - timeSinceLastFetch > TIME_BETWEEN_FETCHES) LoadParticleHelpersAndPresets();
                }
                else
                {
                    string[] presetNames = new string[particleSystemPresets.Length];
                    for(int i = 0; i < particleSystemPresets.Length; i++) presetNames[i] = particleSystemPresets[i].name;

                    GUI.backgroundColor = Color.cyan;
                    selectedIndex = EditorGUILayout.Popup("Particle System Presets", selectedIndex, presetNames);

                    GUI.backgroundColor = Color.yellow;
                    if(GUILayout.Button("Apply Particle System Preset"))
                        for(int i = 0; i < targets.Length; i++)
                            ((AllIn1ParticleHelperComponent)targets[i]).ApplyParticleSystemPreset(particleSystemPresets[selectedIndex]);
                }
                
                EditorGUILayout.EndVertical();
            }

            EditorGUILayout.EndToggleGroup();
            helperNum++;
            GUI.backgroundColor = iniBackgroundColor;
        }

        private void DrawLine(Color color, int thickness = 2, int padding = 10)
        {
            Rect r = EditorGUILayout.GetControlRect(GUILayout.Height(padding + thickness));
            r.height = thickness;
            r.y += (padding / 2f);
            r.x -= 2;
            r.width += 6;
            EditorGUI.DrawRect(r, color);
        }
    }
}
#endif