Browse Source

PropertyGrid: Implemented support for complex properties. You can now drill down into a hierarchy of an object's properties. I an not sure if I will create my own attribute or use the following syntax.

[TypeConverter(typeof(ExpandableObjectConverter))]
        public Person Admin
        {
            get { return _admin; }
            set { _admin = value; }
        }

For now it works with the above syntax.
pull/1645/head
brianlagunas_cp 15 years ago
parent
commit
093c0485c2
  1. 2
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/Editors/CollectionEditor.xaml.cs
  2. 2
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/Editors/TypeEditor.cs
  3. 184
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/PropertyGrid.cs
  4. 184
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/PropertyGridUtilities.cs
  5. 156
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/PropertyItem.cs
  6. 294
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Themes/Generic.xaml
  7. 1
      ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/WPFToolkit.Extended.csproj

2
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/Editors/CollectionEditor.xaml.cs

@ -22,7 +22,7 @@ namespace Microsoft.Windows.Controls.PropertyGrid.Editors
CollectionEditorDialog editor = new CollectionEditorDialog(_item.PropertyType);
Binding binding = new Binding("Value");
binding.Source = _item;
binding.Mode = _item.IsWriteable ? BindingMode.TwoWay : BindingMode.OneWay;
binding.Mode = _item.IsReadOnly ? BindingMode.OneWay : BindingMode.TwoWay;
BindingOperations.SetBinding(editor, CollectionEditorDialog.ItemsSourceProperty, binding);
editor.ShowDialog();
}

2
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/Editors/TypeEditor.cs

@ -40,7 +40,7 @@ namespace Microsoft.Windows.Controls.PropertyGrid.Editors
_binding.Source = propertyItem;
_binding.ValidatesOnExceptions = true;
_binding.ValidatesOnDataErrors = true;
_binding.Mode = propertyItem.IsWriteable ? BindingMode.TwoWay : BindingMode.OneWay;
_binding.Mode = propertyItem.IsReadOnly ? BindingMode.OneWay : BindingMode.TwoWay;
_binding.Converter = CreateValueConverter();
BindingOperations.SetBinding(Editor, ValueProperty, _binding);
}

184
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/PropertyGrid.cs

