DFOptionControl.cs 9.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315
  1. using InABox.Core;
  2. using System;
  3. using System.Collections.Generic;
  4. using System.Linq;
  5. using System.Text;
  6. using System.Threading.Tasks;
  7. using System.Windows;
  8. using System.Windows.Controls;
  9. using System.Windows.Media;
  10. namespace InABox.DynamicGrid
  11. {
  12. public interface IOptionControl
  13. {
  14. public string? GetValue();
  15. public void SetValue(string value);
  16. public bool IsEmpty();
  17. }
  18. public class ButtonsOptionControl : Grid, IOptionControl
  19. {
  20. private Action OnChanged;
  21. private class OptionButton : Border
  22. {
  23. public string Option { get; set; }
  24. private bool _selected { get; set; }
  25. public bool Selected
  26. {
  27. get => _selected;
  28. set
  29. {
  30. _selected = value;
  31. if (value == true)
  32. {
  33. Background = new SolidColorBrush(Colors.LightGray);
  34. }
  35. else if (value == false)
  36. {
  37. Background = new SolidColorBrush(Colors.DarkGray);
  38. }
  39. }
  40. }
  41. public OptionButton(string option, bool selected)
  42. {
  43. Option = option;
  44. Selected = selected;
  45. }
  46. }
  47. public ButtonsOptionControl(string[] options, Action onChanged)
  48. {
  49. OnChanged = onChanged;
  50. foreach (var option in options)
  51. {
  52. ColumnDefinitions.Add(new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) });
  53. var button = new OptionButton(option, false);
  54. var label = new Label()
  55. {
  56. Content = option.Replace("\r", "").Replace("\n", "")
  57. };
  58. label.HorizontalContentAlignment = HorizontalAlignment.Center;
  59. label.VerticalContentAlignment = VerticalAlignment.Center;
  60. button.Child = label;
  61. button.Margin = new Thickness(
  62. Children.Count == 0 ? 0.0F : 2.5F,
  63. 0.0F,
  64. Children.Count == options.Length - 1 ? 0.0F : 2.5F,
  65. 0.0F
  66. );
  67. button.Padding = new Thickness(5.0F, 0.0F, 5.0F, 0.0F);
  68. button.MouseUp += Button_MouseUp;
  69. button.SetValue(ColumnProperty, Children.Count);
  70. Children.Add(button);
  71. }
  72. }
  73. private void Button_MouseUp(object sender, System.Windows.Input.MouseButtonEventArgs e)
  74. {
  75. SelectButton((OptionButton)sender);
  76. OnChanged();
  77. }
  78. private void SelectButton(OptionButton button)
  79. {
  80. foreach (var child in Children)
  81. {
  82. if (child is OptionButton childButton && childButton != button)
  83. {
  84. childButton.Selected = false;
  85. }
  86. }
  87. button.Selected = true;
  88. }
  89. public string? GetValue()
  90. {
  91. foreach (var child in Children)
  92. {
  93. if (child is OptionButton button)
  94. {
  95. if (button.Selected)
  96. {
  97. return button.Option;
  98. }
  99. }
  100. }
  101. return null;
  102. }
  103. public void SetValue(string value)
  104. {
  105. foreach (var child in Children)
  106. {
  107. if (child is OptionButton button)
  108. {
  109. if (button.Option == value)
  110. {
  111. SelectButton(button);
  112. }
  113. }
  114. }
  115. }
  116. public bool IsEmpty() => GetValue() == null;
  117. }
  118. public class RadioOptionControl : Grid, IOptionControl
  119. {
  120. private Action OnChanged;
  121. public RadioOptionControl(string[] options, Action onChanged)
  122. {
  123. Margin = new Thickness(4,2,4,2);
  124. OnChanged = onChanged;
  125. foreach (var option in options)
  126. {
  127. RowDefinitions.Add(new RowDefinition() { Height = new GridLength(1, GridUnitType.Auto) });
  128. var button = new RadioButton();
  129. button.Margin = new Thickness(0, 2, 0, 2);
  130. button.Content = option.Replace("\r", "").Replace("\n", "");
  131. button.VerticalContentAlignment = VerticalAlignment.Center;
  132. button.Padding = new Thickness(5.0F, 0.0F, 5.0F, 0.0F);
  133. button.SetValue(RowProperty, Children.Count);
  134. button.Tag = option;
  135. button.Checked += Button_Checked;
  136. button.Unchecked += Button_Checked;
  137. Children.Add(button);
  138. }
  139. }
  140. private void Button_Checked(object sender, RoutedEventArgs e)
  141. {
  142. OnChanged();
  143. }
  144. public string? GetValue()
  145. {
  146. foreach (var child in Children)
  147. {
  148. if (child is RadioButton radio)
  149. {
  150. if (radio.IsChecked == true)
  151. {
  152. return radio.Tag as string;
  153. }
  154. }
  155. }
  156. return null;
  157. }
  158. public void SetValue(string value)
  159. {
  160. foreach (var child in Children)
  161. {
  162. if (child is RadioButton radio)
  163. {
  164. if ((string)radio.Tag == value)
  165. {
  166. radio.IsChecked = true;
  167. }
  168. }
  169. }
  170. }
  171. public bool IsEmpty() => GetValue() == null;
  172. }
  173. public class ComboBoxOptionControl : ComboBox, IOptionControl
  174. {
  175. private readonly Action OnChanged;
  176. public ComboBoxOptionControl(string[] options, Action onChanged)
  177. {
  178. SetResourceReference(StyleProperty, typeof(ComboBox));
  179. OnChanged = onChanged;
  180. foreach (var option in options)
  181. Items.Add(option);
  182. VerticalContentAlignment = VerticalAlignment.Center;
  183. SelectionChanged += ComboBoxOptionControl_SelectionChanged;
  184. }
  185. private void ComboBoxOptionControl_SelectionChanged(object sender, SelectionChangedEventArgs e)
  186. {
  187. OnChanged();
  188. }
  189. public string? GetValue()
  190. {
  191. return SelectedValue as string;
  192. }
  193. public void SetValue(string value)
  194. {
  195. SelectedValue = value;
  196. }
  197. public bool IsEmpty() => GetValue() == null;
  198. }
  199. public class CheckBoxOptionControl : CheckBox, IOptionControl
  200. {
  201. private readonly Action OnChanged;
  202. private readonly string TrueValue;
  203. private readonly string FalseValue;
  204. public CheckBoxOptionControl(string trueValue, string falseValue, Action onChanged)
  205. {
  206. OnChanged = onChanged;
  207. TrueValue = trueValue;
  208. FalseValue = falseValue;
  209. IsThreeState = false;
  210. HorizontalContentAlignment = HorizontalAlignment.Center;
  211. VerticalContentAlignment = VerticalAlignment.Center;
  212. Checked += CheckBoxOptionControl_Checked;
  213. Unchecked += CheckBoxOptionControl_Checked;
  214. }
  215. private void CheckBoxOptionControl_Checked(object sender, RoutedEventArgs e)
  216. {
  217. OnChanged();
  218. }
  219. public string? GetValue()
  220. {
  221. return IsChecked == true
  222. ? TrueValue
  223. : FalseValue;
  224. }
  225. public void SetValue(string value)
  226. {
  227. IsChecked = value == TrueValue;
  228. }
  229. public bool IsEmpty() => false;
  230. }
  231. public class DFOptionControl : DynamicFormFieldControl<DFLayoutOptionField, DFLayoutOptionFieldProperties, string, string?>
  232. {
  233. private IOptionControl OptionControl = null!; // Late-initialised
  234. protected override FrameworkElement Create()
  235. {
  236. var options = string.IsNullOrWhiteSpace(Field.Properties.Options)
  237. ? new string[] { }
  238. : Field.Properties.Options.Replace(",","\n").Split('\n').Select(x=>x.Trim()).ToArray();
  239. switch (Field.Properties.OptionType)
  240. {
  241. case DFLayoutOptionType.Buttons:
  242. return SetControl(new ButtonsOptionControl(options, ChangeField));
  243. case DFLayoutOptionType.Radio:
  244. return SetControl(new RadioOptionControl(options, ChangeField));
  245. }
  246. return SetControl(new ComboBoxOptionControl(options, ChangeField));
  247. }
  248. private T SetControl<T>(T value)
  249. where T : FrameworkElement, IOptionControl
  250. {
  251. OptionControl = value;
  252. return value;
  253. }
  254. public override void SetSerializedValue(string? value)
  255. {
  256. SetValue(value);
  257. }
  258. public override string? GetSerializedValue()
  259. {
  260. return OptionControl.GetValue();
  261. }
  262. public override string GetValue() => OptionControl.GetValue() ?? "";
  263. public override void SetValue(string? value) => OptionControl.SetValue(value ?? "");
  264. protected override bool IsEmpty() => OptionControl.IsEmpty();
  265. }
  266. }