ProblemsDockGrid.cs 9.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287
  1. using System;
  2. using System.Collections.Generic;
  3. using System.Globalization;
  4. using System.Linq;
  5. using System.Windows.Controls;
  6. using System.Windows.Media.Imaging;
  7. using com.healthmarketscience.jackcess.query;
  8. using com.sun.istack.@internal.localization;
  9. using Comal.Classes;
  10. using InABox.Clients;
  11. using InABox.Core;
  12. using InABox.DynamicGrid;
  13. using InABox.Wpf;
  14. using InABox.WPF;
  15. namespace PRSDesktop;
  16. public class ProblemsDockGrid : DynamicDataGrid<Problems>
  17. {
  18. protected override void Init()
  19. {
  20. base.Init();
  21. HiddenColumns.Add(x=>x.Problem.Notes);
  22. HiddenColumns.Add(x=>x.Problem.AssignedTo.Code);
  23. ActionColumns.Add(new DynamicImageColumn(TypeImage)
  24. {
  25. Position = DynamicActionColumnPosition.Start,
  26. GetFilter = () => new StaticColumnFilter<Type?>(GetType, IMAGES.Keys.Select(x => new Tuple<string, Type?>(x.Name, x)).ToArray())
  27. });
  28. ActionColumns.Add(new DynamicTextColumn(GetLastNote) { Position = DynamicActionColumnPosition.End, Width = 0, HeaderText = "Issues" });
  29. ActionColumns.Add(new DynamicTextColumn(GetAssignedTo) { Position = DynamicActionColumnPosition.End, Width = 100, HeaderText="Assigned To", Alignment = Alignment.MiddleCenter});
  30. ActionColumns.Add(new DynamicMenuColumn(ProblemMenu) { Position = DynamicActionColumnPosition.End });
  31. AddEditButton("Add Note", PRSDesktop.Resources.notification.AsBitmapImage(), AddNote);
  32. AddEditButton("Assign To", PRSDesktop.Resources.employee.AsBitmapImage(), AssignTo);
  33. AddEditButton("Mark Resolved", InABox.Wpf.Resources.delete.AsBitmapImage(), MarkResolved, position: DynamicGridButtonPosition.Right);
  34. }
  35. private Type? GetType(CoreRow row)
  36. {
  37. var typeName = row.Get<Problems, string>(x => x.Type);
  38. return IMAGES.Keys.FirstOrDefault(x => x.Name == typeName);
  39. }
  40. private object? GetAssignedTo(CoreRow? row) => row?.Get<Problems, string>(x => x.Problem.AssignedTo.Code);
  41. private object? GetLastNote(CoreRow? row) => row?.Get<Problems, string[]>(x => x.Problem.Notes).LastOrDefault();
  42. protected override void DoReconfigure(DynamicGridOptions options)
  43. {
  44. base.DoReconfigure(options);
  45. options.FilterRows = true;
  46. options.MultiSelect = true;
  47. }
  48. protected override DynamicGridColumns LoadColumns()
  49. {
  50. var result = new DynamicGridColumns();
  51. result.Add<Problems>(x => x.Code, 150, "Code", "", Alignment.MiddleLeft);
  52. result.Add<Problems>(x => x.Description, 0, "Description", "", Alignment.MiddleLeft);
  53. return result;
  54. }
  55. private static readonly Dictionary<Type, BitmapImage?> IMAGES = new()
  56. {
  57. { typeof(Bill), PRSDesktop.Resources.bill.AsBitmapImage() },
  58. { typeof(Activity), PRSDesktop.Resources.assignments.AsBitmapImage() },
  59. { typeof(ProductStyle), PRSDesktop.Resources.palette.AsBitmapImage() },
  60. { typeof(Product), PRSDesktop.Resources.product.AsBitmapImage() },
  61. { typeof(CostSheet), PRSDesktop.Resources.costsheet.AsBitmapImage() },
  62. { typeof(Kit), PRSDesktop.Resources.kit.AsBitmapImage() },
  63. { typeof(JobBillOfMaterialsItem), PRSDesktop.Resources.box_sml.AsBitmapImage() },
  64. { typeof(JobRequisitionItem), PRSDesktop.Resources.requisition.AsBitmapImage() },
  65. { typeof(ManufacturingPacket), PRSDesktop.Resources.factory.AsBitmapImage() },
  66. };
  67. private BitmapImage? TypeImage(CoreRow? row)
  68. {
  69. var _type = row?.Get<Problems, string>(x => x.Type) ?? "";
  70. var _key = IMAGES.Keys.FirstOrDefault(x => string.Equals(x.Name.Split('.').Last(), _type));
  71. return _key != null
  72. ? IMAGES[_key]
  73. : null;
  74. }
  75. private string? TypeText(CoreRow? row)
  76. {
  77. return row?.Get<Problems, string>(x => x.Type) ?? "";
  78. }
  79. private void ProblemMenu(DynamicMenuColumn menu, CoreRow? row)
  80. {
  81. menu.AddItem("Add Note", null, AddNote);
  82. menu.AddItem("Assign To...", null, AssignTo);
  83. menu.AddSeparator();
  84. menu.AddItem("Edit Item", null, EditItem);
  85. menu.AddSeparator();
  86. menu.AddItem("Mark as Resolved", null, MarkResolved);
  87. }
  88. private IProblems<ManagedProblem>? GetItem(CoreRow? row)
  89. {
  90. if (row is null) return null;
  91. var _type = GetType(row);
  92. if (_type == null)
  93. return null;
  94. var _id = row.Get<Problems, Guid>(x => x.ID);
  95. var item = ClientFactory.CreateClient(_type).Query(
  96. Filter.Create(_type, "ID", Operator.IsEqualTo, _id),
  97. Columns.Local(_type),
  98. null
  99. ).Rows.FirstOrDefault()?.ToObject(_type) as IProblems<ManagedProblem>;
  100. return item;
  101. }
  102. private void AddNote(CoreRow[] rows)
  103. {
  104. var _items = rows.Select(GetItem).Where(x => x != null).ToArray();
  105. if (!_items.Any())
  106. return;
  107. var _note = "";
  108. if (TextBoxDialog.Execute("Add Problem Note", ref _note))
  109. {
  110. Dictionary<Type, List<IProblems<ManagedProblem>>> _updates = new();
  111. foreach (var _item in _items)
  112. {
  113. if (_item == null)
  114. continue;
  115. var _notes = _item.Problem.Notes?.ToList() ?? new List<string>();
  116. _notes.Add(_note);
  117. _item.Problem.Notes = _notes.ToArray();
  118. var _type = _item.GetType();
  119. if (!_updates.ContainsKey(_type))
  120. _updates[_type] = new List<IProblems<ManagedProblem>>();
  121. _updates[_type].Add(_item);
  122. }
  123. Progress.ShowModal("Adding Notes", progress =>
  124. {
  125. foreach (var _update in _updates)
  126. {
  127. progress.Report($"Adding note to {_update.Value.Count} {new Inflector.Inflector(new CultureInfo("en")).Pluralize(_update.Key.Name.Split('.').Last()).SplitCamelCase()}");
  128. ClientFactory.CreateClient(_update.Key).Save(_update.Value, "Added Isse note");
  129. }
  130. });
  131. Refresh(false, true);
  132. }
  133. }
  134. private bool AddNote(Button button, CoreRow[] rows)
  135. {
  136. AddNote(rows);
  137. return false;
  138. }
  139. private void AddNote(CoreRow? row)
  140. {
  141. if (row == null)
  142. return;
  143. AddNote([row]);
  144. }
  145. private void MarkResolved(CoreRow?[] rows)
  146. {
  147. var _items = rows.Select(GetItem).Where(x => x != null).ToArray();
  148. if (!_items.Any())
  149. return;
  150. Dictionary<Type, List<IProblems<ManagedProblem>>> _updates = new();
  151. foreach (var _item in _items)
  152. {
  153. if (_item == null)
  154. continue;
  155. _item.Problem.Resolved = DateTime.Now;
  156. var _type = _item.GetType();
  157. if (!_updates.ContainsKey(_type))
  158. _updates[_type] = new List<IProblems<ManagedProblem>>();
  159. _updates[_type].Add(_item);
  160. }
  161. Progress.ShowModal("Resolving items", progress =>
  162. {
  163. foreach (var _update in _updates)
  164. {
  165. progress.Report($"Resolving {_update.Value.Count} {new Inflector.Inflector(new CultureInfo("en")).Pluralize(_update.Key.Name.Split('.').Last()).SplitCamelCase()}");
  166. ClientFactory.CreateClient(_update.Key).Save(_update.Value, "Issue marked as resolved");
  167. }
  168. });
  169. Refresh(false, true);
  170. }
  171. private void MarkResolved(CoreRow? row)
  172. {
  173. if (row == null)
  174. return;
  175. MarkResolved([row]);
  176. }
  177. private bool MarkResolved(Button button, CoreRow[] rows)
  178. {
  179. if (MessageWindow.ShowYesNo("Mark Selected Issues as resolved?","Confirm"))
  180. MarkResolved(rows);
  181. return false;
  182. }
  183. private void AssignTo(CoreRow[] rows)
  184. {
  185. var _items = rows.Select(GetItem).ToArray();
  186. if (!_items.Any())
  187. return;
  188. var _dlg = new MultiSelectDialog<Employee>(LookupFactory.DefineFilter<Employee>(), null, false);
  189. if (_dlg.ShowDialog())
  190. {
  191. Dictionary<Type, List<IProblems<ManagedProblem>>> _updates = new();
  192. foreach (var _item in _items)
  193. {
  194. if (_item == null)
  195. continue;
  196. _item.Problem.AssignedTo.ID = _dlg.IDs().FirstOrDefault();
  197. var _type = _item.GetType();
  198. if (!_updates.ContainsKey(_type))
  199. _updates[_type] = new List<IProblems<ManagedProblem>>();
  200. _updates[_type].Add(_item);
  201. }
  202. Progress.ShowModal("Reassigning items", progress =>
  203. {
  204. foreach (var _update in _updates)
  205. {
  206. progress.Report($"Reassigning {_update.Value.Count} {new Inflector.Inflector(new CultureInfo("en")).Pluralize(_update.Key.Name.Split('.').Last()).SplitCamelCase()}");
  207. ClientFactory.CreateClient(_update.Key).Save(_update.Value, "Reassigning Problem");
  208. }
  209. });
  210. Refresh(false, true);
  211. }
  212. }
  213. private bool AssignTo(Button button, CoreRow[] rows)
  214. {
  215. AssignTo(rows);
  216. return false;
  217. }
  218. private void AssignTo(CoreRow? row)
  219. {
  220. if (row is null)
  221. return;
  222. AssignTo([row]);
  223. }
  224. protected override void DoDoubleClick(object sender, DynamicGridCellClickEventArgs args)
  225. {
  226. base.DoDoubleClick(sender, args);
  227. if (args.Row == null)
  228. return;
  229. EditItem(args.Row);
  230. }
  231. private void EditItem(CoreRow? row)
  232. {
  233. if (row is null) return;
  234. var _type = GetType(row);
  235. if (_type == null)
  236. return;
  237. var _item = GetItem(row);
  238. if (_item == null)
  239. return;
  240. var _grid = DynamicGridUtils.CreateDynamicGrid(typeof(DynamicDataGrid<>), _type);
  241. if (_grid.EditItems([ _item ], null, false))
  242. Refresh(false,true);
  243. }
  244. }