123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816 |
- using Comal.Classes;
- using InABox.Clients;
- using InABox.Core;
- using InABox.DynamicGrid;
- using InABox.Wpf;
- using InABox.WPF;
- using NPOI.SS.Formula.Functions;
- using Syncfusion.Data;
- using Syncfusion.Data.Extensions;
- using Syncfusion.UI.Xaml.Grid;
- using Syncfusion.Windows.Shared;
- using System;
- using System.Collections;
- using System.Collections.Generic;
- using System.ComponentModel;
- using System.Data;
- using System.Linq;
- using System.Text;
- using System.Threading.Tasks;
- using System.Windows;
- using System.Windows.Controls;
- using System.Windows.Media;
- using System.Windows.Media.Imaging;
- namespace PRSDesktop.Panels.StockForecast.OrderScreen;
- public enum StockForecastOrderingType
- {
- StockOrder,
- JobOrder
- }
- public class StockForecastOrderingItemQuantity
- {
- public event Action? Changed;
- private double _stockTotal;
- public double StockTotal
- {
- get => _stockTotal;
- set
- {
- _stockTotal = value;
- Changed?.Invoke();
- }
- }
- public Dictionary<Guid, double> JobTotals { get; init; } = [];
- public void DoChanged()
- {
- Changed?.Invoke();
- }
- public double JobTotal => JobTotals.Sum(x => x.Value);
- public double GetTotal(StockForecastOrderingType type) => type == StockForecastOrderingType.StockOrder
- ? StockTotal
- : JobTotal;
- }
- public class StockForecastOrderingItem : BaseObject
- {
- [EditorSequence(1)]
- public ProductLink Product { get; set; }
- [EditorSequence(2)]
- public ProductStyleLink Style { get; set; }
- [EditorSequence(3)]
- public StockDimensions Dimensions { get; set; }
- [EditorSequence(4)]
- [DoubleEditor]
- public double RequiredQuantity { get; set; }
- private Dictionary<Guid, double> JobRequiredQuantities { get; set; } = [];
- public Dictionary<Guid, double> GetJobRequiredQuantities()
- {
- return JobRequiredQuantities;
- }
- public void SetJobRequiredQuantity(Guid jobID, double requiredQty)
- {
- JobRequiredQuantities[jobID] = requiredQty;
- }
- private StockForecastOrderingItemQuantity[] Quantities = [];
- public StockForecastOrderingItemQuantity GetQuantity(int i) => Quantities[i];
- public double GetTotalQuantity(StockForecastOrderingType type) => type == StockForecastOrderingType.StockOrder
- ? Quantities.Sum(x => x.StockTotal)
- : Quantities.Sum(x => x.JobTotal);
- public void SetQuantities(StockForecastOrderingItemQuantity[] quantities)
- {
- Quantities = quantities;
- }
- }
- public class StockForecastOrderingResult
- {
- public SupplierLink Supplier { get; set; }
- public JobLink? Job { get; set; }
- public StockForecastOrderingItem Item { get; set; }
- public SupplierProduct SupplierProduct { get; set; }
- public double Quantity { get; set; }
- public StockForecastOrderingResult(SupplierLink supplier, JobLink? job, StockForecastOrderingItem item, double quantity, SupplierProduct supplierProduct)
- {
- Supplier = supplier;
- Job = job;
- Item = item;
- Quantity = quantity;
- SupplierProduct = supplierProduct;
- }
- }
- public class StockForecastOrderingGrid : DynamicItemsListGrid<StockForecastOrderingItem>, ISpecificGrid
- {
- private List<SupplierProduct> SupplierProducts = [];
- private SupplierLink[] Suppliers = [];
- public double TotalQuantity => Items.Sum(x => x.GetTotalQuantity(OrderType));
- private DynamicActionColumn[] QuantityColumns = [];
- private DynamicActionColumn[] CostColumns = [];
- private readonly Dictionary<Guid, Job> JobDetails = [];
- private static BitmapImage _warning = PRSDesktop.Resources.warning.AsBitmapImage();
- private StockForecastOrderingType _orderType = StockForecastOrderingType.JobOrder;
- public StockForecastOrderingType OrderType
- {
- get => _orderType;
- set
- {
- if(_orderType != value)
- {
- _orderType = value;
- CalculateQuantities();
- foreach(var control in QuantityControls)
- {
- control.UpdateControl(OrderType);
- }
- }
- }
- }
- public IEnumerable<StockForecastOrderingResult> Results
- {
- get
- {
- for(int i = 0; i < Suppliers.Length; ++i)
- {
- var supplier = Suppliers[i];
- foreach(var item in Items)
- {
- var qty = item.GetQuantity(i);
- var supplierProduct = GetSupplierProduct(item, supplier.ID);
- if (supplierProduct is null)
- {
- // If this is true, then the quantities also will have to be true.
- continue;
- }
- if(OrderType == StockForecastOrderingType.StockOrder && qty.StockTotal > 0)
- {
- yield return new(supplier, null, item, qty.StockTotal, supplierProduct);
- }
- else
- {
- foreach(var (jobID, q) in qty.JobTotals)
- {
- if(q > 0)
- {
- yield return new(supplier, new() { ID = jobID }, item, q, supplierProduct);
- }
- }
- }
- }
- }
- }
- }
- #region UI Component
- private Component? _uiComponent;
- private Component UIComponent
- {
- get
- {
- _uiComponent ??= new Component(this);
- return _uiComponent;
- }
- }
- protected override IDynamicGridUIComponent<StockForecastOrderingItem> CreateUIComponent()
- {
- return UIComponent;
- }
- private class Component : DynamicGridGridUIComponent<StockForecastOrderingItem>
- {
- private StockForecastOrderingGrid Grid;
- public Component(StockForecastOrderingGrid grid)
- {
- Parent = grid;
- Grid = grid;
- }
- protected override Brush? GetCellSelectionBackgroundBrush()
- {
- return null;
- }
- protected override Brush? GetCellBackground(CoreRow row, DynamicColumnBase column)
- {
- var item = Grid.LoadItem(row);
- if(column is DynamicActionColumn ac)
- {
- var qIdx = Grid.QuantityColumns.IndexOf(ac);
- var idx = Math.Max(qIdx, Grid.CostColumns.IndexOf(ac));
- if(idx != -1)
- {
- var supplierProduct = Grid.GetSupplierProduct(item, Grid.Suppliers[idx].ID);
- if(supplierProduct is null)
- {
- return new SolidColorBrush(Colors.Gainsboro);
- }
- //if(item.GetTotalQuantity(Grid.OrderType) < item.RequiredQuantity)
- //{
- // return new SolidColorBrush(Colors.LightSalmon) { Opacity = 0.5 };
- //}
- //else
- //{
- // return new SolidColorBrush(Colors.LightGreen) { Opacity = 0.5 };
- //}
- }
- }
- return base.GetCellBackground(row, column);
- }
- }
- #endregion
- private bool _observing = true;
- private void SetObserving(bool observing)
- {
- _observing = observing;
- }
- public override void DoChanged()
- {
- if (_observing)
- {
- base.DoChanged();
- }
- }
- protected override void DoReconfigure(FluentList<DynamicGridOption> options)
- {
- options.Clear().Add(DynamicGridOption.FilterRows);
- }
- private bool _loadedData = false;
- private void LoadData()
- {
- var supplierColumns = new Columns<SupplierProduct>(x => x.ID)
- .Add(x => x.SupplierLink.ID)
- .Add(x => x.Product.ID)
- .Add(x => x.Style.ID)
- .Add(x => x.CostPrice)
- .AddDimensionsColumns(x => x.Dimensions)
- .Add(x => x.SupplierLink.Code);
- SupplierProducts = Client.Query(
- new Filter<SupplierProduct>(x => x.Product.ID).InList(Items.Select(x => x.Product.ID).ToArray())
- .And(x => x.SupplierLink.ID).IsNotEqualTo(Guid.Empty),
- supplierColumns,
- new SortOrder<SupplierProduct>(x => x.SupplierLink.Code))
- .ToList<SupplierProduct>();
- Suppliers = SupplierProducts.Select(x => x.SupplierLink).DistinctBy(x => x.ID).ToArray();
- foreach(var (itemIdx, item) in Items.WithIndex())
- {
- var quantities = new StockForecastOrderingItemQuantity[Suppliers.Length];
- for(int i = 0; i < Suppliers.Length; ++i)
- {
- quantities[i] = CreateQuantity(itemIdx);
- }
- item.SetQuantities(quantities);
- }
- CalculateQuantities();
- _loadedData = true;
- }
- private StockForecastOrderingItemQuantity CreateQuantity(int itemIdx)
- {
- var qty = new StockForecastOrderingItemQuantity();
- qty.Changed += () =>
- {
- var row = Data.Rows[itemIdx];
- InvalidateRow(row);
- DoChanged();
- };
- return qty;
- }
- private void CalculateQuantities()
- {
- SetObserving(false);
- foreach(var item in Items)
- {
- var supplierProduct = GetSupplierProduct(item);
- for(int i = 0; i < Suppliers.Length; ++i)
- {
- var qty = item.GetQuantity(i);
- var supplier = Suppliers[i];
- if(supplierProduct is not null && supplier.ID == supplierProduct.SupplierLink.ID)
- {
- if(OrderType == StockForecastOrderingType.StockOrder)
- {
- qty.StockTotal = qty.JobTotal;
- }
- else
- {
- qty.JobTotals.Clear();
- foreach(var (id, q) in item.GetJobRequiredQuantities())
- {
- qty.JobTotals[id] = q;
- }
- }
- }
- else
- {
- if(OrderType == StockForecastOrderingType.StockOrder)
- {
- qty.StockTotal = 0;
- }
- else
- {
- foreach(var id in item.GetJobRequiredQuantities().Keys)
- {
- qty.JobTotals[id] = 0;
- }
- }
- }
- }
- }
- SetObserving(true);
- DoChanged();
- InvalidateGrid();
- }
- protected override DynamicGridColumns LoadColumns()
- {
- if (!_loadedData)
- {
- LoadData();
- }
- ActionColumns.Clear();
- ActionColumns.Add(new DynamicImageColumn(Warning_Image) { Position = DynamicActionColumnPosition.Start });
- ActionColumns.Add(new DynamicImagePreviewColumn<StockForecastOrderingItem>(x => x.Product.Image) { Position = DynamicActionColumnPosition.Start });
- var columns = new DynamicGridColumns();
- columns.Add<StockForecastOrderingItem, string>(x => x.Product.Code, 120, "Product Code", "", Alignment.MiddleCenter);
- columns.Add<StockForecastOrderingItem, string>(x => x.Product.Name, 0, "Product Name", "", Alignment.MiddleLeft);
- columns.Add<StockForecastOrderingItem, string>(x => x.Style.Code, 80, "Style", "", Alignment.MiddleCenter);
- columns.Add<StockForecastOrderingItem, string>(x => x.Dimensions.UnitSize, 80, "Size", "", Alignment.MiddleCenter);
- columns.Add<StockForecastOrderingItem, double>(x => x.RequiredQuantity, 80, "Required", "", Alignment.MiddleCenter);
- QuantityColumns = new DynamicActionColumn[Suppliers.Length];
- CostColumns = new DynamicActionColumn[Suppliers.Length];
- QuantityControls.Clear();
- for(int i = 0; i < Suppliers.Length; ++i)
- {
- InitialiseSupplierColumn(i);
- }
- ActionColumns.Add(new DynamicMenuColumn(BuildMenu));
- return columns;
- }
- private void EditSupplierProductGrid(DynamicGrid<SupplierProduct> grid)
- {
- grid.OnCustomiseEditor += (sender, items, column, editor) =>
- {
- if(new Column<SupplierProduct>(x => x.SupplierLink.ID).IsEqualTo(column.ColumnName)
- || new Column<SupplierProduct>(x => x.Product.ID).IsEqualTo(column.ColumnName)
- || new Column<SupplierProduct>(x => x.Style.ID).IsEqualTo(column.ColumnName)
- || new Column<SupplierProduct>(x => x.Job.ID).IsEqualTo(column.ColumnName)
- || new Column<SupplierProduct>(x => x.Dimensions).IsEqualTo(column.ColumnName))
- {
- editor.Editable = editor.Editable.Combine(Editable.Disabled);
- }
- };
- }
- private void BuildMenu(DynamicMenuColumn column, CoreRow? row)
- {
- if (row is null) return;
- column.AddItem("New Supplier", null, row =>
- {
- if (row is null) return;
- var selection = new MultiSelectDialog<Supplier>(
- new Filter<Supplier>(x => x.ID).NotInList(Suppliers.Select(x => x.ID).ToArray()),
- new Columns<Supplier>(x => x.ID).Add(x => x.Code), multiselect: false);
- if (selection.ShowDialog() != true)
- {
- return;
- }
- var supplier = selection.Data().Rows.First().ToObject<Supplier>();
- var productInstance = LoadItem(row);
- var supplierProduct = new SupplierProduct();
- supplierProduct.Product.CopyFrom(productInstance.Product);
- supplierProduct.Style.CopyFrom(productInstance.Style);
- supplierProduct.Dimensions.CopyFrom(productInstance.Dimensions);
- supplierProduct.SupplierLink.CopyFrom(supplier);
- if (DynamicGridUtils.EditEntity(supplierProduct, customiseGrid: EditSupplierProductGrid))
- {
- SupplierProducts.Add(supplierProduct);
- var newSuppliers = new SupplierLink[Suppliers.Length + 1];
- var newIdx = Suppliers.Length;
- for (int i = 0; i < Suppliers.Length; i++)
- {
- newSuppliers[i] = Suppliers[i];
- }
- newSuppliers[newIdx] = supplierProduct.SupplierLink;
- foreach (var (itemIdx, item) in Items.WithIndex())
- {
- var populateSupplierProduct = GetSupplierProduct(item);
- var quantities = new StockForecastOrderingItemQuantity[newSuppliers.Length];
- for (int i = 0; i < Suppliers.Length; ++i)
- {
- quantities[i] = item.GetQuantity(i);
- }
- var newQty = CreateQuantity(itemIdx);
- quantities[newIdx] = newQty;
- if (OrderType == StockForecastOrderingType.StockOrder)
- {
- newQty.StockTotal = 0;
- }
- else
- {
- foreach (var id in item.GetJobRequiredQuantities().Keys)
- {
- newQty.JobTotals[id] = 0;
- }
- }
- item.SetQuantities(quantities);
- }
- Suppliers = newSuppliers;
- Refresh(true, true);
- }
- });
- }
- private BitmapImage? Warning_Image(CoreRow? row)
- {
- if (row is null) return _warning;
- var item = LoadItem(row);
- if(item.GetTotalQuantity(OrderType) < item.RequiredQuantity)
- {
- return _warning;
- }
- else
- {
- return null;
- }
- }
- protected override void ConfigureColumnGroups()
- {
- for(int idx = 0; idx < Suppliers.Length; ++idx)
- {
- GetColumnGrouping().AddGroup(Suppliers[idx].Code, QuantityColumns[idx], CostColumns[idx]);
- }
- }
- private void LoadJobData(IEnumerable<Guid> ids)
- {
- var neededIDs = ids.Where(x => !JobDetails.ContainsKey(x)).ToArray();
- if(neededIDs.Length > 0)
- {
- var details = Client.Query(
- new Filter<Job>(x => x.ID).InList(neededIDs),
- new Columns<Job>(x => x.ID)
- .Add(x => x.JobNumber)
- .Add(x => x.Name));
- foreach(var job in details.ToObjects<Job>())
- {
- JobDetails[job.ID] = job;
- }
- }
- }
- private class QuantityControl : ContentControl
- {
- private readonly StockForecastOrderingItem Item;
- private readonly int SupplierIndex;
- private readonly StockForecastOrderingGrid Parent;
- public QuantityControl(StockForecastOrderingGrid parent, StockForecastOrderingItem item, int supplierIndex, StockForecastOrderingType mode)
- {
- Parent = parent;
- Item = item;
- SupplierIndex = supplierIndex;
- UpdateControl(mode);
- }
- public void UpdateControl(StockForecastOrderingType mode)
- {
- var supplierProduct = Parent.GetSupplierProduct(Item, Parent.Suppliers[SupplierIndex].ID);
- if(supplierProduct is null)
- {
- Content = null;
- return;
- }
- if(mode == StockForecastOrderingType.StockOrder)
- {
- var editor = new DoubleTextBox
- {
- VerticalAlignment = VerticalAlignment.Stretch,
- HorizontalAlignment = HorizontalAlignment.Stretch,
- Background = new SolidColorBrush(Colors.LightYellow),
- BorderThickness = new Thickness(0.0),
- MinValue = 0.0,
- Value = Item.GetQuantity(SupplierIndex).StockTotal
- };
- editor.ValueChanged += (o, e) =>
- {
- Item.GetQuantity(SupplierIndex).StockTotal = editor.Value ?? default;
- };
- Content = editor;
- }
- else if(mode == StockForecastOrderingType.JobOrder)
- {
- var grid = new Grid();
- grid.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) });
- grid.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(30) });
- var editor = new TextBox
- {
- VerticalAlignment = VerticalAlignment.Stretch,
- HorizontalAlignment = HorizontalAlignment.Stretch,
- VerticalContentAlignment = VerticalAlignment.Center,
- HorizontalContentAlignment = HorizontalAlignment.Center,
- Background = new SolidColorBrush(Colors.White),
- BorderThickness = new Thickness(0.0),
- IsReadOnly = true,
- Text = string.Format("{0:F2}", Item.GetQuantity(SupplierIndex).JobTotal)
- };
- Grid.SetColumn(editor, 0);
- grid.Children.Add(editor);
- var btn = new Button
- {
- VerticalAlignment = VerticalAlignment.Stretch,
- VerticalContentAlignment = VerticalAlignment.Center,
- HorizontalAlignment = HorizontalAlignment.Stretch,
- Content = "..",
- Margin = new Thickness(1),
- Focusable = false
- };
- btn.SetValue(Grid.ColumnProperty, 1);
- btn.SetValue(Grid.RowProperty, 0);
- btn.Click += (o, e) =>
- {
- var qty = Item.GetQuantity(SupplierIndex);
- Parent.LoadJobData(qty.JobTotals.Keys);
- var items = qty.JobTotals.Select(x =>
- {
- var item = new StockForecastOrderingJobItem
- {
- JobID = x.Key,
- RequiredQuantity = Item.GetJobRequiredQuantities().GetValueOrDefault(x.Key),
- Quantity = x.Value
- };
- if(item.JobID == Guid.Empty)
- {
- item.Job = "General Stock";
- }
- else if(Parent.JobDetails.TryGetValue(item.JobID, out var job))
- {
- item.Job = $"{job.JobNumber}: {job.Name}";
- }
- return item;
- }).ToList();
- var window = new StockForecastOrderJobScreen();
- window.Items = items;
- if(window.ShowDialog() == true)
- {
- foreach(var item in items)
- {
- qty.JobTotals[item.JobID] = item.Quantity;
- }
- qty.DoChanged();
- editor.Text = string.Format("{0:F2}", Item.GetQuantity(SupplierIndex).JobTotal);
- }
- };
- grid.Children.Add(btn);
- Content = grid;
- }
- }
- }
- private List<QuantityControl> QuantityControls = [];
- private void InitialiseSupplierColumn(int idx)
- {
- var supplierProducts = SupplierProducts.Where(x => x.SupplierLink.ID == Suppliers[idx].ID).ToArray();
- var contextMenuFunc = (CoreRow[]? rows) =>
- {
- var row = rows?.FirstOrDefault();
- if (row is null) return null;
- var item = LoadItem(row);
- var supplierProduct = GetSupplierProduct(item, Suppliers[idx].ID);
- if (supplierProduct is not null)
- {
- return null;
- }
- var menu = new ContextMenu();
- menu.AddItem("Create Supplier Product", null, new Tuple<StockForecastOrderingItem, int>(item, idx), CreateSupplierProduct_Click);
- return menu;
- };
- // Making local copy of index so that the lambda can use it, and not the changed value of 'i'.
- var qtyColumn = new Tuple<DynamicActionColumn, QuantityControl?>(null!, null);
- QuantityColumns[idx] = new DynamicTemplateColumn(row =>
- {
- var instance = LoadItem(row);
- var control = new QuantityControl(this, instance, idx, OrderType);
- QuantityControls.Add(control);
- return control;
- })
- {
- HeaderText = "Qty.",
- Width = 80,
- ContextMenu = contextMenuFunc
- };
- CostColumns[idx] = new DynamicTextColumn(row =>
- {
- if(row is null)
- {
- return "Cost";
- }
- var instance = LoadItem(row);
- var qty = OrderType == StockForecastOrderingType.StockOrder
- ? instance.GetQuantity(idx).StockTotal
- : instance.GetQuantity(idx).JobTotal;
- var supplierProduct = GetSupplierProduct(instance, Suppliers[idx].ID);
- if(supplierProduct is not null)
- {
- return $"{qty * supplierProduct.CostPrice:C2}";
- }
- else
- {
- return "";
- }
- })
- {
- HeaderText = "Cost",
- Width = 80,
- ContextMenu = contextMenuFunc,
- GetSummary = () =>
- {
- var i = idx * 2 + 1;
- var summary = new GridSummaryColumn
- {
- Format = "{Sum:C2}",
- SummaryType = Syncfusion.Data.SummaryType.Custom,
- CustomAggregate = new CostAggregate(idx, this)
- };
- return summary;
- }
- };
- ActionColumns.Add(QuantityColumns[idx]);
- ActionColumns.Add(CostColumns[idx]);
- }
- private void CreateSupplierProduct_Click(Tuple<StockForecastOrderingItem, int> tuple)
- {
- var (item, supplierIdx) = tuple;
- var supplierProduct = new SupplierProduct();
- supplierProduct.Product.CopyFrom(item.Product);
- supplierProduct.Style.CopyFrom(item.Style);
- supplierProduct.Dimensions.CopyFrom(item.Dimensions);
- supplierProduct.SupplierLink.CopyFrom(Suppliers[supplierIdx]);
- if (DynamicGridUtils.EditEntity(supplierProduct, customiseGrid: EditSupplierProductGrid))
- {
- SupplierProducts.Add(supplierProduct);
- InvalidateGrid();
- }
- }
- private static bool Matches(StockForecastOrderingItem item, SupplierProduct supplierProduct)
- {
- return item.Product.ID == supplierProduct.Product.ID
- && item.Style.ID == supplierProduct.Style.ID
- && item.Dimensions.Equals(supplierProduct.Dimensions);
- }
- private static bool Matches(ProductInstance instance, SupplierProduct supplierProduct)
- {
- return instance.Product.ID == supplierProduct.Product.ID
- && instance.Style.ID == supplierProduct.Style.ID
- && instance.Dimensions.Equals(supplierProduct.Dimensions);
- }
- private SupplierProduct? GetSupplierProduct(StockForecastOrderingItem item)
- {
- var defaultSupplierProduct = SupplierProducts.FirstOrDefault(x => x.ID == item.Product.Supplier.ID);
- if(defaultSupplierProduct is not null && Matches(item, defaultSupplierProduct))
- {
- return defaultSupplierProduct;
- }
- else
- {
- return SupplierProducts.FirstOrDefault(x => Matches(item, x));
- }
- }
- private SupplierProduct? GetSupplierProduct(ProductInstance instance, Guid supplierID)
- {
- return SupplierProducts.FirstOrDefault(x => x.SupplierLink.ID == supplierID && Matches(instance, x));
- }
- private SupplierProduct? GetSupplierProduct(StockForecastOrderingItem item, Guid supplierID)
- {
- return SupplierProducts.FirstOrDefault(x => x.SupplierLink.ID == supplierID && Matches(item, x));
- }
- //private double GetQuantity(SupplierProduct product)
- //{
- // var instance = ProductInstances.WithIndex().Where(x => x.Value.Product.ID == product.ID)
- //}
- private class CostAggregate : ISummaryAggregate
- {
- public double Sum { get; private set; }
- private int SupplierIndex;
- private StockForecastOrderingGrid Grid;
- public CostAggregate(int supplierIndex, StockForecastOrderingGrid grid)
- {
- SupplierIndex = supplierIndex;
- Grid = grid;
- }
- public Action<IEnumerable, string, PropertyDescriptor> CalculateAggregateFunc()
- {
- return AggregateFunc;
- }
- private void AggregateFunc(IEnumerable items, string property, PropertyDescriptor args)
- {
- if (items is IEnumerable<DataRowView> rows)
- {
- Sum = 0;
- foreach (var dataRow in rows)
- {
- var rowIdx = dataRow.Row.Table.Rows.IndexOf(dataRow.Row);
- var item = Grid.LoadItem(Grid.Data.Rows[rowIdx]);
- var supplierProduct = Grid.GetSupplierProduct(item, Grid.Suppliers[SupplierIndex].ID);
- if(supplierProduct is not null)
- {
- var qty = item.GetQuantity(SupplierIndex);
- Sum += qty.GetTotal(Grid.OrderType) * supplierProduct.CostPrice;
- }
- }
- }
- else
- {
- Logger.Send(LogType.Error, "", $"Attempting to calculate aggregate on invalid data type '{items.GetType()}'.");
- }
- }
- }
- }
|