WPF XAML定义的MenuItem重用开始工作,然后消失 [英] WPF XAML defined MenuItem reuse starts working, then disappears

查看:99
本文介绍了WPF XAML定义的MenuItem重用开始工作,然后消失的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下简单代码尝试在两个单独的菜单上重用Window.Resources中定义的MenuItem.

The following simple code attempts to reuse a MenuItem defined in the Window.Resources on two separate Menus.

<Window x:Class="WpfApplication.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:collections="clr-namespace:System.Collections;assembly=mscorlib"
        Title="MainWindow" Height="350" Width="525">
  <Window.Resources>
    <collections:ArrayList x:Key="menuItemValues">
       <MenuItem Header="First"/>
       <MenuItem Header="Second"/>
       <MenuItem Header="Third"/>
    </collections:ArrayList>
    <MenuItem x:Key="menuItem" x:Shared="False"
              ItemsSource="{StaticResource menuItemValues}"
              Header="Shared menu item"/>
  </Window.Resources>
  <StackPanel>
    <Menu HorizontalAlignment="Left" VerticalAlignment="Top">
      <StaticResource ResourceKey="menuItem"/>
      <StaticResource ResourceKey="menuItem"/>
    </Menu>
  </StackPanel>
</Window>

开始时效果很好,当您第一次选择菜单时,一切看起来都不错.第一个菜单具有所需的MenuItems

This starts out great and when you first select the menus, all looks well. The first menu has the desired MenuItems,

第二个也是:

但是当您导航回到第一个菜单时,MenuItems消失了:

But when you navigate back to the first menu, the MenuItems disappear:

有人可以解释为什么菜单消失以及使该菜单起作用的方法吗?

Can someone explain why the menu disappears and a way to get this to work?

这是在调查另一个另一种方法中讨论的策略问题,它似乎可以解决问题,直到您再次导航回到菜单,然后它消失了.

This was discovered while investigating another SO question that was getting an exception. I tried to use a strategy discussed on another SO question and it seemed to solve the problem until you navigate back to the menu a second time and it disappears.

我已在2台单独的计算机上重现了此问题:

I have reproduced this issue on 2 separate machines:

  1. Win 10,VS2013 Ult V12.0.40629.00更新5,.NET V4.6.0138
  2. Win 7,VS2013 Prem V12.0.31101.00更新4,.NET V4.5.51209

推荐答案

之所以发生这种情况是因为,尽管顶级MenuItemx:Shared="False",而集合中的MenuItem对象却没有.它们分别在ArrayList集合中声明一次,然后在创建的menuItem对象的每个实例中重复使用.

This is happening because, while the top-level MenuItem is x:Shared="False", the MenuItem objects in your collection are not. They are declared once each in the ArrayList collection, and then reused in each instance of the menuItem object that's created.

要使代码正常工作,您需要强制WPF创建新实例.一种选择是将x:Shared="False"也应用于集合.例如:

To get the code to work, you'll need to force WPF to create new instances. One option would be to apply the x:Shared="False" to the collection as well. For example:

<Window x:Class="WpfApplication.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:collections="clr-namespace:System.Collections;assembly=mscorlib"
        Title="MainWindow" Height="350" Width="525">
  <Window.Resources>
    <collections:ArrayList x:Key="menuItemValues" x:Shared="False">
       <MenuItem Header="First"/>
       <MenuItem Header="Second"/>
       <MenuItem Header="Third"/>
    </collections:ArrayList>
    <MenuItem x:Key="menuItem" x:Shared="False"
              ItemsSource="{StaticResource menuItemValues}"
              Header="Shared menu item"/>
  </Window.Resources>
  <StackPanel>
    <Menu HorizontalAlignment="Left" VerticalAlignment="Top">
      <StaticResource ResourceKey="menuItem"/>
      <StaticResource ResourceKey="menuItem"/>
    </Menu>
  </StackPanel>
</Window>

当然,只要给项目赋予简单的Header值,就可以通过提供string值而不是MenuItem值来使用默认的MenuItem模板行为.这使您可以重用集合本身(没有潜在的重用能力):

Of course, given that the items are simply given Header values, you could just use the default MenuItem templating behavior, by providing string values instead of MenuItem values. This allows you to reuse the collection itself (which has no underlying inability for reuse):

<Window x:Class="WpfApplication.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:s="clr-namespace:System;assembly=mscorlib"
        xmlns:collections="clr-namespace:System.Collections;assembly=mscorlib"
        Title="MainWindow" Height="350" Width="525">
  <Window.Resources>
    <collections:ArrayList x:Key="menuItemValues">
      <s:String>First</s:String>
      <s:String>Second</s:String>
      <s:String>Third</s:String>
    </collections:ArrayList>
    <MenuItem x:Key="menuItem" x:Shared="False"
              ItemsSource="{StaticResource menuItemValues}"
              Header="Shared menu item"/>
  </Window.Resources>
  <StackPanel>
    <Menu HorizontalAlignment="Left" VerticalAlignment="Top">
      <StaticResource ResourceKey="menuItem"/>
      <StaticResource ResourceKey="menuItem"/>
    </Menu>
  </StackPanel>
</Window>

这篇关于WPF XAML定义的MenuItem重用开始工作,然后消失的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