Dimensions.cs 8.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203
  1. using System;
  2. using System.Collections.Generic;
  3. namespace InABox.Core
  4. {
  5. public abstract class Dimensions<TLink,TUnit> : EnclosedEntity, IDimensions
  6. where TLink : DimensionUnitLink<TUnit>, new()
  7. where TUnit : DimensionUnit, new()
  8. {
  9. public Dimensions() : base() { }
  10. public Dimensions(Func<Entity> entity) : base(entity) { }
  11. [EditorSequence(1)]
  12. [RequiredColumn]
  13. [Caption("Sizing", IncludePath = false)]
  14. public abstract TLink Unit { get; set; }
  15. public IDimensionUnit GetUnit() => Unit;
  16. [DoubleEditor(Visible = Visible.Hidden)]
  17. [EditorSequence(2)]
  18. [Caption("Quantity", IncludePath = false)]
  19. [RequiredColumn]
  20. public abstract double Quantity { get; set; }
  21. [DoubleEditor(Visible = Visible.Hidden)]
  22. [EditorSequence(3)]
  23. [Caption("Length", IncludePath = false)]
  24. [RequiredColumn]
  25. public abstract double Length { get; set; }
  26. [DoubleEditor(Visible = Visible.Hidden)]
  27. [EditorSequence(4)]
  28. [Caption("Width", IncludePath = false)]
  29. [RequiredColumn]
  30. public abstract double Width { get; set; }
  31. [DoubleEditor(Visible = Visible.Hidden)]
  32. [EditorSequence(5)]
  33. [Caption("Height", IncludePath = false)]
  34. [RequiredColumn]
  35. public abstract double Height { get; set; }
  36. [DoubleEditor(Visible = Visible.Hidden)]
  37. [EditorSequence(6)]
  38. [Caption("Weight", IncludePath = false)]
  39. [RequiredColumn]
  40. public abstract double Weight { get; set; }
  41. [DoubleEditor(Visible = Visible.Optional, Editable = Editable.Hidden)]
  42. [Caption("Value", IncludePath = false)]
  43. [EditorSequence(7)]
  44. [RequiredColumn]
  45. public abstract double Value { get; set; }
  46. [TextBoxEditor(Visible = Visible.Default, Editable=Editable.Hidden)]
  47. [EditorSequence(8)]
  48. [Caption("Unit Size", IncludePath = false)]
  49. [RequiredColumn]
  50. public abstract String UnitSize { get; set; }
  51. protected override void Init()
  52. {
  53. base.Init();
  54. Unit = Activator.CreateInstance(typeof(TLink), new object[] { new Func<Entity>(LinkedEntity) }) as TLink;
  55. }
  56. private bool bCalculating = false;
  57. private static Column<Dimensions<TLink,TUnit>> unitid = new Column<Dimensions<TLink,TUnit>>(x => x.Unit.ID);
  58. private static Column<Dimensions<TLink,TUnit>> quantity = new Column<Dimensions<TLink,TUnit>>(x => x.Quantity);
  59. private static Column<Dimensions<TLink,TUnit>> length = new Column<Dimensions<TLink,TUnit>>(x => x.Length);
  60. private static Column<Dimensions<TLink,TUnit>> width = new Column<Dimensions<TLink,TUnit>>(x => x.Width);
  61. private static Column<Dimensions<TLink,TUnit>> height = new Column<Dimensions<TLink,TUnit>>(x => x.Height);
  62. private static Column<Dimensions<TLink,TUnit>> weight = new Column<Dimensions<TLink,TUnit>>(x => x.Weight);
  63. private static Column<Dimensions<TLink,TUnit>> sizeformula = new Column<Dimensions<TLink,TUnit>>(x => x.Unit.Formula);
  64. private static Column<Dimensions<TLink,TUnit>> sizeformat = new Column<Dimensions<TLink,TUnit>>(x => x.Unit.Format);
  65. protected override void DoPropertyChanged(string name, object? before, object? after)
  66. {
  67. base.DoPropertyChanged(name, before, after);
  68. if (bCalculating)
  69. return;
  70. bCalculating = true;
  71. try
  72. {
  73. if (unitid.IsEqualTo(name))
  74. Calculate(Quantity, Length, Width, Height, Weight, Unit.Formula, Unit.Format);
  75. else if (quantity.IsEqualTo(name))
  76. Calculate(after, Length, Width, Height, Weight, Unit.Formula, Unit.Format);
  77. else if (length.IsEqualTo(name))
  78. Calculate(Quantity, after, Width, Height, Weight, Unit.Formula, Unit.Format);
  79. else if (width.IsEqualTo(name))
  80. Calculate(Quantity, Length, after, Height, Weight, Unit.Formula, Unit.Format);
  81. else if (height.IsEqualTo(name))
  82. Calculate(Quantity, Length, Width, after, Weight, Unit.Formula, Unit.Format);
  83. else if (weight.IsEqualTo(name))
  84. Calculate(Quantity, Length, Width, Height, after, Unit.Formula, Unit.Format);
  85. else if (sizeformula.IsEqualTo(name))
  86. Calculate(Quantity, Length, Width, Height, Weight, after as string, Unit.Format);
  87. else if (sizeformat.IsEqualTo(name))
  88. Calculate(Quantity, Length, Width, Height, Weight, Unit.Formula, after as string);
  89. }
  90. finally
  91. {
  92. bCalculating = false;
  93. }
  94. }
  95. public void Set(IDimensionUnit unit, double quantity, double length, double width, double height, double weight)
  96. {
  97. bCalculating = true;
  98. try
  99. {
  100. Unit.ID = unit.ID;
  101. Unit.HasQuantity = unit.HasQuantity;
  102. Unit.HasLength = unit.HasLength;
  103. Unit.HasWidth = unit.HasWidth;
  104. Unit.HasHeight = unit.HasHeight;
  105. Unit.HasWeight = unit.HasWeight;
  106. Unit.Code = unit.Code;
  107. Unit.Description = unit.Description;
  108. Unit.Formula = unit.Formula;
  109. Unit.Format = unit.Format;
  110. Quantity = quantity;
  111. Length = length;
  112. Width = width;
  113. Height = height;
  114. Weight = weight;
  115. Calculate(quantity, length, width, height, weight, unit.Formula, unit.Format);
  116. }
  117. finally
  118. {
  119. bCalculating = false;
  120. }
  121. }
  122. private void Calculate(object? quantity, object? length, object? width, object? height, object? weight, string? formula, string? format)
  123. {
  124. if (Evaluate<double>(formula, quantity, length, width, height, weight, out double value))
  125. Value = value;
  126. if (Evaluate<String>(format, quantity, length, width, height, weight, out string unitsize))
  127. UnitSize = unitsize;
  128. }
  129. private bool Evaluate<T>(string? formula, object? quantity, object? length, object? width, object? height, object? weight, out T result)
  130. {
  131. if (!String.IsNullOrWhiteSpace(formula))
  132. {
  133. var variables = new Dictionary<string, object?>()
  134. {
  135. { "Quantity", Convert.ToDouble(quantity) },
  136. { "Length", Convert.ToDouble(length) },
  137. { "Width", Convert.ToDouble(width) },
  138. { "Height", Convert.ToDouble(height) },
  139. { "Weight", Convert.ToDouble(weight) }
  140. };
  141. try
  142. {
  143. var expr = new CoreExpression(formula);
  144. var eval = expr.Evaluate(variables);
  145. result = (T)CoreUtils.ChangeType(eval,typeof(T));
  146. return true;
  147. }
  148. catch (Exception e)
  149. {
  150. Logger.Send(LogType.Information, "", String.Format("Error in Formula: [{0}] ({1})", formula, e.Message));
  151. result = default(T);
  152. return false;
  153. }
  154. }
  155. result = default(T);
  156. return true;
  157. }
  158. public void CopyFrom(IDimensions source, bool observing = false)
  159. {
  160. if (!observing)
  161. SetObserving(false);
  162. Unit.ID = source.GetUnit().ID;
  163. Unit.Synchronise(source.GetUnit());
  164. Quantity = source.Quantity;
  165. Length = source.Length;
  166. Width = source.Width;
  167. Height = source.Height;
  168. Weight = source.Weight;
  169. Value = source.Value;
  170. UnitSize = source.UnitSize;
  171. if (!observing)
  172. SetObserving(true);
  173. }
  174. }
  175. }