DimensionsEditorControl.cs 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292
  1. using Comal.Classes;
  2. using InABox.Clients;
  3. using InABox.Core;
  4. using PRSClasses;
  5. using Syncfusion.Windows.Shared;
  6. using System.Collections.Generic;
  7. using System.Linq;
  8. using System.Text;
  9. using System.Threading.Tasks;
  10. using System.Windows;
  11. using System.Windows.Controls;
  12. using System.Windows.Media;
  13. using InABox.DynamicGrid;
  14. namespace PRS.Shared
  15. {
  16. /*public class DimensionsEditorControl
  17. {
  18. public static BaseDynamicEditorControl? Create(DimensionsEditor editor)
  19. {
  20. var dimensionsType = editor.DimensionsType;
  21. var dimensions = dimensionsType.GetSuperclassDefinition(typeof(Dimensions<,>));
  22. if (dimensions == null) return null;
  23. var tLink = dimensions.GenericTypeArguments[0];
  24. var tUnit = dimensions.GenericTypeArguments[1];
  25. return Activator.CreateInstance(typeof(DimensionsEditorControl<,,>).MakeGenericType(dimensionsType, tLink, tUnit), editor) as BaseDynamicEditorControl;
  26. }
  27. }*/
  28. public class DimensionsEditorControl<TDimensions, TLink, TUnit> : DynamicEnclosedEditorControl<TDimensions, DimensionsEditor>
  29. where TDimensions : Dimensions<TLink, TUnit>, new()
  30. where TLink : DimensionUnitLink<TUnit>, new()
  31. where TUnit : DimensionUnit, new()
  32. {
  33. private Grid Grid = null!; // Late-initialized in CreateEditor
  34. private ComboBox Combo = null!; // Late-initialized in CreateEditor
  35. private DoubleTextBox QuantityBox = null!; // Late-initialized in CreateEditor
  36. private DoubleTextBox LengthBox = null!; // Late-initialized in CreateEditor
  37. private DoubleTextBox WidthBox = null!; // Late-initialized in CreateEditor
  38. private DoubleTextBox HeightBox = null!; // Late-initialized in CreateEditor
  39. private DoubleTextBox WeightBox = null!; // Late-initialized in CreateEditor
  40. private List<Tuple<string, TUnit>> Units = null!; // Late-initialized in CreateEditor
  41. public override int DesiredHeight()
  42. {
  43. return 25;
  44. }
  45. public override int DesiredWidth()
  46. {
  47. return int.MaxValue;
  48. }
  49. public override void SetColor(Color color)
  50. {
  51. QuantityBox.Background = new SolidColorBrush(color);
  52. LengthBox.Background = new SolidColorBrush(color);
  53. WidthBox.Background = new SolidColorBrush(color);
  54. HeightBox.Background = new SolidColorBrush(color);
  55. WeightBox.Background = new SolidColorBrush(color);
  56. }
  57. public override void SetFocus()
  58. {
  59. Combo.Focus();
  60. }
  61. public override void Configure()
  62. {
  63. }
  64. protected override FrameworkElement CreateEditor()
  65. {
  66. Grid = new Grid
  67. {
  68. VerticalAlignment = VerticalAlignment.Stretch,
  69. HorizontalAlignment = HorizontalAlignment.Stretch
  70. };
  71. Grid.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(150, GridUnitType.Pixel) });
  72. Combo = new ComboBox
  73. {
  74. IsEnabled = EditorDefinition.AllowEditingUnit
  75. };
  76. Combo.SetValue(Grid.ColumnProperty, 0);
  77. Combo.SetValue(Grid.RowProperty, 0);
  78. Grid.Children.Add(Combo);
  79. var result = new Client<TUnit>()
  80. .Query(
  81. LookupFactory.DefineFilter<TUnit>(),
  82. LookupFactory.DefineColumns<TUnit>(),
  83. LookupFactory.DefineSort<TUnit>());
  84. Units = result.Rows.Select(row =>
  85. {
  86. var values = row.ToDictionary(new[] { "Display" });
  87. var display = LookupFactory.FormatLookup(typeof(TUnit), values, Array.Empty<string>());
  88. return new Tuple<string, TUnit>(display, row.ToObject<TUnit>());
  89. }).ToList();
  90. Combo.DisplayMemberPath = "Item1";
  91. Combo.SelectedValuePath = "Item2.ID";
  92. Combo.ItemsSource = Units;
  93. Combo.SelectionChanged += Combo_SelectionChanged;
  94. QuantityBox = AddDimension("Quantity: ", 1);
  95. LengthBox = AddDimension("Length: ", 2);
  96. WidthBox = AddDimension("Width: ", 3);
  97. HeightBox = AddDimension("Height: ", 4);
  98. WeightBox = AddDimension("Weight: ", 5);
  99. return Grid;
  100. }
  101. public override void SetEnabled(bool enabled)
  102. {
  103. base.SetEnabled(enabled);
  104. }
  105. private void UpdateColumn(int column, bool visible, DoubleTextBox box)
  106. {
  107. if (!visible && box.Value != 0.0 && box.Value != null)
  108. {
  109. box.Value = 0.0;
  110. }
  111. var columnDefinition = Grid.ColumnDefinitions[column * 2];
  112. if (visible)
  113. {
  114. columnDefinition.Width = new GridLength(1, GridUnitType.Star);
  115. }
  116. else
  117. {
  118. columnDefinition.Width = new GridLength(0);
  119. }
  120. columnDefinition = Grid.ColumnDefinitions[column * 2 - 1];
  121. if (visible)
  122. {
  123. columnDefinition.Width = GridLength.Auto;
  124. }
  125. else
  126. {
  127. columnDefinition.Width = new GridLength(0);
  128. }
  129. }
  130. private DoubleTextBox AddDimension(string name, int column)
  131. {
  132. Grid.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(0) });
  133. Grid.ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(0) });
  134. var label = new Label
  135. {
  136. Content = name,
  137. VerticalAlignment = VerticalAlignment.Center,
  138. VerticalContentAlignment = VerticalAlignment.Center,
  139. Margin = new Thickness(5, 0, 0, 0)
  140. };
  141. label.SetValue(Grid.ColumnProperty, column * 2 - 1);
  142. var box = new DoubleTextBox
  143. {
  144. VerticalAlignment = VerticalAlignment.Stretch,
  145. VerticalContentAlignment = VerticalAlignment.Center,
  146. HorizontalAlignment = HorizontalAlignment.Stretch,
  147. HorizontalContentAlignment = HorizontalAlignment.Center,
  148. NumberDecimalDigits = 2,
  149. Margin = new Thickness(5, 0, 0, 0)
  150. };
  151. box.SetValue(Grid.ColumnProperty, column * 2);
  152. box.ValueChanged += Box_ValueChanged;
  153. Grid.Children.Add(label);
  154. Grid.Children.Add(box);
  155. return box;
  156. }
  157. private TUnit? GetSelectedUnit()
  158. {
  159. if (Combo.SelectedValue is not Guid unitID) return null;
  160. if (Combo.SelectedItem is not Tuple<string, TUnit> tuple) return null;
  161. return tuple.Item2;
  162. }
  163. private bool IsBoxVisible(DoubleTextBox box)
  164. {
  165. var unit = GetSelectedUnit();
  166. if (unit is null) return false;
  167. if (box == QuantityBox) return unit.HasQuantity;
  168. if (box == LengthBox) return unit.HasLength;
  169. if (box == WidthBox) return unit.HasWidth;
  170. if (box == HeightBox) return unit.HasHeight;
  171. if (box == WeightBox) return unit.HasWeight;
  172. return false;
  173. }
  174. private void Box_ValueChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
  175. {
  176. // Don't trigger value changed if invisible, this will have been handled by the SelectionChanged event handler.
  177. if (d is not DoubleTextBox box || !IsBoxVisible(box)) return;
  178. if(((double?)e.OldValue ?? default(double)) == ((double?)e.NewValue ?? default(double)))
  179. {
  180. return;
  181. }
  182. CheckChanged();
  183. }
  184. private void Combo_SelectionChanged(object sender, SelectionChangedEventArgs e)
  185. {
  186. if (Combo.SelectedValue is not Guid unitID) return;
  187. if (Combo.SelectedItem is not Tuple<string, TUnit> tuple) return;
  188. var unit = tuple.Item2;
  189. UpdateColumn(1, unit.HasQuantity, QuantityBox);
  190. UpdateColumn(2, unit.HasLength, LengthBox);
  191. UpdateColumn(3, unit.HasWidth, WidthBox);
  192. UpdateColumn(4, unit.HasHeight, HeightBox);
  193. UpdateColumn(5, unit.HasWeight, WeightBox);
  194. foreach(var property in DatabaseSchema.Properties(typeof(TUnit)))
  195. {
  196. var value = property.Getter()(unit);
  197. OtherValues[$"{ColumnName}.Unit.{property.Name}"] = value;
  198. }
  199. CheckChanged();
  200. }
  201. protected override object? GetChildValue(string property)
  202. {
  203. if (property == "Quantity") return QuantityBox.Value ?? 0.0;
  204. if (property == "Length") return LengthBox.Value ?? 0.0;
  205. if (property == "Width") return WidthBox.Value ?? 0.0;
  206. if (property == "Height") return HeightBox.Value ?? 0.0;
  207. if (property == "Weight") return WeightBox.Value ?? 0.0;
  208. if (property == "Unit.ID") return Combo.SelectedValue is Guid guid ? guid : Guid.Empty;
  209. return null;
  210. }
  211. protected override IEnumerable<KeyValuePair<string, object?>> GetChildValues()
  212. {
  213. yield return new("Quantity", QuantityBox.Value ?? 0.0);
  214. yield return new("Length", LengthBox.Value ?? 0.0);
  215. yield return new("Width", WidthBox.Value ?? 0.0);
  216. yield return new("Height", HeightBox.Value ?? 0.0);
  217. yield return new("Weight", WeightBox.Value ?? 0.0);
  218. yield return new("Unit.ID", Combo.SelectedValue is Guid guid ? guid : Guid.Empty);
  219. }
  220. protected override void SetChildValue(string property, object? value)
  221. {
  222. if (property == "Unit.ID")
  223. {
  224. Combo.SelectedValue = value is Guid guid ? guid : Guid.Empty;
  225. return;
  226. }
  227. if (property == "Quantity") QuantityBox.Value = (double)(value ?? 0.0);
  228. if (property == "Length") LengthBox.Value = (double)(value ?? 0.0);
  229. if (property == "Width") WidthBox.Value = (double)(value ?? 0.0);
  230. if (property == "Height") HeightBox.Value = (double)(value ?? 0.0);
  231. if (property == "Weight") WeightBox.Value = (double)(value ?? 0.0);
  232. }
  233. }
  234. public class ProductDimensionsEditorControl : DimensionsEditorControl<ProductDimensions, ProductDimensionUnitLink, ProductDimensionUnit> { }
  235. public class QuoteTakeOffDimensionsEditorControl : DimensionsEditorControl<QuoteTakeOffDimensions, QuoteTakeOffUnitLink, QuoteTakeOffUnit> { }
  236. public class StockDimensionsEditorControl : DimensionsEditorControl<StockDimensions, ProductDimensionUnitLink,
  237. ProductDimensionUnit>
  238. {
  239. public StockDimensionsEditorControl()
  240. {
  241. }
  242. }
  243. }