using KarleyLibrary.Erweiterungen;
using System;
using System.Collections.Generic;
using System.Data;
using System.Threading.Tasks;

namespace WK5.Core.Models
{
    public class Preisgruppe
    {
        #region DBFelder
        public string? PRGR_A_BZEICH { get; set; }
        public string PRGR_A_NR { get; set; } = String.Empty;
        public decimal PRGR_N_BRUTTO { get; set; }
        public decimal PRGR_N_RUNDUNG1 { get; set; }
        public decimal PRGR_N_PREIS1 { get; set; }
        public decimal PRGR_N_RUNDUNG2 { get; set; }
        public decimal PRGR_N_PREIS2 { get; set; }
        public decimal PRGR_N_RUNDUNG3 { get; set; }
        public decimal PRGR_N_PREIS3 { get; set; }
        public decimal PRGR_N_RUNDUNG4 { get; set; }
        public decimal PRGR_N_PREIS4 { get; set; }
        public decimal PRGR_N_RUNDUNG5 { get; set; }
        public decimal PRGR_N_PREIS5 { get; set; }
        public decimal PRGR_N_RUNDUNG6 { get; set; }
        public DateTime PRGR_TIMESTAMP { get; set; }
        public int PRGR_N_LASTUSER { get; set; }
        #endregion

        public static async Task<Preisgruppe?> GetPreisgruppeAsync(string PRGR_A_NR)
        {
            using FbController2 _fbController = new FbController2();
            string sql = "SELECT * FROM PREISGRUPPE WHERE PRGR_A_NR = @PRGR_A_NR";
            _fbController.AddParameter("@PRGR_A_NR", PRGR_A_NR);
            var row = await _fbController.SelectRowAsync(sql);
            _fbController.Dispose();

            return row == null ? null : ObjectErweiterung.DataRowZuObjekt(new Preisgruppe(), row);
        }

        public static async IAsyncEnumerable<Preisgruppe> GetPreisgruppenAsync(FbController2 fbController)
        {
            DataTable data = await fbController.SelectDataAsync("SELECT * FROM PREISGRUPPE ORDER BY PRGR_A_BZEICH");
            foreach (DataRow row in data.Rows)
            {
                if (row is not null)
                {
                    yield return ObjectErweiterung.DataRowZuObjekt(new Preisgruppe(), row);
                }
            }

        }

        public decimal GetPreislistenProzent(int preisliste) => preisliste switch
        {
            1 => PRGR_N_BRUTTO,
            2 => PRGR_N_PREIS1,
            3 => PRGR_N_PREIS2,
            4 => PRGR_N_PREIS3,
            5 => PRGR_N_PREIS4,
            6 => PRGR_N_PREIS5,
            _ => 0.0m,
        };

        public int GetPreislistenRundung(int preisliste) => preisliste switch
        {
            1 => ConvertRundungsstellen(PRGR_N_RUNDUNG1),
            2 => ConvertRundungsstellen(PRGR_N_RUNDUNG2),
            3 => ConvertRundungsstellen(PRGR_N_RUNDUNG3),
            4 => ConvertRundungsstellen(PRGR_N_RUNDUNG4),
            5 => ConvertRundungsstellen(PRGR_N_RUNDUNG5),
            6 => ConvertRundungsstellen(PRGR_N_RUNDUNG6),
            _ => 2,
        };

        private int ConvertRundungsstellen(decimal rundung)
        {
            int count = 0;
            while (rundung < 1.0m)
            {
                rundung = rundung * 10;
                count++;
            }
            return count;
        }

        public bool GetPreislisteFix(Artikel artikel, int preisliste) => preisliste switch
        {
            1 => artikel.ARTI_L_FIXPREIS,
            2 => artikel.ARTI_L_FIXPREIS,
            3 => artikel.ARTI_L_FIXPREIS,
            4 => artikel.ARTI_L_FIXVK3,
            5 => artikel.ARTI_L_FIXVK4,
            6 => artikel.ARTI_L_FIXVK5,
            _ => false,
        };

        public decimal GetAbschlagVK(decimal ek, int preisliste)
        {
            decimal proz = GetPreislistenProzent(preisliste);

            /*
             Formel                    
                Marge = VK-EK/VK

                VK-EK/VK = Marge |*VK
                VK-EK = Marge * VK |-Marge * VK
                VK-EK-Marge*VK = 0 |+EK
                VK-Marge*VK = EK|VK ausklammern
                (-Marge+1)*VK = EK|/-y+1
                VK = EK/(-y+1)
                
             */

            decimal wert = (ek / ((proz / 100) - 1)) * -1;


            return Math.Round(wert, GetPreislistenRundung(preisliste));
        }
    }
}
