本文介绍了WPF子菜单样式的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个ContextMenu样式和一个MenuItem样式,它们在顶部菜单上都可以正常工作.问题是,如果我向菜单项添加子菜单,则子菜单的样式不正确.看来您现在只能设置菜单项的样式,而不能设置实际的子菜单,因此不能替换IsMouseOver样式(它默认为Windows上启用的任何主题).

I have a ContextMenu style and a MenuItem style, both of which are working properly on the top menu. The problem is if I add a submenu to a menu item, then the submenu is not being styled properly. It looks like you can only style the menuitem at this point, and not the actual sub menu so you can't replace the IsMouseOver styling (it just defaults to whatever theme is enabled on windows).

我已经搜索了,我能找到的最接近的东西是MSDN上的该论坛帖子 http://social.msdn.microsoft.com/Forums/en-US/wpf/thread/69269d23-f97c-42e3-a9dd-0e7c0ba49bdd ?prof = required ,但实际上也不能正确回答该问题,因为他的示例与我遇到的问题相同.任何帮助,将不胜感激!预先感谢.

I've searched and searched, the closest thing I can find is this forum post on MSDN http://social.msdn.microsoft.com/Forums/en-US/wpf/thread/69269d23-f97c-42e3-a9dd-0e7c0ba49bdd?prof=required but it doesn't actually answer the question correctly either, as his example has the same problem I'm running in to. Any help would be appreciated! Thanks in advance.

周杰伦,这就是我正在做的.这是一些代码,位于UserControl.Resources中,作为我对象的顶部.

Jay, that's what I'm doing. Here's some code, in UserControl.Resources as the top of my object.

    <Style TargetType="{x:Type MenuItem}">
        <Setter Property="Background" Value="#0f3c5a"></Setter>
        <Setter Property="Foreground" Value="White"></Setter>
        <Style.Triggers>
            <Trigger Property="IsHighlighted" Value="True">
                <Setter Property="Background" Value="Black"></Setter>
            </Trigger>
            <Trigger Property="IsEnabled" Value="False">
                <Setter Property="Foreground" Value="LightGray"></Setter>
            </Trigger>
        </Style.Triggers>
    </Style>
    <Style TargetType="{x:Type ContextMenu}">
        <Setter Property="OverridesDefaultStyle" Value="True"/>
        <Setter Property="SnapsToDevicePixels" Value="True"/>
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type ContextMenu}">

                    <!--Here is where you change the border thickness to zero on the menu-->
                    <Border BorderThickness="0" x:Name="Border"  >
                     <StackPanel ClipToBounds="True" Orientation="Vertical"
                     IsItemsHost="True"/>
                     </Border>
                    <ControlTemplate.Triggers>
                        <Trigger Property="IsMouseOver" Value="true">
                            <Setter TargetName="Border" Property="Background" Value="#5082a4" />
                        </Trigger>
                    </ControlTemplate.Triggers>
          </ControlTemplate>
        </Setter.Value>
      </Setter>
    </Style>

然后是类似的菜单

<ContextMenu Closed="ContextMenu_Closed"  >
    <MenuItem  Command="k:Window1.NewCommand" >
       <MenuItem  Command="k:Window1.DeleteCommand"/>
    </MenuItem>
    ...

NewCommand层上的所有内容均已正确设置样式,进入NewCommand内以查看DeleteCommand时,MenuItem本身已正确设置样式,但是实际菜单默认为Windows主题样式,到目前为止,我看不到有任何方法可以覆盖.最重要的部分是获取子菜单的IsMouseOver,以保持与主菜单结构相同的外观.

Everything on the NewCommand layer is styled properly, going inside NewCommand to view DeleteCommand the MenuItem itself is styled properly, but the actual menu is defaulting to the Windows theme styling and I see no way over overwriting that so far. The most important part is to get the IsMouseOver of submenu's to maintain the same look and feel as the main menu structure.

推荐答案

如所承诺的,这是代码.感谢Jay的帮助,引导我朝正确的方向最终在MSDN上找到答案 http://msdn.microsoft.com/zh-cn/library/ms752296.aspx MenuItem和ContextMenu控制基本菜单的样式,其他两个用于子菜单项.杰伊的方法也许奏效了,但不幸的是我无法理解.不过,这非常有效,并且可能允许对子菜单样式进行更多控制.

