using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Ease.Core;
using Ease.Core.Model;
using System.Data;


namespace HRM.BO
{
    #region LeaveParameter
    
    public class LeaveParameter : AuditTrailBase
    {
        

        #region Constructor
        public LeaveParameter()
        {
            //_nLeaveId = 0;
            //_nMaxAccumulatedDays = 0.0;
            //_bIsActive = true;
            //_nForfitedMonth = 0;
            //_nAllowAdvance = false;
            //_nIgnoreHoliday = true;
            //_CalculationType = EnumLeaveCalculationType.Daily;
            //_nApplicableFor = 0;
            //_manager = null;
            //_bIsForfited = false;
            //_nApplicableFor = LeaveApplicableType.Regardless;
            //_PayrollTypeID = 0;
            //_nIsMonthlyBalance = false;
        }
        #endregion

        #region Properties


        public int PayrollTypeID { get; set; }
        public Leave Leave { get; set; }
        //private Leave _oLeave;
        //public Leave Leave
        //{
        //    get
        //    {
        //        if (_oLeave == null)
        //        {
        //            _oLeave = new Leave();
        //            _oLeave = (Leave)_oLeave.Get(ID.FromInteger(_nLeaveId));
        //        }
        //        return _oLeave;
        //    }

        //}

        #region Leave Parameter Details
        public List<LeaveParameterDetail> Details { get; set; }
        //private List<LeaveParameterDetail> _oDetails;
        //public List<LeaveParameterDetail> Details
        //{
        //    get
        //    {
        //        if (_oDetails == null || _oDetails.Count == 0)
        //        {
        //            _oDetails = new List<LeaveParameterDetail>();
        //            if (!this.IsNew)
        //                _oDetails = LeaveParameter.Service.GetDetails(ID);
        //        }
        //        return _oDetails;
        //    }
        //    set
        //    {
        //        _oDetails = value;
        //    }
        //}
        //public LeaveParameterDetail GetDetail(int paramID)
        //{
        //    LeaveParameterDetail oLeaveDetail = null;            
        //    oLeaveDetail = LeaveParameter.Service.GetDetail(paramID);            
        //    return oLeaveDetail;
        //}

        #endregion

        public int LeaveId { get; set; }

        public double MaxAccumulatedDays { get; set; }

       // public SetupManager Manager { get; set; }

        public bool IsActive { get; set; }

        public int ForfitedMonth { get; set; }

        public bool IsForfited { get; set; }

        public bool AllowAdvance { get; set; }

        public bool IgnoreHoliday { get; set; }

        public EnumLeaveCalculationType CalculationType { get; set; }

        public bool IsMonthlyBalance { get; set; }

        public LeaveApplicableType ApplicableFor { get; set; }

        public List<paramItem> ParamItems { get; set; }
        public EnumLeaveparamOn ParamOnType { get; set; }

        #endregion


        public class paramItem
        {
            public int id { get; set; }
            public int paramid { get; set; }
            public int itemID { get; set; }
            public EnumLeaveparamOn ParamOnType { get; set; }
        }
        //public List<LeaveParameterDetail> GetAllDetails()
        //{
        //    List<LeaveParameterDetail> Details = new List<LeaveParameterDetail>();
        //    Details = LeaveParameter.Service.GetDetails();
        //    return Details;

        //}
        //public LeaveParameter Get(ID nLeaveParamId)
        //{
        //    LeaveParameter oLeaveParameter = null;
        //    #region Cache Header
        //    oLeaveParameter = (LeaveParameter)_cache["Get", nLeaveParamId];
        //    if (oLeaveParameter != null)
        //        return oLeaveParameter;
        //    #endregion
        //    oLeaveParameter = LeaveParameter.Service.Get(nLeaveParamId);

        //    #region Cache Footer
        //    _cache.Add(oLeaveParameter, "Get", nLeaveParamId);
        //    #endregion
        //    return oLeaveParameter;
        //}

