PropertyGrid for WPF
プロパティの定義

Property definitions constitute the properties of a bound object and define their appearance in the property grid. These properties are automatically generated when you bind the PropertyGrid control with an object. However, you can customize them as well. Let us explore more about the auto generated properties and methods and how to customize them in the following sections.

Auto Generated Property Definitions

By default when you set the SelectedObject property of PropertyGrid to bind to an object, the members listed in the PropertyGrid control get automatically generated. This is because the AutoGenerateProperties property is set to True by default. However, you can set the AutoGenerateProperties property to False if you do not want properties to be generated automatically. You might do so if you want only a few properties to be editable or you want to customize the way properties appear in the PropertyGrid window.

 Back to Top

Add and Remove Property Items from PropertyGrid

You can add or remove items from the PropertyGrid at design time and runtime. At design time, you can add or remove a property using the PropertyAttributes Collection Editor available under Data category in the Properties window.

The following GIF shows adding and removing properties from the PropertyGrid at runtime.

Adding and removing property items from PropertyGrid

The following steps demonstrates how to add and remove properties from the PropertyGrid at runtime.

  1. In XAML view, add the following code inside <Grid></Grid> tag to create a UI displaying a TextBlock, a TextBox, two Labels, two ListBox controls (one to display textbox properties and the other to display the textbox properties shown in the PropertyGrid), a PropertyGrid control bound to the TextBox, and two button controls (one to add properties and other to remove properties from the PropertyGrid at runtime).
    XAML
    コードのコピー
    <Border Grid.Row="0" Grid.Column="0">
        <StackPanel Margin="10" Orientation="Horizontal">
            <TextBlock Margin="5" FontWeight="Bold">Selected Object :</TextBlock>
            <TextBox x:Name="_txtBox" Margin="5" Width="200" Height="20" Text="TextBox"></TextBox>
        </StackPanel>
    </Border>
    <Border Grid.Column="0" Grid.Row="1">
        <Grid Margin="5,70,38,-319">
            <Grid.RowDefinitions>
                <RowDefinition></RowDefinition>
                <RowDefinition Height="auto"></RowDefinition>
            </Grid.RowDefinitions>
            <Label Content="Select TextBox Properties to display in PropertyGrid"></Label>
            <!--listbox used for displaying textbox properties-->
            <ListBox x:Name="_propertyListBox"
                 SelectedIndex="-1"
                 SelectionMode="Extended" Margin="0,25,5,10" Grid.RowSpan="2"/>
    
            <Button x:Name="btnAdd" Margin="0,68,10,-58" 
                    Grid.Row="1"
                    Height="30"
                    Click="AddItemsToPropertyGrid"
                    ToolTip="Adds selected items to PropertyGrid" 
                    Cursor="Hand"
                    Content="Add Selected Items to Property Grid"></Button>
        </Grid>
    </Border>
    <Border Grid.Row="1" Grid.ColumnSpan="3" Margin="334,0,299,0">
        <c1:C1PropertyGrid x:Name="_propertyGrid" ShowDescription="True" SelectedObject="{Binding ElementName=_txtBox}" AutoGenerateProperties="False" FontSize="15"  ShowResetButton="True" Margin="-37,93,-157,-379"/>
    </Border>
    
    <Border Grid.Column="2" Grid.Row="1">
        <Grid>
            <Grid.ColumnDefinitions>
                <ColumnDefinition/>
            </Grid.ColumnDefinitions>
            <Grid.RowDefinitions>
                <RowDefinition></RowDefinition>
                <RowDefinition Height="auto"></RowDefinition>
            </Grid.RowDefinitions>
            <Label Content="Select TextBox Properties to remove from PropertyGrid" Margin="493,57,-493,-69" Grid.Row="1"/>
            <!--listbox used for displaying textbox properties that are displayed in propertygrid-->
            <ListBox x:Name="_addedPropertyListBox"
                 SelectedIndex="-1"
                 DisplayMemberPath="Name"
                 SelectionMode="Extended" Margin="501,84,-448,-317" Grid.Row="1"/>
    
            <Button x:Name="btnRemove" Margin="501,385,-453,-375" 
                    Grid.Row="1"
                    Height="30"
                    Click="RemoveItemsFromPropertyGrid"
                    ToolTip="Remove selected items from PropertyGrid" 
                    Cursor="Hand"
                    Content="Remove Selected Items from Property Grid"/>
    
        </Grid>
    </Border>
    
  2. Switch to the Code view, add the following code to display the TextBox properties in the ListBox control.
    C#
    コードのコピー
    public PropertyDefinition()
    {
        InitializeComponent();
        InitPropertiesListBox();
    }
    
    private void InitPropertiesListBox()
    {
        // ListBox内にTextBox プロパティを表示します
        var properties = _txtBox.GetType().GetProperties().OrderBy(x => x.Name);
        _propertyListBox.DisplayMemberPath = "Name";
        _propertyListBox.ItemsSource = properties;
    }
    
  3. Add the following code to add the selected properties from the ListBox to the PropertyGrid on button click and remove the selected properties from the PropertyGrid at runtime.
    C#
    コードのコピー
    private void AddItemsToPropertyGrid(object sender, RoutedEventArgs e)
    {
        foreach (PropertyInfo property in _propertyListBox.SelectedItems)
        {
            if (_propertyGrid.PropertyAttributes.Any(x => x.MemberName == property.Name))
                continue;
    
            var category = property.GetCustomAttribute<CategoryAttribute>(); // gets the category of the property
    
            var propertyAttribute = new PropertyAttribute()
            {
                MemberName = property.Name,
                Category = category != null ? category.Category : null
            };
    
            // プロパティグリッドに追加します
            _propertyGrid.PropertyAttributes.Add(propertyAttribute);
    
            // 表示する項目をリストボックスに追加します
            _addedPropertyListBox.Items.Add(property);
        }
    }
    
    private void RemoveItemsFromPropertyGrid(object sender, RoutedEventArgs e)
    {
        foreach (var property in _addedPropertyListBox.SelectedItems.Cast<PropertyInfo>().ToList())
        {
            var propertyAttribute = _propertyGrid.PropertyAttributes.FirstOrDefault(x => x.MemberName == property.Name);
    
            if (propertyAttribute != null)
            {
                // プロパティグリッドから削除します
                _propertyGrid.PropertyAttributes.Remove(propertyAttribute);
                _addedPropertyListBox.Items.Remove(property);
            }
        }
    }
    

