XAML 从WPF功能区创建一个“面板”区域?

kxeu7u2r  于 2023-09-28  发布在  其他
关注(0)|答案(4)|浏览(98)

WPF功能区(System.Windows.Controls.Ribbon)包含许多控件,您可以将这些控件添加到功能区中,这些控件具有“下拉”样式行为,单击控件的主按钮将显示一个新区域。
示例:RibbonMenuButtonRibbonSplitButtonRibbonMenuButtonRibbonGallery等。
然而,据我所知,所有这些都是为了向你展示一个事物列表 *,用户可以从中进行选择 *。但是,*是否有任何方法来显示一个“面板”区域,这是 * 不可选择 ,在其上可以放置其他控件?
作为一个例子,这里是一个截图从MS Outlook:

上面的红色区域本身不是列表中的选择。相反,它有一个自定义控件(表大小选择器)。
但是蓝色的项目是可选择的项目,其功能类似于传统菜单。
这是我感兴趣的红色区域。
(我不知道Outlook是否使用WPF功能区编码,这一点也不重要-我只是用它来说明我正在寻找的东西。
注意-我并不是想复制这个Outlook表选择器特别是,它只是一个例子的方式,你可能会使用一个不可选择的'面板'区域内的下拉区域。

iovurdzv

iovurdzv1#

Microsoft RibbonMenuButton / RibbonSplitButton不支持Windows中的自定义控件。
即使我们通过改变RibbonMenuItem / RibbonGalleryItem的内容来做到这一点,我们仍然会在鼠标悬停时在这些控件周围获得选择装饰
最好的方法是使用RibbonToggleButton和弹出控件的组合,如下所示
然后你可以在弹出控件中放置任何你想要的自定义控件

<StackPanel Orientation="Vertical">
<RibbonToggleButton
            x:Name="yAxis"
            Label="Y Axis"
            SmallImageSource="..\Images\ChartYAxis16.png"
            LargeImageSource="..\Images\ChartYAxis32.png"
            RibbonTwoLineText.HasTwoLines="True"
            RibbonTwoLineText.PathData="M 0 0 L 2.5 3 L 5 0 Z">
        </RibbonToggleButton>
        <Popup
            IsOpen="{Binding IsChecked, ElementName=yAxis}">
            <mycontrols:AnyControl/>
        </Popup>
    </StackPanel>

当然,您可能需要以编程方式处理切换按钮关闭,方法是每当用户在切换按钮或切换弹出窗口之外单击时取消选中切换按钮

umuewwlo

umuewwlo2#

我一直在看类似的文档,最终在Visual Studio 2022上通过反复试验开发了这个解决方案。
我让RibbonSplitButton生成一个可以动态加载按钮的区域,使用以下XAML代码...

<RibbonSplitButton x:Name="btnColor" Height="21" Width="40" Margin="-139,-9,139,9" SmallImageSource="images/font-color.png" ToolTip="Font Color" >
    <RibbonMenuItem x:Name="itmDefaultColor">
        <RibbonMenuItem.Header>
            <StackPanel Orientation="Horizontal">
                <Rectangle x:Name="rctDefaultColor" Width="13" Height="13" Fill="Transparent" Stroke="Black" Margin="-25,0,15,0"/>
                <TextBlock Text="Default Color"/>
            </StackPanel>
        </RibbonMenuItem.Header>
    </RibbonMenuItem>
    <RibbonGallery x:Name="galAllColorSwatches" ScrollViewer.VerticalScrollBarVisibility="Disabled">
        <RibbonGallery.Resources>
            <Style TargetType="Button">
                <EventSetter Event="UIElement.PreviewMouseLeftButtonDown" Handler="Button_PreviewMouseLeftButtonDown" />
                <EventSetter Event="PreviewKeyDown" Handler="Button_PreviewKeyDown" />
                <Style.Triggers>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter Property="BorderBrush" Value="White"/>
                    </Trigger>
                    <Trigger Property="IsFocused" Value="True">
                        <Setter Property="BorderBrush" Value="White"/>
                    </Trigger>
                </Style.Triggers>
            </Style>
            <Style TargetType="Rectangle">
                <Style.Triggers>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter Property="Stroke" Value="White"/>
                    </Trigger>
                </Style.Triggers>
            </Style>
        </RibbonGallery.Resources>
        <RibbonGalleryCategory Header="Custom Colors" FontWeight="Bold" />
        <RibbonGallery x:Name="galCustomColors" MinWidth="130" Width="130" MaxWidth="130" ScrollViewer.VerticalScrollBarVisibility="Disabled">
            <RibbonGallery.ItemsPanel>
                <ItemsPanelTemplate>
                    <WrapPanel Orientation="Horizontal"></WrapPanel>
                </ItemsPanelTemplate>
            </RibbonGallery.ItemsPanel>
        </RibbonGallery>
        <RibbonGalleryCategory Header="Basic Colors" FontWeight="Bold" />
        <RibbonGallery x:Name="galBasicColors" MinWidth="130" Width="130" MaxWidth="130" ScrollViewer.VerticalScrollBarVisibility="Disabled">
            <RibbonGallery.ItemsPanel>
                <ItemsPanelTemplate>
                    <WrapPanel Orientation="Horizontal"></WrapPanel>
                </ItemsPanelTemplate>
            </RibbonGallery.ItemsPanel>
        </RibbonGallery>
    </RibbonGallery>
    <RibbonMenuItem x:Name="itmColor" ImageSource="images/font-color.png" Header="Pick Color..."/>
</RibbonSplitButton>

最终结果类似于下图,但需要代码来插入颜色样本。

请注意,有一个名为galAllColorSwatches的外部 Package 器RibbonGallery,并且该元素具有设置为响应特定事件的资源,当鼠标滚动到通过代码动态添加的按钮上时,还可以响应按钮单击事件。您也可以手动构造所有按钮,并且可以在RibbonGallery中添加其他类型的控件。
通过代码创建和插入按钮可以像这样在Visual Basic中完成。

' Prepares a button for the color swatch...
    Dim [YOUR_BUTTON] As New Button
    ' Works with the button...
    With [YOUR_BUTTON]
        .Name = "btnSwatch"
        .Content = [INSERT_YOUR_CONTENT_HERE]
        .Margin = New Thickness(0, 0, 0, 0)
        .Padding = New Thickness(0, 0, 0, 0)
        .ToolTip = strColor
        .Tag = strColor
    End With
    ' Adds the item to the custom colors...
    [YOUR_RIBBONGALLERY_NAME].Items.Add([YOUR_BUTTON])

但你也可以使用绑定。
如果上面的代码嵌套在For..Next或类似的循环中,它可以生成大量的通用按钮,如您提供的图像中的网格。
所有RibbonGalleryCategory元素都是外部 Package 器中RibbonGallery元素的兄弟元素。内部的RibbonGallery元素每个都包含RibbonGallery.ItemsPanelItemsPanelTemplate,这有助于定义其内容的布局。我的示例使用WrapPanel元素来实现类似网格的布局,但是您也可以在其中添加任何其他兼容的元素。
WrapPanel中内容的布局由RibbonGallery元素的最大和最小宽度设置以及动态插入的按钮的宽度设置控制,因此您需要根据您想要实现的目标自定义这些尺寸。
XAML代码的顶部和底部都有一个标准的RibbonMenuItem元素。如果你将菜单项嵌套在一起,它们应该产生带有>指示符的标准嵌套菜单。顶部项目使用动态色样,可以加载特定颜色。

5tmbdcev

5tmbdcev3#

你可以把任何你喜欢的东西放在一个带状菜单按钮里。
举例来说:

<Ribbon>
        <RibbonMenuButton Label="Button One">
            <Grid Height="100" Width="200">
                <TextBlock VerticalAlignment="Top" Text="AAAA"/>
                <TextBlock VerticalAlignment="Bottom" Text="ZZZZ"/>
            </Grid>
        </RibbonMenuButton>
    </Ribbon>

您可能希望提取并更改ribbonmenubutton模板以避免左侧差距。

yeotifhr

yeotifhr4#

对于繁荣来说,目前还不可能。看起来RibbonMenuButton使用了一个私有的弹出窗口来显示菜单内容。
来源:https://github.com/dotnet/wpf/blob/main/src/Microsoft.DotNet.Wpf/src/System.Windows.Controls.Ribbon/Microsoft/Windows/Controls/Ribbon/RibbonMenuButton.cs第1309和1335行。

相关问题