EnVisageOnline/Main-RMO/Source/EnVisage/Models/WhatIfCalendarModel.cs

437 lines
20 KiB
C#
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using EnVisage.Code;
using System.Linq;
namespace EnVisage.Models
{
public class WhatIfCalendarModel
{
#region Classes and enums
public class ScenarioListElement
{
public System.Guid Id { get; set; }
public string Name { get; set; }
public ScenarioType Type { get; set; }
public string ProjectName { get; set; }
public Nullable<decimal> CGSplit { get; set; }
public Nullable<decimal> EFXSplit { get; set; }
public Nullable<System.DateTime> StartDate { get; set; }
public Nullable<System.DateTime> EndDate { get; set; }
}
public class СhartListElement
{
public Nullable<System.Guid> ScenarioId { get; set; }
public Nullable<System.DateTime> WeekEndingDate { get; set; }
public Nullable<decimal> Quantity { get; set; }
public Nullable<decimal> Cost { get; set; }
public Nullable<int> ScenarioType { get; set; }
public string ScenarioName { get; set; }
public decimal Probability { get; set; }
public string ProjectColor { get; set; }
public string CGEFX { get; set; }
}
#endregion
#region Properties
public List<ScenarioListElement> Scenarios { get; set; }
public string SelectedScenarios { get; set; }
public Guid? GroupId { get; set; }
[Display(Name = "Scenario Group")]
public string GroupName { get; set; }
[Display(Name = "Scenario Type")]
public ScenarioType SelectedScenarioType { get; set; }
[Display(Name = "Labor/Materials")]
public LaborMaterialsType LaborMaterials { get; set; }
[Display(Name = "Seats/Costs")]
public SeatsCostsType SeatsCosts { get; set; }
[Display(Name = "Include Actuals?")]
public YesNoType IncludeActuals { get; set; }
[DataType(DataType.Date), DisplayFormat(DataFormatString = "{0:MM/dd/yy}", ApplyFormatInEditMode = true)]
[Display(Name = "Start Date")]
public DateTime StartDate { get; set; }
[DataType(DataType.Date), DisplayFormat(DataFormatString = "{0:MM/dd/yy}", ApplyFormatInEditMode = true)]
[Display(Name = "End Date")]
public DateTime EndDate { get; set; }
public Dictionary<string, List<СhartListElement>> ChartData { get; set; }
public bool? UOMSwitcherMode { get; set; }
List<СhartListElement> _chartData;
#endregion
public WhatIfCalendarModel()
{
GroupId = Guid.Empty;
GroupName = string.Empty;
SelectedScenarioType = ScenarioType.Portfolio;
StartDate = DateTime.Today.AddMonths(-1);
EndDate = DateTime.Today.AddMonths(11);
}
#region Methods
public void FormScenarioReport(EnVisageEntities db)
{
Scenarios = GetScenarioData(db);
}
public void FormСhartListElements(EnVisageEntities db)
{
_chartData = GetСhartData(db);
ChartData = new Dictionary<string, List<СhartListElement>>();
foreach(var element in _chartData)
{
if(ChartData.Keys.Contains(element.ScenarioName))
{
ChartData[element.ScenarioName].Add(element);
}
else
{
ChartData.Add(element.ScenarioName, new List<СhartListElement>());
ChartData[element.ScenarioName].Add(element);
}
}
}
List<ScenarioListElement> GetScenarioData(EnVisageEntities db)
{
if (GroupId == Guid.Empty)
{
return db.VW_Scenario2Project.Where(t => t.Status.HasValue && t.Status.Value == (int?)ScenarioStatus.Active &&
((!t.SystemAttributeObjectID.HasValue && t.Type == (int?)SelectedScenarioType) ||
(t.Type == (int?)ScenarioType.Capacity ||
t.Type == (int?)ScenarioType.Vacation ||
t.Type == (int?)ScenarioType.Training)))
.Select(x =>
new ScenarioListElement()
{
Name = x.Name,
CGSplit = x.CGSplit,
EFXSplit = x.EFXSplit,
EndDate = x.EndDate,
StartDate = x.StartDate,
Id = x.Id,
ProjectName = x.ShowName + (x.ParentProjectId != null ? ": " + x.ParentProjectName : ""),
Type = (ScenarioType)x.Type
})
.ToList();
}
else
{
return db.VW_Scenario2Project.Where(t => t.Status.HasValue && t.Status.Value == (int?)ScenarioStatus.Active &&
((t.SystemAttributeObjectID.HasValue && t.SystemAttributeObjectID.Value == GroupId &&
t.Type == (int?)SelectedScenarioType) ||
(t.Type == (int?)ScenarioType.Capacity ||
t.Type == (int?)ScenarioType.Vacation ||
t.Type == (int?)ScenarioType.Training))).Select(x =>
new ScenarioListElement()
{
Name = x.Name,
CGSplit = x.CGSplit,
EFXSplit = x.EFXSplit,
EndDate = x.EndDate,
StartDate = x.StartDate,
Id = x.Id,
ProjectName = x.ShowName + (x.ParentProjectId != null ? ": " + x.ParentProjectName : ""),
Type = (ScenarioType)x.Type
})
.ToList();
}
}
List<СhartListElement> GetСhartData(EnVisageEntities db)
{
List<Guid> l = new List<Guid>();
if (!string.IsNullOrEmpty(SelectedScenarios) && !"[]".Equals(SelectedScenarios))
SelectedScenarios.TrimStart('[').TrimEnd(']').Split(',').ToList().ForEach(x => l.Add(new Guid(x.TrimStart('\"').TrimEnd('\"'))));
var expCats = db.ExpenditureCategory.AsNoTracking().ToDictionary(e => e.Id);
var uoms = db.UOMs.AsNoTracking().ToDictionary(u => u.Id);
var result = new List<СhartListElement>();
#region retreieve scenario data
if (GroupId.HasValue && !GroupId.Value.Equals(Guid.Empty))
{
result = (from sd in db.ScenarioDetail
join sc in db.Scenarios on sd.ParentID equals sc.Id
join ec in db.ExpenditureCategory on sd.ExpenditureCategoryId equals ec.Id
join pr in db.Projects on sc.ParentId equals pr.Id
join st in db.Status on pr.StatusId equals st.Id
where ec.Type == 1 & sc.Type > 1 & sc.Status == (int?)ScenarioStatus.Active & sd.WeekEndingDate <= EndDate & sd.WeekEndingDate >= StartDate
& sd.ParentID.HasValue & l.Contains(sd.ParentID.Value) & sc.SystemAttributeObjectID == GroupId
select new
{
ScenarioId = sd.ParentID,
sd.WeekEndingDate,
sd.Quantity,
sd.Cost,
sd.ExpenditureCategoryId,
ec.CGEFX,
ScenarioType = sc.Type,
ScenarioName = sc.Name,
ProjectId = pr.Id,
ProjectName = (pr.ParentProject != null ? pr.ParentProject.Name + ": " : "") + pr.Name,
ProjectTypeId = pr.TypeId,
StatusId = st.Id,
StatusName = st.Name,
pr.Probability,
ProjectColor = !string.IsNullOrEmpty(pr.Color) ? pr.Color :
(pr.ParentProject != null ? pr.ParentProject.Color : null),
sc.Status,
sc.SystemAttributeObjectID
})
.ToArray().Select(t => new
{
t.ScenarioId,
t.WeekEndingDate,
Quantity = t.Quantity * Utils.GetUOMMultiplier(expCats, uoms, t.ExpenditureCategoryId ?? Guid.Empty, UOMSwitcherMode),
t.Cost,
t.CGEFX,
t.ScenarioType,
t.ScenarioName,
t.ProjectId,
t.ProjectName,
t.ProjectTypeId,
t.StatusId,
t.StatusName,
t.Probability,
t.ProjectColor,
t.Status,
t.SystemAttributeObjectID
}).GroupBy(t => new { t.WeekEndingDate, t.CGEFX, t.ScenarioId, t.ScenarioType, t.ScenarioName, t.Probability, t.ProjectColor, t.ProjectId, t.StatusId })
.Select(x =>
new СhartListElement()
{
ScenarioId = x.Key.ScenarioId,
WeekEndingDate = x.Key.WeekEndingDate,
Quantity = x.Sum(s=>s.Quantity),
Cost = x.Sum(s=>s.Cost),
ScenarioType = x.Key.ScenarioType,
ScenarioName = x.Key.ScenarioName,
Probability = x.Key.Probability,
ProjectColor = x.Key.ProjectColor,
CGEFX = x.Key.CGEFX
})
.OrderBy(x => x.WeekEndingDate)
.ThenBy(x => x.ScenarioName)
.ToList();
}
else {
result = (from sd in db.ScenarioDetail
join sc in db.Scenarios on sd.ParentID equals sc.Id
join ec in db.ExpenditureCategory on sd.ExpenditureCategoryId equals ec.Id
join pr in db.Projects on sc.ParentId equals pr.Id
join st in db.Status on pr.StatusId equals st.Id
where ec.Type == 1 & sc.Type > 1 & sc.Status == (int?)ScenarioStatus.Active
& sd.WeekEndingDate <= EndDate & sd.WeekEndingDate >= StartDate & sd.ParentID.HasValue & l.Contains(sd.ParentID.Value)
& !sc.SystemAttributeObjectID.HasValue
select new
{
ScenarioId = sd.ParentID,
sd.WeekEndingDate,
sd.Quantity,
sd.Cost,
sd.ExpenditureCategoryId,
ec.CGEFX,
ScenarioType = sc.Type,
ScenarioName = sc.Name,
ProjectId = pr.Id,
ProjectName = (pr.ParentProject != null ? pr.ParentProject.Name + ": " : "") + pr.Name,
ProjectTypeId = pr.TypeId,
StatusId = st.Id,
StatusName = st.Name,
pr.Probability,
ProjectColor = !string.IsNullOrEmpty(pr.Color) ? pr.Color:
(pr.ParentProject != null ? pr.ParentProject.Color : null),
sc.Status,
sc.SystemAttributeObjectID
})
.ToArray().Select(t => new
{
t.ScenarioId,
t.WeekEndingDate,
Quantity = t.Quantity * Utils.GetUOMMultiplier(expCats, uoms, t.ExpenditureCategoryId ?? Guid.Empty, UOMSwitcherMode),
t.Cost,
t.CGEFX,
t.ScenarioType,
t.ScenarioName,
t.ProjectId,
t.ProjectName,
t.ProjectTypeId,
t.StatusId,
t.StatusName,
t.Probability,
t.ProjectColor,
t.Status,
t.SystemAttributeObjectID
}).GroupBy(t => new { t.WeekEndingDate, t.CGEFX, t.ScenarioId, t.ScenarioType, t.ScenarioName, t.Probability, t.ProjectColor, t.ProjectId, t.StatusId })
.Select(x =>
new СhartListElement()
{
ScenarioId = x.Key.ScenarioId,
WeekEndingDate = x.Key.WeekEndingDate,
Quantity = x.Sum(s=>s.Quantity),
Cost = x.Sum(s=>s.Cost),
ScenarioType = x.Key.ScenarioType,
ScenarioName = x.Key.ScenarioName,
Probability = x.Key.Probability,
ProjectColor = x.Key.ProjectColor,
CGEFX = x.Key.CGEFX
})
.OrderBy(x => x.WeekEndingDate)
.ThenBy(x => x.ScenarioName)
.ToList();
}
#endregion
#region retrieve Training data
if (result.Count > 0)
{
var scenarioIds = result.Select(t => t.ScenarioId).Distinct().ToArray();
var allTrainings = (from trainingWeek in db.PeopleResourceTrainings
join vac in db.Trainings on trainingWeek.TrainingId equals vac.Id
join pa in db.PeopleResourceAllocations on trainingWeek.PeopleResourceId equals pa.PeopleResourceId
join ec in db.ExpenditureCategory on pa.ExpenditureCategoryId equals ec.Id
where scenarioIds.Contains(pa.ScenarioId) & trainingWeek.WeekEndingDate >= StartDate & trainingWeek.WeekEndingDate <= EndDate
select new
{
trainingWeek.Id,
pa.ExpenditureCategoryId,
trainingWeek.WeekEndingDate,
trainingWeek.HoursOff,
ec.CGEFX,
Rate = db.Rates.FirstOrDefault(r => r.ExpenditureCategoryId == pa.ExpenditureCategoryId && r.StartDate <= trainingWeek.WeekEndingDate && r.EndDate >= trainingWeek.WeekEndingDate)
}).Distinct().ToArray();
var dates = result.Select(t => t.WeekEndingDate).Distinct().ToArray();
foreach (var dt in dates)
{
var dtTrainings = allTrainings.Where(t => t.WeekEndingDate <= dt.Value && t.WeekEndingDate >= dt.Value.AddDays(-6)).ToArray();
var q = dtTrainings.Sum(s => s.HoursOff * Utils.GetUOMMultiplier(expCats, uoms, s.ExpenditureCategoryId, UOMSwitcherMode));
var c = dtTrainings.Sum(s => s.HoursOff * (s.Rate == null ? 0 : s.Rate.Rate1));
result.Add(new СhartListElement
{
ScenarioName = "Training",
WeekEndingDate = dt,
Quantity = q,
Cost = c,
ScenarioType = (int)ScenarioType.Training,
Probability = 1,
ScenarioId = Guid.NewGuid(),
CGEFX = "CG ",
ProjectColor = "ff0000"
});
}
}
#endregion
#region retrieve Vacation data
if (result.Count > 0)
{
var scenarioIds = result.Select(t => t.ScenarioId).Distinct().ToArray();
var allVacations = (from vacWeek in db.PeopleResourceVacations
join vac in db.Vacations on vacWeek.VacationId equals vac.Id
join pa in db.PeopleResourceAllocations on vac.PeopleResourceId equals pa.PeopleResourceId
join ec in db.ExpenditureCategory on pa.ExpenditureCategoryId equals ec.Id
where scenarioIds.Contains(pa.ScenarioId) & vacWeek.WeekEndingDate >= StartDate & vacWeek.WeekEndingDate <= EndDate
select new { vacWeek.Id, pa.ExpenditureCategoryId, vacWeek.WeekEndingDate, vacWeek.HoursOff, ec.CGEFX,
Rate = db.Rates.FirstOrDefault(r => r.ExpenditureCategoryId == pa.ExpenditureCategoryId && r.StartDate <= vacWeek.WeekEndingDate && r.EndDate >= vacWeek.WeekEndingDate)
}).Distinct().ToArray();
var dates = result.Select(t => t.WeekEndingDate).Distinct().ToArray();
foreach (var dt in dates)
{
var dtVacations = allVacations.Where(t => t.WeekEndingDate <= dt.Value && t.WeekEndingDate >= dt.Value.AddDays(-6)).ToArray();
var q = dtVacations.Sum(s => s.HoursOff * Utils.GetUOMMultiplier(expCats, uoms, s.ExpenditureCategoryId, UOMSwitcherMode));
var c = dtVacations.Sum(s => s.HoursOff * (s.Rate == null ? 0 : s.Rate.Rate1));
result.Add(new СhartListElement
{
ScenarioName = "Vacation",
WeekEndingDate = dt,
Quantity = q,
Cost = c,
ScenarioType = (int)ScenarioType.Vacation,
Probability = 1,
ScenarioId = Guid.NewGuid(),
CGEFX = "CG ",
ProjectColor = "ff0000"
});
}
}
#endregion
return result;
}
#endregion
}
public class WhatIfCalendarDataModel
{
public class WhatIfCalendarDataRow
{
public Guid ExpCatId { get; set; }
public string ScenarioName { get; set; }
public string ScenarioType { get; set; }
public decimal GrandTotalCost { get; set; }
public decimal GrandTotalQuantity { get; set; }
public bool Checked { get; set; }
public List<long> QuantityValues { get; set; }
public decimal[] CostValues { get; set; }
public Guid?[] ScenarioDetailIds { get; set; }
public WhatIfCalendarDataRow()
{
QuantityValues = new List<long>();
CostValues = new decimal[0];
ScenarioDetailIds = new Guid?[0];
}
}
public Guid? CreditDepartment { get; set; }
[Display(Name = "Quantity Mode")]
public bool IsTableModeQuantity { get; set; }
public DateTime StartDate { get; set; }
public DateTime EndDate { get; set; }
public ScenarioType? ScenarioType { get; set; }
public Guid ScenarioId { get; set; }
public bool GrowthScenario { get; set; }
public Guid ParentId { get; set; }
[Display(Name = "Expenditure Categories")]
public Guid[] SelectedExpCats { get; set; }
public List<string> FiscalCalendarRecordHeaders { get; set; }
public List<long> FiscalCalendarRecordMilliseconds { get; set; }
public List<WhatIfCalendarDataRow> WhatIfCalendar { get; set; }
public int ColumnsCount
{
get
{
return FiscalCalendarRecordHeaders != null ? FiscalCalendarRecordHeaders.Count : 0;
}
}
public WhatIfCalendarDataModel()
{
//AvailableExpenditures = new List<SelectListItem>();
//SelectedExpCats = new Guid[] { };
WhatIfCalendar = new List<WhatIfCalendarDataRow>();
//FiscalCalendarRecordHeaders = new List<string>();
//IsTableModeQuantity = true;
}
}
}