c# - 绑定(bind) MenuItem 的 ItemsSource 和 IsChecked 以获取 WPF 中的可检查项列表

标签 c# wpf binding menuitem

我正在尝试设置一个 MenuItem,它将有一个可以选择的页码子菜单。我想将 ItemsSource 绑定(bind)到页码列表(实际上是使用创建列表的转换器绑定(bind)到 PageCount),然后绑定(bind)每个 MenuItem 的 IsChecked 属性 在 PageIndex 的子菜单中。我的问题是第二个绑定(bind),因为它也需要一个转换器,但该转换器需要知道 MenuItem 代表的页码,但我不知道如何将该信息传递给转换器。到目前为止,这是我尝试过的方法。

<MenuItem Header="_Goto Page" 
          ItemsSource="{Binding 
                        Path=CurrentImage.PageCount, 
                        Converter={StaticResource countToList}}">
    <MenuItem.ItemContainerStyle>
        <Style TargetType="MenuItem">
            <Setter Property="IsCheckable" 
                    Value="True"/>
            <Setter Property="IsChecked" 
                    Value="{Binding 
                            ElementName=MainWindow,
                            Path=CurrentImage.PageIndex, 
                            Mode=TwoWay,
                            Converter={StaticResource pageNumChecked},
                            ConverterParameter={Binding 
                                                RelativeSource={RelativeSource Self}, 
                                                Path=Content}}"/>
        </Style>
    </MenuItem.ItemContainerStyle>
</MenuItem>

当然,问题是 ConverterParameter 不能绑定(bind),因为它不是 DependencyProperty。所以我的问题是如何传递我需要的信息,或者有其他方法可以做到这一点。

注意:我已经尝试将 MenuItem 放入 ListBox 中,就绑定(bind)而言效果非常好,但会导致子菜单的行为以一种非标准的方式。也就是说,当您打开子菜单时,整个 ListBox 都被视为一个 MenuItem

编辑

这就是我到目前为止所做的工作。我尝试绑定(bind)到隐藏的 ListBox 但是当我将 MenuItem.ItemsSource 绑定(bind)到“ListBox.Items”时,我得到了 int 的列表而不是我需要获取 IsSelected 属性的 ListBoxItem 列表。因此,我最终采用了 Quartermeister 的建议,即使用 MultiBinding 获取 IsChecked 属性以在 OneWay 模式下绑定(bind)到 PageIndex。为了处理另一个方向,我在 Click 事件上使用了一个事件处理程序。值得注意的是,起初我将 IsCheckable 设置为 true 并使用 Checked 事件,但结果是一些奇怪的行为。

<MenuItem x:Name="GotoPageMenuItem" Header="_Goto Page"
          ItemsSource="{Binding Path=CurrentImage.PageCount, 
                                Converter={StaticResource countToList}}">
    <MenuItem.ItemContainerStyle>
        <Style TargetType="MenuItem">
            <Setter Property="IsCheckable" 
                    Value="False"/>
            <EventSetter Event="Click"
                         Handler="GotoPageMenuItem_Click"/>
            <Setter Property="IsChecked">
                <Setter.Value>
                    <MultiBinding Converter="{StaticResource pageNumChecked}"
                                              Mode="OneWay">
                        <Binding RelativeSource="{RelativeSource FindAncestor, 
                                                  AncestorType={x:Type Window}}" 
                                                  Path="CurrentImage.PageIndex" 
                                                  Mode="OneWay"/>
                        <Binding RelativeSource="{RelativeSource Self}" 
                                                  Path="Header"
                                                  Mode="OneWay"/>
                    </MultiBinding>
                </Setter.Value>
            </Setter>
        </Style>
    </MenuItem.ItemContainerStyle>
</MenuItem>

这是 GotoPageMenuItem_Click 代码

private void GotoPageMenuItem_Click(object sender, RoutedEventArgs e)
{
    var item = sender as MenuItem;
    if (item != null)
    {
        //If the item is already checked then we don't need to do anything
        if (!item.IsChecked)
        {
            var pageNum = (int)item.Header;
            CurrentImage.PageIndex = (pageNum - 1);
        }
    }
}

最佳答案

听起来您正在尝试构建动态菜单来控制每个菜单项的选中状态。
我扩展了我编写的一些代码,以使用 MVVM 模式在 WPF 中构建动态菜单,并添加了检查逻辑。

这是 XAML:

<Menu DockPanel.Dock="Top">
    <MenuItem ItemsSource="{Binding Commands}"
              Header="_Item Container Style">
        <MenuItem.ItemContainerStyle>
            <Style TargetType="{x:Type MenuItem}">
                <Setter Property="IsCheckable" Value="True"/>
                <Setter Property="IsChecked"  Value="{Binding Path=Checked}"/>
                <Setter Property="Header" Value="{Binding Path=Text}" />
                <Setter Property="Command" Value="{Binding Path=Command}" />
                <Setter Property="CommandParameter" Value="{Binding Path=Parameter}" />
            </Style>
        </MenuItem.ItemContainerStyle>
    </MenuItem>
</Menu>

这是 View 模型:

public class MainViewModel : ViewModelBase
{
  public MainViewModel()
  {
     GoCommand = new DelegateCommand<object>(OnGoCommand, CanGoCommand);
     LoadCommands();
  }

  private List<MyCommand> _commands = new List<MyCommand>();
  public List<MyCommand> Commands
  {
     get { return _commands; }
  }

  private void LoadCommands()
  {
     MyCommand c1 = new MyCommand { Command = GoCommand, Parameter = "1", Text = "Menu1", Checked = true};
     MyCommand c2 = new MyCommand { Command = GoCommand, Parameter = "2", Text = "Menu2", Checked = true };
     MyCommand c3 = new MyCommand { Command = GoCommand, Parameter = "3", Text = "Menu3", Checked = false };
     MyCommand c4 = new MyCommand { Command = GoCommand, Parameter = "4", Text = "Menu4", Checked = true };
     MyCommand c5 = new MyCommand { Command = GoCommand, Parameter = "5", Text = "Menu5", Checked = false };
     _commands.Add(c1);
     _commands.Add(c2);
     _commands.Add(c3);
     _commands.Add(c4);
     _commands.Add(c5);
  }

  public ICommand GoCommand { get; private set; }
  private void OnGoCommand(object obj)
  {
  }

  private bool CanGoCommand(object obj)
  {
     return true;
  }
}

这是保存命令的类:

  public class MyCommand
  {
     public ICommand Command { get; set; }
     public string Text { get; set; }
     public string Parameter { get; set; }
     public Boolean Checked { get; set; }
  }

关于c# - 绑定(bind) MenuItem 的 ItemsSource 和 IsChecked 以获取 WPF 中的可检查项列表,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3113967/

相关文章:

c# - 访问列表中的对象 C#

c# - 线程池可用线程显示非常高的数字

wpf - 两端固定宽度渐变的LinearGradientBrush

c# - MVVM Light - subview 和对话框

ruby - Ruby 中的 block 绑定(bind)

c# - 如何将控件绑定(bind)到 MVVM 中的 visualbrush?

c# - 图表,显示列表中的数据

C#。引用扩展方法的引用返回委托(delegate)

wpf - 我可以为 WPF ComboBox 中的所选项目使用与下拉部分中的项目不同的模板吗?

jquery - 如何将 jQuery 事件添加到所有当前和 future 的元素?