Back to Top

Customize Property Definitions

PropertyGrid allows you to customize the property definitions of any object bound to it. It allows you to define, add, remove or customize the properties easily at design time using the PropertyAttributes Collection Editor. The following image shows the PropertyAttributes Collection Editor with property attributes.

PropertyAttributes Collection Editor of WPF PropertyGrid

PropertyGrid provides you several attributes that can be used to customize the display properties and content of items that are displayed in the property grid. These attributes are listed below:

To set custom property items manually, you need to set the AutoGenerateProperties property to False and set the custom definition of property items through code. In the following example, we set the property definitions for the Button items bound to the PropertyGrid.

XAML
コードのコピー
<!--C1PropertyGridのSelectedObjectとして使用されます。-->
<Button x:Name="btnDemo" Height="30" Width="100" Margin="5" HorizontalAlignment="Left" Content="Sample Button"></Button>

<!-- カスタムプロパティアイテムを手動で設定する前に、C1PropertyGridのAutoGeneratePropertiesプロパティをfalseに設定する必要があります。-->
<c1:C1PropertyGrid x:Name="_propertyGrid" ShowDescription="True" 
    SelectedObject="{Binding ElementName=btnDemo}"
    AutoGenerateProperties="False" Grid.Row="1" Margin="5">


    <c1:C1PropertyGrid.PropertyAttributes>                    
    <!-- プロパティアイテムのカスタム定義。-->
                    
        <!--ボタンのContentプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="Content" Category="Appearance"></c1:PropertyAttribute>

        <!--ボタンのBackgroundプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="Background" Category="Appearance"></c1:PropertyAttribute>

        <!--ボタンのForegroundプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="Foreground" Category="Appearance"></c1:PropertyAttribute>

        <!--ボタンのBorderBrushプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="BorderBrush" Category="Appearance"></c1:PropertyAttribute>

        <!--ボタンのBorderThicknessプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="BorderThickness" Category="Appearance"></c1:PropertyAttribute>

        <!--ボタンのVisibilityプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="Visibility" Category="Appearance"></c1:PropertyAttribute>

        <!--ボタンのContentプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="ClickMode" Category="Interaction"></c1:PropertyAttribute>

        <!--ボタンのIsEnabledプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="IsEnabled" Category="Interaction"></c1:PropertyAttribute>

        <!--ボタンのClickMode プロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="Height" Category="Layout"></c1:PropertyAttribute>

        <!--ボタンのIsEnabledプロパティの定義-->
        <c1:PropertyAttribute Browsable="True" MemberName="Width" Category="Layout"></c1:PropertyAttribute>

   </c1:C1PropertyGrid.PropertyAttributes>
</c1:C1PropertyGrid>

Back to Top