StockLocationSelectionPage.xaml.cs 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529
  1. using Comal.Classes;
  2. using InABox.Clients;
  3. using InABox.Core;
  4. using Plugin.Media;
  5. using System;
  6. using System.Collections.Generic;
  7. using System.IO;
  8. using System.Linq;
  9. using System.Text;
  10. using System.Threading;
  11. using System.Threading.Tasks;
  12. using Xamarin.Forms;
  13. using Xamarin.Forms.Xaml;
  14. using XF.Material.Forms.UI.Dialogs;
  15. namespace comal.timesheets
  16. {
  17. [XamlCompilation(XamlCompilationOptions.Compile)]
  18. public partial class StockLocationSelectionPage : ContentPage
  19. {
  20. #region Constructor and Fields
  21. public delegate void LocationSelected(StockLocationShell shell);
  22. public delegate void MultiLocationSelected(List<StockLocationShell> shells);
  23. public event LocationSelected OnLocationSelected;
  24. public event MultiLocationSelected OnMultiLocationSelected;
  25. Color tealColor = Color.FromHex("#15C7C1");
  26. Color purpleColor = Color.FromHex("#a2006d");
  27. List<StockWarehouseShell> stockWarehouses = new List<StockWarehouseShell>();
  28. List<StockAreaShell> stockAreas = new List<StockAreaShell>();
  29. List<StockLocationShell> stockLocations = new List<StockLocationShell>();
  30. List<StockLocationShell> currentList = new List<StockLocationShell>();
  31. List<StockLocationShell> confirmedList = new List<StockLocationShell>();
  32. List<Button> buttons = new List<Button>();
  33. bool multiselect = false;
  34. public StockLocationSelectionPage(bool _multiselect = false)
  35. {
  36. InitializeComponent();
  37. multiselect = _multiselect;
  38. if (multiselect)
  39. {
  40. Timer timer = new Timer(Timercallback, null, 0, 3000);
  41. DisplayAlert("Info:", "Multiple selection of locations is enabled.", "OK");
  42. }
  43. LoadScreen();
  44. }
  45. private async void Timercallback(object o)
  46. {
  47. await multiLocationConfirmBtn.TranslateTo(0, -10, 250);
  48. await multiLocationConfirmBtn.TranslateTo(0, 0, 250);
  49. await multiLocationConfirmBtn.TranslateTo(0, -10, 250);
  50. await multiLocationConfirmBtn.TranslateTo(0, 0, 250);
  51. }
  52. #endregion
  53. #region Taps
  54. private void ResetScreen(object sender, EventArgs e)
  55. {
  56. try
  57. {
  58. Button button2 = buttons.Find(x => x.BackgroundColor.Equals(purpleColor));
  59. button2.BackgroundColor = tealColor;
  60. }
  61. catch { }
  62. try
  63. {
  64. StockAreaShell shell2 = stockAreas.Find(x => x.Color.Equals(tealColor));
  65. shell2.Color = Color.Default;
  66. }
  67. catch { }
  68. areaListView.ItemsSource = null;
  69. areaListView.ItemsSource = stockAreas;
  70. currentList.Clear();
  71. confirmedList.Clear();
  72. multiLocationConfirmBtn.IsVisible = false;
  73. foreach (StockLocationShell location in stockLocations)
  74. {
  75. if (location.Color.Equals(tealColor))
  76. {
  77. location.Color = Color.Default;
  78. }
  79. currentList.Add(location);
  80. }
  81. locationListView.ItemsSource = stockLocations;
  82. }
  83. private void WarehouseButton_Clicked(object sender, EventArgs e)
  84. {
  85. //handle color change
  86. try
  87. {
  88. Button button2 = buttons.Find(x => x.BackgroundColor.Equals(purpleColor));
  89. button2.BackgroundColor = tealColor;
  90. }
  91. catch { }
  92. string text = (sender as Button).Text;
  93. Button button = buttons.Find(x => x.Text == text);
  94. button.BackgroundColor = purpleColor;
  95. //check if area button needs to be cleared
  96. StockAreaShell shell = stockAreas.Find(x => x.Color.Equals(tealColor));
  97. if (shell != null)
  98. {
  99. shell.Color = Color.Default;
  100. }
  101. //arealist
  102. areaSearchEnt.Text = "";
  103. areaListView.ItemsSource = stockAreas.Where(x => x.WarehouseDescription.Equals(text));
  104. //locationlist
  105. locationSearchEnt.Text = "";
  106. locationListView.ItemsSource = stockLocations.Where(x => x.Warehouse.Contains(text));
  107. currentList.Clear();
  108. var list = stockLocations.Where(x => x.Warehouse.Contains(text));
  109. foreach (StockLocationShell location in list)
  110. {
  111. currentList.Add(location);
  112. }
  113. }
  114. private void AreaList_Tapped(object sender, EventArgs e)
  115. {
  116. //handle color change
  117. try
  118. {
  119. StockAreaShell shell2 = stockAreas.Find(x => x.Color.Equals(tealColor));
  120. shell2.Color = Color.Default;
  121. }
  122. catch { }
  123. string description = (areaListView.SelectedItem as StockAreaShell).Description;
  124. StockAreaShell shell = stockAreas.Find(x => x.Description.Equals(description));
  125. shell.Color = tealColor;
  126. //check if warehouse is selected
  127. Button button = buttons.Find(x => x.BackgroundColor.Equals(purpleColor));
  128. if (button != null) //warehouse is selected
  129. {
  130. if (!string.IsNullOrWhiteSpace(areaSearchEnt.Text))
  131. {
  132. AreaSearch();
  133. }
  134. else
  135. {
  136. areaListView.ItemsSource = null;
  137. areaListView.ItemsSource = stockAreas.Where(x => x.WarehouseDescription.Contains(button.Text));
  138. }
  139. }
  140. else
  141. {
  142. if (!string.IsNullOrWhiteSpace(areaSearchEnt.Text))
  143. {
  144. AreaSearch();
  145. }
  146. else
  147. {
  148. areaListView.ItemsSource = null;
  149. areaListView.ItemsSource = stockAreas;
  150. }
  151. }
  152. //locationlist
  153. locationSearchEnt.Text = "";
  154. locationListView.ItemsSource = stockLocations.Where(x => x.Area.Contains(description));
  155. currentList.Clear();
  156. var list = stockLocations.Where(x => x.Area.Contains(description));
  157. foreach (StockLocationShell location in list)
  158. {
  159. currentList.Add(location);
  160. }
  161. }
  162. private void LocationList_Tapped(object sender, EventArgs e)
  163. {
  164. StockLocationShell shell = locationListView.SelectedItem as StockLocationShell;
  165. if (!multiselect)
  166. {
  167. OnLocationSelected?.Invoke(shell);
  168. Navigation.PopAsync();
  169. }
  170. else
  171. {
  172. StockLocationShell shell1 = currentList.Find(x => x.ID.Equals(shell.ID));
  173. StockLocationShell shell2 = stockLocations.Find(x => x.ID.Equals(shell.ID));
  174. if (shell.Color.Equals(tealColor))
  175. {
  176. confirmedList.Remove(shell);
  177. shell1.Color = Color.Default;
  178. shell2.Color = Color.Default;
  179. }
  180. else
  181. {
  182. confirmedList.Add(shell);
  183. shell1.Color = tealColor;
  184. shell2.Color = tealColor;
  185. }
  186. if (string.IsNullOrWhiteSpace(locationSearchEnt.Text))
  187. {
  188. locationListView.ItemsSource = null;
  189. locationListView.ItemsSource = currentList;
  190. }
  191. else
  192. {
  193. locationListView.ItemsSource = null;
  194. RunLocationSearch(currentList);
  195. }
  196. multiLocationConfirmBtn.Text = "Confirm " + confirmedList.Count + " Location(s)";
  197. if (confirmedList.Count > 0)
  198. multiLocationConfirmBtn.IsVisible = true;
  199. else if (confirmedList.Count == 0)
  200. multiLocationConfirmBtn.IsVisible = false;
  201. }
  202. }
  203. private void MultiLocationConfirm_Clicked(object sender, EventArgs e)
  204. {
  205. OnMultiLocationSelected?.Invoke(confirmedList);
  206. Navigation.PopAsync();
  207. }
  208. #endregion
  209. #region Loading
  210. private void LoadScreen()
  211. {
  212. LoadWarehouses();
  213. LoadAreas();
  214. LoadLocations();
  215. }
  216. private void LoadWarehouses()
  217. {
  218. Task.Run(() =>
  219. {
  220. CoreTable table = new Client<StockWarehouse>().Query(
  221. new Filter<StockWarehouse>(x => x.Active).IsEqualTo(true),
  222. new Columns<StockWarehouse>(x => x.Description)
  223. );
  224. foreach (CoreRow row in table.Rows)
  225. {
  226. List<object> list = row.Values;
  227. if (list[0] == null) list[0] = "";
  228. StockWarehouseShell shell = new StockWarehouseShell()
  229. {
  230. Description = list[0].ToString(),
  231. };
  232. stockWarehouses.Add(shell);
  233. }
  234. foreach (StockWarehouseShell shell in stockWarehouses)
  235. {
  236. Button button = new Button
  237. {
  238. Text = shell.Description,
  239. TextColor = Color.White,
  240. BackgroundColor = tealColor,
  241. CornerRadius = 5,
  242. Margin = 1,
  243. FontAttributes = FontAttributes.Bold,
  244. VerticalOptions = LayoutOptions.Center,
  245. HorizontalOptions = LayoutOptions.Center,
  246. Padding = new Thickness(0)
  247. };
  248. button.Clicked += WarehouseButton_Clicked;
  249. buttons.Add(button);
  250. }
  251. Device.BeginInvokeOnMainThread(() =>
  252. {
  253. foreach (Button button in buttons)
  254. {
  255. warehouseFlexLayout.Children.Add(button);
  256. }
  257. });
  258. });
  259. }
  260. private void LoadAreas()
  261. {
  262. Task.Run(() =>
  263. {
  264. CoreTable table = new Client<StockArea>().Query
  265. (
  266. new Filter<StockArea>(x => x.Active).IsEqualTo(true),
  267. new Columns<StockArea>(x => x.Description, x => x.Warehouse.Description),
  268. new SortOrder<StockArea>(x => x.Description, SortDirection.Ascending)
  269. );
  270. foreach (CoreRow row in table.Rows)
  271. {
  272. List<object> list = row.Values;
  273. if (list[0] == null) list[0] = "";
  274. if (list[1] == null) list[1] = "";
  275. StockAreaShell shell = new StockAreaShell
  276. {
  277. Description = list[0].ToString(),
  278. WarehouseDescription = list[1].ToString(),
  279. };
  280. stockAreas.Add(shell);
  281. }
  282. Device.BeginInvokeOnMainThread(() =>
  283. {
  284. areaLoadingLbl.IsVisible = false;
  285. areaListView.ItemsSource = stockAreas;
  286. });
  287. });
  288. }
  289. private void LoadLocations()
  290. {
  291. Task.Run(() =>
  292. {
  293. CoreTable table = new Client<StockLocation>().Query(
  294. new Filter<StockLocation>(x => x.Active).IsEqualTo(true),
  295. new Columns<StockLocation>(
  296. x => x.ID, //0
  297. x => x.Description, //1
  298. x => x.Code, //2
  299. x => x.Area.Description, //3
  300. x => x.Warehouse.Description, //4
  301. x => x.Job.JobNumber, //5
  302. x => x.Job.ID, //6
  303. x => x.Job.Name, //7
  304. x => x.Holdings
  305. ));
  306. foreach (CoreRow row in table.Rows)
  307. {
  308. List<object> list = row.Values;
  309. if (list[0] == null) list[0] = Guid.Empty; //0
  310. if (list[1] == null) list[1] = ""; //1
  311. if (list[2] == null) list[2] = ""; //2
  312. if (list[3] == null) list[3] = ""; //3
  313. if (list[4] == null) list[4] = ""; //4
  314. if (list[5] == null) list[5] = ""; //5
  315. if (list[6] == null) list[6] = Guid.Empty; //6
  316. if (list[7] == null) list[7] = ""; //7
  317. StockLocationShell shell = new StockLocationShell
  318. {
  319. ID = Guid.Parse(list[0].ToString()),
  320. Description = list[1].ToString(),
  321. Code = list[2].ToString(),
  322. Area = "Area: " + list[3].ToString(),
  323. Warehouse = "Warehouse: " + list[4].ToString(),
  324. JobNumber = "Job: " + list[5].ToString(),
  325. JobID = Guid.Parse(list[6].ToString()),
  326. JobName = list[7].ToString(),
  327. NumberOfHoldings = "Holdings: " + row.Get<StockLocation, double>(x => x.Holdings)
  328. };
  329. stockLocations.Add(shell);
  330. currentList.Add(shell);
  331. }
  332. Device.BeginInvokeOnMainThread(() =>
  333. {
  334. locationLoadingLbl.IsVisible = false;
  335. locationListView.ItemsSource = stockLocations;
  336. });
  337. });
  338. //Task.Run(() =>
  339. //{
  340. // CoreTable table = new Client<StockLocation>().Query(
  341. // new Filter<StockLocation>(x => x.Active).IsEqualTo(true),
  342. // new Columns<StockLocation>(
  343. // x => x.ID, //0
  344. // x => x.Holdings //1
  345. // ));
  346. // foreach (CoreRow row in table.Rows)
  347. // {
  348. // Guid id = row.Get<StockLocation, Guid>(x => x.ID);
  349. // double holdings = row.Get<StockLocation, double>(x => x.Holdings);
  350. // StockLocationShell shell = stockLocations.Find(x => x.ID == id);
  351. // if (shell != null)
  352. // shell.NumberOfHoldings = "Holdings: " + holdings;
  353. // }
  354. // foreach (StockLocationShell shell in currentList)
  355. // {
  356. // StockLocationShell shell2 = stockLocations.Find(x => x.ID.Equals(shell.ID));
  357. // shell.NumberOfHoldings = shell2.NumberOfHoldings;
  358. // }
  359. // Device.BeginInvokeOnMainThread(() =>
  360. // {
  361. // if (!string.IsNullOrWhiteSpace(locationSearchEnt.Text))
  362. // {
  363. // locationListView.ItemsSource = null;
  364. // RunLocationSearch(currentList);
  365. // }
  366. // else
  367. // {
  368. // locationListView.ItemsSource = null;
  369. // locationListView.ItemsSource = currentList;
  370. // }
  371. // });
  372. //});
  373. }
  374. #endregion
  375. #region Searching
  376. private void AreaSearchEnt_Changed(object sender, EventArgs e)
  377. {
  378. AreaSearch();
  379. }
  380. private void AreaSearch()
  381. {
  382. //check if warehouse is selected
  383. Button button = buttons.Find(x => x.BackgroundColor.Equals(purpleColor));
  384. if (button != null) //warehouse is selected
  385. {
  386. var list = stockAreas.Where(x => x.WarehouseDescription.Contains(button.Text));
  387. List<StockAreaShell> searchList = new List<StockAreaShell>();
  388. foreach (var area in list)
  389. {
  390. searchList.Add(area);
  391. }
  392. RunAreaSearch(searchList);
  393. }
  394. else
  395. {
  396. RunAreaSearch(stockAreas);
  397. }
  398. }
  399. private void RunAreaSearch(List<StockAreaShell> list)
  400. {
  401. string text = areaSearchEnt.Text;
  402. areaListView.ItemsSource = list.Where(x =>
  403. x.Description.Contains(text) || x.Description.Contains(UpperCaseFirst(text)) ||
  404. x.Description.Contains(text.ToUpper()) || x.Description.Contains(text.ToLower())
  405. );
  406. }
  407. static String UpperCaseFirst(string s)
  408. {
  409. char[] a = s.ToCharArray();
  410. a[0] = char.ToUpper(a[0]);
  411. return new string(a);
  412. }
  413. private void LocationSearchEnt_Changed(object sender, EventArgs e)
  414. {
  415. StockAreaShell shell = stockAreas.Find(x => x.Color.Equals(tealColor));
  416. List<StockLocationShell> searchList = new List<StockLocationShell>();
  417. //check if warehouse is selected
  418. Button button = buttons.Find(x => x.BackgroundColor.Equals(purpleColor));
  419. if (button != null) //warehouse is selected
  420. {
  421. if (shell != null) //area is also selected
  422. {
  423. var list = stockLocations.Where(x => x.Area.Contains(shell.Description));
  424. foreach (var location in list)
  425. {
  426. searchList.Add(location);
  427. }
  428. RunLocationSearch(searchList);
  429. }
  430. else //only warehouse is selected
  431. {
  432. var list = stockLocations.Where(x => x.Warehouse.Contains(button.Text));
  433. foreach (var location in list)
  434. {
  435. searchList.Add(location);
  436. }
  437. RunLocationSearch(searchList);
  438. }
  439. }
  440. else if (shell != null) //only area is selected
  441. {
  442. var list = stockLocations.Where(x => x.Area.Contains(shell.Description));
  443. foreach (var location in list)
  444. {
  445. searchList.Add(location);
  446. }
  447. RunLocationSearch(searchList);
  448. }
  449. else
  450. {
  451. RunLocationSearch(stockLocations);
  452. }
  453. }
  454. private void RunLocationSearch(List<StockLocationShell> list)
  455. {
  456. string text = locationSearchEnt.Text;
  457. locationListView.ItemsSource = list.Where(x =>
  458. x.Description.Contains(text) || x.Description.Contains(UpperCaseFirst(text)) ||
  459. x.Description.Contains(text.ToLower()) || x.Description.Contains(text.ToUpper())
  460. );
  461. }
  462. #endregion
  463. }
  464. #region Shell Classes
  465. public class StockWarehouseShell
  466. {
  467. public string Description { get; set; }
  468. public StockWarehouseShell()
  469. {
  470. Description = "";
  471. }
  472. }
  473. public class StockAreaShell
  474. {
  475. public string Description { get; set; }
  476. public string WarehouseDescription { get; set; }
  477. public Color Color { get; set; }
  478. public StockAreaShell()
  479. {
  480. Description = "";
  481. WarehouseDescription = "";
  482. Color = Color.Default;
  483. }
  484. }
  485. #endregion
  486. }