private static void ParseUIElement <T>(UIElement uiElement, FieldInfo fieldInfo, int fieldIndex, T parentObject) { // Ignore live fields if (fieldInfo.GetCustomAttributes(false).Any(a => a is LiveAttribute)) { return; } // Ignore readonly fields if (fieldInfo.IsInitOnly) { return; } // Handle simple fields if (fieldInfo.FieldType == typeof(int) || fieldInfo.FieldType == typeof(double) || fieldInfo.FieldType == typeof(string) || fieldInfo.FieldType == typeof(bool) || fieldInfo.FieldType.IsEnum) { // Determine detailed type and parse the value if (fieldInfo.FieldType == typeof(int)) { // Parse the value and submit it string textValue = ((uiElement as WrapPanel).Children[1] as TextBox).Text; fieldInfo.SetValue(parentObject, string.IsNullOrWhiteSpace(textValue) ? 0 : int.Parse(textValue)); return; } if (fieldInfo.FieldType == typeof(double)) { // Parse the value and submit it string textValue = ((uiElement as WrapPanel).Children[1] as TextBox).Text; fieldInfo.SetValue(parentObject, string.IsNullOrWhiteSpace(textValue) ? 0 : double.Parse(textValue, IOConstants.FORMATTER)); return; } if (fieldInfo.FieldType == typeof(string)) { // Get the value and submit it fieldInfo.SetValue(parentObject, ((uiElement as WrapPanel).Children[1] as TextBox).Text); return; } if (fieldInfo.FieldType == typeof(bool)) { // Check the value and submit it fieldInfo.SetValue(parentObject, ((uiElement as WrapPanel).Children[1] as CheckBox).IsChecked == true); return; } if (fieldInfo.FieldType.IsEnum) { // Check the value and submit it object enumVal = Enum.Parse(fieldInfo.FieldType, fieldInfo.FieldType.GetEnumNames()[((uiElement as WrapPanel).Children[1] as ComboBox).SelectedIndex]); fieldInfo.SetValue(parentObject, enumVal); return; } } // Handle lists if (typeof(IList).IsAssignableFrom(fieldInfo.FieldType)) { // Ignore empty lists (if the first element is a button instead of some content element the value is assumed to be null) if ((uiElement as TreeViewItem).Items.Cast <object>().FirstOrDefault() is Button) { return; } // Init list IList listObject = GetContructorFunction(fieldInfo.FieldType)() as IList; fieldInfo.SetValue(parentObject, listObject); // Parse the list elements foreach (var listUIElement in (uiElement as TreeViewItem).Items.OfType <WrapPanel>()) { listObject.Add(ParseListElement(listUIElement, fieldInfo.FieldType)); } return; } // Handle complex fields if (!fieldInfo.FieldType.IsPrimitive && !(fieldInfo.FieldType == typeof(string))) { // Ignore empty ones (if the first element is a button instead of some content element the value is assumed to be null) if ((uiElement as TreeViewItem).Items.Cast <object>().FirstOrDefault() is Button) { return; } // Get subfields to parse (the field itself was already set by the command) var fieldRoot = fieldInfo.GetValue(parentObject); FieldInfo[] fields = fieldRoot.GetType().GetFields(); // Parse all fields of the current method type for (var fieldNo = 0; fieldNo < fields.Length; fieldNo++) { // Ignore live fields if (fields[fieldNo].GetCustomAttributes(false).Any(a => a is LiveAttribute)) { continue; } // Parse the ui element - plus one for skipping the description ui-element ParseUIElement(((uiElement as TreeViewItem).Items[fieldNo + 1] as UIElement), fields[fieldNo], fieldNo, fieldRoot); } return; } // We don't know this type - throw an exception throw new ArgumentException("Unknown field type: " + fieldInfo.FieldType.FullName); }
private static void AddUIElement(Dispatcher uiDispatcher, IList rootCollection, object rootObject, FieldInfo fieldInfo, object fieldValue) { // Get a helping string string helpString = GetHelpString(fieldInfo); // If the field has to be ignored just add a placeholder if (fieldInfo.GetCustomAttributes(false).Any(a => a is LiveAttribute)) { TextBlock placeholder = new TextBlock() { Text = "LiveAttribute: " + fieldInfo.Name, FontFamily = new System.Windows.Media.FontFamily("Consolas"), ToolTip = helpString != null ? helpString : "This field cannot be modified" }; rootCollection.Add(placeholder); return; } // If the field cannot be modified just add a placeholder if (fieldInfo.IsInitOnly) { TextBlock placeholder = new TextBlock() { Text = fieldInfo.Name + ": (readonly)", ToolTip = helpString != null ? helpString : "This field cannot be modified" }; rootCollection.Add(placeholder); return; } // Handle simple fields if (fieldInfo.FieldType == typeof(int) || fieldInfo.FieldType == typeof(double) || fieldInfo.FieldType == typeof(string) || fieldInfo.FieldType == typeof(bool) || fieldInfo.FieldType.IsEnum) { // Begin with a description var wrapPane = new WrapPanel { Orientation = Orientation.Horizontal, Margin = new Thickness(2, 1, 2, 1) }; wrapPane.Children.Add(new TextBlock { Text = fieldInfo.Name + ": " }); if (helpString != null) { wrapPane.ToolTip = helpString; } // Determine detailed type and add the value if (fieldInfo.FieldType == typeof(int)) { // No formatter required for int - just "tostring" the value wrapPane.Children.Add(new TextBox { Text = fieldValue.ToString() }); rootCollection.Add(wrapPane); return; } if (fieldInfo.FieldType == typeof(double)) { // We need a formatter for double - get the suitable method and add an appropriate formatter then "tostring" it double value = (double)fieldValue; wrapPane.Children.Add(new TextBox { Text = value.ToString(IOConstants.FORMATTER) }); rootCollection.Add(wrapPane); return; } if (fieldInfo.FieldType == typeof(string)) { // It is already a string - just "tostring" the object again wrapPane.Children.Add(new TextBox { Text = fieldValue != null ? fieldValue.ToString() : "" }); rootCollection.Add(wrapPane); return; } if (fieldInfo.FieldType == typeof(bool)) { // It's a bool - add a checkbox bool value = (bool)fieldValue; wrapPane.Children.Add(new CheckBox() { IsChecked = value }); rootCollection.Add(wrapPane); return; } if (fieldInfo.FieldType.IsEnum) { // It's an enum - add a combobox string value = fieldValue.ToString(); var visualElement = new ComboBox() { }; foreach (var enumName in fieldInfo.FieldType.GetEnumNames()) { visualElement.Items.Add(enumName); } visualElement.SelectedIndex = fieldInfo.FieldType.GetEnumNames().TakeWhile(n => !value.Equals(n)).Count(); wrapPane.Children.Add(visualElement); rootCollection.Add(wrapPane); return; } } // Handle lists if (typeof(IList).IsAssignableFrom(fieldInfo.FieldType)) { // Generate a root for the field and a button to init and clear it TreeViewItem treeViewRoot = new TreeViewItem() { Header = fieldInfo.Name, }; if (helpString != null) { treeViewRoot.ToolTip = helpString; } if (fieldValue == null) { // List is not instantiated - do it now fieldValue = GetContructorFunction(fieldInfo.FieldType)(); fieldInfo.SetValue(rootObject, fieldValue); } ListHandlerCommand listHandleCommand = new ListHandlerCommand(uiDispatcher, treeViewRoot, fieldInfo.FieldType, fieldValue as IList); listHandleCommand.Init(); rootCollection.Add(treeViewRoot); return; } // Handle complex fields if (!fieldInfo.FieldType.IsPrimitive && !fieldInfo.FieldType.Equals(typeof(string))) { // Generate a root for the field and a button to init and clear it TreeViewItem treeViewRoot = new TreeViewItem() { Header = fieldInfo.Name, }; if (helpString != null) { treeViewRoot.ToolTip = helpString; } DefaultGeneratorCommand initClearCommand = new DefaultGeneratorCommand(uiDispatcher, treeViewRoot, rootObject, fieldInfo); initClearCommand.Init(); rootCollection.Add(treeViewRoot); return; } // We don't know this type - throw an exception throw new ArgumentException("Unknown field type: " + fieldInfo.FieldType.FullName); }