2016-08-03 3 views
3

Я изучаю WPF, и контроль RibbonComboBox дал мне несколько недель головных болей.Styling RibbonComboBox содержимое

У меня наконец-то появилась базовая функциональность. Теперь я застрял в том, что должно быть тривиально, но, как и все остальные WPF, нет.

Вот часть моего XAML:

<RibbonGroup Header="Category"> 
    <RibbonComboBox Label="Category:" HorizontalContentAlignment="Left" SelectionBoxWidth="250"> 
     <RibbonGallery ColumnsStretchToFill="True" SelectedItem="{Binding SelectedCategory}"> 
      <RibbonGalleryCategory DisplayMemberPath="Text" MaxColumnCount="1" ItemsSource="{Binding Categories}"> 
      </RibbonGalleryCategory> 
     </RibbonGallery> 
    </RibbonComboBox> 
    <RibbonComboBox Label="Subcategory:" HorizontalContentAlignment="Left" SelectionBoxWidth="250"> 
     <RibbonGallery MaxColumnCount="1" ColumnsStretchToFill="True" SelectedItem="{Binding SelectedSubcategory}"> 
      <RibbonGalleryCategory DisplayMemberPath="Text" ItemsSource="{Binding Subcategories}"> 
      </RibbonGalleryCategory> 
     </RibbonGallery> 
    </RibbonComboBox> 
    <RibbonButton Label="Edit Categories" Command="local:EditCommands.Categories" SmallImageSource="Images\categories_sm.png" ToolTipTitle="Edit Categories" ToolTipDescription="Add, edit or delete categories and subcategories" ToolTipImageSource="Images\categories_sm.png"></RibbonButton> 
</RibbonGroup> 

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

Как вы можете видеть, я добавил некоторые атрибуты MaxColumnCount и ColumnStretchToFill. Они изначально похоже на работу, но ...

  1. Когда код обновляет содержимое, установка ColumnStretchToFill, кажется, отбрасывают, а строка выбора снова только по ширине текста выбора.

  2. Существует иерархия RibbonComboBox, RibbonGallery и RibbonGalleryCategory. Я не мог понять, почему. Более одного из этих элементов имеют атрибуты MaxColumnCount и ColumnStretchToFill (а также другие атрибуты комментариев). Как узнать, для какого элемента я должен установить эти атрибуты?

ответ

2

Для достижения своей цели, сделайте следующее:

<Ribbon> 
    <RibbonGroup Header="Category" Height="100"> 
     <RibbonComboBox Label="Category:" > 
      <RibbonGallery SelectedItem="{Binding SelectedCategory, Mode=TwoWay, IsAsync=True}" > 
       <RibbonGalleryCategory ItemsSource="{Binding Categories}" DisplayMemberPath="Name" ColumnsStretchToFill="True" MaxColumnCount="1" IsSharedColumnSizeScope="True" /> 
      </RibbonGallery> 
     </RibbonComboBox> 
     <RibbonComboBox Label="Subcategory:" > 
      <RibbonGallery SelectedItem="{Binding SelectedSubCategory}" > 
       <RibbonGalleryCategory ItemsSource="{Binding SelectedCategory.SubCategories}" DisplayMemberPath="Name" ColumnsStretchToFill="True" MaxColumnCount="1" IsSharedColumnSizeScope="True"/> 
      </RibbonGallery> 
     </RibbonComboBox> 
     <RibbonButton Label="Edit Categories" ToolTipTitle="Edit Categories" ToolTipDescription="Add, edit or delete categories and subcategories" Command="{Binding AddCatCommand}"></RibbonButton> 
    </RibbonGroup> 
</Ribbon> 

Вы должны установить IsSharedColumnSizeScope="True" для того, чтобы предметы тянутся к ComboBox. Это обеспечивает правильную компоновку.

Приведенный выше пример показывает вам разницу, так как я не установил это свойство на ваш второй ComboBox.