@ -1,16 +1,13 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Media;
using System.Windows.Controls.Primitives;
using System.ComponentModel;
using System.Windows.Data;
using System.Windows.Input;
using Microsoft.Windows.Controls.PropertyGrid.Editors;
using Microsoft.Windows.Controls.PropertyGrid.Commands;
using Microsoft.Windows.Controls.PropertyGrid.Attributes;
namespace Microsoft.Windows.Controls.PropertyGrid
{
@ -345,9 +342,9 @@ namespace Microsoft.Windows.Controls.PropertyGrid
Filter = String.Empty;
if (isCategorized)
Properties = GetCategorizedProperties(_propertyItemsCache);
Properties = PropertyGridUtilities.GetCategorizedProperties(_propertyItemsCache);
else
Properties = GetAlphabetizedProperties(_propertyItemsCache);
Properties = PropertyGridUtilities.GetAlphabetizedProperties(_propertyItemsCache);
}
private List<PropertyItem> GetObjectProperties(object instance)
@ -358,11 +355,11 @@ namespace Microsoft.Windows.Controls.PropertyGrid
try
{
var descriptors = GetPropertyDescriptors(instance);
var descriptors = PropertyGridUtilities.GetPropertyDescriptors(instance);
foreach (PropertyDescriptor descriptor in descriptors)
{
if (descriptor.IsBrowsable)
propertyItems.Add(CreatePropertyItem(descriptor, instance, this));
propertyItems.Add(PropertyGridUtilities.CreatePropertyItem(descriptor, instance, this, descriptor.Name));
}
}
catch (Exception ex)
@ -373,175 +370,6 @@ namespace Microsoft.Windows.Controls.PropertyGrid
return propertyItems;
}
private static PropertyDescriptorCollection GetPropertyDescriptors(object instance)
{
PropertyDescriptorCollection descriptors;
TypeConverter tc = TypeDescriptor.GetConverter(instance);
if (tc == null || !tc.GetPropertiesSupported())
{
if (instance is ICustomTypeDescriptor)
descriptors = ((ICustomTypeDescriptor)instance).GetProperties();
else
descriptors = TypeDescriptor.GetProperties(instance.GetType());
}
else
{
descriptors = tc.GetProperties(instance);
}
return descriptors;
}
private PropertyItem CreatePropertyItem(PropertyDescriptor property, object instance, PropertyGrid grid)
{
PropertyItem propertyItem = new PropertyItem(instance, property, grid);
var binding = new Binding(property.Name)
{
Source = instance,
ValidatesOnExceptions = true,
ValidatesOnDataErrors = true,
Mode = propertyItem.IsWriteable ? BindingMode.TwoWay : BindingMode.OneWay
};
propertyItem.SetBinding(PropertyItem.ValueProperty, binding);
propertyItem.Editor = GetTypeEditor(propertyItem);
return propertyItem;
}
private FrameworkElement GetTypeEditor(PropertyItem propertyItem)
{
//first check for an attribute editor
FrameworkElement editor = GetAttibuteEditor(propertyItem);
//now look for a custom editor based on editor definitions
if (editor == null)
editor = GetCustomEditor(propertyItem, EditorDefinitions);
//guess we have to use the default editor
if (editor == null)
editor = CreateDefaultEditor(propertyItem);
return editor;
}
private static FrameworkElement GetAttibuteEditor(PropertyItem propertyItem)
{
FrameworkElement editor = null;
var itemsSourceAttribute = GetAttribute<ItemsSourceAttribute>(propertyItem.PropertyDescriptor);
if (itemsSourceAttribute != null)
editor = new ItemsSourceEditor(itemsSourceAttribute).ResolveEditor(propertyItem);
var editorAttribute = GetAttribute<EditorAttribute>(propertyItem.PropertyDescriptor);
if (editorAttribute != null)
{
Type type = Type.GetType(editorAttribute.EditorTypeName);
var instance = Activator.CreateInstance(type);
if (instance is ITypeEditor)
editor = (instance as ITypeEditor).ResolveEditor(propertyItem);
}
return editor;
}
public static T GetAttribute<T>(PropertyDescriptor property) where T : Attribute
{
foreach (Attribute att in property.Attributes)
{
var tAtt = att as T;
if (tAtt != null) return tAtt;
}
return null;
}
private static FrameworkElement GetCustomEditor(PropertyItem propertyItem, EditorDefinitionCollection customTypeEditors)
{
FrameworkElement editor = null;
//check for custom editor
if (customTypeEditors.Count > 0)
{
//first check if the custom editor is type based
IEditorDefinition customEditor = customTypeEditors[propertyItem.PropertyType];
if (customEditor == null)
{
//must be property based
customEditor = customTypeEditors[propertyItem.Name];
}
if (customEditor != null)
{
if (customEditor.EditorTemplate != null)
editor = customEditor.EditorTemplate.LoadContent() as FrameworkElement;
}
}
return editor;
}
private static FrameworkElement CreateDefaultEditor(PropertyItem propertyItem)
{
ITypeEditor editor = null;
if (propertyItem.IsReadOnly)
editor = new TextBlockEditor();
else if (propertyItem.PropertyType == typeof(bool) || propertyItem.PropertyType == typeof(bool?))
editor = new CheckBoxEditor();
else if (propertyItem.PropertyType == typeof(decimal) || propertyItem.PropertyType == typeof(decimal?))
editor = new DecimalUpDownEditor();
else if (propertyItem.PropertyType == typeof(double) || propertyItem.PropertyType == typeof(double?))
editor = new DoubleUpDownEditor();
else if (propertyItem.PropertyType == typeof(int) || propertyItem.PropertyType == typeof(int?))
editor = new IntegerUpDownEditor();
else if (propertyItem.PropertyType == typeof(DateTime) || propertyItem.PropertyType == typeof(DateTime?))
editor = new DateTimeUpDownEditor();
else if ((propertyItem.PropertyType == typeof(Color)))
editor = new ColorEditor();
else if (propertyItem.PropertyType.IsEnum)
editor = new EnumComboBoxEditor();
else if (propertyItem.PropertyType == typeof(TimeSpan))
editor = new TimeSpanEditor();
else if (propertyItem.PropertyType == typeof(FontFamily) || propertyItem.PropertyType == typeof(FontWeight) || propertyItem.PropertyType == typeof(FontStyle) || propertyItem.PropertyType == typeof(FontStretch))
editor = new FontComboBoxEditor();
else if (propertyItem.PropertyType.IsGenericType)
{
if (propertyItem.PropertyType.GetInterface("IList") != null)
{
var t = propertyItem.PropertyType.GetGenericArguments()[0];
if (!t.IsPrimitive && !t.Equals(typeof(String)))
editor = new Microsoft.Windows.Controls.PropertyGrid.Editors.CollectionEditor();
else
editor = new Microsoft.Windows.Controls.PropertyGrid.Editors.PrimitiveTypeCollectionEditor();
}
else
editor = new TextBlockEditor();
}
else
editor = new TextBoxEditor();
return editor.ResolveEditor(propertyItem);
}
private static PropertyItemCollection GetCategorizedProperties(List<PropertyItem> propertyItems)
{
PropertyItemCollection propertyCollection = new PropertyItemCollection(propertyItems);
propertyCollection.GroupBy("Category");
propertyCollection.SortBy("Category", ListSortDirection.Ascending);
propertyCollection.SortBy("DisplayName", ListSortDirection.Ascending);
return propertyCollection;
}
private static PropertyItemCollection GetAlphabetizedProperties(List<PropertyItem> propertyItems)
{
PropertyItemCollection propertyCollection = new PropertyItemCollection(propertyItems);
propertyCollection.SortBy("DisplayName", ListSortDirection.Ascending);
return propertyCollection;
}
private void SetSelectedObjectNameBinding(object selectedObject)
{
if (selectedObject is FrameworkElement)

184
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/PropertyGridUtilities.cs

@ -0,0 +1,184 @@
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Windows;
using System.Windows.Data;
using System.Windows.Media;
using Microsoft.Windows.Controls.PropertyGrid.Attributes;
using Microsoft.Windows.Controls.PropertyGrid.Editors;
namespace Microsoft.Windows.Controls.PropertyGrid
{
internal class PropertyGridUtilities
{
internal static T GetAttribute<T>(PropertyDescriptor property) where T : Attribute
{
foreach (Attribute att in property.Attributes)
{
var tAtt = att as T;
if (tAtt != null) return tAtt;
}
return null;
}
internal static PropertyItemCollection GetAlphabetizedProperties(List<PropertyItem> propertyItems)
{
PropertyItemCollection propertyCollection = new PropertyItemCollection(propertyItems);
propertyCollection.SortBy("DisplayName", ListSortDirection.Ascending);
return propertyCollection;
}
internal static PropertyItemCollection GetCategorizedProperties(List<PropertyItem> propertyItems)
{
PropertyItemCollection propertyCollection = new PropertyItemCollection(propertyItems);
propertyCollection.GroupBy("Category");
propertyCollection.SortBy("Category", ListSortDirection.Ascending);
propertyCollection.SortBy("DisplayName", ListSortDirection.Ascending);
return propertyCollection;
}
internal static PropertyDescriptorCollection GetPropertyDescriptors(object instance)
{
PropertyDescriptorCollection descriptors;
TypeConverter tc = TypeDescriptor.GetConverter(instance);
if (tc == null || !tc.GetPropertiesSupported())
{
if (instance is ICustomTypeDescriptor)
descriptors = ((ICustomTypeDescriptor)instance).GetProperties();
else
descriptors = TypeDescriptor.GetProperties(instance.GetType());
}
else
{
descriptors = tc.GetProperties(instance);
}
return descriptors;
}
internal static PropertyItem CreatePropertyItem(PropertyDescriptor property, object instance, PropertyGrid grid, string bindingPath)
{
PropertyItem propertyItem = new PropertyItem(instance, property, grid, bindingPath);
var binding = new Binding(bindingPath)
{
Source = instance,
ValidatesOnExceptions = true,
ValidatesOnDataErrors = true,
Mode = propertyItem.IsReadOnly ? BindingMode.OneWay : BindingMode.TwoWay
};
propertyItem.SetBinding(PropertyItem.ValueProperty, binding);
propertyItem.Editor = PropertyGridUtilities.GetTypeEditor(propertyItem, grid.EditorDefinitions);
return propertyItem;
}
internal static FrameworkElement GetTypeEditor(PropertyItem propertyItem, EditorDefinitionCollection editorDefinitions)
{
//first check for an attribute editor
FrameworkElement editor = PropertyGridUtilities.GetAttibuteEditor(propertyItem);
//now look for a custom editor based on editor definitions
if (editor == null)
editor = PropertyGridUtilities.GetCustomEditor(propertyItem, editorDefinitions);
//guess we have to use the default editor
if (editor == null)
editor = PropertyGridUtilities.CreateDefaultEditor(propertyItem);
return editor;
}
internal static FrameworkElement GetAttibuteEditor(PropertyItem propertyItem)
{
FrameworkElement editor = null;
var itemsSourceAttribute = GetAttribute<ItemsSourceAttribute>(propertyItem.PropertyDescriptor);
if (itemsSourceAttribute != null)
editor = new ItemsSourceEditor(itemsSourceAttribute).ResolveEditor(propertyItem);
var editorAttribute = GetAttribute<EditorAttribute>(propertyItem.PropertyDescriptor);
if (editorAttribute != null)
{
Type type = Type.GetType(editorAttribute.EditorTypeName);
var instance = Activator.CreateInstance(type);
if (instance is ITypeEditor)
editor = (instance as ITypeEditor).ResolveEditor(propertyItem);
}
return editor;
}
internal static FrameworkElement GetCustomEditor(PropertyItem propertyItem, EditorDefinitionCollection customTypeEditors)
{
FrameworkElement editor = null;
//check for custom editor
if (customTypeEditors.Count > 0)
{
//first check if the custom editor is type based
IEditorDefinition customEditor = customTypeEditors[propertyItem.PropertyType];
if (customEditor == null)
{
//must be property based
customEditor = customTypeEditors[propertyItem.Name];
}
if (customEditor != null)
{
if (customEditor.EditorTemplate != null)
editor = customEditor.EditorTemplate.LoadContent() as FrameworkElement;
}
}
return editor;
}
internal static FrameworkElement CreateDefaultEditor(PropertyItem propertyItem)
{
ITypeEditor editor = null;
if (propertyItem.IsReadOnly)
editor = new TextBlockEditor();
else if (propertyItem.PropertyType == typeof(bool) || propertyItem.PropertyType == typeof(bool?))
editor = new CheckBoxEditor();
else if (propertyItem.PropertyType == typeof(decimal) || propertyItem.PropertyType == typeof(decimal?))
editor = new DecimalUpDownEditor();
else if (propertyItem.PropertyType == typeof(double) || propertyItem.PropertyType == typeof(double?))
editor = new DoubleUpDownEditor();
else if (propertyItem.PropertyType == typeof(int) || propertyItem.PropertyType == typeof(int?))
editor = new IntegerUpDownEditor();
else if (propertyItem.PropertyType == typeof(DateTime) || propertyItem.PropertyType == typeof(DateTime?))
editor = new DateTimeUpDownEditor();
else if ((propertyItem.PropertyType == typeof(Color)))
editor = new ColorEditor();
else if (propertyItem.PropertyType.IsEnum)
editor = new EnumComboBoxEditor();
else if (propertyItem.PropertyType == typeof(TimeSpan))
editor = new TimeSpanEditor();
else if (propertyItem.PropertyType == typeof(FontFamily) || propertyItem.PropertyType == typeof(FontWeight) || propertyItem.PropertyType == typeof(FontStyle) || propertyItem.PropertyType == typeof(FontStretch))
editor = new FontComboBoxEditor();
else if (propertyItem.PropertyType.IsGenericType)
{
if (propertyItem.PropertyType.GetInterface("IList") != null)
{
var t = propertyItem.PropertyType.GetGenericArguments()[0];
if (!t.IsPrimitive && !t.Equals(typeof(String)))
editor = new Microsoft.Windows.Controls.PropertyGrid.Editors.CollectionEditor();
else
editor = new Microsoft.Windows.Controls.PropertyGrid.Editors.PrimitiveTypeCollectionEditor();
}
else
editor = new TextBlockEditor();
}
else
editor = new TextBoxEditor();
return editor.ResolveEditor(propertyItem);
}
}
}

156
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Implementation/PropertyItem.cs

@ -7,6 +7,7 @@ using System.Windows.Data;
using System.Windows.Input;
using Microsoft.Windows.Controls.PropertyGrid.Commands;
using System.Windows.Markup.Primitives;
using System.Collections.Generic;
namespace Microsoft.Windows.Controls.PropertyGrid
{
@ -21,6 +22,8 @@ namespace Microsoft.Windows.Controls.PropertyGrid
#region Properties
public string BindingPath { get; private set; }
#region Category
public static readonly DependencyProperty CategoryProperty = DependencyProperty.Register("Category", typeof(string), typeof(PropertyItem), new UIPropertyMetadata(string.Empty));
@ -32,7 +35,14 @@ namespace Microsoft.Windows.Controls.PropertyGrid
#endregion //Category
public string Description { get { return PropertyDescriptor.Description; } }
#region Desription
public string Description
{
get { return PropertyDescriptor.Description; }
}
#endregion //Desription
#region DisplayName
@ -72,13 +82,12 @@ namespace Microsoft.Windows.Controls.PropertyGrid
#endregion //Editor
#region Instance
private object _instance;
public object Instance
{
get
{
return _instance;
}
get { return _instance; }
private set
{
_instance = value;
@ -86,6 +95,10 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
}
#endregion //Instance
#region IsDataBound
/// <summary>
/// Gets if the property is data bound
/// </summary>
@ -101,6 +114,10 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
}
#endregion //IsDataBound
#region IsDynamicResource
public bool IsDynamicResource
{
get
@ -112,6 +129,47 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
}
#endregion //IsDynamicResource
#region IsExpanded
public static readonly DependencyProperty IsExpandedProperty = DependencyProperty.Register("IsExpanded", typeof(bool), typeof(PropertyItem), new UIPropertyMetadata(false, OnIsExpandedChanged));
public bool IsExpanded
{
get { return (bool)GetValue(IsExpandedProperty); }
set { SetValue(IsExpandedProperty, value); }
}
private static void OnIsExpandedChanged(DependencyObject o, DependencyPropertyChangedEventArgs e)
{
PropertyItem propertyItem = o as PropertyItem;
if (propertyItem != null)
propertyItem.OnIsExpandedChanged((bool)e.OldValue, (bool)e.NewValue);
}
protected virtual void OnIsExpandedChanged(bool oldValue, bool newValue)
{
if (newValue && (Properties == null || Properties.Count == 0))
{
GetChildProperties();
}
}
#endregion IsExpanded
#region HasChildProperties
public static readonly DependencyProperty HasChildPropertiesProperty = DependencyProperty.Register("HasChildProperties", typeof(bool), typeof(PropertyItem), new UIPropertyMetadata(false));
public bool HasChildProperties
{
get { return (bool)GetValue(HasChildPropertiesProperty); }
set { SetValue(HasChildPropertiesProperty, value); }
}
#endregion HasChildProperties
#region HasResourceApplied
public bool HasResourceApplied
{
//TODO: need to find a better way to determine if a StaticResource has been applied to any property not just a style
@ -125,7 +183,16 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
}
public bool IsReadOnly { get { return PropertyDescriptor.IsReadOnly; } }
#endregion //HasResourceApplied
#region IsReadOnly
public bool IsReadOnly
{
get { return PropertyDescriptor.IsReadOnly; }
}
#endregion //IsReadOnly
#region IsSelected
@ -151,7 +218,18 @@ namespace Microsoft.Windows.Controls.PropertyGrid
#endregion //IsSelected
public bool IsWriteable { get { return !IsReadOnly; } }
#region Properties
public static readonly DependencyProperty PropertiesProperty = DependencyProperty.Register("Properties", typeof(PropertyItemCollection), typeof(PropertyItem), new UIPropertyMetadata(null));
public PropertyItemCollection Properties
{
get { return (PropertyItemCollection)GetValue(PropertiesProperty); }
set { SetValue(PropertiesProperty, value); }
}
#endregion //Properties
#region PropertyDescriptor
private PropertyDescriptor _propertyDescriptor;
public PropertyDescriptor PropertyDescriptor
@ -170,9 +248,18 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
}
#endregion //PropertyDescriptor
public PropertyGrid PropertyGrid { get; private set; }
public Type PropertyType { get { return PropertyDescriptor.PropertyType; } }
#region PropertyType
public Type PropertyType
{
get { return PropertyDescriptor.PropertyType; }
}
#endregion //PropertyType
public ICommand ResetValueCommand { get; private set; }
@ -199,6 +286,8 @@ namespace Microsoft.Windows.Controls.PropertyGrid
#endregion //Value
#region ValueSource
/// <summary>
/// Gets the value source.
/// </summary>
@ -214,28 +303,38 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
}
#endregion //ValueSource
#endregion //Properties
#region Constructor
#region Constructors
static PropertyItem()
{
DefaultStyleKeyProperty.OverrideMetadata(typeof(PropertyItem), new FrameworkPropertyMetadata(typeof(PropertyItem)));
}
public PropertyItem(object instance, PropertyDescriptor property, PropertyGrid propertyGrid)
public PropertyItem(object instance, PropertyDescriptor property, PropertyGrid propertyGrid, string bindingPath)
{
PropertyDescriptor = property;
PropertyGrid = propertyGrid;
Instance = instance;
BindingPath = bindingPath;
CommandBindings.Add(new CommandBinding(PropertyItemCommands.ResetValue, ExecuteResetValueCommand, CanExecuteResetValueCommand));
if (!IsReadOnly)
{
TypeConverter converter = PropertyDescriptor.Converter;
if (converter is ExpandableObjectConverter && PropertyDescriptor.GetValue(Instance) != null)
{
HasChildProperties = true;
}
}
CommandBindings.Add(new CommandBinding(PropertyItemCommands.ResetValue, ExecuteResetValueCommand, CanExecuteResetValueCommand));
AddHandler(Mouse.PreviewMouseDownEvent, new MouseButtonEventHandler(PropertyItem_PreviewMouseDown), true);
}
#endregion //Constructor
#endregion //Constructors
#region Event Handlers
@ -269,5 +368,36 @@ namespace Microsoft.Windows.Controls.PropertyGrid
}
#endregion //Commands
#region Methods
private void GetChildProperties()
{
TypeConverter converter = PropertyDescriptor.Converter;
PropertyDescriptorCollection descriptors = null;
if (converter is ExpandableObjectConverter)
descriptors = PropertyDescriptor.GetChildProperties();
var propertyItems = new List<PropertyItem>();
try
{
foreach (PropertyDescriptor descriptor in descriptors)
{
if (descriptor.IsBrowsable)
propertyItems.Add(PropertyGridUtilities.CreatePropertyItem(descriptor, Instance, PropertyGrid, String.Format("{0}.{1}", BindingPath, descriptor.Name)));
}
}
catch (Exception ex)
{
//TODO: handle this some how
}
Properties = PropertyGridUtilities.GetAlphabetizedProperties(propertyItems);
}
#endregion //Methods
}
}

