WPF DataGridComboBoxColumn не отображает текст, если он не находится в ItemsSource

В моем приложении C# WPF я программно добавляю ComboBoxColumn в DataGrid:

public static DataGridComboBoxColumn getCboCol(string colName, Binding textBinding)
{
    List<string> statusItemsList = new StatusStrList();

    DataGridComboBoxColumn cboColumn = new DataGridComboBoxColumn();
    cboColumn.Header = colName;
    cboColumn.SelectedItemBinding = textBinding;
    cboColumn.ItemsSource = statusItemsList;

    return cboColumn;
}

Если элемент в содержащем DataGrid содержит текст, которого нет в моем StatusStrList, он не будет отображаться.

Пример. Если мой StatusStrList содержит A, B, C, а элемент DataGrid имеет X, X не будет отображаться в виде текста в поле со списком.

Как это исправить?

Заранее спасибо, Кристиан


person Christian St.    schedule 21.08.2013    source источник
comment
Есть ли особая причина, по которой этот подход используется вместо чистого XAML?   -  person James Sampica    schedule 21.08.2013
comment
@Jim Ни столбцы, ни свойства элементов для привязки неизвестны во время компиляции.   -  person Christian St.    schedule 21.08.2013


Ответы (1)


DataGridComboBoxColumn недостаточно динамичен, чтобы делать что-то подобное, но вы можете использовать DataGridTemplateColumn. Код ниже должен обеспечить необходимую вам функциональность. Он работает, используя CellTemplate, содержащий TextBlock, который легко отображает элемент, которого не было бы в ItemsSource из ComboBox. При переходе в режим редактирования появится ComboBox, содержащий все элементы списка.

        DataGridTemplateColumn cboColumn = new DataGridTemplateColumn();
        cboColumn.Header = colName;

        //DataTemplate for CellTemplate
        DataTemplate cellTemplate = new DataTemplate();
        FrameworkElementFactory txtBlkFactory = new FrameworkElementFactory(typeof(TextBlock));
        txtBlkFactory.SetValue(TextBlock.TextProperty, textBinding);
        cellTemplate.VisualTree = txtBlkFactory;
        cboColumn.CellTemplate = cellTemplate;

        //DataTemplate for CellEditingTemplate
        DataTemplate editTemplate = new DataTemplate();
        FrameworkElementFactory cboFactory = new FrameworkElementFactory(typeof(ComboBox));
        cboFactory.SetValue(ComboBox.TextProperty, textBinding);
        cboFactory.SetValue(ComboBox.ItemsSourceProperty, statusItemsList);
        cboFactory.SetValue(ComboBox.IsEditableProperty, true);

        MouseEventHandler handler = new MouseEventHandler(delegate(object sender, MouseEventArgs args)
        {
            ComboBox cboBox = (ComboBox)sender;
            cboBox.IsDropDownOpen = true;
        });

        cboFactory.AddHandler(ComboBox.MouseEnterEvent, handler);

        editTemplate.VisualTree = cboFactory;
        cboColumn.CellEditingTemplate = editTemplate;
person James Sampica    schedule 21.08.2013
comment
Спасибо, скоро попробую. Подходит ли ваш код для этого вопроса? - person Christian St.; 22.08.2013
comment
@Christian Я обновил его, чтобы он соответствовал требованиям вашего другого вопроса. Я не совсем уверен, как вы хотите, чтобы он срабатывал, но я думаю, что довольно ясно, как это изменить. Вы также можете удалить код из своего предыдущего вопроса, все это обрабатывается здесь. - person James Sampica; 23.08.2013