Надеюсь, это поможет.

Редактировать

Вот простой Модель

public class Category { 
     private ObservableCollection<Category> _subCats = new ObservableCollection<Category>(); 
     public string Name { get; set; } 

     public ObservableCollection<Category> SubCategories => this._subCats; 
    } 

Теперь некоторые ViewModel -stuff я поставил в CodeBehind

public partial class Window1 : INotifyPropertyChanged { 

     private Category _selectedCategory; 
     private ObservableCollection<Category> _categories = new ObservableCollection<Category>(); 
     private Category _selectedSubCategory; 

     public Window1() { 
      InitializeComponent(); 
      var cat = new Category() { Name = "Category 1" }; 
      cat.SubCategories.Add(new Category { Name = "Cat 1 - Subcat 1" }); 
      cat.SubCategories.Add(new Category { Name = "Cat 1 - Subcat 2" }); 
      cat.SubCategories.Add(new Category { Name = "Cat 1 - Subcat 3" }); 
      var cat2 = new Category() { Name = "Category 2" }; 
      cat2.SubCategories.Add(new Category { Name = "Cat 2 - Subcat 1" }); 
      cat2.SubCategories.Add(new Category { Name = "Cat 2 - Subcat 2" }); 
      var cat3 = new Category() { Name = "Category 3" }; 
      cat2.SubCategories.Add(new Category { Name = "Cat 3 - Subcat 2" }); 
      this.Categories.Add(cat); 
      this.Categories.Add(cat2); 
      this.Categories.Add(cat3); 
      this.SelectedCategory = this.Categories.First(); 
      this.DataContext = this; 
     } 

     public ICommand AddCatCommand => new RelayCommand(x => { 
      var newCat = new Category { Name = "Im New" }; 
      newCat.SubCategories.Add(new Category { Name = "I'm new too" }); 
      this.Categories.Add(newCat); 
     }); 

     public Category SelectedCategory { 
      get { return _selectedCategory; } 
      set { 
       if (Equals(value, _selectedCategory)) return; 
       _selectedCategory = value; 
       OnPropertyChanged(); 
      } 
     } 

     public Category SelectedSubCategory { 
      get { return _selectedSubCategory; } 
      set { 
       if (Equals(value, _selectedSubCategory)) return; 
       _selectedSubCategory = value; 
       OnPropertyChanged(); 
      } 
     } 

     public ObservableCollection<Category> Categories => this._categories; 

     public event PropertyChangedEventHandler PropertyChanged; 

     [NotifyPropertyChangedInvocator] 
     protected virtual void OnPropertyChanged([CallerMemberName] string propertyName = null) { 
      PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); 
     } 
    } 

зазор

Как вы могли заметить, ни одна из используемых коллекций не имеет сеттера, что предотвращает их переопределение. Если ItemsSource используется, связанный сбор должен не сброса, просто очищается .Clear() и новые элементы, добавленные в качестве кнопки в приведенном выше примере покажет вам

+0

Не знаю, почему мне нужно установить три свойства, чтобы заставить их принять полную ширину , Но, в то время как ваши изменения делают это, после того, как я поднимаю 'OnPropertyChanged' для' ItemsSource', и список обновляется, подсветка больше не потребляет полную ширину. Значит, это не помогло. –

+0

Можете ли вы добавить материал для просмотра? Поэтому я могу воспроизвести лучше. Кроме того, я не могу воспроизвести ваше поведение. – lokusking

+0

Я могу попытаться что-то собрать, но сейчас есть много кода, и все это незавершенное и переходное. Чтобы уточнить, если вы добавите кнопку, которая запускает код для установки нового 'ItemsSource', строка выделения по-прежнему занимает всю ширину выпадающего списка для вас? (Обратите внимание, что в моем исходном XAML я устанавливаю атрибуты 'HorizontalContentAlignment' и' SelectionBoxWidth' для моего 'RibbonComboBox'.) –

Смежные вопросы