294
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/PropertyGrid/Themes/Generic.xaml

@ -253,7 +253,299 @@
<MenuItem Header="Reset Value" Command="commands:PropertyItemCommands.ResetValue" />
</ContextMenu>
<Style x:Key="SubExpanderStyle" TargetType="{x:Type Expander}">
<Setter Property="Padding" Value="10 0 0 0"/>
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type Expander}">
<Grid>
<Border Visibility="Collapsed" Grid.Row="1" x:Name="ExpandSite" Padding="0 0 0 0">
<Border BorderThickness="0" Margin="0" Padding="0" VerticalAlignment="Stretch" HorizontalAlignment="Stretch">
<ContentPresenter HorizontalAlignment="{TemplateBinding HorizontalContentAlignment}"
VerticalAlignment="{TemplateBinding VerticalContentAlignment}"
Focusable="false" />
</Border>
</Border>
</Grid>
<ControlTemplate.Triggers>
<Trigger Property="IsExpanded" Value="True">
<Setter Property="Visibility" Value="Visible" TargetName="ExpandSite"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<ControlTemplate x:Key="ExtendedPropertyItemTemplate" TargetType="{x:Type local:PropertyItem}">
<ControlTemplate.Resources>
<ContextMenu x:Key="ContextMenu">
<MenuItem Header="Reset Value" Command="commands:PropertyItemCommands.ResetValue"/>
</ContextMenu>
</ControlTemplate.Resources>
<Border ContextMenu="{StaticResource ContextMenu}"
ContextMenuService.Placement="Bottom">
<Grid VerticalAlignment="Center"
HorizontalAlignment="Stretch">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="{Binding NameColumnWidth, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type local:PropertyGrid}}}" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<Border BorderThickness="0.5"
Padding="{Binding Padding, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Expander}}}"
BorderBrush="#FFF0F0F0"
x:Name="PART_Name">
<Grid Margin="7,2,2,2">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="15" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Border Grid.Column="0" Padding="5 0 0 0">
<ToggleButton Template="{StaticResource ExpanderToggleButton}"
IsChecked="{Binding IsExpanded, RelativeSource={RelativeSource TemplatedParent}}"
OverridesDefaultStyle="True" />
</Border>
<TextBlock Grid.Column="1" Text="{Binding DisplayName, RelativeSource={RelativeSource TemplatedParent}}"
HorizontalAlignment="Stretch"
TextTrimming="CharacterEllipsis" />
<Grid Grid.Column="2"
HorizontalAlignment="Right"
Margin="5,0,5,0"
utilities:ContextMenuUtilities.OpenOnMouseLeftButtonClick="True"
ContextMenu="{StaticResource ContextMenu}">
<Image x:Name="_optionsImage"
Width="11"
Height="11"
Stretch="None"
Source="{Binding ValueSource, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource ValueSourceToImagePathConverter}}"
ToolTip="{Binding ValueSource, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource ValueSourceToToolTipConverter}}" />
</Grid>
</Grid>
</Border>
<Border BorderThickness="0.5"
BorderBrush="#FFF0F0F0"
x:Name="PART_Editor"
Grid.Column="2"
Background="Transparent">
<ContentControl Content="{TemplateBinding Editor}"
VerticalAlignment="Center"
Focusable="False"
IsTabStop="False" />
</Border>
<Expander x:Name="ChildPropertyExpander"
Grid.ColumnSpan="3"
Grid.Row="1"
IsExpanded="{TemplateBinding IsExpanded}"
Style="{StaticResource SubExpanderStyle}"
IsEnabled="True">
<ItemsControl ItemsSource="{Binding Properties, RelativeSource={RelativeSource TemplatedParent}}"
IsTabStop="False"
Focusable="False">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<VirtualizingStackPanel />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
</ItemsControl>
</Expander>
</Grid>
</Border>
<ControlTemplate.Triggers>
<DataTrigger Binding="{Binding IsDataBound, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Database11.png"/>
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Databinding"/>
</DataTrigger>
<DataTrigger Binding="{Binding IsDynamicResource, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Resource11.png"/>
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Resource"/>
</DataTrigger>
<DataTrigger Binding="{Binding HasResourceApplied, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Resource11.png"/>
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Resource"/>
</DataTrigger>
<Trigger Property="IsMouseOver" Value="True">
<Setter TargetName="PART_Name" Property="Background" Value="#CED4DF"/>
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter TargetName="PART_Name" Property="Background" Value="#43577B"/>
<Setter TargetName="PART_Name" Property="TextElement.Foreground" Value="White"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
<ControlTemplate x:Key="BasicPropertyItemTemplate" TargetType="{x:Type local:PropertyItem}">
<ControlTemplate.Resources>
<ContextMenu x:Key="ContextMenu">
<MenuItem Header="Reset Value" Command="commands:PropertyItemCommands.ResetValue"/>
</ContextMenu>
</ControlTemplate.Resources>
<Border ContextMenu="{StaticResource ContextMenu}" ContextMenuService.Placement="Bottom">
<Grid VerticalAlignment="Center" HorizontalAlignment="Stretch">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="{Binding NameColumnWidth, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type local:PropertyGrid}}}" />
<ColumnDefinition Width="*" />
</Grid.ColumnDefinitions>
<Border BorderThickness="0.5"
Padding="{Binding Padding, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Expander}}}"
BorderBrush="#FFF0F0F0"
Grid.Column="0"
x:Name="PART_Name">
<Grid Margin="7,2,2,2">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="15" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<TextBlock Grid.Column="1" Text="{Binding DisplayName, RelativeSource={RelativeSource TemplatedParent}}"
HorizontalAlignment="Stretch"
TextTrimming="CharacterEllipsis" />
<Grid Grid.Column="2" HorizontalAlignment="Right" Margin="5,0,5,0"
utilities:ContextMenuUtilities.OpenOnMouseLeftButtonClick="True"
ContextMenu="{StaticResource ContextMenu}">
<Image x:Name="_optionsImage" Width="11" Height="11" Stretch="None"
Source="{Binding ValueSource, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource ValueSourceToImagePathConverter}}"
ToolTip="{Binding ValueSource, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource ValueSourceToToolTipConverter}}"/>
</Grid>
</Grid>
</Border>
<Border x:Name="PART_Editor" BorderThickness="0.5" BorderBrush="#FFF0F0F0" Grid.Column="1" Background="Transparent">
<ContentControl Content="{TemplateBinding Editor}" VerticalAlignment="Center" Focusable="False" IsTabStop="False"/>
</Border>
</Grid>
</Border>
<ControlTemplate.Triggers>
<DataTrigger Binding="{Binding IsDataBound, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Database11.png"/>
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Databinding"/>
</DataTrigger>
<DataTrigger Binding="{Binding IsDynamicResource, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Resource11.png"/>
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Resource"/>
</DataTrigger>
<DataTrigger Binding="{Binding HasResourceApplied, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Resource11.png"/>
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Resource"/>
</DataTrigger>
<Trigger Property="IsMouseOver" Value="True">
<Setter TargetName="PART_Name" Property="Background" Value="#CED4DF"/>
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter TargetName="PART_Name" Property="Background" Value="#43577B"/>
<Setter TargetName="PART_Name" Property="TextElement.Foreground" Value="White"/>
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
<!--<Style TargetType="{x:Type local:PropertyItem}">
<Setter Property="BorderBrush" Value="#FFF0F0F0"/>
<Setter Property="BorderThickness" Value="1"/>
<Setter Property="Focusable" Value="True"/>
<Setter Property="IsTabStop" Value="False"/>
<Style.Triggers>
<Trigger Property="HasChildProperties" Value="True">
<Setter Property="Template" Value="{StaticResource ExtendedPropertyItemTemplate}"/>
</Trigger>
<Trigger Property="HasChildProperties" Value="False">
<Setter Property="Template" Value="{StaticResource BasicPropertyItemTemplate}"/>
</Trigger>
</Style.Triggers>
</Style>-->
<Style TargetType="{x:Type local:PropertyItem}">
<Setter Property="BorderBrush" Value="#FFF0F0F0" />
<Setter Property="BorderThickness" Value="1" />
<Setter Property="Focusable" Value="True"/>
<Setter Property="IsTabStop" Value="False" />
<Setter Property="Template">
<Setter.Value>
<ControlTemplate TargetType="{x:Type local:PropertyItem}">
<Border Background="White" ContextMenu="{Binding AdvancedOptionsMenu, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=local:PropertyGrid}}" ContextMenuService.Placement="Bottom">
<Grid VerticalAlignment="Center" HorizontalAlignment="Stretch">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="{Binding NameColumnWidth, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type local:PropertyGrid}}}"/>
<ColumnDefinition Width="*"/>
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition />
<RowDefinition />
</Grid.RowDefinitions>
<Border BorderThickness="0.5" BorderBrush="#FFF0F0F0" x:Name="PART_Name">
<Grid Margin="2,2,2,2">
<Grid.ColumnDefinitions>
<ColumnDefinition Width="15" />
<ColumnDefinition Width="*" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Border Grid.Column="0" Padding="0">
<ToggleButton Template="{StaticResource ExpanderToggleButton}" OverridesDefaultStyle="True"
IsChecked="{Binding IsExpanded, RelativeSource={RelativeSource TemplatedParent}}"
Visibility="{Binding HasChildProperties, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource BooleanToVisibilityConverter}}"/>
</Border>
<TextBlock Grid.Column="1" Text="{Binding DisplayName, RelativeSource={RelativeSource TemplatedParent}}" HorizontalAlignment="Stretch" TextTrimming="CharacterEllipsis"/>
<Grid Grid.Column="2" HorizontalAlignment="Right" Margin="5,0,5,0" Visibility="{Binding ShowAdvancedOptions, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=local:PropertyGrid}, Converter={StaticResource BooleanToVisibilityConverter}}"
utilities:ContextMenuUtilities.OpenOnMouseLeftButtonClick="True"
ContextMenu="{Binding AdvancedOptionsMenu, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=local:PropertyGrid}}" >
<Image x:Name="_optionsImage" Width="11" Height="11"
Source="{Binding ValueSource, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource ValueSourceToImagePathConverter}}"
ToolTip="{Binding ValueSource, RelativeSource={RelativeSource TemplatedParent}, Converter={StaticResource ValueSourceToToolTipConverter}}" />
</Grid>
</Grid>
</Border>
<Border BorderThickness="0.5" BorderBrush="#FFF0F0F0" x:Name="PART_Editor" Grid.Column="1" Background="Transparent">
<ContentControl Content="{TemplateBinding Editor}" VerticalAlignment="Center" Focusable="False" IsTabStop="False" />
</Border>
<Expander x:Name="ChildPropertyExpander" Grid.ColumnSpan="2" Grid.Row="1" IsExpanded="{TemplateBinding IsExpanded}" Style="{StaticResource SubExpanderStyle}" IsEnabled="True">
<ItemsControl ItemsSource="{Binding Properties, RelativeSource={RelativeSource TemplatedParent}}" IsTabStop="False" Focusable="False">
<ItemsControl.ItemsPanel>
<ItemsPanelTemplate>
<VirtualizingStackPanel />
</ItemsPanelTemplate>
</ItemsControl.ItemsPanel>
</ItemsControl>
</Expander>
</Grid>
</Border>
<ControlTemplate.Triggers>
<DataTrigger Binding="{Binding IsDataBound, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Database11.png" />
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Databinding" />
</DataTrigger>
<DataTrigger Binding="{Binding IsDynamicResource, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Resource11.png" />
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Resource" />
</DataTrigger>
<DataTrigger Binding="{Binding HasResourceApplied, RelativeSource={RelativeSource Self}}" Value="True">
<Setter TargetName="_optionsImage" Property="Source" Value="/WPFToolkit.Extended;component/PropertyGrid/Images/Resource11.png" />
<Setter TargetName="_optionsImage" Property="ToolTip" Value="Resource" />
</DataTrigger>
<Trigger Property="IsMouseOver" Value="True">
<Setter TargetName="PART_Name" Property="Background" Value="#CED4DF" />
</Trigger>
<Trigger Property="IsSelected" Value="True">
<Setter TargetName="PART_Name" Property="Background" Value="#43577B" />
<Setter TargetName="PART_Name" Property="TextElement.Foreground" Value="White" />
</Trigger>
</ControlTemplate.Triggers>
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
<!--<Style TargetType="{x:Type local:PropertyItem}">
<Setter Property="BorderBrush" Value="#FFF0F0F0" />
<Setter Property="BorderThickness" Value="1" />
<Setter Property="Focusable" Value="True"/>
@ -317,7 +609,7 @@
</ControlTemplate>
</Setter.Value>
</Setter>
</Style>
</Style>-->
<Style TargetType="{x:Type local:PropertyGrid}">
<Setter Property="AdvancedOptionsMenu" Value="{StaticResource DefaultAdvancedOptionsMenu}" />

1
ExtendedWPFToolkitSolution/Src/WPFToolkit.Extended/WPFToolkit.Extended.csproj

@ -271,6 +271,7 @@
<Compile Include="PropertyGrid\Implementation\PropertyItemCollection.cs" />
<Compile Include="PropertyGrid\Implementation\PropertyItem.cs" />
<Compile Include="PropertyGrid\Implementation\Commands\PropertyItemCommands.cs" />
<Compile Include="PropertyGrid\Implementation\PropertyGridUtilities.cs" />
<Compile Include="RichTextBoxFormatBar\IRichTextBoxFormatBar.cs" />
<Compile Include="RichTextBoxFormatBar\RichTextBoxFormatBar.xaml.cs">
<DependentUpon>RichTextBoxFormatBar.xaml</DependentUpon>

Loading…
Cancel
Save