        //public static LeaveParameter ApplicableParam(Employee oEmp, List<EnmSetupManagerTranType> setupTypes, List<SetupDetail> details, LeaveParameter lparam, Leave oLeave)
        //{
        //    List<int> leaveParamIds = SetupManager.ApplicableParametersForReport(oEmp, setupTypes, details);
        //    List<LeaveParameter> leaveParams = new List<LeaveParameter>();
        //    LeaveParameter oLeaveParam = new LeaveParameter();
        //    if (oLeave.ApplicableFor != (EnumGender)oEmp.Gender && oLeave.ApplicableFor != EnumGender.Other && oLeave.ApplicableFor != EnumGender.None)
        //    {
        //        return oLeaveParam;
        //    }

        //    bool found = false;
        //    foreach (int id in leaveParamIds)
        //    {
        //        if (id == lparam.ID.Integer)
        //        {
        //            found = true;
        //            break;
        //        }
        //    }
        //    if (found)
        //    {
        //        switch (lparam.ApplicableFor)
        //        {
        //            case LeaveApplicableType.Probetionary:
        //                if (!oEmp.IsConfirmed)
        //                {
        //                    oLeaveParam = lparam;
        //                }
        //                break;
        //            case LeaveApplicableType.Confirmed:
        //                if (oEmp.IsConfirmed)
        //                {
        //                    oLeaveParam = lparam;
        //                }
        //                break;
        //            case LeaveApplicableType.Regardless:
        //                oLeaveParam = lparam;
        //                break;
        //            default:
        //                break;
        //        }

        //    }
        //    return oLeaveParam;
        //}

        //public LeaveParameterDetail GetApplicableForEmployee(Employee oEmp, DateTime operationDate)
        //{
        //    //#### change by Current date function
        //    TimeSpan ts = operationDate - oEmp.JoiningDate;
        //    double y = Math.Round((double)ts.Days / 365, 2);
        //    //int year = operationDate.Year - oEmp.JoiningDate.Year+1;
        //    //int number=(int)y;
        //    //double number1 =(double)(y-number);
        //    //float f =(float)y;
        //    int year = 0;
        //    //if (y > (int)y)
        //    //    year = (int)y + 1;
        //    //else
        //    year = (int)y;
        //    int maxYear = -1;
        //    LeaveParameterDetail dtl = null;
        //    foreach (LeaveParameterDetail detail in this.Details)
        //    {
        //        if (detail.Year <= year && detail.Year >= maxYear)
        //        {
        //            maxYear = detail.Year;
        //            dtl = detail;
        //        }
        //    }
        //    return dtl;
        //}
        //public LeaveParameterDetail GetApplicableForEmployee(Employee oEmp, DateTime operationDate,List<LeaveParameterDetail> oAllDetails,ID nParamID)
        //{
        //    //#### change by Current date function
        //    TimeSpan ts = operationDate - oEmp.JoiningDate;
        //    double y = Math.Round((double)ts.Days / 365, 2);
        //    //int year = operationDate.Year - oEmp.JoiningDate.Year+1;
        //    //int number=(int)y;
        //    //double number1 =(double)(y-number);
        //    //float f =(float)y;
        //    int year = 0;
        //    //if (y > (int)y)
        //    //    year = (int)y + 1;
        //    //else
        //    year = (int)y;
        //    int maxYear = -1;
        //    LeaveParameterDetail dtl = null;
        //    List<LeaveParameterDetail> oDetails = oAllDetails.FindAll(delegate(LeaveParameterDetail lpd) { return lpd.LeaveParamId ==Convert.ToInt32(nParamID.Integer.ToString()); });
        //    foreach (LeaveParameterDetail detail in oDetails)
        //    {
        //        if (detail.Year <= year && detail.Year >= maxYear)
        //        {
        //            maxYear = detail.Year;
        //            dtl = detail;
        //        }
        //    }
        //    return dtl;
        //}
        //public LeaveParameter GetByLeaveID(int leaveID)
        //{
        //    LeaveParameter oLeaveParameter = null;
        //    oLeaveParameter = LeaveParameter.Service.GetByLeaveID(leaveID);
        //    return oLeaveParameter;
        //}
        //public ID Save()
        //{
        //    this.SetAuditTrailProperties();
        //    return LeaveParameter.Service.Save(this);
        //}
        //public void Delete()
        //{
        //    LeaveParameter.Service.Delete(this.ID);
        //}
        //public static List<Leave> GetApplicableLeaves(Employee oEmp)
        //{
        //    List<LeaveParameter> oLeaveParams = Get(true);
        //    if (oLeaveParams == null) return null;
        //    List<LeaveParameter> oAppParams = LeaveParameter.ApplicableParams(oEmp);
        //    if (oAppParams == null) return null;

        //    List<Leave> oLeaves = new List<Leave>();
        //    foreach (LeaveParameter param in oAppParams)
        //    {
        //        oLeaves.Add(param.Leave);
        //    }
        //    return oLeaves;
        //}
        //public static List<LeaveParameter> ApplicableParams(Employee oEmp, List<EnmSetupManagerTranType> setupTypes, List<SetupDetail> details, List<LeaveParameter> leaveParamss)
        //{
        //    List<int> leaveParamIds = SetupManager.ApplicableParametersForReport(oEmp, setupTypes, details);
        //    List<LeaveParameter> leaveParams = new List<LeaveParameter>();
        //    foreach (LeaveParameter lparam in leaveParamss)
        //    {
        //        if (lparam.Leave.ApplicableFor != (EnumGender)oEmp.Gender && lparam.Leave.ApplicableFor != EnumGender.Other && lparam.Leave.ApplicableFor != EnumGender.None)
        //        {
        //            continue;
        //        }

        //        bool found = false;
        //        foreach (int id in leaveParamIds)
        //        {
        //            if (id == lparam.ID.Integer)
        //            {
        //                found = true;
        //                break;
        //            }
        //        }
        //        if (found)
        //        {
        //            switch (lparam.ApplicableFor)
        //            {
        //                case LeaveApplicableType.Probetionary:
        //                    if (!oEmp.IsConfirmed)
        //                    {
        //                        leaveParams.Add(lparam);
        //                    }
        //                    break;
        //                case LeaveApplicableType.Confirmed:
        //                    if (oEmp.IsConfirmed)
        //                    {
        //                        leaveParams.Add(lparam);
        //                    }
        //                    break;
        //                case LeaveApplicableType.Regardless:
        //                    leaveParams.Add(lparam);
        //                    break;
        //                default:
        //                    break;
        //            }

        //        }
        //    }
        //    return leaveParams;
        //}
        //public LeaveParameterDetail GetApplicableForEmployee(Employee oEmp, DateTime operationDate, List<LeaveParameterDetail> oDetails)
        //{
        //    //#### change by Current date function
        //    TimeSpan ts = operationDate - oEmp.JoiningDate;
        //    double y = Math.Round((double)ts.Days / 365, 2);
        //    //int year = operationDate.Year - oEmp.JoiningDate.Year+1;
        //    //int number=(int)y;
        //    //double number1 =(double)(y-number);
        //    //float f =(float)y;
        //    int year = 0;
        //    if (y > (int)y)
        //        year = (int)y + 1;
        //    else
        //        year = (int)y;
        //    int maxYear = -1;
        //    LeaveParameterDetail dtl = null;
        //    foreach (LeaveParameterDetail detail in oDetails)
        //    {
        //        if (detail.Year <= year && detail.Year >= maxYear)
        //        {
        //            maxYear = detail.Year;
        //            dtl = detail;
        //        }
        //    }
        //    return dtl;
        //}
        //public static LeaveParameter GetLeaveParam(Employee oEmp, int nLeaveID)
        //{
        //    List<LeaveParameter> oLeaveParams = LeaveParameter.Get(true);
        //    if (oLeaveParams == null) return null;
        //    List<LeaveParameter> oAppParams = ApplicableParams(oEmp);
        //    if (oAppParams == null) return null;

