Как я могу соединиться, данные связали список MenuItems к другому MenuItem в WPF?

Вы также могли бы рассмотреть то, что Вы пытаетесь сделать - при хорошем форматировании текста, который ввели люди, Вы могли бы полагать, что фильтр как Скидка с цены позволил Вашим пользователям отформатировать свой текст, не открывая кучу проблем, которая является HTML. Вы знаете, как он здесь при Переполнении стека.

6
задан Dave Clemmer 11 August 2011 в 17:03
поделиться

3 ответа

Я попытался использовать CompositeCollection , предложенный Кентом Бугартом, но мне не удалось заставить его работать из-за ошибки в wpf , не позволяющей использовать привязку RelativeSource в CollectionContainer .

Решение, которое я использовал, - иметь RecentFiles в собственном подменю, привязанном к Collection через Свойство ItemsSource .

Я действительно хотел иметь список в меню «Файл», но я думаю, что это лучший вариант ...

Править

На основе этой статьи Я создал собственный и более общий MenuItemList :

public class MenuItemList : Separator {

  #region Private Members

  private MenuItem m_Parent;
  private List<MenuItem> m_InsertedMenuItems;

  #endregion

  public MenuItemList() {
    Loaded += (s, e) => HookFileMenu();
  }

  private void HookFileMenu() {
    m_Parent = Parent as MenuItem;
    if (m_Parent == null) {
      throw new InvalidOperationException("Parent must be a MenuItem");
    }
    if (ParentMenuItem == m_Parent) {
      return;
    }
    if (ParentMenuItem != null) {
      ParentMenuItem.SubmenuOpened -= _FileMenu_SubmenuOpened;
    }
    ParentMenuItem = m_Parent;
    ParentMenuItem.SubmenuOpened += _FileMenu_SubmenuOpened;
  }

  private void _FileMenu_SubmenuOpened(object sender, RoutedEventArgs e) {
    DataBind();
  }

  #region Properties

  public MenuItem ParentMenuItem { get; private set; }

  #region ItemsSource

  /// <summary>
  /// ItemsSource Dependency Property
  /// </summary>
  public static readonly DependencyProperty ItemsSourceProperty =
      DependencyProperty.Register("ItemsSource", typeof(IEnumerable), typeof(MenuItemList),
          new FrameworkPropertyMetadata(null,
              new PropertyChangedCallback(OnItemsSourceChanged)));

  /// <summary>
  /// Gets or sets a collection used to generate the content of the <see cref="MenuItemList"/>. This is a dependency property.
  /// </summary>
  public IEnumerable ItemsSource {
    get { return (IEnumerable) GetValue(ItemsSourceProperty); }
    set { SetValue(ItemsSourceProperty, value); }
  }

  /// <summary>
  /// Handles changes to the ItemsSource property.
  /// </summary>
  private static void OnItemsSourceChanged(DependencyObject d, DependencyPropertyChangedEventArgs e) {
    ((MenuItemList) d).OnItemsSourceChanged(e);
  }

  /// <summary>
  /// Provides derived classes an opportunity to handle changes to the ItemsSource property.
  /// </summary>
  protected virtual void OnItemsSourceChanged(DependencyPropertyChangedEventArgs e) {
    DataBind();
  }

  #endregion

  #region ItemContainerStyle

  /// <summary>
  /// ItemsContainerStyle Dependency Property
  /// </summary>
  public static readonly DependencyProperty ItemContainerStyleProperty =
      DependencyProperty.Register("ItemContainerStyle", typeof(Style), typeof(MenuItemList),
          new FrameworkPropertyMetadata((Style) null));

  /// <summary>
  /// Gets or sets the <see cref="System.Windows.Style"/> that is applied to the container element generated for each item. This is a dependency property.
  /// </summary>
  public Style ItemContainerStyle {
    get { return (Style) GetValue(ItemContainerStyleProperty); }
    set { SetValue(ItemContainerStyleProperty, value); }
  }

  #endregion

  #endregion

  private void DataBind() {
    RemoveMenuItems();
    InsertMenuItems();
  }

  private void RemoveMenuItems() {
    if (m_InsertedMenuItems != null) {
      foreach (var menuItem in m_InsertedMenuItems) {
        ParentMenuItem.Items.Remove(menuItem);
      }
    }
  }

  private void InsertMenuItems() {
    if (ItemsSource == null) {
      return;
    }
    if (ParentMenuItem != null) {
      m_InsertedMenuItems = new List<MenuItem>();
      int iMenuItem = ParentMenuItem.Items.IndexOf(this);
      foreach (var item in ItemsSource) {
        var menuItem = new MenuItem();
        menuItem.DataContext = item;
        menuItem.Style = ItemContainerStyle;
        ParentMenuItem.Items.Insert(++iMenuItem, menuItem);
        m_InsertedMenuItems.Add(menuItem);
      }
    }
  }

}

Он далек от совершенства, но у меня он работает. Не стесняйтесь комментировать ...

4
ответ дан 9 December 2019 в 22:37
поделиться

«Странное смещение» - это MenuItem . Родительский MenuItem уже создает для вас дочерний MenuItem , но ваш DataTemplate добавляет второй. Попробуй это:

6
ответ дан 9 December 2019 в 22:37
поделиться

Попробуйте вместо этого использовать HierarchicalDataTemplate с внутренним ContentPresenter. Взгляните на этот SO-ответ для получения более подробной информации .

1
ответ дан 9 December 2019 в 22:37
поделиться
Другие вопросы по тегам:

Похожие вопросы: