using FeMM.Common.Checks;
using FeMM.Grasshopper.DataTypes;
using FeMM.Grasshopper.Helpers;
using GH_IO.Serialization;
using Grasshopper.GUI;
using Grasshopper.Kernel;
using Grasshopper.Kernel.Special;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Versioning;

namespace FeMM.Grasshopper.Components.Design
{
#if NETCOREAPP
    [SupportedOSPlatform("windows")]
#endif
    public abstract class SteelPrefsComponent : GH_Component
    {
        GH_SteelPrefs _prefs;

        /// <summary>
        /// Initializes a new instance of the MixedSectionComponent class.
        /// </summary>
        protected SteelPrefsComponent(string name, string nickname, string description)
          : base(name, nickname, description, CategoryNameConstants.CATEGORY_FEMM, CategoryNameConstants.SUBCATEGORY_DESIGN)
        {
            _prefs = null;
        }

        public override void CreateAttributes()
        {
            var attr = new ComponentAttributes.ComponentOneButtonAttributes(this, "Set prefs");
            attr.ButtonPressed += () =>
            {
                Forms.SteelPrefsForm prefsForm = GetForm(_prefs);
                GH_WindowsFormUtil.CenterFormOnCursor(prefsForm, true);
                if (prefsForm.ShowDialog() == System.Windows.Forms.DialogResult.OK && prefsForm.Prefs != null)
                {
                    _prefs = CreateGHSteelPrefs(prefsForm.Prefs);
                    ExpireSolution(true);
                }
            };
            m_attributes = attr;
        }

        protected abstract Forms.SteelPrefsForm GetForm(GH_SteelPrefs prefs);

        protected abstract GH_SteelPrefs CreateGHSteelPrefs(SteelPrefs prefs);

        protected abstract GH_SteelPrefs CreateGHSteelPrefs();


        /// <summary>
        /// Registers all the input parameters for this component.
        /// </summary>
        protected override void RegisterInputParams(GH_InputParamManager pManager)
        {
            int n = pManager.AddTextParameter("Str. results", "SR", "The result cases or combination for strength checks", GH_ParamAccess.list);
            pManager[n].Optional = true;
            n = pManager.AddTextParameter("Def. results", "DR", "The result cases or combination for deflection checks", GH_ParamAccess.list);
            pManager[n].Optional = true;
        }

        /// <summary>
        /// Registers all the output parameters for this component.
        /// </summary>
        protected override void RegisterOutputParams(GH_OutputParamManager pManager)
        {
            pManager.AddGenericParameter("Prefs", "P", "Steel prefs for Sap2000 analysis", GH_ParamAccess.item);
        }

        /// <summary>
        /// This is the method that actually does the work.
        /// </summary>
        /// <param name="DA">The DA object is used to retrieve from inputs and store in outputs.</param>
        protected override void SolveInstance(IGH_DataAccess DA)
        {
            var strResults = new List<string>();
            var defResults = new List<string>();
            GH_SteelPrefs prefs = null;
            DA.GetDataList(0, strResults);
            DA.GetDataList(1, defResults);

            if (strResults.Count == 0 && defResults.Count == 0)
            {
                if (_prefs == null || !_prefs.Value.AutoGenerateCheckCombs)
                {
                    DA.AbortComponentSolution();
                    AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "Empty design combinations");
                    return;
                }
            }
            if (_prefs == null)
            {
                DA.AbortComponentSolution();
                AddRuntimeMessage(GH_RuntimeMessageLevel.Warning, "Please specify preferences");
                return;
            }

            //Creating prefs getting those from form
            prefs = CreateGHSteelPrefs(_prefs.Value);
            //Setting combos
            prefs.Value.ResistanceCombs = strResults;
            prefs.Value.DeformationCombs = defResults;
            DA.SetData(0, prefs);
        }

        public void SetDesignCombos(List<string> analysisCaseResults)
        {
            IEnumerable<IGH_Param> keys = Params.Input[0].Sources.Where(s => s.GetType() == typeof(GH_ValueList))
                                                        .Union(Params.Input[1].Sources.Where(s => s.GetType() == typeof(GH_ValueList)));
            foreach (GH_ValueList vallist in keys)
            {
                if (vallist.ListMode != GH_ValueListMode.CheckList)
                    vallist.ListMode = GH_ValueListMode.CheckList;
                ComponentsHelper.SetValueList(vallist, analysisCaseResults);
                vallist.NickName = "Results";
            }
        }

        public override GH_Exposure Exposure => GH_Exposure.secondary;

        public override bool Write(GH_IWriter writer)
        {
            if (base.Write(writer))
            {
                bool hasPrefs;
                hasPrefs = _prefs != null;
                writer.SetBoolean("hasPrefs", hasPrefs);
                if (hasPrefs)
                {
                    _prefs.Write(writer);
                }
                return true;
            }
            return false;
        }

        public override bool Read(GH_IReader reader)
        {
            if (base.Read(reader))
            {
                bool hasPrefs = false;
                hasPrefs = reader.GetBoolean("hasPrefs");
                if (hasPrefs)
                {
                    _prefs = CreateGHSteelPrefs();
                    _prefs.Read(reader);
                }
                return true;
            }
            return false;
        }

    }
}
303 files24 directories