        //    foreach (LeaveParameter param in oAppParams)
        //    {
        //        if (param.LeaveId == nLeaveID)
        //        {
        //            return param;
        //        }
        //    }
        //    return null;
        //}
        //public LeaveParameterDetail GetDetailForEmp(ID EmpId)
        //{
        //    Employee oEmp = Employee.Service.Get(EmpId);
        //    LeaveParameterDetail oretVal = null;
        //    return oretVal;
        //}

        #region Service Factory
        internal static ILeaveParameterService Service
        {
            get { return Services.Factory.CreateService<ILeaveParameterService>(typeof(ILeaveParameterService)); }
        }
        #endregion

        //#region Functions

        //public static List<LeaveParameter> ApplicableParams(Employee oEmp)
        //{
        //    List<int> leaveParamIds = SetupManager.ApplicableParameters(oEmp, EnumParameterSetup.Leave);
        //    List<LeaveParameter> leaveParamss = LeaveParameter.Get();
        //    List<LeaveParameter> leaveParams = new List<LeaveParameter>();
        //    foreach (LeaveParameter lparam in leaveParamss)
        //    {
        //        if (lparam.Leave.ApplicableFor != (EnumGender)oEmp.Gender && lparam.Leave.ApplicableFor != EnumGender.Other && lparam.Leave.ApplicableFor != EnumGender.None)
        //        {
        //            continue;
        //        }

        //        bool found = false;
        //        foreach (int id in leaveParamIds)
        //        {
        //            if (id == lparam.ID.Integer)
        //            {
        //                found = true;
        //                break;
        //            }
        //        }
        //        if (found)
        //        {
        //            switch (lparam.ApplicableFor)
        //            {
        //                case LeaveApplicableType.Probetionary:
        //                    if (!oEmp.IsConfirmed)
        //                    {
        //                        leaveParams.Add(lparam);
        //                    }
        //                    break;
        //                case LeaveApplicableType.Confirmed:
        //                    if (oEmp.IsConfirmed)
        //                    {
        //                        leaveParams.Add(lparam);
        //                    }
        //                    break;
        //                case LeaveApplicableType.Regardless:
        //                    leaveParams.Add(lparam);
        //                    break;
        //                default:
        //                    break;
        //            }

        //        }
        //    }
        //    return leaveParams;
        //}

        //public LeaveParameterDetail GetApplicableForEmployee(Employee oEmp, LeaveYear lyear)
        //{
        //    int month = Ease.CoreV35.Utility.Global.DateFunctions.DateDiff("m", oEmp.JoiningDate, SystemInformation.GetServerDate());
        //    int year = month / 12;
        //    int maxYear = -1;
        //    LeaveParameterDetail dtl = null;
        //    foreach (LeaveParameterDetail detail in this.Details)
        //    {
        //        if (detail.Year <= year && detail.Year >= maxYear)
        //        {
        //            maxYear = detail.Year;
        //            dtl = detail;

        //        }
        //    }
        //    if (dtl == null) return null;
        //    month = month - (maxYear * 12);
        //    if (month >= 12) month = Ease.CoreV35.Utility.Global.DateFunctions.DateDiff("m", lyear.StartDate, SystemInformation.GetServerDate());
        //    dtl.MonthPassed = month;
        //    month = month + Ease.CoreV35.Utility.Global.DateFunctions.DateDiff("m", SystemInformation.GetServerDate(), lyear.EndDate);
        //    month = month + 1;
        //    dtl.EligibleMonth = month;
        //    dtl.MaxDays = Math.Round((dtl.MaxDays / 12) * month);

        //    return dtl;
        //}


        //public static List<LeaveParameter> Get()
        //{
        //    List<LeaveParameter> oLeaveParameters = null;

