public ProjectStatus GetProjectStatus()
        {
            var result = new ProjectStatus();

            var closedPerson = _persons.SingleOrDefault(p => p.Name == "*Closed");

            var usersIds = _caseSet.Cases
                .Where(c => c.IndexPersonAssignedTo != null)
                .Select(c => c.IndexPersonAssignedTo)
                .Distinct().ToList();

            if (closedPerson != null) usersIds = usersIds.Where(u => u.Value != closedPerson.Index.Value).ToList();

            var projectStartDate = _caseSet.Milestone.DateStart.HasValue ? _caseSet.Milestone.DateStart.Value : DateTime.Now.Date;

            result.DaysToRelease = DateUtils.Difference(DateTime.Now, _caseSet.Milestone.DateRelease.Value).Value;

            var cfRegex = new Regex(@"\(CF *(?<month>\d{1,2})/(?<day>\d{1,2})/(?<year>\d{2}(?:\d{2})?)\)", RegexOptions.Singleline | RegexOptions.Compiled);

            DateTime? endDate = DateUtils.GetCodeFreezeFromName(_caseSet.Milestone.Name, cfRegex) ??
                                _caseSet.Milestone.DateRelease;

            result.EmployeeStatuses.AddRange(usersIds.Select(u => CalculateEmployeeStatus(u.Value, projectStartDate, endDate)).Where(r => r != null).ToList());

            if (result.EmployeeStatuses.Count != 0)
            {
                result.TotalRemainingDays = XConvert.RoundDecimalToHalf(result.EmployeeStatuses.Sum(es => es.RemainingDays) / result.EmployeeStatuses.Count);
                result.TotalOverUnder = XConvert.RoundDecimalToHalf(result.EmployeeStatuses.Sum(es => es.OverUnder));
                result.TotalWorkedDays = (decimal)result.EmployeeStatuses.Sum(es => es.WorkedDays) / result.EmployeeStatuses.Count;
                result.TotalPercentageWorkedDays = result.EmployeeStatuses.Sum(es => es.PercentageWorkedDays) / result.EmployeeStatuses.Count;
                result.TotalAdjustedOverUnder = XConvert.RoundDecimalToHalf(result.EmployeeStatuses.Sum(es => es.AdjustedOverUnder));
                result.TotalActualOverUnder = XConvert.RoundDecimalToHalf(result.EmployeeStatuses.Sum(es => es.ActualOverUnder));
                result.TotalScheduledWorkDays = XConvert.RoundDecimalToHalf(result.EmployeeStatuses.Sum(es => es.ScheduledWorkDays) / result.EmployeeStatuses.Count);

                result.StatusValue = XConvert.RoundDecimalToHalf(result.TotalActualOverUnder / result.EmployeeStatuses.Count);
            }

            result.Status = GetProjectStatus(result.StatusValue);

            return result;
        }
 public ProjectStatusListEventArgs(ProjectStatusListItem projectMilestone, ProjectStatus value, string key)
 {
     ProjectMilestone = projectMilestone;
     Status = value;
     CacheKey = key;
 }
 public ProjectStatusEx(ProjectStatus status)
 {
     Status = status.Status;
     StatusValue = status.StatusValue;
 }