WPF ComboBox ItemsSource Binding Patterns and Selected Value Retrieval

The correct combination of DisplayMemberPath, SelectedItem, SelectedValue, and SelectedValuePath depends on the element type bound to ItemsSource. This article covers the five main patterns.

Overview

In WPF’s ComboBox, the configuration of DisplayMemberPath, ItemTemplate, SelectedItem, SelectedValue, and SelectedValuePath varies depending on the element type of the collection bound to ItemsSource. This article organizes the representative binding patterns and explains how to select the appropriate properties for each case.


Prerequisites / Environment


Problem

When the element type of the collection bound to ItemsSource changes, the method for retrieving the selected value also changes. For example, binding a list of strings differs from binding a list of objects that each have an ID and a display name: the ViewModel property type and the required XAML properties are different in each case. Without understanding this distinction, the selected value may not be reflected, or the initial selection may fail to appear.


Cause / Background

The ComboBox exposes three selection-related properties:

Property Returns Primary use
SelectedItem The element itself from ItemsSource Pass the whole object to the ViewModel
SelectedValue The value of the property named by SelectedValuePath Retrieve only a specific field such as an ID
SelectedIndex The zero-based index of the selected row Manage position only

When ItemsSource holds strings, SelectedItem returns a string. When ItemsSource holds objects and SelectedValuePath is set, SelectedValue returns the value of the specified property. The appropriate binding target depends on the data structure, so the configuration must be aligned accordingly.


Solution

Before looking at implementations, choose the selection properties based on the element type of ItemsSource:

This approach keeps the ViewModel property type aligned with the ComboBox configuration and reduces missed initial selections or update failures.


Implementation

Pattern A: String List

When ItemsSource is ObservableCollection<string>, DisplayMemberPath is unnecessary. Binding SelectedItem to a string property in the ViewModel is sufficient.

<ComboBox ItemsSource="{Binding Regions}"
          SelectedItem="{Binding SelectedRegion}" />

The corresponding ViewModel implementation is as follows.

public ObservableCollection<string> Regions { get; } = new()
{
    "Northeast", "Midwest", "South", "West"
};

private string? _selectedRegion;
public string? SelectedRegion
{
    get => _selectedRegion;
    set { _selectedRegion = value; OnPropertyChanged(); }
}

Binding SelectedItem to a type other than string (for example, int) results in a type mismatch and the binding will not reflect the selection.


Pattern B: Object List + DisplayMemberPath + SelectedItem

When ItemsSource is ObservableCollection<T> and the entire selected object is needed in the ViewModel, specify the display property with DisplayMemberPath and bind SelectedItem to a property of type T.

<ComboBox ItemsSource="{Binding Departments}"
          DisplayMemberPath="Name"
          SelectedItem="{Binding SelectedDepartment}" />

The above XAML displays the Name property of each Department object while binding the entire selected Department to SelectedDepartment. The model and ViewModel definitions are as follows.

public class Department
{
    public int Id { get; set; }
    public string Name { get; set; } = string.Empty;
}

public ObservableCollection<Department> Departments { get; } = new()
{
    new Department { Id = 1, Name = "Sales" },
    new Department { Id = 2, Name = "Engineering" },
    new Department { Id = 3, Name = "Administration" },
};

private Department? _selectedDepartment;
public Department? SelectedDepartment
{
    get => _selectedDepartment;
    set { _selectedDepartment = value; OnPropertyChanged(); }
}

After selection, any field such as SelectedDepartment.Id or SelectedDepartment.Name is accessible. Holding the whole object in the ViewModel makes it straightforward to reference multiple fields later.


Pattern C: Object List + DisplayMemberPath + SelectedValuePath

This pattern applies when only a specific field — such as an ID — needs to be stored in the ViewModel. Specify the desired property name in SelectedValuePath and bind SelectedValue to a property of the matching type.

<ComboBox ItemsSource="{Binding Departments}"
          DisplayMemberPath="Name"
          SelectedValuePath="Id"
          SelectedValue="{Binding SelectedDepartmentId}" />

The corresponding ViewModel property that holds the selected Id is defined as follows.

private int _selectedDepartmentId;
public int SelectedDepartmentId
{
    get => _selectedDepartmentId;
    set { _selectedDepartmentId = value; OnPropertyChanged(); }
}

If the type of SelectedValue does not match the type of the property named by SelectedValuePath, the selection will not be reflected. SelectedItem and SelectedValue can coexist; updating one automatically updates the other.


Pattern D: Custom Display with ItemTemplate

When multiple fields need to appear in a single row, or when an icon is included alongside text, use ItemTemplate. Both DisplayMemberPath and ItemTemplate can be set at the same time, but ItemTemplate takes precedence and DisplayMemberPath is ignored. For custom display, use ItemTemplate only and avoid combining it with DisplayMemberPath.

<ComboBox ItemsSource="{Binding Employees}"
          SelectedItem="{Binding SelectedEmployee}">
    <ComboBox.ItemTemplate>
        <DataTemplate>
            <StackPanel Orientation="Horizontal">
                <TextBlock Text="{Binding Id}" Width="40" Foreground="Gray"/>
                <TextBlock Text="{Binding Name}" />
            </StackPanel>
        </DataTemplate>
    </ComboBox.ItemTemplate>
</ComboBox>

The Employee model referenced by this XAML is defined as follows.

public class Employee
{
    public int Id { get; set; }
    public string Name { get; set; } = string.Empty;
}

When different layouts are needed for the collapsed selection display versus the expanded dropdown list, use ContentTemplate alongside ItemContainerStyle instead of relying on ItemTemplate alone.


Pattern E: Enum List

For a fixed set of choices defined by an enumeration, generating the collection in the ViewModel with Enum.GetValues is more maintainable than using ObjectDataProvider in XAML.

The ViewModel generates the enum values as follows.

public enum Priority { Low, Medium, High }

public IEnumerable<Priority> Priorities { get; }
    = (Priority[])Enum.GetValues(typeof(Priority));

private Priority _selectedPriority = Priority.Medium;
public Priority SelectedPriority
{
    get => _selectedPriority;
    set { _selectedPriority = value; OnPropertyChanged(); }
}

The XAML binds ItemsSource and SelectedItem to these ViewModel properties as follows.

<ComboBox ItemsSource="{Binding Priorities}"
          SelectedItem="{Binding SelectedPriority}" />

SelectedItem is of type Priority. Retrieving the underlying integer value via SelectedValue and SelectedValuePath is possible, but an explicit cast such as (int)SelectedPriority expresses the intent more clearly.


Notes


Alternatives / Comparison

Pattern ItemsSource type Selected value retrieval Best suited for
A: String list ObservableCollection<string> SelectedItem (string) Choices are plain labels only
B: Object + SelectedItem ObservableCollection<T> SelectedItem (T) Multiple fields needed after selection
C: Object + SelectedValuePath ObservableCollection<T> SelectedValue (specified property type) Only a specific field such as an ID is needed
D: ItemTemplate ObservableCollection<T> SelectedItem (T) Multiple fields displayed in a single row
E: Enum IEnumerable<TEnum> SelectedItem (TEnum) Selecting from a fixed enumeration

Summary

The appropriate ComboBox implementation pattern is determined by the type bound to ItemsSource.

Most initial-value failures trace back to either Equals-based mismatch or incorrect assignment order relative to ItemsSource. Using SelectedValuePath, or ensuring the exact same instance is referenced, resolves the majority of these cases.