        //    oLeaveParameters = LeaveParameter.Service.Get(SystemInformation.CurrentSysInfo.PayrollTypeID.Integer);
        //    #region Cache Footer
        //    //_cache.Add(oLeaveParameters, "Get");
        //    #endregion
        //    return oLeaveParameters;
        //}
        //public static List<LeaveParameter> GetByLeaveId(ID leaveId)
        //{
        //    #region Cache Header
        //    List<LeaveParameter> oLeaveParameters = _cache["GetByLeaveId", leaveId] as List<LeaveParameter>;
        //    if (oLeaveParameters != null)
        //        return oLeaveParameters;
        //    #endregion
        //    oLeaveParameters = LeaveParameter.Service.GetbyLeaveID(leaveId);
        //    #region Cache Footer
        //    _cache.Add(oLeaveParameters, "GetByLeaveId", leaveId);
        //    #endregion
        //    return oLeaveParameters;
        //}

        //public static List<Leave> GetApplicableLeave(Employee employee)
        //{
        //    List<LeaveParameter> oLeaveParams = LeaveParameter.Get(true);
        //    if (oLeaveParams == null) return null;
        //    List<LeaveParameter> oAppParams = new List<LeaveParameter>();
        //    oAppParams = ApplicableParams(employee);
        //    if (oAppParams == null) return null;

        //    List<Leave> oLeaves = new List<Leave>();
        //    foreach (LeaveParameter param in oAppParams)
        //    {
        //        oLeaves.Add(param.Leave);
        //    }
        //    return oLeaves;

        //}
        //public static List<LeaveParameter> Get(bool isActive)
        //{
        //    #region Cache Header
        //    List<LeaveParameter> oLeaveParameters = _cache["Get"] as List<LeaveParameter>;
        //    if (oLeaveParameters != null)
        //        return oLeaveParameters;
        //    #endregion
        //    oLeaveParameters = LeaveParameter.Service.Get(isActive,SystemInformation.CurrentSysInfo.PayrollTypeID.Integer);
        //    #region Cache Footer
        //    _cache.Add(oLeaveParameters, "Get", isActive);
        //    #endregion
        //    return oLeaveParameters;
        //}

        //#endregion

        #region ISetupManager Members
        //public List<SetupDetail> SetupDetails { get; set; }

        //public EmployeeSetupParameter ApplicableParameters(Employee employee)
        //{
        //    EmployeeSetupParameter empParameter = new EmployeeSetupParameter(EnumParameterSetup.Leave);
        //    empParameter.Employee = employee;
        //    empParameter.ParameterIDs = SetupManager.ApplicableParameters(employee, EnumParameterSetup.Leave);
        //    return empParameter;
        //}

        //public static List<EmployeeSetupParameter> GetParameters(List<Employee> employees)
        //{

        //    List<EmployeeSetupParameter> empParametes = new List<EmployeeSetupParameter>();
        //    string Params = ConfigurationManager.GetStringValue("leave", "setupparameter", EnumConfigurationType.Logic);
        //    ConfigReader oreader = new ConfigReader(Params);
        //    DataSet setupDetails = SetupDetail.GetParameters(EnumParameterSetup.Leave, oreader.SQLRelationToEmp, Employee.GetInEmpSQL(employees));
        //    if (setupDetails.Tables[0] == null) return empParametes;
        //    int empId = -1;
        //    EmployeeSetupParameter empprm = null;

        //    List<LeaveParameter> allParameters = LeaveParameter.Get();
        //    List<LeaveParameter> allLeave = LeaveParameter.Get();
        //    int nparameterID = 0;
        //    DateTime serverDate = SystemInformation.GetServerDate();
        //    foreach (DataRow orow in setupDetails.Tables[0].Rows)
        //    {
        //        if (empId != Convert.ToInt32(orow["EmployeeID"]))
        //        {
        //            empId = Convert.ToInt32(orow["EmployeeID"]);
        //            if (empprm != null && empprm.ParameterIDs.Count > 0) empParametes.Add(empprm);
        //            empprm = new EmployeeSetupParameter(EnumParameterSetup.Leave);
        //            empprm.Employee = employees.GetItem(ID.FromInteger(empId));
        //            nparameterID = Convert.ToInt32(orow["SetupID"]);
        //        }
        //        else nparameterID = Convert.ToInt32(orow["SetupID"]);

