如何在WPF中支持Windows 11的“快照布局”到自定义最大化/还原按钮?

6
我有一个使用自定义最大化/还原按钮的WPF应用程序。在Windows 11中,鼠标悬停在最大化/还原按钮上不会像下面这样弹出快照布局功能:

enter image description here

有人知道如何解决此问题吗?请提供建议。

TIA!


2
我有一个使用自定义最大化/恢复按钮的WPF应用程序。个人认为,不使用自定义最大化/恢复按钮或任何自定义非客户端打印可能更好。 - Dai
1
你的自定义窗口是否正确处理 WM_NCHITTEST 消息?请参见在 Windows 11 的桌面应用中应用捕捉布局菜单 - Steeeve
@steeve 感谢你的指引。我会去看看的。 - vishal
@dai 当然,窗口可能不是本地的,但Chrome按钮的行为就像本地的一样 :-) - Bent Rasmussen
2
@Steeeve,我能问一下你为什么严格反对自定义NC区域吗?如果Windows在使用深色主题时显示黑色标题栏,我会同意,但实际上标题栏始终是白色的。即使在Windows 11中的新记事本中,微软自己也使用了自定义NC区域。没有自定义的深色标题栏,任何深色主题都会显得不协调。 - Mar
显示剩余4条评论
1个回答

0

在这里,您可以找到关于这个主题的广泛讨论。

https://github.com/dotnet/wpf/issues/4825

包括一些可运行的代码:

https://github.com/ghost1372/HandyControls/commit/41fce1df04b45ab9a7a8ebad33f3810a89a1ad13

然而,在我看来,对于可以通过按下键盘上的Win + Z键轻松显示的快照菜单来说,处理过程太多了。

这是我仅使用XAML想出的解决方案。我没有创建一个包含按钮内容的边框,而是在中心周围创建了一个路径。标志内部的区域将带出快照菜单,因为它没有设置填充,这意味着鼠标指针会击中该区域上方的WindowChrome。以下是样式和结果。你明白了。它不是完美的,但比没有好。

<Style x:Key="TitleBarMaximizeButtonStyle" TargetType="Button">
    <Setter Property="Foreground" Value="{DynamicResource WindowTextBrush}"/>
    <Setter Property="WindowChrome.IsHitTestVisibleInChrome" Value="True"/>
    <Setter Property="IsTabStop" Value="False"/>
    <Setter Property="Template">
        <Setter.Value>
            <ControlTemplate TargetType="{x:Type Button}">
                <Grid>
                    <Path x:Name="p" Width="46" Height="32" ClipToBounds="True" StrokeThickness="0" Stretch="Uniform" Data="M 0,0 45,0 45,31 0,31 Z M 18,11 28,11 28,21 18,21 Z" Fill="Transparent"/>
                    <ContentPresenter HorizontalAlignment="Center" VerticalAlignment="Center" Focusable="False"/>
                </Grid>
                <ControlTemplate.Triggers>
                    <DataTrigger Binding="{Binding IsActive, RelativeSource={RelativeSource AncestorType=Window}}" Value="False">
                        <Setter Property="Foreground" Value="{DynamicResource WindowTitleBarInactiveText}"/>
                    </DataTrigger>
                    <Trigger Property="IsMouseOver" Value="True">
                        <Setter TargetName="p" Property="Fill" Value="{DynamicResource MouseOverOverlayBackgroundBrush}"/>
                    </Trigger>
                    <Trigger Property="IsPressed" Value="True">
                        <Setter TargetName="p" Property="Fill" Value="{DynamicResource MousePressedOverlayBackgroundBrush}"/>
                    </Trigger>
                </ControlTemplate.Triggers>
            </ControlTemplate>
        </Setter.Value>
    </Setter>
</Style>

Snap menu WPF


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接