Запретить/Блокировать выделение выделенного элемента combobox в wpf

Я пишу приложение, в котором я хотел бы отключить несколько элементов в ComboBox, а также хочу запретить/заблокировать выбор отключенных элементов. Обратите внимание, что ComboBox в главном окне имеет другой ComboBox как элемент ComboBox Item init (который определяется во время выполнения с помощью селектора шаблонов данных).

С приведенным ниже кодом я могу отключить ComboBox в ComboBox, но это не помешает пользователю выбрать этот отключенный элемент ComboBox. Любая помощь в запрете/блоке выбора отключенных элементов будет полезна.

Ниже приведены фрагменты кода

ComboBox в главном окне:

<Grid>
    <ComboBox HorizontalAlignment="Left" VerticalAlignment="Top" 
              Width="120" Margin="87.2,44.8,0,0" 
              ItemsSource="{Binding Cars}" 
              ItemsPanel="{DynamicResource ItemsPanelTemplateHorizontal}"
              ItemTemplateSelector="{StaticResource QualityComboBoxTemplateSelector}"
              SelectedItem="{Binding SelectedItm}"/>
</Grid>

Селектор шаблонов данных:

public class QualityComboBoxTemplateSelector : DataTemplateSelector
{
    public override DataTemplate SelectTemplate(object item, DependencyObject container)
    {
        var element = container as FrameworkElement;

        var dataTemplate = element.FindResource(((item is string) && item.Equals("Ferrari")) ?
                                                       "DataTemplateTopLevelCombobox2" : "DataTemplateTopLevelCombobox1") as DataTemplate;

        return dataTemplate;
    }
}

Шаблоны данных для выше ComboBox:

<DataTemplate x:Key="DataTemplateTopLevelCombobox1">
    <Border BorderBrush="Black" BorderThickness="1" >
        <TextBlock HorizontalAlignment="Left" 
                   TextWrapping="Wrap" Text="{Binding}"     
                   VerticalAlignment="Top"/>
    </Border>
</DataTemplate>

<DataTemplate x:Key="DataTemplateTopLevelCombobox2">
    <Border Width="100">
        <ComboBox Text="Custom" Height="21.96"
        ItemsSource="{Binding DataContext.Models, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}}}"
        IsEnabled="{Binding DataContext.EnableCombo, RelativeSource={RelativeSource FindAncestor, AncestorType={x:Type Window}}}" />
    </Border>
</DataTemplate>

Ответ 1

Это можно сделать, установив IsEnabled свойство ComboBoxItem в false;

Таким образом, каждый элемент в ComboBox ItemSource (т.е. Cars в вашем случае) может быть объектом, имеющим какое-либо свойство (скажем IsSelectable), указывающим, следует ли включать или отключать его, а затем использовать его со стилем, чтобы сделать элемент не выбирается. что-то вроде этого -

<Style TargetType="ComboBoxItem"> 
   <Setter Property="IsEnabled" Value="{Binding IsSelectable}"/> 
</Style> 

Update:

<Grid>
    <ComboBox
        Width="120"
        Margin="87.2,44.8,0,0"
        HorizontalAlignment="Left"
        VerticalAlignment="Top"
        ItemTemplateSelector="{StaticResource QualityComboBoxTemplateSelector}"
        ItemsPanel="{DynamicResource ItemsPanelTemplateHorizontal}"
        ItemsSource="{Binding Cars}"
        SelectedItem="{Binding SelectedItm}">
        <ComboBox.ItemContainerStyle>
            <Style TargetType="ComboBoxItem">
                <Setter
                    Property="IsEnabled"
                    Value="{Binding IsSelectable}" />
            </Style>
        </ComboBox.ItemContainerStyle>
    </ComboBox>
</Grid>

Ответ 2

Чтобы решить проблему, указанную @JordyBoom.

ItemsContainerGenerator не генерирует элементы, пока раскрывающееся меню не открывается хотя бы один раз.

Итак, если вы откроете раскрывающийся список и закроете его снова в обработчике событий, загруженных окнами, тогда все должно работать нормально с мышью, а также с выбором клавиатуры.

    public MainWindow()
    {
        InitializeComponent();
        this.Loaded += new RoutedEventHandler(onLoaded);
    }

    private void onLoaded(object sender, RoutedEventArgs e)
    {
         cmbx.IsDropDownOpen = true;
         cmbx.IsDropDownOpen = false;
    }

source: WPF: блокировка элементов со списком - также при доступе с помощью клавиатуры