        //        List<LeaveParameter> lparameters = allParameters.FindAll(delegate(LeaveParameter param) { return param.LeaveId == nparameterID; });
        //        foreach (LeaveParameter param in lparameters)
        //        {
        //            if (param.ApplicableFor == LeaveApplicableType.Confirmed &&
        //                empprm.Employee.IsConfirmed == false) continue;

        //            if (param.ApplicableFor == LeaveApplicableType.Probetionary &&
        //                empprm.Employee.IsConfirmed == true) continue;
        //            int month = Ease.CoreV35.Utility.Global.DateFunctions.DateDiff("m", empprm.Employee.JoiningDate, serverDate);
        //            int year = (month / 12) + 1;
        //            int maxYear = -1;
        //            bool isValidParameter = false;
        //            foreach (LeaveParameterDetail detail in param.Details)
        //            {
        //                if (detail.Year <= year && detail.Year >= maxYear)
        //                {
        //                    maxYear = detail.Year;
        //                    empprm.ParameterIDs.Add(nparameterID);
        //                    isValidParameter = true;
        //                    break;
        //                }
        //            }
        //        }

        //    }
        //    if (empprm != null && empprm.ParameterIDs.Count > 0) empParametes.Add(empprm);

        //    return empParametes;
        //}


        //public List<EmployeeSetupParameter> ApplicableParameters(List<Employee> employees)
        //{
        //    List<SetupDetail> details = SetupDetail.GetParameters(EnumParameterSetup.Leave);
        //    List<EnmSetupManagerTranType> types = SetupDetail.GetTypes(EnumParameterSetup.Leave);
        //    List<EmployeeSetupParameter> empParametes = new List<EmployeeSetupParameter>();
        //    foreach (Employee emp in employees)
        //    {
        //        EmployeeSetupParameter empparameter = new EmployeeSetupParameter(EnumParameterSetup.Leave);
        //        empparameter.Employee = emp;
        //        empparameter.ParameterIDs = SetupManager.ApplicableParameters(emp, EnumParameterSetup.Leave,
        //                 types, details);
        //        empParametes.Add(empparameter);
        //    }
        //    return empParametes;
        //}
        //public void FillMe(ID id)
        //{
        //    LeaveParameter tpm = new LeaveParameter();
        //    tpm = tpm.Get(id);
        //    this.LeaveId = tpm.LeaveId;
        //    this.MaxAccumulatedDays = tpm.MaxAccumulatedDays;
        //    this.IsActive = tpm.IsActive;
        //    this.ForfitedMonth = tpm.ForfitedMonth;
        //    this.IgnoreHoliday = tpm.IgnoreHoliday;
        //    this.CalculationType = tpm.CalculationType;
        //    this.ApplicableFor = tpm.ApplicableFor;
        //    this.IsForfited = tpm.IsForfited;
        //    this.SetID(tpm.ID);
        //    this.SetState(ObjectState.Saved);
        //}
        #endregion
    }
    #endregion

    #region ILeaveParameter Service
    public interface ILeaveParameterService
    {
        List<LeaveParameter> Get();
        LeaveParameter Get(int leaveParameterId);
        List<LeaveParameter> Get(EnumStatus status, int payrollTypeID, int? LeaveID, bool? withDetail=false);
        List<LeaveParameterDetail> GetDetails(int leaveParamID);
        LeaveParameterDetail GetDetail(int paramID);
        int Save(LeaveParameter oLeaveParameter);

        List<LeaveParameter.paramItem> GetUsedParam(int leaveParamID, int payrolltypeid);
        List<LeaveParameter> GetAllByPayrollTypeID(int PayrollTypeID);
        List<LeaveParameter> Get(bool isActive, int payrollTypeId);
        List<LeaveParameterDetail> GetDetails();
        void Delete(int leaveParamID);
        LeaveParameter ApplicableParam(Employee oEmp, int leaveID);

        public LeaveParameterDetail GetApplicableForEmployee(Employee oEmp, DateTime operationDate,
            List<LeaveParameterDetail> oAllDetails, int nParamID);
    }
    #endregion

}