JobRequisitionReviewGrid.cs 29 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647
  1. using Comal.Classes;
  2. using InABox.Clients;
  3. using InABox.Configuration;
  4. using InABox.Core;
  5. using InABox.DynamicGrid;
  6. using InABox.WPF;
  7. using System;
  8. using System.Collections.Generic;
  9. using System.Drawing;
  10. using System.Linq;
  11. using System.Windows;
  12. using System.Windows.Controls;
  13. namespace PRSDesktop
  14. {
  15. public class JobRequisitionReviewUserSettings : IUserConfigurationSettings
  16. {
  17. public DynamicGridFilter Filter { get; set; }
  18. public JobRequisitionReviewUserSettings()
  19. {
  20. Filter = new DynamicGridFilter();
  21. }
  22. }
  23. public delegate void JobRequiItemSelect(CoreRow[] rows);
  24. public delegate void GridRefresh();
  25. public class JobRequisitionReviewGrid : DynamicDataGrid<JobRequisitionItem>
  26. {
  27. public event JobRequiItemSelect OnJobRequiItemSelected;
  28. public event GridRefresh OnGridRefresh;
  29. public Guid empID = new Guid();
  30. string empName = "";
  31. JobRequisitionReviewUserSettings FilterSettings = new JobRequisitionReviewUserSettings();
  32. Dictionary<Guid, double> JobRequisReservedQty = new Dictionary<Guid, double>();
  33. public JobRequisitionReviewGrid()
  34. {
  35. FilterSettings = new UserConfiguration<JobRequisitionReviewUserSettings>().Load();
  36. if (!string.IsNullOrWhiteSpace(FilterSettings.Filter.Name))
  37. {
  38. SelectedFilter = new(FilterSettings.Filter.Name, Serialization.Deserialize<Filter<JobRequisitionItem>>(FilterSettings.Filter.Filter));
  39. UpdateFilterButton(InABox.Wpf.Resources.filter_set, FilterSettings.Filter.Name);
  40. }
  41. Options.AddRange(
  42. DynamicGridOption.FilterRows,
  43. DynamicGridOption.SelectColumns,
  44. DynamicGridOption.RecordCount
  45. );
  46. Options.Remove(DynamicGridOption.AddRows);
  47. Options.Remove(DynamicGridOption.ImportData);
  48. Options.Remove(DynamicGridOption.ExportData);
  49. Options.Remove(DynamicGridOption.Print);
  50. Options.Remove(DynamicGridOption.ShowHelp);
  51. HiddenColumns.Add(x => x.ID);
  52. HiddenColumns.Add(x => x.Product.ID);
  53. HiddenColumns.Add(x => x.Product.Code);
  54. HiddenColumns.Add(x => x.Product.Group.ID);
  55. HiddenColumns.Add(x => x.Product.Group.Code);
  56. HiddenColumns.Add(x => x.Product.Group.Description);
  57. HiddenColumns.Add(x => x.Style.ID);
  58. HiddenColumns.Add(x => x.Style.Code);
  59. HiddenColumns.Add(x => x.Style.Description);
  60. HiddenColumns.Add(x => x.Requisition.ID);
  61. HiddenColumns.Add(x => x.Requisition.Job.ID);
  62. HiddenColumns.Add(x => x.Requisition.Job.JobNumber);
  63. HiddenColumns.Add(x => x.Requisition.Job.Name);
  64. HiddenColumns.Add(x => x.Requisition.Number);
  65. HiddenColumns.Add(x => x.PurchaseOrderItem.ID);
  66. HiddenColumns.Add(x => x.PurchaseOrderItem.PurchaseOrderLink.ID);
  67. HiddenColumns.Add(x => x.PurchaseOrderItem.PurchaseOrderLink.PONumber);
  68. HiddenColumns.Add(x => x.PurchaseOrderItem.DueDate);
  69. HiddenColumns.Add(x => x.Job.ID);
  70. HiddenColumns.Add(x => x.Job.Name);
  71. HiddenColumns.Add(x => x.Job.JobNumber);
  72. HiddenColumns.Add(x => x.Dimensions.UnitSize);
  73. HiddenColumns.Add(x => x.Dimensions.Length);
  74. HiddenColumns.Add(x => x.Dimensions.Width);
  75. HiddenColumns.Add(x => x.Dimensions.Height);
  76. HiddenColumns.Add(x => x.Dimensions.Weight);
  77. HiddenColumns.Add(x => x.Dimensions.Quantity);
  78. HiddenColumns.Add(x => x.Dimensions.Value);
  79. HiddenColumns.Add(x => x.Dimensions.Unit.ID);
  80. HiddenColumns.Add(x => x.Dimensions.Unit.HasLength);
  81. HiddenColumns.Add(x => x.Dimensions.Unit.HasHeight);
  82. HiddenColumns.Add(x => x.Dimensions.Unit.HasWidth);
  83. HiddenColumns.Add(x => x.Dimensions.Unit.HasWeight);
  84. HiddenColumns.Add(x => x.Dimensions.Unit.HasQuantity);
  85. HiddenColumns.Add(x => x.Dimensions.Unit.Formula);
  86. HiddenColumns.Add(x => x.Dimensions.Unit.Format);
  87. HiddenColumns.Add(x => x.Dimensions.Unit.Code);
  88. HiddenColumns.Add(x => x.Dimensions.Unit.Description);
  89. LoadStockMovements();
  90. if (Security.CanEdit<JobRequisitionItem>())
  91. ActionColumns.Add(new DynamicMenuColumn(BuildMenu));
  92. OnSelectItem += JobRequisitionReviewGrid_OnSelectItem;
  93. ColumnsTag = "JobRequisitionReview";
  94. CoreTable table = new Client<Employee>().Query(new Filter<Employee>(x => x.UserLink.UserID).IsEqualTo(ClientFactory.UserID), new Columns<Employee>(x => x.ID, x => x.Name));
  95. if (table.Rows.Any())
  96. {
  97. empID = Guid.Parse(table.Rows.FirstOrDefault().Values[0].ToString());
  98. empName = table.Rows.FirstOrDefault().Values[1].ToString();
  99. }
  100. OnFilterSelected += GridOnFilterSelected;
  101. //Migrate();
  102. }
  103. private bool GridOnFilterSelected(DynamicGridFilter filter)
  104. {
  105. new UserConfiguration<JobRequisitionReviewUserSettings>().Save(new JobRequisitionReviewUserSettings { Filter = filter });
  106. OnGridRefresh?.Invoke();
  107. return true;
  108. }
  109. private void Migrate()
  110. {
  111. CoreTable table = new Client<JobRequisitionItem>().Query(null, new Columns<JobRequisitionItem>(x => x.ID, x => x.PurchaseOrderItem.PurchaseOrderLink.ID));
  112. Dictionary<Guid, Guid> reqPOids = new Dictionary<Guid, Guid>();
  113. List<JobRequisitionItem> affected = new List<JobRequisitionItem>();
  114. foreach (CoreRow row in table.Rows)
  115. {
  116. var item = row.ToObject<JobRequisitionItem>();
  117. if (item.PurchaseOrderItem.PurchaseOrderLink.ID != Guid.Empty)
  118. {
  119. reqPOids.Add(row.Get<JobRequisitionItem, Guid>(x => x.ID), item.PurchaseOrderItem.PurchaseOrderLink.ID);
  120. affected.Add(row.ToObject<JobRequisitionItem>());
  121. }
  122. }
  123. List<JobRequisitionItem> list = new List<JobRequisitionItem>();
  124. CoreTable POs = new Client<PurchaseOrder>().Query(new Filter<PurchaseOrder>(x => x.ID).InList(reqPOids.Values.ToArray()), new Columns<PurchaseOrder>(x => x.ID, x => x.Created));
  125. foreach (CoreRow row in POs.Rows)
  126. {
  127. var items = affected.Where(x => x.PurchaseOrderItem.PurchaseOrderLink.ID == row.Get<PurchaseOrder, Guid>(x => x.ID));
  128. foreach (var item in items)
  129. {
  130. item.Ordered = row.Get<PurchaseOrder, DateTime>(x => x.Created);
  131. list.Add(item);
  132. }
  133. }
  134. new Client<JobRequisitionItem>().Save(list, "Migrate");
  135. }
  136. private void LoadStockMovements()
  137. {
  138. CoreTable table = new Client<StockMovement>().Query(
  139. new Filter<StockMovement>(x => x.JobRequisitionItem.ID).IsNotEqualTo(Guid.Empty),
  140. new Columns<StockMovement>(
  141. x => x.JobRequisitionItem.ID,
  142. x => x.Received
  143. )
  144. );
  145. foreach (CoreRow row in table.Rows)
  146. {
  147. var requiID = row.Get<StockMovement, Guid>(x => x.JobRequisitionItem.ID);
  148. var qty = row.Get<StockMovement, double>(x => x.Received);
  149. if (!JobRequisReservedQty.ContainsKey(requiID))
  150. JobRequisReservedQty.Add(requiID, qty);
  151. else
  152. {
  153. double newQty = JobRequisReservedQty[requiID] + qty;
  154. JobRequisReservedQty.Remove(requiID);
  155. JobRequisReservedQty.Add(requiID, newQty);
  156. }
  157. }
  158. }
  159. public void AddStockMovements(Guid requiItemID)
  160. {
  161. CoreTable table = new Client<StockMovement>().Query(new Filter<StockMovement>(x => x.JobRequisitionItem.ID).IsEqualTo(requiItemID),
  162. new Columns<StockMovement>(
  163. x => x.JobRequisitionItem.ID,
  164. x => x.Received
  165. )
  166. );
  167. if (table.Rows.Any())
  168. {
  169. foreach (CoreRow row in table.Rows)
  170. {
  171. var requiID = row.Get<StockMovement, Guid>(x => x.JobRequisitionItem.ID);
  172. var qty = row.Get<StockMovement, double>(x => x.Received);
  173. if (!JobRequisReservedQty.ContainsKey(requiID))
  174. JobRequisReservedQty.Add(requiID, qty);
  175. else if (JobRequisReservedQty.ContainsKey(requiID) && row == table.Rows.First())
  176. {
  177. JobRequisReservedQty.Remove(requiID);
  178. JobRequisReservedQty.Add(requiID, qty);
  179. }
  180. else
  181. {
  182. double newQty = JobRequisReservedQty[requiID] + qty;
  183. JobRequisReservedQty.Remove(requiID);
  184. JobRequisReservedQty.Add(requiID, newQty);
  185. }
  186. }
  187. }
  188. }
  189. private string? CreateStatus(CoreRow? row)
  190. {
  191. Guid id = row.Get<JobRequisitionItem, Guid>(x => x.ID);
  192. string status = "Not Checked";
  193. if (row.Get<JobRequisitionItem, DateTime>(x => x.Cancelled) != DateTime.MinValue)
  194. return "Cancelled";
  195. if (row.Get<JobRequisitionItem, DateTime>(x => x.Archived) != DateTime.MinValue)
  196. return "Archived";
  197. if (row.Get<JobRequisitionItem, DateTime>(x => x.Ordered) != DateTime.MinValue && !JobRequisReservedQty.ContainsKey(id))
  198. return "On Order";
  199. if (row.Get<JobRequisitionItem, JobRequisitionItemStatus>(x => x.Status) == JobRequisitionItemStatus.OrderRequired)
  200. return "Order Required";
  201. if (JobRequisReservedQty.ContainsKey(id))
  202. if (JobRequisReservedQty[id] >= row.Get<JobRequisitionItem, double>(x => x.Qty))
  203. return "Reserved";
  204. return status;
  205. }
  206. protected override DynamicGridStyle GetRowStyle(CoreRow row, DynamicGridStyle style)
  207. {
  208. var result = base.GetRowStyle(row, style);
  209. //var item = row.ToObject<JobRequisitionItem>();
  210. //if (item.Status == JobRequisitionItemStatus.NotChecked)
  211. //{
  212. // var rowstyle = new DynamicGridRowStyle();
  213. // rowstyle.Background = new SolidColorBrush(Colors.LightSalmon);
  214. // return rowstyle;
  215. //}
  216. //if (item.Status == JobRequisitionItemStatus.OrderRequired)
  217. //{
  218. // var rowstyle = new DynamicGridRowStyle();
  219. // rowstyle.Background = new SolidColorBrush(Colors.LightCoral);
  220. // return rowstyle;
  221. //}
  222. return result;
  223. }
  224. private void JobRequisitionReviewGrid_OnSelectItem(object sender, DynamicGridSelectionEventArgs e)
  225. {
  226. OnJobRequiItemSelected?.Invoke(SelectedRows);
  227. }
  228. private bool CreateTreatmentPO(Button button, CoreRow[] rows)
  229. {
  230. return true;
  231. }
  232. protected override void GenerateColumns(DynamicGridColumns columns)
  233. {
  234. columns.Add<JobRequisitionItem, DateTime>(x => x.Created, 80, "Date", "", Alignment.MiddleLeft);
  235. columns.Add<JobRequisitionItem, string>(x => x.Requisition.Job.JobNumber, 70, "Job", "", Alignment.MiddleLeft);
  236. columns.Add<JobRequisitionItem, int>(x => x.Requisition.Number, 50, "NO.", "", Alignment.MiddleLeft);
  237. columns.Add<JobRequisitionItem, string>(x => x.Product.Code, 70, "Code", "", Alignment.MiddleLeft);
  238. columns.Add<JobRequisitionItem, string>(x => x.Product.Name, 200, "Product Name", "", Alignment.MiddleLeft);
  239. columns.Add<JobRequisitionItem, string>(x => x.Style.Description, 150, "Style", "", Alignment.MiddleLeft);
  240. columns.Add<JobRequisitionItem, double>(x => x.Qty, 50, "Qty", "", Alignment.MiddleLeft);
  241. columns.Add<JobRequisitionItem, string>(x => x.Dimensions.UnitSize, 50, "Size", "", Alignment.MiddleLeft);
  242. columns.Add<JobRequisitionItem, string>(x => x.PurchaseOrderItem.PurchaseOrderLink.PONumber, 80, "PO Number", "", Alignment.MiddleLeft);
  243. columns.Add<JobRequisitionItem, string>(x => x.PurchaseOrderItem.PONumber, 80, "PO Number", "", Alignment.MiddleLeft);
  244. columns.Add<JobRequisitionItem, DateTime>(x => x.PurchaseOrderItem.DueDate, 80, "Due", "", Alignment.MiddleLeft);
  245. columns.Add<JobRequisitionItem, DateTime>(x => x.PurchaseOrderItem.ReceivedDate, 80, "Received", "", Alignment.MiddleLeft);
  246. columns.Add<JobRequisitionItem, string>(x => x.Notes, 300, "Notes", "", Alignment.MiddleLeft);
  247. }
  248. private DynamicMenuStatus EmptyReturnFunction(CoreRow row)
  249. {
  250. return DynamicMenuStatus.Enabled;
  251. }
  252. #region Action Column Buttons
  253. private bool CheckValidAction(JobRequisitionItem item, bool bypassReserved)
  254. {
  255. bool valid = true;
  256. if (item.Status == JobRequisitionItemStatus.Allocated && !bypassReserved)
  257. {
  258. MessageBox.Show("Error. Item has already been reserved!");
  259. return false;
  260. }
  261. else if (item.Status == JobRequisitionItemStatus.OnOrder)
  262. {
  263. MessageBox.Show("Error. Item is already on order!");
  264. return false;
  265. }
  266. if (item.Status == JobRequisitionItemStatus.Received)
  267. {
  268. MessageBox.Show("Error. Item has already been recieved!");
  269. return false;
  270. }
  271. return valid;
  272. }
  273. private void MarkReserved_Clicked(CoreRow? row)
  274. {
  275. JobRequisitionItem item = row.ToObject<JobRequisitionItem>();
  276. if (CheckValidAction(item, false))
  277. {
  278. SaveRow(row, JobRequisitionItemStatus.Allocated, "Line marked as Reserved by " + empName + " on " + DateTime.Now.ToString("dd MMM yy"));
  279. }
  280. }
  281. private void SplitLine(JobRequisitionItem item, double oldItemQty, double newItemQty, string notes)
  282. {
  283. List<JobRequisitionItem> items = new List<JobRequisitionItem>();
  284. JobRequisitionItem newItem = new JobRequisitionItem();
  285. newItem.Requisition.ID = item.Requisition.ID;
  286. newItem.Requisition.Job.ID = item.Requisition.Job.ID;
  287. newItem.Requisition.Job.JobNumber = item.Requisition.Job.JobNumber;
  288. newItem.Requisition.Job.Name = item.Requisition.Job.Name;
  289. newItem.Product.ID = item.Product.ID;
  290. newItem.Product.Name = item.Product.Name;
  291. newItem.Product.Code = item.Product.Code;
  292. newItem.Product.Group.ID = item.Product.Group.ID;
  293. newItem.Product.Group.Description = item.Product.Group.Description;
  294. newItem.Dimensions.CopyFrom(item.Dimensions);
  295. newItem.Style.ID = item.Style.ID;
  296. newItem.Style.Description = item.Style.Description;
  297. newItem.Style.Code = item.Style.Code;
  298. newItem.Notes = item.Notes + Environment.NewLine + notes;
  299. item.Notes = newItem.Notes;
  300. item.Qty = oldItemQty;
  301. newItem.Qty = newItemQty;
  302. items.Add(newItem);
  303. items.Add(item);
  304. new Client<JobRequisitionItem>().Save(items, "Split lines from Job Requi Item Review Dashboard");
  305. MessageBox.Show("Line split - original line Qty is now " + item.Qty + ". New line Qty is " + newItem.Qty, "Success");
  306. OnGridRefresh?.Invoke();
  307. }
  308. private void SplitLine_Clicked(CoreRow row)
  309. {
  310. JobRequisitionItem item = row.ToObject<JobRequisitionItem>();
  311. if (CheckValidAction(item, false))
  312. {
  313. int units = Convert.ToInt32(item.Qty);
  314. if (NumberEdit.Execute("Enter amount to split", 1, units, ref units))
  315. {
  316. SplitLine(item, item.Qty - units, units, "Line split");
  317. }
  318. }
  319. }
  320. private void Archive_Clicked(CoreRow row)
  321. {
  322. JobRequisitionItem item = row.ToObject<JobRequisitionItem>();
  323. item.Archived = DateTime.Now;
  324. SaveRow(row, JobRequisitionItemStatus.Archived, "Line marked as Archived by " + empName + " on " + DateTime.Now.ToString("dd MMM yy"));
  325. }
  326. private void OrderRequired_Clicked(CoreRow row)
  327. {
  328. JobRequisitionItem item = row.ToObject<JobRequisitionItem>();
  329. if (CheckValidAction(item, false))
  330. SaveRow(row, JobRequisitionItemStatus.OrderRequired, "Line marked as Order Required by " + empName + " on " + DateTime.Now.ToString("dd MMM yy"));
  331. }
  332. private void TreatmentRequired_Clicked(CoreRow row)
  333. {
  334. JobRequisitionItem item = row.ToObject<JobRequisitionItem>();
  335. if (item.Status != JobRequisitionItemStatus.Allocated)
  336. {
  337. MessageBox.Show("Stock must first be reserved for this item");
  338. return;
  339. }
  340. SaveRow(row, JobRequisitionItemStatus.TreatmentRequired, "Line marked as Treatment Required by " + empName + " on " + DateTime.Now.ToString("dd MMM yy"));
  341. }
  342. private void Uncheck_Clicked(CoreRow row)
  343. {
  344. string extraMessage = "";
  345. JobRequisitionItem item = row.ToObject<JobRequisitionItem>();
  346. if (!CheckValidAction(item, true))
  347. return;
  348. CoreTable table = new Client<StockMovement>().Query
  349. (
  350. new Filter<StockMovement>(x => x.JobRequisitionItem.ID).IsEqualTo(item.ID),
  351. new Columns<StockMovement>(x => x.ID)
  352. );
  353. if (table.Rows.Any())
  354. {
  355. var result = MessageBox.Show("This will reverse stock movements already created for this Requisition Item. Proceed?", "Alert", MessageBoxButton.YesNo);
  356. switch (result)
  357. {
  358. case MessageBoxResult.Yes:
  359. break;
  360. case MessageBoxResult.No:
  361. return;
  362. default:
  363. return;
  364. }
  365. List<StockMovement> movements = new List<StockMovement>();
  366. foreach (CoreRow stockmovementRow in table.Rows)
  367. {
  368. StockMovement movement = new StockMovement();
  369. movement.ID = Guid.Parse(stockmovementRow.Values[0].ToString());
  370. movements.Add(movement);
  371. }
  372. new Client<StockMovement>().Delete(movements, "Stock movements reversed from Job Requisition Item Review Dashboard");
  373. extraMessage = " and Stock Movements Reversed ";
  374. }
  375. SaveRow(row, JobRequisitionItemStatus.NotChecked, "Line marked as Not Checked by " + empName + extraMessage + " on " + DateTime.Now.ToString("dd MMM yy"));
  376. }
  377. private bool CreatePurchaseOrder(Button btn, CoreRow[] rows)
  378. {
  379. if (!rows.Any())
  380. {
  381. MessageBox.Show("Please select at least one row to add to Purchase Order!");
  382. return false;
  383. }
  384. PurchaseOrder purchaseOrder = new PurchaseOrder();
  385. purchaseOrder.Notes = "Created from Job Requi Item Review Screen" + System.Environment.NewLine;
  386. purchaseOrder.RaisedBy.ID = empID;
  387. var page = new SupplierPurchaseOrders();
  388. page.OnAfterSave += (form, items) =>
  389. {
  390. PurchaseOrderOnSave(form, items.Cast<PurchaseOrder>().ToArray());
  391. };
  392. return page.EditItems(new[] { purchaseOrder }, LoadPurchaseOrderItems, true);
  393. }
  394. private void PurchaseOrderOnSave(IDynamicEditorForm form, PurchaseOrder[] items)
  395. {
  396. Progress.Show("Working");
  397. Guid POID = items[0].ID;
  398. CoreTable table = new Client<PurchaseOrderItem>().Query(new Filter<PurchaseOrderItem>(x => x.PurchaseOrderLink.ID).IsEqualTo(POID),
  399. new Columns<PurchaseOrderItem>(x => x.ID, x => x.Product.ID, x => x.Qty, x => x.Dimensions.UnitSize, x => x.DueDate, x => x.Job.ID));
  400. if (table.Rows.Any())
  401. {
  402. var poItems = AddPOItems(table, new List<PurchaseOrderItem>());
  403. var requiItems = MatchRequiItems(poItems, new List<JobRequisitionItem>());
  404. if (requiItems.Count > 0)
  405. SaveAndRefreshScreen(requiItems);
  406. }
  407. Progress.Close();
  408. }
  409. private void SaveAndRefreshScreen(List<JobRequisitionItem> requiItems)
  410. {
  411. new Client<JobRequisitionItem>().Save(requiItems, "Updated on Create Purchase Order from Job Requi Dashboard");
  412. OnGridRefresh?.Invoke();
  413. }
  414. private List<PurchaseOrderItem> AddPOItems(CoreTable table, List<PurchaseOrderItem> poItems)
  415. {
  416. foreach (CoreRow row in table.Rows)
  417. {
  418. PurchaseOrderItem poItem = row.ToObject<PurchaseOrderItem>();
  419. poItems.Add(poItem);
  420. }
  421. return poItems;
  422. }
  423. private List<JobRequisitionItem> MatchRequiItems(List<PurchaseOrderItem> poItems, List<JobRequisitionItem> requiItems)
  424. {
  425. foreach (CoreRow row in SelectedRows)
  426. {
  427. JobRequisitionItem JobReqItem = row.ToObject<JobRequisitionItem>();
  428. foreach (var item in poItems)
  429. {
  430. if (string.IsNullOrWhiteSpace(JobReqItem.Dimensions.UnitSize))
  431. JobReqItem.Dimensions.UnitSize = QueryUnitSize(JobReqItem.Product.ID);
  432. if (string.IsNullOrWhiteSpace(item.Dimensions.UnitSize))
  433. item.Dimensions.UnitSize = QueryUnitSize(item.Product.ID);
  434. if (JobReqItem.Job.ID == Guid.Empty)
  435. JobReqItem.Job.ID = QueryJobID(JobReqItem.Requisition.ID);
  436. if (item.Job.ID == Guid.Empty)
  437. item.Job.ID = QueryJobID(JobReqItem.Requisition.ID);
  438. if (MatchReqItemToPOItem(JobReqItem, item))
  439. requiItems.Add(UpdateJobReqItemWithPODetails(JobReqItem, item));
  440. }
  441. }
  442. return requiItems;
  443. }
  444. private JobRequisitionItem UpdateJobReqItemWithPODetails(JobRequisitionItem JobReqItem, PurchaseOrderItem poItem)
  445. {
  446. JobReqItem.PurchaseOrderItem.ID = poItem.ID;
  447. JobReqItem.PurchaseOrderItem.DueDate = poItem.DueDate;
  448. if (JobReqItem.Status != JobRequisitionItemStatus.OnOrder)
  449. {
  450. JobReqItem.Notes = JobReqItem.Notes + Environment.NewLine + "Line marked as On Order by " + empName + " on " + DateTime.Now.ToString("dd MMM yy");
  451. JobReqItem.Ordered = poItem.Created;
  452. }
  453. return JobReqItem;
  454. }
  455. private bool MatchReqItemToPOItem(JobRequisitionItem JobReqItem, PurchaseOrderItem item)
  456. {
  457. if (JobReqItem.Product.ID == item.Product.ID &&
  458. JobReqItem.Dimensions.UnitSize == item.Dimensions.UnitSize &&
  459. JobReqItem.Job.ID == item.Job.ID)
  460. return true;
  461. else
  462. return false;
  463. }
  464. private string QueryUnitSize(Guid productID)
  465. {
  466. CoreTable table = new Client<Product>().Query(new Filter<Product>(x => x.ID).IsEqualTo(productID),
  467. new Columns<Product>(x => x.Dimensions.UnitSize));
  468. return table.Rows.FirstOrDefault().Get<string>("Dimensions.UnitSize");
  469. }
  470. private Guid QueryJobID(Guid iD)
  471. {
  472. CoreTable table = new Client<JobRequisition>().Query(new Filter<JobRequisition>(x => x.ID).IsEqualTo(iD),
  473. new Columns<JobRequisition>(x => x.Job.ID));
  474. return table.Rows.FirstOrDefault().Get<Guid>("Job.ID");
  475. }
  476. private CoreTable LoadPurchaseOrderItems(Type arg)
  477. {
  478. Progress.Show("Working");
  479. var result = new CoreTable();
  480. result.LoadColumns(typeof(PurchaseOrderItem));
  481. List<PurchaseOrderItem> items = new List<PurchaseOrderItem>();
  482. foreach (CoreRow row in SelectedRows)
  483. {
  484. JobRequisitionItem JobReqItem = row.ToObject<JobRequisitionItem>();
  485. PurchaseOrderItem POItem = new PurchaseOrderItem();
  486. POItem.Product.ID = JobReqItem.Product.ID;
  487. POItem.Product.Code = JobReqItem.Product.Code;
  488. POItem.Product.Name = JobReqItem.Product.Name;
  489. POItem.Description = JobReqItem.Product.Name;
  490. POItem.Qty = JobReqItem.Qty;
  491. POItem.Dimensions.CopyFrom(JobReqItem.Dimensions);
  492. POItem.Style.ID = JobReqItem.Style.ID;
  493. POItem.Style.Code = JobReqItem.Style.Code;
  494. POItem.Style.Description = JobReqItem.Style.Description;
  495. POItem.Job.ID = JobReqItem.Requisition.Job.ID;
  496. POItem.Dimensions.UnitSize = JobReqItem.Dimensions.UnitSize;
  497. items.Add(POItem);
  498. }
  499. result.LoadRows(items);
  500. Progress.Close();
  501. return result;
  502. }
  503. #endregion
  504. #region Utils
  505. private void SaveRow(CoreRow row, JobRequisitionItemStatus status, string note)
  506. {
  507. if (row == null)
  508. return;
  509. var id = row.Get<JobRequisitionItem, Guid>(c => c.ID);
  510. JobRequisitionItem item = Data.Rows.Where(r => r.Get<JobRequisitionItem, Guid>(c => c.ID).Equals(id)).FirstOrDefault().ToObject<JobRequisitionItem>();
  511. item.Status = status;
  512. item.Notes = item.Notes + Environment.NewLine + note;
  513. new Client<JobRequisitionItem>().Save(item, "Updated From Job Requisition Review Dashboard");
  514. OnGridRefresh?.Invoke();
  515. }
  516. private void SaveItem(JobRequisitionItem item, JobRequisitionItemStatus status, string note)
  517. {
  518. item.Status = status;
  519. item.Notes = item.Notes + Environment.NewLine + note;
  520. new Client<JobRequisitionItem>().Save(item, "Updated From Job Requisition Review Dashboard");
  521. OnGridRefresh?.Invoke();
  522. }
  523. private void MultiSaveRows(CoreRow[] rows, JobRequisitionItemStatus status, string note)
  524. {
  525. List<JobRequisitionItem> items = new List<JobRequisitionItem>();
  526. foreach (CoreRow row in rows)
  527. {
  528. var id = row.Get<JobRequisitionItem, Guid>(c => c.ID);
  529. JobRequisitionItem item = Data.Rows.Where(r => r.Get<JobRequisitionItem, Guid>(c => c.ID).Equals(id)).FirstOrDefault().ToObject<JobRequisitionItem>();
  530. item.Status = status;
  531. item.Notes = item.Notes + Environment.NewLine + note;
  532. items.Add(item);
  533. }
  534. new Client<JobRequisitionItem>().Save(items, "Updated From Job Requisition Review Dashboard");
  535. OnGridRefresh?.Invoke();
  536. }
  537. protected override void Reload(Filters<JobRequisitionItem> criteria, Columns<JobRequisitionItem> columns, ref SortOrder<JobRequisitionItem> sort,
  538. Action<CoreTable, Exception> action)
  539. {
  540. criteria.Add(new Filter<JobRequisitionItem>(x => x.Requisition.Approved).IsNotEqualTo(DateTime.MinValue));
  541. criteria.Add(new Filter<JobRequisitionItem>(x => x.Archived).IsEqualTo(DateTime.MinValue));
  542. sort = new SortOrder<JobRequisitionItem>(x => x.Requisition.Number, SortDirection.Descending);
  543. base.Reload(criteria, columns, ref sort, action);
  544. }
  545. private void BuildMenu(DynamicMenuColumn column, CoreRow row)
  546. {
  547. // column.AddItem("Treatment Required", PRSDesktop.Resources.palette, TreatmentRequired_Clicked);
  548. column.AddItem("Order Required", PRSDesktop.Resources.purchase, OrderRequired_Clicked);
  549. //column.AddItem("Mark as Not Checked", PRSDesktop.Resources.disabled, Uncheck_Clicked);
  550. column.AddItem("Split Line", PRSDesktop.Resources.split, SplitLine_Clicked);
  551. column.AddItem("Archive", PRSDesktop.Resources.archive, Archive_Clicked);
  552. }
  553. #endregion
  554. }
  555. public class JobRequiReviewDashboardFilterItem
  556. {
  557. public Guid SupplierID { get; set; }
  558. public Guid ProductID { get; set; }
  559. public string Text { get; set; }
  560. public JobRequiReviewDashboardFilterItem()
  561. {
  562. SupplierID = Guid.Empty;
  563. ProductID = Guid.Empty;
  564. Text = "";
  565. }
  566. }
  567. }