As promised, here's the code. Thanks for your help Jay, lead me in the right direction to finally find an answer on MSDN http://msdn.microsoft.com/en-us/library/ms752296.aspx MenuItem and ContextMenu control the styling for the base menu, and the other two are for the submenu items. Jay's way may have worked, but I couldn't get it to unfortunately. This works perfectly though, and probably allows for much more control over the submenus styling.

    <UserControl.Resources>

    <!-- Separator -->
    <Style TargetType="{x:Type Separator}"
           x:Key="SeparatorStyle">
        <Setter Property="Height"
                Value="1" />
        <Setter Property="Background"
                Value="#0f3c5a" />
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type Separator}">
                    <Rectangle Height="{TemplateBinding Height}"
                               Fill="White" />
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>

    <!--Outer menu items-->
    <Style TargetType="{x:Type MenuItem}">
        <Setter Property="Background"
                Value="#0f3c5a"></Setter>
        <Setter Property="Foreground"
                Value="White"></Setter>
        <Style.Triggers>
            <Trigger Property="IsHighlighted"
                     Value="True">
                <Setter Property="Background"
                        Value="Black"></Setter>
            </Trigger>
            <Trigger Property="IsEnabled"
                     Value="False">
                <Setter Property="Foreground"
                        Value="LightGray"></Setter>
            </Trigger>
        </Style.Triggers>
    </Style>

    <!-- Outer menu -->
    <Style TargetType="{x:Type ContextMenu}">
        <Setter Property="OverridesDefaultStyle"
                Value="True" />
        <Setter Property="SnapsToDevicePixels"
                Value="True" />
        <Setter Property="Template">
            <Setter.Value>
                <ControlTemplate TargetType="{x:Type ContextMenu}">

                    <!--Here is where you change the border thickness to zero on the menu-->
                    <Border BorderThickness="0"
                            x:Name="Border"
                            Background="Transparent">
                        <StackPanel ClipToBounds="True"
                                    Orientation="Vertical"
                                    IsItemsHost="True" />
                    </Border>
                    <ControlTemplate.Triggers>
                        <Trigger Property="IsMouseOver"
                                 Value="true">
                            <Setter TargetName="Border"
                                    Property="Background"
                                    Value="#0f3c5a" />
                        </Trigger>
                    </ControlTemplate.Triggers>
                </ControlTemplate>
            </Setter.Value>
        </Setter>
    </Style>

    <!-- SubmenuItem -->

    <ControlTemplate x:Key="{x:Static MenuItem.SubmenuItemTemplateKey}"
                     TargetType="{x:Type MenuItem}">
        <Border Name="Border">
            <Grid>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="Auto"
                                      SharedSizeGroup="Icon" />
                    <ColumnDefinition Width="*" />
                    <ColumnDefinition Width="Auto"
                                      SharedSizeGroup="Shortcut" />
                    <ColumnDefinition Width="13" />
                </Grid.ColumnDefinitions>
                <ContentPresenter Name="Icon"
                                  Margin="6,0,6,0"
                                  VerticalAlignment="Center"
                                  ContentSource="Icon" />
                <Border Name="Check"
                        Width="13"
                        Height="13"
                        Visibility="Collapsed"
                        Margin="6,0,6,0"
                        Background="#0f3c5a"
                        BorderThickness="1"
                        BorderBrush="#5082a4">
                    <Path Name="CheckMark"
                          Width="7"
                          Height="7"
                          Visibility="Hidden"
                          SnapsToDevicePixels="False"
                          Stroke="#5082a4"
                          StrokeThickness="2"
                          Data="M 0 0 L 7 7 M 0 7 L 7 0" />
                </Border>
                <ContentPresenter Name="HeaderHost"
                                  Grid.Column="1"
                                  ContentSource="Header"
                                  RecognizesAccessKey="True" />
                <TextBlock x:Name="InputGestureText"
                           Grid.Column="2"
                           Text="{TemplateBinding InputGestureText}"
                           Margin="5,2,0,2"
                           DockPanel.Dock="Right" />
            </Grid>
        </Border>
        <ControlTemplate.Triggers>
            <Trigger Property="Icon"
                     Value="{x:Null}">
                <Setter TargetName="Icon"
                        Property="Visibility"
                        Value="Hidden" />
            </Trigger>
            <Trigger Property="IsChecked"
                     Value="true">
                <Setter TargetName="CheckMark"
                        Property="Visibility"
                        Value="Visible" />
            </Trigger>
            <Trigger Property="IsCheckable"
                     Value="true">
                <Setter TargetName="Check"
                        Property="Visibility"
                        Value="Visible" />
                <Setter TargetName="Icon"
                        Property="Visibility"
                        Value="Hidden" />
            </Trigger>
            <Trigger Property="IsHighlighted"
                     Value="true">
                <Setter TargetName="Border"
                        Property="Background"
                        Value="#5082a4" />
            </Trigger>
            <Trigger Property="IsEnabled"
                     Value="false">
                <Setter Property="Foreground"
                        Value="#0f3c5a" />
            </Trigger>
        </ControlTemplate.Triggers>
    </ControlTemplate>

    <!-- SubmenuHeader -->

    <ControlTemplate x:Key="{x:Static MenuItem.SubmenuHeaderTemplateKey}"
                     TargetType="{x:Type MenuItem}">
        <Border Name="Border">
            <Grid>
                <Grid.ColumnDefinitions>
                    <ColumnDefinition Width="Auto"
                                      SharedSizeGroup="Icon" />
                    <ColumnDefinition Width="*" />
                    <ColumnDefinition Width="Auto"
                                      SharedSizeGroup="Shortcut" />
                    <ColumnDefinition Width="13" />
                </Grid.ColumnDefinitions>
                <ContentPresenter Name="Icon"
                                  Margin="6,0,6,0"
                                  VerticalAlignment="Center"
                                  ContentSource="Icon" />
                <ContentPresenter Name="HeaderHost"
                                  Grid.Column="1"
                                  ContentSource="Header"
                                  RecognizesAccessKey="True" />
                <TextBlock x:Name="InputGestureText"
                           Grid.Column="2"
                           Text="{TemplateBinding InputGestureText}"
                           Margin="5,2,2,2"
                           DockPanel.Dock="Right" />
                <Path Grid.Column="3"
                      HorizontalAlignment="Center"
                      VerticalAlignment="Center"
                      Data="M 0 0 L 0 7 L 4 3.5 Z"
                      Fill="#0f3c5a" />
                <Popup Name="Popup"
                       Placement="Right"
                       HorizontalOffset="-4"
                       IsOpen="{TemplateBinding IsSubmenuOpen}"
                       AllowsTransparency="True"
                       Focusable="False"
                       PopupAnimation="Fade">
                    <Border Name="SubmenuBorder"
                            SnapsToDevicePixels="True"
                            Background="#0f3c5a"
                            BorderBrush="#0f3c5a"
                            BorderThickness="1">
                        <StackPanel IsItemsHost="True"
                                    KeyboardNavigation.DirectionalNavigation="Cycle" />
                    </Border>
                </Popup>
            </Grid>
        </Border>

        <ControlTemplate.Triggers>
            <Trigger Property="Icon"
                     Value="{x:Null}">
                <Setter TargetName="Icon"
                        Property="Visibility"
                        Value="Collapsed" />
            </Trigger>
            <Trigger Property="IsHighlighted"
                     Value="true">
                <Setter TargetName="Border"
                        Property="Background"
                        Value="#5082a4" />
            </Trigger>
            <Trigger SourceName="Popup"
                     Property="Popup.AllowsTransparency"
                     Value="True">
                <Setter TargetName="SubmenuBorder"
                        Property="CornerRadius"
                        Value="4" />
                <Setter TargetName="SubmenuBorder"
                        Property="Padding"
                        Value="0,3,0,3" />
            </Trigger>
            <Trigger Property="IsEnabled"
                     Value="false">
                <Setter Property="Foreground"
                        Value="#0f3c5a" />
            </Trigger>
        </ControlTemplate.Triggers>
    </ControlTemplate>

这篇关于WPF子菜单样式的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

08-31 03:59